+ {valid1 === true}
+ {validPropWrongType1 === true}
+ {invalidProp1}
+
+ {valid2 === true}
+ {validPropWrongType2 === true}
+ {invalidProp2}
+
+
\ No newline at end of file
diff --git a/packages/svelte2tsx/src/htmlxtojsx/nodes/attribute.ts b/packages/svelte2tsx/src/htmlxtojsx/nodes/attribute.ts
index 8b954ccb5..c20995990 100644
--- a/packages/svelte2tsx/src/htmlxtojsx/nodes/attribute.ts
+++ b/packages/svelte2tsx/src/htmlxtojsx/nodes/attribute.ts
@@ -42,6 +42,11 @@ export function handleAttribute(
parent: BaseNode,
preserveCase: boolean
): void {
+ const shouldApplySlotCheck = parent.type === 'Slot' && attr.name !== 'name';
+ const slotName = shouldApplySlotCheck
+ ? parent.attributes?.find((a: BaseNode) => a.name === 'name')?.value[0]?.data || 'default'
+ : undefined;
+ const ensureSlotStr = `__sveltets_ensureSlot("${slotName}","${attr.name}",`;
let transformedFromDirectiveOrNamespace = false;
const transformAttributeCase = (name: string) => {
@@ -118,6 +123,10 @@ export function handleAttribute(
}
str.appendRight(attr.start, `${attrName}=`);
+ if (shouldApplySlotCheck) {
+ str.prependRight(attr.start + 1, ensureSlotStr);
+ str.prependLeft(attr.end - 1, ')');
+ }
return;
}
@@ -145,33 +154,51 @@ export function handleAttribute(
!isNaN(attrVal.data);
if (needsNumberConversion) {
+ const begin = '{' + (shouldApplySlotCheck ? ensureSlotStr : '');
+ const end = shouldApplySlotCheck ? ')}' : '}';
if (needsQuotes) {
- str.prependRight(equals + 1, '{');
- str.appendLeft(attr.end, '}');
+ str.prependRight(equals + 1, begin);
+ str.appendLeft(attr.end, end);
} else {
- str.overwrite(equals + 1, equals + 2, '{');
- str.overwrite(attr.end - 1, attr.end, '}');
+ str.overwrite(equals + 1, equals + 2, begin);
+ str.overwrite(attr.end - 1, attr.end, end);
}
} else if (needsQuotes) {
- str.prependRight(equals + 1, '"');
- str.appendLeft(attr.end, '"');
+ const begin = shouldApplySlotCheck ? `{${ensureSlotStr}"` : '"';
+ const end = shouldApplySlotCheck ? '")}' : '"';
+ str.prependRight(equals + 1, begin);
+ str.appendLeft(attr.end, end);
+ } else if (shouldApplySlotCheck) {
+ str.prependRight(equals + 1, `{${ensureSlotStr}`);
+ str.appendLeft(attr.end, ')}');
}
return;
}
if (attrVal.type == 'MustacheTag') {
+ const isInQuotes = attrVal.end != attr.end;
//if the end doesn't line up, we are wrapped in quotes
- if (attrVal.end != attr.end) {
+ if (isInQuotes) {
str.remove(attrVal.start - 1, attrVal.start);
str.remove(attr.end - 1, attr.end);
}
+ if (shouldApplySlotCheck) {
+ str.prependRight(attrVal.start + 1, ensureSlotStr);
+ str.appendLeft(attr.end - (isInQuotes ? 2 : 1), ')');
+ }
return;
}
return;
}
// We have multiple attribute values, so we build a template string out of them.
- buildTemplateString(attr, str, htmlx, '={`', '`}');
+ buildTemplateString(
+ attr,
+ str,
+ htmlx,
+ shouldApplySlotCheck ? `={${ensureSlotStr}\`` : '={`',
+ shouldApplySlotCheck ? '`)}' : '`}'
+ );
}
function buildTemplateString(
diff --git a/packages/svelte2tsx/src/htmlxtojsx/nodes/slot.ts b/packages/svelte2tsx/src/htmlxtojsx/nodes/slot.ts
index 5a4a701a5..1be21930d 100644
--- a/packages/svelte2tsx/src/htmlxtojsx/nodes/slot.ts
+++ b/packages/svelte2tsx/src/htmlxtojsx/nodes/slot.ts
@@ -17,6 +17,9 @@ interface ComponentNode extends BaseNode {
[shadowedPropsSymbol]?: PropsShadowedByLet[];
}
+/**
+ * Transforms the usage of a slot (let:xx)
+ */
export function handleSlot(
htmlx: string,
str: MagicString,
diff --git a/packages/svelte2tsx/src/svelte2tsx/createRenderFunction.ts b/packages/svelte2tsx/src/svelte2tsx/createRenderFunction.ts
new file mode 100644
index 000000000..c07ca7d89
--- /dev/null
+++ b/packages/svelte2tsx/src/svelte2tsx/createRenderFunction.ts
@@ -0,0 +1,112 @@
+import MagicString from 'magic-string';
+import { Node } from 'estree-walker';
+import { ComponentEvents } from './nodes/ComponentEvents';
+import { createRenderFunctionGetterStr } from './nodes/exportgetters';
+import { InstanceScriptProcessResult } from './processInstanceScriptContent';
+import { surroundWithIgnoreComments } from '../utils/ignore';
+
+export interface CreateRenderFunctionPara extends InstanceScriptProcessResult {
+ str: MagicString;
+ scriptTag: Node;
+ scriptDestination: number;
+ slots: Map