Accessing Closures In SetTimeout?
Sep 20, 2011
When writing JS, I try to encapsulate my code somehow. For instance, in the example below, I have a function ('testFunc') that's encapsulated within jQuery's document.ready callback function :
Code:
$(function(){
var testFunc = function(x){
x++;[code]...
If I then start using JS's base timer functions like settimeout, I've always been unsure of how to access the 'testFunc' function. As I understand it, even if the timer functions are called inside the same function, as in...
Code:
$(function(){
var testFunc = function(x){
x++;
return x;
}
var timer = setTimeout("testFunc", 100);
});
... they will lose the scope of the jQuery callback - instead the timer functions will only be able to access objects in the global scope.
View 5 Replies
ADVERTISEMENT
Nov 16, 2010
Arg, I'm losing hair. I'm having trouble understanding something extremely basic and important. I have functions who call functions who call functions.. but I'm having trouble doing anything useful with their results. I can't seem to "grab" them. They just get garbage collected. Scope is becoming my enemy.
This is also hard to explain because the code is modular, so stuff is calling stuff is calling stuff.
Everything happens inside a large Object.
[Code]...
Where do I have to go to understand basic Javascript things like getting values back out of a function? It's always the same problem I hit every time I use functions to figure out some value. It's always locked away.
If anyone happens to know of some place where one can practice with these things, that would be nice.Closures for morons? Functions for dummies? Something like that. I've got bookmarks of pages explaining functions and values and closures but I can't seem to take that over to what I want to do with them.
View 6 Replies
View Related
Jul 23, 2005
Given the following working code:
function attributes() {
var attr1 = arguments[0] || '_'
var attr2 = arguments[1] || '_'
return (
function (el1, el2) {
var value1 = el1[attr1] + el1[attr2];
var value2 = el2[attr1] + el2[attr2];
if (value1 > value2) return 1;
else if (value1 < value2) return -1;
else return 0;
}
);
}
var a = [
{ a:'smith', b:'john' },
{ a:'jones', b:'bob' },
{ a:'smith', b:'jane' }
];
a.sort(attributes('a', 'b'));
for (var i =0; i < a.length; i++) {
document.write(a[i].a + ', ' + a[i].b + '<br>');
}
My question is, are attr1 and attr2 guaranteed to exist through
the lifetime of a.sort(attributes('a', 'b'))?
As I understand it, the anonymous inner function reference I am
returning is a property of attributes(). As such, when I return a
reference to the anonymous inner function, the outer attributes()
function must continue to exist (as must attr1 and att2) until
there are no further references to the inner anonymous function.
As a result, there is no danger of attr1 or attr2 "disappearing"
during the repeated calling of the anonymous inner function.
Is my explanation basically correct, or am I deluding myself and
I'm just lucky that the garbage collector hasn't recovered attr1
or attr2 while the sort is still going on? In other words, is the
behaviour I'm seeing consistent and predictable, or should I
change my approach?
View 3 Replies
View Related
Oct 18, 2006
I have a question regarding how to prevent memory leaks in Internet
Explorer when using closures. I already knew about the circular
reference problem, and until now was able to prevent memory leak
problems. But I needed to store DOM elements and can't solve it
anymore. So I search the group archive to see if I missed any
valuable information. I found some interesting articles, but somehow
could not apply it to my problem or I did not understand it fully.
In particular the articles that talked about setting variables to
NULL seemed as an easy solution, but I think I didn't understand it,
because it didn't seem to work.
So, let me explain my problem in more detail. I am working on some
very dynamic and complex page. It uses AJAX (XMLHttpRequest) to alter
different parts of the page. This already disqualifies the finalize
method solution to cleanup memory leak problems. I use several
"component classes" to do the work of creating DOM elements in some
container element and provide an easy to use interface for
manipulation the content. For example I can call
component.setBackgroundColor("red")
and the component takes care of changing the style on the correct
DOM element that is encapsulated in the component. In reality the
component uses more complex interface method, but I hope you
get the picture of why I do this.
Let me show you some example code:
function MyComponent()
{
var div;
var handler = null;
this.generate = function generate()
{
div = document.createElement("div");
div.onclick = MyComponent.createClickHandler(this);
// normally more elements are created here
return div;
}
this.setBackgroundColor = function setBackgroundColor(value)
{
div.style.backgroundColor = value;
}
this.getHandler = function getHandler()
{
return handler;
}
this.setHandler = function setHandler(value)
{
handler = value;
}
}
MyComponent.createClickHandler = function createClickHandler(component)
{
return function(event)
{
var handler = component.getHandler();
if (handler != null)
handler(event);
}
}
This "component class" can be used like this:
var container = document.getElementById("container");
var component = new MyComponent();
container.appendChild(component.generate());
....
component.setBackgroundColor("red");
component.setHandler(function(event) {alert("Stop touching me!")});
The problem, of course, is that this code will create a memory leak
in Internet Explorer. I need the component in the event handler to
get the handler dynamically, but the div is stored there too,
creating a circular reference.
One of the things I tried doing is making a DOMStorage "class" like
this:
function DOMStorage()
{
var map = new Object();
this.get = function get(id)
{
return map[id];
}
this.put = function put(id, obj)
{
map[id] = obj;
}
}
var storage = new DOMStorage(); //global
Instead of storing the div element directly in the component, I store
it under an id in the DOMStorage and use it to retrieve it later.
This actually prevented the memory leak. I don't really understand
why, because I still see a circular reference. Maybe Internet
Explorer does not count references in the global scope as a circular
reference? When I move the global storage to inside the container
object I get the memory leak again.
Unfortunately I am unable to use a global DOMStorage, because the
"component class" in instantiated many times, and they must all have
their seperate DOM elements.
Perhaps I have to generate unique ID's when I put a DOM element into
the global storage? It seems so over-the-top for something that works
perfectly fine in Firefox.
What are my alternatives?
View 2 Replies
View Related
Aug 7, 2009
Is it better to use prototype when declaring classes or is it better to use closures inside the definition, e.g.:
Code:
Code:
What are the main differences, and is one method preferred to the other?
As use of the class is the same, I can't really decide which to use.
View 2 Replies
View Related
Aug 22, 2010
I have some confusion about the scripts below:
1) is getRule a local variable or global variable, as it has no var keyword, yet it is an inner function of Validation? So without var, I think global, but being an inner function, I think local. So I'm not sure which.
2) In this line of code: var rule = $.Validation.getRule(types[type]), getRule returns rules, which is just a local variable in Validation. I always see that you return functions, but how does returning a local variable that's just an object literal and not a function be able to return true or false? Now the value of rules is an object literal, and this object returns true or false. So we are basically allowed to use return keyword with local variables that are object literals and not functions?
3) In this line, is foo(age) being called, or is it just being assigned to bar OR is it being called and THEN assigned to bar: var bar = foo(age);
4) Now for the most confusing: age is obviously an object reference as opposed to a literal in the example. Does that make a difference in regards to closures?
Note that I read a number of books, including JavaScript Programmer Reference and Object Oriented JavaScript and jQuery cookbook, which compare primitives vs reference types and how primitive types store directly in memory whereas reference tpyes reference memory, so if one reference changes, they all change where primitive remains ingrained. But when assigning a function as a reference like this, how does that affect the object "age" when passed into bar?
Code:
(function($) {
/*Validation Singleton*/
var Validation = function() {
var rules = {
email : {
check: function(value) {
if(value)
return testPattern(value,".+@.+..+");
return true;
}, .....
$.Validation = new Validation();
})(jQuery);
Code:
function foo(x) {
var tmp = 3;
return function (y) {
alert(x + y + tmp);
x.memb = x.memb ? x.memb + 1 : 1;
alert(x.memb);
}}
var age = new Number(2);
var bar = foo(age); // bar is now a closure referencing age.
bar(10);
View 3 Replies
View Related
Jul 25, 2011
I think the last thing people seem to learn about in JavaScript when they're not coming from other programming languages is variable scope. Some even get all the way into AJAX without having learned about scope, and this is a time when it's really needed. Although the scope of JavaScript variables is non-complex by nature, it's something we should all get a full understanding for before we move too far.
Section 1: What is "scope"?
Section 2: The "var" keyword
Section 3: The "this" keyword
Section 4: Closures or "Anonymous functions and self-invoking closures
View 5 Replies
View Related
Oct 16, 2010
I am confused about the true difference between the two below examples.
first example:
// Demonstrating a problem with closures and loops
var myArray = [“Apple”, “Car”, “Tree”, “Castle”];
var closureArray = new Array();
[code]....
Here we iterate through the length of myArray, assigning the current index of myArray to theItem variable. We declare closureArray 4 times as an anonymous function. The anonymous function in turn declares the predefined write() function, which is passed parameters. Since write() is in closureArray() a closure is created??? During each iteration, theItem is reassigned its value. The four closures reference this value. Since they reference this same value and since this value is reassigned ultimately to the value of the fourth index position, tHe time we execute closureArray later on, all four closures output the same string. This is because all four closures are within the same scope "the same environment" and therefore are referencing the same local variable, which has changed.
I have a couple of problems with this example:
1) I thought a closure is a function that is returned - the inner function is not returned above.
2) theItem is not even a local variable of the parent function (closureArray) - I thought in order for a closure to work, the inner function only accesses the local variables of the outer function, but in this case the local variable is defined OUTSIDE of the parent function.
3) the "the four closures are sharing the same environment." The thing is even in the second example, they are sharing the same environment.
Second example:
// A correct use of closures within loops
var myArray = [“Apple”, “Car”, “Tree”, “Castle”];
var closureArray = new Array();
[code]....
Here we iterate over the length of myArray (4 times), assigning the index of myArray to theItem variable. We also return a function reference to the closureArray during each iteration (closureArray[i]), where i is index number so we assign 4 functon references. So when we iterate through myArray, we immediatelly call the writeItem() fucntion passing an argument of theItem at its current value. This returns a child anonymous function and when that child function is called, it will execute a block that calls the predefined write() method. We assign that returned anonymous function to the variable closureArray. Hence, closureArray holds a reference to that anonymous function. So closureArray during each iteration holds a reference to the anonymous function and we later call closureArray, which in turn calls the anonymous function, therefore calling the predefined write() function to output the local variable of the parent function. This outputs each distinct index of myArray.
This is because since we created the closure, when we call writeItem, passing theItem argument, since theItem is a local variable of the parent function of the closure, it is never destroyed when we later call closureArray (the reference to the child anonymous function)? Yet weren't we using a closure in the first example as well? So whey wasn't those variables preserved?
I don't think it has anything to do with assigning a returned anonymous function to closureArray. Even though an anonymous function creates a new memory position in the javascript engine, therefore not overwriting the other function references we create during the iteration, it's still referring to a local variable declared outside the reference. So if it's about the closure retaining value of parent's local variable even after exiting the parent function allowing for the current indexes to be preserved, then why did the closure in the first example fail to retain each index?
View 7 Replies
View Related
Jul 12, 2010
I have the following function that's supposed to say "Please make a guess" 20 seconds after an initial confirmation is displayed. However, it's immediately displayed as soon as someone hits "Cancel". If I change it's time to 40000 (20 seconds after the initial function is called), it does do it 40 seconds total, so it kind of does what I want. So it seems that the second setTimeout is initiated from the time the script is called generally, but I'm looking for a way specifically to have the 20 seconds start only after the "cancel" button is hit.
[code]...
View 1 Replies
View Related
Jul 23, 2005
I'm wondering if its because I don't fully understand setTimeout(). I have a web page that calls a function on the Onload. This function calls two separate functions and then
uses setTimeout() to keep calling itself. Each function randomly generates
a number and then I update the image.src with that.
If I run setTimeout() on just one function by itself, it almost always displays a new pic...but when I put the setTimeout() in the startup function a get a lot of duplicates. I've been watching it for a long time and I don't think it's a coincidence. Any idea
as to why it seems like both functions don't run/update the pic all the time? If I uncomment the line, alert("hello"), it runs all the time? Code:
View 3 Replies
View Related
Jul 1, 2006
i'm working on a small idea and i would like to run this code:-
document.getElementById(id).style.height = origheight+"px";
after a set time period (about 20ms i guess ;) ), however, the following line creates errors:-
var t1 = setTimeout("document.getElementById('+id+').style.height = '+origheight+'px' ",0.5);
any ideas why?
View 6 Replies
View Related
Jul 23, 2005
<img src=http://xxx.com/yyy.jpg
onmouseover="settimeout("document.location='http://www.google.com'"),
2000">
I want to have a 2 seconds delay before it is directed to an URL when the
mouse is over the image.
However, it seems that setTimtOut does not like parameters in the function
part.
View 5 Replies
View Related
Feb 21, 2006
I have a HTML page with a form with 2 buttons like this
....
<input type="button" value="Add" onClick="ClickAdd();"/>
<input type="button" value="Reset" onClick="ClickReset();"/>
....
I also have this javascript code:
----------------------------------------
function ClickAdd() {
setTimeout(test.Add, 100);
//test.Add();
};
function ClickReset() {
setTimeout(test.Add, 100);
//test.Reset();
};
Test = function () {
this.total = 0;
};
Test.prototype.Add = function() {
this.total++;
alert(this);
};
Test.prototype.Reset = function(i) {
this.total = 0;
alert(this);
};
Test.prototype.toString = function() {
return (this.total);
};
test = new Test();
-------------------------------------------
the thing is:
in the ClickAdd function, if i call test.Add() directly, is works ok But if I call it using setTimeout, the /alert(this)/ shows [object Window]....
View 4 Replies
View Related
Mar 11, 2006
Does anyone know whether the ECMA, or an other standard document,
specifies a maximum for the value that can be pass to the setTimeOut()
function in Javascript?
View 28 Replies
View Related
Aug 14, 2006
The below pasted code is my attempt to get the text of a span to change
every second. However, it seems to just set the text of the span to be the last item
in the array. Code:
View 3 Replies
View Related
Apr 3, 2007
I am modifying the suckerfish dropdown code to use settimeout to have
a slight pause before the menus disappear to make it more user
friendly. I have hit a snag with the following statement:
li.
{
timerID=setTimeout('this.getElementsByTagName("UL")
[0].style.display = "none"', timecount);
}
If I put take the statement
this.getElementsByTagName("UL")[0].style.display = "none";
out of the settimeout function, it works. (w/o the pause, obviously).
With the settimeout function, I get "this.getElementByTagName is not a
function" error.
I have tried putting this.getElementsByTagName("UL")[0] is a variable
and then using that in the settimeout function, but then each li will
only open the very last menu in the list. (ie all the menu items open
the last sub menu) Code:
View 4 Replies
View Related
Apr 3, 2007
Can I have two setTimeouts running at the same time - with two
different intervals?
I want to start one timer and, before it times out, start another one
I've tried this and they seems to interfer with one another.
View 7 Replies
View Related
Oct 25, 2007
var SessionTimer;
function StartSessionTimer()
{
SessionTimer = setTimeout('RedirectToSessionTimedOutPage(),60000)
}
function RestartSessionTimer()
{
clearTimeout(SessionTimer);
StartSessionTimer();
}
function RedirectToSessionTimedOutPage()
{
window.location = '/SessionTimedOut.html'
}
When I load the page and call StartSessionTimer(), I know it works because the page redirects after ten minutes (the value of 60000). However, in certain situations I need to be able to call back to the server with AJAX and then have the timer reset - that's when I call the RestartSessionTimer() function. When I do this, for some reason the ten minute window does not get reset.
To troubleshoot, if I remove the second line in the RestartSessionTimer() function the redirect is getting blocked (as planned). However, when I put the second line back in, the page just redirects as originally called - the SessionTimeout value is never
reset properly.
The code above looks good to me, but for some reason the SessionTimeout var does not get reset in the RestartSessionTimer function; it retains its original value?
View 2 Replies
View Related
Jul 20, 2005
I have a pop-up menu; one of those where you scroll over the menu, and
a submenu pops up beneath it. Everything's running smoothly on every
browser I've tested with, except for one problem on every browser: the
"clearing" of the menu.
The menu itself is being called by:
onMouseOver="menu(1)" onMouseOut="clearIt()"
function menu(x) let's "x" refer to a predefined array, which
determines which menu to pop up. That menu is stored in a variable,
showMenu. If x==0, then it changes showMenu to a whitespace, thus
"clearing" the submenu altogether.
clearIt() is a simple function, pasted here:
function clearIt() { setTimeout("menu(Ɔ')", 7000) }
The idea is that the menu will disappear after 7 seconds. The problem
I'm having, though, is that the 7 seconds starts after the first
onMouseOut, and doesn't restart when the visitor mouses over the
second button. So, if I look at the first submenu for 6 seconds, then
when I go to the second button the menu only stays open for 1 second,
instead of starting the timer over.
View 1 Replies
View Related
Mar 19, 2009
Here we are again pondering why setTimeout will not work, or rather mucks things up. This will work. addOn(obj);
function addOn (obj)
{
var parentNode = obj.parentNode;
var span = parentNode.getElementsByTagName("span")[0];
span.style.display="block";
thkOn(obj);
[Code]...
View 4 Replies
View Related
Nov 7, 2011
function funt()
{
var link = document.getElementsByClassName("class")[0];
[code]....
View 5 Replies
View Related
Jan 10, 2010
I have a window up whose Javascript implementation checks for a cookie with code something like this:
function lookieCookie()
{
alert(document.cookie);
setTimeout(lookieCookie, 10000);
}
The first call to lookieCookie is in the onload event handler. The cookie is actually set by a PHP routine that is in another script. The PHP script certainly appears to be setting the cookie. The alerts from lookieCookie are clearely happening at the appropriate time intervals (I can't get into the room with the actual code at the moment, so if I have messed up the syntax here, I know that it is not messed up in the real code), but the cookie being set from PHP does not show up.
Obviously the PHP might be doing the wrong thing. In tha case I have to get on the guy that writes the PHP script. Should the code I wrote work even if the cookie is set after the page has loaded, but between iterations of lookieCookie()? If yes, then I must get on the PHP coder and get his page fixed.
View 1 Replies
View Related
May 17, 2011
I have an image that when hovered, another image pops up (this popup image has a 'learn more' button on it), but when someone attempts to mouse over the button, the image restores to its original image. I was advised to use 'setTimeout' but do not know how to apply it with the following code...
I understand WHY it's going back to its original state (the mouse is hovering outside of the area coordinates), but how can I apply the setTimeout script to DELAY the image from going back to its original state?
View 3 Replies
View Related
Nov 6, 2004
Script is suppose to print out a string with a short delay between chars... like a typewriter... Why doesn't this work?
<script type="text/javascript">function hehe(bam) { document.write(bam)}function CharPrinter(st) { num = st.length; i = 0; while(i <= num) {bam = st.substr(i,1)setTimeout(hehe(bam),1000)i++; }}CharPrinter("lol");</script>
View 10 Replies
View Related
Sep 3, 2005
I'm trying to build the framework for an AJAX back/forward button fixer. Basically it uses the hash fix for them (using text after the # to add history objects). To this effect, the function to check for updates has to be run every second or so. No problem, I'll just use setInterval for that.
For whatever reason, though, setInterval gives me an error. Specifically that oldLocation (global variable) is undefined (in the checkURL function). So I try setTimeout. Same thing. When I just call the function explicitly once (adding checkURL(); to the end of the script) everything works wonderfuly; it's just setting it up on a timer that messes up. Frankly, I've no idea why it's doing this. (The bug just seems so odd) Maybe a more advanced JS coder can shed some light on it.. Code:
View 6 Replies
View Related
Nov 16, 2006
I know sometimes javascript and php can be used together. Anyone know how to add a javascript set timeout to this? So that this php include will re-execute after so much time? Or is there a php refresh command I can add to this code itself, not the page.
View 4 Replies
View Related