Write in front
Because of the vue.js is very interested in, and the usual work of the technical stack is also vue.js, these months spent some time to study the vue.js source code, and do a summary and output.
The original address of the article: Https://github.com/answershuto/learnVue.
In the course of learning, for Vue added a Chinese annotation https://github.com/answershuto/learnVue/tree/master/vue-src, I hope it can be other to learn the Vue source of small partners to help.
There may be some understanding of the deviation of the place, welcome to mention issue point, common learning, common progress.
Vue Event API
As we all know, Vue.js provides us with four event APIs, namely $on, $once, $off, $emit.
Initializing events
The initialization event creates an _events object on the VM that holds the event. The contents of _events are as follows:
{ eventName: [func1, func2, func3]}
Store the event name and the corresponding execution method.
/ * Initialize event * /Export function initevents (vm:component) {/ * Create an _events object on the VM to hold the event. */Vm._events =Object. Create (NULL)/ * This bool flag bit to indicate whether a hook exists, rather than a hash table to find out if there is a hook, this can reduce unnecessary overhead and optimize performance. */Vm._hashookevent =false //init parent attached Events / * Initialize parent component Attach events * / ConstListeners = VM. $options. _parentlistenersif(listeners) {updatecomponentlisteners (VM, listeners)}}
$on
Emit trigger.
Vue.prototype. $on = function (event:string | Array<string>, fn:function): Component {ConstVm:component = This /* If it is an array, then recursive $on, bind the method to each member */ if(Array. IsArray (Event)) { for( Leti =0, L = event.length; I < L; i++) { This. $on (Event[i], fn)}}Else{(Vm._events[event] | | (Vm._events[event] = [])). Push (FN)//optimize hook:event cost by using a Boolean flag marked at registration //Instead of a hash lookup / * Here, when registering an event, the bool value is also a flag bit to indicate that there is a hook, instead of a hash table to find out if there is a hook, this can reduce unnecessary overhead and optimize performance. */ if(Hookre.test (event)) {vm._hashookevent =true} }returnVM}
$once
The $once listens for an event that can only be triggered once, and automatically removes the event after it is triggered.
Vue.prototype. $once = function (event:string, fn:function): Component {ConstVm:component = This function on () {/ * Destroy the event at the first execution * /VMs. $off (event, ON)/ * method to execute registration * /Fn.apply (VM,arguments)} On.fn = fn vm. $on (event, ON)returnVM}
$off
$off used to remove custom events
Vue.prototype. $off = function (event?: String | Array<string>, fn?: Function): Component {ConstVm:component = This // All / * Log off all Events if no arguments are passed * / if(!arguments. length) {vm._events =Object. Create (NULL)returnVM}//array of events / * Recursive logoff event if event is an array * / if(Array. IsArray (Event)) { for( Leti =0, L = event.length; I < L; i++) { This. $off (Event[i], FN)}returnVM}//Specific event ConstCBS = Vm._events[event]/*github:https://github.com/answershuto*/ / * The event itself does not exist and is returned directly * / if(!CBS) {returnVM}/ * Unregister all methods under the event method if only the event parameter is passed * / if(arguments. length = =1) {Vm._events[event] =NULL returnVM}//Specific handler / * Traverse to find the corresponding method and delete * / LetCb Leti = Cbs.length while(i--) {cb = Cbs[i]if(cb = = = FN | | cb.fn = = FN) {Cbs.splice (I,1) Break} }returnVM}
$emit
$emit used to trigger the specified custom event.
Vue.prototype. $emit = function (event:string): Component {ConstVm:component = This if(Process.env.NODE_ENV!==' production ') {ConstLowercaseevent = Event.tolowercase ()if(Lowercaseevent!== event && Vm._events[lowercaseevent]) {Tip (' Event"${lowercaseevent}"is emittedinchComponent ' + ' ${formatcomponentname (VM)} but the handler is registered for "${event}". ' + ' Note that HTML attributes is Case-insensitive and cannot use ' + ' v-on to listen to CamelCase events when usinginch-dom templates. ' + ' should probably use"${hyphenate (Event)}"Instead of"${event}".` ) } } LetCBS = Vm._events[event]if(CBS) {/ * Convert an object of an array of classes to a group * /CBS = Cbs.length >1? ToArray (CBS): CBSConstargs = ToArray (arguments,1)/ * Traversal execution * / for( Leti =0, L = cbs.length; I < L; i++) {cbs[i].apply (VM, args)}}returnVM}
About
Dyeing mo
Email:[email protected] or [email protected]
Github:https://github.com/answershuto
blog:http://answershuto.github.io/
Home: Https://www.zhihu.com/people/cao-yang-49/activities
Knowledge Column: Https://zhuanlan.zhihu.com/ranmo
Nuggets: https://juejin.im/user/58f87ae844d9040069ca7507
Oschina:https://my.oschina.net/u/3161824/blog
Reprint please indicate the source, thank you.
Please follow my public number.
?
Vue.js Source code--event mechanism