Mirror of static site repo git.pfy.ch/pfych/static
Something went wrong. Try again.
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596export type Attributes<T extends keyof HTMLElementTagNameMap> = Omit< Partial<HTMLElementTagNameMap[T]>, 'style'> & { style?: string;};
export const jsxAsString = <T extends keyof HTMLElementTagNameMap>( tag: T, props: Attributes<T> | null, ...children: (string | HTMLElement)[]): string => { const attributes = props ? Object.entries(props) .map(([key, value]) => { if (value === true) return key; if (value === false || value === null || value === undefined) return ''; // Convert camelCase to kebab-case for attributes const attrName = key.replace(/([A-Z])/g, '-$1').toLowerCase(); return `${attrName}="${String(value).replace(/"/g, '"')}"`; }) .filter(Boolean) .join(' ') : '';
const attributesString = attributes ? ` ${attributes}` : ''; const childrenString = children.join('');
// Self-closing tags const selfClosing = [ 'area', 'base', 'br', 'col', 'embed', 'hr', 'img', 'input', 'link', 'meta', 'param', 'source', 'track', 'wbr', ]; if (selfClosing.includes(tag)) { return `<${tag}${attributesString} />`; }
return `<${tag}${attributesString}>${childrenString}</${tag}>`;};
export const jsxAsElement = <T extends keyof HTMLElementTagNameMap>( tag: T, props: Attributes<T> | null, ...children: (string | HTMLElement)[]) => { const element = document.createElement(tag);
Object.entries(props || {}).forEach(([key, value]) => { const castKey = key as keyof HTMLElementTagNameMap[T];
if (typeof castKey === 'string' && castKey.includes('data-')) { element.dataset[castKey.replace('data-', '')] = value as string; } else if ( typeof castKey === 'string' && ![ 'className', 'style', 'onload', 'onerror', 'onclick', 'onchange', ].includes(castKey) ) { // Use setAttributeNS for custom elements to preserve unknown attributes (and maintain casing) element.setAttributeNS(null, key, value as string); } else { // Since we're replacing the style attribute this complains heaps // @ts-ignore element[castKey] = value; } });
if (Array.isArray(children)) { children.forEach((child) => { element.append(child); }); } else { element.append(children); }
return element;};