diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 79b7921a2..1dfdf52c5 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -111,6 +111,7 @@ jobs: force-avd-creation: false emulator-options: -no-snapshot-save -no-window -gpu swiftshader_indirect -noaudio -no-boot-anim -camera-back none disable-animations: true + enable-hw-keyboard: true working-directory: ./test-fixture/ channel: canary script: | diff --git a/README.md b/README.md index b56685562..29161c388 100644 --- a/README.md +++ b/README.md @@ -155,6 +155,7 @@ jobs: | `disable-animations` | Optional | `true` | Whether to disable animations - `true` or `false`. | | `disable-spellchecker` | Optional | `false` | Whether to disable spellchecker - `true` or `false`. | | `disable-linux-hw-accel` | Optional | `true` | Whether to disable hardware acceleration on Linux machines - `true` or `false`. Note that this is true by default as Github-hosted Linux runners do not support hardware acceleration. | +| `enable-hw-keyboard` | Optional | `false` | Whether to enable hardware keyboard - `true` or `false`. | | `emulator-build` | Optional | N/A | Build number of a specific version of the emulator binary to use e.g. `6061023` for emulator v29.3.0.0. | | `working-directory` | Optional | `./` | A custom working directory - e.g. `./android` if your root Gradle project is under the `./android` sub-directory within your repository. | | `ndk` | Optional | N/A | Version of NDK to install - e.g. `21.0.6113669` | diff --git a/__tests__/input-validator.test.ts b/__tests__/input-validator.test.ts index d861c58d2..8aeb6875d 100644 --- a/__tests__/input-validator.test.ts +++ b/__tests__/input-validator.test.ts @@ -227,6 +227,27 @@ describe('disable-linux-hw-accel validator tests', () => { }); }); +describe('enable-hw-keyboard validator tests', () => { + it('Throws if enable-hw-keyboard is not a boolean', () => { + const func = () => { + validator.checkEnableHardwareKeyboard('yes'); + }; + expect(func).toThrowError(`Input for input.enable-hw-keyboard should be either 'true' or 'false'.`); + }); + + it('Validates successfully if enable-hardware-keyboard is either true or false', () => { + const func1 = () => { + validator.checkEnableHardwareKeyboard('true'); + }; + expect(func1).not.toThrow(); + + const func2 = () => { + validator.checkEnableHardwareKeyboard('false'); + }; + expect(func2).not.toThrow(); + }); +}); + describe('emulator-build validator tests', () => { it('Throws if emulator-build is not a number', () => { const func = () => { diff --git a/action.yml b/action.yml index 704386c34..71467db56 100644 --- a/action.yml +++ b/action.yml @@ -41,6 +41,9 @@ inputs: disable-linux-hw-accel: description: 'whether to disable hardware acceleration on Linux machines - `true` or `false`' default: 'true' + enable-hw-keyboard: + description: 'whether to enable hardware keyboard - `true` or `false`.' + default: 'false' emulator-build: description: 'build number of a specific version of the emulator binary to use - e.g. `6061023` for emulator v29.3.0.0' working-directory: diff --git a/lib/emulator-manager.js b/lib/emulator-manager.js index f0cfbd734..197395e14 100644 --- a/lib/emulator-manager.js +++ b/lib/emulator-manager.js @@ -35,7 +35,7 @@ const EMULATOR_BOOT_TIMEOUT_SECONDS = 600; /** * Creates and launches a new AVD instance with the specified configurations. */ -function launchEmulator(apiLevel, target, arch, profile, cores, ramSize, sdcardPathOrSize, avdName, forceAvdCreation, emulatorOptions, disableAnimations, disableSpellChecker, disableLinuxHardwareAcceleration) { +function launchEmulator(apiLevel, target, arch, profile, cores, ramSize, sdcardPathOrSize, avdName, forceAvdCreation, emulatorOptions, disableAnimations, disableSpellChecker, disableLinuxHardwareAcceleration, enableHardwareKeyboard) { return __awaiter(this, void 0, void 0, function* () { // create a new AVD if AVD directory does not already exist or forceAvdCreation is true const avdPath = `${process.env.ANDROID_AVD_HOME}/${avdName}.avd`; @@ -51,6 +51,9 @@ function launchEmulator(apiLevel, target, arch, profile, cores, ramSize, sdcardP if (ramSize) { yield exec.exec(`sh -c \\"printf 'hw.ramSize=${ramSize}\n' >> ${process.env.ANDROID_AVD_HOME}/"${avdName}".avd"/config.ini`); } + if (enableHardwareKeyboard) { + yield exec.exec(`sh -c \\"printf 'hw.keyboard=yes\n' >> ${process.env.ANDROID_AVD_HOME}/"${avdName}".avd"/config.ini`); + } //turn off hardware acceleration on Linux if (process.platform === 'linux' && disableLinuxHardwareAcceleration) { console.log('Disabling Linux hardware acceleration.'); @@ -70,7 +73,6 @@ function launchEmulator(apiLevel, target, arch, profile, cores, ramSize, sdcardP // wait for emulator to complete booting yield waitForDevice(); yield exec.exec(`adb shell input keyevent 82`); - // disable animations if (disableAnimations) { console.log('Disabling animations.'); yield exec.exec(`adb shell settings put global window_animation_scale 0.0`); @@ -80,6 +82,9 @@ function launchEmulator(apiLevel, target, arch, profile, cores, ramSize, sdcardP if (disableSpellChecker) { yield exec.exec(`adb shell settings put secure spell_checker_enabled 0`); } + if (enableHardwareKeyboard) { + yield exec.exec(`adb shell settings put secure show_ime_with_hard_keyboard 0`); + } }); } exports.launchEmulator = launchEmulator; diff --git a/lib/input-validator.js b/lib/input-validator.js index 69c53f29f..2dcda7155 100644 --- a/lib/input-validator.js +++ b/lib/input-validator.js @@ -1,6 +1,6 @@ "use strict"; Object.defineProperty(exports, "__esModule", { value: true }); -exports.checkEmulatorBuild = exports.checkDisableLinuxHardwareAcceleration = exports.checkDisableSpellchecker = exports.checkDisableAnimations = exports.checkForceAvdCreation = exports.checkChannel = exports.checkArch = exports.checkTarget = exports.checkApiLevel = exports.VALID_CHANNELS = exports.VALID_ARCHS = exports.VALID_TARGETS = exports.MIN_API_LEVEL = void 0; +exports.checkEmulatorBuild = exports.checkEnableHardwareKeyboard = exports.checkDisableLinuxHardwareAcceleration = exports.checkDisableSpellchecker = exports.checkDisableAnimations = exports.checkForceAvdCreation = exports.checkChannel = exports.checkArch = exports.checkTarget = exports.checkApiLevel = exports.VALID_CHANNELS = exports.VALID_ARCHS = exports.VALID_TARGETS = exports.MIN_API_LEVEL = void 0; exports.MIN_API_LEVEL = 15; exports.VALID_TARGETS = ['default', 'google_apis', 'aosp_atd', 'google_atd', 'google_apis_playstore', 'android-wear', 'android-wear-cn', 'android-tv', 'google-tv']; exports.VALID_ARCHS = ['x86', 'x86_64', 'arm64-v8a']; @@ -56,6 +56,12 @@ function checkDisableLinuxHardwareAcceleration(disableLinuxHardwareAcceleration) } } exports.checkDisableLinuxHardwareAcceleration = checkDisableLinuxHardwareAcceleration; +function checkEnableHardwareKeyboard(enableHardwareKeyboard) { + if (!isValidBoolean(enableHardwareKeyboard)) { + throw new Error(`Input for input.enable-hw-keyboard should be either 'true' or 'false'.`); + } +} +exports.checkEnableHardwareKeyboard = checkEnableHardwareKeyboard; function checkEmulatorBuild(emulatorBuild) { if (isNaN(Number(emulatorBuild)) || !Number.isInteger(Number(emulatorBuild))) { throw new Error(`Unexpected emulator build: '${emulatorBuild}'.`); diff --git a/lib/main.js b/lib/main.js index b74dcc32c..2a274461f 100644 --- a/lib/main.js +++ b/lib/main.js @@ -99,6 +99,11 @@ function run() { input_validator_1.checkDisableLinuxHardwareAcceleration(disableLinuxHardwareAccelerationInput); const disableLinuxHardwareAcceleration = disableLinuxHardwareAccelerationInput === 'true'; console.log(`disable Linux hardware acceleration: ${disableLinuxHardwareAcceleration}`); + // enable hardware keyboard + const enableHardwareKeyboardInput = core.getInput('enable-hw-keyboard'); + input_validator_1.checkEnableHardwareKeyboard(enableHardwareKeyboardInput); + const enableHardwareKeyboard = enableHardwareKeyboardInput === 'true'; + console.log(`enable hardware keyboard: ${enableHardwareKeyboard}`); // emulator build const emulatorBuildInput = core.getInput('emulator-build'); if (emulatorBuildInput) { @@ -139,7 +144,7 @@ function run() { // install SDK yield sdk_installer_1.installAndroidSdk(apiLevel, target, arch, channelId, emulatorBuild, ndkVersion, cmakeVersion); // launch an emulator - yield emulator_manager_1.launchEmulator(apiLevel, target, arch, profile, cores, ramSize, sdcardPathOrSize, avdName, forceAvdCreation, emulatorOptions, disableAnimations, disableSpellchecker, disableLinuxHardwareAcceleration); + yield emulator_manager_1.launchEmulator(apiLevel, target, arch, profile, cores, ramSize, sdcardPathOrSize, avdName, forceAvdCreation, emulatorOptions, disableAnimations, disableSpellchecker, disableLinuxHardwareAcceleration, enableHardwareKeyboard); // execute the custom script try { // move to custom working directory if set diff --git a/src/emulator-manager.ts b/src/emulator-manager.ts index 5bb83d116..151bb79fc 100644 --- a/src/emulator-manager.ts +++ b/src/emulator-manager.ts @@ -19,7 +19,8 @@ export async function launchEmulator( emulatorOptions: string, disableAnimations: boolean, disableSpellChecker: boolean, - disableLinuxHardwareAcceleration: boolean + disableLinuxHardwareAcceleration: boolean, + enableHardwareKeyboard: boolean ): Promise { // create a new AVD if AVD directory does not already exist or forceAvdCreation is true const avdPath = `${process.env.ANDROID_AVD_HOME}/${avdName}.avd`; @@ -40,6 +41,10 @@ export async function launchEmulator( await exec.exec(`sh -c \\"printf 'hw.ramSize=${ramSize}\n' >> ${process.env.ANDROID_AVD_HOME}/"${avdName}".avd"/config.ini`); } + if (enableHardwareKeyboard) { + await exec.exec(`sh -c \\"printf 'hw.keyboard=yes\n' >> ${process.env.ANDROID_AVD_HOME}/"${avdName}".avd"/config.ini`); + } + //turn off hardware acceleration on Linux if (process.platform === 'linux' && disableLinuxHardwareAcceleration) { console.log('Disabling Linux hardware acceleration.'); @@ -63,7 +68,6 @@ export async function launchEmulator( await waitForDevice(); await exec.exec(`adb shell input keyevent 82`); - // disable animations if (disableAnimations) { console.log('Disabling animations.'); await exec.exec(`adb shell settings put global window_animation_scale 0.0`); @@ -73,6 +77,9 @@ export async function launchEmulator( if (disableSpellChecker) { await exec.exec(`adb shell settings put secure spell_checker_enabled 0`); } + if (enableHardwareKeyboard) { + await exec.exec(`adb shell settings put secure show_ime_with_hard_keyboard 0`); + } } /** diff --git a/src/input-validator.ts b/src/input-validator.ts index 939c673f5..ac74762d3 100644 --- a/src/input-validator.ts +++ b/src/input-validator.ts @@ -54,6 +54,12 @@ export function checkDisableLinuxHardwareAcceleration(disableLinuxHardwareAccele } } +export function checkEnableHardwareKeyboard(enableHardwareKeyboard: string): void { + if (!isValidBoolean(enableHardwareKeyboard)) { + throw new Error(`Input for input.enable-hw-keyboard should be either 'true' or 'false'.`); + } +} + export function checkEmulatorBuild(emulatorBuild: string): void { if (isNaN(Number(emulatorBuild)) || !Number.isInteger(Number(emulatorBuild))) { throw new Error(`Unexpected emulator build: '${emulatorBuild}'.`); diff --git a/src/main.ts b/src/main.ts index 98df4331b..e167b93c8 100644 --- a/src/main.ts +++ b/src/main.ts @@ -9,7 +9,8 @@ import { checkDisableSpellchecker, checkDisableLinuxHardwareAcceleration, checkForceAvdCreation, - checkChannel + checkChannel, + checkEnableHardwareKeyboard } from './input-validator'; import { launchEmulator, killEmulator } from './emulator-manager'; import * as exec from '@actions/exec'; @@ -94,6 +95,12 @@ async function run() { const disableLinuxHardwareAcceleration = disableLinuxHardwareAccelerationInput === 'true'; console.log(`disable Linux hardware acceleration: ${disableLinuxHardwareAcceleration}`); + // enable hardware keyboard + const enableHardwareKeyboardInput = core.getInput('enable-hw-keyboard'); + checkEnableHardwareKeyboard(enableHardwareKeyboardInput); + const enableHardwareKeyboard = enableHardwareKeyboardInput === 'true'; + console.log(`enable hardware keyboard: ${enableHardwareKeyboard}`); + // emulator build const emulatorBuildInput = core.getInput('emulator-build'); if (emulatorBuildInput) { @@ -154,7 +161,8 @@ async function run() { emulatorOptions, disableAnimations, disableSpellchecker, - disableLinuxHardwareAcceleration + disableLinuxHardwareAcceleration, + enableHardwareKeyboard ); // execute the custom script