feat(website): share card for /logo/ (og:image) so links to the vote get a preview
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01MScAinbyMdeNc7H2BZdnnG
This commit is contained in:
parent
58a99a0d9e
commit
c3c59b4bea
5 changed files with 36 additions and 0 deletions
|
|
@ -5,6 +5,7 @@ translationKey: "logo"
|
|||
layout: single
|
||||
type: poll
|
||||
poll: logo
|
||||
image: /img/logo/vote-card.png
|
||||
sitemap:
|
||||
priority: 0.5
|
||||
m:
|
||||
|
|
|
|||
|
|
@ -6,6 +6,7 @@ url: /logo/
|
|||
layout: single
|
||||
type: poll
|
||||
poll: logo
|
||||
image: /img/logo/vote-card.png
|
||||
sitemap:
|
||||
priority: 0.5
|
||||
m:
|
||||
|
|
|
|||
|
|
@ -11,6 +11,10 @@
|
|||
<meta property="og:description" content="{{ with .Params.description }}{{ . }}{{ else }}{{ site.Params.description }}{{ end }}">
|
||||
<meta property="og:type" content="{{ if .IsPage }}article{{ else }}website{{ end }}">
|
||||
<meta property="og:url" content="{{ .Permalink }}">
|
||||
{{ with .Params.image }}<meta property="og:image" content="{{ . | absURL }}">
|
||||
<meta property="og:image:width" content="1200">
|
||||
<meta property="og:image:height" content="630">
|
||||
<meta name="twitter:card" content="summary_large_image">{{ end }}
|
||||
{{ $parts := split .Site.Language.LanguageCode "-" }}<meta property="og:locale" content="{{ index $parts 0 }}{{ if gt (len $parts) 1 }}_{{ upper (index $parts 1) }}{{ end }}">
|
||||
{{ range .AllTranslations }}
|
||||
<link rel="alternate" hreflang="{{ .Lang }}" href="{{ .Permalink }}">
|
||||
|
|
|
|||
BIN
website/static/img/logo/vote-card.png
Normal file
BIN
website/static/img/logo/vote-card.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 26 KiB |
|
|
@ -232,7 +232,37 @@ def b64png(im):
|
|||
return "data:image/png;base64," + base64.b64encode(buf.getvalue()).decode()
|
||||
|
||||
|
||||
def vote_card(path):
|
||||
"""1200x630 share card for /logo/: M on cream, R on ink, side by side."""
|
||||
W, H = 1200, 630
|
||||
im = Image.new("RGBA", (W, H), "#f7f6f3")
|
||||
ImageDraw.Draw(im).rectangle([W // 2, 0, W, H], fill=MARKS["r"]["ink"])
|
||||
for k, cx in (("m", W // 4), ("r", 3 * W // 4)):
|
||||
m = mark_png(k, "flat", 330)
|
||||
im.alpha_composite(m, (cx - m.width // 2, 110 - (m.height - 330) // 2))
|
||||
size = 46
|
||||
d = ImageDraw.Draw(im)
|
||||
for text, cx, col in (("M", W // 4, "#6b6b6f"), ("R", 3 * W // 4, "#8a8a90")):
|
||||
paths, tw = wordmark(text, size)
|
||||
# letters via the same outlines: rasterise a tiny SVG for crisp text
|
||||
svgtxt = (f'<svg {XMLNS} viewBox="0 -{size} {tw:.0f} {size * 1.3:.0f}">'
|
||||
f'<g fill="{col}">{paths}</g></svg>')
|
||||
t = raster(svgtxt, round(tw), round(size * 1.3))
|
||||
im.alpha_composite(t, (cx - t.width // 2, 500))
|
||||
# url line, centred on the seam
|
||||
paths, tw = wordmark("furtka.org/logo", 40)
|
||||
svgtxt = (f'<svg {XMLNS} viewBox="0 -40 {tw:.0f} 52"><g fill="#c03a28">{paths}</g></svg>')
|
||||
t = raster(svgtxt, round(tw), 52)
|
||||
pad = 18
|
||||
box = Image.new("RGBA", (t.width + 2 * pad, t.height + 2 * pad), "#f7f6f3")
|
||||
ImageDraw.Draw(box).rounded_rectangle([0, 0, box.width - 1, box.height - 1], 14, outline="#e4e3dc")
|
||||
box.alpha_composite(t, (pad, pad))
|
||||
im.alpha_composite(box, (W // 2 - box.width // 2, 40))
|
||||
im.convert("RGB").save(path, optimize=True)
|
||||
|
||||
|
||||
def main():
|
||||
vote_card(os.path.join(SITE, "static", "img", "logo", "vote-card.png"))
|
||||
for k in MARKS:
|
||||
out = os.path.join(SITE, "static", "img", "logo", k)
|
||||
os.makedirs(out, exist_ok=True)
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue