Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Programatically get Svelte component instance

Is it possible to get a component's instance outside components files?

For example, if I programmatically create a component using const myComponent = new Component(options), I can access its instance and call methods such as myComponent.$set(props).

Is it possible to get an instance of some deeply nested component, outside any component scope?

Either to get it by id (the dom class svelte-someid), or to get it internally inside a component (and use it to create a global registry of component instance references).

like image 400
Maciej Krawczyk Avatar asked Oct 30 '20 08:10

Maciej Krawczyk


1 Answers

Since the question gains on popularity and has no answers, I will try to answer it. I'm not aware of a better method to do it.

Basically in the upper scope define an object that will serve as the component registry and expose it in the context. Then you can add the instances to the registry from the parent component containing the instance.

App.svelte

<script>
    import { setContext, onMount } from 'svelte';
    
    import Parent from './Parent.svelte';
    
    const components = { };
    
    setContext('components', components);
    
    onMount(() => {
        components.child1.message = 'Child 1';
        components.child2.message = 'Child 2';
    })
</script>

<Parent></Parent>

Parent.svelte

<script>
    import { onMount, getContext } from 'svelte';
    import Child from './Child.svelte';
    
    let child1, child2;
    
    const components = getContext('components');
    
    onMount(() => {
        components.child1 = child1;
        components.child2 = child2;
    })
</script>

<Child bind:this={child1}></Child>
<Child bind:this={child2}></Child>

Child.svelte

<svelte:options accessors/>

<script>
    export let message = '';
</script>

<p>Child: {message}</p>

REPL

like image 68
Maciej Krawczyk Avatar answered Oct 07 '22 12:10

Maciej Krawczyk