How do i click on a particular image during runtime? - selenium-webdriver

I am working with filling up form where fields can be checkbox/radio button/textbox/datepicker/timepicker etc.
I am facing an issue with clicking on 'TimePicker' basically one clock icon is given on right hand side, when i am clicking on it, one popup displays from which i do have to pick the time.
Please refer image. https://i.stack.imgur.com/MUOXz.jpg There is no locator with help of which i can click on 'clock' icon.
Here is html DOM.
<ac-input _ngcontent-brk-c387="" inputtype="time" _nghost-brk-c374="" class="visible ng-untouched ng-pristine ng-invalid ng-star-inserted" xpath="1">
<div _ngcontent-brk-c374="" class="col-sm-12 col-md ng-star-inserted">
<div _ngcontent-brk-c374="" class="form-group">
<ac-label _ngcontent-brk-c374="" _nghost-brk-c371="">
<label _ngcontent-brk-c371="" aria-hidden="true" class="ql-editor required ng-star-inserted" for="<p>
<p>
2. Time:
</p>
</label>
</ac-label>
<div _ngcontent-brk-c374="">
<input _ngcontent-brk-c374="" class="form-control ng-star-inserted" id="<p></p>" type="time">
</div>
<ac-hint _ngcontent-brk-c374="" _nghost-brk-c372="">
</ac-hint>
<ac-validation-messages _ngcontent-brk-c374="" role="alert" aria-atomic="true" _nghost-brk-c348="" style="">
</ac-validation-messages>
</div>
</div>
</ac-input>
I have captured 'Clock' icon with the help of snipping tool from the application and pasted on desktop as well under my application under the 'Screenshot' folder.
But click event is not happening from application at run time but its clicking the 'Clock' icon from desktop. And console output for it is "[log] DOUBLE CLICK on L[410,442]#S(0) (69 msec)".
Here is what i tried...
else if(answerType.equals("Time"))
{
WebElement timeText = answers.get(ans) .findElement(By.tagName("label"));
System.out.println(timeText.getText());
Screen screen = new Screen();
Pattern image1 = new Pattern("C:\\Selenium\\workspace\\C_Care\\Screenshots\\Clock.PNG");
Pattern image2 = new Pattern("C:\\Selenium\\workspace\\C_Care\\Screenshots\\Twelve.png");
screen.wait(image1, 10);
for(int sc=0; sc<6; sc++)
{
screen.mouseMove(image1);
screen.doubleClick(image1);
break;
}
screen.wait(image2,10);
screen.click(image2);
}
I a working with TestNg framework and used maven dependency for Sikuli is 2.0.4.
Any help will be appreciated.

Related

Angularjs Form dirty not working for Dropdown

I have a simple bootstrap form . For sake of example i have a input field and a dropdown. I want to enable the save button only when the change is made. In order to do that, i made the save button enable only if the form is dirty.
The problem is - When i change the input field it works, the button gets enabled, where as when i change the dropdown, which is basically selecting the list item, the form does not identify it as dirty and hence it is still disabled.
Any ideas?
I also tried creating an hidden input field that gets updated everytime the select value gets updated - but still it is noto working .
My sample form (pls ignore any typos since i stripped of most of the code. The functionality works just fine. it is just the disabling of button that doesnt work)
<form name="customizeForm" id="customize-form" class="bm-form" data-ng-cloak novalidate data-ng-submit="ctrl.saveCustomization(customizeForm.$valid)">
<!--if i change this input, it works -->
<input id="answer" type="text" name="answer" data-ng-model="ctrl.answer">
<!--If i change the below dropdown, it doesnt work and the button is still disabled -->
<div class="form-group dropdown col-xs-12 col-md-6" data-uib-dropdown data-keyboard-nav data-is-open="status[$index].isopen" data-ng-init="status[$index].newSelectedValue = ''">
<button id="profile-menu" type="button" class="form-control select-control dropdown-togglebtn" data-uib-dropdown-toggle>
<span class="selected" data-ng-bind-html="status[$index].newSelectedValue</span>
<span class="icon icon-down-arrow" aria-hidden="true"></span>
</button>
<ul class="dropdown-menu" role="menu" data-aria-labelledby="menu">
<li data-ng-repeat="answer in question.Answers">
{{answer.AnswerDesc}}
</li>
</ul>
</div>
<div id="save-profile" class="text-center form-submit">
<button type="submit" data-ng-disabled="!customizeForm.$dirty" id="btn-profile-questionnaire" class="btn btn-card reverse" title="Save">
Save</span>
</button>
</div>
</form>

Making the Bootstrap navbar searchbox work

