View | Details | Raw Unified | Return to bug 37911
Collapse All | Expand All

(-)a/koha-tmpl/intranet-tmpl/prog/en/modules/intranet-main.tt (-1 / +10 lines)
Lines 13-19 Link Here
13
    [% END %]</title
13
    [% END %]</title
14
>
14
>
15
[% Asset.css("css/mainpage.css") | $raw %]
15
[% Asset.css("css/mainpage.css") | $raw %]
16
[% Asset.js("js/vue/dist/islands.js", "defer" => 1, async => "1") | $raw %]
17
[% INCLUDE 'doc-head-close.inc' %]
16
[% INCLUDE 'doc-head-close.inc' %]
18
</head>
17
</head>
19
18
Lines 338-345 Link Here
338
    <hello-islands message="This is an attribute on the web component, that's bound to a prop in the Vue component. Cool, right?" color="dodgerblue"></hello-islands>
337
    <hello-islands message="This is an attribute on the web component, that's bound to a prop in the Vue component. Cool, right?" color="dodgerblue"></hello-islands>
339
</div>
338
</div>
340
<!-- /.row -->
339
<!-- /.row -->
340
<div class="row w-25 m-auto p-4 border border-4 border-warning br-5 rounded text-center mt-4">
341
    <p>
342
        <span>Uncomment me in <span class="font-monospace">intranet-main.tt</span> 👇</span><br />
343
        <span class="font-monospace text-danger">-&lt;!-- &lt;hello-world&gt;&lt;/hello-world&gt; --&gt;</span><br />
344
        <span class="font-monospace text-success">+&lt;hello-world&gt;&lt;/hello-world&gt;</span>
345
    </p>
346
    <!-- <hello-world></hello-world> -->
347
</div>
348
<!-- /.row -->
341
349
342
[% MACRO jsinclude BLOCK %]
350
[% MACRO jsinclude BLOCK %]
351
    [% Asset.js("js/vue/dist/islands.js", "type" => "module") | $raw %]
343
    <script>
352
    <script>
344
        var MSG_CONFIRM_DELETE = _("Are you sure you want to delete this news item? This cannot be undone.");
353
        var MSG_CONFIRM_DELETE = _("Are you sure you want to delete this news item? This cannot be undone.");
345
        $(document).ready(function () {
354
        $(document).ready(function () {
(-)a/koha-tmpl/intranet-tmpl/prog/js/vue/components/HelloWorld.vue (+18 lines)
Line 0 Link Here
1
<!--
2
Say Hello World with Vue!
3
-->
4
5
<script setup>
6
import { ref } from "vue";
7
8
// A "ref" is a reactive data source that stores a value.
9
// Technically, we don't need to wrap the string with ref()
10
// in order to display it, but we will see in the next
11
// example why it is needed if we ever intend to change
12
// the value.
13
const message = ref("Hello World!");
14
</script>
15
16
<template>
17
    <h1>{{ message }}</h1>
18
</template>
(-)a/koha-tmpl/intranet-tmpl/prog/js/vue/modules/islands.ts (-9 / +38 lines)
Lines 16-31 export const componentRegistry: Map<string, () => Promise<Component>> = new Map( Link Here
16
                return module.default;
16
                return module.default;
17
            },
17
            },
18
        ],
18
        ],
19
        [
20
            "hello-world",
21
            async () => {
22
                const module = await import(
23
                    /* webpackChunkName: "hello-world" */ "../components/HelloWorld.vue"
24
                );
25
                return module.default;
26
            },
27
        ],
19
    ]
28
    ]
20
);
29
);
21
30
22
// Register and define custom elements
31
/**
23
window.requestIdleCallback(async () => {
32
 * Hydrates custom elements by scanning the document and loading only necessary components.
24
    componentRegistry.forEach(async (importFn, name) => {
33
 * @returns {void}
25
        const component = await importFn();
34
 */
26
        customElements.define(
35
export function hydrate(): void {
27
            name,
36
    window.requestIdleCallback(async () => {
28
            defineCustomElement(component as any, { shadowRoot: false })
37
        const islandTagNames = Array.from(componentRegistry.keys()).join(", ");
38
        const requestedIslands = new Set(
39
            Array.from(document.querySelectorAll(islandTagNames)).map(element =>
40
                element.tagName.toLowerCase()
41
            )
29
        );
42
        );
43
44
        requestedIslands.forEach(async name => {
45
            const importFn = componentRegistry.get(name);
46
            if (!importFn) {
47
                return;
48
            }
49
50
            const component = await importFn();
51
            customElements.define(
52
                name,
53
                defineCustomElement(component as any, {
54
                    shadowRoot: false,
55
                })
56
            );
57
        });
30
    });
58
    });
31
});
59
}
60
61
hydrate();
32
- 

Return to bug 37911