Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

react-native-popover-view

Package Overview
Dependencies
Maintainers
1
Versions
76
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

react-native-popover-view - npm Package Compare versions

Comparing version 1.0.5 to 1.0.6

12

package.json
{
"name": "react-native-popover-view",
"version": "1.0.5",
"version": "1.0.6",
"description": "A <Popover /> component for react-native",

@@ -19,4 +19,3 @@ "main": "src/index.js",

"start": "node_modules/react-native/packager/packager.sh",
"test": "jest",
"postinstall": "node ./check-rn.js"
"test": "jest"
},

@@ -51,8 +50,3 @@ "jest": {

},
"peerDependencies": {
"react-navigation": ">=2.0.0"
},
"dependencies": {
"fs": "^0.0.1-security"
}
"dependencies": {}
}

@@ -16,2 +16,4 @@ 'use strict';

const DEBUG = true;
const PLACEMENT_OPTIONS = Object.freeze({

@@ -47,4 +49,3 @@ TOP: 'top',

translateArrow: new Animated.ValueXY()
},
viewport: null
}
};

@@ -57,9 +58,23 @@

setDefaultDisplayArea(evt) {
if (this.safeAreaViewReady || !isIOS()) {
let newDisplayArea = new Rect(evt.nativeEvent.layout.x + 10, evt.nativeEvent.layout.y + 10, evt.nativeEvent.layout.width - 20, evt.nativeEvent.layout.height - 20);
if (!this.state.defaultDisplayArea || rectChanged(this.state.defaultDisplayArea, newDisplayArea)) {
this.setState({defaultDisplayArea: newDisplayArea});//, () => this.handleGeomChange({displayArea: newDisplayArea}));
let newDisplayArea = new Rect(evt.nativeEvent.layout.x + 10, evt.nativeEvent.layout.y + 10, evt.nativeEvent.layout.width - 20, evt.nativeEvent.layout.height - 20);
if (!this.state.defaultDisplayArea || rectChanged(this.state.defaultDisplayArea, newDisplayArea)) {
if (DEBUG) console.log("setDefaultDisplayArea - newDisplayArea: " + JSON.stringify(newDisplayArea));
if (this.safeAreaViewReady || !isIOS()) {
this.setState({defaultDisplayArea: newDisplayArea}, () => {
this.calculateRect(this.props, fromRect => {
if (rectChanged(fromRect, this.state.fromRect)
|| rectChanged(this.getDisplayArea(), this.displayAreaStore)) {
this.displayAreaStore = this.getDisplayArea();
if (DEBUG) console.log("setDefaultDisplayArea (inside calculateRect callback) - fromRect: " + JSON.stringify(fromRect));
if (DEBUG) console.log("setDefaultDisplayArea (inside calculateRect callback) - getDisplayArea(): " + JSON.stringify(this.displayAreaStore));
this.setState({fromRect}, () => {
this.handleGeomChange();
this.waitForResizeToFinish = false;
});
}
})
});
}
this.safeAreaViewReady = true;
}
this.safeAreaViewReady = true;
}

@@ -72,3 +87,3 @@

keyboardDidHide() {
this.setState({shiftedDisplayArea: null}, () => this.handleGeomChange({displayArea: this.getDisplayArea()}));
this.setState({shiftedDisplayArea: null}, () => this.handleGeomChange());
}

@@ -87,3 +102,3 @@

height: combinedY - displayArea.y
}}, () => this.handleGeomChange({displayArea: this.state.shiftedDisplayArea}));
}}, () => this.handleGeomChange());
}

@@ -97,2 +112,8 @@

// This is used so that when the device is rotating or the viewport is expanding for any other reason,
// we can suspend updates due to content changes until we are finished calculating the new display
// area and rect for the new viewport size
// This makes the recalc on rotation much faster
this.waitForResizeToFinish = false;
// Show popover if isVisible is initially true

@@ -112,6 +133,12 @@ if (this.props.isVisible)

