Blaze Blog

Archive for April 2006

Apr26

Mac’s For Sale

By Andy in Apple, News

I’ve got a couple of decent Macintosh computers for sale for those who are interested.

Mac Number 1 ~ SOLD!

Click for Mac Mini Large ImageThe first one is a 3 week old Mac Mini, it’s the dual core 1.66 with a 1GB RAM upgrade installed by Apple.

It runs really fast and I’m very impressed with it, but to be honest I really want to buy a new 17” MacBook Pro, so this one’s going to have to go.

Here are the specs in full:

  • 1.66ghz Intel Core Duo CPU
  • 1 GB DDR-2 667 RAM
  • 80GB 5200rpm Hard Drive
  • Intel 64mb Video Card
  • Dual Layer DVD/CD burner
  • Apple Remote

The full specs can be found on the Apple Mac Mini site.

I have all the original boxes and software – everything, all in perfect condition. I paid $1250 canadian including taxes for this brand new mini, so make me a decent offer and it’s yours.

Mac Number 2 ~ SOLD!

Click for Powerbook ImageThe second Mac for sale is my trusty 15” Aluminum Powerbook. This guy is in excellent condition and is around 2 years old (manufactured in April 2004).

Here are the full specs:

  • 1ghz Power PC G4
  • 1GB DDR RAM
  • 60GB Hard Drive
  • 64MB ATI Radeon 9600 Graphics
  • CD-RW Combo Drive (DVD reader/CD Writer)
  • Airport Extreme & Bluetooth
  • Firewire 400, 800 & USB 2
  • Gigabit Ethernet & 56k Modem

I also have all the original box and packaging for this. Again, make me a decent offer on this and it’s yours.

I can ship either of the Mac’s using UPS, or by regular ground mail, whatever you would prefer.

Payments can be made over Paypal (preferably), certified bankers cheque or on local pickup (I’m in Victoria, British Columbia).

I’m a decent guy, and these are genuine offers, so if you are interested send me an email and we’ll sort something out!

I’ll post a couple of photos of the macs this evening.

Apr18

Web Standards Meetup - Victoria, BC

By Andy in News

Coming to a pub in Victoria BC next month, the first meeting of the “better web” posse!

We’ll be getting together on Thursday, May 11th at 6.30pm at the Sticky Wicket Pub – 919 Douglas Street to talk all things web and web standards.

We’ll be focusing on how best to use web standards, some of the latest best practices, and how new technologies are helping change the way we create and design web apps.

If you’re a web designer or developer in the Victoria area (or want to pop over from Vancouver) I would highly recommend coming along to see what some of your peers are doing in the industry.

Here’s the scoop from Upcoming.org

Oh Canada, Where are Your Web Standards groups?

Inspired by groups like the WSG and Britpack, The Better Web Posse (ok, we might still be looking for another name) is designed to bring together web designers, developers, and uber geeks with hopes in providing support, general discussion, and encouragement in working with web standards. And what better Canadian way than to do this over beer?

Join us, bring your peers, and relish in using terms like AJAX, CSS, and “Web 2.0”

So what ya’ waiting for, go sign up!

Apr2

Creating a Dynamic Navigation Menu

I’ve gotten a few emails recently asking how I created the dynamic menu in the color selection component of the Durable Wordpress theme I released a few weeks back.

Dynamic MenuInstead of answering questions individually, I thought I would run through how I created the menu, so others can benefit.

Here is a step by step guide. You should have an HTML page ready to add code into, and have a blank external javascript file linked in the header to add the javascript functions to.

Step 1: The HTML

The menu is just a simple unordered list with the ID set as “menu”. Each sub-level of the menu is another unordered list within the parents list item. You can create as many levels as your heart desires, as the javascript we’ll write in the next step can handle this.

Here is the HTML I’ll use for the example:


<ul id="menu">
 <li><a href="fruit.htm" title="Fruit">Fruit</a>
   <ul>
     <li><a href="apple.htm" title="Apple">Apple</a>
      <ul>
       <li><a href="grannysmith.htm" title="Granny Smith">Granny Smith</a></li>
      </ul>
     </li>
     <li><a href="orange.htm" title="Orange">Orange</a></li>
     <li><a href="banana.htm" title="Banana">Banana</a></li>
   </ul>
 </li>
 <li><a href="veg.htm" title="Fruit">Vegetables</a>
   <ul>
     <li><a href="carrot.htm" title="Carrot">Carrot</a></li>
     <li><a href="onion.htm" title="Onion">Onion</a></li>
     <li><a href="peas.htm" title="Peas">Peas</a></li>
   </ul>
 </li>
</ul>

This will produce a vanilla HTML list which you can check out in example 1.

Step 2: Collapsing the Menu

The next step is to make that vanilla HTML list into something a little less rigid. This is where we’ll dip into some fancy DOM scripting.

The first thing we want to do is collapse the menu once it’s been loaded. We’ll do this by writing a recursive function called collapseMenu(), to traverse through each nested list in your menu, and hide it.


function collapseMenu(node) {
 if (!document.getElementById) return false;
 if (!document.getElementById("menu")) return false;
 if (!node) node = document.getElementById("menu");

 if (node.childNodes.length > 0) {
  for (var i=0; i<node.childNodes.length; i++) {
   var child = node.childNodes[i];
   if (child.nodeName == “UL”) {
    child.style.display = “none”;
   }
   collapseMenu(child);
  }
 }
}

For those who’re interested, a recursive function is one that calls upon itself.

In this function, we start at the very first node which is the <ul id=”menu”> node. We then count how many child nodes there are, and if there’s 1 or more, we check to see if any of the children are <ul> nodes. If so, then we hide them, by setting child.style.display = “none”.

