1 | 'use strict';
|
2 |
|
3 | Object.defineProperty(exports, '__esModule', { value: true });
|
4 |
|
5 | var update = require('./update.js');
|
6 | var helpers = require('./helpers.js');
|
7 | var render = require('./render.js');
|
8 | var mergeSlots = require('./mergeSlots.js');
|
9 |
|
10 | function getDataScript(node) {
|
11 | return node.querySelector(`script[type="application/mosaic"]`)
|
12 | }
|
13 |
|
14 | function createDataScript(node) {
|
15 | let ds = document.createElement("script");
|
16 | ds.setAttribute("type", "application/mosaic");
|
17 | node.append(ds);
|
18 | return ds
|
19 | }
|
20 |
|
21 | function serialise(node, state) {
|
22 | let ds = getDataScript(node) || createDataScript(node);
|
23 |
|
24 | ds.innerText = JSON.stringify(state);
|
25 | }
|
26 |
|
27 | function deserialise(node) {
|
28 | return JSON.parse(getDataScript(node)?.innerText || "{}")
|
29 | }
|
30 |
|
31 | const define = (name, factory, template) =>
|
32 | customElements.define(
|
33 | name,
|
34 | class extends HTMLElement {
|
35 | async connectedCallback() {
|
36 | if (!this.initialised) {
|
37 | let config = factory(this);
|
38 |
|
39 | if (config instanceof Promise) config = await config;
|
40 |
|
41 | let {
|
42 | update: update$1,
|
43 | middleware,
|
44 | derivations,
|
45 | subscribe,
|
46 | shadow,
|
47 | initialState = {},
|
48 | } = config;
|
49 |
|
50 | this.connectedCallback = config.connectedCallback;
|
51 | this.disconnectedCallback = config.disconnectedCallback;
|
52 |
|
53 | const { dispatch, getState, onUpdate, flush } = update.configure(
|
54 | config,
|
55 | this
|
56 | );
|
57 |
|
58 | dispatch({
|
59 | type: "MERGE",
|
60 | payload: deserialise(this),
|
61 | });
|
62 |
|
63 | initialState = getState();
|
64 |
|
65 | let observedProps = Object.keys(initialState).filter(
|
66 | (v) => v.charAt(0) === "$"
|
67 | );
|
68 |
|
69 | let observedAttributes = observedProps
|
70 | .map((v) => v.slice(1))
|
71 | .map(helpers.pascalToKebab);
|
72 |
|
73 | let sa = this.setAttribute;
|
74 | this.setAttribute = (k, v) => {
|
75 | if (observedAttributes.includes(k)) {
|
76 | let { name, value } = helpers.attributeToProp(k, v);
|
77 | dispatch({
|
78 | type: "SET",
|
79 | payload: { name: "$" + name, value },
|
80 | });
|
81 | }
|
82 | sa.apply(this, [k, v]);
|
83 | };
|
84 |
|
85 | observedAttributes.forEach((name) => {
|
86 | let property = helpers.attributeToProp(name).name;
|
87 |
|
88 | let value;
|
89 |
|
90 | if (this.hasAttribute(name)) {
|
91 | value = this.getAttribute(name);
|
92 | } else {
|
93 | value = this[property] || initialState["$" + property];
|
94 | }
|
95 |
|
96 | Object.defineProperty(this, property, {
|
97 | get() {
|
98 | return getState()["$" + property]
|
99 | },
|
100 | set(v) {
|
101 | dispatch({
|
102 | type: "SET",
|
103 | payload: { name: "$" + property, value: v },
|
104 | });
|
105 | if (helpers.isPrimitive(v)) {
|
106 | helpers.applyAttribute(this, property, v);
|
107 | }
|
108 | },
|
109 | });
|
110 |
|
111 | this[property] = value;
|
112 | });
|
113 |
|
114 | let beforeMountCallback;
|
115 |
|
116 | if (shadow) {
|
117 | this.attachShadow({
|
118 | mode: shadow,
|
119 | });
|
120 | } else {
|
121 | beforeMountCallback = (frag) => mergeSlots.mergeSlots(this, frag);
|
122 | }
|
123 |
|
124 | onUpdate(
|
125 | render.render(
|
126 | this.shadowRoot || this,
|
127 | { getState, dispatch },
|
128 | template,
|
129 | () => {
|
130 | serialise(this, getState());
|
131 |
|
132 | observedProps.forEach((k) => {
|
133 | let v = getState()[k];
|
134 | if (helpers.isPrimitive(v)) helpers.applyAttribute(this, k.slice(1), v);
|
135 | });
|
136 | subscribe?.(getState());
|
137 | flush();
|
138 | },
|
139 | beforeMountCallback
|
140 | )
|
141 | );
|
142 | this.initialised = true;
|
143 | }
|
144 | this.connectedCallback?.();
|
145 | }
|
146 | disconnectedCallback() {
|
147 | this.disconnectedCallback?.();
|
148 | }
|
149 | }
|
150 | );
|
151 |
|
152 | exports.define = define;
|