SitePoint Sponsor

User Tag List

Results 1 to 9 of 9

Thread: Javascript FAQ

  1. #1
    SitePoint Wizard chris_fuel's Avatar
    Join Date
    May 2006
    Location
    Ventura, CA
    Posts
    2,750
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)

    Javascript FAQ

    Seeing some frequently asked questions I made this FAQ up:

    1) What is AJAX?

    AJAX stands for Asyncronous Javascript And XML. This is technology that was created to allow a browser to connect with a server side script and parse the contents, providing dynamic content based on it.

    2) When I view a page with an AJAX, my browser tells me it's denied, what do I do?

    In order to provide security to the user, AJAX calls must be made to the server that the user is accessing. For example, if the user is accessing www.domain.com/ajax.html:

    Code:
    req.open("GET","http://www.othersite.com/ajax.php");
    will produce a permission denied error on the user's browser. If you absolutely need to access content from another site, have the sever script act as a proxy and provide the data for you. A recommendation is to have a config.js file that contains the domain name of the server, making it easy to drag and drop into other servers:

    config.js:
    Code:
    var domain_location = 'www.mysite.com';
    ajax file:
    Code:
    req.open("GET","http://"+domain_location+"/ajax.php");
    also note that:

    Code:
    req.open("GET","http://subdomain.mysite.com/ajax.php");
    will NOT work. The ENTIRE domain must be the same.

    3) IE seems to be getting the same AJAX content over and over again!

    Unfortunately IE caches ajax calls if you make calls to the exact same page. A solution can be created through appending dynamic content at the end of your URL:

    Code:
    req.open("GET","http://www.mysite.com/ajax.php?variable=value&random=" Math.random());
    This will cause the page content to be re-fetched all the time.

    4) POST and GET with AJAX is the same right?

    Actually with GET, you use open() to pass in your variable string. With POST, you use send(). An example of GET:

    Code:
    req.open('GET', 'file.php?var1=1&var2=2', true);
    req.send(null);
    While with POST:

    Code:
    request.open('POST', 'file.php', true);
    request.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
    request.send('var1=1&var2=2');
    (Thanks to all people in http://www.sitepoint.com/forums/showthread.php?t=391052 )

    5) What's the deal with innerHTML and DOM functionality?

    innerHTML was introduced by IE as proprietary functionality. Browsers adopted it later on, and as far as I have tested, this works on IE, Konqueror, Safari, and Firefox's latest versions. However, the main argument is that innerHTML looks at the XML as a string, which it is not. The DOM functions look at XML as a structured document, as it is. However, for large ammounts of document creation, DOM functions can start to get very crowded, and are very slow compared to innerHTML. If you can though, I highly recommend using the DOM functions.

    6) My setAttribute('class', 'css_class') isn't working! Why not?!

    This is sort of awkward, but IE wants:

    Code:
    element.className = 'css_class';
    instead. A similiar nuance is also present with iframe borders:

    Code:
    element.frameBorder = '0';
    7) When I'm in a loop adding event handlers, the variable seem to have incorrect values during the event firing, what's going on?

    Alright, this is a problem with variable closure. Take this for example:

    Code:
    div_list = document.getElementsByTagName('div');
    for ( i = 0 ; i < div_list.length ; i++ )
    {
      div_list[i].onClick = function()
      {
         alert(i);
      }
    }
    Now let's say you have i = 30 at the end. No matter what div you click on, the answer will be 30. This is because the value of i is not finalized within the anonymous function. Instead, browsers will often globalize "i" at the end of the loop, hence why you get 30. In order to solve this, you can create a function which applies the event handler and argument. What this does is finalize the variable by the new scope introduced in calling the function:

    Code:
    div_list = document.getElementsByTagName('div');
    for ( i = 0 ; i < div_list.length ; i++ )
    {
      eventHandler(div,i);
    }
    
    function eventHandler(element, value)
    {
      element.onClick = function()
      {
         alert(value);
      }
    }
    8) When creating a table with the DOM model, it's not showing up in my browser!

    oddly enough, tables have a <tbody> tag. To fix this, simply create a tbody element, and append all tr's to that.

    9) Can I dynamically import css files?

    Yes, see the following code:

    Code:
    function cssAppend(css_file)
    {
      css_link = document.createElement('link');
      css_link.rel = "stylesheet";
      css_link.type = "text/css";
      css_link.href = css_file;
      document.getElementsByTagName('head')[0].appendChild(css_link);
    }
    I have confirmed this on Konqueror, IE, Firefox, and Safari.

    10) Javascript seems to have a lot of XML related functionality. Can I operate on standard XML files as well?

    Yes you can:

    Code:
    var xmlDoc;
    
    if (window.ActiveXObject) //this portion is meant for I.E.
    {
    	xmlDoc = new ActiveXObject("Microsoft.XMLDOM")
     }
    else if (document.implementation && document.implementation.createDocument) //for firefox
    {
    	xmlDoc = document.implementation.createDocument("", "doc", null);
    }
    
    xmlDoc.async=false;
    xmlDoc.load('file.xml');
    You can now parse the xml file as though it was the html document (ie. getElementById, etc.)

    (note: this was gratefully taken from http://www.sitepoint.com/forums/showthread.php?t=383562 created by inter4design)

    11) Is there inheritence in javascript classes?

    Yes, for example:

    Code:
    function Duck()
    {
      // Duck properties and methods
    }
    
    function PlasticDuck()
    {
      Duck.call(this);
      // impl. of PlastickDuck
    }
    
    // Do this before adding other methods with prototype, otherwise 
    // they will be overwritten
    PlasticDuck.prototype = new Duck();
    
    PlasticDuck.prototype.squeak= function()
    {
      // 
    }
    (thanks to Pepejeria for the updated inheritance code)

    12) Can I pass variables through uri's like I can in PHP?

    Yes, you simply need to do a bit of a string operation on document.location.href:

    Code:
    function parse_uri_args()
    {
       if ( document.location.href.indexOf('?') == -1 )
       {
           return false;
       }
       else
       {
            if (document.location.href.indexOf('&') != -1)
            {
                 var arguments_list = document.location.href.split('?')[1].split('&');
                 var arguments = new Array();
                 for ( i = 0 ; i < arguments_list.length ; i++ )
                 {
                      key = arguments_list[i].split('=')[0];
                      value = arguments_list[i].split('=')[1];
                      arguments[key] = value;
                 }
                 return arguments;
            }
            else
            {
                 arguments = new Array();
                 var arguments_list = document.location.href.split('?')[1];
                 key = arguments_list.split('=')[0];
                 value = arguments_list.split('=')[1];
                 arguments[key] = value;
                 return arguments;
            }
       }
    }
    Which given http://www.test.com/test.php?foo=bar&zoo=lion as the current url:

    Code:
    var uri_array = parse_uri_args();
    alert(uri_array['zoo']);
    will produce 'lion';

    13) IE's javascript errors are useless! Is there something better?

    Microsoft actually has a javascript debugger, you can find out more here:

    http://blogs.msdn.com/ie/archive/2004/10/26/247912.aspx

    14) Why doesn't extending builtin objects work in IE?

    Quote Originally Posted by mrhoo
    IE doesn't iterate the 'native object code' the way firefox does.
    Your code would work for an object you created, but not the 'built in' objects.
    You have to enable each prototype property explicitly.
    (http://www.sitepoint.com/forums/showthread.php?t=397581)

    Code:
    function ExtArray() {
    this.push=Array.prototype.push;
    this.length=Array.prototype.length;
    }
     
      var sources = new ExtArray();
      sources.push('First'); 
      sources.push('Second');
      alert(sources.length + ': [' + sources[0] + ',' + sources[1] + ']');
    Is an example of extending push/length members of the builtin Array object.

    Well, that's it for now, I'll try and add more later when I get the chance.

  2. #2
    SitePoint Wizard chris_fuel's Avatar
    Join Date
    May 2006
    Location
    Ventura, CA
    Posts
    2,750
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Added a new section on parsing the curent url's uri string to scrape variables.

  3. #3
    SitePoint Wizard Pepejeria's Avatar
    Join Date
    Jan 2005
    Location
    Too far up north
    Posts
    1,566
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Usually people ask questions on forums, so its kind of interesting that u post answers

    Quote Originally Posted by chris_fuel
    7) When creating a table with the DOM model, it's not showing up in my browser!
    Only an issue with IE (that is generally broken)

    Quote Originally Posted by chris_fuel
    10) Is there inheritence in javascript classes?

    Yes, for example:

    Code:
    function ClassA()
    {
      this.test = "foobar";
      this.test2 = "barfoo";
    }
    
    function ClassB()
    {
      this.superclass = ClassA;
      this.superclass();
      delete this.superclass();
    }
    this.test and this.test2 will now be avaliable to class B. This includes functions as well.
    For real inheritance:
    Code:
    function Duck()
    {
      // Duck properties and methods
    }
    
    function PlasticDuck()
    {
      Duck.call(this);
      // impl. of PlastickDuck
    }
    
    // Do this before adding other methods with prototype, otherwise 
    // they will be overwritten
    PlasticDuck.prototype = new Duck();
    
    PlasticDuck.prototype.squeak= function()
    {
      // 
    }

  4. #4
    SitePoint Member
    Join Date
    Jun 2006
    Posts
    13
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    When I first time created a table with DOM's createElement, also have experienced the "missing of tbody" problem, but at inspecting with the briliant DOM Inspector of the FF a working table, it show me what a table must have a tbody..

    Very interesting solution nr. 6, this is beyond my understand.. JS is even more powerful than i thought.
    Is there more information about this behavior of JS ? When and why it act like this.. Maybe in ECMA docs, somewhere ?

    THis topic should be sticky !
    I think in this topic are presented multiple items from top10 of most usually problems of every js&dom beginner..

  5. #5
    SitePoint Wizard chris_fuel's Avatar
    Join Date
    May 2006
    Location
    Ventura, CA
    Posts
    2,750
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Updated with new inheritence code.

    Only an issue with IE (that is generally broken)
    actually konqueror and safari fail at this too.

  6. #6
    SitePoint Wizard chris_fuel's Avatar
    Join Date
    May 2006
    Location
    Ventura, CA
    Posts
    2,750
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Very interesting solution nr. 6, this is beyond my understand.. JS is even more powerful than i thought.
    Is there more information about this behavior of JS ? When and why it act like this.. Maybe in ECMA docs, somewhere ?
    Ok, I think I have the particular relevant section on that:

    10.2.3 Function Code
    The scope chain is initialised to contain the activation object followed by the objects in the scope
    chain stored in the [[Scope]] property of the Function object.
    (Source: http://www.ecma-international.org/pu...t/ECMA-262.pdf)

    So it seems that the Scope property exists within a function to hold the variables for that function scope. That said, it looks like there is no block level scope like other languages have, it's just in the funciton. This would well expalin the issue in my opinion. The way my workaround operates is that it gives the variable's current value to another function, causing it to be encapsulated in the Scope property of the other function.

  7. #7
    SitePoint Wizard chris_fuel's Avatar
    Join Date
    May 2006
    Location
    Ventura, CA
    Posts
    2,750
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    1) Added in GET/POST logic advice from http://www.sitepoint.com/forums/showthread.php?t=391052

    2) Added in note on where to get IE script debugger

  8. #8
    SitePoint Wizard chris_fuel's Avatar
    Join Date
    May 2006
    Location
    Ventura, CA
    Posts
    2,750
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Added note from http://www.sitepoint.com/forums/showthread.php?t=397581 on extending builtin objects with ie.

    refactoring soon to come

  9. #9
    SitePoint Evangelist
    Join Date
    Jul 2007
    Posts
    345
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Number 7. You have
    Code:
    div_list = document.getElementsByTagName('div');
    for ( i = 0 ; i < div_list.length ; i++ )
    {
      eventHandler(div,i);
    }
    
    function eventHandler(element, value)
    {
      element.onClick = function()
      {
         alert(value);
      }
    }
    Maybe
    Code:
    div_list = document.getElementsByTagName('div');
    for ( i = 0, l = div_list.length; i < l; i++ )
    {
      eventHandler(div_list[i], i);
    }
    
    function eventHandler(element, value)
    {
      element.onclick = function()
      {
         alert(value);
      }
    }
    or even
    Code:
    div_list = document.getElementsByTagName('div');
    for (i = 0, l = div_list.length; i < l; i++  )
    {
      (function(i)
      {
         div_list[i].onclick = function()
         {
            alert(i);
         };
      })(i);
    }


Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •