Vue Typescript 子组件方法

Posted

技术标签:

【中文标题】Vue Typescript 子组件方法【英文标题】:Vue Typescript Child Component Methods 【发布时间】:2020-08-13 20:12:06 【问题描述】:

我已经使用 Vue 工作了一段时间,但已经开始转向使用 Typescript 实现。我遇到了一个问题,我无法通过父级的引用访问子级的方法。

父代码:

<template>
  <ref-test ref="child"/>
</template>

<script lang="ts">
import Vue from "vue";
import RefTest from "./RefTest.vue";

export default Vue.extend(
  name: "RefParent",
  components: 
    RefTest
  ,
  data: () => (),
  methods: ,
  mounted() 
    const child = this.$refs.child as RefTest;
    child.pingMe();
  
);
</script>

<style scoped></style>

子代码:

<template>
  <div>REF TEST...</div>
</template>

<script lang="ts">
import Vue from "vue";

export default Vue.extend(
  name: "RefTest",
  data: () => (),
  methods: 
    pingMe() 
      console.log("refTest pingMe");
    
  
);
</script>

<style scoped></style>

我看到的问题是,当我使用 const child = this.$refs.child as RefTest; 引用孩子时,我看到了错误:'RefTest' refers to a value, but is being used as a type here.。此外,child.pingMe(); 正在报告:Property 'pingMe' does not exist on type 'Vue'.

我尝试了各种变通方法:https://github.com/vuejs/vue/issues/8406 主要围绕接口定义和 Vue.extend&lt;&gt; 调用。

感谢任何帮助我继续思考使用 Typescript 的差异。

【问题讨论】:

错误说明出了什么问题。 RefTest 既不是类型也不是接口,因此不能在需要类型的地方使用。试试as typeof RefTest 谢谢。我想对 Typescript 较新,我不理解错误?使用 as typeof RefTest 会产生新的错误。 TS2352: Conversion of type 'Vue | Element | Vue[] | Element[]' to type 'VueConstructor&lt;Vue&gt;' may be a mistake because neither type sufficiently overlaps with the other. If this was intentional, convert the expression to 'unknown' first.   Type 'Element[]' is missing the following properties from type 'VueConstructor&lt;Vue&gt;': extend, nextTick, set, delete, and 8 more. 【参考方案1】:

好的。做了一些更多的实验,我不确定这是“正确”的解决方案还是最优雅的解决方案,但代码有效并且编译器没有抱怨。最终,我创建了一个接口类型,其中包含我想要达到的方法。在父级中,我现在将 $ref 转换为该接口类型,一切似乎都很好。请让我知道是否有更好更优雅的方式来执行此操作(或者这是否是“最佳”方式)请参阅下面的完整代码。

接口(types/refInterface.ts):

import Vue from "vue";

export interface RefInterface extends Vue 
  pingMe(): void;

家长:

<template>
  <ref-test ref="child" />
</template>

<script lang="ts">
import Vue from "vue";
import RefTest from "./RefTest.vue";
import  RefInterface  from "@/types/refInterface";

export default Vue.extend(
  name: "RefParent",
  components: 
    RefTest
  ,
  data: () => (),
  methods: ,
  mounted() 
    const child = this.$refs.child as RefInterface;
    child.pingMe();
  
);
</script>

<style scoped></style>

“子”代码没有改变,所以没有重新粘贴它。

【讨论】:

以上是关于Vue Typescript 子组件方法的主要内容,如果未能解决你的问题,请参考以下文章

vue ts ,vue使用typescript,三种组件传值方式

停止 typescript-eslint/explicit-module-boundary-types 应用于不使用 Typescript 的 vue 组件

VUE组件的封装--父组件向子组件传值 调用父组件的方法改变子组件data&调用子组件方法

vue3没了$children,如何获取子组件???

vue-type-check: Vue 模板中的 Typescript 类型检查

vue组件之间传值父组件获取子组件的方法