Appearance
命名规范
适用于工程中所有文件、组件、变量、函数、CSS 类名、网页标题。 一致性是命名规范的唯一目标。
网页标题(<title>)命名规则
规则
text
NEXA - <页面功能>各级标题示例
| 场景 | <title> 内容 | 说明 |
|---|---|---|
| 产品首页 | NEXA - 战术仿真引擎 | 品牌 + 产品名 |
| 产品子页面 | NEXA - 场景编辑 | 品牌 + 功能页 |
| 组件库 dev | NEXA - BaseMap Manager Dev | 品牌 + 组件名 |
| 示例中心 | NEXA - 示例中心 | 品牌 + 功能 |
| 文档站 | NEXA - 文档 | 品牌 + 文档 |
实现方式
html
<!-- index.html: 设置默认标题 -->
<title>NEXA - 战术仿真引擎</title>typescript
// Vue Router: 动态设置标题
router.afterEach((to) => {
document.title = to.meta.title
? `NEXA - ${to.meta.title}`
: 'NEXA - 战术仿真引擎'
})禁止事项
- ❌ 使用无意义的默认标题(如
Vite App、Document) - ❌ 标题中不包含产品标识(无法从标签页区分)
- ❌ 标题过长(超过 60 个字符)
品牌与命名空间
工程品牌统一为 NEXA(见 NEXA_CONSTITUTION.md §2,仓库根,VitePress 站点外)。
| 场景 | 命名规则 | 示例 |
|---|---|---|
| npm scope | @nexa/<kebab-case> | @nexa/gis-cesium |
| 文档标题 | NEXA - <功能> | NEXA - 战术仿真引擎 |
| UMD 全局变量 | NexaGIS | window.NexaGIS |
| 构建产物文件名 | nexa-<包名>.<format>.js | nexa-gis-cesium.es.js、scenario-data.es.js |
| 环境变量前缀 | NEXA_*(Vite 侧 VITE_NEXA_*) | VITE_NEXA_GIS_API |
| Docker / 资源命名 | nexa-* | nexa-tactics-sim |
| 仓储 / 仓库 | nexa | 根 package.json name |
品牌禁止事项
- ❌ 新代码引入旧品牌(token 清单见 NEXA_CONSTITUTION.md §2,本文件不重复列)
- ❌ 历史文档除外(
docs/decisions、docs/research、docs/migration豁免) - ❌ 旧品牌 Storage Key 直改导致用户数据丢失——须惰性迁移(见
products/tactics-sim-engine/src/stores/project.ts) - 品牌残留由
pnpm check:architecture全仓扫描自动拦截(防回潮)
文件命名
通用规则
| 类型 | 命名方式 | 示例 |
|---|---|---|
| Vue 组件 | PascalCase | BaseMapPanel.vue、Timeline.vue |
| TypeScript 模块 | camelCase(函数/工具)PascalCase(类) | coordinateUtils.ts、EntityDetectEffect.ts |
| 类型定义文件 | 统一 types.ts | 每个模块目录下 |
| 导出入口 | 统一 index.ts | 每个模块目录下 |
| 测试文件 | <被测文件名>.spec.ts | EntityDetectEffect.spec.ts |
| GLSL 着色器 | PascalCase.glsl | PulseCone.glsl |
| 目录 | kebab-case 或单层 camelCase | base-map-manager/、cesium-timeline-tracks/ |
包内文件命名
src/lib/
├── index.ts # 公共 API 总入口
├── NexaCesium.ts # 版本 + re-export
└── core/
├── effects/
│ ├── index.ts
│ ├── types.ts
│ ├── EntityDetectEffect.ts # 类 → PascalCase
│ └── ExplosionEffect.ts
├── plugins/
│ ├── index.ts
│ ├── types.ts
│ ├── viewerGridMixin.ts # mixin → viewerXxxMixin
│ └── viewerCameraMixin.ts
├── materials/
│ ├── index.ts
│ ├── types.ts
│ ├── Material.ts
│ ├── PulseConeMaterialProperty.ts
│ └── Shaders/
│ └── PulseCone.glsl
├── layers/
│ ├── index.ts
│ ├── types.ts
│ └── LayerManager.ts
├── tools/
│ ├── index.ts
│ ├── types.ts
│ └── coordinateUtils.ts # 工具函数 → camelCase
└── utils/
├── index.ts
├── types.ts
└── fboUtils.ts代码命名
TypeScript / JavaScript
| 类型 | 命名方式 | 示例 |
|---|---|---|
| 类 | PascalCase | CesiumViewer、LayerManager |
| 接口 | PascalCase | XxxOptions、ViewerMixinOptions |
| 类型别名 | PascalCase | EntityId、LayerType |
| 函数 | camelCase | addEntity()、flyToPosition() |
| 变量 | camelCase | currentLayer、isVisible |
| 常量 | UPPER_SNAKE_CASE | VERSION、DEFAULT_RADIUS |
| 私有成员 | _ 前缀 camelCase | _enabled、_viewer |
| 枚举 | PascalCase | EntityType |
| 泛型参数 | 单字母大写 T / 描述性 | T、TEntity |
Vue 组件内
vue
<script setup lang="ts">
// Props 类型:组件名 + Props
interface BaseMapPanelProps {
embedded?: boolean
}
// Emits 类型:组件名 + Emits
interface BaseMapPanelEmits {
close: []
select: [id: string]
}
// composable: use + 功能名
const { basemaps, addBaseMap } = useBaseMap()
// 事件处理: on + 动作
function onQuickSwitch(id: string) { ... }
</script>
<template>
<!-- CSS module class: $style.camelCase -->
<div :class="$style.panel">
<div :class="$style.quickSwitch">...</div>
</div>
</template>
<style module>
.panel { }
.quickSwitch { }
</style>CSS / CSS Modules
| 类型 | 命名方式 | 示例 |
|---|---|---|
| CSS Module class | camelCase | .panel、.switchTrigger、.switchArrowOpen |
| 修饰符 class | 语义化后缀 | .switchArrowOpen(open 状态) |
| Naive UI 主题变量覆盖 | 保持 NUI 原有命名 | --n-color、--n-border-radius |
包命名
| 层级 | 命名规则 | 示例 |
|---|---|---|
| packages/ | @nexa/<kebab-case> | @nexa/gis-cesium、@nexa/scenario-data |
| apps/ | @nexa/<kebab-case> | @nexa/earth-viewer |
| products/ | 简短语义名(不发 npm) | tactics-sim-engine |
| projects/ | 简短语义名(不发 npm) | demo |
示例命名
放在 src/examples/templates/<PascalCase>/ 下:
examples/templates/
├── HelloWord/ # 基础示例
├── DrawManager/ # 功能示例
├── HeatmapLayer/ # 图层示例
├── RadarSensing/ # 传感器示例
└── PulseConeMaterial/ # 材质示例每个示例的 key 字段使用 camelCase:'helloWord'、'drawManager'。