Then there’s that recursive part, we call the same function again, but this time pass in the child as the starting node. This will go through and check all the grandchildren. The recursion will continue until there are no remaining child nodes to cycle through and everything is hidden.

Step 3: Bringing Those Links to Life

As it stands right now, the HTML we created in step one has no javascript associated with it. By removing the javascript completely from the HTML and placing it in an external file we are paving the way for graceful degradation. This means that if any of your users have javascript turned off, the menu will not collapse, and they will be able to use your navigation as though it was a static list.

So, we want to create a function called prepareMenu() that will go through and find every anchor within the menu, and add an “onclick” event to each one.


function prepareMenu() {
 if (!document.getElementById || !document.getElementsByTagName) return false;
 if (!document.getElementById("menu")) return false;
 if (!menu.getElementsByTagName("a")) return false;

var links = document.getElementById("menu").getElementsByTagName("a");
 for (var i=0; i<links.length; i++) {
  links[i].onclick = function() {
   toggleMenu(this.parentNode.getElementsByTagName(”UL”)[0], this.href);
   return false;
  }
 }
}

For every link within the menu, we have added an “onclick” event, which calls the function toggleMenu(). To this function, we will pass the nested list which represents the sub menu items, and also the “href” (destination) of the link.

Here is the code for toggleMenu() which will handle the hiding and displaying of sub-menus when a link is clicked:


function toggleMenu(node, link) {
 if (!document.getElementById) return false;
 if (!link) return false;
 if (!node) location.href = link.href;

 if (node.style.display == "") {
  node.style.display = "none";
 } else {
  node.style.display = "";
 }
}

This is pretty straightforward, the function will check the display property of the node, if it is hidden then display it, if not then hide it. One small detail however is that if the node passed to this function is null, then the links href is followed. This means that if the link clicked has no submenu, then the function will direct the user to the links location rather than trying to display a non-exisistent sub-menu.

Step 4: Add the OnLoad Events

Right now we have our functions ready to go, but they are not being called at all by our code. This means they will quite happily sit in your javascript file doing absolutely nothing. We need to add two “onload” events so that when the page has finished loading, both collapseMenu() and prepareMenu() are executed.

We can add multiple “onload” events using the excellent addLoadEvent() function written by Simon Willison:


function addLoadEvent(func) {
 var oldonload = window.onload;
 if (typeof window.onload != 'function') {
  window.onload = func;
 } else {
  window.onload = function() {
   oldonload();
   func();
  }
 }
}

You can add this function directly into your main javascript file, or you can create a separate javascript file with just this function, and include it with a <script> tag in the header of your HTML.

Now that we have Simon’s function to use, we can add two lines to the top of our javascript file:


addLoadEvent(collapseMenu);
addLoadEvent(prepareMenu);

This will ensure that when the page has finished loading, both the collapse and prepare menu functions are executed.

Now that we have most of the javascript and HTML in place, you should see something like example 2 when you load your page and click around the menu.

Although this is a perfectly adequate menu, it’s a little boring. Now is the time to snazz up the menu with a little extra javascript and some CSS love.

Step 5: Bring on the Goodies

For the menu I made for the Durable Wordpress Theme, whenever you clicked a top level node of the menu, all the other levels would collapse. This meant that the menu wouldn’t ever get too big, and would only allow the user to see one level at a time.

To collapse the top level nodes when any top level node is clicked, we need to add a check to toggleMenu() and create another function hideTopLevels():


function hideTopLevels() {
 if (!document.getElementById) return false;
 if (!(node = document.getElementById("menu"))) return false;

 if (node.childNodes.length > 0) {
  for (var i=0; i<node.childNodes.length; i++) {
   var child = node.childNodes[i];
   for(var j=0; j<child.childNodes.length; j++) {
    var grandchild = child.childNodes[j];
    if (grandchild.nodeName == “UL”) {
     if (grandchild.style.display == ”) {
      grandchild.style.display = “none”;
     }
    }
   }
  }
 }
}

Now we must add a quick check in toggleMenu() that will call this function if we have clicked a top level node:

Add in these lines after if (!node) return false;


if (node.parentNode.parentNode.id == "menu") {
 hideTopLevels();
}

Now you should have something like example 3 where top level nodes will collapse when another is clicked.

Finally, we can really spice up the menu by adding transitional effects using the Script.aculo.us javascript library and adding some nice CSS styles.

Download Script.aculo.us and link the javascript files in the <head> section of your HTML. If you are unsure how to do this, follow the Scriptaculous installation instructions.

Once you’ve got Scriptaculous linked and ready for use, we can change a couple of lines in toggleMenu() and hideTopLevels() so that the effects are used:

In toggleMenu() change:


if (node.style.display == "") {
 node.style.display = "none";
} else {
 node.style.display = "";
}

To this:


if (node.style.display == "") {
 Effect.BlindUp(node, {duration: 0.2});
} else {
 Effect.BlindDown(node, {duration: 0.2});
}

Then in hideTopLevels() change:


grandchild.style.display = "none";

To this:


Effect.BlindUp(grandchild, {duration: 0.2});

Your list should now be displaying some pretty cool looking transitions, rather than jumping from hiding to displaying.

I’ve added some CSS to my final example, but you are free to style the list any way you like to suit your own taste. Here is the final version with the transitions added, some new content, and my own example CSS linked above.

You are free to edit whatever you like and take this code away to use on your own site. I hope you enjoyed the walk through!

A zipped up version of the menu is availiable for download.

UPDATE: Now includes latest version of Prototype and Scriptaculous which fixes the drop down effects bug mentioned in the comments below.

Technorati Tags: , , , ,