开发适用于所有屏幕的游戏

开发 Android 版游戏时,务必要预测各种可能的玩家体验,并一直适应玩家的实时互动需求。通过支持不同的玩家体验,您可以提高游戏的灵活性,从而帮助您扩大游戏的用户群。

玩家体验的具体区别包括以下几点:

  • 设备类型:虽然手机提供了传统的 Android 设备体验,但可以在其他类型的设备上与游戏互动。ChromeOS 设备可以运行显示游戏的 Android 容器。可以运行 Android 系统的平板电脑支持几个不同级别的保真度。Android TV 设备支持细节更丰富且沉浸感更强的体验。玩家可以使用显示扩展工具来模拟多窗口环境。此外,在使用可折叠设备时,玩家可以在游戏过程中改变屏幕的尺寸。
  • 互动方法:玩家可以通过轻触设备的屏幕进行输入,还可以使用鼠标、触控板、键盘或控制器进行输入。此外,通过使用显示扩展工具和可折叠设备,玩家能够在更大的屏幕上体验游戏,从而实现更长的游戏会话和更复杂的界面。
  • 硬件支持:某些 Android 设备不具备手持设备中比较典型的硬件,如后置摄像头、GPS 和网络连接。游戏应适应可用的硬件并妥善处理某些功能不可用的情况。

本指南介绍了针对不同类型的屏幕和用户互动开发游戏的最佳做法。本指南还提供了有关设计游戏和制定有效测试策略的建议。

游戏设计最佳做法

在规划游戏的设计和架构时,请遵循下面几部分中所述的最佳做法。

手动响应配置更改

当 Android 系统检测到配置更改(如屏幕尺寸、屏幕方向或输入法的更改)时,默认情况下,系统会重新开始当前的 activity。为了保留应用或游戏中的状态,默认情况下,该 Activity 会在重新开始之前调用 onSaveInstanceState(),在重新开始之后调用 onRestoreInstanceState()。不过,此过程要求该 Activity 重新加载所有关联的服务和资源。如需详细了解这种默认行为,请参阅有关处理配置更改的指南

典型的游戏会话会经历几项配置更改。如果游戏让系统处理每项配置更改,那么游戏的场景就会被破坏并一遍又一遍地重新开始,降低了游戏的性能。因此,我们强烈建议您在游戏中自行处理这些配置更改。

如需了解如何将此配置更改逻辑添加到游戏中,请参阅有关如何创建自定义配置更改处理程序的部分

创建灵活的架构

如需在尽可能多的设备上添加对您游戏的支持,请遵循以下最佳做法:

  • 部署 Android App Bundle 而不是单独的 APK。Android App Bundle 使您能够将不同分辨率和不同架构模型(如 x86 和 ARM)的工件打包到单个工件中。更好的是,Android App Bundle 支持更高的游戏大小上限;每个基本 APK 的大小可以高达 150 MB,而软件包本身的大小可以为数 GB。
  • 添加对 x86 架构的支持。这种做法可提高游戏在不支持 ARM 的设备上的性能,因为此类设备现在可以执行指令,而不必先转换它们。

添加对 Vulkan 的支持

通过支持 Vulkan,游戏可以实现更高的图形性能。大多数设备都支持此图形 API。

创建自定义配置更改处理程序

如需声明游戏自行处理的配置更改类型,请向清单中表示屏幕或复杂界面的每个 <activity> 元素添加 android:configChanges 属性。

以下代码段演示了如何声明您的游戏会处理屏幕尺寸、屏幕方向和输入法更改:

<activity ...
    android:configChanges="screenSize|orientation|keyboard|keyboardHidden">
</activity>

当发生声明的配置更改时,系统现在会调用另一种方法,即 onConfigurationChanged()。请在此方法中添加用于更新游戏界面的逻辑:

处理屏幕配置更改

只要您在 android:configChanges 属性中分别添加 screenSizeorientation 值,您的游戏就会自行处理屏幕尺寸和屏幕方向更改。您可以使用这些新值更新场景的内容和玩家输入区域。如需了解如何设计游戏的布局以使其更容易更新,请参阅有关支持不同屏幕尺寸的指南

在游戏的 onConfigurationChanged() 实现中,分别使用传入的 Configuration 对象和窗口管理器的 Display 对象确定更新后的屏幕尺寸和屏幕方向值。

以下代码段展示了如何获取游戏更新后的屏幕尺寸和方向:

Kotlin

override fun onConfigurationChanged(newConfig: Configuration) {
    super.onConfigurationChanged(newConfig)
    val density: Float = resources.displayMetrics.density
    val newScreenWidthPixels = (newConfig.screenWidthDp * density).toInt()
    val newScreenHeightPixels = (newConfig.screenHeightDp * density).toInt()

    // Get general orientation; either Configuration.ORIENTATION_PORTRAIT or
    // Configuration.ORIENTATION_LANDSCAPE.
    val newScreenOrientation: Int = newConfig.orientation

    // Get general rotation; one of: ROTATION_0, ROTATION_90, ROTATION_180,
    // or ROTATION_270.
    val newScreenRotation: Int = windowManager.defaultDisplay.rotation
}

Java

@Override
public void onConfigurationChanged(Configuration newConfig) {
    super.onConfigurationChanged(newConfig);
    float density = getResources().getDisplayMetrics().density;
    int newScreenWidthPixels = (int) (newConfig.screenWidthDp * density);
    int newScreenHeightPixels = (int) (newConfig.screenHeightDp * density);

    // Get general orientation; either Configuration.ORIENTATION_PORTRAIT or
    // Configuration.ORIENTATION_LANDSCAPE.
    int newScreenOrientation = newConfig.orientation;

    // Get general rotation; one of: ROTATION_0, ROTATION_90, ROTATION_180,
    // or ROTATION_270.
    int newScreenRotation = getWindowManager().getDefaultDisplay()
            .getRotation();
}

请注意,更改可折叠设备的折叠状态会更改配置,即使应用在全屏模式下运行也是如此。因此,如果用户在游戏应用运行期间折叠或展开设备,则应用可能必须处理屏幕尺寸或像素密度的变化。

特定于游戏的屏幕质量

下面几部分介绍了如何根据游戏的质量来调整游戏对屏幕尺寸或屏幕方向变化的响应:

全屏模式

在某些平台(例如 ChromeOS)上,默认情况下,Android 应用和游戏可以窗口化并调整大小。如果您的游戏应始终在全屏模式下运行,您可以在某个 <activity> 元素中将 android:resizeableActivity 属性设为 false,如以下代码段所示:

<activity ...
    android:resizeableActivity="false">
</activity>

您还可以将 android:resizeableActivity 属性设为 false,以防止发生基于大小的配置更改。不过,除非您的游戏始终在全屏模式下运行,否则您应仅出于测试目的添加此属性作为临时修正措施。

屏幕方向

如果游戏需要设备的传感器朝向特定的方向,请在游戏的 activity 中指定 android:screenOrientation 的值,如以下代码段所示。此设置有助于防止游戏中的场景意外上下颠倒。

<activity ...
    android:screenOrientation="landscape">
</activity>

特定于设备的屏幕质量

下面几部分介绍了在某些设备具有特定质量的情况下如何处理基于屏幕的配置更改。

宽高比

某些设备支持不同的宽高比。例如,可折叠设备在处于折叠状态时支持 21:9 的宽高比。要处理这种潜在的宽高比变化,请至少执行以下一项操作:

  • 以 Android 8.0(API 级别 26)或更高版本为目标平台。
  • 使游戏的场景和界面可调整大小。在搭载 Android 7.0(API 级别 24)及更高版本的设备上,将 android:resizeableActivity 设为 true
  • 声明支持的最大宽高比。在与游戏关联的 <meta-data> 属性中,将 android.max_aspect 设为 2.4,如以下代码段所示。不过请注意,如果宽高比大于您指定的值,会导致游戏在显示屏中出现黑边

    <application>
    <meta-data android:name="android.max_aspect"
               android:value="2.4" />
    </application>
    

多个 Activity 同时可见

许多现代设备都支持多种屏幕布局,包括分屏、画中画和大显示区域。使用其中某种布局时,系统可使多个 Activity 同时可见。

在搭载 Android 9(API 级别 28)或更高版本的设备上,有可能同时恢复所有顶层的可见 Activity。不过,为使此行为正常发挥作用,游戏和设备 OEM 都需要选择使用相应的功能。您可以通过在游戏的清单中将 android.allow_multiple_resumed_activities 设为 true,在游戏中添加支持,如以下代码段所示:

<application>
    <meta-data android:name="android.allow_multiple_resumed_activities"
               android:value="true" />
</application>

然后,您可以在不同的设备上测试游戏,看看哪种设备提供了多项恢复功能正常运行所需的 OEM 支持。

如需详细了解如何配置游戏以使其显示为多窗口显示屏的一部分,请参阅有关如何添加多窗口支持的指南

处理不同类型的互动模式

只要您在 android:configChanges 属性中分别添加 keyboardkeyboardHidden 值,您的游戏就会自行处理键盘的出现情况和可用性。您可以使用这些新值更新游戏的主要输入法。

在配置游戏以支持多种类型的用户输入时,请注意以下几点:

  • 检测输入法而不是各个设备。这种思维模式使您能够更轻松地改善玩家体验,而不必过多地关注玩家可能使用的特定设备。
  • 在自行处理的配置更改列表中添加 keyboardHidden 属性。这样一来,游戏就可以跟踪键盘何时实际连接到了设备但无法使用。
  • 确定当前可用的输入法。为此,请在游戏启动时以及每次更改配置后调用 getInputDeviceIds()

    您通常可以根据玩家喜欢的输入设备确定他们打算如何与游戏进行互动:

    • 玩家通常使用键盘或游戏控制器执行快速的按钮操作。
    • 玩家通常使用触摸屏或触控板执行比较复杂的手势。
    • 玩家通常使用鼠标执行精度较高的输入。

下面几部分介绍了特定类型输入设备的最佳做法。

键盘

为游戏创建键盘布局时,应考虑玩家如何在给定场景中导航,以及他们如何与游戏的设置进行互动。

WASD 键或箭头键通常最适合控制角色运动。此外,最好为可控制的角色可以在游戏中执行的每个重要动作或技能分配一个特定的键。为了最大限度地提升玩家体验,不妨考虑在游戏中支持自定义快捷键组合键。

玩家还应该能够打开游戏菜单,并使用键盘进行浏览。Esc 键是暂停场景并显示游戏菜单的常见快捷键。

如需详细了解如何在游戏中支持键盘输入,请参阅有关如何支持键盘导航的指南以及有关如何处理键盘操作的指南

游戏控制器

如需详细了解如何在游戏中处理控制器输入,请参阅有关如何支持游戏控制器的指南

鼠标或触控板

如果您的游戏支持玩家通过鼠标或触控板输入,请注意,玩家与设备进行互动的方式不同于玩游戏。务必了解,通过请求指针捕获,所有鼠标输入都会定向到您的游戏。因此,在游戏获得所需的信息后,应释放指针捕获,以便玩家重新获得对设备的标准鼠标控制。

在搭载 Android 8.0(API 级别 26)及更高版本的设备上,您可以使用 Mouse Capture API 协助完成指针捕获过程。在对高精度输入做出反应的游戏中,您可以通过调用 getX()getY() 方法获取指针的当前坐标。

如需详细了解如何在游戏中添加对鼠标输入和触控板输入的支持,请参阅有关如何跟踪轻触和指针移动的指南以及有关如何处理多点触控手势的指南

测试游戏

在发布游戏之前,请完成下面几部分中所述的步骤,测试您的游戏如何响应配置更改。

更新测试计划

验证游戏的功能时,请包括以下测试用例:

  • 最小化和最大化游戏所在的窗口。(如果游戏始终在全屏模式下,则不适用。)
  • 更改屏幕尺寸。
  • 更改屏幕方向。(如果游戏的方向固定,则不适用。)
  • 连接和断开输入设备,如键盘和鼠标。
  • 执行多项恢复操作(如果游戏支持此功能)。

此外,不妨考虑更新游戏的质量控制系统,以便针对更广泛的玩家体验进行优化。

如需了解与测试游戏有关的最佳做法,请参阅《测试基础知识》指南

使用测试和调试工具

您可以使用平台支持的各种工具执行测试: