Home > database >  Onclick button, state doesn't change
Onclick button, state doesn't change

Time:11-05

I'm having some troubles understanding the code. Basically if I do this:

<Text onPress={() => console.log('123')} >123</Text> , and I click on the text, it logs me 123 each click.

But I'm doing a dialer app. Basically having a component Tile (representing a single number, also with secondary option (but that will be dealt with later)). So as I'm including my (currently only single one) Tile in App.js, I want onPress event to call function that changes state of currently dialed number. So if user clicks 3 times on '1', I want the final string to be 111. The thing is, I can see that the handleNumber() function is called once after running code and never again after clicking on the number, therefore never changing state, not logging anything.

App.js Tile implementation:


const [getNumber, setNumber] = useState();

  const handleNumber = (newChar) => {
    console.log(newChar);

    setNumber(newChar);
  }

<Tile onPress={() => handleNumber('1')} style={styles.tile} firstChar={'1'} secondChar={'✉'}/>

Tile.js:

const Tile = (props) => {
    return (
        <TouchableOpacity onPress={props.onPress()}> 
            <View>
                <Text style={styles.mainChar}>{props.firstChar}</Text>
                {props.secondChar ? <Text style={styles.secondChar}>{props.secondChar}</Text> : null}
            </View>
        </TouchableOpacity>
    )
}

One more thing: As you can see in App.js::handleNumber(), the implementation is currently wrong, because the final number will always be just the new single number, instead of appending it to the end of string. But if I wanted to do smth like setNumber(getNumber newChar), it would give Maximum update depth exceeded error.

CodePudding user response:

The thing here is the way that you're passing the onPress prop to TouchableOpacity. See, you're calling the props.onPress function instead of just passing it to the component, which causes the function to be executed when the component renders (or rerenders).

You should be fine just by using <TouchableOpacity onPress={props.onPress}> and then setNumber(getNumber newChar) will be fine as well.

As a side note, you could initialize your App.js state with the '1' string that you wish to be your initial value (const [getNumber, setNumber] = useState('1')), and then the Tile component can receive getNumber directly.

  • Related