互动
¥Interaction
PixiJS 主要是一个渲染系统,但它也包括对交互性的支持。向你的项目添加对鼠标和触摸事件的支持既简单又一致。
¥PixiJS is primarily a rendering system, but it also includes support for interactivity. Adding support for mouse and touch events to your project is simple and consistent.
事件模式
¥Event Modes
在 v7 之前,交互由 Interaction
包及其 InteractionManager
定义和管理。然而,从 v7 开始,一个新的基于事件的系统取代了之前的 Interaction
包,并扩展了 Container
交互的定义。
¥Prior to v7, interaction was defined and managed by the Interaction
package and its InteractionManager
.
Beginning with v7, however, a new event-based system has replaced the previous Interaction
package, and
expanded the definition of what it means for a Container
to be interactive.
为此,我们引入了 eventMode
,它允许你控制对象如何响应交互事件。如果你熟悉以前的 Interaction
系统,eventMode
与 interactive
属性类似,但具有更多选项。
¥With this, we have introduced eventMode
which allows you to control how an object responds to interaction events.
If you're familiar with the former Interaction
system, the eventMode
is similar to the interactive
property, but with more options.
eventMode | 描述 |
---|---|
none | 忽略所有交互事件,类似于 CSS 的 pointer-events: none 。对非交互式子项进行良好的优化。 |
passive | 所有容器的默认 eventMode 。不触发事件并忽略自身的命中测试,但允许在其交互式子项上进行事件和命中测试。 |
auto | 不触发事件,但如果父级是交互式的,则进行命中测试。与 v7 中的 interactive = false 相同。 |
static | 触发事件并进行命中测试。与 v7 中的 interaction = true 相同。适用于不移动的按钮等对象。 |
dynamic | 触发事件并进行命中测试,但也会接收从计时器触发的模拟交互事件,以便在鼠标不移动时进行交互。适用于独立移动或动画的元素。 |
事件类型
¥Event Types
PixiJS 支持以下事件类型:
¥PixiJS supports the following event types:
事件类型 | 描述 |
---|---|
pointercancel | 当指针设备按钮在最初注册向下指针的显示对象外部释放时触发。 |
pointerdown | 当在显示对象上按下指针设备按钮时触发。 |
pointerenter | 当指针设备进入显示对象时触发。 |
pointerleave | 当指针设备离开显示对象时触发。 |
pointermove | 当指针设备在显示对象上移动时触发。 |
globalpointermove | 当指针设备移动时触发,无论是否对当前对象进行命中测试。 |
pointerout | 当指针设备移离显示对象时触发。 |
pointerover | 当指针设备移动到显示对象上时触发。 |
pointertap | 当指针设备点击显示对象时触发。 |
pointerup | 当在显示对象上释放指针设备按钮时触发。 |
pointerupoutside | 当指针设备按钮在最初注册向下指针的显示对象外部释放时触发。 |
mousedown | 当在显示对象上按下鼠标按钮时触发。 |
mouseenter | 当鼠标光标进入显示对象时触发。 |
mouseleave | 当鼠标光标离开显示对象时触发。 |
mousemove | 当鼠标光标在显示对象上移动时触发。 |
globalmousemove | 当鼠标移动时触发,无论是否对当前对象进行命中测试。 |
mouseout | 当鼠标光标移离显示对象时触发。 |
mouseover | 当鼠标光标移动到显示对象上时触发。 |
mouseup | 当在显示对象上释放鼠标按钮时触发。 |
mouseupoutside | 当鼠标按钮在最初注册 mousedown 的显示对象之外释放时触发。 |
click | 当在显示对象上单击(按下并释放)鼠标按钮时触发。 |
touchcancel | 当触摸点被移出最初注册触摸启动的显示对象之外时触发。 |
touchend | 当触摸点从显示对象中移除时触发。 |
touchendoutside | 当触摸点被移出最初注册触摸启动的显示对象之外时触发。 |
touchmove | 当触摸点沿着显示对象移动时触发。 |
globaltouchmove | 当触摸点移动时触发,无论是否对当前对象进行命中测试。 |
touchstart | 当触摸点放置在显示对象上时触发。 |
tap | 当触摸点点击显示对象时触发。 |
wheel | 当鼠标滚轮在显示对象上旋转时触发。 |
rightclick | 当在显示对象上单击(按下并释放)鼠标右键时触发。 |
rightdown | 在显示对象上按下鼠标右键时触发。 |
rightup | 当在显示对象上释放鼠标右键时触发。 |
rightupoutside | 当在最初注册 rightdown 的显示对象之外释放鼠标右键时触发。 |
实现互动
¥Enabling Interaction
任何 Container
派生对象(Sprite
、Container
等)都可以通过将其 eventMode
属性设置为上面列出的任何事件模式来实现交互。这样做将导致对象触发可以响应的交互事件,以驱动项目的行为。
¥Any Container
-derived object (Sprite
, Container
, etc.) can become interactive simply by setting its eventMode
property to any of the eventModes listed above. Doing so will cause the object to emit interaction events that can be responded to in order to drive your project's behavior.
看看 点击交互示例代码。
¥Check out the click interactivity example code.
要响应单击和点击,请绑定到在对象上触发的事件,如下所示:
¥To respond to clicks and taps, bind to the events fired on the object, like so:
let sprite = Sprite.from('/some/texture.png');
sprite.on('pointerdown', (event) => { alert('clicked!'); });
sprite.eventMode = 'static';
查看 容器 以获取支持的交互事件列表。
¥Check out the Container for the list of interaction events supported.
检查对象是否可交互
¥Checking if an Object is Interactive
你可以通过调用 isInteractive
属性来检查对象是否是交互式的。如果 eventMode
设置为 static
或 dynamic
,则返回 true。
¥You can check if an object is interactive by calling the isInteractive
property. This will return true if eventMode
is set to static
or dynamic
.
if (sprite.isInteractive()) {
// sprite is interactive
}
使用指针事件
¥Use Pointer Events
PixiJS 支持三种类型的交互事件:鼠标、触摸和指针。
¥PixiJS supports three types of interaction events: mouse, touch, and pointer.
鼠标事件由鼠标移动、点击等触发。
¥Mouse events are fired by mouse movement, clicks etc.
为支持触摸的设备触发触摸事件。并且,
¥Touch events are fired for touch-capable devices. And,
两者都会触发指针事件。
¥Pointer events are fired for both.
这意味着,在许多情况下,你可以编写项目来使用指针事件,并且它在与鼠标或触摸输入一起使用时才可以工作。
¥What this means is that, in many cases, you can write your project to use pointer events and it will just work when used with either mouse or touch input.
鉴于此,使用非指针事件的唯一原因是支持基于输入类型的不同操作模式或支持多点触摸交互。在所有其他情况下,更喜欢指针事件。
¥Given that, the only reason to use non-pointer events is to support different modes of operation based on input type or to support multi-touch interaction. In all other cases, prefer pointer events.
优化
¥Optimization
命中测试需要遍历完整的对象树,这在复杂的项目中可能成为优化瓶颈。
¥Hit testing requires walking the full object tree, which in complex projects can become an optimization bottleneck.
为了缓解此问题,PixiJS Container
派生对象具有一个名为 interactiveChildren
的属性。如果你有 Container
或其他具有复杂子树的对象,并且你知道这些对象永远不会交互,则可以将此属性设置为 false
,命中测试算法将在检查悬停和单击事件时跳过这些子对象。
¥To mitigate this issue, PixiJS Container
-derived objects have a property named interactiveChildren
. If you have Container
s or other objects with complex child trees that you know will never be interactive,
you can set this property to false
, and the hit-testing algorithm will skip those children when checking for hover and click events.
例如,如果你正在构建横向卷轴游戏,你可能希望将 background.interactiveChildren = false
设置为背景层,其中包含岩石、云、花朵等。这样做会大大加快命中测试速度,因为背景层将包含大量不可点击的子对象。
¥As an example, if you were building a side-scrolling game, you would probably want to set background.interactiveChildren = false
for your background layer with rocks, clouds, flowers, etc. Doing so would substantially speed up hit-testing due to the number of unclickable child objects the background layer would contain.
EventSystem
还可以进行定制以提高性能:
¥The EventSystem
can also be customised to be more performant:
const app = new Application({
eventMode: 'passive',
eventFeatures: {
move: true,
/** disables the global move events which can be very expensive in large scenes */
globalMove: false,
click: true,
wheel: true,
}
});