質問の内容に不備がありましたので、再度こちらにて訂正させて載せさせていただきます。
React Native Mapというライブラリで、Animated Viewを表示できるようにしたいと考えています。
こちらのリンク先にあるAnimatedView.jsをコピペするとちゃんと表示されるのですが、自前のデータベースからFetchしてきたデータを当てようとすると下記のエラーが生じてしまいます。
Invariant Violation: outputRange must have at least 2 elements
※こちらのエラーをぐぐってみたのですが、未解決のようです。。。
変更点は下記の部分です。
Fetchするためのredux追加
JavaScript
1・・・ 2const mapStateToProps = (state) => { 3 const markers = _.orderBy(state.markers, ['id'], ['desc']); 4 5 return { markers }; 6}; 7 8export default connect(mapStateToProps, { 9 markersFetch 10})(AnimatedViews);
this.stateで出していたmarkersをthis.propsで書き換え
JavaScript
1 const { 2 ・・・ 3 markers 4 } = this.state;
上記の部分を下記のように書き換えました。
JavaScript
1 const { markers } = this.props;
どのようにして解決すればよろしいでしょうか・・・。
お手数ですが、おたすけくださいませ。
▼ソースコードはこちらです
JavaScript
1・・・ 2 3function getMarkerState(panX, panY, scrollY, i) { 4 const xLeft = (-SNAP_WIDTH * i) + (SNAP_WIDTH / 2); 5 const xRight = (-SNAP_WIDTH * i) - (SNAP_WIDTH / 2); 6 const xPos = -SNAP_WIDTH * i; 7 8 const isIndex = panX.interpolate({ 9 inputRange: [xRight - 1, xRight, xLeft, xLeft + 1], 10 outputRange: [0, 1, 1, 0], 11 extrapolate: 'clamp', 12 }); 13 14 const isNotIndex = panX.interpolate({ 15 inputRange: [xRight - 1, xRight, xLeft, xLeft + 1], 16 outputRange: [1, 0, 0, 1], 17 extrapolate: 'clamp', 18 }); 19 20 const center = panX.interpolate({ 21 inputRange: [xPos - 10, xPos, xPos + 10], 22 outputRange: [0, 1, 0], 23 extrapolate: 'clamp', 24 }); 25 26 const selected = panX.interpolate({ 27 inputRange: [xRight, xPos, xLeft], 28 outputRange: [0, 1, 0], 29 extrapolate: 'clamp', 30 }); 31 32 const translateY = Animated.multiply(isIndex, panY); 33 34 const translateX = panX; 35 36 const anim = Animated.multiply(isIndex, scrollY.interpolate({ 37 inputRange: [0, BREAKPOINT1], 38 outputRange: [0, 1], 39 extrapolate: 'clamp', 40 })); 41 42 const scale = Animated.add(ONE, Animated.multiply(isIndex, scrollY.interpolate({ 43 inputRange: [BREAKPOINT1, BREAKPOINT2], 44 outputRange: [0, SCALE_END - 1], 45 extrapolate: 'clamp', 46 }))); 47 48 // [0 => 1] 49 let opacity = scrollY.interpolate({ 50 inputRange: [BREAKPOINT1, BREAKPOINT2], 51 outputRange: [0, 1], 52 extrapolate: 'clamp', 53 }); 54 55 // if i === index: [0 => 0] 56 // if i !== index: [0 => 1] 57 opacity = Animated.multiply(isNotIndex, opacity); 58 59 60 // if i === index: [1 => 1] 61 // if i !== index: [1 => 0] 62 opacity = opacity.interpolate({ 63 inputRange: [0, 1], 64 outputRange: [1, 0], 65 }); 66 67 let markerOpacity = scrollY.interpolate({ 68 inputRange: [0, BREAKPOINT1], 69 outputRange: [0, 1], 70 extrapolate: 'clamp', 71 }); 72 73 markerOpacity = Animated.multiply(isNotIndex, markerOpacity).interpolate({ 74 inputRange: [0, 1], 75 outputRange: [1, 0], 76 }); 77 78 const markerScale = selected.interpolate({ 79 inputRange: [0, 1], 80 outputRange: [1, 1.2], 81 }); 82 83 return { 84 translateY, 85 translateX, 86 scale, 87 opacity, 88 anim, 89 center, 90 selected, 91 markerOpacity, 92 markerScale, 93 }; 94} 95 96class AnimatedViews extends React.Component { 97 constructor(props) { 98 super(props); 99 100 const { markers } = this.props; 101 102 const panX = new Animated.Value(0); 103 const panY = new Animated.Value(0); 104 105 const scrollY = panY.interpolate({ 106 inputRange: [-1, 1], 107 outputRange: [1, -1], 108 }); 109 110 const scrollX = panX.interpolate({ 111 inputRange: [-1, 1], 112 outputRange: [1, -1], 113 }); 114 115 const scale = scrollY.interpolate({ 116 inputRange: [0, BREAKPOINT1], 117 outputRange: [1, 1.6], 118 extrapolate: 'clamp', 119 }); 120 121 const translateY = scrollY.interpolate({ 122 inputRange: [0, BREAKPOINT1], 123 outputRange: [0, -100], 124 extrapolate: 'clamp', 125 }); 126 127 const animations = markers.map((m, i) => 128 getMarkerState(panX, panY, scrollY, i)); 129 130 this.state = { 131 panX, 132 panY, 133 animations, 134 index: 0, 135 canMoveHorizontal: true, 136 scrollY, 137 scrollX, 138 scale, 139 translateY, 140 region: new AnimatedRegion({ 141 latitude: LATITUDE, 142 longitude: LONGITUDE, 143 latitudeDelta: LATITUDE_DELTA, 144 longitudeDelta: LONGITUDE_DELTA, 145 }), 146 }; 147 } 148 149 componentDidMount() { 150 const { region, panX, panY, scrollX } = this.state; 151 const { markers } = this.props; 152 153 panX.addListener(this.onPanXChange); 154 panY.addListener(this.onPanYChange); 155 156 region.stopAnimation(); 157 region.timing({ 158 latitude: scrollX.interpolate({ 159 inputRange: markers.map((m, i) => i * SNAP_WIDTH), 160 outputRange: markers.map(m => m.coordinate.latitude), 161 }), 162 longitude: scrollX.interpolate({ 163 inputRange: markers.map((m, i) => i * SNAP_WIDTH), 164 outputRange: markers.map(m => m.coordinate.longitude), 165 }), 166 duration: 0, 167 }).start(); 168 } 169 170 onStartShouldSetPanResponder = (e) => { 171 // we only want to move the view if they are starting the gesture on top 172 // of the view, so this calculates that and returns true if so. If we return 173 // false, the gesture should get passed to the map view appropriately. 174 const { panY } = this.state; 175 const { pageY } = e.nativeEvent; 176 const topOfMainWindow = ITEM_PREVIEW_HEIGHT + panY.__getValue(); 177 const topOfTap = screen.height - pageY; 178 179 return topOfTap < topOfMainWindow; 180 } 181 182 onMoveShouldSetPanResponder = (e) => { 183 const { panY } = this.state; 184 const { pageY } = e.nativeEvent; 185 const topOfMainWindow = ITEM_PREVIEW_HEIGHT + panY.__getValue(); 186 const topOfTap = screen.height - pageY; 187 188 return topOfTap < topOfMainWindow; 189 } 190 191 onPanXChange = ({ value }) => { 192 const { index } = this.state; 193 const newIndex = Math.floor(((-1 * value) + (SNAP_WIDTH / 2)) / SNAP_WIDTH); 194 if (index !== newIndex) { 195 this.setState({ index: newIndex }); 196 } 197 } 198 199 onPanYChange = ({ value }) => { 200 const { canMoveHorizontal, region, scrollY, scrollX, index } = this.state; 201 const { markers } = this.props; 202 203・・・ 204 205 onRegionChange(/* region */) { 206 // this.state.region.setValue(region); 207 } 208 209 render() { 210 const { 211 panX, 212 panY, 213 animations, 214 canMoveHorizontal, 215 region, 216 } = this.state; 217 const { markers } = this.props; 218 219 return ( 220 <View style={styles.container}> 221 <PanController 222 style={styles.container} 223 vertical 224 horizontal={canMoveHorizontal} 225 xMode="snap" 226 snapSpacingX={SNAP_WIDTH} 227 yBounds={[-1 * screen.height, 0]} 228 xBounds={[-screen.width * (markers.length - 1), 0]} 229 panY={panY} 230 panX={panX} 231 onStartShouldSetPanResponder={this.onStartShouldSetPanResponder} 232 onMoveShouldSetPanResponder={this.onMoveShouldSetPanResponder} 233 > 234 <AnimatedMap 235 provider={this.props.provider} 236 style={styles.map} 237 region={region} 238 onRegionChange={this.onRegionChange} 239 > 240 {markers.map((marker, i) => { 241 const { 242 selected, 243 markerOpacity, 244 markerScale, 245 } = animations[i]; 246 247 return ( 248 <Marker 249 key={marker.id} 250 coordinate={marker.coordinate} 251 > 252 <PriceMarker 253 style={{ 254 opacity: markerOpacity, 255 transform: [ 256 { scale: markerScale }, 257 ], 258 }} 259 amount={marker.amount} 260 selected={selected} 261 /> 262 </Marker> 263 ); 264 })} 265 </AnimatedMap> 266 <View style={styles.itemContainer}> 267 {markers.map((marker, i) => { 268 const { 269 translateY, 270 translateX, 271 scale, 272 opacity, 273 } = animations[i]; 274 275 return ( 276 <Animated.View 277 key={marker.id} 278 style={[styles.item, { 279 opacity, 280 transform: [ 281 { translateY }, 282 { translateX }, 283 { scale }, 284 ], 285 }]} 286 /> 287 ); 288 })} 289 </View> 290 </PanController> 291 </View> 292 ); 293 } 294} 295 296AnimatedViews.propTypes = { 297 provider: ProviderPropType, 298}; 299 300 ... 301 302const mapStateToProps = (state) => { 303 const markers = _.orderBy(state.markers, ['id'], ['desc']); 304 305 return { markers }; 306}; 307 308export default connect(mapStateToProps, { 309 markersFetch 310})(AnimatedViews);
回答4件
あなたの回答
tips
プレビュー
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
2018/05/15 06:11