0

Basically, I'm trying to setup a Flatlist in which multiple values can be selected.

My problem is with the styling of elements, when clicked the first time they don't get highlighted but when clicked the 2nd time they get highlighted.

FlatList Code



renderRow = ({item}) => (
    <RowItem data={item} />
)

data = [
    {
        value: 'element1'
    },
    {
        value: 'element2'
    }
]


render(){
    return (
        <FlatList
            data={this.data}
            renderItem={this.renderRow}
            keyExtractor={(item, index) => item + index}/>
    )
}


RowItem Code

export default class RowItem extends React.Component {

    state = {
        isElementActive: false,
    }

    highlightElement = () => {
        this.setState(prevState => ({
            isElementActive: !prevState.isElementActive
        }))
    }

    render() {
        return (
            <TouchableOpacity 
                activeOpacity={0.7}
                onPress={this.highlightElement} 
                style={[styles.container, this.state.isElementActive ? styles.activeContainer : styles.inactiveContainer]}>
            <Text>{this.props.data.value}</Text>
            </TouchableOpacity>
        ) 
    }
}

const styles = Stylesheet.create({
    container: {
       height: 100,
       width: 300,
       backgroundColor: 'red',
    },
    activeContainer: {
        opacity: 0.7,
    },
    inactiveContainer: {
        opacity: 1,
    }
});

When clicking on the element once, the value of the isElementActive returns true (when I console.log it) but the styling "activeContainer" does not apply. However, when I click it again, the styling applies even though the value of isElementActive then becomes false.

By default the value starts off as false, and they are not highlighted (i.e. have opacity of 1) and for this reason I'm kind of confused when clicked the first time, the value of isElementActive changes but the styling does not apply.

  • Possible duplicate [Dynamic Opacity not changing when component rerenders in react native](https://stackoverflow.com/questions/47979866/dynamic-opacity-not-changing-when-component-rerenders-in-react-native?rq=1) . if it's a bug on the TouchableOpacity component, but the opacity won't update on a re-render until the component is clicked – Mehran Khan Sep 12 '19 at 03:45

1 Answers1

0

I was able to make it work with setOpacityTo after the setState.

Working example: https://snack.expo.io/SJNSKQPIB

import React from 'react';
import {TouchableOpacity, FlatList, StyleSheet, Text} from 'react-native';

type State = {
  active: boolean;
};

type Props = {
  value: string;
};

class RowItem extends React.Component<Props, State> {
  state = {
    active: null,
  };

  ref = null;

  highlightElement = () => {
    this.setState(
      prevState => ({
        active: !prevState.active,
      }),
      () => {
        this.ref.setOpacityTo(this.state.active ? 0.7 : 1);
      },
    );
  };

  render() {
    return (
      <TouchableOpacity
        ref={ref => (this.ref = ref)}
        onPress={this.highlightElement}
        style={[styles.container]}>
        <Text>{this.props.value}</Text>
      </TouchableOpacity>
    );
  }
}

const styles = StyleSheet.create({
  container: {
    flex: 1,
    height: 100,
    backgroundColor: 'red',
  },
});

export default class App extends React.Component {
  data = [
    {
      value: 'element1',
    },
    {
      value: 'element2',
    },
  ];

  render() {
    return (
      <FlatList
        keyExtractor={(_, index) => index.toString()}
        data={this.data}
        renderItem={({item}) => <RowItem value={item.value} />}
      />
    );
  }
}

Pedro Henrique
  • 394
  • 1
  • 6