yes
All checks were successful
continuous-integration/drone/push Build is passing

This commit is contained in:
yinsx
2026-01-05 18:06:37 +08:00
parent 24cebd2179
commit 2e59bae10b
18 changed files with 207 additions and 569 deletions

View File

@ -0,0 +1,105 @@
# SDK API 参考
下列 API 均可在全局挂载或 ESM 模式下使用。示例统一使用 `kernel` 作为实例,若为全局构建请替换为 `window.faceSDK.kernel`
## 相机 Camera
```ts
// 设置视角
kernel.camera.set({
position: [2.5, 1.6, 3.2],
target: [0, 0.8, 0],
fov: 45,
near: 0.1,
far: 200,
})
// 平滑过渡
kernel.camera.animateTo(
{ position: [1.2, 1, 2.4], target: [0, 0.8, 0], fov: 50 },
{ duration: 0.8, easing: 'easeOutCubic', onFinish: () => console.log('camera done') }
)
```
## 灯光 Lights
```ts
// 主方向光
kernel.lights.update('key', {
intensity: 1.5,
color: '#ffffff',
direction: [0.3, -1, 0.25],
castShadow: true,
})
// 环境光 / 辅光
kernel.lights.update('fill', { intensity: 0.6, color: '#dfe8ff' })
kernel.lights.update('ambient', { intensity: 0.25 })
```
## 环境贴图 Environment
```ts
await kernel.environment.setHDRI('/envs/showroom_2k.hdr', {
exposure: 1.1,
rotation: [0, 45, 0], // yaw/pitch/roll
blur: 0.2,
})
```
## 热点 Hotspot
```ts
const hotspots = [
{ id: 'engine', position: [0.8, 0.6, -0.2], icon: 'info', label: '发动机舱', event: 'show-engine' },
{ id: 'door', position: [1.1, 0.9, 0.4], icon: 'action', label: '开启车门', event: 'toggle-door' },
]
kernel.hotspot.render(hotspots)
kernel.hotspot.on('click', ({ id, payload }) => {
console.log('hotspot click', id, payload)
})
kernel.hotspot.on('hover', ({ id, hovering }) => {
console.log('hotspot hover', id, hovering)
})
```
## 模型 Model
```ts
// 加载
await kernel.model.load({ id: 'car', url: '/models/car.glb', draco: true })
// 销毁
await kernel.model.destroy('car')
// 替换
await kernel.model.replace('car', { url: '/models/car-white.glb' })
// 事件
kernel.model.on('loaded', (data) => console.log('loaded', data))
kernel.model.on('replaced', (data) => console.log('replaced', data))
kernel.model.on('destroyed', (data) => console.log('destroyed', data))
```
## 材质 Material
```ts
// 应用预设
kernel.material.apply({ target: 'body', material: 'paint/blue' })
// 批量切换
kernel.material.batch([
{ target: 'wheel', material: 'rim/chrome' },
{ target: 'glass', material: 'glass/clear' },
])
// 还原
kernel.material.reset('body')
```
## 事件总线与调试
```ts
// 订阅/取消
kernel.on('hotspot:click', (evt) => console.log(evt))
kernel.off('hotspot:click', handler)
// 开启调试日志
kernel.debug(true)
```

View File

@ -1,43 +0,0 @@
# 相机与灯光/环境
## 相机控制
```ts
// 直接设置视角
sdk.camera.set({
position: [2.5, 1.6, 3.2],
target: [0, 0.8, 0],
fov: 45,
near: 0.1,
far: 200,
})
// 平滑过渡到指定视角
sdk.camera.animateTo(
{ position: [1.2, 1, 2.4], target: [0, 0.8, 0], fov: 50 },
{ duration: 0.8, easing: 'easeOutCubic' }
)
```
## 灯光调参
```ts
// 更新主方向光
sdk.lights.update('key', {
intensity: 1.5,
color: '#ffffff',
direction: [0.3, -1, 0.25],
castShadow: true,
})
// 环境光/辅光
sdk.lights.update('fill', { intensity: 0.6, color: '#dfe8ff' })
sdk.lights.update('ambient', { intensity: 0.25 })
```
## 环境贴图
```ts
await sdk.environment.setHDRI('/envs/showroom_2k.hdr', {
exposure: 1.1,
rotation: [0, 45, 0], // yaw/pitch/roll
blur: 0.2,
})
```

View File

