FUNDAMENTAL
 JAVASCRIPT
   Aaron Gustafson
DOM SCRIPTING
(a.k.a. Document Manipulation via JavaScript)
FUNDAMENTAL JAVASCRIPT




    DHTML
๏   …was all about animation and interactivity
๏   ...was invented by marketing wonks...
FUNDAMENTAL JAVASCRIPT




    DOM Scripting
๏   …is the web standards approach to manipulating documents
๏   ...only requ...
FUNDAMENTAL JAVASCRIPT




The document
<!DOCTYPE html PUBLIC quot;-//W3C//DTD XHTML 1.0 Strict//ENquot;
 quot;http://www....
FUNDAMENTAL JAVASCRIPT




The DOM
                         html




IN CONTROL 2009                 6
FUNDAMENTAL JAVASCRIPT




The DOM
                                        html




                         head         ...
FUNDAMENTAL JAVASCRIPT




The DOM
                                                p




                          this is...
FUNDAMENTAL JAVASCRIPT




CSS



                    getter { setter }




IN CONTROL 2009                         7
FUNDAMENTAL JAVASCRIPT




CSS



                    p { color: red; }




IN CONTROL 2009                         7
FUNDAMENTAL JAVASCRIPT




CSS


           #footer {
             font-size: small;
           }



IN CONTROL 2009      ...
FUNDAMENTAL JAVASCRIPT




DOM Scripting




IN CONTROL 2009          8
FUNDAMENTAL JAVASCRIPT




DOM Scripting


         var myNode =
           document.getter();



IN CONTROL 2009         ...
FUNDAMENTAL JAVASCRIPT




DOM Scripting



                         myNode.setter();




IN CONTROL 2009                 ...
FUNDAMENTAL JAVASCRIPT




    Getters
๏   document.getElementById( ID );

๏   document.getElementsByTagName( tagName );

...
FUNDAMENTAL JAVASCRIPT




    Using getters
๏   var content = document.getElementById( 'content' );

๏   var abbrs = docu...
FUNDAMENTAL JAVASCRIPT




    Language comparison
๏   English
    Get the element with the ID “content”.
๏   CSS
    #con...
FUNDAMENTAL JAVASCRIPT




    Language comparison
๏   English
    Get all the paragraphs in a document.
๏   CSS
    p { }...
FUNDAMENTAL JAVASCRIPT




    Language comparison
๏   English
    Get all the paragraphs within the element with the ID
 ...
FUNDAMENTAL JAVASCRIPT




    Content generation
๏   Bad:
    ‣ document.write();

    ‣ innerHTML




    IN CONTROL 200...
FUNDAMENTAL JAVASCRIPT




    Content generation
๏   Good:
    ‣ document.createElement( tagName );

    ‣ document.creat...
FUNDAMENTAL JAVASCRIPT




    Generation in action
๏   var abbr = document.createElement( 'abbr' );

๏   var text = docum...
FUNDAMENTAL JAVASCRIPT




    Adding to the DOM
