Vue 3.x에서 부모-자식 컴포넌트 간 데이터 전달: Props와 Ref 활용

부모 컴포넌트에서 자식 컴포넌트로 데이터 전달

1. 부모 컴포넌트에서 자식 컴포넌트에 바인딩된 매개변수 사용하기

<template>
  <div>
    <!-- 자식 컴포넌트에 :headerText="welcomeMsg" 매개변수 전달 -->
    <app-header :headerText="welcomeMsg" parentContext="this"></app-header>
  </div>
</template>

<script>
// 1. 컴포넌트 임포트
import AppHeader from '../components/AppHeader.vue'
export default {
  data() {
    return {
      welcomeMsg: "홈페이지"
    }
  },
  // 2. 컴포넌트 등록
  components:{
      AppHeader
  }
};
</script>

:headerText="welcomeMsg"<app-header> 자식 컴포넌터에 headerText 매개변수를 전달하는 것을 의미합니다. 이 매개변수는 카멜 케이스를 사용할 수 없으며, HTML 속성은 카멜 케이스를 지원하지 않기 때문입니다. 여러 단어로 구성된 이름은 하이픈(-)으로 연결할 수 있습니다: my-title 또는 header-text. 하이픈으로 명명된 경우, 자식 컴포넌트의 prop에서는 하이픈 대신 카멜 케이스를 사용해야 합니다.

<app-header :header-text="welcomeMsg" parentContext="this"></app-header> <!-- 올바름 -->
<app-header :headerText="welcomeMsg" parentContext="this"></app-header> <!-- 오류 -->
props: ['headerText] <!-- 올바름 -->
props: ['header-text] <!-- 오류 -->

2. 자식 컴포넌트에서 props로 부모 컴포넌트 데이터 수신하기

<template>
    <div>
        <h2>{{ componentMessage }}</h2>
        <hr>
        <h2>{{ headerText }}</h2>
        <button @click="retrieveHeaderText">부모 컴포넌트의 headerText 가져오기</button>
    </div>
</template>

<script>
    export default {
        data() {
            return {
                componentMessage: "헤더 컴포넌트"
            }
        },
        // props로 부모 컴포넌트의 값 수신 (배열 형식, 여러 매개변수는 쉼표로 구분)
        props:["headerText", "parentContext"],
        methods:{
            retrieveHeaderText(){
                // this를 사용하여 부모 컴포넌트에서 전달된 매개변수 사용
                alert(this.headerText)
                // 또는 this.parentContext.headerText
            }
        }
    }
</script>

<style lang="scss" scoped>
</style>

참고: props는 배열이며 여러 매개변수는 쉼표로 구분할 수 있습니다. 메서드에서 부모 컴포넌트의 매개변수를 사용할 때는 this를 사용합니다.

3. props 검증

props:{
  inputValue:{
    type:[Number,String],
    default:20, // 기본값
    required:true  // required 옵션으로 이 매개변수가 필수인지 선언
    
   // default와 required는 보통 함께 사용하지 않음
 }
props: {
    // numberA는 숫자 타입만 허용
    numberA: Number,
    // numberB는 문자열과 숫자 타입 허용
    numberB: [String, Number],
    // textMessage는 문자열 타입이며 필수 전달
    textMessage: {
        type: String,
        required: true
    },
    // countValue는 숫자 타입이며, 기본값 100
    countValue: {
        type: Number,
        default: 100
    },
    // userInfo는 객체 타입
    userInfo: {
        type: Object,
        // 객체 타입의 기본값은 함수로 반환해야 함
        default: function(){
            return { name: '사용자', message: '안녕하세요' }
        }
    },
    // scoreValue는 사용자 정의 검증기 사용
    scoreValue: {
        validator: function(value){
            return value>=0 && value<=100;
        }
    }
}

4. 단방향 데이터 흐름

부모 컴포넌트의 props 값이 변경되면 자식 컴포넌트의 값도 함께 변경되지만, 자식 컴포넌트에서 직접 값을 변경해도 부모 컴포넌트는 변경되지 않습니다.

자식 컴포넌트에서 부모 컴포넌트로 데이터 전달

방법 1: ref 사용하기

  • 태그에 ref를 사용하면 원본 DOM 노드를 가져옵니다
  • 컴포넌트에 ref를 사용하면 컴포넌트 객체를 가져옵니다

1. 자식 컴포넌트 호출 시 ref 정의

<app-header ref="headerRef"></app-header>

2. 부모 컴포넌트에서 자식 컴포넌트 데이터 가져오기

this.$refs.headerRef.속성
this.$refs.headerRef.메서드

3. 자식 컴포넌트에서 부모 컴포넌트 데이터 가져오기

this.$parent.데이터
this.$parent.메서드

위 방법을 사용하면 부모 컴포넌트의 데이터를 변경할 수 있습니다: this.$parent.userName="김민수" 부모 컴포넌트의 userName이 김민수로 변경됩니다.

방법 2: $emit 사용하기

태그: Vue.js 컴포넌트 통신 props ref $emit

5월 26일 19:57에 게시됨