@ -1,39 +0,0 @@
# 案例模板(可直接复制改内容)
> 这是一个 Markdown 案例模板,你可以复制成 `case-xxx.md`,然后在页面里直接预览。
## 项目背景
- 行业 / 场景:
- 目标(转化/展示/提效):
- 时间周期:
- 我的角色:前端 / 全栈 / Web3D / 小程序
## 交付内容
- 核心页面:
- 核心功能:
- 技术栈:
- 部署方式:
## 难点与解决方案
1. 难点:
2. 方案:
3. 结果:
## 代码片段(示例)
```ts
export type ApiResponse<T> = {
code: number
message: string
data: T
}
```
## 复盘
- 做得好的:
- 下次会更好的:

View File

@ -1,30 +0,0 @@
# 配置示例与事件清单
## 推荐的配置结构
```json
{
"camera": { "position": [2.5, 1.6, 3.2], "target": [0, 0.8, 0], "fov": 45 },
"environment": { "hdr": "/envs/showroom_2k.hdr", "exposure": 1.1, "rotation": [0, 45, 0] },
"lights": {
"key": { "intensity": 1.5, "color": "#ffffff", "direction": [0.3, -1, 0.25] },
"fill": { "intensity": 0.6, "color": "#dfe8ff" },
"ambient": { "intensity": 0.25 }
},
"hotspots": [
{ "id": "engine", "position": [0.8, 0.6, -0.2], "icon": "info", "label": "发动机舱", "event": "show-engine" },
{ "id": "door", "position": [1.1, 0.9, 0.4], "icon": "action", "label": "开启车门", "event": "toggle-door" }
]
}
```
## 事件清单(示例)
- 相机:`camera:changed`
- 热点:`hotspot:click``hotspot:hover``hotspot:rendered`
- 模型:`model:loaded``model:replaced``model:destroyed`
- 材质:`material:applied``material:reset`
订阅方式:
```ts
sdk.on('hotspot:click', (evt) => console.log(evt))
sdk.off('hotspot:click', handler) // 移除监听
```

View File

@ -1,16 +0,0 @@
# 联系方式
> 建议把这里的联系方式换成你的真实信息。
- 微信:`TyTinSx`
- 邮箱:`14154666@qq.com`
## 发需求时建议包含
1. 项目类型:官网/后台/全栈/Web3D/小程序
2. 目标:要达成什么效果或指标
3. 范围:页面/功能清单(越具体越好)
4. 参考:竞品/参考链接、设计稿、文案素材
5. 时间:期望上线时间、是否有阶段节点
6. 现状:是否已有代码、接口、服务器、域名等

View File

@ -0,0 +1,71 @@
# 事件监听指南
说明如何订阅/取消订阅 SDK 事件,适用于全局挂载与 ESM 两种集成方式。
## 获取实例
- ESM`import { kernel } from '.../index.js'`
- 全局:`const kernel = window.faceSDK?.kernel`
以下示例统一使用 `kernel`
## 常见事件
- 相机:`camera:changed`
- 热点:`hotspot:click``hotspot:hover``hotspot:focus``hotspot:rendered`
- 模型:`model:loaded``model:replaced``model:destroyed``model:load:progress`
- 材质:`material:applied``material:reset`
- 其他:业务自定义事件(若有)
## 订阅与取消
```ts
// 订阅
const handleHotspotClick = (evt) => {
console.log('hotspot click', evt.id, evt.payload)
}
kernel.on('hotspot:click', handleHotspotClick)
// 取消订阅
kernel.off('hotspot:click', handleHotspotClick)
```
## 示例:热点事件
```ts
kernel.on('hotspot:hover', ({ id, hovering }) => {
// 根据 hovering 控制高亮/提示
})
kernel.on('hotspot:rendered', () => {
console.log('所有热点已就绪')
})
```
## 示例:模型事件
```ts
kernel.on('model:load:progress', ({ id, progress }) => {
console.log(`模型 ${id} 进度`, progress)
})
kernel.on('model:loaded', ({ id }) => {
console.log(`模型 ${id} 加载完成`)
})
kernel.on('model:replaced', ({ id }) => {
console.log(`模型 ${id} 已替换`)
})
```
## 示例:相机与材质
```ts
kernel.on('camera:changed', (state) => {
console.log('相机状态', state)
})
kernel.on('material:applied', ({ target, material }) => {
console.log(`材质已应用到 ${target}: ${material}`)
})
```
## 调试与日志
```ts
// 输出加载、事件、性能相关的调试信息
kernel.debug(true)
```

