【问题标题】:Is there a proved mouseOver workaround for FirefoxDriver in Selenium2?Selenium2 中的 FirefoxDriver 是否有经过验证的 mouseOver 解决方法?
【发布时间】:2011-09-08 02:39:57
【问题描述】:

我正在使用 Selenium Java 2.0b3。我有这个代码:

...
WebDriver driver = new InternetExplorerDriver();
Selenium seleniumDriver = new WebDriverBackedSelenium(driver, "http://localhost:8088/Sistema/");
...
...
RenderedWebElement menuRegistrar = (RenderedWebElement)driver.findElement(By.xpath("//a[normalize-space()='Registrar']"));
seleniumDriver.mouseOver("//a[normalize-space()='Registrar']"); //makes element visible     
menuRegistrar.click();
seleniumDriver.mouseOut("//a[normalize-space()='Registrar']");
...

使用 InternetExplorerDriver(使用 IE 8)就像一个魅力,但它不适用于 FirefoxDriver(使用 Firefox 4)。我已经用代码尝试了很多东西,但没有任何效果。而且我必须使用 FirefoxDriver,因为我正在测试的应用程序在 IE 上表现不佳。

正如您可能猜到的,“注册器”链接在 mouseOver 事件触发之前是隐藏的。

任何经过验证的解决方法?感谢您的宝贵时间...

编辑:还尝试了 ChromeDriver 和 Chrome 11。也没有用。如果有适用于 Chrome 的解决方法,我会接受!


答案(使用 Selenium Java 2.0RC1、Windows 7、Firefox 4 的工作代码):感谢 Andy Tinkham 和 Luke Inman-Semerau:

//get the element that shows menu with the mouseOver event
WebElement menu = driver.findElement(By.xpath("//div[@id='nav']/li[3]"));

//the element that I want to click (hidden)
WebElement menuOption = driver.findElement(By.xpath("//a[normalize-space()='Registrar']"));

//build and perform the mouseOver with Advanced User Interactions API
Actions builder = new Actions(driver);    
builder.moveToElement(menu).build().perform();

//then click when menu option is visible
menuOption.click();

注意:高级用户交互 API 在浏览器上使用 NativeEvents(不支持跨平台)。因此,如果您更改操作系统,此代码可能无法正常工作。这就是我添加操作系统和浏览器详细信息的原因。见question in selenium users group

【问题讨论】:

  • 你不需要打电话给builder.moveToElement(menu).build().perform();,但builder.moveToElement(menu).perform();会做同样的事情

标签: java webdriver selenium-webdriver


【解决方案1】:

我建议尝试昨天在 2.0rc1 版本中添加的Advanced User Actions API,因为看起来您仍在使用 Selenium 1 API(通过 WebDriverBackedSelenium),而且我不确定 Firefox 4 有多少提供的支持。我没有使用 Java 进行 Selenium 测试,但在我看来,您想要做的是这样的:

   Actions builder = new Actions(driver); // Or maybe seleniumDriver? Not sure which one to use

   Actions hoverOverRegistrar = builder.moveToElement(menuRegistrar);

   hoverOverRegistrar.perform();

【讨论】:

  • 感谢您将我指向 2.0rc1!我知道我正在使用 Selenium 1 API,因为我已经尝试过使用 Selenium 2 API 并且我不断收到 UnsopportedOperationException(或类似的东西)。但是使用 rc1 的高级用户操作效果很好!工作代码在问题的最终编辑中。非常感谢您的宝贵时间!
  • 让我添加一条关于构建器的评论(尽管示例还可以):构建器模式将始终返回添加了附加功能的相同对象,因此创建新变量没有意义看起来构建器是不可变的。要么使用 Actions builder = new ...; builder.move ...;或者只使用一个语句并在新的之后添加功能
【解决方案2】:

我使用此代码来获取特定 web 元素的鼠标悬停事件。它不需要原生事件。

protected void mouseOver(WebElement element) {
    String code = "var fireOnThis = arguments[0];"
                + "var evObj = document.createEvent('MouseEvents');"
                + "evObj.initEvent( 'mouseover', true, true );"
                + "fireOnThis.dispatchEvent(evObj);";
    ((JavascriptExecutor) driver).executeScript(code, element);
}

【讨论】:

  • 这个例子效果很好,非常感谢@MarkusHeberling !我正在使用 selenium 1,ff 版本 3.6
  • 在最新版本的 Firefox 不再提供它的原生事件 API 之后,这种方法对我来说非常有用!
【解决方案3】:
Actions action = new Actions(driver);
action.moveToElement(element).build().perform();
action.moveByOffset(1, 1).build().perform();

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2016-09-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-08-08
    • 1970-01-01
    • 2013-12-10
    • 1970-01-01
    相关资源
    最近更新 更多