React

onChange 이벤트란? (리액트에서 onChange 코드 리팩토링)

hihiha2 2023. 4. 26. 15:17

🔍 onChange 이벤트

input요소의 onChange 이벤트는 입력필드의 값을 변경할때 발생하는 이벤트

이벤트핸들러 함수를 통해 입력된 값에 대한 처리를 한다.

 

onChange 이벤트는 사용자가 입력필드에 값을 입력/삭제할때마다 발생하기 때문에 실시간으로 값을 업데이트하거나 다른 처리를 수행 

➡️ 사용자에게 좀 더 유연한 UI를 제공

 

🔍 형태 

<input type="text" onChange={handleInputChange} />

1️⃣ 사용하고 싶은 함수명을 바로 적어줘도 되고,

2️⃣ e 매개변수를 <input />안에서 바로 사용도 가능하다.

<input
            type="text"
            name="username"
            value={username}
            onChange={(event) => setUsername(event.target.value)}
            required
          />

 

 

🔫  onChange 코드 좀 더 나은 코드로  🔫

여러개의 input이 있으면 각각의 useState와 또 각각의 onChange함수를 만들어줘서 코드가 길어지는 경향이 있었다.

또한 함수를 따로 빼지 않고 input안에서 바로 e.target.value를 사용하기도 하였다.

이렇게만 해도 정상적으로 작동은 하지만, 코드의 가독성을 위해서 리팩토링을 하였다.

 

1. onChange 함수 따로 빼주기

코드의 가독성을 위해서 1️⃣ 함수명을 사용하는 방법을 사용하려고 한다.

 

 

위의 코드를 함수명을 사용한 코드로 바꿔보았다.

input안에는 함수명만 적고, 함수를 선언하여 그 함수 안에서 e.taarget.value를 사용하여 입력된 값을 가지고 오고 있다.

function Login() {
  const [username, setUsername] = useState("");

  const handleUsernameChange = (e) => {
    setUsername(e.target.value);
  };


  return (
          <input
            type="text"
            name="username"
            value={username}
            onChange={handleUsernameChange}
            required

다른 코드는 다 지우고 관련 코드만 남겨서 보면 위와 같다.

 

 

2개의 input을 다 보면, 아래의 코드와 같다. 

function Login() {
  const [username, setUsername] = useState("");
  const [password, setPassword] = useState("");

  const handleUsernameChange = (e) => {
    setUsername(e.target.value);
  };

  const handlePasswordChange = (e) => {
    setPassword(e.target.value);
  };


  return (
    
          <input
            type="text"
            name="username"
            value={username}
            onChange={handleUsernameChange}
            required
          />
          <label>Username</label>
        </div>
        <div className="user-box">
          <input
            type="password"
            name="password"
            value={password}
            onChange={handlePasswordChange}
            required
          />
          <label>Password</label>
        </div>
       
   
  );
}

export default Login;

 

 

 

 

2. 여러개의 input의 onChange를 한번에 관리하기

내가 만들고 있는 페이지에는 username과 password라는 2개의 input이 있다.

각각 useState를 만들고 그에 따른 각각의 onChange함수를 만들수도 있겠지만, 코드의 가독성을 위해서 하나로 합치는 작업을 해주었다.

 

여러개의 input을 하나로 합치는 방법

1️⃣ 여러개의 input을 하나로 관리하는 useState를 만들고, 초기값객체의 형태로 넣어준다. (객체의 key값은 각 input의 name과 일치시킨다)

const [inputs, setInputs] = useState({
username: "",
password: "",
});

 

 

2️⃣ username과 password를 구조분해할당을 통해 선언해준다.

const { username, password } = inputs;

이러한 작업을 하는 이유는 input의 value값으로 {username},{password}가 들어가있는데 이렇게 선언을 해주지 않으면 undefined가 뜬다. 기존에는 useState를 통해서 각각 선언을 해주었기때문에 그와 같은 작업을 해주어야한다.

 

기존에 각각 따로 useState를 만들었던 것을 하나로 합치는 작업이 = 1️⃣ + 2️⃣ 라고 할수있다

 

코드를 통해서 보면, 왼쪽코드오른쪽 코드 바꾼것이다.

 

3️⃣ onChange를 관리하는 하나의 이벤트핸들러함수를 만든다.

const handleChange = (e) => {
const { name, value } = e.target;
setInputs({
...inputs,
[name]: value,
});
};

...inputs를 통해서 기존의 input값들을 복사하고, [name]:value를 통해서 input안의 name의 value를 찾고, 그것을 새롭게 들어오는 e.target.value로 변경해줄 수 있다.

 

4️⃣ 각각의 input의 onChange의 값으로 handleChange를 넣어준다.

<input
type="text"
name="username"
value={username}
onChange={handleChange}
required
/>
<label>Username</label>
</div>
<div className="user-box">
<input
type="password"
name="password"
value={password}
onChange={handleChange}
required
/>
<label>Password</label>

 

 

 

 

 

💻 전체코드

function Login() {
  const [inputs, setInputs] = useState({
    username: "",
    password: "",
  });

  const { username, password } = inputs;

  const handleChange = (e) => {
    const { name, value } = e.target;
    setInputs({
      ...inputs,
      [name]: value,
    });
  };

  return (
  <>
          <input
            type="text"
            name="username"
            value={username}
            onChange={handleChange}
            required
          />
          <label>Username</label>
        </div>
        <div className="user-box">
          <input
            type="password"
            name="password"
            value={password}
            onChange={handleChange}
            required
          />
          <label>Password</label>
        </div>
     </>
  );
}

export default Login;

 

 

🕵️‍♀️ 느낀점

그냥 코드를 짜더라도 사실 작동을 하기 때문에 이런식으로 바꿔야한다는 생각은 못했는데,

공부를 하면서 이해가 되니까 조금 더 가독성이 좋은 코드를 짤수있게 되어서 좋다.

 

항상 더 가독성이 좋고 다른 사람들도 이해할 수 있는 코드를 짜고 싶다는 생각은 하는데 

공부와 이해가 부족하면 작동만 하는 코드를 짜게 되는 것같다.

 

onChange 이벤트핸들러와 useState를 통해 상태를 업데이트하는 것을 전부터 계속 해왔지만,

이번에 뭔가 더 확 와닿게 이해한것같아서 좋다.

앞으로도 하나하나 차근차근 다른 리액트 훅이나 자바스크립트 코드들도 이해를 바탕으로 더 좋은 코드로 바꿀수있도록 해야겠다.