Search code examples
automationappiumappium-androidappium-iosappium-java

Wait element By iOSXCUITFindBy


I need to add in my declaration a way to wait the element, for so then to click it. I am using Appium with Java, in a IOS device.

 @iOSXCUITFindBy (xpath = "//XCUIElementTypeButton[@name=\"Enviar depois\"]")
private RemoteWebElement BtnEnviarDepois;


public void ClickBtnEnviarDepois(){
    **// I need to Add a way to wait the element here**
    BtnEnviarDepois.click();
}

I need to add in the declaration something like this, but I don't know how to implement:

public void wait(By ID) {
   WebDriverWait wait = new WebDriverWait(DriverFactory.getDriver(), (180));
   WebElement element = wait.until(ExpectedConditions.elementToBeClickable((ID)));
}

Solution

  • Simplest way to initialise wait and reuse it in the page objects is to use the concept of Inheritance. Here's one example how you can do it.

    Page class:

    public class MyPage extends BasePage {
        @iOSXCUITFindBy(xpath = "//XCUIElementTypeButton[@name=\"Enviar depois\"]")
        private WebElement btnEnviarDepois;
    
        public MyPage(AppiumDriver driver){
            super(driver);
        }
    
        public void ClickBtnEnviarDepois(){
            waitForElementToBeClickable(btnEnviarDepois).click();
        }
    }
    

    BasePage class:

    public class BasePage {
        private final WebDriverWait wait;
    
        public BasePage(AppiumDriver driver){
            PageFactory.initElements(new AppiumFieldDecorator(driver), this);
            wait = new WebDriverWait(driver, Duration.ofSeconds(10));
        }
    
        public WebElement waitForElementToBeClickable(WebElement element){
            return wait.until(ExpectedConditions.elementToBeClickable(element));
        }
    }
    

    Some people don't like to write custom methods like waitForElementToBeClickable(). So alternatively, you can slightly change the code as below:

    Page class:

    public class MyPage extends BasePage {
        @iOSXCUITFindBy(xpath = "//XCUIElementTypeButton[@name=\"Enviar depois\"]")
        private WebElement btnEnviarDepois;
    
        public MyPage(AppiumDriver driver){
            super(driver);
        }
    
        public void ClickBtnEnviarDepois(){
            wait.until(ExpectedConditions.elementToBeClickable(btnEnviarDepois)).click();
        }
    }
    

    BasePage class:

    public class BasePage {
        protected final WebDriverWait wait;
    
        public BasePage(AppiumDriver driver){
            PageFactory.initElements(new AppiumFieldDecorator(driver), this);
            wait = new WebDriverWait(driver, Duration.ofSeconds(10));
        }
    }