0

i'm rendering an string array 'options' as this

<View ref={refInput}>
        {options.map((item, index) => (
          <View key={index}>
            <View style={{ display: "flex", flexDirection: "row" }}>
              <TextInput placeholder={item}></TextInput>
              {options.length > 2 && index === options.length - 1 && (
                <TouchableOpacity onPress={removeOption}>
                  <Text>Remover</Text>
                </TouchableOpacity>
              )}
            </View>
            {index >= options.length - 1 && index < 3 && (
              <TouchableOpacity onPress={() => addOption(index)}>
                <Text>Adicionar</Text>
              </TouchableOpacity>
            )}
          </View>
        ))}
      </View>

For each element in my array i'm rendering a text input. It starts with 2 and can go up to 4 inputs. What is the best way to get those inputs values?

I passed a ref to the first View that renders the map and i have a function that get that ref by

const input = refInput.current

It returns to me a HTML collection that's a bit complicated to iterate and i don't even know how to type it with typescript.

So is there a better way to get the values?

1 Answer 1

1

You could store the input values inside a state. Since you have multiple inputs that you generate dynamically inside a loop, we could store these states inside a state array and induce a bijection between indices and input values.

Here is one possible implementation using your initial code as a basis.

const [values, setValues] = useState([]);

React.useEffect(() => {
    setValues(options.map(item => ""));
}, [options])

function handleTextChange(index, newValue) {
    setValues(prev => prev.map((val, i) => index === i ? newValue : val))
}

<View ref={refInput}>
        {options.map((item, index) => (
          <View key={index}>
            <View style={{ display: "flex", flexDirection: "row" }}>
              <TextInput onChangeText={(newValue) => handleTextChange(index, newValue)} value={values[index]} placeholder={item}></TextInput>
              {options.length > 2 && index === options.length - 1 && (
                <TouchableOpacity onPress={removeOption}>
                  <Text>Remover</Text>
                </TouchableOpacity>
              )}
            </View>
            {index >= options.length - 1 && index < 3 && (
              <TouchableOpacity onPress={() => addOption(index)}>
                <Text>Adicionar</Text>
              </TouchableOpacity>
            )}
          </View>
        ))}
      </View>
Sign up to request clarification or add additional context in comments.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.