export function createImetaVariants(variants, utils) { const { createListEmpty, createPlaceholder, createLinkMarkup } = utils; if (!Array.isArray(variants) || variants.length === 0) { return createListEmpty("No media variants provided."); } const ol = document.createElement("ol"); ol.className = "space-y-3"; variants.forEach((variant, index) => { if (!variant) return; const li = document.createElement("li"); li.className = "rounded-md border border-overlay bg-overlay-muted p-3 space-y-3"; // Header const headerDiv = document.createElement("div"); headerDiv.className = "flex flex-wrap items-center justify-between gap-2 text-xs text-muted"; const variantLabel = document.createElement("span"); variantLabel.className = "font-semibold text-primary"; variantLabel.textContent = `Variant ${index + 1}`; headerDiv.appendChild(variantLabel); if (variant.autoGenerated) { const badgesDiv = document.createElement("div"); badgesDiv.className = "flex flex-wrap gap-2"; const badge = document.createElement("span"); badge.className = "badge"; badge.dataset.variant = "warning"; badge.textContent = "Auto-generated"; badgesDiv.appendChild(badge); headerDiv.appendChild(badgesDiv); } li.appendChild(headerDiv); // DL Grid const dl = document.createElement("dl"); dl.className = "grid gap-3 sm:grid-cols-2 text-xs text-subtle"; const createDtDd = (label, contentNode, colSpan = false) => { const div = document.createElement("div"); if (colSpan) div.className = "sm:col-span-2"; const dt = document.createElement("dt"); dt.className = "font-semibold text-primary"; dt.textContent = label; div.appendChild(dt); const dd = document.createElement("dd"); dd.className = "mt-1"; dd.appendChild(contentNode); div.appendChild(dd); return div; }; // Mime const mimeNode = variant.m ? (() => { const c = document.createElement("code"); c.className = "rounded bg-overlay-panel-soft px-1.5 py-0.5 text-primary"; c.textContent = variant.m; return c; })() : createPlaceholder(); dl.appendChild(createDtDd("MIME type", mimeNode)); // Dim const dimNode = variant.dim ? (() => { const c = document.createElement("code"); c.className = "rounded bg-overlay-panel-soft px-1.5 py-0.5 text-primary"; c.textContent = variant.dim; return c; })() : createPlaceholder(); dl.appendChild(createDtDd("Dimensions", dimNode)); // URL const urlNode = variant.url ? createLinkMarkup(variant.url) : createPlaceholder("No URL"); dl.appendChild(createDtDd("URL", urlNode, true)); // Hash const hashNode = variant.x ? (() => { const c = document.createElement("code"); c.className = "break-all rounded bg-overlay-panel-soft px-1.5 py-0.5 text-primary"; c.textContent = variant.x; return c; })() : createPlaceholder("Not provided"); dl.appendChild(createDtDd("Content hash", hashNode, true)); li.appendChild(dl); // Nested lists const nestedGrid = document.createElement("div"); nestedGrid.className = "grid gap-3 sm:grid-cols-3 text-xs text-subtle"; const createNestedList = (label, values, emptyLabel) => { const container = document.createElement("div"); const p = document.createElement("p"); p.className = "text-2xs uppercase tracking-wide text-subtle"; p.textContent = label; container.appendChild(p); if (!Array.isArray(values) || values.length === 0) { container.appendChild(createListEmpty(emptyLabel)); return container; } const validItems = values .map(v => createLinkMarkup(v)) .filter(node => node.textContent !== ""); if (validItems.length === 0) { container.appendChild(createListEmpty(emptyLabel)); return container; } const ul = document.createElement("ul"); ul.className = "mt-1 space-y-1 text-xs text-primary"; validItems.forEach(itemNode => { const itemLi = document.createElement("li"); itemLi.appendChild(itemNode); ul.appendChild(itemLi); }); container.appendChild(ul); return container; }; nestedGrid.appendChild(createNestedList("Images", variant.image, "No image URLs.")); nestedGrid.appendChild(createNestedList("Fallbacks", variant.fallback, "No fallback URLs.")); nestedGrid.appendChild(createNestedList("Services", variant.service, "No service hints.")); li.appendChild(nestedGrid); ol.appendChild(li); }); return ol; } export function createTextTracks(tracks, utils) { const { createListEmpty, createPlaceholder, createLinkMarkup } = utils; if (!Array.isArray(tracks) || tracks.length === 0) { return createListEmpty("No caption tracks."); } const ol = document.createElement("ol"); ol.className = "space-y-3"; tracks.forEach((track, index) => { const li = document.createElement("li"); li.className = "rounded-md border border-overlay bg-overlay-muted p-3 space-y-3"; const headerDiv = document.createElement("div"); headerDiv.className = "flex items-center justify-between text-xs text-muted"; const label = document.createElement("span"); label.className = "font-semibold text-primary"; label.textContent = `Track ${index + 1}`; headerDiv.appendChild(label); if (track.language) { const langSpan = document.createElement("span"); langSpan.className = "pill"; langSpan.dataset.size = "compact"; langSpan.dataset.variant = "neutral"; langSpan.textContent = track.language; headerDiv.appendChild(langSpan); } li.appendChild(headerDiv); const dl = document.createElement("dl"); dl.className = "grid gap-3 sm:grid-cols-2 text-xs text-subtle"; const createDtDd = (label, contentNode, colSpan = false) => { const div = document.createElement("div"); if (colSpan) div.className = "sm:col-span-2"; const dt = document.createElement("dt"); dt.className = "font-semibold text-primary"; dt.textContent = label; div.appendChild(dt); const dd = document.createElement("dd"); dd.className = "mt-1"; dd.appendChild(contentNode); div.appendChild(dd); return div; }; const urlNode = track.url ? createLinkMarkup(track.url) : createPlaceholder("No URL"); dl.appendChild(createDtDd("URL", urlNode, true)); const typeNode = track.type ? (() => { const c = document.createElement("code"); c.className = "rounded bg-overlay-panel-soft px-1.5 py-0.5 text-primary"; c.textContent = track.type; return c; })() : createPlaceholder(); dl.appendChild(createDtDd("Type", typeNode)); const langNode = track.language ? (() => { const s = document.createElement("span"); s.className = "pill"; s.dataset.size = "compact"; s.dataset.variant = "neutral"; s.textContent = track.language; return s; })() : createPlaceholder(); dl.appendChild(createDtDd("Language", langNode)); li.appendChild(dl); ol.appendChild(li); }); return ol; } export function createSegments(segments, utils) { const { createListEmpty, createPlaceholder, createLinkMarkup, formatDurationSeconds } = utils; if (!Array.isArray(segments) || segments.length === 0) { return createListEmpty("No chapter segments."); } const ol = document.createElement("ol"); ol.className = "space-y-3"; const createTimeNode = (seconds, raw) => { if (Number.isFinite(seconds)) { const display = formatDurationSeconds(seconds); const suffix = seconds === 1 ? "second" : "seconds"; const frag = document.createDocumentFragment(); const span1 = document.createElement("span"); span1.className = "text-primary"; span1.textContent = display; frag.appendChild(span1); const space = document.createTextNode(" "); frag.appendChild(space); const span2 = document.createElement("span"); span2.className = "text-subtle"; span2.textContent = `(${seconds} ${suffix})`; frag.appendChild(span2); return frag; } if (raw) { const span = document.createElement("span"); span.className = "text-primary"; span.textContent = raw; return span; } return createPlaceholder(); }; segments.forEach((segment, index) => { const li = document.createElement("li"); li.className = "rounded-md border border-overlay bg-overlay-muted p-3 space-y-3"; const headerDiv = document.createElement("div"); headerDiv.className = "text-xs font-semibold text-primary"; headerDiv.textContent = `Chapter ${index + 1}`; li.appendChild(headerDiv); const dl = document.createElement("dl"); dl.className = "grid gap-3 sm:grid-cols-2 text-xs text-subtle"; const createDtDd = (label, contentNode, colSpan = false) => { const div = document.createElement("div"); if (colSpan) div.className = "sm:col-span-2"; const dt = document.createElement("dt"); dt.className = "font-semibold text-primary"; dt.textContent = label; div.appendChild(dt); const dd = document.createElement("dd"); dd.className = "mt-1"; dd.appendChild(contentNode); div.appendChild(dd); return div; }; dl.appendChild(createDtDd("Start", createTimeNode(segment.startSeconds, segment.startRaw))); dl.appendChild(createDtDd("End", createTimeNode(segment.endSeconds, segment.endRaw))); const titleNode = segment.title ? (() => { const p = document.createElement("p"); p.className = "whitespace-pre-wrap text-primary"; p.textContent = segment.title; return p; })() : createPlaceholder("No title"); dl.appendChild(createDtDd("Title", titleNode, true)); const thumbNode = segment.thumbnail ? createLinkMarkup(segment.thumbnail) : createPlaceholder("No thumbnail"); dl.appendChild(createDtDd("Thumbnail", thumbNode, true)); li.appendChild(dl); ol.appendChild(li); }); return ol; } export function createHashtags(hashtags, utils) { const { createListEmpty } = utils; if (!Array.isArray(hashtags) || hashtags.length === 0) { return createListEmpty("No hashtags provided."); } const div = document.createElement("div"); div.className = "flex flex-wrap gap-2"; hashtags.forEach(tag => { const label = tag.startsWith("#") ? tag : `#${tag}`; const span = document.createElement("span"); span.className = "pill"; span.dataset.size = "compact"; span.dataset.variant = "neutral"; span.textContent = label; div.appendChild(span); }); return div; } export function createParticipants(participants, utils) { const { createListEmpty, createPlaceholder, createLinkMarkup, truncateMiddle } = utils; if (!Array.isArray(participants) || participants.length === 0) { return createListEmpty("No participants listed."); } const ol = document.createElement("ol"); ol.className = "space-y-3"; participants.forEach((participant, index) => { const li = document.createElement("li"); li.className = "rounded-md border border-overlay bg-overlay-muted p-3 space-y-2"; const headerDiv = document.createElement("div"); headerDiv.className = "text-xs font-semibold text-primary"; headerDiv.textContent = `Participant ${index + 1}`; li.appendChild(headerDiv); const dl = document.createElement("dl"); dl.className = "grid gap-3 sm:grid-cols-2 text-xs text-subtle"; const createDtDd = (label, contentNode, colSpan = false) => { const div = document.createElement("div"); if (colSpan) div.className = "sm:col-span-2"; const dt = document.createElement("dt"); dt.className = "font-semibold text-primary"; dt.textContent = label; div.appendChild(dt); const dd = document.createElement("dd"); dd.className = "mt-1"; dd.appendChild(contentNode); div.appendChild(dd); return div; }; const displayPubkey = participant.pubkey ? truncateMiddle ? truncateMiddle(participant.pubkey, 48) : participant.pubkey : ""; const pubkeyNode = participant.pubkey ? (() => { const c = document.createElement("code"); c.className = "break-all rounded bg-overlay-panel-soft px-1.5 py-0.5 text-primary"; c.title = participant.pubkey; c.textContent = displayPubkey; return c; })() : createPlaceholder("No pubkey"); dl.appendChild(createDtDd("Pubkey", pubkeyNode, true)); const relayNode = participant.relay ? createLinkMarkup(participant.relay, { breakAll: false }) : createPlaceholder("No relay specified"); dl.appendChild(createDtDd("Relay", relayNode, true)); li.appendChild(dl); ol.appendChild(li); }); return ol; } export function createReferences(references, utils) { const { createListEmpty, createLinkMarkup } = utils; if (!Array.isArray(references) || references.length === 0) { return createListEmpty("No external references."); } const items = references .map((entry) => createLinkMarkup(entry)) .filter(node => node.textContent !== ""); if (items.length === 0) { return createListEmpty("No external references."); } const ul = document.createElement("ul"); ul.className = "space-y-1 text-xs text-primary"; items.forEach(node => { const li = document.createElement("li"); li.appendChild(node); ul.appendChild(li); }); return ul; } /* Shared Helpers (internal to this module, or exported if needed elsewhere) */ function createDl() { const dl = document.createElement("dl"); dl.className = "grid gap-3 sm:grid-cols-2 text-xs text-subtle"; return dl; } function createDtDd(label, contentNode, colSpan = 1) { const div = document.createElement("div"); if (colSpan > 1) div.className = "sm:col-span-2"; const dt = document.createElement("dt"); dt.className = "font-semibold text-primary"; dt.textContent = label; div.appendChild(dt); const dd = document.createElement("dd"); dd.className = "mt-1"; dd.appendChild(contentNode); div.appendChild(dd); return div; } export function createSection(title) { const s = document.createElement("section"); s.className = "space-y-2"; const h = document.createElement("h4"); h.className = "text-sm font-semibold text-primary"; h.textContent = title; s.appendChild(h); return s; } function createTimestampNode(seconds, raw, utils) { const { formatAbsoluteTimestamp, formatTimeAgo, createPlaceholder } = utils; if (Number.isFinite(seconds)) { const abs = formatAbsoluteTimestamp ? formatAbsoluteTimestamp(seconds) : `${seconds}`; const rel = formatTimeAgo ? formatTimeAgo(seconds) : ""; const frag = document.createDocumentFragment(); if (abs) { const s = document.createElement("span"); s.className = "text-primary"; s.textContent = abs; frag.appendChild(s); frag.appendChild(document.createTextNode(" ")); } if (rel) { const s = document.createElement("span"); s.className = "text-muted"; s.textContent = `(${rel})`; frag.appendChild(s); } return frag; } if (raw) { const s = document.createElement("span"); s.className = "text-primary"; s.textContent = raw; return s; } return createPlaceholder(); } function createDurationNode(seconds, raw, utils) { const { formatDurationSeconds, createPlaceholder } = utils; if (Number.isFinite(seconds)) { const display = formatDurationSeconds ? formatDurationSeconds(seconds) : `${seconds}`; const suffix = seconds === 1 ? "second" : "seconds"; const frag = document.createDocumentFragment(); const s1 = document.createElement("span"); s1.className = "text-primary"; s1.textContent = display; frag.appendChild(s1); frag.appendChild(document.createTextNode(" ")); const s2 = document.createElement("span"); s2.className = "text-subtle"; s2.textContent = `(${seconds} ${suffix})`; frag.appendChild(s2); return frag; } if (raw) { const s = document.createElement("span"); s.className = "text-primary"; s.textContent = raw; return s; } return createPlaceholder(); } function createFlagStatus(value, { yes, no, unspecified }, utils) { const { createPlaceholder } = utils; if (value === true) { const s = document.createElement("span"); s.className = "text-primary"; s.textContent = yes; return s; } if (value === false) { const s = document.createElement("span"); s.className = "text-primary"; s.textContent = no; return s; } return createPlaceholder(unspecified); } /* New Exported Renderers */ export function createHeader(version, nip71Metadata, utils) { const { formatAbsoluteTimestamp, formatTimeAgo, truncateMiddle, createPlaceholder, createLinkMarkup, fallbackThumbnailSrc, } = utils; const wrapper = document.createElement("div"); wrapper.className = "space-y-6"; const createdAt = typeof version.created_at === "number" ? version.created_at : 0; const absolute = formatAbsoluteTimestamp ? formatAbsoluteTimestamp(createdAt) : ""; const relative = formatTimeAgo ? formatTimeAgo(createdAt) : ""; const timestampText = [absolute, relative ? `(${relative})` : ""].filter(Boolean).join(" "); const thumbnail = typeof version.thumbnail === "string" ? version.thumbnail.trim() : ""; const thumbnailSrc = thumbnail || fallbackThumbnailSrc; const thumbnailAlt = thumbnail ? "Revision thumbnail" : "Fallback thumbnail"; const url = typeof version.url === "string" ? version.url.trim() : ""; const urlNode = url ? createLinkMarkup(url) : createPlaceholder("None"); const magnet = typeof version.magnet === "string" ? version.magnet.trim() : ""; const rawMagnet = typeof version.rawMagnet === "string" ? version.rawMagnet.trim() : ""; const displayMagnet = magnet || rawMagnet; const isPrivate = version.isPrivate === true; const magnetNode = displayMagnet ? (() => { const div = document.createElement("div"); div.className = "break-all"; const label = truncateMiddle ? truncateMiddle(displayMagnet, 72) : displayMagnet; div.textContent = label; if (isPrivate) { const span = document.createElement("span"); span.className = "block mt-1 text-xs text-status-private-on"; span.textContent = "Magnet stays visible only to you — private notes keep the raw string local."; div.appendChild(span); } return div; })() : createPlaceholder("None"); // Chips const chipsDiv = document.createElement("div"); chipsDiv.className = "flex flex-wrap gap-2"; const nsfwFlag = version.isNsfw === true; const forKidsFlag = version.isForKids === true; const conflictingAudienceFlags = nsfwFlag && forKidsFlag; if (version.deleted) { const s = document.createElement("span"); s.className = "pill"; s.dataset.size = "compact"; s.dataset.variant = "critical"; s.textContent = "Marked deleted"; chipsDiv.appendChild(s); } if (isPrivate) { const s = document.createElement("span"); s.className = "pill"; s.dataset.size = "compact"; s.dataset.variant = "private"; s.textContent = "Private"; chipsDiv.appendChild(s); } if (conflictingAudienceFlags) { const s = document.createElement("span"); s.className = "pill"; s.dataset.size = "compact"; s.dataset.variant = "warning"; s.textContent = "NSFW + For kids conflict"; chipsDiv.appendChild(s); } else { if (nsfwFlag) { const s = document.createElement("span"); s.className = "pill"; s.dataset.size = "compact"; s.dataset.variant = "critical"; s.textContent = "Marked NSFW"; chipsDiv.appendChild(s); } if (forKidsFlag) { const s = document.createElement("span"); s.className = "pill"; s.dataset.size = "compact"; s.dataset.variant = "success"; s.textContent = "For kids"; chipsDiv.appendChild(s); } } if (version.version !== undefined) { const s = document.createElement("span"); s.className = "pill"; s.dataset.size = "compact"; s.dataset.variant = "neutral"; s.textContent = `Schema v${version.version}`; chipsDiv.appendChild(s); } // DOM construction const headerRow = document.createElement("div"); headerRow.className = "flex flex-col gap-4 lg:flex-row lg:items-start"; const imgDiv = document.createElement("div"); imgDiv.className = "overflow-hidden rounded-md border border-overlay bg-overlay-strong w-full max-w-sm"; const img = document.createElement("img"); img.src = thumbnailSrc; img.alt = thumbnailAlt; img.className = "w-full h-auto object-cover"; img.loading = "lazy"; imgDiv.appendChild(img); headerRow.appendChild(imgDiv); const headerContent = document.createElement("div"); headerContent.className = "flex-1 space-y-3"; const titleTimeDiv = document.createElement("div"); titleTimeDiv.className = "space-y-1"; const titleH3 = document.createElement("h3"); titleH3.className = "text-lg font-semibold text-primary"; titleH3.textContent = version.title || "Untitled"; titleTimeDiv.appendChild(titleH3); const timeP = document.createElement("p"); timeP.className = "text-xs text-muted"; timeP.textContent = timestampText; titleTimeDiv.appendChild(timeP); headerContent.appendChild(titleTimeDiv); if (chipsDiv.hasChildNodes()) { headerContent.appendChild(chipsDiv); } const headerDl = createDl(); headerDl.appendChild(createDtDd("Hosted URL", urlNode)); headerDl.appendChild(createDtDd("Magnet", magnetNode)); headerContent.appendChild(headerDl); headerRow.appendChild(headerContent); wrapper.appendChild(headerRow); return wrapper; } export function createDescription(description, utils) { const descSection = createSection("Description"); const descriptionNode = description ? (() => { const p = document.createElement("p"); p.className = "whitespace-pre-wrap text-primary"; p.textContent = description; return p; })() : (() => { const p = document.createElement("p"); p.className = "text-subtle"; p.textContent = "No description provided."; return p; })(); descSection.appendChild(descriptionNode); return descSection; } export function createAudienceFlags(version, utils) { const audSection = createSection("Audience flags"); const audDl = createDl(); const nsfwStatusNode = createFlagStatus(version.isNsfw, { yes: "Yes — marked NSFW", no: "No — not flagged as NSFW", unspecified: "Not specified", }, utils); const kidsStatusNode = createFlagStatus(version.isForKids, { yes: "Yes — marked for kids", no: "No — not marked for kids", unspecified: "Not specified", }, utils); audDl.appendChild(createDtDd("NSFW flag", nsfwStatusNode)); audDl.appendChild(createDtDd("For kids flag", kidsStatusNode)); audSection.appendChild(audDl); if (version.isNsfw === true && version.isForKids === true) { const p = document.createElement("p"); p.className = "text-xs text-status-warning-on"; p.textContent = "Conflicting flags detected — this revision is marked both NSFW and for kids. Review before reverting."; audSection.appendChild(p); } return audSection; } export function createEventMetadata(nip71Metadata, utils) { const { createPlaceholder } = utils; const eventSection = createSection("NIP-71 event metadata"); const eventDl = createDl(); const kindValue = nip71Metadata.kind; const kindNode = (() => { if (kindValue !== "" && kindValue !== null && kindValue !== undefined) { const label = typeof kindValue === "number" ? kindValue : `${kindValue}`; const numeric = Number(label); let suffix = ""; if (Number.isFinite(numeric)) { if (numeric === 22) suffix = "short"; else if (numeric === 21) suffix = "video"; } const frag = document.createDocumentFragment(); const code = document.createElement("code"); code.className = "rounded bg-overlay-panel-soft px-1.5 py-0.5 text-primary"; code.textContent = `kind ${label}`; frag.appendChild(code); if (suffix) { frag.appendChild(document.createTextNode(" ")); const s = document.createElement("span"); s.className = "text-muted"; s.textContent = `(${suffix})`; frag.appendChild(s); } return frag; } return createPlaceholder(); })(); eventDl.appendChild(createDtDd("NIP-71 kind", kindNode)); const summaryNode = nip71Metadata.summary ? (() => { const p = document.createElement("p"); p.className = "whitespace-pre-wrap text-primary"; p.textContent = nip71Metadata.summary; return p; })() : createPlaceholder("Not provided"); eventDl.appendChild(createDtDd("Summary", summaryNode, 2)); const contentWarningNode = nip71Metadata.contentWarning ? (() => { const s = document.createElement("span"); s.className = "pill"; s.dataset.size = "compact"; s.dataset.variant = "warning"; s.textContent = nip71Metadata.contentWarning; return s; })() : createPlaceholder("Not provided"); eventDl.appendChild(createDtDd("Content warning", contentWarningNode, 2)); const publishedAtNode = createTimestampNode( nip71Metadata.publishedAtSeconds, nip71Metadata.publishedAtRaw, utils ); eventDl.appendChild(createDtDd("Published timestamp", publishedAtNode)); const durationNode = createDurationNode( nip71Metadata.durationSeconds, nip71Metadata.durationRaw, utils ); eventDl.appendChild(createDtDd("Duration", durationNode)); const altNode = nip71Metadata.alt ? (() => { const p = document.createElement("p"); p.className = "whitespace-pre-wrap text-primary"; p.textContent = nip71Metadata.alt; return p; })() : createPlaceholder("Not provided"); eventDl.appendChild(createDtDd("Alt text", altNode, 2)); eventSection.appendChild(eventDl); return eventSection; } export function createNotePointers(version, dTagValue, utils) { const { createPlaceholder, truncateMiddle } = utils; const ptrSection = createSection("Note pointers"); const ptrDl = createDl(); ptrDl.appendChild(createDtDd("Mode", document.createTextNode(version.mode || "live"))); const dTagNode = dTagValue ? (() => { const c = document.createElement("code"); c.className = "rounded bg-overlay-panel-soft px-1.5 py-0.5 text-primary"; c.textContent = dTagValue; return c; })() : createPlaceholder("Not provided"); ptrDl.appendChild(createDtDd("d tag", dTagNode)); const rootId = typeof version.videoRootId === "string" ? version.videoRootId : ""; const rootDisplay = rootId ? truncateMiddle ? truncateMiddle(rootId, 64) : rootId : ""; const rootIdNode = rootDisplay ? (() => { const c = document.createElement("code"); c.className = "break-all rounded bg-overlay-panel-soft px-1.5 py-0.5 text-primary"; c.title = rootId; c.textContent = rootDisplay; return c; })() : createPlaceholder("Not provided"); ptrDl.appendChild(createDtDd("videoRootId", rootIdNode)); const eventDisplay = version.id ? truncateMiddle ? truncateMiddle(version.id, 64) : version.id : ""; const eventIdNode = eventDisplay ? (() => { const c = document.createElement("code"); c.className = "break-all rounded bg-overlay-panel-soft px-1.5 py-0.5 text-primary"; c.title = version.id || ""; c.textContent = eventDisplay; return c; })() : (() => { const s = document.createElement("span"); s.className = "text-subtle"; s.textContent = "Unknown"; return s; })(); ptrDl.appendChild(createDtDd("Event ID", eventIdNode)); ptrSection.appendChild(ptrDl); return ptrSection; }