13

I'm making some Rocket launching effect by jQuery. When I click on Rocket, it'll swap with another rocket image, and then launch up. When I click "Reset" link, Rocket must reset starting location and image must revert back. But there are two problems. First, "my rocket image is not reverting back". Second - after it's reverted to initial location, if I click on Rocket again, it's not launching. Can you see and find me solutions?

http://jsfiddle.net/thisizmonster/QQRsW/

$("#resetlink").click(function(){
    clearInterval(timerRocket);
    $("#wrapper").css('top', '250px');
    $("#rocket").attr('src', 'http://www.kidostore.com/images/uploads/P-SAM-rocket-blk.jpg');
});

You can see $("rocket").attr() row.

Gereltod
  • 2,043
  • 8
  • 25
  • 39

2 Answers2

9

You remove the original image here:

newImg.animate(css, SPEED, function() {
    img.remove();
    newImg.removeClass('morpher');
    (callback || function() {})();
});

And all that's left behind is newImg. Then you reset link references the image using #rocket:

$("#rocket").attr('src', ...

But your newImg doesn't have an id attribute let alone an id of rocket.

To fix this, you need to remove img and then set the id attribute of newImg to rocket:

newImg.animate(css, SPEED, function() {
    var old_id = img.attr('id');
    img.remove();
    newImg.attr('id', old_id);
    newImg.removeClass('morpher');
    (callback || function() {})();
});

And then you'll get the shiny black rocket back again: http://jsfiddle.net/ambiguous/W2K9D/

UPDATE: A better approach (as noted by mellamokb) would be to hide the original image and then show it again when you hit the reset button. First, change the reset action to something like this:

$("#resetlink").click(function(){
    clearInterval(timerRocket);
    $("#wrapper").css('top', '250px');
    $('.throbber, .morpher').remove(); // Clear out the new stuff.
    $("#rocket").show();               // Bring the original back.
});

And in the newImg.load function, grab the images original size:

var orig = {
    width: img.width(),
    height: img.height()
};

And finally, the callback for finishing the morphing animation becomes this:

newImg.animate(css, SPEED, function() {
    img.css(orig).hide();
    (callback || function() {})();
});

New and improved: http://jsfiddle.net/ambiguous/W2K9D/1/

The leaking of $('.throbber, .morpher') outside the plugin isn't the best thing ever but it isn't a big deal as long as it is documented.

mu is too short
  • 426,620
  • 70
  • 833
  • 800
  • 3
    +1 Beat me to it. I think OP needs to hide the old image instead of removing it, then reset by `newImg.remove()` and `img.show()`. – mellamokb May 13 '11 at 03:34
  • I see, that used changing effect is not made by me. I just copy pasted that function. Then should I use .append() or there are other good solution? – Gereltod May 13 '11 at 03:35
  • Can you check http://jsfiddle.net/ambiguous/W2K9D/ again? its not working perfect. – Gereltod May 13 '11 at 03:38
  • 1
    @mellamokb @Gerelt: Hiding `#rocket` would be better as you wouldn't have to worry about transferring the `id` or rebinding any event handlers. – mu is too short May 13 '11 at 03:39
  • 1
    @Gerelt: What's missing with my modified version? I know you lose the click handler, is there anything else? And the size doesn't get reset. – mu is too short May 13 '11 at 03:40
  • Yes, Click handler missed. How can i add that? – Gereltod May 13 '11 at 03:48
  • 1
    @Gerelt: I made a few changes (hide the original, remove the new stuff, restore the original size): http://jsfiddle.net/ambiguous/W2K9D/1/ – mu is too short May 13 '11 at 03:58
  • @mu I really appreciete your helps. You made what i wanted make. Thanks million times. – Gereltod May 13 '11 at 04:19
  • 1
    @mu: There is still just one minor issue. If you hit reset really fast, before it finishes morphing, it will not work correctly. Try it out to see what I mean, the original image grows in size and then disappears completely. – mellamokb May 13 '11 at 04:26
  • @mellamokb: True enough and I should have spotted that myself (I just finished sorting out some "impatient user" issues). For something like this I'd probably take the easy way out have the reset handler ignore clicks until the morph callback has executed. Or, integrate the reset handler into the plugin to make it easier to cancel the animations and put everything back to where it should be. – mu is too short May 13 '11 at 04:33
3
  1. Function imageMorph will create a new img element therefore the id is removed. Changed to

    $("#wrapper > img")

  2. You should use live() function for click event if you want you rocket lanch again.

Updated demo: http://jsfiddle.net/ynhat/QQRsW/4/

Khoa Nguyen
  • 1,319
  • 7
  • 21