Merge change 26379 into eclair
* changes:
Add parameter for the restore set (device id) data is being restored from to the restore_start event
diff --git a/api/current.xml b/api/current.xml
index 15bc2fa..fa54a10 100644
--- a/api/current.xml
+++ b/api/current.xml
@@ -2825,6 +2825,28 @@
visibility="public"
>
</field>
+<field name="detailColumn"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="16843427"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
+<field name="detailSocialSummary"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="16843428"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
<field name="dial"
type="int"
transient="false"
@@ -7522,6 +7544,17 @@
visibility="public"
>
</field>
+<field name="summaryColumn"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="16843426"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
<field name="summaryOff"
type="int"
transient="false"
diff --git a/core/java/android/app/SearchDialog.java b/core/java/android/app/SearchDialog.java
index caf72af..a2c95f4 100644
--- a/core/java/android/app/SearchDialog.java
+++ b/core/java/android/app/SearchDialog.java
@@ -1144,7 +1144,7 @@
String query = mSearchAutoComplete.getText().toString();
String action = mGlobalSearchMode ? Intent.ACTION_WEB_SEARCH : Intent.ACTION_SEARCH;
Intent intent = createIntent(action, null, null, query, null,
- actionKey, actionMsg);
+ actionKey, actionMsg, null);
// Allow GlobalSearch to log and create shortcut for searches launched by
// the search button, enter key or an action key.
if (mGlobalSearchMode) {
@@ -1579,9 +1579,10 @@
String query = getColumnString(c, SearchManager.SUGGEST_COLUMN_QUERY);
String extraData = getColumnString(c, SearchManager.SUGGEST_COLUMN_INTENT_EXTRA_DATA);
+ String mode = mGlobalSearchMode ? SearchManager.MODE_GLOBAL_SEARCH_SUGGESTION : null;
return createIntent(action, dataUri, extraData, query, componentName, actionKey,
- actionMsg);
+ actionMsg, mode);
} catch (RuntimeException e ) {
int rowNum;
try { // be really paranoid now
@@ -1607,13 +1608,18 @@
* or {@link KeyEvent#KEYCODE_UNKNOWN} if none.
* @param actionMsg The message for the action key that was pressed,
* or <code>null</code> if none.
+ * @param mode The search mode, one of the acceptable values for
+ * {@link SearchManager#SEARCH_MODE}, or {@code null}.
* @return The intent.
*/
private Intent createIntent(String action, Uri data, String extraData, String query,
- String componentName, int actionKey, String actionMsg) {
+ String componentName, int actionKey, String actionMsg, String mode) {
// Now build the Intent
Intent intent = new Intent(action);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+ // We need CLEAR_TOP to avoid reusing an old task that has other activities
+ // on top of the one we want.
+ intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
if (data != null) {
intent.setData(data);
}
@@ -1634,6 +1640,9 @@
intent.putExtra(SearchManager.ACTION_KEY, actionKey);
intent.putExtra(SearchManager.ACTION_MSG, actionMsg);
}
+ if (mode != null) {
+ intent.putExtra(SearchManager.SEARCH_MODE, mode);
+ }
// Only allow 3rd-party intents from GlobalSearch
if (!mGlobalSearchMode) {
intent.setComponent(mSearchable.getSearchActivity());
diff --git a/core/java/android/app/SearchManager.java b/core/java/android/app/SearchManager.java
index 6a0285d..f0876f4 100644
--- a/core/java/android/app/SearchManager.java
+++ b/core/java/android/app/SearchManager.java
@@ -1289,6 +1289,25 @@
public final static String SOURCE = "source";
/**
+ * Intent extra data key: Use {@link android.content.Intent#getBundleExtra
+ * content.Intent.getBundleExtra(SEARCH_MODE)} to get the search mode used
+ * to launch the intent.
+ * The only current value for this is {@link #MODE_GLOBAL_SEARCH_SUGGESTION}.
+ *
+ * @hide
+ */
+ public final static String SEARCH_MODE = "search_mode";
+
+ /**
+ * Value for the {@link #SEARCH_MODE} key.
+ * This is used if the intent was launched by clicking a suggestion in global search
+ * mode (Quick Search Box).
+ *
+ * @hide
+ */
+ public static final String MODE_GLOBAL_SEARCH_SUGGESTION = "global_search_suggestion";
+
+ /**
* Intent extra data key: Use this key with Intent.ACTION_SEARCH and
* {@link android.content.Intent#getIntExtra content.Intent.getIntExtra()}
* to obtain the keycode that the user used to trigger this query. It will be zero if the
diff --git a/core/java/android/content/res/CompatibilityInfo.java b/core/java/android/content/res/CompatibilityInfo.java
index 50faf57..11c67cc 100644
--- a/core/java/android/content/res/CompatibilityInfo.java
+++ b/core/java/android/content/res/CompatibilityInfo.java
@@ -274,6 +274,25 @@
* Apply translation to the canvas that is necessary to draw the content.
*/
public void translateCanvas(Canvas canvas) {
+ if (applicationScale == 1.5f) {
+ /* When we scale for compatibility, we can put our stretched
+ bitmaps and ninepatches on exacty 1/2 pixel boundaries,
+ which can give us inconsistent drawing due to imperfect
+ float precision in the graphics engine's inverse matrix.
+
+ As a work-around, we translate by a tiny amount to avoid
+ landing on exact pixel centers and boundaries, giving us
+ the slop we need to draw consistently.
+
+ This constant is meant to resolve to 1/255 after it is
+ scaled by 1.5 (applicationScale). Note, this is just a guess
+ as to what is small enough not to create its own artifacts,
+ and big enough to avoid the precision problems. Feel free
+ to experiment with smaller values as you choose.
+ */
+ final float tinyOffset = 2.0f / (3 * 255);
+ canvas.translate(tinyOffset, tinyOffset);
+ }
canvas.scale(applicationScale, applicationScale);
}
diff --git a/core/java/android/webkit/BrowserFrame.java b/core/java/android/webkit/BrowserFrame.java
index dbddb2e..e233a02 100644
--- a/core/java/android/webkit/BrowserFrame.java
+++ b/core/java/android/webkit/BrowserFrame.java
@@ -605,8 +605,8 @@
}
// Called by JNI when an apple-touch-icon attribute was found.
- private void didReceiveTouchIconUrl(String url) {
- mCallbackProxy.onReceivedTouchIconUrl(url);
+ private void didReceiveTouchIconUrl(String url, boolean precomposed) {
+ mCallbackProxy.onReceivedTouchIconUrl(url, precomposed);
}
/**
@@ -707,6 +707,10 @@
return value.string.toString();
}
+ private float density() {
+ return mContext.getResources().getDisplayMetrics().density;
+ }
+
//==========================================================================
// native functions
//==========================================================================
diff --git a/core/java/android/webkit/CallbackProxy.java b/core/java/android/webkit/CallbackProxy.java
index b051675..1ec769b 100644
--- a/core/java/android/webkit/CallbackProxy.java
+++ b/core/java/android/webkit/CallbackProxy.java
@@ -249,7 +249,7 @@
case RECEIVED_TOUCH_ICON_URL:
if (mWebChromeClient != null) {
mWebChromeClient.onReceivedTouchIconUrl(mWebView,
- (String) msg.obj);
+ (String) msg.obj, msg.arg1 == 1);
}
break;
@@ -1065,19 +1065,22 @@
sendMessage(obtainMessage(RECEIVED_ICON, icon));
}
- /* package */ void onReceivedTouchIconUrl(String url) {
+ /* package */ void onReceivedTouchIconUrl(String url, boolean precomposed) {
// We should have a current item but we do not want to crash so check
// for null.
WebHistoryItem i = mBackForwardList.getCurrentItem();
if (i != null) {
- i.setTouchIconUrl(url);
+ if (precomposed || i.getTouchIconUrl() != null) {
+ i.setTouchIconUrl(url);
+ }
}
// Do an unsynchronized quick check to avoid posting if no callback has
// been set.
if (mWebChromeClient == null) {
return;
}
- sendMessage(obtainMessage(RECEIVED_TOUCH_ICON_URL, url));
+ sendMessage(obtainMessage(RECEIVED_TOUCH_ICON_URL,
+ precomposed ? 1 : 0, 0, url));
}
public void onReceivedTitle(String title) {
diff --git a/core/java/android/webkit/GeolocationPermissions.java b/core/java/android/webkit/GeolocationPermissions.java
index e985ccc..c0cac01 100755
--- a/core/java/android/webkit/GeolocationPermissions.java
+++ b/core/java/android/webkit/GeolocationPermissions.java
@@ -19,10 +19,9 @@
import android.os.Handler;
import android.os.Message;
import android.util.Log;
-import java.util.concurrent.locks.Condition;
-import java.util.concurrent.locks.Lock;
-import java.util.concurrent.locks.ReentrantLock;
+import java.util.HashMap;
import java.util.HashSet;
+import java.util.Map;
import java.util.Set;
@@ -47,15 +46,13 @@
private static GeolocationPermissions sInstance;
private Handler mHandler;
+ private Handler mUIHandler;
// Members used to transfer the origins and permissions between threads.
private Set<String> mOrigins;
private boolean mAllowed;
private Set<String> mOriginsToClear;
private Set<String> mOriginsToAllow;
- private static Lock mLock = new ReentrantLock();
- private static boolean mUpdated;
- private static Condition mUpdatedCondition = mLock.newCondition();
// Message ids
static final int GET_ORIGINS = 0;
@@ -64,6 +61,15 @@
static final int ALLOW = 3;
static final int CLEAR_ALL = 4;
+ // Message ids on the UI thread
+ static final int RETURN_ORIGINS = 0;
+ static final int RETURN_ALLOWED = 1;
+
+ private static final String ORIGINS = "origins";
+ private static final String ORIGIN = "origin";
+ private static final String CALLBACK = "callback";
+ private static final String ALLOWED = "allowed";
+
/**
* Gets the singleton instance of the class.
*/
@@ -75,22 +81,62 @@
}
/**
+ * Creates the UI message handler. Must be called on the UI thread.
+ */
+ public void createUIHandler() {
+ if (mUIHandler == null) {
+ mUIHandler = new Handler() {
+ @Override
+ public void handleMessage(Message msg) {
+ // Runs on the UI thread.
+ switch (msg.what) {
+ case RETURN_ORIGINS: {
+ Map values = (Map) msg.obj;
+ Set origins = (Set) values.get(ORIGINS);
+ ValueCallback<Set> callback = (ValueCallback<Set>) values.get(CALLBACK);
+ callback.onReceiveValue(origins);
+ } break;
+ case RETURN_ALLOWED: {
+ Map values = (Map) msg.obj;
+ Boolean allowed = (Boolean) values.get(ALLOWED);
+ ValueCallback<Boolean> callback = (ValueCallback<Boolean>) values.get(CALLBACK);
+ callback.onReceiveValue(allowed);
+ } break;
+ }
+ }
+ };
+ }
+ }
+
+ /**
* Creates the message handler. Must be called on the WebKit thread.
*/
public void createHandler() {
- mLock.lock();
if (mHandler == null) {
mHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
// Runs on the WebKit thread.
switch (msg.what) {
- case GET_ORIGINS:
+ case GET_ORIGINS: {
getOriginsImpl();
- break;
- case GET_ALLOWED:
- getAllowedImpl((String) msg.obj);
- break;
+ ValueCallback callback = (ValueCallback) msg.obj;
+ Set origins = new HashSet(mOrigins);
+ Map values = new HashMap<String, Object>();
+ values.put(CALLBACK, callback);
+ values.put(ORIGINS, origins);
+ postUIMessage(Message.obtain(null, RETURN_ORIGINS, values));
+ } break;
+ case GET_ALLOWED: {
+ Map values = (Map) msg.obj;
+ String origin = (String) values.get(ORIGIN);
+ ValueCallback callback = (ValueCallback) values.get(CALLBACK);
+ getAllowedImpl(origin);
+ Map retValues = new HashMap<String, Object>();
+ retValues.put(CALLBACK, callback);
+ retValues.put(ALLOWED, new Boolean(mAllowed));
+ postUIMessage(Message.obtain(null, RETURN_ALLOWED, retValues));
+ } break;
case CLEAR:
nativeClear((String) msg.obj);
break;
@@ -115,7 +161,6 @@
}
}
}
- mLock.unlock();
}
/**
@@ -127,29 +172,31 @@
}
/**
+ * Utility function to send a message to the handler on the UI thread
+ */
+ private void postUIMessage(Message msg) {
+ if (mUIHandler != null) {
+ mUIHandler.sendMessage(msg);
+ }
+ }
+
+ /**
* Gets the set of origins for which Geolocation permissions are stored.
* Note that we represent the origins as strings. These are created using
* WebCore::SecurityOrigin::toString(). As long as all 'HTML 5 modules'
* (Database, Geolocation etc) do so, it's safe to match up origins for the
* purposes of displaying UI.
*/
- public Set getOrigins() {
- // Called on the UI thread.
- Set origins = null;
- mLock.lock();
- try {
- mUpdated = false;
- postMessage(Message.obtain(null, GET_ORIGINS));
- while (!mUpdated) {
- mUpdatedCondition.await();
+ public void getOrigins(ValueCallback<Set> callback) {
+ if (callback != null) {
+ if (WebViewCore.THREAD_NAME.equals(Thread.currentThread().getName())) {
+ getOriginsImpl();
+ Set origins = new HashSet(mOrigins);
+ callback.onReceiveValue(origins);
+ } else {
+ postMessage(Message.obtain(null, GET_ORIGINS, callback));
}
- origins = mOrigins;
- } catch (InterruptedException e) {
- Log.e(TAG, "Exception while waiting for update", e);
- } finally {
- mLock.unlock();
}
- return origins;
}
/**
@@ -157,33 +204,29 @@
*/
private void getOriginsImpl() {
// Called on the WebKit thread.
- mLock.lock();
mOrigins = nativeGetOrigins();
- mUpdated = true;
- mUpdatedCondition.signal();
- mLock.unlock();
}
/**
* Gets the permission state for the specified origin.
*/
- public boolean getAllowed(String origin) {
- // Called on the UI thread.
- boolean allowed = false;
- mLock.lock();
- try {
- mUpdated = false;
- postMessage(Message.obtain(null, GET_ALLOWED, origin));
- while (!mUpdated) {
- mUpdatedCondition.await();
- }
- allowed = mAllowed;
- } catch (InterruptedException e) {
- Log.e(TAG, "Exception while waiting for update", e);
- } finally {
- mLock.unlock();
+ public void getAllowed(String origin, ValueCallback<Boolean> callback) {
+ if (callback == null) {
+ return;
}
- return allowed;
+ if (origin == null) {
+ callback.onReceiveValue(null);
+ return;
+ }
+ if (WebViewCore.THREAD_NAME.equals(Thread.currentThread().getName())) {
+ getAllowedImpl(origin);
+ callback.onReceiveValue(new Boolean(mAllowed));
+ } else {
+ Map values = new HashMap<String, Object>();
+ values.put(ORIGIN, origin);
+ values.put(CALLBACK, callback);
+ postMessage(Message.obtain(null, GET_ALLOWED, values));
+ }
}
/**
@@ -191,11 +234,7 @@
*/
private void getAllowedImpl(String origin) {
// Called on the WebKit thread.
- mLock.lock();
mAllowed = nativeGetAllowed(origin);
- mUpdated = true;
- mUpdatedCondition.signal();
- mLock.unlock();
}
/**
@@ -205,7 +244,6 @@
*/
public void clear(String origin) {
// Called on the UI thread.
- mLock.lock();
if (mHandler == null) {
if (mOriginsToClear == null) {
mOriginsToClear = new HashSet<String>();
@@ -217,7 +255,6 @@
} else {
postMessage(Message.obtain(null, CLEAR, origin));
}
- mLock.unlock();
}
/**
@@ -227,7 +264,6 @@
*/
public void allow(String origin) {
// Called on the UI thread.
- mLock.lock();
if (mHandler == null) {
if (mOriginsToAllow == null) {
mOriginsToAllow = new HashSet<String>();
@@ -239,7 +275,6 @@
} else {
postMessage(Message.obtain(null, ALLOW, origin));
}
- mLock.unlock();
}
/**
diff --git a/core/java/android/webkit/GoogleLocationSettingManager.java b/core/java/android/webkit/GoogleLocationSettingManager.java
index fe7fce6..1b6e77c 100644
--- a/core/java/android/webkit/GoogleLocationSettingManager.java
+++ b/core/java/android/webkit/GoogleLocationSettingManager.java
@@ -35,8 +35,6 @@
* @hide pending API council review
*/
class GoogleLocationSettingManager {
- // The application context.
- private Context mContext;
// The observer used to listen to the system setting.
private GoogleLocationSettingObserver mSettingObserver;
@@ -48,6 +46,8 @@
// by the browser.
private final static String LAST_READ_USE_LOCATION_FOR_SERVICES =
"lastReadUseLocationForServices";
+ // The Browser package name.
+ private static final String BROWSER_PACKAGE_NAME = "com.android.browser";
// The Google origins we consider.
private static HashSet<String> sGoogleOrigins;
static {
@@ -57,38 +57,72 @@
sGoogleOrigins.add("http://www.google.co.uk");
}
- GoogleLocationSettingManager(Context context) {
- mContext = context;
+ private static GoogleLocationSettingManager sGoogleLocationSettingManager = null;
+ private static int sRefCount = 0;
+
+ static GoogleLocationSettingManager getInstance() {
+ if (sGoogleLocationSettingManager == null) {
+ sGoogleLocationSettingManager = new GoogleLocationSettingManager();
+ }
+ return sGoogleLocationSettingManager;
}
+ private GoogleLocationSettingManager() {}
+
/**
* Starts the manager. Checks whether the setting has changed and
* installs an observer to listen for future changes.
*/
- public void start() {
- maybeApplySetting();
-
+ public void start(Context context) {
+ // Are we running in the browser?
+ if (context == null || !BROWSER_PACKAGE_NAME.equals(context.getPackageName())) {
+ return;
+ }
+ // Increase the refCount
+ sRefCount++;
+ // Are we already registered?
+ if (mSettingObserver != null) {
+ return;
+ }
+ // Read and apply the settings if needed.
+ maybeApplySetting(context);
+ // Register to receive notifications when the system settings change.
mSettingObserver = new GoogleLocationSettingObserver();
- mSettingObserver.observe();
+ mSettingObserver.observe(context);
}
/**
+ * Stops the manager.
+ */
+ public void stop() {
+ // Are we already registered?
+ if (mSettingObserver == null) {
+ return;
+ }
+ if (--sRefCount == 0) {
+ mSettingObserver.doNotObserve();
+ mSettingObserver = null;
+ }
+ }
+ /**
* Checks to see if the system setting has changed and if so,
* updates the Geolocation permissions accordingly.
+ * @param the Application context
*/
- private void maybeApplySetting() {
- int setting = getSystemSetting();
- if (settingChanged(setting)) {
+ private void maybeApplySetting(Context context) {
+ int setting = getSystemSetting(context);
+ if (settingChanged(setting, context)) {
applySetting(setting);
}
}
/**
* Gets the current system setting for 'Use location for Google services'.
+ * @param the Application context
* @return The system setting.
*/
- private int getSystemSetting() {
- return Settings.Secure.getInt(mContext.getContentResolver(),
+ private int getSystemSetting(Context context) {
+ return Settings.Secure.getInt(context.getContentResolver(),
Settings.Secure.USE_LOCATION_FOR_SERVICES,
sSystemSettingFalse);
}
@@ -97,12 +131,13 @@
* Determines whether the supplied setting has changed from the last
* value read by the browser.
* @param setting The setting.
+ * @param the Application context
* @return Whether the setting has changed from the last value read
* by the browser.
*/
- private boolean settingChanged(int setting) {
+ private boolean settingChanged(int setting, Context context) {
SharedPreferences preferences =
- PreferenceManager.getDefaultSharedPreferences(mContext);
+ PreferenceManager.getDefaultSharedPreferences(context);
// Default to false. If the system setting is false the first time it is ever read by the
// browser, there's nothing to do.
int lastReadSetting = sSystemSettingFalse;
@@ -137,20 +172,35 @@
* This class implements an observer to listen for changes to the
* system setting.
*/
- class GoogleLocationSettingObserver extends ContentObserver {
+ private class GoogleLocationSettingObserver extends ContentObserver {
+ private Context mContext;
+
GoogleLocationSettingObserver() {
super(new Handler());
}
- void observe() {
- ContentResolver resolver = mContext.getContentResolver();
+ void observe(Context context) {
+ if (mContext != null) {
+ return;
+ }
+ ContentResolver resolver = context.getContentResolver();
resolver.registerContentObserver(Settings.Secure.getUriFor(
Settings.Secure.USE_LOCATION_FOR_SERVICES), false, this);
+ mContext = context;
+ }
+
+ void doNotObserve() {
+ if (mContext == null) {
+ return;
+ }
+ ContentResolver resolver = mContext.getContentResolver();
+ resolver.unregisterContentObserver(this);
+ mContext = null;
}
@Override
public void onChange(boolean selfChange) {
- maybeApplySetting();
+ maybeApplySetting(mContext);
}
}
}
diff --git a/core/java/android/webkit/ValueCallback.java b/core/java/android/webkit/ValueCallback.java
new file mode 100644
index 0000000..d8c5cdc
--- /dev/null
+++ b/core/java/android/webkit/ValueCallback.java
@@ -0,0 +1,29 @@
+/*
+ * Copyright (C) 2009 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.webkit;
+
+/**
+ * A callback interface used to returns values asynchronously
+ *
+ * @hide pending council approval
+ */
+public interface ValueCallback<T> {
+ /**
+ * Invoked when we have the result
+ */
+ public void onReceiveValue(T value);
+};
diff --git a/core/java/android/webkit/WebChromeClient.java b/core/java/android/webkit/WebChromeClient.java
index 0e08514..1ae1d85 100644
--- a/core/java/android/webkit/WebChromeClient.java
+++ b/core/java/android/webkit/WebChromeClient.java
@@ -48,9 +48,11 @@
* Notify the host application of the url for an apple-touch-icon.
* @param view The WebView that initiated the callback.
* @param url The icon url.
+ * @param precomposed True if the url is for a precomposed touch icon.
* @hide pending council approval
*/
- public void onReceivedTouchIconUrl(WebView view, String url) {}
+ public void onReceivedTouchIconUrl(WebView view, String url,
+ boolean precomposed) {}
/**
* A callback interface used by the host application to notify
diff --git a/core/java/android/webkit/WebSettings.java b/core/java/android/webkit/WebSettings.java
index 3c43fd15..0cfcb95 100644
--- a/core/java/android/webkit/WebSettings.java
+++ b/core/java/android/webkit/WebSettings.java
@@ -190,12 +190,8 @@
private boolean mAllowFileAccess = true;
private boolean mLoadWithOverviewMode = false;
- // Manages interaction of the system setting 'Location & security - Share
- // with Google' and the browser.
- static GoogleLocationSettingManager sGoogleLocationSettingManager;
-
// private WebSettings, not accessible by the host activity
- private int mDoubleTapToastCount = 3;
+ static private int mDoubleTapToastCount = 3;
private static final String PREF_FILE = "WebViewSettings";
private static final String DOUBLE_TAP_TOAST_COUNT = "double_tap_toast_count";
@@ -1353,17 +1349,28 @@
if (DebugFlags.WEB_SETTINGS) {
junit.framework.Assert.assertTrue(frame.mNativeFrame != 0);
}
- sGoogleLocationSettingManager = new GoogleLocationSettingManager(mContext);
- sGoogleLocationSettingManager.start();
+
+ GoogleLocationSettingManager.getInstance().start(mContext);
+
SharedPreferences sp = mContext.getSharedPreferences(PREF_FILE,
Context.MODE_PRIVATE);
- mDoubleTapToastCount = sp.getInt(DOUBLE_TAP_TOAST_COUNT,
- mDoubleTapToastCount);
+ if (mDoubleTapToastCount > 0) {
+ mDoubleTapToastCount = sp.getInt(DOUBLE_TAP_TOAST_COUNT,
+ mDoubleTapToastCount);
+ }
nativeSync(frame.mNativeFrame);
mSyncPending = false;
mEventHandler.createHandler();
}
+ /**
+ * Let the Settings object know that our owner is being destroyed.
+ */
+ /*package*/
+ synchronized void onDestroyed() {
+ GoogleLocationSettingManager.getInstance().stop();
+ }
+
private int pin(int size) {
// FIXME: 72 is just an arbitrary max text size value.
if (size < 1) {
diff --git a/core/java/android/webkit/WebStorage.java b/core/java/android/webkit/WebStorage.java
index ae560fb..0022248 100644
--- a/core/java/android/webkit/WebStorage.java
+++ b/core/java/android/webkit/WebStorage.java
@@ -20,9 +20,8 @@
import android.os.Message;
import android.util.Log;
-import java.util.concurrent.locks.Condition;
-import java.util.concurrent.locks.Lock;
-import java.util.concurrent.locks.ReentrantLock;
+import java.util.Collection;
+import java.util.Map;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
@@ -51,28 +50,41 @@
// Global instance of a WebStorage
private static WebStorage sWebStorage;
- // We keep the origins, quotas and usages as member values
- // that we protect via a lock and update in syncValues().
- // This is needed to transfer this data across threads.
- private static Lock mLock = new ReentrantLock();
- private static Condition mUpdateCondition = mLock.newCondition();
- private static boolean mUpdateAvailable;
-
// Message ids
static final int UPDATE = 0;
static final int SET_QUOTA_ORIGIN = 1;
static final int DELETE_ORIGIN = 2;
static final int DELETE_ALL = 3;
+ static final int GET_ORIGINS = 4;
+ static final int GET_USAGE_ORIGIN = 5;
+ static final int GET_QUOTA_ORIGIN = 6;
- private Set <String> mOrigins;
- private HashMap <String, Long> mQuotas = new HashMap<String, Long>();
- private HashMap <String, Long> mUsages = new HashMap<String, Long>();
+ // Message ids on the UI thread
+ static final int RETURN_ORIGINS = 0;
+ static final int RETURN_USAGE_ORIGIN = 1;
+ static final int RETURN_QUOTA_ORIGIN = 2;
+
+ private static final String ORIGINS = "origins";
+ private static final String ORIGIN = "origin";
+ private static final String CALLBACK = "callback";
+ private static final String USAGE = "usage";
+ private static final String QUOTA = "quota";
+
+ private Map <String, Origin> mOrigins;
private Handler mHandler = null;
+ private Handler mUIHandler = null;
- private static class Origin {
+ static class Origin {
String mOrigin = null;
long mQuota = 0;
+ long mUsage = 0;
+
+ public Origin(String origin, long quota, long usage) {
+ mOrigin = origin;
+ mQuota = quota;
+ mUsage = usage;
+ }
public Origin(String origin, long quota) {
mOrigin = origin;
@@ -90,11 +102,49 @@
public long getQuota() {
return mQuota;
}
+
+ public long getUsage() {
+ return mUsage;
+ }
}
/**
* @hide
- * Message handler
+ * Message handler, UI side
+ */
+ public void createUIHandler() {
+ if (mUIHandler == null) {
+ mUIHandler = new Handler() {
+ @Override
+ public void handleMessage(Message msg) {
+ switch (msg.what) {
+ case RETURN_ORIGINS: {
+ Map values = (Map) msg.obj;
+ Map origins = (Map) values.get(ORIGINS);
+ ValueCallback<Map> callback = (ValueCallback<Map>) values.get(CALLBACK);
+ callback.onReceiveValue(origins);
+ } break;
+
+ case RETURN_USAGE_ORIGIN: {
+ Map values = (Map) msg.obj;
+ ValueCallback<Long> callback = (ValueCallback<Long>) values.get(CALLBACK);
+ callback.onReceiveValue((Long)values.get(USAGE));
+ } break;
+
+ case RETURN_QUOTA_ORIGIN: {
+ Map values = (Map) msg.obj;
+ ValueCallback<Long> callback = (ValueCallback<Long>) values.get(CALLBACK);
+ callback.onReceiveValue((Long)values.get(QUOTA));
+ } break;
+ }
+ }
+ };
+ }
+ }
+
+ /**
+ * @hide
+ * Message handler, webcore side
*/
public void createHandler() {
if (mHandler == null) {
@@ -117,6 +167,46 @@
nativeDeleteAllData();
break;
+ case GET_ORIGINS: {
+ syncValues();
+ ValueCallback callback = (ValueCallback) msg.obj;
+ Map origins = new HashMap(mOrigins);
+ Map values = new HashMap<String, Object>();
+ values.put(CALLBACK, callback);
+ values.put(ORIGINS, origins);
+ postUIMessage(Message.obtain(null, RETURN_ORIGINS, values));
+ } break;
+
+ case GET_USAGE_ORIGIN: {
+ syncValues();
+ Map values = (Map) msg.obj;
+ String origin = (String) values.get(ORIGIN);
+ ValueCallback callback = (ValueCallback) values.get(CALLBACK);
+ Origin website = mOrigins.get(origin);
+ Map retValues = new HashMap<String, Object>();
+ retValues.put(CALLBACK, callback);
+ if (website != null) {
+ long usage = website.getUsage();
+ retValues.put(USAGE, new Long(usage));
+ }
+ postUIMessage(Message.obtain(null, RETURN_USAGE_ORIGIN, retValues));
+ } break;
+
+ case GET_QUOTA_ORIGIN: {
+ syncValues();
+ Map values = (Map) msg.obj;
+ String origin = (String) values.get(ORIGIN);
+ ValueCallback callback = (ValueCallback) values.get(CALLBACK);
+ Origin website = mOrigins.get(origin);
+ Map retValues = new HashMap<String, Object>();
+ retValues.put(CALLBACK, callback);
+ if (website != null) {
+ long quota = website.getQuota();
+ retValues.put(QUOTA, new Long(quota));
+ }
+ postUIMessage(Message.obtain(null, RETURN_QUOTA_ORIGIN, retValues));
+ } break;
+
case UPDATE:
syncValues();
break;
@@ -126,82 +216,91 @@
}
}
+ /*
+ * When calling getOrigins(), getUsageForOrigin() and getQuotaForOrigin(),
+ * we need to get the values from webcore, but we cannot block while doing so
+ * as we used to do, as this could result in a full deadlock (other webcore
+ * messages received while we are still blocked here, see http://b/2127737).
+ *
+ * We have to do everything asynchronously, by providing a callback function.
+ * We post a message on the webcore thread (mHandler) that will get the result
+ * from webcore, and we post it back on the UI thread (using mUIHandler).
+ * We can then use the callback function to return the value.
+ */
+
/**
* @hide
* Returns a list of origins having a database
*/
- public Set getOrigins() {
- Set ret = null;
- mLock.lock();
- try {
- mUpdateAvailable = false;
- update();
- while (!mUpdateAvailable) {
- mUpdateCondition.await();
+ public void getOrigins(ValueCallback<Map> callback) {
+ if (callback != null) {
+ if (WebViewCore.THREAD_NAME.equals(Thread.currentThread().getName())) {
+ syncValues();
+ callback.onReceiveValue(mOrigins);
+ } else {
+ postMessage(Message.obtain(null, GET_ORIGINS, callback));
}
- ret = mOrigins;
- } catch (InterruptedException e) {
- Log.e(TAG, "Exception while waiting on the updated origins", e);
- } finally {
- mLock.unlock();
}
- return ret;
+ }
+
+ /**
+ * Returns a list of origins having a database
+ * should only be called from WebViewCore.
+ */
+ Collection<Origin> getOriginsSync() {
+ if (WebViewCore.THREAD_NAME.equals(Thread.currentThread().getName())) {
+ update();
+ return mOrigins.values();
+ }
+ return null;
}
/**
* @hide
* Returns the use for a given origin
*/
- public long getUsageForOrigin(String origin) {
- long ret = 0;
+ public void getUsageForOrigin(String origin, ValueCallback<Long> callback) {
+ if (callback == null) {
+ return;
+ }
if (origin == null) {
- return ret;
+ callback.onReceiveValue(null);
+ return;
}
- mLock.lock();
- try {
- mUpdateAvailable = false;
- update();
- while (!mUpdateAvailable) {
- mUpdateCondition.await();
- }
- Long usage = mUsages.get(origin);
- if (usage != null) {
- ret = usage.longValue();
- }
- } catch (InterruptedException e) {
- Log.e(TAG, "Exception while waiting on the updated origins", e);
- } finally {
- mLock.unlock();
+ if (WebViewCore.THREAD_NAME.equals(Thread.currentThread().getName())) {
+ syncValues();
+ Origin website = mOrigins.get(origin);
+ callback.onReceiveValue(new Long(website.getUsage()));
+ } else {
+ HashMap values = new HashMap<String, Object>();
+ values.put(ORIGIN, origin);
+ values.put(CALLBACK, callback);
+ postMessage(Message.obtain(null, GET_USAGE_ORIGIN, values));
}
- return ret;
}
/**
* @hide
* Returns the quota for a given origin
*/
- public long getQuotaForOrigin(String origin) {
- long ret = 0;
+ public void getQuotaForOrigin(String origin, ValueCallback<Long> callback) {
+ if (callback == null) {
+ return;
+ }
if (origin == null) {
- return ret;
+ callback.onReceiveValue(null);
+ return;
}
- mLock.lock();
- try {
- mUpdateAvailable = false;
- update();
- while (!mUpdateAvailable) {
- mUpdateCondition.await();
- }
- Long quota = mQuotas.get(origin);
- if (quota != null) {
- ret = quota.longValue();
- }
- } catch (InterruptedException e) {
- Log.e(TAG, "Exception while waiting on the updated origins", e);
- } finally {
- mLock.unlock();
+ if (WebViewCore.THREAD_NAME.equals(Thread.currentThread().getName())) {
+ syncValues();
+ Origin website = mOrigins.get(origin);
+ callback.onReceiveValue(new Long(website.getUsage()));
+ } else {
+ HashMap values = new HashMap<String, Object>();
+ values.put(ORIGIN, origin);
+ values.put(CALLBACK, callback);
+ postMessage(Message.obtain(null, GET_QUOTA_ORIGIN, values));
}
- return ret;
}
/**
@@ -256,6 +355,15 @@
}
/**
+ * Utility function to send a message to the handler on the UI thread
+ */
+ private void postUIMessage(Message msg) {
+ if (mUIHandler != null) {
+ mUIHandler.sendMessage(msg);
+ }
+ }
+
+ /**
* @hide
* Get the global instance of WebStorage.
* @return A single instance of WebStorage.
@@ -284,21 +392,14 @@
* set the local values with the current ones
*/
private void syncValues() {
- mLock.lock();
- Set tmp = nativeGetOrigins();
- mOrigins = new HashSet<String>();
- mQuotas.clear();
- mUsages.clear();
- Iterator<String> iter = tmp.iterator();
- while (iter.hasNext()) {
- String origin = iter.next();
- mOrigins.add(origin);
- mQuotas.put(origin, new Long(nativeGetQuotaForOrigin(origin)));
- mUsages.put(origin, new Long(nativeGetUsageForOrigin(origin)));
+ Set<String> tmp = nativeGetOrigins();
+ mOrigins = new HashMap<String, Origin>();
+ for (String origin : tmp) {
+ Origin website = new Origin(origin,
+ nativeGetUsageForOrigin(origin),
+ nativeGetQuotaForOrigin(origin));
+ mOrigins.put(origin, website);
}
- mUpdateAvailable = true;
- mUpdateCondition.signal();
- mLock.unlock();
}
// Native functions
diff --git a/core/java/android/webkit/WebView.java b/core/java/android/webkit/WebView.java
index eaf6c05..51c5e1f 100644
--- a/core/java/android/webkit/WebView.java
+++ b/core/java/android/webkit/WebView.java
@@ -3772,10 +3772,10 @@
mZoomButtonsController.setVisible(true);
int count = settings.getDoubleTapToastCount();
if (mInZoomOverview && count > 0) {
- settings.setDoubleTapToastCount(count--);
+ settings.setDoubleTapToastCount(--count);
Toast.makeText(mContext,
com.android.internal.R.string.double_tap_toast,
- Toast.LENGTH_SHORT).show();
+ Toast.LENGTH_LONG).show();
}
}
}
@@ -4868,7 +4868,7 @@
/ draw.mMinPrefWidth;
mMinZoomScaleFixed = false;
} else {
- mMinZoomScale = mDefaultScale;
+ mMinZoomScale = restoreState.mDefaultScale;
mMinZoomScaleFixed = true;
}
} else {
@@ -4891,7 +4891,7 @@
&& settings.getLoadWithOverviewMode()) {
if (restoreState.mViewScale == 0
|| (restoreState.mMobileSite
- && mMinZoomScale < mDefaultScale)) {
+ && mMinZoomScale < restoreState.mDefaultScale)) {
mInZoomOverview = true;
}
}
diff --git a/core/java/android/webkit/WebViewCore.java b/core/java/android/webkit/WebViewCore.java
index d4142bb..52bf508 100644
--- a/core/java/android/webkit/WebViewCore.java
+++ b/core/java/android/webkit/WebViewCore.java
@@ -37,6 +37,7 @@
import android.view.View;
import java.util.ArrayList;
+import java.util.Collection;
import java.util.Map;
import java.util.Set;
@@ -100,6 +101,15 @@
private boolean mViewportUserScalable = true;
+ /*
+ * range is from 70 to 400.
+ * 0 is a special value means device-dpi. The default scale factor will be
+ * always 100.
+ * -1 means undefined. The default scale factor will be
+ * WebView.DEFAULT_SCALE_PERCENT.
+ */
+ private int mViewportDensityDpi = -1;
+
private int mRestoredScale = 0;
private int mRestoredScreenWidthScale = 0;
private int mRestoredX = 0;
@@ -153,8 +163,10 @@
// The WebIconDatabase needs to be initialized within the UI thread so
// just request the instance here.
WebIconDatabase.getInstance();
- // Create the WebStorage singleton
- WebStorage.getInstance();
+ // Create the WebStorage singleton and the UI handler
+ WebStorage.getInstance().createUIHandler();
+ // Create the UI handler for GeolocationPermissions
+ GeolocationPermissions.getInstance().createUIHandler();
// Send a message to initialize the WebViewCore.
Message init = sWebCoreHandler.obtainMessage(
WebCoreThread.INITIALIZE, this);
@@ -841,6 +853,7 @@
synchronized (WebViewCore.this) {
mBrowserFrame.destroy();
mBrowserFrame = null;
+ mSettings.onDestroyed();
mNativeClass = 0;
}
break;
@@ -1510,13 +1523,14 @@
// callbacks. Computes the sum of database quota for all origins.
private long getUsedQuota() {
WebStorage webStorage = WebStorage.getInstance();
- Set<String> origins = webStorage.getOrigins();
+ Collection<WebStorage.Origin> origins = webStorage.getOriginsSync();
+
if (origins == null) {
return 0;
}
long usedQuota = 0;
- for (String origin : origins) {
- usedQuota += webStorage.getQuotaForOrigin(origin);
+ for (WebStorage.Origin website : origins) {
+ usedQuota += website.getQuota();
}
return usedQuota;
}
@@ -1539,6 +1553,7 @@
float mMaxScale;
float mViewScale;
float mTextWrapScale;
+ float mDefaultScale;
int mScrollX;
int mScrollY;
boolean mMobileSite;
@@ -1842,47 +1857,48 @@
// set the viewport settings from WebKit
setViewportSettingsFromNative();
- // adjust the default scale to match the density
- if (WebView.DEFAULT_SCALE_PERCENT != 100) {
- float adjust = (float) WebView.DEFAULT_SCALE_PERCENT / 100.0f;
- if (mViewportInitialScale > 0) {
- mViewportInitialScale *= adjust;
+ // adjust the default scale to match the densityDpi
+ float adjust = 1.0f;
+ if (mViewportDensityDpi == -1) {
+ if (WebView.DEFAULT_SCALE_PERCENT != 100) {
+ adjust = WebView.DEFAULT_SCALE_PERCENT / 100.0f;
}
- if (mViewportMinimumScale > 0) {
- mViewportMinimumScale *= adjust;
- }
- if (mViewportMaximumScale > 0) {
- mViewportMaximumScale *= adjust;
- }
+ } else if (mViewportDensityDpi > 0) {
+ adjust = (float) mContext.getResources().getDisplayMetrics().densityDpi
+ / mViewportDensityDpi;
+ }
+ int defaultScale = (int) (adjust * 100);
+
+ if (mViewportInitialScale > 0) {
+ mViewportInitialScale *= adjust;
+ }
+ if (mViewportMinimumScale > 0) {
+ mViewportMinimumScale *= adjust;
+ }
+ if (mViewportMaximumScale > 0) {
+ mViewportMaximumScale *= adjust;
}
// infer the values if they are not defined.
if (mViewportWidth == 0) {
if (mViewportInitialScale == 0) {
- mViewportInitialScale = WebView.DEFAULT_SCALE_PERCENT;
+ mViewportInitialScale = defaultScale;
}
}
if (mViewportUserScalable == false) {
- mViewportInitialScale = WebView.DEFAULT_SCALE_PERCENT;
- mViewportMinimumScale = WebView.DEFAULT_SCALE_PERCENT;
- mViewportMaximumScale = WebView.DEFAULT_SCALE_PERCENT;
+ mViewportInitialScale = defaultScale;
+ mViewportMinimumScale = defaultScale;
+ mViewportMaximumScale = defaultScale;
}
- if (mViewportMinimumScale > mViewportInitialScale) {
- if (mViewportInitialScale == 0) {
- mViewportInitialScale = mViewportMinimumScale;
- } else {
- mViewportMinimumScale = mViewportInitialScale;
- }
+ if (mViewportMinimumScale > mViewportInitialScale
+ && mViewportInitialScale != 0) {
+ mViewportMinimumScale = mViewportInitialScale;
}
- if (mViewportMaximumScale > 0) {
- if (mViewportMaximumScale < mViewportInitialScale) {
- mViewportMaximumScale = mViewportInitialScale;
- } else if (mViewportInitialScale == 0) {
- mViewportInitialScale = mViewportMaximumScale;
- }
+ if (mViewportMaximumScale > 0
+ && mViewportMaximumScale < mViewportInitialScale) {
+ mViewportMaximumScale = mViewportInitialScale;
}
- if (mViewportWidth < 0
- && mViewportInitialScale == WebView.DEFAULT_SCALE_PERCENT) {
+ if (mViewportWidth < 0 && mViewportInitialScale == defaultScale) {
mViewportWidth = 0;
}
@@ -1899,7 +1915,7 @@
// we call WebView method from WebCore thread. But not perfect
// reference is better than no reference.
webViewWidth = mWebView.getViewWidth();
- viewportWidth = webViewWidth * 100 / WebView.DEFAULT_SCALE_PERCENT;
+ viewportWidth = (int) (webViewWidth / adjust);
if (viewportWidth == 0) {
Log.w(LOGTAG, "Can't get the viewWidth after the first layout");
}
@@ -1909,6 +1925,7 @@
mRestoreState = new RestoreState();
mRestoreState.mMinScale = mViewportMinimumScale / 100.0f;
mRestoreState.mMaxScale = mViewportMaximumScale / 100.0f;
+ mRestoreState.mDefaultScale = adjust;
mRestoreState.mScrollX = mRestoredX;
mRestoreState.mScrollY = mRestoredY;
mRestoreState.mMobileSite = (0 == mViewportWidth);
@@ -1930,8 +1947,7 @@
mRestoreState.mViewScale = mRestoreState.mTextWrapScale =
(float) webViewWidth / mViewportWidth;
} else {
- mRestoreState.mTextWrapScale =
- WebView.DEFAULT_SCALE_PERCENT / 100.0f;
+ mRestoreState.mTextWrapScale = adjust;
// 0 will trigger WebView to turn on zoom overview mode
mRestoreState.mViewScale = 0;
}
diff --git a/core/java/android/widget/ScrollView.java b/core/java/android/widget/ScrollView.java
index 703cd8e2..31c7814 100644
--- a/core/java/android/widget/ScrollView.java
+++ b/core/java/android/widget/ScrollView.java
@@ -743,7 +743,7 @@
final int maxJump = getMaxScrollAmount();
- if (nextFocused != null && isWithinDeltaOfScreen(nextFocused, maxJump)) {
+ if (nextFocused != null && isWithinDeltaOfScreen(nextFocused, maxJump, getHeight())) {
nextFocused.getDrawingRect(mTempRect);
offsetDescendantRectToMyCoords(nextFocused, mTempRect);
int scrollDelta = computeScrollDeltaToGetChildRectOnScreen(mTempRect);
@@ -792,19 +792,19 @@
* screen.
*/
private boolean isOffScreen(View descendant) {
- return !isWithinDeltaOfScreen(descendant, 0);
+ return !isWithinDeltaOfScreen(descendant, 0, getHeight());
}
/**
* @return whether the descendant of this scroll view is within delta
* pixels of being on the screen.
*/
- private boolean isWithinDeltaOfScreen(View descendant, int delta) {
+ private boolean isWithinDeltaOfScreen(View descendant, int delta, int height) {
descendant.getDrawingRect(mTempRect);
offsetDescendantRectToMyCoords(descendant, mTempRect);
return (mTempRect.bottom + delta) >= getScrollY()
- && (mTempRect.top - delta) <= (getScrollY() + getHeight());
+ && (mTempRect.top - delta) <= (getScrollY() + height);
}
/**
@@ -1124,9 +1124,10 @@
if (null == currentFocused || this == currentFocused)
return;
- final int maxJump = mBottom - mTop;
-
- if (isWithinDeltaOfScreen(currentFocused, maxJump)) {
+ // If the currently-focused view was visible on the screen when the
+ // screen was at the old height, then scroll the screen to make that
+ // view visible with the new screen height.
+ if (isWithinDeltaOfScreen(currentFocused, 0, oldh)) {
currentFocused.getDrawingRect(mTempRect);
offsetDescendantRectToMyCoords(currentFocused, mTempRect);
int scrollDelta = computeScrollDeltaToGetChildRectOnScreen(mTempRect);
diff --git a/core/java/android/widget/TextView.java b/core/java/android/widget/TextView.java
index 2e3364b..3c61c1c 100644
--- a/core/java/android/widget/TextView.java
+++ b/core/java/android/widget/TextView.java
@@ -2874,26 +2874,23 @@
* @attr ref android.R.styleable#TextView_inputType
*/
public void setInputType(int type) {
+ final boolean wasPassword = isPasswordInputType(mInputType);
+ final boolean wasVisiblePassword = isVisiblePasswordInputType(mInputType);
setInputType(type, false);
- final int variation = type&(EditorInfo.TYPE_MASK_CLASS
- |EditorInfo.TYPE_MASK_VARIATION);
- final boolean isPassword = variation
- == (EditorInfo.TYPE_CLASS_TEXT
- |EditorInfo.TYPE_TEXT_VARIATION_PASSWORD);
+ final boolean isPassword = isPasswordInputType(type);
+ final boolean isVisiblePassword = isVisiblePasswordInputType(type);
boolean forceUpdate = false;
if (isPassword) {
setTransformationMethod(PasswordTransformationMethod.getInstance());
setTypefaceByIndex(MONOSPACE, 0);
- } else if (mTransformation == PasswordTransformationMethod.getInstance()) {
- // We need to clean up if we were previously in password mode.
- if (variation != (EditorInfo.TYPE_CLASS_TEXT
- |EditorInfo.TYPE_TEXT_VARIATION_VISIBLE_PASSWORD)) {
- setTypefaceByIndex(-1, -1);
- }
- forceUpdate = true;
- } else if (variation == (EditorInfo.TYPE_CLASS_TEXT
- |EditorInfo.TYPE_TEXT_VARIATION_VISIBLE_PASSWORD)) {
+ } else if (isVisiblePassword) {
setTypefaceByIndex(MONOSPACE, 0);
+ } else if (wasPassword || wasVisiblePassword) {
+ // not in password mode, clean up typeface and transformation
+ setTypefaceByIndex(-1, -1);
+ if (mTransformation == PasswordTransformationMethod.getInstance()) {
+ forceUpdate = true;
+ }
}
boolean multiLine = (type&(EditorInfo.TYPE_MASK_CLASS
@@ -2913,6 +2910,22 @@
if (imm != null) imm.restartInput(this);
}
+ private boolean isPasswordInputType(int inputType) {
+ final int variation = inputType & (EditorInfo.TYPE_MASK_CLASS
+ | EditorInfo.TYPE_MASK_VARIATION);
+ return variation
+ == (EditorInfo.TYPE_CLASS_TEXT
+ | EditorInfo.TYPE_TEXT_VARIATION_PASSWORD);
+ }
+
+ private boolean isVisiblePasswordInputType(int inputType) {
+ final int variation = inputType & (EditorInfo.TYPE_MASK_CLASS
+ | EditorInfo.TYPE_MASK_VARIATION);
+ return variation
+ == (EditorInfo.TYPE_CLASS_TEXT
+ | EditorInfo.TYPE_TEXT_VARIATION_VISIBLE_PASSWORD);
+ }
+
/**
* Directly change the content type integer of the text view, without
* modifying any other state.
diff --git a/core/java/com/android/internal/widget/ContactHeaderWidget.java b/core/java/com/android/internal/widget/ContactHeaderWidget.java
index 4a9c077..35d637d 100644
--- a/core/java/com/android/internal/widget/ContactHeaderWidget.java
+++ b/core/java/com/android/internal/widget/ContactHeaderWidget.java
@@ -63,6 +63,7 @@
private static final String TAG = "ContactHeaderWidget";
private TextView mDisplayNameView;
+ private View mAggregateBadge;
private TextView mPhoneticNameView;
private CheckBox mStarredView;
private FasttrackBadgeWidget mPhotoView;
@@ -159,6 +160,8 @@
mDisplayNameView = (TextView) findViewById(R.id.name);
mDisplayNameView.setOnLongClickListener(this);
+ mAggregateBadge = findViewById(R.id.aggregate_badge);
+ mAggregateBadge.setVisibility(View.GONE);
mPhoneticNameView = (TextView) findViewById(R.id.phonetic_name);
@@ -284,6 +287,13 @@
}
/**
+ * Turn on/off showing of the aggregate bage element.
+ */
+ public void showAggregateBadge(boolean showBagde) {
+ mAggregateBadge.setVisibility(showBagde ? View.VISIBLE : View.GONE);
+ }
+
+ /**
* Turn on/off showing of the star element.
*/
public void showStar(boolean showStar) {
diff --git a/core/res/res/drawable-hdpi/ic_aggregated.png b/core/res/res/drawable-hdpi/ic_aggregated.png
new file mode 100644
index 0000000..7ca15b1
--- /dev/null
+++ b/core/res/res/drawable-hdpi/ic_aggregated.png
Binary files differ
diff --git a/core/res/res/drawable-mdpi/ic_aggregated.png b/core/res/res/drawable-mdpi/ic_aggregated.png
new file mode 100644
index 0000000..7c2e2b0
--- /dev/null
+++ b/core/res/res/drawable-mdpi/ic_aggregated.png
Binary files differ
diff --git a/core/res/res/layout/contact_header.xml b/core/res/res/layout/contact_header.xml
index e800dfa..d19bb04 100644
--- a/core/res/res/layout/contact_header.xml
+++ b/core/res/res/layout/contact_header.xml
@@ -38,8 +38,24 @@
android:layout_marginTop="5dip"
android:orientation="vertical">
- <!-- "Name" field is locale-specific. -->
- <include layout="@layout/contact_header_name"/>
+ <LinearLayout
+ android:layout_width="fill_parent"
+ android:layout_height="wrap_content"
+ android:orientation="horizontal">
+
+ <ImageView
+ android:id="@+id/aggregate_badge"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:paddingRight="3dip"
+ android:paddingTop="3dip"
+ android:src="@drawable/ic_aggregated"
+ />
+
+ <!-- "Name" field is locale-specific. -->
+ <include layout="@layout/contact_header_name"/>
+
+ </LinearLayout>
<TextView android:id="@+id/status"
android:layout_width="fill_parent"
diff --git a/core/res/res/values/attrs.xml b/core/res/res/values/attrs.xml
index e7b379a..c3b7a2c9 100644
--- a/core/res/res/values/attrs.xml
+++ b/core/res/res/values/attrs.xml
@@ -3486,13 +3486,29 @@
<!-- Contacts meta-data attributes -->
<!-- =============================== -->
+ <!-- TODO: remove this deprecated styleable -->
<declare-styleable name="Icon">
<attr name="icon" />
<attr name="mimeType" />
</declare-styleable>
+ <!-- TODO: remove this deprecated styleable -->
<declare-styleable name="IconDefault">
<attr name="icon" />
</declare-styleable>
+ <!-- Maps a specific contact data MIME-type to styling information -->
+ <declare-styleable name="ContactsDataKind">
+ <!-- Mime-type handled by this mapping -->
+ <attr name="mimeType" />
+ <!-- Icon used to represent data of this kind -->
+ <attr name="icon" />
+ <!-- Column in data table that summarizes this data -->
+ <attr name="summaryColumn" format="string" />
+ <!-- Column in data table that contains details for this data -->
+ <attr name="detailColumn" format="string" />
+ <!-- Flag indicating that detail should be built from SocialProvider -->
+ <attr name="detailSocialSummary" format="boolean" />
+ </declare-styleable>
+
</resources>
diff --git a/core/res/res/values/public.xml b/core/res/res/values/public.xml
index 89581e6..b08a58a 100644
--- a/core/res/res/values/public.xml
+++ b/core/res/res/values/public.xml
@@ -1166,6 +1166,9 @@
<public type="attr" name="accountPreferences" />
<public type="attr" name="textAppearanceSearchResultSubtitle" />
<public type="attr" name="textAppearanceSearchResultTitle" />
+ <public type="attr" name="summaryColumn" />
+ <public type="attr" name="detailColumn" />
+ <public type="attr" name="detailSocialSummary" />
<public type="style" name="Theme.Wallpaper" />
<public type="style" name="Theme.Wallpaper.NoTitleBar" />
diff --git a/graphics/java/android/renderscript/Allocation.java b/graphics/java/android/renderscript/Allocation.java
index 30c81ab..957f2dd 100644
--- a/graphics/java/android/renderscript/Allocation.java
+++ b/graphics/java/android/renderscript/Allocation.java
@@ -48,50 +48,49 @@
}
public void data(int[] d) {
- int size;
- if(mType != null && mType.mElement != null) {
- size = mType.mElement.mSize;
- for(int ct=0; ct < mType.mValues.length; ct++) {
- if(mType.mValues[ct] != 0) {
- size *= mType.mValues[ct];
- }
- }
- if((d.length * 4) < size) {
- throw new IllegalArgumentException("Array too small for allocation type.");
- }
- Log.e("rs", "Alloc data size=" + size);
- mRS.nAllocationData(mID, d, size);
- return;
- }
- mRS.nAllocationData(mID, d, d.length * 4);
+ subData1D(0, mType.getElementCount(), d);
+ }
+ public void data(short[] d) {
+ subData1D(0, mType.getElementCount(), d);
+ }
+ public void data(byte[] d) {
+ subData1D(0, mType.getElementCount(), d);
+ }
+ public void data(float[] d) {
+ subData1D(0, mType.getElementCount(), d);
}
- public void data(float[] d) {
- int size;
- if(mType != null && mType.mElement != null) {
- size = mType.mElement.mSize;
- for(int ct=0; ct < mType.mValues.length; ct++) {
- if(mType.mValues[ct] != 0) {
- size *= mType.mValues[ct];
- }
- }
- if((d.length * 4) < size) {
- throw new IllegalArgumentException("Array too small for allocation type.");
- }
- Log.e("rs", "Alloc data size=" + size);
- mRS.nAllocationData(mID, d, size);
- return;
+ private void data1DChecks(int off, int count, int len, int dataSize) {
+ if((off < 0) || (count < 1) || ((off + count) > mType.getElementCount())) {
+ throw new IllegalArgumentException("Offset or Count out of bounds.");
}
- mRS.nAllocationData(mID, d, d.length * 4);
+ if((len) < dataSize) {
+ throw new IllegalArgumentException("Array too small for allocation type.");
+ }
}
public void subData1D(int off, int count, int[] d) {
- mRS.nAllocationSubData1D(mID, off, count, d, count * 4);
+ int dataSize = mType.mElement.getSizeBytes() * count;
+ data1DChecks(off, count, d.length * 4, dataSize);
+ mRS.nAllocationSubData1D(mID, off, count, d, dataSize);
+ }
+ public void subData1D(int off, int count, short[] d) {
+ int dataSize = mType.mElement.getSizeBytes() * count;
+ data1DChecks(off, count, d.length * 2, dataSize);
+ mRS.nAllocationSubData1D(mID, off, count, d, dataSize);
+ }
+ public void subData1D(int off, int count, byte[] d) {
+ int dataSize = mType.mElement.getSizeBytes() * count;
+ data1DChecks(off, count, d.length, dataSize);
+ mRS.nAllocationSubData1D(mID, off, count, d, dataSize);
+ }
+ public void subData1D(int off, int count, float[] d) {
+ int dataSize = mType.mElement.getSizeBytes() * count;
+ data1DChecks(off, count, d.length * 4, dataSize);
+ mRS.nAllocationSubData1D(mID, off, count, d, dataSize);
}
- public void subData1D(int off, int count, float[] d) {
- mRS.nAllocationSubData1D(mID, off, count, d, d.length * 4);
- }
+
public void subData2D(int xoff, int yoff, int w, int h, int[] d) {
mRS.nAllocationSubData2D(mID, xoff, yoff, w, h, d, d.length * 4);
@@ -213,11 +212,15 @@
static public Allocation createSized(RenderScript rs, Element e, int count)
throws IllegalArgumentException {
- int id = rs.nAllocationCreateSized(e.mID, count);
+ Type.Builder b = new Type.Builder(rs, e);
+ b.add(Dimension.X, count);
+ Type t = b.create();
+
+ int id = rs.nAllocationCreateTyped(t.mID);
if(id == 0) {
throw new IllegalStateException("Bad element.");
}
- return new Allocation(id, rs, null);
+ return new Allocation(id, rs, t);
}
static public Allocation createFromBitmap(RenderScript rs, Bitmap b, Element dstFmt, boolean genMips)
diff --git a/graphics/java/android/renderscript/Element.java b/graphics/java/android/renderscript/Element.java
index 04c36fd..0a586c4 100644
--- a/graphics/java/android/renderscript/Element.java
+++ b/graphics/java/android/renderscript/Element.java
@@ -26,18 +26,40 @@
int mSize;
Entry[] mEntries;
+ int getSizeBytes() {
+ return mSize;
+ }
+ int getComponentCount() {
+ return mEntries.length;
+ }
+ Element.DataType getComponentDataType(int num) {
+ return mEntries[num].mType;
+ }
+ Element.DataKind getComponentDataKind(int num) {
+ return mEntries[num].mKind;
+ }
+ boolean getComponentIsNormalized(int num) {
+ return mEntries[num].mIsNormalized;
+ }
+ int getComponentBits(int num) {
+ return mEntries[num].mBits;
+ }
+ String getComponentName(int num) {
+ return mEntries[num].mName;
+ }
+
static class Entry {
- Element mElement;
+ //Element mElement;
Element.DataType mType;
Element.DataKind mKind;
boolean mIsNormalized;
int mBits;
String mName;
- Entry(Element e, int bits) {
- mElement = e;
- int mBits = bits;
- }
+ //Entry(Element e, int bits) {
+ //mElement = e;
+ //int mBits = bits;
+ //}
Entry(DataType dt, DataKind dk, boolean isNorm, int bits, String name) {
mType = dt;
@@ -266,14 +288,11 @@
int bits = 0;
for (int ct=0; ct < e.mEntries.length; ct++) {
Entry en = e.mEntries[ct];
- if(en.mElement != null) {
+ //if(en.mElement != null) {
//rs.nElementAdd(en.mElement.mID);
- } else {
- int norm = 0;
- if (en.mIsNormalized) {
- norm = 1;
- }
- rs.nElementAdd(en.mKind.mID, en.mType.mID, norm, en.mBits, en.mName);
+ //} else
+ {
+ rs.nElementAdd(en.mKind.mID, en.mType.mID, en.mIsNormalized, en.mBits, en.mName);
bits += en.mBits;
}
}
@@ -308,11 +327,11 @@
mEntryCount++;
}
- public Builder add(Element e) throws IllegalArgumentException {
- Entry en = new Entry(e, e.mSize * 8);
- addEntry(en);
- return this;
- }
+ //public Builder add(Element e) throws IllegalArgumentException {
+ //Entry en = new Entry(e, e.mSize * 8);
+ //addEntry(en);
+ //return this;
+ //}
public Builder add(Element.DataType dt, Element.DataKind dk, boolean isNormalized, int bits, String name) {
Entry en = new Entry(dt, dk, isNormalized, bits, name);
diff --git a/graphics/java/android/renderscript/RenderScript.java b/graphics/java/android/renderscript/RenderScript.java
index d35c5e3..5831d13 100644
--- a/graphics/java/android/renderscript/RenderScript.java
+++ b/graphics/java/android/renderscript/RenderScript.java
@@ -80,7 +80,7 @@
native int nFileOpen(byte[] name);
native void nElementBegin();
- native void nElementAdd(int kind, int type, int norm, int bits, String s);
+ native void nElementAdd(int kind, int type, boolean norm, int bits, String s);
native int nElementCreate();
native void nTypeBegin(int elementID);
@@ -90,17 +90,19 @@
native void nTypeSetupFields(Type t, int[] types, int[] bits, Field[] IDs);
native int nAllocationCreateTyped(int type);
- native int nAllocationCreateSized(int elem, int count);
+ //native int nAllocationCreateSized(int elem, int count);
native int nAllocationCreateFromBitmap(int dstFmt, boolean genMips, Bitmap bmp);
native int nAllocationCreateFromBitmapBoxed(int dstFmt, boolean genMips, Bitmap bmp);
native int nAllocationCreateFromAssetStream(int dstFmt, boolean genMips, int assetStream);
native void nAllocationUploadToTexture(int alloc, int baseMioLevel);
native void nAllocationUploadToBufferObject(int alloc);
- native void nAllocationData(int id, int[] d, int sizeBytes);
- native void nAllocationData(int id, float[] d, int sizeBytes);
+
native void nAllocationSubData1D(int id, int off, int count, int[] d, int sizeBytes);
+ native void nAllocationSubData1D(int id, int off, int count, short[] d, int sizeBytes);
+ native void nAllocationSubData1D(int id, int off, int count, byte[] d, int sizeBytes);
native void nAllocationSubData1D(int id, int off, int count, float[] d, int sizeBytes);
+
native void nAllocationSubData2D(int id, int xoff, int yoff, int w, int h, int[] d, int sizeBytes);
native void nAllocationSubData2D(int id, int xoff, int yoff, int w, int h, float[] d, int sizeBytes);
native void nAllocationRead(int id, int[] d);
diff --git a/graphics/java/android/renderscript/SimpleMesh.java b/graphics/java/android/renderscript/SimpleMesh.java
index 5d87654..dc74c61 100644
--- a/graphics/java/android/renderscript/SimpleMesh.java
+++ b/graphics/java/android/renderscript/SimpleMesh.java
@@ -162,7 +162,6 @@
}
public SimpleMesh create() {
- Log.e("rs", "SimpleMesh create");
SimpleMesh sm = internalCreate(mRS, this);
sm.mVertexTypes = new Type[mVertexTypeCount];
for(int ct=0; ct < mVertexTypeCount; ct++) {
@@ -177,7 +176,7 @@
public static class TriangleMeshBuilder {
float mVtxData[];
int mVtxCount;
- int mIndexData[];
+ short mIndexData[];
int mIndexCount;
RenderScript mRS;
Element mElement;
@@ -191,7 +190,7 @@
mVtxCount = 0;
mIndexCount = 0;
mVtxData = new float[128];
- mIndexData = new int[128];
+ mIndexData = new short[128];
mVtxSize = vtxSize;
mNorm = norm;
mTex = tex;
@@ -268,13 +267,13 @@
public void addTriangle(int idx1, int idx2, int idx3) {
if((mIndexCount + 3) >= mIndexData.length) {
- int t[] = new int[mIndexData.length * 2];
+ short t[] = new short[mIndexData.length * 2];
System.arraycopy(mIndexData, 0, t, 0, mIndexData.length);
mIndexData = t;
}
- mIndexData[mIndexCount++] = idx1;
- mIndexData[mIndexCount++] = idx2;
- mIndexData[mIndexCount++] = idx3;
+ mIndexData[mIndexCount++] = (short)idx1;
+ mIndexData[mIndexCount++] = (short)idx2;
+ mIndexData[mIndexCount++] = (short)idx3;
}
public SimpleMesh create() {
@@ -309,10 +308,6 @@
vertexAlloc.data(mVtxData);
vertexAlloc.uploadToBufferObject();
- // This is safe because length is a pow2
- for(int ct=0; ct < (mIndexCount+1); ct += 2) {
- mIndexData[ct >> 1] = mIndexData[ct] | (mIndexData[ct+1] << 16);
- }
indexAlloc.data(mIndexData);
indexAlloc.uploadToBufferObject();
diff --git a/graphics/java/android/renderscript/Type.java b/graphics/java/android/renderscript/Type.java
index b6b7adf..df60990 100644
--- a/graphics/java/android/renderscript/Type.java
+++ b/graphics/java/android/renderscript/Type.java
@@ -23,13 +23,74 @@
*
**/
public class Type extends BaseObj {
- Dimension[] mDimensions;
- int[] mValues;
+ int mDimX;
+ int mDimY;
+ int mDimZ;
+ boolean mDimLOD;
+ boolean mDimFaces;
+ int mElementCount;
Element mElement;
+
private int mNativeCache;
Class mJavaClass;
+ public int getX() {
+ return mDimX;
+ }
+ public int getY() {
+ return mDimY;
+ }
+ public int getZ() {
+ return mDimZ;
+ }
+ public boolean getLOD() {
+ return mDimLOD;
+ }
+ public boolean getFaces() {
+ return mDimFaces;
+ }
+ public int getElementCount() {
+ return mElementCount;
+ }
+
+ void calcElementCount() {
+ boolean hasLod = getLOD();
+ int x = getX();
+ int y = getY();
+ int z = getZ();
+ int faces = 1;
+ if(getFaces()) {
+ faces = 6;
+ }
+ if(x == 0) {
+ x = 1;
+ }
+ if(y == 0) {
+ y = 1;
+ }
+ if(z == 0) {
+ z = 1;
+ }
+
+ int count = x * y * z * faces;
+ if(hasLod && (x > 1) && (y > 1) && (z > 1)) {
+ if(x > 1) {
+ x >>= 1;
+ }
+ if(y > 1) {
+ y >>= 1;
+ }
+ if(z > 1) {
+ z >>= 1;
+ }
+
+ count += x * y * z * faces;
+ }
+ mElementCount = count;
+ }
+
+
Type(int id, RenderScript rs) {
super(rs);
mID = id;
@@ -131,12 +192,25 @@
public Type create() {
Type t = internalCreate(mRS, this);
t.mElement = mElement;
- t.mDimensions = new Dimension[mEntryCount];
- t.mValues = new int[mEntryCount];
+
for(int ct=0; ct < mEntryCount; ct++) {
- t.mDimensions[ct] = mEntries[ct].mDim;
- t.mValues[ct] = mEntries[ct].mValue;
+ if(mEntries[ct].mDim == Dimension.X) {
+ t.mDimX = mEntries[ct].mValue;
+ }
+ if(mEntries[ct].mDim == Dimension.Y) {
+ t.mDimY = mEntries[ct].mValue;
+ }
+ if(mEntries[ct].mDim == Dimension.Z) {
+ t.mDimZ = mEntries[ct].mValue;
+ }
+ if(mEntries[ct].mDim == Dimension.LOD) {
+ t.mDimLOD = mEntries[ct].mValue != 0;
+ }
+ if(mEntries[ct].mDim == Dimension.FACE) {
+ t.mDimFaces = mEntries[ct].mValue != 0;
+ }
}
+ t.calcElementCount();
return t;
}
}
diff --git a/graphics/jni/android_renderscript_RenderScript.cpp b/graphics/jni/android_renderscript_RenderScript.cpp
index c7b5448..56a4223 100644
--- a/graphics/jni/android_renderscript_RenderScript.cpp
+++ b/graphics/jni/android_renderscript_RenderScript.cpp
@@ -181,7 +181,7 @@
static void
-nElementAdd(JNIEnv *_env, jobject _this, jint kind, jint type, jint norm, jint bits, jstring name)
+nElementAdd(JNIEnv *_env, jobject _this, jint kind, jint type, jboolean norm, jint bits, jstring name)
{
RsContext con = (RsContext)(_env->GetIntField(_this, gContextId));
const char* n = NULL;
@@ -359,14 +359,6 @@
return (jint) rsAllocationCreateTyped(con, (RsElement)e);
}
-static jint
-nAllocationCreateSized(JNIEnv *_env, jobject _this, jint e, jint count)
-{
- RsContext con = (RsContext)(_env->GetIntField(_this, gContextId));
- LOG_API("nAllocationCreateSized, con(%p), e(%p), count(%i)", con, (RsElement)e, count);
- return (jint) rsAllocationCreateSized(con, (RsElement)e, count);
-}
-
static void
nAllocationUploadToTexture(JNIEnv *_env, jobject _this, jint a, jint mip)
{
@@ -476,44 +468,44 @@
static void
-nAllocationData_i(JNIEnv *_env, jobject _this, jint alloc, jintArray data, int sizeBytes)
-{
- RsContext con = (RsContext)(_env->GetIntField(_this, gContextId));
- jint len = _env->GetArrayLength(data);
- LOG_API("nAllocationData_i, con(%p), alloc(%p), len(%i)", con, (RsAllocation)alloc, len);
- jint *ptr = _env->GetIntArrayElements(data, NULL);
- rsAllocationData(con, (RsAllocation)alloc, ptr, sizeBytes);
- _env->ReleaseIntArrayElements(data, ptr, JNI_ABORT);
-}
-
-static void
-nAllocationData_f(JNIEnv *_env, jobject _this, jint alloc, jfloatArray data, int sizeBytes)
-{
- RsContext con = (RsContext)(_env->GetIntField(_this, gContextId));
- jint len = _env->GetArrayLength(data);
- LOG_API("nAllocationData_i, con(%p), alloc(%p), len(%i)", con, (RsAllocation)alloc, len);
- jfloat *ptr = _env->GetFloatArrayElements(data, NULL);
- rsAllocationData(con, (RsAllocation)alloc, ptr, sizeBytes);
- _env->ReleaseFloatArrayElements(data, ptr, JNI_ABORT);
-}
-
-static void
nAllocationSubData1D_i(JNIEnv *_env, jobject _this, jint alloc, jint offset, jint count, jintArray data, int sizeBytes)
{
RsContext con = (RsContext)(_env->GetIntField(_this, gContextId));
jint len = _env->GetArrayLength(data);
- LOG_API("nAllocation1DSubData_i, con(%p), adapter(%p), offset(%i), count(%i), len(%i)", con, (RsAllocation)alloc, offset, count, len);
+ LOG_API("nAllocation1DSubData_i, con(%p), adapter(%p), offset(%i), count(%i), len(%i), sizeBytes(%i)", con, (RsAllocation)alloc, offset, count, len, sizeBytes);
jint *ptr = _env->GetIntArrayElements(data, NULL);
rsAllocation1DSubData(con, (RsAllocation)alloc, offset, count, ptr, sizeBytes);
_env->ReleaseIntArrayElements(data, ptr, JNI_ABORT);
}
static void
+nAllocationSubData1D_s(JNIEnv *_env, jobject _this, jint alloc, jint offset, jint count, jshortArray data, int sizeBytes)
+{
+ RsContext con = (RsContext)(_env->GetIntField(_this, gContextId));
+ jint len = _env->GetArrayLength(data);
+ LOG_API("nAllocation1DSubData_s, con(%p), adapter(%p), offset(%i), count(%i), len(%i), sizeBytes(%i)", con, (RsAllocation)alloc, offset, count, len, sizeBytes);
+ jshort *ptr = _env->GetShortArrayElements(data, NULL);
+ rsAllocation1DSubData(con, (RsAllocation)alloc, offset, count, ptr, sizeBytes);
+ _env->ReleaseShortArrayElements(data, ptr, JNI_ABORT);
+}
+
+static void
+nAllocationSubData1D_b(JNIEnv *_env, jobject _this, jint alloc, jint offset, jint count, jbyteArray data, int sizeBytes)
+{
+ RsContext con = (RsContext)(_env->GetIntField(_this, gContextId));
+ jint len = _env->GetArrayLength(data);
+ LOG_API("nAllocation1DSubData_b, con(%p), adapter(%p), offset(%i), count(%i), len(%i), sizeBytes(%i)", con, (RsAllocation)alloc, offset, count, len, sizeBytes);
+ jbyte *ptr = _env->GetByteArrayElements(data, NULL);
+ rsAllocation1DSubData(con, (RsAllocation)alloc, offset, count, ptr, sizeBytes);
+ _env->ReleaseByteArrayElements(data, ptr, JNI_ABORT);
+}
+
+static void
nAllocationSubData1D_f(JNIEnv *_env, jobject _this, jint alloc, jint offset, jint count, jfloatArray data, int sizeBytes)
{
RsContext con = (RsContext)(_env->GetIntField(_this, gContextId));
jint len = _env->GetArrayLength(data);
- LOG_API("nAllocation1DSubData_f, con(%p), adapter(%p), offset(%i), count(%i), len(%i)", con, (RsAllocation)alloc, offset, count, len);
+ LOG_API("nAllocation1DSubData_f, con(%p), adapter(%p), offset(%i), count(%i), len(%i), sizeBytes(%i)", con, (RsAllocation)alloc, offset, count, len, sizeBytes);
jfloat *ptr = _env->GetFloatArrayElements(data, NULL);
rsAllocation1DSubData(con, (RsAllocation)alloc, offset, count, ptr, sizeBytes);
_env->ReleaseFloatArrayElements(data, ptr, JNI_ABORT);
@@ -1323,7 +1315,7 @@
{"nFileOpen", "([B)I", (void*)nFileOpen },
{"nElementBegin", "()V", (void*)nElementBegin },
-{"nElementAdd", "(IIIILjava/lang/String;)V", (void*)nElementAdd },
+{"nElementAdd", "(IIZILjava/lang/String;)V", (void*)nElementAdd },
{"nElementCreate", "()I", (void*)nElementCreate },
{"nTypeBegin", "(I)V", (void*)nTypeBegin },
@@ -1333,15 +1325,14 @@
{"nTypeSetupFields", "(Landroid/renderscript/Type;[I[I[Ljava/lang/reflect/Field;)V", (void*)nTypeSetupFields },
{"nAllocationCreateTyped", "(I)I", (void*)nAllocationCreateTyped },
-{"nAllocationCreateSized", "(II)I", (void*)nAllocationCreateSized },
{"nAllocationCreateFromBitmap", "(IZLandroid/graphics/Bitmap;)I", (void*)nAllocationCreateFromBitmap },
{"nAllocationCreateFromBitmapBoxed","(IZLandroid/graphics/Bitmap;)I", (void*)nAllocationCreateFromBitmapBoxed },
{"nAllocationCreateFromAssetStream","(IZI)I", (void*)nAllocationCreateFromAssetStream },
{"nAllocationUploadToTexture", "(II)V", (void*)nAllocationUploadToTexture },
{"nAllocationUploadToBufferObject","(I)V", (void*)nAllocationUploadToBufferObject },
-{"nAllocationData", "(I[II)V", (void*)nAllocationData_i },
-{"nAllocationData", "(I[FI)V", (void*)nAllocationData_f },
{"nAllocationSubData1D", "(III[II)V", (void*)nAllocationSubData1D_i },
+{"nAllocationSubData1D", "(III[SI)V", (void*)nAllocationSubData1D_s },
+{"nAllocationSubData1D", "(III[BI)V", (void*)nAllocationSubData1D_b },
{"nAllocationSubData1D", "(III[FI)V", (void*)nAllocationSubData1D_f },
{"nAllocationSubData2D", "(IIIII[II)V", (void*)nAllocationSubData2D_i },
{"nAllocationSubData2D", "(IIIII[FI)V", (void*)nAllocationSubData2D_f },
diff --git a/libs/audioflinger/AudioFlinger.cpp b/libs/audioflinger/AudioFlinger.cpp
index e534447..6500791 100644
--- a/libs/audioflinger/AudioFlinger.cpp
+++ b/libs/audioflinger/AudioFlinger.cpp
@@ -1227,44 +1227,46 @@
enabledTracks = prepareTracks_l(activeTracks, &tracksToRemove);
}
-
- // output audio to hardware
- if (mSuspended) {
- usleep(kMaxBufferRecoveryInUsecs);
+ if (LIKELY(enabledTracks)) {
+ // mix buffers...
+ mAudioMixer->process(curBuf);
+ sleepTime = 0;
+ standbyTime = systemTime() + kStandbyTimeInNsecs;
} else {
- if (LIKELY(enabledTracks)) {
- // mix buffers...
- mAudioMixer->process(curBuf);
+ sleepTime += kBufferRecoveryInUsecs;
+ if (sleepTime > kMaxBufferRecoveryInUsecs) {
+ sleepTime = kMaxBufferRecoveryInUsecs;
+ }
+ // There was nothing to mix this round, which means all
+ // active tracks were late. Sleep a little bit to give
+ // them another chance. If we're too late, write 0s to audio
+ // hardware to avoid underrun.
+ if (mBytesWritten != 0 && sleepTime >= kMaxBufferRecoveryInUsecs) {
+ memset (curBuf, 0, mixBufferSize);
sleepTime = 0;
- standbyTime = systemTime() + kStandbyTimeInNsecs;
- } else {
- sleepTime += kBufferRecoveryInUsecs;
- // There was nothing to mix this round, which means all
- // active tracks were late. Sleep a little bit to give
- // them another chance. If we're too late, write 0s to audio
- // hardware to avoid underrun.
- if (mBytesWritten == 0 || sleepTime < kMaxBufferRecoveryInUsecs) {
- usleep(kBufferRecoveryInUsecs);
- } else {
- memset (curBuf, 0, mixBufferSize);
- sleepTime = 0;
- }
}
- // sleepTime == 0 means PCM data were written to mMixBuffer[]
- if (sleepTime == 0) {
- mLastWriteTime = systemTime();
- mInWrite = true;
- int bytesWritten = (int)mOutput->write(curBuf, mixBufferSize);
- if (bytesWritten > 0) mBytesWritten += bytesWritten;
- mNumWrites++;
- mInWrite = false;
- mStandby = false;
- nsecs_t delta = systemTime() - mLastWriteTime;
- if (delta > maxPeriod) {
- LOGW("write blocked for %llu msecs", ns2ms(delta));
- mNumDelayedWrites++;
- }
+ }
+
+ if (mSuspended) {
+ sleepTime = kMaxBufferRecoveryInUsecs;
+ }
+ // sleepTime == 0 means we must write to audio hardware
+ if (sleepTime == 0) {
+ mLastWriteTime = systemTime();
+ mInWrite = true;
+ LOGV("mOutput->write() thread %p frames %d", this, mFrameCount);
+ int bytesWritten = (int)mOutput->write(curBuf, mixBufferSize);
+ if (bytesWritten > 0) mBytesWritten += bytesWritten;
+ mNumWrites++;
+ mInWrite = false;
+ mStandby = false;
+ nsecs_t delta = systemTime() - mLastWriteTime;
+ if (delta > maxPeriod) {
+ LOGW("write blocked for %llu msecs, thread %p", ns2ms(delta), this);
+ mNumDelayedWrites++;
}
+ } else {
+ usleep(sleepTime);
}
// finally let go of all our tracks, without the lock held
@@ -1718,50 +1720,55 @@
}
}
- // output audio to hardware
- if (mSuspended) {
- usleep(kMaxBufferRecoveryInUsecs);
+ if (activeTrack != 0) {
+ AudioBufferProvider::Buffer buffer;
+ size_t frameCount = mFrameCount;
+ curBuf = (int8_t *)mMixBuffer;
+ // output audio to hardware
+ while(frameCount) {
+ buffer.frameCount = frameCount;
+ activeTrack->getNextBuffer(&buffer);
+ if (UNLIKELY(buffer.raw == 0)) {
+ memset(curBuf, 0, frameCount * mFrameSize);
+ break;
+ }
+ memcpy(curBuf, buffer.raw, buffer.frameCount * mFrameSize);
+ frameCount -= buffer.frameCount;
+ curBuf += buffer.frameCount * mFrameSize;
+ activeTrack->releaseBuffer(&buffer);
+ }
+ sleepTime = 0;
+ standbyTime = systemTime() + kStandbyTimeInNsecs;
} else {
- if (activeTrack != 0) {
- AudioBufferProvider::Buffer buffer;
- size_t frameCount = mFrameCount;
- curBuf = (int8_t *)mMixBuffer;
- // output audio to hardware
- while(frameCount) {
- buffer.frameCount = frameCount;
- activeTrack->getNextBuffer(&buffer);
- if (UNLIKELY(buffer.raw == 0)) {
- memset(curBuf, 0, frameCount * mFrameSize);
- break;
- }
- memcpy(curBuf, buffer.raw, buffer.frameCount * mFrameSize);
- frameCount -= buffer.frameCount;
- curBuf += buffer.frameCount * mFrameSize;
- activeTrack->releaseBuffer(&buffer);
- }
+ sleepTime += kBufferRecoveryInUsecs;
+ if (sleepTime > kMaxBufferRecoveryInUsecs) {
+ sleepTime = kMaxBufferRecoveryInUsecs;
+ }
+ // There was nothing to mix this round, which means all
+ // active tracks were late. Sleep a little bit to give
+ // them another chance. If we're too late, write 0s to audio
+ // hardware to avoid underrun.
+ if (mBytesWritten != 0 && sleepTime >= kMaxBufferRecoveryInUsecs &&
+ AudioSystem::isLinearPCM(mFormat)) {
+ memset (mMixBuffer, 0, mFrameCount * mFrameSize);
sleepTime = 0;
- standbyTime = systemTime() + kStandbyTimeInNsecs;
- } else {
- sleepTime += kBufferRecoveryInUsecs;
- if (mBytesWritten == 0 || !AudioSystem::isLinearPCM(mFormat) ||
- sleepTime < kMaxBufferRecoveryInUsecs) {
- usleep(kBufferRecoveryInUsecs);
- } else {
- memset (mMixBuffer, 0, mFrameCount * mFrameSize);
- sleepTime = 0;
- }
}
+ }
- // sleepTime == 0 means PCM data were written to mMixBuffer[]
- if (sleepTime == 0) {
- mLastWriteTime = systemTime();
- mInWrite = true;
- int bytesWritten = (int)mOutput->write(mMixBuffer, mixBufferSize);
- if (bytesWritten) mBytesWritten += bytesWritten;
- mNumWrites++;
- mInWrite = false;
- mStandby = false;
- }
+ if (mSuspended) {
+ sleepTime = kMaxBufferRecoveryInUsecs;
+ }
+ // sleepTime == 0 means we must write to audio hardware
+ if (sleepTime == 0) {
+ mLastWriteTime = systemTime();
+ mInWrite = true;
+ int bytesWritten = (int)mOutput->write(mMixBuffer, mixBufferSize);
+ if (bytesWritten) mBytesWritten += bytesWritten;
+ mNumWrites++;
+ mInWrite = false;
+ mStandby = false;
+ } else {
+ usleep(sleepTime);
}
// finally let go of removed track, without the lock held
@@ -1913,38 +1920,40 @@
}
enabledTracks = prepareTracks_l(activeTracks, &tracksToRemove);
- }
+ }
- bool mustSleep = true;
if (LIKELY(enabledTracks)) {
// mix buffers...
mAudioMixer->process(curBuf);
- if (!mSuspended) {
- for (size_t i = 0; i < outputTracks.size(); i++) {
- outputTracks[i]->write(curBuf, mFrameCount);
- mustSleep = false;
- }
- mStandby = false;
- mBytesWritten += mixBufferSize;
- }
+ sleepTime = 0;
+ standbyTime = systemTime() + kStandbyTimeInNsecs;
} else {
- // flush remaining overflow buffers in output tracks
- for (size_t i = 0; i < outputTracks.size(); i++) {
- if (outputTracks[i]->isActive()) {
- outputTracks[i]->write(curBuf, 0);
- standbyTime = systemTime() + kStandbyTimeInNsecs;
- mustSleep = false;
- }
+ sleepTime += kBufferRecoveryInUsecs;
+ if (sleepTime > kMaxBufferRecoveryInUsecs) {
+ sleepTime = kMaxBufferRecoveryInUsecs;
+ }
+ // There was nothing to mix this round, which means all
+ // active tracks were late. Sleep a little bit to give
+ // them another chance. If we're too late, write 0s to audio
+ // hardware to avoid underrun.
+ if (mBytesWritten != 0 && sleepTime >= kMaxBufferRecoveryInUsecs) {
+ memset (curBuf, 0, mixBufferSize);
+ sleepTime = 0;
}
}
- if (mustSleep) {
-// LOGV("threadLoop() sleeping %d", sleepTime);
- usleep(sleepTime);
- if (sleepTime < kMaxBufferRecoveryInUsecs) {
- sleepTime += kBufferRecoveryInUsecs;
+
+ if (mSuspended) {
+ sleepTime = kMaxBufferRecoveryInUsecs;
+ }
+ // sleepTime == 0 means we must write to audio hardware
+ if (sleepTime == 0) {
+ for (size_t i = 0; i < outputTracks.size(); i++) {
+ outputTracks[i]->write(curBuf, mFrameCount);
}
+ mStandby = false;
+ mBytesWritten += mixBufferSize;
} else {
- sleepTime = kBufferRecoveryInUsecs;
+ usleep(sleepTime);
}
// finally let go of all our tracks, without the lock held
diff --git a/libs/rs/rsContext.cpp b/libs/rs/rsContext.cpp
index 04f6e07..3e4c9af 100644
--- a/libs/rs/rsContext.cpp
+++ b/libs/rs/rsContext.cpp
@@ -112,8 +112,8 @@
#endif
rsAssert(mRootScript->mEnviroment.mIsRoot);
- //glColor4f(1,1,1,1);
- //glEnable(GL_LIGHT0);
+ eglQuerySurface(mEGL.mDisplay, mEGL.mSurface, EGL_WIDTH, &mEGL.mWidth);
+ eglQuerySurface(mEGL.mDisplay, mEGL.mSurface, EGL_HEIGHT, &mEGL.mHeight);
glViewport(0, 0, mEGL.mWidth, mEGL.mHeight);
glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
glEnable(GL_POINT_SMOOTH);
diff --git a/media/java/android/media/MediaScanner.java b/media/java/android/media/MediaScanner.java
index 37a3bd5..3ac5df5 100644
--- a/media/java/android/media/MediaScanner.java
+++ b/media/java/android/media/MediaScanner.java
@@ -736,6 +736,28 @@
if (time != -1) {
values.put(Images.Media.DATE_TAKEN, time);
}
+
+ int orientation = exif.getAttributeInt(
+ ExifInterface.TAG_ORIENTATION, -1);
+ if (orientation != -1) {
+ // We only recognize a subset of orientation tag values.
+ int degree;
+ switch(orientation) {
+ case ExifInterface.ORIENTATION_ROTATE_90:
+ degree = 90;
+ break;
+ case ExifInterface.ORIENTATION_ROTATE_180:
+ degree = 180;
+ break;
+ case ExifInterface.ORIENTATION_ROTATE_270:
+ degree = 270;
+ break;
+ default:
+ degree = 0;
+ break;
+ }
+ values.put(Images.Media.ORIENTATION, degree);
+ }
}
}
diff --git a/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/MediaProfileReader.java b/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/MediaProfileReader.java
index 0401390..53afb1d 100644
--- a/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/MediaProfileReader.java
+++ b/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/MediaProfileReader.java
@@ -32,6 +32,29 @@
return s;
}
+ public static boolean getWMAEnable() {
+ // push all the property into one big table
+ int wmaEnable = 1;
+ wmaEnable = SystemProperties.getInt("ro.media.dec.aud.wma.enabled",
+ wmaEnable);
+ if (wmaEnable == 1) {
+ return true;
+ } else {
+ return false;
+ }
+ }
+
+ public static boolean getWMVEnable(){
+ int wmvEnable = 1;
+ wmvEnable = SystemProperties.getInt("ro.media.dec.vid.wmv.enabled",
+ wmvEnable);
+ if (wmvEnable == 1) {
+ return true;
+ } else {
+ return false;
+ }
+ }
+
public static void createVideoProfileTable() {
// push all the property into one big table
String encoderType = getVideoCodecProperty();
diff --git a/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaPlayerApiTest.java b/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaPlayerApiTest.java
index 30e2d6c..392d1d5 100644
--- a/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaPlayerApiTest.java
+++ b/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaPlayerApiTest.java
@@ -18,6 +18,7 @@
import com.android.mediaframeworktest.MediaFrameworkTest;
import com.android.mediaframeworktest.MediaNames;
+import com.android.mediaframeworktest.MediaProfileReader;
import android.content.Context;
import android.test.ActivityInstrumentationTestCase;
@@ -35,11 +36,15 @@
public class MediaPlayerApiTest extends ActivityInstrumentationTestCase<MediaFrameworkTest> {
private boolean duratoinWithinTolerence = false;
private String TAG = "MediaPlayerApiTest";
+ private boolean isWMAEnable = false;
+ private boolean isWMVEnable = false;
Context mContext;
public MediaPlayerApiTest() {
super("com.android.mediaframeworktest", MediaFrameworkTest.class);
+ isWMAEnable = MediaProfileReader.getWMAEnable();
+ isWMVEnable = MediaProfileReader.getWMVEnable();
}
protected void setUp() throws Exception {
@@ -82,9 +87,11 @@
@MediumTest
public void testWMA9GetDuration() throws Exception {
- int duration = CodecTest.getDuration(MediaNames.WMA9);
- duratoinWithinTolerence = verifyDuration(duration, MediaNames.WMA9_LENGTH);
- assertTrue("WMA9 getDuration", duratoinWithinTolerence);
+ if (isWMAEnable) {
+ int duration = CodecTest.getDuration(MediaNames.WMA9);
+ duratoinWithinTolerence = verifyDuration(duration, MediaNames.WMA9_LENGTH);
+ assertTrue("WMA9 getDuration", duratoinWithinTolerence);
+ }
}
@MediumTest
@@ -123,8 +130,10 @@
@LargeTest
public void testWMA9GetCurrentPosition() throws Exception {
- boolean currentPosition = CodecTest.getCurrentPosition(MediaNames.WMA9);
- assertTrue("WMA9 GetCurrentPosition", currentPosition);
+ if (isWMAEnable) {
+ boolean currentPosition = CodecTest.getCurrentPosition(MediaNames.WMA9);
+ assertTrue("WMA9 GetCurrentPosition", currentPosition);
+ }
}
@LargeTest
@@ -160,8 +169,10 @@
@LargeTest
public void testWMA9Pause() throws Exception {
- boolean isPaused = CodecTest.pause(MediaNames.WMA9);
- assertTrue("WMA9 Pause", isPaused);
+ if (isWMAEnable) {
+ boolean isPaused = CodecTest.pause(MediaNames.WMA9);
+ assertTrue("WMA9 Pause", isPaused);
+ }
}
@LargeTest
@@ -269,8 +280,10 @@
@LargeTest
public void testWMA9SeekTo() throws Exception {
- boolean isLoop = CodecTest.seekTo(MediaNames.WMA9);
- assertTrue("WMA9 seekTo", isLoop);
+ if (isWMAEnable) {
+ boolean isLoop = CodecTest.seekTo(MediaNames.WMA9);
+ assertTrue("WMA9 seekTo", isLoop);
+ }
}
@LargeTest
@@ -309,8 +322,10 @@
@Suppress
@LargeTest
public void testWMA9SeekToEnd() throws Exception {
- boolean isEnd = CodecTest.seekToEnd(MediaNames.WMA9);
- assertTrue("WMA9 seekToEnd", isEnd);
+ if (isWMAEnable) {
+ boolean isEnd = CodecTest.seekToEnd(MediaNames.WMA9);
+ assertTrue("WMA9 seekToEnd", isEnd);
+ }
}
@LargeTest
@@ -327,8 +342,10 @@
@LargeTest
public void testWAVSeekToEnd() throws Exception {
- boolean isEnd = CodecTest.seekToEnd(MediaNames.WAV);
- assertTrue("WAV seekToEnd", isEnd);
+ if (isWMVEnable) {
+ boolean isEnd = CodecTest.seekToEnd(MediaNames.WAV);
+ assertTrue("WAV seekToEnd", isEnd);
+ }
}
@MediumTest
@@ -385,8 +402,12 @@
@LargeTest
public void testVideoWMVSeekTo() throws Exception {
- boolean isSeek = CodecTest.videoSeekTo(MediaNames.VIDEO_WMV);
- assertTrue("WMV SeekTo", isSeek);
+ Log.v(TAG, "wmv not enable");
+ if (isWMVEnable) {
+ Log.v(TAG, "wmv enable");
+ boolean isSeek = CodecTest.videoSeekTo(MediaNames.VIDEO_WMV);
+ assertTrue("WMV SeekTo", isSeek);
+ }
}
@LargeTest
diff --git a/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaRecorderTest.java b/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaRecorderTest.java
index b4d265d..690eff6 100644
--- a/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaRecorderTest.java
+++ b/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaRecorderTest.java
@@ -239,7 +239,7 @@
validVideo = true;
}
Log.v(TAG, "width = " + mOutputVideoWidth + " height = " + mOutputVideoHeight + " Duration = " + mOutputDuration);
- removeFile(filePath);
+ //removeFile(filePath);
return validVideo;
}
@@ -428,8 +428,9 @@
}
@LargeTest
- //est cases for the new codec
+ //test cases for the new codec
public void testDeviceSpecificCodec() throws Exception {
+ int noOfFailure = 0;
boolean recordSuccess = false;
String deviceType = MediaProfileReader.getDeviceType();
Log.v(TAG, "deviceType = " + deviceType);
@@ -450,10 +451,18 @@
} else {
recordSuccess = recordVideoWithPara(encoder[i], audio[j], "low");
}
- assertTrue((encoder[i] + audio[j]), recordSuccess);
+ if (!recordSuccess){
+ Log.v(TAG, "testDeviceSpecificCodec failed");
+ Log.v(TAG, "Encoder = " + encoder[i] + "Audio Encoder = " + audio[j]);
+ noOfFailure++;
+ }
+ //assertTrue((encoder[i] + audio[j]), recordSuccess);
}
}
}
}
+ if (noOfFailure != 0){
+ assertTrue("testDeviceSpecificCodec", false);
+ }
}
}
diff --git a/packages/VpnServices/src/com/android/server/vpn/L2tpIpsecService.java b/packages/VpnServices/src/com/android/server/vpn/L2tpIpsecService.java
index 13b4952..9909905 100644
--- a/packages/VpnServices/src/com/android/server/vpn/L2tpIpsecService.java
+++ b/packages/VpnServices/src/com/android/server/vpn/L2tpIpsecService.java
@@ -17,7 +17,7 @@
package com.android.server.vpn;
import android.net.vpn.L2tpIpsecProfile;
-import android.security.CertTool;
+import android.security.Credentials;
import java.io.IOException;
@@ -30,16 +30,18 @@
@Override
protected void connect(String serverIp, String username, String password)
throws IOException {
+ L2tpIpsecProfile p = getProfile();
// IPSEC
DaemonProxy ipsec = startDaemon(IPSEC);
ipsec.sendCommand(serverIp, L2tpService.L2TP_PORT,
- getUserkeyPath(), getUserCertPath(), getCaCertPath());
+ Credentials.USER_PRIVATE_KEY + p.getUserCertificate(),
+ Credentials.USER_CERTIFICATE + p.getUserCertificate(),
+ Credentials.CA_CERTIFICATE + p.getCaCertificate());
ipsec.closeControlSocket();
sleep(2000); // 2 seconds
// L2TP
- L2tpIpsecProfile p = getProfile();
MtpdHelper.sendCommand(this, L2tpService.L2TP_DAEMON, serverIp,
L2tpService.L2TP_PORT,
(p.isSecretEnabled() ? p.getSecretString() : null),
@@ -51,19 +53,4 @@
stopDaemon(IPSEC);
stopDaemon(MtpdHelper.MTPD);
}
-
- private String getCaCertPath() {
- return CertTool.getInstance().getCaCertificate(
- getProfile().getCaCertificate());
- }
-
- private String getUserCertPath() {
- return CertTool.getInstance().getUserCertificate(
- getProfile().getUserCertificate());
- }
-
- private String getUserkeyPath() {
- return CertTool.getInstance().getUserPrivateKey(
- getProfile().getUserCertificate());
- }
}
diff --git a/services/java/com/android/server/PowerManagerService.java b/services/java/com/android/server/PowerManagerService.java
index 9d2fc27..b2e3a8c 100644
--- a/services/java/com/android/server/PowerManagerService.java
+++ b/services/java/com/android/server/PowerManagerService.java
@@ -2131,7 +2131,9 @@
long milliseconds = event.timestamp / 1000000;
synchronized (mLocks) {
float distance = event.values[0];
- if (distance >= 0.0 && distance < PROXIMITY_THRESHOLD) {
+ // compare against getMaximumRange to support sensors that only return 0 or 1
+ if (distance >= 0.0 && distance < PROXIMITY_THRESHOLD &&
+ distance < mProximitySensor.getMaximumRange()) {
if (mSpew) {
Log.d(TAG, "onSensorChanged: proximity active, distance: " + distance);
}
diff --git a/wifi/java/android/net/wifi/WifiConfiguration.java b/wifi/java/android/net/wifi/WifiConfiguration.java
index 954930e..01bc919 100644
--- a/wifi/java/android/net/wifi/WifiConfiguration.java
+++ b/wifi/java/android/net/wifi/WifiConfiguration.java
@@ -71,7 +71,7 @@
/** {@hide} */
public EnterpriseField phase2 = new EnterpriseField("phase2");
/** {@hide} */
- public EnterpriseField identity = new EnterpriseField("anonymous_identity");
+ public EnterpriseField identity = new EnterpriseField("identity");
/** {@hide} */
public EnterpriseField anonymous_identity = new EnterpriseField("anonymous_identity");
/** {@hide} */
diff --git a/wifi/java/android/net/wifi/WifiStateTracker.java b/wifi/java/android/net/wifi/WifiStateTracker.java
index e3d8bf4..5638480 100644
--- a/wifi/java/android/net/wifi/WifiStateTracker.java
+++ b/wifi/java/android/net/wifi/WifiStateTracker.java
@@ -907,6 +907,7 @@
}
}
} else if (newState == SupplicantState.DISCONNECTED) {
+ mHaveIpAddress = false;
if (isDriverStopped() || mDisconnectExpected) {
handleDisconnectedState(DetailedState.DISCONNECTED);
} else {
@@ -1007,20 +1008,17 @@
setNotificationVisible(false, 0, false, 0);
boolean wasDisconnectPending = mDisconnectPending;
cancelDisconnect();
- if (!TextUtils.equals(mWifiInfo.getSSID(), mLastSsid)) {
- /*
- * The connection is fully configured as far as link-level
- * connectivity is concerned, but we may still need to obtain
- * an IP address. But do this only if we are connecting to
- * a different network than we were connected to previously.
- */
- if (wasDisconnectPending) {
- DetailedState saveState = getNetworkInfo().getDetailedState();
- handleDisconnectedState(DetailedState.DISCONNECTED);
- setDetailedStateInternal(saveState);
- }
- configureInterface();
+ /*
+ * The connection is fully configured as far as link-level
+ * connectivity is concerned, but we may still need to obtain
+ * an IP address.
+ */
+ if (wasDisconnectPending) {
+ DetailedState saveState = getNetworkInfo().getDetailedState();
+ handleDisconnectedState(DetailedState.DISCONNECTED);
+ setDetailedStateInternal(saveState);
}
+ configureInterface();
mLastBssid = result.BSSID;
mLastSsid = mWifiInfo.getSSID();
mLastNetworkId = result.networkId;