View File

@ -1,40 +0,0 @@
# 热点与事件
## 渲染热点
```ts
const hotspots = [
{
id: 'engine',
position: [0.8, 0.6, -0.2],
icon: 'info',
label: '发动机舱',
event: 'show-engine',
payload: { part: 'engine' },
},
{
id: 'door',
position: [1.1, 0.9, 0.4],
icon: 'action',
label: '开启车门',
event: 'toggle-door',
payload: { side: 'left' },
},
]
sdk.hotspot.render(hotspots)
```
## 订阅事件
```ts
sdk.hotspot.on('click', ({ id, payload }) => {
// 根据 id/payload 触发业务逻辑
})
sdk.hotspot.on('hover', ({ id, hovering }) => {
// hover 高亮或提示
})
```
## 事件命名建议
- `hotspot:click``hotspot:hover``hotspot:focus`
- `hotspot:rendered`(所有热点就绪)

View File

@ -14,9 +14,9 @@
console.error('SDK 未加载')
} else {
kernel.init({
container: 'renderDom', // 容器 IDcanvas
container: '#renderDom', // 容器 IDcanvas 或者 DOM 元素引用
modelUrlList: ['./model.glb'], // 模型列表
env: { hdrPath: '/hdr/my.env' }, // 环境贴图等参数
env: { envPath: '/public/hdr/hdr.env', intensity: 1.2, rotationY: 0.3 }, // 环境贴图等参数
})
}
```
@ -29,9 +29,9 @@
2. 初始化(与全局方式一致):
```js
kernel.init({
container: 'renderDom',
container: '#renderDom', // 容器 IDcanvas 或者 DOM 元素引用
modelUrlList: ['./model.glb'],
env: { envPath: '/hdr/my.env' },
env: { envPath: '/public/hdr/hdr.env', intensity: 1.2, rotationY: 0.3 }, // 环境贴图等参数
})
```
@ -44,3 +44,15 @@ kernel.on('model:click', (data) => console.log('模型点击', data))
// 需要时可移除
// kernel.off('model:loaded', handler)
```
## 提供测试用的模型和环境贴图
```
https://sdk.zguiy.com/resurces/model/model.glb
```
```
https://sdk.zguiy.com/resurces/hdr/hdr.env
```

View File

@ -1,38 +0,0 @@
# 模型热更新与材质切换
## 模型热加载 / 销毁 / 替换
```ts
// 加载
await sdk.model.load({ id: 'car', url: '/models/car.glb', draco: true })
// 销毁
await sdk.model.destroy('car')
// 替换(内部自动销毁旧实例并加载新实例)
await sdk.model.replace('car', { url: '/models/car-white.glb' })
```
监听状态:
```ts
sdk.model.on('loaded', handler)
sdk.model.on('replaced', handler)
sdk.model.on('destroyed', handler)
```
## 材质切换
```ts
// 应用材质预设
sdk.material.apply({
target: 'body', // 部件或分组名称
material: 'paint/blue', // 预设 Key
})
// 批量切换
sdk.material.batch([
{ target: 'wheel', material: 'rim/chrome' },
{ target: 'glass', material: 'glass/clear' },
])
// 还原默认材质
sdk.material.reset('body')
```

View File

@ -1,35 +0,0 @@
# 快速开始
面向 Web 场景的三维展示与互动 SDK提供相机、灯光、环境贴图、热点、模型热更新与材质切换等能力。
## 安装
```bash
npm install your-web3d-sdk
```
## 初始化 Viewer
```ts
import { createViewer } from 'your-web3d-sdk'
const sdk = await createViewer({
container: '#viewer',
assetsBase: '/assets',
background: '#0f172a',
})
// 加载初始场景或模型
await sdk.model.load({ id: 'scene', url: '/models/showroom.glb' })
```
## 基础生命周期
1. 初始化 viewer`createViewer({ container })`
2. 加载模型或场景:`sdk.model.load(...)`
3. 设置环境贴图/灯光:`sdk.environment.setHDRI(...)``sdk.lights.update(...)`
4. 渲染热点:`sdk.hotspot.render(config.hotspots)`
5. 订阅事件:`sdk.on('hotspot:click', handler)`
6. 按需调用相机/材质/模型热更新 API
## 调试建议
- 启用 `sdk.debug(true)` 查看加载、事件、帧率等日志。
- 逐步应用配置:先确认相机与灯光,再添加环境贴图与热点,最后再做材质/模型热更新。
- 热更新前后记录 ID/实例,避免重复销毁或遗漏解绑事件。

