在使用optgroup时遇到的缺陷与修复

简介:
在IE6.0里微软提供对 HTML4.0中定义元素optgroup的支持,不过当我今天使用optgroup时,居然发现其在事件处理上存在bug。该bug影响select元素上的onchange事件,具体表现及处理如下。

    我们看一下这个带有optgroup的select事例: 
   

    HTML代码及演示脚本如下:
< html >
< head >
     < title >optgroup demo </ title >
     < meta  name ="author"  content ="birdshome@cnblogs"   />
</ head >
< body >
     < select  size ="11"  style ="width: 150px" >
         < optgroup  label ="Group01" >
             < option >Option01 Item </ option >
         </ optgroup >
         < optgroup  label ="Group02" >
             < option >Option02 Item </ option >
         </ optgroup >
         < optgroup  label ="Group03" >
             < option >Option03 Item </ option >
             < option >Option04 Item </ option >
         </ optgroup >
         < optgroup  label ="Group04" >
             < option >Option05 Item </ option >
             < option >Option06 Item </ option >
             < option >Option07 Item </ option >
         </ optgroup >
     </ select >
     < script  language ="javascript" > </ script >
</ body >
</ html >

    本演示示例的意图是当select上的选中的条目一旦改变,就执行 一次doChange()方法。你可以点击列表框中的条目并注意一下状态栏,是不是每一次点击都会使数字加一?这是我们希望的效果,同时也说明onchange事件响应是正确的。这时如果你换用键盘上下键来移动列表框中的条目,继续注意状态栏,您会发现什么?状态栏数字的变化没有规律了 ,说明doChange()方法不总是在随条目状态改变而执行。仔细观察,会发现如果使用鼠标使在 Group0n这样的条目上下移动时,select元素的onchange事件不会促发。不过此时select元素的selectedIndex属性指示状态是正确的,真是一个烦人的bug

    怎样修复这个缺陷呢?如果我们使用了optgroup这个元素,为了确保onchange事件不被遗漏,我们同时响应select元素的键盘事件就可以了。为了能监测selectedIndex的改变,我们需要使用select的onkeyup事件(因为这个事件在onchange之后触发),可是如果我们简单的同时注册这两个事件,似乎还是有问题的说。看下面的例子,我们把onkeyup也等于了doChange()方法。
     

    使用键盘操作条目,会在原来正常的地方出问题,就是doChange()方法会被触发两次。上面我们不是说了为什么一定要使用onkeyup监视键盘吗?就是因为onkeyup事件在onchange事件之后执行,所以我们可以利用这个事件触发顺序,自己来检测onchange事件是否已执行。效果如下:
   
 
    
    修复bug的脚本代码为:
< script  language ="javascript" >
var  g_count  =   0 ;
slt.onchange 
=  doChange;
slt.onkeyup 
=  doKeyup;

function  doChange(elmt)
{
    elmt.__selectedIndex 
=  elmt.selectedIndex;
    
    status 
=  g_count ++ ;
}


function  doKeyup(elmt)
{
    
if  ( elmt.__selectedIndex  !=  elmt.selectedIndex )
    
{
        doChange(elmt);
    }

}

</ script >

本文转自博客园鸟食轩的博客,原文链接:http://www.cnblogs.com/birdshome/,如需转载请自行联系原博主。

目录
相关文章
|
存储 自然语言处理 编译器
C陷阱与缺陷
C陷阱与缺陷
84 0
C陷阱与缺陷
|
24天前
|
测试技术
更正以前风险调整中的一个缺陷
以前在我写的书《软件测试技术实战——设计、工具及管理》中提及一个关于风险调整的策略是完全错误的,现在更正如下
70 40
|
8月前
|
供应链 测试技术
修复糟糕的代码气味
修复糟糕的代码气味
73 11
|
9月前
|
设计模式 测试技术
什么是缺陷预防和缺陷改进?
什么是缺陷预防和缺陷改进?
273 0
|
程序员
缺陷(bug)管理
理论上软件的缺陷是可修复的,不过有的修复成本比较高,不能追求软件的完美,根据风险来确定是否修复缺陷
|
消息中间件 NoSQL Redis
修复过的一个bug
高并发的功能调用云产品时走过的路
174 0
|
移动开发 JavaScript 前端开发
|
存储 容器 程序员