Así que quiero pasar accesorios a un componente de Vue, pero espero que estos accesorios cambien en el futuro desde dentro de ese componente, por ejemplo, cuando actualizo ese componente de Vue desde adentro usando AJAX. Por lo que son solo para la inicialización del componente.
Mi cars-list
elemento de componente Vue donde paso accesorios con propiedades iniciales a 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>
La forma en que lo hago en este momento es que dentro de mi single-car
componente estoy asignando this.initialProperties
a mi this.data.properties
en el created()
gancho de inicialización. Y funciona y es reactivo.
// 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>
Pero mi problema con eso es que no sé si esa es la forma correcta de hacerlo. ¿No me causará algunos problemas en el camino? ¿O hay una mejor manera de hacerlo?
fuente
data
estátwo-way
vinculado, pero no puede pasardata
a componentes, pasaprops
, pero no puede cambiar el recibidoprops
ni convertir elprops
adata
. ¿Y que? Una cosa que aprendí es que debes transmitirprops
y desencadenar eventos. Es decir, si el componente quiere cambiar elprops
que recibió, debe llamar a un evento y ser "re-renderizado". Pero luego te quedas con unone-way
enlace exactamente como React y no veo el uso paradata
entonces. Bastante confuso.Respuestas:
Gracias a esto https://github.com/vuejs/vuejs.org/pull/567 ahora sé la respuesta.
Método 1
Pase el apoyo inicial directamente a los datos. Como el ejemplo en documentos actualizados:
Pero tenga en cuenta que si la propiedad pasada es un objeto o matriz que se usa en el estado del componente principal, cualquier modificación a esa propiedad dará como resultado el cambio en el estado de ese componente principal.
Advertencia : este método no se recomienda. Hará que sus componentes sean impredecibles. Si necesita configurar los datos principales de los componentes secundarios, use la administración de estado como Vuex o use "v-model". https://vuejs.org/v2/guide/components.html#Using-v-model-on-Components
Método 2
Si su accesorio inicial es un objeto o matriz y si no desea que los cambios en el estado de los niños se propaguen al estado principal, simplemente use, por ejemplo,
Vue.util.extend
[1] para hacer una copia de los accesorios en lugar de apuntarlo directamente a los datos de los niños, así:Método 3
También puede usar el operador de propagación para clonar los accesorios. Más detalles en la respuesta de Igor: https://stackoverflow.com/a/51911118/3143704
Pero tenga en cuenta que los operadores de propagación no son compatibles con los navegadores más antiguos y, para una mejor compatibilidad, deberá transpilar el código, por ejemplo, usando
babel
.Notas al pie
[1] Tenga en cuenta que esta es una utilidad interna de Vue y puede cambiar con nuevas versiones. Es posible que desee utilizar otros métodos para copiar ese accesorio, consulte " ¿Cómo clono correctamente un objeto JavaScript? ".
Mi violín donde lo estaba probando: https://jsfiddle.net/sm4kx7p9/3/
fuente
{ ok: 1, notOk: { meh: 2 } }
si se establece en un dato interno con cualquiera de los métodos de clonación anteriores, todavía cambiaría el accesorionotOk.meh
initial
solo poder usarlos dentro de mi composición. Sería mucho más limpio si pudiéramos pasar un prop llamadodata
a cualquier compilación y hacer que propague automáticamente los datos localizados sin toda estainitialPropName
locura.prop --> comp.data
para usar Vue-Stash para todos los datos (o Vuex también funcionaría). Pero ahora estoy rebotando mis datos delwindow
objeto como solía hacer antes de que los marcos JS "modernos" me impusieran su opinión. Entonces surge la pregunta: ¿Cuál es el objetivo de la propiedad comp.data?En compañía de la respuesta de @ dominik-serafin:
En caso de que esté pasando un objeto, puede clonarlo fácilmente usando el operador de extensión (sintaxis ES6):
Pero lo más importante es recordar utilizar opt. 2 en caso de que esté pasando un valor calculado, o más que un valor asincrónico. De lo contrario, el valor local no se actualizará.
Manifestación:
https://jsfiddle.net/nomikos3/eywraw8t/281070/
fuente
recordLocal: [...this.record]
(en mi caso, el registro es una matriz) no funcionó para mí: después de cargar e inspeccionar el componente vue,record
contiene los elementos yrecordLocal
era una matriz vacía.computed
Creo que lo está haciendo bien porque es lo que se indica en los documentos.
https://vuejs.org/guide/components.html#One-Way-Data-Flow
fuente
window
objeto.