View File

@ -1,22 +0,0 @@
# 服务清单
## 我能做什么
- 企业官网 / 产品官网 / 落地页品牌展示、动效、响应式、SEO 基础、上线部署。
- 后台管理系统:权限、表格、筛选、导入导出、图表看板、审批流(按需)。
- 全栈业务开发:接口设计、鉴权、数据库建模、联调、部署(按需)。
- Web3D 互动展示Three.js / Babylon.js模型加载、交互热点、性能优化与业务联动。
- 3D 建模与渲染建模、UV、贴图烘焙、PBR 材质、灯光渲染与出片(静帧/视频)。
- 小程序开发:微信小程序 / uni-app按需常见业务页面与接口联调发布。
## 你需要提供什么
- 目标与范围:要解决什么问题?核心流程是什么?
- 参考与素材参考链接、设计稿Figma/蓝湖/Sketch、文案、图片、Logo 等。
- 约束条件:时间节点、预算范围、技术限制、已有接口/账号/服务器(如有)。
## 我会交付什么
- 可运行项目(源码 + 构建产物)
- 交付说明(部署/环境变量/使用说明)
- 里程碑验收清单(对照验收更省心)

View File

@ -1,63 +0,0 @@
# Web3D 案例展示
基于 Three.js / Babylon.js 开发的 3D 互动展示项目。
---
## 小型货车 3D 配置器
![蓝擎X1货车](/案例图片/web3d/5b86f5fffbab10515fa800a435620437.png)
蓝擎X1小型货车在线配置器支持颜色切换极光蓝/珠光白)、外观/内饰/行驶模式预览,可触发车门开关、车灯等交互动画。
🔗 暂无分享链接
---
## SUV 汽车 3D 展示
![星仓SUV](/案例图片/web3d/dfcac2db610f8005a823d0dc93d8cea9.png)
星仓系列 SUV 3D 展厅,支持宝石蓝、水晶紫、冰川银、岩石灰等多种车漆颜色实时切换,外观与内饰双视角浏览。
🔗 暂无分享链接
---
## 虚拟数字展厅
![虚拟展厅](/案例图片/web3d/de96ab4609d15338c15f7eb97ec82cc1.png)
企业虚拟展馆,第三人称漫游模式,集成产品陈列、数据大屏、中国地图可视化,支持虚拟人物导览。
🔗 暂无分享链接
---
## 摩托车 3D 展示
![摩托车展示](/案例图片/web3d/xw_20251231091651.png)
高精度摩托车模型展示,展厅灯光环境,支持 360° 旋转查看细节。
🔗 暂无分享链接
---
## 运动鞋 3D 配置器
![运动鞋配置](/案例图片/web3d/xw_20251231091744.png)
运动鞋在线定制工具,支持多种配色方案实时切换,材质纹理清晰可见。
🔗 暂无分享链接
---
## 自行车 3D 展示
![自行车展示](/案例图片/web3d/xw_20251231091809.png)
山地自行车户外场景展示,支持车型配置选择,实时渲染骑行效果预览。
🔗 暂无分享链接

View File

@ -1,33 +0,0 @@
# 建模与渲染PBR 流程)
面向「产品 / 角色 / 场景」资产制作:建模 → UV → 烘焙 → PBR 材质 → 灯光渲染 → 出片(静帧/视频)。流程可按你的项目预算与时间裁剪。
## 适合的需求
- 产品展示电商主图、详情图、爆炸图、360 展示、质感渲染
- 角色/道具:游戏或宣传视觉的资产制作与渲染出片
- 场景/小片段:镜头分镜、氛围灯光、简单动画与剪辑出片(按需)
## 标准流程(可按项目裁剪)
1. 需求对齐:用途(电商/游戏/交互/视频)、风格参考、镜头与交付规格(分辨率/FPS/时长)
2. 建模:高模/低模(按需)、拓扑优化、模型命名与层级整理
3. UV拆分、展开、打包为贴图与烘焙做准备
4. 烘焙Normal / AO / Curvature / ID 等(按项目需要)
5. 材质PBRBaseColor / Metallic / Roughness / Normal / AO+ Emissive/Opacity 按需)
6. 灯光与渲染HDRI/三点布光、材质校色、渲染参数与降噪(按引擎与预算)
7. 合成与出片通道AOV合成、调色、字幕/转场、输出静帧或视频
8. 交付:源文件 + 贴图 + 成片;需要适配引擎/平台也可输出 glTF/FBX按需
## 你需要提供什么
- 参考与目标:风格图/竞品链接、用途与核心卖点
- 素材Logo/贴纸/花纹(如有)、尺寸/结构信息(如有)
- 交付规格:分辨率、画幅、背景(透明/纯色/场景)、视频时长与帧率
## 我会交付什么
- 源文件(按工具):工程文件/模型文件/材质节点(按约定)
- 贴图文件PBR 贴图与烘焙贴图(按约定打包)
- 成片静帧PNG/JPG或视频MP4可提供可复用的镜头与灯光设置按需

