Permalink
Browse files

Fix timestamps on android touch events to use milliseconds, to be con…

…sistent with iOS

Summary:
So `PanReponder.onPanResponderRelease/onPanResponderTerminate` receive a `gestureState` object containing a `onPanResponderTerminate.vx/vy` property. On Android and iOS, they appear to be orders of magnitude different, which appear to be due to the different scale of timestamps that are used when generating touch events.

This pull request fixes the timestamps to be milliseconds on both platforms (since I assume iOS is the more authoritative one, and is the one that `react-native-viewpager`'s vx thresholds written written to compare against.)

As far as I can tell, the RN code doesn't use the `vx/vy` properties, so they should be okay. And looks like the RN code only cares about relative values of `startTimestamp/currentTimestamp/previousTimestamp` though, so should be fine too. it's quite possible there will be downstream android breakage with this change, particularly for those who are already compensating for the RN discrepancy.
Closes #8199

Differential Revision: D3528215

Pulled By: dmmiller

fbshipit-source-id: cbd25bb7e7bb87fa77b661a057643a6ea97bc3f1
  • Loading branch information...
1 parent f534560 commit 4f5c2b48fe9e0e9d2f5024838ee16006f35ba326 @mikelambert mikelambert committed with Facebook Github Bot 2 Jul 7, 2016
Showing with 57 additions and 53 deletions.
  1. +6 −6 ReactAndroid/src/androidTest/java/com/facebook/react/tests/TextInputTestCase.java
  2. +4 −0 ReactAndroid/src/main/java/com/facebook/react/common/SystemClock.java
  3. +1 −1 ReactAndroid/src/main/java/com/facebook/react/modules/core/Timing.java
  4. +6 −6 ReactAndroid/src/main/java/com/facebook/react/uimanager/JSTouchDispatcher.java
  5. +1 −1 ReactAndroid/src/main/java/com/facebook/react/uimanager/OnLayoutEvent.java
  6. +4 −4 ReactAndroid/src/main/java/com/facebook/react/views/drawer/ReactDrawerLayoutManager.java
  7. +5 −5 ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
  8. +2 −2 ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostManager.java
  9. +1 −1 ReactAndroid/src/main/java/com/facebook/react/views/picker/ReactPickerManager.java
  10. +2 −2 ReactAndroid/src/main/java/com/facebook/react/views/recyclerview/RecyclerViewBackedScrollView.java
  11. +1 −1 ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewHelper.java
  12. +2 −2 ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
  13. +1 −1 ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/SwipeRefreshLayoutManager.java
  14. +1 −1 ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
  15. +7 −7 ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
  16. +2 −2 ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java
  17. +3 −3 ReactAndroid/src/main/java/com/facebook/react/views/viewpager/ReactViewPager.java
  18. +4 −4 ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
  19. +3 −3 ReactAndroid/src/test/java/com/facebook/react/RootViewTest.java
  20. +1 −1 ReactAndroid/src/test/java/com/facebook/react/modules/timing/TimingModuleTest.java
@@ -116,7 +116,7 @@ public void testMetionsInputColors() throws Throwable {
eventDispatcher.dispatchEvent(
new ReactTextChangedEvent(
reactEditText.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
newText.toString(),
(int) PixelUtil.toDIPFromPixel(contentWidth),
(int) PixelUtil.toDIPFromPixel(contentHeight),
@@ -125,7 +125,7 @@ public void testMetionsInputColors() throws Throwable {
eventDispatcher.dispatchEvent(
new ReactTextInputEvent(
reactEditText.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
newText.toString(),
"",
start,
@@ -150,7 +150,7 @@ public void testMetionsInputColors() throws Throwable {
eventDispatcher.dispatchEvent(
new ReactTextChangedEvent(
reactEditText.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
newText.toString(),
(int) PixelUtil.toDIPFromPixel(contentWidth),
(int) PixelUtil.toDIPFromPixel(contentHeight),
@@ -159,7 +159,7 @@ public void testMetionsInputColors() throws Throwable {
eventDispatcher.dispatchEvent(
new ReactTextInputEvent(
reactEditText.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
moreText,
"",
start,
@@ -184,7 +184,7 @@ public void testMetionsInputColors() throws Throwable {
eventDispatcher.dispatchEvent(
new ReactTextChangedEvent(
reactEditText.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
newText.toString(),
(int) PixelUtil.toDIPFromPixel(contentWidth),
(int) PixelUtil.toDIPFromPixel(contentHeight),
@@ -193,7 +193,7 @@ public void testMetionsInputColors() throws Throwable {
eventDispatcher.dispatchEvent(
new ReactTextInputEvent(
reactEditText.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
moreText,
"",
start,
@@ -22,4 +22,8 @@ public static long currentTimeMillis() {
public static long nanoTime() {
return System.nanoTime();
}
+
+ public static long elapsedRealtime() {
+ return android.os.SystemClock.elapsedRealtime();
+ }
}
@@ -244,7 +244,7 @@ public void createTimer(
return;
}
- long initialTargetTime = SystemClock.nanoTime() / 1000000 + adjustedDuration;
+ long initialTargetTime = SystemClock.elapsedRealtime() + adjustedDuration;
Timer timer = new Timer(executorToken, callbackID, initialTargetTime, duration, repeat);
synchronized (mTimerGuard) {
mTimers.add(timer);
@@ -82,7 +82,7 @@ public void handleTouchEvent(MotionEvent ev, EventDispatcher eventDispatcher) {
eventDispatcher.dispatchEvent(
TouchEvent.obtain(
mTargetTag,
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
TouchEventType.START,
ev,
mTargetCoordinates[0],
@@ -105,7 +105,7 @@ public void handleTouchEvent(MotionEvent ev, EventDispatcher eventDispatcher) {
eventDispatcher.dispatchEvent(
TouchEvent.obtain(
mTargetTag,
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
TouchEventType.END,
ev,
mTargetCoordinates[0],
@@ -117,7 +117,7 @@ public void handleTouchEvent(MotionEvent ev, EventDispatcher eventDispatcher) {
eventDispatcher.dispatchEvent(
TouchEvent.obtain(
mTargetTag,
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
TouchEventType.MOVE,
ev,
mTargetCoordinates[0],
@@ -128,7 +128,7 @@ public void handleTouchEvent(MotionEvent ev, EventDispatcher eventDispatcher) {
eventDispatcher.dispatchEvent(
TouchEvent.obtain(
mTargetTag,
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
TouchEventType.START,
ev,
mTargetCoordinates[0],
@@ -139,7 +139,7 @@ public void handleTouchEvent(MotionEvent ev, EventDispatcher eventDispatcher) {
eventDispatcher.dispatchEvent(
TouchEvent.obtain(
mTargetTag,
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
TouchEventType.END,
ev,
mTargetCoordinates[0],
@@ -180,7 +180,7 @@ private void dispatchCancelEvent(MotionEvent androidEvent, EventDispatcher event
Assertions.assertNotNull(eventDispatcher).dispatchEvent(
TouchEvent.obtain(
mTargetTag,
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
TouchEventType.CANCEL,
androidEvent,
mTargetCoordinates[0],
@@ -45,7 +45,7 @@ private OnLayoutEvent() {
}
protected void init(int viewTag, int x, int y, int width, int height) {
- super.init(viewTag, SystemClock.nanoTime());
+ super.init(viewTag, SystemClock.elapsedRealtime());
mX = x;
mY = y;
mWidth = width;
@@ -188,25 +188,25 @@ public DrawerEventEmitter(DrawerLayout drawerLayout, EventDispatcher eventDispat
@Override
public void onDrawerSlide(View view, float v) {
mEventDispatcher.dispatchEvent(
- new DrawerSlideEvent(mDrawerLayout.getId(), SystemClock.nanoTime(), v));
+ new DrawerSlideEvent(mDrawerLayout.getId(), SystemClock.elapsedRealtime(), v));
}
@Override
public void onDrawerOpened(View view) {
mEventDispatcher.dispatchEvent(
- new DrawerOpenedEvent(mDrawerLayout.getId(), SystemClock.nanoTime()));
+ new DrawerOpenedEvent(mDrawerLayout.getId(), SystemClock.elapsedRealtime()));
}
@Override
public void onDrawerClosed(View view) {
mEventDispatcher.dispatchEvent(
- new DrawerClosedEvent(mDrawerLayout.getId(), SystemClock.nanoTime()));
+ new DrawerClosedEvent(mDrawerLayout.getId(), SystemClock.elapsedRealtime()));
}
@Override
public void onDrawerStateChanged(int i) {
mEventDispatcher.dispatchEvent(
- new DrawerStateChangedEvent(mDrawerLayout.getId(), SystemClock.nanoTime(), i));
+ new DrawerStateChangedEvent(mDrawerLayout.getId(), SystemClock.elapsedRealtime(), i));
}
}
}
@@ -192,7 +192,7 @@ public void setShouldNotifyLoadEvents(boolean shouldNotify) {
@Override
public void onSubmit(String id, Object callerContext) {
mEventDispatcher.dispatchEvent(
- new ImageLoadEvent(getId(), SystemClock.nanoTime(), ImageLoadEvent.ON_LOAD_START));
+ new ImageLoadEvent(getId(), SystemClock.elapsedRealtime(), ImageLoadEvent.ON_LOAD_START));
}
@Override
@@ -202,18 +202,18 @@ public void onFinalImageSet(
@Nullable Animatable animatable) {
if (imageInfo != null) {
mEventDispatcher.dispatchEvent(
- new ImageLoadEvent(getId(), SystemClock.nanoTime(), ImageLoadEvent.ON_LOAD));
+ new ImageLoadEvent(getId(), SystemClock.elapsedRealtime(), ImageLoadEvent.ON_LOAD));
mEventDispatcher.dispatchEvent(
- new ImageLoadEvent(getId(), SystemClock.nanoTime(), ImageLoadEvent.ON_LOAD_END));
+ new ImageLoadEvent(getId(), SystemClock.elapsedRealtime(), ImageLoadEvent.ON_LOAD_END));
}
}
@Override
public void onFailure(String id, Throwable throwable) {
mEventDispatcher.dispatchEvent(
- new ImageLoadEvent(getId(), SystemClock.nanoTime(), ImageLoadEvent.ON_ERROR));
+ new ImageLoadEvent(getId(), SystemClock.elapsedRealtime(), ImageLoadEvent.ON_ERROR));
mEventDispatcher.dispatchEvent(
- new ImageLoadEvent(getId(), SystemClock.nanoTime(), ImageLoadEvent.ON_LOAD_END));
+ new ImageLoadEvent(getId(), SystemClock.elapsedRealtime(), ImageLoadEvent.ON_LOAD_END));
}
};
}
@@ -85,14 +85,14 @@ protected void addEventEmitters(
new ReactModalHostView.OnRequestCloseListener() {
@Override
public void onRequestClose(DialogInterface dialog) {
- dispatcher.dispatchEvent(new RequestCloseEvent(view.getId(), SystemClock.nanoTime()));
+ dispatcher.dispatchEvent(new RequestCloseEvent(view.getId(), SystemClock.elapsedRealtime()));
}
});
view.setOnShowListener(
new DialogInterface.OnShowListener() {
@Override
public void onShow(DialogInterface dialog) {
- dispatcher.dispatchEvent(new ShowEvent(view.getId(), SystemClock.nanoTime()));
+ dispatcher.dispatchEvent(new ShowEvent(view.getId(), SystemClock.elapsedRealtime()));
}
});
}
@@ -157,7 +157,7 @@ public PickerEventEmitter(ReactPicker reactPicker, EventDispatcher eventDispatch
@Override
public void onItemSelected(int position) {
mEventDispatcher.dispatchEvent( new PickerItemSelectEvent(
- mReactPicker.getId(), SystemClock.nanoTime(), position));
+ mReactPicker.getId(), SystemClock.elapsedRealtime(), position));
}
}
}
@@ -344,7 +344,7 @@ protected void onScrollChanged(int l, int t, int oldl, int oldt) {
((ReactContext) getContext()).getNativeModule(UIManagerModule.class).getEventDispatcher()
.dispatchEvent(ScrollEvent.obtain(
getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
ScrollEventType.SCROLL,
0, /* offsetX = 0, horizontal scrolling only */
calculateAbsoluteOffset(),
@@ -359,7 +359,7 @@ private void onTotalChildrenHeightChange(int newTotalChildrenHeight) {
((ReactContext) getContext()).getNativeModule(UIManagerModule.class).getEventDispatcher()
.dispatchEvent(new ContentSizeChangeEvent(
getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
getWidth(),
newTotalChildrenHeight));
}
@@ -57,7 +57,7 @@ private static void emitScrollEvent(ViewGroup scrollView, ScrollEventType scroll
reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
ScrollEvent.obtain(
scrollView.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
scrollEventType,
scrollView.getScrollX(),
scrollView.getScrollY(),
@@ -81,7 +81,7 @@ public void onProgressChanged(SeekBar seekbar, int progress, boolean fromUser) {
reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
new ReactSliderEvent(
seekbar.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
((ReactSlider)seekbar).toRealProgress(progress),
fromUser));
}
@@ -96,7 +96,7 @@ public void onStopTrackingTouch(SeekBar seekbar) {
reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
new ReactSlidingCompleteEvent(
seekbar.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
((ReactSlider)seekbar).toRealProgress(seekbar.getProgress())));
}
};
@@ -89,7 +89,7 @@ protected void addEventEmitters(
@Override
public void onRefresh() {
reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher()
- .dispatchEvent(new RefreshEvent(view.getId(), SystemClock.nanoTime()));
+ .dispatchEvent(new RefreshEvent(view.getId(), SystemClock.elapsedRealtime()));
}
});
}
@@ -78,7 +78,7 @@ public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
new ReactSwitchEvent(
buttonView.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
isChecked));
}
};
@@ -567,7 +567,7 @@ public void onTextChanged(CharSequence s, int start, int before, int count) {
mEventDispatcher.dispatchEvent(
new ReactTextChangedEvent(
mEditText.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
s.toString(),
(int) PixelUtil.toDIPFromPixel(contentWidth),
(int) PixelUtil.toDIPFromPixel(contentHeight),
@@ -576,7 +576,7 @@ public void onTextChanged(CharSequence s, int start, int before, int count) {
mEventDispatcher.dispatchEvent(
new ReactTextInputEvent(
mEditText.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
newText,
oldText,
start,
@@ -602,17 +602,17 @@ public void onFocusChange(View v, boolean hasFocus) {
eventDispatcher.dispatchEvent(
new ReactTextInputFocusEvent(
editText.getId(),
- SystemClock.nanoTime()));
+ SystemClock.elapsedRealtime()));
} else {
eventDispatcher.dispatchEvent(
new ReactTextInputBlurEvent(
editText.getId(),
- SystemClock.nanoTime()));
+ SystemClock.elapsedRealtime()));
eventDispatcher.dispatchEvent(
new ReactTextInputEndEditingEvent(
editText.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
editText.getText().toString()));
}
}
@@ -630,7 +630,7 @@ public boolean onEditorAction(TextView v, int actionId, KeyEvent keyEvent) {
eventDispatcher.dispatchEvent(
new ReactTextInputSubmitEditingEvent(
editText.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
editText.getText().toString()));
}
if (actionId == EditorInfo.IME_ACTION_NEXT ||
@@ -667,7 +667,7 @@ public void onSelectionChanged(int start, int end) {
mEventDispatcher.dispatchEvent(
new ReactTextInputSelectionEvent(
mReactEditText.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
start,
end
)
@@ -131,7 +131,7 @@ protected void addEventEmitters(final ThemedReactContext reactContext, final Rea
@Override
public void onClick(View v) {
mEventDispatcher.dispatchEvent(
- new ToolbarClickEvent(view.getId(), SystemClock.nanoTime(), -1));
+ new ToolbarClickEvent(view.getId(), SystemClock.elapsedRealtime(), -1));
}
});
@@ -142,7 +142,7 @@ public boolean onMenuItemClick(MenuItem menuItem) {
mEventDispatcher.dispatchEvent(
new ToolbarClickEvent(
view.getId(),
- SystemClock.nanoTime(),
+ SystemClock.elapsedRealtime(),
menuItem.getOrder()));
return true;
}
@@ -91,14 +91,14 @@ public boolean isViewFromObject(View view, Object object) {
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
mEventDispatcher.dispatchEvent(
- new PageScrollEvent(getId(), SystemClock.nanoTime(), position, positionOffset));
+ new PageScrollEvent(getId(), SystemClock.elapsedRealtime(), position, positionOffset));
}
@Override
public void onPageSelected(int position) {
if (!mIsCurrentItemFromJs) {
mEventDispatcher.dispatchEvent(
- new PageSelectedEvent(getId(), SystemClock.nanoTime(), position));
+ new PageSelectedEvent(getId(), SystemClock.elapsedRealtime(), position));
}
}
@@ -119,7 +119,7 @@ public void onPageScrollStateChanged(int state) {
throw new IllegalStateException("Unsupported pageScrollState");
}
mEventDispatcher.dispatchEvent(
- new PageScrollStateChangedEvent(getId(), SystemClock.nanoTime(), pageScrollState));
+ new PageScrollStateChangedEvent(getId(), SystemClock.elapsedRealtime(), pageScrollState));
}
}
Oops, something went wrong.

0 comments on commit 4f5c2b4

Please sign in to comment.