MarcL
MarcL

Reputation: 3593

React/Next.js how to get other Element event target value on button click

I have an input element and a button in React:

      <li><input type="text" placeholder="Enter new ID"></input>
      <button onClick={(e)=>this.saveKonfigElementHandler()}>Save</button></li>  

Now, when I enter some value into the input field, I want to save the value into some array when I click on the button. Is it somehow possible to get a reference to that input field (e.g. the target.value of the input field) to save it when clicking the button?

Or would I simply have to do it with an onChange event that saves the current input value into some Variable, and when I click the button, I will simply retrieve that value to save it into some array? Maybe that would be a lot simpler.

E.g:

<input type="text" value={this.state.inputFieldText.join('')} onChange={(event) => this.textHandler(event)}></input>

in the textHandler Method, I will save the target value from the input field into a Class Component state variable in the textHandler() method. And when I click the button, I retrieve that state value and can do some manipulation with it?

Upvotes: 4

Views: 24788

Answers (3)

acjay
acjay

Reputation: 36671

A modern way to do it, with function components, hooks and a controlled form element, is:

import { useState } from 'react'

function MyComponent({ initialId, onSave }) {
  const [newId, setNewId] = useState(initialId)

  return (
    <li>
      <input 
        type="text" 
        placeholder="Enter new ID" 
        onChange={(e) => setNewId(e.target.value)} 
      />
      <button onClick={() => onSave(newId)}>Save</button>
    </li>
  )
}

I'd also note that it is considered better accessibility practice to use a label element for describing the purpose of your field, rather than a placeholder. Placeholders are more appropriate for example input.

Upvotes: 9

Alexandre Mouyen
Alexandre Mouyen

Reputation: 109

I'm not sure about your question. Do you want something like this ?

<button data-input="#id-input" onClick={this.saveKonfigElementHandler(value)}>Save</button></li>

saveKonfigElementHandler = (value) => (event) => {}

Upvotes: 0

T.J. Crowder
T.J. Crowder

Reputation: 1075567

Is it somehow possible to get a reference to that input field (e.g. the target.value of the input field) to save it when clicking the button?

Yes.

Or would I simply have to do it with an onChange event that saves the current input value into some Variable, and when I click the button, I will simply retrieve that value to save it into some array? Maybe that would be a lot simpler.

That would be a slightly more React way to do it.

Your DOM-only approach is more "uncontrolled" (see these docs for what controlled/uncontrolled means). You'd do it like this:

  1. Change your onClick to pass e to the handler:

    onClick={(e)=>this.saveKonfigElementHandler(e)}
    
  2. In saveKonfigElementHandler, use e.target.previousElementSibling to access the input:

    saveKonfigElementHandler(e) {
        const { value } = e.target.previousElementSibling;
        // Use `value` ...
    }
    

That's fragile, of course; if you change your structure so another element is between the button and the input, or the input is within a container element, etc., it'll break — which is one argument for the controlled approach. You could store a link to the input in a data attribute on the button:

<li><input id="id-input" type="text" placeholder="Enter new ID"/>
<button data-input="#id-input" onClick={(e)=>this.saveKonfigElementHandler(e)}>Save</button></li> 

and then use querySelector to get it:

saveKonfigElementHandler(e) {
    const { value } = document.querySelector(e.target.getAttribute("data-input"));
    // Use `value` ...
}

but the you're having to keep selectors unique, etc.

Which you choose, controlled or uncontrolled, is ultimately up to you.

Upvotes: 2

Related Questions