Results 1 to 4 of 4

Thread: Passing Variables Function to Function

  1. #1
    Join Date
    Mar 2005
    Location
    SE PA USA
    Posts
    29,070
    Thanks
    44
    Thanked 3,216 Times in 3,178 Posts
    Blog Entries
    12

    Default Passing Variables Function to Function

    Here's one that has bothered me for some time, the answer is probably simple yet, so far has eluded me. When I write code and want to pass the arguments from one function to another I often, if not always have to do something like this (example from some code I'm working on, it works but, looks sloppy):

    Code:
    <script type="text/JavaScript"><!--
    i=100;
    function moz_switch(arg1,arg2){
    x=arg1;// why are these two declarations necessary?
    y=arg2;
    fade=setInterval("moz_fade(x,y)",90);
    }
    function moz_fade(img1,img2){
    document.getElementById(img1).style.MozOpacity=i/100;
    document.getElementById(img2).style.MozOpacity=Math.abs(i/100-1)
    i=(i-1);
    if (i==0){
    clearInterval(fade);
    i=100;
    }
    }
    //-->
    </script>
    Notice the comment. If I pass arg1 and arg2 directly to the moz_fade function, I get an error like img1 is not defined or has no properties. Using the above code, it works. There must be a better way.

  2. #2
    Join Date
    Dec 2004
    Location
    UK
    Posts
    2,358
    Thanks
    0
    Thanked 0 Times in 0 Posts

    Default

    Quote Originally Posted by jscheuer1
    Here's one that has bothered me for some time, the answer is probably simple yet, so far has eluded me.
    I did touch on the subject in the closures thread. The problem is specific to the string argument version of setTimeout/setInterval.

    <!--
    Stop including that. Seriously. It has absolutely no value any more and just perpetuates the myth of its necessity.

    function moz_switch(arg1,arg2){
    x=arg1;// why are these two declarations necessary?
    y=arg2;
    fade=setInterval("moz_fade(x,y)",90);
    }
    When setInterval evaluates the string argument, it does it in the only sensible scope it can: global. Clearly, arg1 and arg2 don't exist at that level so you need to provide a globally accessible pair of variables.

    Note the phrase "globally accessible". The variables in question don't need to be global themselves, but they have to be reachable in some way, whether it be through a series of member accessors, or through function calls.

    An alternative is to use a closure:

    Code:
    var i = 100,
        fadeTimer;
    
    function mozSwitch(a, b) {
      function fade() {
        /* The images collection is the preferred way to access
         * images. The images can be identified by either their
         * id or name attributes (id takes precedence).
         */
        document.images[a].style.MozOpacity = i / 100;
        /* Wouldn't (1 - i / 100) (without the
         * Math.abs call) achieve the same thing?
         */
        document.images[b].style.MozOpacity = Math.abs(i / 100 - 1);
        if(!--i) {
          clearInterval(fadeTimer);
          i = 100;
        }
      }
      fadeTimer = setInterval(fade, 90);
    }
    However, the caveat I mentioned in the closures thread applies.

    Mike

  3. #3
    Join Date
    Mar 2005
    Location
    SE PA USA
    Posts
    29,070
    Thanks
    44
    Thanked 3,216 Times in 3,178 Posts
    Blog Entries
    12

    Default

    Thanks Mike, I'm too busy to go over all that now but, will get back to you if I have any questions. I did take a quick look through and it seems like what I am looking for. I did understand the explanation of why I had to resort to what I did, as I had a feeling it was something like that but, didn't quite 'get it'. Again, thanks for taking the time.

  4. #4
    Join Date
    Dec 2004
    Location
    UK
    Posts
    2,358
    Thanks
    0
    Thanked 0 Times in 0 Posts

    Default

    Reading through the code I posted, I realised that no globals are necessary. Probably wasn't considering the code properly first time around...

    Code:
    function mozSwitch(a, b) {
      var i     = 100,
          timer = setInterval(fade, 90);
    
      function fade() {
        document.images[a].style.MozOpacity = i / 100;
        document.images[b].style.MozOpacity = 1 - (i / 100);
        /* As the i local will be initialised to 100 every time
         * mozSwitch is called, there's no need to reset it's value below.
         */
        if(!--i) {clearInterval(timer);}
      }
    }
    Mike

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •