简体   繁体   English

Vue & Typescript:访问子组件方法时如何避免 TS 错误

[英]Vue & Typescript: How to avoid TS error when accessing child component's methods

I've created a custom class-based vue component and I'm trying to access its methods and/or computed properties from a parent component.我创建了一个自定义的基于类的 vue 组件,我正在尝试从父组件访问它的方法和/或计算属性。 There is an example in the Vue Docs that explains what I'm trying to do ( https://v2.vuejs.org/v2/guide/components-edge-cases.html#Accessing-Child-Component-Instances-amp-Child-Elements ). Vue Docs 中有一个示例解释了我正在尝试做的事情( https://v2.vuejs.org/v2/guide/components-edge-cases.html#Accessing-Child-Component-Instances-amp-子元素)。 So basically it's this所以基本上就是这样

class ParentComponent extends Vue {
    someMethod() {
        (this.$refs.myChildRef as ChildComponent).focus()
    }
}

class ChildComponent extends Vue {
    focus() {
        // do something
    }
}

Now, this leads to a TS error: "TS2339: Property 'focus' does not exist on type 'Vue'"现在,这会导致 TS 错误:“TS2339:属性 'focus' 在类型 'Vue' 上不存在”

So apparently, typescript doesn't see that my ChildComponent has additional methods.显然,打字稿没有看到我的 ChildComponent 有其他方法。

The code still works during runtime though, so it just appears to be a typescript issue.该代码在运行时仍然有效,所以它似乎只是一个打字稿问题。

Does anyone have an idea how to solve this?有谁知道如何解决这个问题?

Option 1: Ignore it选项1:忽略它

//@ts-ignore

Option 2: Type any选项 2:键入任何

const child: any = this.$refs.myChildRef;
child.focus();

Option 3: Interface, as mentioned by @LLai选项 3:接口,如@LLai 所述

interface ComponentInterface {
    focus: () => void
}

Option 4: Merge types选项 4:合并类型

As a one liner as @LaLai says正如@LaLai 所说的那样

(this.$refs.myChildRef as ChildComponent & { focus: () => void }).focus()

or if you need it more often或者如果您更频繁地需要它

Class ParentComponent extends Vue {
    $refs: Vue["$refs"] & {
      myChildRef: { focus: () => void }
    };  
}

Option 5: @Ref() decorator from vue-property-decorator选项 5:来自vue-property-decorator @Ref()装饰器

Class ParentComponent extends Vue {
  @Ref()
  childComponent: ChildComponent
}

One solution is to implement an interface on your child component.一种解决方案是在您的子组件上实现一个接口。

interface ComponentInterface {
    focus: () => void
}

class ChildComponent extends Vue implements ComponentInterface {
    focus () {
        // do something
    }
}

Another option is to merge the types另一种选择是合并类型

class ParentComponent extends Vue {
    someMethod() {
        (this.$refs.myChildRef as ChildComponent & { focus: () => void }).focus()
    }
}

But this can get repetitive if you are calling focus a lot outside of the child component.但是,如果您在子组件之外大量调用焦点,这可能会变得重复。 I prefer option 1.我更喜欢选项1。

We have similar issues with our components which were built using typescript.我们使用 typescript 构建的组件也有类似的问题。 The solution we are using for now, is just adding a ts-ignore comment before each of issue.我们现在使用的解决方案只是在每个问题之前添加一个 ts-ignore 注释。 It's not the best way but it works.这不是最好的方法,但它有效。

//@ts-ignore

try it out试试看

I don't want to declare the method name twice so I use this way:我不想两次声明方法名称,所以我使用这种方式:

In ChildComponent.ts在 ChildComponent.ts 中

import Vue from 'vue'

export default class ChildComponent extends Vue.extend({
    methods: {
        focus() {}
    }
}){}

In ChildComponent.vue在 ChildComponent.vue 中

<template>...</template>

<script lang="ts">
    import ChildComponent from './ChildComponent'

    export default ChildComponent;
</script>

In ParentComponent在父组件中

import Vue from 'vue'

import ChildComponent from './ChildComponent.vue'
import ChildComponentClass from './ChildComponent'

export default class ParentComponent extends Vue.extend({
    components: {ChildComponent},
    methods: {
        someMethod() {
            (<ChildComponentsClass>this.$refs.child).focus();
        }
    }
}){}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 Vue&TypeScript:在项目目录之外的TypeScript组件中实施导入时,如何避免错误TS2345? - Vue&TypeScript: how to avoid error TS2345 when import implemented in TypeScript component outside of project directory? Vue Typescript 子组件方法 - Vue Typescript Child Component Methods 如何在 TypeScript Vue 组件中访问全局 mixin 的方法? - How to access global mixin's methods in TypeScript Vue component? Vue 2 和 Typescript:VS 代码错误 TS2769 将任何道具传递给自定义组件时 - Vue 2 and Typescript: VS Code Error TS2769 When passing ANY prop to custom component 分配属性时,如何避免 Microsoft Bot Framework 的 StatePropertyAccessor 中的 Typescript 错误 TS2345 - How can I avoid a Typescript Error, TS2345, in the Microsoft Bot Framework's StatePropertyAccessor when I assign a property 如何使用 typescript 在 Vue3 中注册子组件 - How to register a child component in Vue3 with typescript 如何在子 vue 组件中声明方法? - how to declare methods in child vue component? 如何使用 ts 在 vue3 中渲染 function 中的组件方法 - how to expose component methods in render function in vue3 with ts Vue组件导入接口时如何避免TS2614错误 - How to avoid TS2614 error when importing interfaces from Vue components vue3 typescript 问题,如何修复 ts(2305) 错误? - vue3 typescript question, how to fix ts(2305) error?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM