游戏手柄输入

GameMaker具有许多专用函数,可用于检测来自多个连接的游戏手柄的模拟和数字控件。这些函数的工作原理类似于设备输入,因为您可以检测到多达四个不同的XInput游戏垫连接 (最多8个DirectInput游戏手柄),并使用相同的函数处理每个输入。请注意,将游戏手柄插入设备 (或将其删除) 后,将触发异步系统事件,您可以在其中使用适当的函数处理情况。

游戏手柄 “插槽” 是从 0 向上索引的,而游戏手柄分配的实际插槽将取决于多种因素,尤其是运行项目的操作系统。在Windows目标上,包括 0-3 在内的插槽仅适用于 Xinput 游戏手柄,即:Xbox360 控制器和兼容产品。但是,您也可以查看DirectInput游戏手柄的插槽 4-11(含),这意味着通过这些插槽连接时,您可以检测到许多其他型号的控制器。在其他平台上,可以在操作系统分配的任何插槽上检测到 pad,这些插槽可能是插槽 3 或插槽 20 或更多。例如,Android设备会将蓝牙游戏手柄存储在插槽中,然后在将来为该游戏手柄保留该插槽,无论它是否连接,因此不能假设单个连接的游戏手柄已连接到插槽 0,因为事实可能并非如此。

值得注意的是,当在Windows上使用DirectInput游戏手柄或在其他平台上使用通用游戏手柄时,下面给出的常量可能与您在按下按钮时所期望的完全匹配,这是由于控制器制造商实现API的零散和非标准化方式。因此,建议您在游戏中有某种游戏手柄设置屏幕,人们可以根据来自任何连接设备的输入重新定义游戏手柄按钮,以缓解任何问题 (有游戏手柄 “映射” 函数可以帮助在Windows桌面,Ubuntu,macOS,和Android的目标,而在所有其他的,你将需要做到这一点自己使用代码)。

输入常数

使用游戏手柄函数时,输入可以来自axesbuttonshatsGameMaker会将其分配给以下内置常量(注意 “十字键” 通常只能在非标准控制器上检测到):

游戏手柄按钮常数
常量描述
gp_face1Top button 1 (this maps to the "A" on an Xbox controller and the cross on a PS controller)
gp_face2Top button 2 (this maps to the "B" on an Xbox controller and the circle on a PS controller)
gp_face3Top button 3 (this maps to the "X" on an Xbox controller and the square on a PS controller)
gp_face4Top button 4 (this maps to the "Y" on an Xbox controller and the triangle on a PS controller)
gp_shoulderlLeft shoulder button
gp_shoulderlbLeft shoulder trigger
gp_shoulderrRight shoulder button
gp_shoulderrbRight shoulder trigger
gp_selectThe select button (on a PS controller, this triggers when you press the touchpad down)
gp_startThe start button (this is the "options" button on a PS controller)
gp_sticklThe left stick pressed (as a button)
gp_stickrThe right stick pressed (as a button)
gp_paduD-pad up
gp_paddD-pad down
gp_padlD-pad left
gp_padrD-pad right
gp_homeThe "home" button on Switch controllers, and the PS/XBOX logo buttons on some controllers
gp_touchpadbuttonThe touchpad button on a PS controller
gp_paddlerUpper or primary paddle, under your right hand (e.g. Xbox Elite paddle P1)
gp_paddlelUpper or primary paddle, under your left hand (e.g. Xbox Elite paddle P3)
gp_paddlerbLower or secondary paddle, under your right hand (e.g. Xbox Elite paddle P2)
gp_paddlelbLower or secondary paddle, under your left hand (e.g. Xbox Elite paddle P4)
gp_extra1An extra button that may be mapped to anything
gp_extra2An extra button that may be mapped to anything
gp_extra3An extra button that may be mapped to anything
gp_extra4An extra button that may be mapped to anything
gp_extra5An extra button that may be mapped to anything
gp_extra6An extra button that may be mapped to anything
游戏手柄轴常数
常量描述
gp_axislhLeft stick horizontal axis (analog)
gp_axislvLeft stick vertical axis (analog)
gp_axisrhRight stick horizontal axis (analog)
gp_axisrvRight stick vertical axis (analog)
以下常量只能与 PS4 或 PS5 上的 DualSense 游戏手柄一起使用
gp_axis_acceleration_x*The gamepad's acceleration on the X axis
gp_axis_acceleration_y*The gamepad's acceleration on the Y axis
gp_axis_acceleration_z*The gamepad's acceleration on the Z axis
gp_axis_angular_velocity_x*The gamepad's angular velocity on the X axis
gp_axis_angular_velocity_y*The gamepad's angular velocity on the Y axis
gp_axis_angular_velocity_z*The gamepad's angular velocity on the Z axis
gp_axis_orientation_x*The gamepad's X orientation
gp_axis_orientation_y*The gamepad's Y orientation
gp_axis_orientation_z*The gamepad's Z orientation
gp_axis_orientation_w*The gamepad's W orientation

注意游戏手柄的方向是一个四元数,这就是为什么它有四个值(X,y,Z和w)。

*这些常量仅在PS4和PS5上受支持,在其他平台上使用时,输入函数将返回0,即使使用DualSense游戏手柄也是如此。

为了更好地了解每个常量代表控制器的哪一部分,您可以参考标准XInput游戏手柄的以下图像:

Xinput gamepad illustration

函数

下面,您可以找到所有gamepad函数的列表:

 

以下游戏板函数也存在,并且用于将内置常数重新映射到给定游戏手柄的直接物理输入。这些函数仅适用于 Windows 桌面、Ubuntu、macOS 和 Android 目标平台,在 Windows 上仅对直接输入设备有效。GameMaker提供基于SDL Gamepad Controller DB的多种不同游戏手柄的映射,但由于控制器类型和品牌数量巨大,无法将 GML 常量映射到每个品牌和型号的正确输入,因此使用这些函数,您可以创建自己的自定义映射。

 

值得注意的是,直接输入游戏手柄以合作模式运行,这意味着您的游戏只有在前台应用程序时才能访问它们,反过来,如果游戏失去焦点,则会导致直接输入控制器 “丢失”,然后在重新聚焦时再次 “找到” (这可以在系统事件中检测到并处理)。同样,当游戏不在焦点中时,不会检测到来自游戏手柄的输入,并且我们建议您使用函数os_is_pauzed()window_has_focus()来检测到这一点,并暂停游戏或类似在游戏失去焦点时被按住的任何按钮将保持被按住的状态,直到游戏重新获得焦点。

兼容性

以下列表显示了当前跨平台的兼容性(请注意,这将随着以后的更新而改变):

理想情况下,在所有目标平台上,您要枚举可用的游戏手柄 “插槽” 列表,然后检查它们以查看是否检测到任何设备,如下:

var _maxpads = gamepad_get_device_count();

for (var i = 0; i < _maxpads; i++)
{
    if (gamepad_is_connected(i))
    {
        // do stuff with pad "i"
    }
}