Empresas
Empleos
  • Sobre nosotros
  • Soluciones
    • Publicación de vacantes
      Publica tu vacante y recibe candidatos calificados en 48h.
    • Evaluación de candidatos
      500+ pruebas técnicas y psicológicas, más anti-fraude.
    • Headhunting
      Búsqueda ejecutiva a la medida de principio a fin.
    • Nómina + EOR
      Dispersión de nómina y EOR en más de 15 países de LATAM.
  • Precios
  • Empleos

0

267
Vistas
¿Cómo despedir a Watcher, cuando newValue es la misma cadena?

Estoy insertando base64 images en un editor asignando su base64 string al objeto reactivo state.image y señalándolo con un observador. El problema es que cuando quiero insertar la misma imagen dos veces, el observador no dispara.

watcher :

 const renderImage = (editor) => { const unwatch = watch(() => state.image, () => { console.log('watcher fires!') editor.chain().focus().setImage({ src: state.image }).run() unwatch() state.image = null }) }

Como puede ver, estoy tratando de matar al observador con unwatch() y, además, configuro state.image = null , pero aún no se dispara cuando se carga la misma imagen.

El evento @click se activa en este elemento:

 <button @click="$refs.image.click(); renderImage(editor)"></button> <input type="file" ref="image" style="display: none" @change="getImageUrl">

y el dataUrl de la imagen se crea en getImageUrl :

 const getImageUrl = (event) => { const files = event.target.files; if (!files.length) return; const reader = new FileReader(); reader.onload = (event) => { state.image = event.target.result; }; reader.readAsDataURL(files[0]); }

Ambos elementos parecen funcionar como se desea.

¿Cómo hago que el vigilante dispare?

about 4 years ago · Juan Pablo Isaza
1 Respuestas
Responde la pregunta

0

La pregunta asume que la devolución de llamada del watch no se activa, pero en este caso, en realidad es el <input> el que no activa su evento.

<input> solo activa el evento change / input cuando su valor realmente cambia. Al seleccionar el mismo archivo, el valor no ha cambiado y, por lo tanto, no se produce ningún evento de change para llamar al controlador getImageUrl() , que habría activado el watch cuando se carga el archivo.

Para resolver el problema, restablezca el valor de <input> después de copiar la ruta del archivo seleccionado:

 ⋮ const image = ref() // template ref on input const getImageUrl = (event) => { const files = event.target.files; if (!files.length) return; const fileToRead = files[0]; // 1️⃣ copy input's value image.value.value = null; // 2️⃣ and reset the input const reader = new FileReader(); reader.onload = (event) => { state.image = event.target.result; }; reader.readAsDataURL(fileToRead); }

demostración 1

Refactorización menor

renderImage() en realidad solo usa watch para crear esencialmente una devolución de llamada asíncrona para el evento de load de FileReader . Parece que esto podría simplificarse moviendo el código de representación de imágenes directamente a ese controlador de eventos de load :

 const getImageUrl = (event) => { const files = event.target.files; if (!files.length) return; const fileToRead = files[0]; image.value.value = null; const reader = new FileReader(); reader.onload = (event) => { // 👇 render image editor.chain().focus().setImage({ src: event.target.result }).run(); }; reader.onerror = reject; reader.readAsDataURL(fileToRead); }

Entonces podrías eliminar renderImage() :

 <!-- <button @click="$refs.image.click(); renderImage(editor)"></button> --> <!-- no longer needed --> <button @click="$refs.image.click()"></button>

... y también state.image :

 const state = reactive({ // image: '' // no longer needed })

demostración 2

about 4 years ago · Juan Pablo Isaza Denunciar
Responde la pregunta
Encuentra empleos remotos

¡Descubre la nueva forma de encontrar empleo!

Top de empleos
Top categorías de empleo
Empresas
Publicar vacante Precios Comercial
Legal
Términos y condiciones Política de privacidad
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomiéndame algunas ofertas
Necesito ayuda