iOS UIAutomation UIAElement.isVisible()抛出过时的响应?

时间:2011-08-12 17:16:16

标签: automator

我正在尝试在循环中使用isVisible()来为我的iOS UIAutomation创建一个waitForElement类型的函数。当我尝试使用以下代码时,在弹出新屏幕时等待元素时它会失败。元素显然是因为如果我在点击元素之前做了延迟(2)它完全正常。其他人怎么做到这一点,因为我不知所措......

这是我正在使用的waitForElement代码:

function waitForElement(element, timeout, step) {
        if (step == null) {
                step = 0.5;
        }

        if (timeout == null) {
            timeout = 10;
        }

        var stop = timeout/step;

        for (var i = 0; i < stop; i++) {
                if (element.isVisible()) {
                        return;
                }
                target.delay(step);
        }
        element.logElement();
        throw("Not visible");
}

4 个答案:

答案 0 :(得分:1)

这是一个可以使用的简单wait_for_element方法:

this.wait_for_element = function(element, preDelay) {
    if (!preDelay) {
        target.delay(0);
    }
    else {
        target.delay(preDelay);
    }

    var found = false;
    var counter = 0;      
    while ((!found) && (counter < 60)) {    
        if (!element.isValid()) {
            target.delay(0.5);
            counter++;
        }
        else {
            found = true;
            target.delay(1);
        }
    }
}

答案 1 :(得分:1)

我倾向于远离我的wait_for_element并在屏幕上查找任何activityIndi​​cator对象。我使用此方法实际等待页面加载。

this.wait_for_page_load = function(preDelay) {        
    if (!preDelay) {
        target.delay(0);
    }
    else {
        target.delay(preDelay);
    }

    var done = false;
    var counter = 0;      
    while ((!done) && (counter < 60)) {
        var progressIndicator = UIATarget.localTarget().frontMostApp().windows()[0].activityIndicators()[0];
        if (progressIndicator != "[object UIAElementNil]") {
            target.delay(0.25);
            counter++;  
        }
        else {
            done = true;           
        }
    }
    target.delay(0.25);
}

答案 2 :(得分:0)

这是一个使用递归的简单而且更好的方法。不需要“return true”,但是你想要它。

waitForElementToDismiss:function(elementToWait,waitTime){ //Using recursion to wait for an element. pass in 0 for waitTime 

    if(elementToWait && elementToWait.isValid() && elementToWait.isVisible() && (waitTime < 30)){
        this.log("Waiting for element to invisible");
        target.delay(1);
        this.waitForElementToDismiss(elementToWait, waitTime++);
    }

    if(waitTime >=30){
        fail("Possible login failed or too long to login. Took more than     "+waitTime +" seconds")
    }

    return true;

}

答案 3 :(得分:0)

<强>解决方案

我知道这是一个老问题,但这是我的解决方案,我必须针对可变定时事件执行重复性任务。由于UIAutomation在javascript上运行,我使用带有空循环的递归函数,该循环在进入下一个屏幕之前检查所需的关键控制状态。这样就不必对延迟进行硬编码。

// Local target is the running simulator
var target = UIATarget.localTarget();
// Get the frontmost app running in the target
var app = target.frontMostApp();
// Grab the main window of the application
var window = app.mainWindow();
//Get the array of images on the screen
var allImages = window.images();

var helpButton = window.buttons()[0];
var nextButton = window.buttons()[2];

doSomething();

function doSomething ()
{   
    //only need to tap button for half the items in array
    for (var i=0; i<(allImages.length/2); i++){
        helpButton.tap();
    }

    //loop while my control is NOT enabled
    while (!nextButton.isEnabled())
    {
        //wait  
    }   

    //proceed to next screen
    nextButton.tap();

    //go again
    doSomething();
}