Skip to content

Commit 19d2bda

Browse files
Update index.md
1 parent 5bf689f commit 19d2bda

File tree

1 file changed

+9
-46
lines changed

1 file changed

+9
-46
lines changed

blog/posts/rfc2/index.md

+9-46
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@ tags: ['RFC']
1111

1212
第三次提交版本,2024年1月31日,更新了有关应用 CSS IN JS 实现样式替换的方案。
1313

14+
第四次提交版本,2024年2月16日,更新了有关 `applyStyle` 指令如何运转的描述和热替换的新方案。
15+
1416
## 总体方案
1517

1618
WebGAL 将使用模板思想进行 UI 自定义。在 WebGAL Terre 编辑器中,额外添加一个模板编辑器。在创建 WebGAL 游戏时和创建 WebGAL 游戏后,可以选择要使用的模板。
@@ -123,48 +125,22 @@ applyStyle:Title_button->Title_button_2, Dialog->Dialog_1;
123125

124126
首先,在初始化模板时,WebGAL 维护一个从原始的模板中类名到要应用的类名的映射:
125127

126-
```
127-
const styleMap = new Map<string,{targetClass:string, currentApplyClass:string}>();
128+
```ts
129+
type replacedUIlable = Record<string, string>
128130
```
129131
130-
`targetClass` 代表在 `applyStyle` 时注册的某个组件的标识符,比如 `Title_button``currentApplyClass` 代表目前应用的类名,在初始化时与标识符保持一致,但是可以被 `applyStyle` 指令切换
132+
`` 代表在 `applyStyle` 时注册的某个组件的标识符,比如 `Title_button``` 代表目前应用的类名, `applyStyle` 指令写入
131133
132-
在注册时,就订阅类名切换的事件。如果某个插入的 css 段中的类名发生了“切换类名”,那么这个事件就会发出。指令会重新注册 `currentApplyClass`,然后重新在获取到的样式文件中寻找指定的类名,然后使用 CSS IN JS 框架应用。
134+
如果 `applyStyle` 指令被执行,指令会写 `replacedUIlable`,更新状态,然后被 CSS IN JS 框架应用。
133135
134-
比如,原有的 `styleMap` 中有一个实体 `"Title_button"->{targetClass:"Title_button", currentApplyClass:"Title_button"}`
136+
比如,原有的 `replacedUIlable` 中有一个实体 `"Title_button"->"Title_button"`
135137
136138
运行了指令`applyStyle:Title_button->Title_button_2;`
137139
138-
此时更新 Map,注册为 `Title_button"->{targetClass:"Title_button", currentApplyClass:"Title_button_2"}`
140+
此时更新为 `Title_button"->"Title_button_2"`
139141

140142
这时候,要替换到标识符被注册为`Title_button` 的类名就变为 `Title_button_2`,原有的 `Title_button` 不再生效。
141143

142-
由此可见,切换类名的脚本要发出事件
143-
144-
```
145-
// ... 其他逻辑
146-
eventBus.emit('classname-change',类名)
147-
```
148-
149-
`useApplyStyle` 要接受事件并判断是否要重新替换 CSS:
150-
151-
```ts
152-
const useApplyStyle = (url:string) => {
153-
useEffect(()=>{
154-
const applyStyle = ()=>{
155-
// ...... 其他代码
156-
}
157-
eventBus.on('classname-change',className=>{
158-
const isHotReplace = Object.keys(classNameMap).findIndex(e === className) > -1;
159-
if(isHotReplace) applyStyle();
160-
})
161-
return ()=>{
162-
eventBus.off(......)
163-
}
164-
},[])
165-
}
166-
```
167-
168144
### 引用资源
169145

170146
如果一个模板要引用资源,必须引用在模板资源目录下的资源。
@@ -241,20 +217,7 @@ registerStyleEditor('UI/Title/title.scss', "Title_button", t("标题按钮")) //
241217

242218
为了在编辑的流程中优化编辑体验,要实现热替换特性。
243219

244-
还记得我们定义的 `useApplyStyle` 吗?在这个函数中,我们在全局注册一个文件路径到指定的 `style` 块的映射,比如
245-
246-
```ts
247-
const useApplyStyle = (url:string) => {
248-
useEffect(()=>{
249-
const applyStyle = ()=>{
250-
// ...... 其他代码
251-
}
252-
register(url, applyStyle);// 注册回调函数,当编辑器后端通知时,重新跑一遍 applyStyle
253-
},[])
254-
}
255-
```
256-
257-
这样,当我们的编辑器后端向引擎发送一个 WebSocket 消息时,就可以让引擎重新请求对应的 scss 文件,然后删除之前动态添加的 style 标签,重新转换 css ,然后动态添加标签。
220+
编辑器只需要向引擎发送一个消息,让引擎去重新请求所有的样式文件就可以了。由于编辑器大多数情况下在本地运行,所以网络请求的延迟可以忽略不计。
258221

259222
## 双模编辑
260223

0 commit comments

Comments
 (0)