¿Cómo oculto la sintaxis de VueJS mientras se carga la página?

156

Tal vez esta es una pregunta trivial.

Entonces, cuando ejecuto mi aplicación vuejs en el navegador, habilita la velocidad de descarga de la aceleración (se establece en una conexión baja). Obtuve la salida de sintaxis vue sin terminar en el navegador.

La sintaxis de Vue js aparece en el navegador

Sé que podemos engañarlo mostrando la imagen de carga antes de que se cargue toda la página, pero ¿hay alguna mejor solución para solucionar esto?

antoniputra
fuente

Respuestas:

240

Puedes usar la capa v directiva , que ocultará la instancia de Vue hasta que finalice la compilación.

HTML:

<div v-cloak>{{ message }}</div>

CSS:

[v-cloak] { display: none; }
Gus
fuente
en api dice: [v-cloak] { display: none; } <div v-cloak> {{ message }} </div> significa, ¿debería agregar un v-cloakatributo en cada elemento que deseo ocultar?
antoniputra
23
Solo para el Appdiv principal debería estar bien
Jeff
3
Esto funciona pero el hombre es torpe. Realmente esperaba algo más elegante. +1 aunque
Wesley Smith
28
Parece que v-cloakdebería ser el valor predeterminado y que si alguien realmente quisiera mostrarlo {{ }}, debería usar algo como v-uncloak.
nu everest
3
display:noneen HTML existente, es una mala bandera para SEO. Creo que puede ser mejor usar algún tipo de superposición hasta que se cargue la página.
T.Todua
41

Adjunto el siguiente codepen. Puedes ver la diferencia con y sin v-cloak.

<div id="js-app">
[regular]Hold it... <span>{{test}}</span><br/>
[cloak]Hold it... <span v-cloak>{{test}}</span>
</div>

http://codepen.io/gurghet/pen/PNLQwy

Gurghet
fuente
1
Sí, lo tengo ... gracias, tu codepen sería una ayuda para los recién llegados.
antoniputra
aún obtienes el primer {{test}} mientras vuejs se está cargando, por lo que no es una respuesta perfecta
twigg
12
@twigg Ese es el punto. El primero muestra una etiqueta normal y el segundo muestra una etiqueta encubierta usando el v-cloakatributo.
kb.
29

Según lo sugerido por otros, usar v-cloak es la solución adecuada. Sin embargo, como @ DelightedD0D mencionó, ES torpe. La solución simple es agregar un poco de CSS en el pseudo selector ::beforede v-cloakdirectiva.

En su archivo sass / less, algo parecido a

[v-cloak] > * { display:none; }
[v-cloak]::before {
  content: " ";
  display: block;
  position: absolute;
  width: 80px;
  height: 80px;
  background-image: url(/images/svg/loader.svg);
  background-size: cover;
  left: 50%;
  top: 50%;
}

Por supuesto, deberá proporcionar una ruta válida y accesible para la imagen del cargador. Se renderizará algo así.

ingrese la descripción de la imagen aquí

Espero eso ayude.

schartz
fuente
7

Con la v-cloakdirectiva, puede ocultar los enlaces de bigote sin compilar hasta que la instancia de vue haya terminado de compilarse. Debe usar el bloque CSS para ocultarlo hasta que se compile.

HTML:

<div v-cloak>
  {{ vueVariable }}
</div>

CSS:

[v-cloak] {
  display: none;
}

Esto <div>no será visible hasta que se complete la compilación.

Puede ver este enlace Ocultar elementos durante la carga utilizandov-cloak para una mejor comprensión.

Summonjoy
fuente
5

No incluya ninguna sintaxis vuejs en el archivo HTML:

<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width,initial-scale=1.0">
    <title>My Super app</title>
  </head>
  <body>
    <div id="app"></div>
    <script src="/app.js"></script>
  </body>
</html>

En su JavaScript principal, puede:

import Vue from 'vue'
import App from './App'

new Vue({
  el: '#app',
  components: { App },
  template: '<App/>'
})

Consulte la plantilla de paquete web vuetify como referencia.

Otra solución es usar:

<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width,initial-scale=1.0">
    <title>My Super app</title>
  </head>
  <body>
    <div id="app" is="App"></div>
    <script src="/app.js"></script>
  </body>
</html>

Con:

import Vue from 'vue'
import App from './App'
Vue.component("App", App);

const app = new Vue({});

window.addEventListener("load", async () => {    
  app.$mount("#app")
})
ysdx
fuente
3

Puede mover cualquier renderizado a un componente contenedor simple . La inicialización de VueJS, por ejemplo, el nuevo Vue (...) no debe contener ningún HTML aparte de ese componente de contenedor único.

Dependiendo de la configuración, incluso podría tener <app>Loading...</app>dónde la aplicación es el componente contenedor con cualquier carga de HTML o texto en el medio que luego se reemplaza en la carga.

Una sala
fuente
3
**html**
<div v-cloak>{{ message }}</div>

**css**
[v-cloak] { display: none; }
gotocartik
fuente
2

Use <v-cloak>para ocultar su código Vue antes de vincular datos a lugares relevantes. En realidad, se encuentra en un lugar en la documentación de Vue que cualquiera podría perderlo a menos que lo busque o lea detenidamente.

dakshinasd
fuente
2

Sí, puedes usar v-cloak, me gusta usar spinkit , es una gran biblioteca con solo CSS, mira un ejemplo simple:

var vm = null;
    setTimeout(function() {
    	vm = new Vue({
         el: '#app',
        data: {
          msg: 'Is great, using: ',
          url: 'http://tobiasahlin.com/spinkit/'
         }
      });
     }, 3000);
#app .sk-rotating-plane,
[v-cloak] > * { display:none }
body{
	background: #42b983;
	color: #35495e;
}
#app[v-cloak] .sk-rotating-plane {
	display:block;
	background-color: #35495e;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.2.6/vue.min.js"></script>

<link rel="stylesheet" type="text/css" href="https://cdn.rawgit.com/tobiasahlin/SpinKit/master/css/spinkit.css">


<div id="app" v-cloak>
    <div class="sk-rotating-plane"></div>
    <h1>Vue with c-cloak</h1>
  <p>
    {{ msg }}
    <a :href='url'>{{ url }}</a>
  <p>
</div>

Enlace: - http://tobiasahlin.com/spinkit/

fitorec
fuente
1

Prefiero usar v-ifcon una propiedad calculada que verifica si mis datos están listos, como este:

<template>
    <div v-if="shouldDisplay">
        {{ variableName }}
    </div>
    <div v-else>
      Here you can insert a loader
    </div>
</template>
<script>
export default {
    name: 'Test',
    data() {
        return {
            variableName: null,
        };
    },
    computed() {
        shouldDisplay() {
            return this.variableName !== null;
        }
    },
    mounted() {
        this.variableName = 'yes';
    },
};
</script>

De esta manera, es más fácil mostrar un cargador solo si los datos no están listos (usando v-else).

En este caso particular v-if="variableName"también funcionaría, pero puede haber escenarios más complicados.

Giorgio Tempesta
fuente
0

Para aquellos que usan v-cloak en una vista con múltiples archivos Laravel Blade y no funciona, intente usar v-cloak en el archivo Blade principal en lugar de en cualquier archivo Blade secundario.

usuario8581607
fuente