๏   element.appendChild( newNode );
๏   element.insertBefore( newNode, ta...
FUNDAMENTAL JAVASCRIPT




Adding to the DOM
var abbr = document.createElement( 'abbr' );

var text = document.createTextN...
TIME FOR AN
  EXAMPLE
FUNDAMENTAL JAVASCRIPT




The idea
Make use of the cite attribute in blockquotes.




IN CONTROL 2009                    ...
FUNDAMENTAL JAVASCRIPT




The document
<!DOCTYPE html PUBLIC quot;-//W3C//DTD XHTML 1.0 Strict//ENquot;
 quot;http://www....
FUNDAMENTAL JAVASCRIPT




The page

                  Progressive Enhancement, as a label for a
                  strateg...
FUNDAMENTAL JAVASCRIPT




The document
<!DOCTYPE html PUBLIC quot;-//W3C//DTD XHTML 1.0 Strict//ENquot;
 quot;http://www....
FUNDAMENTAL JAVASCRIPT




The idea
1. Find all the blockquotes in a document

2. Get the value of the cite attribute

3. ...
FUNDAMENTAL JAVASCRIPT




The idea
1. Find all the blockquotes in a document

2. Get the value of the cite attribute

3. ...
FUNDAMENTAL JAVASCRIPT




The idea
1. Find all the blockquotes in a document getElementsByTagName

2. Get the value of th...
FUNDAMENTAL JAVASCRIPT




The idea
1. Find all the blockquotes in a document getElementsByTagName

2. Get the value of th...
FUNDAMENTAL JAVASCRIPT




The idea
1. Find all the blockquotes in a document getElementsByTagName

2. Get the value of th...
FUNDAMENTAL JAVASCRIPT




The idea
1. Find all the blockquotes in a document getElementsByTagName

2. Get the value of th...
FUNDAMENTAL JAVASCRIPT




The idea
1. Find all the blockquotes in a document getElementsByTagName

2. Get the value of th...
FUNDAMENTAL JAVASCRIPT




The idea
1. Find all the blockquotes in a document getElementsByTagName

2. Get the value of th...
FUNDAMENTAL JAVASCRIPT




The idea
1. Find all the blockquotes in a document getElementsByTagName

2. Get the value of th...
FUNDAMENTAL JAVASCRIPT




The code
var quotes = document.getElementsByTagName( 'blockquote' );
for( var i=0; i < quotes.l...
FUNDAMENTAL JAVASCRIPT




The code
var quotes = document.getElementsByTagName( 'blockquote' );
for( var i=0; i < quotes.l...
FUNDAMENTAL JAVASCRIPT




The code
function sourceQuotes(){
  var quotes = document.getElementsByTagName( 'blockquote' );...
FUNDAMENTAL JAVASCRIPT




The result

                  Progressive Enhancement, as a label for a
                  strat...
FUNDAMENTAL JAVASCRIPT




The result

                  Progressive Enhancement, as a label for a
                  strat...
PROGRESSIVE
ENHANCEMENT
WHAT IS
 PROGRESSIVE
ENHANCEMENT?
PROGRESSIVE
ENHANCEMENT
     VS.
  GRACEFUL
DEGRADATION
GRACEFUL
DEGRADATION
FUNDAMENTAL JAVASCRIPT




    Graceful Degradation
๏   A holdover from engineering
๏ Build        for the latest browsers...
WEB STANDARDS: FUELING INNOVATION




WEB BUILDER 2.0                     35
WEB STANDARDS: FUELING INNOVATION




WEB BUILDER 2.0                     35
PROGRESSIVE
ENHANCEMENT
 FOCUSES ON
  CONTENT
PROGRESSIVE
ENHANCEMENT
 FOCUSES ON
  CONTENT
CONTENT IS WHY
WE BUILD WEBSITES
  AND SHOULD
     BE OUR
 CENTRAL FOCUS
WEB STANDARDS: FUELING INNOVATION




WEB BUILDER 2.0                     38
WEB STANDARDS: FUELING INNOVATION




WEB BUILDER 2.0                     39
HOW DOES IT
  WORK?
WEB STANDARDS: FUELING INNOVATION




WEB BUILDER 2.0                     41
FUNDAMENTAL JAVASCRIPT




Flavorful nugget of content
(semantic goodness)




IN CONTROL 2009               42
FUNDAMENTAL JAVASCRIPT




Rich, indulgent design




IN CONTROL 2009          43
FUNDAMENTAL JAVASCRIPT




Sweet interactivity
(keeps it from melting in your hands)




IN CONTROL 2009                  ...
WEB STANDARDS: FUELING INNOVATION




WEB BUILDER 2.0                     45
TECHNOLOGIES
APPLIED AS LAYERS
WEB STANDARDS: FUELING INNOVATION




WEB BUILDER 2.0                     47
WEB STANDARDS: FUELING INNOVATION




                                    stuffandnonsense.co.uk/archives/web_standards_tr...
WHY A PEANUT
   M&M?
FUNDAMENTAL JAVASCRIPT




    The peanut is good for
๏   diabetics




    IN CONTROL 2009          50
FUNDAMENTAL JAVASCRIPT




    The peanut is good for
๏   diabetics
๏   search engine spiders




    IN CONTROL 2009     ...
FUNDAMENTAL JAVASCRIPT




    The peanut is good for
๏   diabetics
๏   search engine spiders
๏   mobile devices




    I...
IT’S A BASIC LEVEL
   OF SUPPORT
FUNDAMENTAL JAVASCRIPT




The chocolate is good for




IN CONTROL 2009             52
FUNDAMENTAL JAVASCRIPT




    The chocolate is good for
๏   diabetics




    IN CONTROL 2009             52
FUNDAMENTAL JAVASCRIPT




    Rich, chocolaty goodness
๏   some browsers only handle
    a certain level of CSS
๏   some ...
IT CAN BE
BEAUTIFUL
 (and progressive)
FUNDAMENTAL JAVASCRIPT




The candy coating




IN CONTROL 2009          54
FUNDAMENTAL JAVASCRIPT




    The candy coating
๏   JavaScript can turn a website
    into an experience




    IN CONTR...
FUNDAMENTAL JAVASCRIPT




    The candy coating
๏   JavaScript can turn a website
    into an experience
๏   we can deliv...
PROGRESSIVE
 ENHANCEMENT
WITH JAVASCRIPT
RESTRAINT
& PLANNING
FUNDAMENTAL JAVASCRIPT




A long time ago, in a
cubicle far, far away...




                         Dear George Lucas, ...
FUNDAMENTAL JAVASCRIPT




A long time ago, in a
cubicle far, far away...




                         Dear George Lucas, ...
WHAT CAN
JAVASCRIPT DO?
HOW SHOULD
 JAVASCRIPT
   BE USED?
PROGRESSIVE
ENHANCEMENT
  REMINDS US
 TO FOCUS ON
THE CONTENT
FUNDAMENTAL JAVASCRIPT




Back to basics




IN CONTROL 2009          60
FUNDAMENTAL JAVASCRIPT




Back to basics



         XHTML + HTTP


IN CONTROL 2009          60
FUNDAMENTAL JAVASCRIPT




Back to basics



         solid foundation


IN CONTROL 2009             60
FUNDAMENTAL JAVASCRIPT




         ALL CODE NEEDED
         TO UNDERSTAND
          AND USE A SITE
       SHOULD EXIST BE...
FUNDAMENTAL JAVASCRIPT




                         PERIOD.

IN CONTROL 2009                    61
FUNDAMENTAL JAVASCRIPT




Consider lala.com




IN CONTROL 2009          62
FUNDAMENTAL JAVASCRIPT




Without JavaScript




IN CONTROL 2009          63
FUNDAMENTAL JAVASCRIPT




Without JavaScript




IN CONTROL 2009          63
FUNDAMENTAL JAVASCRIPT




Without JavaScript



                         Doh!

IN CONTROL 2009                 63
FUNDAMENTAL JAVASCRIPT




And looking at the




IN CONTROL 2009          64
FUNDAMENTAL JAVASCRIPT




And looking at the




                         Ug h !

IN CONTROL 2009                   64
WHAT ABOUT
 SEARCH?
WHAT ABOUT
ALTERNATIVE
  DEVICES?
ENTER
UNOBTRUSIVE
 JAVASCRIPT
ENTER
UNOBTRUSIVE
 JAVASCRIPT
(           )
 the cornerstone of Progressive
  Enhancement with JavaScript
FUNDAMENTAL JAVASCRIPT




Don’t do this
<a href=quot;javascript:someFunction();quot;>some text</a>


                    ...
FUNDAMENTAL JAVASCRIPT




An improvement, but still...
<a href=quot;http://offsite.comquot;
   onclick=quot;newWin( this....
FUNDAMENTAL JAVASCRIPT




Getting warmer...
window.onload = handleExternalLinks;

function handleExternalLinks(){
  var s...
FUNDAMENTAL JAVASCRIPT




Getting warmer...
window.onload = handleExternalLinks;

function handleExternalLinks(){
  var s...
FUNDAMENTAL JAVASCRIPT




Getting warmer...
window.onload = handleExternalLinks;

function handleExternalLinks(){
  var s...
FUNDAMENTAL JAVASCRIPT




Getting warmer...
window.onload = handleExternalLinks;

function handleExternalLinks(){
  var s...
FUNDAMENTAL JAVASCRIPT




Getting warmer...
window.onload = handleExternalLinks;

function handleExternalLinks(){
  var s...
FUNDAMENTAL JAVASCRIPT




Getting warmer...
window.onload = handleExternalLinks;

function handleExternalLinks(){
  var s...
FUNDAMENTAL JAVASCRIPT




Getting warmer...
window.onload = handleExternalLinks;

function handleExternalLinks(){
  var s...
FUNDAMENTAL JAVASCRIPT




Getting warmer...
window.onload = handleExternalLinks;

function handleExternalLinks(){
  var s...
FUNDAMENTAL JAVASCRIPT




You’re hot
document.getElementsByTagName( 'body' )[0]
        .onclick = clickDelegator;

funct...
FUNDAMENTAL JAVASCRIPT




You’re hot
document.getElementsByTagName( 'body' )[0]
        .onclick = clickDelegator;

funct...
FUNDAMENTAL JAVASCRIPT




You’re hot
document.getElementsByTagName( 'body' )[0]
        .onclick = clickDelegator;

funct...
FUNDAMENTAL JAVASCRIPT




You’re hot
document.getElementsByTagName( 'body' )[0]
        .onclick = clickDelegator;

funct...
FUNDAMENTAL JAVASCRIPT




You’re hot
document.getElementsByTagName( 'body' )[0]
        .onclick = clickDelegator;

funct...
FUNDAMENTAL JAVASCRIPT




You’re hot
document.getElementsByTagName( 'body' )[0]
        .onclick = clickDelegator;

funct...
WEB STANDARDS: FUELING INNOVATION




WEB BUILDER 2.0                     71
JavaScript
             CSS
FUNDAMENTAL JAVASCRIPT




Remember stuff like this?
<a href=quot;foo.htmlquot;
   style=quot;color:blue;quot;
   onmouseo...
FUNDAMENTAL JAVASCRIPT




Remember stuff like this?
<a href=quot;foo.htmlquot;
   style=quot;color:blue;quot;
   onmouseo...
FUNDAMENTAL JAVASCRIPT




Isn’t this the same?
for( i=0; i<objects.length; i++){
  objects[i].style.display = 'none';
}

...
FUNDAMENTAL JAVASCRIPT




Small improvement
for( i=0; i<objects.length; i++){
  objects[i].style.position = 'absolute';
 ...
FUNDAMENTAL JAVASCRIPT




Separation
CSS:
.hidden {
  position: absolute;
  left: -999em;
}


JavaScript:
for( i=0; i<obj...
FUNDAMENTAL JAVASCRIPT




    Maintenance options
๏   external style rules added to your CSS file (by hand)
๏   external C...
FUNDAMENTAL JAVASCRIPT




Option 1: Add by hand
At the end of your screen layout CSS file:
/* =START WickedCool Script CSS...
FUNDAMENTAL JAVASCRIPT




Option 2: Include by hand
Added to the head of your document:

<script type=quot;text/javascrip...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
function FindPath( filename ){
  var path = false;
  var scripts = d...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
function FindPath( filename ){
  var path = false;
  var scripts = d...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
function FindPath( filename ){
  var path = false;
  var scripts = d...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
function FindPath( filename ){
  var path = false;
  var scripts = d...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
function FindPath( filename ){
  var path = false;
  var scripts = d...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
function FindPath( filename ){
  var path = false;
  var scripts = d...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
function FindPath( filename ){
  var path = false;
  var scripts = d...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
function FindPath( filename ){
  var path = false;
  var scripts = d...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
var WickedCool = {
  jsFile:    'WickedCool.js',
  cssFile:   'Wicke...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
var WickedCool = {
  jsFile:    'WickedCool.js',
  cssFile:   'Wicke...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
var WickedCool = {
  jsFile:    'WickedCool.js',
  cssFile:   'Wicke...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
var WickedCool = {
  jsFile:    'WickedCool.js',
  cssFile:   'Wicke...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
var WickedCool = {
  jsFile:    'WickedCool.js',
  cssFile:   'Wicke...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
var WickedCool = {
  jsFile:    'WickedCool.js',
  cssFile:   'Wicke...
FUNDAMENTAL JAVASCRIPT




Option 3: Scripted include
var WickedCool = {
  jsFile:    'WickedCool.js',
  cssFile:   'Wicke...
FUNDAMENTAL JAVASCRIPT




Option 4: Scripted embed
function addCSS( styles ){
  var el = document.createElement( 'style' ...
FUNDAMENTAL JAVASCRIPT




Option 4: Scripted embed
function addCSS( styles ){
  var el = document.createElement( 'style' ...
FUNDAMENTAL JAVASCRIPT




Option 4: Scripted embed
function addCSS( styles ){
  var el = document.createElement( 'style' ...
FUNDAMENTAL JAVASCRIPT




Option 4: Scripted embed
function addCSS( styles ){
  var el = document.createElement( 'style' ...
FUNDAMENTAL JAVASCRIPT




Option 4: Scripted embed
function addCSS( styles ){
  var el = document.createElement( 'style' ...
FUNDAMENTAL JAVASCRIPT




Option 4: Scripted embed
function addCSS( styles ){
  var el = document.createElement( 'style' ...
FUNDAMENTAL JAVASCRIPT




Option 4: Scripted embed
var WickedCool = {
  _css: '.wicked { color: red; ' +
        '       ...
FUNDAMENTAL JAVASCRIPT




Option 4: Scripted embed
var WickedCool = {
  _css: '.wicked { color: red; ' +
        '       ...
FUNDAMENTAL JAVASCRIPT




Option 4: Scripted embed
var WickedCool = {
  _css: '.wicked { color: red; ' +
        '       ...
FUNDAMENTAL JAVASCRIPT




Option 4: Scripted embed
var WickedCool = {
  _css: '.wicked { color: red; ' +
        '       ...
FUNDAMENTAL JAVASCRIPT




Option 4: Scripted embed
var WickedCool = {
  _css: '.wicked { color: red; ' +
        '       ...
BUT KEEP IN MIND
YOU NEED TO
   AVOID APPLYING
SCRIPT-RELATED STYLES
UNTIL YOU KNOW
YOUR SCRIPT CAN RUN
     AND IT HAS
INITIALIZED PROPERLY
FUNDAMENTAL JAVASCRIPT




    How do we do that?
๏   make your style rules specific:

    .TabInterface-folder {
      ......
FUNDAMENTAL JAVASCRIPT




How do we do that?
<div id=quot;mainquot; class=quot;tabbedquot;>

becomes

<div id=quot;mainqu...
FUNDAMENTAL JAVASCRIPT




How do we do that?
                               Default        Activated
add “-on” to the cla...
WEB STANDARDS: FUELING INNOVATION




WEB BUILDER 2.0                     87
FUNDAMENTAL JAVASCRIPT




Look for methods
function someFunction(){
  if( !document.getElementsByTagName ) return;
  // c...
FUNDAMENTAL JAVASCRIPT




Look for methods
function someFunction(){
  if( !document.getElementsByTagName ||
      !docume...
FUNDAMENTAL JAVASCRIPT




Look for elements
function someFunction(){
  if( !document.getElementsByTagName ||
       !docu...
FUNDAMENTAL JAVASCRIPT




Look for identified elements
function someFunction(){
  if( !document.getElementById ||
      !d...
FUNDAMENTAL JAVASCRIPT




Look for objects
function someFunction(){
  if( typeof( Prototype ) == 'undefined' ) return;
  ...
FUNDAMENTAL JAVASCRIPT




Look for object versions
function someFunction(){
  if( typeof( jQuery ) == 'undefined' ||
    ...
FUNDAMENTAL JAVASCRIPT




Look before you leap
window.onload = function(){
   if( document.getElementsByTagName &&
      ...
FUNDAMENTAL JAVASCRIPT




    PE with JavaScript
๏   Start with the content, then work your way out
๏   Get unobtrusive
๏...
HOW DOES IT
  ALL COME
 TOGETHER?
FUNDAMENTAL JAVASCRIPT




Example 1: Tab Interface




IN CONTROL 2009            97
FUNDAMENTAL JAVASCRIPT




Traditional approach
<h1>Pumpkin Pie</h1>

<div class=quot;containerquot;>
  <div class=quot;se...
FUNDAMENTAL JAVASCRIPT




Traditional approach
<h1>Pumpkin Pie</h1>

<div class=quot;containerquot;>
  <div class=quot;se...
FUNDAMENTAL JAVASCRIPT




Traditional approach
<h1>Pumpkin Pie</h1>

<div class=quot;containerquot;>
  <div class=quot;se...
FUNDAMENTAL JAVASCRIPT




Traditional approach
<h1>Pumpkin Pie</h1>

<div class=quot;containerquot;>
  <div class=quot;se...
FUNDAMENTAL JAVASCRIPT




No style




IN CONTROL 2009          99
FUNDAMENTAL JAVASCRIPT




A little typography




IN CONTROL 2009          100
FUNDAMENTAL JAVASCRIPT




Typography & color




IN CONTROL 2009          101
FUNDAMENTAL JAVASCRIPT




No style




IN CONTROL 2009          102
FUNDAMENTAL JAVASCRIPT




No style




                         .tabbed
IN CONTROL 2009                    102
FUNDAMENTAL JAVASCRIPT




The actual source
<h1>Pumpkin Pie</h1>

<div class=quot;tabbedquot;>
  <h2>Overview</h2>
  <img...
FUNDAMENTAL JAVASCRIPT




The actual source
<h1>Pumpkin Pie</h1>

<div class=quot;tabbedquot;>
  <h2>Overview</h2>
  <img...
FUNDAMENTAL JAVASCRIPT




Understanding the flow




IN CONTROL 2009          104
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  // Public Properties
  this.Version = '0.3'; // vers...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  // Public Properties
  this.Version = '0.3'; // vers...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  // Public Properties
  this.Version = '0.3'; // vers...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  // Public Properties
  this.Version = '0.3'; // vers...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  // Public Properties
  this.Version = '0.3'; // vers...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  ...
  function initialize(){
    // code to come
  }...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  ...
  function initialize(){
    // code to come
  }...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  ...
  function initialize(){
    // code to come
  }...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  ...
  function initialize(){
    // code to come
  }...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  ...
  function initialize(){
    // code to come
  }...
FUNDAMENTAL JAVASCRIPT




THE CODE
function TabInterface( el, i ){
  function initialize(){

     // set the id
     _id ...
FUNDAMENTAL JAVASCRIPT




THE CODE
function TabInterface( el, i ){
  function initialize(){

     // set the id
     _id ...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  function initialize(){
    ...

     // find the fir...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  function initialize(){
    ...

     // establish th...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  function initialize(){
    ...
    for( var k=0, aLe...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  function initialize(){
    ...
    for( var k=0, aLe...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  function initialize(){
    ...
    for( var k=0, aLe...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
  function initialize(){
    ...
    for( var k=0, aLe...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
   function initialize(){
     ...
     for( var k=0, ...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
   function initialize(){
     ...
     for( var k=0, ...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
   ...
   function swap( e ){
     e = ( e ) ? e : eve...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
   ...
   function swap( e ){
     e = ( e ) ? e : eve...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
   ...
   function swap( e ){
     e = ( e ) ? e : eve...
FUNDAMENTAL JAVASCRIPT




The code
function TabInterface( el, i ){
   ...
   function swap( e ){
     e = ( e ) ? e : eve...
FUNDAMENTAL JAVASCRIPT




Greater flexibility
function TabInterface( el, i ){
   function initialize(){
     ...
     for(...
FUNDAMENTAL JAVASCRIPT




Greater flexibility
function TabInterface( el, i ){
   function initialize(){
     ...
     for(...
FUNDAMENTAL JAVASCRIPT




Running it
// Load up TabInterface
if( document.getElementById &&
    document.getElementsByTag...
FUNDAMENTAL JAVASCRIPT




Running it
// Load up TabInterface
if( document.getElementById &&
    document.getElementsByTag...
FUNDAMENTAL JAVASCRIPT




Running it
// Load up TabInterface
if( document.getElementById &&
    document.getElementsByTag...
FUNDAMENTAL JAVASCRIPT




Running it
// Load up TabInterface
if( document.getElementById &&
    document.getElementsByTag...
FUNDAMENTAL JAVASCRIPT




The full experience




IN CONTROL 2009          115
QUESTIONS?
FUNDAMENTAL JAVASCRIPT




Example 2: Collapsing Form




IN CONTROL 2009              117
FUNDAMENTAL JAVASCRIPT




Collapsing Form as HTML




IN CONTROL 2009           118
FUNDAMENTAL JAVASCRIPT




Collapsing Form with CSS




IN CONTROL 2009            119
FUNDAMENTAL JAVASCRIPT




Collapsing Form with CSS




IN CONTROL 2009            120
FUNDAMENTAL JAVASCRIPT




Collapsing Form with CSS




IN CONTROL 2009            121
FUNDAMENTAL JAVASCRIPT




HTML hooks




IN CONTROL 2009          122
FUNDAMENTAL JAVASCRIPT




HTML hooks




                         form.collapsing
IN CONTROL 2009                        ...
FUNDAMENTAL JAVASCRIPT




HTML hooks




                         fieldset.optional
IN CONTROL 2009                      ...
FUNDAMENTAL JAVASCRIPT




Understanding the flow




IN CONTROL 2009          123
FUNDAMENTAL JAVASCRIPT




The code
var Easy = {
   addClassName: function( e, c ){
     var classes = ( !e.className ) ? ...
FUNDAMENTAL JAVASCRIPT




The code
var Easy = {
   addClassName: function( e, c ){
     var classes = ( !e.className ) ? ...
FUNDAMENTAL JAVASCRIPT




The code
var Easy = {
   addClassName: function( e, c ){
     var classes = ( !e.className ) ? ...
FUNDAMENTAL JAVASCRIPT




The code
var Easy = {
   addClassName: function( e, c ){
     var classes = ( !e.className ) ? ...
FUNDAMENTAL JAVASCRIPT




The code
var Easy = {
   addClassName: function( e, c ){
     var classes = ( !e.className ) ? ...
FUNDAMENTAL JAVASCRIPT




The code
var CollapsingForm = Class.create();
CollapsingForm.prototype = {

  link:            ...
FUNDAMENTAL JAVASCRIPT




The code
var CollapsingForm = Class.create();
CollapsingForm.prototype = {

  link:            ...
FUNDAMENTAL JAVASCRIPT




The code
var CollapsingForm = Class.create();
CollapsingForm.prototype = {

  link:            ...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   ...
   initialize: function( form, i ){
     // set th...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   ...
   initialize: function( form, i ){
     // set th...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   ...
   initialize: function( form, i ){
     // set th...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   ...
   initialize: function( form, i ){
     // set th...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   ...
   initialize: function( form, i ){
     ...
     ...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   ...
   initialize: function( form, i ){
     ...
     ...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   ...
   initialize: function( form, i ){
     ...
     ...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   ...
   initialize: function( form, i ){
     ...
     ...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   initialize: function( form, i ){
     ...
   },
   tog...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   initialize: function( form, i ){
     ...
   },
   tog...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   ...
   showMore:   function(){
     for( var i=0; i<th...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   ...
   showMore:   function(){
     for( var i=0; i<th...
FUNDAMENTAL JAVASCRIPT




The code
CollapsingForm.prototype = {
   ...
   showMore:   function(){
     for( var i=0; i<th...
FUNDAMENTAL JAVASCRIPT




Collapsing Form with JS




IN CONTROL 2009           130
QUESTIONS?
WORKING
WITH LIBRARIES
FUNDAMENTAL JAVASCRIPT




    Popular Libraries
๏   jQuery (jquery.com)
๏   Prototype (prototypejs.org) & Scriptaculous (...
FUNDAMENTAL JAVASCRIPT




    Popular Libraries
๏   jQuery - fast & easy to write, selector-based
๏   Prototype & Scripta...
FUNDAMENTAL JAVASCRIPT




    Popular Libraries
๏   jQuery - fast & easy to write, selector-based
๏   Prototype & Scripta...
FUNDAMENTAL JAVASCRIPT




    Getters 2.0
๏   jQuery:
    ‣ $(selector)

    ‣ $(selector).attr(attribute)

๏   Prototype...
FUNDAMENTAL JAVASCRIPT




    Setters 2.0
๏   jQuery:
    ‣ $(x).text(text)        or $(x).html(html) or $(x).append([el|...
LET’S REVISIT
 OUR FIRST
  EXAMPLE
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Fundamental JavaScript [In Control 2009]
Upcoming SlideShare
Loading in...5
×

Fundamental JavaScript [In Control 2009]

3,858

Published on

In this session, Aaron Gustafson introduces attendees to the client-side scripting language known as JavaScript. After being taken on a quick tour through the language's features and syntax, attendees will be introduced through a series of examples to ways in which JavaScript can progressively enhance the user experience and really make their designs sing. This session also introduces attendees to several JavaScript libraries and demonstrate how to execute the same task in each.

Published in: Technology
0 Comments
24 Likes
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total Views
3,858
On Slideshare
0
From Embeds
0
Number of Embeds
0
Actions
Shares
0
Downloads
330
Comments
0
Likes
24
Embeds 0
No embeds

No notes for slide



















































  • As an example of how graceful degradation would look at a website, here&#x2019;s the &#x201C;hi-fi&#x201D; version of my own site.

    Graceful degradation would assume that my site should look roughly like this in all modern browsers and roughly like this [switch] in older browsers. It&#x2019;s usable, but isn&#x2019;t great. We can do better.
  • By contrast, PE would tell me to look at this site from the content-out and work to determine the best way to meet my users&#x2019; needs. It&#x2019;s about your site and its content adapting to users instead of forcing users to get by with the scraps you&#x2019;ve left them.
  • By contrast, PE would tell me to look at this site from the content-out and work to determine the best way to meet my users&#x2019; needs. It&#x2019;s about your site and its content adapting to users instead of forcing users to get by with the scraps you&#x2019;ve left them.
  • By contrast, PE would tell me to look at this site from the content-out and work to determine the best way to meet my users&#x2019; needs. It&#x2019;s about your site and its content adapting to users instead of forcing users to get by with the scraps you&#x2019;ve left them.
  • By contrast, PE would tell me to look at this site from the content-out and work to determine the best way to meet my users&#x2019; needs. It&#x2019;s about your site and its content adapting to users instead of forcing users to get by with the scraps you&#x2019;ve left them.

  • Developing a website is a lot like waiting tables...

    * some people drink a lot* some drink very littlewe need to anticipate and meet our customers&#x2019; needs in as seemless a way possible. They should never have to ask us for more water. That&#x2019;s customer service.

    Taking it a bit further...
  • As a waiter, you&#x2019;d never throw water in a customer&#x2019;s face. That would be bad customer service. But websites do it all the time when they don&#x2019;t build with PE in mind.

    We&#x2019;ll touch on an example shortly.

























  • You need to wield your power wisely.

    Let me spin a yarn...
  • DHTML, which arrived in the mid-90s, was awful.

    How many were doing JavaScript at the time? How many liked it? How many looked @ JavaScript and said &#x201C;no way&#x201D;?

    I don&#x2019;t blame you, it was spaghetti code. Code forking. Forked ourselves. Truth be told, however, our HTML was spaghetti too.
  • DHTML, which arrived in the mid-90s, was awful.

    How many were doing JavaScript at the time? How many liked it? How many looked @ JavaScript and said &#x201C;no way&#x201D;?

    I don&#x2019;t blame you, it was spaghetti code. Code forking. Forked ourselves. Truth be told, however, our HTML was spaghetti too.
  • Things are better now, but we have new challenges. We need to move from thinking about what Javascript can do that&#x2019;s cool to how it should be used to improve the user experience.

    [slide] And there&#x2019;s a balance there that PE helps with maintaining as it does put a focus on content.
  • Things are better now, but we have new challenges. We need to move from thinking about what Javascript can do that&#x2019;s cool to how it should be used to improve the user experience.

    [slide] And there&#x2019;s a balance there that PE helps with maintaining as it does put a focus on content.
  • Things are better now, but we have new challenges. We need to move from thinking about what Javascript can do that&#x2019;s cool to how it should be used to improve the user experience.

    [slide] And there&#x2019;s a balance there that PE helps with maintaining as it does put a focus on content.

  • The reason I got in to JS: solid foundation to build neat stuff on - XHTML & HTTP.

    Ajax is cool, but we should never lose sight of the fact that these are the two core technologies that drive the web. Without either, websites would cease to be.
  • The reason I got in to JS: solid foundation to build neat stuff on - XHTML & HTTP.

    Ajax is cool, but we should never lose sight of the fact that these are the two core technologies that drive the web. Without either, websites would cease to be.
  • The reason I got in to JS: solid foundation to build neat stuff on - XHTML & HTTP.

    Ajax is cool, but we should never lose sight of the fact that these are the two core technologies that drive the web. Without either, websites would cease to be.
  • And if you try to leapfrog over either, you&#x2019;re doomed.

    This is one statement I always want you to keep in mind when you&#x2019;re working with JavaScript. And here&#x2019;s an example of why:
  • And if you try to leapfrog over either, you&#x2019;re doomed.

    This is one statement I always want you to keep in mind when you&#x2019;re working with JavaScript. And here&#x2019;s an example of why:








  • What happens if JS is off?

    Unfortunately you still see this all over the web... if I hear of any of you doing it, I will track you down.
  • For a while, we thought this was a good improvement over the previous because at least there was an action for the user if Javascript was off, but it&#x2019;s not maintainable.
  • We then started to think about externalizing the scripting to functions like this.
  • We then started to think about externalizing the scripting to functions like this.
  • We then started to think about externalizing the scripting to functions like this.
  • We then started to think about externalizing the scripting to functions like this.
  • We then started to think about externalizing the scripting to functions like this.
  • We then started to think about externalizing the scripting to functions like this.
  • We then started to think about externalizing the scripting to functions like this.
  • We then started to think about externalizing the scripting to functions like this.
  • We then started to think about externalizing the scripting to functions like this.
  • We then started to think about externalizing the scripting to functions like this.
  • We then started to think about externalizing the scripting to functions like this.
  • We then started to think about externalizing the scripting to functions like this.
  • We can do so much better with far less code.
  • We can do so much better with far less code.
  • We can do so much better with far less code.
  • We can do so much better with far less code.
  • We can do so much better with far less code.
  • We can do so much better with far less code.
  • We can do so much better with far less code.
  • We can do so much better with far less code.

  • Who remembers this little treat?

    I&#x2019;d like you to think about your web work like the McDLT, where JavaScript and CSS are separated as much as humanly possible. Why? because it makes a lot of things easier.
  • Who remembers this little treat?

    I&#x2019;d like you to think about your web work like the McDLT, where JavaScript and CSS are separated as much as humanly possible. Why? because it makes a lot of things easier.
  • Who remembers this little treat?

    I&#x2019;d like you to think about your web work like the McDLT, where JavaScript and CSS are separated as much as humanly possible. Why? because it makes a lot of things easier.
  • CSS was poorly understood back then, but we know better now...don&#x2019;t we? Don&#x2019;t be so sure.
  • CSS was poorly understood back then, but we know better now...don&#x2019;t we? Don&#x2019;t be so sure.
  • This was taken from a popular JavaScript library. I won&#x2019;t say which, but most of them have stuff like this.

    That&#x2019;s an accessibility issue
  • But what if best practices change?

    Your Javascript needs to be flexible to be maintainable. Just like the McDLT, JavaScript and CSS come together to create a tasty treat, but to be at their best, they need a little separation.
  • in this example, I&#x2019;m using a function (addClassName) that adds CLASS names in a maintainable way
    (Prototype has an element method like this)

  • Simple and straightforward. Scripts like sIFR that require some manual edits to the CSS take this path.

    Requires diligence in implementation to keep errors out.
  • Numerous widget scripts and libraries take this path (Lightbox, for instance).

    Still requires implementation to be error-free.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Relies only on the JS and CSS being in the same folder. It doesn&#x2019;t matter where though.
  • Implementation example.
  • Implementation example.
  • Implementation example.
  • Implementation example.
  • Implementation example.
  • Implementation example.
  • Implementation example.
  • Implementation example.
  • Implementation example.
  • Implementation example.
  • A little messier, but still very maintainable.
  • A little messier, but still very maintainable.
  • A little messier, but still very maintainable.
  • A little messier, but still very maintainable.
  • A little messier, but still very maintainable.
  • A little messier, but still very maintainable.
  • A little messier, but still very maintainable.
  • A little messier, but still very maintainable.
  • your CSS would be added in the configuration of the script and would be easy to maintain and update along with the script as it is a single file. You are still including the two together, but it is a little more separation than writing inline styles.
  • your CSS would be added in the configuration of the script and would be easy to maintain and update along with the script as it is a single file. You are still including the two together, but it is a little more separation than writing inline styles.
  • your CSS would be added in the configuration of the script and would be easy to maintain and update along with the script as it is a single file. You are still including the two together, but it is a little more separation than writing inline styles.
  • your CSS would be added in the configuration of the script and would be easy to maintain and update along with the script as it is a single file. You are still including the two together, but it is a little more separation than writing inline styles.
  • your CSS would be added in the configuration of the script and would be easy to maintain and update along with the script as it is a single file. You are still including the two together, but it is a little more separation than writing inline styles.
  • your CSS would be added in the configuration of the script and would be easy to maintain and update along with the script as it is a single file. You are still including the two together, but it is a little more separation than writing inline styles.




  • separate your style rules from others by prefacing them in some way with the name of the script








  • Prototype stores its version info as a string


























































  • Using Jesse Skinner&#x2019;s addDOMLoadEvent()
  • Using Jesse Skinner&#x2019;s addDOMLoadEvent()
  • Using Jesse Skinner&#x2019;s addDOMLoadEvent()
  • Using Jesse Skinner&#x2019;s addDOMLoadEvent()
  • Using Jesse Skinner&#x2019;s addDOMLoadEvent()
  • Using Jesse Skinner&#x2019;s addDOMLoadEvent()
  • Using Jesse Skinner&#x2019;s addDOMLoadEvent()
  • Using Jesse Skinner&#x2019;s addDOMLoadEvent()
  • Using Jesse Skinner&#x2019;s addDOMLoadEvent()


  • Talk about client and lack of modern computers & mobile.





  • Fundamental JavaScript [In Control 2009]

    1. 1. FUNDAMENTAL JAVASCRIPT Aaron Gustafson
    2. 2. DOM SCRIPTING (a.k.a. Document Manipulation via JavaScript)
    3. 3. FUNDAMENTAL JAVASCRIPT DHTML ๏ …was all about animation and interactivity ๏ ...was invented by marketing wonks ๏ ...is really three technologies: JavaScript, CSS & HTML ๏ ...carried a lot of baggage: browser-specific, forked code, screen only & non-standard markup ๏ ...was a maintenance nightmare IN CONTROL 2009 3
    4. 4. FUNDAMENTAL JAVASCRIPT DOM Scripting ๏ …is the web standards approach to manipulating documents ๏ ...only requires a scripting language and valid markup ๏ ...is browser independent ๏ ...makes use of progressive enhancement ๏ ...just makes sense IN CONTROL 2009 4
    5. 5. FUNDAMENTAL JAVASCRIPT The document <!DOCTYPE html PUBLIC quot;-//W3C//DTD XHTML 1.0 Strict//ENquot; quot;http://www.w3.org/TR/XHTML1/DTD/XHTML1-strict.dtdquot;> <html xmlns=quot;http://www.w3.org/1999/XHTMLquot; xml:lang=quot;enquot; lang=quot;enquot;> <head> <title>Page Title</title> <meta http-equiv=quot;content-typequot; content=quot;text/html; charset=utf-8quot; /> <meta http-equiv=quot;Content-Languagequot; content=quot;en-usquot; /> </head> <body> <h1>This is a heading</h1> <p>This is a paragraph with a <a href=quot;http://easy-reader.netquot;>link</a></p> <ul> <li>a list item</li> <li>another list item</li> <li>a third list item</li> </ul> </body> </html> IN CONTROL 2009 5
    6. 6. FUNDAMENTAL JAVASCRIPT The DOM html IN CONTROL 2009 6
    7. 7. FUNDAMENTAL JAVASCRIPT The DOM html head body title meta meta h1 p ul a li li li IN CONTROL 2009 6
    8. 8. FUNDAMENTAL JAVASCRIPT The DOM p this is a paragraph a . of text with a href=quot;http://easy-reader.netquot; link IN CONTROL 2009 6
    9. 9. FUNDAMENTAL JAVASCRIPT CSS getter { setter } IN CONTROL 2009 7
    10. 10. FUNDAMENTAL JAVASCRIPT CSS p { color: red; } IN CONTROL 2009 7
    11. 11. FUNDAMENTAL JAVASCRIPT CSS #footer { font-size: small; } IN CONTROL 2009 7
    12. 12. FUNDAMENTAL JAVASCRIPT DOM Scripting IN CONTROL 2009 8
    13. 13. FUNDAMENTAL JAVASCRIPT DOM Scripting var myNode = document.getter(); IN CONTROL 2009 8
    14. 14. FUNDAMENTAL JAVASCRIPT DOM Scripting myNode.setter(); IN CONTROL 2009 8
    15. 15. FUNDAMENTAL JAVASCRIPT Getters ๏ document.getElementById( ID ); ๏ document.getElementsByTagName( tagName ); ๏ element.getAttribute( attributeName ); IN CONTROL 2009 9
    16. 16. FUNDAMENTAL JAVASCRIPT Using getters ๏ var content = document.getElementById( 'content' ); ๏ var abbrs = document.getElementsByTagName( 'abbr' ); ๏ var title = abbrs[0].getAttribute( 'title' ); IN CONTROL 2009 10
    17. 17. FUNDAMENTAL JAVASCRIPT Language comparison ๏ English Get the element with the ID “content”. ๏ CSS #content { } ๏ DOM document.getElementById( 'content' ) IN CONTROL 2009 11
    18. 18. FUNDAMENTAL JAVASCRIPT Language comparison ๏ English Get all the paragraphs in a document. ๏ CSS p { } ๏ DOM document.getElementsByTagName( 'p' ); IN CONTROL 2009 12
    19. 19. FUNDAMENTAL JAVASCRIPT Language comparison ๏ English Get all the paragraphs within the element with the ID “content”. ๏ CSS #content p { } ๏ DOM document.getElementById( 'content' ) .getElementsByTagName( 'p' ); IN CONTROL 2009 13
    20. 20. FUNDAMENTAL JAVASCRIPT Content generation ๏ Bad: ‣ document.write(); ‣ innerHTML IN CONTROL 2009 14
    21. 21. FUNDAMENTAL JAVASCRIPT Content generation ๏ Good: ‣ document.createElement( tagName ); ‣ document.createTextNode( text ); ‣ element.setAttribute( name, value ); IN CONTROL 2009 15
    22. 22. FUNDAMENTAL JAVASCRIPT Generation in action ๏ var abbr = document.createElement( 'abbr' ); ๏ var text = document.createTextNode( 'TN' ); ๏ abbr.setAttribute( 'title', 'Tennessee' ); IN CONTROL 2009 16
    23. 23. FUNDAMENTAL JAVASCRIPT Adding to the DOM ๏ element.appendChild( newNode ); ๏ element.insertBefore( newNode, targetNode ); IN CONTROL 2009 17
    24. 24. FUNDAMENTAL JAVASCRIPT Adding to the DOM var abbr = document.createElement( 'abbr' ); var text = document.createTextNode( 'TN' ); abbr.setAttribute( 'title', 'Tennessee' ); abbr.appendChild( text ); var p = document.getElementsByTagName( 'p' )[0]; p.appendChild( abbr ); IN CONTROL 2009 18
    25. 25. TIME FOR AN EXAMPLE
    26. 26. FUNDAMENTAL JAVASCRIPT The idea Make use of the cite attribute in blockquotes. IN CONTROL 2009 20
    27. 27. FUNDAMENTAL JAVASCRIPT The document <!DOCTYPE html PUBLIC quot;-//W3C//DTD XHTML 1.0 Strict//ENquot; quot;http://www.w3.org/TR/XHTML1/DTD/XHTML1-strict.dtdquot;> <html xmlns=quot;http://www.w3.org/1999/XHTMLquot; xml:lang=quot;enquot; lang=quot;enquot;> <head> <title>Example 1</title> <meta http-equiv=quot;content-typequot; content=quot;text/html; charset=utf-8quot; /> <meta http-equiv=quot;Content-Languagequot; content=quot;en-usquot; /> </head> <body> <blockquote cite=quot;http://en.wikipedia.org/wiki/Progressive_Enhancementquot;> <p>Progressive Enhancement, as a label for a strategy for Web design, was coined by Steven Champeon in a series of articles and presentations for Webmonkey and the SxSW Interactive conference.</p> </blockquote> </body> </html> IN CONTROL 2009 21
    28. 28. FUNDAMENTAL JAVASCRIPT The page Progressive Enhancement, as a label for a strategy for Web design, was coined by Steven Champeon in a series of articles and presentations for Webmonkey and the SxSW Interactive conference. IN CONTROL 2009 22
    29. 29. FUNDAMENTAL JAVASCRIPT The document <!DOCTYPE html PUBLIC quot;-//W3C//DTD XHTML 1.0 Strict//ENquot; quot;http://www.w3.org/TR/XHTML1/DTD/XHTML1-strict.dtdquot;> <html xmlns=quot;http://www.w3.org/1999/XHTMLquot; xml:lang=quot;enquot; lang=quot;enquot;> <head> <title>Example 1</title> <meta http-equiv=quot;content-typequot; content=quot;text/html; charset=utf-8quot; /> <meta http-equiv=quot;Content-Languagequot; content=quot;en-usquot; /> </head> <body> <blockquote cite=quot;http://en.wikipedia.org/wiki/Progressive_Enhancementquot;> <p>Progressive Enhancement, as a label for a strategy for Web design, was coined by Steven Champeon in a series of articles and presentations for Webmonkey and the SxSW Interactive conference.</p> </blockquote> </body> </html> IN CONTROL 2009 23
    30. 30. FUNDAMENTAL JAVASCRIPT The idea 1. Find all the blockquotes in a document 2. Get the value of the cite attribute 3. Create a new anchor element node 4. Set the href attribute of the anchor 5. Create a new text node with the word “source” 6. Insert the text into the anchor 7. Insert the anchor into the blockquote. IN CONTROL 2009 24
    31. 31. FUNDAMENTAL JAVASCRIPT The idea 1. Find all the blockquotes in a document 2. Get the value of the cite attribute 3. Create a new anchor element node 4. Set the href attribute of the anchor 5. Create a new text node with the word “source” 6. Insert the text into the anchor 7. Insert the anchor into the blockquote. IN CONTROL 2009 25
    32. 32. FUNDAMENTAL JAVASCRIPT The idea 1. Find all the blockquotes in a document getElementsByTagName 2. Get the value of the cite attribute 3. Create a new anchor element node 4. Set the href attribute of the anchor 5. Create a new text node with the word “source” 6. Insert the text into the anchor 7. Insert the anchor into the blockquote. IN CONTROL 2009 25
    33. 33. FUNDAMENTAL JAVASCRIPT The idea 1. Find all the blockquotes in a document getElementsByTagName 2. Get the value of the cite attribute getAttribute 3. Create a new anchor element node 4. Set the href attribute of the anchor 5. Create a new text node with the word “source” 6. Insert the text into the anchor 7. Insert the anchor into the blockquote. IN CONTROL 2009 25
    34. 34. FUNDAMENTAL JAVASCRIPT The idea 1. Find all the blockquotes in a document getElementsByTagName 2. Get the value of the cite attribute getAttribute 3. Create a new anchor element node createElement 4. Set the href attribute of the anchor 5. Create a new text node with the word “source” 6. Insert the text into the anchor 7. Insert the anchor into the blockquote. IN CONTROL 2009 25
    35. 35. FUNDAMENTAL JAVASCRIPT The idea 1. Find all the blockquotes in a document getElementsByTagName 2. Get the value of the cite attribute getAttribute 3. Create a new anchor element node createElement 4. Set the href attribute of the anchor setAttribute 5. Create a new text node with the word “source” 6. Insert the text into the anchor 7. Insert the anchor into the blockquote. IN CONTROL 2009 25
    36. 36. FUNDAMENTAL JAVASCRIPT The idea 1. Find all the blockquotes in a document getElementsByTagName 2. Get the value of the cite attribute getAttribute 3. Create a new anchor element node createElement 4. Set the href attribute of the anchor setAttribute 5. Create a new text node with the word “source” createTextNode 6. Insert the text into the anchor 7. Insert the anchor into the blockquote. IN CONTROL 2009 25
    37. 37. FUNDAMENTAL JAVASCRIPT The idea 1. Find all the blockquotes in a document getElementsByTagName 2. Get the value of the cite attribute getAttribute 3. Create a new anchor element node createElement 4. Set the href attribute of the anchor setAttribute 5. Create a new text node with the word “source” createTextNode 6. Insert the text into the anchor appendChild 7. Insert the anchor into the blockquote. IN CONTROL 2009 25
    38. 38. FUNDAMENTAL JAVASCRIPT The idea 1. Find all the blockquotes in a document getElementsByTagName 2. Get the value of the cite attribute getAttribute 3. Create a new anchor element node createElement 4. Set the href attribute of the anchor setAttribute 5. Create a new text node with the word “source” createTextNode 6. Insert the text into the anchor appendChild 7. Insert the anchor into the blockquote. appendChild IN CONTROL 2009 25
    39. 39. FUNDAMENTAL JAVASCRIPT The code var quotes = document.getElementsByTagName( 'blockquote' ); for( var i=0; i < quotes.length; i++ ){ var source = quotes[i].getAttribute( 'cite' ); if( source ){ var link = document.createElement( 'a' ); link.setAttribute( 'href', source ); var text = document.createTextNode( 'source' ); link.appendChild( text ); quotes[i].appendChild( link ); } } IN CONTROL 2009 26
    40. 40. FUNDAMENTAL JAVASCRIPT The code var quotes = document.getElementsByTagName( 'blockquote' ); for( var i=0; i < quotes.length; i++ ){ var source = quotes[i].getAttribute( 'cite' ); if( source ){ var link = document.createElement( 'a' ); link.setAttribute( 'href', source ); var text = document.createTextNode( 'source' ); link.appendChild( text ); var para = document.createElement( 'p' ); para.className = 'attribution'; para.appendChild( link ); quotes[i].appendChild( para ); } } IN CONTROL 2009 27
    41. 41. FUNDAMENTAL JAVASCRIPT The code function sourceQuotes(){ var quotes = document.getElementsByTagName( 'blockquote' ); for( var i=0; i < quotes.length; i++ ){ var source = quotes[i].getAttribute( 'cite' ); if( source ){ var link = document.createElement( 'a' ); link.setAttribute( 'href', source ); var text = document.createTextNode( 'source' ); link.appendChild( text ); var para = document.createElement( 'p' ); para.className = 'attribution'; para.appendChild( link ); quotes[i].appendChild( para ); } } } window.onload = sourceQuotes; IN CONTROL 2009 28
    42. 42. FUNDAMENTAL JAVASCRIPT The result Progressive Enhancement, as a label for a strategy for Web design, was coined by Steven Champeon in a series of articles and presentations for Webmonkey and the SxSW Interactive conference. IN CONTROL 2009 29
    43. 43. FUNDAMENTAL JAVASCRIPT The result Progressive Enhancement, as a label for a strategy for Web design, was coined by Steven Champeon in a series of articles and presentations for Webmonkey and the SxSW Interactive conference. source IN CONTROL 2009 30
    44. 44. PROGRESSIVE ENHANCEMENT
    45. 45. WHAT IS PROGRESSIVE ENHANCEMENT?
    46. 46. PROGRESSIVE ENHANCEMENT VS. GRACEFUL DEGRADATION
    47. 47. GRACEFUL DEGRADATION
    48. 48. FUNDAMENTAL JAVASCRIPT Graceful Degradation ๏ A holdover from engineering ๏ Build for the latest browsers ๏ Test on older devices ‣ Happens at the end ‣ Accounts for few versions ๏ Expects a poor experience for older browsers ๏ Fixes major issues but little else IN CONTROL 2009 34
    49. 49. WEB STANDARDS: FUELING INNOVATION WEB BUILDER 2.0 35
    50. 50. WEB STANDARDS: FUELING INNOVATION WEB BUILDER 2.0 35
    51. 51. PROGRESSIVE ENHANCEMENT FOCUSES ON CONTENT
    52. 52. PROGRESSIVE ENHANCEMENT FOCUSES ON CONTENT
    53. 53. CONTENT IS WHY WE BUILD WEBSITES AND SHOULD BE OUR CENTRAL FOCUS
    54. 54. WEB STANDARDS: FUELING INNOVATION WEB BUILDER 2.0 38
    55. 55. WEB STANDARDS: FUELING INNOVATION WEB BUILDER 2.0 39
    56. 56. HOW DOES IT WORK?
    57. 57. WEB STANDARDS: FUELING INNOVATION WEB BUILDER 2.0 41
    58. 58. FUNDAMENTAL JAVASCRIPT Flavorful nugget of content (semantic goodness) IN CONTROL 2009 42
    59. 59. FUNDAMENTAL JAVASCRIPT Rich, indulgent design IN CONTROL 2009 43
    60. 60. FUNDAMENTAL JAVASCRIPT Sweet interactivity (keeps it from melting in your hands) IN CONTROL 2009 44
    61. 61. WEB STANDARDS: FUELING INNOVATION WEB BUILDER 2.0 45
    62. 62. TECHNOLOGIES APPLIED AS LAYERS
    63. 63. WEB STANDARDS: FUELING INNOVATION WEB BUILDER 2.0 47
    64. 64. WEB STANDARDS: FUELING INNOVATION stuffandnonsense.co.uk/archives/web_standards_trifle.html WEB BUILDER 2.0 48
    65. 65. WHY A PEANUT M&M?
    66. 66. FUNDAMENTAL JAVASCRIPT The peanut is good for ๏ diabetics IN CONTROL 2009 50
    67. 67. FUNDAMENTAL JAVASCRIPT The peanut is good for ๏ diabetics ๏ search engine spiders IN CONTROL 2009 50
    68. 68. FUNDAMENTAL JAVASCRIPT The peanut is good for ๏ diabetics ๏ search engine spiders ๏ mobile devices IN CONTROL 2009 50
    69. 69. IT’S A BASIC LEVEL OF SUPPORT
    70. 70. FUNDAMENTAL JAVASCRIPT The chocolate is good for IN CONTROL 2009 52
    71. 71. FUNDAMENTAL JAVASCRIPT The chocolate is good for ๏ diabetics IN CONTROL 2009 52
    72. 72. FUNDAMENTAL JAVASCRIPT Rich, chocolaty goodness ๏ some browsers only handle a certain level of CSS ๏ some companies turn off JavaScript IN CONTROL 2009 52
    73. 73. IT CAN BE BEAUTIFUL (and progressive)
    74. 74. FUNDAMENTAL JAVASCRIPT The candy coating IN CONTROL 2009 54
    75. 75. FUNDAMENTAL JAVASCRIPT The candy coating ๏ JavaScript can turn a website into an experience IN CONTROL 2009 54
    76. 76. FUNDAMENTAL JAVASCRIPT The candy coating ๏ JavaScript can turn a website into an experience ๏ we can deliver our scripts a la carte IN CONTROL 2009 54
    77. 77. PROGRESSIVE ENHANCEMENT WITH JAVASCRIPT
    78. 78. RESTRAINT & PLANNING
    79. 79. FUNDAMENTAL JAVASCRIPT A long time ago, in a cubicle far, far away... Dear George Lucas, please don’t sue me. Kthxbye. IN CONTROL 2009 57
    80. 80. FUNDAMENTAL JAVASCRIPT A long time ago, in a cubicle far, far away... Dear George Lucas, please don’t sue me. Kthxbye. IN CONTROL 2009 57
    81. 81. WHAT CAN JAVASCRIPT DO?
    82. 82. HOW SHOULD JAVASCRIPT BE USED?
    83. 83. PROGRESSIVE ENHANCEMENT REMINDS US TO FOCUS ON THE CONTENT
    84. 84. FUNDAMENTAL JAVASCRIPT Back to basics IN CONTROL 2009 60
    85. 85. FUNDAMENTAL JAVASCRIPT Back to basics XHTML + HTTP IN CONTROL 2009 60
    86. 86. FUNDAMENTAL JAVASCRIPT Back to basics solid foundation IN CONTROL 2009 60
    87. 87. FUNDAMENTAL JAVASCRIPT ALL CODE NEEDED TO UNDERSTAND AND USE A SITE SHOULD EXIST BEFORE ANY SCRIPTS RUN IN CONTROL 2009 61
    88. 88. FUNDAMENTAL JAVASCRIPT PERIOD. IN CONTROL 2009 61
    89. 89. FUNDAMENTAL JAVASCRIPT Consider lala.com IN CONTROL 2009 62
    90. 90. FUNDAMENTAL JAVASCRIPT Without JavaScript IN CONTROL 2009 63
    91. 91. FUNDAMENTAL JAVASCRIPT Without JavaScript IN CONTROL 2009 63
    92. 92. FUNDAMENTAL JAVASCRIPT Without JavaScript Doh! IN CONTROL 2009 63
    93. 93. FUNDAMENTAL JAVASCRIPT And looking at the IN CONTROL 2009 64
    94. 94. FUNDAMENTAL JAVASCRIPT And looking at the Ug h ! IN CONTROL 2009 64
    95. 95. WHAT ABOUT SEARCH?
    96. 96. WHAT ABOUT ALTERNATIVE DEVICES?
    97. 97. ENTER UNOBTRUSIVE JAVASCRIPT
    98. 98. ENTER UNOBTRUSIVE JAVASCRIPT ( ) the cornerstone of Progressive Enhancement with JavaScript
    99. 99. FUNDAMENTAL JAVASCRIPT Don’t do this <a href=quot;javascript:someFunction();quot;>some text</a> or <a href=quot;javascript:void(null);quot; onclick=quot;someFunction();quot;>some text</a> or <a href=quot;#quot; onclick=quot;someFunction();quot;>some text</a> IN CONTROL 2009 67
    100. 100. FUNDAMENTAL JAVASCRIPT An improvement, but still... <a href=quot;http://offsite.comquot; onclick=quot;newWin( this.href ); return false;quot;> some text</a> IN CONTROL 2009 68
    101. 101. FUNDAMENTAL JAVASCRIPT Getting warmer... window.onload = handleExternalLinks; function handleExternalLinks(){ var server = document.location.hostname; var anchors = document.getElementsByTagName(quot;aquot;); var i, href; for( i=0; i < anchors.length; i++ ){ href = anchors[i].href; if( href.indexOf(quot;http://quot; + server) == -1 && href.indexOf(quot;https://quot; + server) == -1 ){ // HREF is not a file on my server anchors[i].onclick = function(){ newWin( this.href ); }; } } } IN CONTROL 2009 69
    102. 102. FUNDAMENTAL JAVASCRIPT Getting warmer... window.onload = handleExternalLinks; function handleExternalLinks(){ var server = document.location.hostname; var anchors = document.getElementsByTagName(quot;aquot;); var i, href; for( i=0; i < anchors.length; i++ ){ href = anchors[i].href; if( href.indexOf(quot;http://quot; + server) == -1 && href.indexOf(quot;https://quot; + server) == -1 ){ // HREF is not a file on my server anchors[i].onclick = function(){ newWin( this.href ); }; } } } IN CONTROL 2009 69
    103. 103. FUNDAMENTAL JAVASCRIPT Getting warmer... window.onload = handleExternalLinks; function handleExternalLinks(){ var server = document.location.hostname; var anchors = document.getElementsByTagName(quot;aquot;); var i, href; for( i=0; i < anchors.length; i++ ){ href = anchors[i].href; if( href.indexOf(quot;http://quot; + server) == -1 && href.indexOf(quot;https://quot; + server) == -1 ){ // HREF is not a file on my server anchors[i].onclick = function(){ newWin( this.href ); }; } } } IN CONTROL 2009 69
    104. 104. FUNDAMENTAL JAVASCRIPT Getting warmer... window.onload = handleExternalLinks; function handleExternalLinks(){ var server = document.location.hostname; var anchors = document.getElementsByTagName(quot;aquot;); var i, href; for( i=0; i < anchors.length; i++ ){ href = anchors[i].href; if( href.indexOf(quot;http://quot; + server) == -1 && href.indexOf(quot;https://quot; + server) == -1 ){ // HREF is not a file on my server anchors[i].onclick = function(){ newWin( this.href ); }; } } } IN CONTROL 2009 69
    105. 105. FUNDAMENTAL JAVASCRIPT Getting warmer... window.onload = handleExternalLinks; function handleExternalLinks(){ var server = document.location.hostname; var anchors = document.getElementsByTagName(quot;aquot;); var i, href; for( i=0; i < anchors.length; i++ ){ href = anchors[i].href; if( href.indexOf(quot;http://quot; + server) == -1 && href.indexOf(quot;https://quot; + server) == -1 ){ // HREF is not a file on my server anchors[i].onclick = function(){ newWin( this.href ); }; } } } IN CONTROL 2009 69
    106. 106. FUNDAMENTAL JAVASCRIPT Getting warmer... window.onload = handleExternalLinks; function handleExternalLinks(){ var server = document.location.hostname; var anchors = document.getElementsByTagName(quot;aquot;); var i, href; for( i=0; i < anchors.length; i++ ){ href = anchors[i].href; if( href.indexOf(quot;http://quot; + server) == -1 && href.indexOf(quot;https://quot; + server) == -1 ){ // HREF is not a file on my server anchors[i].onclick = function(){ newWin( this.href ); }; } } } IN CONTROL 2009 69
    107. 107. FUNDAMENTAL JAVASCRIPT Getting warmer... window.onload = handleExternalLinks; function handleExternalLinks(){ var server = document.location.hostname; var anchors = document.getElementsByTagName(quot;aquot;); var i, href; for( i=0; i < anchors.length; i++ ){ href = anchors[i].href; if( href.indexOf(quot;http://quot; + server) == -1 && href.indexOf(quot;https://quot; + server) == -1 ){ // HREF is not a file on my server anchors[i].onclick = function(){ newWin( this.href ); }; } } } IN CONTROL 2009 69
    108. 108. FUNDAMENTAL JAVASCRIPT Getting warmer... window.onload = handleExternalLinks; function handleExternalLinks(){ var server = document.location.hostname; var anchors = document.getElementsByTagName(quot;aquot;); var i, href; for( i=0; i < anchors.length; i++ ){ href = anchors[i].href; if( href.indexOf(quot;http://quot; + server) == -1 && href.indexOf(quot;https://quot; + server) == -1 ){ // HREF is not a file on my server anchors[i].onclick = function(){ newWin( this.href ); }; } } } IN CONTROL 2009 69
    109. 109. FUNDAMENTAL JAVASCRIPT You’re hot document.getElementsByTagName( 'body' )[0] .onclick = clickDelegator; function clickDelegator( e ){ e = ( e ) ? e : event; var el = e.target || e.srcElement; // external links if( el.nodeName.toLowerCase() == 'a' && el.getAttribute( 'rel' ) == 'external' ){ newWin( el.href ); } } IN CONTROL 2009 70
    110. 110. FUNDAMENTAL JAVASCRIPT You’re hot document.getElementsByTagName( 'body' )[0] .onclick = clickDelegator; function clickDelegator( e ){ e = ( e ) ? e : event; var el = e.target || e.srcElement; // external links if( el.nodeName.toLowerCase() == 'a' && el.getAttribute( 'rel' ) == 'external' ){ newWin( el.href ); } } IN CONTROL 2009 70
    111. 111. FUNDAMENTAL JAVASCRIPT You’re hot document.getElementsByTagName( 'body' )[0] .onclick = clickDelegator; function clickDelegator( e ){ e = ( e ) ? e : event; var el = e.target || e.srcElement; // external links if( el.nodeName.toLowerCase() == 'a' && el.getAttribute( 'rel' ) == 'external' ){ newWin( el.href ); } } IN CONTROL 2009 70
    112. 112. FUNDAMENTAL JAVASCRIPT You’re hot document.getElementsByTagName( 'body' )[0] .onclick = clickDelegator; function clickDelegator( e ){ e = ( e ) ? e : event; var el = e.target || e.srcElement; // external links if( el.nodeName.toLowerCase() == 'a' && el.getAttribute( 'rel' ) == 'external' ){ newWin( el.href ); } } IN CONTROL 2009 70
    113. 113. FUNDAMENTAL JAVASCRIPT You’re hot document.getElementsByTagName( 'body' )[0] .onclick = clickDelegator; function clickDelegator( e ){ e = ( e ) ? e : event; var el = e.target || e.srcElement; // external links if( el.nodeName.toLowerCase() == 'a' && el.getAttribute( 'rel' ) == 'external' ){ newWin( el.href ); } } IN CONTROL 2009 70
    114. 114. FUNDAMENTAL JAVASCRIPT You’re hot document.getElementsByTagName( 'body' )[0] .onclick = clickDelegator; function clickDelegator( e ){ e = ( e ) ? e : event; var el = e.target || e.srcElement; // external links if( el.nodeName.toLowerCase() == 'a' && el.getAttribute( 'rel' ) == 'external' ){ newWin( el.href ); } } IN CONTROL 2009 70
    115. 115. WEB STANDARDS: FUELING INNOVATION WEB BUILDER 2.0 71
    116. 116. JavaScript CSS
    117. 117. FUNDAMENTAL JAVASCRIPT Remember stuff like this? <a href=quot;foo.htmlquot; style=quot;color:blue;quot; onmouseover=quot;this.style.color='red'quot; onmouseout=quot;this.style.color='blue'quot;>Foo</a> IN CONTROL 2009 73
    118. 118. FUNDAMENTAL JAVASCRIPT Remember stuff like this? <a href=quot;foo.htmlquot; style=quot;color:blue;quot; onmouseover=quot;this.style.color='red'quot; onmouseout=quot;this.style.color='blue'quot;>Foo</a> Obvisouly, we should be doing this instead: a, a:link, a:visited { color: blue; } a:hover { color: red; } IN CONTROL 2009 73
    119. 119. FUNDAMENTAL JAVASCRIPT Isn’t this the same? for( i=0; i<objects.length; i++){ objects[i].style.display = 'none'; } IN CONTROL 2009 74
    120. 120. FUNDAMENTAL JAVASCRIPT Small improvement for( i=0; i<objects.length; i++){ objects[i].style.position = 'absolute'; objects[i].style.left = '-999em'; } IN CONTROL 2009 75
    121. 121. FUNDAMENTAL JAVASCRIPT Separation CSS: .hidden { position: absolute; left: -999em; } JavaScript: for( i=0; i<objects.length; i++){ objects[i].addClassName( 'hidden' ); } IN CONTROL 2009 76
    122. 122. FUNDAMENTAL JAVASCRIPT Maintenance options ๏ external style rules added to your CSS file (by hand) ๏ external CSS file added to the document (by hand) ๏ external CSS file added to the document via script ๏ embedding CSS in the document via script IN CONTROL 2009 77
    123. 123. FUNDAMENTAL JAVASCRIPT Option 1: Add by hand At the end of your screen layout CSS file: /* =START WickedCool Script CSS (do not remove) */ .wicked { color: red; font: bold 4em/2 quot;Comic Sansquot;; } .cool { color: blue; font: bold 4em/2 quot;Comic Sansquot;; } /* =END WickedCool Script CSS */ IN CONTROL 2009 78
    124. 124. FUNDAMENTAL JAVASCRIPT Option 2: Include by hand Added to the head of your document: <script type=quot;text/javascriptquot; src=quot;WickedCool.jsquot;></script> <link rel=quot;stylesheetquot; type=quot;text/cssquot; media=quot;screenquot; href=quot;WickedCool.cssquot; /> IN CONTROL 2009 79
    125. 125. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include function FindPath( filename ){ var path = false; var scripts = document.getElementsByTagName( 'script' ); for( var i=0; i<scripts.length; i++ ){ if( scripts[i].getAttribute( 'src' ) && scripts[i].getAttribute( 'src' ) .indexOf( filename ) != -1 ){ path = scripts[i].getAttribute( 'src' ) .replace( new RegExp( filename ), '' ); break; } } return path; } IN CONTROL 2009 80
    126. 126. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include function FindPath( filename ){ var path = false; var scripts = document.getElementsByTagName( 'script' ); for( var i=0; i<scripts.length; i++ ){ if( scripts[i].getAttribute( 'src' ) && scripts[i].getAttribute( 'src' ) .indexOf( filename ) != -1 ){ path = scripts[i].getAttribute( 'src' ) .replace( new RegExp( filename ), '' ); break; } } return path; } IN CONTROL 2009 80
    127. 127. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include function FindPath( filename ){ var path = false; var scripts = document.getElementsByTagName( 'script' ); for( var i=0; i<scripts.length; i++ ){ if( scripts[i].getAttribute( 'src' ) && scripts[i].getAttribute( 'src' ) .indexOf( filename ) != -1 ){ path = scripts[i].getAttribute( 'src' ) .replace( new RegExp( filename ), '' ); break; } } return path; } IN CONTROL 2009 80
    128. 128. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include function FindPath( filename ){ var path = false; var scripts = document.getElementsByTagName( 'script' ); for( var i=0; i<scripts.length; i++ ){ if( scripts[i].getAttribute( 'src' ) && scripts[i].getAttribute( 'src' ) .indexOf( filename ) != -1 ){ path = scripts[i].getAttribute( 'src' ) .replace( new RegExp( filename ), '' ); break; } } return path; } IN CONTROL 2009 80
    129. 129. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include function FindPath( filename ){ var path = false; var scripts = document.getElementsByTagName( 'script' ); for( var i=0; i<scripts.length; i++ ){ if( scripts[i].getAttribute( 'src' ) && scripts[i].getAttribute( 'src' ) .indexOf( filename ) != -1 ){ path = scripts[i].getAttribute( 'src' ) .replace( new RegExp( filename ), '' ); break; } } return path; } IN CONTROL 2009 80
    130. 130. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include function FindPath( filename ){ var path = false; var scripts = document.getElementsByTagName( 'script' ); for( var i=0; i<scripts.length; i++ ){ if( scripts[i].getAttribute( 'src' ) && scripts[i].getAttribute( 'src' ) .indexOf( filename ) != -1 ){ path = scripts[i].getAttribute( 'src' ) .replace( new RegExp( filename ), '' ); break; } } return path; } IN CONTROL 2009 80
    131. 131. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include function FindPath( filename ){ var path = false; var scripts = document.getElementsByTagName( 'script' ); for( var i=0; i<scripts.length; i++ ){ if( scripts[i].getAttribute( 'src' ) && scripts[i].getAttribute( 'src' ) .indexOf( filename ) != -1 ){ path = scripts[i].getAttribute( 'src' ) .replace( new RegExp( filename ), '' ); break; } } return path; } IN CONTROL 2009 80
    132. 132. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include function FindPath( filename ){ var path = false; var scripts = document.getElementsByTagName( 'script' ); for( var i=0; i<scripts.length; i++ ){ if( scripts[i].getAttribute( 'src' ) && scripts[i].getAttribute( 'src' ) .indexOf( filename ) != -1 ){ path = scripts[i].getAttribute( 'src' ) .replace( new RegExp( filename ), '' ); break; } } return path; } IN CONTROL 2009 80
    133. 133. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include var WickedCool = { jsFile: 'WickedCool.js', cssFile: 'WickedCool.css', basePath: false, initialize: function(){ // determine the path this.basePath = FindPath( this.jsFile ); // add the CSS file var css = document.createElement( 'link' ); css.setAttribute( 'rel', 'stylesheet' ); css.setAttribute( 'type', 'text/css' ); css.setAttribute( 'media', 'screen' ); css.setAttribute( 'href', this.basePath + this.cssFile ); document.getElementsByTagName( 'head' )[0] .appendChild( css ); // do the rest of the wicked cool stuff } }; IN CONTROL 2009 81
    134. 134. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include var WickedCool = { jsFile: 'WickedCool.js', cssFile: 'WickedCool.css', basePath: false, initialize: function(){ // determine the path this.basePath = FindPath( this.jsFile ); // add the CSS file var css = document.createElement( 'link' ); css.setAttribute( 'rel', 'stylesheet' ); css.setAttribute( 'type', 'text/css' ); css.setAttribute( 'media', 'screen' ); css.setAttribute( 'href', this.basePath + this.cssFile ); document.getElementsByTagName( 'head' )[0] .appendChild( css ); // do the rest of the wicked cool stuff } }; IN CONTROL 2009 81
    135. 135. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include var WickedCool = { jsFile: 'WickedCool.js', cssFile: 'WickedCool.css', basePath: false, initialize: function(){ // determine the path this.basePath = FindPath( this.jsFile ); // add the CSS file var css = document.createElement( 'link' ); css.setAttribute( 'rel', 'stylesheet' ); css.setAttribute( 'type', 'text/css' ); css.setAttribute( 'media', 'screen' ); css.setAttribute( 'href', this.basePath + this.cssFile ); document.getElementsByTagName( 'head' )[0] .appendChild( css ); // do the rest of the wicked cool stuff } }; IN CONTROL 2009 81
    136. 136. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include var WickedCool = { jsFile: 'WickedCool.js', cssFile: 'WickedCool.css', basePath: false, initialize: function(){ // determine the path this.basePath = FindPath( this.jsFile ); // add the CSS file var css = document.createElement( 'link' ); css.setAttribute( 'rel', 'stylesheet' ); css.setAttribute( 'type', 'text/css' ); css.setAttribute( 'media', 'screen' ); css.setAttribute( 'href', this.basePath + this.cssFile ); document.getElementsByTagName( 'head' )[0] .appendChild( css ); // do the rest of the wicked cool stuff } }; IN CONTROL 2009 81
    137. 137. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include var WickedCool = { jsFile: 'WickedCool.js', cssFile: 'WickedCool.css', basePath: false, initialize: function(){ // determine the path this.basePath = FindPath( this.jsFile ); // add the CSS file var css = document.createElement( 'link' ); css.setAttribute( 'rel', 'stylesheet' ); css.setAttribute( 'type', 'text/css' ); css.setAttribute( 'media', 'screen' ); css.setAttribute( 'href', this.basePath + this.cssFile ); document.getElementsByTagName( 'head' )[0] .appendChild( css ); // do the rest of the wicked cool stuff } }; IN CONTROL 2009 81
    138. 138. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include var WickedCool = { jsFile: 'WickedCool.js', cssFile: 'WickedCool.css', basePath: false, initialize: function(){ // determine the path this.basePath = FindPath( this.jsFile ); // add the CSS file var css = document.createElement( 'link' ); css.setAttribute( 'rel', 'stylesheet' ); css.setAttribute( 'type', 'text/css' ); css.setAttribute( 'media', 'screen' ); css.setAttribute( 'href', this.basePath + this.cssFile ); document.getElementsByTagName( 'head' )[0] .appendChild( css ); // do the rest of the wicked cool stuff } }; IN CONTROL 2009 81
    139. 139. FUNDAMENTAL JAVASCRIPT Option 3: Scripted include var WickedCool = { jsFile: 'WickedCool.js', cssFile: 'WickedCool.css', basePath: false, initialize: function(){ // determine the path this.basePath = FindPath( this.jsFile ); // add the CSS file var css = document.createElement( 'link' ); css.setAttribute( 'rel', 'stylesheet' ); css.setAttribute( 'type', 'text/css' ); css.setAttribute( 'media', 'screen' ); css.setAttribute( 'href', this.basePath + this.cssFile ); document.getElementsByTagName( 'head' )[0] .appendChild( css ); // do the rest of the wicked cool stuff } }; IN CONTROL 2009 81
    140. 140. FUNDAMENTAL JAVASCRIPT Option 4: Scripted embed function addCSS( styles ){ var el = document.createElement( 'style' ); el.setAttribute( 'type', 'text/css' ); if( el.styleSheet ){ el.styleSheet.cssText = styles; } else { el.appendChild( document.createTextNode( styles ) ); } document.getElementsByTagName( 'head' )[0] .appendChild( el ); } based on the work of Nicholas Zakas IN CONTROL 2009 82
    141. 141. FUNDAMENTAL JAVASCRIPT Option 4: Scripted embed function addCSS( styles ){ var el = document.createElement( 'style' ); el.setAttribute( 'type', 'text/css' ); if( el.styleSheet ){ el.styleSheet.cssText = styles; } else { el.appendChild( document.createTextNode( styles ) ); } document.getElementsByTagName( 'head' )[0] .appendChild( el ); } based on the work of Nicholas Zakas IN CONTROL 2009 82
    142. 142. FUNDAMENTAL JAVASCRIPT Option 4: Scripted embed function addCSS( styles ){ var el = document.createElement( 'style' ); el.setAttribute( 'type', 'text/css' ); if( el.styleSheet ){ el.styleSheet.cssText = styles; } else { el.appendChild( document.createTextNode( styles ) ); } document.getElementsByTagName( 'head' )[0] .appendChild( el ); } based on the work of Nicholas Zakas IN CONTROL 2009 82
    143. 143. FUNDAMENTAL JAVASCRIPT Option 4: Scripted embed function addCSS( styles ){ var el = document.createElement( 'style' ); el.setAttribute( 'type', 'text/css' ); if( el.styleSheet ){ el.styleSheet.cssText = styles; } else { el.appendChild( document.createTextNode( styles ) ); } document.getElementsByTagName( 'head' )[0] .appendChild( el ); } based on the work of Nicholas Zakas IN CONTROL 2009 82
    144. 144. FUNDAMENTAL JAVASCRIPT Option 4: Scripted embed function addCSS( styles ){ var el = document.createElement( 'style' ); el.setAttribute( 'type', 'text/css' ); if( el.styleSheet ){ el.styleSheet.cssText = styles; } else { el.appendChild( document.createTextNode( styles ) ); } document.getElementsByTagName( 'head' )[0] .appendChild( el ); } based on the work of Nicholas Zakas IN CONTROL 2009 82
    145. 145. FUNDAMENTAL JAVASCRIPT Option 4: Scripted embed function addCSS( styles ){ var el = document.createElement( 'style' ); el.setAttribute( 'type', 'text/css' ); if( el.styleSheet ){ el.styleSheet.cssText = styles; } else { el.appendChild( document.createTextNode( styles ) ); } document.getElementsByTagName( 'head' )[0] .appendChild( el ); } based on the work of Nicholas Zakas IN CONTROL 2009 82
    146. 146. FUNDAMENTAL JAVASCRIPT Option 4: Scripted embed var WickedCool = { _css: '.wicked { color: red; ' + ' font: bold 4em/2 quot;Comic Sansquot;; } ' + '.cool { color: blue; ' + ' font: bold 4em/2' quot;Comic Sansquot;; }', initialize: function(){ // add the CSS addCSS( this._css ); // do the rest of the wicked cool stuff } }; based on the work of Nicholas Zakas IN CONTROL 2009 83
    147. 147. FUNDAMENTAL JAVASCRIPT Option 4: Scripted embed var WickedCool = { _css: '.wicked { color: red; ' + ' font: bold 4em/2 quot;Comic Sansquot;; } ' + '.cool { color: blue; ' + ' font: bold 4em/2' quot;Comic Sansquot;; }', initialize: function(){ // add the CSS addCSS( this._css ); // do the rest of the wicked cool stuff } }; based on the work of Nicholas Zakas IN CONTROL 2009 83
    148. 148. FUNDAMENTAL JAVASCRIPT Option 4: Scripted embed var WickedCool = { _css: '.wicked { color: red; ' + ' font: bold 4em/2 quot;Comic Sansquot;; } ' + '.cool { color: blue; ' + ' font: bold 4em/2' quot;Comic Sansquot;; }', initialize: function(){ // add the CSS addCSS( this._css ); // do the rest of the wicked cool stuff } }; based on the work of Nicholas Zakas IN CONTROL 2009 83
    149. 149. FUNDAMENTAL JAVASCRIPT Option 4: Scripted embed var WickedCool = { _css: '.wicked { color: red; ' + ' font: bold 4em/2 quot;Comic Sansquot;; } ' + '.cool { color: blue; ' + ' font: bold 4em/2' quot;Comic Sansquot;; }', initialize: function(){ // add the CSS addCSS( this._css ); // do the rest of the wicked cool stuff } }; based on the work of Nicholas Zakas IN CONTROL 2009 83
    150. 150. FUNDAMENTAL JAVASCRIPT Option 4: Scripted embed var WickedCool = { _css: '.wicked { color: red; ' + ' font: bold 4em/2 quot;Comic Sansquot;; } ' + '.cool { color: blue; ' + ' font: bold 4em/2' quot;Comic Sansquot;; }', initialize: function(){ // add the CSS addCSS( this._css ); // do the rest of the wicked cool stuff } }; based on the work of Nicholas Zakas IN CONTROL 2009 83
    151. 151. BUT KEEP IN MIND
    152. 152. YOU NEED TO AVOID APPLYING SCRIPT-RELATED STYLES
    153. 153. UNTIL YOU KNOW YOUR SCRIPT CAN RUN AND IT HAS INITIALIZED PROPERLY
    154. 154. FUNDAMENTAL JAVASCRIPT How do we do that? ๏ make your style rules specific: .TabInterface-folder { ... } or #TabInterface .tab { ... } #TabInterface .tab.active { ... } IN CONTROL 2009 85
    155. 155. FUNDAMENTAL JAVASCRIPT How do we do that? <div id=quot;mainquot; class=quot;tabbedquot;> becomes <div id=quot;mainquot; class=quot;tabbed-onquot;> IN CONTROL 2009 86
    156. 156. FUNDAMENTAL JAVASCRIPT How do we do that? Default Activated add “-on” to the class .tabbed .tabbed-on add an activation class .auto-submit .auto-submit.active change the form of the class .replace-me .replaced IN CONTROL 2009 86
    157. 157. WEB STANDARDS: FUELING INNOVATION WEB BUILDER 2.0 87
    158. 158. FUNDAMENTAL JAVASCRIPT Look for methods function someFunction(){ if( !document.getElementsByTagName ) return; // code that uses document.getElementsByTagName() ... } IN CONTROL 2009 88
    159. 159. FUNDAMENTAL JAVASCRIPT Look for methods function someFunction(){ if( !document.getElementsByTagName || !document.getElementById ) return; /* code that uses document.getElementsByTagName() and document.getElementById() */ } IN CONTROL 2009 89
    160. 160. FUNDAMENTAL JAVASCRIPT Look for elements function someFunction(){ if( !document.getElementsByTagName || !document.getElementsByTagName( 'p' ) ) return; /* code that uses document.getElementsByTagName() and requires the presence of a P element */ ... } IN CONTROL 2009 90
    161. 161. FUNDAMENTAL JAVASCRIPT Look for identified elements function someFunction(){ if( !document.getElementById || !document.getElementById( 'content' ) ) return; // code that requires the presence of #content ... } IN CONTROL 2009 91
    162. 162. FUNDAMENTAL JAVASCRIPT Look for objects function someFunction(){ if( typeof( Prototype ) == 'undefined' ) return; // code that uses Prototype ... } IN CONTROL 2009 92
    163. 163. FUNDAMENTAL JAVASCRIPT Look for object versions function someFunction(){ if( typeof( jQuery ) == 'undefined' || parseFloat( jQuery.jquery ) < 1.2 ) return; // code that uses jQuery 1.2 or higher ... } IN CONTROL 2009 93
    164. 164. FUNDAMENTAL JAVASCRIPT Look before you leap window.onload = function(){ if( document.getElementsByTagName && document.getElementById ){ someFunction(); } }; IN CONTROL 2009 94
    165. 165. FUNDAMENTAL JAVASCRIPT PE with JavaScript ๏ Start with the content, then work your way out ๏ Get unobtrusive ๏ Keep some distance between your styles & your scripts ๏ Always wear your detective hat IN CONTROL 2009 95
    166. 166. HOW DOES IT ALL COME TOGETHER?
    167. 167. FUNDAMENTAL JAVASCRIPT Example 1: Tab Interface IN CONTROL 2009 97
    168. 168. FUNDAMENTAL JAVASCRIPT Traditional approach <h1>Pumpkin Pie</h1> <div class=quot;containerquot;> <div class=quot;sectionquot;> <h2>Overview</h2> <img src=quot;pie.jpgquot; alt=quot;quot;> <p>Whether you're hosting a festive party or a casual get-together with friends, our Pumpkin Pie will make entertaining easy!</p> ... </div> ... <ul class=quot;tabsquot;> <li><a href=quot;#quot;>Overview</a></li> <li><a href=quot;#quot;>Ingredients</a></li> <li><a href=quot;#quot;>Directions</a></li> <li><a href=quot;#quot;>Nutrition</a></li> </ul> </div> IN CONTROL 2009 98
    169. 169. FUNDAMENTAL JAVASCRIPT Traditional approach <h1>Pumpkin Pie</h1> <div class=quot;containerquot;> <div class=quot;sectionquot;> <h2>Overview</h2> <img src=quot;pie.jpgquot; alt=quot;quot;> <p>Whether you're hosting a festive party or a casual get-together with friends, our Pumpkin Pie will make entertaining easy!</p> ... </div> ... <ul class=quot;tabsquot;> <li><a href=quot;#quot;>Overview</a></li> <li><a href=quot;#quot;>Ingredients</a></li> <li><a href=quot;#quot;>Directions</a></li> <li><a href=quot;#quot;>Nutrition</a></li> </ul> </div> IN CONTROL 2009 98
    170. 170. FUNDAMENTAL JAVASCRIPT Traditional approach <h1>Pumpkin Pie</h1> <div class=quot;containerquot;> <div class=quot;sectionquot;> <h2>Overview</h2> <img src=quot;pie.jpgquot; alt=quot;quot;> <p>Whether you're hosting a festive party or a casual get-together with friends, our Pumpkin Pie will make entertaining easy!</p> ... </div> ... <ul class=quot;tabsquot;> <li><a href=quot;#quot;>Overview</a></li> <li><a href=quot;#quot;>Ingredients</a></li> <li><a href=quot;#quot;>Directions</a></li> <li><a href=quot;#quot;>Nutrition</a></li> </ul> </div> IN CONTROL 2009 98
    171. 171. FUNDAMENTAL JAVASCRIPT Traditional approach <h1>Pumpkin Pie</h1> <div class=quot;containerquot;> <div class=quot;sectionquot;> <h2>Overview</h2> <img src=quot;pie.jpgquot; alt=quot;quot;> <p>Whether you're hosting a festive party or a casual get-together with friends, our Pumpkin Pie will make entertaining easy!</p> ... </div> ... <ul class=quot;tabsquot;> <li><a href=quot;#quot;>Overview</a></li> <li><a href=quot;#quot;>Ingredients</a></li> <li><a href=quot;#quot;>Directions</a></li> <li><a href=quot;#quot;>Nutrition</a></li> </ul> </div> IN CONTROL 2009 98
    172. 172. FUNDAMENTAL JAVASCRIPT No style IN CONTROL 2009 99
    173. 173. FUNDAMENTAL JAVASCRIPT A little typography IN CONTROL 2009 100
    174. 174. FUNDAMENTAL JAVASCRIPT Typography & color IN CONTROL 2009 101
    175. 175. FUNDAMENTAL JAVASCRIPT No style IN CONTROL 2009 102
    176. 176. FUNDAMENTAL JAVASCRIPT No style .tabbed IN CONTROL 2009 102
    177. 177. FUNDAMENTAL JAVASCRIPT The actual source <h1>Pumpkin Pie</h1> <div class=quot;tabbedquot;> <h2>Overview</h2> <img src=quot;pie.jpgquot; alt=quot;quot; /> <p>Whether you're hosting a festive party or a casual get-together with friends, our Pumpkin Pie will make entertaining easy!</p> ... <h2>Ingredients</h2> <ul> <li>1 (9<abbr title=quot;inchquot;>in</abbr>) unbaked deep dish pie crust</li> <li>½ cup white sugar</li> <li>1 <abbr title=quot;teaspoonquot;>tsp</abbr> ground cinnamon</li> ... </ul> <h2>Directions</h2> ... </div> IN CONTROL 2009 103
    178. 178. FUNDAMENTAL JAVASCRIPT The actual source <h1>Pumpkin Pie</h1> <div class=quot;tabbedquot;> <h2>Overview</h2> <img src=quot;pie.jpgquot; alt=quot;quot; /> <p>Whether you're hosting a festive party or a casual get-together with friends, our Pumpkin Pie will make entertaining easy!</p> ... <h2>Ingredients</h2> <ul> <li>1 (9<abbr title=quot;inchquot;>in</abbr>) unbaked deep dish pie crust</li> <li>½ cup white sugar</li> <li>1 <abbr title=quot;teaspoonquot;>tsp</abbr> ground cinnamon</li> ... </ul> <h2>Directions</h2> ... </div> IN CONTROL 2009 103
    179. 179. FUNDAMENTAL JAVASCRIPT Understanding the flow IN CONTROL 2009 104
    180. 180. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ // Public Properties this.Version = '0.3'; // version // Private Properties var _i = i; // incrementor var _cabinet = el; // the quot;cabinetquot; element (container) var _id = false; // ID of _cabinet var _active = false; // ID of the active quot;folderquot; var _tag = false; // tag we'll split it on // the tab list var _index = document.createElement( 'ul' ); // prototype elements var _els = { li: document.createElement( 'li' ), div: document.createElement( 'div' ) }; // methods to go here }; IN CONTROL 2009 105
    181. 181. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ // Public Properties this.Version = '0.3'; // version // Private Properties var _i = i; // incrementor var _cabinet = el; // the quot;cabinetquot; element (container) var _id = false; // ID of _cabinet var _active = false; // ID of the active quot;folderquot; var _tag = false; // tag we'll split it on // the tab list var _index = document.createElement( 'ul' ); // prototype elements var _els = { li: document.createElement( 'li' ), div: document.createElement( 'div' ) }; // methods to go here }; IN CONTROL 2009 105
    182. 182. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ // Public Properties this.Version = '0.3'; // version // Private Properties var _i = i; // incrementor var _cabinet = el; // the quot;cabinetquot; element (container) var _id = false; // ID of _cabinet var _active = false; // ID of the active quot;folderquot; var _tag = false; // tag we'll split it on // the tab list var _index = document.createElement( 'ul' ); // prototype elements var _els = { li: document.createElement( 'li' ), div: document.createElement( 'div' ) }; // methods to go here }; IN CONTROL 2009 105
    183. 183. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ // Public Properties this.Version = '0.3'; // version // Private Properties var _i = i; // incrementor var _cabinet = el; // the quot;cabinetquot; element (container) var _id = false; // ID of _cabinet var _active = false; // ID of the active quot;folderquot; var _tag = false; // tag we'll split it on // the tab list var _index = document.createElement( 'ul' ); // prototype elements var _els = { li: document.createElement( 'li' ), div: document.createElement( 'div' ) }; // methods to go here }; IN CONTROL 2009 105
    184. 184. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ // Public Properties this.Version = '0.3'; // version // Private Properties var _i = i; // incrementor var _cabinet = el; // the quot;cabinetquot; element (container) var _id = false; // ID of _cabinet var _active = false; // ID of the active quot;folderquot; var _tag = false; // tag we'll split it on // the tab list var _index = document.createElement( 'ul' ); // prototype elements var _els = { li: document.createElement( 'li' ), div: document.createElement( 'div' ) }; // methods to go here }; IN CONTROL 2009 105
    185. 185. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ ... function initialize(){ // code to come } function addClassName( e, c ){ var classes = ( !e.className ) ? [] : e.className.split( ' ' ); classes.push( c ); e.className = classes.join( ' ' ); } function removeClassName( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) classes.splice( i, 1 ); } e.className = classes.join( ' ' ); } // start it up initialize(); }; IN CONTROL 2009 106
    186. 186. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ ... function initialize(){ // code to come } function addClassName( e, c ){ var classes = ( !e.className ) ? [] : e.className.split( ' ' ); classes.push( c ); e.className = classes.join( ' ' ); } function removeClassName( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) classes.splice( i, 1 ); } e.className = classes.join( ' ' ); } // start it up initialize(); }; IN CONTROL 2009 106
    187. 187. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ ... function initialize(){ // code to come } function addClassName( e, c ){ var classes = ( !e.className ) ? [] : e.className.split( ' ' ); classes.push( c ); e.className = classes.join( ' ' ); } function removeClassName( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) classes.splice( i, 1 ); } e.className = classes.join( ' ' ); } // start it up initialize(); }; IN CONTROL 2009 106
    188. 188. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ ... function initialize(){ // code to come } function addClassName( e, c ){ var classes = ( !e.className ) ? [] : e.className.split( ' ' ); classes.push( c ); e.className = classes.join( ' ' ); } function removeClassName( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) classes.splice( i, 1 ); } e.className = classes.join( ' ' ); } // start it up initialize(); }; IN CONTROL 2009 106
    189. 189. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ ... function initialize(){ // code to come } function addClassName( e, c ){ var classes = ( !e.className ) ? [] : e.className.split( ' ' ); classes.push( c ); e.className = classes.join( ' ' ); } function removeClassName( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) classes.splice( i, 1 ); } e.className = classes.join( ' ' ); } // start it up initialize(); }; IN CONTROL 2009 106
    190. 190. FUNDAMENTAL JAVASCRIPT THE CODE function TabInterface( el, i ){ function initialize(){ // set the id _id = el.getAttribute( 'id' ) || 'folder-' + _i; if( !el.getAttribute( 'id' ) ) el.setAttribute( 'id', _id ); // trim whitespace var node = _cabinet.firstChild; while( node ){ var nextNode = node.nextSibling; if( node.nodeType == 3 && !/S/.test( node.nodeValue ) ) _cabinet.removeChild( node ); node = nextNode; } } ... }; IN CONTROL 2009 107
    191. 191. FUNDAMENTAL JAVASCRIPT THE CODE function TabInterface( el, i ){ function initialize(){ // set the id _id = el.getAttribute( 'id' ) || 'folder-' + _i; if( !el.getAttribute( 'id' ) ) el.setAttribute( 'id', _id ); // trim whitespace var node = _cabinet.firstChild; while( node ){ var nextNode = node.nextSibling; if( node.nodeType == 3 && !/S/.test( node.nodeValue ) ) _cabinet.removeChild( node ); node = nextNode; } } ... }; IN CONTROL 2009 107
    192. 192. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ function initialize(){ ... // find the first heading var headers = [ 'h1', 'h2', 'h3', 'h4', 'h5', 'h6' ]; var hLen = headers.length; for( var i=0; i<hLen; i++ ){ if( _cabinet.firstChild.nodeName.toLowerCase() == headers[i] ){ _tag = headers[i]; break; } } } ... }; IN CONTROL 2009 108
    193. 193. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ function initialize(){ ... // establish the folders var rexp = new RegExp( '<(' + _tag + ')', 'ig' ); var arr = _cabinet.innerHTML.replace( rexp, quot;||||<$1quot; ).split( '||||' ); arr.shift(); _cabinet.innerHTML = ''; removeClassName( _cabinet, 'tabbed' ); addClassName( _cabinet, 'tabbed-on' ); } ... }; IN CONTROL 2009 109
    194. 194. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ function initialize(){ ... for( var k=0, aLen = arr.length; k<aLen; k++ ){ // build the div var folder = _els.div.cloneNode( true ); addClassName( folder, 'folder' ); folder.setAttribute( 'id', _id + '-' + k ); folder.innerHTML = arr[k]; _cabinet.appendChild( folder ); // build the tab var tab = _els.li.cloneNode( true ); tab.folder = folder.getAttribute( 'id' ); tab.setAttribute( 'id', tab.folder + '-tab' ); tab.onclick = swap; // set the action var heading = folder.getElementsByTagName( _tag )[0]; tab.innerHTML = heading.innerHTML; addClassName( heading, 'hidden' ); _index.appendChild( tab ); } } ... IN CONTROL 2009 110
    195. 195. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ function initialize(){ ... for( var k=0, aLen = arr.length; k<aLen; k++ ){ // build the div var folder = _els.div.cloneNode( true ); addClassName( folder, 'folder' ); folder.setAttribute( 'id', _id + '-' + k ); folder.innerHTML = arr[k]; _cabinet.appendChild( folder ); // build the tab var tab = _els.li.cloneNode( true ); tab.folder = folder.getAttribute( 'id' ); tab.setAttribute( 'id', tab.folder + '-tab' ); tab.onclick = swap; // set the action var heading = folder.getElementsByTagName( _tag )[0]; tab.innerHTML = heading.innerHTML; addClassName( heading, 'hidden' ); _index.appendChild( tab ); } } ... IN CONTROL 2009 110
    196. 196. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ function initialize(){ ... for( var k=0, aLen = arr.length; k<aLen; k++ ){ // build the div var folder = _els.div.cloneNode( true ); addClassName( folder, 'folder' ); folder.setAttribute( 'id', _id + '-' + k ); folder.innerHTML = arr[k]; _cabinet.appendChild( folder ); // build the tab var tab = _els.li.cloneNode( true ); tab.folder = folder.getAttribute( 'id' ); tab.setAttribute( 'id', tab.folder + '-tab' ); tab.onclick = swap; // set the action var heading = folder.getElementsByTagName( _tag )[0]; tab.innerHTML = heading.innerHTML; addClassName( heading, 'hidden' ); _index.appendChild( tab ); } } ... IN CONTROL 2009 110
    197. 197. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ function initialize(){ ... for( var k=0, aLen = arr.length; k<aLen; k++ ){ // build the div var folder = _els.div.cloneNode( true ); addClassName( folder, 'folder' ); folder.setAttribute( 'id', _id + '-' + k ); folder.innerHTML = arr[k]; _cabinet.appendChild( folder ); // build the tab var tab = _els.li.cloneNode( true ); tab.folder = folder.getAttribute( 'id' ); tab.setAttribute( 'id', tab.folder + '-tab' ); tab.onclick = swap; // set the action var heading = folder.getElementsByTagName( _tag )[0]; tab.innerHTML = heading.innerHTML; addClassName( heading, 'hidden' ); _index.appendChild( tab ); } } ... IN CONTROL 2009 110
    198. 198. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ function initialize(){ ... for( var k=0, aLen = arr.length; k<aLen; k++ ){ ... // active? if( k == 0 ){ addClassName( folder, 'visible' ); _active = folder.getAttribute( 'id' ); addClassName( tab, 'active-tab' ); } } // add the index _index.className = 'tab-list'; _cabinet.appendChild( _index ); } ... }; IN CONTROL 2009 111
    199. 199. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ function initialize(){ ... for( var k=0, aLen = arr.length; k<aLen; k++ ){ ... // active? if( k == 0 ){ addClassName( folder, 'visible' ); _active = folder.getAttribute( 'id' ); addClassName( tab, 'active-tab' ); } } // add the index _index.className = 'tab-list'; _cabinet.appendChild( _index ); } ... }; IN CONTROL 2009 111
    200. 200. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ ... function swap( e ){ e = ( e ) ? e : event; var tab = e.target || e.srcElement; removeClassName( document.getElementById( _active + '-tab' ), 'active-tab' ); removeClassName( document.getElementById( _active ), 'visible' ); addClassName( tab, 'active-tab' ); addClassName( document.getElementById( tab.folder ), 'visible' ); _active = tab.folder; } ... }; IN CONTROL 2009 112
    201. 201. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ ... function swap( e ){ e = ( e ) ? e : event; var tab = e.target || e.srcElement; removeClassName( document.getElementById( _active + '-tab' ), 'active-tab' ); removeClassName( document.getElementById( _active ), 'visible' ); addClassName( tab, 'active-tab' ); addClassName( document.getElementById( tab.folder ), 'visible' ); _active = tab.folder; } ... }; IN CONTROL 2009 112
    202. 202. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ ... function swap( e ){ e = ( e ) ? e : event; var tab = e.target || e.srcElement; removeClassName( document.getElementById( _active + '-tab' ), 'active-tab' ); removeClassName( document.getElementById( _active ), 'visible' ); addClassName( tab, 'active-tab' ); addClassName( document.getElementById( tab.folder ), 'visible' ); _active = tab.folder; } ... }; IN CONTROL 2009 112
    203. 203. FUNDAMENTAL JAVASCRIPT The code function TabInterface( el, i ){ ... function swap( e ){ e = ( e ) ? e : event; var tab = e.target || e.srcElement; removeClassName( document.getElementById( _active + '-tab' ), 'active-tab' ); removeClassName( document.getElementById( _active ), 'visible' ); addClassName( tab, 'active-tab' ); addClassName( document.getElementById( tab.folder ), 'visible' ); _active = tab.folder; } ... }; IN CONTROL 2009 112
    204. 204. FUNDAMENTAL JAVASCRIPT Greater flexibility function TabInterface( el, i ){ function initialize(){ ... for( var k=0, aLen = arr.length; k<aLen; k++ ){ ... var heading = folder.getElementsByTagName( _tag )[0]; tab.innerHTML = heading.innerHTML; if( heading.getAttribute( 'title' ) ){ addClassName( heading, 'hidden' ); tab.innerHTML = heading.getAttribute( 'title' ) _index.appendChild( tab ); } else { ... tab.innerHTML = heading.innerHTML; } addClassName( heading, 'hidden' ); } } ... _index.appendChild( tab ); }; ... } } ... }; IN CONTROL 2009 113
    205. 205. FUNDAMENTAL JAVASCRIPT Greater flexibility function TabInterface( el, i ){ function initialize(){ ... for( var k=0, aLen = arr.length; k<aLen; k++ ){ ... var heading = folder.getElementsByTagName( _tag )[0]; if( heading.getAttribute( 'title' ) ){ tab.innerHTML = heading.getAttribute( 'title' ) } else { tab.innerHTML = heading.innerHTML; addClassName( heading, 'hidden' ); } _index.appendChild( tab ); ... } } ... }; IN CONTROL 2009 113
    206. 206. FUNDAMENTAL JAVASCRIPT Running it // Load up TabInterface if( document.getElementById && document.getElementsByTagName && document.createElement ){ var cabinets = Array(); addDOMLoadEvent( function(){ var collection = document.getElementsByTagName( '*' ); for( var i=0, cLen = collection.length; i<cLen; i++ ){ if( collection[i] && /s*tabbeds*/.test( collection[i].className ) ){ cabinets.push( new TabInterface( collection[i], i ) ); } } } ); } IN CONTROL 2009 114
    207. 207. FUNDAMENTAL JAVASCRIPT Running it // Load up TabInterface if( document.getElementById && document.getElementsByTagName && document.createElement ){ var cabinets = Array(); addDOMLoadEvent( function(){ var collection = document.getElementsByTagName( '*' ); for( var i=0, cLen = collection.length; i<cLen; i++ ){ if( collection[i] && /s*tabbeds*/.test( collection[i].className ) ){ cabinets.push( new TabInterface( collection[i], i ) ); } } } ); } IN CONTROL 2009 114
    208. 208. FUNDAMENTAL JAVASCRIPT Running it // Load up TabInterface if( document.getElementById && document.getElementsByTagName && document.createElement ){ var cabinets = Array(); addDOMLoadEvent( function(){ var collection = document.getElementsByTagName( '*' ); for( var i=0, cLen = collection.length; i<cLen; i++ ){ if( collection[i] && /s*tabbeds*/.test( collection[i].className ) ){ cabinets.push( new TabInterface( collection[i], i ) ); } } } ); } IN CONTROL 2009 114
    209. 209. FUNDAMENTAL JAVASCRIPT Running it // Load up TabInterface if( document.getElementById && document.getElementsByTagName && document.createElement ){ var cabinets = Array(); addDOMLoadEvent( function(){ var collection = document.getElementsByTagName( '*' ); for( var i=0, cLen = collection.length; i<cLen; i++ ){ if( collection[i] && /s*tabbeds*/.test( collection[i].className ) ){ cabinets.push( new TabInterface( collection[i], i ) ); } } } ); } IN CONTROL 2009 114
    210. 210. FUNDAMENTAL JAVASCRIPT The full experience IN CONTROL 2009 115
    211. 211. QUESTIONS?
    212. 212. FUNDAMENTAL JAVASCRIPT Example 2: Collapsing Form IN CONTROL 2009 117
    213. 213. FUNDAMENTAL JAVASCRIPT Collapsing Form as HTML IN CONTROL 2009 118
    214. 214. FUNDAMENTAL JAVASCRIPT Collapsing Form with CSS IN CONTROL 2009 119
    215. 215. FUNDAMENTAL JAVASCRIPT Collapsing Form with CSS IN CONTROL 2009 120
    216. 216. FUNDAMENTAL JAVASCRIPT Collapsing Form with CSS IN CONTROL 2009 121
    217. 217. FUNDAMENTAL JAVASCRIPT HTML hooks IN CONTROL 2009 122
    218. 218. FUNDAMENTAL JAVASCRIPT HTML hooks form.collapsing IN CONTROL 2009 122
    219. 219. FUNDAMENTAL JAVASCRIPT HTML hooks fieldset.optional IN CONTROL 2009 122
    220. 220. FUNDAMENTAL JAVASCRIPT Understanding the flow IN CONTROL 2009 123
    221. 221. FUNDAMENTAL JAVASCRIPT The code var Easy = { addClassName: function( e, c ){ var classes = ( !e.className ) ? [] : e.className.split( ' ' ); classes.push( c ); e.className = classes.join( ' ' ); }, removeClassName: function( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) classes.splice( i, 1 ); } e.className = classes.join( ' ' ); }, hasClassName: function( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) return true; } return false; } }; IN CONTROL 2009 124
    222. 222. FUNDAMENTAL JAVASCRIPT The code var Easy = { addClassName: function( e, c ){ var classes = ( !e.className ) ? [] : e.className.split( ' ' ); classes.push( c ); e.className = classes.join( ' ' ); }, removeClassName: function( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) classes.splice( i, 1 ); } e.className = classes.join( ' ' ); }, hasClassName: function( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) return true; } return false; } }; IN CONTROL 2009 124
    223. 223. FUNDAMENTAL JAVASCRIPT The code var Easy = { addClassName: function( e, c ){ var classes = ( !e.className ) ? [] : e.className.split( ' ' ); classes.push( c ); e.className = classes.join( ' ' ); }, removeClassName: function( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) classes.splice( i, 1 ); } e.className = classes.join( ' ' ); }, hasClassName: function( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) return true; } return false; } }; IN CONTROL 2009 124
    224. 224. FUNDAMENTAL JAVASCRIPT The code var Easy = { addClassName: function( e, c ){ var classes = ( !e.className ) ? [] : e.className.split( ' ' ); classes.push( c ); e.className = classes.join( ' ' ); }, removeClassName: function( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) classes.splice( i, 1 ); } e.className = classes.join( ' ' ); }, hasClassName: function( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) return true; } return false; } }; IN CONTROL 2009 124
    225. 225. FUNDAMENTAL JAVASCRIPT The code var Easy = { addClassName: function( e, c ){ var classes = ( !e.className ) ? [] : e.className.split( ' ' ); classes.push( c ); e.className = classes.join( ' ' ); }, removeClassName: function( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) classes.splice( i, 1 ); } e.className = classes.join( ' ' ); }, hasClassName: function( e, c ){ var classes = e.className.split( ' ' ); for( var i=classes.length-1; i>=0; i-- ){ if( classes[i] == c ) return true; } return false; } }; IN CONTROL 2009 124
    226. 226. FUNDAMENTAL JAVASCRIPT The code var CollapsingForm = Class.create(); CollapsingForm.prototype = { link: document.createElement( 'a' ), linkText: [ document.createTextNode( 'More options' ), document.createTextNode( 'Fewer options' ) ], hidden: [], state: false, id: false, }; IN CONTROL 2009 125
    227. 227. FUNDAMENTAL JAVASCRIPT The code var CollapsingForm = Class.create(); CollapsingForm.prototype = { link: document.createElement( 'a' ), linkText: [ document.createTextNode( 'More options' ), document.createTextNode( 'Fewer options' ) ], hidden: [], state: false, id: false, }; IN CONTROL 2009 125
    228. 228. FUNDAMENTAL JAVASCRIPT The code var CollapsingForm = Class.create(); CollapsingForm.prototype = { link: document.createElement( 'a' ), linkText: [ document.createTextNode( 'More options' ), document.createTextNode( 'Fewer options' ) ], hidden: [], state: false, id: false, }; IN CONTROL 2009 125
    229. 229. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { ... initialize: function( form, i ){ // set the id this.id = i; // get the fieldsets var coll = form.getElementsByTagName( 'fieldset' ); // look for hiddens var hide = false; for( var i=coll.length-1; i>=0; i-- ){ if( coll[i].className.indexOf( 'hide-me' ) != -1 ){ hide = true; Easy.addClassName( coll[i], 'hidden' ); Easy.removeClassName( coll[i], 'hide-me' ); this.hidden.push( coll[i] ); } } // more to come } }; IN CONTROL 2009 126
    230. 230. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { ... initialize: function( form, i ){ // set the id this.id = i; // get the fieldsets var coll = form.getElementsByTagName( 'fieldset' ); // look for hiddens var hide = false; for( var i=coll.length-1; i>=0; i-- ){ if( coll[i].className.indexOf( 'hide-me' ) != -1 ){ hide = true; Easy.addClassName( coll[i], 'hidden' ); Easy.removeClassName( coll[i], 'hide-me' ); this.hidden.push( coll[i] ); } } // more to come } }; IN CONTROL 2009 126
    231. 231. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { ... initialize: function( form, i ){ // set the id this.id = i; // get the fieldsets var coll = form.getElementsByTagName( 'fieldset' ); // look for hiddens var hide = false; for( var i=coll.length-1; i>=0; i-- ){ if( coll[i].className.indexOf( 'hide-me' ) != -1 ){ hide = true; Easy.addClassName( coll[i], 'hidden' ); Easy.removeClassName( coll[i], 'hide-me' ); this.hidden.push( coll[i] ); } } // more to come } }; IN CONTROL 2009 126
    232. 232. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { ... initialize: function( form, i ){ // set the id this.id = i; // get the fieldsets var coll = form.getElementsByTagName( 'fieldset' ); // look for hiddens var hide = false; for( var i=coll.length-1; i>=0; i-- ){ if( coll[i].className.indexOf( 'hide-me' ) != -1 ){ hide = true; Easy.addClassName( coll[i], 'hidden' ); Easy.removeClassName( coll[i], 'hide-me' ); this.hidden.push( coll[i] ); } } // more to come } }; IN CONTROL 2009 126
    233. 233. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { ... initialize: function( form, i ){ ... // stop if no hiddens if( hide === false ) return; this.state = 'less'; // create & append the link to the first fieldset this.link = document.createElement( 'a' ); this.link.className = 'show-hide-link'; this.link.setAttribute( 'href', '#' ); Event.observe( this.link, 'click', this.toggle.bindAsEventListener( this ), false ); this.link.appendChild( this.linkText[0] ); coll[0].appendChild( this.link ); Easy.addClassName( form, 'collapsible' ); Easy.removeClassName( form, 'collapsing' ); } }; IN CONTROL 2009 127
    234. 234. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { ... initialize: function( form, i ){ ... // stop if no hiddens if( hide === false ) return; this.state = 'less'; // create & append the link to the first fieldset this.link = document.createElement( 'a' ); this.link.className = 'show-hide-link'; this.link.setAttribute( 'href', '#' ); Event.observe( this.link, 'click', this.toggle.bindAsEventListener( this ), false ); this.link.appendChild( this.linkText[0] ); coll[0].appendChild( this.link ); Easy.addClassName( form, 'collapsible' ); Easy.removeClassName( form, 'collapsing' ); } }; IN CONTROL 2009 127
    235. 235. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { ... initialize: function( form, i ){ ... // stop if no hiddens if( hide === false ) return; this.state = 'less'; // create & append the link to the first fieldset this.link = document.createElement( 'a' ); this.link.className = 'show-hide-link'; this.link.setAttribute( 'href', '#' ); Event.observe( this.link, 'click', this.toggle.bindAsEventListener( this ), false ); this.link.appendChild( this.linkText[0] ); coll[0].appendChild( this.link ); Easy.addClassName( form, 'collapsible' ); Easy.removeClassName( form, 'collapsing' ); } }; IN CONTROL 2009 127
    236. 236. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { ... initialize: function( form, i ){ ... // stop if no hiddens if( hide === false ) return; this.state = 'less'; // create & append the link to the first fieldset this.link = document.createElement( 'a' ); this.link.className = 'show-hide-link'; this.link.setAttribute( 'href', '#' ); Event.observe( this.link, 'click', this.toggle.bindAsEventListener( this ), false ); this.link.appendChild( this.linkText[0] ); coll[0].appendChild( this.link ); Easy.addClassName( form, 'collapsible' ); Easy.removeClassName( form, 'collapsing' ); } }; IN CONTROL 2009 127
    237. 237. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { initialize: function( form, i ){ ... }, toggle: function(){ if( this.state == 'less' ){ this.showMore(); } else { this.showLess(); } }, showMore: function(){ // code to come }, showLess: function(){ // code to come } }; IN CONTROL 2009 128
    238. 238. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { initialize: function( form, i ){ ... }, toggle: function(){ if( this.state == 'less' ){ this.showMore(); } else { this.showLess(); } }, showMore: function(){ // code to come }, showLess: function(){ // code to come } }; IN CONTROL 2009 128
    239. 239. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { ... showMore: function(){ for( var i=0; i<this.hidden.length; i++ ){ Easy.removeClassName( this.hidden[i], 'hidden' ); } this.link.replaceChild( this.linkText[1], this.link.childNodes[0] ); this.state = 'more'; }, showLess: function(){ for( var i=0; i<this.hidden.length; i++ ){ Easy.addClassName( this.hidden[i], 'hidden' ); } this.link.replaceChild( this.linkText[0], this.link.childNodes[0] ); this.state = 'less'; } }; IN CONTROL 2009 129
    240. 240. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { ... showMore: function(){ for( var i=0; i<this.hidden.length; i++ ){ Easy.removeClassName( this.hidden[i], 'hidden' ); } this.link.replaceChild( this.linkText[1], this.link.childNodes[0] ); this.state = 'more'; }, showLess: function(){ for( var i=0; i<this.hidden.length; i++ ){ Easy.addClassName( this.hidden[i], 'hidden' ); } this.link.replaceChild( this.linkText[0], this.link.childNodes[0] ); this.state = 'less'; } }; IN CONTROL 2009 129
    241. 241. FUNDAMENTAL JAVASCRIPT The code CollapsingForm.prototype = { ... showMore: function(){ for( var i=0; i<this.hidden.length; i++ ){ Easy.removeClassName( this.hidden[i], 'hidden' ); } this.link.replaceChild( this.linkText[1], this.link.childNodes[0] ); this.state = 'more'; }, showLess: function(){ for( var i=0; i<this.hidden.length; i++ ){ Easy.addClassName( this.hidden[i], 'hidden' ); } this.link.replaceChild( this.linkText[0], this.link.childNodes[0] ); this.state = 'less'; } }; IN CONTROL 2009 129
    242. 242. FUNDAMENTAL JAVASCRIPT Collapsing Form with JS IN CONTROL 2009 130
    243. 243. QUESTIONS?
    244. 244. WORKING WITH LIBRARIES
    245. 245. FUNDAMENTAL JAVASCRIPT Popular Libraries ๏ jQuery (jquery.com) ๏ Prototype (prototypejs.org) & Scriptaculous (script.aculo.us) ๏ YUI (developer.yahoo.com/yui) ๏ Dojo (dojotoolkit.org) ๏ Spry (labs.adobe.com/technologies/spry) ๏ MooTools (mootools.net) ๏ MochiKit (mochikit.com) IN CONTROL 2009 133
    246. 246. FUNDAMENTAL JAVASCRIPT Popular Libraries ๏ jQuery - fast & easy to write, selector-based ๏ Prototype & Scriptaculous - powerful, Ruby-like ๏ YUI - powerful, backed by Yahoo! ๏ Dojo - powerful, backed by IBM ๏ Spry - supported in Dreamweaver, backed by Adobe ๏ MochiKit - powerful, Python-like IN CONTROL 2009 134
    247. 247. FUNDAMENTAL JAVASCRIPT Popular Libraries ๏ jQuery - fast & easy to write, selector-based ๏ Prototype & Scriptaculous - powerful, Ruby-like ๏ YUI - powerful, backed by Yahoo! IN CONTROL 2009 134
    248. 248. FUNDAMENTAL JAVASCRIPT Getters 2.0 ๏ jQuery: ‣ $(selector) ‣ $(selector).attr(attribute) ๏ Prototype: ‣ $(id) or $$(selector) ‣ $$(selector).readAttribute(attribute) ๏ YUI: ‣ YAHOO.util.Dom.get(id) or YAHOO.util.Selector.query(selector) ‣ YAHOO.util.Dom.getAttribute(element, attribute) IN CONTROL 2009 135
    249. 249. FUNDAMENTAL JAVASCRIPT Setters 2.0 ๏ jQuery: ‣ $(x).text(text) or $(x).html(html) or $(x).append([el|text]) ‣ $(x).attr([attr, value|map]) ๏ Prototype: ‣ $(x).insert([text|element]) // after by default ‣ $(x).writeAttribute([attr, value|map]) ๏ YUI: ‣ YAHOO.util.Dom.insertAfter( [str|el], reference) ‣ YAHOO.util.Dom.addClass(el, class) IN CONTROL 2009 136
    250. 250. LET’S REVISIT OUR FIRST EXAMPLE
    1. A particular slide catching your eye?

      Clipping is a handy way to collect important slides you want to go back to later.

    ×