Theme Structure

Directory layout

Only theme.json and css/style.css are required for a theme to be detected by the CMS. All other files are optional — missing templates fall back to theme/default/.

That said, a fully functional theme needs at minimum: theme.json, css/style.css, header.php, footer.php, and home.php. Without those, the CMS will silently use the default theme's versions, meaning your CSS loads but the HTML structure is someone else's.

theme/my-theme/
│
├── theme.json                  ← REQUIRED — theme manifest
├── functions.php               ← Optional — theme-specific PHP helpers
│
├── css/
│   ├── style.css               ← REQUIRED — must be named exactly style.css
│   ├── contact.css             ← Optional — contact form styles
│   └── shortcodes.css          ← Optional — CMS shortcode styles
│
├── js/
│   └── script.js               ← Optional — must be named exactly script.js
│
├── header.php                  ← Page opening (<!DOCTYPE> → <main>)
├── footer.php                  ← Page closing (</main> → </html>)
├── home.php                    ← Homepage template
├── 404.php                     ← 404 error template
│
├── content-articles.php        ← Single article view
├── content-projects.php        ← Single project view
├── content-pages.php           ← Single static page view
├── content-list.php            ← List view (articles/projects/categories/tags)
│
├── partials/
│   ├── article-card.php        ← Article card HTML override
│   └── project-card.php        ← Project card HTML override
│
├── page-templates/             ← Custom page templates (selectable per page in admin)
│   ├── contact.php
│   └── landing.php
│
└── preview.jpg                 ← 350×350px screenshot for the theme manager

theme.json

{
    "synaptik_theme": true,
    "name": "My Theme",
    "version": "1.0.0",
    "description": "A minimal theme for SynaptikCMS.",
    "author": "Your Name",
    "author_url": "https://example.com",
    "screenshot": "preview.jpg"
}

"synaptik_theme": true is required — it identifies the folder as a valid theme.


Asset naming conventions

AssetRequired namePath
Main CSSstyle.csstheme/{name}/css/style.css
Theme JSscript.jstheme/{name}/js/script.js

Both are detected and injected automatically by render_header_scripts(). Do not hardcode them in your templates.


Installing a theme

Manual: create theme/my-theme/ and add at minimum:

  • theme.json — with "synaptik_theme": true
  • css/style.css
  • header.php — your <!DOCTYPE html> to <main> opening
  • footer.php — your </main> to </html> closing
  • home.php — the homepage template

The theme appears automatically in Admin → Appearance → Themes once the folder contains a valid theme.json. Other templates (content-articles.php, content-list.php, 404.php, etc.) can be added progressively — the CMS falls back to theme/default/ for any file that is missing.

ZIP upload: zip the theme folder so the ZIP contains the folder itself (not just the loose files inside it), then go to Admin → Appearance → Import Theme.


Pre-publish checklist

[ ] theme.json present with "synaptik_theme": true
[ ] css/style.css present — named exactly style.css
[ ] header.php, footer.php, home.php present
[ ] preview.jpg present (350×350px)
[ ] header.php calls render_header_scripts($headerScripts)
[ ] footer.php calls render_search_ui() before </body>
[ ] CSS defines .articles-grid, .article-card, .projects-grid, .project-card
[ ] All UI strings use __t()
[ ] Theme works without partials/ and without content-list.php (both optional)
[ ] Tested on mobile