sw-fe/src/components/Map/templateSpecs.js

72 lines
2.6 KiB
JavaScript

/**
* Frontend-only template specs (no DB changes).
* Keep pointers as-is:
* - compact triangle: .post-pin-pointer-small
* - expanded triangle: .post-card-pointer
*/
export const TEMPLATE_SPECS = {
news: {
mini_spec: {
size: { w: 280, h: 110 },
background: { type: "gradient", value: "newsBlue" },
radius: 18,
layers: [
{ id: "badge", type: "chip", x: 14, y: 12, text: "NEWS", style: "chip.news" },
{ id: "title", type: "text", x: 14, y: 40, w: 252, h: 44, bind: "data.headline", style: "text.title", maxLines: 2 },
{ id: "meta", type: "text", x: 14, y: 88, w: 252, h: 16, bind: "data.source", style: "text.meta", maxLines: 1 }
],
},
full_spec: {
size: { w: 360, h: 520 },
background: { type: "solid", value: "surface" },
radius: 22,
layers: [
{ id: "hero", type: "image", x: 0, y: 0, w: 360, h: 220, bind: "data.image" },
{ id: "badge", type: "chip", x: 16, y: 16, text: "NEWS", style: "chip.news" },
{ id: "title", type: "text", x: 16, y: 240, w: 328, h: 78, bind: "data.headline", style: "text.h1", maxLines: 3 },
{ id: "summary", type: "text", x: 16, y: 325, w: 328, h: 110, bind: "data.summary", style: "text.body", maxLines: 5 },
{
id: "cta",
type: "button",
x: 16, y: 450, w: 328, h: 48,
text: "Open source",
style: "button.primary",
action: { type: "open_url", bind: "data.url" }
}
],
},
},
};
function normCat(post) {
const c = (post?.category || "").toString().toUpperCase();
if (c === "NEWS") return "news";
if (c === "EVENT") return "news";
if (c === "FRIENDS") return "news";
if (c === "MARKET") return "news";
return "news";
}
export function getTemplateKeyForPost(post) {
// Future mapping: if (post.template_id === 101) return "news";
return normCat(post);
}
export function getTemplateSpecForPost(post, variant /* "mini"|"full" */) {
const key = getTemplateKeyForPost(post);
const t = TEMPLATE_SPECS[key] || TEMPLATE_SPECS.news;
return variant === "full" ? t.full_spec : t.mini_spec;
}
export function adaptPostToTemplateData(post) {
const headline = post?.title || "Untitled";
const author = post?.author ? `by ${post.author}` : "";
const sub = post?.sub_category ? String(post.sub_category) : "";
const source = author || sub || "";
const summary = post?.snippet || post?.body || "";
const url = post?.url || "";
const image = post?.image_large || post?.image_small || post?.image || post?.media_url || "";
return { headline, source, summary, url, image };
}