• This is the third day of my participation in the November Gwen Challenge. Check out the details: the last Gwen Challenge 2021

Programmatic event listeners

In addition to V-ON and $EMIT, the Vue instance provides other methods in its event interface. We can:

  • Listen for an event with $on(eventName, eventHandler)
  • Listen for one event at a time with $once(eventName, eventHandler)
  • Stop listening for an event with $off(eventName, eventHandler)

These methods are not typically used, but they can be useful when you need to manually listen for events on a component instance.

For example, sometimes we integrate third-party libraries with components:

Vue.component('my-cmp', {
   // Attach the date picker to an input box once
   // It will be mounted to the DOM.
  mounted () {
     // Pikaday is a library of third-party date pickers
    this.picker = new Pikaday({
      field: this.$refs.input,
      format: 'YYYY-MM-DD',}}),// Before the component is destroyed,
   // Also destroy the date picker.
  beforeDestroy () {
    this.picked.destroy();
  },
  template: ` < div > < input type = "text" ref = "input" / > < button @ click = "$destroy ()" > destroying components < / button > < / div > `,})Copy the code

There are two potential problems with the above approach:

  • It needs to store the picker in the component instance, preferably accessible only by lifecycle hooks if possible. This is not a serious problem, but it can be considered clutter.
  • Our build code is separate from our cleanup code, which makes it harder to programmatically clean up everything we build.

So, we can solve these two problems with programmatic listeners:

Vue.component('my-cmp', {
  mounted () {
    var picker = new Pikaday({
      field: this.$refs.input,
      format: 'YYYY-MM-DD',})this.$once('hook:beforeDestroy'.() = >{ picker.destroy(); })},template: ` < div > < input type = "text" ref = "input" / > < button @ click = "$destroy ()" > destroying components < / button > < / div > `
})
Copy the code

Using this strategy, we can also make multiple input field elements use different pikaday:

Vue.component('my-cmp', {
  mounted () {
    this.datePicker('inputA');
    this.datePicker('inputB');
  },
  methods: {
    datePicker (refName) {
      var picker = new Pikaday({
        field: this.$refs[refName],
        format: 'YYYY-MM-DD',})this.$once('hook:beforeDestroy'.() = >{ picker.destroy(); })}},template: 
      
`
}) Copy the code

Note, though, that if you find yourself having to do a lot of setup and cleanup in a single component, the best approach is usually to create more modular components. In this case, we recommend creating a reusable

component.

The last

If it is helpful to you, I hope to give you a 👍 comment/collection/three even!

Bloggers are honest and answer questions for free ❤