Branding
The Branding page (left rail in the admin panel) controls how your PicPeak instance looks: company name, logo, colors, fonts, footer, and the public-facing landing page. Anything brand-related that isn’t tied to a specific event lives here.
For per-event theming (specific layout, presets, custom CSS) and how a gallery follows the global theme, see Themes & Branding.
Identity
| Setting | What it does |
|---|---|
| Company name | Shown in the page title (<title> tag), the email header, the gallery footer, and as the OG og:site_name. |
| Tagline | Optional one-liner under the company name on the public landing page. |
| Support email | Linked in the gallery footer (“Support” link) and the password-reset email body. |
| Footer text | Custom HTML/text rendered in the gallery footer. Sanitised — no scripts. |
Logo & favicon
| Setting | What it does |
|---|---|
| Logo upload | PNG, JPG, or SVG. Recommended: transparent PNG, ~400×120 px. Used in the admin header, gallery header, and as the default OG image for share previews. |
| Logo size | small / medium / large — affects max-height in the gallery header. |
| Logo position | top-left / top-center / top-right — placement in the gallery hero. |
| Favicon | Square PNG, 32×32 minimum. Falls back to picpeak-logo-transparent.png if not set. |
Uploaded files are served from /uploads/logos/ and /uploads/favicons/ and cached for 7 days at the nginx layer.
In builds containing PicPeak PR #1478 , only image files (PNG, JPG, JPEG, GIF, WebP, SVG, ICO) are served from these folders and from /favicon.ico; anything else answers 404. Older versions could leave non-image files in storage/uploads/logos or storage/uploads/favicons — if you upgraded, look for such files and delete them.
Colors
The color picker exposes eight colours in three groups that propagate through the UI as CSS variables:
| Group | Colour | What it controls |
|---|---|---|
| Surfaces | Background | The page itself — every gallery, admin page and CMS page |
| Surface | Cards, sidebar, header bar and navigation | |
| Elevated | Panels above cards: image placeholders, hover rows, modal headers | |
| Border | Dividers, table lines, card outlines, input borders | |
| Text | Text | Headlines, body copy, table cells, form values |
| Muted text | Captions, helper text, column headers, dates | |
| Accent | Accent Color | Links, icons, focus rings, hover states |
| Accent (filled) | Filled buttons, active sidebar item, badges and tags |
Color Mode (Auto, Light, Dark) and Force color mode decide whether visitors get the light or dark palette.
On the beta channel from v3.168.0-beta.0 a fourth group, Status, sets the colours for success, warning, danger, info and cancelled documents site-wide, and readability warnings appear under the pickers. The colours then also drive the admin and the colour of PDF documents and emails; see Themes & Branding → Status colours, documents and emails.
Theme presets
Theme presets bundle layout + color + typography choices into one click. The full list:
| Preset | Key | Layout |
|---|---|---|
| Classic Grid | default | Grid |
| Elegant Wedding | elegantWedding | Grid |
| Modern Masonry | modernMasonry | Masonry (columns) |
| Birthday Celebration | birthdayFun | Carousel |
| Corporate Timeline | corporateTimeline | Timeline |
| Artistic Mosaic | artisticMosaic | Mosaic |
| Dark Classic | darkClassic | Grid |
| Dark Elegant | darkElegant | Grid |
| Dark Modern | darkModern | Masonry (columns) |
| Gallery Premium (Beta) | galleryPremium | Gallery Premium |
| Gallery Story (Beta) | galleryStory | Gallery Story |
A gallery’s own theme wins over the global one for that gallery. On the beta channel a gallery follows the global theme until its Custom gallery styling is switched on; on stable each gallery keeps the copy of the theme it was created with. See Themes & Branding.
Hero divider
The slope between the gallery hero and the photo grid:
wave (default), straight, angle, curve, none.
Style is controlled by the active theme preset but can be overridden per-event.
Watermark
The brand watermark applied to downloaded images (and optionally to thumbnails) when the per-event Add watermark to downloads toggle is on. Without a watermark logo, the watermark is text: the company name, or on the beta channel the gallery’s own Watermark text (see Themes & Branding → Watermark text per gallery).
| Setting | What it does |
|---|---|
| Watermark logo | PNG with transparency. Different file from the brand logo. |
| Position | top-left / top-right / bottom-left / bottom-right / center |
| Opacity | 0–100 % |
| Size | Relative to image width (e.g. 15 %) |
Watermarks are baked into the downloaded copy on demand — never into the original on disk.
Public landing page
The page served at / when nobody is logged in. By default this redirects to /admin/login. Enable the public-site toggle on this page to serve a custom HTML/CSS welcome page instead.
| Setting | What it does |
|---|---|
| Enable public site | Master toggle. Off = redirect to admin login. |
| HTML | Full HTML body. Sanitised — <script> tags stripped. |
| Custom CSS | Scoped to the public landing page. |
The HTML editor supports a small set of placeholders that are substituted at render time:
{{ company_name }} — your branded company name
{{ company_tagline }} — your tagline
{{ support_email }} — clickable mailto link
{{ brand_logo_url }} — URL of the uploaded logo
{{ brand_primary_hex }}, {{ brand_accent_hex }}, etc. — color tokensSocial link previews
When a gallery URL is shared on WhatsApp, Facebook, Slack, etc., the link preview that appears in chat is fetched by the receiving platform — not generated client-side. PicPeak serves three different responses depending on who’s asking:
| Fetcher | What gets served | Configured by |
|---|---|---|
Known social crawlers (WhatsApp, Facebook, Slack, Telegram, Discord, LinkedIn, Pinterest, Mastodon, Bluesky, etc.) hitting /gallery/<slug> | A small HTML page with per-event og:title (event name) + og:description (welcome message or fallback) + og:image (brand logo, or hero photo if opted in) | Admin Branding (company name, logo) + per-event settings |
Regular browsers hitting /gallery/<slug> | The SPA shell — React loads, fetches gallery data, updates the document title client-side | Admin Branding (company name → <title>) |
| Anything else: link-preview services that cache metadata with a non-crawler User-Agent (WhatsApp Business API, Twilio, LinkPreview.net, Slack ImgProxy, etc.) | The static SPA shell as-is — no JS executes, no per-event lookup, just the raw HTML head | BRAND_TITLE / BRAND_DESCRIPTION env vars on the frontend container |
The first two paths cover most cases automatically — admin Branding settings flow through. The third path is what bites you when someone shares a gallery via WhatsApp’s Business API or a marketing automation tool: those fetchers don’t carry a recognisable crawler UA, so they end up reading the static shell.
Branding the static fallback
Set these two env vars on the frontend container (root .env file, picked up by both docker-compose.yml and docker-compose.production.yml):
BRAND_TITLE=Your Studio Name
BRAND_DESCRIPTION=Wedding and event photography by Your Studio Name.Then restart the frontend service:
docker compose -f docker-compose.production.yml up -d frontendNo frontend rebuild required — the values are substituted into index.html at container start via envsubst. Defaults to BRAND_TITLE=PicPeak and a generic description when unset, so existing deployments see no behaviour change until you flip them.
Receiving platforms cache link previews aggressively — WhatsApp Business in particular can hold a preview for hours to days. After changing BRAND_TITLE, expect previously-sent links to keep showing the old metadata until the receiver re-crawls. New sends pick up the change immediately.
See Environment Variables → Social link preview fallback for the reference table.
White-label admin
The admin panel itself shows your logo and company name in place of the PicPeak branding when these fields are set. The “Powered by PicPeak” footer link can be hidden from the public site only — the admin panel always credits the project (this is a community norm, not a license requirement).