You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Vue中如何为动态挂载的自定义组件设置绑定的事件属性

修复方案

你的代码存在3个核心逻辑错误,按以下步骤调整即可:

  • 错误1:混淆了props传参和事件绑定逻辑。propsData仅用于向组件传递props值,自定义事件不能写在propsData里,Vue2中动态创建的组件实例需要通过$on方法绑定事件监听。
  • 错误2:子组件中$emit用法错误。$emit的作用是向父组件派发事件通知,无法直接获取父组件的返回值,你需要的鉴权状态应该通过props由父组件传入,而不是靠emit触发获取。
  • 错误3:props中传入的方法提前执行。你在propsData里写的this.isUserAuthenticated()?this.signOut():this.signInUser()会在组件初始化时直接执行,不会等到事件触发时运行。

第一步:修正子组件代码

把需要父组件传入的参数明确定义为props,事件仅用于派发点击通知,不要通过emit拿返回值:

<template>
  <button :class="btnClass" :style="btnStyle" @click="handleClick">
    {{ btnText }}
  </button>
</template>
<script>
export default {
  props: {
    btnClass: String,
    btnStyle: String,
    isAuth: Boolean
  },
  emits: ['action'],
  computed: {
    btnText() {
      return this.isAuth ? 'Sign out from Microsoft' : 'Sign in with Microsoft'
    }
  },
  methods: {
    handleClick() {
      this.$emit('action')
    }
  }
}
</script>

第二步:修正父组件动态挂载逻辑

propsData仅传props值,事件通过$on绑定,逻辑放到事件回调里执行:

insertBtnComponent() {
  const ComponentClass = Vue.extend(buttonVue)
  const instance = new ComponentClass({
    propsData: {
      btnClass: "buttonMs",
      btnStyle: "position: static;",
      isAuth: this.isUserAuthenticated()
    }
  })
  // 绑定自定义事件
  instance.$on('action', () => {
    this.isUserAuthenticated() ? this.signOut() : this.signInUser()
  })
  const selector = document.querySelector(".classNAMEofDiv");
  instance.$mount()
  selector.appendChild(instance.$el)
  // 组件移除前记得调用 instance.$destroy() 避免内存泄漏
}

额外注意事项

  • 不要在props里传执行后的函数结果,需要传回调的话直接传函数引用,不要加括号调用。
  • Vue单向数据流规则要遵守:父传子用props,子通知父用emit,不要试图通过emit反向获取父组件数据。
  • 动态创建的组件实例在不需要时必须手动调用$destroy()销毁,避免内存泄漏。

内容的提问来源于stack exchange,提问作者Nurbek Ss

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.30 04:45:38