컴포넌트 통신(부모, 자식)

soplia080 gyp·2022년 1월 30일

Vue Js

목록 보기
5/18

  • 컴포넌트를 구분했을 때 컴포넌트 간의 관계가 생김 -> 규칙도 생김
  • 뷰 컴포넌트는 각 고유한 데이터 유효범위를 가짐(각각의 컴포넌트는 데이터를 각각 관리)
  • 서로 데이터를 공유하기 위해서는 props, event 전달 방식을 이용해야 됨.

컴포넌트 통신 규칙

  • 상위에서 하위로 데이터를 내려줌, 프롭스 속성
  • 하위에서 상위로는 이벤트를 올려줌, 이벤트 발생
  • 통신 규칙이 생김으로서 얻는 이점
    - 특정 컴포넌트의 변화에 따라 나머지 컴포넌트가 유기적으로 데이터를 주고 받을 시 데이터의 방향을 예측하기 어려움(버그 추적도 어려움 -> N방향 통신의 문제점) -> 데이터의 흐름을 추척할 수 있음(내려가는 데이터는 props, 아래에서 위로 올라오는건 event)

props 예시

  • root 컴포넌트에서 할당된 data가 자식 컴포넌트(app-header, app-content)에서 Reactivity
<body>
    <div id="app">
        <!-- <app-header v-bind:프롭스 속성 이름="상위 컴포넌트의 데이터 이름"></app-header> -->
        <app-header v-bind:propsdata="message"></app-header>
        <app-content v-bind:propsdata="num"></app-content>
    </div>

    <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
    <script>
    	// 상위 컴포넌트 message='hi' 값이 propsdata에 할당 -> template에 \
        var appHeader = {
            template: '<h1>{{ propsdata}}</h1>',
            props: ['propsdata']
        }
		
        var appContent = {
            template : '<div>{{propsdata}}</div>',
            props: ['propsdata']
        }

        new Vue({
            el: '#app',
            components:{
                'app-header' : appHeader,
                'app-content' : appContent
            },
            data:{
                message: 'hi',
                num:10
            }
        })
    </script>
</body>

event emit

  • click add라는 버튼을 누르면 1씩 증가
<body>
    <div id="app">
        <!-- <app-header v-on:하위 컴포넌트에서 발생한 이벤트 이름="상위 컴포넌트의 메서드 이름"></app-header> -->
        <!-- 1. 'pass' 라는 event가 아래에서 올라옴
            2. 컴포넌트 태그에서 'pass' event를 받아서 logText라는 메서드를 실행
            3. root 컴포넌트에서 정의된 logText method가 실행-->
        <app-header v-on:pass="logText"></app-header>
        <app-content v-on:increase="logNum"></app-content>
        <p>{{ num }}</p>
    </div>

    <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
    <script>
        var appHeader = {
            template: '<button v-on:click="passEvent">Click Me</button>',
            methods: {
                passEvent: function () {
                    this.$emit('pass');
                }
            }
        }

        var appContent = {
            template: '<button v-on:click="addNumber">Click add</button>',
            methods: {
                addNumber: function () {
                    this.$emit('increase');
                }
            }
        }

        new Vue({
            el: '#app',
            components: {
                'app-header': appHeader,
                'app-content': appContent
            },
            methods: {
                logText: function () {
                    console.log('hi');
                },
                logNum: function () {
                    this.num += 1;
                    console.log(this.num);
                }
            },
            data: {
                num: 10
            }
        })
    </script>
</body>

profile
배우면서 나아가자

0개의 댓글