I'd like to get the innerHTML of a rendered component in Vue 3 but I don't figure out how.
I know how to do this with refs on standard HTML markup, but it doesn't work with components.
<template>
<div>
<div ref="hello"><span>Hello World</span></div>
<HelloWorld ref="helloworld"><span>Hello World</span></HelloWorld>
</div>
</template>
<script setup>
import { onMounted, ref, unref } from 'vue';
import HelloWorld from './components/HelloWorld.vue';
const hello = ref();
const helloworld = ref();
onMounted(() => {
console.log(unref(hello).innerHTML); // <span>Hello World</span>
console.log(unref(helloworld).innerHTML); // undefined
});
</script>
I'm not using SSR, my current requirement is on a SPA.
I managed to do it by wrapping <HelloWorld> into a div with and id and querying it but that's a bit crappy.
Any ideas?
Thanks!
CodePudding user response:
I don’t remember the exact sources, but I came across code like this:
const stopWatch = watch(helloworld, value => {
if (value) {
stopWatch();
// TODO: Start using the element
}
}, { immediate: true });
The problem is that when the current component is finished mounting, the child component may not yet have time to be mounted.
As part of a more reasonable description, you can wrap it all in a function:
function onRefReady (ref, cb) {
const stopWatch = watch(ref, value => {
if (value) {
stopWatch();
cb(value);
}
}, { immediate: true });
onScopeDispose(stopWatch);
}
And use it like this:
onRefReady(helloworld, el => {
// TODO: Start using the element
})
CodePudding user response:
Add a ref="helloWorldRef" to the component then helloWorldRef.value?.$el it's similar as document.querySelector(".hello-world").
Note that the optional chaining is necessary because it can be null if not mounted yet. You'd have to implement something to be sure it is available and assigned.
E.g.
watch(
() => helloWorldRef.value?.$el,
(n) => console.log(n)
);