View File

@ -1,34 +0,0 @@
# 按天合作
适合短期支援、技术咨询或灵活用工需求。
## 合作方式
1. 确认工作内容与时间
2. 按天计费,灵活安排
3. 每日同步进度
4. 按实际工作天数结算
## 适用场景
- 项目紧急支援
- 技术难题攻关
- 代码审查与优化
- 架构设计咨询
## 日费参考
| 服务类型 | 日费 |
|---------|------|
| 前端开发 | ¥800 - ¥1,500 |
| 后端开发 | ¥1,000 - ¥2,000 |
| 全栈开发 | ¥1,200 - ¥2,500 |
| 技术咨询 | ¥1,500 - ¥3,000 |
## 工作时间
- 标准8小时/天
- 支持远程协作
- 可根据需求调整
> 长期合作可享优惠价格

View File

@ -1,27 +0,0 @@
# 按项目合作
适合有明确需求、完整功能模块的客户。
## 合作方式
1. 需求沟通与评估
2. 报价与合同签订
3. 分阶段交付与验收
4. 项目上线与维护
## 适用场景
- 企业官网开发
- 小程序/App 开发
- 后台管理系统
- 定制化功能模块
## 报价参考
| 项目类型 | 周期 | 价格区间 |
|---------|------|---------|
| 企业官网 | 1-2周 | ¥3,000 - ¥8,000 |
| 小程序 | 2-4周 | ¥5,000 - ¥15,000 |
| 管理后台 | 3-6周 | ¥10,000 - ¥30,000 |
> 具体报价根据实际需求评估

View File

