programing

Vue.js 2에서 소품을 초기 데이터로 전달하는 올바른 방법은 무엇입니까?

itsource 2022. 7. 2. 23:04
반응형

Vue.js 2에서 소품을 초기 데이터로 전달하는 올바른 방법은 무엇입니까?

따라서 Vue 컴포넌트에 소품을 전달하고 싶은데, 향후 AJAX를 사용하여 내부에서 Vue 컴포넌트를 업데이트하면 해당 컴포넌트 내부에서 소품이 변경될 것으로 예상됩니다.컴포넌트 초기화 전용입니다.

★★★cars-list 특성을 가진 소품을 Vue에 하는 Vue .single-car:

// cars-list.vue

<script>
    export default {
        data: function() {
            return {
                cars: [
                    {
                        color: 'red',
                        maxSpeed: 200,
                    },
                    {
                        color: 'blue',
                        maxSpeed: 195,
                    },
                ]
            }
        },
    }
</script>

<template>
    <div>
        <template v-for="car in cars">
            <single-car :initial-properties="car"></single-car>
        </template>
    </div>
</template>

가 있는 으로는 내 single-carthis.initialProperties 나 my my mythis.data.propertiescreated() 그것은 있고 반응적이다.그리고 효과가 있고 반응적입니다.

// single-car.vue

<script>
    export default {
        data: function() {
            return {
                properties: {},
            }
        },
        created: function(){
            this.data.properties = this.initialProperties;
        },
    }
</script>

<template>
    <div>Car is in {{properties.color}} and has a max speed of {{properties.maxSpeed}}</div>
</template>

하지만 내 문제는 그게 옳은 방법인지 모르겠다는 거야가는 길에 문제가 생기지 않을까요?아니면 더 좋은 방법이 있을까요?

이 https://github.com/vuejs/vuejs.org/pull/567 덕분에 답을 알 수 있게 되었습니다.

방법 1

초기 프로포즈를 데이터에 직접 전달합니다.업데이트된 문서의 예시와 같습니다.

props: ['initialCounter'],
data: function () {
    return {
        counter: this.initialCounter
    }
}

그러나 전달된 프로포트가 부모 컴포넌트에서 사용되는 오브젝트 또는 어레이인 경우 해당 프로포넌트를 변경하면 부모 컴포넌트 상태가 변경됩니다.

경고: 이 방법은 권장되지 않습니다.컴포넌트를 예측할 수 없게 됩니다.하위 구성 요소에서 상위 데이터를 설정해야 하는 경우 Vuex와 같은 상태 관리를 사용하거나 "v-model"을 사용하십시오.https://vuejs.org/v2/guide/components.html#Using-v-model-on-Components

방법 2

초기 소포가 개체 또는 어레이이고 하위 상태의 변경이 상위 상태로 전파되지 않으려면 예를 사용하십시오. Vue.util.extend 대신, [1] 이렇게 소품을 할 수

props: ['initialCounter'],
data: function () {
    return {
        counter: Vue.util.extend({}, this.initialCounter)
    }
}

방법 3

확산 연산자를 사용하여 소품을 복제할 수도 있습니다.자세한 내용은 Igor 답변:https://stackoverflow.com/a/51911118/3143704

, 오래된 을 높이기 를 들어 ""를 사용하여 babel.

각주

[1] 이 유틸리티는 내부 Vue 유틸리티이므로 새로운 버전에 따라 변경될 수 있습니다.다른 방법을 사용하여 해당 프로펠을 복사할 수도 있습니다. "How do I correctly clone a JavaScript object?"를 참조하십시오.

제가 테스트한 바이올린은 https://jsfiddle.net/sm4kx7p9/3/ 입니다.

@dominik-serafin의 답변과 함께:

오브젝트를 전달하고 있는 경우 확산 연산자(ES6 구문)를 사용하여 쉽게 복제할 수 있습니다.

 props: {
   record: {
     type: Object,
     required: true
   }
 },

data () { // opt. 1
  return {
    recordLocal: {...this.record}
  }
},

computed: { // opt. 2
  recordLocal () {
    return {...this.record}
  }
},

그러나 가장 중요한 것은 계산된 값 또는 그 이상의 비동기 값을 전달할 경우 옵션 2를 사용하는 것입니다.그렇지 않으면 로컬 값이 업데이트되지 않습니다.

데모:

Vue.component('card', { 
  template: '#app2',
  props: {
    test1: null,
    test2: null
  },
  data () { // opt. 1
    return {
      test1AsData: {...this.test1}
    }
  },
  computed: { // opt. 2
    test2AsComputed () {
      return {...this.test2}
    }
  }
})

new Vue({
  el: "#app1",
  data () {
    return {
      test1: {1: 'will not update'},
      test2: {2: 'will update after 1 second'}
    }
  },
  mounted () {
    setTimeout(() => {
      this.test1 = {1: 'updated!'}
      this.test2 = {2: 'updated!'}
    }, 1000)
  }
})
<script src="https://cdn.jsdelivr.net/npm/vue@2.5.17/dist/vue.js"></script>

<div id="app1">
  <card :test1="test1" :test2="test2"></card>
</div>

<template id="app2">
  <div>
    test1 as data: {{test1AsData}}
    <hr />
    test2 as computed: {{test2AsComputed}}
  </div>
</template>

https://jsfiddle.net/nomikos3/eywraw8t/281070/

나는 당신이 그것을 제대로 하고 있다고 믿는다 왜냐하면 그것은 문서에 명시되어 있기 때문이다.

프로포트의 초기값을 초기값으로 사용하는 로컬 데이터 속성 정의

https://vuejs.org/guide/components.html#One-Way-Data-Flow

이전 vue 프로젝트로 돌아가면 두 번째 또는 세 번째 문제가 발생합니다.

vue에서는 왜 이렇게 복잡한지 모르겠지만 watch를 통해 실행할 수 있습니다.

export default {

  props: ["username"],

  data () {
    return {
      usernameForLabel: "",
    }
  },

  watch: {
    username: {
      immediate: true,
      handler (newVal, oldVal) {
        this.usernameForLabel = newVal;
      }
    },
  },

또 다른 접근법으로, 저는 아이 컴포넌트의 감시자를 통해 이 작업을 수행했습니다.

이 방법은 특히 비동기 값을 전달할 때 자식 구성 요소에서 전달된 값을 v-model에 바인딩하려는 경우에 유용합니다.

또한 반응시키기 위해 다른 워처의 부모에게 로컬 값을 내보냅니다.

예:

  data() {
    return {
      properties: {},
    };
  },
  props: {
    initial-properties: {
      type: Object,
      default: {},
    },
  },
  watch: {
    initial-properties: function(newVal) {
      this.properties = {...newVal};
    },
    properties: function(newVal) {
      this.$emit('propertiesUpdated', newVal);
    },
  },

이렇게 하면 나는 더 많은 통제력을 갖게 되고 예상치 못한 행동도 덜 할 수 있다.예를 들어 부모로부터 전달받은 소품이 비동기일 경우 작성되거나 마운트된 라이프사이클에 사용할 수 없습니다.따라서 @Igor-Parra가 언급한 대로 계산된 속성을 사용하거나 프로펠을 보고 내보낼 수 있습니다.

언급URL : https://stackoverflow.com/questions/40408096/whats-the-correct-way-to-pass-props-as-initial-data-in-vue-js-2

반응형