label for object

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • David McDivitt

    label for object

    We have a massive java application to be made ADA compliant. We want onfocus
    and onblur events for each text field. The best way seems to be javascript,
    by cycling through all the nodes recursively after page load, and attaching
    the events. We already cycle through everything to set tabs. If nodename is
    LABEL, we should be able to use the FOR attribute, get the object
    referenced, and attach events on that object.

    When cycling through nodes, if I get to a label I can print the attribute
    collection, and there is a FOR having the correct value for the associated
    text object. I can't get any further than that.

    This is a piece of code:

    if (child.nodeName =='LABEL') {
    //var sss = ''+child.attrib utes.length+"\n ";
    //for (var k=0;k<child.att ributes.length; k++) sss +=
    ''+child.attrib utes[k].nodeName+'='+c hild.attributes[k].nodeValue+"\n" ;
    //alert(sss);
    try {
    var cont = child.attribute s.getNamedItem( "for");
    alert(''+cont.n odeName);
    cont.attacheven t('onfocus',ale rt("xxx"));
    cont.attacheven t('onblur',aler t("zzz"));
    }
    catch (e) {
    }
    }

    Maybe by reading the code you can see what I'm trying to do. When it
    executes "alert(''+cont. nodeName);", it displays "for". I need to display
    "textarea" because that's what the label is associated with. If anyone can
    help I'd appreciate it.

  • VK

    #2
    Re: label for object

    cont.nodeValue will give you the object ID (but *not* the reference).
    So you need to:

    var cont = child.attribute s.getNamedItem( ­"for");
    var obj = document.getEle mentById(cont.n odeValue);
    // attachEvent, not attachevent - case makes difference:
    obj.attachEvent ('onfocus',ale­ rt("xxx"));
    obj.attachEvent ('onblur',aler­ t("zzz"));

    I predict a big mess though because label and textbox are sharing the
    same event stream (thus clicking on label will trig 'onclick' for
    associated textbox either).
    So it's going to be a bunch of dublicate events you'll have to kill
    with returnValue=nul l;

    Comment

    • VK

      #3
      Re: label for object

      > kill with returnValue=nul l;

      returnValue=fal se;

      or by checking event.srcElemen t.tagName ("LABEL" or "INPUT") every time.

      Comment

      • Yep

        #4
        Re: label for object

        David McDivitt wrote:

        Hi,
        [color=blue]
        > We have a massive java application to be made ADA compliant. We want onfocus
        > and onblur events for each text field. The best way seems to be javascript,
        > by cycling through all the nodes recursively after page load, and attaching
        > the events. We already cycle through everything to set tabs. If nodename is
        > LABEL, we should be able to use the FOR attribute, get the object
        > referenced, and attach events on that object.[/color]


        <style type="text/css">
        label input[type=text] {background-color:#ccc;}
        </style>

        <form>
        <label for="foo1"><inp ut type="text" id="foo1"></label>
        <label for="foo2"><inp ut type="text" id="foo2"></label>
        <label for="foo3"><inp ut type="text" id="foo3"></label>
        </form>

        <script type="text/javascript">
        var Utils = {

        //getElementsWith TagName
        getElementsWith TagName : function(root, tag) {
        var d=document, func, fail=null;
        if(d.all) {
        func = function(root, tag) {
        return root && tag &&
        (tag=="*" ? root.all : root.all.tags(t ag)) || fail;
        }
        } else if(d.getElement sByTagName) {
        func = function(root, tag) {
        return root && tag && root.getElement sByTagName(tag) || fail;
        }
        } else {
        func = function(){retu rn fail;}
        }
        return (Utils.getEleme ntsWithTagName = func)(root, tag);
        },

        //getElementWithI d
        getElementWithI d : function(id) {
        var d=document, func, fail=null;
        if(d.getElement ById) {
        func = function(id) {return d.getElementByI d(id);}
        } else if(d.all) {
        func = function(id) {return d.all[id]; }
        } else {
        func = function() {return fail;}
        }
        return (Utils.getEleme ntWithId = func)(id);
        },

        //addEventListene r
        addEventListene r : function(obj, evt, handler) {
        var d=document, func;
        if(d.addEventLi stener) {
        func = function(obj, evt, handler) {
        evt=evt.replace (/^on/i,"").toLowerCa se();
        obj.addEventLis tener(evt, handler, false);
        }
        } else {
        func = function(obj, evt, handler) {
        evt="on"+evt.re place(/^on/i,"").toLowerCa se();
        obj[evt]=handler;
        }
        }
        return (Utils.addEvent Listener = func)(obj, evt, handler);
        }
        };

        function initLabels() {
        var labels=Utils.ge tElementsWithTa gName(document. body, "label");
        if(labels){
        for(var ii=labels.lengt h; ii--;) {
        var target=Utils.ge tElementWithId( labels[ii].htmlFor);
        if(target && target.type.toL owerCase()=="te xt") {
        Utils.addEventL istener(target, "onfocus", focusHandler);
        Utils.addEventL istener(target, "onblur", blurHandler);
        }
        }
        }
        function focusHandler(){ this.style.back groundColor="ye llow";}
        function blurHandler(){t his.style.backg roundColor="";}
        }

        Utils.addEventL istener(window, "onload", initLabels);
        </script>


        HTH,
        Yep.

        Comment

        • YD

          #5
          Re: label for object

          David McDivitt a écrit :[color=blue]
          > We have a massive java application to be made ADA compliant. We want onfocus
          > and onblur events for each text field. The best way seems to be javascript,
          > by cycling through all the nodes recursively after page load, and attaching
          > the events. We already cycle through everything to set tabs. If nodename is
          > LABEL, we should be able to use the FOR attribute, get the object
          > referenced, and attach events on that object.[/color]

          If you cycle through everything, why don't you attach events on the node named
          'TEXTAREA'?
          [color=blue]
          > var cont = child.attribute s.getNamedItem( "for");[/color]

          then cont is the attribute 'FOR' of the element you call child.
          To achieve what you want, try:

          var cont=document.g etElementById(c hild.attributes .getNamedItem(" for").nodeValue );

          as the value of the FOR element is the id of the form element it refers.

          HTH

          --
          Y.D.

          Comment

          • David McDivitt

            #6
            Re: label for object

            >From: "VK" <schools_ring@y ahoo.com>[color=blue]
            >Subject: Re: label for object
            >Date: 8 Jun 2005 13:45:44 -0700
            >
            >cont.nodeVal ue will give you the object ID (but *not* the reference).
            >So you need to:
            >
            >var cont = child.attribute s.getNamedItem( ­"for");
            >var obj = document.getEle mentById(cont.n odeValue);
            >// attachEvent, not attachevent - case makes difference:
            >obj.attachEven t('onfocus',ale ­rt("xxx"));
            >obj.attachEven t('onblur',aler ­t("zzz"));
            >
            >I predict a big mess though because label and textbox are sharing the
            >same event stream (thus clicking on label will trig 'onclick' for
            >associated textbox either).
            >So it's going to be a bunch of dublicate events you'll have to kill
            >with returnValue=nul l;[/color]

            Thanks VK. YD helped, too.

            What I have now is:

            if (child.nodeName =='LABEL') {
            try {
            var cont = child.attribute s.getNamedItem( "for");
            var obj = document.getEle mentById(cont.n odeValue);
            alert(''+obj.no deName); //says INPUT or TEXTAREA, good
            obj.attachEvent ("onfocus",aler t("xxx"));
            obj.attachEvent ("onblur",alert ("zzz"));
            }
            catch (e) {
            }
            }

            What should be the onfocus event executes while the javascript is running,
            so I get several xxx alert boxes. Clicking on the textarea does not generate
            an onfocus. In reading documentation for attachEvent, I don't know if syntax
            allows arguments.

            When finished it will be something like:

            if (child.nodeName =='LABEL') {
            try {
            var cont = child.attribute s.getNamedItem( "for");
            var obj = document.getEle mentById(cont.n odeValue);
            obj.attachEvent ("onfocus",wind ow.status=<labe l text>);
            obj.attachEvent ("onblur",windo w.status='');
            }
            catch (e) {
            }
            }

            Doing this will save endless man hours. All we have to do is put label tags
            on all the pages. We are using the struts framework. The id of text, input,
            textarea, etc., is set with the styleId attribute in the <HTML:WHATEVE R
            struts tag, and that matches FOR in the label tag.

            Comment

            • Yann-Erwan Perio

              #7
              Re: label for object

              David McDivitt wrote:

              Hi,
              [color=blue]
              > obj.attachEvent ("onfocus",aler t("xxx"));[/color]

              obj.attachEvent ("onfocus", functionRef);

              The second argument should be a function reference, like

              function funcRef(){windo w.status=""}


              FYI, your using try/catch and attachEvent limits your application to IE
              on intranets, which may or not be fine to you.


              HTH,
              Yep.

              Comment

              • VK

                #8
                Re: label for object

                attachEvent() supports anonymous function call:
                obj.attachEvent ('onfocus', function(args){ body;});

                *But* it will lead to the circular reference memory leak in IE:
                <http://support.microso ft.com/default.aspx?sc id=kb;en-us;830555>
                (say thank you to Martin Honner, Matt Kruz and Co who pulled out this
                not so well known bug).

                On your scale (> "We have a massive java application") this leak may
                eventually crash the system.

                The only way to secure your memory on IE is to use pure function
                references. Also if you guarantee that you need one function call per
                event and this call is static (will not be altered/canceled later), you
                are free to use universal property set instead of attachEvent:
                obj.onfocus = f1;
                obj.onblur = f2;

                The trick is to store the LABEL object reference in the INPUT object.
                This solves all your problem:

                <html>
                <head>
                <title>Untitl ed Document</title>
                <meta http-equiv="Content-Type" content="text/html;
                charset=iso-8859-1">
                <script>
                <!-- BHW: ADA also requires to not lock users to a partucular platform
                and software.
                So could we be a bit more cross-browser friendly? ;-) Like this
                code. -->
                function init() {
                var arr = document.getEle mentsByTagName( 'LABEL');
                var len = arr.length;
                var txt = null;
                for (i=0; i<len; i++) {
                txt = document.getEle mentById((arr[i].htmlFor));
                txt.thisLabel = arr[i];
                txt.onfocus = f1;
                txt.onblur = f2;
                }
                }
                function f1(e) {
                var obj = (e)? e.target.thisLa bel : event.srcElemen t.thisLabel;
                obj.style.color ='red';
                }
                function f2(e) {
                var obj = (e)? e.target.thisLa bel : event.srcElemen t.thisLabel;
                obj.style.color ='black';
                }
                window.onload = init;
                </script>
                </head>

                <body bgcolor="#FFFFF F">
                <form>
                <label id="oLbl" for="oTxt1" accesskey="1">L abel <u>1</u>:</label>
                <input type="text" id="oTxt1">
                <label id="oLb2" for="oTxt2" accesskey="2">L abel <u>2</u>:</label>
                <input type="text" id="oTxt2">
                </form>
                </body>
                </html>

                The posted code is the most resource/time wise. But if you need to
                iterate through the DOM nodes anyway for other reasons, then just keep
                your approach.

                Comment

                • David McDivitt

                  #9
                  Re: label for object

                  >From: "VK" <schools_ring@y ahoo.com>[color=blue]
                  >Subject: Re: label for object
                  >Date: 9 Jun 2005 02:14:05 -0700
                  >
                  >attachEvent( ) supports anonymous function call:
                  >obj.attachEven t('onfocus', function(args){ body;});
                  >
                  >*But* it will lead to the circular reference memory leak in IE:
                  ><http://support.microso ft.com/default.aspx?sc id=kb;en-us;830555>
                  >(say thank you to Martin Honner, Matt Kruz and Co who pulled out this
                  >not so well known bug).
                  >
                  >On your scale (> "We have a massive java application") this leak may
                  >eventually crash the system.
                  >
                  >The only way to secure your memory on IE is to use pure function
                  >references. Also if you guarantee that you need one function call per
                  >event and this call is static (will not be altered/canceled later), you
                  >are free to use universal property set instead of attachEvent:
                  >obj.onfocus = f1;
                  >obj.onblur = f2;
                  >
                  >The trick is to store the LABEL object reference in the INPUT object.
                  >This solves all your problem:
                  >
                  ><html>
                  ><head>
                  ><title>Untitle d Document</title>
                  ><meta http-equiv="Content-Type" content="text/html;
                  >charset=iso-8859-1">
                  ><script>
                  ><!-- BHW: ADA also requires to not lock users to a partucular platform
                  >and software.
                  > So could we be a bit more cross-browser friendly? ;-) Like this
                  >code. -->
                  >function init() {
                  > var arr = document.getEle mentsByTagName( 'LABEL');
                  > var len = arr.length;
                  > var txt = null;
                  > for (i=0; i<len; i++) {
                  > txt = document.getEle mentById((arr[i].htmlFor));
                  > txt.thisLabel = arr[i];
                  > txt.onfocus = f1;
                  > txt.onblur = f2;
                  > }
                  >}
                  >function f1(e) {
                  > var obj = (e)? e.target.thisLa bel : event.srcElemen t.thisLabel;
                  > obj.style.color ='red';
                  >}
                  >function f2(e) {
                  > var obj = (e)? e.target.thisLa bel : event.srcElemen t.thisLabel;
                  > obj.style.color ='black';
                  >}
                  >window.onloa d = init;
                  ></script>
                  ></head>
                  >
                  ><body bgcolor="#FFFFF F">
                  ><form>
                  > <label id="oLbl" for="oTxt1" accesskey="1">L abel <u>1</u>:</label>
                  > <input type="text" id="oTxt1">
                  > <label id="oLb2" for="oTxt2" accesskey="2">L abel <u>2</u>:</label>
                  > <input type="text" id="oTxt2">
                  > </form>
                  ></body>
                  ></html>
                  >
                  >The posted code is the most resource/time wise. But if you need to
                  >iterate through the DOM nodes anyway for other reasons, then just keep
                  >your approach.[/color]

                  Thanks VK! You made my day. I adapted my code and it works perfect.

                  Comment

                  Working...