Selenium WebDriver:使用XPath单击SVG中的元素

jgo*_*ode 41 java firefox selenium xpath webdriver

我有一个带有几个圆形和矩形元素的SVG对象.使用webdriver,我可以单击主svg对象,但不能单击其中的任何元素.问题似乎只是点击(或任何鼠标交互),因为我可以使用getAttribute()返回宽度,ID,x/y,文本等的值,以及它下面的任何内容.

以下是HTML的示例:

    <div id="canvas">
        <svg height="840" version="1.1" width="757" xmlns="http://www.w3.org/2000/svg" style="overflow: hidden; position: relative;">
            <image x="0" y="0" width="757" height="840" preserveAspectRatio="none">
            <circle cx="272.34" cy="132.14">
            <rect x="241.47" y="139.23">
            <text style="text-anchor: middle; x="272.47" y="144.11">
        </svg>
    </div>
Run Code Online (Sandbox Code Playgroud)

并且WebDriver尝试右键单击矩形元素(并失败)的示例:

    WebElement mapObject = driver.findElement(By.xpath("//*[name()='svg']/*[name()='rect']"));
    Actions builder = new Actions(driver);
    builder.contextClick(mapObject).perform();
Run Code Online (Sandbox Code Playgroud)

但这可以工作并返回一个值:

    driver.findElement(By.xpath("//*[name()='svg']/*[name()='rect']")).getAttribute("x");    
Run Code Online (Sandbox Code Playgroud)

当WebDriver出错时,通常是这样的:

    org.openqa.selenium.WebDriverException: '[JavaScript Error: "a.scrollIntoView is not a function" {file: "file:///var/folders/sm/jngvd6s97ldb916b7h25d57r0000gn/T/anonymous490577185394048506webdriver-profile/extensions/fxdriver@googlecode.com/components/synthetic_mouse.js" line: 8544}]' when calling method: [wdIMouse::move]
Run Code Online (Sandbox Code Playgroud)

我花了一些时间研究这个问题,它似乎是Selenium和SVG的一个常见问题,但是我想知道是否有解决方法.我发现的唯一解决方案是与SVG本身进行交互,我已经可以做了.

我正在使用Selenium 2.28(并尝试使用2.29)w/Java + Firefox 17.

任何想法都非常感激.

jgo*_*ode 24

对于有兴趣的人,我通过以下方式解决了这个问题:

1)我最初使用Firefox 17和Selenium 2.28/29在OSX上测试它,但发现它只能在Windows 18上使用Firefox 18和Selenium 2.29工作(至少对我而言)

2)与标准的SVG交互:

driver.findElement(By.xpath(YOUR XPATH)).click();
Run Code Online (Sandbox Code Playgroud)

不起作用.您需要使用Actions.

3)与SVG对象交互,以下XPath有效:

"/*[name()='svg']/*[name()='SVG OBJECT']";
Run Code Online (Sandbox Code Playgroud)

SVG对象是SVG元素下的任何内容(例如,circle,rect,text等).

单击SVG对象的示例:

WebElement svgObject = driver.findElement(By.xpath(YOUR XPATH));
Actions builder = new Actions(driver);
builder.click(svgObject).build().perform();
Run Code Online (Sandbox Code Playgroud)

注意:你需要调用click()函数内的路径; 使用:

moveToElement(YOUR XPATH).click().build().perform();
Run Code Online (Sandbox Code Playgroud)

不起作用.

  • 使用name()进行XPath检查是必要的,因为SVG DOM节点位于不同的命名空间中. (3认同)
  • 我得到“元素在该点不可点击(231.1666717529297、312.04998779296875)”。当我尝试单击 svg 中的圆圈时,其他元素会收到 click:' 异常。对这个有什么想法吗? (2认同)

Ioa*_*oan 12

试试这个解决方法:

WebElement mapObject = driver.findElement(By.xpath("//*[name()='svg']/*[name()='rect']"));
((JavascriptExecutor) driver).executeScript("arguments[0].click();", mapObject);
Run Code Online (Sandbox Code Playgroud)

每当我在尝试点击它们时遇到一些元素的问题太多时,我就会使用此解决方法.


cas*_*son 5

通过执行这两件事,我们能够避免奇怪的 xpath 选择

WebElement mapObject = (WebElement) driver.executeScript('return document.querySelector(arguments[0])', "svg rect")

((JavascriptExecutor) driver).executeScript("arguments[0].dispatchEvent(new MouseEvent('click', {view: window, bubbles:true, cancelable: true}))", mapObject);
Run Code Online (Sandbox Code Playgroud)

这适用于 osx 和 phantomjs,但我认为在任何现代浏览器中都应该没问题。

(我们使用了 js 驱动程序,因此请随意修复任何编译错误)