I am trying to make a search function which works if I put in the query params into my URL directly but I don't know how to make it work so that it picks it up from the search box and executes it. I have used ng-model to map the text itself to the controller which works but the execution isn't working.
The navbar form:
<form ng-submit="doSearch()" class="navbar-form">
<div class="form-group" style="display:inline;">
<div class="col-md-offset-4 input-group" style="display:table;">
<input ng-model="search.text" class="form-control" name="search" placeholder="Search Here" autocomplete="off" autofocus="autofocus" type="text">
<span class="input-group-addon" style="width:1%;">
<span class="glyphicon glyphicon-search"></span>
</span>
</div>
</div>
By the way, my doSearch() function works just fine when I run it manually and so is the search itself. I have also validated that search.text comes through. I guess what I am asking is how do I make the icon (glyphicon-search) execute ng-submit="doSearch()" when the user clicks on it or presses enter.
Sorry if this is very obvious. I was always more on the backend side of things so am sorta new to HTML and Angular.
Thanks
You could place the icon inside a <button> element instead of <span>, tweak a bit of css to integrate it to the form field.
In regards to trigger search on enter, with jQuery something like this could be used:
$('input').keypress(function (e) {
var key = e.which;
if(key == 13) // the enter key code
{
doSearch();
}
});
did you try using <button type="submit"> before your search icon
<span class="glyphicon glyphicon-search"></span>
to specify that clicking on that button is equivalent to a submit event for that form.
So this worked in the end. First, the proper HTML which works:
<form ng-submit="doSearch()" class="navbar-form">
<div class="form-group" style="display:inline;">
<div class="col-md-offset-4 input-group" style="display:table;">
<input ng-model="search.text" class="form-control" name="search" placeholder="Search Here" autocomplete="off" autofocus="autofocus" type="text">
<span ng-click="doSearch()" class="input-group-addon" style="width:1%;">
<span class="glyphicon glyphicon-search"></span>
</span>
</div>
</div>
</form>
Furthermore, there was an issue with the view not connecting to the controller. Actually, let me rephrase that - it was connecting to the controller but only when the whole page loaded and for my test, I had a console.log('I have loaded') put in there. So when I saw "I have loaded", I thought my controller was invoked properly.
However, the doSearch() was in the controller which was connecting via angular routing, so the ng-View was not connecting to the right controller.
I am not sure if this means anything to anyone but I am writing this in case someone else comes across an issue like mine.
So just to summarise the issue was not with the HTML as I originally thought. ng-submit (for form submission when pressing enter) and ng-click (for clicking the glyphicon) does the trick.

Protractor having problems pressing a hidden radio button

