Vuejs
Tutorial Vuejs: Binding bidireccional con v-model y defineModel
Aprende a implementar el binding bidireccional en Vue con v-model y defineModel. Optimiza la sincronización de datos en tus componentes y formularios.
Aprende Vuejs GRATIS y certifícate¿Qué es el Binding Bidireccional?
El binding bidireccional es una característica fundamental de Vue que permite sincronizar automáticamente las propiedades de un componente con los datos del modelo subyacente. Esto significa que cualquier cambio en el valor de una propiedad de entrada se reflejará automáticamente en el modelo de datos, y viceversa. Esta capacidad es particularmente útil para formularios y componentes de entrada de datos, donde la sincronización manual de los datos puede ser tediosa y propensa a errores.
En Vue, el binding bidireccional se implementa principalmente a través de la directiva v-model
. Esta directiva se utiliza para crear enlaces reactivos entre los elementos de formulario y los datos del componente. Por ejemplo, en un campo de entrada de texto, el uso de v-model
garantiza que cualquier cambio realizado por el usuario en el campo de texto se refleje en el modelo de datos del componente, y cualquier modificación del modelo de datos se actualice en el campo de texto automáticamente.
<template>
<input v-model="mensaje" placeholder="Escribe algo">
<p>El mensaje es: {{ mensaje }}</p>
</template>
<script>
export default {
data() {
return {
mensaje: ''
};
}
}
</script>
En el ejemplo anterior, el valor del campo de entrada está vinculado bidireccionalmente a la propiedad mensaje
del modelo de datos del componente. Cualquier cambio en el campo de entrada actualizará el valor de mensaje
, y cualquier cambio en mensaje
actualizará el valor del campo de entrada.
El binding bidireccional también se puede aplicar a componentes personalizados. En este caso, v-model
se utiliza para vincular una propiedad del componente hijo con una propiedad del componente padre. Para lograr esto, el componente hijo debe emitir un evento específico que notifique al componente padre sobre los cambios en el valor de la propiedad. Por defecto, este evento se llama update:modelValue
.
<!-- Componente Padre -->
<template>
<custom-input v-model="valorPadre"></custom-input>
</template>
<script>
import CustomInput from './CustomInput.vue';
export default {
components: {
CustomInput
},
data() {
return {
valorPadre: ''
};
}
}
</script>
<!-- Componente Hijo -->
<template>
<input :value="modelValue" @input="$emit('update:modelValue', $event.target.value)">
</template>
<script>
export default {
props: ['modelValue']
}
</script>
En este ejemplo, el componente CustomInput
está diseñado para trabajar con v-model
. Se espera que el componente hijo acepte una prop llamada modelValue
y emita un evento update:modelValue
cuando el valor cambie. Esto permite que el valor del componente padre se actualice automáticamente cuando el usuario interactúa con el componente hijo.
El binding bidireccional es una herramienta poderosa para simplificar la gestión de estados en aplicaciones Vue, especialmente cuando se trabaja con formularios y componentes de entrada de datos.
Uso básico de v-model
El uso de v-model
en Vue.js permite crear enlaces bidireccionales entre los datos y los elementos del DOM de manera sencilla y eficiente. La directiva v-model
se utiliza principalmente en elementos de formulario como input
, textarea
y select
, así como en componentes personalizados.
Para entender cómo funciona v-model
, veamos algunos ejemplos prácticos.
Uso en elementos de formulario nativos:
- Input de texto:
<template>
<input v-model="nombre" placeholder="Introduce tu nombre">
<p>Nombre: {{ nombre }}</p>
</template>
<script>
export default {
data() {
return {
nombre: ''
};
}
}
</script>
En este ejemplo, el valor del campo de entrada de texto está vinculado a la propiedad nombre
del modelo de datos del componente. Cualquier cambio en el campo de entrada actualizará nombre
, y cualquier cambio en nombre
se reflejará automáticamente en el campo de entrada.
- Textarea:
<template>
<textarea v-model="mensaje" placeholder="Escribe un mensaje"></textarea>
<p>Mensaje: {{ mensaje }}</p>
</template>
<script>
export default {
data() {
return {
mensaje: ''
};
}
}
</script>
Similar al ejemplo anterior, pero utilizando un textarea
. La sincronización bidireccional funciona de la misma manera.
- Select:
<template>
<select v-model="opcionSeleccionada">
<option disabled value="">Seleccione una opción</option>
<option>A</option>
<option>B</option>
<option>C</option>
</select>
<p>Opción seleccionada: {{ opcionSeleccionada }}</p>
</template>
<script>
export default {
data() {
return {
opcionSeleccionada: ''
};
}
}
</script>
En este caso, v-model
se utiliza con un elemento select
. La opción seleccionada está vinculada a la propiedad opcionSeleccionada
.
Uso en componentes personalizados:
Para utilizar v-model
en componentes personalizados, es necesario realizar algunas configuraciones adicionales. El componente hijo debe aceptar una prop llamada modelValue
y emitir un evento update:modelValue
cuando el valor cambie.
<!-- Componente Hijo -->
<template>
<input :value="modelValue" @input="$emit('update:modelValue', $event.target.value)">
</template>
<script>
export default {
props: ['modelValue']
}
</script>
<!-- Componente Padre -->
<template>
<custom-input v-model="valorPadre"></custom-input>
<p>Valor en el componente padre: {{ valorPadre }}</p>
</template>
<script>
import CustomInput from './CustomInput.vue';
export default {
components: {
CustomInput
},
data() {
return {
valorPadre: ''
};
}
}
</script>
El componente hijo acepta una prop modelValue
y emite un evento update:modelValue
cuando el valor del input cambia.
En el componente padre, v-model
se utiliza para crear un enlace bidireccional entre valorPadre
y el componente CustomInput
.
Estos ejemplos demuestran cómo v-model
facilita la sincronización de datos entre el modelo y la vista, eliminando la necesidad de manejar eventos y actualizaciones manualmente. Esta funcionalidad es esencial para mantener el código limpio y fácil de mantener en aplicaciones Vue.js.
Introducción a defineModel
defineModel
es una nueva API introducida en Vue 3.3 que facilita la creación de enlaces bidireccionales entre componentes padre e hijo, similar a v-model
, pero con mayor flexibilidad y claridad en la gestión de propiedades y eventos. A diferencia de v-model
, defineModel
permite definir explícitamente las propiedades y eventos utilizados para el binding bidireccional, proporcionando un control más granular sobre el comportamiento del enlace.
Para utilizar defineModel
, primero es necesario definir el modelo en el componente hijo utilizando la función defineModel
. Esta función se importa desde vue
y se utiliza dentro del setup function del componente hijo.
<!-- Componente Hijo -->
<template>
<input type="text" v-model="value">
</template>
<script setup>
const value = defineModel("value");
</script>
En este ejemplo, defineModel
se utiliza para crear una propiedad reactiva value
. Esto permite que el componente hijo gestione su propio estado y notifique al componente padre sobre los cambios.0
<!-- Componente Padre -->
<template>
<mi-componente v-model:value="valorPadre" />
<p>Valor en el componente padre: {{ valorPadre }}</p>
</template>
<script setup lang="ts">
import { ref } from 'vue';
import MiComponente from './components/mi-componente.vue';
const valorPadre = ref("");
</script>
En este ejemplo, v-model
se utiliza en el componente padre para crear un enlace bidireccional con el componente hijo MiComponente
, utilizando la constante valorPadre
en el model value referenciandola al argumento, en este caso sólo tenemos uno que es value
. De esta manera, cambiará de manera reactiva en cuanto se detecte cualquier cambio en el componente hijo.
defineModel
ofrece varias ventajas sobre v-model
en términos de flexibilidad y control. Por ejemplo, permite definir múltiples modelos en un mismo componente, lo que es útil cuando se necesita gestionar varios estados de manera independiente.
<!-- Componente Hijo -->
<template>
<div class="name-container">
<input v-model="nombre">
<input v-model="apellido">
</div>
</template>
<script setup lang="ts">
const nombre = defineModel('nombre')
const apellido = defineModel('apellido')
</script>
<style>
.name-container {
display: flex;
flex-direction: column;
gap: 1em;
}
</style>
<!-- Componente Padre -->
<template>
<mi-componente v-model:nombre="nombre" v-model:apellido="apellido" />
<p>Nombre: {{nombre }}</p>
<p>Apellido: {{ apellido }}</p>
</template>
<script setup lang="ts">
import { ref } from 'vue';
import MiComponente from './components/mi-componente.vue';
const nombre = ref("");
const apellido = ref("");
</script>
En este ejemplo, se definen dos modelos separados, nombre
y apellido
, que permiten gestionar los nombres y apellidos de forma independiente.
En resumen, defineModel
proporciona una forma más explícita y flexible de gestionar el binding bidireccional en Vue, permitiendo una mejor organización del código y una mayor claridad en la gestión de propiedades y eventos.
Cuándo usar v-model y cuándo defineModel
La elección entre v-model
y defineModel
depende del nivel de control y flexibilidad que necesites al crear enlaces bidireccionales en tus componentes Vue.
v-model
es la opción más sencilla y directa para la mayoría de los casos, especialmente cuando se trabaja con formularios y componentes de entrada de datos. Su uso es intuitivo y requiere menos configuración, permitiendo una rápida implementación de enlaces bidireccionales. Es ideal para:
- Elementos de formulario nativos: Como
input
,textarea
yselect
, dondev-model
proporciona una forma rápida y eficiente de sincronizar los datos del modelo con la vista. - Componentes personalizados simples: Donde se necesita solo un enlace bidireccional básico. Por ejemplo, un componente de entrada de texto personalizado que solo requiere una prop
modelValue
y emite un eventoupdate:modelValue
.
Sin embargo, v-model
tiene limitaciones cuando se requiere un control más granular o se necesitan múltiples enlaces bidireccionales dentro de un mismo componente. Aquí es donde defineModel
resulta útil. defineModel
permite definir explícitamente las propiedades y eventos utilizados para el binding bidireccional, proporcionando mayor flexibilidad y control. Es adecuado para:
- Componentes complejos: Donde se necesitan múltiples enlaces bidireccionales. Por ejemplo, un componente de formulario avanzado que maneja varios campos de entrada de manera independiente.
- Personalización y claridad: Cuando se requiere una configuración más explícita y personalizada de las propiedades y eventos, evitando colisiones y manteniendo el código más organizado.
En resumen, usa v-model
para escenarios simples y directos donde la configuración mínima es suficiente, y opta por defineModel
cuando necesites un mayor control y flexibilidad sobre las propiedades y eventos de tus componentes.
Ejercicios de esta lección Binding bidireccional con v-model y defineModel
Evalúa tus conocimientos de esta lección Binding bidireccional con v-model y defineModel con nuestros retos de programación de tipo Test, Puzzle, Código y Proyecto con VSCode, guiados por IA.
Solicitud HTTP con Axios
Estilización de componentes en Vue.js
Comunicación de componentes con props
Uso de hooks de ciclo de vida en Vue
Introducción a los componentes
Introducción a Vue
Navegación programática y redirección
Uso de la directiva v-if en Vuejs
Crear componente Composition API
Realizar una solicitud GET con Fetch API en Vue
Uso avanzado de los composables
Galería de imágenes con navegación y rutas
Uso de rutas anidadas y dinámicas
Definición y manejo de rutas en Vue
Uso de la directiva v-for en Vuejs
Manejo de eventos con v-on
Crear un componente con Options API en Vue
Creación de rutas con Vue Router
Uso básico de los composables
Binding bidireccional con v-model y defineModel
Instalación y configuración
Lista de tareas básica en Vuejs
Uso de provide e inject
Gestión de tareas con estado global y API
Introducción a la sintaxis de plantillas
Implementar reactividad con ref y reactive
Componente Vue con Suspense
Evaluación test de conocimientos Vuejs
Todas las lecciones de Vuejs
Accede a todas las lecciones de Vuejs y aprende con ejemplos prácticos de código y ejercicios de programación con IDE web sin instalar nada.
Introducción A Vue Y Su Ecosistema
Introducción Y Entorno
Instalar Y Configurar Vue Con Vite
Introducción Y Entorno
Introducción A La Sintaxis De Plantillas
Componentes
Introducción A Componentes
Componentes
Componentes Con Options Api
Componentes
Componentes Con Composition Api
Componentes
Renderizado Condicional Con V-if
Componentes
Renderizado Iterativo Con V-for
Componentes
Props Y Comunicación Entre Componentes
Componentes
Manejo De Eventos En Vue Con V-on
Componentes
Binding Bidireccional Con V-model Y Definemodel
Componentes
Estilización De Componentes
Componentes
Reactividad Con Ref Y Reactive
Composición Y Reactividad
Ciclo De Vida Con Composition Api
Composición Y Reactividad
Composition Api: Provide E Inject
Composición Y Reactividad
Introducción A Los Composables
Composición Y Reactividad
Uso Avanzado De Composables
Composición Y Reactividad
Introducción A Vue Router
Navegación Y Enrutamiento
Definición Y Manejo De Rutas
Navegación Y Enrutamiento
Rutas Anidadas Y Dinámicas
Navegación Y Enrutamiento
Navegación Programática Y Redirección
Navegación Y Enrutamiento
Solicitudes Http Con Fetch Api
Interacción Http Con Apis De Backend
Solicitudes Http Con Axios
Interacción Http Con Apis De Backend
Introducción A Suspense
Interacción Http Con Apis De Backend
Evaluación Test De Conocimientos Vuejs
Evaluación
Certificados de superación de Vuejs
Supera todos los ejercicios de programación del curso de Vuejs y obtén certificados de superación para mejorar tu currículum y tu empleabilidad.
En esta lección
Objetivos de aprendizaje de esta lección
- Comprender el concepto y la importancia del binding bidireccional.
- Implementar
v-model
en elementos de formulario nativos y componentes personalizados. - Configurar enlaces bidireccionales utilizando
defineModel
en Vue 3.3. - Diferenciar cuándo usar
v-model
y cuándodefineModel
para una mayor flexibilidad y control.