Enhance component functionality and styling across the project
Deploy to Firebase Hosting / deploy (push) Failing after 1m46s
Deploy to Firebase Hosting / deploy (push) Failing after 1m46s
- Updated .gitignore to include raw image files for better asset management. - Added optional icon and color properties to Tag and TagItem interfaces for improved tag customization. - Enhanced BlogOverview and PostCard components to support new tag features, including icon and color display. - Refined Card component to accept target and rel attributes for better link handling. - Improved layout responsiveness in ContentRows and PostCard components. - Updated OrganisationsBlock to include a new CTA link feature for adding organizations. - Enhanced QuoteBlock styling for better visual emphasis on quotes. - Refactored image handling in various components to ensure consistent display and performance. - Introduced utility functions for resolving body content and filtering hidden posts in blog utilities.
This commit is contained in:
@@ -13,25 +13,41 @@
|
||||
: "https://opnform.pm86.de"
|
||||
).replace(/\/$/, ""),
|
||||
);
|
||||
const iframeSrc = $derived(
|
||||
formId ? `${baseUrl}/forms/${formId}` : "",
|
||||
);
|
||||
const iframeTitle = $derived(
|
||||
block.iframeTitle?.trim() || "Kontaktformular",
|
||||
);
|
||||
const iframeSrc = $derived(formId ? `${baseUrl}/forms/${formId}` : "");
|
||||
const iframeTitle = $derived(block.iframeTitle?.trim() || "Kontaktformular");
|
||||
|
||||
/**
|
||||
* Wie im OpnForm-Embed: initEmbed erst wenn iframe.min.js fertig geladen ist
|
||||
* (entspricht <script … onload="initEmbed('…', { autoResize: true })">).
|
||||
* Zusätzlich min-height, weil das Widget oft ~150px inline setzt, bevor autoResize greift.
|
||||
*/
|
||||
const iframeStyle =
|
||||
"border: none; width: 100%; min-height: min(88vh, 48rem) !important;";
|
||||
let iframeEl = $state<HTMLIFrameElement | null>(null);
|
||||
|
||||
onMount(() => {
|
||||
if (!formId) return;
|
||||
if (!formId || !iframeEl) return;
|
||||
|
||||
const el = iframeEl;
|
||||
// Höhe ausschließlich per DOM verwalten – nie über Sveltes style= Prop.
|
||||
el.style.height = "600px";
|
||||
el.style.transition = "height 0.25s ease";
|
||||
// Verhindert native Browser-Scrollbar im Iframe, egal ob Höhe stimmt oder nicht.
|
||||
el.setAttribute("scrolling", "no");
|
||||
|
||||
const scriptUrl = `${baseUrl}/widgets/iframe.min.js`;
|
||||
|
||||
function handleMessage(event: MessageEvent) {
|
||||
if (event.source !== el.contentWindow) return;
|
||||
const d = event.data;
|
||||
let h: number | undefined;
|
||||
if (typeof d === "number") {
|
||||
h = d;
|
||||
} else if (d && typeof d === "object") {
|
||||
h = d.height ?? d.frameHeight ?? d.iFrameHeight;
|
||||
} else if (typeof d === "string" && d.startsWith("[iFrameSizer]")) {
|
||||
const parts = d.split(":");
|
||||
h = parts.length >= 2 ? parseFloat(parts[1]) : undefined;
|
||||
}
|
||||
if (typeof h === "number" && h > 50) {
|
||||
el.style.height = `${Math.ceil(h)}px`;
|
||||
}
|
||||
}
|
||||
window.addEventListener("message", handleMessage);
|
||||
|
||||
function runInit() {
|
||||
const w = window as Window & {
|
||||
initEmbed?: (id: string, opts: { autoResize?: boolean }) => void;
|
||||
@@ -50,27 +66,31 @@
|
||||
} else {
|
||||
existing.addEventListener("load", runInit, { once: true });
|
||||
}
|
||||
return;
|
||||
} else {
|
||||
const s = document.createElement("script");
|
||||
s.type = "text/javascript";
|
||||
s.async = true;
|
||||
s.src = scriptUrl;
|
||||
s.dataset.opnformEmbedJs = baseUrl;
|
||||
s.onload = () => runInit();
|
||||
document.body.appendChild(s);
|
||||
}
|
||||
|
||||
const s = document.createElement("script");
|
||||
s.type = "text/javascript";
|
||||
s.async = true;
|
||||
s.src = scriptUrl;
|
||||
s.dataset.opnformEmbedJs = baseUrl;
|
||||
s.onload = () => runInit();
|
||||
document.body.appendChild(s);
|
||||
return () => {
|
||||
window.removeEventListener("message", handleMessage);
|
||||
};
|
||||
});
|
||||
</script>
|
||||
|
||||
<div
|
||||
class="{layoutClasses} content-opnform w-full min-w-0 overflow-visible -mx-6"
|
||||
class="{layoutClasses} content-opnform w-[calc(100%+2rem)] max-w-none -mx-4 min-w-0 overflow-visible border border-stein-200 lg:rounded-lg px-0 py-3 md:w-[calc(100%+3rem)] md:-mx-6 md:px-4 md:py-4"
|
||||
data-block-type="opnform"
|
||||
data-block-slug={block._slug}
|
||||
>
|
||||
{#if iframeSrc}
|
||||
<iframe
|
||||
style={iframeStyle}
|
||||
bind:this={iframeEl}
|
||||
style="border: none; width: 100%;"
|
||||
id={formId}
|
||||
title={iframeTitle}
|
||||
src={iframeSrc}
|
||||
|
||||
@@ -34,6 +34,30 @@
|
||||
? (marked.parse(block.addOrganisationMarkdown) as string)
|
||||
: ""
|
||||
);
|
||||
|
||||
const addOrganisationCtaLink = $derived.by(() => {
|
||||
const raw = block.addOrganisationLink;
|
||||
if (!raw || typeof raw !== "object") return undefined;
|
||||
const url = typeof raw.url === "string" ? raw.url.trim() : "";
|
||||
if (!url) return undefined;
|
||||
const linkName =
|
||||
typeof raw.linkName === "string" && raw.linkName.trim() !== ""
|
||||
? raw.linkName.trim()
|
||||
: url;
|
||||
return { url, linkName, newTab: Boolean(raw.newTab) };
|
||||
});
|
||||
|
||||
const showAddOrganisationCard = $derived(
|
||||
Boolean(
|
||||
block.addOrganisationTitle?.trim() ||
|
||||
block.addOrganisationMarkdown?.trim() ||
|
||||
addOrganisationCtaLink
|
||||
)
|
||||
);
|
||||
|
||||
const addOrganisationCardClass = $derived(
|
||||
`${compact ? "border-dashed border-wald-300 bg-wald-50! p-3! gap-1.5!" : "border-dashed border-wald-300 bg-wald-50!"}${addOrganisationCtaLink ? " cursor-pointer" : ""}`,
|
||||
);
|
||||
</script>
|
||||
|
||||
<div class={layoutClasses} data-block-type="organisations" data-block-slug={block._slug}>
|
||||
@@ -103,12 +127,7 @@
|
||||
{/if}
|
||||
</div>
|
||||
<div class="min-w-0 flex-1 flex flex-col gap-0.5">
|
||||
<div class="flex flex-wrap items-center gap-2">
|
||||
<h5 class="text-sm font-semibold text-stein-900 leading-snug">{o.name ?? ""}</h5>
|
||||
{#if o.badge && typeof o.badge === "object" && o.badge.label}
|
||||
<Badge color={o.badge.color}>{o.badge.label}</Badge>
|
||||
{/if}
|
||||
</div>
|
||||
<h5 class="text-sm font-semibold text-stein-900 leading-snug">{o.name ?? ""}</h5>
|
||||
{#if o.description}
|
||||
<p class="text-xs text-stein-600 line-clamp-2">{o.description}</p>
|
||||
{/if}
|
||||
@@ -165,7 +184,7 @@
|
||||
<Badge color={o.badge.color}>{o.badge.label}</Badge>
|
||||
</div>
|
||||
{/if}
|
||||
<h5 class="text-base font-semibold text-stein-900 leading-snug">{o.name ?? ""}</h5>
|
||||
<h5 class="min-w-0 text-sm font-semibold leading-snug text-stein-900 truncate">{o.name ?? ""}</h5>
|
||||
{#if o.description}
|
||||
<p class="text-sm text-stein-600">{o.description}</p>
|
||||
{/if}
|
||||
@@ -174,11 +193,12 @@
|
||||
{/if}
|
||||
{/each}
|
||||
|
||||
{#if block.addOrganisationTitle || block.addOrganisationMarkdown}
|
||||
{#if showAddOrganisationCard}
|
||||
<Card
|
||||
class={compact
|
||||
? "border-dashed border-wald-300 bg-wald-50 p-3! gap-1.5!"
|
||||
: "border-dashed border-wald-300 bg-wald-50"}
|
||||
href={addOrganisationCtaLink?.url}
|
||||
target={addOrganisationCtaLink?.newTab ? "_blank" : undefined}
|
||||
rel={addOrganisationCtaLink?.newTab ? "noopener noreferrer" : undefined}
|
||||
class={addOrganisationCardClass}
|
||||
>
|
||||
{#if block.addOrganisationTitle}
|
||||
<h5
|
||||
@@ -194,6 +214,15 @@
|
||||
{@html ctaHtml}
|
||||
</div>
|
||||
{/if}
|
||||
{#if addOrganisationCtaLink}
|
||||
<p
|
||||
class={compact
|
||||
? "mb-0 mt-1 text-xs font-medium text-wald-800"
|
||||
: "mb-0 mt-2 text-sm font-medium text-wald-800"}
|
||||
>
|
||||
{addOrganisationCtaLink.linkName}
|
||||
</p>
|
||||
{/if}
|
||||
</Card>
|
||||
{/if}
|
||||
</div>
|
||||
|
||||
@@ -9,10 +9,10 @@
|
||||
</script>
|
||||
|
||||
<div class={layoutClasses} data-block-type="quote" data-block-slug={block._slug}>
|
||||
<blockquote class="border-l-4 border-green-700 pl-4 {variantClass}">
|
||||
<p class="text-lg italic text-zinc-700">"{block.quote ?? ""}"</p>
|
||||
<blockquote class="border-l-4 border-wald-700 pl-4 {variantClass}">
|
||||
<p class="text-xl font-semibold text-wald-700">{block.quote ?? ""}</p>
|
||||
{#if block.author}
|
||||
<cite class="mt-1 block not-italic text-sm text-zinc-500">— {block.author}</cite>
|
||||
<cite class="mt-1 block not-italic text-sm text-wald-300">{block.author}</cite>
|
||||
{/if}
|
||||
</blockquote>
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user