I am having issues pressing a hidden radio button on my page using protractor. Below you will find a single test where the flow should work as following.
Page is navigated too, and make sure that the radio button exists. (Two ways to verify existence below, both work)
Attempt to click the button in a variety of different ways. All of the commented out ways, as well as the real one below do not error out the test, but they do also not "Click" the radio button. I am able to confirm this because of the 3 expects at the bottom that look to see if the form that shows up when the button is clicked actually shows up, and those are turning false every single time.
Any help with this would be greatly appreciated, Below I've also put the sample html that this code is looking at. Any help would be great, not sure if it is even possible. Thank you for any help in advance
it('Should press one of the radio buttons and have the form pop up', function() {
// Make sure that the value equals bank is found (This passing its test)
expect(element.all(by.model('bankConnection.bank')).get(0).getAttribute('ng-value')).toEqual('bank');
// Another way to make sure that the element is found (This is passing the test)
// expect(element.all(by.css('[ng-value="bank"]')).get(0).getAttribute('ng-value')).toEqual('bank');
// browser.driver.executeScript("return arguments[0].click();", element.all(by.css('[ng-value="bank"]')).get(0).getAttribute('ng-value').getWebElement());
// browser.driver.executeScript("return arguments[0].click();", element.all(by.model('bankConnection.bank')).get(0).getAttribute('ng-value').getWebElement());
// #1 Way THIS WAY WORKS BUT DOESNT PRESS ANYTHING
// var input = element.all(by.model('bankConnection.bank')).get(0);
// browser.driver.executeScript('angular.element(arguments[0]).triggerHandler("touchstart");', input.getWebElement());
// #2 Way THIS WAY WORKS BUT DOESNT PRESS ANYTHING
var input = element.all(by.model('bankConnection.bank')).get(0).getAttribute('ng-value');
browser.driver.executeScript('angular.element(arguments[0]).triggerHandler("touchstart");', input.getWebElement());
// To verify button was pressed. 2 seconds
browser.driver.sleep(2000);
// Make sure that the form pops up (IT IS CURRENTLY NOT SHOWING UP)
expect(element(by.model('bankConnect.username')).isPresent()).toBe(true);
expect(element(by.model('bankConnect.password')).isPresent()).toBe(true);
// Once click is figured out this should flow through properly BOA CLICK
expect(bank_page.idText).toEqual('Online ID');
});
Radio Button Element
<div class="col" ng-repeat="bank in firstBanks">
<div style="font-size: 2em; ">
<label class="bank_radio">
<input type="radio" ng-model="bankConnection.bank" ng-value="bank" class="ng-valid ng-dirty" value="[object Object]">
<img ng-src="img/banks/bofa.png" src="img/banks/bofa.png">
</label>
</div>
</div>
Form that pops up element
<div class="list card" style="margin-bottom: 0;margin-top:0;" ng-show="bankConnection.bank != null ">
<div class-="list">
<label class="item item-input">
<span class="input-label ng-binding">Online ID</span>
<input type="text" ng-model="bankConnection.username" class="ng-pristine ng-valid">
</label>
<label class="item item-input">
<span class="input-label ng-binding">Password</span>
<input type="password" ng-model="bankConnection.password" class="ng-pristine ng-valid" autocomplete="off" style="cursor: auto; background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAASCAYAAABSO15qAAAABmJLR0QA/wD/AP+gvaeTAAAACXBIWXMAAAsTAAALEwEAmpwYAAAAB3RJTUUH3QsPDhss3LcOZQAAAU5JREFUOMvdkzFLA0EQhd/bO7iIYmklaCUopLAQA6KNaawt9BeIgnUwLHPJRchfEBR7CyGWgiDY2SlIQBT/gDaCoGDudiy8SLwkBiwz1c7y+GZ25i0wnFEqlSZFZKGdi8iiiOR7aU32QkR2c7ncPcljAARAkgckb8IwrGf1fg/oJ8lRAHkR2VDVmOQ8AKjqY1bMHgCGYXhFchnAg6omJGcBXEZRtNoXYK2dMsaMt1qtD9/3p40x5yS9tHICYF1Vn0mOxXH8Uq/Xb389wff9PQDbQRB0t/QNOiPZ1h4B2MoO0fxnYz8dOOcOVbWhqq8kJzzPa3RAXZIkawCenHMjJN/+GiIqlcoFgKKq3pEMAMwAuCa5VK1W3SAfbAIopum+cy5KzwXn3M5AI6XVYlVt1mq1U8/zTlS1CeC9j2+6o1wuz1lrVzpWXLDWTg3pz/0CQnd2Jos49xUAAAAASUVORK5CYII=); background-attachment: scroll; background-position: 100% 50%; background-repeat: no-repeat;">
</label>
</div>
</div>
Here is what was able to fix my problem in the end. Courtesy of: How to click on hidden element in protractor?
I added this block to my code to hover over the area of the image, and then issue a click command.
// Move mouse over the button
browser.driver.actions().mouseMove(element(by.css('[ng-src="img/banks/bofa.png"]'))).perform();
element.all(by.css('[ng-src="img/banks/bofa.png"]')).then(function (elm) {
elm[0].click();
});
Thank you for the help!

Why is click ignored on non-Angular page in a Protractor test?

