티스토리 뷰

728x90

 

공식 문서

https://vue-multiselect.js.org/

 

Vue-Multiselect | Vue Select Library.

Probably the most complete selecting solution for Vue.js, without jQuery.

vue-multiselect.js.org

참고 프로젝트

https://github.com/jungyr98/devcollab

 

GitHub - jungyr98/devcollab: 개발자들을 위한 협업 게시판 및 실시간 채팅 플랫폼

개발자들을 위한 협업 게시판 및 실시간 채팅 플랫폼. Contribute to jungyr98/devcollab development by creating an account on GitHub.

github.com

 

 

개발자 커뮤니티를 구현하던 중, 스킬 검색 기능을 추가하려고 Vue-Multiselect 라이브러리를 사용했다.

✅ 내가 필요했던 주요 기능

  • 여러 개의 스킬을 검색해서 선택 가능
  • 입력 시 필터링 기능 제공
  • 선택한 스킬이 태그 형태로 표시됨
  • 선택한 태그는 클릭으로 제거 가능
  • (선택 사항) 선택값을 외부 폼이나 상태로 연결 가능

먼저 install 하기

npm install vue-multiselect

 

 

✅ 기본 구조 이해

vue-multiselect의 드롭다운 구조는 대략 다음과 같다.

<div class="multiselect__content-wrapper">
  <ul class="multiselect__content">
    <li class="multiselect__element">...</li>
  </ul>
</div>

 

✅ 방법 1: 슬롯으로 커스터마이징 (추천)

vue-multiselect은 선택된 항목(태그)을 렌더링 하는 슬롯을 제공한다.
이 슬롯을 통해 원하는 구조와 스타일로 태그를 꾸밀 수 있다.

<multiselect
  ...
>
  <!-- 🎨 선택된 태그 UI 커스터마이징 -->
  <template #tag="{ option, remove }">
    <span
      class="bg-blue-100 text-blue-800 text-sm font-medium mr-1 mb-1 px-2.5 py-0.5 rounded-full inline-flex items-center"
    >
      {{ option.name }}
      <button
        type="button"
        @click="remove(option)"
        class="ml-2 text-blue-600 hover:text-red-600 focus:outline-none"
      >
        ×
      </button>
    </span>
  </template>
</multiselect>

 

결과

커스텀 된 태그 UI

 

✅ 방법 2: CSS 오버라이딩

scoped 스타일 사용 시, ::v-deep 또는 :deep() 사용

Tailwind를 병행하고 있다면, border-none focus:outline-none 같은 클래스를 수동으로 설정하기는 어려우므로 위처럼 :deep()으로 잡아주는 게 가장 확실하다.

<style scoped>
/* Vue 3에서는 scoped 안에서 깊게 선택하려면 아래 방식처럼 사용 */
:deep(.multiselect__content-wrapper) {
  ...
}

:deep(.multiselect:focus) {
  ...
}
</style>

 

💡 참고: 왜 :deep을 써야 하나요?

scoped 스타일은 기본적으로 컴포넌트 바깥 요소에 영향을 주지 않기 때문에,
내부 라이브러리 컴포넌트의 깊은 DOM을 스타일링할 때는 반드시 :deep() 혹은 ::v-deep을 사용해야 한다.

 

🔧 추가로 커스터마이징할 수 있는 것들

클래스기능
.multiselect__option 각 항목 스타일
.multiselect__option--highlight hover 또는 선택된 항목
.multiselect__option--selected 이미 선택된 항목
.multiselect__content-wrapper 드롭다운 컨테이너
.multiselect__tags 선택된 태그들 감싸는 wrapper

 

728x90
250x250
공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
링크