@ -134,7 +134,7 @@ const features: Feature[] = [
},
{
title: '事件总线与调试',
description: '统一事件接口;sdk.debug 输出加载、事件、性能日志,便于排障。',
description: '统一事件接口;kernel.debug 输出加载、事件、性能日志,便于排障。',
icon: ShieldCheck,
},
]
@ -142,84 +142,84 @@ const features: Feature[] = [
const featureTerminalScripts: TypeItTerminalSegment[][] = [
[
{
html: '<div><span class="text-gray-500">sdk.camera.set</span>({ fov: 45, position: [2,1.2,3] })</div>',
html: '<div><span class="text-gray-500">kernel.camera.set</span>({ fov: 45, position: [2,1.2,3] })</div>',
speed: 26,
pauseAfter: 900,
deleteAfter: true,
deleteSpeed: 18,
},
{
html: '<div><span class="text-gray-500">sdk.camera.animateTo</span>({ target: [0,0.8,0] }, { duration: 0.8 })</div>',
html: '<div><span class="text-gray-500">kernel.camera.animateTo</span>({ target: [0,0.8,0] }, { duration: 0.8 })</div>',
speed: 24,
pauseAfter: 1200,
},
],
[
{
html: '<div><span class="text-gray-500">sdk.lights.update</span>(<span class="text-amber-600">"key"</span>, { intensity: 1.4, castShadow: true })</div>',
html: '<div><span class="text-gray-500">kernel.lights.update</span>(<span class="text-amber-600">"key"</span>, { intensity: 1.4, castShadow: true })</div>',
speed: 24,
pauseAfter: 900,
deleteAfter: true,
deleteSpeed: 18,
},
{
html: '<div><span class="text-gray-500">sdk.environment.setHDRI</span>("showroom.hdr", { exposure: 1.1, rotation: [0,45,0] })</div>',
html: '<div><span class="text-gray-500">kernel.environment.setHDRI</span>("showroom.hdr", { exposure: 1.1, rotation: [0,45,0] })</div>',
speed: 22,
pauseAfter: 1200,
},
],
[
{
html: '<div><span class="text-gray-500">sdk.hotspot.render</span>([{ id: "engine", event: "show-engine" }])</div>',
html: '<div><span class="text-gray-500">kernel.hotspot.render</span>([{ id: "engine", event: "show-engine" }])</div>',
speed: 24,
pauseAfter: 900,
deleteAfter: true,
deleteSpeed: 18,
},
{
html: '<div><span class="text-gray-500">sdk.on</span>(<span class="text-emerald-600">"hotspot:click"</span>, ({ id }) =&gt; highlight(id))</div>',
html: '<div><span class="text-gray-500">kernel.on</span>(<span class="text-emerald-600">"hotspot:click"</span>, ({ id }) =&gt; highlight(id))</div>',
speed: 22,
pauseAfter: 1200,
},
],
[
{
html: '<div><span class="text-gray-500">sdk.model.load</span>({ id: "car", url: "/car.glb" })</div>',
html: '<div><span class="text-gray-500">kernel.model.load</span>({ id: "car", url: "/car.glb" })</div>',
speed: 24,
pauseAfter: 900,
deleteAfter: true,
deleteSpeed: 18,
},
{
html: '<div><span class="text-gray-500">sdk.model.replace</span>("car", { url: "/car-white.glb" })</div>',
html: '<div><span class="text-gray-500">kernel.model.replace</span>("car", { url: "/car-white.glb" })</div>',
speed: 24,
pauseAfter: 1200,
},
],
[
{
html: '<div><span class="text-gray-500">sdk.material.apply</span>({ target: "body", material: "paint/blue" })</div>',
html: '<div><span class="text-gray-500">kernel.material.apply</span>({ target: "body", material: "paint/blue" })</div>',
speed: 24,
pauseAfter: 900,
deleteAfter: true,
deleteSpeed: 18,
},
{
html: '<div><span class="text-gray-500">sdk.material.batch</span>([{ target: "glass", material: "glass/clear" }])</div>',
html: '<div><span class="text-gray-500">kernel.material.batch</span>([{ target: "glass", material: "glass/clear" }])</div>',
speed: 22,
pauseAfter: 1200,
},
],
[
{
html: '<div><span class="text-gray-500">sdk.on</span>(<span class="text-emerald-600">"model:loaded"</span>, log)</div>',
html: '<div><span class="text-gray-500">kernel.on</span>(<span class="text-emerald-600">"model:loaded"</span>, log)</div>',
speed: 22,
pauseAfter: 900,
deleteAfter: true,
deleteSpeed: 18,
},
{
html: '<div><span class="text-gray-500">sdk.debug</span>(<span class="text-amber-600">true</span>)</div>',
html: '<div><span class="text-gray-500">kernel.debug</span>(<span class="text-amber-600">true</span>)</div>',
speed: 18,
pauseAfter: 1200,
},

View File

@ -41,12 +41,9 @@ const BASE_URL = import.meta.env.BASE_URL
// SDK 文档列表
const docsFiles = [
'quickstart.md',
'camera-light.md',
'hotspot-events.md',
'model-material.md',
'config-template.md',
'import-guide.md',
'api-reference.md',
'event-listening.md',
]
const mdFiles = ref<string[]>([])

View File

@ -1,127 +0,0 @@
<template>
<section class="grid gap-10 pt-3 pb-12">
<div class="grid gap-2 text-center">
<div class="inline-flex flex-wrap justify-center gap-3.5 text-xs text-gray-500">
<span>前端开发</span>
<span>全栈开发</span>
<span>后台管理</span>
<span>Web3DThree/Babylon</span>
<span>3D建模/渲染PBR</span>
<span>小程序</span>
</div>
<div class="text-[11px] tracking-[0.3em] text-gray-400">SERVICES</div>
<h1 class="m-0 text-[clamp(26px,4vw,36px)] font-extrabold tracking-[-0.02em]">服务与报价</h1>
<p class="m-0 mx-auto max-w-[680px] leading-relaxed text-gray-500">
按需求评估按里程碑交付可从 0 1 搭建也可接手存量项目重构/优化/继续迭代
</p>
</div>
<div class="grid gap-4">
<h2 class="m-0 text-lg font-bold">常见合作套餐</h2>
<div class="grid grid-cols-3 gap-[18px] max-[1024px]:grid-cols-2 max-[640px]:grid-cols-1">
<PlanCard v-for="plan in projectPlans" :key="plan.subtitle" v-bind="plan" />
</div>
</div>
<div class="grid gap-4">
<h2 class="m-0 text-lg font-bold">长期合作</h2>
<div class="grid grid-cols-2 gap-[18px] max-[1024px]:grid-cols-1">
<PlanCard v-for="plan in retainerPlans" :key="plan.subtitle" v-bind="plan" />
</div>
<div class="grid grid-cols-1 gap-[18px]">
<PlanCard v-bind="customPlan" />
</div>
</div>
</section>
</template>
<script setup lang="ts">
import PlanCard from '@/components/PlanCard/index.vue'
type Plan = {
title: string
subtitle: string
badge?: string
price: string
note?: string
features: string[]
footerNote: string
highlight?: boolean
}
const projectPlans: Plan[] = [
{
title: '企业官网 / 落地页',
subtitle: '品牌展示 · SEO 基础',
badge: '快速交付',
price: '¥ 按需求报价',
note: '适合活动页、产品官网、品牌介绍、营销落地。',
features: ['响应式适配 · 兼容主流浏览器', '高还原 UI + 动效', 'SEO/OG/站点地图(按需)', '表单/埋点/转化链路(按需)'],
footerNote: '交付:源码 + 部署说明',
},
{
title: '后台管理系统',
subtitle: '权限 · 表格 · 图表',
badge: '业务提效',
price: '¥ 按需求报价',
note: '适合数据看板、运营后台、CRM/ERP 子系统。',
features: ['账号/角色/权限模型', '列表/筛选/导出/批处理', '接口联调 + 错误处理', '可维护的组件与路由结构'],
footerNote: '交付:可部署版本 + 使用说明',
highlight: true,
},
{
title: 'Web3D 互动展示',
subtitle: 'Three.js / Babylon.js',
badge: '更强体验',
price: '¥ 按需求报价',
note: '适合产品展示、展厅导览、互动营销、3D 组件开发。',
features: ['模型加载/压缩glTF/DRACO', '交互与镜头控制', '性能优化LOD/合批/纹理)', '与页面业务联动UI/数据)'],
footerNote: '交付:可复用组件 + 性能建议',
},
{
title: '3D建模与渲染',
subtitle: '建模 · 材质 · PBR · 出片',
badge: '可出视频',
price: '¥ 按需求报价',
note: '适合产品/角色/场景资产制作,支持从建模到渲染出片(静帧/视频)。',
features: [
'高模/低模建模 + 拓扑优化(按需)',
'UV 展开与贴图烘焙Normal/AO 等)',
'PBR 材质流程Substance/Blender 等)',
'灯光/渲染/合成与视频输出(按需)',
],
footerNote: '交付:源文件 + 贴图 + 成片',
},
]
const retainerPlans: Plan[] = [
{
title: '长期迭代(按月)',
subtitle: '稳定排期 · 迭代交付',
badge: '长期合作',
price: '¥ 按月报价',
note: '适合长期运营产品、版本迭代、活动频繁的团队。',
features: ['每周同步进度与风险', '按里程碑验收与交付', '代码规范/CI/质量把控', '线上问题响应(按约定)'],
footerNote: '方式:远程协作 · 里程碑结算',
},
{
title: '全栈开发(按需求)',
subtitle: '接口 · 数据库 · 部署',
badge: '从 0 到 1',
price: '¥ 按需求报价',
note: '适合需要后端接口、数据建模、部署上线的一体化项目。',
features: ['API 设计与鉴权JWT/OAuth', '数据库建模与迁移', '日志/监控/告警(按需)', 'Docker/服务器部署(按需)'],
footerNote: '交付:接口文档 + 部署脚本(按需)',
},
]
const customPlan: Plan = {
title: '定制合作',
subtitle: '按需求评估报价',
badge: '欢迎咨询',
price: '¥ 面议',
note: '把你的需求发我:目标、时间、参考风格、已有资料/接口。我会给出排期与报价建议。',
features: ['支持接手存量项目:重构/性能优化/修 Bug', '支持小程序开发:微信小程序/uni-app按需', '支持设计对接Figma/蓝湖/Sketch', '可签 NDA/合同与发票(按需)'],
footerNote: '微信/邮箱咨询 · 先评估再开工',
}
</script>