| 1 | diff --git a/android/src/main/java/com/reactnativecommunity/webview/RNCWebView.java b/android/src/main/java/com/reactnativecommunity/webview/RNCWebView.java |
| 2 | index 80c6803..374f824 100644 |
| 3 | --- a/android/src/main/java/com/reactnativecommunity/webview/RNCWebView.java |
| 4 | +++ b/android/src/main/java/com/reactnativecommunity/webview/RNCWebView.java |
| 5 | @@ -122,14 +122,50 @@ public class RNCWebView extends WebView implements LifecycleEventListener { |
| 6 | cleanupCallbacksAndDestroy(); |
| 7 | } |
| 8 | |
| 9 | + private float touchDownX; |
| 10 | + private float touchDownY; |
| 11 | + private float lastTouchY; |
| 12 | + private boolean multiTouch; |
| 13 | + |
| 14 | @Override |
| 15 | public boolean onTouchEvent(MotionEvent event) { |
| 16 | if (this.nestedScrollEnabled) { |
| 17 | - requestDisallowInterceptTouchEvent(true); |
| 18 | + requestDisallowInterceptTouchEvent(!shouldYieldToParent(event)); |
| 19 | } |
| 20 | return super.onTouchEvent(event); |
| 21 | } |
| 22 | |
| 23 | + // A page that scrolls vertically hands a mostly vertical drag to the scrolling |
| 24 | + // parent once it cannot scroll further that way, as nested scroll views do on iOS |
| 25 | + // and the web. A page that never scrolls vertically keeps every gesture, since it |
| 26 | + // may scroll inside an iframe this view cannot measure. A gesture that ever has |
| 27 | + // a second finger, such as a pinch, stays with the page until every finger lifts. |
| 28 | + private boolean shouldYieldToParent(MotionEvent event) { |
| 29 | + switch (event.getActionMasked()) { |
| 30 | + case MotionEvent.ACTION_DOWN: |
| 31 | + touchDownX = event.getX(); |
| 32 | + touchDownY = event.getY(); |
| 33 | + lastTouchY = touchDownY; |
| 34 | + multiTouch = false; |
| 35 | + return false; |
| 36 | + case MotionEvent.ACTION_POINTER_DOWN: |
| 37 | + multiTouch = true; |
| 38 | + return false; |
| 39 | + case MotionEvent.ACTION_MOVE: |
| 40 | + if (multiTouch) return false; |
| 41 | + float dy = event.getY() - lastTouchY; |
| 42 | + lastTouchY = event.getY(); |
| 43 | + if (dy == 0) return false; |
| 44 | + if (Math.abs(event.getY() - touchDownY) < Math.abs(event.getX() - touchDownX)) { |
| 45 | + return false; |
| 46 | + } |
| 47 | + if (!canScrollVertically(1) && !canScrollVertically(-1)) return false; |
| 48 | + return !canScrollVertically(dy > 0 ? -1 : 1); |
| 49 | + default: |
| 50 | + return false; |
| 51 | + } |
| 52 | + } |
| 53 | + |
| 54 | @Override |
| 55 | protected void onSizeChanged(int w, int h, int ow, int oh) { |
| 56 | super.onSizeChanged(w, h, ow, oh); |