diff --git a/lib/commonjs/ReactNativeZoomableView.js b/lib/commonjs/ReactNativeZoomableView.js index ded22ae..96e48a2 100644 --- a/lib/commonjs/ReactNativeZoomableView.js +++ b/lib/commonjs/ReactNativeZoomableView.js @@ -352,8 +352,8 @@ class ReactNativeZoomableView extends _react.Component { contentHeight } = this.props; // Offset for the static pin - const pinX = staticPinPosition.x - originalWidth / 2; - const pinY = staticPinPosition.y - originalHeight / 2; + const pinX = (staticPinPosition === null || staticPinPosition === void 0 ? void 0 : staticPinPosition.x) - originalWidth / 2; + const pinY = (staticPinPosition === null || staticPinPosition === void 0 ? void 0 : staticPinPosition.y) - originalHeight / 2; this.offsetX = contentWidth / 2 - position.x + pinX / this.zoomLevel; this.offsetY = contentHeight / 2 - position.y + pinY / this.zoomLevel; this.panAnim.setValue({ @@ -363,10 +363,12 @@ class ReactNativeZoomableView extends _react.Component { }); _defineProperty(this, "_staticPinPosition", () => { + var _this$props8, _this$props8$staticPi, _this$props9, _this$props9$staticPi; + return (0, _coordinateConversion.viewportPositionToImagePosition)({ viewportPosition: { - x: this.props.staticPinPosition.x, - y: this.props.staticPinPosition.y + x: (_this$props8 = this.props) === null || _this$props8 === void 0 ? void 0 : (_this$props8$staticPi = _this$props8.staticPinPosition) === null || _this$props8$staticPi === void 0 ? void 0 : _this$props8$staticPi.x, + y: (_this$props9 = this.props) === null || _this$props9 === void 0 ? void 0 : (_this$props9$staticPi = _this$props9.staticPinPosition) === null || _this$props9$staticPi === void 0 ? void 0 : _this$props9$staticPi.y }, imageSize: { height: this.props.contentHeight, @@ -381,9 +383,9 @@ class ReactNativeZoomableView extends _react.Component { }); _defineProperty(this, "_updateStaticPin", () => { - var _this$props$onStaticP2, _this$props8; + var _this$props$onStaticP2, _this$props10; - (_this$props$onStaticP2 = (_this$props8 = this.props).onStaticPinPositionChange) === null || _this$props$onStaticP2 === void 0 ? void 0 : _this$props$onStaticP2.call(_this$props8, this._staticPinPosition()); + (_this$props$onStaticP2 = (_this$props10 = this.props).onStaticPinPositionChange) === null || _this$props$onStaticP2 === void 0 ? void 0 : _this$props$onStaticP2.call(_this$props10, this._staticPinPosition()); }); this.gestureHandlers = _reactNative.PanResponder.create({ @@ -392,7 +394,7 @@ class ReactNativeZoomableView extends _react.Component { onPanResponderMove: this._handlePanResponderMove, onPanResponderRelease: this._handlePanResponderEnd, onPanResponderTerminate: (evt, gestureState) => { - var _this$props$onPanResp3, _this$props9; + var _this$props$onPanResp3, _this$props11; // We should also call _handlePanResponderEnd // to properly perform cleanups when the gesture is terminated @@ -402,28 +404,28 @@ class ReactNativeZoomableView extends _react.Component { // but onPanResponderTerminate is called instead for no apparent reason. this._handlePanResponderEnd(evt, gestureState); - (_this$props$onPanResp3 = (_this$props9 = this.props).onPanResponderTerminate) === null || _this$props$onPanResp3 === void 0 ? void 0 : _this$props$onPanResp3.call(_this$props9, evt, gestureState, this._getZoomableViewEventObject()); + (_this$props$onPanResp3 = (_this$props11 = this.props).onPanResponderTerminate) === null || _this$props$onPanResp3 === void 0 ? void 0 : _this$props$onPanResp3.call(_this$props11, evt, gestureState, this._getZoomableViewEventObject()); }, onPanResponderTerminationRequest: (evt, gestureState) => { - var _this$props$onPanResp4, _this$props10; + var _this$props$onPanResp4, _this$props12; - return !!((_this$props$onPanResp4 = (_this$props10 = this.props).onPanResponderTerminationRequest) !== null && _this$props$onPanResp4 !== void 0 && _this$props$onPanResp4.call(_this$props10, evt, gestureState, this._getZoomableViewEventObject())); + return !!((_this$props$onPanResp4 = (_this$props12 = this.props).onPanResponderTerminationRequest) !== null && _this$props$onPanResp4 !== void 0 && _this$props$onPanResp4.call(_this$props12, evt, gestureState, this._getZoomableViewEventObject())); }, // Defaults to true to prevent parent components, such as React Navigation's tab view, from taking over as responder. onShouldBlockNativeResponder: (evt, gestureState) => { - var _this$props$onShouldB, _this$props$onShouldB2, _this$props11; + var _this$props$onShouldB, _this$props$onShouldB2, _this$props13; - return (_this$props$onShouldB = (_this$props$onShouldB2 = (_this$props11 = this.props).onShouldBlockNativeResponder) === null || _this$props$onShouldB2 === void 0 ? void 0 : _this$props$onShouldB2.call(_this$props11, evt, gestureState, this._getZoomableViewEventObject())) !== null && _this$props$onShouldB !== void 0 ? _this$props$onShouldB : true; + return (_this$props$onShouldB = (_this$props$onShouldB2 = (_this$props13 = this.props).onShouldBlockNativeResponder) === null || _this$props$onShouldB2 === void 0 ? void 0 : _this$props$onShouldB2.call(_this$props13, evt, gestureState, this._getZoomableViewEventObject())) !== null && _this$props$onShouldB !== void 0 ? _this$props$onShouldB : true; }, onStartShouldSetPanResponderCapture: (evt, gestureState) => { - var _this$props$onStartSh, _this$props12; + var _this$props$onStartSh, _this$props14; - return (_this$props$onStartSh = (_this$props12 = this.props).onStartShouldSetPanResponderCapture) === null || _this$props$onStartSh === void 0 ? void 0 : _this$props$onStartSh.call(_this$props12, evt, gestureState); + return (_this$props$onStartSh = (_this$props14 = this.props).onStartShouldSetPanResponderCapture) === null || _this$props$onStartSh === void 0 ? void 0 : _this$props$onStartSh.call(_this$props14, evt, gestureState); }, onMoveShouldSetPanResponderCapture: (evt, gestureState) => { - var _this$props$onMoveSho, _this$props13; + var _this$props$onMoveSho, _this$props15; - return (_this$props$onMoveSho = (_this$props13 = this.props).onMoveShouldSetPanResponderCapture) === null || _this$props$onMoveSho === void 0 ? void 0 : _this$props$onMoveSho.call(_this$props13, evt, gestureState); + return (_this$props$onMoveSho = (_this$props15 = this.props).onMoveShouldSetPanResponderCapture) === null || _this$props$onMoveSho === void 0 ? void 0 : _this$props$onMoveSho.call(_this$props15, evt, gestureState); } }); this.zoomSubjectWrapperRef = /*#__PURE__*/(0, _react.createRef)(); @@ -581,15 +583,15 @@ class ReactNativeZoomableView extends _react.Component { * @private */ _invokeOnTransform() { - var _this$props$onTransfo, _this$props14, _this$props$onStaticP3, _this$props15; + var _this$props$onTransfo, _this$props16, _this$props$onStaticP3, _this$props17; const zoomableViewEvent = this._getZoomableViewEventObject(); if (!zoomableViewEvent.originalWidth || !zoomableViewEvent.originalHeight) return { successful: false }; - (_this$props$onTransfo = (_this$props14 = this.props).onTransform) === null || _this$props$onTransfo === void 0 ? void 0 : _this$props$onTransfo.call(_this$props14, zoomableViewEvent); - (_this$props$onStaticP3 = (_this$props15 = this.props).onStaticPinPositionMove) === null || _this$props$onStaticP3 === void 0 ? void 0 : _this$props$onStaticP3.call(_this$props15, this._staticPinPosition()); + (_this$props$onTransfo = (_this$props16 = this.props).onTransform) === null || _this$props$onTransfo === void 0 ? void 0 : _this$props$onTransfo.call(_this$props16, zoomableViewEvent); + (_this$props$onStaticP3 = (_this$props17 = this.props).onStaticPinPositionMove) === null || _this$props$onStaticP3 === void 0 ? void 0 : _this$props$onStaticP3.call(_this$props17, this._staticPinPosition()); this.debouncedOnStaticPinPositionChange(this._staticPinPosition()); return { successful: true @@ -632,7 +634,7 @@ class ReactNativeZoomableView extends _react.Component { * @private */ _handlePinching(e, gestureState) { - var _this$props$onZoomAft, _this$props16; + var _this$props$onZoomAft, _this$props18; if (!this.props.zoomEnabled) return; const { @@ -709,7 +711,7 @@ class ReactNativeZoomableView extends _react.Component { y: this.offsetY }); this.zoomAnim.setValue(this.zoomLevel); - (_this$props$onZoomAft = (_this$props16 = this.props).onZoomAfter) === null || _this$props$onZoomAft === void 0 ? void 0 : _this$props$onZoomAft.call(_this$props16, e, gestureState, this._getZoomableViewEventObject()); + (_this$props$onZoomAft = (_this$props18 = this.props).onZoomAfter) === null || _this$props$onZoomAft === void 0 ? void 0 : _this$props$onZoomAft.call(_this$props18, e, gestureState, this._getZoomableViewEventObject()); } /** * Used to debug pinch events @@ -938,10 +940,10 @@ class ReactNativeZoomableView extends _react.Component { async _zoomToLocation(x, y, newZoomLevel) { - var _this$props$onZoomBef, _this$props17, _this$props$onZoomAft2, _this$props18; + var _this$props$onZoomBef, _this$props19, _this$props$onZoomAft2, _this$props20; if (!this.props.zoomEnabled) return; - (_this$props$onZoomBef = (_this$props17 = this.props).onZoomBefore) === null || _this$props$onZoomBef === void 0 ? void 0 : _this$props$onZoomBef.call(_this$props17, null, null, this._getZoomableViewEventObject()); // == Perform Zoom Animation == + (_this$props$onZoomBef = (_this$props19 = this.props).onZoomBefore) === null || _this$props$onZoomBef === void 0 ? void 0 : _this$props$onZoomBef.call(_this$props19, null, null, this._getZoomableViewEventObject()); // == Perform Zoom Animation == // Calculates panAnim values based on changes in zoomAnim. let prevScale = this.zoomLevel; // Since zoomAnim is calculated in native driver, @@ -962,7 +964,7 @@ class ReactNativeZoomableView extends _react.Component { this.zoomAnim.removeListener(listenerId); }); // == Zoom Animation Ends == - (_this$props$onZoomAft2 = (_this$props18 = this.props).onZoomAfter) === null || _this$props$onZoomAft2 === void 0 ? void 0 : _this$props$onZoomAft2.call(_this$props18, null, null, this._getZoomableViewEventObject()); + (_this$props$onZoomAft2 = (_this$props20 = this.props).onZoomAfter) === null || _this$props$onZoomAft2 === void 0 ? void 0 : _this$props$onZoomAft2.call(_this$props20, null, null, this._getZoomableViewEventObject()); } /** * Zooms to a specificied zoom level. diff --git a/lib/commonjs/ReactNativeZoomableView.js.map b/lib/commonjs/ReactNativeZoomableView.js.map index ac9aa7f..77ca0e8 100644 --- a/lib/commonjs/ReactNativeZoomableView.js.map +++ b/lib/commonjs/ReactNativeZoomableView.js.map @@ -1 +1 @@ -{"version":3,"sources":["ReactNativeZoomableView.tsx"],"names":["initialState","originalWidth","originalHeight","originalPageX","originalPageY","pinSize","width","height","ReactNativeZoomableView","Component","gestureStarted","v","_gestureStarted","constructor","props","Animated","ValueXY","x","y","Value","value","boundaryCrossedAnimInEffect","position","onStaticPinPositionChange","requestAnimationFrame","setTimeout","zoomSubjectWrapperRef","current","measureInWindow","setState","e","gestureState","onStartShouldSetPanResponder","_getZoomableViewEventObject","onLongPress","longPressTimeout","longPressDuration","onPanResponderGrant","panAnim","stopAnimation","zoomAnim","raisePin","gestureType","_resolveAndHandleTap","debugPoints","lastGestureCenterPosition","disableMomentum","panEnabled","disablePanOnInitialZoom","zoomLevel","initialZoom","vx","vy","start","clearTimeout","onPanResponderEnd","onZoomEnd","onShiftingEnd","staticPinPosition","_updateStaticPin","dropPin","onPanResponderMove","numberActiveTouches","_handlePanResponderGrant","_handlePanResponderEnd","lastGestureTouchDistance","_handlePinching","Math","abs","dx","dy","isShiftGesture","_handleShifting","now","Date","doubleTapFirstTapReleaseTimestamp","doubleTapDelay","_addTouch","doubleTapFirstTap","id","toString","isSecondTap","singleTapTimeoutId","_handleDoubleTap","nativeEvent","pageX","state","pageY","persist","tapX","tapY","timing","toValue","offsetX","offsetY","useNativeDriver","duration","onSingleTap","contentWidth","contentHeight","pinX","pinY","setValue","viewportPosition","imageSize","zoomableEvent","_staticPinPosition","gestureHandlers","PanResponder","create","_handleStartShouldSetPanResponder","_handlePanResponderMove","onPanResponderRelease","onPanResponderTerminate","evt","onPanResponderTerminationRequest","onShouldBlockNativeResponder","onStartShouldSetPanResponderCapture","onMoveShouldSetPanResponderCapture","zoomAnimatedValue","panAnimatedValueXY","initialOffsetX","initialOffsetY","addListener","animatePin","pinAnim","easing","Easing","out","ease","__setOffset","__getOffset","axis","offset","offsetState","__offsets","animValue","bindToBorders","containerSize","contentSize","boundOffset","panBoundaryPadding","boundariesApplied","toFixed","componentDidUpdate","prevProps","prevState","zoomEnabled","onTransformInvocationInitialized","_invokeOnTransform","successful","currState","originalMeasurementsChanged","staticPinPositionChanged","componentDidMount","grabZoomSubjectOriginalMeasurements","measureZoomSubjectInterval","setInterval","componentWillUnmount","clearInterval","zoomableViewEvent","onTransform","onStaticPinPositionMove","debouncedOnStaticPinPositionChange","overwriteObj","maxZoom","minZoom","pinchToZoomInSensitivity","pinchToZoomOutSensitivity","distance","onZoomBefore","zoomGrowthFromLastGestureState","pinchToZoomSensitivity","deltaGrowth","deltaGrowthAdjustedBySensitivity","newZoomLevel","gestureCenterPoint","zoomCenter","debug","_setPinchDebugPoints","oldOffsetX","oldOffsetY","oldScale","newScale","offsetShift","_calcOffsetShiftSinceLastGestureState","onZoomAfter","gestureResponderEvent","points","touches","movementSensibility","shift","shiftX","shiftY","moveX","moveY","_setNewOffsetPosition","newOffsetX","newOffsetY","onShiftingBefore","onShiftingAfter","touch","push","_removeTouch","splice","indexOf","onDoubleTapBefore","onDoubleTapAfter","doubleTapZoomToCenter","nextZoomStep","_getNextZoomStep","zoomPositionCoordinates","_zoomToLocation","then","zoomStep","prevScale","listenerId","removeListener","zoomTo","zoomBy","zoomLevelChange","moveTo","moveBy","offsetChangeX","offsetChangeY","render","staticPinIcon","children","visualTouchFeedbackEnabled","onStaticPinLongPress","onStaticPinPress","pinProps","styles","container","panHandlers","zoomSubject","style","transform","scale","getTranslateTransform","map","animationDuration","index","size","undefined","StyleSheet","flex","justifyContent","alignItems","overflow"],"mappings":";;;;;;;AAAA;;AACA;;AAmBA;;AACA;;AACA;;AAKA;;AACA;;AACA;;AACA;;AACA;;;;;;;;;;AAMA,MAAMA,YAAY,GAAG;AACnBC,EAAAA,aAAa,EAAE,IADI;AAEnBC,EAAAA,cAAc,EAAE,IAFG;AAGnBC,EAAAA,aAAa,EAAE,IAHI;AAInBC,EAAAA,aAAa,EAAE,IAJI;AAKnBC,EAAAA,OAAO,EAAE;AAAEC,IAAAA,KAAK,EAAE,CAAT;AAAYC,IAAAA,MAAM,EAAE;AAApB;AALU,CAArB;;AAQA,MAAMC,uBAAN,SAAsCC,gBAAtC,CAGE;AAsD0B,MAAdC,cAAc,CAACC,CAAD,EAAa;AACrC,SAAKC,eAAL,GAAuBD,CAAvB;AACD;;AACwB,MAAdD,cAAc,GAAG;AAC1B,WAAO,KAAKE,eAAZ;AACD;AAED;AACF;AACA;AACA;;;AAQEC,EAAAA,WAAW,CAACC,KAAD,EAAQ;AACjB,UAAMA,KAAN;;AADiB;;AAAA;;AAAA;;AAAA,qCAvCD,IAAIC,sBAASC,OAAb,CAAqB;AAAEC,MAAAA,CAAC,EAAE,CAAL;AAAQC,MAAAA,CAAC,EAAE;AAAX,KAArB,CAuCC;;AAAA,sCAtCA,IAAIH,sBAASI,KAAb,CAAmB,CAAnB,CAsCA;;AAAA,qCArCD,IAAIJ,sBAASC,OAAb,CAAqB;AAAEC,MAAAA,CAAC,EAAE,CAAL;AAAQC,MAAAA,CAAC,EAAE;AAAX,KAArB,CAqCC;;AAAA,uCAnCC;AAClBD,MAAAA,CAAC,EAAE;AACDG,QAAAA,KAAK,EAAE,CADN;AAEDC,QAAAA,2BAA2B,EAAE;AAF5B,OADe;AAKlBH,MAAAA,CAAC,EAAE;AACDE,QAAAA,KAAK,EAAE,CADN;AAEDC,QAAAA,2BAA2B,EAAE;AAF5B;AALe,KAmCD;;AAAA,uCAxBC,CAwBD;;AAAA,uDAvB2C,IAuB3C;;AAAA;;AAAA;;AAAA,6CAnBO,KAmBP;;AAAA,8CAPwB,IAOxB;;AAAA;;AAAA;;AAAA,qCAJa,EAIb;;AAAA;;AAAA;;AAAA,gEA8MkB,sBAClCC,QAAD;AAAA;;AAAA,sCAAqB,oBAAKR,KAAL,EAAWS,yBAAhC,0DAAqB,wCAAuCD,QAAvC,CAArB;AAAA,KADmC,EAEnC,GAFmC,CA9MlB;;AAAA,iEA+P2B,MAAM;AAClD;AACAE,MAAAA,qBAAqB,CAAC,MAAM;AAC1B;AACA;AACA;AACAC,QAAAA,UAAU,CAAC,MAAM;AAAA;;AACf;AACA;AACA;AACA;AACA;AACA,gBAAMC,qBAAqB,GAAG,KAAKA,qBAAnC,CANe,CAOf;;AACA,mCAAAA,qBAAqB,CAACC,OAAtB,gFAA+BC,eAA/B,CACE,CAACX,CAAD,EAAIC,CAAJ,EAAOZ,KAAP,EAAcC,MAAd,KAAyB;AACvB,iBAAKsB,QAAL,CAAc;AACZ5B,cAAAA,aAAa,EAAEK,KADH;AAEZJ,cAAAA,cAAc,EAAEK,MAFJ;AAGZJ,cAAAA,aAAa,EAAEc,CAHH;AAIZb,cAAAA,aAAa,EAAEc;AAJH,aAAd;AAMD,WARH;AAUD,SAlBS,CAAV;AAmBD,OAvBoB,CAArB;AAwBD,KAzRkB;;AAAA,+DAoSiB,CAClCY,CADkC,EAElCC,YAFkC,KAG/B;AACH,UAAI,KAAKjB,KAAL,CAAWkB,4BAAf,EAA6C;AAC3C,aAAKlB,KAAL,CAAWkB,4BAAX,CACEF,CADF,EAEEC,YAFF,EAGE,KAAKE,2BAAL,EAHF,EAIE,KAJF;AAMD,OARE,CAUH;AACA;AACA;AACA;;;AACA,aAAO,IAAP;AACD,KAtTkB;;AAAA,sDA+TQ,CAACH,CAAD,EAAIC,YAAJ,KAAqB;AAAA;;AAC9C,UAAI,KAAKjB,KAAL,CAAWoB,WAAf,EAA4B;AAC1B,aAAKC,gBAAL,GAAwBV,UAAU,CAAC,MAAM;AAAA;;AACvC,wDAAKX,KAAL,EAAWoB,WAAX,mGACEJ,CADF,EAEEC,YAFF,EAGE,KAAKE,2BAAL,EAHF;AAKA,eAAKE,gBAAL,GAAwB,IAAxB;AACD,SAPiC,EAO/B,KAAKrB,KAAL,CAAWsB,iBAPoB,CAAlC;AAQD;;AAED,oDAAKtB,KAAL,EAAWuB,mBAAX,mGACEP,CADF,EAEEC,YAFF,EAGE,KAAKE,2BAAL,EAHF;AAMA,WAAKK,OAAL,CAAaC,aAAb;AACA,WAAKC,QAAL,CAAcD,aAAd;AACA,WAAK7B,cAAL,GAAsB,IAAtB;AAEA,WAAK+B,QAAL;AACD,KAtVkB;;AAAA,oDAgWM,CAACX,CAAD,EAAIC,YAAJ,KAAqB;AAAA;;AAC5C,UAAI,CAAC,KAAKW,WAAV,EAAuB;AACrB,aAAKC,oBAAL,CAA0Bb,CAA1B;AACD;;AAED,WAAKD,QAAL,CAAc;AAAEe,QAAAA,WAAW,EAAE;AAAf,OAAd;AAEA,WAAKC,yBAAL,GAAiC,IAAjC;AAEA,YAAMC,eAAe,GACnB,KAAKhC,KAAL,CAAWgC,eAAX,IACC,KAAKhC,KAAL,CAAWiC,UAAX,IACC,KAAKL,WAAL,KAAqB,OADtB,IAEC,KAAK5B,KAAL,CAAWkC,uBAFZ,IAGC,KAAKC,SAAL,KAAmB,KAAKnC,KAAL,CAAWoC,WALlC,CAT4C,CAgB5C;AACA;;AACA,UAAI,CAACJ,eAAL,EAAsB;AACpB,iDAAwB,KAAKR,OAA7B,EAAsC;AACpCrB,UAAAA,CAAC,EAAEc,YAAY,CAACoB,EAAb,GAAkB,KAAKF,SADU;AAEpC/B,UAAAA,CAAC,EAAEa,YAAY,CAACqB,EAAb,GAAkB,KAAKH;AAFU,SAAtC,EAGGI,KAHH;AAID;;AAED,UAAI,KAAKlB,gBAAT,EAA2B;AACzBmB,QAAAA,YAAY,CAAC,KAAKnB,gBAAN,CAAZ;AACA,aAAKA,gBAAL,GAAwB,IAAxB;AACD;;AAED,qDAAKrB,KAAL,EAAWyC,iBAAX,qGACEzB,CADF,EAEEC,YAFF,EAGE,KAAKE,2BAAL,EAHF;;AAMA,UAAI,KAAKS,WAAL,KAAqB,OAAzB,EAAkC;AAAA;;AAChC,sDAAK5B,KAAL,EAAW0C,SAAX,mGACE1B,CADF,EAEEC,YAFF,EAGE,KAAKE,2BAAL,EAHF;AAKD,OAND,MAMO,IAAI,KAAKS,WAAL,KAAqB,OAAzB,EAAkC;AAAA;;AACvC,sDAAK5B,KAAL,EAAW2C,aAAX,mGACE3B,CADF,EAEEC,YAFF,EAGE,KAAKE,2BAAL,EAHF;AAKD;;AAED,UAAI,KAAKnB,KAAL,CAAW4C,iBAAf,EAAkC;AAChC,aAAKC,gBAAL;AACD;;AAED,WAAKC,OAAL;AAEA,WAAKlB,WAAL,GAAmB,IAAnB;AACA,WAAKhC,cAAL,GAAsB,KAAtB;AACD,KA1ZkB;;AAAA,qDAoaO,CACxBoB,CADwB,EAExBC,YAFwB,KAGrB;AACH,UAAI,KAAKjB,KAAL,CAAW+C,kBAAf,EAAmC;AACjC,YACE,KAAK/C,KAAL,CAAW+C,kBAAX,CACE/B,CADF,EAEEC,YAFF,EAGE,KAAKE,2BAAL,EAHF,CADF,EAME;AACA,iBAAO,KAAP;AACD;AACF,OAXE,CAaH;AACA;;;AACA,UAAIF,YAAY,CAAC+B,mBAAb,IAAoC,CAAxC,EAA2C;AACzC,YAAI,CAAC,KAAKpD,cAAV,EAA0B;AACxB,eAAKqD,wBAAL,CAA8BjC,CAA9B,EAAiCC,YAAjC;AACD;AACF,OAJD,MAIO;AACL,YAAI,KAAKrB,cAAT,EAAyB;AACvB,eAAKsD,sBAAL,CAA4BlC,CAA5B,EAA+BC,YAA/B;AACD;;AACD,eAAO,IAAP;AACD;;AAED,UAAIA,YAAY,CAAC+B,mBAAb,KAAqC,CAAzC,EAA4C;AAC1C,YAAI,KAAK3B,gBAAT,EAA2B;AACzBmB,UAAAA,YAAY,CAAC,KAAKnB,gBAAN,CAAZ;AACA,eAAKA,gBAAL,GAAwB,IAAxB;AACD,SAJyC,CAM1C;;;AACA,YAAI,KAAKO,WAAL,KAAqB,OAAzB,EAAkC;AAChC,eAAKG,yBAAL,GAAiC,oCAC/Bf,CAD+B,EAE/BC,YAF+B,CAAjC;AAIA,eAAKkC,wBAAL,GAAgC,sCAC9BnC,CAD8B,EAE9BC,YAF8B,CAAhC;AAID;;AACD,aAAKW,WAAL,GAAmB,OAAnB;;AACA,aAAKwB,eAAL,CAAqBpC,CAArB,EAAwBC,YAAxB;AACD,OAnBD,MAmBO,IAAIA,YAAY,CAAC+B,mBAAb,KAAqC,CAAzC,EAA4C;AACjD,YACE,KAAK3B,gBAAL,KACCgC,IAAI,CAACC,GAAL,CAASrC,YAAY,CAACsC,EAAtB,IAA4B,CAA5B,IAAiCF,IAAI,CAACC,GAAL,CAASrC,YAAY,CAACuC,EAAtB,IAA4B,CAD9D,CADF,EAGE;AACAhB,UAAAA,YAAY,CAAC,KAAKnB,gBAAN,CAAZ;AACA,eAAKA,gBAAL,GAAwB,IAAxB;AACD,SAPgD,CAQjD;;;AACA,YAAI,KAAKO,WAAL,KAAqB,OAAzB,EAAkC;AAChC,eAAKG,yBAAL,GAAiC,oCAC/Bf,CAD+B,EAE/BC,YAF+B,CAAjC;AAID;;AAED,cAAM;AAAEsC,UAAAA,EAAF;AAAMC,UAAAA;AAAN,YAAavC,YAAnB;AACA,cAAMwC,cAAc,GAAGJ,IAAI,CAACC,GAAL,CAASC,EAAT,IAAe,CAAf,IAAoBF,IAAI,CAACC,GAAL,CAASE,EAAT,IAAe,CAA1D;;AACA,YAAIC,cAAJ,EAAoB;AAClB,eAAK7B,WAAL,GAAmB,OAAnB;;AACA,eAAK8B,eAAL,CAAqBzC,YAArB;AACD;AACF;AACF,KA3ekB;;AAAA,kDAwuBaD,CAAD,IAA8B;AAC3D,YAAM2C,GAAG,GAAGC,IAAI,CAACD,GAAL,EAAZ;;AACA,UACE,KAAKE,iCAAL,IACAF,GAAG,GAAG,KAAKE,iCAAX,GAA+C,KAAK7D,KAAL,CAAW8D,cAF5D,EAGE;AACA,aAAKC,SAAL,CAAe,EACb,GAAG,KAAKC,iBADK;AAEbC,UAAAA,EAAE,EAAEN,GAAG,CAACO,QAAJ,EAFS;AAGbC,UAAAA,WAAW,EAAE;AAHA,SAAf;;AAKA3B,QAAAA,YAAY,CAAC,KAAK4B,kBAAN,CAAZ;AACA,eAAO,KAAKP,iCAAZ;AACA,eAAO,KAAKO,kBAAZ;AACA,eAAO,KAAKJ,iBAAZ;;AACA,aAAKK,gBAAL,CAAsBrD,CAAtB;AACD,OAdD,MAcO;AACL,aAAK6C,iCAAL,GAAyCF,GAAzC;AACA,aAAKK,iBAAL,GAAyB;AACvBC,UAAAA,EAAE,EAAEN,GAAG,CAACO,QAAJ,EADmB;AAEvB/D,UAAAA,CAAC,EAAEa,CAAC,CAACsD,WAAF,CAAcC,KAAd,GAAsB,KAAKC,KAAL,CAAWnF,aAFb;AAGvBe,UAAAA,CAAC,EAAEY,CAAC,CAACsD,WAAF,CAAcG,KAAd,GAAsB,KAAKD,KAAL,CAAWlF;AAHb,SAAzB;;AAKA,aAAKyE,SAAL,CAAe,KAAKC,iBAApB,EAPK,CASL;;;AACAhD,QAAAA,CAAC,CAAC0D,OAAF;AACA,aAAKN,kBAAL,GAA0BzD,UAAU,CAAC,MAAM;AAAA;;AACzC,iBAAO,KAAKkD,iCAAZ;AACA,iBAAO,KAAKO,kBAAZ,CAFyC,CAIzC;;AACA,cAAI,KAAKpE,KAAL,CAAW4C,iBAAX,IAAgC,KAAKoB,iBAAzC,EAA4D;AAC1D,kBAAMW,IAAI,GACR,KAAK3E,KAAL,CAAW4C,iBAAX,CAA6BzC,CAA7B,GAAiC,KAAK6D,iBAAL,CAAuB7D,CAD1D;AAEA,kBAAMyE,IAAI,GACR,KAAK5E,KAAL,CAAW4C,iBAAX,CAA6BxC,CAA7B,GAAiC,KAAK4D,iBAAL,CAAuB5D,CAD1D;;AAGAH,kCAAS4E,MAAT,CAAgB,KAAKrD,OAArB,EAA8B;AAC5BsD,cAAAA,OAAO,EAAE;AACP3E,gBAAAA,CAAC,EAAE,KAAK4E,OAAL,GAAeJ,IAAI,GAAG,KAAKxC,SADvB;AAEP/B,gBAAAA,CAAC,EAAE,KAAK4E,OAAL,GAAeJ,IAAI,GAAG,KAAKzC;AAFvB,eADmB;AAK5B8C,cAAAA,eAAe,EAAE,IALW;AAM5BC,cAAAA,QAAQ,EAAE;AANkB,aAA9B,EAOG3C,KAPH,CAOS,MAAM;AACb,mBAAKM,gBAAL;AACD,aATD;AAUD;;AAED,wDAAK7C,KAAL,EAAWmF,WAAX,mGAAyBnE,CAAzB,EAA4B,KAAKG,2BAAL,EAA5B;AACD,SAxBmC,EAwBjC,KAAKnB,KAAL,CAAW8D,cAxBsB,CAApC;AAyBD;AACF,KA7xBkB;;AAAA;;AAAA,6CAgyBAtD,QAAD,IAAqB;AACrC,YAAM;AAAErB,QAAAA,aAAF;AAAiBC,QAAAA;AAAjB,UAAoC,KAAKoF,KAA/C;AACA,YAAM;AAAE5B,QAAAA,iBAAF;AAAqBwC,QAAAA,YAArB;AAAmCC,QAAAA;AAAnC,UAAqD,KAAKrF,KAAhE,CAFqC,CAIrC;;AACA,YAAMsF,IAAI,GAAG1C,iBAAiB,CAACzC,CAAlB,GAAsBhB,aAAa,GAAG,CAAnD;AACA,YAAMoG,IAAI,GAAG3C,iBAAiB,CAACxC,CAAlB,GAAsBhB,cAAc,GAAG,CAApD;AAEA,WAAK2F,OAAL,GAAeK,YAAY,GAAG,CAAf,GAAmB5E,QAAQ,CAACL,CAA5B,GAAgCmF,IAAI,GAAG,KAAKnD,SAA3D;AACA,WAAK6C,OAAL,GAAeK,aAAa,GAAG,CAAhB,GAAoB7E,QAAQ,CAACJ,CAA7B,GAAiCmF,IAAI,GAAG,KAAKpD,SAA5D;AAEA,WAAKX,OAAL,CAAagE,QAAb,CAAsB;AAAErF,QAAAA,CAAC,EAAE,KAAK4E,OAAV;AAAmB3E,QAAAA,CAAC,EAAE,KAAK4E;AAA3B,OAAtB;AACD,KA5yBkB;;AAAA,gDA8yBU,MAAM;AACjC,aAAO,2DAAgC;AACrCS,QAAAA,gBAAgB,EAAE;AAChBtF,UAAAA,CAAC,EAAE,KAAKH,KAAL,CAAW4C,iBAAX,CAA6BzC,CADhB;AAEhBC,UAAAA,CAAC,EAAE,KAAKJ,KAAL,CAAW4C,iBAAX,CAA6BxC;AAFhB,SADmB;AAKrCsF,QAAAA,SAAS,EAAE;AACTjG,UAAAA,MAAM,EAAE,KAAKO,KAAL,CAAWqF,aADV;AAET7F,UAAAA,KAAK,EAAE,KAAKQ,KAAL,CAAWoF;AAFT,SAL0B;AASrCO,QAAAA,aAAa,EAAE,EACb,GAAG,KAAKxE,2BAAL,EADU;AAEb4D,UAAAA,OAAO,EAAE,KAAKA,OAFD;AAGbC,UAAAA,OAAO,EAAE,KAAKA,OAHD;AAIb7C,UAAAA,SAAS,EAAE,KAAKA;AAJH;AATsB,OAAhC,CAAP;AAgBD,KA/zBkB;;AAAA,8CAi0BQ,MAAM;AAAA;;AAC/B,qDAAKnC,KAAL,EAAWS,yBAAX,qGAAuC,KAAKmF,kBAAL,EAAvC;AACD,KAn0BkB;;AAGjB,SAAKC,eAAL,GAAuBC,0BAAaC,MAAb,CAAoB;AACzC7E,MAAAA,4BAA4B,EAAE,KAAK8E,iCADM;AAEzCzE,MAAAA,mBAAmB,EAAE,KAAK0B,wBAFe;AAGzCF,MAAAA,kBAAkB,EAAE,KAAKkD,uBAHgB;AAIzCC,MAAAA,qBAAqB,EAAE,KAAKhD,sBAJa;AAKzCiD,MAAAA,uBAAuB,EAAE,CAACC,GAAD,EAAMnF,YAAN,KAAuB;AAAA;;AAC9C;AACA;AACA;AACA;AACA;AACA;AACA,aAAKiC,sBAAL,CAA4BkD,GAA5B,EAAiCnF,YAAjC;;AACA,uDAAKjB,KAAL,EAAWmG,uBAAX,qGACEC,GADF,EAEEnF,YAFF,EAGE,KAAKE,2BAAL,EAHF;AAKD,OAlBwC;AAmBzCkF,MAAAA,gCAAgC,EAAE,CAACD,GAAD,EAAMnF,YAAN;AAAA;;AAAA,eAChC,CAAC,4BAAC,sBAAKjB,KAAL,EAAWqG,gCAAZ,mDAAC,2CACAD,GADA,EAEAnF,YAFA,EAGA,KAAKE,2BAAL,EAHA,CAAD,CAD+B;AAAA,OAnBO;AAyBzC;AACAmF,MAAAA,4BAA4B,EAAE,CAACF,GAAD,EAAMnF,YAAN;AAAA;;AAAA,kEAC5B,sBAAKjB,KAAL,EAAWsG,4BADiB,2DAC5B,2CACEF,GADF,EAEEnF,YAFF,EAGE,KAAKE,2BAAL,EAHF,CAD4B,yEAKvB,IALuB;AAAA,OA1BW;AAgCzCoF,MAAAA,mCAAmC,EAAE,CAACH,GAAD,EAAMnF,YAAN;AAAA;;AAAA,wCACnC,sBAAKjB,KAAL,EAAWuG,mCADwB,0DACnC,0CAAiDH,GAAjD,EAAsDnF,YAAtD,CADmC;AAAA,OAhCI;AAkCzCuF,MAAAA,kCAAkC,EAAE,CAACJ,GAAD,EAAMnF,YAAN;AAAA;;AAAA,wCAClC,sBAAKjB,KAAL,EAAWwG,kCADuB,0DAClC,0CAAgDJ,GAAhD,EAAqDnF,YAArD,CADkC;AAAA;AAlCK,KAApB,CAAvB;AAsCA,SAAKL,qBAAL,gBAA6B,uBAA7B;AAEA,QAAI,KAAKZ,KAAL,CAAWyG,iBAAf,EACE,KAAK/E,QAAL,GAAgB,KAAK1B,KAAL,CAAWyG,iBAA3B;AACF,QAAI,KAAKzG,KAAL,CAAW0G,kBAAf,EACE,KAAKlF,OAAL,GAAe,KAAKxB,KAAL,CAAW0G,kBAA1B;AAEF,SAAKvE,SAAL,GAAiBnC,KAAK,CAACoC,WAAvB;AACA,SAAK2C,OAAL,GAAe/E,KAAK,CAAC2G,cAArB;AACA,SAAK3B,OAAL,GAAehF,KAAK,CAAC4G,cAArB;AAEA,SAAKpF,OAAL,CAAagE,QAAb,CAAsB;AAAErF,MAAAA,CAAC,EAAE,KAAK4E,OAAV;AAAmB3E,MAAAA,CAAC,EAAE,KAAK4E;AAA3B,KAAtB;AACA,SAAKtD,QAAL,CAAc8D,QAAd,CAAuB,KAAKrD,SAA5B;AACA,SAAKX,OAAL,CAAaqF,WAAb,CAAyB,CAAC;AAAE1G,MAAAA,CAAF;AAAKC,MAAAA;AAAL,KAAD,KAAc;AACrC,WAAK2E,OAAL,GAAe5E,CAAf;AACA,WAAK6E,OAAL,GAAe5E,CAAf;AACD,KAHD;AAIA,SAAKsB,QAAL,CAAcmF,WAAd,CAA0B,CAAC;AAAEvG,MAAAA;AAAF,KAAD,KAAe;AACvC,WAAK6B,SAAL,GAAiB7B,KAAjB;AACD,KAFD;AAIA,SAAKkE,KAAL,GAAa,EACX,GAAGtF;AADQ,KAAb;AAIA,SAAKiE,wBAAL,GAAgC,GAAhC;AAEA,SAAKvB,WAAL,GAAmB,IAAnB;AACD;;AAEOD,EAAAA,QAAQ,GAAG;AACjB,QAAI,CAAC,KAAK3B,KAAL,CAAW8G,UAAhB,EAA4B;;AAC5B7G,0BAAS4E,MAAT,CAAgB,KAAKkC,OAArB,EAA8B;AAC5BjC,MAAAA,OAAO,EAAE;AAAE3E,QAAAA,CAAC,EAAE,CAAL;AAAQC,QAAAA,CAAC,EAAE,CAAC;AAAZ,OADmB;AAE5B6E,MAAAA,eAAe,EAAE,IAFW;AAG5B+B,MAAAA,MAAM,EAAEC,oBAAOC,GAAP,CAAWD,oBAAOE,IAAlB,CAHoB;AAI5BjC,MAAAA,QAAQ,EAAE;AAJkB,KAA9B,EAKG3C,KALH;AAMD;;AAEOO,EAAAA,OAAO,GAAG;AAChB,QAAI,CAAC,KAAK9C,KAAL,CAAW8G,UAAhB,EAA4B;;AAC5B7G,0BAAS4E,MAAT,CAAgB,KAAKkC,OAArB,EAA8B;AAC5BjC,MAAAA,OAAO,EAAE;AAAE3E,QAAAA,CAAC,EAAE,CAAL;AAAQC,QAAAA,CAAC,EAAE;AAAX,OADmB;AAE5B6E,MAAAA,eAAe,EAAE,IAFW;AAG5B+B,MAAAA,MAAM,EAAEC,oBAAOC,GAAP,CAAWD,oBAAOE,IAAlB,CAHoB;AAI5BjC,MAAAA,QAAQ,EAAE;AAJkB,KAA9B,EAKG3C,KALH;AAMD;;AAEkB,MAAPwC,OAAO,CAAC5E,CAAD,EAAY;AAC7B,SAAKiH,WAAL,CAAiB,GAAjB,EAAsBjH,CAAtB;AACD;;AACkB,MAAP6E,OAAO,CAAC5E,CAAD,EAAY;AAC7B,SAAKgH,WAAL,CAAiB,GAAjB,EAAsBhH,CAAtB;AACD;;AACkB,MAAP2E,OAAO,GAAG;AACpB,WAAO,KAAKsC,WAAL,CAAiB,GAAjB,CAAP;AACD;;AACkB,MAAPrC,OAAO,GAAG;AACpB,WAAO,KAAKqC,WAAL,CAAiB,GAAjB,CAAP;AACD;;AACOD,EAAAA,WAAW,CAACE,IAAD,EAAkBC,MAAlB,EAA0B;AAAA;;AAC3C,UAAMC,WAAW,GAAG,KAAKC,SAAL,CAAeH,IAAf,CAApB;AACA,UAAMI,SAAS,oBAAG,KAAKlG,OAAR,kDAAG,cAAe8F,IAAf,CAAlB;;AAEA,QAAI,KAAKtH,KAAL,CAAW2H,aAAf,EAA8B;AAAA;;AAC5B,YAAMC,aAAa,GACjBN,IAAI,KAAK,GAAT,kBAAe,KAAK9C,KAApB,gDAAe,YAAYrF,aAA3B,mBAA2C,KAAKqF,KAAhD,iDAA2C,aAAYpF,cADzD;AAEA,YAAMyI,WAAW,GACfP,IAAI,KAAK,GAAT,GACI,KAAKtH,KAAL,CAAWoF,YAAX,qBAA2B,KAAKZ,KAAhC,iDAA2B,aAAYrF,aAAvC,CADJ,GAEI,KAAKa,KAAL,CAAWqF,aAAX,qBAA4B,KAAKb,KAAjC,iDAA4B,aAAYpF,cAAxC,CAHN;AAKA,YAAM0I,WAAW,GACfD,WAAW,IAAID,aAAf,GACI,4DACEL,MADF,EAEEK,aAFF,EAGEC,WAHF,EAIE,KAAK1F,SAJP,EAKE,KAAKnC,KAAL,CAAW+H,kBALb,CADJ,GAQIR,MATN;;AAWA,UACEG,SAAS,IACT,CAAC,KAAK9F,WADN,IAEA,CAAC4F,WAAW,CAACjH,2BAHf,EAIE;AACA,cAAMyH,iBAAiB,GACrBF,WAAW,KAAKP,MAAhB,IACAO,WAAW,CAACG,OAAZ,CAAoB,CAApB,MAA2BV,MAAM,CAACU,OAAP,CAAe,CAAf,CAF7B;;AAGA,YAAID,iBAAJ,EAAuB;AACrBR,UAAAA,WAAW,CAACjH,2BAAZ,GAA0C,IAA1C;AACA,kDAAuB,KAAKiB,OAAL,CAAa8F,IAAb,CAAvB,EAA2CQ,WAA3C,EAAwDvF,KAAxD,CAA8D,MAAM;AAClEiF,YAAAA,WAAW,CAACjH,2BAAZ,GAA0C,KAA1C;AACD,WAFD;AAGA;AACD;AACF;AACF;;AAEDiH,IAAAA,WAAW,CAAClH,KAAZ,GAAoBiH,MAApB;AACD;;AACOF,EAAAA,WAAW,CAACC,IAAD,EAAkB;AACnC,WAAO,KAAKG,SAAL,CAAeH,IAAf,EAAqBhH,KAA5B;AACD;;AAED4H,EAAAA,kBAAkB,CAChBC,SADgB,EAEhBC,SAFgB,EAGhB;AAAA;;AACA,UAAM;AAAEC,MAAAA,WAAF;AAAejG,MAAAA;AAAf,QAA+B,KAAKpC,KAA1C;;AACA,QAAImI,SAAS,CAACE,WAAV,IAAyB,CAACA,WAA9B,EAA2C;AACzC,WAAKlG,SAAL,GAAiBC,WAAjB;AACA,WAAKV,QAAL,CAAc8D,QAAd,CAAuB,KAAKrD,SAA5B;AACD;;AACD,QACE,CAAC,KAAKmG,gCAAN,IACA,KAAKC,kBAAL,GAA0BC,UAF5B,EAGE;AACA,WAAKhH,OAAL,CAAaqF,WAAb,CAAyB,MAAM,KAAK0B,kBAAL,EAA/B;AACA,WAAK7G,QAAL,CAAcmF,WAAd,CAA0B,MAAM,KAAK0B,kBAAL,EAAhC;AACA,WAAKD,gCAAL,GAAwC,IAAxC;AACD;;AAED,UAAMG,SAAS,GAAG,KAAKjE,KAAvB;AACA,UAAMkE,2BAA2B,GAC/BD,SAAS,CAACrJ,cAAV,KAA6BgJ,SAAS,CAAChJ,cAAvC,IACAqJ,SAAS,CAACtJ,aAAV,KAA4BiJ,SAAS,CAACjJ,aADtC,IAEAsJ,SAAS,CAACpJ,aAAV,KAA4B+I,SAAS,CAAC/I,aAFtC,IAGAoJ,SAAS,CAACnJ,aAAV,KAA4B8I,SAAS,CAAC9I,aAJxC;AAMA,UAAMqJ,wBAAwB,GAC5B,0BAAAR,SAAS,CAACvF,iBAAV,gFAA6BzC,CAA7B,gCAAmC,KAAKH,KAAL,CAAW4C,iBAA9C,0DAAmC,sBAA8BzC,CAAjE,KACA,2BAAAgI,SAAS,CAACvF,iBAAV,kFAA6BxC,CAA7B,iCAAmC,KAAKJ,KAAL,CAAW4C,iBAA9C,2DAAmC,uBAA8BxC,CAAjE,CAFF;;AAIA,QACE,KAAKkI,gCAAL,KACCI,2BAA2B,IAAIC,wBADhC,CADF,EAGE;AACA,WAAKJ,kBAAL;AACD;AACF;;AAEDK,EAAAA,iBAAiB,GAAG;AAClB,SAAKC,mCAAL,GADkB,CAElB;AACA;AACA;AACA;AACA;AACA;AACA;;AACA,SAAKC,0BAAL,GAAkCC,WAAW,CAC3C,KAAKF,mCADsC,EAE3C,GAF2C,CAA7C;AAID;;AAEDG,EAAAA,oBAAoB,GAAG;AACrBC,IAAAA,aAAa,CAAC,KAAKH,0BAAN,CAAb;AACD;;AAOD;AACF;AACA;AACA;AACEP,EAAAA,kBAAkB,GAAG;AAAA;;AACnB,UAAMW,iBAAiB,GAAG,KAAK/H,2BAAL,EAA1B;;AAEA,QAAI,CAAC+H,iBAAiB,CAAC/J,aAAnB,IAAoC,CAAC+J,iBAAiB,CAAC9J,cAA3D,EACE,OAAO;AAAEoJ,MAAAA,UAAU,EAAE;AAAd,KAAP;AAEF,mDAAKxI,KAAL,EAAWmJ,WAAX,oGAAyBD,iBAAzB;AAEA,oDAAKlJ,KAAL,EAAWoJ,uBAAX,sGAAqC,KAAKxD,kBAAL,EAArC;AAEA,SAAKyD,kCAAL,CAAwC,KAAKzD,kBAAL,EAAxC;AAEA,WAAO;AAAE4C,MAAAA,UAAU,EAAE;AAAd,KAAP;AACD;AAED;AACF;AACA;AACA;AACA;AACA;;;AACErH,EAAAA,2BAA2B,CAACmI,YAAY,GAAG,EAAhB,EAAuC;AAChE,WAAO;AACLnH,MAAAA,SAAS,EAAE,KAAKA,SADX;AAEL4C,MAAAA,OAAO,EAAE,KAAKA,OAFT;AAGLC,MAAAA,OAAO,EAAE,KAAKA,OAHT;AAIL5F,MAAAA,cAAc,EAAE,KAAKoF,KAAL,CAAWpF,cAJtB;AAKLD,MAAAA,aAAa,EAAE,KAAKqF,KAAL,CAAWrF,aALrB;AAMLE,MAAAA,aAAa,EAAE,KAAKmF,KAAL,CAAWnF,aANrB;AAOLC,MAAAA,aAAa,EAAE,KAAKkF,KAAL,CAAWlF,aAPrB;AAQL,SAAGgK;AARE,KAAP;AAUD;AAED;AACF;AACA;AACA;AACA;AACA;;;AA+OE;AACF;AACA;AACA;AACA;AACA;AACA;AACA;AACElG,EAAAA,eAAe,CACbpC,CADa,EAEbC,YAFa,EAGb;AAAA;;AACA,QAAI,CAAC,KAAKjB,KAAL,CAAWqI,WAAhB,EAA6B;AAE7B,UAAM;AACJkB,MAAAA,OADI;AAEJC,MAAAA,OAFI;AAGJC,MAAAA,wBAHI;AAIJC,MAAAA;AAJI,QAKF,KAAK1J,KALT;AAOA,UAAM2J,QAAQ,GAAG,sCAAyB3I,CAAzB,EAA4BC,YAA5B,CAAjB;;AAEA,QACE,KAAKjB,KAAL,CAAW4J,YAAX,IACA,KAAK5J,KAAL,CAAW4J,YAAX,CACE5I,CADF,EAEEC,YAFF,EAGE,KAAKE,2BAAL,EAHF,CAFF,EAOE;AACA;AACD,KArBD,CAuBA;;;AACA,UAAM0I,8BAA8B,GAClCF,QAAQ,GAAG,KAAKxG,wBADlB;AAEA,SAAKA,wBAAL,GAAgCwG,QAAhC;AAEA,UAAMG,sBAAsB,GAC1BD,8BAA8B,GAAG,CAAjC,GACIH,yBADJ,GAEID,wBAHN;AAKA,UAAMM,WAAW,GAAGF,8BAA8B,GAAG,CAArD,CAjCA,CAkCA;AACA;;AACA,UAAMG,gCAAgC,GACpCD,WAAW,IAAI,IAAKD,sBAAsB,GAAG,CAA1B,GAA+B,GAAvC,CADb;AAGA,QAAIG,YAAY,GAAG,KAAK9H,SAAL,IAAkB,IAAI6H,gCAAtB,CAAnB,CAvCA,CAyCA;;AACA,QAAIT,OAAO,KAAK,IAAZ,IAAoBU,YAAY,GAAGV,OAAvC,EAAgD;AAC9CU,MAAAA,YAAY,GAAGV,OAAf;AACD;;AAED,QAAIU,YAAY,GAAGT,OAAnB,EAA4B;AAC1BS,MAAAA,YAAY,GAAGT,OAAf;AACD;;AAED,UAAMU,kBAAkB,GAAG,oCAAuBlJ,CAAvB,EAA0BC,YAA1B,CAA3B;AAEA,QAAI,CAACiJ,kBAAL,EAAyB;AAEzB,QAAIC,UAAU,GAAG;AACfhK,MAAAA,CAAC,EAAE+J,kBAAkB,CAAC/J,CAAnB,GAAuB,KAAKqE,KAAL,CAAWnF,aADtB;AAEfe,MAAAA,CAAC,EAAE8J,kBAAkB,CAAC9J,CAAnB,GAAuB,KAAKoE,KAAL,CAAWlF;AAFtB,KAAjB;;AAKA,QAAI,KAAKU,KAAL,CAAW4C,iBAAf,EAAkC;AAChC;AACA;AACAuH,MAAAA,UAAU,GAAG;AACXhK,QAAAA,CAAC,EAAE,KAAKH,KAAL,CAAW4C,iBAAX,CAA6BzC,CADrB;AAEXC,QAAAA,CAAC,EAAE,KAAKJ,KAAL,CAAW4C,iBAAX,CAA6BxC;AAFrB,OAAb;AAID,KAlED,CAoEA;;;AACA,SAAKJ,KAAL,CAAWoK,KAAX,IAAoB,KAAKC,oBAAL,CAA0BrJ,CAA1B,EAA6BmJ,UAA7B,CAApB;AAEA,UAAM;AAAE/K,MAAAA,cAAF;AAAkBD,MAAAA;AAAlB,QAAoC,KAAKqF,KAA/C;AAEA,UAAM8F,UAAU,GAAG,KAAKvF,OAAxB;AACA,UAAMwF,UAAU,GAAG,KAAKvF,OAAxB;AACA,UAAMwF,QAAQ,GAAG,KAAKrI,SAAtB;AACA,UAAMsI,QAAQ,GAAGR,YAAjB;AAEA,QAAIjF,OAAO,GAAG,iDACZuF,UADY,EAEZnL,cAFY,EAGZoL,QAHY,EAIZC,QAJY,EAKZN,UAAU,CAAC/J,CALC,CAAd;AAOA,QAAI2E,OAAO,GAAG,iDACZuF,UADY,EAEZnL,aAFY,EAGZqL,QAHY,EAIZC,QAJY,EAKZN,UAAU,CAAChK,CALC,CAAd;;AAQA,UAAMuK,WAAW,GACf,KAAKC,qCAAL,CAA2CT,kBAA3C,CADF;;AAEA,QAAIQ,WAAJ,EAAiB;AACf3F,MAAAA,OAAO,IAAI2F,WAAW,CAACvK,CAAvB;AACA6E,MAAAA,OAAO,IAAI0F,WAAW,CAACtK,CAAvB;AACD;;AAED,SAAK2E,OAAL,GAAeA,OAAf;AACA,SAAKC,OAAL,GAAeA,OAAf;AACA,SAAK7C,SAAL,GAAiBsI,QAAjB;AAEA,SAAKjJ,OAAL,CAAagE,QAAb,CAAsB;AAAErF,MAAAA,CAAC,EAAE,KAAK4E,OAAV;AAAmB3E,MAAAA,CAAC,EAAE,KAAK4E;AAA3B,KAAtB;AACA,SAAKtD,QAAL,CAAc8D,QAAd,CAAuB,KAAKrD,SAA5B;AAEA,mDAAKnC,KAAL,EAAW4K,WAAX,oGACE5J,CADF,EAEEC,YAFF,EAGE,KAAKE,2BAAL,EAHF;AAKD;AAED;AACF;AACA;AACA;AACA;AACA;;;AACEkJ,EAAAA,oBAAoB,CAClBQ,qBADkB,EAElBV,UAFkB,EAGlB,GAAGW,MAHe,EAIlB;AACA,UAAM;AAAEC,MAAAA;AAAF,QAAcF,qBAAqB,CAACvG,WAA1C;AACA,UAAM;AAAEhF,MAAAA,aAAF;AAAiBD,MAAAA;AAAjB,QAAmC,KAAKmF,KAA9C;AACA,SAAKzD,QAAL,CAAc;AACZe,MAAAA,WAAW,EAAE,CACX;AACE3B,QAAAA,CAAC,EAAE4K,OAAO,CAAC,CAAD,CAAP,CAAWxG,KAAX,GAAmBlF,aADxB;AAEEe,QAAAA,CAAC,EAAE2K,OAAO,CAAC,CAAD,CAAP,CAAWtG,KAAX,GAAmBnF;AAFxB,OADW,EAKX;AACEa,QAAAA,CAAC,EAAE4K,OAAO,CAAC,CAAD,CAAP,CAAWxG,KAAX,GAAmBlF,aADxB;AAEEe,QAAAA,CAAC,EAAE2K,OAAO,CAAC,CAAD,CAAP,CAAWtG,KAAX,GAAmBnF;AAFxB,OALW,EASX6K,UATW,EAUX,GAAGW,MAVQ;AADD,KAAd;AAcD;AAED;AACF;AACA;AACA;AACA;AACA;AACA;;;AACEH,EAAAA,qCAAqC,CAACT,kBAAD,EAA4B;AAC/D,UAAM;AAAEc,MAAAA;AAAF,QAA0B,KAAKhL,KAArC;AAEA,QAAIiL,KAAK,GAAG,IAAZ;;AAEA,QAAI,KAAKlJ,yBAAT,EAAoC;AAClC,YAAMwB,EAAE,GAAG2G,kBAAkB,CAAC/J,CAAnB,GAAuB,KAAK4B,yBAAL,CAA+B5B,CAAjE;AACA,YAAMqD,EAAE,GAAG0G,kBAAkB,CAAC9J,CAAnB,GAAuB,KAAK2B,yBAAL,CAA+B3B,CAAjE;AAEA,YAAM8K,MAAM,GAAG3H,EAAE,GAAG,KAAKpB,SAAV,GAAsB6I,mBAArC;AACA,YAAMG,MAAM,GAAG3H,EAAE,GAAG,KAAKrB,SAAV,GAAsB6I,mBAArC;AAEAC,MAAAA,KAAK,GAAG;AACN9K,QAAAA,CAAC,EAAE+K,MADG;AAEN9K,QAAAA,CAAC,EAAE+K;AAFG,OAAR;AAID;;AAED,SAAKpJ,yBAAL,GAAiCmI,kBAAjC;AAEA,WAAOe,KAAP;AACD;AAED;AACF;AACA;AACA;AACA;AACA;AACA;;;AACEvH,EAAAA,eAAe,CAACzC,YAAD,EAAyC;AACtD;AACA,QACE,CAAC,KAAKjB,KAAL,CAAWiC,UAAZ,IACC,KAAKjC,KAAL,CAAWkC,uBAAX,IACC,KAAKC,SAAL,KAAmB,KAAKnC,KAAL,CAAWoC,WAHlC,EAIE;AACA;AACD;;AACD,UAAM6I,KAAK,GAAG,KAAKN,qCAAL,CAA2C;AACvDxK,MAAAA,CAAC,EAAEc,YAAY,CAACmK,KADuC;AAEvDhL,MAAAA,CAAC,EAAEa,YAAY,CAACoK;AAFuC,KAA3C,CAAd;;AAIA,QAAI,CAACJ,KAAL,EAAY;AAEZ,UAAMlG,OAAO,GAAG,KAAKA,OAAL,GAAekG,KAAK,CAAC9K,CAArC;AACA,UAAM6E,OAAO,GAAG,KAAKA,OAAL,GAAeiG,KAAK,CAAC7K,CAArC;;AAEA,QAAI,KAAKJ,KAAL,CAAWoK,KAAf,EAAsB;AACpB,YAAMjK,CAAC,GAAGc,YAAY,CAACmK,KAAb,GAAqB,KAAK5G,KAAL,CAAWnF,aAA1C;AACA,YAAMe,CAAC,GAAGa,YAAY,CAACoK,KAAb,GAAqB,KAAK7G,KAAL,CAAWlF,aAA1C;AACA,WAAKyB,QAAL,CAAc;AAAEe,QAAAA,WAAW,EAAE,CAAC;AAAE3B,UAAAA,CAAF;AAAKC,UAAAA;AAAL,SAAD;AAAf,OAAd;AACD;;AAED,SAAKkL,qBAAL,CAA2BvG,OAA3B,EAAoCC,OAApC;;AAEA,SAAKrD,QAAL;AACD;AAED;AACF;AACA;AACA;AACA;AACA;AACA;;;AAC6B,QAArB2J,qBAAqB,CAACC,UAAD,EAAqBC,UAArB,EAAyC;AAClE,UAAM;AAAEC,MAAAA,gBAAF;AAAoBC,MAAAA;AAApB,QAAwC,KAAK1L,KAAnD;;AAEA,QAAIyL,gBAAJ,aAAIA,gBAAJ,eAAIA,gBAAgB,CAAG,IAAH,EAAS,IAAT,EAAe,KAAKtK,2BAAL,EAAf,CAApB,EAAwE;AACtE;AACD;;AAED,SAAK4D,OAAL,GAAewG,UAAf;AACA,SAAKvG,OAAL,GAAewG,UAAf;AAEA,SAAKhK,OAAL,CAAagE,QAAb,CAAsB;AAAErF,MAAAA,CAAC,EAAE,KAAK4E,OAAV;AAAmB3E,MAAAA,CAAC,EAAE,KAAK4E;AAA3B,KAAtB;AACA,SAAKtD,QAAL,CAAc8D,QAAd,CAAuB,KAAKrD,SAA5B;AAEAuJ,IAAAA,eAAe,SAAf,IAAAA,eAAe,WAAf,YAAAA,eAAe,CAAG,IAAH,EAAS,IAAT,EAAe,KAAKvK,2BAAL,EAAf,CAAf;AACD;AAED;AACF;AACA;AACA;AACA;AACA;AACA;AACA;;;AA8FU4C,EAAAA,SAAS,CAAC4H,KAAD,EAAoB;AACnC,SAAKZ,OAAL,CAAaa,IAAb,CAAkBD,KAAlB;AACA,SAAK5K,QAAL,CAAc;AAAEgK,MAAAA,OAAO,EAAE,CAAC,GAAG,KAAKA,OAAT;AAAX,KAAd;AACD;;AAEOc,EAAAA,YAAY,CAACF,KAAD,EAAoB;AACtC,SAAKZ,OAAL,CAAae,MAAb,CAAoB,KAAKf,OAAL,CAAagB,OAAb,CAAqBJ,KAArB,CAApB,EAAiD,CAAjD;AACA,SAAK5K,QAAL,CAAc;AAAEgK,MAAAA,OAAO,EAAE,CAAC,GAAG,KAAKA,OAAT;AAAX,KAAd;AACD;AAED;AACF;AACA;AACA;AACA;AACA;AACA;;;AACE1G,EAAAA,gBAAgB,CAACrD,CAAD,EAA2B;AACzC,UAAM;AAAEgL,MAAAA,iBAAF;AAAqBC,MAAAA,gBAArB;AAAuCC,MAAAA;AAAvC,QACJ,KAAKlM,KADP;AAGAgM,IAAAA,iBAAiB,SAAjB,IAAAA,iBAAiB,WAAjB,YAAAA,iBAAiB,CAAGhL,CAAH,EAAM,KAAKG,2BAAL,EAAN,CAAjB;;AAEA,UAAMgL,YAAY,GAAG,KAAKC,gBAAL,EAArB;;AACA,UAAM;AAAE/M,MAAAA,aAAF;AAAiBC,MAAAA;AAAjB,QAAmC,KAAKkF,KAA9C,CAPyC,CASzC;;AACA,UAAM6H,uBAAuB,GAAG;AAC9BlM,MAAAA,CAAC,EAAEa,CAAC,CAACsD,WAAF,CAAcC,KAAd,GAAsBlF,aADK;AAE9Be,MAAAA,CAAC,EAAEY,CAAC,CAACsD,WAAF,CAAcG,KAAd,GAAsBnF;AAFK,KAAhC,CAVyC,CAezC;;AACA,QAAI4M,qBAAJ,EAA2B;AACzBG,MAAAA,uBAAuB,CAAClM,CAAxB,GAA4B,CAA5B;AACAkM,MAAAA,uBAAuB,CAACjM,CAAxB,GAA4B,CAA5B;AACD;;AAED,SAAKkM,eAAL,CACED,uBAAuB,CAAClM,CAD1B,EAEEkM,uBAAuB,CAACjM,CAF1B,EAGE+L,YAHF,EAIEI,IAJF,CAIO,MAAM;AACXN,MAAAA,gBAAgB,SAAhB,IAAAA,gBAAgB,WAAhB,YAAAA,gBAAgB,CACdjL,CADc,EAEd,KAAKG,2BAAL,CAAiC;AAAEgB,QAAAA,SAAS,EAAEgK;AAAb,OAAjC,CAFc,CAAhB;AAID,KATD;AAUD;AAED;AACF;AACA;AACA;AACA;AACA;;;AACEC,EAAAA,gBAAgB,GAAG;AACjB,UAAM;AAAEI,MAAAA,QAAF;AAAYjD,MAAAA,OAAZ;AAAqBnH,MAAAA;AAArB,QAAqC,KAAKpC,KAAhD;AACA,UAAM;AAAEmC,MAAAA;AAAF,QAAgB,IAAtB;;AAEA,QAAIA,SAAS,CAAC8F,OAAV,CAAkB,CAAlB,MAAyBsB,OAAO,CAACtB,OAAR,CAAgB,CAAhB,CAA7B,EAAiD;AAC/C,aAAO7F,WAAP;AACD;;AAED,UAAM+J,YAAY,GAAGhK,SAAS,IAAI,IAAIqK,QAAR,CAA9B;;AACA,QAAIL,YAAY,GAAG5C,OAAnB,EAA4B;AAC1B,aAAOA,OAAP;AACD;;AAED,WAAO4C,YAAP;AACD;AAED;AACF;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;;AACuB,QAAfG,eAAe,CAACnM,CAAD,EAAYC,CAAZ,EAAuB6J,YAAvB,EAA6C;AAAA;;AAChE,QAAI,CAAC,KAAKjK,KAAL,CAAWqI,WAAhB,EAA6B;AAE7B,mDAAKrI,KAAL,EAAW4J,YAAX,oGAA0B,IAA1B,EAAgC,IAAhC,EAAsC,KAAKzI,2BAAL,EAAtC,EAHgE,CAKhE;AACA;;AACA,QAAIsL,SAAS,GAAG,KAAKtK,SAArB,CAPgE,CAQhE;AACA;AACA;AACA;;AACA,UAAMuK,UAAU,GAAG,KAAKhL,QAAL,CAAcmF,WAAd,CAA0B,CAAC;AAAEvG,MAAAA,KAAK,EAAEmK;AAAT,KAAD,KAAyB;AACpE,WAAKjJ,OAAL,CAAagE,QAAb,CAAsB;AACpBrF,QAAAA,CAAC,EAAE,iDACD,KAAK4E,OADJ,EAED,KAAKP,KAAL,CAAWrF,aAFV,EAGDsN,SAHC,EAIDhC,QAJC,EAKDtK,CALC,CADiB;AAQpBC,QAAAA,CAAC,EAAE,iDACD,KAAK4E,OADJ,EAED,KAAKR,KAAL,CAAWpF,cAFV,EAGDqN,SAHC,EAIDhC,QAJC,EAKDrK,CALC;AARiB,OAAtB;AAgBAqM,MAAAA,SAAS,GAAGhC,QAAZ;AACD,KAlBkB,CAAnB;AAmBA,wCAAmB,KAAK/I,QAAxB,EAAkCuI,YAAlC,EAAgD1H,KAAhD,CAAsD,MAAM;AAC1D,WAAKb,QAAL,CAAciL,cAAd,CAA6BD,UAA7B;AACD,KAFD,EA/BgE,CAkChE;;AAEA,oDAAK1M,KAAL,EAAW4K,WAAX,sGAAyB,IAAzB,EAA+B,IAA/B,EAAqC,KAAKzJ,2BAAL,EAArC;AACD;AAED;AACF;AACA;AACA;AACA;AACA;AACA;AACA;;;AACc,QAANyL,MAAM,CAAC3C,YAAD,EAAyC;AACnD,SACE;AACAA,IAAAA,YAAY,GAAG,KAAKjK,KAAL,CAAWuJ,OAA1B,IACAU,YAAY,GAAG,KAAKjK,KAAL,CAAWwJ,OAH5B,EAKE,OAAO,KAAP;AAEF,UAAM,KAAK8C,eAAL,CAAqB,CAArB,EAAwB,CAAxB,EAA2BrC,YAA3B,CAAN;AACA,WAAO,IAAP;AACD;AAED;AACF;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;;AACE4C,EAAAA,MAAM,CAACC,eAAuB,GAAG,IAA3B,EAAmD;AACvD;AACA,QAAI,CAACA,eAAL,EAAsB;AACpBA,MAAAA,eAAe,GAAG,KAAK9M,KAAL,CAAWwM,QAA7B;AACD;;AAED,WAAO,KAAKI,MAAL,CAAY,KAAKzK,SAAL,GAAiB2K,eAA7B,CAAP;AACD;AAED;AACF;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;;AACEC,EAAAA,MAAM,CAACxB,UAAD,EAAqBC,UAArB,EAAwD;AAC5D,UAAM;AAAErM,MAAAA,aAAF;AAAiBC,MAAAA;AAAjB,QAAoC,KAAKoF,KAA/C;AAEA,UAAMO,OAAO,GAAG,CAACwG,UAAU,GAAGpM,aAAa,GAAG,CAA9B,IAAmC,KAAKgD,SAAxD;AACA,UAAM6C,OAAO,GAAG,CAACwG,UAAU,GAAGpM,cAAc,GAAG,CAA/B,IAAoC,KAAK+C,SAAzD;AAEA,WAAO,KAAKmJ,qBAAL,CAA2B,CAACvG,OAA5B,EAAqC,CAACC,OAAtC,CAAP;AACD;AAED;AACF;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;;AACEgI,EAAAA,MAAM,CAACC,aAAD,EAAwBC,aAAxB,EAA8D;AAClE,UAAMnI,OAAO,GACX,CAAC,KAAKA,OAAL,GAAe,KAAK5C,SAApB,GAAgC8K,aAAjC,IAAkD,KAAK9K,SADzD;AAEA,UAAM6C,OAAO,GACX,CAAC,KAAKA,OAAL,GAAe,KAAK7C,SAApB,GAAgC+K,aAAjC,IAAkD,KAAK/K,SADzD;AAGA,WAAO,KAAKmJ,qBAAL,CAA2BvG,OAA3B,EAAoCC,OAApC,CAAP;AACD;;AAEDmI,EAAAA,MAAM,GAAG;AACP,UAAM;AACJC,MAAAA,aADI;AAEJC,MAAAA,QAFI;AAGJC,MAAAA,0BAHI;AAIJxJ,MAAAA,cAJI;AAKJlB,MAAAA,iBALI;AAMJ2K,MAAAA,oBANI;AAOJC,MAAAA,gBAPI;AAQJC,MAAAA;AARI,QASF,KAAKzN,KATT;AAUA,UAAM;AAAET,MAAAA,OAAF;AAAWwL,MAAAA,OAAX;AAAoBjJ,MAAAA,WAAW,GAAG;AAAlC,QAAyC,KAAK0C,KAApD;AAEA,wBACE,6BAAC,iBAAD;AACE,MAAA,KAAK,EAAEkJ,MAAM,CAACC;AADhB,OAEM,KAAK9H,eAAL,CAAqB+H,WAF3B;AAGE,MAAA,GAAG,EAAE,KAAKhN,qBAHZ;AAIE,MAAA,QAAQ,EAAE,KAAKiI;AAJjB,qBAME,6BAAC,qBAAD,CAAU,IAAV;AACE,MAAA,KAAK,EAAE,CACL6E,MAAM,CAACG,WADF,EAEL,KAAK7N,KAAL,CAAW8N,KAFN,EAGL;AACEC,QAAAA,SAAS,EAAE,CACT;AAAEC,UAAAA,KAAK,EAAE,KAAKtM;AAAd,SADS,EAET,GAAG,KAAKF,OAAL,CAAayM,qBAAb,EAFM;AADb,OAHK;AADT,OAYGZ,QAZH,CANF,EAqBGC,0BAA0B,KACzBvC,OADyB,aACzBA,OADyB,uBACzBA,OAAO,CAAEmD,GAAT,CAAcvC,KAAD,IAAW;AACtB,YAAMwC,iBAAiB,GAAGrK,cAA1B;AACA,0BACE,6BAAC,iCAAD;AACE,QAAA,CAAC,EAAE6H,KAAK,CAACxL,CADX;AAEE,QAAA,CAAC,EAAEwL,KAAK,CAACvL,CAFX;AAGE,QAAA,GAAG,EAAEuL,KAAK,CAAC1H,EAHb;AAIE,QAAA,iBAAiB,EAAEkK,iBAJrB;AAKE,QAAA,eAAe,EAAE,MAAM,KAAKtC,YAAL,CAAkBF,KAAlB;AALzB,QADF;AASD,KAXD,CADyB,CArB7B,EAoCG7J,WAAW,CAACoM,GAAZ,CAAgB,CAAC;AAAE/N,MAAAA,CAAF;AAAKC,MAAAA;AAAL,KAAD,EAAWgO,KAAX,KAAqB;AACpC,0BAAO,6BAAC,4BAAD;AAAiB,QAAA,GAAG,EAAEA,KAAtB;AAA6B,QAAA,CAAC,EAAEjO,CAAhC;AAAmC,QAAA,CAAC,EAAEC;AAAtC,QAAP;AACD,KAFA,CApCH,EAwCGwC,iBAAiB,iBAChB,6BAAC,oBAAD;AACE,MAAA,aAAa,EAAEwK,aADjB;AAEE,MAAA,iBAAiB,EAAExK,iBAFrB;AAGE,MAAA,OAAO,EAAErD,OAHX;AAIE,MAAA,OAAO,EAAEiO,gBAJX;AAKE,MAAA,WAAW,EAAED,oBALf;AAME,MAAA,YAAY,EAAE,KAAKtH,uBANrB;AAOE,MAAA,OAAO,EAAE,KAAKc,OAPhB;AAQE,MAAA,UAAU,EAAGsH,IAAD,IAAkB,KAAKtN,QAAL,CAAc;AAAExB,QAAAA,OAAO,EAAE8O;AAAX,OAAd,CARhC;AASE,MAAA,QAAQ,EAAEZ;AATZ,MAzCJ,CADF;AAwDD;;AAvpCD;;;;gBAHI/N,uB,kBAQkB;AACpB2I,EAAAA,WAAW,EAAE,IADO;AAEpBpG,EAAAA,UAAU,EAAE,IAFQ;AAGpBG,EAAAA,WAAW,EAAE,CAHO;AAIpBuE,EAAAA,cAAc,EAAE,CAJI;AAKpBC,EAAAA,cAAc,EAAE,CALI;AAMpB2C,EAAAA,OAAO,EAAE,GANW;AAOpBC,EAAAA,OAAO,EAAE,GAPW;AAQpBC,EAAAA,wBAAwB,EAAE,CARN;AASpBC,EAAAA,yBAAyB,EAAE,CATP;AAUpBsB,EAAAA,mBAAmB,EAAE,CAVD;AAWpBlH,EAAAA,cAAc,EAAE,GAXI;AAYpB6D,EAAAA,aAAa,EAAE,IAZK;AAapB6E,EAAAA,QAAQ,EAAE,GAbU;AAcpBpL,EAAAA,WAAW,EAAE,IAdO;AAepBE,EAAAA,iBAAiB,EAAE,GAfC;AAgBpB8D,EAAAA,YAAY,EAAEkJ,SAhBM;AAiBpBjJ,EAAAA,aAAa,EAAEiJ,SAjBK;AAkBpBvG,EAAAA,kBAAkB,EAAE,CAlBA;AAmBpBuF,EAAAA,0BAA0B,EAAE,IAnBR;AAoBpB1K,EAAAA,iBAAiB,EAAE0L,SApBC;AAqBpBlB,EAAAA,aAAa,EAAEkB,SArBK;AAsBpB7N,EAAAA,yBAAyB,EAAE6N,SAtBP;AAuBpBlF,EAAAA,uBAAuB,EAAEkF,SAvBL;AAwBpBxH,EAAAA,UAAU,EAAE,IAxBQ;AAyBpB5E,EAAAA,uBAAuB,EAAE;AAzBL,C;;AAqpCxB,MAAMwL,MAAM,GAAGa,wBAAWxI,MAAX,CAAkB;AAC/B8H,EAAAA,WAAW,EAAE;AACXW,IAAAA,IAAI,EAAE,CADK;AAEXhP,IAAAA,KAAK,EAAE,MAFI;AAGXiP,IAAAA,cAAc,EAAE,QAHL;AAIXC,IAAAA,UAAU,EAAE;AAJD,GADkB;AAO/Bf,EAAAA,SAAS,EAAE;AACTa,IAAAA,IAAI,EAAE,CADG;AAETC,IAAAA,cAAc,EAAE,QAFP;AAGTC,IAAAA,UAAU,EAAE,QAHH;AAITlO,IAAAA,QAAQ,EAAE,UAJD;AAKTmO,IAAAA,QAAQ,EAAE;AALD;AAPoB,CAAlB,CAAf;;eAgBejP,uB","sourcesContent":["import React, { Component, createRef, RefObject } from 'react';\nimport {\n Animated,\n Easing,\n GestureResponderEvent,\n PanResponder,\n PanResponderGestureState,\n StyleSheet,\n View,\n} from 'react-native';\n\nimport {\n Vec2D,\n ReactNativeZoomableViewProps,\n ReactNativeZoomableViewState,\n TouchPoint,\n ZoomableViewEvent,\n Size2D,\n} from './typings';\n\nimport { AnimatedTouchFeedback } from './components';\nimport { DebugTouchPoint } from './debugHelper';\nimport {\n calcGestureCenterPoint,\n calcGestureTouchDistance,\n calcNewScaledOffsetForZoomCentering,\n} from './helper';\nimport { applyPanBoundariesToOffset } from './helper/applyPanBoundariesToOffset';\nimport { viewportPositionToImagePosition } from './helper/coordinateConversion';\nimport { StaticPin } from './components/StaticPin';\nimport { debounce } from 'lodash';\nimport {\n getBoundaryCrossedAnim,\n getPanMomentumDecayAnim,\n getZoomToAnimation,\n} from './animations';\n\nconst initialState = {\n originalWidth: null,\n originalHeight: null,\n originalPageX: null,\n originalPageY: null,\n pinSize: { width: 0, height: 0 },\n} as ReactNativeZoomableViewState;\n\nclass ReactNativeZoomableView extends Component<\n ReactNativeZoomableViewProps,\n ReactNativeZoomableViewState\n> {\n zoomSubjectWrapperRef: RefObject;\n gestureHandlers: any;\n doubleTapFirstTapReleaseTimestamp: number;\n\n static defaultProps = {\n zoomEnabled: true,\n panEnabled: true,\n initialZoom: 1,\n initialOffsetX: 0,\n initialOffsetY: 0,\n maxZoom: 1.5,\n minZoom: 0.5,\n pinchToZoomInSensitivity: 1,\n pinchToZoomOutSensitivity: 1,\n movementSensibility: 1,\n doubleTapDelay: 300,\n bindToBorders: true,\n zoomStep: 0.5,\n onLongPress: null,\n longPressDuration: 700,\n contentWidth: undefined,\n contentHeight: undefined,\n panBoundaryPadding: 0,\n visualTouchFeedbackEnabled: true,\n staticPinPosition: undefined,\n staticPinIcon: undefined,\n onStaticPinPositionChange: undefined,\n onStaticPinPositionMove: undefined,\n animatePin: true,\n disablePanOnInitialZoom: false,\n };\n\n private panAnim = new Animated.ValueXY({ x: 0, y: 0 });\n private zoomAnim = new Animated.Value(1);\n private pinAnim = new Animated.ValueXY({ x: 0, y: 0 });\n\n private __offsets = {\n x: {\n value: 0,\n boundaryCrossedAnimInEffect: false,\n },\n y: {\n value: 0,\n boundaryCrossedAnimInEffect: false,\n },\n };\n\n private zoomLevel = 1;\n private lastGestureCenterPosition: { x: number; y: number } = null;\n private lastGestureTouchDistance: number;\n private gestureType: 'pinch' | 'shift' | 'null';\n\n private _gestureStarted = false;\n private set gestureStarted(v: boolean) {\n this._gestureStarted = v;\n }\n public get gestureStarted() {\n return this._gestureStarted;\n }\n\n /**\n * Last press time (used to evaluate whether user double tapped)\n * @type {number}\n */\n private longPressTimeout: NodeJS.Timeout = null;\n private onTransformInvocationInitialized: boolean;\n private singleTapTimeoutId: NodeJS.Timeout;\n private touches: TouchPoint[] = [];\n private doubleTapFirstTap: TouchPoint;\n private measureZoomSubjectInterval: NodeJS.Timer;\n\n constructor(props) {\n super(props);\n\n this.gestureHandlers = PanResponder.create({\n onStartShouldSetPanResponder: this._handleStartShouldSetPanResponder,\n onPanResponderGrant: this._handlePanResponderGrant,\n onPanResponderMove: this._handlePanResponderMove,\n onPanResponderRelease: this._handlePanResponderEnd,\n onPanResponderTerminate: (evt, gestureState) => {\n // We should also call _handlePanResponderEnd\n // to properly perform cleanups when the gesture is terminated\n // (aka gesture handling responsibility is taken over by another component).\n // This also fixes a weird issue where\n // on real device, sometimes onPanResponderRelease is not called when you lift 2 fingers up,\n // but onPanResponderTerminate is called instead for no apparent reason.\n this._handlePanResponderEnd(evt, gestureState);\n this.props.onPanResponderTerminate?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n );\n },\n onPanResponderTerminationRequest: (evt, gestureState) =>\n !!this.props.onPanResponderTerminationRequest?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n ),\n // Defaults to true to prevent parent components, such as React Navigation's tab view, from taking over as responder.\n onShouldBlockNativeResponder: (evt, gestureState) =>\n this.props.onShouldBlockNativeResponder?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n ) ?? true,\n onStartShouldSetPanResponderCapture: (evt, gestureState) =>\n this.props.onStartShouldSetPanResponderCapture?.(evt, gestureState),\n onMoveShouldSetPanResponderCapture: (evt, gestureState) =>\n this.props.onMoveShouldSetPanResponderCapture?.(evt, gestureState),\n });\n\n this.zoomSubjectWrapperRef = createRef();\n\n if (this.props.zoomAnimatedValue)\n this.zoomAnim = this.props.zoomAnimatedValue;\n if (this.props.panAnimatedValueXY)\n this.panAnim = this.props.panAnimatedValueXY;\n\n this.zoomLevel = props.initialZoom;\n this.offsetX = props.initialOffsetX;\n this.offsetY = props.initialOffsetY;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n this.panAnim.addListener(({ x, y }) => {\n this.offsetX = x;\n this.offsetY = y;\n });\n this.zoomAnim.addListener(({ value }) => {\n this.zoomLevel = value;\n });\n\n this.state = {\n ...initialState,\n };\n\n this.lastGestureTouchDistance = 150;\n\n this.gestureType = null;\n }\n\n private raisePin() {\n if (!this.props.animatePin) return;\n Animated.timing(this.pinAnim, {\n toValue: { x: 0, y: -10 },\n useNativeDriver: true,\n easing: Easing.out(Easing.ease),\n duration: 100,\n }).start();\n }\n\n private dropPin() {\n if (!this.props.animatePin) return;\n Animated.timing(this.pinAnim, {\n toValue: { x: 0, y: 0 },\n useNativeDriver: true,\n easing: Easing.out(Easing.ease),\n duration: 100,\n }).start();\n }\n\n private set offsetX(x: number) {\n this.__setOffset('x', x);\n }\n private set offsetY(y: number) {\n this.__setOffset('y', y);\n }\n private get offsetX() {\n return this.__getOffset('x');\n }\n private get offsetY() {\n return this.__getOffset('y');\n }\n private __setOffset(axis: 'x' | 'y', offset) {\n const offsetState = this.__offsets[axis];\n const animValue = this.panAnim?.[axis];\n\n if (this.props.bindToBorders) {\n const containerSize =\n axis === 'x' ? this.state?.originalWidth : this.state?.originalHeight;\n const contentSize =\n axis === 'x'\n ? this.props.contentWidth || this.state?.originalWidth\n : this.props.contentHeight || this.state?.originalHeight;\n\n const boundOffset =\n contentSize && containerSize\n ? applyPanBoundariesToOffset(\n offset,\n containerSize,\n contentSize,\n this.zoomLevel,\n this.props.panBoundaryPadding\n )\n : offset;\n\n if (\n animValue &&\n !this.gestureType &&\n !offsetState.boundaryCrossedAnimInEffect\n ) {\n const boundariesApplied =\n boundOffset !== offset &&\n boundOffset.toFixed(3) !== offset.toFixed(3);\n if (boundariesApplied) {\n offsetState.boundaryCrossedAnimInEffect = true;\n getBoundaryCrossedAnim(this.panAnim[axis], boundOffset).start(() => {\n offsetState.boundaryCrossedAnimInEffect = false;\n });\n return;\n }\n }\n }\n\n offsetState.value = offset;\n }\n private __getOffset(axis: 'x' | 'y') {\n return this.__offsets[axis].value;\n }\n\n componentDidUpdate(\n prevProps: ReactNativeZoomableViewProps,\n prevState: ReactNativeZoomableViewState\n ) {\n const { zoomEnabled, initialZoom } = this.props;\n if (prevProps.zoomEnabled && !zoomEnabled) {\n this.zoomLevel = initialZoom;\n this.zoomAnim.setValue(this.zoomLevel);\n }\n if (\n !this.onTransformInvocationInitialized &&\n this._invokeOnTransform().successful\n ) {\n this.panAnim.addListener(() => this._invokeOnTransform());\n this.zoomAnim.addListener(() => this._invokeOnTransform());\n this.onTransformInvocationInitialized = true;\n }\n\n const currState = this.state;\n const originalMeasurementsChanged =\n currState.originalHeight !== prevState.originalHeight ||\n currState.originalWidth !== prevState.originalWidth ||\n currState.originalPageX !== prevState.originalPageX ||\n currState.originalPageY !== prevState.originalPageY;\n\n const staticPinPositionChanged =\n prevProps.staticPinPosition?.x !== this.props.staticPinPosition?.x ||\n prevProps.staticPinPosition?.y !== this.props.staticPinPosition?.y;\n\n if (\n this.onTransformInvocationInitialized &&\n (originalMeasurementsChanged || staticPinPositionChanged)\n ) {\n this._invokeOnTransform();\n }\n }\n\n componentDidMount() {\n this.grabZoomSubjectOriginalMeasurements();\n // We've already run `grabZoomSubjectOriginalMeasurements` at various events\n // to make sure the measurements are promptly updated.\n // However, there might be cases we haven't accounted for, especially when\n // native processes are involved. To account for those cases,\n // we'll use an interval here to ensure we're always up-to-date.\n // The `setState` in `grabZoomSubjectOriginalMeasurements` won't trigger a rerender\n // if the values given haven't changed, so we're not running performance risk here.\n this.measureZoomSubjectInterval = setInterval(\n this.grabZoomSubjectOriginalMeasurements,\n 1e3\n );\n }\n\n componentWillUnmount() {\n clearInterval(this.measureZoomSubjectInterval);\n }\n\n debouncedOnStaticPinPositionChange = debounce(\n (position: Vec2D) => this.props.onStaticPinPositionChange?.(position),\n 100\n );\n\n /**\n * try to invoke onTransform\n * @private\n */\n _invokeOnTransform() {\n const zoomableViewEvent = this._getZoomableViewEventObject();\n\n if (!zoomableViewEvent.originalWidth || !zoomableViewEvent.originalHeight)\n return { successful: false };\n\n this.props.onTransform?.(zoomableViewEvent);\n\n this.props.onStaticPinPositionMove?.(this._staticPinPosition());\n\n this.debouncedOnStaticPinPositionChange(this._staticPinPosition());\n\n return { successful: true };\n }\n\n /**\n * Returns additional information about components current state for external event hooks\n *\n * @returns {{}}\n * @private\n */\n _getZoomableViewEventObject(overwriteObj = {}): ZoomableViewEvent {\n return {\n zoomLevel: this.zoomLevel,\n offsetX: this.offsetX,\n offsetY: this.offsetY,\n originalHeight: this.state.originalHeight,\n originalWidth: this.state.originalWidth,\n originalPageX: this.state.originalPageX,\n originalPageY: this.state.originalPageY,\n ...overwriteObj,\n } as ZoomableViewEvent;\n }\n\n /**\n * Get the original box dimensions and save them for later use.\n * (They will be used to calculate boxBorders)\n *\n * @private\n */\n private grabZoomSubjectOriginalMeasurements = () => {\n // make sure we measure after animations are complete\n requestAnimationFrame(() => {\n // this setTimeout is here to fix a weird issue on iOS where the measurements are all `0`\n // when navigating back (react-navigation stack) from another view\n // while closing the keyboard at the same time\n setTimeout(() => {\n // In normal conditions, we're supposed to measure zoomSubject instead of its wrapper.\n // However, our zoomSubject may have been transformed by an initial zoomLevel or offset,\n // in which case these measurements will not represent the true \"original\" measurements.\n // We just need to make sure the zoomSubjectWrapper perfectly aligns with the zoomSubject\n // (no border, space, or anything between them)\n const zoomSubjectWrapperRef = this.zoomSubjectWrapperRef;\n // we don't wanna measure when zoomSubjectWrapperRef is not yet available or has been unmounted\n zoomSubjectWrapperRef.current?.measureInWindow(\n (x, y, width, height) => {\n this.setState({\n originalWidth: width,\n originalHeight: height,\n originalPageX: x,\n originalPageY: y,\n });\n }\n );\n });\n });\n };\n\n /**\n * Handles the start of touch events and checks for taps\n *\n * @param e\n * @param gestureState\n * @returns {boolean}\n *\n * @private\n */\n _handleStartShouldSetPanResponder = (\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) => {\n if (this.props.onStartShouldSetPanResponder) {\n this.props.onStartShouldSetPanResponder(\n e,\n gestureState,\n this._getZoomableViewEventObject(),\n false\n );\n }\n\n // Always set pan responder on start\n // of gesture so we can handle tap.\n // \"Pan threshold validation\" will be handled\n // in `onPanResponderMove` instead of in `onMoveShouldSetPanResponder`\n return true;\n };\n\n /**\n * Calculates pinch distance\n *\n * @param e\n * @param gestureState\n * @private\n */\n _handlePanResponderGrant = (e, gestureState) => {\n if (this.props.onLongPress) {\n this.longPressTimeout = setTimeout(() => {\n this.props.onLongPress?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n this.longPressTimeout = null;\n }, this.props.longPressDuration);\n }\n\n this.props.onPanResponderGrant?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n\n this.panAnim.stopAnimation();\n this.zoomAnim.stopAnimation();\n this.gestureStarted = true;\n\n this.raisePin();\n };\n\n /**\n * Handles the end of touch events\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePanResponderEnd = (e, gestureState) => {\n if (!this.gestureType) {\n this._resolveAndHandleTap(e);\n }\n\n this.setState({ debugPoints: [] });\n\n this.lastGestureCenterPosition = null;\n\n const disableMomentum =\n this.props.disableMomentum ||\n (this.props.panEnabled &&\n this.gestureType === 'shift' &&\n this.props.disablePanOnInitialZoom &&\n this.zoomLevel === this.props.initialZoom);\n\n // Trigger final shift animation unless disablePanOnInitialZoom is set and we're on the initial zoom level\n // or disableMomentum\n if (!disableMomentum) {\n getPanMomentumDecayAnim(this.panAnim, {\n x: gestureState.vx / this.zoomLevel,\n y: gestureState.vy / this.zoomLevel,\n }).start();\n }\n\n if (this.longPressTimeout) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n\n this.props.onPanResponderEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n\n if (this.gestureType === 'pinch') {\n this.props.onZoomEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n } else if (this.gestureType === 'shift') {\n this.props.onShiftingEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n }\n\n if (this.props.staticPinPosition) {\n this._updateStaticPin();\n }\n\n this.dropPin();\n\n this.gestureType = null;\n this.gestureStarted = false;\n };\n\n /**\n * Handles the actual movement of our pan responder\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePanResponderMove = (\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) => {\n if (this.props.onPanResponderMove) {\n if (\n this.props.onPanResponderMove(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n )\n ) {\n return false;\n }\n }\n\n // Only supports 2 touches and below,\n // any invalid number will cause the gesture to end.\n if (gestureState.numberActiveTouches <= 2) {\n if (!this.gestureStarted) {\n this._handlePanResponderGrant(e, gestureState);\n }\n } else {\n if (this.gestureStarted) {\n this._handlePanResponderEnd(e, gestureState);\n }\n return true;\n }\n\n if (gestureState.numberActiveTouches === 2) {\n if (this.longPressTimeout) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n\n // change some measurement states when switching gesture to ensure a smooth transition\n if (this.gestureType !== 'pinch') {\n this.lastGestureCenterPosition = calcGestureCenterPoint(\n e,\n gestureState\n );\n this.lastGestureTouchDistance = calcGestureTouchDistance(\n e,\n gestureState\n );\n }\n this.gestureType = 'pinch';\n this._handlePinching(e, gestureState);\n } else if (gestureState.numberActiveTouches === 1) {\n if (\n this.longPressTimeout &&\n (Math.abs(gestureState.dx) > 5 || Math.abs(gestureState.dy) > 5)\n ) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n // change some measurement states when switching gesture to ensure a smooth transition\n if (this.gestureType !== 'shift') {\n this.lastGestureCenterPosition = calcGestureCenterPoint(\n e,\n gestureState\n );\n }\n\n const { dx, dy } = gestureState;\n const isShiftGesture = Math.abs(dx) > 2 || Math.abs(dy) > 2;\n if (isShiftGesture) {\n this.gestureType = 'shift';\n this._handleShifting(gestureState);\n }\n }\n };\n\n /**\n * Handles the pinch movement and zooming\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePinching(\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) {\n if (!this.props.zoomEnabled) return;\n\n const {\n maxZoom,\n minZoom,\n pinchToZoomInSensitivity,\n pinchToZoomOutSensitivity,\n } = this.props;\n\n const distance = calcGestureTouchDistance(e, gestureState);\n\n if (\n this.props.onZoomBefore &&\n this.props.onZoomBefore(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n )\n ) {\n return;\n }\n\n // define the new zoom level and take zoom level sensitivity into consideration\n const zoomGrowthFromLastGestureState =\n distance / this.lastGestureTouchDistance;\n this.lastGestureTouchDistance = distance;\n\n const pinchToZoomSensitivity =\n zoomGrowthFromLastGestureState < 1\n ? pinchToZoomOutSensitivity\n : pinchToZoomInSensitivity;\n\n const deltaGrowth = zoomGrowthFromLastGestureState - 1;\n // 0 - no resistance\n // 10 - 90% resistance\n const deltaGrowthAdjustedBySensitivity =\n deltaGrowth * (1 - (pinchToZoomSensitivity * 9) / 100);\n\n let newZoomLevel = this.zoomLevel * (1 + deltaGrowthAdjustedBySensitivity);\n\n // make sure max and min zoom levels are respected\n if (maxZoom !== null && newZoomLevel > maxZoom) {\n newZoomLevel = maxZoom;\n }\n\n if (newZoomLevel < minZoom) {\n newZoomLevel = minZoom;\n }\n\n const gestureCenterPoint = calcGestureCenterPoint(e, gestureState);\n\n if (!gestureCenterPoint) return;\n\n let zoomCenter = {\n x: gestureCenterPoint.x - this.state.originalPageX,\n y: gestureCenterPoint.y - this.state.originalPageY,\n };\n\n if (this.props.staticPinPosition) {\n // When we use a static pin position, the zoom centre is the same as that position,\n // otherwise the pin moves around way too much while zooming.\n zoomCenter = {\n x: this.props.staticPinPosition.x,\n y: this.props.staticPinPosition.y,\n };\n }\n\n // Uncomment to debug\n this.props.debug && this._setPinchDebugPoints(e, zoomCenter);\n\n const { originalHeight, originalWidth } = this.state;\n\n const oldOffsetX = this.offsetX;\n const oldOffsetY = this.offsetY;\n const oldScale = this.zoomLevel;\n const newScale = newZoomLevel;\n\n let offsetY = calcNewScaledOffsetForZoomCentering(\n oldOffsetY,\n originalHeight,\n oldScale,\n newScale,\n zoomCenter.y\n );\n let offsetX = calcNewScaledOffsetForZoomCentering(\n oldOffsetX,\n originalWidth,\n oldScale,\n newScale,\n zoomCenter.x\n );\n\n const offsetShift =\n this._calcOffsetShiftSinceLastGestureState(gestureCenterPoint);\n if (offsetShift) {\n offsetX += offsetShift.x;\n offsetY += offsetShift.y;\n }\n\n this.offsetX = offsetX;\n this.offsetY = offsetY;\n this.zoomLevel = newScale;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n\n this.props.onZoomAfter?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n }\n\n /**\n * Used to debug pinch events\n * @param gestureResponderEvent\n * @param zoomCenter\n * @param points\n */\n _setPinchDebugPoints(\n gestureResponderEvent: GestureResponderEvent,\n zoomCenter: Vec2D,\n ...points: Vec2D[]\n ) {\n const { touches } = gestureResponderEvent.nativeEvent;\n const { originalPageY, originalPageX } = this.state;\n this.setState({\n debugPoints: [\n {\n x: touches[0].pageX - originalPageX,\n y: touches[0].pageY - originalPageY,\n },\n {\n x: touches[1].pageX - originalPageX,\n y: touches[1].pageY - originalPageY,\n },\n zoomCenter,\n ...points,\n ],\n });\n }\n\n /**\n * Calculates the amount the offset should shift since the last position during panning\n *\n * @param {Vec2D} gestureCenterPoint\n *\n * @private\n */\n _calcOffsetShiftSinceLastGestureState(gestureCenterPoint: Vec2D) {\n const { movementSensibility } = this.props;\n\n let shift = null;\n\n if (this.lastGestureCenterPosition) {\n const dx = gestureCenterPoint.x - this.lastGestureCenterPosition.x;\n const dy = gestureCenterPoint.y - this.lastGestureCenterPosition.y;\n\n const shiftX = dx / this.zoomLevel / movementSensibility;\n const shiftY = dy / this.zoomLevel / movementSensibility;\n\n shift = {\n x: shiftX,\n y: shiftY,\n };\n }\n\n this.lastGestureCenterPosition = gestureCenterPoint;\n\n return shift;\n }\n\n /**\n * Handles movement by tap and move\n *\n * @param gestureState\n *\n * @private\n */\n _handleShifting(gestureState: PanResponderGestureState) {\n // Skips shifting if panEnabled is false or disablePanOnInitialZoom is true and we're on the initial zoom level\n if (\n !this.props.panEnabled ||\n (this.props.disablePanOnInitialZoom &&\n this.zoomLevel === this.props.initialZoom)\n ) {\n return;\n }\n const shift = this._calcOffsetShiftSinceLastGestureState({\n x: gestureState.moveX,\n y: gestureState.moveY,\n });\n if (!shift) return;\n\n const offsetX = this.offsetX + shift.x;\n const offsetY = this.offsetY + shift.y;\n\n if (this.props.debug) {\n const x = gestureState.moveX - this.state.originalPageX;\n const y = gestureState.moveY - this.state.originalPageY;\n this.setState({ debugPoints: [{ x, y }] });\n }\n\n this._setNewOffsetPosition(offsetX, offsetY);\n\n this.raisePin();\n }\n\n /**\n * Set the state to offset moved\n *\n * @param {number} newOffsetX\n * @param {number} newOffsetY\n * @returns\n */\n async _setNewOffsetPosition(newOffsetX: number, newOffsetY: number) {\n const { onShiftingBefore, onShiftingAfter } = this.props;\n\n if (onShiftingBefore?.(null, null, this._getZoomableViewEventObject())) {\n return;\n }\n\n this.offsetX = newOffsetX;\n this.offsetY = newOffsetY;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n\n onShiftingAfter?.(null, null, this._getZoomableViewEventObject());\n }\n\n /**\n * Check whether the press event is double tap\n * or single tap and handle the event accordingly\n *\n * @param e\n *\n * @private\n */\n private _resolveAndHandleTap = (e: GestureResponderEvent) => {\n const now = Date.now();\n if (\n this.doubleTapFirstTapReleaseTimestamp &&\n now - this.doubleTapFirstTapReleaseTimestamp < this.props.doubleTapDelay\n ) {\n this._addTouch({\n ...this.doubleTapFirstTap,\n id: now.toString(),\n isSecondTap: true,\n });\n clearTimeout(this.singleTapTimeoutId);\n delete this.doubleTapFirstTapReleaseTimestamp;\n delete this.singleTapTimeoutId;\n delete this.doubleTapFirstTap;\n this._handleDoubleTap(e);\n } else {\n this.doubleTapFirstTapReleaseTimestamp = now;\n this.doubleTapFirstTap = {\n id: now.toString(),\n x: e.nativeEvent.pageX - this.state.originalPageX,\n y: e.nativeEvent.pageY - this.state.originalPageY,\n };\n this._addTouch(this.doubleTapFirstTap);\n\n // persist event so e.nativeEvent is preserved after a timeout delay\n e.persist();\n this.singleTapTimeoutId = setTimeout(() => {\n delete this.doubleTapFirstTapReleaseTimestamp;\n delete this.singleTapTimeoutId;\n\n // Pan to the tapped location\n if (this.props.staticPinPosition && this.doubleTapFirstTap) {\n const tapX =\n this.props.staticPinPosition.x - this.doubleTapFirstTap.x;\n const tapY =\n this.props.staticPinPosition.y - this.doubleTapFirstTap.y;\n\n Animated.timing(this.panAnim, {\n toValue: {\n x: this.offsetX + tapX / this.zoomLevel,\n y: this.offsetY + tapY / this.zoomLevel,\n },\n useNativeDriver: true,\n duration: 200,\n }).start(() => {\n this._updateStaticPin();\n });\n }\n\n this.props.onSingleTap?.(e, this._getZoomableViewEventObject());\n }, this.props.doubleTapDelay);\n }\n };\n\n _moveTimeout: NodeJS.Timeout;\n moveStaticPinTo = (position: Vec2D) => {\n const { originalWidth, originalHeight } = this.state;\n const { staticPinPosition, contentWidth, contentHeight } = this.props;\n\n // Offset for the static pin\n const pinX = staticPinPosition.x - originalWidth / 2;\n const pinY = staticPinPosition.y - originalHeight / 2;\n\n this.offsetX = contentWidth / 2 - position.x + pinX / this.zoomLevel;\n this.offsetY = contentHeight / 2 - position.y + pinY / this.zoomLevel;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n };\n\n private _staticPinPosition = () => {\n return viewportPositionToImagePosition({\n viewportPosition: {\n x: this.props.staticPinPosition.x,\n y: this.props.staticPinPosition.y,\n },\n imageSize: {\n height: this.props.contentHeight,\n width: this.props.contentWidth,\n },\n zoomableEvent: {\n ...this._getZoomableViewEventObject(),\n offsetX: this.offsetX,\n offsetY: this.offsetY,\n zoomLevel: this.zoomLevel,\n },\n });\n };\n\n private _updateStaticPin = () => {\n this.props.onStaticPinPositionChange?.(this._staticPinPosition());\n };\n\n private _addTouch(touch: TouchPoint) {\n this.touches.push(touch);\n this.setState({ touches: [...this.touches] });\n }\n\n private _removeTouch(touch: TouchPoint) {\n this.touches.splice(this.touches.indexOf(touch), 1);\n this.setState({ touches: [...this.touches] });\n }\n\n /**\n * Handles the double tap event\n *\n * @param e\n *\n * @private\n */\n _handleDoubleTap(e: GestureResponderEvent) {\n const { onDoubleTapBefore, onDoubleTapAfter, doubleTapZoomToCenter } =\n this.props;\n\n onDoubleTapBefore?.(e, this._getZoomableViewEventObject());\n\n const nextZoomStep = this._getNextZoomStep();\n const { originalPageX, originalPageY } = this.state;\n\n // define new zoom position coordinates\n const zoomPositionCoordinates = {\n x: e.nativeEvent.pageX - originalPageX,\n y: e.nativeEvent.pageY - originalPageY,\n };\n\n // if doubleTapZoomToCenter enabled -> always zoom to center instead\n if (doubleTapZoomToCenter) {\n zoomPositionCoordinates.x = 0;\n zoomPositionCoordinates.y = 0;\n }\n\n this._zoomToLocation(\n zoomPositionCoordinates.x,\n zoomPositionCoordinates.y,\n nextZoomStep\n ).then(() => {\n onDoubleTapAfter?.(\n e,\n this._getZoomableViewEventObject({ zoomLevel: nextZoomStep })\n );\n });\n }\n\n /**\n * Returns the next zoom step based on current step and zoomStep property.\n * If we are zoomed all the way in -> return to initialzoom\n *\n * @returns {*}\n */\n _getNextZoomStep() {\n const { zoomStep, maxZoom, initialZoom } = this.props;\n const { zoomLevel } = this;\n\n if (zoomLevel.toFixed(2) === maxZoom.toFixed(2)) {\n return initialZoom;\n }\n\n const nextZoomStep = zoomLevel * (1 + zoomStep);\n if (nextZoomStep > maxZoom) {\n return maxZoom;\n }\n\n return nextZoomStep;\n }\n\n /**\n * Zooms to a specific location in our view\n *\n * @param x\n * @param y\n * @param newZoomLevel\n *\n * @private\n */\n async _zoomToLocation(x: number, y: number, newZoomLevel: number) {\n if (!this.props.zoomEnabled) return;\n\n this.props.onZoomBefore?.(null, null, this._getZoomableViewEventObject());\n\n // == Perform Zoom Animation ==\n // Calculates panAnim values based on changes in zoomAnim.\n let prevScale = this.zoomLevel;\n // Since zoomAnim is calculated in native driver,\n // it will jitter panAnim once in a while,\n // because here panAnim is being calculated in js.\n // However the jittering should mostly occur in simulator.\n const listenerId = this.zoomAnim.addListener(({ value: newScale }) => {\n this.panAnim.setValue({\n x: calcNewScaledOffsetForZoomCentering(\n this.offsetX,\n this.state.originalWidth,\n prevScale,\n newScale,\n x\n ),\n y: calcNewScaledOffsetForZoomCentering(\n this.offsetY,\n this.state.originalHeight,\n prevScale,\n newScale,\n y\n ),\n });\n prevScale = newScale;\n });\n getZoomToAnimation(this.zoomAnim, newZoomLevel).start(() => {\n this.zoomAnim.removeListener(listenerId);\n });\n // == Zoom Animation Ends ==\n\n this.props.onZoomAfter?.(null, null, this._getZoomableViewEventObject());\n }\n\n /**\n * Zooms to a specificied zoom level.\n * Returns a promise if everything was updated and a boolean, whether it could be updated or if it exceeded the min/max zoom limits.\n *\n * @param {number} newZoomLevel\n *\n * @return {Promise}\n */\n async zoomTo(newZoomLevel: number): Promise {\n if (\n // if we would go out of our min/max limits -> abort\n newZoomLevel > this.props.maxZoom ||\n newZoomLevel < this.props.minZoom\n )\n return false;\n\n await this._zoomToLocation(0, 0, newZoomLevel);\n return true;\n }\n\n /**\n * Zooms in or out by a specified change level\n * Use a positive number for `zoomLevelChange` to zoom in\n * Use a negative number for `zoomLevelChange` to zoom out\n *\n * Returns a promise if everything was updated and a boolean, whether it could be updated or if it exceeded the min/max zoom limits.\n *\n * @param {number | null} zoomLevelChange\n *\n * @return {Promise}\n */\n zoomBy(zoomLevelChange: number = null): Promise {\n // if no zoom level Change given -> just use zoom step\n if (!zoomLevelChange) {\n zoomLevelChange = this.props.zoomStep;\n }\n\n return this.zoomTo(this.zoomLevel + zoomLevelChange);\n }\n\n /**\n * Moves the zoomed view to a specified position\n * Returns a promise when finished\n *\n * @param {number} newOffsetX the new position we want to move it to (x-axis)\n * @param {number} newOffsetY the new position we want to move it to (y-axis)\n *\n * @return {Promise}\n */\n moveTo(newOffsetX: number, newOffsetY: number): Promise {\n const { originalWidth, originalHeight } = this.state;\n\n const offsetX = (newOffsetX - originalWidth / 2) / this.zoomLevel;\n const offsetY = (newOffsetY - originalHeight / 2) / this.zoomLevel;\n\n return this._setNewOffsetPosition(-offsetX, -offsetY);\n }\n\n /**\n * Moves the zoomed view by a certain amount.\n *\n * Returns a promise when finished\n *\n * @param {number} offsetChangeX the amount we want to move the offset by (x-axis)\n * @param {number} offsetChangeY the amount we want to move the offset by (y-axis)\n *\n * @return {Promise}\n */\n moveBy(offsetChangeX: number, offsetChangeY: number): Promise {\n const offsetX =\n (this.offsetX * this.zoomLevel - offsetChangeX) / this.zoomLevel;\n const offsetY =\n (this.offsetY * this.zoomLevel - offsetChangeY) / this.zoomLevel;\n\n return this._setNewOffsetPosition(offsetX, offsetY);\n }\n\n render() {\n const {\n staticPinIcon,\n children,\n visualTouchFeedbackEnabled,\n doubleTapDelay,\n staticPinPosition,\n onStaticPinLongPress,\n onStaticPinPress,\n pinProps,\n } = this.props;\n const { pinSize, touches, debugPoints = [] } = this.state;\n\n return (\n \n \n {children}\n \n\n {visualTouchFeedbackEnabled &&\n touches?.map((touch) => {\n const animationDuration = doubleTapDelay;\n return (\n this._removeTouch(touch)}\n />\n );\n })}\n\n {/* For Debugging Only */}\n {debugPoints.map(({ x, y }, index) => {\n return ;\n })}\n\n {staticPinPosition && (\n this.setState({ pinSize: size })}\n pinProps={pinProps}\n />\n )}\n \n );\n }\n}\n\nconst styles = StyleSheet.create({\n zoomSubject: {\n flex: 1,\n width: '100%',\n justifyContent: 'center',\n alignItems: 'center',\n },\n container: {\n flex: 1,\n justifyContent: 'center',\n alignItems: 'center',\n position: 'relative',\n overflow: 'hidden',\n },\n});\n\nexport default ReactNativeZoomableView;\n\nexport { ReactNativeZoomableView };\n"]} \ No newline at end of file +{"version":3,"sources":["ReactNativeZoomableView.tsx"],"names":["initialState","originalWidth","originalHeight","originalPageX","originalPageY","pinSize","width","height","ReactNativeZoomableView","Component","gestureStarted","v","_gestureStarted","constructor","props","Animated","ValueXY","x","y","Value","value","boundaryCrossedAnimInEffect","position","onStaticPinPositionChange","requestAnimationFrame","setTimeout","zoomSubjectWrapperRef","current","measureInWindow","setState","e","gestureState","onStartShouldSetPanResponder","_getZoomableViewEventObject","onLongPress","longPressTimeout","longPressDuration","onPanResponderGrant","panAnim","stopAnimation","zoomAnim","raisePin","gestureType","_resolveAndHandleTap","debugPoints","lastGestureCenterPosition","disableMomentum","panEnabled","disablePanOnInitialZoom","zoomLevel","initialZoom","vx","vy","start","clearTimeout","onPanResponderEnd","onZoomEnd","onShiftingEnd","staticPinPosition","_updateStaticPin","dropPin","onPanResponderMove","numberActiveTouches","_handlePanResponderGrant","_handlePanResponderEnd","lastGestureTouchDistance","_handlePinching","Math","abs","dx","dy","isShiftGesture","_handleShifting","now","Date","doubleTapFirstTapReleaseTimestamp","doubleTapDelay","_addTouch","doubleTapFirstTap","id","toString","isSecondTap","singleTapTimeoutId","_handleDoubleTap","nativeEvent","pageX","state","pageY","persist","tapX","tapY","timing","toValue","offsetX","offsetY","useNativeDriver","duration","onSingleTap","contentWidth","contentHeight","pinX","pinY","setValue","viewportPosition","imageSize","zoomableEvent","_staticPinPosition","gestureHandlers","PanResponder","create","_handleStartShouldSetPanResponder","_handlePanResponderMove","onPanResponderRelease","onPanResponderTerminate","evt","onPanResponderTerminationRequest","onShouldBlockNativeResponder","onStartShouldSetPanResponderCapture","onMoveShouldSetPanResponderCapture","zoomAnimatedValue","panAnimatedValueXY","initialOffsetX","initialOffsetY","addListener","animatePin","pinAnim","easing","Easing","out","ease","__setOffset","__getOffset","axis","offset","offsetState","__offsets","animValue","bindToBorders","containerSize","contentSize","boundOffset","panBoundaryPadding","boundariesApplied","toFixed","componentDidUpdate","prevProps","prevState","zoomEnabled","onTransformInvocationInitialized","_invokeOnTransform","successful","currState","originalMeasurementsChanged","staticPinPositionChanged","componentDidMount","grabZoomSubjectOriginalMeasurements","measureZoomSubjectInterval","setInterval","componentWillUnmount","clearInterval","zoomableViewEvent","onTransform","onStaticPinPositionMove","debouncedOnStaticPinPositionChange","overwriteObj","maxZoom","minZoom","pinchToZoomInSensitivity","pinchToZoomOutSensitivity","distance","onZoomBefore","zoomGrowthFromLastGestureState","pinchToZoomSensitivity","deltaGrowth","deltaGrowthAdjustedBySensitivity","newZoomLevel","gestureCenterPoint","zoomCenter","debug","_setPinchDebugPoints","oldOffsetX","oldOffsetY","oldScale","newScale","offsetShift","_calcOffsetShiftSinceLastGestureState","onZoomAfter","gestureResponderEvent","points","touches","movementSensibility","shift","shiftX","shiftY","moveX","moveY","_setNewOffsetPosition","newOffsetX","newOffsetY","onShiftingBefore","onShiftingAfter","touch","push","_removeTouch","splice","indexOf","onDoubleTapBefore","onDoubleTapAfter","doubleTapZoomToCenter","nextZoomStep","_getNextZoomStep","zoomPositionCoordinates","_zoomToLocation","then","zoomStep","prevScale","listenerId","removeListener","zoomTo","zoomBy","zoomLevelChange","moveTo","moveBy","offsetChangeX","offsetChangeY","render","staticPinIcon","children","visualTouchFeedbackEnabled","onStaticPinLongPress","onStaticPinPress","pinProps","styles","container","panHandlers","zoomSubject","style","transform","scale","getTranslateTransform","map","animationDuration","index","size","undefined","StyleSheet","flex","justifyContent","alignItems","overflow"],"mappings":"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","sourcesContent":["import React, { Component, createRef, RefObject } from 'react';\nimport {\n Animated,\n Easing,\n GestureResponderEvent,\n PanResponder,\n PanResponderGestureState,\n StyleSheet,\n View,\n} from 'react-native';\n\nimport {\n Vec2D,\n ReactNativeZoomableViewProps,\n ReactNativeZoomableViewState,\n TouchPoint,\n ZoomableViewEvent,\n Size2D,\n} from './typings';\n\nimport { AnimatedTouchFeedback } from './components';\nimport { DebugTouchPoint } from './debugHelper';\nimport {\n calcGestureCenterPoint,\n calcGestureTouchDistance,\n calcNewScaledOffsetForZoomCentering,\n} from './helper';\nimport { applyPanBoundariesToOffset } from './helper/applyPanBoundariesToOffset';\nimport { viewportPositionToImagePosition } from './helper/coordinateConversion';\nimport { StaticPin } from './components/StaticPin';\nimport { debounce } from 'lodash';\nimport {\n getBoundaryCrossedAnim,\n getPanMomentumDecayAnim,\n getZoomToAnimation,\n} from './animations';\n\nconst initialState = {\n originalWidth: null,\n originalHeight: null,\n originalPageX: null,\n originalPageY: null,\n pinSize: { width: 0, height: 0 },\n} as ReactNativeZoomableViewState;\n\nclass ReactNativeZoomableView extends Component<\n ReactNativeZoomableViewProps,\n ReactNativeZoomableViewState\n> {\n zoomSubjectWrapperRef: RefObject;\n gestureHandlers: any;\n doubleTapFirstTapReleaseTimestamp: number;\n\n static defaultProps = {\n zoomEnabled: true,\n panEnabled: true,\n initialZoom: 1,\n initialOffsetX: 0,\n initialOffsetY: 0,\n maxZoom: 1.5,\n minZoom: 0.5,\n pinchToZoomInSensitivity: 1,\n pinchToZoomOutSensitivity: 1,\n movementSensibility: 1,\n doubleTapDelay: 300,\n bindToBorders: true,\n zoomStep: 0.5,\n onLongPress: null,\n longPressDuration: 700,\n contentWidth: undefined,\n contentHeight: undefined,\n panBoundaryPadding: 0,\n visualTouchFeedbackEnabled: true,\n staticPinPosition: undefined,\n staticPinIcon: undefined,\n onStaticPinPositionChange: undefined,\n onStaticPinPositionMove: undefined,\n animatePin: true,\n disablePanOnInitialZoom: false,\n };\n\n private panAnim = new Animated.ValueXY({ x: 0, y: 0 });\n private zoomAnim = new Animated.Value(1);\n private pinAnim = new Animated.ValueXY({ x: 0, y: 0 });\n\n private __offsets = {\n x: {\n value: 0,\n boundaryCrossedAnimInEffect: false,\n },\n y: {\n value: 0,\n boundaryCrossedAnimInEffect: false,\n },\n };\n\n private zoomLevel = 1;\n private lastGestureCenterPosition: { x: number; y: number } = null;\n private lastGestureTouchDistance: number;\n private gestureType: 'pinch' | 'shift' | 'null';\n\n private _gestureStarted = false;\n private set gestureStarted(v: boolean) {\n this._gestureStarted = v;\n }\n public get gestureStarted() {\n return this._gestureStarted;\n }\n\n /**\n * Last press time (used to evaluate whether user double tapped)\n * @type {number}\n */\n private longPressTimeout: NodeJS.Timeout = null;\n private onTransformInvocationInitialized: boolean;\n private singleTapTimeoutId: NodeJS.Timeout;\n private touches: TouchPoint[] = [];\n private doubleTapFirstTap: TouchPoint;\n private measureZoomSubjectInterval: NodeJS.Timer;\n\n constructor(props) {\n super(props);\n\n this.gestureHandlers = PanResponder.create({\n onStartShouldSetPanResponder: this._handleStartShouldSetPanResponder,\n onPanResponderGrant: this._handlePanResponderGrant,\n onPanResponderMove: this._handlePanResponderMove,\n onPanResponderRelease: this._handlePanResponderEnd,\n onPanResponderTerminate: (evt, gestureState) => {\n // We should also call _handlePanResponderEnd\n // to properly perform cleanups when the gesture is terminated\n // (aka gesture handling responsibility is taken over by another component).\n // This also fixes a weird issue where\n // on real device, sometimes onPanResponderRelease is not called when you lift 2 fingers up,\n // but onPanResponderTerminate is called instead for no apparent reason.\n this._handlePanResponderEnd(evt, gestureState);\n this.props.onPanResponderTerminate?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n );\n },\n onPanResponderTerminationRequest: (evt, gestureState) =>\n !!this.props.onPanResponderTerminationRequest?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n ),\n // Defaults to true to prevent parent components, such as React Navigation's tab view, from taking over as responder.\n onShouldBlockNativeResponder: (evt, gestureState) =>\n this.props.onShouldBlockNativeResponder?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n ) ?? true,\n onStartShouldSetPanResponderCapture: (evt, gestureState) =>\n this.props.onStartShouldSetPanResponderCapture?.(evt, gestureState),\n onMoveShouldSetPanResponderCapture: (evt, gestureState) =>\n this.props.onMoveShouldSetPanResponderCapture?.(evt, gestureState),\n });\n\n this.zoomSubjectWrapperRef = createRef();\n\n if (this.props.zoomAnimatedValue)\n this.zoomAnim = this.props.zoomAnimatedValue;\n if (this.props.panAnimatedValueXY)\n this.panAnim = this.props.panAnimatedValueXY;\n\n this.zoomLevel = props.initialZoom;\n this.offsetX = props.initialOffsetX;\n this.offsetY = props.initialOffsetY;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n this.panAnim.addListener(({ x, y }) => {\n this.offsetX = x;\n this.offsetY = y;\n });\n this.zoomAnim.addListener(({ value }) => {\n this.zoomLevel = value;\n });\n\n this.state = {\n ...initialState,\n };\n\n this.lastGestureTouchDistance = 150;\n\n this.gestureType = null;\n }\n\n private raisePin() {\n if (!this.props.animatePin) return;\n Animated.timing(this.pinAnim, {\n toValue: { x: 0, y: -10 },\n useNativeDriver: true,\n easing: Easing.out(Easing.ease),\n duration: 100,\n }).start();\n }\n\n private dropPin() {\n if (!this.props.animatePin) return;\n Animated.timing(this.pinAnim, {\n toValue: { x: 0, y: 0 },\n useNativeDriver: true,\n easing: Easing.out(Easing.ease),\n duration: 100,\n }).start();\n }\n\n private set offsetX(x: number) {\n this.__setOffset('x', x);\n }\n private set offsetY(y: number) {\n this.__setOffset('y', y);\n }\n private get offsetX() {\n return this.__getOffset('x');\n }\n private get offsetY() {\n return this.__getOffset('y');\n }\n private __setOffset(axis: 'x' | 'y', offset) {\n const offsetState = this.__offsets[axis];\n const animValue = this.panAnim?.[axis];\n\n if (this.props.bindToBorders) {\n const containerSize =\n axis === 'x' ? this.state?.originalWidth : this.state?.originalHeight;\n const contentSize =\n axis === 'x'\n ? this.props.contentWidth || this.state?.originalWidth\n : this.props.contentHeight || this.state?.originalHeight;\n\n const boundOffset =\n contentSize && containerSize\n ? applyPanBoundariesToOffset(\n offset,\n containerSize,\n contentSize,\n this.zoomLevel,\n this.props.panBoundaryPadding\n )\n : offset;\n\n if (\n animValue &&\n !this.gestureType &&\n !offsetState.boundaryCrossedAnimInEffect\n ) {\n const boundariesApplied =\n boundOffset !== offset &&\n boundOffset.toFixed(3) !== offset.toFixed(3);\n if (boundariesApplied) {\n offsetState.boundaryCrossedAnimInEffect = true;\n getBoundaryCrossedAnim(this.panAnim[axis], boundOffset).start(() => {\n offsetState.boundaryCrossedAnimInEffect = false;\n });\n return;\n }\n }\n }\n\n offsetState.value = offset;\n }\n private __getOffset(axis: 'x' | 'y') {\n return this.__offsets[axis].value;\n }\n\n componentDidUpdate(\n prevProps: ReactNativeZoomableViewProps,\n prevState: ReactNativeZoomableViewState\n ) {\n const { zoomEnabled, initialZoom } = this.props;\n if (prevProps.zoomEnabled && !zoomEnabled) {\n this.zoomLevel = initialZoom;\n this.zoomAnim.setValue(this.zoomLevel);\n }\n if (\n !this.onTransformInvocationInitialized &&\n this._invokeOnTransform().successful\n ) {\n this.panAnim.addListener(() => this._invokeOnTransform());\n this.zoomAnim.addListener(() => this._invokeOnTransform());\n this.onTransformInvocationInitialized = true;\n }\n\n const currState = this.state;\n const originalMeasurementsChanged =\n currState.originalHeight !== prevState.originalHeight ||\n currState.originalWidth !== prevState.originalWidth ||\n currState.originalPageX !== prevState.originalPageX ||\n currState.originalPageY !== prevState.originalPageY;\n\n const staticPinPositionChanged =\n prevProps.staticPinPosition?.x !== this.props.staticPinPosition?.x ||\n prevProps.staticPinPosition?.y !== this.props.staticPinPosition?.y;\n\n if (\n this.onTransformInvocationInitialized &&\n (originalMeasurementsChanged || staticPinPositionChanged)\n ) {\n this._invokeOnTransform();\n }\n }\n\n componentDidMount() {\n this.grabZoomSubjectOriginalMeasurements();\n // We've already run `grabZoomSubjectOriginalMeasurements` at various events\n // to make sure the measurements are promptly updated.\n // However, there might be cases we haven't accounted for, especially when\n // native processes are involved. To account for those cases,\n // we'll use an interval here to ensure we're always up-to-date.\n // The `setState` in `grabZoomSubjectOriginalMeasurements` won't trigger a rerender\n // if the values given haven't changed, so we're not running performance risk here.\n this.measureZoomSubjectInterval = setInterval(\n this.grabZoomSubjectOriginalMeasurements,\n 1e3\n );\n }\n\n componentWillUnmount() {\n clearInterval(this.measureZoomSubjectInterval);\n }\n\n debouncedOnStaticPinPositionChange = debounce(\n (position: Vec2D) => this.props.onStaticPinPositionChange?.(position),\n 100\n );\n\n /**\n * try to invoke onTransform\n * @private\n */\n _invokeOnTransform() {\n const zoomableViewEvent = this._getZoomableViewEventObject();\n\n if (!zoomableViewEvent.originalWidth || !zoomableViewEvent.originalHeight)\n return { successful: false };\n\n this.props.onTransform?.(zoomableViewEvent);\n\n this.props.onStaticPinPositionMove?.(this._staticPinPosition());\n\n this.debouncedOnStaticPinPositionChange(this._staticPinPosition());\n\n return { successful: true };\n }\n\n /**\n * Returns additional information about components current state for external event hooks\n *\n * @returns {{}}\n * @private\n */\n _getZoomableViewEventObject(overwriteObj = {}): ZoomableViewEvent {\n return {\n zoomLevel: this.zoomLevel,\n offsetX: this.offsetX,\n offsetY: this.offsetY,\n originalHeight: this.state.originalHeight,\n originalWidth: this.state.originalWidth,\n originalPageX: this.state.originalPageX,\n originalPageY: this.state.originalPageY,\n ...overwriteObj,\n } as ZoomableViewEvent;\n }\n\n /**\n * Get the original box dimensions and save them for later use.\n * (They will be used to calculate boxBorders)\n *\n * @private\n */\n private grabZoomSubjectOriginalMeasurements = () => {\n // make sure we measure after animations are complete\n requestAnimationFrame(() => {\n // this setTimeout is here to fix a weird issue on iOS where the measurements are all `0`\n // when navigating back (react-navigation stack) from another view\n // while closing the keyboard at the same time\n setTimeout(() => {\n // In normal conditions, we're supposed to measure zoomSubject instead of its wrapper.\n // However, our zoomSubject may have been transformed by an initial zoomLevel or offset,\n // in which case these measurements will not represent the true \"original\" measurements.\n // We just need to make sure the zoomSubjectWrapper perfectly aligns with the zoomSubject\n // (no border, space, or anything between them)\n const zoomSubjectWrapperRef = this.zoomSubjectWrapperRef;\n // we don't wanna measure when zoomSubjectWrapperRef is not yet available or has been unmounted\n zoomSubjectWrapperRef.current?.measureInWindow(\n (x, y, width, height) => {\n this.setState({\n originalWidth: width,\n originalHeight: height,\n originalPageX: x,\n originalPageY: y,\n });\n }\n );\n });\n });\n };\n\n /**\n * Handles the start of touch events and checks for taps\n *\n * @param e\n * @param gestureState\n * @returns {boolean}\n *\n * @private\n */\n _handleStartShouldSetPanResponder = (\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) => {\n if (this.props.onStartShouldSetPanResponder) {\n this.props.onStartShouldSetPanResponder(\n e,\n gestureState,\n this._getZoomableViewEventObject(),\n false\n );\n }\n\n // Always set pan responder on start\n // of gesture so we can handle tap.\n // \"Pan threshold validation\" will be handled\n // in `onPanResponderMove` instead of in `onMoveShouldSetPanResponder`\n return true;\n };\n\n /**\n * Calculates pinch distance\n *\n * @param e\n * @param gestureState\n * @private\n */\n _handlePanResponderGrant = (e, gestureState) => {\n if (this.props.onLongPress) {\n this.longPressTimeout = setTimeout(() => {\n this.props.onLongPress?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n this.longPressTimeout = null;\n }, this.props.longPressDuration);\n }\n\n this.props.onPanResponderGrant?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n\n this.panAnim.stopAnimation();\n this.zoomAnim.stopAnimation();\n this.gestureStarted = true;\n\n this.raisePin();\n };\n\n /**\n * Handles the end of touch events\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePanResponderEnd = (e, gestureState) => {\n if (!this.gestureType) {\n this._resolveAndHandleTap(e);\n }\n\n this.setState({ debugPoints: [] });\n\n this.lastGestureCenterPosition = null;\n\n const disableMomentum =\n this.props.disableMomentum ||\n (this.props.panEnabled &&\n this.gestureType === 'shift' &&\n this.props.disablePanOnInitialZoom &&\n this.zoomLevel === this.props.initialZoom);\n\n // Trigger final shift animation unless disablePanOnInitialZoom is set and we're on the initial zoom level\n // or disableMomentum\n if (!disableMomentum) {\n getPanMomentumDecayAnim(this.panAnim, {\n x: gestureState.vx / this.zoomLevel,\n y: gestureState.vy / this.zoomLevel,\n }).start();\n }\n\n if (this.longPressTimeout) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n\n this.props.onPanResponderEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n\n if (this.gestureType === 'pinch') {\n this.props.onZoomEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n } else if (this.gestureType === 'shift') {\n this.props.onShiftingEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n }\n\n if (this.props.staticPinPosition) {\n this._updateStaticPin();\n }\n\n this.dropPin();\n\n this.gestureType = null;\n this.gestureStarted = false;\n };\n\n /**\n * Handles the actual movement of our pan responder\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePanResponderMove = (\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) => {\n if (this.props.onPanResponderMove) {\n if (\n this.props.onPanResponderMove(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n )\n ) {\n return false;\n }\n }\n\n // Only supports 2 touches and below,\n // any invalid number will cause the gesture to end.\n if (gestureState.numberActiveTouches <= 2) {\n if (!this.gestureStarted) {\n this._handlePanResponderGrant(e, gestureState);\n }\n } else {\n if (this.gestureStarted) {\n this._handlePanResponderEnd(e, gestureState);\n }\n return true;\n }\n\n if (gestureState.numberActiveTouches === 2) {\n if (this.longPressTimeout) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n\n // change some measurement states when switching gesture to ensure a smooth transition\n if (this.gestureType !== 'pinch') {\n this.lastGestureCenterPosition = calcGestureCenterPoint(\n e,\n gestureState\n );\n this.lastGestureTouchDistance = calcGestureTouchDistance(\n e,\n gestureState\n );\n }\n this.gestureType = 'pinch';\n this._handlePinching(e, gestureState);\n } else if (gestureState.numberActiveTouches === 1) {\n if (\n this.longPressTimeout &&\n (Math.abs(gestureState.dx) > 5 || Math.abs(gestureState.dy) > 5)\n ) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n // change some measurement states when switching gesture to ensure a smooth transition\n if (this.gestureType !== 'shift') {\n this.lastGestureCenterPosition = calcGestureCenterPoint(\n e,\n gestureState\n );\n }\n\n const { dx, dy } = gestureState;\n const isShiftGesture = Math.abs(dx) > 2 || Math.abs(dy) > 2;\n if (isShiftGesture) {\n this.gestureType = 'shift';\n this._handleShifting(gestureState);\n }\n }\n };\n\n /**\n * Handles the pinch movement and zooming\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePinching(\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) {\n if (!this.props.zoomEnabled) return;\n\n const {\n maxZoom,\n minZoom,\n pinchToZoomInSensitivity,\n pinchToZoomOutSensitivity,\n } = this.props;\n\n const distance = calcGestureTouchDistance(e, gestureState);\n\n if (\n this.props.onZoomBefore &&\n this.props.onZoomBefore(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n )\n ) {\n return;\n }\n\n // define the new zoom level and take zoom level sensitivity into consideration\n const zoomGrowthFromLastGestureState =\n distance / this.lastGestureTouchDistance;\n this.lastGestureTouchDistance = distance;\n\n const pinchToZoomSensitivity =\n zoomGrowthFromLastGestureState < 1\n ? pinchToZoomOutSensitivity\n : pinchToZoomInSensitivity;\n\n const deltaGrowth = zoomGrowthFromLastGestureState - 1;\n // 0 - no resistance\n // 10 - 90% resistance\n const deltaGrowthAdjustedBySensitivity =\n deltaGrowth * (1 - (pinchToZoomSensitivity * 9) / 100);\n\n let newZoomLevel = this.zoomLevel * (1 + deltaGrowthAdjustedBySensitivity);\n\n // make sure max and min zoom levels are respected\n if (maxZoom !== null && newZoomLevel > maxZoom) {\n newZoomLevel = maxZoom;\n }\n\n if (newZoomLevel < minZoom) {\n newZoomLevel = minZoom;\n }\n\n const gestureCenterPoint = calcGestureCenterPoint(e, gestureState);\n\n if (!gestureCenterPoint) return;\n\n let zoomCenter = {\n x: gestureCenterPoint.x - this.state.originalPageX,\n y: gestureCenterPoint.y - this.state.originalPageY,\n };\n\n if (this.props.staticPinPosition) {\n // When we use a static pin position, the zoom centre is the same as that position,\n // otherwise the pin moves around way too much while zooming.\n zoomCenter = {\n x: this.props.staticPinPosition.x,\n y: this.props.staticPinPosition.y,\n };\n }\n\n // Uncomment to debug\n this.props.debug && this._setPinchDebugPoints(e, zoomCenter);\n\n const { originalHeight, originalWidth } = this.state;\n\n const oldOffsetX = this.offsetX;\n const oldOffsetY = this.offsetY;\n const oldScale = this.zoomLevel;\n const newScale = newZoomLevel;\n\n let offsetY = calcNewScaledOffsetForZoomCentering(\n oldOffsetY,\n originalHeight,\n oldScale,\n newScale,\n zoomCenter.y\n );\n let offsetX = calcNewScaledOffsetForZoomCentering(\n oldOffsetX,\n originalWidth,\n oldScale,\n newScale,\n zoomCenter.x\n );\n\n const offsetShift =\n this._calcOffsetShiftSinceLastGestureState(gestureCenterPoint);\n if (offsetShift) {\n offsetX += offsetShift.x;\n offsetY += offsetShift.y;\n }\n\n this.offsetX = offsetX;\n this.offsetY = offsetY;\n this.zoomLevel = newScale;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n\n this.props.onZoomAfter?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n }\n\n /**\n * Used to debug pinch events\n * @param gestureResponderEvent\n * @param zoomCenter\n * @param points\n */\n _setPinchDebugPoints(\n gestureResponderEvent: GestureResponderEvent,\n zoomCenter: Vec2D,\n ...points: Vec2D[]\n ) {\n const { touches } = gestureResponderEvent.nativeEvent;\n const { originalPageY, originalPageX } = this.state;\n this.setState({\n debugPoints: [\n {\n x: touches[0].pageX - originalPageX,\n y: touches[0].pageY - originalPageY,\n },\n {\n x: touches[1].pageX - originalPageX,\n y: touches[1].pageY - originalPageY,\n },\n zoomCenter,\n ...points,\n ],\n });\n }\n\n /**\n * Calculates the amount the offset should shift since the last position during panning\n *\n * @param {Vec2D} gestureCenterPoint\n *\n * @private\n */\n _calcOffsetShiftSinceLastGestureState(gestureCenterPoint: Vec2D) {\n const { movementSensibility } = this.props;\n\n let shift = null;\n\n if (this.lastGestureCenterPosition) {\n const dx = gestureCenterPoint.x - this.lastGestureCenterPosition.x;\n const dy = gestureCenterPoint.y - this.lastGestureCenterPosition.y;\n\n const shiftX = dx / this.zoomLevel / movementSensibility;\n const shiftY = dy / this.zoomLevel / movementSensibility;\n\n shift = {\n x: shiftX,\n y: shiftY,\n };\n }\n\n this.lastGestureCenterPosition = gestureCenterPoint;\n\n return shift;\n }\n\n /**\n * Handles movement by tap and move\n *\n * @param gestureState\n *\n * @private\n */\n _handleShifting(gestureState: PanResponderGestureState) {\n // Skips shifting if panEnabled is false or disablePanOnInitialZoom is true and we're on the initial zoom level\n if (\n !this.props.panEnabled ||\n (this.props.disablePanOnInitialZoom &&\n this.zoomLevel === this.props.initialZoom)\n ) {\n return;\n }\n const shift = this._calcOffsetShiftSinceLastGestureState({\n x: gestureState.moveX,\n y: gestureState.moveY,\n });\n if (!shift) return;\n\n const offsetX = this.offsetX + shift.x;\n const offsetY = this.offsetY + shift.y;\n\n if (this.props.debug) {\n const x = gestureState.moveX - this.state.originalPageX;\n const y = gestureState.moveY - this.state.originalPageY;\n this.setState({ debugPoints: [{ x, y }] });\n }\n\n this._setNewOffsetPosition(offsetX, offsetY);\n\n this.raisePin();\n }\n\n /**\n * Set the state to offset moved\n *\n * @param {number} newOffsetX\n * @param {number} newOffsetY\n * @returns\n */\n async _setNewOffsetPosition(newOffsetX: number, newOffsetY: number) {\n const { onShiftingBefore, onShiftingAfter } = this.props;\n\n if (onShiftingBefore?.(null, null, this._getZoomableViewEventObject())) {\n return;\n }\n\n this.offsetX = newOffsetX;\n this.offsetY = newOffsetY;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n\n onShiftingAfter?.(null, null, this._getZoomableViewEventObject());\n }\n\n /**\n * Check whether the press event is double tap\n * or single tap and handle the event accordingly\n *\n * @param e\n *\n * @private\n */\n private _resolveAndHandleTap = (e: GestureResponderEvent) => {\n const now = Date.now();\n if (\n this.doubleTapFirstTapReleaseTimestamp &&\n now - this.doubleTapFirstTapReleaseTimestamp < this.props.doubleTapDelay\n ) {\n this._addTouch({\n ...this.doubleTapFirstTap,\n id: now.toString(),\n isSecondTap: true,\n });\n clearTimeout(this.singleTapTimeoutId);\n delete this.doubleTapFirstTapReleaseTimestamp;\n delete this.singleTapTimeoutId;\n delete this.doubleTapFirstTap;\n this._handleDoubleTap(e);\n } else {\n this.doubleTapFirstTapReleaseTimestamp = now;\n this.doubleTapFirstTap = {\n id: now.toString(),\n x: e.nativeEvent.pageX - this.state.originalPageX,\n y: e.nativeEvent.pageY - this.state.originalPageY,\n };\n this._addTouch(this.doubleTapFirstTap);\n\n // persist event so e.nativeEvent is preserved after a timeout delay\n e.persist();\n this.singleTapTimeoutId = setTimeout(() => {\n delete this.doubleTapFirstTapReleaseTimestamp;\n delete this.singleTapTimeoutId;\n\n // Pan to the tapped location\n if (this.props.staticPinPosition && this.doubleTapFirstTap) {\n const tapX =\n this.props.staticPinPosition.x - this.doubleTapFirstTap.x;\n const tapY =\n this.props.staticPinPosition.y - this.doubleTapFirstTap.y;\n\n Animated.timing(this.panAnim, {\n toValue: {\n x: this.offsetX + tapX / this.zoomLevel,\n y: this.offsetY + tapY / this.zoomLevel,\n },\n useNativeDriver: true,\n duration: 200,\n }).start(() => {\n this._updateStaticPin();\n });\n }\n\n this.props.onSingleTap?.(e, this._getZoomableViewEventObject());\n }, this.props.doubleTapDelay);\n }\n };\n\n _moveTimeout: NodeJS.Timeout;\n moveStaticPinTo = (position: Vec2D) => {\n const { originalWidth, originalHeight } = this.state;\n const { staticPinPosition, contentWidth, contentHeight } = this.props;\n\n // Offset for the static pin\n const pinX = staticPinPosition?.x - originalWidth / 2;\n const pinY = staticPinPosition?.y - originalHeight / 2;\n\n this.offsetX = contentWidth / 2 - position.x + pinX / this.zoomLevel;\n this.offsetY = contentHeight / 2 - position.y + pinY / this.zoomLevel;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n };\n\n private _staticPinPosition = () => {\n return viewportPositionToImagePosition({\n viewportPosition: {\n x: this.props?.staticPinPosition?.x,\n y: this.props?.staticPinPosition?.y,\n },\n imageSize: {\n height: this.props.contentHeight,\n width: this.props.contentWidth,\n },\n zoomableEvent: {\n ...this._getZoomableViewEventObject(),\n offsetX: this.offsetX,\n offsetY: this.offsetY,\n zoomLevel: this.zoomLevel,\n },\n });\n };\n\n private _updateStaticPin = () => {\n this.props.onStaticPinPositionChange?.(this._staticPinPosition());\n };\n\n private _addTouch(touch: TouchPoint) {\n this.touches.push(touch);\n this.setState({ touches: [...this.touches] });\n }\n\n private _removeTouch(touch: TouchPoint) {\n this.touches.splice(this.touches.indexOf(touch), 1);\n this.setState({ touches: [...this.touches] });\n }\n\n /**\n * Handles the double tap event\n *\n * @param e\n *\n * @private\n */\n _handleDoubleTap(e: GestureResponderEvent) {\n const { onDoubleTapBefore, onDoubleTapAfter, doubleTapZoomToCenter } =\n this.props;\n\n onDoubleTapBefore?.(e, this._getZoomableViewEventObject());\n\n const nextZoomStep = this._getNextZoomStep();\n const { originalPageX, originalPageY } = this.state;\n\n // define new zoom position coordinates\n const zoomPositionCoordinates = {\n x: e.nativeEvent.pageX - originalPageX,\n y: e.nativeEvent.pageY - originalPageY,\n };\n\n // if doubleTapZoomToCenter enabled -> always zoom to center instead\n if (doubleTapZoomToCenter) {\n zoomPositionCoordinates.x = 0;\n zoomPositionCoordinates.y = 0;\n }\n\n this._zoomToLocation(\n zoomPositionCoordinates.x,\n zoomPositionCoordinates.y,\n nextZoomStep\n ).then(() => {\n onDoubleTapAfter?.(\n e,\n this._getZoomableViewEventObject({ zoomLevel: nextZoomStep })\n );\n });\n }\n\n /**\n * Returns the next zoom step based on current step and zoomStep property.\n * If we are zoomed all the way in -> return to initialzoom\n *\n * @returns {*}\n */\n _getNextZoomStep() {\n const { zoomStep, maxZoom, initialZoom } = this.props;\n const { zoomLevel } = this;\n\n if (zoomLevel.toFixed(2) === maxZoom.toFixed(2)) {\n return initialZoom;\n }\n\n const nextZoomStep = zoomLevel * (1 + zoomStep);\n if (nextZoomStep > maxZoom) {\n return maxZoom;\n }\n\n return nextZoomStep;\n }\n\n /**\n * Zooms to a specific location in our view\n *\n * @param x\n * @param y\n * @param newZoomLevel\n *\n * @private\n */\n async _zoomToLocation(x: number, y: number, newZoomLevel: number) {\n if (!this.props.zoomEnabled) return;\n\n this.props.onZoomBefore?.(null, null, this._getZoomableViewEventObject());\n\n // == Perform Zoom Animation ==\n // Calculates panAnim values based on changes in zoomAnim.\n let prevScale = this.zoomLevel;\n // Since zoomAnim is calculated in native driver,\n // it will jitter panAnim once in a while,\n // because here panAnim is being calculated in js.\n // However the jittering should mostly occur in simulator.\n const listenerId = this.zoomAnim.addListener(({ value: newScale }) => {\n this.panAnim.setValue({\n x: calcNewScaledOffsetForZoomCentering(\n this.offsetX,\n this.state.originalWidth,\n prevScale,\n newScale,\n x\n ),\n y: calcNewScaledOffsetForZoomCentering(\n this.offsetY,\n this.state.originalHeight,\n prevScale,\n newScale,\n y\n ),\n });\n prevScale = newScale;\n });\n getZoomToAnimation(this.zoomAnim, newZoomLevel).start(() => {\n this.zoomAnim.removeListener(listenerId);\n });\n // == Zoom Animation Ends ==\n\n this.props.onZoomAfter?.(null, null, this._getZoomableViewEventObject());\n }\n\n /**\n * Zooms to a specificied zoom level.\n * Returns a promise if everything was updated and a boolean, whether it could be updated or if it exceeded the min/max zoom limits.\n *\n * @param {number} newZoomLevel\n *\n * @return {Promise}\n */\n async zoomTo(newZoomLevel: number): Promise {\n if (\n // if we would go out of our min/max limits -> abort\n newZoomLevel > this.props.maxZoom ||\n newZoomLevel < this.props.minZoom\n )\n return false;\n\n await this._zoomToLocation(0, 0, newZoomLevel);\n return true;\n }\n\n /**\n * Zooms in or out by a specified change level\n * Use a positive number for `zoomLevelChange` to zoom in\n * Use a negative number for `zoomLevelChange` to zoom out\n *\n * Returns a promise if everything was updated and a boolean, whether it could be updated or if it exceeded the min/max zoom limits.\n *\n * @param {number | null} zoomLevelChange\n *\n * @return {Promise}\n */\n zoomBy(zoomLevelChange: number = null): Promise {\n // if no zoom level Change given -> just use zoom step\n if (!zoomLevelChange) {\n zoomLevelChange = this.props.zoomStep;\n }\n\n return this.zoomTo(this.zoomLevel + zoomLevelChange);\n }\n\n /**\n * Moves the zoomed view to a specified position\n * Returns a promise when finished\n *\n * @param {number} newOffsetX the new position we want to move it to (x-axis)\n * @param {number} newOffsetY the new position we want to move it to (y-axis)\n *\n * @return {Promise}\n */\n moveTo(newOffsetX: number, newOffsetY: number): Promise {\n const { originalWidth, originalHeight } = this.state;\n\n const offsetX = (newOffsetX - originalWidth / 2) / this.zoomLevel;\n const offsetY = (newOffsetY - originalHeight / 2) / this.zoomLevel;\n\n return this._setNewOffsetPosition(-offsetX, -offsetY);\n }\n\n /**\n * Moves the zoomed view by a certain amount.\n *\n * Returns a promise when finished\n *\n * @param {number} offsetChangeX the amount we want to move the offset by (x-axis)\n * @param {number} offsetChangeY the amount we want to move the offset by (y-axis)\n *\n * @return {Promise}\n */\n moveBy(offsetChangeX: number, offsetChangeY: number): Promise {\n const offsetX =\n (this.offsetX * this.zoomLevel - offsetChangeX) / this.zoomLevel;\n const offsetY =\n (this.offsetY * this.zoomLevel - offsetChangeY) / this.zoomLevel;\n\n return this._setNewOffsetPosition(offsetX, offsetY);\n }\n\n render() {\n const {\n staticPinIcon,\n children,\n visualTouchFeedbackEnabled,\n doubleTapDelay,\n staticPinPosition,\n onStaticPinLongPress,\n onStaticPinPress,\n pinProps,\n } = this.props;\n const { pinSize, touches, debugPoints = [] } = this.state;\n\n return (\n \n \n {children}\n \n\n {visualTouchFeedbackEnabled &&\n touches?.map((touch) => {\n const animationDuration = doubleTapDelay;\n return (\n this._removeTouch(touch)}\n />\n );\n })}\n\n {/* For Debugging Only */}\n {debugPoints.map(({ x, y }, index) => {\n return ;\n })}\n\n {staticPinPosition && (\n this.setState({ pinSize: size })}\n pinProps={pinProps}\n />\n )}\n \n );\n }\n}\n\nconst styles = StyleSheet.create({\n zoomSubject: {\n flex: 1,\n width: '100%',\n justifyContent: 'center',\n alignItems: 'center',\n },\n container: {\n flex: 1,\n justifyContent: 'center',\n alignItems: 'center',\n position: 'relative',\n overflow: 'hidden',\n },\n});\n\nexport default ReactNativeZoomableView;\n\nexport { ReactNativeZoomableView };\n"]} \ No newline at end of file diff --git a/lib/module/ReactNativeZoomableView.js b/lib/module/ReactNativeZoomableView.js index fd92c4e..5af962c 100644 --- a/lib/module/ReactNativeZoomableView.js +++ b/lib/module/ReactNativeZoomableView.js @@ -330,8 +330,8 @@ class ReactNativeZoomableView extends Component { contentHeight } = this.props; // Offset for the static pin - const pinX = staticPinPosition.x - originalWidth / 2; - const pinY = staticPinPosition.y - originalHeight / 2; + const pinX = (staticPinPosition === null || staticPinPosition === void 0 ? void 0 : staticPinPosition.x) - originalWidth / 2; + const pinY = (staticPinPosition === null || staticPinPosition === void 0 ? void 0 : staticPinPosition.y) - originalHeight / 2; this.offsetX = contentWidth / 2 - position.x + pinX / this.zoomLevel; this.offsetY = contentHeight / 2 - position.y + pinY / this.zoomLevel; this.panAnim.setValue({ @@ -341,10 +341,12 @@ class ReactNativeZoomableView extends Component { }); _defineProperty(this, "_staticPinPosition", () => { + var _this$props8, _this$props8$staticPi, _this$props9, _this$props9$staticPi; + return viewportPositionToImagePosition({ viewportPosition: { - x: this.props.staticPinPosition.x, - y: this.props.staticPinPosition.y + x: (_this$props8 = this.props) === null || _this$props8 === void 0 ? void 0 : (_this$props8$staticPi = _this$props8.staticPinPosition) === null || _this$props8$staticPi === void 0 ? void 0 : _this$props8$staticPi.x, + y: (_this$props9 = this.props) === null || _this$props9 === void 0 ? void 0 : (_this$props9$staticPi = _this$props9.staticPinPosition) === null || _this$props9$staticPi === void 0 ? void 0 : _this$props9$staticPi.y }, imageSize: { height: this.props.contentHeight, @@ -359,9 +361,9 @@ class ReactNativeZoomableView extends Component { }); _defineProperty(this, "_updateStaticPin", () => { - var _this$props$onStaticP2, _this$props8; + var _this$props$onStaticP2, _this$props10; - (_this$props$onStaticP2 = (_this$props8 = this.props).onStaticPinPositionChange) === null || _this$props$onStaticP2 === void 0 ? void 0 : _this$props$onStaticP2.call(_this$props8, this._staticPinPosition()); + (_this$props$onStaticP2 = (_this$props10 = this.props).onStaticPinPositionChange) === null || _this$props$onStaticP2 === void 0 ? void 0 : _this$props$onStaticP2.call(_this$props10, this._staticPinPosition()); }); this.gestureHandlers = PanResponder.create({ @@ -370,7 +372,7 @@ class ReactNativeZoomableView extends Component { onPanResponderMove: this._handlePanResponderMove, onPanResponderRelease: this._handlePanResponderEnd, onPanResponderTerminate: (evt, gestureState) => { - var _this$props$onPanResp3, _this$props9; + var _this$props$onPanResp3, _this$props11; // We should also call _handlePanResponderEnd // to properly perform cleanups when the gesture is terminated @@ -380,28 +382,28 @@ class ReactNativeZoomableView extends Component { // but onPanResponderTerminate is called instead for no apparent reason. this._handlePanResponderEnd(evt, gestureState); - (_this$props$onPanResp3 = (_this$props9 = this.props).onPanResponderTerminate) === null || _this$props$onPanResp3 === void 0 ? void 0 : _this$props$onPanResp3.call(_this$props9, evt, gestureState, this._getZoomableViewEventObject()); + (_this$props$onPanResp3 = (_this$props11 = this.props).onPanResponderTerminate) === null || _this$props$onPanResp3 === void 0 ? void 0 : _this$props$onPanResp3.call(_this$props11, evt, gestureState, this._getZoomableViewEventObject()); }, onPanResponderTerminationRequest: (evt, gestureState) => { - var _this$props$onPanResp4, _this$props10; + var _this$props$onPanResp4, _this$props12; - return !!((_this$props$onPanResp4 = (_this$props10 = this.props).onPanResponderTerminationRequest) !== null && _this$props$onPanResp4 !== void 0 && _this$props$onPanResp4.call(_this$props10, evt, gestureState, this._getZoomableViewEventObject())); + return !!((_this$props$onPanResp4 = (_this$props12 = this.props).onPanResponderTerminationRequest) !== null && _this$props$onPanResp4 !== void 0 && _this$props$onPanResp4.call(_this$props12, evt, gestureState, this._getZoomableViewEventObject())); }, // Defaults to true to prevent parent components, such as React Navigation's tab view, from taking over as responder. onShouldBlockNativeResponder: (evt, gestureState) => { - var _this$props$onShouldB, _this$props$onShouldB2, _this$props11; + var _this$props$onShouldB, _this$props$onShouldB2, _this$props13; - return (_this$props$onShouldB = (_this$props$onShouldB2 = (_this$props11 = this.props).onShouldBlockNativeResponder) === null || _this$props$onShouldB2 === void 0 ? void 0 : _this$props$onShouldB2.call(_this$props11, evt, gestureState, this._getZoomableViewEventObject())) !== null && _this$props$onShouldB !== void 0 ? _this$props$onShouldB : true; + return (_this$props$onShouldB = (_this$props$onShouldB2 = (_this$props13 = this.props).onShouldBlockNativeResponder) === null || _this$props$onShouldB2 === void 0 ? void 0 : _this$props$onShouldB2.call(_this$props13, evt, gestureState, this._getZoomableViewEventObject())) !== null && _this$props$onShouldB !== void 0 ? _this$props$onShouldB : true; }, onStartShouldSetPanResponderCapture: (evt, gestureState) => { - var _this$props$onStartSh, _this$props12; + var _this$props$onStartSh, _this$props14; - return (_this$props$onStartSh = (_this$props12 = this.props).onStartShouldSetPanResponderCapture) === null || _this$props$onStartSh === void 0 ? void 0 : _this$props$onStartSh.call(_this$props12, evt, gestureState); + return (_this$props$onStartSh = (_this$props14 = this.props).onStartShouldSetPanResponderCapture) === null || _this$props$onStartSh === void 0 ? void 0 : _this$props$onStartSh.call(_this$props14, evt, gestureState); }, onMoveShouldSetPanResponderCapture: (evt, gestureState) => { - var _this$props$onMoveSho, _this$props13; + var _this$props$onMoveSho, _this$props15; - return (_this$props$onMoveSho = (_this$props13 = this.props).onMoveShouldSetPanResponderCapture) === null || _this$props$onMoveSho === void 0 ? void 0 : _this$props$onMoveSho.call(_this$props13, evt, gestureState); + return (_this$props$onMoveSho = (_this$props15 = this.props).onMoveShouldSetPanResponderCapture) === null || _this$props$onMoveSho === void 0 ? void 0 : _this$props$onMoveSho.call(_this$props15, evt, gestureState); } }); this.zoomSubjectWrapperRef = /*#__PURE__*/createRef(); @@ -557,15 +559,15 @@ class ReactNativeZoomableView extends Component { * @private */ _invokeOnTransform() { - var _this$props$onTransfo, _this$props14, _this$props$onStaticP3, _this$props15; + var _this$props$onTransfo, _this$props16, _this$props$onStaticP3, _this$props17; const zoomableViewEvent = this._getZoomableViewEventObject(); if (!zoomableViewEvent.originalWidth || !zoomableViewEvent.originalHeight) return { successful: false }; - (_this$props$onTransfo = (_this$props14 = this.props).onTransform) === null || _this$props$onTransfo === void 0 ? void 0 : _this$props$onTransfo.call(_this$props14, zoomableViewEvent); - (_this$props$onStaticP3 = (_this$props15 = this.props).onStaticPinPositionMove) === null || _this$props$onStaticP3 === void 0 ? void 0 : _this$props$onStaticP3.call(_this$props15, this._staticPinPosition()); + (_this$props$onTransfo = (_this$props16 = this.props).onTransform) === null || _this$props$onTransfo === void 0 ? void 0 : _this$props$onTransfo.call(_this$props16, zoomableViewEvent); + (_this$props$onStaticP3 = (_this$props17 = this.props).onStaticPinPositionMove) === null || _this$props$onStaticP3 === void 0 ? void 0 : _this$props$onStaticP3.call(_this$props17, this._staticPinPosition()); this.debouncedOnStaticPinPositionChange(this._staticPinPosition()); return { successful: true @@ -608,7 +610,7 @@ class ReactNativeZoomableView extends Component { * @private */ _handlePinching(e, gestureState) { - var _this$props$onZoomAft, _this$props16; + var _this$props$onZoomAft, _this$props18; if (!this.props.zoomEnabled) return; const { @@ -685,7 +687,7 @@ class ReactNativeZoomableView extends Component { y: this.offsetY }); this.zoomAnim.setValue(this.zoomLevel); - (_this$props$onZoomAft = (_this$props16 = this.props).onZoomAfter) === null || _this$props$onZoomAft === void 0 ? void 0 : _this$props$onZoomAft.call(_this$props16, e, gestureState, this._getZoomableViewEventObject()); + (_this$props$onZoomAft = (_this$props18 = this.props).onZoomAfter) === null || _this$props$onZoomAft === void 0 ? void 0 : _this$props$onZoomAft.call(_this$props18, e, gestureState, this._getZoomableViewEventObject()); } /** * Used to debug pinch events @@ -914,10 +916,10 @@ class ReactNativeZoomableView extends Component { async _zoomToLocation(x, y, newZoomLevel) { - var _this$props$onZoomBef, _this$props17, _this$props$onZoomAft2, _this$props18; + var _this$props$onZoomBef, _this$props19, _this$props$onZoomAft2, _this$props20; if (!this.props.zoomEnabled) return; - (_this$props$onZoomBef = (_this$props17 = this.props).onZoomBefore) === null || _this$props$onZoomBef === void 0 ? void 0 : _this$props$onZoomBef.call(_this$props17, null, null, this._getZoomableViewEventObject()); // == Perform Zoom Animation == + (_this$props$onZoomBef = (_this$props19 = this.props).onZoomBefore) === null || _this$props$onZoomBef === void 0 ? void 0 : _this$props$onZoomBef.call(_this$props19, null, null, this._getZoomableViewEventObject()); // == Perform Zoom Animation == // Calculates panAnim values based on changes in zoomAnim. let prevScale = this.zoomLevel; // Since zoomAnim is calculated in native driver, @@ -938,7 +940,7 @@ class ReactNativeZoomableView extends Component { this.zoomAnim.removeListener(listenerId); }); // == Zoom Animation Ends == - (_this$props$onZoomAft2 = (_this$props18 = this.props).onZoomAfter) === null || _this$props$onZoomAft2 === void 0 ? void 0 : _this$props$onZoomAft2.call(_this$props18, null, null, this._getZoomableViewEventObject()); + (_this$props$onZoomAft2 = (_this$props20 = this.props).onZoomAfter) === null || _this$props$onZoomAft2 === void 0 ? void 0 : _this$props$onZoomAft2.call(_this$props20, null, null, this._getZoomableViewEventObject()); } /** * Zooms to a specificied zoom level. diff --git a/lib/module/ReactNativeZoomableView.js.map b/lib/module/ReactNativeZoomableView.js.map index dbca6f0..4f7ccd1 100644 --- a/lib/module/ReactNativeZoomableView.js.map +++ b/lib/module/ReactNativeZoomableView.js.map @@ -1 +1 @@ -{"version":3,"sources":["ReactNativeZoomableView.tsx"],"names":["React","Component","createRef","Animated","Easing","PanResponder","StyleSheet","View","AnimatedTouchFeedback","DebugTouchPoint","calcGestureCenterPoint","calcGestureTouchDistance","calcNewScaledOffsetForZoomCentering","applyPanBoundariesToOffset","viewportPositionToImagePosition","StaticPin","debounce","getBoundaryCrossedAnim","getPanMomentumDecayAnim","getZoomToAnimation","initialState","originalWidth","originalHeight","originalPageX","originalPageY","pinSize","width","height","ReactNativeZoomableView","gestureStarted","v","_gestureStarted","constructor","props","ValueXY","x","y","Value","value","boundaryCrossedAnimInEffect","position","onStaticPinPositionChange","requestAnimationFrame","setTimeout","zoomSubjectWrapperRef","current","measureInWindow","setState","e","gestureState","onStartShouldSetPanResponder","_getZoomableViewEventObject","onLongPress","longPressTimeout","longPressDuration","onPanResponderGrant","panAnim","stopAnimation","zoomAnim","raisePin","gestureType","_resolveAndHandleTap","debugPoints","lastGestureCenterPosition","disableMomentum","panEnabled","disablePanOnInitialZoom","zoomLevel","initialZoom","vx","vy","start","clearTimeout","onPanResponderEnd","onZoomEnd","onShiftingEnd","staticPinPosition","_updateStaticPin","dropPin","onPanResponderMove","numberActiveTouches","_handlePanResponderGrant","_handlePanResponderEnd","lastGestureTouchDistance","_handlePinching","Math","abs","dx","dy","isShiftGesture","_handleShifting","now","Date","doubleTapFirstTapReleaseTimestamp","doubleTapDelay","_addTouch","doubleTapFirstTap","id","toString","isSecondTap","singleTapTimeoutId","_handleDoubleTap","nativeEvent","pageX","state","pageY","persist","tapX","tapY","timing","toValue","offsetX","offsetY","useNativeDriver","duration","onSingleTap","contentWidth","contentHeight","pinX","pinY","setValue","viewportPosition","imageSize","zoomableEvent","_staticPinPosition","gestureHandlers","create","_handleStartShouldSetPanResponder","_handlePanResponderMove","onPanResponderRelease","onPanResponderTerminate","evt","onPanResponderTerminationRequest","onShouldBlockNativeResponder","onStartShouldSetPanResponderCapture","onMoveShouldSetPanResponderCapture","zoomAnimatedValue","panAnimatedValueXY","initialOffsetX","initialOffsetY","addListener","animatePin","pinAnim","easing","out","ease","__setOffset","__getOffset","axis","offset","offsetState","__offsets","animValue","bindToBorders","containerSize","contentSize","boundOffset","panBoundaryPadding","boundariesApplied","toFixed","componentDidUpdate","prevProps","prevState","zoomEnabled","onTransformInvocationInitialized","_invokeOnTransform","successful","currState","originalMeasurementsChanged","staticPinPositionChanged","componentDidMount","grabZoomSubjectOriginalMeasurements","measureZoomSubjectInterval","setInterval","componentWillUnmount","clearInterval","zoomableViewEvent","onTransform","onStaticPinPositionMove","debouncedOnStaticPinPositionChange","overwriteObj","maxZoom","minZoom","pinchToZoomInSensitivity","pinchToZoomOutSensitivity","distance","onZoomBefore","zoomGrowthFromLastGestureState","pinchToZoomSensitivity","deltaGrowth","deltaGrowthAdjustedBySensitivity","newZoomLevel","gestureCenterPoint","zoomCenter","debug","_setPinchDebugPoints","oldOffsetX","oldOffsetY","oldScale","newScale","offsetShift","_calcOffsetShiftSinceLastGestureState","onZoomAfter","gestureResponderEvent","points","touches","movementSensibility","shift","shiftX","shiftY","moveX","moveY","_setNewOffsetPosition","newOffsetX","newOffsetY","onShiftingBefore","onShiftingAfter","touch","push","_removeTouch","splice","indexOf","onDoubleTapBefore","onDoubleTapAfter","doubleTapZoomToCenter","nextZoomStep","_getNextZoomStep","zoomPositionCoordinates","_zoomToLocation","then","zoomStep","prevScale","listenerId","removeListener","zoomTo","zoomBy","zoomLevelChange","moveTo","moveBy","offsetChangeX","offsetChangeY","render","staticPinIcon","children","visualTouchFeedbackEnabled","onStaticPinLongPress","onStaticPinPress","pinProps","styles","container","panHandlers","zoomSubject","style","transform","scale","getTranslateTransform","map","animationDuration","index","size","undefined","flex","justifyContent","alignItems","overflow"],"mappings":"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","sourcesContent":["import React, { Component, createRef, RefObject } from 'react';\nimport {\n Animated,\n Easing,\n GestureResponderEvent,\n PanResponder,\n PanResponderGestureState,\n StyleSheet,\n View,\n} from 'react-native';\n\nimport {\n Vec2D,\n ReactNativeZoomableViewProps,\n ReactNativeZoomableViewState,\n TouchPoint,\n ZoomableViewEvent,\n Size2D,\n} from './typings';\n\nimport { AnimatedTouchFeedback } from './components';\nimport { DebugTouchPoint } from './debugHelper';\nimport {\n calcGestureCenterPoint,\n calcGestureTouchDistance,\n calcNewScaledOffsetForZoomCentering,\n} from './helper';\nimport { applyPanBoundariesToOffset } from './helper/applyPanBoundariesToOffset';\nimport { viewportPositionToImagePosition } from './helper/coordinateConversion';\nimport { StaticPin } from './components/StaticPin';\nimport { debounce } from 'lodash';\nimport {\n getBoundaryCrossedAnim,\n getPanMomentumDecayAnim,\n getZoomToAnimation,\n} from './animations';\n\nconst initialState = {\n originalWidth: null,\n originalHeight: null,\n originalPageX: null,\n originalPageY: null,\n pinSize: { width: 0, height: 0 },\n} as ReactNativeZoomableViewState;\n\nclass ReactNativeZoomableView extends Component<\n ReactNativeZoomableViewProps,\n ReactNativeZoomableViewState\n> {\n zoomSubjectWrapperRef: RefObject;\n gestureHandlers: any;\n doubleTapFirstTapReleaseTimestamp: number;\n\n static defaultProps = {\n zoomEnabled: true,\n panEnabled: true,\n initialZoom: 1,\n initialOffsetX: 0,\n initialOffsetY: 0,\n maxZoom: 1.5,\n minZoom: 0.5,\n pinchToZoomInSensitivity: 1,\n pinchToZoomOutSensitivity: 1,\n movementSensibility: 1,\n doubleTapDelay: 300,\n bindToBorders: true,\n zoomStep: 0.5,\n onLongPress: null,\n longPressDuration: 700,\n contentWidth: undefined,\n contentHeight: undefined,\n panBoundaryPadding: 0,\n visualTouchFeedbackEnabled: true,\n staticPinPosition: undefined,\n staticPinIcon: undefined,\n onStaticPinPositionChange: undefined,\n onStaticPinPositionMove: undefined,\n animatePin: true,\n disablePanOnInitialZoom: false,\n };\n\n private panAnim = new Animated.ValueXY({ x: 0, y: 0 });\n private zoomAnim = new Animated.Value(1);\n private pinAnim = new Animated.ValueXY({ x: 0, y: 0 });\n\n private __offsets = {\n x: {\n value: 0,\n boundaryCrossedAnimInEffect: false,\n },\n y: {\n value: 0,\n boundaryCrossedAnimInEffect: false,\n },\n };\n\n private zoomLevel = 1;\n private lastGestureCenterPosition: { x: number; y: number } = null;\n private lastGestureTouchDistance: number;\n private gestureType: 'pinch' | 'shift' | 'null';\n\n private _gestureStarted = false;\n private set gestureStarted(v: boolean) {\n this._gestureStarted = v;\n }\n public get gestureStarted() {\n return this._gestureStarted;\n }\n\n /**\n * Last press time (used to evaluate whether user double tapped)\n * @type {number}\n */\n private longPressTimeout: NodeJS.Timeout = null;\n private onTransformInvocationInitialized: boolean;\n private singleTapTimeoutId: NodeJS.Timeout;\n private touches: TouchPoint[] = [];\n private doubleTapFirstTap: TouchPoint;\n private measureZoomSubjectInterval: NodeJS.Timer;\n\n constructor(props) {\n super(props);\n\n this.gestureHandlers = PanResponder.create({\n onStartShouldSetPanResponder: this._handleStartShouldSetPanResponder,\n onPanResponderGrant: this._handlePanResponderGrant,\n onPanResponderMove: this._handlePanResponderMove,\n onPanResponderRelease: this._handlePanResponderEnd,\n onPanResponderTerminate: (evt, gestureState) => {\n // We should also call _handlePanResponderEnd\n // to properly perform cleanups when the gesture is terminated\n // (aka gesture handling responsibility is taken over by another component).\n // This also fixes a weird issue where\n // on real device, sometimes onPanResponderRelease is not called when you lift 2 fingers up,\n // but onPanResponderTerminate is called instead for no apparent reason.\n this._handlePanResponderEnd(evt, gestureState);\n this.props.onPanResponderTerminate?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n );\n },\n onPanResponderTerminationRequest: (evt, gestureState) =>\n !!this.props.onPanResponderTerminationRequest?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n ),\n // Defaults to true to prevent parent components, such as React Navigation's tab view, from taking over as responder.\n onShouldBlockNativeResponder: (evt, gestureState) =>\n this.props.onShouldBlockNativeResponder?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n ) ?? true,\n onStartShouldSetPanResponderCapture: (evt, gestureState) =>\n this.props.onStartShouldSetPanResponderCapture?.(evt, gestureState),\n onMoveShouldSetPanResponderCapture: (evt, gestureState) =>\n this.props.onMoveShouldSetPanResponderCapture?.(evt, gestureState),\n });\n\n this.zoomSubjectWrapperRef = createRef();\n\n if (this.props.zoomAnimatedValue)\n this.zoomAnim = this.props.zoomAnimatedValue;\n if (this.props.panAnimatedValueXY)\n this.panAnim = this.props.panAnimatedValueXY;\n\n this.zoomLevel = props.initialZoom;\n this.offsetX = props.initialOffsetX;\n this.offsetY = props.initialOffsetY;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n this.panAnim.addListener(({ x, y }) => {\n this.offsetX = x;\n this.offsetY = y;\n });\n this.zoomAnim.addListener(({ value }) => {\n this.zoomLevel = value;\n });\n\n this.state = {\n ...initialState,\n };\n\n this.lastGestureTouchDistance = 150;\n\n this.gestureType = null;\n }\n\n private raisePin() {\n if (!this.props.animatePin) return;\n Animated.timing(this.pinAnim, {\n toValue: { x: 0, y: -10 },\n useNativeDriver: true,\n easing: Easing.out(Easing.ease),\n duration: 100,\n }).start();\n }\n\n private dropPin() {\n if (!this.props.animatePin) return;\n Animated.timing(this.pinAnim, {\n toValue: { x: 0, y: 0 },\n useNativeDriver: true,\n easing: Easing.out(Easing.ease),\n duration: 100,\n }).start();\n }\n\n private set offsetX(x: number) {\n this.__setOffset('x', x);\n }\n private set offsetY(y: number) {\n this.__setOffset('y', y);\n }\n private get offsetX() {\n return this.__getOffset('x');\n }\n private get offsetY() {\n return this.__getOffset('y');\n }\n private __setOffset(axis: 'x' | 'y', offset) {\n const offsetState = this.__offsets[axis];\n const animValue = this.panAnim?.[axis];\n\n if (this.props.bindToBorders) {\n const containerSize =\n axis === 'x' ? this.state?.originalWidth : this.state?.originalHeight;\n const contentSize =\n axis === 'x'\n ? this.props.contentWidth || this.state?.originalWidth\n : this.props.contentHeight || this.state?.originalHeight;\n\n const boundOffset =\n contentSize && containerSize\n ? applyPanBoundariesToOffset(\n offset,\n containerSize,\n contentSize,\n this.zoomLevel,\n this.props.panBoundaryPadding\n )\n : offset;\n\n if (\n animValue &&\n !this.gestureType &&\n !offsetState.boundaryCrossedAnimInEffect\n ) {\n const boundariesApplied =\n boundOffset !== offset &&\n boundOffset.toFixed(3) !== offset.toFixed(3);\n if (boundariesApplied) {\n offsetState.boundaryCrossedAnimInEffect = true;\n getBoundaryCrossedAnim(this.panAnim[axis], boundOffset).start(() => {\n offsetState.boundaryCrossedAnimInEffect = false;\n });\n return;\n }\n }\n }\n\n offsetState.value = offset;\n }\n private __getOffset(axis: 'x' | 'y') {\n return this.__offsets[axis].value;\n }\n\n componentDidUpdate(\n prevProps: ReactNativeZoomableViewProps,\n prevState: ReactNativeZoomableViewState\n ) {\n const { zoomEnabled, initialZoom } = this.props;\n if (prevProps.zoomEnabled && !zoomEnabled) {\n this.zoomLevel = initialZoom;\n this.zoomAnim.setValue(this.zoomLevel);\n }\n if (\n !this.onTransformInvocationInitialized &&\n this._invokeOnTransform().successful\n ) {\n this.panAnim.addListener(() => this._invokeOnTransform());\n this.zoomAnim.addListener(() => this._invokeOnTransform());\n this.onTransformInvocationInitialized = true;\n }\n\n const currState = this.state;\n const originalMeasurementsChanged =\n currState.originalHeight !== prevState.originalHeight ||\n currState.originalWidth !== prevState.originalWidth ||\n currState.originalPageX !== prevState.originalPageX ||\n currState.originalPageY !== prevState.originalPageY;\n\n const staticPinPositionChanged =\n prevProps.staticPinPosition?.x !== this.props.staticPinPosition?.x ||\n prevProps.staticPinPosition?.y !== this.props.staticPinPosition?.y;\n\n if (\n this.onTransformInvocationInitialized &&\n (originalMeasurementsChanged || staticPinPositionChanged)\n ) {\n this._invokeOnTransform();\n }\n }\n\n componentDidMount() {\n this.grabZoomSubjectOriginalMeasurements();\n // We've already run `grabZoomSubjectOriginalMeasurements` at various events\n // to make sure the measurements are promptly updated.\n // However, there might be cases we haven't accounted for, especially when\n // native processes are involved. To account for those cases,\n // we'll use an interval here to ensure we're always up-to-date.\n // The `setState` in `grabZoomSubjectOriginalMeasurements` won't trigger a rerender\n // if the values given haven't changed, so we're not running performance risk here.\n this.measureZoomSubjectInterval = setInterval(\n this.grabZoomSubjectOriginalMeasurements,\n 1e3\n );\n }\n\n componentWillUnmount() {\n clearInterval(this.measureZoomSubjectInterval);\n }\n\n debouncedOnStaticPinPositionChange = debounce(\n (position: Vec2D) => this.props.onStaticPinPositionChange?.(position),\n 100\n );\n\n /**\n * try to invoke onTransform\n * @private\n */\n _invokeOnTransform() {\n const zoomableViewEvent = this._getZoomableViewEventObject();\n\n if (!zoomableViewEvent.originalWidth || !zoomableViewEvent.originalHeight)\n return { successful: false };\n\n this.props.onTransform?.(zoomableViewEvent);\n\n this.props.onStaticPinPositionMove?.(this._staticPinPosition());\n\n this.debouncedOnStaticPinPositionChange(this._staticPinPosition());\n\n return { successful: true };\n }\n\n /**\n * Returns additional information about components current state for external event hooks\n *\n * @returns {{}}\n * @private\n */\n _getZoomableViewEventObject(overwriteObj = {}): ZoomableViewEvent {\n return {\n zoomLevel: this.zoomLevel,\n offsetX: this.offsetX,\n offsetY: this.offsetY,\n originalHeight: this.state.originalHeight,\n originalWidth: this.state.originalWidth,\n originalPageX: this.state.originalPageX,\n originalPageY: this.state.originalPageY,\n ...overwriteObj,\n } as ZoomableViewEvent;\n }\n\n /**\n * Get the original box dimensions and save them for later use.\n * (They will be used to calculate boxBorders)\n *\n * @private\n */\n private grabZoomSubjectOriginalMeasurements = () => {\n // make sure we measure after animations are complete\n requestAnimationFrame(() => {\n // this setTimeout is here to fix a weird issue on iOS where the measurements are all `0`\n // when navigating back (react-navigation stack) from another view\n // while closing the keyboard at the same time\n setTimeout(() => {\n // In normal conditions, we're supposed to measure zoomSubject instead of its wrapper.\n // However, our zoomSubject may have been transformed by an initial zoomLevel or offset,\n // in which case these measurements will not represent the true \"original\" measurements.\n // We just need to make sure the zoomSubjectWrapper perfectly aligns with the zoomSubject\n // (no border, space, or anything between them)\n const zoomSubjectWrapperRef = this.zoomSubjectWrapperRef;\n // we don't wanna measure when zoomSubjectWrapperRef is not yet available or has been unmounted\n zoomSubjectWrapperRef.current?.measureInWindow(\n (x, y, width, height) => {\n this.setState({\n originalWidth: width,\n originalHeight: height,\n originalPageX: x,\n originalPageY: y,\n });\n }\n );\n });\n });\n };\n\n /**\n * Handles the start of touch events and checks for taps\n *\n * @param e\n * @param gestureState\n * @returns {boolean}\n *\n * @private\n */\n _handleStartShouldSetPanResponder = (\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) => {\n if (this.props.onStartShouldSetPanResponder) {\n this.props.onStartShouldSetPanResponder(\n e,\n gestureState,\n this._getZoomableViewEventObject(),\n false\n );\n }\n\n // Always set pan responder on start\n // of gesture so we can handle tap.\n // \"Pan threshold validation\" will be handled\n // in `onPanResponderMove` instead of in `onMoveShouldSetPanResponder`\n return true;\n };\n\n /**\n * Calculates pinch distance\n *\n * @param e\n * @param gestureState\n * @private\n */\n _handlePanResponderGrant = (e, gestureState) => {\n if (this.props.onLongPress) {\n this.longPressTimeout = setTimeout(() => {\n this.props.onLongPress?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n this.longPressTimeout = null;\n }, this.props.longPressDuration);\n }\n\n this.props.onPanResponderGrant?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n\n this.panAnim.stopAnimation();\n this.zoomAnim.stopAnimation();\n this.gestureStarted = true;\n\n this.raisePin();\n };\n\n /**\n * Handles the end of touch events\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePanResponderEnd = (e, gestureState) => {\n if (!this.gestureType) {\n this._resolveAndHandleTap(e);\n }\n\n this.setState({ debugPoints: [] });\n\n this.lastGestureCenterPosition = null;\n\n const disableMomentum =\n this.props.disableMomentum ||\n (this.props.panEnabled &&\n this.gestureType === 'shift' &&\n this.props.disablePanOnInitialZoom &&\n this.zoomLevel === this.props.initialZoom);\n\n // Trigger final shift animation unless disablePanOnInitialZoom is set and we're on the initial zoom level\n // or disableMomentum\n if (!disableMomentum) {\n getPanMomentumDecayAnim(this.panAnim, {\n x: gestureState.vx / this.zoomLevel,\n y: gestureState.vy / this.zoomLevel,\n }).start();\n }\n\n if (this.longPressTimeout) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n\n this.props.onPanResponderEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n\n if (this.gestureType === 'pinch') {\n this.props.onZoomEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n } else if (this.gestureType === 'shift') {\n this.props.onShiftingEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n }\n\n if (this.props.staticPinPosition) {\n this._updateStaticPin();\n }\n\n this.dropPin();\n\n this.gestureType = null;\n this.gestureStarted = false;\n };\n\n /**\n * Handles the actual movement of our pan responder\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePanResponderMove = (\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) => {\n if (this.props.onPanResponderMove) {\n if (\n this.props.onPanResponderMove(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n )\n ) {\n return false;\n }\n }\n\n // Only supports 2 touches and below,\n // any invalid number will cause the gesture to end.\n if (gestureState.numberActiveTouches <= 2) {\n if (!this.gestureStarted) {\n this._handlePanResponderGrant(e, gestureState);\n }\n } else {\n if (this.gestureStarted) {\n this._handlePanResponderEnd(e, gestureState);\n }\n return true;\n }\n\n if (gestureState.numberActiveTouches === 2) {\n if (this.longPressTimeout) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n\n // change some measurement states when switching gesture to ensure a smooth transition\n if (this.gestureType !== 'pinch') {\n this.lastGestureCenterPosition = calcGestureCenterPoint(\n e,\n gestureState\n );\n this.lastGestureTouchDistance = calcGestureTouchDistance(\n e,\n gestureState\n );\n }\n this.gestureType = 'pinch';\n this._handlePinching(e, gestureState);\n } else if (gestureState.numberActiveTouches === 1) {\n if (\n this.longPressTimeout &&\n (Math.abs(gestureState.dx) > 5 || Math.abs(gestureState.dy) > 5)\n ) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n // change some measurement states when switching gesture to ensure a smooth transition\n if (this.gestureType !== 'shift') {\n this.lastGestureCenterPosition = calcGestureCenterPoint(\n e,\n gestureState\n );\n }\n\n const { dx, dy } = gestureState;\n const isShiftGesture = Math.abs(dx) > 2 || Math.abs(dy) > 2;\n if (isShiftGesture) {\n this.gestureType = 'shift';\n this._handleShifting(gestureState);\n }\n }\n };\n\n /**\n * Handles the pinch movement and zooming\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePinching(\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) {\n if (!this.props.zoomEnabled) return;\n\n const {\n maxZoom,\n minZoom,\n pinchToZoomInSensitivity,\n pinchToZoomOutSensitivity,\n } = this.props;\n\n const distance = calcGestureTouchDistance(e, gestureState);\n\n if (\n this.props.onZoomBefore &&\n this.props.onZoomBefore(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n )\n ) {\n return;\n }\n\n // define the new zoom level and take zoom level sensitivity into consideration\n const zoomGrowthFromLastGestureState =\n distance / this.lastGestureTouchDistance;\n this.lastGestureTouchDistance = distance;\n\n const pinchToZoomSensitivity =\n zoomGrowthFromLastGestureState < 1\n ? pinchToZoomOutSensitivity\n : pinchToZoomInSensitivity;\n\n const deltaGrowth = zoomGrowthFromLastGestureState - 1;\n // 0 - no resistance\n // 10 - 90% resistance\n const deltaGrowthAdjustedBySensitivity =\n deltaGrowth * (1 - (pinchToZoomSensitivity * 9) / 100);\n\n let newZoomLevel = this.zoomLevel * (1 + deltaGrowthAdjustedBySensitivity);\n\n // make sure max and min zoom levels are respected\n if (maxZoom !== null && newZoomLevel > maxZoom) {\n newZoomLevel = maxZoom;\n }\n\n if (newZoomLevel < minZoom) {\n newZoomLevel = minZoom;\n }\n\n const gestureCenterPoint = calcGestureCenterPoint(e, gestureState);\n\n if (!gestureCenterPoint) return;\n\n let zoomCenter = {\n x: gestureCenterPoint.x - this.state.originalPageX,\n y: gestureCenterPoint.y - this.state.originalPageY,\n };\n\n if (this.props.staticPinPosition) {\n // When we use a static pin position, the zoom centre is the same as that position,\n // otherwise the pin moves around way too much while zooming.\n zoomCenter = {\n x: this.props.staticPinPosition.x,\n y: this.props.staticPinPosition.y,\n };\n }\n\n // Uncomment to debug\n this.props.debug && this._setPinchDebugPoints(e, zoomCenter);\n\n const { originalHeight, originalWidth } = this.state;\n\n const oldOffsetX = this.offsetX;\n const oldOffsetY = this.offsetY;\n const oldScale = this.zoomLevel;\n const newScale = newZoomLevel;\n\n let offsetY = calcNewScaledOffsetForZoomCentering(\n oldOffsetY,\n originalHeight,\n oldScale,\n newScale,\n zoomCenter.y\n );\n let offsetX = calcNewScaledOffsetForZoomCentering(\n oldOffsetX,\n originalWidth,\n oldScale,\n newScale,\n zoomCenter.x\n );\n\n const offsetShift =\n this._calcOffsetShiftSinceLastGestureState(gestureCenterPoint);\n if (offsetShift) {\n offsetX += offsetShift.x;\n offsetY += offsetShift.y;\n }\n\n this.offsetX = offsetX;\n this.offsetY = offsetY;\n this.zoomLevel = newScale;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n\n this.props.onZoomAfter?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n }\n\n /**\n * Used to debug pinch events\n * @param gestureResponderEvent\n * @param zoomCenter\n * @param points\n */\n _setPinchDebugPoints(\n gestureResponderEvent: GestureResponderEvent,\n zoomCenter: Vec2D,\n ...points: Vec2D[]\n ) {\n const { touches } = gestureResponderEvent.nativeEvent;\n const { originalPageY, originalPageX } = this.state;\n this.setState({\n debugPoints: [\n {\n x: touches[0].pageX - originalPageX,\n y: touches[0].pageY - originalPageY,\n },\n {\n x: touches[1].pageX - originalPageX,\n y: touches[1].pageY - originalPageY,\n },\n zoomCenter,\n ...points,\n ],\n });\n }\n\n /**\n * Calculates the amount the offset should shift since the last position during panning\n *\n * @param {Vec2D} gestureCenterPoint\n *\n * @private\n */\n _calcOffsetShiftSinceLastGestureState(gestureCenterPoint: Vec2D) {\n const { movementSensibility } = this.props;\n\n let shift = null;\n\n if (this.lastGestureCenterPosition) {\n const dx = gestureCenterPoint.x - this.lastGestureCenterPosition.x;\n const dy = gestureCenterPoint.y - this.lastGestureCenterPosition.y;\n\n const shiftX = dx / this.zoomLevel / movementSensibility;\n const shiftY = dy / this.zoomLevel / movementSensibility;\n\n shift = {\n x: shiftX,\n y: shiftY,\n };\n }\n\n this.lastGestureCenterPosition = gestureCenterPoint;\n\n return shift;\n }\n\n /**\n * Handles movement by tap and move\n *\n * @param gestureState\n *\n * @private\n */\n _handleShifting(gestureState: PanResponderGestureState) {\n // Skips shifting if panEnabled is false or disablePanOnInitialZoom is true and we're on the initial zoom level\n if (\n !this.props.panEnabled ||\n (this.props.disablePanOnInitialZoom &&\n this.zoomLevel === this.props.initialZoom)\n ) {\n return;\n }\n const shift = this._calcOffsetShiftSinceLastGestureState({\n x: gestureState.moveX,\n y: gestureState.moveY,\n });\n if (!shift) return;\n\n const offsetX = this.offsetX + shift.x;\n const offsetY = this.offsetY + shift.y;\n\n if (this.props.debug) {\n const x = gestureState.moveX - this.state.originalPageX;\n const y = gestureState.moveY - this.state.originalPageY;\n this.setState({ debugPoints: [{ x, y }] });\n }\n\n this._setNewOffsetPosition(offsetX, offsetY);\n\n this.raisePin();\n }\n\n /**\n * Set the state to offset moved\n *\n * @param {number} newOffsetX\n * @param {number} newOffsetY\n * @returns\n */\n async _setNewOffsetPosition(newOffsetX: number, newOffsetY: number) {\n const { onShiftingBefore, onShiftingAfter } = this.props;\n\n if (onShiftingBefore?.(null, null, this._getZoomableViewEventObject())) {\n return;\n }\n\n this.offsetX = newOffsetX;\n this.offsetY = newOffsetY;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n\n onShiftingAfter?.(null, null, this._getZoomableViewEventObject());\n }\n\n /**\n * Check whether the press event is double tap\n * or single tap and handle the event accordingly\n *\n * @param e\n *\n * @private\n */\n private _resolveAndHandleTap = (e: GestureResponderEvent) => {\n const now = Date.now();\n if (\n this.doubleTapFirstTapReleaseTimestamp &&\n now - this.doubleTapFirstTapReleaseTimestamp < this.props.doubleTapDelay\n ) {\n this._addTouch({\n ...this.doubleTapFirstTap,\n id: now.toString(),\n isSecondTap: true,\n });\n clearTimeout(this.singleTapTimeoutId);\n delete this.doubleTapFirstTapReleaseTimestamp;\n delete this.singleTapTimeoutId;\n delete this.doubleTapFirstTap;\n this._handleDoubleTap(e);\n } else {\n this.doubleTapFirstTapReleaseTimestamp = now;\n this.doubleTapFirstTap = {\n id: now.toString(),\n x: e.nativeEvent.pageX - this.state.originalPageX,\n y: e.nativeEvent.pageY - this.state.originalPageY,\n };\n this._addTouch(this.doubleTapFirstTap);\n\n // persist event so e.nativeEvent is preserved after a timeout delay\n e.persist();\n this.singleTapTimeoutId = setTimeout(() => {\n delete this.doubleTapFirstTapReleaseTimestamp;\n delete this.singleTapTimeoutId;\n\n // Pan to the tapped location\n if (this.props.staticPinPosition && this.doubleTapFirstTap) {\n const tapX =\n this.props.staticPinPosition.x - this.doubleTapFirstTap.x;\n const tapY =\n this.props.staticPinPosition.y - this.doubleTapFirstTap.y;\n\n Animated.timing(this.panAnim, {\n toValue: {\n x: this.offsetX + tapX / this.zoomLevel,\n y: this.offsetY + tapY / this.zoomLevel,\n },\n useNativeDriver: true,\n duration: 200,\n }).start(() => {\n this._updateStaticPin();\n });\n }\n\n this.props.onSingleTap?.(e, this._getZoomableViewEventObject());\n }, this.props.doubleTapDelay);\n }\n };\n\n _moveTimeout: NodeJS.Timeout;\n moveStaticPinTo = (position: Vec2D) => {\n const { originalWidth, originalHeight } = this.state;\n const { staticPinPosition, contentWidth, contentHeight } = this.props;\n\n // Offset for the static pin\n const pinX = staticPinPosition.x - originalWidth / 2;\n const pinY = staticPinPosition.y - originalHeight / 2;\n\n this.offsetX = contentWidth / 2 - position.x + pinX / this.zoomLevel;\n this.offsetY = contentHeight / 2 - position.y + pinY / this.zoomLevel;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n };\n\n private _staticPinPosition = () => {\n return viewportPositionToImagePosition({\n viewportPosition: {\n x: this.props.staticPinPosition.x,\n y: this.props.staticPinPosition.y,\n },\n imageSize: {\n height: this.props.contentHeight,\n width: this.props.contentWidth,\n },\n zoomableEvent: {\n ...this._getZoomableViewEventObject(),\n offsetX: this.offsetX,\n offsetY: this.offsetY,\n zoomLevel: this.zoomLevel,\n },\n });\n };\n\n private _updateStaticPin = () => {\n this.props.onStaticPinPositionChange?.(this._staticPinPosition());\n };\n\n private _addTouch(touch: TouchPoint) {\n this.touches.push(touch);\n this.setState({ touches: [...this.touches] });\n }\n\n private _removeTouch(touch: TouchPoint) {\n this.touches.splice(this.touches.indexOf(touch), 1);\n this.setState({ touches: [...this.touches] });\n }\n\n /**\n * Handles the double tap event\n *\n * @param e\n *\n * @private\n */\n _handleDoubleTap(e: GestureResponderEvent) {\n const { onDoubleTapBefore, onDoubleTapAfter, doubleTapZoomToCenter } =\n this.props;\n\n onDoubleTapBefore?.(e, this._getZoomableViewEventObject());\n\n const nextZoomStep = this._getNextZoomStep();\n const { originalPageX, originalPageY } = this.state;\n\n // define new zoom position coordinates\n const zoomPositionCoordinates = {\n x: e.nativeEvent.pageX - originalPageX,\n y: e.nativeEvent.pageY - originalPageY,\n };\n\n // if doubleTapZoomToCenter enabled -> always zoom to center instead\n if (doubleTapZoomToCenter) {\n zoomPositionCoordinates.x = 0;\n zoomPositionCoordinates.y = 0;\n }\n\n this._zoomToLocation(\n zoomPositionCoordinates.x,\n zoomPositionCoordinates.y,\n nextZoomStep\n ).then(() => {\n onDoubleTapAfter?.(\n e,\n this._getZoomableViewEventObject({ zoomLevel: nextZoomStep })\n );\n });\n }\n\n /**\n * Returns the next zoom step based on current step and zoomStep property.\n * If we are zoomed all the way in -> return to initialzoom\n *\n * @returns {*}\n */\n _getNextZoomStep() {\n const { zoomStep, maxZoom, initialZoom } = this.props;\n const { zoomLevel } = this;\n\n if (zoomLevel.toFixed(2) === maxZoom.toFixed(2)) {\n return initialZoom;\n }\n\n const nextZoomStep = zoomLevel * (1 + zoomStep);\n if (nextZoomStep > maxZoom) {\n return maxZoom;\n }\n\n return nextZoomStep;\n }\n\n /**\n * Zooms to a specific location in our view\n *\n * @param x\n * @param y\n * @param newZoomLevel\n *\n * @private\n */\n async _zoomToLocation(x: number, y: number, newZoomLevel: number) {\n if (!this.props.zoomEnabled) return;\n\n this.props.onZoomBefore?.(null, null, this._getZoomableViewEventObject());\n\n // == Perform Zoom Animation ==\n // Calculates panAnim values based on changes in zoomAnim.\n let prevScale = this.zoomLevel;\n // Since zoomAnim is calculated in native driver,\n // it will jitter panAnim once in a while,\n // because here panAnim is being calculated in js.\n // However the jittering should mostly occur in simulator.\n const listenerId = this.zoomAnim.addListener(({ value: newScale }) => {\n this.panAnim.setValue({\n x: calcNewScaledOffsetForZoomCentering(\n this.offsetX,\n this.state.originalWidth,\n prevScale,\n newScale,\n x\n ),\n y: calcNewScaledOffsetForZoomCentering(\n this.offsetY,\n this.state.originalHeight,\n prevScale,\n newScale,\n y\n ),\n });\n prevScale = newScale;\n });\n getZoomToAnimation(this.zoomAnim, newZoomLevel).start(() => {\n this.zoomAnim.removeListener(listenerId);\n });\n // == Zoom Animation Ends ==\n\n this.props.onZoomAfter?.(null, null, this._getZoomableViewEventObject());\n }\n\n /**\n * Zooms to a specificied zoom level.\n * Returns a promise if everything was updated and a boolean, whether it could be updated or if it exceeded the min/max zoom limits.\n *\n * @param {number} newZoomLevel\n *\n * @return {Promise}\n */\n async zoomTo(newZoomLevel: number): Promise {\n if (\n // if we would go out of our min/max limits -> abort\n newZoomLevel > this.props.maxZoom ||\n newZoomLevel < this.props.minZoom\n )\n return false;\n\n await this._zoomToLocation(0, 0, newZoomLevel);\n return true;\n }\n\n /**\n * Zooms in or out by a specified change level\n * Use a positive number for `zoomLevelChange` to zoom in\n * Use a negative number for `zoomLevelChange` to zoom out\n *\n * Returns a promise if everything was updated and a boolean, whether it could be updated or if it exceeded the min/max zoom limits.\n *\n * @param {number | null} zoomLevelChange\n *\n * @return {Promise}\n */\n zoomBy(zoomLevelChange: number = null): Promise {\n // if no zoom level Change given -> just use zoom step\n if (!zoomLevelChange) {\n zoomLevelChange = this.props.zoomStep;\n }\n\n return this.zoomTo(this.zoomLevel + zoomLevelChange);\n }\n\n /**\n * Moves the zoomed view to a specified position\n * Returns a promise when finished\n *\n * @param {number} newOffsetX the new position we want to move it to (x-axis)\n * @param {number} newOffsetY the new position we want to move it to (y-axis)\n *\n * @return {Promise}\n */\n moveTo(newOffsetX: number, newOffsetY: number): Promise {\n const { originalWidth, originalHeight } = this.state;\n\n const offsetX = (newOffsetX - originalWidth / 2) / this.zoomLevel;\n const offsetY = (newOffsetY - originalHeight / 2) / this.zoomLevel;\n\n return this._setNewOffsetPosition(-offsetX, -offsetY);\n }\n\n /**\n * Moves the zoomed view by a certain amount.\n *\n * Returns a promise when finished\n *\n * @param {number} offsetChangeX the amount we want to move the offset by (x-axis)\n * @param {number} offsetChangeY the amount we want to move the offset by (y-axis)\n *\n * @return {Promise}\n */\n moveBy(offsetChangeX: number, offsetChangeY: number): Promise {\n const offsetX =\n (this.offsetX * this.zoomLevel - offsetChangeX) / this.zoomLevel;\n const offsetY =\n (this.offsetY * this.zoomLevel - offsetChangeY) / this.zoomLevel;\n\n return this._setNewOffsetPosition(offsetX, offsetY);\n }\n\n render() {\n const {\n staticPinIcon,\n children,\n visualTouchFeedbackEnabled,\n doubleTapDelay,\n staticPinPosition,\n onStaticPinLongPress,\n onStaticPinPress,\n pinProps,\n } = this.props;\n const { pinSize, touches, debugPoints = [] } = this.state;\n\n return (\n \n \n {children}\n \n\n {visualTouchFeedbackEnabled &&\n touches?.map((touch) => {\n const animationDuration = doubleTapDelay;\n return (\n this._removeTouch(touch)}\n />\n );\n })}\n\n {/* For Debugging Only */}\n {debugPoints.map(({ x, y }, index) => {\n return ;\n })}\n\n {staticPinPosition && (\n this.setState({ pinSize: size })}\n pinProps={pinProps}\n />\n )}\n \n );\n }\n}\n\nconst styles = StyleSheet.create({\n zoomSubject: {\n flex: 1,\n width: '100%',\n justifyContent: 'center',\n alignItems: 'center',\n },\n container: {\n flex: 1,\n justifyContent: 'center',\n alignItems: 'center',\n position: 'relative',\n overflow: 'hidden',\n },\n});\n\nexport default ReactNativeZoomableView;\n\nexport { ReactNativeZoomableView };\n"]} \ No newline at end of file +{"version":3,"sources":["ReactNativeZoomableView.tsx"],"names":["React","Component","createRef","Animated","Easing","PanResponder","StyleSheet","View","AnimatedTouchFeedback","DebugTouchPoint","calcGestureCenterPoint","calcGestureTouchDistance","calcNewScaledOffsetForZoomCentering","applyPanBoundariesToOffset","viewportPositionToImagePosition","StaticPin","debounce","getBoundaryCrossedAnim","getPanMomentumDecayAnim","getZoomToAnimation","initialState","originalWidth","originalHeight","originalPageX","originalPageY","pinSize","width","height","ReactNativeZoomableView","gestureStarted","v","_gestureStarted","constructor","props","ValueXY","x","y","Value","value","boundaryCrossedAnimInEffect","position","onStaticPinPositionChange","requestAnimationFrame","setTimeout","zoomSubjectWrapperRef","current","measureInWindow","setState","e","gestureState","onStartShouldSetPanResponder","_getZoomableViewEventObject","onLongPress","longPressTimeout","longPressDuration","onPanResponderGrant","panAnim","stopAnimation","zoomAnim","raisePin","gestureType","_resolveAndHandleTap","debugPoints","lastGestureCenterPosition","disableMomentum","panEnabled","disablePanOnInitialZoom","zoomLevel","initialZoom","vx","vy","start","clearTimeout","onPanResponderEnd","onZoomEnd","onShiftingEnd","staticPinPosition","_updateStaticPin","dropPin","onPanResponderMove","numberActiveTouches","_handlePanResponderGrant","_handlePanResponderEnd","lastGestureTouchDistance","_handlePinching","Math","abs","dx","dy","isShiftGesture","_handleShifting","now","Date","doubleTapFirstTapReleaseTimestamp","doubleTapDelay","_addTouch","doubleTapFirstTap","id","toString","isSecondTap","singleTapTimeoutId","_handleDoubleTap","nativeEvent","pageX","state","pageY","persist","tapX","tapY","timing","toValue","offsetX","offsetY","useNativeDriver","duration","onSingleTap","contentWidth","contentHeight","pinX","pinY","setValue","viewportPosition","imageSize","zoomableEvent","_staticPinPosition","gestureHandlers","create","_handleStartShouldSetPanResponder","_handlePanResponderMove","onPanResponderRelease","onPanResponderTerminate","evt","onPanResponderTerminationRequest","onShouldBlockNativeResponder","onStartShouldSetPanResponderCapture","onMoveShouldSetPanResponderCapture","zoomAnimatedValue","panAnimatedValueXY","initialOffsetX","initialOffsetY","addListener","animatePin","pinAnim","easing","out","ease","__setOffset","__getOffset","axis","offset","offsetState","__offsets","animValue","bindToBorders","containerSize","contentSize","boundOffset","panBoundaryPadding","boundariesApplied","toFixed","componentDidUpdate","prevProps","prevState","zoomEnabled","onTransformInvocationInitialized","_invokeOnTransform","successful","currState","originalMeasurementsChanged","staticPinPositionChanged","componentDidMount","grabZoomSubjectOriginalMeasurements","measureZoomSubjectInterval","setInterval","componentWillUnmount","clearInterval","zoomableViewEvent","onTransform","onStaticPinPositionMove","debouncedOnStaticPinPositionChange","overwriteObj","maxZoom","minZoom","pinchToZoomInSensitivity","pinchToZoomOutSensitivity","distance","onZoomBefore","zoomGrowthFromLastGestureState","pinchToZoomSensitivity","deltaGrowth","deltaGrowthAdjustedBySensitivity","newZoomLevel","gestureCenterPoint","zoomCenter","debug","_setPinchDebugPoints","oldOffsetX","oldOffsetY","oldScale","newScale","offsetShift","_calcOffsetShiftSinceLastGestureState","onZoomAfter","gestureResponderEvent","points","touches","movementSensibility","shift","shiftX","shiftY","moveX","moveY","_setNewOffsetPosition","newOffsetX","newOffsetY","onShiftingBefore","onShiftingAfter","touch","push","_removeTouch","splice","indexOf","onDoubleTapBefore","onDoubleTapAfter","doubleTapZoomToCenter","nextZoomStep","_getNextZoomStep","zoomPositionCoordinates","_zoomToLocation","then","zoomStep","prevScale","listenerId","removeListener","zoomTo","zoomBy","zoomLevelChange","moveTo","moveBy","offsetChangeX","offsetChangeY","render","staticPinIcon","children","visualTouchFeedbackEnabled","onStaticPinLongPress","onStaticPinPress","pinProps","styles","container","panHandlers","zoomSubject","style","transform","scale","getTranslateTransform","map","animationDuration","index","size","undefined","flex","justifyContent","alignItems","overflow"],"mappings":"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","sourcesContent":["import React, { Component, createRef, RefObject } from 'react';\nimport {\n Animated,\n Easing,\n GestureResponderEvent,\n PanResponder,\n PanResponderGestureState,\n StyleSheet,\n View,\n} from 'react-native';\n\nimport {\n Vec2D,\n ReactNativeZoomableViewProps,\n ReactNativeZoomableViewState,\n TouchPoint,\n ZoomableViewEvent,\n Size2D,\n} from './typings';\n\nimport { AnimatedTouchFeedback } from './components';\nimport { DebugTouchPoint } from './debugHelper';\nimport {\n calcGestureCenterPoint,\n calcGestureTouchDistance,\n calcNewScaledOffsetForZoomCentering,\n} from './helper';\nimport { applyPanBoundariesToOffset } from './helper/applyPanBoundariesToOffset';\nimport { viewportPositionToImagePosition } from './helper/coordinateConversion';\nimport { StaticPin } from './components/StaticPin';\nimport { debounce } from 'lodash';\nimport {\n getBoundaryCrossedAnim,\n getPanMomentumDecayAnim,\n getZoomToAnimation,\n} from './animations';\n\nconst initialState = {\n originalWidth: null,\n originalHeight: null,\n originalPageX: null,\n originalPageY: null,\n pinSize: { width: 0, height: 0 },\n} as ReactNativeZoomableViewState;\n\nclass ReactNativeZoomableView extends Component<\n ReactNativeZoomableViewProps,\n ReactNativeZoomableViewState\n> {\n zoomSubjectWrapperRef: RefObject;\n gestureHandlers: any;\n doubleTapFirstTapReleaseTimestamp: number;\n\n static defaultProps = {\n zoomEnabled: true,\n panEnabled: true,\n initialZoom: 1,\n initialOffsetX: 0,\n initialOffsetY: 0,\n maxZoom: 1.5,\n minZoom: 0.5,\n pinchToZoomInSensitivity: 1,\n pinchToZoomOutSensitivity: 1,\n movementSensibility: 1,\n doubleTapDelay: 300,\n bindToBorders: true,\n zoomStep: 0.5,\n onLongPress: null,\n longPressDuration: 700,\n contentWidth: undefined,\n contentHeight: undefined,\n panBoundaryPadding: 0,\n visualTouchFeedbackEnabled: true,\n staticPinPosition: undefined,\n staticPinIcon: undefined,\n onStaticPinPositionChange: undefined,\n onStaticPinPositionMove: undefined,\n animatePin: true,\n disablePanOnInitialZoom: false,\n };\n\n private panAnim = new Animated.ValueXY({ x: 0, y: 0 });\n private zoomAnim = new Animated.Value(1);\n private pinAnim = new Animated.ValueXY({ x: 0, y: 0 });\n\n private __offsets = {\n x: {\n value: 0,\n boundaryCrossedAnimInEffect: false,\n },\n y: {\n value: 0,\n boundaryCrossedAnimInEffect: false,\n },\n };\n\n private zoomLevel = 1;\n private lastGestureCenterPosition: { x: number; y: number } = null;\n private lastGestureTouchDistance: number;\n private gestureType: 'pinch' | 'shift' | 'null';\n\n private _gestureStarted = false;\n private set gestureStarted(v: boolean) {\n this._gestureStarted = v;\n }\n public get gestureStarted() {\n return this._gestureStarted;\n }\n\n /**\n * Last press time (used to evaluate whether user double tapped)\n * @type {number}\n */\n private longPressTimeout: NodeJS.Timeout = null;\n private onTransformInvocationInitialized: boolean;\n private singleTapTimeoutId: NodeJS.Timeout;\n private touches: TouchPoint[] = [];\n private doubleTapFirstTap: TouchPoint;\n private measureZoomSubjectInterval: NodeJS.Timer;\n\n constructor(props) {\n super(props);\n\n this.gestureHandlers = PanResponder.create({\n onStartShouldSetPanResponder: this._handleStartShouldSetPanResponder,\n onPanResponderGrant: this._handlePanResponderGrant,\n onPanResponderMove: this._handlePanResponderMove,\n onPanResponderRelease: this._handlePanResponderEnd,\n onPanResponderTerminate: (evt, gestureState) => {\n // We should also call _handlePanResponderEnd\n // to properly perform cleanups when the gesture is terminated\n // (aka gesture handling responsibility is taken over by another component).\n // This also fixes a weird issue where\n // on real device, sometimes onPanResponderRelease is not called when you lift 2 fingers up,\n // but onPanResponderTerminate is called instead for no apparent reason.\n this._handlePanResponderEnd(evt, gestureState);\n this.props.onPanResponderTerminate?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n );\n },\n onPanResponderTerminationRequest: (evt, gestureState) =>\n !!this.props.onPanResponderTerminationRequest?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n ),\n // Defaults to true to prevent parent components, such as React Navigation's tab view, from taking over as responder.\n onShouldBlockNativeResponder: (evt, gestureState) =>\n this.props.onShouldBlockNativeResponder?.(\n evt,\n gestureState,\n this._getZoomableViewEventObject()\n ) ?? true,\n onStartShouldSetPanResponderCapture: (evt, gestureState) =>\n this.props.onStartShouldSetPanResponderCapture?.(evt, gestureState),\n onMoveShouldSetPanResponderCapture: (evt, gestureState) =>\n this.props.onMoveShouldSetPanResponderCapture?.(evt, gestureState),\n });\n\n this.zoomSubjectWrapperRef = createRef();\n\n if (this.props.zoomAnimatedValue)\n this.zoomAnim = this.props.zoomAnimatedValue;\n if (this.props.panAnimatedValueXY)\n this.panAnim = this.props.panAnimatedValueXY;\n\n this.zoomLevel = props.initialZoom;\n this.offsetX = props.initialOffsetX;\n this.offsetY = props.initialOffsetY;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n this.panAnim.addListener(({ x, y }) => {\n this.offsetX = x;\n this.offsetY = y;\n });\n this.zoomAnim.addListener(({ value }) => {\n this.zoomLevel = value;\n });\n\n this.state = {\n ...initialState,\n };\n\n this.lastGestureTouchDistance = 150;\n\n this.gestureType = null;\n }\n\n private raisePin() {\n if (!this.props.animatePin) return;\n Animated.timing(this.pinAnim, {\n toValue: { x: 0, y: -10 },\n useNativeDriver: true,\n easing: Easing.out(Easing.ease),\n duration: 100,\n }).start();\n }\n\n private dropPin() {\n if (!this.props.animatePin) return;\n Animated.timing(this.pinAnim, {\n toValue: { x: 0, y: 0 },\n useNativeDriver: true,\n easing: Easing.out(Easing.ease),\n duration: 100,\n }).start();\n }\n\n private set offsetX(x: number) {\n this.__setOffset('x', x);\n }\n private set offsetY(y: number) {\n this.__setOffset('y', y);\n }\n private get offsetX() {\n return this.__getOffset('x');\n }\n private get offsetY() {\n return this.__getOffset('y');\n }\n private __setOffset(axis: 'x' | 'y', offset) {\n const offsetState = this.__offsets[axis];\n const animValue = this.panAnim?.[axis];\n\n if (this.props.bindToBorders) {\n const containerSize =\n axis === 'x' ? this.state?.originalWidth : this.state?.originalHeight;\n const contentSize =\n axis === 'x'\n ? this.props.contentWidth || this.state?.originalWidth\n : this.props.contentHeight || this.state?.originalHeight;\n\n const boundOffset =\n contentSize && containerSize\n ? applyPanBoundariesToOffset(\n offset,\n containerSize,\n contentSize,\n this.zoomLevel,\n this.props.panBoundaryPadding\n )\n : offset;\n\n if (\n animValue &&\n !this.gestureType &&\n !offsetState.boundaryCrossedAnimInEffect\n ) {\n const boundariesApplied =\n boundOffset !== offset &&\n boundOffset.toFixed(3) !== offset.toFixed(3);\n if (boundariesApplied) {\n offsetState.boundaryCrossedAnimInEffect = true;\n getBoundaryCrossedAnim(this.panAnim[axis], boundOffset).start(() => {\n offsetState.boundaryCrossedAnimInEffect = false;\n });\n return;\n }\n }\n }\n\n offsetState.value = offset;\n }\n private __getOffset(axis: 'x' | 'y') {\n return this.__offsets[axis].value;\n }\n\n componentDidUpdate(\n prevProps: ReactNativeZoomableViewProps,\n prevState: ReactNativeZoomableViewState\n ) {\n const { zoomEnabled, initialZoom } = this.props;\n if (prevProps.zoomEnabled && !zoomEnabled) {\n this.zoomLevel = initialZoom;\n this.zoomAnim.setValue(this.zoomLevel);\n }\n if (\n !this.onTransformInvocationInitialized &&\n this._invokeOnTransform().successful\n ) {\n this.panAnim.addListener(() => this._invokeOnTransform());\n this.zoomAnim.addListener(() => this._invokeOnTransform());\n this.onTransformInvocationInitialized = true;\n }\n\n const currState = this.state;\n const originalMeasurementsChanged =\n currState.originalHeight !== prevState.originalHeight ||\n currState.originalWidth !== prevState.originalWidth ||\n currState.originalPageX !== prevState.originalPageX ||\n currState.originalPageY !== prevState.originalPageY;\n\n const staticPinPositionChanged =\n prevProps.staticPinPosition?.x !== this.props.staticPinPosition?.x ||\n prevProps.staticPinPosition?.y !== this.props.staticPinPosition?.y;\n\n if (\n this.onTransformInvocationInitialized &&\n (originalMeasurementsChanged || staticPinPositionChanged)\n ) {\n this._invokeOnTransform();\n }\n }\n\n componentDidMount() {\n this.grabZoomSubjectOriginalMeasurements();\n // We've already run `grabZoomSubjectOriginalMeasurements` at various events\n // to make sure the measurements are promptly updated.\n // However, there might be cases we haven't accounted for, especially when\n // native processes are involved. To account for those cases,\n // we'll use an interval here to ensure we're always up-to-date.\n // The `setState` in `grabZoomSubjectOriginalMeasurements` won't trigger a rerender\n // if the values given haven't changed, so we're not running performance risk here.\n this.measureZoomSubjectInterval = setInterval(\n this.grabZoomSubjectOriginalMeasurements,\n 1e3\n );\n }\n\n componentWillUnmount() {\n clearInterval(this.measureZoomSubjectInterval);\n }\n\n debouncedOnStaticPinPositionChange = debounce(\n (position: Vec2D) => this.props.onStaticPinPositionChange?.(position),\n 100\n );\n\n /**\n * try to invoke onTransform\n * @private\n */\n _invokeOnTransform() {\n const zoomableViewEvent = this._getZoomableViewEventObject();\n\n if (!zoomableViewEvent.originalWidth || !zoomableViewEvent.originalHeight)\n return { successful: false };\n\n this.props.onTransform?.(zoomableViewEvent);\n\n this.props.onStaticPinPositionMove?.(this._staticPinPosition());\n\n this.debouncedOnStaticPinPositionChange(this._staticPinPosition());\n\n return { successful: true };\n }\n\n /**\n * Returns additional information about components current state for external event hooks\n *\n * @returns {{}}\n * @private\n */\n _getZoomableViewEventObject(overwriteObj = {}): ZoomableViewEvent {\n return {\n zoomLevel: this.zoomLevel,\n offsetX: this.offsetX,\n offsetY: this.offsetY,\n originalHeight: this.state.originalHeight,\n originalWidth: this.state.originalWidth,\n originalPageX: this.state.originalPageX,\n originalPageY: this.state.originalPageY,\n ...overwriteObj,\n } as ZoomableViewEvent;\n }\n\n /**\n * Get the original box dimensions and save them for later use.\n * (They will be used to calculate boxBorders)\n *\n * @private\n */\n private grabZoomSubjectOriginalMeasurements = () => {\n // make sure we measure after animations are complete\n requestAnimationFrame(() => {\n // this setTimeout is here to fix a weird issue on iOS where the measurements are all `0`\n // when navigating back (react-navigation stack) from another view\n // while closing the keyboard at the same time\n setTimeout(() => {\n // In normal conditions, we're supposed to measure zoomSubject instead of its wrapper.\n // However, our zoomSubject may have been transformed by an initial zoomLevel or offset,\n // in which case these measurements will not represent the true \"original\" measurements.\n // We just need to make sure the zoomSubjectWrapper perfectly aligns with the zoomSubject\n // (no border, space, or anything between them)\n const zoomSubjectWrapperRef = this.zoomSubjectWrapperRef;\n // we don't wanna measure when zoomSubjectWrapperRef is not yet available or has been unmounted\n zoomSubjectWrapperRef.current?.measureInWindow(\n (x, y, width, height) => {\n this.setState({\n originalWidth: width,\n originalHeight: height,\n originalPageX: x,\n originalPageY: y,\n });\n }\n );\n });\n });\n };\n\n /**\n * Handles the start of touch events and checks for taps\n *\n * @param e\n * @param gestureState\n * @returns {boolean}\n *\n * @private\n */\n _handleStartShouldSetPanResponder = (\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) => {\n if (this.props.onStartShouldSetPanResponder) {\n this.props.onStartShouldSetPanResponder(\n e,\n gestureState,\n this._getZoomableViewEventObject(),\n false\n );\n }\n\n // Always set pan responder on start\n // of gesture so we can handle tap.\n // \"Pan threshold validation\" will be handled\n // in `onPanResponderMove` instead of in `onMoveShouldSetPanResponder`\n return true;\n };\n\n /**\n * Calculates pinch distance\n *\n * @param e\n * @param gestureState\n * @private\n */\n _handlePanResponderGrant = (e, gestureState) => {\n if (this.props.onLongPress) {\n this.longPressTimeout = setTimeout(() => {\n this.props.onLongPress?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n this.longPressTimeout = null;\n }, this.props.longPressDuration);\n }\n\n this.props.onPanResponderGrant?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n\n this.panAnim.stopAnimation();\n this.zoomAnim.stopAnimation();\n this.gestureStarted = true;\n\n this.raisePin();\n };\n\n /**\n * Handles the end of touch events\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePanResponderEnd = (e, gestureState) => {\n if (!this.gestureType) {\n this._resolveAndHandleTap(e);\n }\n\n this.setState({ debugPoints: [] });\n\n this.lastGestureCenterPosition = null;\n\n const disableMomentum =\n this.props.disableMomentum ||\n (this.props.panEnabled &&\n this.gestureType === 'shift' &&\n this.props.disablePanOnInitialZoom &&\n this.zoomLevel === this.props.initialZoom);\n\n // Trigger final shift animation unless disablePanOnInitialZoom is set and we're on the initial zoom level\n // or disableMomentum\n if (!disableMomentum) {\n getPanMomentumDecayAnim(this.panAnim, {\n x: gestureState.vx / this.zoomLevel,\n y: gestureState.vy / this.zoomLevel,\n }).start();\n }\n\n if (this.longPressTimeout) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n\n this.props.onPanResponderEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n\n if (this.gestureType === 'pinch') {\n this.props.onZoomEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n } else if (this.gestureType === 'shift') {\n this.props.onShiftingEnd?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n }\n\n if (this.props.staticPinPosition) {\n this._updateStaticPin();\n }\n\n this.dropPin();\n\n this.gestureType = null;\n this.gestureStarted = false;\n };\n\n /**\n * Handles the actual movement of our pan responder\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePanResponderMove = (\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) => {\n if (this.props.onPanResponderMove) {\n if (\n this.props.onPanResponderMove(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n )\n ) {\n return false;\n }\n }\n\n // Only supports 2 touches and below,\n // any invalid number will cause the gesture to end.\n if (gestureState.numberActiveTouches <= 2) {\n if (!this.gestureStarted) {\n this._handlePanResponderGrant(e, gestureState);\n }\n } else {\n if (this.gestureStarted) {\n this._handlePanResponderEnd(e, gestureState);\n }\n return true;\n }\n\n if (gestureState.numberActiveTouches === 2) {\n if (this.longPressTimeout) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n\n // change some measurement states when switching gesture to ensure a smooth transition\n if (this.gestureType !== 'pinch') {\n this.lastGestureCenterPosition = calcGestureCenterPoint(\n e,\n gestureState\n );\n this.lastGestureTouchDistance = calcGestureTouchDistance(\n e,\n gestureState\n );\n }\n this.gestureType = 'pinch';\n this._handlePinching(e, gestureState);\n } else if (gestureState.numberActiveTouches === 1) {\n if (\n this.longPressTimeout &&\n (Math.abs(gestureState.dx) > 5 || Math.abs(gestureState.dy) > 5)\n ) {\n clearTimeout(this.longPressTimeout);\n this.longPressTimeout = null;\n }\n // change some measurement states when switching gesture to ensure a smooth transition\n if (this.gestureType !== 'shift') {\n this.lastGestureCenterPosition = calcGestureCenterPoint(\n e,\n gestureState\n );\n }\n\n const { dx, dy } = gestureState;\n const isShiftGesture = Math.abs(dx) > 2 || Math.abs(dy) > 2;\n if (isShiftGesture) {\n this.gestureType = 'shift';\n this._handleShifting(gestureState);\n }\n }\n };\n\n /**\n * Handles the pinch movement and zooming\n *\n * @param e\n * @param gestureState\n *\n * @private\n */\n _handlePinching(\n e: GestureResponderEvent,\n gestureState: PanResponderGestureState\n ) {\n if (!this.props.zoomEnabled) return;\n\n const {\n maxZoom,\n minZoom,\n pinchToZoomInSensitivity,\n pinchToZoomOutSensitivity,\n } = this.props;\n\n const distance = calcGestureTouchDistance(e, gestureState);\n\n if (\n this.props.onZoomBefore &&\n this.props.onZoomBefore(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n )\n ) {\n return;\n }\n\n // define the new zoom level and take zoom level sensitivity into consideration\n const zoomGrowthFromLastGestureState =\n distance / this.lastGestureTouchDistance;\n this.lastGestureTouchDistance = distance;\n\n const pinchToZoomSensitivity =\n zoomGrowthFromLastGestureState < 1\n ? pinchToZoomOutSensitivity\n : pinchToZoomInSensitivity;\n\n const deltaGrowth = zoomGrowthFromLastGestureState - 1;\n // 0 - no resistance\n // 10 - 90% resistance\n const deltaGrowthAdjustedBySensitivity =\n deltaGrowth * (1 - (pinchToZoomSensitivity * 9) / 100);\n\n let newZoomLevel = this.zoomLevel * (1 + deltaGrowthAdjustedBySensitivity);\n\n // make sure max and min zoom levels are respected\n if (maxZoom !== null && newZoomLevel > maxZoom) {\n newZoomLevel = maxZoom;\n }\n\n if (newZoomLevel < minZoom) {\n newZoomLevel = minZoom;\n }\n\n const gestureCenterPoint = calcGestureCenterPoint(e, gestureState);\n\n if (!gestureCenterPoint) return;\n\n let zoomCenter = {\n x: gestureCenterPoint.x - this.state.originalPageX,\n y: gestureCenterPoint.y - this.state.originalPageY,\n };\n\n if (this.props.staticPinPosition) {\n // When we use a static pin position, the zoom centre is the same as that position,\n // otherwise the pin moves around way too much while zooming.\n zoomCenter = {\n x: this.props.staticPinPosition.x,\n y: this.props.staticPinPosition.y,\n };\n }\n\n // Uncomment to debug\n this.props.debug && this._setPinchDebugPoints(e, zoomCenter);\n\n const { originalHeight, originalWidth } = this.state;\n\n const oldOffsetX = this.offsetX;\n const oldOffsetY = this.offsetY;\n const oldScale = this.zoomLevel;\n const newScale = newZoomLevel;\n\n let offsetY = calcNewScaledOffsetForZoomCentering(\n oldOffsetY,\n originalHeight,\n oldScale,\n newScale,\n zoomCenter.y\n );\n let offsetX = calcNewScaledOffsetForZoomCentering(\n oldOffsetX,\n originalWidth,\n oldScale,\n newScale,\n zoomCenter.x\n );\n\n const offsetShift =\n this._calcOffsetShiftSinceLastGestureState(gestureCenterPoint);\n if (offsetShift) {\n offsetX += offsetShift.x;\n offsetY += offsetShift.y;\n }\n\n this.offsetX = offsetX;\n this.offsetY = offsetY;\n this.zoomLevel = newScale;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n\n this.props.onZoomAfter?.(\n e,\n gestureState,\n this._getZoomableViewEventObject()\n );\n }\n\n /**\n * Used to debug pinch events\n * @param gestureResponderEvent\n * @param zoomCenter\n * @param points\n */\n _setPinchDebugPoints(\n gestureResponderEvent: GestureResponderEvent,\n zoomCenter: Vec2D,\n ...points: Vec2D[]\n ) {\n const { touches } = gestureResponderEvent.nativeEvent;\n const { originalPageY, originalPageX } = this.state;\n this.setState({\n debugPoints: [\n {\n x: touches[0].pageX - originalPageX,\n y: touches[0].pageY - originalPageY,\n },\n {\n x: touches[1].pageX - originalPageX,\n y: touches[1].pageY - originalPageY,\n },\n zoomCenter,\n ...points,\n ],\n });\n }\n\n /**\n * Calculates the amount the offset should shift since the last position during panning\n *\n * @param {Vec2D} gestureCenterPoint\n *\n * @private\n */\n _calcOffsetShiftSinceLastGestureState(gestureCenterPoint: Vec2D) {\n const { movementSensibility } = this.props;\n\n let shift = null;\n\n if (this.lastGestureCenterPosition) {\n const dx = gestureCenterPoint.x - this.lastGestureCenterPosition.x;\n const dy = gestureCenterPoint.y - this.lastGestureCenterPosition.y;\n\n const shiftX = dx / this.zoomLevel / movementSensibility;\n const shiftY = dy / this.zoomLevel / movementSensibility;\n\n shift = {\n x: shiftX,\n y: shiftY,\n };\n }\n\n this.lastGestureCenterPosition = gestureCenterPoint;\n\n return shift;\n }\n\n /**\n * Handles movement by tap and move\n *\n * @param gestureState\n *\n * @private\n */\n _handleShifting(gestureState: PanResponderGestureState) {\n // Skips shifting if panEnabled is false or disablePanOnInitialZoom is true and we're on the initial zoom level\n if (\n !this.props.panEnabled ||\n (this.props.disablePanOnInitialZoom &&\n this.zoomLevel === this.props.initialZoom)\n ) {\n return;\n }\n const shift = this._calcOffsetShiftSinceLastGestureState({\n x: gestureState.moveX,\n y: gestureState.moveY,\n });\n if (!shift) return;\n\n const offsetX = this.offsetX + shift.x;\n const offsetY = this.offsetY + shift.y;\n\n if (this.props.debug) {\n const x = gestureState.moveX - this.state.originalPageX;\n const y = gestureState.moveY - this.state.originalPageY;\n this.setState({ debugPoints: [{ x, y }] });\n }\n\n this._setNewOffsetPosition(offsetX, offsetY);\n\n this.raisePin();\n }\n\n /**\n * Set the state to offset moved\n *\n * @param {number} newOffsetX\n * @param {number} newOffsetY\n * @returns\n */\n async _setNewOffsetPosition(newOffsetX: number, newOffsetY: number) {\n const { onShiftingBefore, onShiftingAfter } = this.props;\n\n if (onShiftingBefore?.(null, null, this._getZoomableViewEventObject())) {\n return;\n }\n\n this.offsetX = newOffsetX;\n this.offsetY = newOffsetY;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n this.zoomAnim.setValue(this.zoomLevel);\n\n onShiftingAfter?.(null, null, this._getZoomableViewEventObject());\n }\n\n /**\n * Check whether the press event is double tap\n * or single tap and handle the event accordingly\n *\n * @param e\n *\n * @private\n */\n private _resolveAndHandleTap = (e: GestureResponderEvent) => {\n const now = Date.now();\n if (\n this.doubleTapFirstTapReleaseTimestamp &&\n now - this.doubleTapFirstTapReleaseTimestamp < this.props.doubleTapDelay\n ) {\n this._addTouch({\n ...this.doubleTapFirstTap,\n id: now.toString(),\n isSecondTap: true,\n });\n clearTimeout(this.singleTapTimeoutId);\n delete this.doubleTapFirstTapReleaseTimestamp;\n delete this.singleTapTimeoutId;\n delete this.doubleTapFirstTap;\n this._handleDoubleTap(e);\n } else {\n this.doubleTapFirstTapReleaseTimestamp = now;\n this.doubleTapFirstTap = {\n id: now.toString(),\n x: e.nativeEvent.pageX - this.state.originalPageX,\n y: e.nativeEvent.pageY - this.state.originalPageY,\n };\n this._addTouch(this.doubleTapFirstTap);\n\n // persist event so e.nativeEvent is preserved after a timeout delay\n e.persist();\n this.singleTapTimeoutId = setTimeout(() => {\n delete this.doubleTapFirstTapReleaseTimestamp;\n delete this.singleTapTimeoutId;\n\n // Pan to the tapped location\n if (this.props.staticPinPosition && this.doubleTapFirstTap) {\n const tapX =\n this.props.staticPinPosition.x - this.doubleTapFirstTap.x;\n const tapY =\n this.props.staticPinPosition.y - this.doubleTapFirstTap.y;\n\n Animated.timing(this.panAnim, {\n toValue: {\n x: this.offsetX + tapX / this.zoomLevel,\n y: this.offsetY + tapY / this.zoomLevel,\n },\n useNativeDriver: true,\n duration: 200,\n }).start(() => {\n this._updateStaticPin();\n });\n }\n\n this.props.onSingleTap?.(e, this._getZoomableViewEventObject());\n }, this.props.doubleTapDelay);\n }\n };\n\n _moveTimeout: NodeJS.Timeout;\n moveStaticPinTo = (position: Vec2D) => {\n const { originalWidth, originalHeight } = this.state;\n const { staticPinPosition, contentWidth, contentHeight } = this.props;\n\n // Offset for the static pin\n const pinX = staticPinPosition?.x - originalWidth / 2;\n const pinY = staticPinPosition?.y - originalHeight / 2;\n\n this.offsetX = contentWidth / 2 - position.x + pinX / this.zoomLevel;\n this.offsetY = contentHeight / 2 - position.y + pinY / this.zoomLevel;\n\n this.panAnim.setValue({ x: this.offsetX, y: this.offsetY });\n };\n\n private _staticPinPosition = () => {\n return viewportPositionToImagePosition({\n viewportPosition: {\n x: this.props?.staticPinPosition?.x,\n y: this.props?.staticPinPosition?.y,\n },\n imageSize: {\n height: this.props.contentHeight,\n width: this.props.contentWidth,\n },\n zoomableEvent: {\n ...this._getZoomableViewEventObject(),\n offsetX: this.offsetX,\n offsetY: this.offsetY,\n zoomLevel: this.zoomLevel,\n },\n });\n };\n\n private _updateStaticPin = () => {\n this.props.onStaticPinPositionChange?.(this._staticPinPosition());\n };\n\n private _addTouch(touch: TouchPoint) {\n this.touches.push(touch);\n this.setState({ touches: [...this.touches] });\n }\n\n private _removeTouch(touch: TouchPoint) {\n this.touches.splice(this.touches.indexOf(touch), 1);\n this.setState({ touches: [...this.touches] });\n }\n\n /**\n * Handles the double tap event\n *\n * @param e\n *\n * @private\n */\n _handleDoubleTap(e: GestureResponderEvent) {\n const { onDoubleTapBefore, onDoubleTapAfter, doubleTapZoomToCenter } =\n this.props;\n\n onDoubleTapBefore?.(e, this._getZoomableViewEventObject());\n\n const nextZoomStep = this._getNextZoomStep();\n const { originalPageX, originalPageY } = this.state;\n\n // define new zoom position coordinates\n const zoomPositionCoordinates = {\n x: e.nativeEvent.pageX - originalPageX,\n y: e.nativeEvent.pageY - originalPageY,\n };\n\n // if doubleTapZoomToCenter enabled -> always zoom to center instead\n if (doubleTapZoomToCenter) {\n zoomPositionCoordinates.x = 0;\n zoomPositionCoordinates.y = 0;\n }\n\n this._zoomToLocation(\n zoomPositionCoordinates.x,\n zoomPositionCoordinates.y,\n nextZoomStep\n ).then(() => {\n onDoubleTapAfter?.(\n e,\n this._getZoomableViewEventObject({ zoomLevel: nextZoomStep })\n );\n });\n }\n\n /**\n * Returns the next zoom step based on current step and zoomStep property.\n * If we are zoomed all the way in -> return to initialzoom\n *\n * @returns {*}\n */\n _getNextZoomStep() {\n const { zoomStep, maxZoom, initialZoom } = this.props;\n const { zoomLevel } = this;\n\n if (zoomLevel.toFixed(2) === maxZoom.toFixed(2)) {\n return initialZoom;\n }\n\n const nextZoomStep = zoomLevel * (1 + zoomStep);\n if (nextZoomStep > maxZoom) {\n return maxZoom;\n }\n\n return nextZoomStep;\n }\n\n /**\n * Zooms to a specific location in our view\n *\n * @param x\n * @param y\n * @param newZoomLevel\n *\n * @private\n */\n async _zoomToLocation(x: number, y: number, newZoomLevel: number) {\n if (!this.props.zoomEnabled) return;\n\n this.props.onZoomBefore?.(null, null, this._getZoomableViewEventObject());\n\n // == Perform Zoom Animation ==\n // Calculates panAnim values based on changes in zoomAnim.\n let prevScale = this.zoomLevel;\n // Since zoomAnim is calculated in native driver,\n // it will jitter panAnim once in a while,\n // because here panAnim is being calculated in js.\n // However the jittering should mostly occur in simulator.\n const listenerId = this.zoomAnim.addListener(({ value: newScale }) => {\n this.panAnim.setValue({\n x: calcNewScaledOffsetForZoomCentering(\n this.offsetX,\n this.state.originalWidth,\n prevScale,\n newScale,\n x\n ),\n y: calcNewScaledOffsetForZoomCentering(\n this.offsetY,\n this.state.originalHeight,\n prevScale,\n newScale,\n y\n ),\n });\n prevScale = newScale;\n });\n getZoomToAnimation(this.zoomAnim, newZoomLevel).start(() => {\n this.zoomAnim.removeListener(listenerId);\n });\n // == Zoom Animation Ends ==\n\n this.props.onZoomAfter?.(null, null, this._getZoomableViewEventObject());\n }\n\n /**\n * Zooms to a specificied zoom level.\n * Returns a promise if everything was updated and a boolean, whether it could be updated or if it exceeded the min/max zoom limits.\n *\n * @param {number} newZoomLevel\n *\n * @return {Promise}\n */\n async zoomTo(newZoomLevel: number): Promise {\n if (\n // if we would go out of our min/max limits -> abort\n newZoomLevel > this.props.maxZoom ||\n newZoomLevel < this.props.minZoom\n )\n return false;\n\n await this._zoomToLocation(0, 0, newZoomLevel);\n return true;\n }\n\n /**\n * Zooms in or out by a specified change level\n * Use a positive number for `zoomLevelChange` to zoom in\n * Use a negative number for `zoomLevelChange` to zoom out\n *\n * Returns a promise if everything was updated and a boolean, whether it could be updated or if it exceeded the min/max zoom limits.\n *\n * @param {number | null} zoomLevelChange\n *\n * @return {Promise}\n */\n zoomBy(zoomLevelChange: number = null): Promise {\n // if no zoom level Change given -> just use zoom step\n if (!zoomLevelChange) {\n zoomLevelChange = this.props.zoomStep;\n }\n\n return this.zoomTo(this.zoomLevel + zoomLevelChange);\n }\n\n /**\n * Moves the zoomed view to a specified position\n * Returns a promise when finished\n *\n * @param {number} newOffsetX the new position we want to move it to (x-axis)\n * @param {number} newOffsetY the new position we want to move it to (y-axis)\n *\n * @return {Promise}\n */\n moveTo(newOffsetX: number, newOffsetY: number): Promise {\n const { originalWidth, originalHeight } = this.state;\n\n const offsetX = (newOffsetX - originalWidth / 2) / this.zoomLevel;\n const offsetY = (newOffsetY - originalHeight / 2) / this.zoomLevel;\n\n return this._setNewOffsetPosition(-offsetX, -offsetY);\n }\n\n /**\n * Moves the zoomed view by a certain amount.\n *\n * Returns a promise when finished\n *\n * @param {number} offsetChangeX the amount we want to move the offset by (x-axis)\n * @param {number} offsetChangeY the amount we want to move the offset by (y-axis)\n *\n * @return {Promise}\n */\n moveBy(offsetChangeX: number, offsetChangeY: number): Promise {\n const offsetX =\n (this.offsetX * this.zoomLevel - offsetChangeX) / this.zoomLevel;\n const offsetY =\n (this.offsetY * this.zoomLevel - offsetChangeY) / this.zoomLevel;\n\n return this._setNewOffsetPosition(offsetX, offsetY);\n }\n\n render() {\n const {\n staticPinIcon,\n children,\n visualTouchFeedbackEnabled,\n doubleTapDelay,\n staticPinPosition,\n onStaticPinLongPress,\n onStaticPinPress,\n pinProps,\n } = this.props;\n const { pinSize, touches, debugPoints = [] } = this.state;\n\n return (\n \n \n {children}\n \n\n {visualTouchFeedbackEnabled &&\n touches?.map((touch) => {\n const animationDuration = doubleTapDelay;\n return (\n this._removeTouch(touch)}\n />\n );\n })}\n\n {/* For Debugging Only */}\n {debugPoints.map(({ x, y }, index) => {\n return ;\n })}\n\n {staticPinPosition && (\n this.setState({ pinSize: size })}\n pinProps={pinProps}\n />\n )}\n \n );\n }\n}\n\nconst styles = StyleSheet.create({\n zoomSubject: {\n flex: 1,\n width: '100%',\n justifyContent: 'center',\n alignItems: 'center',\n },\n container: {\n flex: 1,\n justifyContent: 'center',\n alignItems: 'center',\n position: 'relative',\n overflow: 'hidden',\n },\n});\n\nexport default ReactNativeZoomableView;\n\nexport { ReactNativeZoomableView };\n"]} \ No newline at end of file diff --git a/src/ReactNativeZoomableView.tsx b/src/ReactNativeZoomableView.tsx index bb6b415..fc07b81 100644 --- a/src/ReactNativeZoomableView.tsx +++ b/src/ReactNativeZoomableView.tsx @@ -923,8 +923,8 @@ class ReactNativeZoomableView extends Component< const { staticPinPosition, contentWidth, contentHeight } = this.props; // Offset for the static pin - const pinX = staticPinPosition.x - originalWidth / 2; - const pinY = staticPinPosition.y - originalHeight / 2; + const pinX = staticPinPosition?.x - originalWidth / 2; + const pinY = staticPinPosition?.y - originalHeight / 2; this.offsetX = contentWidth / 2 - position.x + pinX / this.zoomLevel; this.offsetY = contentHeight / 2 - position.y + pinY / this.zoomLevel; @@ -935,8 +935,8 @@ class ReactNativeZoomableView extends Component< private _staticPinPosition = () => { return viewportPositionToImagePosition({ viewportPosition: { - x: this.props.staticPinPosition.x, - y: this.props.staticPinPosition.y, + x: this.props?.staticPinPosition?.x, + y: this.props?.staticPinPosition?.y, }, imageSize: { height: this.props.contentHeight,