平面表测量项目X位置 [英] Flatlist measure Items X position
本文介绍了平面表测量项目X位置的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!
问题描述
我的水平列表中有大约10个项目。我如下所示存储了对每个项目的引用。
const Item = ({ title, image, index }) => {
linkRefs[index] = useRef(null);
return (
<Animated.View ref={linkRefs[index]}>
<Image
resizeMode="cover"
style={styles.tinyLogo}
source={{
uri: image,
}}
/>
</Animated.View>
);
};
我想获取可见元素的X位置。所以我尝试了下面的代码,它运行良好。
const Measure = () => {
Object.keys(itemsY).forEach(function (key) {
linkRefs[key].current.measure((x, y, width, height, pageX, pageY) => {
if(typeof pageX != "undefined")
{
itemsY[key].setValue(pageX);
console.log(key+"--"+pageX);
console.log("width--"+width);
console.log("---");
}
});
});
};
问题是,测量仅对完全可见的项目起作用。我甚至希望测量位置,即使它很少可见。我该如何做?
我尝试了itemVisiblePercentThreshold,仍然只对完全可见的项进行度量。
const viewabilityConfig = useRef({
itemVisiblePercentThreshold:20
}).current;
<Animated.FlatList
horizontal
pagingenabled
snapToInterval={125}
snapToAlignment="center"
decelerationRate="fast"
showsVerticalScrollIndicator={true}
showsHorizontalScrollIndicator={false}
data={DATA}
renderItem={renderItem}
keyExtractor={item => item.id}
initialNumToRender={4}
horizontal={true}
viewabilityConfig={viewabilityConfig}
/>
推荐答案
当我使用平面列表时,我决定想知道列表滚动的方向,所以我最终使用onScroll道具来获取该值:
import React , { useState, useRef,useCallback } from 'react';
import { SafeAreaView, Image , View, FlatList, StyleSheet, Text, StatusBar } from 'react-native';
import { Ionicons, MaterialCommunityIcons , FontAwesome5 } from "@expo/vector-icons";
import * as Animatable from 'react-native-animatable';
import FlatListWrapper from "../components/FlatListWrapper";
const FlatListAnimation = () => {
const DATA = [
{
id: 'bd7acbea-c1b1-46c2-aed5-3ad53abb28ba',
title: 'First Item Item Item',
image : 'https://res.cloudinary.com/Sony-liv/image/fetch/c_fill,e_brightness:10,f_auto,fl_lossy,h_494,q_auto:low,w_344/https://origin-staticv2.sonyliv.com/portrait_thumb/scam_Lang_Protrait_Thumb.jpg'
},
{
id: '3ac68afc-c605-48d3-a4f8-fbd91aa97f63',
title: 'Second Item',
image : 'https://res.cloudinary.com/Sony-liv/image/fetch/c_fill,e_brightness:10,f_auto,fl_lossy,h_494,q_auto:low,w_344/https://origin-staticv2.sonyliv.com/portrait_thumb/Ramsingh-CharlieA_07062021_Lang_Protrait_Thumb.jpg'
},
{
id: '58694a0f-3da1-471f-bd96-145571e29d72-3-3',
title: 'Third Item',
image : 'https://res.cloudinary.com/Sony-liv/image/fetch/c_fill,e_brightness:10,f_auto,fl_lossy,h_494,q_auto:low,w_344/https://origin-staticv2.sonyliv.com/portrait_thumb/6028647473001.jpg'
},
{
id: '58694a0sdsf-3da1-471f-bd96-145571e29d72-4-4',
title: 'Fourth Item',
image : 'https://res.cloudinary.com/Sony-liv/image/fetch/c_fill,e_brightness:10,f_auto,fl_lossy,h_494,q_auto:low,w_344/https://origin-staticv2.sonyliv.com/portrait_thumb/6033313370001.jpg'
},
{
id: '58694a0f-3ddsda1-471f-bd96-145571e29d72-5-5',
title: 'Fifth Item',
image : 'https://res.cloudinary.com/Sony-liv/image/fetch/c_fill,e_brightness:10,f_auto,fl_lossy,h_494,q_auto:low,w_344/https://origin-staticv2.sonyliv.com/portrait_thumb/6033325319001_v2.jpg'
},
{
id: 'bd7acbea-c1b1-46c2-aed5-3ad531abb28ba-6-6',
title: 'Sixth Item Item Item',
image : 'https://res.cloudinary.com/Sony-liv/image/fetch/c_fill,e_brightness:10,f_auto,fl_lossy,h_494,q_auto:low,w_344/https://origin-staticv2.sonyliv.com/portrait_thumb/scam_Lang_Protrait_Thumb.jpg'
},
{
id: '3ac68afc-c605-48d3-a4f8-fbd912aa97f63-7-7',
title: 'Seventh Item',
image : 'https://res.cloudinary.com/Sony-liv/image/fetch/c_fill,e_brightness:10,f_auto,fl_lossy,h_494,q_auto:low,w_344/https://origin-staticv2.sonyliv.com/portrait_thumb/Ramsingh-CharlieA_07062021_Lang_Protrait_Thumb.jpg'
},
{
id: '58694a0f-3da1-471f-bd96-1455371e29d72-8-8',
title: 'Eighth Item',
image : 'https://res.cloudinary.com/Sony-liv/image/fetch/c_fill,e_brightness:10,f_auto,fl_lossy,h_494,q_auto:low,w_344/https://origin-staticv2.sonyliv.com/portrait_thumb/6028647473001.jpg'
},
{
id: '58694a0sdsf-3da1-471f-bd96-1445571e29d72-9-9',
title: 'Ninth Item',
image : 'https://res.cloudinary.com/Sony-liv/image/fetch/c_fill,e_brightness:10,f_auto,fl_lossy,h_494,q_auto:low,w_344/https://origin-staticv2.sonyliv.com/portrait_thumb/6033313370001.jpg'
},
];
const maxlimit = 20;
// store the indices of the viewableItmes
const [ viewableItemsIndices, setViewableItemsIndices ] = useState([]);
const itemRefs = useRef(
DATA.map( item=> {})
);
const isScrollingForward = useRef(true);
// use last and current scroll position to determine scroll direction
const lastScrollPosition = useRef(0);
const handleScroll = ({nativeEvent})=>{
let currentPosition = nativeEvent.contentOffset.x
isScrollingForward.current = currentPosition > lastScrollPosition.current
lastScrollPosition.current = currentPosition
}
// Item.js
const Item = (props) => {
let {
item:{ image , title, isViewable },
index
} = props
return (
//add animation to Animated.View
<Animatable.View style={styles.itemContainer} ref={ref=>itemRefs[index]=ref} >
<Image
resizeMode="contain"
style={styles.tinyLogo}
source={{
uri: image,
}}
/>
</Animatable.View>
);
}
return (
<SafeAreaView style={styles.container}>
<FlatListWrapper
horizontal={true}
//{/*give each data item an isViewable prop*/}
data={ DATA }
renderItem={(item,i)=><Item {...item} />}
keyExtractor={item => item.id}
onViewableItemsChanged={({viewableItems, changed})=>{
let duration = 2000;
viewableItems.forEach(item=>{
let itemRef = itemRefs[item.index];
itemRef?.transitionTo({opacity:1},duration)
isScrollingForward.current ?
itemRef?.bounceInRight() :
itemRef?.bounceInLeft()
})
changed.forEach(item=>{
let itemRef = itemRefs[item.index];
if(!item.isViewable){
itemRef?.transitionTo({opacity:0})
isScrollingForward.current ?
itemRef?.bounceOutLeft() :
itemRef?.bounceInRight()
}
})
}}
//{/*config that decides when an item is viewable*/}
viewabilityConfig={{itemVisiblePercentThreshold:100}}
onScroll={handleScroll}
disableScrollMomentum={true}
/>
{/* Extra stuff that just tells you what items should be visible*/}
<Text>Items that should be visible:</Text>
{viewableItemsIndices.map(i=><Text key={'text-'+i}> {DATA[i].title}</Text>)}
</SafeAreaView>
);
}
const styles = StyleSheet.create({
container: {
// flex: 1,
marginTop: StatusBar.currentHeight || 0,
},
itemContainer: {
opacity:0
},
title: {
fontSize: 32,
},
tinyLogo: {
borderRadius : 4,
width: 150,
height:150
},
});
export default FlatListAnimation;
这篇关于平面表测量项目X位置的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!
查看全文