handleResizeEvent = (event) => this.setState({viewport: event.window});
// First thing called when device rotates
handleResizeEvent = (event) => {
if (this.props.isVisible) {
this.safeAreaViewReady = false;
this.waitForResizeToFinish = true;
}
}
measureContent(requestedContentSize) {
if (requestedContentSize.width && requestedContentSize.height) {
if (requestedContentSize.width && requestedContentSize.height && !this.waitForResizeToFinish) {
if (this.state.isAwaitingShow) {

@@ -125,3 +152,4 @@ if ((this.props.fromView && !this.state.fromRect) || !this.getDisplayArea() || !this.safeAreaViewReady) {

} else if (requestedContentSize.width !== this.state.requestedContentSize.width || requestedContentSize.height !== this.state.requestedContentSize.height) {
this.handleGeomChange({requestedContentSize});
if (DEBUG) console.log("measureContent - requestedContentSize: " + JSON.stringify(requestedContentSize));
this.handleGeomChange(requestedContentSize);
}

@@ -136,2 +164,7 @@ }

if (DEBUG) {
console.log("computeGeometry - displayArea: " + JSON.stringify(displayArea));
console.log("computeGeometry - fromRect: " + JSON.stringify(fromRect));
}
if (fromRect && isRect(fromRect)) {

@@ -438,11 +471,11 @@ //check to see if fromRect is outside of displayArea, and adjust if it is

getTranslateOrigin() {
const {forcedContentSize, requestedContentSize, popoverOrigin, anchorPoint} = this.state;
const {forcedContentSize, requestedContentSize, popoverOrigin, anchorPoint} = this.state;
const viewWidth = forcedContentSize.width || requestedContentSize.width || 0;
const viewHeight = forcedContentSize.height || requestedContentSize.height || 0;
const popoverCenter = new Point(popoverOrigin.x + (viewWidth / 2),
popoverOrigin.y + (viewHeight / 2));
const shiftHorizantal = anchorPoint.x - popoverCenter.x;
const shiftVertical = anchorPoint.y - popoverCenter.y;
return new Point(popoverOrigin.x + shiftHorizantal, popoverOrigin.y + shiftVertical);
const viewWidth = forcedContentSize.width || requestedContentSize.width || 0;
const viewHeight = forcedContentSize.height || requestedContentSize.height || 0;
const popoverCenter = new Point(popoverOrigin.x + (viewWidth / 2),
popoverOrigin.y + (viewHeight / 2));
const shiftHorizantal = anchorPoint.x - popoverCenter.x;
const shiftVertical = anchorPoint.y - popoverCenter.y;
return new Point(popoverOrigin.x + shiftHorizantal, popoverOrigin.y + shiftVertical);
}

@@ -454,28 +487,34 @@

componentWillReceiveProps(nextProps:any) {
let willBeVisible = nextProps.isVisible;
let {
isVisible,
displayArea
} = this.props;
componentWillReceiveProps(nextProps) {
if (willBeVisible !== isVisible) {
if (willBeVisible) {
// We want to start the show animation only when contentSize is known
// so that we can have some logic depending on the geometry
this.calculateRect(nextProps, fromRect => this.setState({fromRect, isAwaitingShow: true, visible: true}));
} else {
this.animateOut();
// Make sure a value we care about has actually changed
let importantProps = ["isVisible", "fromRect", "displayArea", "verticalOffset", "placement"]
if (!importantProps.reduce((acc, key) => acc || this.props[key] !== nextProps[key], false))
return;
let willBeVisible = nextProps.isVisible;
let {
isVisible,
displayArea
} = this.props;
if (willBeVisible !== isVisible) {
if (willBeVisible) {
// We want to start the show animation only when contentSize is known
// so that we can have some logic depending on the geometry
this.calculateRect(nextProps, fromRect => this.setState({fromRect, isAwaitingShow: true, visible: true}));
} else {
this.animateOut();
}
} else if (willBeVisible) {
this.calculateRect(nextProps, fromRect => {
if (rectChanged(fromRect, this.state.fromRect)
|| (nextProps.displayArea && !this.props.displayArea)
|| rectChanged(nextProps.displayArea, this.props.displayArea)
|| rectChanged(this.getDisplayArea(), this.displayAreaStore)) {
this.displayAreaStore = this.getDisplayArea();
this.setState({fromRect}, () => this.handleGeomChange());
}
} else if (willBeVisible) {
this.calculateRect(nextProps, fromRect => {
if (rectChanged(fromRect, this.state.fromRect)
|| (nextProps.displayArea && !this.props.displayArea)
|| rectChanged(nextProps.displayArea, this.props.displayArea)
|| rectChanged(this.getDisplayArea(), this.displayAreaStore)) {
this.displayAreaStore = this.getDisplayArea();
this.setState({fromRect}, () => this.handleGeomChange(Object.assign({}, nextProps, {fromRect})))
}
})
}
})
}
}

@@ -495,17 +534,28 @@

handleGeomChange({displayArea, fromRect, requestedContentSize}) {
handleGeomChange(requestedContentSize) {
const { forcedContentSize, placement, anchorPoint, popoverOrigin, animatedValues } = this.state;
requestedContentSize = requestedContentSize || Object.assign({}, this.state.requestedContentSize);
let geom = this.computeGeometry({requestedContentSize, displayArea, fromRect});
if (DEBUG) console.log("handleGeomChange - requestedContentSize: " + JSON.stringify(requestedContentSize));
if (pointChanged(geom.popoverOrigin, popoverOrigin)) {
// handleGeomChange may be called more than one times before the first has a chance to finish,
// so we use updateCount to make sure that we only trigger an animation on the last one
if (!this.updatesCount || this.updatesCount < 0) this.updateCount = 0;
this.updateCount++;
let geom = this.computeGeometry({requestedContentSize});
if (pointChanged(geom.popoverOrigin, popoverOrigin) || rectChanged(geom.forcedContentSize, forcedContentSize)) {
this.setState(Object.assign(geom, {requestedContentSize}), () => {
this.animateTo({
values: animatedValues,
fade: 1,
scale: 1,
translatePoint: new Point(geom.popoverOrigin.x, geom.popoverOrigin.y),
easing: Easing.inOut(Easing.quad)
});
if (this.updateCount <= 1) {
this.updateCount--;
if (DEBUG) console.log("handleGeomChange - Triggering popover move")
this.animateTo({
values: animatedValues,
fade: 1,
scale: 1,
translatePoint: new Point(geom.popoverOrigin.x, geom.popoverOrigin.y),
easing: Easing.inOut(Easing.quad)
});
}
});

@@ -597,105 +647,105 @@ }

render() {
var { popoverOrigin, placement, forcedHeight, animatedValues, anchorPoint, forcedContentSize } = this.state;
const { popoverStyle, arrowStyle } = this.props;
const { arrowWidth, arrowHeight } = this.getCalculatedArrowDims();
var { popoverOrigin, placement, forcedHeight, animatedValues, anchorPoint, forcedContentSize } = this.state;
const { popoverStyle, arrowStyle } = this.props;
const { arrowWidth, arrowHeight } = this.getCalculatedArrowDims();
let arrowScale = animatedValues.scale.interpolate({
inputRange: [0, 1],
outputRange: [0, 1],
extrapolate: 'clamp',
})
let arrowScale = animatedValues.scale.interpolate({
inputRange: [0, 1],
outputRange: [0, 1],
extrapolate: 'clamp',
})
var arrowViewStyle = {
position: 'absolute',
top: 0,
left: 0,
width: arrowWidth,
height: arrowHeight,
var arrowViewStyle = {
position: 'absolute',
top: 0,
left: 0,
width: arrowWidth,
height: arrowHeight,
transform: [
{translateX: animatedValues.translateArrow.x},
{translateY: animatedValues.translateArrow.y},
{scale: arrowScale},
]
};
let arrowInnerStyle = [
styles.arrow,
this.getArrowDynamicStyle(),
{
borderTopColor: arrowStyle.backgroundColor || popoverStyle.backgroundColor || styles.popoverContent.backgroundColor,
transform: [
{translateX: animatedValues.translateArrow.x},
{translateY: animatedValues.translateArrow.y},
{scale: arrowScale},
{rotate: this.getArrowRotation(placement)}
]
};
}
];
let arrowInnerStyle = [
styles.arrow,
this.getArrowDynamicStyle(),
{
borderTopColor: arrowStyle.backgroundColor || popoverStyle.backgroundColor || styles.popoverContent.backgroundColor,
transform: [
{rotate: this.getArrowRotation(placement)}
]
}
];
// Temp fix for useNativeDriver issue
let backgroundShift = animatedValues.fade.interpolate({
inputRange: [0, 0.0001, 1],
outputRange: [0, FIX_SHIFT, FIX_SHIFT]
})
// Temp fix for useNativeDriver issue
let backgroundShift = animatedValues.fade.interpolate({
inputRange: [0, 0.0001, 1],
outputRange: [0, FIX_SHIFT, FIX_SHIFT]
})
let backgroundStyle = {
...styles.background,
transform: [
{translateX: backgroundShift}
]
};
if (this.props.showBackground)
backgroundStyle.backgroundColor = 'rgba(0,0,0,0.5)'
let backgroundStyle = {
...styles.background,
transform: [
{translateX: backgroundShift}
]
};
if (this.props.showBackground)
backgroundStyle.backgroundColor = 'rgba(0,0,0,0.5)'
let containerStyle = {
...styles.container,
opacity: animatedValues.fade
};
let containerStyle = {
...styles.container,
opacity: animatedValues.fade
};
let popoverViewStyle = Object.assign({
maxWidth: forcedContentSize.width,
maxHeight: forcedContentSize.height,
position: 'absolute',
}, styles.dropShadow, styles.popoverContent, popoverStyle, {
transform: [
{translateX: animatedValues.translate.x},
{translateY: animatedValues.translate.y},
{scale: animatedValues.scale},
{perspective: 1000}
],
});
let popoverViewStyle = Object.assign({
maxWidth: forcedContentSize.width,
maxHeight: forcedContentSize.height,
position: 'absolute',
}, styles.dropShadow, styles.popoverContent, popoverStyle, {
transform: [
{translateX: animatedValues.translate.x},
{translateY: animatedValues.translate.y},
{scale: animatedValues.scale},
{perspective: 1000}
],
});
let contentView = (
<View style={[styles.container, {left: 0}]}>
<SafeAreaView pointerEvent="none" style={{position: 'absolute', top: 0, left: 0, right: 0, bottom: 0}}>
<View style={{flex: 1}} onLayout={evt => this.setDefaultDisplayArea(evt)} />
</SafeAreaView>
let contentView = (
<View style={[styles.container, {left: 0}]}>
<SafeAreaView pointerEvent="none" style={{position: 'absolute', top: 0, left: 0, right: 0, bottom: 0}}>
<View style={{flex: 1}} onLayout={evt => this.setDefaultDisplayArea(evt)} />
</SafeAreaView>
<Animated.View style={containerStyle}>
<TouchableWithoutFeedback onPress={this.props.onClose}>
<Animated.View style={backgroundStyle}/>
</TouchableWithoutFeedback>
<Animated.View style={containerStyle}>
<TouchableWithoutFeedback onPress={this.props.onClose}>
<Animated.View style={backgroundStyle}/>
</TouchableWithoutFeedback>
<View style={{top: 0, left: 0}}>
<Animated.View style={popoverViewStyle} onLayout={evt => this.measureContent(evt.nativeEvent.layout)}>
{this.props.children}
</Animated.View>
<View style={{top: 0, left: 0}}>
<Animated.View style={popoverViewStyle} onLayout={evt => this.measureContent(evt.nativeEvent.layout)}>
{this.props.children}
</Animated.View>
{(this.props.fromRect || this.state.fromRect) &&
<Animated.View style={arrowViewStyle}>
<View style={arrowInnerStyle}/>
</Animated.View>
}
</View>
</Animated.View>
</View>
);
{(this.props.fromRect || this.state.fromRect) &&
<Animated.View style={arrowViewStyle}>
<View style={arrowInnerStyle}/>
</Animated.View>
}
</View>
</Animated.View>
</View>
if (this.props.showInModal) {
return (
<Modal transparent={true} supportedOrientations={['portrait', 'landscape']} hardwareAccelerated={true} visible={this.state.visible} onRequestClose={this.props.onClose}>
{contentView}
</Modal>
);
if (this.props.showInModal) {
return (
<Modal transparent={true} supportedOrientations={['portrait', 'landscape']} hardwareAccelerated={true} visible={this.state.visible} onRequestClose={this.props.onClose}>
{contentView}
</Modal>
);
} else {
return contentView;
}
} else {
return contentView;
}
}

@@ -702,0 +752,0 @@ }

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc