1

I know this is basic but after looking at multiple resources (like this) I'm stuck. How do I nest functionTwo so that it runs only after functionOne is complete? Here are my attempts. (I actually want to do something more complicated in functionTwo, I'm just simplifying for this test case.)

$(function () {
    functionOne();
});

function functionOne() {
    $(".foo:first").attr('id','bar');
    functionTwo();
}

function functionTwo() {
    console.log($('.foo:first').attr('id'));     // log the new id: 'bar'
}

fiddle

This works, but are they running independently? When I put a timeout on the first function, nothing gets logged (unless that's a separate error).

Then I tried this:

$(function () {
    functionOne();
});

function functionOne() {
    $(".foo:first").attr('id', 'bar', function () {
            functionTwo();
        });
    }

function functionTwo() {
    console.log($('.foo:first').attr('id'));
}

fiddle

Nothing gets logged. Maybe a callback can't be a parameter if .attr

Then:

  $(function () {
      $.when.functionOne().done(function () {
          functionTwo();
      });
  });

  function functionOne() {
      $(".foo:first").attr('id', 'bar');
  }

  function functionTwo() {
      console.log($('.foo:first').attr('id'));
  }

fiddle

Nothing gets logged. I don't think .when and .done are supposed to be used this way.

So how should I nest these?

11
  • setTimeout(function functionOne() { doesn't do what you think it does. Commented Nov 4, 2013 at 19:35
  • 1
    doesn't seem to be a reason why the first one wouldn't work. And no, attr doesn't take a callback. And you're right, when doesn't work like that. Commented Nov 4, 2013 at 19:35
  • What's wrong with the 1st one? Commented Nov 4, 2013 at 19:36
  • can't chain a non jquery method to $.when you pass it as argument Commented Nov 4, 2013 at 19:36
  • 1
    I can see the log in chrome. Commented Nov 4, 2013 at 19:37

2 Answers 2

2

The 1st one is the way to go here.

$(function () {
    functionOne();
});

function functionOne() {
    $(".foo:first").attr('id','bar');
    functionTwo();
}

function functionTwo() {
    console.log($('.foo:first').attr('id'));     // log the new id: 'bar'
}

.attr is synchronous, so this works as expected.

In your setTimeout example (http://jsfiddle.net/nathanbweb/t9pAR/2/), you are using setTimeout incorrectly.

setTimeout(function functionOne() {}, 2000)

This doesn't do what you think it does. This will create a function, and run it after 2 seconds. The name functionOne will only exist inside the function's own scope.

You probably wanted this:

$(function () {
    functionOne();
});

function functionOne() {
    setTimeout(function(){
        $(".foo:first").attr('id','bar');
        functionTwo();
    }, 2000);
}

function functionTwo() {
    console.log($('.foo:first').attr('id'));     // log the new id: 'bar'
}

DEMO: http://jsfiddle.net/t9pAR/6/

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

Comments

1

Why not try returning the function you want to call second.

function functionOne() {
    $(".foo:first").attr('id','bar');
    return functionTwo();
}

http://jsfiddle.net/t9pAR/5/

3 Comments

How is this any different from his 1st example? What's the point of the return here? How does that fix/change anything?
It provides the ability to pass back success/failure messages back to the caller. 1 as it stands gives no feedback to calling functions.
That doesn't really answer the question here, though.

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.