27

我想用来onMounted启动第三方库。为此,我需要组件元素作为其上下文。在 Vue 2 中,我会得到它,this.$el但不确定如何使用组合函数来完成它。setup有两个参数,它们都不包含元素。

setup(props, context) {
    onMounted(() => {
        interact($el)
            .resizable();
    })
}
4

2 回答 2

39

tl;博士:

在 Vue 3 中,组件不再仅限于 1 个根元素。隐含地,这意味着您不再拥有$el.
您必须使用ref与模板中的任何元素进行交互。

正如@AndrewSee 在评论中指出的那样,当使用渲染函数(不是模板)时,您可以refcreateElement选项中指定所需的:

render: function (createElement) {
  return createElement('div', { ref: 'root' })
}
// or, in short form:
render: h => h('div', { ref: 'root' })

初步答案:

文档中所述,

[...]反应式引用模板引用的概念在 Vue 3 中是统一的。

您还有一个关于如何ref创建“根”元素的示例。显然,您不需要将其命名为 root。命名它$el,如果你愿意的话。但是,这样做并不意味着它将以 . 的形式提供this.$el,而是以this.$refs.$el.

<template>
  <div ref="root"></div>
</template>

<script>
  import { ref, onMounted } from 'vue'

  export default {
    setup() {
      const root = ref(null)

      onMounted(() => {
        // the DOM element will be assigned to the ref after initial render
        console.log(root.value) // this is your $el
      })

      return {
        root
      }
    }
  }
</script>

在 Vue 3 中,您不再仅限于 中的一个根元素<template>,因此您必须专门ref指定要与之交互的任何元素。

于 2020-05-04T20:04:59.570 回答
2

在 Vue 3 + Composition API 中没有$el提供替代方案。

即使您使用带有 Options API 的 Vue 3,由于 Fragments 的可用性,建议使用模板 refs 来直接访问 DOM 节点,而不是依赖this.$el.


如何启动第三方库

假设我们有一个用于第三方库的 div 元素:

<template>
  Below we have a third-party-lib
  <div class="third-party-lib"></div>
</template>

然后我们想从 Javascript 启动它:

解决方案 1(推荐):使用模板引用

<script setup>
import { ref, onMounted } from 'vue';

const $thirdPartyLib = ref(null); // template ref

onMounted(() => {
  $thirdPartyLib.value.innerText = 'Dynamically loaded';
});
</script>

<template>
  Below we have a third-party-lib
  <div ref="$thirdPartyLib" class="third-party-lib"></div>
</template>

解决方案 2(不推荐):使用未记录的@VnodeMounted

<script setup>
function initLib({ el }) {
  el.innerText = 'Dynamic content';
}
</script>

<template>
  Below we have a third-party-lib
  <div class="third-party-lib" @VnodeMounted="initLib"></div>
</template>

实时查看两种解决方案

于 2022-01-29T19:01:20.647 回答