跳到主要内容

元素

元素是用户界面中的矩形。图像、文本和组都由带 Element 组件的实体表示,相对父元素布局;直接位于屏幕下时,则相对屏幕布局。本页介绍共同布局规则,绘制内容详见图像元素和文本元素。

元素类型​

type 决定元素绘制什么:

类型绘制内容用途
Group(pc.ELEMENTTYPE_GROUP)不绘制容器、布局组和不可见输入区,详见组元素
Image(pc.ELEMENTTYPE_IMAGE)纯色、纹理或精灵面板、图标、按钮和遮罩,详见图像元素
Text(pc.ELEMENTTYPE_TEXT)使用字体资源的字符串标签和其他文本,详见文本元素

锚点​

锚点指定元素附着在父项何处,以父项宽高的比例表示,从左下角 0, 0 到右上角 1, 1,共有四个数字,依次为左、下、右、上边界。左右相等且上下相等时,锚点是单个点;元素保留自身宽高,其位置是相对此点的偏移。锚定角落后,无论父项尺寸如何变化,元素都会保持在该角落。

面板中的九个矩形分别位于四角、四边中点和中央,菱形标记各自锚点

编辑器 Preset 提供常用组合。除 Stretch 外,各预设有两种形式:Anchor 仅设置锚点,Anchor & Pivot 还将轴心移至相同位置,使元素位于角落或边缘内侧,而不是中心压在边界上:

预设锚点轴心
Top Left Anchor & Pivot(左上)0, 1, 0, 10, 1
Top Anchor & Pivot(顶部)0.5, 1, 0.5, 10.5, 1
Top Right Anchor & Pivot(右上)1, 1, 1, 11, 1
Left Anchor & Pivot(左侧)0, 0.5, 0, 0.50, 0.5
Center Anchor & Pivot(中央)0.5, 0.5, 0.5, 0.50.5, 0.5
Right Anchor & Pivot(右侧)1, 0.5, 1, 0.51, 0.5
Bottom Left Anchor & Pivot(左下)0, 0, 0, 00, 0
Bottom Anchor & Pivot(底部)0.5, 0, 0.5, 00.5, 0
Bottom Right Anchor & Pivot(右下)1, 0, 1, 01, 0
Stretch(拉伸)0, 0, 1, 1不变,同时将边距设为 0

例如,下列分数位于屏幕右上角,距两条边各 20 个单位:

const score = new pc.Entity('score');
score.addComponent('element', {
type: pc.ELEMENTTYPE_TEXT,
fontAsset: font.id,
text: '1250',
anchor: [1, 1, 1, 1],
pivot: [1, 1]
});
score.setLocalPosition(-20, -20, 0);
screen.addChild(score);

无论从代码、React 还是 Web Components 创建元素,不指定锚点和轴心时,默认分别为 0, 0, 0, 0 与 0, 0,即父项左下角。创建时应显式设置两者。

轴心​

轴心是元素自身被放到其位置上的参照点,以自身宽高比例表示:0, 0 为左下角,0.5, 0.5 为中心,1, 1 为右上角。锚点和轴心都居中时,元素位于父项中央;锚点居中而轴心为 0, 0 时,元素左下角位于父项中央。

轴心也是旋转和缩放的中心:

同一矩形分别绕左下角、中心和右上角轴心旋转 20 度

// Spin an icon about its center
icon.element.pivot = new pc.Vec2(0.5, 0.5);
icon.setLocalEulerAngles(0, 0, 20);

分离锚点​

某轴上的两个锚点边界不相等时,该轴的锚点处于分离状态。元素两侧分别附着父项的不同位置,随父项在该轴上拉伸。这一轴的宽度或高度由锚点和边距确定,width 或 height 值会被忽略。

例如,横跨屏幕顶部的条可使用水平分离锚点,同时保持固定高度:

// Attach the bar's left and right edges to the left and right of its parent, at the top
bar.element.anchor = new pc.Vec4(0, 1, 1, 1);
bar.element.pivot = new pc.Vec2(0.5, 1);
bar.element.left = 0;
bar.element.right = 0;
bar.element.height = 80;

