My javascript function cannot be found - javascript

I have the following:
$(function () {
$.ajaxSetup({ cache: false });
var dialogs = {};
var formSubmitHandler = function (e) {
...
}
}
then in another script I try to call
function dialogClick(link) {
$.get(viewUrl + parameters)
.success(function (content) {
if (content.match(/^[eE]rror/)) {
mvcOnFailure(data)
} else {
$.modal({
title: title,
closeButton: true,
content: content,
width: false,
resizeOnLoad: true
}).find('form').submit(formSubmitHandler).end();
}
})
Note that I have cut out parts of the script to make it easy to read. There are no script errors showing just the following error:
In the second script I get an error message saying "SCRIPT5009: 'formSubmitHandler' is undefined' in Internet Explorer.
Am I calling it wrongly? I thought the function would be global and when I check
the script that it is inside of is attached to the page.

No, it's not global; your "formSubmitHandler" function is declared within the "ready" callback in the first block of sample code you posted. It's therefore private to that function.
What you could do, if you really want a global function, is:
window['formSubmitHandler'] = formSubmitHandler;
in the first function. Or, alternatively, you could make it a jQuery "global" function:
$['formSubmitHandler'] = formSubmitHandler;
In that case, you'd get to it as $.formSubmitHandler.

Try moving your function out of the function block e.g
$(function () {
$.ajaxSetup({ cache: false });
var dialogs = {};
}
var formSubmitHandler = function (e) {
...
}

formSubmitHandler only exists within the function scope you declare it, since you used the var variable.
You need to either:
declare dialogClick in the same scope
declare formSubmitHandler in the global scope, using window.formSubmitHandler or simply function formSubmitHandler(){}

formSubmitHandler is a function declared in a scope not visible for the dialogClick() function
So
Either you declare formSubmitHandler as global
or you define the function dialogClick inside document.ready function (and formSubmitHandler is reachable since is in a parent scope)

Related

Passing variable that detects specific button in jQuery

I created function that recognize which post has been clicked on.
jQuery(document).ready(function() {
jQuery(.recognize-post).on("click", function() {
var clickedButton = jQuery(this).data("id")
console.log("click button with post id: ", clickedButton)
button-id = "recognize-post"
...
...
})
})
}
html
<button id="recognize-post" class="recognize-post" data-id="<?php the_title() ?>">POST</button>
Code above works perfectly and in recognizes the correct post, but I need to pass clickedButton outside of this function and I don't know how to do so.
I need to have it in else if function, this is my attempt
else () {
...
} else if (button-id === "recognize-post") {
console.log(clickedButton)
}
Here the problem comes, clickedButton is underfined and need it to recognize post in exactly the same way how in on click function. Is it possible?
You can make a separate function that takes in the information you want to preserve.
// make a new function
function doSomethingWithTheIdAndBtn(id, btn) {
// take in arguments that represent the id or btn or whatever you need
else () {
...
} else if (id === "recognize-post") {
console.log(btn)
}
}
jQuery(document).ready(function() {
jQuery(.recognize-post).on("click", function() {
var clickedButton = jQuery(this).data("id")
console.log("click button with post id: ", clickedButton)
button-id = "recognize-post"
doSomethingWithTheIdAndBtn(button-id, clickedBtn) // call the function
...
...
})
})
}
So, the issue here is that if you declare a variable function in a given "scope" — in your case, the anonymous function's scope — it will only be defined inside of that scope. If you want to use the variable outside of the function, you need to declare it outside of the function.
So, for instance, if your code was
function foo() {
var myVariable = 0;
}
foo();
// This will throw an error, cuz myVariable is not defined in this scope
console.log(myVariable);
you could fix it by declaring the variable outside of the function's scope
var myVariable; // declare it outside of the function
function foo() {
myVariable = 0; // give it a value inside of the function
}
foo(); // call foo so that myVariable has a value
console.log(myVariable); // this will print 0. Success!

Is it bad practice to instantiate variables inside of $(document).ready as opposed to globally declaring them?

I'm trying to avoid the use of global variables in my code, so I'm trying to use a work around by declaring them inside of $(document).ready and passing them as parameters to functions outside of $(document).ready, updating them, and then returning the updated value from those functions to manipulate the variables inside of $(document).ready.
Another way around this is to use hidden input fields to store variables but I also heard that was bad practice.
I'm wondering if I should just use global variables, do it the way I'm currently doing it, or use hidden input fields?
Below is a brief example of what I'm trying to accomplish. The variable validations is the variable I want to be able to use and update.
$(document).ready(function(){
var validations = [];
$('#inp').keypress(function(e){
if(e.which == 13){
e.preventDefault();
scanValidation(validations, function(valid){
validations = valid;
});
}
});
}):
function scanValidation(valid, cb){
var scanval = $('#inp').val();
if(valid.includes(scanval)){
//display error
}
else{
var validarr = valid.slice();
validarr.push(scanval);
var myData=JSON.stringify({ "name":"user1", "validations":validarr});
//Makes an ajax call to see if the sent array validarr is a valid request
apiCall(myData,'scanValidation',function(decoded) {
if (decoded.Status!="ERROR") {
valid = validarr;
}
else {
//display error
}
return(cb(valid));
});
}
}
Any variables declared within the immediately executed function below will NOT be in the global scope.
(function () {
var someVar = 'someValue';
$(document).ready(function() {
});
})();
Is it bad practice to instantiate variables inside of $(document).ready as opposed to globally declaring them?
No, not at all! Variables should always be declared in the scope they're needed in, nowhere else.
Another way around this is to use hidden input fields to store variables but I also heard that was bad practice.
I've never heard of that, but yes it definitely sounds like a bad practise. That's just the same as a global variable, but a global variable stored in the DOM for some odd reason.
I'm trying to avoid the use of global variables in my code, so I'm trying to use a work around by declaring them inside of $(document).ready and passing them as parameters to functions outside of $(document).ready, updating them, and then returning the updated value from those functions to manipulate the variables inside of $(document).ready.
That, admittedly, is a bit weird.
The easiest way to improve this is to move the function declaration inside the ready handler as well, and just access the variable there directly - with the additional bonus of not having a scanValidation global variable:
$(document).ready(function() {
var validations = [];
function scanValidation() {
var scanval = $('#inp').val();
if (validations.includes(scanval)) {
//display error
} else {
var validarr = validations.slice();
validarr.push(scanval);
var myData = JSON.stringify({"name": "user1", "validations": validarr});
// Makes an ajax call to see if the sent array validarr is a valid request
apiCall(myData, 'scanValidation', function(decoded) {
if (decoded.Status!="ERROR") {
validations = validarr;
} else {
//display error
}
});
}
}
$('#inp').keypress(function(e){
if(e.which == 13){
e.preventDefault();
scanValidation();
}
});
});
If you want to make scanValidation reusable, so that it could be called from other places as well with its own array, I would suggest to create a factory function that creates validators, each of which is a closure over its own array. That way, the array is declared where it belongs, so that the user of the function does not have to store the state for them:
function makeScanValidator(display) { // any other configuration
var validations = [];
// returns closure
return function scanValidation(scanval) { // take it as an argument
if (validations.includes(scanval)) {
display(/* error */);
} else {
var validarr = validations.concat([scanval]);
var myData = JSON.stringify({"name": "user1", "validations": validarr});
apiCall(myData, 'scanValidation', function(decoded) {
if (decoded.Status!="ERROR") {
validations = validarr;
} else {
display(/* error */);
}
});
}
}
$(document).ready(function() {
var validate = makeScanValidator(function display() { … });
$('#inp').keypress(function(e){
if(e.which == 13){
e.preventDefault();
validate(this.value);
}
});
});

Sharing variable between functions in jQuery

I'd like to share my variable called str with setInterval function. Its needed to build whole url passing to php script. It works fine with ajax function and GET parameter is passing to php script, but I've got some trouble with setInterval function. I dont know to share the same str variable between these two functions. I enclose my code below:
$(function () {
$(document).ready(function () {
var ultimox;
var ultimoy;
$('#list li a').on('click',function() {
var str = $(this).data('driver');
$.ajax({
url: "live-data.php" + str,
type: 'get',
success: function(DatosRecuperados) {
$.each(DatosRecuperados, function(i,o){
//some body of function
});
setx(DatosRecuperados[(DatosRecuperados.length)-1].x);
sety(DatosRecuperados[(DatosRecuperados.length)-1].y);
$('#container').highcharts({
//this part draws chart
}});
});
});
setInterval(function () {
$.get( "live-data.php?Consultar=1" + str , function( UltimosDatos ) {
//this part draws updated chart
}
});}, 1000);
function getx(){return ultimox;}
function gety(){return ultimoy;}
function setx(x){ultimox=x;}
function sety(y){ultimoy=y;}
});
In JavaScript, scope refers to the current context of your code. Scopes can be globally or locally defined. Understanding JavaScript scope is key to writing good javascript. You’ll need to understand where variables/functions are accessible.
Javascript scope can be thought of as function scoped. You should take the setInterval() function and move it inside $(document).ready(function() { ... });. Since var str; is declared in that function $(document).ready(function() { ... }); the function setInterval can now read str.
I would recommend not polluting the global namespace unless you need to. By this I mean not having the var str; outside of $(document).ready(function() { ... }); . Keep the variable where you need it.
You can have a global variable in JQuery, try the following example.
<script>
var str = "";
$(document).ready(function() {
//do something with 'str'
//e.g. str = 'Some value';
});
function setInterval()
{
//do something with 'str'
//e.g. str = 'Some other value';
}
</script>

How do I access this variable without a global?

I'm trying to figure out how to make this work.
function foo(a) {
$('#this-button').show();
}
function buttonClicked() {
//get access to var a
}
HTML
<button id="this-button" onclick="buttonClicked();">
This is a simplified version of what I have but the idea is the same.
foo takes a variable, and then makes a button visible. When the button is clicked, I want to do more things with var a.
So like wait until the button is clicked to continue the function?
Can't seem to figure it out.
Thanks
Bind the click handler using jQuery. You can use jQuery.Proxy to bind a as an argument:
function foo(a) {
$('#this-button').show().click( $.proxy( buttonClicked, null, a ) );
}
function buttonClicked(a) {
// Use a here
}
and remove the JavaScript from your html attribute:
<button id="this-button" />
EDIT, if all you want to do is execute some code after the button is clicked, you can do something like this:
function foo(a) {
// Code up here executes before the button is clicked
$('#this-button').show().unbind( 'click.foo' ).one( 'click.foo', function ( ) {
console.log( a );
// This code executes after the click, and has access to a
} );
// Code down here executes before the button is clicked
}
You use an event handler content attribute. Those have access to:
Properties defined in the element (if any)
Properties defined in the form owner of the element 8if any)
Properties defined in the document
Properties in the global object (i.e. global variables).
Therefore, you can add the variable as a property of the element:
function foo(a) {
$('#this-button').show().prop('myProp', a);
}
function buttonClicked(a) {
alert(a);
}
foo(123);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<button id="this-button" onclick="buttonClicked(myProp)">Click me</button>
Of course, using an event handler IDL attribute or an event listener would be a better practice.
This is the reason for a global, either that or create an object with functions that could use closure.
You can always access the global scope:
window.a = a;
But this is generally bad practice. Can you restructure the code so that both places have a available.
Ie
var a = {}; //set a
$("#button").click(function(){
// a is available here
});
foo(a);
HTML
<button id="this-button">
JS
function foo(a) {
$('#this-button').show();
$('#this-button').click(buttonClicked);
function buttonClicked() {
//a can be accesed here
}
}
Put buttonClicked method inside foo to get access of variable a
There's a few different ways to skin this cat but one method is to use a closure to capture the a variable:
var myButton = document.getElementById('this-button');
function foo(a) {
myButton.addEventListener("click", buttonClicked(a));
...
}
function buttonClicked(a) {
return function() {
console.log('buttonClicked', a);
}
}
foo('Success!');
In this case, the function buttonClicked returns a function that captures the value of a when run by the foo function. This resulting function is then passed to the event handler and run when triggered.
See the fiddle here: https://jsfiddle.net/ToddT/ae5h1src/
You could use HTML5 localstorage...
function foo(a) {
$('#this-button').show();
localStorage.setItem("variable_a", a); // variable in localstorage =variable_a
}
function buttonClicked() {
localStorage.getItem('variable_a');
//get access to var a
}
HTML5 localstorage allows you to store data on the client browser, and you can access it via getItem()... more info here: [w3schools], [jenkov.com]
Use closure.
(function(){
var dummy_a;
function foo(a) {
//$('#this-button').show();
dummy_a = a;
}
function buttonClicked() {
//get access to var a
alert(dummy_a)
}
foo(2)
buttonClicked()
})();

Calling a custom function in JQuery

I want to call a JavaScript function that I made after a JQuery event has been called. I defined a function called scrambleDot earlier like this var scrambleDot = new function()
{ //my code }. Here's the code that I tried to use:
$('#reveal').click(function() {
$('.cover').css({'visibility':'hidden'});
$('#under').css({'visibility':'visible'});
})
$('#conceal').click(function() {
$('scrambleDot');
})
})
You have to call it just like:
scrambleDot();
To define a function, you don't need the new operator, so you should have:
var scrambleDot = function() { //my code }
If it still throws an error, it means it was defined in other scope. To make it globally accesible, do this when defining it:
window.scrambleDot = function() { //my code }
Cheers
We have to use new keyword, only when the function is used as a constructor for new Objects. So, the definition should not use new.
var scrambleDot = function() { //my code }
If the function need not be created dynamically, I would recommend
function scrambleDot() {
...
}
To invoke the function, simply do
scrambleDot();
For that call the function instead of selecting an element as:
$('#reveal').click(function() {
$('.cover').css({'visibility':'hidden'});
$('#under').css({'visibility':'visible'});
})
$('#conceal').click(function() {
scrambleDot();
});
And also, you write functions as:
function scrambleDot () {
// your code
}
It is a better practice than the variable one.

Categories

Resources