I have an app I'm trying to do e2e tests with. The app uses a non-Angular login page (Microsoft AD account). So, I fill in the user and password then click the "sign in" button with the following code:
var user = asAdmin ? config.adminUser : config.user;
browser.driver.findElement(by.id('cred_userid_inputtext')).sendKeys(user);
browser.driver.findElement(by.id('cred_password_inputtext')).sendKeys(config.pass);
browser.driver.findElement(by.id('cred_sign_in_button')).click();
The user and password get filled in and the "sign in" button (which is a <span>) looks like it was clicked (changes color), but nothing happens.
I wait for quite a while (minutes) and it just doesn't work. However, if I just use the mouse, it does work. I have also tried tacking on a "\n" to the end of the password string to simulate the enter key. This is ignored.
The html for the pertinent parts of the login look like this:
<form id="credentials" method="post" action="https://login.microsoftonline.com/...">
<div id="cred_userid_container" class="login_textfield textfield">
<span class="input_field textfield">
<label for="cred_userid_inputtext" class="no_display" aria-hidden="true">User account</label>
<div class="input_border">
<input tabindex="1" id="cred_userid_inputtext" class="login_textfield textfield required email field normaltext" placeholder="someone#example.com " type="email" name="login" spellcheck="false" alt="someone#example.com " aria-label="User account" value="" autocomplete="off">
</div>
</span>
</div>
...
<div id="cred_password_container" class="login_textfield textfield" style="opacity: 1;">
<span class="input_field textfield">
<label for="cred_password_inputtext" class="no_display" aria-hidden="true">Password</label>
<div class="input_border">
<input tabindex="2" id="cred_password_inputtext" class="login_textfield textfield required field normaltext" placeholder="Password" spellcheck="false" aria-label="Password" alt="Password" type="password" name="passwd" value="">
</div>
</span>
</div>
...
<li class="login_cred_options_container">
<div id="cred_kmsi_container" class="subtext normaltext">
<span class="input_field ">
<input tabindex="10" id="cred_keep_me_signed_in_checkbox" type="checkbox" value="0" name="persist">
<label id="keep_me_signed_in_label_text" for="cred_keep_me_signed_in_checkbox" class="persist_text">Keep me signed in</label>
</span>
</div>
<span id="cred_sign_in_button" tabindex="11" onclick="Post.SubmitCreds();return false;" class="button normaltext cred_sign_in_button refresh_domain_state disabled_button" role="button" style="opacity: 1;">Sign in</span>
<div id="recover_container" class="subtext smalltext" style="opacity: 1;">
<span>
<a id="cred_forgot_password_link" tabindex="12" href="https://login.microsoftonline.com/resetpw.srf?lc=1033&id=501148">Can’t access your account?</a>
</span>
</div>
</li>
...
</form>
I can't, for the life of me figure out what's going on here.
Any help is greatly appreciated.
UPDATED: added the missing "button" span
UPDATE 2: also tested with Firefox, same problem. The click on the span just doesn't seem to work..
UPDATE 3: For some strange reason, the following code works:
browser.actions()
.mouseMove(browser.driver.findElement(by.id('cred_sign_in_button')))
.click()
.perform();
browser.sleep(500);
browser.driver.findElement(by.id('cred_sign_in_button')).click();
If I take either the mouseMove/click or the last click out, it stops working. If I take out the sleep, it is intermittent.
I have no idea why that's working.
Testing non-angular pages with Protractor can be tricky regarding waiting for stuff.
I suggest you upgrade Protractor to latest (1.3.1 as of now), use a custom function waitReady() that browser.wait for elements ready and rewrite your test like this:
var user = asAdmin ? config.adminUser : config.user;
// TODO: use page objects
var userIdInputElm = $('#cred_userid_inputtext');
var passwordInputElm = $('#cred_password_inputtext');
var signinButtonElm = $('#cred_sign_in_button');
it('waits for the elements present and visible (non-angular)', function() {
expect(userIdInputElm.waitReady()).toBeTruthy();
expect(passwordInputElm.waitReady()).toBeTruthy();
expect(signinButtonElm.waitReady()).toBeTruthy();
});
it('fills user and password', function() {
userIdInputElm.sendKeys(user);
passwordInputElm.sendKeys(config.pass);
});
it('clicks sign in button', function() {
signinButtonElm.click();
});
More details of why waitReady here.

keyboard not comes up on textarea insight an bootstrap modal window at an HTML5/cordova app

I have an HTML5 application using cordova to run on an android mobile phone.
This works fine.
Then, I changed the application. I use angluarJS as basic framework and bootstrap to build layout and small animations.
The textarea still works fine.
In the next step, I moved the textarea insight a form, that looks like this:
<form novalidate ng-submit="sendeForm()">
<div class="container">
<div class="row">
<div class="col-xs-12 col-sm-12" >
<textarea style="width:100%" ng-model="form.msg" name="news" autofocus>
</textarea>
</div>
</div>
</div>
<input type="hidden" name="nr" ng-model="form.nr" >{{form.nr}}
<input class="btn btn-default" type="submit" value="send">
<input class="btn btn-default" ng-click="cancel()" value="cancel">
</form>
This form is stored in views/_annotateForm.html and hidden, until the users tap on a button.
In this case, a bootstrap modal window opens, using that code:
$scope.open = function() {
var modalInstance = $modal.open({
templateUrl: 'views/_annotateForm.html',
controller: 'messageSendCtrl',
size: 'lg',
});
then ... the form appears, but when I tap the textarea, no keyboard comes up.
The problem only occurs, if the form is loaded as a view insight the modal window. There is no problem, if the form is part of the main page.
Btw: I know, there are other questions on SO to the topic "keyboard not shown", like this: Phonegap, textarea will not accept input But all of those questions does not fit this case. Removeing -webkit-user-select does not change anything.

Resources