修改锚点会保留当前边距,因此新分离的轴也应设置边距,就像示例中的 left 和 right。创建分离锚点元素时同样如此:若不指定 margin,会保留默认 32 × 32 尺寸对应的 0, 0, -32, -32,使右边和上边各超出锚点 32 个单位。

宽窄父项中的面板和顶部横条,面板保留四周边距,两者均跟随父项宽度

边距​

边距表示锚点分离的轴上,元素各边到锚点的距离,依次为左、下、右、上;正值使边缘向内收缩。要让面板填满父项并保留 20 单位边框,使用 Stretch 锚点 0, 0, 1, 1,四边边距均为 20:

const background = new pc.Entity('background');
background.addComponent('element', {
type: pc.ELEMENTTYPE_IMAGE,
anchor: [0, 0, 1, 1],
margin: [20, 20, 20, 20],
color: new pc.Color(0.16, 0.18, 0.23)
});
panel.addChild(background);

left、bottom、right 和 top 可分别读写四个边距。要通过代码一次设置全部边距,请赋予新的 pc.Vec4,因为 margin setter 会从该向量复制值:

background.element.left = 40;
background.element.margin = new pc.Vec4(10, 10, 10, 10);
锚点

宽度与高度​

元素有两组尺寸:

  • width 和 height:设置的屏幕单位尺寸,适用于锚点为单点的轴。
  • calculatedWidth 和 calculatedHeight:实际尺寸。锚点分离或由布局组调整尺寸时,可能与设置值不同。

文本元素还可根据文本自动设置自身尺寸。需要实际显示尺寸时应读取计算值,例如让背景适应标签:

background.element.width = label.element.calculatedWidth + 40;

在编辑器中调整尺寸​

选中元素,选择工具栏中的 Resize Element Component,或按 4,再拖动视口角点手柄调整宽高,另一角保持不动。选中屏幕上的元素时,锚点角落还会显示灰色手柄,拖动可修改锚点。

视口将二维屏幕显示为三维场景中的平面矩形,切换摄像机为 Front 可正面观察。

组元素​

组元素不绘制内容,但和其他元素一样具有位置与尺寸,因此适合组织界面:

  • 容器。 将面板、菜单或 HUD 的各部分放到组下,可统一移动、调整尺寸、显示或隐藏。禁用组实体会隐藏全部子项。
  • 布局。 布局组通常就是负责排列子项的组元素。
  • 不可见输入区域。 启用输入的组会在整个矩形内接收输入,因此滚动视图的内容可从空白处拖动。

元素颜色和不透明度只作用于自身,不向子项传递。因此要淡出面板,需要同时淡出其下所有图像和文本,详见常用控件。

旋转、缩放与深度​

元素通过实体的 setLocalEulerAngles 和 setLocalScale 绕轴心旋转和缩放,如前面的轴心示例。绕 Z 轴旋转可让元素保持在屏幕平面内。

屏幕空间中,Z 位置不影响显示顺序,由层级决定上下关系,详见绘制顺序与性能。世界空间屏幕中,Z 位置会让元素离开屏幕平面。

读取元素边界​

以下三个属性提供四个角点,顺序为左下、右下、右上、左上:

属性坐标空间用途
screenCorners绘制缓冲区像素,以画布左下角为原点,适用于屏幕空间元素比较元素之间或其他绘制缓冲坐标之间的位置
canvasCornersCSS 像素,以画布左上角为原点,适用于屏幕空间元素将 HTML 放到元素上方,或与鼠标位置比较
worldCorners世界空间,适用于世界空间屏幕元素或没有屏幕祖先的元素将三维对象放在元素处,或对其进行射线检测

没有屏幕的元素​

元素并非必须位于屏幕下。没有屏幕祖先时,它像普通实体一样由变换定位,宽高采用世界单位,因此 32 × 32 元素宽达 32 米。锚点不会移动它,但分离锚点仍可根据父元素设置尺寸:在 100 × 100 父项中,锚点 0, 0, 1, 1 得到 100 × 100,0, 0, 0.5, 0.5 得到 50 × 50。单个元素适合世界中的独立标签或图像;需要带布局面板或菜单等复杂结构时,请使用世界空间屏幕。

另请参阅​