Cette fois, je vais vous donner une explication détaillée des étapes pour utiliser la fonction Vue Mixin. Quelles sont les précautions lors de l'utilisation de la fonction Vue Mixin. Voici un cas pratique, jetons un coup d'œil.
Après être passé à l'utilisation de Typescript pour écrire des applications Vue, après une série de chaînes d'outils et de dépendances, j'ai finalement commencé à trébucher. Cependant, il existe une fonction mixin très couramment utilisée, et il ne semble pas y avoir de solution officielle. encore.
Je souhaite profiter de la flexibilité et de la commodité des mixins, mais je souhaite également bénéficier de la garantie de sécurité et de l'expérience fluide d'utilisation d'IntelliSense pendant le développement apportée par le système de type ts.
Il existe un 'vue-class-component'
et un 'vue-property-decorator'
recommandé dans l'organisation officielle vuejs, mais ils n'ont pas été mis en œuvre en conséquence. Après avoir examiné le premier problème, il existe une fonctionnalité en attente depuis longtemps, à savoir la prise en charge du mixin.
Ce n’est pas compliqué, écrivez-en un vous-même.
Dernière remarque : vue-class-component 6.2.0 commence à fournir la méthode mixins, qui est similaire à l'idée d'implémentation de cet article.
Impléments
import Vue, { VueConstructor } from 'vue' export type VClass<T> = { new(): T } & Pick<VueConstructor, keyof VueConstructor> /** * mixins for class style vue component */ function Mixins<A>(c: VClass<A>): VClass<A> function Mixins<A, B>(c: VClass<A>, c1: VClass<B>): VClass<A&B> function Mixins<A, B, C>(c: VClass<A>, c1: VClass<B>, c2: VClass<C>): VClass<A&B&C> function Mixins<T>(c: VClass<T>, ...traits: Array<VClass<T>>): VClass<T> { return c.extend({ mixins: traits }) }
Déclarez VClass
function Mixins<T>(c: VClass<T>, ...traits: Array<VClass<T>>): VClass<T> { return c.extend({ mixins: traits }) }
Quant à ABC, il s'agit d'un travail purement manuel de déclaration de type.
Utilisation
En utilisation réelle :
import { Component, Vue } from 'vue-property-decorator' import { Mixins } from '../../util/mixins' @Component class PageMixin extends Vue { title = 'Test Page' redirectTo(path: string) { console.log('calling reidrectTo', path) this.$router.push({ path }) } } interface IDisposable { dispose(...args: any[]): any } class DisposableMixin extends Vue { _disposables: IDisposable[] created() { console.log('disposable mixin created'); this._disposables = [] } beforeDestroy() { console.log('about to clear disposables') this._disposables.map((d) => { d.dispose() }) delete this._disposables } registerDisposable(d: IDisposable) { this._disposables.push(d) } } @Component({ template: ` <p> <h1>{{ title }}</h1> <p>Counted: {{ counter }}</p> </p> ` }) export default class TimerPage extends Mixins(PageMixin, DisposableMixin) { counter = 0 mounted() { const timer = setInterval(() => { if (this.counter++ >= 3) { return this.redirectTo('/otherpage') } console.log('count to', this.counter); }, 1000) this.registerDisposable({ dispose() { clearInterval(timer) } }) } } count to 1 count to 2 count to 3 calling reidrectTo /otherpage about to clear disposables
Notez que le DisposableMixin qui étend directement Vue n'est pas un composant Vue valide, et il ne peut pas non plus be Utilisez-le directement dans l'option mixins. S'il doit être utilisé par un composant de définition personnalisé étendu par Vue.extend, n'oubliez pas de l'envelopper avec Component.
const ExtendedComponent = Vue.extend({ name: 'ExtendedComponent', mixins: [Component(DisposableMixin)], })
Classe abstraite
Les mixins utilisés dans les systèmes d'entreprise sont en fait plus complexes dans la plupart des cas et fournissent certaines fonctions de base, mais certaines parties doivent être laissées aux successeurs pour qu'ils les mettent en œuvre eux-mêmes. cette fois, il convient d'utiliser la classe abstraite.
abstract class AbstractMusicPlayer extends Vue { abstract audioSrc: string playing = false togglePlay() { this.playing = !this.playing } } class MusicPlayerA extends AbstractMusicPlayer { audioSrc = '/audio-a.mp3' } class MusicPlayerB extends AbstractMusicPlayer { staticBase = '/statics' get audioSrc() { return `${this.staticBase}/audio-b.mp3` } }
Mais les classes abstraites ne peuvent pas être instanciées et ne répondent pas aux exigences { new(): T }
, elles ne peuvent donc qu'être héritées et ne peuvent pas être mélangées. Pour la même raison, les classes abstraites ne peuvent pas être 'vue-class-component'
🎜 > Décoration des fonctions des composants.
À ce stade, nous devons écrire les fonctions implémentées dans Mixin, mettre les fonctions à implémenter dans l'interface et laisser la classe spécifique les implémenter.
interface IMusicSourceProvider { audioSrc: string } /** * @implements IPlayerImplementation */ class PlayerMixin extends Vue { /** @abstract */ audioSrc: string logSrc() { console.log(this.audioSrc) } } interface IPlayerImplementation extends IMusicSourceProvider {} class RealPlayer extends Mixins(PlayerMixin) implements IPlayerImplementation { audioSrc = '/audio-c.mp3' }
Cette façon de tromper le compilateur est en fait assez maladroite. Si une classe spécifique hérite de PlayerMixin mais ne déclare pas explicitement implémenter IPlayerImplementation, le compilateur ne peut pas vous signaler cette erreur. Nous ne pouvons qu'écrire soigneusement des commentaires dans le code et espérer que les utilisateurs ne l'oublieront pas.
Je pense que vous maîtrisez la méthode après avoir lu le cas dans cet article. Pour des informations plus intéressantes, veuillez prêter attention aux autres articles connexes sur le site Web chinois de php !
Lecture recommandée :
Redirection vers la page d'accueil après avoir partagé la page
Explication détaillée de l'utilisation de la méthode de surveillance dans Vue
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!