8
votes

Afficher les images dans FlatList

J'essaie de rendre les images en mode grille à l'aide de FlatList mais j'ai été confronté au problème suivant:

Mon extrait de code:

...
renderItem = ({item}) => {
        return (
        <Image source = {{uri: item.photoUrl[0].photoUrl}} style = {{margin: 1,
                                                                    height: Dimensions.get('window').width / 3,
                                                                    width: Dimensions.get('window').width / 3,
                                                                    resizeMode: 'cover'}}
        />
    )
}

render() {
    if(this.props.viewOption === 'grid') {
        return <FlatList
                    data = {this.state.photosKeysArray}
                    keyExtractor={(item, index) => item.id}
                    numColumns = {3}
                    renderItem={this.renderItem}
                />
    } ...

Le problème est que FlatList devrait calculer la largeur de item par lui-même en fonction de numColumns , non? Donc dans Image je ne devrais spécifier que la hauteur. Puisque je veux rendre des images carrées, j'attribue à la hauteur une valeur égale à Dimensions.get ('window'). Width / 3 , où 3 est la valeur de numColumns .

Après cela, FlatList restitue des espaces vides au lieu d'images.

Si j'ajoute la propriété width à Image code> (comme dans mon extrait de code) et définissez-le comme hauteur (image carrée, vous vous souvenez?) puis FlatList rend 3 colonnes avec des images carrées mais elles sont affichées comme sur mon croquis (deux images complètes et la dernière colonne est coupée):

 entrez la description de l'image ici

Comment afficher trois colonnes complètes?


1 commentaires

Il est probablement préférable d'utiliser une propriété width de '33% 'sur le composant image


3 Réponses :


3
votes

numColumns

Plusieurs colonnes ne peuvent être rendues qu'avec horizontal = {false}

renderItem(item) {
    return (
        <TouchableOpacity>
            <View style={{
                width: (Constant.SCREEN.width - 32) / 3,
                height: (Constant.SCREEN.width - 32) / 3,
                justifyContent: 'center'
            }}>
                <Image style={{ width: '70%', height: '70%', alignSelf: 'center' }} resizeMode='contain' source={{ uri: item.image }}></Image>
                <SPText
                    style={{ flex: 1.0, textAlign: 'center', marginLeft: 4, marginRight: 4 }}
                    text={item.text}
                    fontSize={10}
                    textColor='white' />
            </View>
        </TouchableOpacity>
    )
}

renderItem

Élément de configuration (flex / largeur / hauteur) selon les exigences

<FlatList
   numColumns={3}
   data={this.state.data}
   renderItem={({ item }) => this.renderItem(item)}
/>


0 commentaires

0
votes

Le problème a été résolu en utilisant les valeurs suivantes de largeur et hauteur de l'image:

height: (Dimensions.get('window').width - (30 + 2*this.state.columns)) / this.state.columns,
width: (Dimensions.get('window').width - (30 + 2*this.state.columns)) / this.state.columns,

30 code> est la double marge (gauche et droite) de l'écran principal et 2 est la double marge de l'image.


0 commentaires

12
votes

Voulez-vous des carrés faciles? , ok alors vous devriez connaître cette propriété qui réagit native a, elle s'appelle Format d'image , il vous suffit de définir la largeur ou la hauteur, de définir le rapport hauteur / largeur sur 1 avec style et vous avez un carré.

Cela reste le même

renderItem(item) {
    return (
        <TouchableOpacity  
                 style={{flex:1/3, //here you can use flex:1 also
                 aspectRatio:1}}>
                <Image style={{flex: 1}} resizeMode='cover' source={{ uri:  item.photoUrl[0].photoUrl}}></Image>
        </TouchableOpacity>
    )
}

mais c'est plus simple

<FlatList
   numColumns={3}
   data={this.state.data}
   renderItem={({ item }) => this.renderItem(item)}
/>

Il convient de noter que si vous avez un élément supplémentaire sous toutes les lignes, et que vous utilisez flex: 1 au lieu de flex: 1/3 ça va être un grand, très grand carré, pour cela, vous pouvez utiliser les méthodes décrites ici


1 commentaires

Oh! Upvote cette réponse les gars. AspectRatio est la voie à suivre. Merci beaucoup @ValdaXD!