web-dev-qa-db-fra.com

Comment définir des styles CSS pour un composant vue.js lors de l'enregistrement de ce composant?

Je peux enregistrer un composant personnalisé vue.js avec

// register
Vue.component('my-component', {
  template: '<div class="my-class">A custom component!</div>'
})   

Voir aussi https://vuejs.org/v2/guide/components.html

Comment puis-je inclure des classes CSS pour mon composant?

Je m'attendais à quelque chose comme

 Vue.component('my-component', {
      template: '<div class="my-class">A custom component!</div>',
      css: '#... my css stylesheet...'
    })

mais il ne semble pas y avoir d'option css.

Je sais que je pourrais

a) définir toutes les classes css dans une feuille de style css globale ou

b) utiliser singe-file-vue-components (nécessiterait un outil de construction pour supprimer les fichiers * .vue, voir https://vuejs.org/v2/guide/single-file-components.html )

mais je préfère

c) spécifier une feuille de style CSS pour le composant lors de l'enregistrement du composant.

=> Comment faire?

8
Stefan

il ne semble pas y avoir d'option css.

C'est exact. Vous ne pouvez pas faire ce que vous décrivez. Le documentation sur les composants d'un seul fichier est assez clair que l'un des avantages est que vous pouvez le faire avec eux et ne pouvez pas le faire sans eux.

Dans de nombreux projets Vue, les composants globaux seront définis en utilisant Vue.component, Suivi de new Vue({ el: '#container' }) pour cibler un élément conteneur dans le corps de chaque page.

Cela peut très bien fonctionner pour les projets de petite à moyenne taille, où JavaScript n'est utilisé que pour améliorer certaines vues. Cependant, dans des projets plus complexes, ou lorsque votre frontend est entièrement piloté par JavaScript, ces inconvénients deviennent évidents:

[...] Aucun support CSS signifie que même si HTML et JavaScript sont modulaires en composants, CSS est visiblement omis

6
Roy J

Il est vrai que vous ne pouvez pas ajouter <style> à l'intérieur d'un modèle Vue ou ajoutez CSS directement dans le composant, sauf si vous le liez ou définissez votre CSS globalement. Mais vous pouvez créer un composant personnalisé qui le fera dynamiquement pour vous. échantillon

4
ken

Gardez à l'esprit que les composants Vue sont des macros effectivement.

render est la fonction de substitution et vueDefinition (defn3 ci-dessous) est effectivement un class pour le tagName donné.

Un template est juste un raccourci syntactic-sugar qui sera compiled (avec quelques restrictions de modèle d'utilisation de la vue) = dans une fonction render si vous ne fournissez pas votre propre fonction render.

const defn3 = {
  tagName: 'ae-css',
  mounted() {
    const vueDefinition = this.$options;
    this.$el.appendChild(document.createTextNode(vueDefinition.css));
  },
  css: `
    * {
      color: blue;
    }
  `,
  render(h) {
    return h('style');
  }
}
Vue.component(defn3.tagName, defn3);

Avec cette solution en main, il y a plusieurs bonnes raisons pour lesquelles vous ne voulez probablement pas quelque chose d'aussi simpliste que ce que je viens de fournir.

A savoir, vous voulez avoir votre css modularisé de telle sorte que cela n'affecte aucun aspect de votre page que vous n'avez pas l'intention de le faire. Pour cela, vous avez besoin soit de règles soigneusement conçues css avec l'héritage et la portée prévus; utilisant probablement un class=... Mais une meilleure approche serait d'utiliser simplement les installations de Vue qui offrent automatiquement des capacités similaires.

Si vous souhaitez utiliser des fonctionnalités d'architecture de navigateur modernes pour cela, vous souhaiterez peut-être que vos composants soient de vrais navigateurs DOM WebComponents qui utilisent le shadowDOM et gardez vos éléments et styles internes encapsulés dans un shadowRoot. Voir cette bibliothèque , pour le faire dans Vue .

1
smallscript

Voici une réponse depuis le Pakistan :)

export const ContactUs = Vue.component(
'mycomponent-contact-us'
,{
    props: {
        backgroundColor: {
            type: String
            ,required: false
            ,default: "red"
        }
    }
    ,data: function(){
        return {

        }
    }
    ,template: `
        <div>
            <span class='contact_us_text' >Contact Us Component and its bg color will be {{backgroundColor}}</span>
        </div>
    `
    ,mounted: function(){
        var css_text = `
        .contact_us_text{
            color: `+this.backgroundColor+`;
        }
        `;
        var css = document.createElement('style');
        css.type='text/css';
        css.setAttributeNode( document.createAttribute('scopped') );
        css.appendChild(    document.createTextNode( css_text )     );
        this.$el.appendChild(   css     );
    }
}

);

0
Talha

Vous pouvez incorporer une balise de style dans l'élément racine de votre modèle:

Vue.component('my-component', {
      template: `
      <div class="my-class">
            A custom component!

            <style>
                  // ... my css stylesheet...
            </style>
      </div>
      `
})
0
Ferkze