본문 바로가기
Vue

[Vue] v-bind="$attrs"를 사용해 컴포넌트의 속성 상속시키기

by 메이플 🍁 2022. 6. 17.

부모 컴포넌트의 속성 상속받기

부모 컴포넌트 App.vue에서 MyBtn에게 class와 style 속성을 전달해주었다.

<--! App.vue -->
<template>
  <MyBtn class="maple" style="color: red">Banana</MyBtn>
</template>

<script>
import MyBtn from './components/MyBtn.vue';

export default {
  name: 'App',
  components: {
    MyBtn,
  },
};
</script>


부모 컴포넌트에서 받은 속성은 최상위 요소(루트 요소)에게만 전달된다. 아래 예제에서 최상위 컴포넌트는 btn이라는 클래스를 가진 div 요소이므로 해당 요소에 maple이라는 클래스가 추가되고 color: red라는 style 속성도 추가되어 화면에 출력된다.

<!-- MyBtn.vue -->
<template>
  <div class="btn">
    <slot></slot>
  </div>
</template>

<style scoped>
.btn {
  display: inline-block;
  margin: 4px;
  padding: 6px 12px;
  border-radius: 4px;
  background-color: gray;
  color: white;
  cursor: pointer;
}
</style>

 

만약 부모 컴포넌트의 속성을 상속받고 싶지 않다면 inheritAttrs에 false값을 주면 된다.

<!-- MyBtn.vue -->
<template>
  <div class="btn">
    <slot></slot>
  </div>
</template>

<script>
export default {
  inheritAttrs: false,
};
</script>

<style scoped>
.btn {
  display: inline-block;
  margin: 4px;
  padding: 6px 12px;
  border-radius: 4px;
  background-color: gray;
  color: white;
  cursor: pointer;
}
</style>

 

만약 최상위 요소가 여러개면 부모 컴포넌트의 속성은 상속되지 않는다.

<!-- MyBtn.vue -->
<template>
  <div class="btn">
    <slot></slot>
  </div>
  <p>I love fruits</p>
</template>

<style scoped>
.btn {
  display: inline-block;
  margin: 4px;
  padding: 6px 12px;
  border-radius: 4px;
  background-color: gray;
  color: white;
  cursor: pointer;
}
</style>

 

한개 이상의 최상위 요소가 있을때 부모 컴포넌트의 속성을 상속받을 수 있는 방법

$attrs로 부모 컴포넌트의 속성에 접근한 뒤 원하는 속성이름을 불러오면 부모 컴포넌트의 모든 속성 중 원하는 속성만 개별적으로 부여할 수 있다.

<!-- MyBtn.vue -->
<template>
  <div class="btn">
    <slot></slot>
  </div>
  <p :class="$attrs.class" :style="$attrs.style">I love fruits</p>
</template>

<style scoped>
.btn {
  display: inline-block;
  margin: 4px;
  padding: 6px 12px;
  border-radius: 4px;
  background-color: gray;
  color: white;
  cursor: pointer;
}
</style>

 

부모 컴포넌트의 모든 속성을 상속하고 싶다면 v-bind="$attrs"를 부여해주면 된다.

<!-- MyBtn.vue -->
<template>
  <div class="btn">
    <slot></slot>
  </div>
  <p :class="$attrs.class" :style="$attrs.style">I love fruits</p>
  <p v-bind="$attrs">I love fruits</p>
</template>

<style scoped>
.btn {
  display: inline-block;
  margin: 4px;
  padding: 6px 12px;
  border-radius: 4px;
  background-color: gray;
  color: white;
  cursor: pointer;
}
</style>

댓글