# 主题开发教程(10 分钟上手)
配套示例:**`themes/demo/`**。本文用最小结构带你做一个能用的主题。
## 1. 最小主题结构
```
themes/demo/
├── theme.json # 主题清单(必填)
├── views/
│ └── partials/ # 覆盖公共片段
│ ├── head.blade.php
│ ├── header.blade.php
│ └── footer.blade.php
└── assets/
└── style.css # 主题样式(/themes/demo/assets/style.css 访问)
```
**核心机制**:激活主题的 `views/` 目录被前置到全局视图路径。页面视图(`index`/`show`/`list`…)按名字解析——主题有同名视图就用主题的,**没有就自动回退默认视图**(`resources/views/`)。
所以最小主题只需要覆盖 `partials/`(head/header/sidebar/footer),页面样式自己定,其他全部继承默认。
## 2. theme.json
```json
{
"title": "Demo 演示主题",
"version": "1.0.0",
"description": "一句话描述",
"author": "你的名字",
"screenshot": "screenshot.png",
"inject_points": ["head", "header", "footer"]
}
```
- `screenshot`:`assets/` 下的预览图,后台主题卡片展示(可选)
- `inject_points`:声明实现了哪些注入点(后台会展示);缺省视为全部支持
## 3. 覆盖 partials
`views/partials/head.blade.php` 需要包含:`
`、meta、CSS 引用。**必须保留注入点** `@stack('theme:head')`(后台「主题注入」的内容会渲染到这里):
```blade
@stack('head')
@stack('theme:head')
```
`header.blade.php` / `footer.blade.php` 同理,尾部保留 `@stack('theme:footer')` / `@stack('theme:body_end')`。
## 4. 视图解析规则
| 场景 | 结果 |
|------|------|
| 主题有 `index.blade.php` | 覆盖默认首页 |
| 主题没有 | 用 `resources/views/index.blade.php` |
| 主题只有 partials | 页面用默认,公共片段用主题的 |
想完全自定义某类页面,就在主题 views 下放同名文件(如 `show.blade.php`、`tag.blade.php`),控制器传的变量清单见 `docs/themes.md`。
## 5. 主题变量(可后台编辑)
`theme.json` 之外,可以在后台「主题注入 → 主题变量」里给主题加任意键值,视图用:
```blade
{{ theme('var', 'footer_about', '默认文本') }}
```
适合放广告位 HTML、自定义文案等,不用改代码。
## 6. 资产与发布
- **开发期**:`GET /themes/{name}/assets/{path}` 流式返回(带缓存头),改 CSS 刷新即生效
- **生产**:`php artisan theme:publish` 拷贝到 `public/themes/`,由 Web 服务器托管
## 7. 打包与安装
```bash
cd themes/demo && zip -r ../demo.zip . -x ".*"
```
后台「主题管理」→ 上传 ZIP 安装 → 启用。**不能删除当前激活的主题**。
## 8. 好主题的检查清单
- [ ] 移动端适配:`@media (max-width: 768px)` 两栏改单栏(参照 sablog/modern)
- [ ] 语义化 HTML:`/