1

This is a very simple question/problem, and I can easily work around it, but since I'm learning javascript I was very eager to know WHY exactly this particular problem is happening.

$("#go").click(function() {
    $("p").append(array[x] + " ")
    functionlist[array[x]]()
    x++
})​

This does not work as I expect it to. I want it to write the current content of array, perform a simple animation that is associated with a certain function name, and then increment x. Everything works, except it doesn't increment x.

If I do this:

$("#go").click(function() {
    $("p").append(array[x] + " ")
    //functionlist[array[x]]()
    x++
})​

x is incremented successfully.

So my question is, why does this happen?

Here is a link to a jsfiddle that I am using: http://jsfiddle.net/mxy6N/3/

6
  • var x = 0 -- you're redeclaring x as zero each click. Commented Nov 27, 2012 at 1:24
  • I don't think x is incremented in the second case either... Commented Nov 27, 2012 at 1:24
  • My bad, however my issue still exists if I define x = 0 in the global space. Commented Nov 27, 2012 at 1:26
  • no function smooch, throwing error, not executing x++ Commented Nov 27, 2012 at 1:27
  • 3
    Uncaught TypeError: functionlist has no method 'smooch' Commented Nov 27, 2012 at 1:27

1 Answer 1

5

Well, if you check your script console (F12 is most browsers), you'll see that functionlist[array[x]]() throws an error something like:

Object has no method "smooch"

This is because array[x] is equal to "smooch", and functionlist["smooch"] is undefined, so it errors out before it makes it to your x++.

Other things going on in this code:

  • x is declared inside of your function, therefore it will always be 0 at the time it is used.
  • even if it were declared outside of your function, as you increment it, it will run out of items to look at in your array. You'll need to use a modulo operator or two here.
  • You're not referencing an .js files that have a definition for $.fn.transition, so your transition calls will also error out.
  • flip and flop both have the same rotateY value, so once it "flips" it won't "flop"

Here is something that might do what you're looking to do: http://jsfiddle.net/g5mJd/3/

And the updated code:

var array = ["smooch", "jab", "flip"];
var move = "flip";
var x = 0;
var functionlist = {
    flip: function() {
        $("#block").transition({
            perspective: '0px',
            rotateY: '180deg'
        }, 1000);
    },
    flop: function() {
        $("#block").transition({
            perspective: '0px',
            rotateY: '0deg'
        }, 100);
    }
};


$("#go").click(function() {
    var functionName = (x % 2 == 0) ? 'flip' : 'flop';
    var fn = functionlist[functionName];
    if($.isFunction(fn)) {
        fn();
    }
    var say = array[x % array.length];
    $('p').append(say + ' ');
    x++;
})​;

EDIT: Updated with $.isFunction() check.

Sign up to request clarification or add additional context in comments.

5 Comments

I'm surprised to see F12 works in Chrome as well. I thought it was an IE9 specialty.
This is great! Thanks allot. Any hints or pointers to how I would go about making the code realize whether the content of the array is also the name of a function? (And in that case executing it)?
@LeMarcin yes, if you're using jQuery, you can do: $.isFunction(someobj)... I'll update the answer.
This is excellent! With $.isFunction I get exactly the results I was looking for. Although the flipping and flopping/the array running out of options weren't part of my intended use, I'm very curious how you got them to loop. Particularly what does [x % array.length] do? I figured out that (x % 2 == 0) ? 'flip' : 'flop'; keeps going between one and the other, but again, how does it do this?
% is the modulo operator. Basically a % b will return the remainder of a / b... so 1 % 3 == 1, 2 % 3 == 2, 3 % 3 == 0, 4 % 3 == 1... it's a trick to infinitely loop through the items in an array: while(true) { alert(myArray[i++ % myArray.length]); }

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.