Merge "Font provider cleaning ups." into oc-dev

This commit is contained in:
Seigo Nonaka
2017-04-25 21:40:35 +00:00
committed by Android (Google) Code Review
6 changed files with 45 additions and 99 deletions

View File

@@ -350,10 +350,6 @@ package android.provider {
field public static final deprecated java.lang.String TIMESTAMP = "timestamp";
}
public static final class FontsContract.Columns implements android.provider.BaseColumns {
field public static final java.lang.String STYLE = "font_style";
}
public static final class Settings.Global extends android.provider.Settings.NameValueTable {
field public static final deprecated java.lang.String CONTACT_METADATA_SYNC = "contact_metadata_sync";
}

View File

@@ -344,10 +344,6 @@ package android.provider {
field public static final deprecated java.lang.String TIMESTAMP = "timestamp";
}
public static final class FontsContract.Columns implements android.provider.BaseColumns {
field public static final java.lang.String STYLE = "font_style";
}
public static final class Settings.Global extends android.provider.Settings.NameValueTable {
field public static final deprecated java.lang.String CONTACT_METADATA_SYNC = "contact_metadata_sync";
}

View File

@@ -350,10 +350,6 @@ package android.provider {
field public static final deprecated java.lang.String TIMESTAMP = "timestamp";
}
public static final class FontsContract.Columns implements android.provider.BaseColumns {
field public static final java.lang.String STYLE = "font_style";
}
public static final class Settings.Global extends android.provider.Settings.NameValueTable {
field public static final deprecated java.lang.String CONTACT_METADATA_SYNC = "contact_metadata_sync";
}

View File

