Page 2 of 2 FirstFirst 12
Results 11 to 14 of 14

Thread: Doing a thing only once another thing is complete

  1. #11
    Join Date
    Mar 2005
    Location
    SE PA USA
    Posts
    30,495
    Thanks
    82
    Thanked 3,449 Times in 3,410 Posts
    Blog Entries
    12

    Default

    This should be easy:

    Code:
    a = e.target.href || e.target.getElement('a') || e.target.getParents('a') || null;
    But Mootools is poorly coded for IE in that if there are no child nodes, getElement throws an error instead of returning a falsy value. And getParents just doesn't seem to work at all for IE, at least not like that. Both are fine in all other browsers I tested though. So we can do some IE gynastics (highlighted and green in the below) to get it to work out in IE and leave others unaffected. The only pitfall in IE is that if there will be nested elements within the element(s) nested within the a tag, more code will be needed. The getParents method in Mootools takes care of that for all others.

    Here's the finished code with some other stuff (highlighted and black) added so that on a real page where the domready may take a while to fire, the mainContent will remain unseen until it slides in:

    Code:
    <script type="text/javascript">
    document.write('<style type="text/css">#mainContent {visibility: hidden;}<\/style>');
    window.addEvent('domready', function(){
    	var MC = $('mainContent'), myPanel = new Fx.Slide(MC).hide(), a;
    	myPanel.addEvent('start', function(){MC.setStyle('visibility', 'visible');});
    	myPanel.slideIn();
    	$$('.menu').addEvent('click', function(e){
    		e.stop();
    		/*@cc_on @*/
    		/*@if(@_jscript_version >= 5)
    		try{
    		@end @*/
    		a = e.target.href || e.target.getElement('a') || e.target.getParents('a') || null;
    		/*@if(@_jscript_version >= 5)
    		}catch(err){a = e.target.parentNode && e.target.parentNode.href? e.target.parentNode : null;}
    		@end @*/
    		if(a){
    			myPanel.addEvent('complete', function() {
    				location = a;
    			});
    			myPanel.slideOut();
    		}
    	});
    
    });
    </script>
    Also note highlighted and red - a test for all browsers to make absolutely sure we found a link before attempting to proceed with the slide out and page change.
    Last edited by jscheuer1; 12-08-2009 at 01:28 PM. Reason: spelling, punctuation, general sense
    - John
    ________________________

    Show Additional Thanks: International Rescue Committee - Donate or: The Ocean Conservancy - Donate or: PayPal - Donate

  2. #12
    Join Date
    Apr 2006
    Posts
    205
    Thanks
    11
    Thanked 0 Times in 0 Posts

    Default

    Hey John,

    Thanks once again. I am really impressed. I am surprised that, with the exception of the green highlighted stuff, I understand almost all of this.

    The bit that writes CSS to hide #mainContent until Mootools kicks-in is simple genius. I love it! Hopefully that will do away with the flicker that I was getting on some browsers when going from one page to another.

    Could you please tell me a little more about 'e.target.href'. You wrote that 'e' is the event object. In this case it is the thing that gets clicked, right? Until you click something inside '.menu' it could be anything, true? And, 'target' and 'href', how do they differ? In 'e.target.getElement('a')' there is no mention of href so why is it needed in 'e.target.href'?

    With more thanks, and best wishes,
    Laurence

  3. #13
    Join Date
    Mar 2005
    Location
    SE PA USA
    Posts
    30,495
    Thanks
    82
    Thanked 3,449 Times in 3,410 Posts
    Blog Entries
    12

    Default

    You are right about e and e.target. The href thing too, except there is an oddity about how that works out in javascript that makes the code much shorter than it would otherwise have to be.

    I know what you might be thinking - maybe it's this shortcut that doesn't work in IE. Nope, I tested it written out the long way, no help.

    Anyways, the trick is that an anchor link tag, unlike all other tags, when viewed by javascript as an object (how it sees all other tags that are part of the DOM), is seen as a string. That string is the anchor link's href. So the first test:

    Code:
    e.target.href
    determines whether or not we have a link, as well as returning the href because if it has no href, it's not an anchor link. The second test:

    Code:
     e.target.getElement('a')
    since it can only (when working as expected, and as it does in all non-IE I tested), returns either an a tag or a falsy value, when it returns a truthy value, it will already be the href value.

    Similarly for the third test.

    As you are probably also interested, this stuff:

    Code:
    		/*@cc_on @*/
    		/*@if(@_jscript_version >= 5)
    Code:
    		@end @*/
    when placed around a code block makes that block appear to be a commnet to all but IE 5+.

    The code I'm hiding is an ordinary try/catch which catches the errors thrown by IE in some of the situations it may encounter with that line:

    Code:
    a = e.target.href || e.target.getElement('a') || e.target.getParents('a') || null;
    and performs the required actions IE otherwise cannot perform when an error is thrown by it for that line.
    - John
    ________________________

    Show Additional Thanks: International Rescue Committee - Donate or: The Ocean Conservancy - Donate or: PayPal - Donate

  4. #14
    Join Date
    Mar 2005
    Location
    SE PA USA
    Posts
    30,495
    Thanks
    82
    Thanked 3,449 Times in 3,410 Posts
    Blog Entries
    12

    Default

    Ooops! I discovered another problem with IE. If the element that was clicked on (e.target) is an image tag with a src attribute, IE sees that attribute as qualifying as an href property of the image tag. So this messes things up. I've decided to therefore do everything in a manner that IE can handle and that also will work in other browsers:

    Code:
    <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
    <html>
    <head>
    <title></title>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
    <script type="text/javascript" src="http://mootools.net/download/get/mootools-1.2.4-core-yc.js"></script>
    <script type="text/javascript" src="mootools-1.2.4.2-more.js"></script>
    <script type="text/javascript">
    document.write('<style type="text/css">#mainContent {visibility: hidden;}<\/style>');
    window.addEvent('domready', function(){
    	var MC = $('mainContent'), myPanel = new Fx.Slide(MC).hide(), lnks = $(document.body).getElements('a'), a, t, tp, tc, cn;
    	myPanel.addEvent('start', function(){MC.setStyle('visibility', 'visible');});
    	myPanel.slideIn();
    	$$('.menu').addEvent('click', function(e){
    		e.stop();
    		cn = 0;
    		t = tp = tc = e.target;
    		while(lnks.indexOf(tp) < 0 && lnks.indexOf(tc) < 0){
    			tp = tp.parentNode || {parentNode: null};
    			tc = t.getElementsByTagName('a')[cn++] || null;
    		}
    		a = lnks.indexOf(tp) > -1? tp : lnks.indexOf(tc) > -1? tc : null;
    		if(a && a.href){
    			myPanel.addEvent('complete', function() {
    				location = a;
    			});
    			myPanel.slideOut();
    		}
    	});
    
    });
    </script>
    </head>
    <body>
    <ul>
     <li class="menu"><a href="page2.html">Page 2</a></li>
     <li class="menu"><a href="page3.html"><span>Page 3</span></a></li>
     <li class="menu"><a name="ulMenu">Dummy</a></li>
    </ul>
    
    <div id="mainContent">content here!</div>
    </body>
    </html>
    Last edited by jscheuer1; 12-09-2009 at 05:04 AM. Reason: minor code improvement
    - John
    ________________________

    Show Additional Thanks: International Rescue Committee - Donate or: The Ocean Conservancy - Donate or: PayPal - Donate

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
  •