본문 바로가기
🍀오늘도 삽질 중🍀/Javascript

filter method 이용해서 아이디 검색 기능 구현하기

by 매진2 2023. 6. 13.
728x90

이번 과제 중에 제일 어려웠던것 같다.

다른것들도 하루종일 고민했지만 이건 하루종일 고민해도 너무 어려웠다.

다른 기능은 다 구현했는데 여기서 filter를 통해 원하는 검색결과만 보이게 하는 기능이 제일 어렵게 느껴졌다.


<Mission 7 아이디 검색 기능>

실제 인스타 nav 검색창에 아이디를 입력 시 검색 기능이 실행됩니다.

아이디 데이터를 담고 있는 배열을 선언해주세요.

검색 창에 텍스트 입력 시 배열의 요소 중 해당 텍스트에 일치하는 아이디만 보일 수 있도록 구현해주세요.

for 문이 아닌 다른 array method를 사용해 구현해주세요.


DB가 아닌 그냥 간단하게 보여줄 정도라서 javascript 파일 상단에 배열로 id list를 만들어준다.

let userArray = [
  {
    id: "wecode_bootcamp",
    subname: ">wecode | 위코드",
    url: "https://image.rocketpunch.com/company/99609/wecode_logo_1590553949.jpg?s=400x400&t=inside",
  },
  {
    id: "wecode_founder",
    subname: "송은우 (Eun Woo Song)",
    url: "https://images.unsplash.com/photo-1685856861907-0c20cd9d22c7?ixlib=rb-4.0.3&ixid=M3wxMjA3fDB8MHx0b3BpYy1mZWVkfDF8dG93SlpGc2twR2d8fGVufDB8fHx8fA%3D%3D&auto=format&fit=crop&w=1400&q=60",
  },
  {
    id: "wecode_korea",
    subname: "",
    url: "https://images.unsplash.com/photo-1686110432947-293cb3c7ac54?ixlib=rb-4.0.3&ixid=M3wxMjA3fDB8MHx0b3BpYy1mZWVkfDJ8dG93SlpGc2twR2d8fGVufDB8fHx8fA%3D%3D&auto=format&fit=crop&w=1400&q=60",
  },
  {
    id: "Wecode",
    subname: "강남구 테헤란로 427, 서울",
    url: "https://images.unsplash.com/photo-1685944722478-284349a10211?ixlib=rb-4.0.3&ixid=M3wxMjA3fDB8MHx0b3BpYy1mZWVkfDV8dG93SlpGc2twR2d8fGVufDB8fHx8fA%3D%3D&auto=format&fit=crop&w=1400&q=60",
  },
  {
    id: "ggulbbang",
    subname: "꿀빵이와 앙꼬",
    url: "https://images.unsplash.com/photo-1425082661705-1834bfd09dca?ixlib=rb-4.0.3&ixid=M3wxMjA3fDB8MHxzZWFyY2h8Mnx8aGFtc3RlcnxlbnwwfHwwfHx8MA%3D%3D&auto=format&fit=crop&w=1400&q=60",
  },
];

필요한 값들을 DOM으로 불러온다.

const searchUserId = document.getElementsByClassName("searchUser")[0];
const search = document.getElementById("search");
const explore = document.getElementsByClassName("explore")[0];

 

사용자가 input에 값을 적으면 serchValue에 값이 생기고 그와 동일한 값을 가진 id만 골라서 보여줄 수 있도록 filter를 사용했다.

그리고 값이 생기면 바로 opacity를 1로 변경해 숨어있는 div가 보이게 해주었다.

 

방법을 2개를 찾아서 원하는걸로 골라 적으면 될 것 같다.

먼저 첫번째는  userArray의 index값을 user로 넣어주고 user 중 id 값에서 input 값과 같은 것 filter해서 보여준다.

function searchUserNameData(e) {
  const searchValue = e.target.value;

  if (searchValue) {
    let filterArr = userArray.filter((user) => user.id.includes(searchValue));
    search.style.opacity = "1";

두번째는  indexOf를 사용해 user 중 id 값에서 input 값과 같지 않은 것 제외하고 filter해서 보여준다.

function searchUserNameData(e) {
  const searchValue = e.target.value;

  if (searchValue) {
    let filterArr = userArray.filter(
      (user) => user.id.indexOf(searchValue) !== -1
    );

    search.style.opacity = "1";

앞서 했던 댓글기능의 addComment 함수처럼 할 수도 있지만 다른 방법을 써보고 싶어서 ${}를 써보았다.

map으로 filter된 userArray 배열을 돌면서 변수에 값을 넣어 보여주었다.

map과 forEach를 쓸 수 있지만 forEach의 경우 새로운 배열을 반환하지 않기때문에 return 못한다.
변수가 들어가는 곳을 ${}로 감싸주고 넣어줄 html 부분 작성 후 앞 뒤를 백틱으로 감싸주었다.

search.innerHTML = filterArr.map((data) => {
      return `<div class="eachUser">
        <img alt="user" src=${data.url} />
        <div class="userPTag">
          <p class="weightbolder userPTagP">${data.id}</p>
          <p class="gray userPTagP">${data.subname}</p>
        </div>
      </div>`;
    });

값이 없으면 opacity를 0으로 해주었다

  } else {
    search.style.opacity = "0";
  }
}

그리고 input 태그에 변화가 생기면, 함수가 작동하도록 input event를 넣었다.

(사용자가 키보드로 입력할 수도 있고 마우스로 복붙을 할수도 있기때문에 keyup은 한정적이다.)

explore.addEventListener("input", searchUserNameData);

아래는 전체코드이다.

 

const inputComment = document.getElementById("input");
const buttonComment = document.getElementById("button");
const newComment = document.getElementById("newComment");
const commentForm = document.getElementsByClassName("comment")[0];

const searchUserId = document.getElementsByClassName("searchUser")[0];
const search = document.getElementById("search");
const explore = document.getElementsByClassName("explore")[0];

function searchUserNameData(e) {
  const searchValue = e.target.value;

  if (searchValue) {

    let filterArr = userArray.filter(
      (user) => user.id.indexOf(searchValue) !== -1
    );

    search.style.opacity = "1";

    search.innerHTML = filterArr.map((data) => {

      return `<div class="eachUser">
        <img alt="user" src=${data.url} />
        <div class="userPTag">
          <p class="weightbolder userPTagP">${data.id}</p>
          <p class="gray userPTagP">${data.subname}</p>
        </div>
      </div>`;
    });
  } else {
    search.style.opacity = "0";
  }
}

explore.addEventListener("input", searchUserNameData);
728x90