onbeforeunload function not working properly - javascript

$(function(){
var a=document.getElementById('text_editor_textarea'),regEx=/^\s*$/,
updateOrig = function() {
var sc = $(a).data('sceditor');
if(sc){
sc.bind('keypress', sc.updateOriginal);
sc.blur(sc.updateOriginal);
}else {
setTimeout(updateOrig , 200);
}
};
updateOrig();
if(a.value !== "" && regEx.test(a.value) ){
window.onbeforeunload = function(){
return "You have a post waiting to be submitted";
};
}
});
This code should check if there is data in a and if there is onbeforeunload the alert should be prompted. It works except that even if there is no data in the textarea it still is prompted. Am I doing something wrong here?

Just do a.value !== "" instead of a.value !== null || a.value !== "" inside of this if block:
if (a.value !== null || a.value !== "") {
window.onbeforeunload = function () {
return "You have a post waiting to be submitted";
};
}
Also, flip the if and the event function assignment to this:
window.onbeforeunload = function () {
if (a.value !== "") {
return "You have a post waiting to be submitted";
}
};
I didn't realize this before, but only on page load would your message get called since otherwise the assignment wouldn't occur since the textarea would be empty when you first opened the page.
jsFiddle

Related

Javascript OR statment result different in Chrome

I have a problem with following code:
var status = null;
var action = 1;
function test() {
if(status != null || action == 3) {
alert('Why am i her?');
}else {
alert('I should be here');
}
}
test();
I get expected results in Firefox and IE alert('I should be here'). But in Chrome i get alert('Why am i here?').
I'm not able to reproduce this for you, but I might just have the answer:
if(status !== null || action === 3) {
Compare the variable not just by value but also by type, by using an extra =
status and action var names seem too good to not be system reserved. maybe your chrome has something running with a status var allocated. try changing them to something else and see if it makes a difference.
var myStatus = null;
var myAction = 1;
function test() {
if(myStatus != null || myAction == 3) {
alert('Why am i her?');
}else {
alert('I should be here');
}
}
test();

Javascript data not loading at first time

I have the following code, it have one problem, on first load it wont display anything, but when I press next button on my carousel, everything will work perfectly, so the problem resides somewhere on the first call, as the other calls are exactly the same but theese are working :S
I wont put where the display code, as it is working because it's only jquery adding data to divs and stuff, but as I said, on first time, data is empty.
var dificildecision = function() {
}
dificildecision.prototype = {
is_animating : false,
base_url : window.base_url,
current_decision : null,
decisiones_seen : 0,
historial_decisiones : {
"decisiones" : []
},
is_previous : false,
previous_id : 1,
next_decision : function(replace) {
if (this.is_animating != true) {
this.is_animating = true;
if (this.is_previous) {
decision = this.get_decision(this.previous_id);
} else {
if (this.get_current_decision() === false)
decision_id = 1;
else
decision_id = this.current_decision.id;
this.get_new_decision(decision_id);
decision = this.get_current_decision();
$('#decision-carousel').html("This is: " + decision.key);
this.is_animating = false;
this.is_previous = false;
}
} else {
// console.log("Slow down");
}
},
get_new_decision : function(decision_id) {
if (typeof (decision_id) === "undefined" || decision_id === null) {
decision_id = 1;
}
$.getJSON('http://echo.jsontest.com/key/value', this.set_current_decision);
},
get_current_decision : function() {
return (this.current_decision) ? this.current_decision : false;
},
set_current_decision : function(decision) {
// THIS DOESN'T WORK
this.current_decision = decision;
// THIS WORK SECOND+ TIME EXECUTED
//dificildecision.prototype.current_decision = decision;
}
};
var dificil = new dificildecision();
dificil.next_decision(true);
$('#testlink').on('click', function(){
dificil.next_decision(true);
});
With this code nothing is displayed on console, but if I change
set_current_decision : function(decision) {
this.current_decision = decision;
}
to
set_current_decision : function(decision) {
dificildecision.prototype.current_decision = decision;
}
It outputs the object only when the carousel function is handled, but not at page load...
I've also tried to change
get_new_decision : function(decision_id) {
if (typeof (decision_id) === "undefined" || decision_id === null) {
decision_id = 1;
}
$.getJSON('/~robhunter/dificildecision/web/app_dev.php/new/'
+ decision_id, this.set_current_decision);
},
to
get_new_decision : function(decision_id) {
if (typeof (decision_id) === "undefined" || decision_id === null) {
decision_id = 1;
}
$.getJSON('/~robhunter/dificildecision/web/app_dev.php/new/'
+ decision_id, dificildecision.prototype.set_current_decision);
},
But exactly as original code, nothing is displayed ever :S
You can try it out here http://jsfiddle.net/TUX5a/
Try:
$(document).ready(function() {
// window.dificildecision = new dificildecision();
var dificildecision = new dificildecision();
}
And use this inside your dificildecision.prototype.next_decision
Explanation:
When you declare your function using this line: function dificildecision() in global scope, there will be a new property named dificildecision assigned to your window object.
When you call window.dificildecision = new dificildecision();, this property (a reference to a function) is replaced with an instance
=> this would cause unpredictable behavior in the application and should be avoided.
Update after the OP created a fiddle:
I have checked your fiddle, you have problem with asynchronous nature of ajax. When you call decision = this.get_new_decision();, you fire an ajax request to server to get the decision. And the next line you call decision = this.get_current_decision();, the decision is not set yet ( the callback set_current_decision is not run yet).
There are 2 solutions to this problem:
Use synchronous ajax by using $.ajax function with async: false. However, this solution is not recommended because it will block the browser and degrade user experience.
Use callback or promise API (recommended). Below is a demo how to do this:
DEMO
Return a promise from getJSON
get_new_decision : function(decision_id) {
if (typeof (decision_id) === "undefined" || decision_id === null) {
decision_id = 1;
}
return $.getJSON('http://echo.jsontest.com/key/value', this.set_current_decision);
}
And return it again inside next_decision:
next_decision : function(replace) {
if (this.is_animating != true) {
this.is_animating = true;
if (this.is_previous) {
decision = this.get_decision(this.previous_id);
} else {
if (this.get_current_decision() === false)
decision_id = 1;
else
decision_id = this.current_decision.id;
decision = this.get_new_decision(decision_id);
this.is_animating = false;
this.is_previous = false;
}
} else {
// console.log("Slow down");
}
return decision;//this could be a promise or a value.
},
Use $.when to execute a callback when data is ready, if the parameter is not a promise, the callback will be called immediately (considered it as a resolved promise):
$.when(dificil.next_decision(true)).then(function(decision){
$('#decision-carousel').html("This is: " + decision.key);
});
This code is just a demo of how to use promise API, you may need to restructure your code to make it fit into this programming model.
Actually I've found that I needed to change get_new_decision method to use $.ajax instead of $.getJSON and set async: false to store variable this way
get_new_decision : function(decision_id) {
if (typeof (decision_id) === "undefined" || decision_id === null) {
decision_id = 1;
}
$.ajax({
async : false,
type : 'GET',
url : '/~robhunter/dificildecision/web/app_dev.php/new/'
+ decision_id,
dataType : 'json',
// data: myData,
success : function(data) {
dificildecision.prototype.set_current_decision(data);
}
});
},
And change into set_current_decision method to use this.current_decision = decision; :)
With this change, everything works perfectly!

Javascript If statement evaluation not working correctly [duplicate]

This question already has answers here:
How do I return the response from an asynchronous call?
(41 answers)
Closed 9 years ago.
So this is my code for some ajax that I'm doing.
function check_password(){
var username = $("#username").val();
if(username.length > 0){
var bool = -1;
$('#Loading2').show();
$.post("check_login.php", {
username: $('#username').val(),
password: $('#password').val(),
},
function(response) {
$('#Info2').fadeOut(500);
$('#Loading2').hide();
bool = response.indexOf('success');
setTimeout("finishAjax('Info2', '"+escape(response)+"')", 450);
$('#password').after(bool);
return response.indexOf('success');
});
}
}
function finishAjax(id, response){
$('#'+id).html(unescape(response));
$('#'+id).fadeIn(750);
}
and here I'm trying to handle the return value from the check password function.
jQuery(function() {
$("#submitl").click(function(){
$(".error").hide();
var hasError = false;
var passwordVal = $("#password").val();
var username = $("#username").val();
if (username == '') {
$("#username").after('<span style="color:red" class="error"><p></p>Please enter a username.</span>');
hasError = true;
} else if (passwordVal == '') {
$("#password").after('<span style="color:red" class="error"><p></p>Please enter a password.</span>');
hasError = true;
} else if (check_password() != 73) {
hasError = true;
$("#password").after(check_password());
}
if (hasError == true) {
return false;
}
});
});
For some reason the if statement is returning true even when the index(return value) is 73. I test this by using jquery within the if statement to print out the value of the returning function and it prints out 73. I have a feeling my error is caused because of dynamically typed variables in javascript.
Typical asynchronous behavior issue of AJAX calls. You return response.indexOf('success'); from your AJAX callback, but since it is an asynchronous callback, there is nothing to return to. The rest of you check_password function has long finished when the callback is being called.
To fix this you need to completely restructure your code. In your click handler, you first need to call your post() function and then in the callback you need to go through your if/else if blocks.
Your function ´checkpassword()´ doesn't actually return a value.
It launches a request to a PHP-file and immediately returns (without a value).
You do specify a callback for when the call returns, but that never gets back to your original function.
You could do something like this:
function check_password(callback){
var username = $("#username").val();
if(username.length > 0){
var bool = -1;
$('#Loading2').show();
$.post("check_login.php", {
username: $('#username').val(),
password: $('#password').val(),
}, function(response){
$('#Info2').fadeOut(500);
$('#Loading2').hide();
bool = response.indexOf('success');
setTimeout("finishAjax('Info2', '"+escape(response)+"')", 450);
$('#password').after(bool);
callback(response.indexOf('success'));
});
}
}
function finishAjax(id, response){
$('#'+id).html(unescape(response));
$('#'+id).fadeIn(750);
}
jQuery(function(){
$("#submitl").click(function(){
$(".error").hide();
var hasError = false;
var passwordVal = $("#password").val();
var username = $("#username").val();
if (username == '') {
$("#username").after('<span style="color:red" class="error"><p></p>Please enter a username.</span>');
hasError = true;
}
else if (passwordVal == '') {
$("#password").after('<span style="color:red" class="error"><p></p>Please enter a password.</span>');
hasError = true;
}
else (
check_password(function(returnValue) {
if (returnValue != 73) {
hasError = true;
$("#password").after(check_password());
}
})){
}
if(hasError == true) {return false;}
});
});
Of course, this code just shows you how to get the value inside the other function, but you still need to handle the fact that you're other function doesn't return immediately and that for example the value of HasError is not set immediately.
Your problem is that you return from within a inner function, which will never ever work in JavaScript. Pass a callback:
function check_password(callback) {
// ...
callback(response.indexOf('success'));
}
// ...
check_password(function(result) {
if(result != 73) {
// ...
}
})
Just search for JavaScript AJAX and you will find a lot of sites to study. Here is one of them: http://www.html5rocks.com/en/tutorials/async/deferred/

What's wrong with this javascript code?

var act = false;
var newprod = prompt("tell me somthing", "");
if (newprod != '' && newprod != null) {
$.ajax({
//posting code here
});
}
if (act != false) { document.location.href = window.location; }
The page is refresh in every condition even act false or not.
It is fired on an event.
Can anyone tell me why it page is refreshed in all condition?
var act = false;
var newprod = prompt("tell me somthing", "");
if (newprod) { // not null, undefined or 0
$.ajax({
//posting code here
});
}
if (act) { window.location.reload(1); }
assuming that is what the code was supposed to do. document.location is deprecated and in theory read-only.
This should work
if( newprod != null && newproda.length != 0) {
//Execute the code
}
To the reason why it was always working was that newprod was not the same as ''.
As the question is what is wrong with that JavaScript code i will advise.
if(act) {
document.location.href = window.location;
}
You may want to learn more about false-y values in JavaScript. My guess is that your if statement is giving you some problems because it does not compare the way you think it should compare.

jquery function doesn't return values correctly

I have this function
$.fn.validate.checkValidationName = function(id) {
$.post("PHP/submitButtonName.php", {checkValidation: id},
function(data) {
if(data.returnValue === true) {
name = true;
} else {
name = false;
}
**console.log("name = "+name); **//this prints out "true"****
}, "json");
};
and this .click function that calls it. All the variables are declared outside this function so that they should be accessible by other functions
$('.submitBtn').click(function() {
//clears the array before re-submitting the click function
nameValues = [];
usernameValues = [];
emailValues = [];
name = false;
username = false;
email = false;
//for each of the input tags
$("input").each(function() {
//if the curent input tag has the class .name, .userpass, or .email
if(($(this).hasClass("name"))) {
nameValues.push($(this).val());
} else if(($(this).hasClass("userpass"))) {
usernameValues.push($(this).val());
} else if(($(this).hasClass("email"))) {
emailValues.push($(this).val());
}
});
//call the checkValidation function with the array "values"
$.fn.validate.checkValidationName(nameValues);
$.fn.validate.checkValidationUsername(usernameValues);
$.fn.validate.checkValidationEmail(emailValues);
console.log("name = "+name); //but this prints out "false"
console.log("username = "+username);
console.log("email = "+email);
if((name === "true") && (username === "true") && (email === "true")) {
alert("Everything checks out great");
} else {
alert("You missed one!");
}
});
When I click the link to trigger the first function, it returns the value as "true" inside the function, but when I console.log("name"+name); in the .click function after the function call, it prints out false.
Why is this? Do I need to return something from the checkValidatoinName function?
$.post is asynchronous, which means that it won't wait for the result to get back before proceeding. You're probably initializing name to true somewhere, and it's getting true the first time, but all the other times, it's false, because the AJAX from the first one finished and set it to false.
Try using $.ajax instead of $.post, and set async to false in the options. The $.post documentation shows the options that $.post would give to $.ajax.

Categories