跳转到内容

UI 构建器

UI 构建器提供代码优先的方式创建 UI 层级。无需手动创建实体和插入组件,使用工厂方法自动完成所有连接。

工厂方法

每个方法创建一个完整配置的 UI 实体并返回其 Entity ID:

import { UI } from 'esengine';
const btn = UI.button(world, { text: 'Play', parent: rootEntity });
const slider = UI.slider(world, { value: 0.5, parent: rootEntity });
const label = UI.label(world, { text: 'Score: 0', parent: rootEntity });

可用工厂

方法说明
UI.label(world, options)文本标签
UI.panel(world, options)带背景色的容器
UI.button(world, options)可点击按钮
UI.slider(world, options)带填充和手柄的值滑块
UI.toggle(world, options)复选框/开关
UI.progressBar(world, options)非交互式进度条
UI.textInput(world, options)可编辑文本框
UI.dropdown(world, options)下拉选择器
UI.scrollView(world, options)可滚动容器
UI.flexRow(world, options)水平 Flex 布局容器
UI.flexColumn(world, options)垂直 Flex 布局容器

控件选项

所有选项除特别标注外均为可选,默认值来自当前主题。

ButtonOptions

UI.button(world, {
text: 'Click Me', // 默认: 'Button'
fontSize: 16, // 默认: theme.fontSize.md
size: { x: 150, y: 40 }, // 默认: { x: 120, y: 36 }
color: { r: 0.2, g: 0.5, b: 0.9, a: 1 },
textColor: { r: 1, g: 1, b: 1, a: 1 },
transition: null, // ColorTransition 或 null
parent: rootEntity,
events: uiEvents, // onClick/onHover 需要此参数
onClick: (entity) => console.log('Clicked!'),
});

SliderOptions

UI.slider(world, {
value: 0.5,
minValue: 0,
maxValue: 1,
wholeNumbers: false,
size: { x: 200, y: 16 },
trackColor: { r: 0.15, g: 0.15, b: 0.15, a: 1 },
fillColor: { r: 0.25, g: 0.56, b: 0.96, a: 1 },
handleSize: { x: 24, y: 24 },
handleColor: { r: 1, g: 1, b: 1, a: 1 },
parent: rootEntity,
events: uiEvents, // onChange 需要此参数
onChange: (value, entity) => console.log('Value:', value),
});

ToggleOptions

UI.toggle(world, {
isOn: true,
size: { x: 24, y: 24 },
onColor: { r: 0.2, g: 0.6, b: 1, a: 1 },
offColor: { r: 0.4, g: 0.4, b: 0.4, a: 1 },
label: 'Enable sound', // 可选文本标签
group: toggleGroupEntity, // 用于单选按钮行为
parent: rootEntity,
events: uiEvents,
onChange: (isOn, entity) => console.log('Toggle:', isOn),
});

TextInputOptions

UI.textInput(world, {
placeholder: 'Enter name...',
value: '',
size: { x: 200, y: 36 },
fontSize: 16,
maxLength: 0, // 0 = 无限
multiline: false,
password: false,
parent: rootEntity,
events: uiEvents,
onChange: (value, entity) => console.log('Text:', value),
onSubmit: (value, entity) => console.log('Submit:', value),
});
UI.dropdown(world, {
options: ['Easy', 'Normal', 'Hard'], // 必填
selectedIndex: 1,
size: { x: 160, y: 32 },
parent: rootEntity,
events: uiEvents,
onChange: (index, entity) => console.log('Selected:', index),
});

FlexOptions

UI.flexRow(world, {
gap: 8,
padding: { left: 12, top: 12, right: 12, bottom: 12 },
wrap: false,
justifyContent: 'center',
alignItems: 'stretch',
parent: rootEntity,
});

声明式树构建

对于复杂 UI,使用 UI.build() 从嵌套定义创建整个层级:

import { UI } from 'esengine';
let nameInput: Entity;
const form = UI.build(world, {
type: 'panel',
options: { size: { x: 400, y: 300 } },
children: [
{
type: 'label',
options: { text: 'Player Setup', fontSize: 20 },
},
{
type: 'textInput',
options: { placeholder: 'Enter name' },
ref: (entity) => { nameInput = entity; },
},
{
type: 'flexRow',
options: { gap: 8 },
children: [
{
type: 'button',
options: { text: 'Cancel' },
},
{
type: 'button',
options: { text: 'Start', onClick: () => startGame() },
},
],
},
],
});

节点类型

类型子节点说明
element原始 UI 实体,手动配置组件
label文本标签
button按钮控件
slider滑块控件
toggle开关控件
textInput文本输入
dropdown下拉选择
progressBar进度条
panel带背景的容器
flexRow水平 Flex 容器
flexColumn垂直 Flex 容器
scrollView可滚动容器(子节点自动挂载到 content 实体)

实体引用

使用 ref 捕获创建的实体:

let sliderRef: Entity;
UI.build(world, {
type: 'slider',
options: { value: 0.5 },
ref: (entity) => { sliderRef = entity; },
});

主题

所有控件使用当前 UITheme 的默认颜色、尺寸和字体。内置 DARK_THEME 为默认主题。

自定义主题

在初始化前插入 UIThemeRes 覆盖主题:

import { UIThemeRes, DARK_THEME } from 'esengine';
const myTheme = {
...DARK_THEME,
primary: { r: 0.9, g: 0.3, b: 0.1, a: 1 },
button: {
...DARK_THEME.button,
color: { r: 0.9, g: 0.3, b: 0.1, a: 1 },
},
};
cmds.insertResource(UIThemeRes, myTheme);

UITheme 属性

分组属性
颜色primary, secondary, background, surface, error, text, textSecondary, border
排版fontFamily, fontSizexs, sm, md, lg, xl
间距spacingxs, sm, md, lg, xl
按钮height, color, textColor, transition
滑块trackHeight, trackColor, fillColor, handleSize, handleColor
开关size, onColor, offColor, checkColor
输入框height, backgroundColor, textColor, placeholderColor, fontSize, padding
下拉框height, backgroundColor, itemHeight
面板backgroundColor, padding

清理

移除 UI 实体及其所有子实体:

UI.destroy(world, formEntity);

下一步