Reputation: 1116
I'm working on a webpage where jquery is loaded and there is an input field on the webpage, which supports auto completion, so after typing several characters, a selection of suggestion box shows itself. By using dev tools' console, i can be able force that suggestion list to be generated and be appeared on demand, by executing following jquery functions (in browser console):
$('input#PrincipalPolicyHolder_EmploymentOccupationDescription').val("soft");
setTimeout(function() { $('input#PrincipalPolicyHolder_EmploymentOccupationDescription').focus(); }, 5000);
setTimeout(function() { $('input#PrincipalPolicyHolder_EmploymentOccupationDescription').keyup(); }, 6000);
The delay is required for me to change the focus to the window from console. These jQuery commands are enough to get $('#PrincipalPolicyHolder_EmploymentOccupationDescription').is('focus')
true which is required to generate a list of suggestions, as long as i don't click to somewhere else.
However, the same steps don't work in casperjs environment. This is how i execute;
casper.then(function () {
this.evaluate(function () {
$('input#PrincipalPolicyHolder_EmploymentOccupationDescription').val("soft");
$('input#PrincipalPolicyHolder_EmploymentOccupationDescription').focus();
$('input#PrincipalPolicyHolder_EmploymentOccupationDescription').keyup();
});
});
I also tried to use sendKeys with keepFocus: true
, but never got is(':focus')
check positive. Is there any way to accomplish this?
Edit: I narrowed down the problem to work on a very simple webpage, Here is the code snippet that captures the issue:
var casper = require('casper').create({
verbose: true,
loglevel: "debug"
});
casper.start('http://jsfiddle.net/vhermL99/embedded/result/');
casper.on('remote.message', function(msg) {
this.echo('remote message caught: ' + msg);
});
casper.withFrame(0, function () {
casper.thenEvaluate( function () {
var input = $('#input1');
input.val("value set by jquery");
input.focus();
console.log("is input focussed: " + input.is(':focus'));
});
casper.then(function () {
this.capture('before-sendkey.png');
});
casper.then(function () {
casper.sendKeys('#input1', 'value set by sendKeys', {'reset': true, 'keepFocus': true});
});
casper.thenEvaluate(function () {
console.log("is input focussed: " + $('#input1').is(':focus'));
});
casper.then(function () {
this.capture('before-sendkey.png');
});
});
casper.run();
The expectation is having .is(':focus')
true in one of two methods.
Upvotes: 0
Views: 1178
Reputation: 81
this is not a good idea at all to set timeouts.
Considering you are using the latest CasperJS release, it's better to use the waitFor utility method: http://casperjs.readthedocs.org/en/latest/modules/casper.html?highlight=waitfor#waitfor.
Also, you may emulate the behavior to "type" into your text input by using the sendKeys method: http://casperjs.readthedocs.org/en/latest/modules/casper.html?highlight=waitfor#sendkeys.
Regards,
Upvotes: 0
Reputation: 61952
You can do the same thing in CasperJS that you have done in the browser console too. You only need to be aware that you break out of the control flow of CasperJS when you start asynchronous processes in the page context. So you need to wait for results in the casper context, because now you have effectively two control flows.
casper.thenEvaluate(function () {
$('input#PrincipalPolicyHolder_EmploymentOccupationDescription').val("soft");
setTimeout(function() {
$('input#PrincipalPolicyHolder_EmploymentOccupationDescription').focus();
}, 5000);
setTimeout(function() {
$('input#PrincipalPolicyHolder_EmploymentOccupationDescription').keyup();
}, 6000);
});
casper.wait(10000, function(){
// waited 10 seconds, so do something with the autocomplete result
});
You can also try it with the native PhantomJS sendEvent
function:
casper.then(function () {
this.evaluate(function(){
var el = document.querySelector('input#PrincipalPolicyHolder_EmploymentOccupationDescription');
el.focus();
});
this.page.sendEvent('keypress', 'soft');
});
casper.wait(10000, function(){
// waited 10 seconds, so do something with the autocomplete result
});
Upvotes: 1