mirror of
https://github.com/sveltejs/svelte.git
synced 2024-12-01 17:30:59 +01:00
support $$props and $$restProps for custom elements (#5608)
This commit is contained in:
parent
0ca36a16b5
commit
6fa3e91b5d
@ -2,6 +2,7 @@
|
||||
|
||||
## Unreleased
|
||||
|
||||
* Fix `$$props` and `$$restProps` when compiling to a custom element ([#5482](https://github.com/sveltejs/svelte/issues/5482))
|
||||
* Add `Element` and `Node` to known globals ([#5586](https://github.com/sveltejs/svelte/issues/5586))
|
||||
|
||||
## 3.29.4
|
||||
|
@ -474,7 +474,7 @@ export default function dom(
|
||||
|
||||
${css.code && b`this.shadowRoot.innerHTML = \`<style>${css.code.replace(/\\/g, '\\\\')}${options.dev ? `\n/*# sourceMappingURL=${css.map.toUrl()} */` : ''}</style>\`;`}
|
||||
|
||||
@init(this, { target: this.shadowRoot }, ${definition}, ${has_create_fragment ? 'create_fragment': 'null'}, ${not_equal}, ${prop_indexes}, ${dirty});
|
||||
@init(this, { target: this.shadowRoot, props: @attribute_to_object(this.attributes) }, ${definition}, ${has_create_fragment ? 'create_fragment': 'null'}, ${not_equal}, ${prop_indexes}, ${dirty});
|
||||
|
||||
${dev_props_check}
|
||||
|
||||
|
@ -360,3 +360,11 @@ export class HtmlTag {
|
||||
this.n.forEach(detach);
|
||||
}
|
||||
}
|
||||
|
||||
export function attribute_to_object(attributes) {
|
||||
const result = {};
|
||||
for (const attribute of attributes) {
|
||||
result[attribute.name] = attribute.value;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
@ -31,3 +31,24 @@ export function equal(a, b, message) {
|
||||
export function ok(condition, message) {
|
||||
if (!condition) throw new Error(message || `Expected ${condition} to be truthy`);
|
||||
}
|
||||
|
||||
export function htmlEqual(actual, expected, message) {
|
||||
return deepEqual(
|
||||
normalizeHtml(window, actual),
|
||||
normalizeHtml(window, expected),
|
||||
message
|
||||
);
|
||||
}
|
||||
|
||||
function normalizeHtml(window, html) {
|
||||
try {
|
||||
const node = window.document.createElement('div');
|
||||
node.innerHTML = html
|
||||
.replace(/<!--.*?-->/g, '')
|
||||
.replace(/>[\s\r\n]+</g, '><')
|
||||
.trim();
|
||||
return node.innerHTML.replace(/<\/?noscript\/?>/g, '');
|
||||
} catch (err) {
|
||||
throw new Error(`Failed to normalize HTML:\n${html}`);
|
||||
}
|
||||
}
|
||||
|
10
test/custom-elements/samples/$$props/main.svelte
Normal file
10
test/custom-elements/samples/$$props/main.svelte
Normal file
@ -0,0 +1,10 @@
|
||||
<svelte:options tag="custom-element"/>
|
||||
|
||||
<script>
|
||||
export let name;
|
||||
</script>
|
||||
|
||||
<p>name: {name}</p>
|
||||
<p>$$props: {JSON.stringify($$props)}</p>
|
||||
<p>$$restProps: {JSON.stringify($$restProps)}</p>
|
||||
|
13
test/custom-elements/samples/$$props/test.js
Normal file
13
test/custom-elements/samples/$$props/test.js
Normal file
@ -0,0 +1,13 @@
|
||||
import * as assert from 'assert';
|
||||
import './main.svelte';
|
||||
|
||||
export default function (target) {
|
||||
target.innerHTML = '<custom-element name="world" answer="42" test="svelte"></custom-element>';
|
||||
const el = target.querySelector('custom-element');
|
||||
|
||||
assert.htmlEqual(el.shadowRoot.innerHTML, `
|
||||
<p>name: world</p>
|
||||
<p>$$props: {"name":"world","answer":"42","test":"svelte"}</p>
|
||||
<p>$$restProps: {"answer":"42","test":"svelte"}</p>
|
||||
`);
|
||||
}
|
@ -1,6 +1,7 @@
|
||||
/* generated by Svelte vX.Y.Z */
|
||||
import {
|
||||
SvelteElement,
|
||||
attribute_to_object,
|
||||
detach,
|
||||
element,
|
||||
init,
|
||||
@ -34,7 +35,18 @@ class Component extends SvelteElement {
|
||||
constructor(options) {
|
||||
super();
|
||||
this.shadowRoot.innerHTML = `<style>div{animation:foo 1s}@keyframes foo{0%{opacity:0}100%{opacity:1}}</style>`;
|
||||
init(this, { target: this.shadowRoot }, null, create_fragment, safe_not_equal, {});
|
||||
|
||||
init(
|
||||
this,
|
||||
{
|
||||
target: this.shadowRoot,
|
||||
props: attribute_to_object(this.attributes)
|
||||
},
|
||||
null,
|
||||
create_fragment,
|
||||
safe_not_equal,
|
||||
{}
|
||||
);
|
||||
|
||||
if (options) {
|
||||
if (options.target) {
|
||||
|
Loading…
Reference in New Issue
Block a user