Johnnie Walker
Johnnie Walker

Reputation: 73

Appium hidekeyboard() method

I'm trying to automate a zipcode input field which popup a num keyboard for user input. Appium could input the zipcode properly, but facing a problem when folding the keyboard, I notice there's appium menthod driver.hidekeyboard()

But unfortunately it's gives error when I using it.

Webdriver error:

org.openqa.selenium.WebDriverException: An unknown server-side error occurred while processing the command. Original error: [object Object]

Appium Server log:

debug] [JSONWP Proxy] Matched '/element/undefined/click' to command name 'click'
[debug] [JSONWP Proxy] Proxying [POST /element/undefined/click] to [POST http://localhost:8100/session/83293E4F-4B7A-462A-B5B1-1D729D54E36B/element/undefined/click] with body: {}
[debug] [XCUITest] Connection to WDA timed out
[debug] [iProxy] recv failed: Operation not permitted
[debug] [JSONWP Proxy] Got response with status 200: {"value":{},"sessionId":"83293E4F-4B7A-462A-B5B1-1D729D54E36B","status":13}
[JSONWP Proxy] Got an unexpected response: {"value":{},"sessionId":"83293E4F-4B7A-462A-B5B1-1D729D54E36B","status":13}
[debug] [MJSONWP] Matched JSONWP error code 13 to UnknownError
[debug] [XCUITest] Connection to WDA timed out
[debug] [iProxy] recv failed: Operation not permitted
[debug] [W3C (bac0efb8)] Encountered internal error running command: UnknownError: An unknown server-side error occurred while processing the command. Original error: [object Object]
[debug] [W3C (bac0efb8)]     at errorFromMJSONWPStatusCode (/usr/local/lib/node_modules/appium/node_modules/[email protected]@appium-base-driver/lib/protocol/errors.js:789:10)
[debug] [W3C (bac0efb8)]     at ProxyRequestError.getActualError (/usr/local/lib/node_modules/appium/node_modules/[email protected]@appium-base-driver/lib/protocol/errors.js:683:14)
[debug] [W3C (bac0efb8)]     at JWProxy.command (/usr/local/lib/node_modules/appium/node_modules/[email protected]@appium-base-driver/lib/jsonwp-proxy/proxy.js:234:19)
[HTTP] <-- POST /wd/hub/session/bac0efb8-601a-4558-a50c-f909f2ccb25a/appium/device/hide_keyboard 500 1

I also noticed there's a override method for keyboard with parameters as: https://github.com/appium/java-client/blob/1991a8a0f9e4a3ff467dbb713cb5c51c8edc060f/src/main/java/io/appium/java_client/HidesKeyboardWithKeyName.java

driver.hideKeyboard(HideKeyboardStrategy.PRESS_KEY, "Done");

But regardless that I've imported the necessary class, it still says 'The method hideKeyboard() in the type HidesKeyboard is not applicable for the arguments (String, String)'

Anyone could help on any of the above 2 issues?

Many Thanks!

Upvotes: 7

Views: 10517

Answers (10)

scipilot
scipilot

Reputation: 7447

I'm testing a React Native app in a iPad simulator via Appium and WebdriverIO.

import { remote } from 'webdriverio';
client = await remote(opts);

I eventually found doing two actions in a row worked reliably, but one doesn't e.g.

await client.hideKeyboard('tapOut')
await client.hideKeyboard('tapOut')

I also agree with Mat Lavin's comment on the accepted answer that sending '\n' is reliable too.

await client.sendKeys(["\n"])

I also found using no param or "default" caused the keyboard to become kind of minimised to a bar which then couldn't be used until reboot.

Upvotes: 0

Mark Han
Mark Han

Reputation: 3135

    public void clickAfterFindingElement(By by) {
        try {
            getDriver().waitForCondition(ExpectedConditions.elementToBeClickable(by));
            getDriver().findElement(by).click();
        } catch (NoSuchElementException | TimeoutException e) {
            swipeUp();
            getDriver().findElement(by).click();
        }
    }


    public void hideKeyBoard() {
        if (isKeyboardShown()) {
            if (isConfigurationIOS()) {
                try {
                    clickAfterFindingElement(By.id("keyboard_done_btn"));
                } catch (Exception e) {
                    try {
                        getDriver().click(By.id("Done"));
                    } catch (Exception e1) {
                        //noop
                    }
                }
            } else {
                ((AndroidDriver) getDriver().getAppiumDriver()).pressKey(new KeyEvent(AndroidKey.BACK));
            }
        }
    }

This solution has been incredibly stable for us for hiding a keyboard on simulators and emulators

Upvotes: 1

rajkumar97005659
rajkumar97005659

Reputation: 1

Best solution for this problem is, just add capability in your program.

capabilities.setCapability(MobileCapabilityType.AUTOMATION_NAME, "uiautomator2");

Upvotes: 0

Sakthi
Sakthi

Reputation: 111

If you are using android, use the below method.

If keyboard is visible (by id)

 driver.pressKeyCode(4);  //Android back button

else

 logger keyboard is not active

Above method will dismiss the keyboard by invoking system back button.

Upvotes: 0

krishna chetan
krishna chetan

Reputation: 659

If you're using Android u can use adb to hide the keyboard , send adb command from your code

adb shell input keyevent 111

Upvotes: 0

Prajeeth Anand
Prajeeth Anand

Reputation: 49

You define the capabilities like this.

desiredCapabilities.setCapability("unicodeKeyboard", true);
desiredCapabilities.setCapability("resetKeyboard", true);

Upvotes: 0

VSB
VSB

Reputation: 327

The problem is trying to hide the keyboard on the first place. Set DesiredCapabilities as

cap.setCapability("connectHardwareKeyboard", false);

This will keep the keyboard hidden by default.

Do your operation of entering data by sendKeys()

appDriver.findElementByXPath("//XCUIElementTypeOther[@name=\"Confirm password\"]/XCUIElementTypeSecureTextField").sendKeys(confirmPassword);

once done call

appDriver.hideKeyboard();

and the keyboard goes away. Hope this helps

Upvotes: 0

shweta kaushik
shweta kaushik

Reputation: 43

You can also simply use

driver.navigate().back(); (for the older version of appium)

Upvotes: 0

Suban Dhyako
Suban Dhyako

Reputation: 2526

The Appium method hideKeyboard() is known to be unstable when used on iPhone devices, as listed in Appium’s currently known open issues. Using this method for an iOS device may cause the Appium script to hang. Appium identifies that the problem is because - "There is no automation hook for hiding the keyboard,...rather than using this method, to think about how a user would hide the keyboard in your app, and tell Appium to do that instead (swipe, tap on a certain coordinate, etc…)"

Workaround: Following the advice of the Appium documentation - use Appium to automate the action that a user would use to hide the keyboard. For example, use the swipe method to hide the keyboard if the application defines this action, or if the application defines a "hide-KB" button, automate clicking on this button.

The other workaround is to use sendkey() without clicking on the text input field.

Upvotes: 5

Shrirang
Shrirang

Reputation: 198

The Appium method hideKeyboard() is known to be unstable when used on iPhone devices, as listed in Appium’s currently known open issues. Using this method for an iOS device may cause the Appium script to hang. Appium identifies that the problem is because - "There is no automation hook for hiding the keyboard,...rather than using this method, to think about how a user would hide the keyboard in your app, and tell Appium to do that instead (swipe, tap on a certain coordinate, etc..

If you want to hide the keyboard, you can write a function like below

public void typeAndEnter(MobileElement mobileElement, String keyword) {
        LOGGER.info(String.format("Typing %s ...",keyword));
        mobileElement.sendKeys(keyword, Keys.ENTER);
    }

Hope this helps

Upvotes: 0

Related Questions