最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - How to call a vue component method from another js file - Stack Overflow

programmeradmin0浏览0评论

I have a Vue v2.3.4 (quasar-framework v0.14.2) modal ComponentA working when clicking on a button in the same ponent. The MyModal ponent seems to work fine (as I can trigger it with a button). However I have code in a separate util.js file which should trigger the modal (from a 'myUtilElement'). How can I do that?

ComponentA.vue

<template>
  <div>
    <div id='lotsofstuff'></div>
    <myModal ref="myModal"></myModal>
  </div>
</template>

<script>
import MyModal from '../MyModal.vue'

export default {
  name: 'ponentA',
  ponents: {MyModal},
  methods: {
    openModal: function () {
      this.$refs.myModal.open()
    },
    otherMethods:...etc.
}

Util.js

import ComponentA from '../ComponentA.vue'

myUtilElement.addEventListener('click', triggerModal, false)

function triggerModal () {
  ComponentA.methods.openModal()
}

I now get following error in the console:

Uncaught TypeError: Cannot read property 'openModal' of undefined
    at HTMLElement.triggerModal

I have a Vue v2.3.4 (quasar-framework v0.14.2) modal ComponentA working when clicking on a button in the same ponent. The MyModal ponent seems to work fine (as I can trigger it with a button). However I have code in a separate util.js file which should trigger the modal (from a 'myUtilElement'). How can I do that?

ComponentA.vue

<template>
  <div>
    <div id='lotsofstuff'></div>
    <myModal ref="myModal"></myModal>
  </div>
</template>

<script>
import MyModal from '../MyModal.vue'

export default {
  name: 'ponentA',
  ponents: {MyModal},
  methods: {
    openModal: function () {
      this.$refs.myModal.open()
    },
    otherMethods:...etc.
}

Util.js

import ComponentA from '../ComponentA.vue'

myUtilElement.addEventListener('click', triggerModal, false)

function triggerModal () {
  ComponentA.methods.openModal()
}

I now get following error in the console:

Uncaught TypeError: Cannot read property 'openModal' of undefined
    at HTMLElement.triggerModal
Share Improve this question edited Sep 11, 2017 at 6:47 musicformellons asked Sep 10, 2017 at 19:41 musicformellonsmusicformellons 13.4k5 gold badges57 silver badges94 bronze badges 6
  • new ComponentA? – freethinker Commented Sep 10, 2017 at 19:50
  • 2 See Non Parent-Child Communication on the docs. – Etheryte Commented Sep 10, 2017 at 19:57
  • It seems that you are using this.$refs.myModal while you named your reference modalTest in <myModal ref="modalTest"></myModal>. – Vincent Cantin Commented Sep 11, 2017 at 1:42
  • @Vincent Mmh, yes, you're right! This was an presentation error (I made some adaptions before presenting, but forgot to change this ref...). I corrected it now in the question. Problem persists. I think the eventbus that Nit suggests is the way to go. – musicformellons Commented Sep 11, 2017 at 6:50
  • I think so, event bus is a solution. – Vincent Cantin Commented Sep 11, 2017 at 6:51
 |  Show 1 more ment

2 Answers 2

Reset to default 4

See non parent-child munication on the docs. Essentially, you have two mon options: an event bus or centralized state management.
An event bus is a simple pub-sub pattern:

var bus = new Vue()
// in ponent A's method
bus.$emit('openModal', params)
// in ponent B's created hook
bus.$on('openModal', function(params) {
  // ...
})

The most mon centralized state management library for Vue is Vuex, which is analogous to Flux/Redux/etc.

src/eventBus.js

import Vue from 'vue';
export default new Vue();

src/ponents/ComponentA.vue

<template>
  <div>
    <div id="lotsofstuff">
      <!-- some code here -->
      <button type="button" class="btn btn-outline-secondary" @click="openModal">Open Modal</button>
    </div>
    <myModal></myModal>
  </div>
</template>

<script>
import MyModal from './MyModal.vue';
import EventBus from '../eventBus';

export default {
  name: 'ponentA',

  ponents: {
    MyModal
  },

  methods: {
    openModal: function () {
      var params = {title: 'My Modal Title'}
      EventBus.$emit('OPEN_MODAL', params)
    },
    // otherMethods:...etc.
}
</script>

src/ponents/MyModal.vue

<template>
  <div v-show="show">
    <div class="modal-title">{{ title }}</div>
    <!-- some code here -->
  </div>
</template>

<script>
import EventBus from '../eventBus';

export default {
  name: 'MyModal',

  data () {
    return {
      show: false,
      title: 'Default Title'
    }
  },

  created () {
    var self = this;

    EventBus.$on('OPEN_MODAL', function (params) {
      self.show = true;
      self.title = params.title;
    });
  },

  methods: {
    open () {
      this.show = true;
    },

    close () {
      this.show = false;
    }
  }
}
</script>
发布评论

评论列表(0)

  1. 暂无评论