@@ -51,7 +51,6 @@ import android.database.sqlite.SQLiteDebug;
import android.database.sqlite.SQLiteDebug.DbStats;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Typeface;
import android.hardware.display.DisplayManagerGlobal;
import android.net.ConnectivityManager;
import android.net.IConnectivityManager;
@@ -90,6 +89,7 @@ import android.provider.CalendarContract;
import android.provider.CallLog;
import android.provider.ContactsContract;
import android.provider.Downloads;
import android.provider.FontsContract;
import android.provider.Settings;
import android.security.NetworkSecurityPolicy;
import android.security.net.config.NetworkSecurityConfigProvider;
@@ -5793,7 +5793,7 @@ public final class ActivityThread {
}
// Preload fonts resources
Typeface.setApplicationContext(appContext);
FontsContract.setApplicationContextForResources(appContext);
try {
final ApplicationInfo info =
getPackageManager().getApplicationInfo(

View File

@@ -104,14 +104,6 @@ public class FontsContract {
* font.
*/
public static final String VARIATION_SETTINGS = "font_variation_settings";
/**
* DO NOT USE THIS COLUMN.
* This column is kept for preventing demo apps.
* TODO: Remove once nobody uses this column.
* @hide
* @removed
*/
public static final String STYLE = "font_style";
/**
* Constant used to request data from a font provider. The cursor returned from the query
* should have this column populated with the int weight for the resulting font. This value
@@ -159,38 +151,24 @@ public class FontsContract {
public static final int RESULT_CODE_MALFORMED_QUERY = 3;
}
/**
* Constant used to identify the List of {@link ParcelFileDescriptor} item in the Bundle
* returned to the ResultReceiver in getFont.
* @hide
*/
public static final String PARCEL_FONT_RESULTS = "font_results";
// Error codes internal to the system, which can not come from a provider. To keep the number
// space open for new provider codes, these should all be negative numbers.
/** @hide */
public static final int RESULT_CODE_PROVIDER_NOT_FOUND = -1;
/** @hide */
public static final int RESULT_CODE_WRONG_CERTIFICATES = -2;
// Note -3 is used by Typeface to indicate the font failed to load.
private static final Object sLock = new Object();
@GuardedBy("sLock")
private static Handler sHandler;
@GuardedBy("sLock")
private static HandlerThread sThread;
@GuardedBy("sLock")
private static Set<String> sInQueueSet;
private static final int THREAD_RENEWAL_THRESHOLD_MS = 10000;
private final Context mContext;
private final PackageManager mPackageManager;
private final Object mLock = new Object();
@GuardedBy("mLock")
private Handler mHandler;
@GuardedBy("mLock")
private HandlerThread mThread;
@GuardedBy("mLock")
private Set<String> mInQueueSet;
private volatile static Context sContext; // set once in setApplicationContextForResources
private static final LruCache<String, Typeface> sTypefaceCache = new LruCache<>(16);
private FontsContract() {
}
/** @hide */
public FontsContract(Context context) {
mContext = context.getApplicationContext();
mPackageManager = mContext.getPackageManager();
public static void setApplicationContextForResources(Context context) {
sContext = context.getApplicationContext();
}
/**
@@ -323,24 +301,27 @@ public class FontsContract {
}
}
private static final int THREAD_RENEWAL_THRESHOLD_MS = 10000;
// We use a background thread to post the content resolving work for all requests on. This
// thread should be quit/stopped after all requests are done.
private final Runnable mReplaceDispatcherThreadRunnable = new Runnable() {
// TODO: Factor out to other class. Consider to switch MessageQueue.IdleHandler.
private static final Runnable sReplaceDispatcherThreadRunnable = new Runnable() {
@Override
public void run() {
synchronized (mLock) {
if (mThread != null) {
mThread.quitSafely();
mThread = null;
mHandler = null;
mInQueueSet = null;
synchronized (sLock) {
if (sThread != null) {
sThread.quitSafely();
sThread = null;
sHandler = null;
sInQueueSet = null;
}
}
}
};
/** @hide */
public Typeface getFontOrWarmUpCache(FontRequest request) {
public static Typeface getFontOrWarmUpCache(FontRequest request) {
final String id = request.getIdentifier();
Typeface cachedTypeface = sTypefaceCache.get(id);
if (cachedTypeface != null) {
@@ -350,25 +331,25 @@ public class FontsContract {
// Unfortunately the typeface is not available at this time, but requesting from the font
// provider takes too much time. For now, request the font data to ensure it is in the cache
// next time and return.
synchronized (mLock) {
if (mHandler == null) {
mThread = new HandlerThread("fonts", Process.THREAD_PRIORITY_BACKGROUND);
mThread.start();
mHandler = new Handler(mThread.getLooper());
mInQueueSet = new ArraySet<String>();
synchronized (sLock) {
if (sHandler == null) {
sThread = new HandlerThread("fonts", Process.THREAD_PRIORITY_BACKGROUND);
sThread.start();
sHandler = new Handler(sThread.getLooper());
sInQueueSet = new ArraySet<>();
}
if (mInQueueSet.contains(id)) {
if (sInQueueSet.contains(id)) {
return null; // Already requested.
}
mInQueueSet.add(id);
mHandler.post(() -> {
synchronized (mLock) {
mInQueueSet.remove(id);
sInQueueSet.add(id);
sHandler.post(() -> {
synchronized (sLock) {
sInQueueSet.remove(id);
}
try {
FontFamilyResult result = fetchFonts(mContext, null, request);
FontFamilyResult result = fetchFonts(sContext, null, request);
if (result.getStatusCode() == FontFamilyResult.STATUS_OK) {
Typeface typeface = buildTypeface(mContext, null, result.getFonts());
Typeface typeface = buildTypeface(sContext, null, result.getFonts());
if (typeface != null) {
sTypefaceCache.put(id, typeface);
}
@@ -377,8 +358,8 @@ public class FontsContract {
// Ignore.
}
});
mHandler.removeCallbacks(mReplaceDispatcherThreadRunnable);
mHandler.postDelayed(mReplaceDispatcherThreadRunnable, THREAD_RENEWAL_THRESHOLD_MS);
sHandler.removeCallbacks(sReplaceDispatcherThreadRunnable);
sHandler.postDelayed(sReplaceDispatcherThreadRunnable, THREAD_RENEWAL_THRESHOLD_MS);
}
return null;
}
@@ -391,12 +372,12 @@ public class FontsContract {
* Constant returned by {@link #onTypefaceRequestFailed(int)} signaling that the given
* provider was not found on the device.
*/
public static final int FAIL_REASON_PROVIDER_NOT_FOUND = RESULT_CODE_PROVIDER_NOT_FOUND;
public static final int FAIL_REASON_PROVIDER_NOT_FOUND = -1;
/**
* Constant returned by {@link #onTypefaceRequestFailed(int)} signaling that the given
* provider must be authenticated and the given certificates do not match its signature.
*/
public static final int FAIL_REASON_WRONG_CERTIFICATES = RESULT_CODE_WRONG_CERTIFICATES;
public static final int FAIL_REASON_WRONG_CERTIFICATES = -2;
/**
* Constant returned by {@link #onTypefaceRequestFailed(int)} signaling that the font
* returned by the provider was not loaded properly.
@@ -767,7 +748,7 @@ public class FontsContract {
.build();
try (Cursor cursor = context.getContentResolver().query(uri, new String[] { Columns._ID,
Columns.FILE_ID, Columns.TTC_INDEX, Columns.VARIATION_SETTINGS,
Columns.STYLE, Columns.WEIGHT, Columns.ITALIC, Columns.RESULT_CODE },
Columns.WEIGHT, Columns.ITALIC, Columns.RESULT_CODE },
"query = ?", new String[] { request.getQuery() }, null, cancellationSignal);) {
// TODO: Should we restrict the amount of fonts that can be returned?
// TODO: Write documentation explaining that all results should be from the same family.
@@ -780,7 +761,6 @@ public class FontsContract {
final int vsColumnIndex = cursor.getColumnIndex(Columns.VARIATION_SETTINGS);
final int weightColumnIndex = cursor.getColumnIndex(Columns.WEIGHT);
final int italicColumnIndex = cursor.getColumnIndex(Columns.ITALIC);
final int styleColumnIndex = cursor.getColumnIndex(Columns.STYLE);
while (cursor.moveToNext()) {
int resultCode = resultCodeColumnIndex != -1
? cursor.getInt(resultCodeColumnIndex) : Columns.RESULT_CODE_OK;
@@ -797,17 +777,11 @@ public class FontsContract {
long id = cursor.getLong(fileIdColumnIndex);
fileUri = ContentUris.withAppendedId(fileBaseUri, id);
}
// TODO: Stop using STYLE column and enforce WEIGHT/ITALIC column.
int weight;
boolean italic;
if (weightColumnIndex != -1 && italicColumnIndex != -1) {
weight = cursor.getInt(weightColumnIndex);
italic = cursor.getInt(italicColumnIndex) == 1;
} else if (styleColumnIndex != -1) {
final int style = cursor.getInt(styleColumnIndex);
weight = (style & Typeface.BOLD) != 0 ?
Typeface.Builder.BOLD_WEIGHT : Typeface.Builder.NORMAL_WEIGHT;
italic = (style & Typeface.ITALIC) != 0;
} else {
weight = Typeface.Builder.NORMAL_WEIGHT;
italic = false;

View File

@@ -27,7 +27,6 @@ import android.annotation.IntDef;
import android.annotation.IntRange;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.content.Context;
import android.content.res.AssetManager;
import android.graphics.FontListParser;
import android.graphics.fonts.FontRequest;
@@ -99,8 +98,6 @@ public class Typeface {
static Typeface[] sDefaults;
private static final LongSparseArray<SparseArray<Typeface>> sTypefaceCache =
new LongSparseArray<>(3);
@GuardedBy("sLock")
private static FontsContract sFontsContract;
/**
* Cache for Typeface objects dynamically loaded from assets. Currently max size is 16.
@@ -221,7 +218,7 @@ public class Typeface {
// default font instead (nothing we can do now).
FontRequest request = new FontRequest(providerEntry.getAuthority(),
providerEntry.getPackage(), providerEntry.getQuery(), certs);
Typeface typeface = sFontsContract.getFontOrWarmUpCache(request);
Typeface typeface = FontsContract.getFontOrWarmUpCache(request);
return typeface == null ? DEFAULT : typeface;
}
@@ -276,19 +273,6 @@ public class Typeface {
return null;
}
/**
* Set the application context so we can generate font requests from the provider. This should
* be called from ActivityThread when the application binds, as we preload fonts.
* @hide
*/
public static void setApplicationContext(Context context) {
synchronized (sLock) {
if (sFontsContract == null) {
sFontsContract = new FontsContract(context);
}
}
}
/**
* A builder class for creating new Typeface instance.
*