如何根据在本机中呈现的项目数来设置项目的宽度

how to set up a width of an item depending on how many items render in react native

我正在渲染来自循环值的平面列表项目,它当前正在渲染 5 个项目,我想根据正在渲染的数量更改这些项目的宽度,例如,如果我想渲染 10 个项目,宽度将相应调整。我尝试了不同的方法,但 none 似乎有效。 ps:我的目标是在不需要滚动的情况下呈现这些项目,我希望完全显示这 10 个项目

到目前为止,这是我的代码:

    import React, { useEffect, useState } from 'react';
import { View, FlatList, Text, TouchableOpacity } from 'react-native';
import { StyleSheet } from 'react-native';
import { Button } from 'react-native-paper';

export default function Detailmodal({ value, update, setModal }) {
    const [ max, setMax ] = useState(35);
    const [ min, setMin ] = useState(30);
    const [ data, setData ] = useState([]);

    useEffect(
        () => {
            let tempData = [];

            for (let i = min; i <= max; i++) {
                tempData.push(i);
            }
            setData(tempData);
        },
        [ min, max ]
    );

    const toggleNext = () => {
        setMin(max);
        setMax(max + 5);
    };

    const togglePrev = () => {
        setMax(min);
        setMin(min - 5);
    };

    const Item = ({ value }) => (
        <TouchableOpacity onPress={() => updateParent(value)}>
            <View style={styles.temp}>
                <Text style={styles.title}>{value}</Text>
            </View>
        </TouchableOpacity>
    );

    const renderItem = ({ item }) => {
        return <Item value={item} />;
    };

    const updateParent = (value) => {
        update(value);
        setModal(false);
    };

    return (
        <View style={styles.container}>
            <Button mode='contained' onPress={togglePrev}>
                prev
            </Button>
            <FlatList data={data} renderItem={renderItem} keyExtractor={(item) => item.name} horizontal />
            <Button mode='contained' onPress={toggleNext}>
                next
            </Button>
        </View>
    );
}

const styles = StyleSheet.create({
    container             : {
        flexDirection   : 'row',
        justifyContent  : 'center',
        alignItems      : 'center',
        margin          : 50,
        paddingVertical : 50,
        backgroundColor : 'white'
    },
    contentContainerStyle : {
        justifyContent : 'center',
        alignItems     : 'center'
    },
    value                 : {
        fontWeight : '500',
        fontSize   : 50,
        color      : 'black',
        position   : 'absolute'
    },
    txtInput              : {
        fontSize  : 25,
        textAlign : 'center'
    },
    temp                  : {
        backgroundColor  : '#b19cd9',
        height           : 170,
        justifyContent   : 'center',
        marginVertical   : 20,
        marginHorizontal : 15,
        padding          : 15,
        width            : 140,

        alignItems       : 'center'
    },
    title                 : {
        fontSize : 32
    }
});

您确定要这种方法吗?因为如果有 100 个项目,不滚动显示全部会有点乱

如果是,那么您想要那种方法 -> 请在此处查看工作解决方案:snakc link

您可以更改样式。 基本上我在方法 calculateWidth.

中添加了一个 10px 的填充

解决方法如下:

import { View, FlatList, Text, TouchableOpacity,Dimensions } from 'react-native';
import { StyleSheet } from 'react-native';
import { Button } from 'react-native-paper';

export default function Detailmodal({ value, update, setModal }) {
    const [ max, setMax ] = useState(35);
    const [ min, setMin ] = useState(30);
    const [ data, setData ] = useState([]);

    const deviceWidth = Dimensions.get('window').width;

    useEffect(
        () => {
            let tempData = [];

            for (let i = min; i <= max; i++) {
                tempData.push(i);
            }
            setData(tempData);
        },
        [ min, max ]
    );

    const toggleNext = () => {
        setMin(max);
        setMax(max + 5);
    };

    const togglePrev = () => {
        setMax(min);
        setMin(min - 5);
    };

    const calculateWidth = () => {
      const dataLength = data.length;
      const paddingRequired = (dataLength+2)*10;
      const finalWidth = (deviceWidth - paddingRequired)/dataLength;
      return finalWidth;

    }

    const Item = ({ value }) => {
      const width = calculateWidth()
      return(
        <TouchableOpacity style={[styles.temp,{width:width}]} onPress={() => updateParent(value)}>
                <Text style={styles.title}>{value}</Text>
        </TouchableOpacity>
      )
       
    }

    const renderItem = ({ item }) => {
        return <Item value={item} />;
    };

    const updateParent = (value) => {
        update(value);
        setModal(false);
    };

    return (
        <View style={styles.container}>
            <Button mode='contained' onPress={togglePrev}>
                prev
            </Button>
            <FlatList data={data} renderItem={renderItem} keyExtractor={(item) => item.name} horizontal />
            <Button mode='contained' onPress={toggleNext}>
                next
            </Button>
        </View>
    );
}

const styles = StyleSheet.create({
    container             : {
        justifyContent  : 'center',
        alignItems      : 'center',
        backgroundColor : 'white'
    },
    contentContainerStyle : {
        justifyContent : 'center',
        alignItems     : 'center'
    },
    value                 : {
        fontWeight : '500',
        fontSize   : 50,
        color      : 'black',
        position   : 'absolute'
    },
    txtInput              : {
        fontSize  : 25,
        textAlign : 'center'
    },
    temp                  : {
        backgroundColor  : '#b19cd9',
        height           : 170,
        justifyContent   : 'center',
        marginVertical   : 20,
        marginHorizontal : 5,
        // padding          : 15,
        // width            : 140,

        alignItems       : 'center'
    },
    title                 : {
        fontSize : 32
    }
});