rohini chaudhary rohini chaudhary - 5 months ago 31
Javascript Question

Element not visible error (not able to click an element)

I want to click on a radio button, appears on a webpage. Code is as follow:

HTML code:

<div class="small-checkbox red-theme raleway-regular text-muted2 position-relative">

<div class="city-checkbox inline-block position-relative" ng-class="{'rounded-checkbox': main.current_city_id == 1, 'mb-20': main.ifDeviceIsPhone}">
<label class="mdl-radio mdl-js-radio mdl-js-ripple-effect mh-20" for="mumbaiCity" ng-class="{'is-checked' : main.current_city_id == 1}">
<input type="radio" id="mumbaiCity" class="mdl-radio__button position-relative vertical-middle" name="city" value="1" ng-click="main.setCity('Mumbai', 1)">
<span class="mdl-radio__label position-relative font15"><img class="city-icon" src="../../../assets/img/cities/mumbai-icon.png">Mumbai</span>
</label>
</div>
</div>


Tesstcase:

// demo-test.js
describe('Protractor Demo App', function() {
jasmine.DEFAULT_TIMEOUT_INTERVAL = 10000000;

it('check item count', function() {
browser.get('<link>');
element(by.id('mumbaiCity')).click();
});

});


This test throughs error:


1) Protractor Demo App check item count

Message:

Failed: element not visible


I also tried with:

element(by.css('[ng-click="main.setCity('Mumbai', 1)"]')).click();


It gives error:


[16:16:26] E/launcher - Error: SyntaxError: missing ) after argument list


Please suggest, how the radio button will get click?

Answer

This is a rather common problem in test automation with selenium.

Here are the common solutions:

  • make sure the element you want to click is actually visible. Sometimes you need to make extra actions on a page to make the element visible. For example, open up a dropdown for an option to appear or open menu for submenu to appear
  • wait for the visibility of the element:

    var EC = protractor.ExpectedConditions;
    var mumbaiCity = element(by.id('mumbaiCity'));
    browser.wait(EC.visibilityOf(mumbaiCity), 5000);
    mumbaiCity.click();
    
  • there is an another element with the same id that is actually invisible. In this case, you need to improve your locator to match this specific element. For instance:

    element(by.css(".city-checkbox #mumbaiCity")).click();
    element(by.css(".city-checkbox input[ng-click*=Mumbai]")).click();
    
  • Or, if you got multiple elements matching the same locator - you can "filter" out a visible element:

    var mumbaiCity = element.all(by.id('mumbaiCity')).filter(elm) {
        return elm.isDisplayed().then(function (isDisplayed) {
            return isDisplayed;
        });
    }).first();
    mumbaiCity.click();
    
  • move to element and then click via browser.actions():

    var mumbaiCity = element(by.id('mumbaiCity'));
    browser.actions().mouseMove(mumbaiCity).click().perform();
    
  • scroll into view of the element and then click:

    var mumbaiCity = element(by.id('mumbaiCity'));
    browser.executeScript("arguments[0].scrollIntoView();", mumbaiCity.getWebElement());
    mumbaiCity.click();
    
  • click via javascript (beware of the differences though):

    var mumbaiCity = element(by.id('mumbaiCity'));
    browser.executeScript("arguments[0].click();", mumbaiCity.getWebElement());
    
  • sometimes, you just need to maximize the browser window:

    browser.driver.manage().window().maximize();