summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--api/11.xml8
-rw-r--r--api/current.xml347
-rw-r--r--core/java/android/animation/KeyframeSet.java9
-rw-r--r--core/java/android/animation/ObjectAnimator.java12
-rw-r--r--core/java/android/animation/PropertyValuesHolder.java5
-rwxr-xr-xcore/java/android/animation/ValueAnimator.java11
-rw-r--r--core/java/android/app/admin/DeviceAdminReceiver.java6
-rw-r--r--core/java/android/app/admin/DevicePolicyManager.java10
-rw-r--r--core/java/android/content/SyncManager.java6
-rwxr-xr-xcore/java/android/view/InputDevice.java230
-rwxr-xr-xcore/java/android/view/InputEvent.java45
-rwxr-xr-xcore/java/android/view/KeyEvent.java29
-rw-r--r--core/java/android/view/MotionEvent.java1342
-rw-r--r--core/java/android/view/View.java28
-rw-r--r--core/java/android/webkit/BrowserFrame.java16
-rw-r--r--core/java/android/webkit/CacheManager.java7
-rw-r--r--core/java/android/webkit/WebSettings.java21
-rw-r--r--core/java/android/webkit/WebView.java14
-rw-r--r--core/java/android/widget/AutoCompleteTextView.java4
-rw-r--r--core/java/android/widget/ListPopupWindow.java19
-rw-r--r--core/java/android/widget/PopupWindow.java14
-rw-r--r--core/java/android/widget/StackView.java6
-rw-r--r--core/jni/android_view_MotionEvent.cpp943
-rw-r--r--core/res/res/drawable-hdpi/text_cursor_holo_dark.9.pngbin0 -> 274 bytes
-rw-r--r--core/res/res/drawable-hdpi/text_cursor_holo_light.9.pngbin0 -> 249 bytes
-rw-r--r--core/res/res/raw-es/incognito_mode_start_page.html26
-rw-r--r--core/res/res/raw/incognito_mode_start_page.html24
-rwxr-xr-xcore/res/res/values/strings.xml6
-rw-r--r--graphics/java/android/graphics/Bitmap.java13
-rw-r--r--graphics/java/android/graphics/Paint.java4
-rw-r--r--graphics/tests/graphicstests/src/android/graphics/BitmapTest.java6
-rw-r--r--include/ui/Input.h182
-rw-r--r--libs/rs/java/ModelViewer/AndroidManifest.xml11
-rw-r--r--libs/rs/java/ModelViewer/res/menu/loader_menu.xml25
-rw-r--r--libs/rs/java/ModelViewer/res/values/strings.xml24
-rw-r--r--libs/rs/java/ModelViewer/src/com/android/modelviewer/A3DSelector.java110
-rw-r--r--libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModel.java43
-rw-r--r--libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelRS.java97
-rw-r--r--libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelView.java130
-rw-r--r--libs/rs/java/ModelViewer/src/com/android/modelviewer/simplemodel.rs124
-rw-r--r--libs/ui/Android.mk7
-rw-r--r--libs/ui/Input.cpp297
-rw-r--r--libs/ui/tests/InputPublisherAndConsumer_test.cpp78
-rw-r--r--native/android/input.cpp11
-rw-r--r--native/include/android/input.h50
-rw-r--r--services/input/InputDispatcher.cpp41
-rw-r--r--services/input/InputReader.cpp69
-rw-r--r--services/input/tests/InputReader_test.cpp39
-rw-r--r--services/java/com/android/server/DevicePolicyManagerService.java4
-rw-r--r--services/jni/com_android_server_InputManager.cpp4
-rw-r--r--services/surfaceflinger/Layer.cpp7
-rw-r--r--services/surfaceflinger/Layer.h1
-rw-r--r--services/surfaceflinger/LayerBase.cpp17
-rw-r--r--services/surfaceflinger/LayerBase.h2
-rw-r--r--wifi/java/android/net/wifi/WifiManager.java40
55 files changed, 3269 insertions, 1355 deletions
diff --git a/api/11.xml b/api/11.xml
index 6a1f909..76669e3 100644
--- a/api/11.xml
+++ b/api/11.xml
@@ -207458,22 +207458,22 @@
</method>
<method name="getDeviceId"
return="int"
- abstract="false"
+ abstract="true"
native="false"
synchronized="false"
static="false"
- final="true"
+ final="false"
deprecated="not deprecated"
visibility="public"
>
</method>
<method name="getSource"
return="int"
- abstract="false"
+ abstract="true"
native="false"
synchronized="false"
static="false"
- final="true"
+ final="false"
deprecated="not deprecated"
visibility="public"
>
diff --git a/api/current.xml b/api/current.xml
index 1ce49d4..9a38459 100644
--- a/api/current.xml
+++ b/api/current.xml
@@ -76371,6 +76371,17 @@
<parameter name="offsetXY" type="int[]">
</parameter>
</method>
+<method name="getByteCount"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
<method name="getConfig"
return="android.graphics.Bitmap.Config"
abstract="false"
@@ -121174,6 +121185,17 @@
visibility="public"
>
</field>
+<field name="WIFI_MODE_FULL_HIGH_PERF"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="3"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
<field name="WIFI_MODE_SCAN_ONLY"
type="int"
transient="false"
@@ -210563,7 +210585,7 @@
deprecated="not deprecated"
visibility="public"
>
-<parameter name="rangeType" type="int">
+<parameter name="axis" type="int">
</parameter>
</method>
<method name="getName"
@@ -210653,7 +210675,7 @@
value="8"
static="true"
final="true"
- deprecated="not deprecated"
+ deprecated="deprecated"
visibility="public"
>
</field>
@@ -210664,7 +210686,7 @@
value="2"
static="true"
final="true"
- deprecated="not deprecated"
+ deprecated="deprecated"
visibility="public"
>
</field>
@@ -210675,7 +210697,7 @@
value="3"
static="true"
final="true"
- deprecated="not deprecated"
+ deprecated="deprecated"
visibility="public"
>
</field>
@@ -210686,7 +210708,7 @@
value="6"
static="true"
final="true"
- deprecated="not deprecated"
+ deprecated="deprecated"
visibility="public"
>
</field>
@@ -210697,7 +210719,7 @@
value="7"
static="true"
final="true"
- deprecated="not deprecated"
+ deprecated="deprecated"
visibility="public"
>
</field>
@@ -210708,7 +210730,7 @@
value="4"
static="true"
final="true"
- deprecated="not deprecated"
+ deprecated="deprecated"
visibility="public"
>
</field>
@@ -210719,7 +210741,7 @@
value="5"
static="true"
final="true"
- deprecated="not deprecated"
+ deprecated="deprecated"
visibility="public"
>
</field>
@@ -210730,7 +210752,7 @@
value="0"
static="true"
final="true"
- deprecated="not deprecated"
+ deprecated="deprecated"
visibility="public"
>
</field>
@@ -210741,7 +210763,7 @@
value="1"
static="true"
final="true"
- deprecated="not deprecated"
+ deprecated="deprecated"
visibility="public"
>
</field>
@@ -211020,22 +211042,22 @@
</method>
<method name="getDeviceId"
return="int"
- abstract="false"
+ abstract="true"
native="false"
synchronized="false"
static="false"
- final="true"
+ final="false"
deprecated="not deprecated"
visibility="public"
>
</method>
<method name="getSource"
return="int"
- abstract="false"
+ abstract="true"
native="false"
synchronized="false"
static="false"
- final="true"
+ final="false"
deprecated="not deprecated"
visibility="public"
>
@@ -211825,6 +211847,17 @@
<parameter name="c" type="int">
</parameter>
</method>
+<method name="getDeviceId"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
<method name="getDisplayLabel"
return="char"
abstract="false"
@@ -211998,6 +212031,17 @@
visibility="public"
>
</method>
+<method name="getSource"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
<method name="getUnicodeChar"
return="int"
abstract="false"
@@ -212254,6 +212298,19 @@
<parameter name="metaState" type="int">
</parameter>
</method>
+<method name="setSource"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="source" type="int">
+</parameter>
+</method>
<method name="startTracking"
return="void"
abstract="false"
@@ -216510,6 +216567,45 @@
visibility="public"
>
</method>
+<method name="getAxisValue"
+ return="float"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="axis" type="int">
+</parameter>
+</method>
+<method name="getAxisValue"
+ return="float"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="axis" type="int">
+</parameter>
+<parameter name="pointerIndex" type="int">
+</parameter>
+</method>
+<method name="getDeviceId"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
<method name="getDownTime"
return="long"
abstract="false"
@@ -216554,6 +216650,38 @@
visibility="public"
>
</method>
+<method name="getHistoricalAxisValue"
+ return="float"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="axis" type="int">
+</parameter>
+<parameter name="pos" type="int">
+</parameter>
+</method>
+<method name="getHistoricalAxisValue"
+ return="float"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="axis" type="int">
+</parameter>
+<parameter name="pointerIndex" type="int">
+</parameter>
+<parameter name="pos" type="int">
+</parameter>
+</method>
<method name="getHistoricalEventTime"
return="long"
abstract="false"
@@ -216991,6 +217119,17 @@
<parameter name="pointerIndex" type="int">
</parameter>
</method>
+<method name="getSource"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
<method name="getToolMajor"
return="float"
abstract="false"
@@ -217299,7 +217438,7 @@
deprecated="not deprecated"
visibility="public"
>
-<parameter name="o" type="android.view.MotionEvent">
+<parameter name="other" type="android.view.MotionEvent">
</parameter>
</method>
<method name="obtainNoHistory"
@@ -217312,7 +217451,7 @@
deprecated="not deprecated"
visibility="public"
>
-<parameter name="o" type="android.view.MotionEvent">
+<parameter name="other" type="android.view.MotionEvent">
</parameter>
</method>
<method name="offsetLocation"
@@ -217382,6 +217521,19 @@
<parameter name="y" type="float">
</parameter>
</method>
+<method name="setSource"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="source" type="int">
+</parameter>
+</method>
<method name="transform"
return="void"
abstract="false"
@@ -217608,6 +217760,105 @@
visibility="public"
>
</field>
+<field name="AXIS_ORIENTATION"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="8"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
+<field name="AXIS_PRESSURE"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="2"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
+<field name="AXIS_SIZE"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="3"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
+<field name="AXIS_TOOL_MAJOR"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="6"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
+<field name="AXIS_TOOL_MINOR"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="7"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
+<field name="AXIS_TOUCH_MAJOR"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="4"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
+<field name="AXIS_TOUCH_MINOR"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="5"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
+<field name="AXIS_X"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="0"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
+<field name="AXIS_Y"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="1"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
<field name="CREATOR"
type="android.os.Parcelable.Creator"
transient="false"
@@ -217690,6 +217941,68 @@
visibility="public"
>
</constructor>
+<constructor name="MotionEvent.PointerCoords"
+ type="android.view.MotionEvent.PointerCoords"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="other" type="android.view.MotionEvent.PointerCoords">
+</parameter>
+</constructor>
+<method name="clear"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
+<method name="copyFrom"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="other" type="android.view.MotionEvent.PointerCoords">
+</parameter>
+</method>
+<method name="getAxisValue"
+ return="float"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="axis" type="int">
+</parameter>
+</method>
+<method name="setAxisValue"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="axis" type="int">
+</parameter>
+<parameter name="value" type="float">
+</parameter>
+</method>
<field name="orientation"
type="float"
transient="false"
@@ -265799,7 +266112,7 @@
deprecated="not deprecated"
visibility="public"
>
-<parameter name="t" type="T">
+<parameter name="arg0" type="T">
</parameter>
</method>
</interface>
diff --git a/core/java/android/animation/KeyframeSet.java b/core/java/android/animation/KeyframeSet.java
index fa61b71..6172aab 100644
--- a/core/java/android/animation/KeyframeSet.java
+++ b/core/java/android/animation/KeyframeSet.java
@@ -212,4 +212,13 @@ class KeyframeSet {
// shouldn't reach here
return mLastKeyframe.getValue();
}
+
+ @Override
+ public String toString() {
+ String returnVal = " ";
+ for (int i = 0; i < mNumKeyframes; ++i) {
+ returnVal += mKeyframes.get(i).getValue() + " ";
+ }
+ return returnVal;
+ }
}
diff --git a/core/java/android/animation/ObjectAnimator.java b/core/java/android/animation/ObjectAnimator.java
index d038cd6..b8a7cb2 100644
--- a/core/java/android/animation/ObjectAnimator.java
+++ b/core/java/android/animation/ObjectAnimator.java
@@ -394,4 +394,16 @@ public final class ObjectAnimator extends ValueAnimator {
final ObjectAnimator anim = (ObjectAnimator) super.clone();
return anim;
}
+
+ @Override
+ public String toString() {
+ String returnVal = "ObjectAnimator@" + Integer.toHexString(hashCode()) + ", target " +
+ mTarget;
+ if (mValues != null) {
+ for (int i = 0; i < mValues.length; ++i) {
+ returnVal += "\n " + mValues[i].toString();
+ }
+ }
+ return returnVal;
+ }
}
diff --git a/core/java/android/animation/PropertyValuesHolder.java b/core/java/android/animation/PropertyValuesHolder.java
index 0c30aad..6f91fc0 100644
--- a/core/java/android/animation/PropertyValuesHolder.java
+++ b/core/java/android/animation/PropertyValuesHolder.java
@@ -578,6 +578,11 @@ public class PropertyValuesHolder implements Cloneable {
return mAnimatedValue;
}
+ @Override
+ public String toString() {
+ return mPropertyName + ": " + mKeyframeSet.toString();
+ }
+
/**
* Utility method to derive a setter/getter method name from a property name, where the
* prefix is typically "set" or "get" and the first letter of the property name is
diff --git a/core/java/android/animation/ValueAnimator.java b/core/java/android/animation/ValueAnimator.java
index 5a8a74a..2e44d6d 100755
--- a/core/java/android/animation/ValueAnimator.java
+++ b/core/java/android/animation/ValueAnimator.java
@@ -1207,4 +1207,15 @@ public class ValueAnimator extends Animator {
sPendingAnimations.get().clear();
sDelayedAnims.get().clear();
}
+
+ @Override
+ public String toString() {
+ String returnVal = "ValueAnimator@" + Integer.toHexString(hashCode());
+ if (mValues != null) {
+ for (int i = 0; i < mValues.length; ++i) {
+ returnVal += "\n " + mValues[i].toString();
+ }
+ }
+ return returnVal;
+ }
}
diff --git a/core/java/android/app/admin/DeviceAdminReceiver.java b/core/java/android/app/admin/DeviceAdminReceiver.java
index eccd7c9..29f8caf 100644
--- a/core/java/android/app/admin/DeviceAdminReceiver.java
+++ b/core/java/android/app/admin/DeviceAdminReceiver.java
@@ -148,7 +148,7 @@ public class DeviceAdminReceiver extends BroadcastReceiver {
/**
* Action periodically sent to a device administrator when the device password
- * is expiring.
+ * is expiring.
*
* <p>The calling device admin must have requested
* {@link DeviceAdminInfo#USES_POLICY_EXPIRE_PASSWORD} to receive
@@ -266,8 +266,8 @@ public class DeviceAdminReceiver extends BroadcastReceiver {
/**
* Called periodically when the password is about to expire or has expired. It will typically
- * be called on device boot, once per day before the password expires and at the time when it
- * expires.
+ * be called at these times: on device boot, once per day before the password expires,
+ * and at the time when the password expires.
*
* <p>If the password is not updated by the user, this method will continue to be called
* once per day until the password is changed or the device admin disables password expiration.
diff --git a/core/java/android/app/admin/DevicePolicyManager.java b/core/java/android/app/admin/DevicePolicyManager.java
index d71a7a3..440cb54 100644
--- a/core/java/android/app/admin/DevicePolicyManager.java
+++ b/core/java/android/app/admin/DevicePolicyManager.java
@@ -730,8 +730,10 @@ public class DevicePolicyManager {
}
/**
- * Get the current password expiration timeout for the given admin or the aggregate
- * of all admins if admin is null.
+ * Get the password expiration timeout for the given admin. The expiration timeout is the
+ * recurring expiration timeout provided in the call to
+ * {@link #setPasswordExpirationTimeout(ComponentName, long)} for the given admin or the
+ * aggregate of all policy administrators if admin is null.
*
* @param admin The name of the admin component to check, or null to aggregate all admins.
* @return The timeout for the given admin or the minimum of all timeouts
@@ -749,7 +751,9 @@ public class DevicePolicyManager {
/**
* Get the current password expiration time for the given admin or an aggregate of
- * all admins if admin is null.
+ * all admins if admin is null. If the password is expired, this will return the time since
+ * the password expired as a negative number. If admin is null, then a composite of all
+ * expiration timeouts is returned - which will be the minimum of all timeouts.
*
* @param admin The name of the admin component to check, or null to aggregate all admins.
* @return The password expiration time, in ms.
diff --git a/core/java/android/content/SyncManager.java b/core/java/android/content/SyncManager.java
index ebc1882..2cb8a86 100644
--- a/core/java/android/content/SyncManager.java
+++ b/core/java/android/content/SyncManager.java
@@ -241,7 +241,7 @@ public class SyncManager implements OnAccountsUpdateListener {
// don't use the intent to figure out if network is connected, just check
// ConnectivityManager directly.
- mDataConnectionIsConnected = isNetworkConnected();
+ mDataConnectionIsConnected = readDataConnectionState();
if (mDataConnectionIsConnected) {
if (!wasConnected) {
if (Log.isLoggable(TAG, Log.VERBOSE)) {
@@ -254,7 +254,7 @@ public class SyncManager implements OnAccountsUpdateListener {
}
};
- private boolean isNetworkConnected() {
+ private boolean readDataConnectionState() {
NetworkInfo networkInfo = getConnectivityManager().getActiveNetworkInfo();
return (networkInfo != null) && networkInfo.isConnected();
}
@@ -1429,7 +1429,7 @@ public class SyncManager implements OnAccountsUpdateListener {
// to have the most recent value used.
try {
waitUntilReadyToRun();
- mDataConnectionIsConnected = isNetworkConnected();
+ mDataConnectionIsConnected = readDataConnectionState();
mSyncManagerWakeLock.acquire();
// Always do this first so that we be sure that any periodic syncs that
// are ready to run have been converted into pending syncs. This allows the
diff --git a/core/java/android/view/InputDevice.java b/core/java/android/view/InputDevice.java
index e799f76..7abbce6 100755
--- a/core/java/android/view/InputDevice.java
+++ b/core/java/android/view/InputDevice.java
@@ -20,6 +20,7 @@ import android.os.Parcel;
import android.os.Parcelable;
import android.os.RemoteException;
import android.os.ServiceManager;
+import android.util.SparseArray;
/**
* Describes the capabilities of a particular input device.
@@ -41,9 +42,9 @@ public final class InputDevice implements Parcelable {
private String mName;
private int mSources;
private int mKeyboardType;
-
- private MotionRange[] mMotionRanges;
-
+
+ private final SparseArray<MotionRange> mMotionRanges = new SparseArray<MotionRange>();
+
/**
* A mask for input source classes.
*
@@ -181,70 +182,85 @@ public final class InputDevice implements Parcelable {
public static final int SOURCE_ANY = 0xffffff00;
/**
- * Constant for retrieving the range of values for {@link MotionEvent.PointerCoords#x}.
+ * Constant for retrieving the range of values for {@link MotionEvent#AXIS_X}.
*
* @see #getMotionRange
+ * @deprecated Use {@link MotionEvent#AXIS_X} instead.
*/
- public static final int MOTION_RANGE_X = 0;
-
+ @Deprecated
+ public static final int MOTION_RANGE_X = MotionEvent.AXIS_X;
+
/**
- * Constant for retrieving the range of values for {@link MotionEvent.PointerCoords#y}.
+ * Constant for retrieving the range of values for {@link MotionEvent#AXIS_Y}.
*
* @see #getMotionRange
+ * @deprecated Use {@link MotionEvent#AXIS_Y} instead.
*/
- public static final int MOTION_RANGE_Y = 1;
-
+ @Deprecated
+ public static final int MOTION_RANGE_Y = MotionEvent.AXIS_Y;
+
/**
- * Constant for retrieving the range of values for {@link MotionEvent.PointerCoords#pressure}.
+ * Constant for retrieving the range of values for {@link MotionEvent#AXIS_PRESSURE}.
*
* @see #getMotionRange
+ * @deprecated Use {@link MotionEvent#AXIS_PRESSURE} instead.
*/
- public static final int MOTION_RANGE_PRESSURE = 2;
-
+ @Deprecated
+ public static final int MOTION_RANGE_PRESSURE = MotionEvent.AXIS_PRESSURE;
+
/**
- * Constant for retrieving the range of values for {@link MotionEvent.PointerCoords#size}.
+ * Constant for retrieving the range of values for {@link MotionEvent#AXIS_SIZE}.
*
* @see #getMotionRange
+ * @deprecated Use {@link MotionEvent#AXIS_SIZE} instead.
*/
- public static final int MOTION_RANGE_SIZE = 3;
-
+ @Deprecated
+ public static final int MOTION_RANGE_SIZE = MotionEvent.AXIS_SIZE;
+
/**
- * Constant for retrieving the range of values for {@link MotionEvent.PointerCoords#touchMajor}.
+ * Constant for retrieving the range of values for {@link MotionEvent#AXIS_TOUCH_MAJOR}.
*
* @see #getMotionRange
+ * @deprecated Use {@link MotionEvent#AXIS_TOUCH_MAJOR} instead.
*/
- public static final int MOTION_RANGE_TOUCH_MAJOR = 4;
-
+ @Deprecated
+ public static final int MOTION_RANGE_TOUCH_MAJOR = MotionEvent.AXIS_TOUCH_MAJOR;
+
/**
- * Constant for retrieving the range of values for {@link MotionEvent.PointerCoords#touchMinor}.
+ * Constant for retrieving the range of values for {@link MotionEvent#AXIS_TOUCH_MINOR}.
*
* @see #getMotionRange
+ * @deprecated Use {@link MotionEvent#AXIS_TOUCH_MINOR} instead.
*/
- public static final int MOTION_RANGE_TOUCH_MINOR = 5;
-
+ @Deprecated
+ public static final int MOTION_RANGE_TOUCH_MINOR = MotionEvent.AXIS_TOUCH_MINOR;
+
/**
- * Constant for retrieving the range of values for {@link MotionEvent.PointerCoords#toolMajor}.
+ * Constant for retrieving the range of values for {@link MotionEvent#AXIS_TOOL_MAJOR}.
*
* @see #getMotionRange
+ * @deprecated Use {@link MotionEvent#AXIS_TOOL_MAJOR} instead.
*/
- public static final int MOTION_RANGE_TOOL_MAJOR = 6;
-
+ @Deprecated
+ public static final int MOTION_RANGE_TOOL_MAJOR = MotionEvent.AXIS_TOOL_MAJOR;
+
/**
- * Constant for retrieving the range of values for {@link MotionEvent.PointerCoords#toolMinor}.
+ * Constant for retrieving the range of values for {@link MotionEvent#AXIS_TOOL_MINOR}.
*
* @see #getMotionRange
+ * @deprecated Use {@link MotionEvent#AXIS_TOOL_MINOR} instead.
*/
- public static final int MOTION_RANGE_TOOL_MINOR = 7;
-
+ @Deprecated
+ public static final int MOTION_RANGE_TOOL_MINOR = MotionEvent.AXIS_TOOL_MINOR;
+
/**
- * Constant for retrieving the range of values for
- * {@link MotionEvent.PointerCoords#orientation}.
+ * Constant for retrieving the range of values for {@link MotionEvent#AXIS_ORIENTATION}.
*
* @see #getMotionRange
+ * @deprecated Use {@link MotionEvent#AXIS_ORIENTATION} instead.
*/
- public static final int MOTION_RANGE_ORIENTATION = 8;
-
- private static final int MOTION_RANGE_LAST = MOTION_RANGE_ORIENTATION;
+ @Deprecated
+ public static final int MOTION_RANGE_ORIENTATION = MotionEvent.AXIS_ORIENTATION;
/**
* There is no keyboard.
@@ -261,10 +277,9 @@ public final class InputDevice implements Parcelable {
* The keyboard supports a complement of alphabetic keys.
*/
public static final int KEYBOARD_TYPE_ALPHABETIC = 2;
-
+
// Called by native code.
private InputDevice() {
- mMotionRanges = new MotionRange[MOTION_RANGE_LAST + 1];
}
/**
@@ -335,72 +350,69 @@ public final class InputDevice implements Parcelable {
public KeyCharacterMap getKeyCharacterMap() {
return KeyCharacterMap.load(mId);
}
-
+
/**
- * Gets information about the range of values for a particular {@link MotionEvent}
- * coordinate.
- * @param rangeType The motion range constant.
- * @return The range of values, or null if the requested coordinate is not
+ * Gets information about the range of values for a particular {@link MotionEvent} axis.
+ * @param axis The axis constant.
+ * @return The range of values, or null if the requested axis is not
* supported by the device.
+ *
+ * @see MotionEvent#AXIS_X
+ * @see MotionEvent#AXIS_Y
*/
- public MotionRange getMotionRange(int rangeType) {
- if (rangeType < 0 || rangeType > MOTION_RANGE_LAST) {
- throw new IllegalArgumentException("Requested range is out of bounds.");
- }
-
- return mMotionRanges[rangeType];
+ public MotionRange getMotionRange(int axis) {
+ return mMotionRanges.get(axis);
}
-
- private void addMotionRange(int rangeType, float min, float max, float flat, float fuzz) {
- if (rangeType >= 0 && rangeType <= MOTION_RANGE_LAST) {
- MotionRange range = new MotionRange(min, max, flat, fuzz);
- mMotionRanges[rangeType] = range;
- }
+
+ // Called by native code.
+ private void addMotionRange(int axis, float min, float max, float flat, float fuzz) {
+ mMotionRanges.append(axis, new MotionRange(min, max, flat, fuzz));
}
-
+
/**
- * Provides information about the range of values for a particular {@link MotionEvent}
- * coordinate.
+ * Provides information about the range of values for a particular {@link MotionEvent} axis.
+ *
+ * @see InputDevice#getMotionRange(int)
*/
public static final class MotionRange {
private float mMin;
private float mMax;
private float mFlat;
private float mFuzz;
-
+
private MotionRange(float min, float max, float flat, float fuzz) {
mMin = min;
mMax = max;
mFlat = flat;
mFuzz = fuzz;
}
-
+
/**
- * Gets the minimum value for the coordinate.
- * @return The minimum value.
+ * Gets the minimum value for the axis.
+ * @return The (inclusive) minimum value.
*/
public float getMin() {
return mMin;
}
-
+
/**
- * Gets the maximum value for the coordinate.
- * @return The minimum value.
+ * Gets the maximum value for the axis.
+ * @return The (inclusive) maximum value.
*/
public float getMax() {
return mMax;
}
-
+
/**
- * Gets the range of the coordinate (difference between maximum and minimum).
+ * Gets the range of the axis (difference between maximum and minimum plus one).
* @return The range of values.
*/
public float getRange() {
- return mMax - mMin;
+ return mMax - mMin + 1;
}
-
+
/**
- * Gets the extent of the center flat position with respect to this coordinate.
+ * Gets the extent of the center flat position with respect to this axis.
* For example, a flat value of 8 means that the center position is between -8 and +8.
* This value is mainly useful for calibrating self-centering devices.
* @return The extent of the center flat position.
@@ -408,9 +420,9 @@ public final class InputDevice implements Parcelable {
public float getFlat() {
return mFlat;
}
-
+
/**
- * Gets the error tolerance for input device measurements with respect to this coordinate.
+ * Gets the error tolerance for input device measurements with respect to this axis.
* For example, a value of 2 indicates that the measured value may be up to +/- 2 units
* away from the actual value due to noise and device sensitivity limitations.
* @return The error tolerance.
@@ -419,7 +431,7 @@ public final class InputDevice implements Parcelable {
return mFuzz;
}
}
-
+
public static final Parcelable.Creator<InputDevice> CREATOR
= new Parcelable.Creator<InputDevice>() {
public InputDevice createFromParcel(Parcel in) {
@@ -438,15 +450,13 @@ public final class InputDevice implements Parcelable {
mName = in.readString();
mSources = in.readInt();
mKeyboardType = in.readInt();
-
+
for (;;) {
- int rangeType = in.readInt();
- if (rangeType < 0) {
+ int axis = in.readInt();
+ if (axis < 0) {
break;
}
-
- addMotionRange(rangeType,
- in.readFloat(), in.readFloat(), in.readFloat(), in.readFloat());
+ addMotionRange(axis, in.readFloat(), in.readFloat(), in.readFloat(), in.readFloat());
}
}
@@ -456,25 +466,25 @@ public final class InputDevice implements Parcelable {
out.writeString(mName);
out.writeInt(mSources);
out.writeInt(mKeyboardType);
-
- for (int i = 0; i <= MOTION_RANGE_LAST; i++) {
- MotionRange range = mMotionRanges[i];
- if (range != null) {
- out.writeInt(i);
- out.writeFloat(range.mMin);
- out.writeFloat(range.mMax);
- out.writeFloat(range.mFlat);
- out.writeFloat(range.mFuzz);
- }
+
+ final int numAxes = mMotionRanges.size();
+ for (int i = 0; i < numAxes; i++) {
+ int axis = mMotionRanges.keyAt(i);
+ MotionRange range = mMotionRanges.valueAt(i);
+ out.writeInt(axis);
+ out.writeFloat(range.mMin);
+ out.writeFloat(range.mMax);
+ out.writeFloat(range.mFlat);
+ out.writeFloat(range.mFuzz);
}
out.writeInt(-1);
}
-
+
@Override
public int describeContents() {
return 0;
}
-
+
@Override
public String toString() {
StringBuilder description = new StringBuilder();
@@ -493,29 +503,32 @@ public final class InputDevice implements Parcelable {
break;
}
description.append("\n");
-
- description.append(" Sources:");
+
+ description.append(" Sources: ").append(Integer.toHexString(mSources)).append(" (");
appendSourceDescriptionIfApplicable(description, SOURCE_KEYBOARD, "keyboard");
appendSourceDescriptionIfApplicable(description, SOURCE_DPAD, "dpad");
appendSourceDescriptionIfApplicable(description, SOURCE_TOUCHSCREEN, "touchscreen");
appendSourceDescriptionIfApplicable(description, SOURCE_MOUSE, "mouse");
appendSourceDescriptionIfApplicable(description, SOURCE_TRACKBALL, "trackball");
appendSourceDescriptionIfApplicable(description, SOURCE_TOUCHPAD, "touchpad");
- description.append("\n");
-
- appendRangeDescriptionIfApplicable(description, MOTION_RANGE_X, "x");
- appendRangeDescriptionIfApplicable(description, MOTION_RANGE_Y, "y");
- appendRangeDescriptionIfApplicable(description, MOTION_RANGE_PRESSURE, "pressure");
- appendRangeDescriptionIfApplicable(description, MOTION_RANGE_SIZE, "size");
- appendRangeDescriptionIfApplicable(description, MOTION_RANGE_TOUCH_MAJOR, "touchMajor");
- appendRangeDescriptionIfApplicable(description, MOTION_RANGE_TOUCH_MINOR, "touchMinor");
- appendRangeDescriptionIfApplicable(description, MOTION_RANGE_TOOL_MAJOR, "toolMajor");
- appendRangeDescriptionIfApplicable(description, MOTION_RANGE_TOOL_MINOR, "toolMinor");
- appendRangeDescriptionIfApplicable(description, MOTION_RANGE_ORIENTATION, "orientation");
-
+ appendSourceDescriptionIfApplicable(description, SOURCE_JOYSTICK, "joystick");
+ appendSourceDescriptionIfApplicable(description, SOURCE_GAMEPAD, "gamepad");
+ description.append(" )\n");
+
+ final int numAxes = mMotionRanges.size();
+ for (int i = 0; i < numAxes; i++) {
+ int axis = mMotionRanges.keyAt(i);
+ MotionRange range = mMotionRanges.valueAt(i);
+ description.append(" ").append(MotionEvent.axisToString(axis));
+ description.append(": min=").append(range.mMin);
+ description.append(" max=").append(range.mMax);
+ description.append(" flat=").append(range.mFlat);
+ description.append(" fuzz=").append(range.mFuzz);
+ description.append("\n");
+ }
return description.toString();
}
-
+
private void appendSourceDescriptionIfApplicable(StringBuilder description, int source,
String sourceName) {
if ((mSources & source) == source) {
@@ -523,17 +536,4 @@ public final class InputDevice implements Parcelable {
description.append(sourceName);
}
}
-
- private void appendRangeDescriptionIfApplicable(StringBuilder description,
- int rangeType, String rangeName) {
- MotionRange range = mMotionRanges[rangeType];
- if (range != null) {
- description.append(" Range[").append(rangeName);
- description.append("]: min=").append(range.mMin);
- description.append(" max=").append(range.mMax);
- description.append(" flat=").append(range.mFlat);
- description.append(" fuzz=").append(range.mFuzz);
- description.append("\n");
- }
- }
}
diff --git a/core/java/android/view/InputEvent.java b/core/java/android/view/InputEvent.java
index 184e0fc..f6aeb39 100755
--- a/core/java/android/view/InputEvent.java
+++ b/core/java/android/view/InputEvent.java
@@ -24,11 +24,6 @@ import android.os.Parcelable;
*/
public abstract class InputEvent implements Parcelable {
/** @hide */
- protected int mDeviceId;
- /** @hide */
- protected int mSource;
-
- /** @hide */
protected static final int PARCEL_TOKEN_MOTION_EVENT = 1;
/** @hide */
protected static final int PARCEL_TOKEN_KEY_EVENT = 2;
@@ -45,55 +40,37 @@ public abstract class InputEvent implements Parcelable {
* @return The device id.
* @see InputDevice#getDevice
*/
- public final int getDeviceId() {
- return mDeviceId;
- }
-
+ public abstract int getDeviceId();
+
/**
* Gets the device that this event came from.
*
* @return The device, or null if unknown.
*/
public final InputDevice getDevice() {
- return InputDevice.getDevice(mDeviceId);
+ return InputDevice.getDevice(getDeviceId());
}
-
+
/**
* Gets the source of the event.
*
* @return The event source or {@link InputDevice#SOURCE_UNKNOWN} if unknown.
* @see InputDevice#getSourceInfo
*/
- public final int getSource() {
- return mSource;
- }
-
+ public abstract int getSource();
+
/**
* Modifies the source of the event.
- * @param source The source.
- *
+ *
+ * @param source The new source.
* @hide
*/
- public final void setSource(int source) {
- mSource = source;
- }
-
+ public abstract void setSource(int source);
+
public int describeContents() {
return 0;
}
-
- /** @hide */
- protected final void readBaseFromParcel(Parcel in) {
- mDeviceId = in.readInt();
- mSource = in.readInt();
- }
-
- /** @hide */
- protected final void writeBaseToParcel(Parcel out) {
- out.writeInt(mDeviceId);
- out.writeInt(mSource);
- }
-
+
public static final Parcelable.Creator<InputEvent> CREATOR
= new Parcelable.Creator<InputEvent>() {
public InputEvent createFromParcel(Parcel in) {
diff --git a/core/java/android/view/KeyEvent.java b/core/java/android/view/KeyEvent.java
index 766969a..3f6a04b 100755
--- a/core/java/android/view/KeyEvent.java
+++ b/core/java/android/view/KeyEvent.java
@@ -1180,6 +1180,8 @@ public class KeyEvent extends InputEvent implements Parcelable {
private KeyEvent mNext;
private boolean mRecycled;
+ private int mDeviceId;
+ private int mSource;
private int mMetaState;
private int mAction;
private int mKeyCode;
@@ -1651,6 +1653,23 @@ public class KeyEvent extends InputEvent implements Parcelable {
return native_hasDefaultAction(mKeyCode);
}
+ /** {@inheritDoc} */
+ @Override
+ public final int getDeviceId() {
+ return mDeviceId;
+ }
+
+ /** {@inheritDoc} */
+ @Override
+ public final int getSource() {
+ return mSource;
+ }
+
+ /** {@inheritDoc} */
+ @Override
+ public final void setSource(int source) {
+ mSource = source;
+ }
/**
* <p>Returns the state of the meta keys.</p>
@@ -2651,8 +2670,8 @@ public class KeyEvent extends InputEvent implements Parcelable {
}
private KeyEvent(Parcel in) {
- readBaseFromParcel(in);
-
+ mDeviceId = in.readInt();
+ mSource = in.readInt();
mAction = in.readInt();
mKeyCode = in.readInt();
mRepeatCount = in.readInt();
@@ -2665,9 +2684,9 @@ public class KeyEvent extends InputEvent implements Parcelable {
public void writeToParcel(Parcel out, int flags) {
out.writeInt(PARCEL_TOKEN_KEY_EVENT);
-
- writeBaseToParcel(out);
-
+
+ out.writeInt(mDeviceId);
+ out.writeInt(mSource);
out.writeInt(mAction);
out.writeInt(mKeyCode);
out.writeInt(mRepeatCount);
diff --git a/core/java/android/view/MotionEvent.java b/core/java/android/view/MotionEvent.java
index 5db4895..6673be2 100644
--- a/core/java/android/view/MotionEvent.java
+++ b/core/java/android/view/MotionEvent.java
@@ -102,7 +102,7 @@ import android.os.SystemClock;
* </p>
*/
public final class MotionEvent extends InputEvent implements Parcelable {
- private static final long MS_PER_NS = 1000000;
+ private static final long NS_PER_MS = 1000000;
private static final boolean TRACK_RECYCLED_LOCATION = false;
/**
@@ -261,123 +261,241 @@ public final class MotionEvent extends InputEvent implements Parcelable {
*/
public static final int EDGE_RIGHT = 0x00000008;
- /*
- * Offset for the sample's X coordinate.
- */
- static private final int SAMPLE_X = 0;
-
- /*
- * Offset for the sample's Y coordinate.
- */
- static private final int SAMPLE_Y = 1;
-
- /*
- * Offset for the sample's pressure.
- */
- static private final int SAMPLE_PRESSURE = 2;
-
- /*
- * Offset for the sample's size
+ /**
+ * Constant used to identify the X axis of a motion event.
+ *
+ * The interpretation of the X axis varies by input source.
+ * It may represent the X position of the center of the touch contact area,
+ * a relative horizontal displacement of a trackball or joystick, or something else.
+ *
+ * @see #getX(int)
+ * @see #getHistoricalX(int, int)
+ * @see MotionEvent.PointerCoords#x
+ * @see InputDevice#getMotionRange
*/
- static private final int SAMPLE_SIZE = 3;
-
- /*
- * Offset for the sample's touch major axis length.
+ public static final int AXIS_X = 0;
+
+ /**
+ * Constant used to identify the Y axis of a motion event.
+ *
+ * The interpretation of the Y axis varies by input source.
+ * It may represent the Y position of the center of the touch contact area,
+ * a relative vertical displacement of a trackball or joystick, or something else.
+ *
+ * @see #getY(int)
+ * @see #getHistoricalY(int, int)
+ * @see MotionEvent.PointerCoords#y
+ * @see InputDevice#getMotionRange
*/
- static private final int SAMPLE_TOUCH_MAJOR = 4;
+ public static final int AXIS_Y = 1;
- /*
- * Offset for the sample's touch minor axis length.
+ /**
+ * Constant used to identify the Pressure axis of a motion event.
+ *
+ * The pressure axis specifies a normalized value that describes the approximate
+ * pressure applied to the device by a finger or other tool.
+ * The pressure generally ranges from 0 (no pressure at all) to 1 (normal pressure),
+ * although values higher than 1 may be generated depending on the calibration of
+ * the input device.
+ *
+ * @see #getPressure(int)
+ * @see #getHistoricalPressure(int, int)
+ * @see MotionEvent.PointerCoords#pressure
+ * @see InputDevice#getMotionRange
*/
- static private final int SAMPLE_TOUCH_MINOR = 5;
-
- /*
- * Offset for the sample's tool major axis length.
+ public static final int AXIS_PRESSURE = 2;
+
+ /**
+ * Constant used to identify the Size axis of a motion event.
+ *
+ * The size axis specifies a normalized value that describes the approximate size
+ * of the pointer touch area in relation to the maximum detectable size for the device.
+ * It represents some approximation of the area of the screen being
+ * pressed; the actual value in pixels corresponding to the
+ * touch is normalized with the device specific range of values
+ * and scaled to a value between 0 and 1. The value of size can be used to
+ * determine fat touch events.
+ *
+ * To obtain calibrated size information in terms of pixels, use
+ * {@link #AXIS_TOUCH_MAJOR} or {@link #AXIS_TOOL_MAJOR} instead.
+ *
+ * @see #getSize(int)
+ * @see #getHistoricalSize(int, int)
+ * @see MotionEvent.PointerCoords#size
+ * @see InputDevice#getMotionRange
*/
- static private final int SAMPLE_TOOL_MAJOR = 6;
+ public static final int AXIS_SIZE = 3;
- /*
- * Offset for the sample's tool minor axis length.
+ /**
+ * Constant used to identify the TouchMajor axis of a motion event.
+ *
+ * The touch major axis specifies the length of the major axis of an ellipse that
+ * describes the touch area at the point of contact.
+ * If the device is a touch screen, the length is reported in pixels, otherwise it is
+ * reported in device-specific units.
+ *
+ * @see #getTouchMajor(int)
+ * @see #getHistoricalTouchMajor(int, int)
+ * @see MotionEvent.PointerCoords#touchMajor
+ * @see InputDevice#getMotionRange
*/
- static private final int SAMPLE_TOOL_MINOR = 7;
-
- /*
- * Offset for the sample's orientation.
+ public static final int AXIS_TOUCH_MAJOR = 4;
+
+ /**
+ * Constant used to identify the TouchMinor axis of a motion event.
+ *
+ * The touch major axis specifies the length of the minor axis of an ellipse that
+ * describes the touch area at the point of contact.
+ * If the device is a touch screen, the length is reported in pixels, otherwise it is
+ * reported in device-specific units.
+ *
+ * @see #getTouchMinor(int)
+ * @see #getHistoricalTouchMinor(int, int)
+ * @see MotionEvent.PointerCoords#touchMinor
+ * @see InputDevice#getMotionRange
*/
- static private final int SAMPLE_ORIENTATION = 8;
+ public static final int AXIS_TOUCH_MINOR = 5;
- /*
- * Number of data items for each sample.
+ /**
+ * Constant used to identify the ToolMajor axis of a motion event.
+ *
+ * The tool major axis specifies the length of the major axis of an ellipse that
+ * describes the size of the approaching tool.
+ * The tool area represents the estimated size of the finger or pen that is
+ * touching the device independent of its actual touch area at the point of contact.
+ * If the device is a touch screen, the length is reported in pixels, otherwise it is
+ * reported in device-specific units.
+ *
+ * @see #getToolMajor(int)
+ * @see #getHistoricalToolMajor(int, int)
+ * @see MotionEvent.PointerCoords#toolMajor
+ * @see InputDevice#getMotionRange
*/
- static private final int NUM_SAMPLE_DATA = 9;
-
- /*
- * Minimum number of pointers for which to reserve space when allocating new
- * motion events. This is explicitly not a bound on the maximum number of pointers.
+ public static final int AXIS_TOOL_MAJOR = 6;
+
+ /**
+ * Constant used to identify the ToolMinor axis of a motion event.
+ *
+ * The tool minor axis specifies the length of the major axis of an ellipse that
+ * describes the size of the approaching tool.
+ * The tool area represents the estimated size of the finger or pen that is
+ * touching the device independent of its actual touch area at the point of contact.
+ * If the device is a touch screen, the length is reported in pixels, otherwise it is
+ * reported in device-specific units.
+ *
+ * @see #getToolMinor(int)
+ * @see #getHistoricalToolMinor(int, int)
+ * @see MotionEvent.PointerCoords#toolMinor
+ * @see InputDevice#getMotionRange
*/
- static private final int BASE_AVAIL_POINTERS = 5;
-
- /*
- * Minimum number of samples for which to reserve space when allocating new motion events.
+ public static final int AXIS_TOOL_MINOR = 7;
+
+ /**
+ * Constant used to identify the Orientation axis of a motion event.
+ *
+ * The orientation axis specifies the orientation of the touch area and tool area in
+ * radians clockwise from vertical relative to the vertical plane of the device.
+ * An angle of 0 degrees indicates that the major axis of contact is oriented
+ * upwards, is perfectly circular or is of unknown orientation. A positive angle
+ * indicates that the major axis of contact is oriented to the right. A negative angle
+ * indicates that the major axis of contact is oriented to the left.
+ * The full range is from -PI/2 radians (finger pointing fully left) to PI/2 radians
+ * (finger pointing fully right).
+ *
+ * @see #getOrientation(int)
+ * @see #getHistoricalOrientation(int, int)
+ * @see MotionEvent.PointerCoords#orientation
+ * @see InputDevice#getMotionRange
*/
- static private final int BASE_AVAIL_SAMPLES = 8;
-
+ public static final int AXIS_ORIENTATION = 8;
+
+ // Private value for history pos that obtains the current sample.
+ private static final int HISTORY_CURRENT = -0x80000000;
+
private static final int MAX_RECYCLED = 10;
private static final Object gRecyclerLock = new Object();
private static int gRecyclerUsed;
private static MotionEvent gRecyclerTop;
- private long mDownTimeNano;
- private int mAction;
- private float mXOffset;
- private float mYOffset;
- private float mXPrecision;
- private float mYPrecision;
- private int mEdgeFlags;
- private int mMetaState;
- private int mFlags;
-
- private int mNumPointers;
- private int mNumSamples;
-
- private int mLastDataSampleIndex;
- private int mLastEventTimeNanoSampleIndex;
-
- // Array of mNumPointers size of identifiers for each pointer of data.
- private int[] mPointerIdentifiers;
-
- // Array of (mNumSamples * mNumPointers * NUM_SAMPLE_DATA) size of event data.
- // Samples are ordered from oldest to newest.
- private float[] mDataSamples;
-
- // Array of mNumSamples size of event time stamps in nanoseconds.
- // Samples are ordered from oldest to newest.
- private long[] mEventTimeNanoSamples;
+ // Shared temporary objects used when translating coordinates supplied by
+ // the caller into single element PointerCoords and pointer id arrays.
+ // Must lock gTmpPointerCoords prior to use.
+ private static final PointerCoords[] gTmpPointerCoords =
+ new PointerCoords[] { new PointerCoords() };
+ private static final int[] gTmpPointerIds = new int[] { 0 /*always 0*/ };
+
+ // Pointer to the native MotionEvent object that contains the actual data.
+ private int mNativePtr;
private MotionEvent mNext;
private RuntimeException mRecycledLocation;
private boolean mRecycled;
- private native void nativeTransform(Matrix matrix);
+ private static native int nativeInitialize(int nativePtr,
+ int deviceId, int source, int action, int flags, int edgeFlags, int metaState,
+ float xOffset, float yOffset, float xPrecision, float yPrecision,
+ long downTimeNanos, long eventTimeNanos,
+ int pointerCount, int[] pointerIds, PointerCoords[] pointerCoords);
+ private static native int nativeCopy(int destNativePtr, int sourceNativePtr,
+ boolean keepHistory);
+ private static native void nativeDispose(int nativePtr);
+ private static native void nativeAddBatch(int nativePtr, long eventTimeNanos,
+ PointerCoords[] pointerCoords, int metaState);
+
+ private static native int nativeGetDeviceId(int nativePtr);
+ private static native int nativeGetSource(int nativePtr);
+ private static native int nativeSetSource(int nativePtr, int source);
+ private static native int nativeGetAction(int nativePtr);
+ private static native void nativeSetAction(int nativePtr, int action);
+ private static native int nativeGetFlags(int nativePtr);
+ private static native int nativeGetEdgeFlags(int nativePtr);
+ private static native void nativeSetEdgeFlags(int nativePtr, int action);
+ private static native int nativeGetMetaState(int nativePtr);
+ private static native void nativeOffsetLocation(int nativePtr, float deltaX, float deltaY);
+ private static native float nativeGetXPrecision(int nativePtr);
+ private static native float nativeGetYPrecision(int nativePtr);
+ private static native long nativeGetDownTimeNanos(int nativePtr);
+
+ private static native int nativeGetPointerCount(int nativePtr);
+ private static native int nativeGetPointerId(int nativePtr, int pointerIndex);
+ private static native int nativeFindPointerIndex(int nativePtr, int pointerId);
+
+ private static native int nativeGetHistorySize(int nativePtr);
+ private static native long nativeGetEventTimeNanos(int nativePtr, int historyPos);
+ private static native float nativeGetRawAxisValue(int nativePtr,
+ int axis, int pointerIndex, int historyPos);
+ private static native float nativeGetAxisValue(int nativePtr,
+ int axis, int pointerIndex, int historyPos);
+ private static native void nativeGetPointerCoords(int nativePtr,
+ int pointerIndex, int historyPos, PointerCoords outPointerCoords);
+
+ private static native void nativeScale(int nativePtr, float scale);
+ private static native void nativeTransform(int nativePtr, Matrix matrix);
+
+ private static native int nativeReadFromParcel(int nativePtr, Parcel parcel);
+ private static native void nativeWriteToParcel(int nativePtr, Parcel parcel);
+
+ private MotionEvent() {
+ }
- private MotionEvent(int pointerCount, int sampleCount) {
- mPointerIdentifiers = new int[pointerCount];
- mDataSamples = new float[pointerCount * sampleCount * NUM_SAMPLE_DATA];
- mEventTimeNanoSamples = new long[sampleCount];
+ @Override
+ protected void finalize() throws Throwable {
+ try {
+ if (mNativePtr != 0) {
+ nativeDispose(mNativePtr);
+ mNativePtr = 0;
+ }
+ } finally {
+ super.finalize();
+ }
}
- static private MotionEvent obtain(int pointerCount, int sampleCount) {
+ static private MotionEvent obtain() {
final MotionEvent ev;
synchronized (gRecyclerLock) {
ev = gRecyclerTop;
if (ev == null) {
- if (pointerCount < BASE_AVAIL_POINTERS) {
- pointerCount = BASE_AVAIL_POINTERS;
- }
- if (sampleCount < BASE_AVAIL_SAMPLES) {
- sampleCount = BASE_AVAIL_SAMPLES;
- }
- return new MotionEvent(pointerCount, sampleCount);
+ return new MotionEvent();
}
gRecyclerTop = ev.mNext;
gRecyclerUsed -= 1;
@@ -385,23 +503,9 @@ public final class MotionEvent extends InputEvent implements Parcelable {
ev.mRecycledLocation = null;
ev.mRecycled = false;
ev.mNext = null;
-
- if (ev.mPointerIdentifiers.length < pointerCount) {
- ev.mPointerIdentifiers = new int[pointerCount];
- }
-
- if (ev.mEventTimeNanoSamples.length < sampleCount) {
- ev.mEventTimeNanoSamples = new long[sampleCount];
- }
-
- final int neededDataSamplesLength = pointerCount * sampleCount * NUM_SAMPLE_DATA;
- if (ev.mDataSamples.length < neededDataSamplesLength) {
- ev.mDataSamples = new float[neededDataSamplesLength];
- }
-
return ev;
}
-
+
/**
* Create a new MotionEvent, filling in all of the basic values that
* define the motion.
@@ -434,34 +538,15 @@ public final class MotionEvent extends InputEvent implements Parcelable {
int action, int pointers, int[] pointerIds, PointerCoords[] pointerCoords,
int metaState, float xPrecision, float yPrecision, int deviceId,
int edgeFlags, int source, int flags) {
- MotionEvent ev = obtain(pointers, 1);
- ev.mDeviceId = deviceId;
- ev.mSource = source;
- ev.mEdgeFlags = edgeFlags;
- ev.mDownTimeNano = downTime * MS_PER_NS;
- ev.mAction = action;
- ev.mFlags = flags;
- ev.mMetaState = metaState;
- ev.mXOffset = 0;
- ev.mYOffset = 0;
- ev.mXPrecision = xPrecision;
- ev.mYPrecision = yPrecision;
-
- ev.mNumPointers = pointers;
- ev.mNumSamples = 1;
-
- ev.mLastDataSampleIndex = 0;
- ev.mLastEventTimeNanoSampleIndex = 0;
-
- System.arraycopy(pointerIds, 0, ev.mPointerIdentifiers, 0, pointers);
-
- ev.mEventTimeNanoSamples[0] = eventTime * MS_PER_NS;
-
- ev.setPointerCoordsAtSampleIndex(0, pointerCoords);
-
+ MotionEvent ev = obtain();
+ ev.mNativePtr = nativeInitialize(ev.mNativePtr,
+ deviceId, source, action, flags, edgeFlags, metaState,
+ 0, 0, xPrecision, yPrecision,
+ downTime * NS_PER_MS, eventTime * NS_PER_MS,
+ pointers, pointerIds, pointerCoords);
return ev;
}
-
+
/**
* Create a new MotionEvent, filling in all of the basic values that
* define the motion.
@@ -496,31 +581,22 @@ public final class MotionEvent extends InputEvent implements Parcelable {
static public MotionEvent obtain(long downTime, long eventTime, int action,
float x, float y, float pressure, float size, int metaState,
float xPrecision, float yPrecision, int deviceId, int edgeFlags) {
- MotionEvent ev = obtain(1, 1);
- ev.mDeviceId = deviceId;
- ev.mSource = InputDevice.SOURCE_UNKNOWN;
- ev.mEdgeFlags = edgeFlags;
- ev.mDownTimeNano = downTime * MS_PER_NS;
- ev.mAction = action;
- ev.mFlags = 0;
- ev.mMetaState = metaState;
- ev.mXOffset = 0;
- ev.mYOffset = 0;
- ev.mXPrecision = xPrecision;
- ev.mYPrecision = yPrecision;
-
- ev.mNumPointers = 1;
- ev.mNumSamples = 1;
-
- ev.mLastDataSampleIndex = 0;
- ev.mLastEventTimeNanoSampleIndex = 0;
-
- ev.mPointerIdentifiers[0] = 0;
-
- ev.mEventTimeNanoSamples[0] = eventTime * MS_PER_NS;
-
- ev.setPointerCoordsAtSampleIndex(0, x, y, pressure, size);
- return ev;
+ synchronized (gTmpPointerCoords) {
+ final PointerCoords pc = gTmpPointerCoords[0];
+ pc.clear();
+ pc.x = x;
+ pc.y = y;
+ pc.pressure = pressure;
+ pc.size = size;
+
+ MotionEvent ev = obtain();
+ ev.mNativePtr = nativeInitialize(ev.mNativePtr,
+ deviceId, InputDevice.SOURCE_UNKNOWN, action, 0, edgeFlags, metaState,
+ 0, 0, xPrecision, yPrecision,
+ downTime * NS_PER_MS, eventTime * NS_PER_MS,
+ 1, gTmpPointerIds, gTmpPointerCoords);
+ return ev;
+ }
}
/**
@@ -592,31 +668,13 @@ public final class MotionEvent extends InputEvent implements Parcelable {
/**
* Create a new MotionEvent, copying from an existing one.
*/
- static public MotionEvent obtain(MotionEvent o) {
- MotionEvent ev = obtain(o.mNumPointers, o.mNumSamples);
- ev.mDeviceId = o.mDeviceId;
- ev.mSource = o.mSource;
- ev.mEdgeFlags = o.mEdgeFlags;
- ev.mDownTimeNano = o.mDownTimeNano;
- ev.mAction = o.mAction;
- ev.mFlags = o.mFlags;
- ev.mMetaState = o.mMetaState;
- ev.mXOffset = o.mXOffset;
- ev.mYOffset = o.mYOffset;
- ev.mXPrecision = o.mXPrecision;
- ev.mYPrecision = o.mYPrecision;
- int numPointers = ev.mNumPointers = o.mNumPointers;
- int numSamples = ev.mNumSamples = o.mNumSamples;
-
- ev.mLastDataSampleIndex = o.mLastDataSampleIndex;
- ev.mLastEventTimeNanoSampleIndex = o.mLastEventTimeNanoSampleIndex;
-
- System.arraycopy(o.mPointerIdentifiers, 0, ev.mPointerIdentifiers, 0, numPointers);
-
- System.arraycopy(o.mEventTimeNanoSamples, 0, ev.mEventTimeNanoSamples, 0, numSamples);
-
- System.arraycopy(o.mDataSamples, 0, ev.mDataSamples, 0,
- numPointers * numSamples * NUM_SAMPLE_DATA);
+ static public MotionEvent obtain(MotionEvent other) {
+ if (other == null) {
+ throw new IllegalArgumentException("other motion event must not be null");
+ }
+
+ MotionEvent ev = obtain();
+ ev.mNativePtr = nativeCopy(ev.mNativePtr, other.mNativePtr, true /*keepHistory*/);
return ev;
}
@@ -624,32 +682,13 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* Create a new MotionEvent, copying from an existing one, but not including
* any historical point information.
*/
- static public MotionEvent obtainNoHistory(MotionEvent o) {
- MotionEvent ev = obtain(o.mNumPointers, 1);
- ev.mDeviceId = o.mDeviceId;
- ev.mSource = o.mSource;
- ev.mEdgeFlags = o.mEdgeFlags;
- ev.mDownTimeNano = o.mDownTimeNano;
- ev.mAction = o.mAction;
- o.mFlags = o.mFlags;
- ev.mMetaState = o.mMetaState;
- ev.mXOffset = o.mXOffset;
- ev.mYOffset = o.mYOffset;
- ev.mXPrecision = o.mXPrecision;
- ev.mYPrecision = o.mYPrecision;
-
- int numPointers = ev.mNumPointers = o.mNumPointers;
- ev.mNumSamples = 1;
-
- ev.mLastDataSampleIndex = 0;
- ev.mLastEventTimeNanoSampleIndex = 0;
-
- System.arraycopy(o.mPointerIdentifiers, 0, ev.mPointerIdentifiers, 0, numPointers);
-
- ev.mEventTimeNanoSamples[0] = o.mEventTimeNanoSamples[o.mLastEventTimeNanoSampleIndex];
-
- System.arraycopy(o.mDataSamples, o.mLastDataSampleIndex, ev.mDataSamples, 0,
- numPointers * NUM_SAMPLE_DATA);
+ static public MotionEvent obtainNoHistory(MotionEvent other) {
+ if (other == null) {
+ throw new IllegalArgumentException("other motion event must not be null");
+ }
+
+ MotionEvent ev = obtain();
+ ev.mNativePtr = nativeCopy(ev.mNativePtr, other.mNativePtr, false /*keepHistory*/);
return ev;
}
@@ -675,7 +714,6 @@ public final class MotionEvent extends InputEvent implements Parcelable {
synchronized (gRecyclerLock) {
if (gRecyclerUsed < MAX_RECYCLED) {
gRecyclerUsed++;
- mNumSamples = 0;
mNext = gRecyclerTop;
gRecyclerTop = this;
}
@@ -688,23 +726,25 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @hide
*/
public final void scale(float scale) {
- mXOffset *= scale;
- mYOffset *= scale;
- mXPrecision *= scale;
- mYPrecision *= scale;
-
- float[] history = mDataSamples;
- final int length = mNumPointers * mNumSamples * NUM_SAMPLE_DATA;
- for (int i = 0; i < length; i += NUM_SAMPLE_DATA) {
- history[i + SAMPLE_X] *= scale;
- history[i + SAMPLE_Y] *= scale;
- // no need to scale pressure
- history[i + SAMPLE_SIZE] *= scale; // TODO: square this?
- history[i + SAMPLE_TOUCH_MAJOR] *= scale;
- history[i + SAMPLE_TOUCH_MINOR] *= scale;
- history[i + SAMPLE_TOOL_MAJOR] *= scale;
- history[i + SAMPLE_TOOL_MINOR] *= scale;
- }
+ nativeScale(mNativePtr, scale);
+ }
+
+ /** {@inheritDoc} */
+ @Override
+ public final int getDeviceId() {
+ return nativeGetDeviceId(mNativePtr);
+ }
+
+ /** {@inheritDoc} */
+ @Override
+ public final int getSource() {
+ return nativeGetSource(mNativePtr);
+ }
+
+ /** {@inheritDoc} */
+ @Override
+ public final void setSource(int source) {
+ nativeSetSource(mNativePtr, source);
}
/**
@@ -715,7 +755,7 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* and pointer index.
*/
public final int getAction() {
- return mAction;
+ return nativeGetAction(mNativePtr);
}
/**
@@ -727,7 +767,7 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* pointer actions.
*/
public final int getActionMasked() {
- return mAction & ACTION_MASK;
+ return nativeGetAction(mNativePtr) & ACTION_MASK;
}
/**
@@ -739,7 +779,8 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* gone down or up.
*/
public final int getActionIndex() {
- return (mAction & ACTION_POINTER_INDEX_MASK) >> ACTION_POINTER_INDEX_SHIFT;
+ return (nativeGetAction(mNativePtr) & ACTION_POINTER_INDEX_MASK)
+ >> ACTION_POINTER_INDEX_SHIFT;
}
/**
@@ -748,7 +789,7 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @see #FLAG_WINDOW_IS_OBSCURED
*/
public final int getFlags() {
- return mFlags;
+ return nativeGetFlags(mNativePtr);
}
/**
@@ -756,14 +797,14 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* a stream of position events.
*/
public final long getDownTime() {
- return mDownTimeNano / MS_PER_NS;
+ return nativeGetDownTimeNanos(mNativePtr) / NS_PER_MS;
}
/**
* Returns the time (in ms) when this specific event was generated.
*/
public final long getEventTime() {
- return mEventTimeNanoSamples[mLastEventTimeNanoSampleIndex] / MS_PER_NS;
+ return nativeGetEventTimeNanos(mNativePtr, HISTORY_CURRENT) / NS_PER_MS;
}
/**
@@ -773,79 +814,110 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @hide
*/
public final long getEventTimeNano() {
- return mEventTimeNanoSamples[mLastEventTimeNanoSampleIndex];
+ return nativeGetEventTimeNanos(mNativePtr, HISTORY_CURRENT);
}
/**
* {@link #getX(int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @see #AXIS_X
*/
public final float getX() {
- return mDataSamples[mLastDataSampleIndex + SAMPLE_X] + mXOffset;
+ return nativeGetAxisValue(mNativePtr, AXIS_X, 0, HISTORY_CURRENT);
}
/**
* {@link #getY(int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @see #AXIS_Y
*/
public final float getY() {
- return mDataSamples[mLastDataSampleIndex + SAMPLE_Y] + mYOffset;
+ return nativeGetAxisValue(mNativePtr, AXIS_Y, 0, HISTORY_CURRENT);
}
/**
* {@link #getPressure(int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @see #AXIS_PRESSURE
*/
public final float getPressure() {
- return mDataSamples[mLastDataSampleIndex + SAMPLE_PRESSURE];
+ return nativeGetAxisValue(mNativePtr, AXIS_PRESSURE, 0, HISTORY_CURRENT);
}
/**
* {@link #getSize(int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @see #AXIS_SIZE
*/
public final float getSize() {
- return mDataSamples[mLastDataSampleIndex + SAMPLE_SIZE];
+ return nativeGetAxisValue(mNativePtr, AXIS_SIZE, 0, HISTORY_CURRENT);
}
/**
* {@link #getTouchMajor(int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @see #AXIS_TOUCH_MAJOR
*/
public final float getTouchMajor() {
- return mDataSamples[mLastDataSampleIndex + SAMPLE_TOUCH_MAJOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOUCH_MAJOR, 0, HISTORY_CURRENT);
}
/**
* {@link #getTouchMinor(int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @see #AXIS_TOUCH_MINOR
*/
public final float getTouchMinor() {
- return mDataSamples[mLastDataSampleIndex + SAMPLE_TOUCH_MINOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOUCH_MINOR, 0, HISTORY_CURRENT);
}
/**
* {@link #getToolMajor(int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @see #AXIS_TOOL_MAJOR
*/
public final float getToolMajor() {
- return mDataSamples[mLastDataSampleIndex + SAMPLE_TOOL_MAJOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOOL_MAJOR, 0, HISTORY_CURRENT);
}
/**
* {@link #getToolMinor(int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @see #AXIS_TOOL_MINOR
*/
public final float getToolMinor() {
- return mDataSamples[mLastDataSampleIndex + SAMPLE_TOOL_MINOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOOL_MINOR, 0, HISTORY_CURRENT);
}
-
+
/**
* {@link #getOrientation(int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @see #AXIS_ORIENTATION
*/
public final float getOrientation() {
- return mDataSamples[mLastDataSampleIndex + SAMPLE_ORIENTATION];
+ return nativeGetAxisValue(mNativePtr, AXIS_ORIENTATION, 0, HISTORY_CURRENT);
+ }
+
+ /**
+ * {@link #getAxisValue(int)} for the first pointer index (may be an
+ * arbitrary pointer identifier).
+ *
+ * @param axis The axis identifier for the axis value to retrieve.
+ *
+ * @see #AXIS_X
+ * @see #AXIS_Y
+ */
+ public final float getAxisValue(int axis) {
+ return nativeGetAxisValue(mNativePtr, axis, 0, HISTORY_CURRENT);
}
/**
@@ -853,7 +925,7 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* >= 1.
*/
public final int getPointerCount() {
- return mNumPointers;
+ return nativeGetPointerCount(mNativePtr);
}
/**
@@ -865,7 +937,7 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* (the first pointer that is down) to {@link #getPointerCount()}-1.
*/
public final int getPointerId(int pointerIndex) {
- return mPointerIdentifiers[pointerIndex];
+ return nativeGetPointerId(mNativePtr, pointerIndex);
}
/**
@@ -877,14 +949,7 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* that pointer identifier.
*/
public final int findPointerIndex(int pointerId) {
- int i = mNumPointers;
- while (i > 0) {
- i--;
- if (mPointerIdentifiers[i] == pointerId) {
- return i;
- }
- }
- return -1;
+ return nativeFindPointerIndex(mNativePtr, pointerId);
}
/**
@@ -895,10 +960,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* value may have a fraction for input devices that are sub-pixel precise.
* @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
* (the first pointer that is down) to {@link #getPointerCount()}-1.
+ *
+ * @see #AXIS_X
*/
public final float getX(int pointerIndex) {
- return mDataSamples[mLastDataSampleIndex
- + pointerIndex * NUM_SAMPLE_DATA + SAMPLE_X] + mXOffset;
+ return nativeGetAxisValue(mNativePtr, AXIS_X, pointerIndex, HISTORY_CURRENT);
}
/**
@@ -909,10 +975,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* value may have a fraction for input devices that are sub-pixel precise.
* @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
* (the first pointer that is down) to {@link #getPointerCount()}-1.
+ *
+ * @see #AXIS_Y
*/
public final float getY(int pointerIndex) {
- return mDataSamples[mLastDataSampleIndex
- + pointerIndex * NUM_SAMPLE_DATA + SAMPLE_Y] + mYOffset;
+ return nativeGetAxisValue(mNativePtr, AXIS_Y, pointerIndex, HISTORY_CURRENT);
}
/**
@@ -925,10 +992,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* the input device.
* @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
* (the first pointer that is down) to {@link #getPointerCount()}-1.
+ *
+ * @see #AXIS_PRESSURE
*/
public final float getPressure(int pointerIndex) {
- return mDataSamples[mLastDataSampleIndex
- + pointerIndex * NUM_SAMPLE_DATA + SAMPLE_PRESSURE];
+ return nativeGetAxisValue(mNativePtr, AXIS_PRESSURE, pointerIndex, HISTORY_CURRENT);
}
/**
@@ -942,10 +1010,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* determine fat touch events.
* @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
* (the first pointer that is down) to {@link #getPointerCount()}-1.
+ *
+ * @see #AXIS_SIZE
*/
public final float getSize(int pointerIndex) {
- return mDataSamples[mLastDataSampleIndex
- + pointerIndex * NUM_SAMPLE_DATA + SAMPLE_SIZE];
+ return nativeGetAxisValue(mNativePtr, AXIS_SIZE, pointerIndex, HISTORY_CURRENT);
}
/**
@@ -955,10 +1024,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* identifier for this index).
* @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
* (the first pointer that is down) to {@link #getPointerCount()}-1.
+ *
+ * @see #AXIS_TOUCH_MAJOR
*/
public final float getTouchMajor(int pointerIndex) {
- return mDataSamples[mLastDataSampleIndex
- + pointerIndex * NUM_SAMPLE_DATA + SAMPLE_TOUCH_MAJOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOUCH_MAJOR, pointerIndex, HISTORY_CURRENT);
}
/**
@@ -968,10 +1038,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* identifier for this index).
* @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
* (the first pointer that is down) to {@link #getPointerCount()}-1.
+ *
+ * @see #AXIS_TOUCH_MINOR
*/
public final float getTouchMinor(int pointerIndex) {
- return mDataSamples[mLastDataSampleIndex
- + pointerIndex * NUM_SAMPLE_DATA + SAMPLE_TOUCH_MINOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOUCH_MINOR, pointerIndex, HISTORY_CURRENT);
}
/**
@@ -983,10 +1054,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* touching the device independent of its actual touch area at the point of contact.
* @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
* (the first pointer that is down) to {@link #getPointerCount()}-1.
+ *
+ * @see #AXIS_TOOL_MAJOR
*/
public final float getToolMajor(int pointerIndex) {
- return mDataSamples[mLastDataSampleIndex
- + pointerIndex * NUM_SAMPLE_DATA + SAMPLE_TOOL_MAJOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOOL_MAJOR, pointerIndex, HISTORY_CURRENT);
}
/**
@@ -998,10 +1070,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* touching the device independent of its actual touch area at the point of contact.
* @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
* (the first pointer that is down) to {@link #getPointerCount()}-1.
+ *
+ * @see #AXIS_TOOL_MINOR
*/
public final float getToolMinor(int pointerIndex) {
- return mDataSamples[mLastDataSampleIndex
- + pointerIndex * NUM_SAMPLE_DATA + SAMPLE_TOOL_MINOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOOL_MINOR, pointerIndex, HISTORY_CURRENT);
}
/**
@@ -1016,12 +1089,29 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* (finger pointing fully right).
* @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
* (the first pointer that is down) to {@link #getPointerCount()}-1.
+ *
+ * @see #AXIS_ORIENTATION
*/
public final float getOrientation(int pointerIndex) {
- return mDataSamples[mLastDataSampleIndex
- + pointerIndex * NUM_SAMPLE_DATA + SAMPLE_ORIENTATION];
+ return nativeGetAxisValue(mNativePtr, AXIS_ORIENTATION, pointerIndex, HISTORY_CURRENT);
}
-
+
+ /**
+ * Returns the value of the requested axis for the given pointer <em>index</em>
+ * (use {@link #getPointerId(int)} to find the pointer identifier for this index).
+ *
+ * @param axis The axis identifier for the axis value to retrieve.
+ * @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
+ * (the first pointer that is down) to {@link #getPointerCount()}-1.
+ * @return The value of the axis, or 0 if the axis is not available.
+ *
+ * @see #AXIS_X
+ * @see #AXIS_Y
+ */
+ public final float getAxisValue(int axis, int pointerIndex) {
+ return nativeGetAxisValue(mNativePtr, axis, pointerIndex, HISTORY_CURRENT);
+ }
+
/**
* Populates a {@link PointerCoords} object with pointer coordinate data for
* the specified pointer index.
@@ -1029,10 +1119,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
* (the first pointer that is down) to {@link #getPointerCount()}-1.
* @param outPointerCoords The pointer coordinate object to populate.
+ *
+ * @see PointerCoords
*/
public final void getPointerCoords(int pointerIndex, PointerCoords outPointerCoords) {
- final int sampleIndex = mLastDataSampleIndex + pointerIndex * NUM_SAMPLE_DATA;
- getPointerCoordsAtSampleIndex(sampleIndex, outPointerCoords);
+ nativeGetPointerCoords(mNativePtr, pointerIndex, HISTORY_CURRENT, outPointerCoords);
}
/**
@@ -1046,7 +1137,7 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @see KeyEvent#getMetaState()
*/
public final int getMetaState() {
- return mMetaState;
+ return nativeGetMetaState(mNativePtr);
}
/**
@@ -1054,39 +1145,49 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* events on the screen, this is the original location of the event
* on the screen, before it had been adjusted for the containing window
* and views.
+ *
+ * @see getX()
+ * @see #AXIS_X
*/
public final float getRawX() {
- return mDataSamples[mLastDataSampleIndex + SAMPLE_X];
+ return nativeGetRawAxisValue(mNativePtr, AXIS_X, 0, HISTORY_CURRENT);
}
-
+
/**
* Returns the original raw Y coordinate of this event. For touch
* events on the screen, this is the original location of the event
* on the screen, before it had been adjusted for the containing window
* and views.
+ *
+ * @see getY()
+ * @see #AXIS_Y
*/
public final float getRawY() {
- return mDataSamples[mLastDataSampleIndex + SAMPLE_Y];
+ return nativeGetRawAxisValue(mNativePtr, AXIS_Y, 0, HISTORY_CURRENT);
}
/**
* Return the precision of the X coordinates being reported. You can
- * multiple this number with {@link #getX} to find the actual hardware
+ * multiply this number with {@link #getX} to find the actual hardware
* value of the X coordinate.
* @return Returns the precision of X coordinates being reported.
+ *
+ * @see #AXIS_X
*/
public final float getXPrecision() {
- return mXPrecision;
+ return nativeGetXPrecision(mNativePtr);
}
/**
* Return the precision of the Y coordinates being reported. You can
- * multiple this number with {@link #getY} to find the actual hardware
+ * multiply this number with {@link #getY} to find the actual hardware
* value of the Y coordinate.
* @return Returns the precision of Y coordinates being reported.
+ *
+ * @see #AXIS_Y
*/
public final float getYPrecision() {
- return mYPrecision;
+ return nativeGetYPrecision(mNativePtr);
}
/**
@@ -1098,7 +1199,7 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @return Returns the number of historical points in the event.
*/
public final int getHistorySize() {
- return mLastEventTimeNanoSampleIndex;
+ return nativeGetHistorySize(mNativePtr);
}
/**
@@ -1112,81 +1213,161 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @see #getEventTime
*/
public final long getHistoricalEventTime(int pos) {
- return mEventTimeNanoSamples[pos] / MS_PER_NS;
+ return nativeGetEventTimeNanos(mNativePtr, pos) / NS_PER_MS;
}
/**
- * {@link #getHistoricalX(int)} for the first pointer index (may be an
+ * {@link #getHistoricalX(int, int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @param pos Which historical value to return; must be less than
+ * {@link #getHistorySize}
+ *
+ * @see #getHistorySize
+ * @see #getX()
+ * @see #AXIS_X
*/
public final float getHistoricalX(int pos) {
- return mDataSamples[pos * mNumPointers * NUM_SAMPLE_DATA + SAMPLE_X] + mXOffset;
+ return nativeGetAxisValue(mNativePtr, AXIS_X, 0, pos);
}
/**
- * {@link #getHistoricalY(int)} for the first pointer index (may be an
+ * {@link #getHistoricalY(int, int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @param pos Which historical value to return; must be less than
+ * {@link #getHistorySize}
+ *
+ * @see #getHistorySize
+ * @see #getY()
+ * @see #AXIS_Y
*/
public final float getHistoricalY(int pos) {
- return mDataSamples[pos * mNumPointers * NUM_SAMPLE_DATA + SAMPLE_Y] + mYOffset;
+ return nativeGetAxisValue(mNativePtr, AXIS_Y, 0, pos);
}
/**
- * {@link #getHistoricalPressure(int)} for the first pointer index (may be an
+ * {@link #getHistoricalPressure(int, int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @param pos Which historical value to return; must be less than
+ * {@link #getHistorySize}
+ *
+ * @see #getHistorySize
+ * @see #getPressure()
+ * @see #AXIS_PRESSURE
*/
public final float getHistoricalPressure(int pos) {
- return mDataSamples[pos * mNumPointers * NUM_SAMPLE_DATA + SAMPLE_PRESSURE];
+ return nativeGetAxisValue(mNativePtr, AXIS_PRESSURE, 0, pos);
}
/**
- * {@link #getHistoricalSize(int)} for the first pointer index (may be an
+ * {@link #getHistoricalSize(int, int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @param pos Which historical value to return; must be less than
+ * {@link #getHistorySize}
+ *
+ * @see #getHistorySize
+ * @see #getSize()
+ * @see #AXIS_SIZE
*/
public final float getHistoricalSize(int pos) {
- return mDataSamples[pos * mNumPointers * NUM_SAMPLE_DATA + SAMPLE_SIZE];
+ return nativeGetAxisValue(mNativePtr, AXIS_SIZE, 0, pos);
}
/**
- * {@link #getHistoricalTouchMajor(int)} for the first pointer index (may be an
+ * {@link #getHistoricalTouchMajor(int, int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @param pos Which historical value to return; must be less than
+ * {@link #getHistorySize}
+ *
+ * @see #getHistorySize
+ * @see #getTouchMajor()
+ * @see #AXIS_TOUCH_MAJOR
*/
public final float getHistoricalTouchMajor(int pos) {
- return mDataSamples[pos * mNumPointers * NUM_SAMPLE_DATA + SAMPLE_TOUCH_MAJOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOUCH_MAJOR, 0, pos);
}
/**
- * {@link #getHistoricalTouchMinor(int)} for the first pointer index (may be an
+ * {@link #getHistoricalTouchMinor(int, int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @param pos Which historical value to return; must be less than
+ * {@link #getHistorySize}
+ *
+ * @see #getHistorySize
+ * @see #getTouchMinor()
+ * @see #AXIS_TOUCH_MINOR
*/
public final float getHistoricalTouchMinor(int pos) {
- return mDataSamples[pos * mNumPointers * NUM_SAMPLE_DATA + SAMPLE_TOUCH_MINOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOUCH_MINOR, 0, pos);
}
/**
- * {@link #getHistoricalToolMajor(int)} for the first pointer index (may be an
+ * {@link #getHistoricalToolMajor(int, int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @param pos Which historical value to return; must be less than
+ * {@link #getHistorySize}
+ *
+ * @see #getHistorySize
+ * @see #getToolMajor()
+ * @see #AXIS_TOOL_MAJOR
*/
public final float getHistoricalToolMajor(int pos) {
- return mDataSamples[pos * mNumPointers * NUM_SAMPLE_DATA + SAMPLE_TOOL_MAJOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOOL_MAJOR, 0, pos);
}
/**
- * {@link #getHistoricalToolMinor(int)} for the first pointer index (may be an
+ * {@link #getHistoricalToolMinor(int, int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @param pos Which historical value to return; must be less than
+ * {@link #getHistorySize}
+ *
+ * @see #getHistorySize
+ * @see #getToolMinor()
+ * @see #AXIS_TOOL_MINOR
*/
public final float getHistoricalToolMinor(int pos) {
- return mDataSamples[pos * mNumPointers * NUM_SAMPLE_DATA + SAMPLE_TOOL_MINOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOOL_MINOR, 0, pos);
}
/**
- * {@link #getHistoricalOrientation(int)} for the first pointer index (may be an
+ * {@link #getHistoricalOrientation(int, int)} for the first pointer index (may be an
* arbitrary pointer identifier).
+ *
+ * @param pos Which historical value to return; must be less than
+ * {@link #getHistorySize}
+ *
+ * @see #getHistorySize
+ * @see #getOrientation()
+ * @see #AXIS_ORIENTATION
*/
public final float getHistoricalOrientation(int pos) {
- return mDataSamples[pos * mNumPointers * NUM_SAMPLE_DATA + SAMPLE_ORIENTATION];
+ return nativeGetAxisValue(mNativePtr, AXIS_ORIENTATION, 0, pos);
}
-
+
+ /**
+ * {@link #getHistoricalAxisValue(int, int, int)} for the first pointer index (may be an
+ * arbitrary pointer identifier).
+ *
+ * @param axis The axis identifier for the axis value to retrieve.
+ * @param pos Which historical value to return; must be less than
+ * {@link #getHistorySize}
+ *
+ * @see #getHistorySize
+ * @see #getAxisValue(int)
+ * @see #AXIS_X
+ * @see #AXIS_Y
+ */
+ public final float getHistoricalAxisValue(int axis, int pos) {
+ return nativeGetAxisValue(mNativePtr, axis, 0, pos);
+ }
+
/**
* Returns a historical X coordinate, as per {@link #getX(int)}, that
* occurred between this event and the previous event for the given pointer.
@@ -1198,11 +1379,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* {@link #getHistorySize}
*
* @see #getHistorySize
- * @see #getX
+ * @see #getX(int)
+ * @see #AXIS_X
*/
public final float getHistoricalX(int pointerIndex, int pos) {
- return mDataSamples[(pos * mNumPointers + pointerIndex)
- * NUM_SAMPLE_DATA + SAMPLE_X] + mXOffset;
+ return nativeGetAxisValue(mNativePtr, AXIS_X, pointerIndex, pos);
}
/**
@@ -1216,11 +1397,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* {@link #getHistorySize}
*
* @see #getHistorySize
- * @see #getY
+ * @see #getY(int)
+ * @see #AXIS_Y
*/
public final float getHistoricalY(int pointerIndex, int pos) {
- return mDataSamples[(pos * mNumPointers + pointerIndex)
- * NUM_SAMPLE_DATA + SAMPLE_Y] + mYOffset;
+ return nativeGetAxisValue(mNativePtr, AXIS_Y, pointerIndex, pos);
}
/**
@@ -1234,11 +1415,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* {@link #getHistorySize}
*
* @see #getHistorySize
- * @see #getPressure
+ * @see #getPressure(int)
+ * @see #AXIS_PRESSURE
*/
public final float getHistoricalPressure(int pointerIndex, int pos) {
- return mDataSamples[(pos * mNumPointers + pointerIndex)
- * NUM_SAMPLE_DATA + SAMPLE_PRESSURE];
+ return nativeGetAxisValue(mNativePtr, AXIS_PRESSURE, pointerIndex, pos);
}
/**
@@ -1252,11 +1433,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* {@link #getHistorySize}
*
* @see #getHistorySize
- * @see #getSize
+ * @see #getSize(int)
+ * @see #AXIS_SIZE
*/
public final float getHistoricalSize(int pointerIndex, int pos) {
- return mDataSamples[(pos * mNumPointers + pointerIndex)
- * NUM_SAMPLE_DATA + SAMPLE_SIZE];
+ return nativeGetAxisValue(mNativePtr, AXIS_SIZE, pointerIndex, pos);
}
/**
@@ -1270,11 +1451,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* {@link #getHistorySize}
*
* @see #getHistorySize
- * @see #getTouchMajor
+ * @see #getTouchMajor(int)
+ * @see #AXIS_TOUCH_MAJOR
*/
public final float getHistoricalTouchMajor(int pointerIndex, int pos) {
- return mDataSamples[(pos * mNumPointers + pointerIndex)
- * NUM_SAMPLE_DATA + SAMPLE_TOUCH_MAJOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOUCH_MAJOR, pointerIndex, pos);
}
/**
@@ -1288,11 +1469,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* {@link #getHistorySize}
*
* @see #getHistorySize
- * @see #getTouchMinor
+ * @see #getTouchMinor(int)
+ * @see #AXIS_TOUCH_MINOR
*/
public final float getHistoricalTouchMinor(int pointerIndex, int pos) {
- return mDataSamples[(pos * mNumPointers + pointerIndex)
- * NUM_SAMPLE_DATA + SAMPLE_TOUCH_MINOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOUCH_MINOR, pointerIndex, pos);
}
/**
@@ -1306,11 +1487,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* {@link #getHistorySize}
*
* @see #getHistorySize
- * @see #getToolMajor
+ * @see #getToolMajor(int)
+ * @see #AXIS_TOOL_MAJOR
*/
public final float getHistoricalToolMajor(int pointerIndex, int pos) {
- return mDataSamples[(pos * mNumPointers + pointerIndex)
- * NUM_SAMPLE_DATA + SAMPLE_TOOL_MAJOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOOL_MAJOR, pointerIndex, pos);
}
/**
@@ -1324,11 +1505,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* {@link #getHistorySize}
*
* @see #getHistorySize
- * @see #getToolMinor
+ * @see #getToolMinor(int)
+ * @see #AXIS_TOOL_MINOR
*/
public final float getHistoricalToolMinor(int pointerIndex, int pos) {
- return mDataSamples[(pos * mNumPointers + pointerIndex)
- * NUM_SAMPLE_DATA + SAMPLE_TOOL_MINOR];
+ return nativeGetAxisValue(mNativePtr, AXIS_TOOL_MINOR, pointerIndex, pos);
}
/**
@@ -1342,11 +1523,30 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* {@link #getHistorySize}
*
* @see #getHistorySize
- * @see #getOrientation
+ * @see #getOrientation(int)
+ * @see #AXIS_ORIENTATION
*/
public final float getHistoricalOrientation(int pointerIndex, int pos) {
- return mDataSamples[(pos * mNumPointers + pointerIndex)
- * NUM_SAMPLE_DATA + SAMPLE_ORIENTATION];
+ return nativeGetAxisValue(mNativePtr, AXIS_ORIENTATION, pointerIndex, pos);
+ }
+
+ /**
+ * Returns the historical value of the requested axis, as per {@link #getAxisValue(int, int)},
+ * occurred between this event and the previous event for the given pointer.
+ * Only applies to ACTION_MOVE events.
+ *
+ * @param axis The axis identifier for the axis value to retrieve.
+ * @param pointerIndex Raw index of pointer to retrieve. Value may be from 0
+ * (the first pointer that is down) to {@link #getPointerCount()}-1.
+ * @param pos Which historical value to return; must be less than
+ * {@link #getHistorySize}
+ * @return The value of the axis, or 0 if the axis is not available.
+ *
+ * @see #AXIS_X
+ * @see #AXIS_Y
+ */
+ public final float getHistoricalAxisValue(int axis, int pointerIndex, int pos) {
+ return nativeGetAxisValue(mNativePtr, axis, pointerIndex, pos);
}
/**
@@ -1363,11 +1563,11 @@ public final class MotionEvent extends InputEvent implements Parcelable {
*
* @see #getHistorySize
* @see #getPointerCoords
+ * @see PointerCoords
*/
public final void getHistoricalPointerCoords(int pointerIndex, int pos,
PointerCoords outPointerCoords) {
- final int sampleIndex = (pos * mNumPointers + pointerIndex) * NUM_SAMPLE_DATA;
- getPointerCoordsAtSampleIndex(sampleIndex, outPointerCoords);
+ nativeGetPointerCoords(mNativePtr, pointerIndex, pos, outPointerCoords);
}
/**
@@ -1381,10 +1581,9 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @see #EDGE_BOTTOM
*/
public final int getEdgeFlags() {
- return mEdgeFlags;
+ return nativeGetEdgeFlags(mNativePtr);
}
-
/**
* Sets the bitfield indicating which edges, if any, were touched by this
* MotionEvent.
@@ -1392,14 +1591,14 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @see #getEdgeFlags()
*/
public final void setEdgeFlags(int flags) {
- mEdgeFlags = flags;
+ nativeSetEdgeFlags(mNativePtr, flags);
}
/**
* Sets this event's action.
*/
public final void setAction(int action) {
- mAction = action;
+ nativeSetAction(mNativePtr, action);
}
/**
@@ -1408,8 +1607,7 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @param deltaY Amount to add to the current Y coordinate of the event.
*/
public final void offsetLocation(float deltaX, float deltaY) {
- mXOffset += deltaX;
- mYOffset += deltaY;
+ nativeOffsetLocation(mNativePtr, deltaX, deltaY);
}
/**
@@ -1420,10 +1618,9 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @param y New absolute Y location.
*/
public final void setLocation(float x, float y) {
- final float[] dataSamples = mDataSamples;
- final int lastDataSampleIndex = mLastDataSampleIndex;
- mXOffset = x - dataSamples[lastDataSampleIndex + SAMPLE_X];
- mYOffset = y - dataSamples[lastDataSampleIndex + SAMPLE_Y];
+ float oldX = getX();
+ float oldY = getY();
+ nativeOffsetLocation(mNativePtr, x - oldX, y - oldY);
}
/**
@@ -1436,85 +1633,14 @@ public final class MotionEvent extends InputEvent implements Parcelable {
throw new IllegalArgumentException("matrix must not be null");
}
- nativeTransform(matrix);
- }
-
- private final void getPointerCoordsAtSampleIndex(int sampleIndex,
- PointerCoords outPointerCoords) {
- final float[] dataSamples = mDataSamples;
- outPointerCoords.x = dataSamples[sampleIndex + SAMPLE_X] + mXOffset;
- outPointerCoords.y = dataSamples[sampleIndex + SAMPLE_Y] + mYOffset;
- outPointerCoords.pressure = dataSamples[sampleIndex + SAMPLE_PRESSURE];
- outPointerCoords.size = dataSamples[sampleIndex + SAMPLE_SIZE];
- outPointerCoords.touchMajor = dataSamples[sampleIndex + SAMPLE_TOUCH_MAJOR];
- outPointerCoords.touchMinor = dataSamples[sampleIndex + SAMPLE_TOUCH_MINOR];
- outPointerCoords.toolMajor = dataSamples[sampleIndex + SAMPLE_TOOL_MAJOR];
- outPointerCoords.toolMinor = dataSamples[sampleIndex + SAMPLE_TOOL_MINOR];
- outPointerCoords.orientation = dataSamples[sampleIndex + SAMPLE_ORIENTATION];
- }
-
- private final void setPointerCoordsAtSampleIndex(int sampleIndex,
- PointerCoords[] pointerCoords) {
- final int numPointers = mNumPointers;
- for (int i = 0; i < numPointers; i++) {
- setPointerCoordsAtSampleIndex(sampleIndex, pointerCoords[i]);
- sampleIndex += NUM_SAMPLE_DATA;
- }
- }
-
- private final void setPointerCoordsAtSampleIndex(int sampleIndex,
- PointerCoords pointerCoords) {
- final float[] dataSamples = mDataSamples;
- dataSamples[sampleIndex + SAMPLE_X] = pointerCoords.x - mXOffset;
- dataSamples[sampleIndex + SAMPLE_Y] = pointerCoords.y - mYOffset;
- dataSamples[sampleIndex + SAMPLE_PRESSURE] = pointerCoords.pressure;
- dataSamples[sampleIndex + SAMPLE_SIZE] = pointerCoords.size;
- dataSamples[sampleIndex + SAMPLE_TOUCH_MAJOR] = pointerCoords.touchMajor;
- dataSamples[sampleIndex + SAMPLE_TOUCH_MINOR] = pointerCoords.touchMinor;
- dataSamples[sampleIndex + SAMPLE_TOOL_MAJOR] = pointerCoords.toolMajor;
- dataSamples[sampleIndex + SAMPLE_TOOL_MINOR] = pointerCoords.toolMinor;
- dataSamples[sampleIndex + SAMPLE_ORIENTATION] = pointerCoords.orientation;
- }
-
- private final void setPointerCoordsAtSampleIndex(int sampleIndex,
- float x, float y, float pressure, float size) {
- final float[] dataSamples = mDataSamples;
- dataSamples[sampleIndex + SAMPLE_X] = x - mXOffset;
- dataSamples[sampleIndex + SAMPLE_Y] = y - mYOffset;
- dataSamples[sampleIndex + SAMPLE_PRESSURE] = pressure;
- dataSamples[sampleIndex + SAMPLE_SIZE] = size;
- dataSamples[sampleIndex + SAMPLE_TOUCH_MAJOR] = pressure;
- dataSamples[sampleIndex + SAMPLE_TOUCH_MINOR] = pressure;
- dataSamples[sampleIndex + SAMPLE_TOOL_MAJOR] = size;
- dataSamples[sampleIndex + SAMPLE_TOOL_MINOR] = size;
- dataSamples[sampleIndex + SAMPLE_ORIENTATION] = 0;
- }
-
- private final void incrementNumSamplesAndReserveStorage(int dataSampleStride) {
- if (mNumSamples == mEventTimeNanoSamples.length) {
- long[] newEventTimeNanoSamples = new long[mNumSamples + BASE_AVAIL_SAMPLES];
- System.arraycopy(mEventTimeNanoSamples, 0, newEventTimeNanoSamples, 0, mNumSamples);
- mEventTimeNanoSamples = newEventTimeNanoSamples;
- }
-
- int nextDataSampleIndex = mLastDataSampleIndex + dataSampleStride;
- if (nextDataSampleIndex + dataSampleStride > mDataSamples.length) {
- float[] newDataSamples = new float[nextDataSampleIndex
- + BASE_AVAIL_SAMPLES * dataSampleStride];
- System.arraycopy(mDataSamples, 0, newDataSamples, 0, nextDataSampleIndex);
- mDataSamples = newDataSamples;
- }
-
- mLastEventTimeNanoSampleIndex = mNumSamples;
- mLastDataSampleIndex = nextDataSampleIndex;
- mNumSamples += 1;
+ nativeTransform(mNativePtr, matrix);
}
/**
* Add a new movement to the batch of movements in this event. The event's
* current location, position and size is updated to the new values.
* The current values in the event are added to a list of historical values.
- *
+ *
* Only applies to {@link #ACTION_MOVE} events.
*
* @param eventTime The time stamp (in ms) for this data.
@@ -1526,19 +1652,22 @@ public final class MotionEvent extends InputEvent implements Parcelable {
*/
public final void addBatch(long eventTime, float x, float y,
float pressure, float size, int metaState) {
- incrementNumSamplesAndReserveStorage(NUM_SAMPLE_DATA);
-
- mEventTimeNanoSamples[mLastEventTimeNanoSampleIndex] = eventTime * MS_PER_NS;
- setPointerCoordsAtSampleIndex(mLastDataSampleIndex, x, y, pressure, size);
-
- mMetaState |= metaState;
+ synchronized (gTmpPointerCoords) {
+ final PointerCoords pc = gTmpPointerCoords[0];
+ pc.clear();
+ pc.x = x;
+ pc.y = y;
+ pc.pressure = pressure;
+ pc.size = size;
+ nativeAddBatch(mNativePtr, eventTime * NS_PER_MS, gTmpPointerCoords, metaState);
+ }
}
/**
* Add a new movement to the batch of movements in this event. The event's
* current location, position and size is updated to the new values.
* The current values in the event are added to a list of historical values.
- *
+ *
* Only applies to {@link #ACTION_MOVE} events.
*
* @param eventTime The time stamp (in ms) for this data.
@@ -1546,20 +1675,14 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* @param metaState Meta key state.
*/
public final void addBatch(long eventTime, PointerCoords[] pointerCoords, int metaState) {
- final int dataSampleStride = mNumPointers * NUM_SAMPLE_DATA;
- incrementNumSamplesAndReserveStorage(dataSampleStride);
-
- mEventTimeNanoSamples[mLastEventTimeNanoSampleIndex] = eventTime * MS_PER_NS;
- setPointerCoordsAtSampleIndex(mLastDataSampleIndex, pointerCoords);
-
- mMetaState |= metaState;
+ nativeAddBatch(mNativePtr, eventTime * NS_PER_MS, pointerCoords, metaState);
}
@Override
public String toString() {
return "MotionEvent{" + Integer.toHexString(System.identityHashCode(this))
+ " pointerId=" + getPointerId(0)
- + " action=" + actionToString(mAction)
+ + " action=" + actionToString(getAction())
+ " x=" + getX()
+ " y=" + getY()
+ " pressure=" + getPressure()
@@ -1569,13 +1692,13 @@ public final class MotionEvent extends InputEvent implements Parcelable {
+ " toolMajor=" + getToolMajor()
+ " toolMinor=" + getToolMinor()
+ " orientation=" + getOrientation()
- + " meta=" + KeyEvent.metaStateToString(mMetaState)
+ + " meta=" + KeyEvent.metaStateToString(getMetaState())
+ " pointerCount=" + getPointerCount()
+ " historySize=" + getHistorySize()
- + " flags=0x" + Integer.toHexString(mFlags)
- + " edgeFlags=0x" + Integer.toHexString(mEdgeFlags)
- + " device=" + mDeviceId
- + " source=0x" + Integer.toHexString(mSource)
+ + " flags=0x" + Integer.toHexString(getFlags())
+ + " edgeFlags=0x" + Integer.toHexString(getEdgeFlags())
+ + " device=" + getDeviceId()
+ + " source=0x" + Integer.toHexString(getSource())
+ (getPointerCount() > 1 ?
" pointerId2=" + getPointerId(1) + " x2=" + getX(1) + " y2=" + getY(1) : "")
+ "}";
@@ -1583,7 +1706,8 @@ public final class MotionEvent extends InputEvent implements Parcelable {
/**
* Returns a string that represents the symbolic name of the specified action
- * such as "ACTION_DOWN", "ACTION_POINTER_DOWN(3)" or "35" (if unknown).
+ * such as "ACTION_DOWN", "ACTION_POINTER_DOWN(3)" or an equivalent numeric constant
+ * such as "35" if unknown.
*
* @param action The action.
* @return The symbolic name of the specified action.
@@ -1611,6 +1735,39 @@ public final class MotionEvent extends InputEvent implements Parcelable {
}
}
+ /**
+ * Returns a string that represents the symbolic name of the specified axis
+ * such as "AXIS_X" or an equivalent numeric constants such as "42" if unknown.
+ *
+ * @param axis The axis
+ * @return The symbolic name of the specified axis.
+ * @hide
+ */
+ public static String axisToString(int axis) {
+ switch (axis) {
+ case AXIS_X:
+ return "AXIS_X";
+ case AXIS_Y:
+ return "AXIS_Y";
+ case AXIS_PRESSURE:
+ return "AXIS_PRESSURE";
+ case AXIS_SIZE:
+ return "AXIS_SIZE";
+ case AXIS_TOUCH_MAJOR:
+ return "AXIS_TOUCH_MAJOR";
+ case AXIS_TOUCH_MINOR:
+ return "AXIS_TOUCH_MINOR";
+ case AXIS_TOOL_MAJOR:
+ return "AXIS_TOOL_MAJOR";
+ case AXIS_TOOL_MINOR:
+ return "AXIS_TOOL_MINOR";
+ case AXIS_ORIENTATION:
+ return "AXIS_ORIENTATION";
+ default:
+ return Integer.toString(axis);
+ }
+ }
+
public static final Parcelable.Creator<MotionEvent> CREATOR
= new Parcelable.Creator<MotionEvent>() {
public MotionEvent createFromParcel(Parcel in) {
@@ -1625,84 +1782,16 @@ public final class MotionEvent extends InputEvent implements Parcelable {
/** @hide */
public static MotionEvent createFromParcelBody(Parcel in) {
- final int NP = in.readInt();
- final int NS = in.readInt();
- final int NI = NP * NS * NUM_SAMPLE_DATA;
-
- MotionEvent ev = obtain(NP, NS);
- ev.mNumPointers = NP;
- ev.mNumSamples = NS;
-
- ev.readBaseFromParcel(in);
-
- ev.mDownTimeNano = in.readLong();
- ev.mAction = in.readInt();
- ev.mXOffset = in.readFloat();
- ev.mYOffset = in.readFloat();
- ev.mXPrecision = in.readFloat();
- ev.mYPrecision = in.readFloat();
- ev.mEdgeFlags = in.readInt();
- ev.mMetaState = in.readInt();
- ev.mFlags = in.readInt();
-
- final int[] pointerIdentifiers = ev.mPointerIdentifiers;
- for (int i = 0; i < NP; i++) {
- pointerIdentifiers[i] = in.readInt();
- }
-
- final long[] eventTimeNanoSamples = ev.mEventTimeNanoSamples;
- for (int i = 0; i < NS; i++) {
- eventTimeNanoSamples[i] = in.readLong();
- }
-
- final float[] dataSamples = ev.mDataSamples;
- for (int i = 0; i < NI; i++) {
- dataSamples[i] = in.readFloat();
- }
-
- ev.mLastEventTimeNanoSampleIndex = NS - 1;
- ev.mLastDataSampleIndex = (NS - 1) * NP * NUM_SAMPLE_DATA;
+ MotionEvent ev = obtain();
+ ev.mNativePtr = nativeReadFromParcel(ev.mNativePtr, in);
return ev;
}
-
+
public void writeToParcel(Parcel out, int flags) {
out.writeInt(PARCEL_TOKEN_MOTION_EVENT);
-
- final int NP = mNumPointers;
- final int NS = mNumSamples;
- final int NI = NP * NS * NUM_SAMPLE_DATA;
-
- out.writeInt(NP);
- out.writeInt(NS);
-
- writeBaseToParcel(out);
-
- out.writeLong(mDownTimeNano);
- out.writeInt(mAction);
- out.writeFloat(mXOffset);
- out.writeFloat(mYOffset);
- out.writeFloat(mXPrecision);
- out.writeFloat(mYPrecision);
- out.writeInt(mEdgeFlags);
- out.writeInt(mMetaState);
- out.writeInt(mFlags);
-
- final int[] pointerIdentifiers = mPointerIdentifiers;
- for (int i = 0; i < NP; i++) {
- out.writeInt(pointerIdentifiers[i]);
- }
-
- final long[] eventTimeNanoSamples = mEventTimeNanoSamples;
- for (int i = 0; i < NS; i++) {
- out.writeLong(eventTimeNanoSamples[i]);
- }
-
- final float[] dataSamples = mDataSamples;
- for (int i = 0; i < NI; i++) {
- out.writeFloat(dataSamples[i]);
- }
+ nativeWriteToParcel(mNativePtr, out);
}
-
+
/**
* Transfer object for pointer coordinates.
*
@@ -1713,49 +1802,87 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* input devices and sources represent pointer coordinates.
*/
public static final class PointerCoords {
+ private static final int INITIAL_PACKED_AXIS_VALUES = 8;
+ private int mPackedAxisBits; // 32bits are enough for now, can raise to 64bit when needed
+ private float[] mPackedAxisValues;
+
+ /**
+ * Creates a pointer coords object with all axes initialized to zero.
+ */
+ public PointerCoords() {
+ }
+
+ /**
+ * Creates a pointer coords object as a copy of the
+ * contents of another pointer coords object.
+ *
+ * @param other The pointer coords object to copy.
+ */
+ public PointerCoords(PointerCoords other) {
+ copyFrom(other);
+ }
+
/**
* The X coordinate of the pointer movement.
- * The interpretation varies by input source and may represent the position of
- * the center of the contact area, a relative displacement in device-specific units
- * or something else.
+ * The interpretation of the X axis varies by input source.
+ * It may represent the X position of the center of the touch contact area,
+ * a relative horizontal displacement of a trackball or joystick, or something else.
+ *
+ * @see MotionEvent#AXIS_X
*/
public float x;
/**
* The Y coordinate of the pointer movement.
- * The interpretation varies by input source and may represent the position of
- * the center of the contact area, a relative displacement in device-specific units
- * or something else.
+ * The interpretation of the Y axis varies by input source.
+ * It may represent the Y position of the center of the touch contact area,
+ * a relative vertical displacement of a trackball or joystick, or something else.
+ *
+ * @see MotionEvent#AXIS_Y
*/
public float y;
/**
- * A scaled value that describes the pressure applied to the pointer.
+ * A normalized value that describes the pressure applied to the device
+ * by a finger or other tool.
* The pressure generally ranges from 0 (no pressure at all) to 1 (normal pressure),
- * however values higher than 1 may be generated depending on the calibration of
+ * although values higher than 1 may be generated depending on the calibration of
* the input device.
+ *
+ * @see MotionEvent#AXIS_PRESSURE
*/
public float pressure;
/**
- * A scaled value of the approximate size of the pointer touch area.
- * This represents some approximation of the area of the screen being
+ * A normalized value that describes the approximate size of the pointer touch area
+ * in relation to the maximum detectable size of the device.
+ * It represents some approximation of the area of the screen being
* pressed; the actual value in pixels corresponding to the
* touch is normalized with the device specific range of values
* and scaled to a value between 0 and 1. The value of size can be used to
* determine fat touch events.
+ *
+ * @see MotionEvent#AXIS_SIZE
*/
public float size;
/**
* The length of the major axis of an ellipse that describes the touch area at
* the point of contact.
+ * If the device is a touch screen, the length is reported in pixels, otherwise it is
+ * reported in device-specific units.
+ *
+ * @see MotionEvent#AXIS_TOUCH_MAJOR
*/
public float touchMajor;
/**
* The length of the minor axis of an ellipse that describes the touch area at
* the point of contact.
+ * If the device is a touch screen, the length is reported in pixels, otherwise it is
+ * reported in device-specific units.
+ *
+ * @see MotionEvent#AXIS_TOUCH_MINOR
*/
public float touchMinor;
@@ -1764,6 +1891,10 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* the approaching tool.
* The tool area represents the estimated size of the finger or pen that is
* touching the device independent of its actual touch area at the point of contact.
+ * If the device is a touch screen, the length is reported in pixels, otherwise it is
+ * reported in device-specific units.
+ *
+ * @see MotionEvent#AXIS_TOOL_MAJOR
*/
public float toolMajor;
@@ -1772,6 +1903,10 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* the approaching tool.
* The tool area represents the estimated size of the finger or pen that is
* touching the device independent of its actual touch area at the point of contact.
+ * If the device is a touch screen, the length is reported in pixels, otherwise it is
+ * reported in device-specific units.
+ *
+ * @see MotionEvent#AXIS_TOOL_MINOR
*/
public float toolMinor;
@@ -1783,27 +1918,168 @@ public final class MotionEvent extends InputEvent implements Parcelable {
* indicates that the major axis of contact is oriented to the left.
* The full range is from -PI/2 radians (finger pointing fully left) to PI/2 radians
* (finger pointing fully right).
+ *
+ * @see MotionEvent#AXIS_ORIENTATION
*/
public float orientation;
-
- /*
- private static final float PI_4 = (float) (Math.PI / 4);
-
- public float getTouchWidth() {
- return Math.abs(orientation) > PI_4 ? touchMajor : touchMinor;
+
+ /**
+ * Clears the contents of this object.
+ * Resets all axes to zero.
+ */
+ public void clear() {
+ mPackedAxisBits = 0;
+
+ x = 0;
+ y = 0;
+ pressure = 0;
+ size = 0;
+ touchMajor = 0;
+ touchMinor = 0;
+ toolMajor = 0;
+ toolMinor = 0;
+ orientation = 0;
}
-
- public float getTouchHeight() {
- return Math.abs(orientation) > PI_4 ? touchMinor : touchMajor;
+
+ /**
+ * Copies the contents of another pointer coords object.
+ *
+ * @param other The pointer coords object to copy.
+ */
+ public void copyFrom(PointerCoords other) {
+ final int bits = other.mPackedAxisBits;
+ mPackedAxisBits = bits;
+ if (bits != 0) {
+ final float[] otherValues = other.mPackedAxisValues;
+ final int count = Integer.bitCount(bits);
+ float[] values = mPackedAxisValues;
+ if (values == null || count > values.length) {
+ values = new float[otherValues.length];
+ mPackedAxisValues = values;
+ }
+ System.arraycopy(otherValues, 0, values, 0, count);
+ }
+
+ x = other.x;
+ y = other.y;
+ pressure = other.pressure;
+ size = other.size;
+ touchMajor = other.touchMajor;
+ touchMinor = other.touchMinor;
+ toolMajor = other.toolMajor;
+ toolMinor = other.toolMinor;
+ orientation = other.orientation;
}
-
- public float getToolWidth() {
- return Math.abs(orientation) > PI_4 ? toolMajor : toolMinor;
+
+ /**
+ * Gets the value associated with the specified axis.
+ *
+ * @param axis The axis identifier for the axis value to retrieve.
+ * @return The value associated with the axis, or 0 if none.
+ *
+ * @see MotionEvent#AXIS_X
+ * @see MotionEvent#AXIS_Y
+ */
+ public float getAxisValue(int axis) {
+ switch (axis) {
+ case AXIS_X:
+ return x;
+ case AXIS_Y:
+ return y;
+ case AXIS_PRESSURE:
+ return pressure;
+ case AXIS_SIZE:
+ return size;
+ case AXIS_TOUCH_MAJOR:
+ return touchMajor;
+ case AXIS_TOUCH_MINOR:
+ return touchMinor;
+ case AXIS_TOOL_MAJOR:
+ return toolMajor;
+ case AXIS_TOOL_MINOR:
+ return toolMinor;
+ case AXIS_ORIENTATION:
+ return orientation;
+ default: {
+ final int bits = mPackedAxisBits;
+ final int axisBit = 1 << axis;
+ if ((bits & axisBit) == 0) {
+ return 0;
+ }
+ final int index = Integer.bitCount(bits & (axisBit - 1));
+ return mPackedAxisValues[index];
+ }
+ }
}
-
- public float getToolHeight() {
- return Math.abs(orientation) > PI_4 ? toolMinor : toolMajor;
+
+ /**
+ * Sets the value associated with the specified axis.
+ *
+ * @param axis The axis identifier for the axis value to assign.
+ * @param value The value to set.
+ *
+ * @see MotionEvent#AXIS_X
+ * @see MotionEvent#AXIS_Y
+ */
+ public void setAxisValue(int axis, float value) {
+ switch (axis) {
+ case AXIS_X:
+ x = value;
+ break;
+ case AXIS_Y:
+ y = value;
+ break;
+ case AXIS_PRESSURE:
+ pressure = value;
+ break;
+ case AXIS_SIZE:
+ size = value;
+ break;
+ case AXIS_TOUCH_MAJOR:
+ touchMajor = value;
+ break;
+ case AXIS_TOUCH_MINOR:
+ touchMinor = value;
+ break;
+ case AXIS_TOOL_MAJOR:
+ toolMajor = value;
+ break;
+ case AXIS_TOOL_MINOR:
+ toolMinor = value;
+ break;
+ case AXIS_ORIENTATION:
+ orientation = value;
+ break;
+ default: {
+ final int bits = mPackedAxisBits;
+ final int axisBit = 1 << axis;
+ final int index = Integer.bitCount(bits & (axisBit - 1));
+ float[] values = mPackedAxisValues;
+ if ((bits & axisBit) == 0) {
+ if (values == null) {
+ values = new float[INITIAL_PACKED_AXIS_VALUES];
+ mPackedAxisValues = values;
+ } else {
+ final int count = Integer.bitCount(bits);
+ if (count < values.length) {
+ if (index != count) {
+ System.arraycopy(values, index, values, index + 1,
+ count - index);
+ }
+ } else {
+ float[] newValues = new float[count * 2];
+ System.arraycopy(values, 0, newValues, 0, index);
+ System.arraycopy(values, index, newValues, index + 1,
+ count - index);
+ values = newValues;
+ mPackedAxisValues = values;
+ }
+ }
+ mPackedAxisBits = bits | axisBit;
+ }
+ values[index] = value;
+ }
+ }
}
- */
}
}
diff --git a/core/java/android/view/View.java b/core/java/android/view/View.java
index b982c7b..48451ba 100644
--- a/core/java/android/view/View.java
+++ b/core/java/android/view/View.java
@@ -6061,9 +6061,7 @@ public class View implements Drawable.Callback, KeyEvent.Callback, Accessibility
if (top != mTop) {
updateMatrix();
if (mMatrixIsIdentity) {
- final ViewParent p = mParent;
- if (p != null && mAttachInfo != null) {
- final Rect r = mAttachInfo.mTmpInvalRect;
+ if (mAttachInfo != null) {
int minTop;
int yLoc;
if (top < mTop) {
@@ -6073,8 +6071,7 @@ public class View implements Drawable.Callback, KeyEvent.Callback, Accessibility
minTop = mTop;
yLoc = 0;
}
- r.set(0, yLoc, mRight - mLeft, mBottom - minTop);
- p.invalidateChild(this, r);
+ invalidate(0, yLoc, mRight - mLeft, mBottom - minTop);
}
} else {
// Double-invalidation is necessary to capture view's old and new areas
@@ -6131,17 +6128,14 @@ public class View implements Drawable.Callback, KeyEvent.Callback, Accessibility
if (bottom != mBottom) {
updateMatrix();
if (mMatrixIsIdentity) {
- final ViewParent p = mParent;
- if (p != null && mAttachInfo != null) {
- final Rect r = mAttachInfo.mTmpInvalRect;
+ if (mAttachInfo != null) {
int maxBottom;
if (bottom < mBottom) {
maxBottom = mBottom;
} else {
maxBottom = bottom;
}
- r.set(0, 0, mRight - mLeft, maxBottom - mTop);
- p.invalidateChild(this, r);
+ invalidate(0, 0, mRight - mLeft, maxBottom - mTop);
}
} else {
// Double-invalidation is necessary to capture view's old and new areas
@@ -6189,9 +6183,7 @@ public class View implements Drawable.Callback, KeyEvent.Callback, Accessibility
if (left != mLeft) {
updateMatrix();
if (mMatrixIsIdentity) {
- final ViewParent p = mParent;
- if (p != null && mAttachInfo != null) {
- final Rect r = mAttachInfo.mTmpInvalRect;
+ if (mAttachInfo != null) {
int minLeft;
int xLoc;
if (left < mLeft) {
@@ -6201,8 +6193,7 @@ public class View implements Drawable.Callback, KeyEvent.Callback, Accessibility
minLeft = mLeft;
xLoc = 0;
}
- r.set(xLoc, 0, mRight - minLeft, mBottom - mTop);
- p.invalidateChild(this, r);
+ invalidate(xLoc, 0, mRight - minLeft, mBottom - mTop);
}
} else {
// Double-invalidation is necessary to capture view's old and new areas
@@ -6250,17 +6241,14 @@ public class View implements Drawable.Callback, KeyEvent.Callback, Accessibility
if (right != mRight) {
updateMatrix();
if (mMatrixIsIdentity) {
- final ViewParent p = mParent;
- if (p != null && mAttachInfo != null) {
- final Rect r = mAttachInfo.mTmpInvalRect;
+ if (mAttachInfo != null) {
int maxRight;
if (right < mRight) {
maxRight = mRight;
} else {
maxRight = right;
}
- r.set(0, 0, maxRight - mLeft, mBottom - mTop);
- p.invalidateChild(this, r);
+ invalidate(0, 0, maxRight - mLeft, mBottom - mTop);
}
} else {
// Double-invalidation is necessary to capture view's old and new areas
diff --git a/core/java/android/webkit/BrowserFrame.java b/core/java/android/webkit/BrowserFrame.java
index 8e09986..fc1240f 100644
--- a/core/java/android/webkit/BrowserFrame.java
+++ b/core/java/android/webkit/BrowserFrame.java
@@ -21,6 +21,8 @@ import android.content.ComponentCallbacks;
import android.content.Context;
import android.content.res.AssetManager;
import android.content.res.Configuration;
+import android.content.res.Resources;
+import android.content.res.Resources.NotFoundException;
import android.graphics.Bitmap;
import android.net.ParseException;
import android.net.Uri;
@@ -933,7 +935,19 @@ class BrowserFrame extends Handler {
if (androidResource != null) {
return new WebResourceResponse(null, null, androidResource);
}
- return mCallbackProxy.shouldInterceptRequest(url);
+ WebResourceResponse response = mCallbackProxy.shouldInterceptRequest(url);
+ if (response == null && "browser:incognito".equals(url)) {
+ try {
+ Resources res = mContext.getResources();
+ InputStream ins = res.openRawResource(
+ com.android.internal.R.raw.incognito_mode_start_page);
+ response = new WebResourceResponse("text/html", "utf8", ins);
+ } catch (NotFoundException ex) {
+ // This shouldn't happen, but try and gracefully handle it jic
+ Log.w(LOGTAG, "Failed opening raw.incognito_mode_start_page", ex);
+ }
+ }
+ return response;
}
/**
diff --git a/core/java/android/webkit/CacheManager.java b/core/java/android/webkit/CacheManager.java
index 04062fe..3ce0730 100644
--- a/core/java/android/webkit/CacheManager.java
+++ b/core/java/android/webkit/CacheManager.java
@@ -198,8 +198,6 @@ public final class CacheManager {
mBaseDir = new File(context.getCacheDir(), "webviewCacheChromiumStaging");
if (!mBaseDir.exists()) {
mBaseDir.mkdirs();
- } else {
- // TODO: Should we clear out old files?
}
return;
}
@@ -605,11 +603,12 @@ public final class CacheManager {
* @return Whether the removal succeeded.
*/
static boolean removeAllCacheFiles() {
- assert !JniUtil.useChromiumHttpStack();
-
// Note, this is called before init() when the database is
// created or upgraded.
if (mBaseDir == null) {
+ // This method should not be called before init() when using the
+ // chrome http stack
+ assert !JniUtil.useChromiumHttpStack();
// Init() has not been called yet, so just flag that
// we need to clear the cache when init() is called.
mClearCacheOnInit = true;
diff --git a/core/java/android/webkit/WebSettings.java b/core/java/android/webkit/WebSettings.java
index 0bf0eab..71d6080 100644
--- a/core/java/android/webkit/WebSettings.java
+++ b/core/java/android/webkit/WebSettings.java
@@ -174,6 +174,7 @@ public class WebSettings {
private boolean mBlockNetworkImage = false;
private boolean mBlockNetworkLoads;
private boolean mJavaScriptEnabled = false;
+ private boolean mShowVisualIndicator = false;
private PluginState mPluginState = PluginState.OFF;
private boolean mJavaScriptCanOpenWindowsAutomatically = false;
private boolean mUseDoubleTree = false;
@@ -1191,6 +1192,26 @@ public class WebSettings {
}
/**
+ * Tell the WebView to show the visual indicator
+ * @param flag True if the WebView should show the visual indicator
+ * @hide
+ */
+ public synchronized void setShowVisualIndicator(boolean flag) {
+ if (mShowVisualIndicator != flag) {
+ mShowVisualIndicator = flag;
+ postSync();
+ }
+ }
+
+ /**
+ * @return True if the WebView is showing the visual indicator
+ * @hide
+ */
+ public synchronized boolean getShowVisualIndicator() {
+ return mShowVisualIndicator;
+ }
+
+ /**
* Tell the WebView to enable plugins.
* @param flag True if the WebView should load plugins.
* @deprecated This method has been deprecated in favor of
diff --git a/core/java/android/webkit/WebView.java b/core/java/android/webkit/WebView.java
index 7d8289a..69e658f 100644
--- a/core/java/android/webkit/WebView.java
+++ b/core/java/android/webkit/WebView.java
@@ -2089,7 +2089,7 @@ public class WebView extends AbsoluteLayout
public void clearView() {
mContentWidth = 0;
mContentHeight = 0;
- setBaseLayer(0, null);
+ setBaseLayer(0, null, false);
mWebViewCore.sendMessage(EventHub.CLEAR_CONTENT);
}
@@ -3996,14 +3996,14 @@ public class WebView extends AbsoluteLayout
}
}
- void setBaseLayer(int layer, Rect invalRect) {
+ void setBaseLayer(int layer, Rect invalRect, boolean showVisualIndciator) {
if (mNativeClass == 0)
return;
if (invalRect == null) {
Rect rect = new Rect(0, 0, mContentWidth, mContentHeight);
- nativeSetBaseLayer(layer, rect);
+ nativeSetBaseLayer(layer, rect, showVisualIndciator);
} else {
- nativeSetBaseLayer(layer, invalRect);
+ nativeSetBaseLayer(layer, invalRect, showVisualIndciator);
}
}
@@ -7205,7 +7205,8 @@ public class WebView extends AbsoluteLayout
case NEW_PICTURE_MSG_ID: {
// called for new content
final WebViewCore.DrawData draw = (WebViewCore.DrawData) msg.obj;
- setBaseLayer(draw.mBaseLayer, draw.mInvalRegion.getBounds());
+ setBaseLayer(draw.mBaseLayer, draw.mInvalRegion.getBounds(),
+ getSettings().getShowVisualIndicator());
final Point viewSize = draw.mViewSize;
WebViewCore.ViewState viewState = draw.mViewState;
boolean isPictureAfterFirstLayout = viewState != null;
@@ -8337,7 +8338,8 @@ public class WebView extends AbsoluteLayout
private native void nativeSetFindIsEmpty();
private native void nativeSetFindIsUp(boolean isUp);
private native void nativeSetHeightCanMeasure(boolean measure);
- private native void nativeSetBaseLayer(int layer, Rect invalRect);
+ private native void nativeSetBaseLayer(int layer, Rect invalRect,
+ boolean showVisualIndciator);
private native void nativeShowCursorTimed();
private native void nativeReplaceBaseContent(int content);
private native void nativeCopyBaseContentToPicture(Picture pict);
diff --git a/core/java/android/widget/AutoCompleteTextView.java b/core/java/android/widget/AutoCompleteTextView.java
index 3bdba62..27610b9 100644
--- a/core/java/android/widget/AutoCompleteTextView.java
+++ b/core/java/android/widget/AutoCompleteTextView.java
@@ -92,6 +92,8 @@ public class AutoCompleteTextView extends EditText implements Filter.FilterListe
static final boolean DEBUG = false;
static final String TAG = "AutoCompleteTextView";
+ static final int EXPAND_MAX = 3;
+
private CharSequence mHintText;
private TextView mHintView;
private int mHintResource;
@@ -1057,8 +1059,10 @@ public class AutoCompleteTextView extends EditText implements Filter.FilterListe
if (!isPopupShowing()) {
// Make sure the list does not obscure the IME when shown for the first time.
mPopup.setInputMethodMode(ListPopupWindow.INPUT_METHOD_NEEDED);
+ mPopup.setListItemExpandMax(EXPAND_MAX);
}
mPopup.show();
+ mPopup.getListView().setOverScrollMode(View.OVER_SCROLL_ALWAYS);
}
/**
diff --git a/core/java/android/widget/ListPopupWindow.java b/core/java/android/widget/ListPopupWindow.java
index 560fc68..5642877 100644
--- a/core/java/android/widget/ListPopupWindow.java
+++ b/core/java/android/widget/ListPopupWindow.java
@@ -65,6 +65,7 @@ public class ListPopupWindow {
private boolean mDropDownAlwaysVisible = false;
private boolean mForceIgnoreOutsideTouch = false;
+ int mListItemExpandMaximum = Integer.MAX_VALUE;
private View mPromptView;
private int mPromptPosition = POSITION_PROMPT_ABOVE;
@@ -519,6 +520,7 @@ public class ListPopupWindow {
int heightSpec = 0;
boolean noInputMethod = isInputMethodNotNeeded();
+ mPopup.setAllowScrollingAnchorParent(!noInputMethod);
if (mPopup.isShowing()) {
if (mDropDownWidth == ViewGroup.LayoutParams.MATCH_PARENT) {
@@ -775,6 +777,16 @@ public class ListPopupWindow {
}
/**
+ * The maximum number of list items that can be visible and still have
+ * the list expand when touched.
+ *
+ * @param max Max number of items that can be visible and still allow the list to expand.
+ */
+ void setListItemExpandMax(int max) {
+ mListItemExpandMaximum = max;
+ }
+
+ /**
* Filter key down events. By forwarding key down events to this function,
* views using non-modal ListPopupWindow can have it handle key selection of items.
*
@@ -1210,8 +1222,11 @@ public class ListPopupWindow {
private class ResizePopupRunnable implements Runnable {
public void run() {
- mPopup.setInputMethodMode(PopupWindow.INPUT_METHOD_NOT_NEEDED);
- show();
+ if (mDropDownList != null && mDropDownList.getCount() > mDropDownList.getChildCount() &&
+ mDropDownList.getChildCount() <= mListItemExpandMaximum) {
+ mPopup.setInputMethodMode(PopupWindow.INPUT_METHOD_NOT_NEEDED);
+ show();
+ }
}
}
diff --git a/core/java/android/widget/PopupWindow.java b/core/java/android/widget/PopupWindow.java
index 439e0ca..53932af 100644
--- a/core/java/android/widget/PopupWindow.java
+++ b/core/java/android/widget/PopupWindow.java
@@ -90,6 +90,7 @@ public class PopupWindow {
private int mSplitTouchEnabled = -1;
private boolean mLayoutInScreen;
private boolean mClipToScreen;
+ private boolean mAllowScrollingAnchorParent = true;
private OnTouchListener mTouchInterceptor;
@@ -592,6 +593,16 @@ public class PopupWindow {
mClipToScreen = enabled;
setClippingEnabled(!enabled);
}
+
+ /**
+ * Allow PopupWindow to scroll the anchor's parent to provide more room
+ * for the popup. Enabled by default.
+ *
+ * @param enabled True to scroll the anchor's parent when more room is desired by the popup.
+ */
+ void setAllowScrollingAnchorParent(boolean enabled) {
+ mAllowScrollingAnchorParent = enabled;
+ }
/**
* <p>Indicates whether the popup window supports splitting touches.</p>
@@ -1045,7 +1056,8 @@ public class PopupWindow {
anchor.getWindowVisibleDisplayFrame(displayFrame);
final View root = anchor.getRootView();
- if (p.y + mPopupHeight > displayFrame.bottom || p.x + mPopupWidth - root.getWidth() > 0) {
+ if (mAllowScrollingAnchorParent && (p.y + mPopupHeight > displayFrame.bottom ||
+ p.x + mPopupWidth - root.getWidth() > 0)) {
// if the drop down disappears at the bottom of the screen. we try to
// scroll a parent scrollview or move the drop down back up on top of
// the edit box
diff --git a/core/java/android/widget/StackView.java b/core/java/android/widget/StackView.java
index 6a09d35..e6cf31e 100644
--- a/core/java/android/widget/StackView.java
+++ b/core/java/android/widget/StackView.java
@@ -1207,6 +1207,7 @@ public class StackView extends AdapterViewAnimator {
void invalidateGlobalRegion(View v, Rect r) {
// We need to make a new rect here, so as not to modify the one passed
globalInvalidateRect.set(r);
+ globalInvalidateRect.union(0, 0, getWidth(), getHeight());
View p = v;
if (!(v.getParent() != null && v.getParent() instanceof View)) return;
@@ -1223,8 +1224,9 @@ public class StackView extends AdapterViewAnimator {
firstPass = false;
p = (View) p.getParent();
parentRect.set(p.getScrollX(), p.getScrollY(),
- p.getWidth() + p.getScrollX(), p.getHeight() + p.getScrollY());
-
+ p.getWidth() + p.getScrollX(), p.getHeight() + p.getScrollY());
+ p.invalidate(globalInvalidateRect.left, globalInvalidateRect.top,
+ globalInvalidateRect.right, globalInvalidateRect.bottom);
}
p.invalidate(globalInvalidateRect.left, globalInvalidateRect.top,
diff --git a/core/jni/android_view_MotionEvent.cpp b/core/jni/android_view_MotionEvent.cpp
index f32f0ff..99fbbe9 100644
--- a/core/jni/android_view_MotionEvent.cpp
+++ b/core/jni/android_view_MotionEvent.cpp
@@ -22,24 +22,10 @@
#include <utils/Log.h>
#include <ui/Input.h>
#include "android_view_MotionEvent.h"
+#include "android_util_Binder.h"
#include "android/graphics/Matrix.h"
-#include <math.h>
#include "SkMatrix.h"
-#include "SkScalar.h"
-
-// Number of float items per entry in a DVM sample data array
-#define NUM_SAMPLE_DATA 9
-
-#define SAMPLE_X 0
-#define SAMPLE_Y 1
-#define SAMPLE_PRESSURE 2
-#define SAMPLE_SIZE 3
-#define SAMPLE_TOUCH_MAJOR 4
-#define SAMPLE_TOUCH_MINOR 5
-#define SAMPLE_TOOL_MAJOR 6
-#define SAMPLE_TOOL_MINOR 7
-#define SAMPLE_ORIENTATION 8
namespace android {
@@ -52,35 +38,41 @@ static struct {
jmethodID obtain;
jmethodID recycle;
- jfieldID mDeviceId;
- jfieldID mSource;
- jfieldID mDownTimeNano;
- jfieldID mAction;
- jfieldID mXOffset;
- jfieldID mYOffset;
- jfieldID mXPrecision;
- jfieldID mYPrecision;
- jfieldID mEdgeFlags;
- jfieldID mMetaState;
- jfieldID mFlags;
- jfieldID mNumPointers;
- jfieldID mNumSamples;
- jfieldID mPointerIdentifiers;
- jfieldID mDataSamples;
- jfieldID mEventTimeNanoSamples;
- jfieldID mLastDataSampleIndex;
- jfieldID mLastEventTimeNanoSampleIndex;
+ jfieldID mNativePtr;
} gMotionEventClassInfo;
+static struct {
+ jclass clazz;
+
+ jfieldID mPackedAxisBits;
+ jfieldID mPackedAxisValues;
+ jfieldID x;
+ jfieldID y;
+ jfieldID pressure;
+ jfieldID size;
+ jfieldID touchMajor;
+ jfieldID touchMinor;
+ jfieldID toolMajor;
+ jfieldID toolMinor;
+ jfieldID orientation;
+} gPointerCoordsClassInfo;
+
// ----------------------------------------------------------------------------
-jobject android_view_MotionEvent_fromNative(JNIEnv* env, const MotionEvent* event) {
- jint numPointers = jint(event->getPointerCount());
- jint numHistoricalSamples = jint(event->getHistorySize());
- jint numSamples = numHistoricalSamples + 1;
+static MotionEvent* android_view_MotionEvent_getNativePtr(JNIEnv* env, jobject eventObj) {
+ return reinterpret_cast<MotionEvent*>(
+ env->GetIntField(eventObj, gMotionEventClassInfo.mNativePtr));
+}
+static void android_view_MotionEvent_setNativePtr(JNIEnv* env, jobject eventObj,
+ MotionEvent* event) {
+ env->SetIntField(eventObj, gMotionEventClassInfo.mNativePtr,
+ reinterpret_cast<int>(event));
+}
+
+jobject android_view_MotionEvent_fromNative(JNIEnv* env, const MotionEvent* event) {
jobject eventObj = env->CallStaticObjectMethod(gMotionEventClassInfo.clazz,
- gMotionEventClassInfo.obtain, numPointers, numSamples);
+ gMotionEventClassInfo.obtain);
if (env->ExceptionCheck()) {
LOGE("An exception occurred while obtaining a motion event.");
LOGE_EX(env);
@@ -88,261 +80,648 @@ jobject android_view_MotionEvent_fromNative(JNIEnv* env, const MotionEvent* even
return NULL;
}
- env->SetIntField(eventObj, gMotionEventClassInfo.mDeviceId,
- event->getDeviceId());
- env->SetIntField(eventObj, gMotionEventClassInfo.mSource,
- event->getSource());
- env->SetLongField(eventObj, gMotionEventClassInfo.mDownTimeNano,
- event->getDownTime());
- env->SetIntField(eventObj, gMotionEventClassInfo.mAction,
- event->getAction());
- env->SetFloatField(eventObj, gMotionEventClassInfo.mXOffset,
- event->getXOffset());
- env->SetFloatField(eventObj, gMotionEventClassInfo.mYOffset,
- event->getYOffset());
- env->SetFloatField(eventObj, gMotionEventClassInfo.mXPrecision,
- event->getXPrecision());
- env->SetFloatField(eventObj, gMotionEventClassInfo.mYPrecision,
- event->getYPrecision());
- env->SetIntField(eventObj, gMotionEventClassInfo.mEdgeFlags,
- event->getEdgeFlags());
- env->SetIntField(eventObj, gMotionEventClassInfo.mMetaState,
- event->getMetaState());
- env->SetIntField(eventObj, gMotionEventClassInfo.mFlags,
- event->getFlags());
- env->SetIntField(eventObj, gMotionEventClassInfo.mNumPointers,
- numPointers);
- env->SetIntField(eventObj, gMotionEventClassInfo.mNumSamples,
- numSamples);
- env->SetIntField(eventObj, gMotionEventClassInfo.mLastDataSampleIndex,
- (numSamples - 1) * numPointers * NUM_SAMPLE_DATA);
- env->SetIntField(eventObj, gMotionEventClassInfo.mLastEventTimeNanoSampleIndex,
- numSamples - 1);
-
- jintArray pointerIdentifierArray = jintArray(env->GetObjectField(eventObj,
- gMotionEventClassInfo.mPointerIdentifiers));
- jfloatArray dataSampleArray = jfloatArray(env->GetObjectField(eventObj,
- gMotionEventClassInfo.mDataSamples));
- jlongArray eventTimeNanoSampleArray = jlongArray(env->GetObjectField(eventObj,
- gMotionEventClassInfo.mEventTimeNanoSamples));
-
- jint* pointerIdentifiers = (jint*)env->GetPrimitiveArrayCritical(pointerIdentifierArray, NULL);
- jfloat* dataSamples = (jfloat*)env->GetPrimitiveArrayCritical(dataSampleArray, NULL);
- jlong* eventTimeNanoSamples = (jlong*)env->GetPrimitiveArrayCritical(
- eventTimeNanoSampleArray, NULL);
-
- const int32_t* srcPointerIdentifiers = event->getPointerIds();
- jint* destPointerIdentifiers = pointerIdentifiers;
- for (jint i = 0; i < numPointers; i++) {
- *(destPointerIdentifiers++) = *(srcPointerIdentifiers++);
- }
-
- const nsecs_t* srcSampleEventTimes = event->getSampleEventTimes();
- jlong* destEventTimeNanoSamples = eventTimeNanoSamples;
- for (jint i = 0; i < numSamples; i++) {
- *(destEventTimeNanoSamples++) = *(srcSampleEventTimes++);
- }
-
- const PointerCoords* srcSamplePointerCoords = event->getSamplePointerCoords();
- jfloat* destDataSamples = dataSamples;
- jint numItems = numSamples * numPointers;
- for (jint i = 0; i < numItems; i++) {
- *(destDataSamples++) = srcSamplePointerCoords->x;
- *(destDataSamples++) = srcSamplePointerCoords->y;
- *(destDataSamples++) = srcSamplePointerCoords->pressure;
- *(destDataSamples++) = srcSamplePointerCoords->size;
- *(destDataSamples++) = srcSamplePointerCoords->touchMajor;
- *(destDataSamples++) = srcSamplePointerCoords->touchMinor;
- *(destDataSamples++) = srcSamplePointerCoords->toolMajor;
- *(destDataSamples++) = srcSamplePointerCoords->toolMinor;
- *(destDataSamples++) = srcSamplePointerCoords->orientation;
- srcSamplePointerCoords += 1;
- }
-
- env->ReleasePrimitiveArrayCritical(pointerIdentifierArray, pointerIdentifiers, 0);
- env->ReleasePrimitiveArrayCritical(dataSampleArray, dataSamples, 0);
- env->ReleasePrimitiveArrayCritical(eventTimeNanoSampleArray, eventTimeNanoSamples, 0);
-
- env->DeleteLocalRef(pointerIdentifierArray);
- env->DeleteLocalRef(dataSampleArray);
- env->DeleteLocalRef(eventTimeNanoSampleArray);
+ MotionEvent* destEvent = android_view_MotionEvent_getNativePtr(env, eventObj);
+ if (!destEvent) {
+ destEvent = new MotionEvent();
+ android_view_MotionEvent_setNativePtr(env, eventObj, destEvent);
+ }
+
+ destEvent->copyFrom(event, true);
return eventObj;
}
status_t android_view_MotionEvent_toNative(JNIEnv* env, jobject eventObj,
MotionEvent* event) {
- jint deviceId = env->GetIntField(eventObj, gMotionEventClassInfo.mDeviceId);
- jint source = env->GetIntField(eventObj, gMotionEventClassInfo.mSource);
- jlong downTimeNano = env->GetLongField(eventObj, gMotionEventClassInfo.mDownTimeNano);
- jint action = env->GetIntField(eventObj, gMotionEventClassInfo.mAction);
- jfloat xOffset = env->GetFloatField(eventObj, gMotionEventClassInfo.mXOffset);
- jfloat yOffset = env->GetFloatField(eventObj, gMotionEventClassInfo.mYOffset);
- jfloat xPrecision = env->GetFloatField(eventObj, gMotionEventClassInfo.mXPrecision);
- jfloat yPrecision = env->GetFloatField(eventObj, gMotionEventClassInfo.mYPrecision);
- jint edgeFlags = env->GetIntField(eventObj, gMotionEventClassInfo.mEdgeFlags);
- jint metaState = env->GetIntField(eventObj, gMotionEventClassInfo.mMetaState);
- jint flags = env->GetIntField(eventObj, gMotionEventClassInfo.mFlags);
- jint numPointers = env->GetIntField(eventObj, gMotionEventClassInfo.mNumPointers);
- jint numSamples = env->GetIntField(eventObj, gMotionEventClassInfo.mNumSamples);
-
- if (numPointers == 0) {
- LOGE("Malformed MotionEvent: mNumPointers was zero");
+ MotionEvent* srcEvent = android_view_MotionEvent_getNativePtr(env, eventObj);
+ if (!srcEvent) {
+ LOGE("MotionEvent was finalized");
return BAD_VALUE;
}
- if (numSamples == 0) {
- LOGE("Malformed MotionEvent: mNumSamples was zero");
- return BAD_VALUE;
+
+ event->copyFrom(srcEvent, true);
+ return OK;
+}
+
+status_t android_view_MotionEvent_recycle(JNIEnv* env, jobject eventObj) {
+ env->CallVoidMethod(eventObj, gMotionEventClassInfo.recycle);
+ if (env->ExceptionCheck()) {
+ LOGW("An exception occurred while recycling a motion event.");
+ LOGW_EX(env);
+ env->ExceptionClear();
+ return UNKNOWN_ERROR;
+ }
+ return OK;
+}
+
+// ----------------------------------------------------------------------------
+
+static const jint HISTORY_CURRENT = -0x80000000;
+
+static bool validatePointerCount(JNIEnv* env, jint pointerCount) {
+ if (pointerCount < 1) {
+ jniThrowException(env, "java/lang/IllegalArgumentException",
+ "pointerCount must be at least 1");
+ return false;
+ }
+ return true;
+}
+
+static bool validatePointerIdsArray(JNIEnv* env, jintArray pointerIdsArray,
+ size_t pointerCount) {
+ if (!pointerIdsArray) {
+ jniThrowException(env, "java/lang/IllegalArgumentException",
+ "pointerIds array must not be null");
+ return false;
+ }
+ size_t length = size_t(env->GetArrayLength(pointerIdsArray));
+ if (length < pointerCount) {
+ jniThrowException(env, "java/lang/IllegalArgumentException",
+ "pointerIds array must be large enough to hold all pointers");
+ return false;
+ }
+ return true;
+}
+
+static bool validatePointerCoordsObjArray(JNIEnv* env, jobjectArray pointerCoordsObjArray,
+ size_t pointerCount) {
+ if (!pointerCoordsObjArray) {
+ jniThrowException(env, "java/lang/IllegalArgumentException",
+ "pointerCoords array must not be null");
+ return false;
+ }
+ size_t length = size_t(env->GetArrayLength(pointerCoordsObjArray));
+ if (length < pointerCount) {
+ jniThrowException(env, "java/lang/IllegalArgumentException",
+ "pointerCoords array must be large enough to hold all pointers");
+ return false;
+ }
+ return true;
+}
+
+static bool validatePointerIndex(JNIEnv* env, jint pointerIndex, size_t pointerCount) {
+ if (pointerIndex < 0 || size_t(pointerIndex) >= pointerCount) {
+ jniThrowException(env, "java/lang/IllegalArgumentException",
+ "pointerIndex out of range");
+ return false;
+ }
+ return true;
+}
+
+static bool validateHistoryPos(JNIEnv* env, jint historyPos, size_t historySize) {
+ if (historyPos < 0 || size_t(historyPos) >= historySize) {
+ jniThrowException(env, "java/lang/IllegalArgumentException",
+ "historyPos out of range");
+ return false;
+ }
+ return true;
+}
+
+static bool validatePointerCoords(JNIEnv* env, jobject pointerCoordsObj) {
+ if (!pointerCoordsObj) {
+ jniThrowException(env, "java/lang/IllegalArgumentException",
+ "pointerCoords must not be null");
+ return false;
+ }
+ return true;
+}
+
+static void pointerCoordsToNative(JNIEnv* env, jobject pointerCoordsObj,
+ float xOffset, float yOffset, PointerCoords* outRawPointerCoords) {
+ outRawPointerCoords->clear();
+ outRawPointerCoords->setAxisValue(AINPUT_MOTION_AXIS_X,
+ env->GetFloatField(pointerCoordsObj, gPointerCoordsClassInfo.x) - xOffset);
+ outRawPointerCoords->setAxisValue(AINPUT_MOTION_AXIS_Y,
+ env->GetFloatField(pointerCoordsObj, gPointerCoordsClassInfo.y) - yOffset);
+ outRawPointerCoords->setAxisValue(AINPUT_MOTION_AXIS_PRESSURE,
+ env->GetFloatField(pointerCoordsObj, gPointerCoordsClassInfo.pressure));
+ outRawPointerCoords->setAxisValue(AINPUT_MOTION_AXIS_SIZE,
+ env->GetFloatField(pointerCoordsObj, gPointerCoordsClassInfo.size));
+ outRawPointerCoords->setAxisValue(AINPUT_MOTION_AXIS_TOUCH_MAJOR,
+ env->GetFloatField(pointerCoordsObj, gPointerCoordsClassInfo.touchMajor));
+ outRawPointerCoords->setAxisValue(AINPUT_MOTION_AXIS_TOUCH_MINOR,
+ env->GetFloatField(pointerCoordsObj, gPointerCoordsClassInfo.touchMinor));
+ outRawPointerCoords->setAxisValue(AINPUT_MOTION_AXIS_TOOL_MAJOR,
+ env->GetFloatField(pointerCoordsObj, gPointerCoordsClassInfo.toolMajor));
+ outRawPointerCoords->setAxisValue(AINPUT_MOTION_AXIS_TOOL_MINOR,
+ env->GetFloatField(pointerCoordsObj, gPointerCoordsClassInfo.toolMinor));
+ outRawPointerCoords->setAxisValue(AINPUT_MOTION_AXIS_ORIENTATION,
+ env->GetFloatField(pointerCoordsObj, gPointerCoordsClassInfo.orientation));
+
+ uint32_t bits = env->GetIntField(pointerCoordsObj,
+ gPointerCoordsClassInfo.mPackedAxisBits);
+ if (bits) {
+ jfloatArray valuesArray = jfloatArray(env->GetObjectField(pointerCoordsObj,
+ gPointerCoordsClassInfo.mPackedAxisValues));
+ if (valuesArray) {
+ jfloat* values = static_cast<jfloat*>(
+ env->GetPrimitiveArrayCritical(valuesArray, NULL));
+
+ uint32_t index = 0;
+ do {
+ uint32_t axis = __builtin_ctz(bits);
+ uint32_t axisBit = 1 << axis;
+ bits &= ~axisBit;
+ outRawPointerCoords->setAxisValue(axis, values[index++]);
+ } while (bits);
+
+ env->ReleasePrimitiveArrayCritical(valuesArray, values, JNI_ABORT);
+ env->DeleteLocalRef(valuesArray);
+ }
+ }
+}
+
+static jfloatArray obtainPackedAxisValuesArray(JNIEnv* env, uint32_t minSize,
+ jobject outPointerCoordsObj) {
+ jfloatArray outValuesArray = jfloatArray(env->GetObjectField(outPointerCoordsObj,
+ gPointerCoordsClassInfo.mPackedAxisValues));
+ if (outValuesArray) {
+ uint32_t size = env->GetArrayLength(outValuesArray);
+ if (minSize <= size) {
+ return outValuesArray;
+ }
+ env->DeleteLocalRef(outValuesArray);
+ }
+ uint32_t size = 8;
+ while (size < minSize) {
+ size *= 2;
+ }
+ outValuesArray = env->NewFloatArray(size);
+ env->SetObjectField(outPointerCoordsObj,
+ gPointerCoordsClassInfo.mPackedAxisValues, outValuesArray);
+ return outValuesArray;
+}
+
+static void pointerCoordsFromNative(JNIEnv* env, const PointerCoords* rawPointerCoords,
+ float xOffset, float yOffset, jobject outPointerCoordsObj) {
+ env->SetFloatField(outPointerCoordsObj, gPointerCoordsClassInfo.x,
+ rawPointerCoords->getAxisValue(AINPUT_MOTION_AXIS_X) + xOffset);
+ env->SetFloatField(outPointerCoordsObj, gPointerCoordsClassInfo.y,
+ rawPointerCoords->getAxisValue(AINPUT_MOTION_AXIS_Y) + yOffset);
+ env->SetFloatField(outPointerCoordsObj, gPointerCoordsClassInfo.pressure,
+ rawPointerCoords->getAxisValue(AINPUT_MOTION_AXIS_PRESSURE));
+ env->SetFloatField(outPointerCoordsObj, gPointerCoordsClassInfo.size,
+ rawPointerCoords->getAxisValue(AINPUT_MOTION_AXIS_SIZE));
+ env->SetFloatField(outPointerCoordsObj, gPointerCoordsClassInfo.touchMajor,
+ rawPointerCoords->getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MAJOR));
+ env->SetFloatField(outPointerCoordsObj, gPointerCoordsClassInfo.touchMinor,
+ rawPointerCoords->getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MINOR));
+ env->SetFloatField(outPointerCoordsObj, gPointerCoordsClassInfo.toolMajor,
+ rawPointerCoords->getAxisValue(AINPUT_MOTION_AXIS_TOOL_MAJOR));
+ env->SetFloatField(outPointerCoordsObj, gPointerCoordsClassInfo.toolMinor,
+ rawPointerCoords->getAxisValue(AINPUT_MOTION_AXIS_TOOL_MINOR));
+ env->SetFloatField(outPointerCoordsObj, gPointerCoordsClassInfo.orientation,
+ rawPointerCoords->getAxisValue(AINPUT_MOTION_AXIS_ORIENTATION));
+
+ const uint32_t unpackedAxisBits = 0
+ | (1 << AINPUT_MOTION_AXIS_X)
+ | (1 << AINPUT_MOTION_AXIS_Y)
+ | (1 << AINPUT_MOTION_AXIS_PRESSURE)
+ | (1 << AINPUT_MOTION_AXIS_SIZE)
+ | (1 << AINPUT_MOTION_AXIS_TOUCH_MAJOR)
+ | (1 << AINPUT_MOTION_AXIS_TOUCH_MINOR)
+ | (1 << AINPUT_MOTION_AXIS_TOOL_MAJOR)
+ | (1 << AINPUT_MOTION_AXIS_TOOL_MINOR)
+ | (1 << AINPUT_MOTION_AXIS_ORIENTATION);
+
+ uint32_t outBits = 0;
+ uint32_t remainingBits = rawPointerCoords->bits & ~unpackedAxisBits;
+ if (remainingBits) {
+ uint32_t packedAxesCount = __builtin_popcount(remainingBits);
+ jfloatArray outValuesArray = obtainPackedAxisValuesArray(env, packedAxesCount,
+ outPointerCoordsObj);
+ if (!outValuesArray) {
+ return; // OOM
+ }
+
+ jfloat* outValues = static_cast<jfloat*>(env->GetPrimitiveArrayCritical(
+ outValuesArray, NULL));
+
+ const float* values = rawPointerCoords->values;
+ uint32_t index = 0;
+ do {
+ uint32_t axis = __builtin_ctz(remainingBits);
+ uint32_t axisBit = 1 << axis;
+ remainingBits &= ~axisBit;
+ outBits |= axisBit;
+ outValues[index++] = rawPointerCoords->getAxisValue(axis);
+ } while (remainingBits);
+
+ env->ReleasePrimitiveArrayCritical(outValuesArray, outValues, 0);
+ env->DeleteLocalRef(outValuesArray);
}
+ env->SetIntField(outPointerCoordsObj, gPointerCoordsClassInfo.mPackedAxisBits, outBits);
+}
- jintArray pointerIdentifierArray = jintArray(env->GetObjectField(eventObj,
- gMotionEventClassInfo.mPointerIdentifiers));
- jfloatArray dataSampleArray = jfloatArray(env->GetObjectField(eventObj,
- gMotionEventClassInfo.mDataSamples));
- jlongArray eventTimeNanoSampleArray = jlongArray(env->GetObjectField(eventObj,
- gMotionEventClassInfo.mEventTimeNanoSamples));
- jint* pointerIdentifiers = (jint*)env->GetPrimitiveArrayCritical(pointerIdentifierArray, NULL);
- jfloat* dataSamples = (jfloat*)env->GetPrimitiveArrayCritical(dataSampleArray, NULL);
- jlong* eventTimeNanoSamples = (jlong*)env->GetPrimitiveArrayCritical(
- eventTimeNanoSampleArray, NULL);
+// ----------------------------------------------------------------------------
- jfloat* srcDataSamples = dataSamples;
- jlong* srcEventTimeNanoSamples = eventTimeNanoSamples;
+static jint android_view_MotionEvent_nativeInitialize(JNIEnv* env, jclass clazz,
+ jint nativePtr,
+ jint deviceId, jint source, jint action, jint flags, jint edgeFlags, jint metaState,
+ jfloat xOffset, jfloat yOffset, jfloat xPrecision, jfloat yPrecision,
+ jlong downTimeNanos, jlong eventTimeNanos,
+ jint pointerCount, jintArray pointerIdsArray, jobjectArray pointerCoordsObjArray) {
+ if (!validatePointerCount(env, pointerCount)
+ || !validatePointerIdsArray(env, pointerIdsArray, pointerCount)
+ || !validatePointerCoordsObjArray(env, pointerCoordsObjArray, pointerCount)) {
+ return 0;
+ }
- jlong sampleEventTime = *(srcEventTimeNanoSamples++);
- PointerCoords samplePointerCoords[MAX_POINTERS];
- for (jint j = 0; j < numPointers; j++) {
- samplePointerCoords[j].x = *(srcDataSamples++);
- samplePointerCoords[j].y = *(srcDataSamples++);
- samplePointerCoords[j].pressure = *(srcDataSamples++);
- samplePointerCoords[j].size = *(srcDataSamples++);
- samplePointerCoords[j].touchMajor = *(srcDataSamples++);
- samplePointerCoords[j].touchMinor = *(srcDataSamples++);
- samplePointerCoords[j].toolMajor = *(srcDataSamples++);
- samplePointerCoords[j].toolMinor = *(srcDataSamples++);
- samplePointerCoords[j].orientation = *(srcDataSamples++);
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ if (!event) {
+ event = new MotionEvent();
}
+ PointerCoords rawPointerCoords[pointerCount];
+
+ for (jint i = 0; i < pointerCount; i++) {
+ jobject pointerCoordsObj = env->GetObjectArrayElement(pointerCoordsObjArray, i);
+ if (!pointerCoordsObj) {
+ jniThrowNullPointerException(env, "pointerCoords");
+ if (!nativePtr) {
+ delete event;
+ }
+ return 0;
+ }
+ pointerCoordsToNative(env, pointerCoordsObj, xOffset, yOffset, &rawPointerCoords[i]);
+ env->DeleteLocalRef(pointerCoordsObj);
+ }
+
+ int* pointerIds = static_cast<int*>(env->GetPrimitiveArrayCritical(pointerIdsArray, NULL));
+
event->initialize(deviceId, source, action, flags, edgeFlags, metaState,
- xOffset, yOffset, xPrecision, yPrecision, downTimeNano, sampleEventTime,
- numPointers, pointerIdentifiers, samplePointerCoords);
-
- for (jint i = 1; i < numSamples; i++) {
- sampleEventTime = *(srcEventTimeNanoSamples++);
- for (jint j = 0; j < numPointers; j++) {
- samplePointerCoords[j].x = *(srcDataSamples++);
- samplePointerCoords[j].y = *(srcDataSamples++);
- samplePointerCoords[j].pressure = *(srcDataSamples++);
- samplePointerCoords[j].size = *(srcDataSamples++);
- samplePointerCoords[j].touchMajor = *(srcDataSamples++);
- samplePointerCoords[j].touchMinor = *(srcDataSamples++);
- samplePointerCoords[j].toolMajor = *(srcDataSamples++);
- samplePointerCoords[j].toolMinor = *(srcDataSamples++);
- samplePointerCoords[j].orientation = *(srcDataSamples++);
+ xOffset, yOffset, xPrecision, yPrecision,
+ downTimeNanos, eventTimeNanos, pointerCount, pointerIds, rawPointerCoords);
+
+ env->ReleasePrimitiveArrayCritical(pointerIdsArray, pointerIds, JNI_ABORT);
+ return reinterpret_cast<jint>(event);
+}
+
+static jint android_view_MotionEvent_nativeCopy(JNIEnv* env, jclass clazz,
+ jint destNativePtr, jint sourceNativePtr, jboolean keepHistory) {
+ MotionEvent* destEvent = reinterpret_cast<MotionEvent*>(destNativePtr);
+ if (!destEvent) {
+ destEvent = new MotionEvent();
+ }
+ MotionEvent* sourceEvent = reinterpret_cast<MotionEvent*>(sourceNativePtr);
+ destEvent->copyFrom(sourceEvent, keepHistory);
+ return reinterpret_cast<jint>(destEvent);
+}
+
+static void android_view_MotionEvent_nativeDispose(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ delete event;
+}
+
+static void android_view_MotionEvent_nativeAddBatch(JNIEnv* env, jclass clazz,
+ jint nativePtr, jlong eventTimeNanos, jobjectArray pointerCoordsObjArray,
+ jint metaState) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ size_t pointerCount = event->getPointerCount();
+ if (!validatePointerCoordsObjArray(env, pointerCoordsObjArray, pointerCount)) {
+ return;
+ }
+
+ PointerCoords rawPointerCoords[pointerCount];
+
+ for (size_t i = 0; i < pointerCount; i++) {
+ jobject pointerCoordsObj = env->GetObjectArrayElement(pointerCoordsObjArray, i);
+ if (!pointerCoordsObj) {
+ jniThrowNullPointerException(env, "pointerCoords");
+ return;
}
- event->addSample(sampleEventTime, samplePointerCoords);
+ pointerCoordsToNative(env, pointerCoordsObj,
+ event->getXOffset(), event->getYOffset(), &rawPointerCoords[i]);
+ env->DeleteLocalRef(pointerCoordsObj);
}
- env->ReleasePrimitiveArrayCritical(eventTimeNanoSampleArray, eventTimeNanoSamples, JNI_ABORT);
- env->ReleasePrimitiveArrayCritical(dataSampleArray, dataSamples, JNI_ABORT);
- env->ReleasePrimitiveArrayCritical(pointerIdentifierArray, pointerIdentifiers, JNI_ABORT);
+ event->addSample(eventTimeNanos, rawPointerCoords);
+ event->setMetaState(event->getMetaState() | metaState);
+}
- env->DeleteLocalRef(eventTimeNanoSampleArray);
- env->DeleteLocalRef(dataSampleArray);
- env->DeleteLocalRef(pointerIdentifierArray);
- return OK;
+static jint android_view_MotionEvent_nativeGetDeviceId(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return event->getDeviceId();
}
-status_t android_view_MotionEvent_recycle(JNIEnv* env, jobject eventObj) {
- env->CallVoidMethod(eventObj, gMotionEventClassInfo.recycle);
- if (env->ExceptionCheck()) {
- LOGW("An exception occurred while recycling a motion event.");
- LOGW_EX(env);
- env->ExceptionClear();
- return UNKNOWN_ERROR;
+static jint android_view_MotionEvent_nativeGetSource(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return event->getSource();
+}
+
+static void android_view_MotionEvent_nativeSetSource(JNIEnv* env, jclass clazz,
+ jint nativePtr, jint source) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ event->setSource(source);
+}
+
+static jint android_view_MotionEvent_nativeGetAction(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return event->getAction();
+}
+
+static void android_view_MotionEvent_nativeSetAction(JNIEnv* env, jclass clazz,
+ jint nativePtr, jint action) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ event->setAction(action);
+}
+
+static jint android_view_MotionEvent_nativeGetFlags(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return event->getFlags();
+}
+
+static jint android_view_MotionEvent_nativeGetEdgeFlags(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return event->getEdgeFlags();
+}
+
+static void android_view_MotionEvent_nativeSetEdgeFlags(JNIEnv* env, jclass clazz,
+ jint nativePtr, jint edgeFlags) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ event->setEdgeFlags(edgeFlags);
+}
+
+static jint android_view_MotionEvent_nativeGetMetaState(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return event->getMetaState();
+}
+
+static void android_view_MotionEvent_nativeOffsetLocation(JNIEnv* env, jclass clazz,
+ jint nativePtr, jfloat deltaX, jfloat deltaY) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return event->offsetLocation(deltaX, deltaY);
+}
+
+static jfloat android_view_MotionEvent_nativeGetXPrecision(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return event->getXPrecision();
+}
+
+static jfloat android_view_MotionEvent_nativeGetYPrecision(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return event->getYPrecision();
+}
+
+static jlong android_view_MotionEvent_nativeGetDownTimeNanos(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return event->getDownTime();
+}
+
+static jint android_view_MotionEvent_nativeGetPointerCount(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return jint(event->getPointerCount());
+}
+
+static jint android_view_MotionEvent_nativeGetPointerId(JNIEnv* env, jclass clazz,
+ jint nativePtr, jint pointerIndex) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ size_t pointerCount = event->getPointerCount();
+ if (!validatePointerIndex(env, pointerIndex, pointerCount)) {
+ return -1;
}
- return OK;
+ return event->getPointerId(pointerIndex);
}
-static inline float transformAngle(const SkMatrix* matrix, float angleRadians) {
- // Construct and transform a vector oriented at the specified clockwise angle from vertical.
- // Coordinate system: down is increasing Y, right is increasing X.
- SkPoint vector;
- vector.fX = SkFloatToScalar(sinf(angleRadians));
- vector.fY = SkFloatToScalar(- cosf(angleRadians));
- matrix->mapVectors(& vector, 1);
+static jint android_view_MotionEvent_nativeFindPointerIndex(JNIEnv* env, jclass clazz,
+ jint nativePtr, jint pointerId) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ size_t pointerCount = event->getPointerCount();
+ for (size_t i = 0; i < pointerCount; i++) {
+ if (event->getPointerId(i) == pointerId) {
+ return i;
+ }
+ }
+ return -1;
+}
+
+static jint android_view_MotionEvent_nativeGetHistorySize(JNIEnv* env, jclass clazz,
+ jint nativePtr) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ return jint(event->getHistorySize());
+}
- // Derive the transformed vector's clockwise angle from vertical.
- float result = atan2f(SkScalarToFloat(vector.fX), SkScalarToFloat(- vector.fY));
- if (result < - M_PI_2) {
- result += M_PI;
- } else if (result > M_PI_2) {
- result -= M_PI;
+static jlong android_view_MotionEvent_nativeGetEventTimeNanos(JNIEnv* env, jclass clazz,
+ jint nativePtr, jint historyPos) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ if (historyPos == HISTORY_CURRENT) {
+ return event->getEventTime();
+ } else {
+ size_t historySize = event->getHistorySize();
+ if (!validateHistoryPos(env, historyPos, historySize)) {
+ return 0;
+ }
+ return event->getHistoricalEventTime(historyPos);
}
- return result;
}
-static void android_view_MotionEvent_nativeTransform(JNIEnv* env,
- jobject eventObj, jobject matrixObj) {
- SkMatrix* matrix = android_graphics_Matrix_getSkMatrix(env, matrixObj);
+static jfloat android_view_MotionEvent_nativeGetRawAxisValue(JNIEnv* env, jclass clazz,
+ jint nativePtr, jint axis, jint pointerIndex, jint historyPos) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ size_t pointerCount = event->getPointerCount();
+ if (!validatePointerIndex(env, pointerIndex, pointerCount)) {
+ return 0;
+ }
- jfloat oldXOffset = env->GetFloatField(eventObj, gMotionEventClassInfo.mXOffset);
- jfloat oldYOffset = env->GetFloatField(eventObj, gMotionEventClassInfo.mYOffset);
- jint numPointers = env->GetIntField(eventObj, gMotionEventClassInfo.mNumPointers);
- jint numSamples = env->GetIntField(eventObj, gMotionEventClassInfo.mNumSamples);
- jfloatArray dataSampleArray = jfloatArray(env->GetObjectField(eventObj,
- gMotionEventClassInfo.mDataSamples));
- jfloat* dataSamples = (jfloat*)env->GetPrimitiveArrayCritical(dataSampleArray, NULL);
-
- // The tricky part of this implementation is to preserve the value of
- // rawX and rawY. So we apply the transformation to the first point
- // then derive an appropriate new X/Y offset that will preserve rawX and rawY.
- SkPoint point;
- jfloat rawX = dataSamples[SAMPLE_X];
- jfloat rawY = dataSamples[SAMPLE_Y];
- matrix->mapXY(SkFloatToScalar(rawX + oldXOffset), SkFloatToScalar(rawY + oldYOffset),
- & point);
- jfloat newX = SkScalarToFloat(point.fX);
- jfloat newY = SkScalarToFloat(point.fY);
- jfloat newXOffset = newX - rawX;
- jfloat newYOffset = newY - rawY;
-
- dataSamples[SAMPLE_ORIENTATION] = transformAngle(matrix, dataSamples[SAMPLE_ORIENTATION]);
-
- // Apply the transformation to all samples.
- jfloat* currentDataSample = dataSamples;
- jfloat* endDataSample = dataSamples + numPointers * numSamples * NUM_SAMPLE_DATA;
- for (;;) {
- currentDataSample += NUM_SAMPLE_DATA;
- if (currentDataSample == endDataSample) {
- break;
+ if (historyPos == HISTORY_CURRENT) {
+ return event->getRawAxisValue(axis, pointerIndex);
+ } else {
+ size_t historySize = event->getHistorySize();
+ if (!validateHistoryPos(env, historyPos, historySize)) {
+ return 0;
}
+ return event->getHistoricalRawAxisValue(axis, pointerIndex, historyPos);
+ }
+}
- jfloat x = currentDataSample[SAMPLE_X] + oldXOffset;
- jfloat y = currentDataSample[SAMPLE_Y] + oldYOffset;
- matrix->mapXY(SkFloatToScalar(x), SkFloatToScalar(y), & point);
- currentDataSample[SAMPLE_X] = SkScalarToFloat(point.fX) - newXOffset;
- currentDataSample[SAMPLE_Y] = SkScalarToFloat(point.fY) - newYOffset;
+static jfloat android_view_MotionEvent_nativeGetAxisValue(JNIEnv* env, jclass clazz,
+ jint nativePtr, jint axis, jint pointerIndex, jint historyPos) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ size_t pointerCount = event->getPointerCount();
+ if (!validatePointerIndex(env, pointerIndex, pointerCount)) {
+ return 0;
+ }
- currentDataSample[SAMPLE_ORIENTATION] = transformAngle(matrix,
- currentDataSample[SAMPLE_ORIENTATION]);
+ if (historyPos == HISTORY_CURRENT) {
+ return event->getAxisValue(axis, pointerIndex);
+ } else {
+ size_t historySize = event->getHistorySize();
+ if (!validateHistoryPos(env, historyPos, historySize)) {
+ return 0;
+ }
+ return event->getHistoricalAxisValue(axis, pointerIndex, historyPos);
}
+}
- env->ReleasePrimitiveArrayCritical(dataSampleArray, dataSamples, 0);
+static void android_view_MotionEvent_nativeGetPointerCoords(JNIEnv* env, jclass clazz,
+ jint nativePtr, jint pointerIndex, jint historyPos, jobject outPointerCoordsObj) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ size_t pointerCount = event->getPointerCount();
+ if (!validatePointerIndex(env, pointerIndex, pointerCount)
+ || !validatePointerCoords(env, outPointerCoordsObj)) {
+ return;
+ }
- env->SetFloatField(eventObj, gMotionEventClassInfo.mXOffset, newXOffset);
- env->SetFloatField(eventObj, gMotionEventClassInfo.mYOffset, newYOffset);
+ const PointerCoords* rawPointerCoords;
+ if (historyPos == HISTORY_CURRENT) {
+ rawPointerCoords = event->getRawPointerCoords(pointerIndex);
+ } else {
+ size_t historySize = event->getHistorySize();
+ if (!validateHistoryPos(env, historyPos, historySize)) {
+ return;
+ }
+ rawPointerCoords = event->getHistoricalRawPointerCoords(pointerIndex, historyPos);
+ }
+ pointerCoordsFromNative(env, rawPointerCoords, event->getXOffset(), event->getYOffset(),
+ outPointerCoordsObj);
+}
+
+static void android_view_MotionEvent_nativeScale(JNIEnv* env, jclass clazz,
+ jint nativePtr, jfloat scale) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ event->scale(scale);
+}
+
+static void android_view_MotionEvent_nativeTransform(JNIEnv* env, jclass clazz,
+ jint nativePtr, jobject matrixObj) {
+ SkMatrix* matrix = android_graphics_Matrix_getSkMatrix(env, matrixObj);
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ event->transform(matrix);
+}
+
+static jint android_view_MotionEvent_nativeReadFromParcel(JNIEnv* env, jclass clazz,
+ jint nativePtr, jobject parcelObj) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ if (!event) {
+ event = new MotionEvent();
+ }
+
+ Parcel* parcel = parcelForJavaObject(env, parcelObj);
- env->DeleteLocalRef(dataSampleArray);
+ status_t status = event->readFromParcel(parcel);
+ if (!status) {
+ if (!nativePtr) {
+ delete event;
+ }
+ jniThrowRuntimeException(env, "Failed to read MotionEvent parcel.");
+ return 0;
+ }
+ return reinterpret_cast<jint>(event);
+}
+
+static void android_view_MotionEvent_nativeWriteToParcel(JNIEnv* env, jclass clazz,
+ jint nativePtr, jobject parcelObj) {
+ MotionEvent* event = reinterpret_cast<MotionEvent*>(nativePtr);
+ Parcel* parcel = parcelForJavaObject(env, parcelObj);
+
+ status_t status = event->writeToParcel(parcel);
+ if (!status) {
+ jniThrowRuntimeException(env, "Failed to write MotionEvent parcel.");
+ }
}
// ----------------------------------------------------------------------------
static JNINativeMethod gMotionEventMethods[] = {
/* name, signature, funcPtr */
+ { "nativeInitialize",
+ "(IIIIIIIFFFFJJI[I[Landroid/view/MotionEvent$PointerCoords;)I",
+ (void*)android_view_MotionEvent_nativeInitialize },
+ { "nativeCopy",
+ "(IIZ)I",
+ (void*)android_view_MotionEvent_nativeCopy },
+ { "nativeDispose",
+ "(I)V",
+ (void*)android_view_MotionEvent_nativeDispose },
+ { "nativeAddBatch",
+ "(IJ[Landroid/view/MotionEvent$PointerCoords;I)V",
+ (void*)android_view_MotionEvent_nativeAddBatch },
+ { "nativeGetDeviceId",
+ "(I)I",
+ (void*)android_view_MotionEvent_nativeGetDeviceId },
+ { "nativeGetSource",
+ "(I)I",
+ (void*)android_view_MotionEvent_nativeGetSource },
+ { "nativeSetSource",
+ "(II)I",
+ (void*)android_view_MotionEvent_nativeSetSource },
+ { "nativeGetAction",
+ "(I)I",
+ (void*)android_view_MotionEvent_nativeGetAction },
+ { "nativeSetAction",
+ "(II)V",
+ (void*)android_view_MotionEvent_nativeSetAction },
+ { "nativeGetFlags",
+ "(I)I",
+ (void*)android_view_MotionEvent_nativeGetFlags },
+ { "nativeGetEdgeFlags",
+ "(I)I",
+ (void*)android_view_MotionEvent_nativeGetEdgeFlags },
+ { "nativeSetEdgeFlags",
+ "(II)V",
+ (void*)android_view_MotionEvent_nativeSetEdgeFlags },
+ { "nativeGetMetaState",
+ "(I)I",
+ (void*)android_view_MotionEvent_nativeGetMetaState },
+ { "nativeOffsetLocation",
+ "(IFF)V",
+ (void*)android_view_MotionEvent_nativeOffsetLocation },
+ { "nativeGetXPrecision",
+ "(I)F",
+ (void*)android_view_MotionEvent_nativeGetXPrecision },
+ { "nativeGetYPrecision",
+ "(I)F",
+ (void*)android_view_MotionEvent_nativeGetYPrecision },
+ { "nativeGetDownTimeNanos",
+ "(I)J",
+ (void*)android_view_MotionEvent_nativeGetDownTimeNanos },
+ { "nativeGetPointerCount",
+ "(I)I",
+ (void*)android_view_MotionEvent_nativeGetPointerCount },
+ { "nativeGetPointerId",
+ "(II)I",
+ (void*)android_view_MotionEvent_nativeGetPointerId },
+ { "nativeFindPointerIndex",
+ "(II)I",
+ (void*)android_view_MotionEvent_nativeFindPointerIndex },
+ { "nativeGetHistorySize",
+ "(I)I",
+ (void*)android_view_MotionEvent_nativeGetHistorySize },
+ { "nativeGetEventTimeNanos",
+ "(II)J",
+ (void*)android_view_MotionEvent_nativeGetEventTimeNanos },
+ { "nativeGetRawAxisValue",
+ "(IIII)F",
+ (void*)android_view_MotionEvent_nativeGetRawAxisValue },
+ { "nativeGetAxisValue",
+ "(IIII)F",
+ (void*)android_view_MotionEvent_nativeGetAxisValue },
+ { "nativeGetPointerCoords",
+ "(IIILandroid/view/MotionEvent$PointerCoords;)V",
+ (void*)android_view_MotionEvent_nativeGetPointerCoords },
+ { "nativeScale",
+ "(IF)V",
+ (void*)android_view_MotionEvent_nativeScale },
{ "nativeTransform",
- "(Landroid/graphics/Matrix;)V",
+ "(ILandroid/graphics/Matrix;)V",
(void*)android_view_MotionEvent_nativeTransform },
+ { "nativeReadFromParcel",
+ "(ILandroid/os/Parcel;)I",
+ (void*)android_view_MotionEvent_nativeReadFromParcel },
+ { "nativeWriteToParcel",
+ "(ILandroid/os/Parcel;)V",
+ (void*)android_view_MotionEvent_nativeWriteToParcel },
};
#define FIND_CLASS(var, className) \
@@ -370,46 +749,36 @@ int register_android_view_MotionEvent(JNIEnv* env) {
FIND_CLASS(gMotionEventClassInfo.clazz, "android/view/MotionEvent");
GET_STATIC_METHOD_ID(gMotionEventClassInfo.obtain, gMotionEventClassInfo.clazz,
- "obtain", "(II)Landroid/view/MotionEvent;");
+ "obtain", "()Landroid/view/MotionEvent;");
GET_METHOD_ID(gMotionEventClassInfo.recycle, gMotionEventClassInfo.clazz,
"recycle", "()V");
-
- GET_FIELD_ID(gMotionEventClassInfo.mDeviceId, gMotionEventClassInfo.clazz,
- "mDeviceId", "I");
- GET_FIELD_ID(gMotionEventClassInfo.mSource, gMotionEventClassInfo.clazz,
- "mSource", "I");
- GET_FIELD_ID(gMotionEventClassInfo.mDownTimeNano, gMotionEventClassInfo.clazz,
- "mDownTimeNano", "J");
- GET_FIELD_ID(gMotionEventClassInfo.mAction, gMotionEventClassInfo.clazz,
- "mAction", "I");
- GET_FIELD_ID(gMotionEventClassInfo.mXOffset, gMotionEventClassInfo.clazz,
- "mXOffset", "F");
- GET_FIELD_ID(gMotionEventClassInfo.mYOffset, gMotionEventClassInfo.clazz,
- "mYOffset", "F");
- GET_FIELD_ID(gMotionEventClassInfo.mXPrecision, gMotionEventClassInfo.clazz,
- "mXPrecision", "F");
- GET_FIELD_ID(gMotionEventClassInfo.mYPrecision, gMotionEventClassInfo.clazz,
- "mYPrecision", "F");
- GET_FIELD_ID(gMotionEventClassInfo.mEdgeFlags, gMotionEventClassInfo.clazz,
- "mEdgeFlags", "I");
- GET_FIELD_ID(gMotionEventClassInfo.mMetaState, gMotionEventClassInfo.clazz,
- "mMetaState", "I");
- GET_FIELD_ID(gMotionEventClassInfo.mFlags, gMotionEventClassInfo.clazz,
- "mFlags", "I");
- GET_FIELD_ID(gMotionEventClassInfo.mNumPointers, gMotionEventClassInfo.clazz,
- "mNumPointers", "I");
- GET_FIELD_ID(gMotionEventClassInfo.mNumSamples, gMotionEventClassInfo.clazz,
- "mNumSamples", "I");
- GET_FIELD_ID(gMotionEventClassInfo.mPointerIdentifiers, gMotionEventClassInfo.clazz,
- "mPointerIdentifiers", "[I");
- GET_FIELD_ID(gMotionEventClassInfo.mDataSamples, gMotionEventClassInfo.clazz,
- "mDataSamples", "[F");
- GET_FIELD_ID(gMotionEventClassInfo.mEventTimeNanoSamples, gMotionEventClassInfo.clazz,
- "mEventTimeNanoSamples", "[J");
- GET_FIELD_ID(gMotionEventClassInfo.mLastDataSampleIndex, gMotionEventClassInfo.clazz,
- "mLastDataSampleIndex", "I");
- GET_FIELD_ID(gMotionEventClassInfo.mLastEventTimeNanoSampleIndex, gMotionEventClassInfo.clazz,
- "mLastEventTimeNanoSampleIndex", "I");
+ GET_FIELD_ID(gMotionEventClassInfo.mNativePtr, gMotionEventClassInfo.clazz,
+ "mNativePtr", "I");
+
+ FIND_CLASS(gPointerCoordsClassInfo.clazz, "android/view/MotionEvent$PointerCoords");
+
+ GET_FIELD_ID(gPointerCoordsClassInfo.mPackedAxisBits, gPointerCoordsClassInfo.clazz,
+ "mPackedAxisBits", "I");
+ GET_FIELD_ID(gPointerCoordsClassInfo.mPackedAxisValues, gPointerCoordsClassInfo.clazz,
+ "mPackedAxisValues", "[F");
+ GET_FIELD_ID(gPointerCoordsClassInfo.x, gPointerCoordsClassInfo.clazz,
+ "x", "F");
+ GET_FIELD_ID(gPointerCoordsClassInfo.y, gPointerCoordsClassInfo.clazz,
+ "y", "F");
+ GET_FIELD_ID(gPointerCoordsClassInfo.pressure, gPointerCoordsClassInfo.clazz,
+ "pressure", "F");
+ GET_FIELD_ID(gPointerCoordsClassInfo.size, gPointerCoordsClassInfo.clazz,
+ "size", "F");
+ GET_FIELD_ID(gPointerCoordsClassInfo.touchMajor, gPointerCoordsClassInfo.clazz,
+ "touchMajor", "F");
+ GET_FIELD_ID(gPointerCoordsClassInfo.touchMinor, gPointerCoordsClassInfo.clazz,
+ "touchMinor", "F");
+ GET_FIELD_ID(gPointerCoordsClassInfo.toolMajor, gPointerCoordsClassInfo.clazz,
+ "toolMajor", "F");
+ GET_FIELD_ID(gPointerCoordsClassInfo.toolMinor, gPointerCoordsClassInfo.clazz,
+ "toolMinor", "F");
+ GET_FIELD_ID(gPointerCoordsClassInfo.orientation, gPointerCoordsClassInfo.clazz,
+ "orientation", "F");
return 0;
}
diff --git a/core/res/res/drawable-hdpi/text_cursor_holo_dark.9.png b/core/res/res/drawable-hdpi/text_cursor_holo_dark.9.png
new file mode 100644
index 0000000..b9435b6
--- /dev/null
+++ b/core/res/res/drawable-hdpi/text_cursor_holo_dark.9.png
Binary files differ
diff --git a/core/res/res/drawable-hdpi/text_cursor_holo_light.9.png b/core/res/res/drawable-hdpi/text_cursor_holo_light.9.png
new file mode 100644
index 0000000..477d820
--- /dev/null
+++ b/core/res/res/drawable-hdpi/text_cursor_holo_light.9.png
Binary files differ
diff --git a/core/res/res/raw-es/incognito_mode_start_page.html b/core/res/res/raw-es/incognito_mode_start_page.html
new file mode 100644
index 0000000..43fd37f
--- /dev/null
+++ b/core/res/res/raw-es/incognito_mode_start_page.html
@@ -0,0 +1,26 @@
+<html>
+ <head>
+ <meta name="viewport" content="width=device-width, initial-scale=1.0, user-scalable=no"/>
+ <title>Nueva ventana de incógnito</title>
+ </head>
+ <body>
+ <p><strong>Has entrado en el modo &quot;Navegar de incógnito&quot;</strong>. Las páginas
+ que consultes a través de esta ventana no quedarán registradas en el historial del navegador
+ ni en el historial de búsquedas, y tampoco dejarán otros rastros en el equipo (como cookies)
+ una vez cerrada. Aunque sí quedarán almacenados los archivos que descargues y los marcadores
+ que guardes durante la sesión.</p>
+
+ <p><strong>La función &quot;Navegar de incógnito&quot; no afecta al comportamiento de
+ otros usuarios, servidores o programas. Atención con:</strong></p>
+
+ <ul>
+ <li>sitios web que recopilan o comparten información personal,</li>
+ <li>proveedores de servicios de Internet o trabajadores de estas empresas que
+ supervisan las páginas que visita el usuario,</li>
+ <li>software malicioso que realiza un seguimiento de las teclas que pulsa el usuario a
+ cambio de unos emoticones gratuitos,</li>
+ <li>el seguimiento por parte de detectives privados,</li>
+ <li>personas merodeando cerca de tu equipo.</li>
+ </ul>
+ </body>
+</html>
diff --git a/core/res/res/raw/incognito_mode_start_page.html b/core/res/res/raw/incognito_mode_start_page.html
new file mode 100644
index 0000000..5d7a3fb
--- /dev/null
+++ b/core/res/res/raw/incognito_mode_start_page.html
@@ -0,0 +1,24 @@
+<html>
+ <head>
+ <meta name="viewport" content="width=device-width, initial-scale=1.0, user-scalable=no"/>
+ <title>New incognito window</title>
+ </head>
+ <body>
+ <p><strong>You've gone incognito</strong>. Pages you view in this window
+ won't appear in your browser history or search history, and they won't
+ leave other traces, like cookies, on your device after you close the
+ incognito window. Any files you download or bookmarks you create will be
+ preserved, however.</p>
+
+ <p><strong>Going incognito doesn't affect the behavior of other people,
+ servers, or software. Be wary of:</strong></p>
+
+ <ul>
+ <li>Websites that collect or share information about you</li>
+ <li>Internet service providers or employers that track the pages you visit</li>
+ <li>Malicious software that tracks your keystrokes in exchange for free smileys</li>
+ <li>Surveillance by secret agents</li>
+ <li>People standing behind you</li>
+ </ul>
+ </body>
+</html>
diff --git a/core/res/res/values/strings.xml b/core/res/res/values/strings.xml
index d09210e..361bb6c 100755
--- a/core/res/res/values/strings.xml
+++ b/core/res/res/values/strings.xml
@@ -1413,10 +1413,10 @@
to be used while policy is enabled. Only the first device admin
sets the effective global proxy.</string>
<!-- Title of policy access to enforce password expiration [CHAR LIMIT=30]-->
- <string name="policylab_expirePassword">Set password expiration</string>
+ <string name="policylab_expirePassword">Set lock-screen password expiration</string>
<!-- Description of policy access to enforce password expiration [CHAR LIMIT=110]-->
- <string name="policydesc_expirePassword">Control how long before lockscreen password needs to be
- changed</string>
+ <string name="policydesc_expirePassword">Control how frequently the lock-screen password must be
+ changed</string>
<!-- Title of policy access to require encrypted storage [CHAR LIMIT=30]-->
<string name="policylab_encryptedStorage">Set storage encryption</string>
<!-- Description of policy access to require encrypted storage [CHAR LIMIT=110]-->
diff --git a/graphics/java/android/graphics/Bitmap.java b/graphics/java/android/graphics/Bitmap.java
index b2f4379..12dc93c 100644
--- a/graphics/java/android/graphics/Bitmap.java
+++ b/graphics/java/android/graphics/Bitmap.java
@@ -19,7 +19,6 @@ package android.graphics;
import android.os.Parcel;
import android.os.Parcelable;
import android.util.DisplayMetrics;
-
import java.io.OutputStream;
import java.nio.Buffer;
import java.nio.ByteBuffer;
@@ -342,7 +341,7 @@ public final class Bitmap implements Parcelable {
}
long bufferSize = (long)elements << shift;
- long pixelSize = (long)getRowBytes() * getHeight();
+ long pixelSize = getByteCount();
if (bufferSize < pixelSize) {
throw new RuntimeException("Buffer not large enough for pixels");
@@ -378,7 +377,7 @@ public final class Bitmap implements Parcelable {
}
long bufferBytes = (long)elements << shift;
- long bitmapBytes = (long)getRowBytes() * getHeight();
+ long bitmapBytes = getByteCount();
if (bufferBytes < bitmapBytes) {
throw new RuntimeException("Buffer not large enough for pixels");
@@ -822,6 +821,14 @@ public final class Bitmap implements Parcelable {
}
/**
+ * Returns the number of bytes used to store this bitmap's pixels.
+ */
+ public final int getByteCount() {
+ // int result permits bitmaps up to 46,340 x 46,340
+ return getRowBytes() * getHeight();
+ }
+
+ /**
* If the bitmap's internal config is in one of the public formats, return
* that config, otherwise return null.
*/
diff --git a/graphics/java/android/graphics/Paint.java b/graphics/java/android/graphics/Paint.java
index d8a7f9d..0a23bae 100644
--- a/graphics/java/android/graphics/Paint.java
+++ b/graphics/java/android/graphics/Paint.java
@@ -1254,9 +1254,7 @@ public class Paint {
* @param text The text to measure
* @param index The offset into text to begin measuring at
* @param count The number of maximum number of entries to measure. If count
- * is negative, then the characters before index are measured
- * in reverse order. This allows for measuring the end of
- * string.
+ * is negative, then the characters are measured in reverse order.
* @param maxWidth The maximum width to accumulate.
* @param measuredWidth Optional. If not null, returns the actual width
* measured.
diff --git a/graphics/tests/graphicstests/src/android/graphics/BitmapTest.java b/graphics/tests/graphicstests/src/android/graphics/BitmapTest.java
index 6734bb7..685a998 100644
--- a/graphics/tests/graphicstests/src/android/graphics/BitmapTest.java
+++ b/graphics/tests/graphicstests/src/android/graphics/BitmapTest.java
@@ -16,8 +16,6 @@
package android.graphics;
-import android.graphics.Bitmap;
-import android.graphics.Color;
import android.test.suitebuilder.annotation.SmallTest;
import junit.framework.TestCase;
@@ -42,6 +40,10 @@ public class BitmapTest extends TestCase {
assertEquals("rowbytes", 200, bm2.getRowBytes());
assertEquals("rowbytes", 200, bm3.getRowBytes());
+ assertEquals("byteCount", 80000, bm1.getByteCount());
+ assertEquals("byteCount", 40000, bm2.getByteCount());
+ assertEquals("byteCount", 40000, bm3.getByteCount());
+
assertEquals("height", 200, bm1.getHeight());
assertEquals("height", 200, bm2.getHeight());
assertEquals("height", 200, bm3.getHeight());
diff --git a/include/ui/Input.h b/include/ui/Input.h
index 2012fcc..b7b5a8d 100644
--- a/include/ui/Input.h
+++ b/include/ui/Input.h
@@ -28,6 +28,10 @@
#include <utils/RefBase.h>
#include <utils/String8.h>
+#ifdef HAVE_ANDROID_OS
+class SkMatrix;
+#endif
+
/*
* Additional private constants not defined in ndk/ui/input.h.
*/
@@ -79,6 +83,10 @@ struct AInputDevice {
namespace android {
+#ifdef HAVE_ANDROID_OS
+class Parcel;
+#endif
+
/*
* Flags that flow alongside events in the input dispatch system to help with certain
* policy decisions such as waking from device sleep.
@@ -162,15 +170,61 @@ struct InputConfiguration {
* Pointer coordinate data.
*/
struct PointerCoords {
- float x;
- float y;
- float pressure;
- float size;
- float touchMajor;
- float touchMinor;
- float toolMajor;
- float toolMinor;
- float orientation;
+ static const size_t MAX_AXES = 15; // 15 so that sizeof(PointerCoords) == 16 * 4 == 64
+
+ // Bitfield of axes that are present in this structure.
+ uint32_t bits; // 32bits are enough for now, can raise to 64bit when needed
+
+ // Values of axes that are stored in this structure packed in order by axis id
+ // for each axis that is present in the structure according to 'bits'.
+ float values[MAX_AXES];
+
+ inline void clear() {
+ bits = 0;
+ }
+
+ inline float getAxisValue(int32_t axis) const {
+ uint32_t axisBit = 1 << axis;
+ if (!(bits & axisBit)) {
+ return 0;
+ }
+ uint32_t index = __builtin_popcount(bits & (axisBit - 1));
+ return values[index];
+ }
+
+ inline void setAxisValue(int32_t axis, float value) {
+ uint32_t axisBit = 1 << axis;
+ uint32_t index = __builtin_popcount(bits & (axisBit - 1));
+ if (!(bits & axisBit)) {
+ uint32_t count = __builtin_popcount(bits);
+ if (count >= MAX_AXES) {
+ tooManyAxes(axis);
+ return;
+ }
+ bits |= axisBit;
+ for (uint32_t i = count; i > index; i--) {
+ values[i] = values[i - 1];
+ }
+ }
+ values[index] = value;
+ }
+
+ inline float* editAxisValue(int32_t axis) {
+ uint32_t axisBit = 1 << axis;
+ if (!(bits & axisBit)) {
+ return NULL;
+ }
+ uint32_t index = __builtin_popcount(bits & (axisBit - 1));
+ return &values[index];
+ }
+
+#ifdef HAVE_ANDROID_OS
+ status_t readFromParcel(Parcel* parcel);
+ status_t writeToParcel(Parcel* parcel) const;
+#endif
+
+private:
+ void tooManyAxes(int axis);
};
/*
@@ -185,12 +239,13 @@ public:
inline int32_t getDeviceId() const { return mDeviceId; }
inline int32_t getSource() const { return mSource; }
-
+
+ inline void setSource(int32_t source) { mSource = source; }
+
protected:
void initialize(int32_t deviceId, int32_t source);
void initialize(const InputEvent& from);
-private:
int32_t mDeviceId;
int32_t mSource;
};
@@ -241,7 +296,7 @@ public:
nsecs_t eventTime);
void initialize(const KeyEvent& from);
-private:
+protected:
int32_t mAction;
int32_t mFlags;
int32_t mKeyCode;
@@ -263,12 +318,18 @@ public:
inline int32_t getAction() const { return mAction; }
+ inline void setAction(int32_t action) { mAction = action; }
+
inline int32_t getFlags() const { return mFlags; }
inline int32_t getEdgeFlags() const { return mEdgeFlags; }
+ inline void setEdgeFlags(int32_t edgeFlags) { mEdgeFlags = edgeFlags; }
+
inline int32_t getMetaState() const { return mMetaState; }
+ inline void setMetaState(int32_t metaState) { mMetaState = metaState; }
+
inline float getXOffset() const { return mXOffset; }
inline float getYOffset() const { return mYOffset; }
@@ -285,48 +346,54 @@ public:
inline nsecs_t getEventTime() const { return mSampleEventTimes[getHistorySize()]; }
+ const PointerCoords* getRawPointerCoords(size_t pointerIndex) const;
+
+ float getRawAxisValue(int32_t axis, size_t pointerIndex) const;
+
inline float getRawX(size_t pointerIndex) const {
- return getCurrentPointerCoords(pointerIndex).x;
+ return getRawAxisValue(AINPUT_MOTION_AXIS_X, pointerIndex);
}
inline float getRawY(size_t pointerIndex) const {
- return getCurrentPointerCoords(pointerIndex).y;
+ return getRawAxisValue(AINPUT_MOTION_AXIS_Y, pointerIndex);
}
+ float getAxisValue(int32_t axis, size_t pointerIndex) const;
+
inline float getX(size_t pointerIndex) const {
- return getRawX(pointerIndex) + mXOffset;
+ return getAxisValue(AINPUT_MOTION_AXIS_X, pointerIndex);
}
inline float getY(size_t pointerIndex) const {
- return getRawY(pointerIndex) + mYOffset;
+ return getAxisValue(AINPUT_MOTION_AXIS_Y, pointerIndex);
}
inline float getPressure(size_t pointerIndex) const {
- return getCurrentPointerCoords(pointerIndex).pressure;
+ return getAxisValue(AINPUT_MOTION_AXIS_PRESSURE, pointerIndex);
}
inline float getSize(size_t pointerIndex) const {
- return getCurrentPointerCoords(pointerIndex).size;
+ return getAxisValue(AINPUT_MOTION_AXIS_SIZE, pointerIndex);
}
inline float getTouchMajor(size_t pointerIndex) const {
- return getCurrentPointerCoords(pointerIndex).touchMajor;
+ return getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MAJOR, pointerIndex);
}
inline float getTouchMinor(size_t pointerIndex) const {
- return getCurrentPointerCoords(pointerIndex).touchMinor;
+ return getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MINOR, pointerIndex);
}
inline float getToolMajor(size_t pointerIndex) const {
- return getCurrentPointerCoords(pointerIndex).toolMajor;
+ return getAxisValue(AINPUT_MOTION_AXIS_TOOL_MAJOR, pointerIndex);
}
inline float getToolMinor(size_t pointerIndex) const {
- return getCurrentPointerCoords(pointerIndex).toolMinor;
+ return getAxisValue(AINPUT_MOTION_AXIS_TOOL_MINOR, pointerIndex);
}
inline float getOrientation(size_t pointerIndex) const {
- return getCurrentPointerCoords(pointerIndex).orientation;
+ return getAxisValue(AINPUT_MOTION_AXIS_ORIENTATION, pointerIndex);
}
inline size_t getHistorySize() const { return mSampleEventTimes.size() - 1; }
@@ -335,48 +402,67 @@ public:
return mSampleEventTimes[historicalIndex];
}
+ const PointerCoords* getHistoricalRawPointerCoords(
+ size_t pointerIndex, size_t historicalIndex) const;
+
+ float getHistoricalRawAxisValue(int32_t axis, size_t pointerIndex,
+ size_t historicalIndex) const;
+
inline float getHistoricalRawX(size_t pointerIndex, size_t historicalIndex) const {
- return getHistoricalPointerCoords(pointerIndex, historicalIndex).x;
+ return getHistoricalRawAxisValue(
+ AINPUT_MOTION_AXIS_X, pointerIndex, historicalIndex);
}
inline float getHistoricalRawY(size_t pointerIndex, size_t historicalIndex) const {
- return getHistoricalPointerCoords(pointerIndex, historicalIndex).y;
+ return getHistoricalRawAxisValue(
+ AINPUT_MOTION_AXIS_Y, pointerIndex, historicalIndex);
}
+ float getHistoricalAxisValue(int32_t axis, size_t pointerIndex, size_t historicalIndex) const;
+
inline float getHistoricalX(size_t pointerIndex, size_t historicalIndex) const {
- return getHistoricalRawX(pointerIndex, historicalIndex) + mXOffset;
+ return getHistoricalAxisValue(
+ AINPUT_MOTION_AXIS_X, pointerIndex, historicalIndex);
}
inline float getHistoricalY(size_t pointerIndex, size_t historicalIndex) const {
- return getHistoricalRawY(pointerIndex, historicalIndex) + mYOffset;
+ return getHistoricalAxisValue(
+ AINPUT_MOTION_AXIS_Y, pointerIndex, historicalIndex);
}
inline float getHistoricalPressure(size_t pointerIndex, size_t historicalIndex) const {
- return getHistoricalPointerCoords(pointerIndex, historicalIndex).pressure;
+ return getHistoricalAxisValue(
+ AINPUT_MOTION_AXIS_PRESSURE, pointerIndex, historicalIndex);
}
inline float getHistoricalSize(size_t pointerIndex, size_t historicalIndex) const {
- return getHistoricalPointerCoords(pointerIndex, historicalIndex).size;
+ return getHistoricalAxisValue(
+ AINPUT_MOTION_AXIS_SIZE, pointerIndex, historicalIndex);
}
inline float getHistoricalTouchMajor(size_t pointerIndex, size_t historicalIndex) const {
- return getHistoricalPointerCoords(pointerIndex, historicalIndex).touchMajor;
+ return getHistoricalAxisValue(
+ AINPUT_MOTION_AXIS_TOUCH_MAJOR, pointerIndex, historicalIndex);
}
inline float getHistoricalTouchMinor(size_t pointerIndex, size_t historicalIndex) const {
- return getHistoricalPointerCoords(pointerIndex, historicalIndex).touchMinor;
+ return getHistoricalAxisValue(
+ AINPUT_MOTION_AXIS_TOUCH_MINOR, pointerIndex, historicalIndex);
}
inline float getHistoricalToolMajor(size_t pointerIndex, size_t historicalIndex) const {
- return getHistoricalPointerCoords(pointerIndex, historicalIndex).toolMajor;
+ return getHistoricalAxisValue(
+ AINPUT_MOTION_AXIS_TOOL_MAJOR, pointerIndex, historicalIndex);
}
inline float getHistoricalToolMinor(size_t pointerIndex, size_t historicalIndex) const {
- return getHistoricalPointerCoords(pointerIndex, historicalIndex).toolMinor;
+ return getHistoricalAxisValue(
+ AINPUT_MOTION_AXIS_TOOL_MINOR, pointerIndex, historicalIndex);
}
inline float getHistoricalOrientation(size_t pointerIndex, size_t historicalIndex) const {
- return getHistoricalPointerCoords(pointerIndex, historicalIndex).orientation;
+ return getHistoricalAxisValue(
+ AINPUT_MOTION_AXIS_ORIENTATION, pointerIndex, historicalIndex);
}
void initialize(
@@ -396,12 +482,23 @@ public:
const int32_t* pointerIds,
const PointerCoords* pointerCoords);
+ void copyFrom(const MotionEvent* other, bool keepHistory);
+
void addSample(
nsecs_t eventTime,
const PointerCoords* pointerCoords);
void offsetLocation(float xOffset, float yOffset);
+ void scale(float scaleFactor);
+
+#ifdef HAVE_ANDROID_OS
+ void transform(const SkMatrix* matrix);
+
+ status_t readFromParcel(Parcel* parcel);
+ status_t writeToParcel(Parcel* parcel) const;
+#endif
+
// Low-level accessors.
inline const int32_t* getPointerIds() const { return mPointerIds.array(); }
inline const nsecs_t* getSampleEventTimes() const { return mSampleEventTimes.array(); }
@@ -409,7 +506,7 @@ public:
return mSamplePointerCoords.array();
}
-private:
+protected:
int32_t mAction;
int32_t mFlags;
int32_t mEdgeFlags;
@@ -422,15 +519,6 @@ private:
Vector<int32_t> mPointerIds;
Vector<nsecs_t> mSampleEventTimes;
Vector<PointerCoords> mSamplePointerCoords;
-
- inline const PointerCoords& getCurrentPointerCoords(size_t pointerIndex) const {
- return mSamplePointerCoords[getHistorySize() * getPointerCount() + pointerIndex];
- }
-
- inline const PointerCoords& getHistoricalPointerCoords(
- size_t pointerIndex, size_t historicalIndex) const {
- return mSamplePointerCoords[historicalIndex * getPointerCount() + pointerIndex];
- }
};
/*
@@ -486,11 +574,11 @@ public:
inline const String8 getName() const { return mName; }
inline uint32_t getSources() const { return mSources; }
- const MotionRange* getMotionRange(int32_t rangeType) const;
+ const MotionRange* getMotionRange(int32_t axis) const;
void addSource(uint32_t source);
- void addMotionRange(int32_t rangeType, float min, float max, float flat, float fuzz);
- void addMotionRange(int32_t rangeType, const MotionRange& range);
+ void addMotionRange(int32_t axis, float min, float max, float flat, float fuzz);
+ void addMotionRange(int32_t axis, const MotionRange& range);
inline void setKeyboardType(int32_t keyboardType) { mKeyboardType = keyboardType; }
inline int32_t getKeyboardType() const { return mKeyboardType; }
diff --git a/libs/rs/java/ModelViewer/AndroidManifest.xml b/libs/rs/java/ModelViewer/AndroidManifest.xml
index 959fe53..e5e449b 100644
--- a/libs/rs/java/ModelViewer/AndroidManifest.xml
+++ b/libs/rs/java/ModelViewer/AndroidManifest.xml
@@ -3,14 +3,19 @@
package="com.android.modelviewer">
<application android:label="ModelViewer">
<activity android:name="SimpleModel"
- android:label="SimpleModel"
- android:screenOrientation="portrait"
- android:theme="@android:style/Theme.Black.NoTitleBar">
+ android:label="SimpleModel">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
+ <activity android:name="A3DSelector"
+ android:label="A3DSelector"
+ android:hardwareAccelerated="true">
+ <intent-filter>
+ <action android:name="android.intent.action.MAIN" />
+ </intent-filter>
+ </activity>
<activity android:name="SceneGraph"
android:label="SceneGraph"
android:theme="@android:style/Theme.Black.NoTitleBar">
diff --git a/libs/rs/java/ModelViewer/res/menu/loader_menu.xml b/libs/rs/java/ModelViewer/res/menu/loader_menu.xml
new file mode 100644
index 0000000..3c34023
--- /dev/null
+++ b/libs/rs/java/ModelViewer/res/menu/loader_menu.xml
@@ -0,0 +1,25 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+* Copyright (C) 2011 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.
+*/
+-->
+
+<menu xmlns:android="http://schemas.android.com/apk/res/android">
+ <item android:id="@+id/load_model"
+ android:title="@string/load_model" />
+ <item android:id="@+id/display_options"
+ android:title="@string/display_options" />
+</menu>
diff --git a/libs/rs/java/ModelViewer/res/values/strings.xml b/libs/rs/java/ModelViewer/res/values/strings.xml
new file mode 100644
index 0000000..8e1673f
--- /dev/null
+++ b/libs/rs/java/ModelViewer/res/values/strings.xml
@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+* Copyright (C) 2011 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.
+*/
+-->
+
+<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <skip />
+ <string name="load_model">Load Model</string>
+ <string name="display_options">Display Options</string>
+</resources>
diff --git a/libs/rs/java/ModelViewer/src/com/android/modelviewer/A3DSelector.java b/libs/rs/java/ModelViewer/src/com/android/modelviewer/A3DSelector.java
new file mode 100644
index 0000000..0e2004f
--- /dev/null
+++ b/libs/rs/java/ModelViewer/src/com/android/modelviewer/A3DSelector.java
@@ -0,0 +1,110 @@
+/*
+ * Copyright (C) 2011 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 com.android.modelviewer;
+
+import java.io.File;
+import java.io.FileFilter;
+import java.util.ArrayList;
+import java.util.List;
+
+import android.app.ListActivity;
+import android.content.Intent;
+import android.net.Uri;
+import android.os.Bundle;
+import android.view.View;
+import android.widget.ArrayAdapter;
+import android.widget.ListView;
+
+/**
+ * A list view where the last item the user clicked is placed in
+ * the "activated" state, causing its background to highlight.
+ */
+public class A3DSelector extends ListActivity {
+
+ File[] mCurrentSubList;
+ File mCurrentFile;
+
+ class A3DFilter implements FileFilter {
+ public boolean accept(File file) {
+ if (file.isDirectory()) {
+ return true;
+ }
+ return file.getName().endsWith(".a3d");
+ }
+ }
+
+ private void populateList(File file) {
+
+ mCurrentFile = file;
+ setTitle(mCurrentFile.getAbsolutePath() + "/*.a3d");
+ List<String> names = new ArrayList<String>();
+ names.add("..");
+
+ mCurrentSubList = mCurrentFile.listFiles(new A3DFilter());
+
+ if (mCurrentSubList != null) {
+ for (int i = 0; i < mCurrentSubList.length; i ++) {
+ String fileName = mCurrentSubList[i].getName();
+ if (mCurrentSubList[i].isDirectory()) {
+ fileName = "/" + fileName;
+ }
+ names.add(fileName);
+ }
+ }
+
+ // Use the built-in layout for showing a list item with a single
+ // line of text whose background is changes when activated.
+ setListAdapter(new ArrayAdapter<String>(this,
+ android.R.layout.simple_list_item_activated_1, names));
+ getListView().setTextFilterEnabled(true);
+
+ // Tell the list view to show one checked/activated item at a time.
+ getListView().setChoiceMode(ListView.CHOICE_MODE_SINGLE);
+ }
+
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+
+ populateList(new File("/sdcard/"));
+ }
+
+ @Override
+ protected void onListItemClick(ListView l, View v, int position, long id) {
+ if (position == 0) {
+ File parent = mCurrentFile.getParentFile();
+ if (parent == null) {
+ return;
+ }
+ populateList(parent);
+ return;
+ }
+
+ // the first thing in list is parent directory
+ File selectedFile = mCurrentSubList[position - 1];
+ if (selectedFile.isDirectory()) {
+ populateList(selectedFile);
+ return;
+ }
+
+ Intent resultIntent = new Intent();
+ resultIntent.setData(Uri.fromFile(selectedFile));
+ setResult(RESULT_OK, resultIntent);
+ finish();
+ }
+
+}
diff --git a/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModel.java b/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModel.java
index 9910970..01cb709 100644
--- a/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModel.java
+++ b/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModel.java
@@ -21,6 +21,7 @@ import android.renderscript.RenderScript;
import android.app.Activity;
import android.content.res.Configuration;
+import android.content.Intent;
import android.os.Bundle;
import android.os.Handler;
import android.os.Looper;
@@ -31,9 +32,11 @@ import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
+import android.view.MenuInflater;
import android.view.Window;
import android.widget.Button;
import android.widget.ListView;
+import android.net.Uri;
import java.lang.Runtime;
@@ -67,5 +70,45 @@ public class SimpleModel extends Activity {
mView.pause();
}
+ @Override
+ public boolean onCreateOptionsMenu(Menu menu) {
+ MenuInflater inflater = getMenuInflater();
+ inflater.inflate(R.menu.loader_menu, menu);
+ return true;
+ }
+
+ @Override
+ public boolean onOptionsItemSelected(MenuItem item) {
+ // Handle item selection
+ switch (item.getItemId()) {
+ case R.id.load_model:
+ loadModel();
+ return true;
+ case R.id.display_options:
+ return true;
+ default:
+ return super.onOptionsItemSelected(item);
+ }
+ }
+
+ private static final int FIND_A3D_MODEL = 10;
+ public void onActivityResult(int requestCode, int resultCode, Intent data) {
+ if (resultCode == RESULT_OK) {
+ if (requestCode == FIND_A3D_MODEL) {
+ Uri selectedImageUri = data.getData();
+ Log.e("Selected Path: ", selectedImageUri.getPath());
+ mView.loadA3DFile(selectedImageUri.getPath());
+ }
+ }
+ }
+
+ public void loadModel() {
+ Intent intent = new Intent();
+ intent.setAction(Intent.ACTION_PICK);
+ intent.setClassName("com.android.modelviewer",
+ "com.android.modelviewer.A3DSelector");
+ startActivityForResult(intent, FIND_A3D_MODEL);
+ }
+
}
diff --git a/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelRS.java b/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelRS.java
index b18a327..63ef466 100644
--- a/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelRS.java
+++ b/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelRS.java
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2008 The Android Open Source Project
+ * Copyright (C) 2011 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.
@@ -26,24 +26,20 @@ import android.util.Log;
public class SimpleModelRS {
- private final int STATE_LAST_FOCUS = 1;
-
- int mWidth;
- int mHeight;
- int mRotation;
-
public SimpleModelRS() {
}
- public void init(RenderScriptGL rs, Resources res, int width, int height) {
+ public void init(RenderScriptGL rs, Resources res) {
mRS = rs;
mRes = res;
- mWidth = width;
- mHeight = height;
- mRotation = 0;
initRS();
}
+ public void surfaceChanged() {
+ mRS.getWidth();
+ mRS.getHeight();
+ }
+
private Resources mRes;
private RenderScriptGL mRS;
private Sampler mSampler;
@@ -55,34 +51,23 @@ public class SimpleModelRS {
private Allocation mGridImage;
private Allocation mAllocPV;
- private Mesh mMesh;
-
private Font mItalic;
private Allocation mTextAlloc;
+ private ScriptField_MeshInfo mMeshes;
private ScriptC_simplemodel mScript;
- int mLastX;
- int mLastY;
- public void touchEvent(int x, int y) {
- int dx = mLastX - x;
- if (Math.abs(dx) > 50 || Math.abs(dx) < 3) {
- dx = 0;
- }
-
- mRotation -= dx;
- if (mRotation > 360) {
- mRotation -= 360;
- }
- if (mRotation < 0) {
- mRotation += 360;
- }
+ public void onActionDown(float x, float y) {
+ mScript.invoke_onActionDown(x, y);
+ }
- mScript.set_gRotate((float)mRotation);
+ public void onActionScale(float scale) {
+ mScript.invoke_onActionScale(scale);
+ }
- mLastX = x;
- mLastY = y;
+ public void onActionMove(float x, float y) {
+ mScript.invoke_onActionMove(x, y);
}
private void initPFS() {
@@ -130,12 +115,48 @@ public class SimpleModelRS {
mScript.set_gTGrid(mGridImage);
}
- private void initTextAllocation() {
- String allocString = "Displaying file: R.raw.robot";
+ private void initTextAllocation(String fileName) {
+ String allocString = "Displaying file: " + fileName;
mTextAlloc = Allocation.createFromString(mRS, allocString, Allocation.USAGE_SCRIPT);
mScript.set_gTextAlloc(mTextAlloc);
}
+ private void initMeshes(FileA3D model) {
+ int numEntries = model.getIndexEntryCount();
+ int numMeshes = 0;
+ for (int i = 0; i < numEntries; i ++) {
+ FileA3D.IndexEntry entry = model.getIndexEntry(i);
+ if (entry != null && entry.getEntryType() == FileA3D.EntryType.MESH) {
+ numMeshes ++;
+ }
+ }
+
+ if (numMeshes > 0) {
+ mMeshes = new ScriptField_MeshInfo(mRS, numMeshes);
+
+ for (int i = 0; i < numEntries; i ++) {
+ FileA3D.IndexEntry entry = model.getIndexEntry(i);
+ if (entry != null && entry.getEntryType() == FileA3D.EntryType.MESH) {
+ Mesh mesh = entry.getMesh();
+ mMeshes.set_mMesh(i, mesh, false);
+ mMeshes.set_mNumIndexSets(i, mesh.getPrimitiveCount(), false);
+ }
+ }
+ mMeshes.copyAll();
+ } else {
+ throw new RSRuntimeException("No valid meshes in file");
+ }
+
+ mScript.bind_gMeshes(mMeshes);
+ mScript.invoke_updateMeshInfo();
+ }
+
+ public void loadA3DFile(String path) {
+ FileA3D model = FileA3D.createFromFile(mRS, path);
+ initMeshes(model);
+ initTextAllocation(path);
+ }
+
private void initRS() {
mScript = new ScriptC_simplemodel(mRS, mRes, R.raw.simplemodel);
@@ -147,18 +168,12 @@ public class SimpleModelRS {
loadImage();
FileA3D model = FileA3D.createFromResource(mRS, mRes, R.raw.robot);
- FileA3D.IndexEntry entry = model.getIndexEntry(0);
- if (entry == null || entry.getEntryType() != FileA3D.EntryType.MESH) {
- Log.e("rs", "could not load model");
- } else {
- mMesh = (Mesh)entry.getObject();
- mScript.set_gTestMesh(mMesh);
- }
+ initMeshes(model);
mItalic = Font.create(mRS, mRes, "serif", Font.Style.ITALIC, 8);
mScript.set_gItalic(mItalic);
- initTextAllocation();
+ initTextAllocation("R.raw.robot");
mRS.bindRootScript(mScript);
}
diff --git a/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelView.java b/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelView.java
index 5c5956d..9ab0f22 100644
--- a/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelView.java
+++ b/libs/rs/java/ModelViewer/src/com/android/modelviewer/SimpleModelView.java
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2008 The Android Open Source Project
+ * Copyright (C) 2011 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.
@@ -16,81 +16,129 @@
package com.android.modelviewer;
-import java.io.Writer;
-import java.util.ArrayList;
-import java.util.concurrent.Semaphore;
-
import android.renderscript.RSSurfaceView;
-import android.renderscript.RenderScript;
import android.renderscript.RenderScriptGL;
import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.drawable.BitmapDrawable;
-import android.graphics.drawable.Drawable;
-import android.os.Handler;
-import android.os.Message;
-import android.util.AttributeSet;
-import android.util.Log;
-import android.view.Surface;
-import android.view.SurfaceHolder;
-import android.view.SurfaceView;
-import android.view.KeyEvent;
import android.view.MotionEvent;
+import android.view.SurfaceHolder;
+import android.view.ScaleGestureDetector;
+import android.util.Log;
public class SimpleModelView extends RSSurfaceView {
- public SimpleModelView(Context context) {
- super(context);
- //setFocusable(true);
- }
-
private RenderScriptGL mRS;
private SimpleModelRS mRender;
+ private ScaleGestureDetector mScaleDetector;
- public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) {
- super.surfaceChanged(holder, format, w, h);
+ private static final int INVALID_POINTER_ID = -1;
+ private int mActivePointerId = INVALID_POINTER_ID;
+
+ public SimpleModelView(Context context) {
+ super(context);
+ ensureRenderScript();
+ mScaleDetector = new ScaleGestureDetector(context, new ScaleListener());
+ }
+
+ private void ensureRenderScript() {
if (mRS == null) {
RenderScriptGL.SurfaceConfig sc = new RenderScriptGL.SurfaceConfig();
sc.setDepth(16, 24);
mRS = createRenderScriptGL(sc);
- mRS.setSurface(holder, w, h);
mRender = new SimpleModelRS();
- mRender.init(mRS, getResources(), w, h);
+ mRender.init(mRS, getResources());
}
}
@Override
+ protected void onAttachedToWindow() {
+ super.onAttachedToWindow();
+ ensureRenderScript();
+ }
+
+ @Override
+ public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) {
+ super.surfaceChanged(holder, format, w, h);
+ mRender.surfaceChanged();
+ }
+
+ @Override
protected void onDetachedFromWindow() {
+ mRender = null;
if (mRS != null) {
mRS = null;
destroyRenderScriptGL();
}
}
- @Override
- public boolean onKeyDown(int keyCode, KeyEvent event)
- {
- // break point at here
- // this method doesn't work when 'extends View' include 'extends ScrollView'.
- return super.onKeyDown(keyCode, event);
+ public void loadA3DFile(String path) {
+ mRender.loadA3DFile(path);
}
-
@Override
- public boolean onTouchEvent(MotionEvent ev)
- {
- boolean ret = true;
- int act = ev.getAction();
- if (act == ev.ACTION_UP) {
- ret = false;
+ public boolean onTouchEvent(MotionEvent ev) {
+ mScaleDetector.onTouchEvent(ev);
+
+ boolean ret = false;
+ float x = ev.getX();
+ float y = ev.getY();
+
+ final int action = ev.getAction();
+
+ switch (action & MotionEvent.ACTION_MASK) {
+ case MotionEvent.ACTION_DOWN: {
+ mRender.onActionDown(x, y);
+ mActivePointerId = ev.getPointerId(0);
+ ret = true;
+ break;
+ }
+ case MotionEvent.ACTION_MOVE: {
+ if (!mScaleDetector.isInProgress()) {
+ mRender.onActionMove(x, y);
+ }
+ mRender.onActionDown(x, y);
+ ret = true;
+ break;
+ }
+
+ case MotionEvent.ACTION_UP: {
+ mActivePointerId = INVALID_POINTER_ID;
+ break;
+ }
+
+ case MotionEvent.ACTION_CANCEL: {
+ mActivePointerId = INVALID_POINTER_ID;
+ break;
+ }
+
+ case MotionEvent.ACTION_POINTER_UP: {
+ final int pointerIndex = (ev.getAction() & MotionEvent.ACTION_POINTER_INDEX_MASK)
+ >> MotionEvent.ACTION_POINTER_INDEX_SHIFT;
+ final int pointerId = ev.getPointerId(pointerIndex);
+ if (pointerId == mActivePointerId) {
+ // This was our active pointer going up. Choose a new
+ // active pointer and adjust accordingly.
+ final int newPointerIndex = pointerIndex == 0 ? 1 : 0;
+ x = ev.getX(newPointerIndex);
+ y = ev.getY(newPointerIndex);
+ mRender.onActionDown(x, y);
+ mActivePointerId = ev.getPointerId(newPointerIndex);
+ }
+ break;
+ }
}
- mRender.touchEvent((int)ev.getX(), (int)ev.getY());
return ret;
}
+
+ private class ScaleListener extends ScaleGestureDetector.SimpleOnScaleGestureListener {
+ @Override
+ public boolean onScale(ScaleGestureDetector detector) {
+ mRender.onActionScale(detector.getScaleFactor());
+ return true;
+ }
+ }
}
diff --git a/libs/rs/java/ModelViewer/src/com/android/modelviewer/simplemodel.rs b/libs/rs/java/ModelViewer/src/com/android/modelviewer/simplemodel.rs
index 419de62..1034b85 100644
--- a/libs/rs/java/ModelViewer/src/com/android/modelviewer/simplemodel.rs
+++ b/libs/rs/java/ModelViewer/src/com/android/modelviewer/simplemodel.rs
@@ -1,4 +1,4 @@
-// Copyright (C) 2009 The Android Open Source Project
+// Copyright (C) 2011 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.
@@ -22,17 +22,112 @@ rs_program_vertex gPVBackground;
rs_program_fragment gPFBackground;
rs_allocation gTGrid;
-rs_mesh gTestMesh;
rs_program_store gPFSBackground;
-float gRotate;
-
rs_font gItalic;
rs_allocation gTextAlloc;
+typedef struct MeshInfo {
+ rs_mesh mMesh;
+ int mNumIndexSets;
+ float3 bBoxMin;
+ float3 bBoxMax;
+} MeshInfo_t;
+
+MeshInfo_t *gMeshes;
+
+static float3 gLookAt;
+
+static float gRotateX;
+static float gRotateY;
+static float gZoom;
+
+static float gLastX;
+static float gLastY;
+
+void onActionDown(float x, float y) {
+ gLastX = x;
+ gLastY = y;
+}
+
+void onActionScale(float scale) {
+
+ gZoom *= 1.0f / scale;
+ gZoom = max(0.1f, min(gZoom, 500.0f));
+}
+
+void onActionMove(float x, float y) {
+ float dx = gLastX - x;
+ float dy = gLastY - y;
+
+ if (fabs(dy) <= 2.0f) {
+ dy = 0.0f;
+ }
+ if (fabs(dx) <= 2.0f) {
+ dx = 0.0f;
+ }
+
+ gRotateY -= dx;
+ if (gRotateY > 360) {
+ gRotateY -= 360;
+ }
+ if (gRotateY < 0) {
+ gRotateY += 360;
+ }
+
+ gRotateX -= dy;
+ gRotateX = min(gRotateX, 80.0f);
+ gRotateX = max(gRotateX, -80.0f);
+
+ gLastX = x;
+ gLastY = y;
+}
+
void init() {
- gRotate = 0.0f;
+ gRotateX = 0.0f;
+ gRotateY = 0.0f;
+ gZoom = 50.0f;
+ gLookAt = 0.0f;
+}
+
+void updateMeshInfo() {
+ rs_allocation allMeshes = rsGetAllocation(gMeshes);
+ int size = rsAllocationGetDimX(allMeshes);
+ gLookAt = 0.0f;
+ float minX, minY, minZ, maxX, maxY, maxZ;
+ for (int i = 0; i < size; i++) {
+ MeshInfo_t *info = (MeshInfo_t*)rsGetElementAt(allMeshes, i);
+ rsgMeshComputeBoundingBox(info->mMesh,
+ &minX, &minY, &minZ,
+ &maxX, &maxY, &maxZ);
+ info->bBoxMin = (minX, minY, minZ);
+ info->bBoxMax = (maxX, maxY, maxZ);
+ gLookAt += (info->bBoxMin + info->bBoxMax)*0.5f;
+ }
+ gLookAt = gLookAt / (float)size;
+}
+
+static void renderAllMeshes() {
+ rs_allocation allMeshes = rsGetAllocation(gMeshes);
+ int size = rsAllocationGetDimX(allMeshes);
+ gLookAt = 0.0f;
+ float minX, minY, minZ, maxX, maxY, maxZ;
+ for (int i = 0; i < size; i++) {
+ MeshInfo_t *info = (MeshInfo_t*)rsGetElementAt(allMeshes, i);
+ rsgDrawMesh(info->mMesh);
+ }
+}
+
+void drawDescription() {
+ uint width = rsgGetWidth();
+ uint height = rsgGetHeight();
+ int left = 0, right = 0, top = 0, bottom = 0;
+
+ rsgBindFont(gItalic);
+
+ rsgMeasureText(gTextAlloc, &left, &right, &top, &bottom);
+ rsgDrawText(gTextAlloc, 2 -left, height - 2 + bottom);
}
int root(int launchID) {
@@ -43,7 +138,7 @@ int root(int launchID) {
rsgBindProgramVertex(gPVBackground);
rs_matrix4x4 proj;
float aspect = (float)rsgGetWidth() / (float)rsgGetHeight();
- rsMatrixLoadPerspective(&proj, 30.0f, aspect, 0.1f, 100.0f);
+ rsMatrixLoadPerspective(&proj, 30.0f, aspect, 1.0f, 100.0f);
rsgProgramVertexLoadProjectionMatrix(&proj);
rsgBindProgramFragment(gPFBackground);
@@ -52,20 +147,15 @@ int root(int launchID) {
rs_matrix4x4 matrix;
rsMatrixLoadIdentity(&matrix);
- // Position our model on the screen
- rsMatrixTranslate(&matrix, 0.0f, -0.3f, -10.0f);
- rsMatrixScale(&matrix, 0.2f, 0.2f, 0.2f);
- rsMatrixRotate(&matrix, 25.0f, 1.0f, 0.0f, 0.0f);
- rsMatrixRotate(&matrix, gRotate, 0.0f, 1.0f, 0.0f);
+ // Position our models on the screen
+ rsMatrixTranslate(&matrix, gLookAt.x, gLookAt.y, gLookAt.z - gZoom);
+ rsMatrixRotate(&matrix, gRotateX, 1.0f, 0.0f, 0.0f);
+ rsMatrixRotate(&matrix, gRotateY, 0.0f, 1.0f, 0.0f);
rsgProgramVertexLoadModelMatrix(&matrix);
- rsgDrawMesh(gTestMesh);
-
- rsgFontColor(0.3f, 0.3f, 0.3f, 1.0f);
- rsgDrawText("Renderscript model test", 30, 695);
+ renderAllMeshes();
- rsgBindFont(gItalic);
- rsgDrawText(gTextAlloc, 30, 730);
+ drawDescription();
return 10;
}
diff --git a/libs/ui/Android.mk b/libs/ui/Android.mk
index 0d55f08..f9990bb 100644
--- a/libs/ui/Android.mk
+++ b/libs/ui/Android.mk
@@ -60,7 +60,12 @@ LOCAL_SHARED_LIBRARIES := \
libEGL \
libpixelflinger \
libhardware \
- libhardware_legacy
+ libhardware_legacy \
+ libskia \
+ libbinder
+
+LOCAL_C_INCLUDES := \
+ external/skia/include/core
LOCAL_MODULE:= libui
diff --git a/libs/ui/Input.cpp b/libs/ui/Input.cpp
index b8d59e6..90b954e 100644
--- a/libs/ui/Input.cpp
+++ b/libs/ui/Input.cpp
@@ -15,6 +15,16 @@
#include <ui/Input.h>
+#include <math.h>
+
+#ifdef HAVE_ANDROID_OS
+#include <binder/Parcel.h>
+
+#include "SkPoint.h"
+#include "SkMatrix.h"
+#include "SkScalar.h"
+#endif
+
namespace android {
static const char* CONFIGURATION_FILE_DIR[] = {
@@ -237,6 +247,41 @@ void KeyEvent::initialize(const KeyEvent& from) {
mEventTime = from.mEventTime;
}
+
+// --- PointerCoords ---
+
+#ifdef HAVE_ANDROID_OS
+status_t PointerCoords::readFromParcel(Parcel* parcel) {
+ bits = parcel->readInt32();
+
+ uint32_t count = __builtin_popcount(bits);
+ if (count > MAX_AXES) {
+ return BAD_VALUE;
+ }
+
+ for (uint32_t i = 0; i < count; i++) {
+ values[i] = parcel->readInt32();
+ }
+ return OK;
+}
+
+status_t PointerCoords::writeToParcel(Parcel* parcel) const {
+ parcel->writeInt32(bits);
+
+ uint32_t count = __builtin_popcount(bits);
+ for (uint32_t i = 0; i < count; i++) {
+ parcel->writeInt32(values[i]);
+ }
+ return OK;
+}
+#endif
+
+void PointerCoords::tooManyAxes(int axis) {
+ LOGW("Could not set value for axis %d because the PointerCoords structure is full and "
+ "cannot contain more than %d axis values.", axis, int(MAX_AXES));
+}
+
+
// --- MotionEvent ---
void MotionEvent::initialize(
@@ -272,6 +317,33 @@ void MotionEvent::initialize(
addSample(eventTime, pointerCoords);
}
+void MotionEvent::copyFrom(const MotionEvent* other, bool keepHistory) {
+ InputEvent::initialize(other->mDeviceId, other->mSource);
+ mAction = other->mAction;
+ mFlags = other->mFlags;
+ mEdgeFlags = other->mEdgeFlags;
+ mMetaState = other->mMetaState;
+ mXOffset = other->mXOffset;
+ mYOffset = other->mYOffset;
+ mXPrecision = other->mXPrecision;
+ mYPrecision = other->mYPrecision;
+ mDownTime = other->mDownTime;
+ mPointerIds = other->mPointerIds;
+
+ if (keepHistory) {
+ mSampleEventTimes = other->mSampleEventTimes;
+ mSamplePointerCoords = other->mSamplePointerCoords;
+ } else {
+ mSampleEventTimes.clear();
+ mSampleEventTimes.push(other->getEventTime());
+ mSamplePointerCoords.clear();
+ size_t pointerCount = other->getPointerCount();
+ size_t historySize = other->getHistorySize();
+ mSamplePointerCoords.appendArray(other->mSamplePointerCoords.array()
+ + (historySize * pointerCount), pointerCount);
+ }
+}
+
void MotionEvent::addSample(
int64_t eventTime,
const PointerCoords* pointerCoords) {
@@ -279,11 +351,224 @@ void MotionEvent::addSample(
mSamplePointerCoords.appendArray(pointerCoords, getPointerCount());
}
+const PointerCoords* MotionEvent::getRawPointerCoords(size_t pointerIndex) const {
+ return &mSamplePointerCoords[getHistorySize() * getPointerCount() + pointerIndex];
+}
+
+float MotionEvent::getRawAxisValue(int32_t axis, size_t pointerIndex) const {
+ return getRawPointerCoords(pointerIndex)->getAxisValue(axis);
+}
+
+float MotionEvent::getAxisValue(int32_t axis, size_t pointerIndex) const {
+ float value = getRawPointerCoords(pointerIndex)->getAxisValue(axis);
+ switch (axis) {
+ case AINPUT_MOTION_AXIS_X:
+ value += mXOffset;
+ break;
+ case AINPUT_MOTION_AXIS_Y:
+ value += mYOffset;
+ break;
+ }
+ return value;
+}
+
+const PointerCoords* MotionEvent::getHistoricalRawPointerCoords(
+ size_t pointerIndex, size_t historicalIndex) const {
+ return &mSamplePointerCoords[historicalIndex * getPointerCount() + pointerIndex];
+}
+
+float MotionEvent::getHistoricalRawAxisValue(int32_t axis, size_t pointerIndex,
+ size_t historicalIndex) const {
+ return getHistoricalRawPointerCoords(pointerIndex, historicalIndex)->getAxisValue(axis);
+}
+
+float MotionEvent::getHistoricalAxisValue(int32_t axis, size_t pointerIndex,
+ size_t historicalIndex) const {
+ float value = getHistoricalRawPointerCoords(pointerIndex, historicalIndex)->getAxisValue(axis);
+ switch (axis) {
+ case AINPUT_MOTION_AXIS_X:
+ value += mXOffset;
+ break;
+ case AINPUT_MOTION_AXIS_Y:
+ value += mYOffset;
+ break;
+ }
+ return value;
+}
+
void MotionEvent::offsetLocation(float xOffset, float yOffset) {
mXOffset += xOffset;
mYOffset += yOffset;
}
+static inline void scaleAxisValue(PointerCoords& c, int axis, float scaleFactor) {
+ float* value = c.editAxisValue(axis);
+ if (value) {
+ *value *= scaleFactor;
+ }
+}
+
+void MotionEvent::scale(float scaleFactor) {
+ mXOffset *= scaleFactor;
+ mYOffset *= scaleFactor;
+ mXPrecision *= scaleFactor;
+ mYPrecision *= scaleFactor;
+
+ size_t numSamples = mSamplePointerCoords.size();
+ for (size_t i = 0; i < numSamples; i++) {
+ PointerCoords& c = mSamplePointerCoords.editItemAt(i);
+ // No need to scale pressure or size since they are normalized.
+ // No need to scale orientation since it is meaningless to do so.
+ scaleAxisValue(c, AINPUT_MOTION_AXIS_X, scaleFactor);
+ scaleAxisValue(c, AINPUT_MOTION_AXIS_Y, scaleFactor);
+ scaleAxisValue(c, AINPUT_MOTION_AXIS_TOUCH_MAJOR, scaleFactor);
+ scaleAxisValue(c, AINPUT_MOTION_AXIS_TOUCH_MINOR, scaleFactor);
+ scaleAxisValue(c, AINPUT_MOTION_AXIS_TOOL_MAJOR, scaleFactor);
+ scaleAxisValue(c, AINPUT_MOTION_AXIS_TOOL_MINOR, scaleFactor);
+ }
+}
+
+#ifdef HAVE_ANDROID_OS
+static inline float transformAngle(const SkMatrix* matrix, float angleRadians) {
+ // Construct and transform a vector oriented at the specified clockwise angle from vertical.
+ // Coordinate system: down is increasing Y, right is increasing X.
+ SkPoint vector;
+ vector.fX = SkFloatToScalar(sinf(angleRadians));
+ vector.fY = SkFloatToScalar(-cosf(angleRadians));
+ matrix->mapVectors(& vector, 1);
+
+ // Derive the transformed vector's clockwise angle from vertical.
+ float result = atan2f(SkScalarToFloat(vector.fX), SkScalarToFloat(-vector.fY));
+ if (result < - M_PI_2) {
+ result += M_PI;
+ } else if (result > M_PI_2) {
+ result -= M_PI;
+ }
+ return result;
+}
+
+void MotionEvent::transform(const SkMatrix* matrix) {
+ float oldXOffset = mXOffset;
+ float oldYOffset = mYOffset;
+
+ // The tricky part of this implementation is to preserve the value of
+ // rawX and rawY. So we apply the transformation to the first point
+ // then derive an appropriate new X/Y offset that will preserve rawX and rawY.
+ SkPoint point;
+ float rawX = getRawX(0);
+ float rawY = getRawY(0);
+ matrix->mapXY(SkFloatToScalar(rawX + oldXOffset), SkFloatToScalar(rawY + oldYOffset),
+ & point);
+ float newX = SkScalarToFloat(point.fX);
+ float newY = SkScalarToFloat(point.fY);
+ float newXOffset = newX - rawX;
+ float newYOffset = newY - rawY;
+
+ mXOffset = newXOffset;
+ mYOffset = newYOffset;
+
+ // Apply the transformation to all samples.
+ size_t numSamples = mSamplePointerCoords.size();
+ for (size_t i = 0; i < numSamples; i++) {
+ PointerCoords& c = mSamplePointerCoords.editItemAt(i);
+ float* xPtr = c.editAxisValue(AINPUT_MOTION_AXIS_X);
+ float* yPtr = c.editAxisValue(AINPUT_MOTION_AXIS_Y);
+ if (xPtr && yPtr) {
+ float x = *xPtr + oldXOffset;
+ float y = *yPtr + oldYOffset;
+ matrix->mapXY(SkFloatToScalar(x), SkFloatToScalar(y), & point);
+ *xPtr = SkScalarToFloat(point.fX) - newXOffset;
+ *yPtr = SkScalarToFloat(point.fY) - newYOffset;
+ }
+
+ float* orientationPtr = c.editAxisValue(AINPUT_MOTION_AXIS_ORIENTATION);
+ if (orientationPtr) {
+ *orientationPtr = transformAngle(matrix, *orientationPtr);
+ }
+ }
+}
+
+status_t MotionEvent::readFromParcel(Parcel* parcel) {
+ size_t pointerCount = parcel->readInt32();
+ size_t sampleCount = parcel->readInt32();
+ if (pointerCount == 0 || pointerCount > MAX_POINTERS || sampleCount == 0) {
+ return BAD_VALUE;
+ }
+
+ mDeviceId = parcel->readInt32();
+ mSource = parcel->readInt32();
+ mAction = parcel->readInt32();
+ mFlags = parcel->readInt32();
+ mEdgeFlags = parcel->readInt32();
+ mMetaState = parcel->readInt32();
+ mXOffset = parcel->readFloat();
+ mYOffset = parcel->readFloat();
+ mXPrecision = parcel->readFloat();
+ mYPrecision = parcel->readFloat();
+ mDownTime = parcel->readInt64();
+
+ mPointerIds.clear();
+ mPointerIds.setCapacity(pointerCount);
+ mSampleEventTimes.clear();
+ mSampleEventTimes.setCapacity(sampleCount);
+ mSamplePointerCoords.clear();
+ mSamplePointerCoords.setCapacity(sampleCount * pointerCount);
+
+ for (size_t i = 0; i < pointerCount; i++) {
+ mPointerIds.push(parcel->readInt32());
+ }
+
+ while (sampleCount-- > 0) {
+ mSampleEventTimes.push(parcel->readInt64());
+ for (size_t i = 0; i < pointerCount; i++) {
+ mSamplePointerCoords.push();
+ status_t status = mSamplePointerCoords.editTop().readFromParcel(parcel);
+ if (!status) {
+ return status;
+ }
+ }
+ }
+ return OK;
+}
+
+status_t MotionEvent::writeToParcel(Parcel* parcel) const {
+ size_t pointerCount = mPointerIds.size();
+ size_t sampleCount = mSampleEventTimes.size();
+
+ parcel->writeInt32(pointerCount);
+ parcel->writeInt32(sampleCount);
+
+ parcel->writeInt32(mDeviceId);
+ parcel->writeInt32(mSource);
+ parcel->writeInt32(mAction);
+ parcel->writeInt32(mFlags);
+ parcel->writeInt32(mEdgeFlags);
+ parcel->writeInt32(mMetaState);
+ parcel->writeFloat(mXOffset);
+ parcel->writeFloat(mYOffset);
+ parcel->writeFloat(mXPrecision);
+ parcel->writeFloat(mYPrecision);
+ parcel->writeInt64(mDownTime);
+
+ for (size_t i = 0; i < pointerCount; i++) {
+ parcel->writeInt32(mPointerIds.itemAt(i));
+ }
+
+ const PointerCoords* pc = mSamplePointerCoords.array();
+ for (size_t h = 0; h < sampleCount; h++) {
+ parcel->writeInt64(mSampleEventTimes.itemAt(h));
+ for (size_t i = 0; i < pointerCount; i++) {
+ status_t status = (pc++)->writeToParcel(parcel);
+ if (!status) {
+ return status;
+ }
+ }
+ }
+ return OK;
+}
+#endif
+
+
// --- InputDeviceInfo ---
InputDeviceInfo::InputDeviceInfo() {
@@ -307,8 +592,8 @@ void InputDeviceInfo::initialize(int32_t id, const String8& name) {
mMotionRanges.clear();
}
-const InputDeviceInfo::MotionRange* InputDeviceInfo::getMotionRange(int32_t rangeType) const {
- ssize_t index = mMotionRanges.indexOfKey(rangeType);
+const InputDeviceInfo::MotionRange* InputDeviceInfo::getMotionRange(int32_t axis) const {
+ ssize_t index = mMotionRanges.indexOfKey(axis);
return index >= 0 ? & mMotionRanges.valueAt(index) : NULL;
}
@@ -316,14 +601,14 @@ void InputDeviceInfo::addSource(uint32_t source) {
mSources |= source;
}
-void InputDeviceInfo::addMotionRange(int32_t rangeType, float min, float max,
+void InputDeviceInfo::addMotionRange(int32_t axis, float min, float max,
float flat, float fuzz) {
MotionRange range = { min, max, flat, fuzz };
- addMotionRange(rangeType, range);
+ addMotionRange(axis, range);
}
-void InputDeviceInfo::addMotionRange(int32_t rangeType, const MotionRange& range) {
- mMotionRanges.add(rangeType, range);
+void InputDeviceInfo::addMotionRange(int32_t axis, const MotionRange& range) {
+ mMotionRanges.add(axis, range);
}
} // namespace android
diff --git a/libs/ui/tests/InputPublisherAndConsumer_test.cpp b/libs/ui/tests/InputPublisherAndConsumer_test.cpp
index 903fcaf..1819a8b 100644
--- a/libs/ui/tests/InputPublisherAndConsumer_test.cpp
+++ b/libs/ui/tests/InputPublisherAndConsumer_test.cpp
@@ -159,15 +159,17 @@ void InputPublisherAndConsumerTest::PublishAndConsumeMotionEvent(
sampleEventTimes.push(i + 10);
for (size_t j = 0; j < pointerCount; j++) {
samplePointerCoords.push();
- samplePointerCoords.editTop().x = 100 * i + j;
- samplePointerCoords.editTop().y = 200 * i + j;
- samplePointerCoords.editTop().pressure = 0.5 * i + j;
- samplePointerCoords.editTop().size = 0.7 * i + j;
- samplePointerCoords.editTop().touchMajor = 1.5 * i + j;
- samplePointerCoords.editTop().touchMinor = 1.7 * i + j;
- samplePointerCoords.editTop().toolMajor = 2.5 * i + j;
- samplePointerCoords.editTop().toolMinor = 2.7 * i + j;
- samplePointerCoords.editTop().orientation = 3.5 * i + j;
+ PointerCoords& pc = samplePointerCoords.editTop();
+ pc.clear();
+ pc.setAxisValue(AINPUT_MOTION_AXIS_X, 100 * i + j);
+ pc.setAxisValue(AINPUT_MOTION_AXIS_Y, 200 * i + j);
+ pc.setAxisValue(AINPUT_MOTION_AXIS_PRESSURE, 0.5 * i + j);
+ pc.setAxisValue(AINPUT_MOTION_AXIS_SIZE, 0.7 * i + j);
+ pc.setAxisValue(AINPUT_MOTION_AXIS_TOUCH_MAJOR, 1.5 * i + j);
+ pc.setAxisValue(AINPUT_MOTION_AXIS_TOUCH_MINOR, 1.7 * i + j);
+ pc.setAxisValue(AINPUT_MOTION_AXIS_TOOL_MAJOR, 2.5 * i + j);
+ pc.setAxisValue(AINPUT_MOTION_AXIS_TOOL_MAJOR, 2.7 * i + j);
+ pc.setAxisValue(AINPUT_MOTION_AXIS_ORIENTATION, 3.5 * i + j);
}
}
@@ -239,27 +241,27 @@ void InputPublisherAndConsumerTest::PublishAndConsumeMotionEvent(
for (size_t i = 0; i < pointerCount; i++) {
SCOPED_TRACE(i);
size_t offset = sampleIndex * pointerCount + i;
- EXPECT_EQ(samplePointerCoords[offset].x,
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_X),
motionEvent->getHistoricalRawX(i, sampleIndex));
- EXPECT_EQ(samplePointerCoords[offset].y,
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_Y),
motionEvent->getHistoricalRawY(i, sampleIndex));
- EXPECT_EQ(samplePointerCoords[offset].x + xOffset,
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_X) + xOffset,
motionEvent->getHistoricalX(i, sampleIndex));
- EXPECT_EQ(samplePointerCoords[offset].y + yOffset,
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_Y) + yOffset,
motionEvent->getHistoricalY(i, sampleIndex));
- EXPECT_EQ(samplePointerCoords[offset].pressure,
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_PRESSURE),
motionEvent->getHistoricalPressure(i, sampleIndex));
- EXPECT_EQ(samplePointerCoords[offset].size,
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_SIZE),
motionEvent->getHistoricalSize(i, sampleIndex));
- EXPECT_EQ(samplePointerCoords[offset].touchMajor,
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MAJOR),
motionEvent->getHistoricalTouchMajor(i, sampleIndex));
- EXPECT_EQ(samplePointerCoords[offset].touchMinor,
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MINOR),
motionEvent->getHistoricalTouchMinor(i, sampleIndex));
- EXPECT_EQ(samplePointerCoords[offset].toolMajor,
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_TOOL_MAJOR),
motionEvent->getHistoricalToolMajor(i, sampleIndex));
- EXPECT_EQ(samplePointerCoords[offset].toolMinor,
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_TOOL_MINOR),
motionEvent->getHistoricalToolMinor(i, sampleIndex));
- EXPECT_EQ(samplePointerCoords[offset].orientation,
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_ORIENTATION),
motionEvent->getHistoricalOrientation(i, sampleIndex));
}
}
@@ -269,17 +271,28 @@ void InputPublisherAndConsumerTest::PublishAndConsumeMotionEvent(
for (size_t i = 0; i < pointerCount; i++) {
SCOPED_TRACE(i);
size_t offset = lastSampleIndex * pointerCount + i;
- EXPECT_EQ(samplePointerCoords[offset].x, motionEvent->getRawX(i));
- EXPECT_EQ(samplePointerCoords[offset].y, motionEvent->getRawY(i));
- EXPECT_EQ(samplePointerCoords[offset].x + xOffset, motionEvent->getX(i));
- EXPECT_EQ(samplePointerCoords[offset].y + yOffset, motionEvent->getY(i));
- EXPECT_EQ(samplePointerCoords[offset].pressure, motionEvent->getPressure(i));
- EXPECT_EQ(samplePointerCoords[offset].size, motionEvent->getSize(i));
- EXPECT_EQ(samplePointerCoords[offset].touchMajor, motionEvent->getTouchMajor(i));
- EXPECT_EQ(samplePointerCoords[offset].touchMinor, motionEvent->getTouchMinor(i));
- EXPECT_EQ(samplePointerCoords[offset].toolMajor, motionEvent->getToolMajor(i));
- EXPECT_EQ(samplePointerCoords[offset].toolMinor, motionEvent->getToolMinor(i));
- EXPECT_EQ(samplePointerCoords[offset].orientation, motionEvent->getOrientation(i));
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_X),
+ motionEvent->getRawX(i));
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_Y),
+ motionEvent->getRawY(i));
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_X) + xOffset,
+ motionEvent->getX(i));
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_Y) + yOffset,
+ motionEvent->getY(i));
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_PRESSURE),
+ motionEvent->getPressure(i));
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_SIZE),
+ motionEvent->getSize(i));
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MAJOR),
+ motionEvent->getTouchMajor(i));
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MINOR),
+ motionEvent->getTouchMinor(i));
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_TOOL_MAJOR),
+ motionEvent->getToolMajor(i));
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_TOOL_MINOR),
+ motionEvent->getToolMinor(i));
+ EXPECT_EQ(samplePointerCoords[offset].getAxisValue(AINPUT_MOTION_AXIS_ORIENTATION),
+ motionEvent->getOrientation(i));
}
status = mConsumer->sendFinishedSignal(false);
@@ -328,7 +341,8 @@ TEST_F(InputPublisherAndConsumerTest, PublishMotionEvent_WhenNotReset_ReturnsErr
const size_t pointerCount = 1;
int32_t pointerIds[pointerCount] = { 0 };
- PointerCoords pointerCoords[pointerCount] = { { 0, 0, 0, 0, 0, 0, 0, 0, 0 } };
+ PointerCoords pointerCoords[pointerCount];
+ pointerCoords[0].clear();
status = mPublisher->publishMotionEvent(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
pointerCount, pointerIds, pointerCoords);
diff --git a/native/android/input.cpp b/native/android/input.cpp
index a96240c..ed26667 100644
--- a/native/android/input.cpp
+++ b/native/android/input.cpp
@@ -172,6 +172,11 @@ float AMotionEvent_getOrientation(const AInputEvent* motion_event, size_t pointe
return static_cast<const MotionEvent*>(motion_event)->getOrientation(pointer_index);
}
+float AMotionEvent_getAxisValue(const AInputEvent* motion_event,
+ int32_t axis, size_t pointer_index) {
+ return static_cast<const MotionEvent*>(motion_event)->getAxisValue(axis, pointer_index);
+}
+
size_t AMotionEvent_getHistorySize(const AInputEvent* motion_event) {
return static_cast<const MotionEvent*>(motion_event)->getHistorySize();
}
@@ -248,6 +253,12 @@ float AMotionEvent_getHistoricalOrientation(AInputEvent* motion_event, size_t po
pointer_index, history_index);
}
+float AMotionEvent_getHistoricalAxisValue(const AInputEvent* motion_event,
+ int32_t axis, size_t pointer_index, size_t history_index) {
+ return static_cast<const MotionEvent*>(motion_event)->getHistoricalAxisValue(
+ axis, pointer_index, history_index);
+}
+
void AInputQueue_attachLooper(AInputQueue* queue, ALooper* looper,
int ident, ALooper_callbackFunc callback, void* data) {
diff --git a/native/include/android/input.h b/native/include/android/input.h
index bad363d..0ffb8b5 100644
--- a/native/include/android/input.h
+++ b/native/include/android/input.h
@@ -363,23 +363,40 @@ enum {
};
/*
+ * Constants that identify each individual axis of a motion event.
+ */
+enum {
+ AINPUT_MOTION_AXIS_X = 0,
+ AINPUT_MOTION_AXIS_Y = 1,
+ AINPUT_MOTION_AXIS_PRESSURE = 2,
+ AINPUT_MOTION_AXIS_SIZE = 3,
+ AINPUT_MOTION_AXIS_TOUCH_MAJOR = 4,
+ AINPUT_MOTION_AXIS_TOUCH_MINOR = 5,
+ AINPUT_MOTION_AXIS_TOOL_MAJOR = 6,
+ AINPUT_MOTION_AXIS_TOOL_MINOR = 7,
+ AINPUT_MOTION_AXIS_ORIENTATION = 8,
+};
+
+/*
* Constants used to retrieve information about the range of motion for a particular
* coordinate of a motion event.
*
* Refer to the documentation on android.view.InputDevice for more details about input sources
* and their correct interpretation.
+ *
+ * DEPRECATION NOTICE: These constants are deprecated. Use AINPUT_MOTION_AXIS_* constants instead.
*/
enum {
- AINPUT_MOTION_RANGE_X = 0,
- AINPUT_MOTION_RANGE_Y = 1,
- AINPUT_MOTION_RANGE_PRESSURE = 2,
- AINPUT_MOTION_RANGE_SIZE = 3,
- AINPUT_MOTION_RANGE_TOUCH_MAJOR = 4,
- AINPUT_MOTION_RANGE_TOUCH_MINOR = 5,
- AINPUT_MOTION_RANGE_TOOL_MAJOR = 6,
- AINPUT_MOTION_RANGE_TOOL_MINOR = 7,
- AINPUT_MOTION_RANGE_ORIENTATION = 8,
-};
+ AINPUT_MOTION_RANGE_X = AINPUT_MOTION_AXIS_X,
+ AINPUT_MOTION_RANGE_Y = AINPUT_MOTION_AXIS_Y,
+ AINPUT_MOTION_RANGE_PRESSURE = AINPUT_MOTION_AXIS_PRESSURE,
+ AINPUT_MOTION_RANGE_SIZE = AINPUT_MOTION_AXIS_SIZE,
+ AINPUT_MOTION_RANGE_TOUCH_MAJOR = AINPUT_MOTION_AXIS_TOUCH_MAJOR,
+ AINPUT_MOTION_RANGE_TOUCH_MINOR = AINPUT_MOTION_AXIS_TOUCH_MINOR,
+ AINPUT_MOTION_RANGE_TOOL_MAJOR = AINPUT_MOTION_AXIS_TOOL_MAJOR,
+ AINPUT_MOTION_RANGE_TOOL_MINOR = AINPUT_MOTION_AXIS_TOOL_MINOR,
+ AINPUT_MOTION_RANGE_ORIENTATION = AINPUT_MOTION_AXIS_ORIENTATION,
+} __attribute__ ((deprecated));
/*
@@ -526,7 +543,7 @@ float AMotionEvent_getY(const AInputEvent* motion_event, size_t pointer_index);
/* Get the current pressure of this event for the given pointer index.
* The pressure generally ranges from 0 (no pressure at all) to 1 (normal pressure),
- * however values higher than 1 may be generated depending on the calibration of
+ * although values higher than 1 may be generated depending on the calibration of
* the input device. */
float AMotionEvent_getPressure(const AInputEvent* motion_event, size_t pointer_index);
@@ -568,6 +585,10 @@ float AMotionEvent_getToolMinor(const AInputEvent* motion_event, size_t pointer_
* (finger pointing fully right). */
float AMotionEvent_getOrientation(const AInputEvent* motion_event, size_t pointer_index);
+/* Get the value of the request axis for the given pointer index. */
+float AMotionEvent_getAxisValue(const AInputEvent* motion_event,
+ int32_t axis, size_t pointer_index);
+
/* Get the number of historical points in this event. These are movements that
* have occurred between this event and the previous event. This only applies
* to AMOTION_EVENT_ACTION_MOVE events -- all other actions will have a size of 0.
@@ -614,7 +635,7 @@ float AMotionEvent_getHistoricalY(AInputEvent* motion_event, size_t pointer_inde
/* Get the historical pressure of this event for the given pointer index that
* occurred between this event and the previous motion event.
* The pressure generally ranges from 0 (no pressure at all) to 1 (normal pressure),
- * however values higher than 1 may be generated depending on the calibration of
+ * although values higher than 1 may be generated depending on the calibration of
* the input device. */
float AMotionEvent_getHistoricalPressure(AInputEvent* motion_event, size_t pointer_index,
size_t history_index);
@@ -669,6 +690,11 @@ float AMotionEvent_getHistoricalToolMinor(const AInputEvent* motion_event, size_
float AMotionEvent_getHistoricalOrientation(const AInputEvent* motion_event, size_t pointer_index,
size_t history_index);
+/* Get the historical value of the request axis for the given pointer index
+ * that occurred between this event and the previous motion event. */
+float AMotionEvent_getHistoricalAxisValue(const AInputEvent* motion_event,
+ int32_t axis, size_t pointer_index, size_t history_index);
+
/*
* Input queue
diff --git a/services/input/InputDispatcher.cpp b/services/input/InputDispatcher.cpp
index cbfdd75..466a9b3 100644
--- a/services/input/InputDispatcher.cpp
+++ b/services/input/InputDispatcher.cpp
@@ -482,8 +482,10 @@ bool InputDispatcher::enqueueInboundEventLocked(EventEntry* entry) {
&& (motionEntry->source & AINPUT_SOURCE_CLASS_POINTER)
&& mInputTargetWaitCause == INPUT_TARGET_WAIT_CAUSE_APPLICATION_NOT_READY
&& mInputTargetWaitApplication != NULL) {
- int32_t x = int32_t(motionEntry->firstSample.pointerCoords[0].x);
- int32_t y = int32_t(motionEntry->firstSample.pointerCoords[0].y);
+ int32_t x = int32_t(motionEntry->firstSample.pointerCoords[0].
+ getAxisValue(AINPUT_MOTION_AXIS_X));
+ int32_t y = int32_t(motionEntry->firstSample.pointerCoords[0].
+ getAxisValue(AINPUT_MOTION_AXIS_Y));
const InputWindow* touchedWindow = findTouchedWindowAtLocked(x, y);
if (touchedWindow
&& touchedWindow->inputWindowHandle != NULL
@@ -888,11 +890,15 @@ void InputDispatcher::logOutboundMotionDetailsLocked(const char* prefix, const M
"touchMajor=%f, touchMinor=%f, toolMajor=%f, toolMinor=%f, "
"orientation=%f",
i, entry->pointerIds[i],
- sample->pointerCoords[i].x, sample->pointerCoords[i].y,
- sample->pointerCoords[i].pressure, sample->pointerCoords[i].size,
- sample->pointerCoords[i].touchMajor, sample->pointerCoords[i].touchMinor,
- sample->pointerCoords[i].toolMajor, sample->pointerCoords[i].toolMinor,
- sample->pointerCoords[i].orientation);
+ sample->pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_X),
+ sample->pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_Y),
+ sample->pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_PRESSURE),
+ sample->pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_SIZE),
+ sample->pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MAJOR),
+ sample->pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MINOR),
+ sample->pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_TOOL_MAJOR),
+ sample->pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_TOOL_MINOR),
+ sample->pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_ORIENTATION));
}
// Keep in mind that due to batching, it is possible for the number of samples actually
@@ -1188,8 +1194,10 @@ int32_t InputDispatcher::findTouchedWindowTargetsLocked(nsecs_t currentTime,
/* Case 1: New splittable pointer going down. */
int32_t pointerIndex = getMotionEventActionPointerIndex(action);
- int32_t x = int32_t(entry->firstSample.pointerCoords[pointerIndex].x);
- int32_t y = int32_t(entry->firstSample.pointerCoords[pointerIndex].y);
+ int32_t x = int32_t(entry->firstSample.pointerCoords[pointerIndex].
+ getAxisValue(AINPUT_MOTION_AXIS_X));
+ int32_t y = int32_t(entry->firstSample.pointerCoords[pointerIndex].
+ getAxisValue(AINPUT_MOTION_AXIS_Y));
const InputWindow* newTouchedWindow = NULL;
const InputWindow* topErrorWindow = NULL;
@@ -2275,11 +2283,16 @@ void InputDispatcher::notifyMotion(nsecs_t eventTime, int32_t deviceId, uint32_t
LOGD(" Pointer %d: id=%d, x=%f, y=%f, pressure=%f, size=%f, "
"touchMajor=%f, touchMinor=%f, toolMajor=%f, toolMinor=%f, "
"orientation=%f",
- i, pointerIds[i], pointerCoords[i].x, pointerCoords[i].y,
- pointerCoords[i].pressure, pointerCoords[i].size,
- pointerCoords[i].touchMajor, pointerCoords[i].touchMinor,
- pointerCoords[i].toolMajor, pointerCoords[i].toolMinor,
- pointerCoords[i].orientation);
+ i, pointerIds[i],
+ pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_X),
+ pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_Y),
+ pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_PRESSURE),
+ pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_SIZE),
+ pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MAJOR),
+ pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MINOR),
+ pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_TOOL_MAJOR),
+ pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_TOOL_MINOR),
+ pointerCoords[i].getAxisValue(AINPUT_MOTION_AXIS_ORIENTATION));
}
#endif
if (! validateMotionEvent(action, pointerCount, pointerIds)) {
diff --git a/services/input/InputReader.cpp b/services/input/InputReader.cpp
index a4d5f35..577da01 100644
--- a/services/input/InputReader.cpp
+++ b/services/input/InputReader.cpp
@@ -1285,24 +1285,23 @@ void CursorInputMapper::sync(nsecs_t when) {
}
}
+ pointerCoords.clear();
+
if (mPointerController != NULL) {
mPointerController->move(deltaX, deltaY);
if (downChanged) {
mPointerController->setButtonState(mLocked.down ? POINTER_BUTTON_1 : 0);
}
- mPointerController->getPosition(&pointerCoords.x, &pointerCoords.y);
+ float x, y;
+ mPointerController->getPosition(&x, &y);
+ pointerCoords.setAxisValue(AINPUT_MOTION_AXIS_X, x);
+ pointerCoords.setAxisValue(AINPUT_MOTION_AXIS_Y, y);
} else {
- pointerCoords.x = deltaX;
- pointerCoords.y = deltaY;
+ pointerCoords.setAxisValue(AINPUT_MOTION_AXIS_X, deltaX);
+ pointerCoords.setAxisValue(AINPUT_MOTION_AXIS_Y, deltaY);
}
- pointerCoords.pressure = mLocked.down ? 1.0f : 0.0f;
- pointerCoords.size = 0;
- pointerCoords.touchMajor = 0;
- pointerCoords.touchMinor = 0;
- pointerCoords.toolMajor = 0;
- pointerCoords.toolMinor = 0;
- pointerCoords.orientation = 0;
+ pointerCoords.setAxisValue(AINPUT_MOTION_AXIS_PRESSURE, mLocked.down ? 1.0f : 0.0f);
} // release lock
int32_t metaState = mContext->getGlobalMetaState();
@@ -2641,9 +2640,11 @@ void TouchInputMapper::dispatchTouch(nsecs_t when, uint32_t policyFlags,
int32_t c2 = signExtendNybble(in.orientation & 0x0f);
if (c1 != 0 || c2 != 0) {
orientation = atan2f(c1, c2) * 0.5f;
- float minorAxisScale = (16.0f - pythag(c1, c2)) / 16.0f;
- toolMinor *= minorAxisScale;
- touchMinor *= minorAxisScale;
+ float scale = 1.0f + pythag(c1, c2) / 16.0f;
+ touchMajor *= scale;
+ touchMinor /= scale;
+ toolMajor *= scale;
+ toolMinor /= scale;
} else {
orientation = 0;
}
@@ -2684,15 +2685,16 @@ void TouchInputMapper::dispatchTouch(nsecs_t when, uint32_t policyFlags,
// Write output coords.
PointerCoords& out = pointerCoords[outIndex];
- out.x = x;
- out.y = y;
- out.pressure = pressure;
- out.size = size;
- out.touchMajor = touchMajor;
- out.touchMinor = touchMinor;
- out.toolMajor = toolMajor;
- out.toolMinor = toolMinor;
- out.orientation = orientation;
+ out.clear();
+ out.setAxisValue(AINPUT_MOTION_AXIS_X, x);
+ out.setAxisValue(AINPUT_MOTION_AXIS_Y, y);
+ out.setAxisValue(AINPUT_MOTION_AXIS_PRESSURE, pressure);
+ out.setAxisValue(AINPUT_MOTION_AXIS_SIZE, size);
+ out.setAxisValue(AINPUT_MOTION_AXIS_TOUCH_MAJOR, touchMajor);
+ out.setAxisValue(AINPUT_MOTION_AXIS_TOUCH_MINOR, touchMinor);
+ out.setAxisValue(AINPUT_MOTION_AXIS_TOOL_MAJOR, toolMajor);
+ out.setAxisValue(AINPUT_MOTION_AXIS_TOOL_MINOR, toolMinor);
+ out.setAxisValue(AINPUT_MOTION_AXIS_ORIENTATION, orientation);
pointerIds[outIndex] = int32_t(id);
@@ -2704,14 +2706,17 @@ void TouchInputMapper::dispatchTouch(nsecs_t when, uint32_t policyFlags,
// Check edge flags by looking only at the first pointer since the flags are
// global to the event.
if (motionEventAction == AMOTION_EVENT_ACTION_DOWN) {
- if (pointerCoords[0].x <= 0) {
+ float x = pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_X);
+ float y = pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_Y);
+
+ if (x <= 0) {
motionEventEdgeFlags |= AMOTION_EVENT_EDGE_FLAG_LEFT;
- } else if (pointerCoords[0].x >= mLocked.orientedSurfaceWidth) {
+ } else if (x >= mLocked.orientedSurfaceWidth) {
motionEventEdgeFlags |= AMOTION_EVENT_EDGE_FLAG_RIGHT;
}
- if (pointerCoords[0].y <= 0) {
+ if (y <= 0) {
motionEventEdgeFlags |= AMOTION_EVENT_EDGE_FLAG_TOP;
- } else if (pointerCoords[0].y >= mLocked.orientedSurfaceHeight) {
+ } else if (y >= mLocked.orientedSurfaceHeight) {
motionEventEdgeFlags |= AMOTION_EVENT_EDGE_FLAG_BOTTOM;
}
}
@@ -3851,15 +3856,9 @@ void JoystickInputMapper::sync(nsecs_t when) {
if (motionAxisChanged) {
PointerCoords pointerCoords;
- pointerCoords.x = mAxes.x.value;
- pointerCoords.y = mAxes.y.value;
- pointerCoords.touchMajor = 0;
- pointerCoords.touchMinor = 0;
- pointerCoords.toolMajor = 0;
- pointerCoords.toolMinor = 0;
- pointerCoords.pressure = 0;
- pointerCoords.size = 0;
- pointerCoords.orientation = 0;
+ pointerCoords.clear();
+ pointerCoords.setAxisValue(AINPUT_MOTION_AXIS_X, mAxes.x.value);
+ pointerCoords.setAxisValue(AINPUT_MOTION_AXIS_Y, mAxes.y.value);
int32_t pointerId = 0;
getDispatcher()->notifyMotion(when, getDeviceId(), AINPUT_SOURCE_JOYSTICK, 0,
diff --git a/services/input/tests/InputReader_test.cpp b/services/input/tests/InputReader_test.cpp
index 8ec1fd4..34d613a 100644
--- a/services/input/tests/InputReader_test.cpp
+++ b/services/input/tests/InputReader_test.cpp
@@ -1473,15 +1473,15 @@ protected:
float x, float y, float pressure, float size,
float touchMajor, float touchMinor, float toolMajor, float toolMinor,
float orientation) {
- ASSERT_NEAR(x, coords.x, 1);
- ASSERT_NEAR(y, coords.y, 1);
- ASSERT_NEAR(pressure, coords.pressure, EPSILON);
- ASSERT_NEAR(size, coords.size, EPSILON);
- ASSERT_NEAR(touchMajor, coords.touchMajor, 1);
- ASSERT_NEAR(touchMinor, coords.touchMinor, 1);
- ASSERT_NEAR(toolMajor, coords.toolMajor, 1);
- ASSERT_NEAR(toolMinor, coords.toolMinor, 1);
- ASSERT_NEAR(orientation, coords.orientation, EPSILON);
+ ASSERT_NEAR(x, coords.getAxisValue(AINPUT_MOTION_AXIS_X), 1);
+ ASSERT_NEAR(y, coords.getAxisValue(AINPUT_MOTION_AXIS_Y), 1);
+ ASSERT_NEAR(pressure, coords.getAxisValue(AINPUT_MOTION_AXIS_PRESSURE), EPSILON);
+ ASSERT_NEAR(size, coords.getAxisValue(AINPUT_MOTION_AXIS_SIZE), EPSILON);
+ ASSERT_NEAR(touchMajor, coords.getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MAJOR), 1);
+ ASSERT_NEAR(touchMinor, coords.getAxisValue(AINPUT_MOTION_AXIS_TOUCH_MINOR), 1);
+ ASSERT_NEAR(toolMajor, coords.getAxisValue(AINPUT_MOTION_AXIS_TOOL_MAJOR), 1);
+ ASSERT_NEAR(toolMinor, coords.getAxisValue(AINPUT_MOTION_AXIS_TOOL_MINOR), 1);
+ ASSERT_NEAR(orientation, coords.getAxisValue(AINPUT_MOTION_AXIS_ORIENTATION), EPSILON);
}
};
@@ -2078,7 +2078,6 @@ TEST_F(CursorInputMapperTest, Process_ShouldHandleIndependentXYUpdates) {
process(mapper, ARBITRARY_TIME, DEVICE_ID, EV_SYN, SYN_REPORT, 0, 0, 0);
ASSERT_NO_FATAL_FAILURE(mFakeDispatcher->assertNotifyMotionWasCalled(&args));
ASSERT_EQ(AMOTION_EVENT_ACTION_MOVE, args.action);
- ASSERT_NEAR(0.0f, args.pointerCoords[0].x, EPSILON);
ASSERT_NO_FATAL_FAILURE(assertPointerCoords(args.pointerCoords[0],
0.0f, -2.0f / TRACKBALL_MOVEMENT_THRESHOLD, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f));
}
@@ -2893,8 +2892,8 @@ TEST_F(SingleTouchInputMapperTest, Process_WhenNotOrientationAware_DoesNotRotate
processSync(mapper);
ASSERT_NO_FATAL_FAILURE(mFakeDispatcher->assertNotifyMotionWasCalled(&args));
- ASSERT_NEAR(50, args.pointerCoords[0].x, 1);
- ASSERT_NEAR(75, args.pointerCoords[0].y, 1);
+ ASSERT_NEAR(50, args.pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_X), 1);
+ ASSERT_NEAR(75, args.pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_Y), 1);
processUp(mapper);
processSync(mapper);
@@ -2915,8 +2914,8 @@ TEST_F(SingleTouchInputMapperTest, Process_WhenOrientationAware_RotatesMotions)
processSync(mapper);
ASSERT_NO_FATAL_FAILURE(mFakeDispatcher->assertNotifyMotionWasCalled(&args));
- ASSERT_NEAR(50, args.pointerCoords[0].x, 1);
- ASSERT_NEAR(75, args.pointerCoords[0].y, 1);
+ ASSERT_NEAR(50, args.pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_X), 1);
+ ASSERT_NEAR(75, args.pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_Y), 1);
processUp(mapper);
processSync(mapper);
@@ -2928,8 +2927,8 @@ TEST_F(SingleTouchInputMapperTest, Process_WhenOrientationAware_RotatesMotions)
processSync(mapper);
ASSERT_NO_FATAL_FAILURE(mFakeDispatcher->assertNotifyMotionWasCalled(&args));
- ASSERT_NEAR(75, args.pointerCoords[0].x, 1);
- ASSERT_NEAR(DISPLAY_WIDTH - 50, args.pointerCoords[0].y, 1);
+ ASSERT_NEAR(75, args.pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_X), 1);
+ ASSERT_NEAR(DISPLAY_WIDTH - 50, args.pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_Y), 1);
processUp(mapper);
processSync(mapper);
@@ -2941,8 +2940,8 @@ TEST_F(SingleTouchInputMapperTest, Process_WhenOrientationAware_RotatesMotions)
processSync(mapper);
ASSERT_NO_FATAL_FAILURE(mFakeDispatcher->assertNotifyMotionWasCalled(&args));
- ASSERT_NEAR(DISPLAY_WIDTH - 50, args.pointerCoords[0].x, 1);
- ASSERT_NEAR(DISPLAY_HEIGHT - 75, args.pointerCoords[0].y, 1);
+ ASSERT_NEAR(DISPLAY_WIDTH - 50, args.pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_X), 1);
+ ASSERT_NEAR(DISPLAY_HEIGHT - 75, args.pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_Y), 1);
processUp(mapper);
processSync(mapper);
@@ -2954,8 +2953,8 @@ TEST_F(SingleTouchInputMapperTest, Process_WhenOrientationAware_RotatesMotions)
processSync(mapper);
ASSERT_NO_FATAL_FAILURE(mFakeDispatcher->assertNotifyMotionWasCalled(&args));
- ASSERT_NEAR(DISPLAY_HEIGHT - 75, args.pointerCoords[0].x, 1);
- ASSERT_NEAR(50, args.pointerCoords[0].y, 1);
+ ASSERT_NEAR(DISPLAY_HEIGHT - 75, args.pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_X), 1);
+ ASSERT_NEAR(50, args.pointerCoords[0].getAxisValue(AINPUT_MOTION_AXIS_Y), 1);
processUp(mapper);
processSync(mapper);
diff --git a/services/java/com/android/server/DevicePolicyManagerService.java b/services/java/com/android/server/DevicePolicyManagerService.java
index b2d534b..df2cd1b 100644
--- a/services/java/com/android/server/DevicePolicyManagerService.java
+++ b/services/java/com/android/server/DevicePolicyManagerService.java
@@ -79,9 +79,9 @@ import java.util.Set;
* Implementation of the device policy APIs.
*/
public class DevicePolicyManagerService extends IDevicePolicyManager.Stub {
- private static final int REQUEST_EXPIRE_PASSWORD = 5571;
+ private static final String TAG = "DevicePolicyManagerService";
- static final String TAG = "DevicePolicyManagerService";
+ private static final int REQUEST_EXPIRE_PASSWORD = 5571;
private static final long EXPIRATION_GRACE_PERIOD_MS = 5 * 86400 * 1000; // 5 days, in ms
diff --git a/services/jni/com_android_server_InputManager.cpp b/services/jni/com_android_server_InputManager.cpp
index 5b329bb..427af23 100644
--- a/services/jni/com_android_server_InputManager.cpp
+++ b/services/jni/com_android_server_InputManager.cpp
@@ -87,7 +87,6 @@ static struct {
jfieldID mName;
jfieldID mSources;
jfieldID mKeyboardType;
- jfieldID mMotionRanges;
} gInputDeviceClassInfo;
static struct {
@@ -1221,9 +1220,6 @@ int register_android_server_InputManager(JNIEnv* env) {
GET_FIELD_ID(gInputDeviceClassInfo.mKeyboardType, gInputDeviceClassInfo.clazz,
"mKeyboardType", "I");
- GET_FIELD_ID(gInputDeviceClassInfo.mMotionRanges, gInputDeviceClassInfo.clazz,
- "mMotionRanges", "[Landroid/view/InputDevice$MotionRange;");
-
// Configuration
FIND_CLASS(gConfigurationClassInfo.clazz, "android/content/res/Configuration");
diff --git a/services/surfaceflinger/Layer.cpp b/services/surfaceflinger/Layer.cpp
index fde8e67..0f7d639 100644
--- a/services/surfaceflinger/Layer.cpp
+++ b/services/surfaceflinger/Layer.cpp
@@ -142,7 +142,8 @@ void Layer::onRemoved()
sp<LayerBaseClient::Surface> Layer::createSurface() const
{
- return mSurface;
+ sp<Surface> sur(new SurfaceLayer(mFlinger, const_cast<Layer *>(this)));
+ return sur;
}
status_t Layer::ditch()
@@ -152,9 +153,6 @@ status_t Layer::ditch()
// the layer is not on screen anymore. free as much resources as possible
mFreezeLock.clear();
- // Free our own reference to ISurface
- mSurface.clear();
-
Mutex::Autolock _l(mLock);
mWidth = mHeight = 0;
return NO_ERROR;
@@ -202,7 +200,6 @@ status_t Layer::setBuffers( uint32_t w, uint32_t h,
int layerRedsize = info.getSize(PixelFormatInfo::INDEX_RED);
mNeedsDithering = layerRedsize > displayRedSize;
- mSurface = new SurfaceLayer(mFlinger, this);
return NO_ERROR;
}
diff --git a/services/surfaceflinger/Layer.h b/services/surfaceflinger/Layer.h
index d9a8be3..2b38414 100644
--- a/services/surfaceflinger/Layer.h
+++ b/services/surfaceflinger/Layer.h
@@ -213,7 +213,6 @@ private:
ClientRef mUserClientRef;
// constants
- sp<Surface> mSurface;
PixelFormat mFormat;
const GLExtensions& mGLExtensions;
bool mNeedsBlending;
diff --git a/services/surfaceflinger/LayerBase.cpp b/services/surfaceflinger/LayerBase.cpp
index 86057f8..6025ed4 100644
--- a/services/surfaceflinger/LayerBase.cpp
+++ b/services/surfaceflinger/LayerBase.cpp
@@ -540,7 +540,9 @@ int32_t LayerBaseClient::sIdentity = 1;
LayerBaseClient::LayerBaseClient(SurfaceFlinger* flinger, DisplayID display,
const sp<Client>& client)
- : LayerBase(flinger, display), mClientRef(client),
+ : LayerBase(flinger, display),
+ mHasSurface(false),
+ mClientRef(client),
mIdentity(uint32_t(android_atomic_inc(&sIdentity)))
{
}
@@ -557,12 +559,13 @@ sp<LayerBaseClient::Surface> LayerBaseClient::getSurface()
{
sp<Surface> s;
Mutex::Autolock _l(mLock);
- s = mClientSurface.promote();
- if (s == 0) {
- s = createSurface();
- mClientSurface = s;
- mClientSurfaceBinder = s->asBinder();
- }
+
+ LOG_ALWAYS_FATAL_IF(mHasSurface,
+ "LayerBaseClient::getSurface() has already been called");
+
+ mHasSurface = true;
+ s = createSurface();
+ mClientSurfaceBinder = s->asBinder();
return s;
}
diff --git a/services/surfaceflinger/LayerBase.h b/services/surfaceflinger/LayerBase.h
index 184edd7..bfe92e6 100644
--- a/services/surfaceflinger/LayerBase.h
+++ b/services/surfaceflinger/LayerBase.h
@@ -337,7 +337,7 @@ protected:
private:
mutable Mutex mLock;
- mutable wp<Surface> mClientSurface;
+ mutable bool mHasSurface;
wp<IBinder> mClientSurfaceBinder;
const wp<Client> mClientRef;
// only read
diff --git a/wifi/java/android/net/wifi/WifiManager.java b/wifi/java/android/net/wifi/WifiManager.java
index d05918f..4ac03a8 100644
--- a/wifi/java/android/net/wifi/WifiManager.java
+++ b/wifi/java/android/net/wifi/WifiManager.java
@@ -356,16 +356,6 @@ public class WifiManager {
public static final String ACTION_PICK_WIFI_NETWORK = "android.net.wifi.PICK_WIFI_NETWORK";
/**
- * In this Wi-Fi lock mode, Wi-Fi will behave as in the mode
- * {@link #WIFI_MODE_FULL} but it operates at high performance
- * at the expense of power. This mode should be used
- * only when the wifi connection needs to have minimum loss and low
- * latency as it can impact the battery life.
- * @hide
- */
- public static final int WIFI_MODE_FULL_HIGH_PERF = 3;
-
- /**
* In this Wi-Fi lock mode, Wi-Fi will be kept active,
* and will behave normally, i.e., it will attempt to automatically
* establish a connection to a remembered access point that is
@@ -383,10 +373,29 @@ public class WifiManager {
* an application in this mode.
*/
public static final int WIFI_MODE_SCAN_ONLY = 2;
+ /**
+ * In this Wi-Fi lock mode, Wi-Fi will be kept active as in mode
+ * {@link #WIFI_MODE_FULL} but it operates at high performance
+ * with minimum packet loss and low packet latency even when
+ * the device screen is off. This mode will consume more power
+ * and hence should be used only when there is a need for such
+ * an active connection.
+ * <p>
+ * An example use case is when a voice connection needs to be
+ * kept active even after the device screen goes off. Holding the
+ * regular {@link #WIFI_MODE_FULL} lock will keep the wifi
+ * connection active, but the connection can be lossy.
+ * Holding a {@link #WIFI_MODE_FULL_HIGH_PERF} lock for the
+ * duration of the voice call will improve the call quality.
+ * <p>
+ * When there is no support from the hardware, this lock mode
+ * will have the same behavior as {@link #WIFI_MODE_FULL}
+ */
+ public static final int WIFI_MODE_FULL_HIGH_PERF = 3;
/** Anything worse than or equal to this will show 0 bars. */
private static final int MIN_RSSI = -100;
-
+
/** Anything better than or equal to this will show the max bars. */
private static final int MAX_RSSI = -55;
@@ -1288,9 +1297,10 @@ public class WifiManager {
* Creates a new WifiLock.
*
* @param lockType the type of lock to create. See {@link #WIFI_MODE_FULL},
- * and {@link #WIFI_MODE_SCAN_ONLY} for descriptions of the types of Wi-Fi locks.
- * @param tag a tag for the WifiLock to identify it in debugging messages. This string is
- * never shown to the user under normal conditions, but should be descriptive
+ * {@link #WIFI_MODE_FULL_HIGH_PERF} and {@link #WIFI_MODE_SCAN_ONLY} for
+ * descriptions of the types of Wi-Fi locks.
+ * @param tag a tag for the WifiLock to identify it in debugging messages. This string is
+ * never shown to the user under normal conditions, but should be descriptive
* enough to identify your application and the specific WifiLock within it, if it
* holds multiple WifiLocks.
*
@@ -1301,7 +1311,7 @@ public class WifiManager {
public WifiLock createWifiLock(int lockType, String tag) {
return new WifiLock(lockType, tag);
}
-
+
/**
* Creates a new WifiLock.
*