코딩응애의 개발블로그

Main-Project 하면서 배운 내용 (select box, useRef) 본문

코드스테이츠(부트캠프)

Main-Project 하면서 배운 내용 (select box, useRef)

이너멜 2022. 11. 17. 01:22

이거 구현할려고 하는데 처음에는 이걸 뭐라고 부르는지 몰라서 한참을 찾다가 select 태그를 찾게되고 구현을 시작을 하게 됨 

내가 최종적으로 구현을 할려는건 지역에 따른 군/구를 선택할수 있도록 구현하는게 목표였다

예를들어 네이버 카페처럼 게시판에 따라서 말머리가 달라지는 그러니까 

이렇게 구현을 할려고 하는데 처음엔 이런식으로 하니까 

<select>
	  <option value="서울특별시">서울특별시</option>
      <option value="부산광역시">부산광역시</option>
      <option value="인천광역시">인천광역시</option>
      <option value="대구광역시">대구광역시</option>
      <option value="대전광역시">대전광역시</option>
      <option value="광주광역시">광주광역시</option>
      <option value="울산광역시">울산광역시</option>
    </select>
    <select
      className="selectDistrict">
      <option value="서울특별시">강남구</option>
      <option value="서울특별시">강동구</option>
      <option value="서울특별시">강북구</option>
      <option value="인천광역시">남구</option>
      <option value="서울특별시">관악구</option>
      <option value="서울특별시">광진구</option>
      <option value="서울특별시">구로구</option>
      <option value="서울특별시">금천구</option>
      <option value="서울특별시">노원구</option>
      <option value="서울특별시">도봉구</option>
    </select>

앞에 select box가 서울이든 경기도든 간에 2번째 select box가 지역에 맞게 안바뀌고 들어가 있어서 지역에 따라서 

다르게 나오게 어떻게 구현을 해야할까 엄청 오래 걸렸다 그러다가 

https://imivory.tistory.com/9   이분 코드를 참고해서 내 나름대로 리액트로 바꿔서 했는데 

이분 코드중에 var target = document.getElementById("good"); 이렇게 특정 DOM을 자바스크립트로 하는 코드가 있는데 

지금 내가 리액트로 하는 거니가 리액트로 이렇게 하는 방법은 없을까 하고 검색을 해보니 useRef()라는 것을 쓰면 된다고 한다

useRef()

js에서는 특정 DOM을 선택할때 위에쓴 코드처럼 DOM selector 함수를 사용해서 선택을 하는데 리액트에서는 ref라는 것을 사용한다 그리고 이 ref를 사용하기 위해선 useRef라는 hook을 사용을 해야 한다 

import { useRef} from 'react';

const Test() => {
    const 원하는변수명 = useRef();
    .
    .
    .
    return(
    <div>
    	<input
        ref={원하는변수명}/>
    </div>
    )
    
}

먼저 useRef()를 이용해서 ref 객체를 만들어주고 이 객체를 우리가 선택하고 싶은 DOM에 ref 값으로 설정을 해줘야 한다.

이 말만 보고 나도 그대로 했는데 var target = document.getElementById("good"); 이렇게 했을때는 잘되던게 안되는 것이다..

그래서 뭔가를 잘못했나 하고 계속 다르게 해보고 하다가 안돼서 다시 검색해서 찾아보는데 

useRef .current 프로퍼티로 전달된 인자로 초기화된 변경 가능한 ref 객체를 반환한다고 한다

<input ref={inputRef} /> 와 같이 html 태그의 ref 속성에 우리가 만든 inputRef 라는 객체를 할당 해주게 되면, 

inputRef.current에 input 태그에 해당하는 DOM이 담기게 됩니다.(DOM 또한 객체입니다!) 

출처: https://velog.io/@juno7803/React-useRef-200-%ED%99%9C%EC%9A%A9%ED%95%98%EA%B8%B0   

라고 한다 여기서 주목할건 .current 이다 이거를 추가를 해주니 바로 됨! 그렇게 완성된 전체 코드를 보자면 

import { useRef, useState } from 'react';

const DropDown = () => {
  const [selectValue, setSelectValue] = useState('');
  const state = useRef();
  const onChangeSelect = (e) => {
    const seoul = [
      '강남구',
      '강동구',
      '강북구',
    ];
    const gyeonggi = [
      '고양시',
      '과천시',
      '광명시',
    ];
    const gyeongsangnam = [
      '거제시',
      '김해시',
      '마산시',
    ];
    const gyeongsangbuk = [
      '경산시',
      '경주시',
      '구미시',
    ];
    // let state = document.getElementById('good'); 이걸 useRef로 바꿈 
    let d;
    const currentRegion = e.target.value;

    if (currentRegion === '서울특별시') {
      d = seoul;
    } else if (currentRegion === '경기도') {
      d = gyeonggi;
    } else if (currentRegion === '경상남도') {
      d = gyeongsangnam;
    } else if (currentRegion === '경상북도') {
      d = gyeongsangbuk;
    }

    state.current.options.length = 1; // 여기에 current를 추가하니 됐다

    for (let x in d) {
      let opt = document.createElement('option');
      opt.innerHTML = d[x];
      state.current.appendChild(opt); // 여기에 current를 추가하니 됐다
    }
    setSelectValue(currentRegion);
  };

  return (
    <SelectRegionStyle>
      <select
        className="selectRegion"
        value={selectValue}
        onChange={onChangeSelect}
      >
        <option>--지역을 선택해주세요--</option>
        <option value="서울특별시">서울특별시</option>
        <option value="경기도">경기도</option>
        <option value="경상북도">경상북도</option>
        <option value="경상남도">경상남도</option>
      </select>
      <select className="selectDistrict" id="good" ref={state}>
        <option>시/군/구 선택</option>
      </select>
    </SelectRegionStyle>
  );
};

export default DropDown;

여기서 for in문을 보자면 option 태그를 생성하고, 이걸 opt에 담은 다음,

변수 opt에  innerHTML을 for in 문으로 만들어진 객체 value 값으로 할당을 해줌. (d[x]가 d라는 객체에 value값을 뜻하니까)

이렇게 만들어진 option을 state에 appendChild로 넣어준다는 의미이다 

 

내가 이걸 완벽하게 이해를 한건지는 모르겠다. 이게 끝이 아니라 지금은 내가 데이터를 넣어주었지만 나중에 백엔드에 db에서 

받아와야 될것 같기도 해서 할일이 너무 많다 .. 

Comments