HTML5 datalist与动态邮箱地址(兼容IE)效果演示实例页面

回到相关文章 »

代码:

HTML代码:
邮箱:<input type="email" id="email" list="emailList" name="off_autocomplete" />
<datalist id="emailList">
    <option value="*@qq.com">
    <option value="*@163.com">
    <option value="*@gmail.com">
    <option value="*@yahoo.com.cn">
    <option value="*@126.com">
</datalist>
                
JS代码:
document.createElement("datalist");
                
var eleList = document.getElementById("emailList")
	, eleMail = document.getElementById("email");
	
if ("placeholder" in document.createElement("input")) {	
    // 得到类似["qq.com", "163.com", "gmail.com", ...]的数据
    var arrEmailList = [].slice.call(eleList.getElementsByTagName("option")).map(function(option) {
        return option.value.replace("*@", "");    
    }), htmlListInit = eleList.innerHTML;    
    
    eleMail.fnListReplace = function() {
        var arrValue = this.value.trim().split("@");
        // 修复FireFox浏览器下无限input问题
        // 如果值不完全匹配某option值,执行动态替换 
        if (arrValue.length !== 2 || arrEmailList.indexOf(arrValue[1]) === -1) {
            eleList.innerHTML = htmlListInit.replace(/\*/g, arrValue[0]);
        }        
        return this;
    };
    // 绑定输入事件侦听
    eleMail.addEventListener("input", function() {
        this.fnListReplace.call(this);        
    }, false);
    
    //  载入即匹配
    eleMail.fnListReplace.call(eleMail).focus();
} else {
    // IE6-9浏览器
    var option = eleList.getElementsByTagName("option"), eleSelect = null, indexOption = -1
    , arrEmailList = (function() {
        var arr = [], index = 0, length = option.length;
        for (; index < length; index+=1) {
            arr.push(option[index].value);
        }
        return arr;
    })();
        
    eleMail.parentNode.insertBefore(eleList, eleMail);
    
    eleMail.fnListReplace = function() {
        var htmlNewOption = '', value = this.value, arrValue = value.split("@"), lengthOption = 0;
        for (var index = 0; index<arrEmailList.length; index+=1) {
            if (arrValue.length !== 2 || 
            	arrValue[1] === "" || 
                arrEmailList[index].replace("*@", "").indexOf(arrValue[1]) === 0
            ) {
                htmlNewOption = htmlNewOption + 
                    '<option value="'+ arrEmailList[index] +'">'+
                    	arrEmailList[index] +
                '</option>';    
                lengthOption++;
            }
        }
        eleList.style.visibility = value && htmlNewOption? "visible": "hidden";
       eleList.innerHTML = (lengthOption == 1?
            '<select size="2" style="height:'+ (window.localStorage? "19": "24") +'px;">' :
            '<select size="'+ lengthOption +'">') +        
                htmlNewOption.replace(/\*/g, arrValue[0]) +
            '</select>';
        
        // 三个全局变量重置
        eleSelect = eleList.getElementsByTagName("select")[0];
        option = eleList.getElementsByTagName("option");
        indexOption = -1;
        
        // 宽度
        if (this.offsetWidth > eleSelect.offsetWidth) {
            eleSelect.style.width = this.offsetWidth;
        } else {
            eleSelect.style.width = '';    
        }
    };
    
    // 样式
    var style = {
        position: "absolute",
        marginTop: eleMail.offsetHeight,
        visibility: "hidden"
    }, key;        
    for (key in style) {
        eleList.style[key] = style[key];        
    }

    // 事件
    eleMail.attachEvent("onpropertychange", function() {
        if (e && e.propertyName == "value") {
            eleMail.fnListReplace.call(eleMail);
        }
    });
    // 键盘上下
    eleMail.attachEvent("onkeyup", function(e) {
        switch(e.keyCode) {
            case 38: {
                indexOption--;
                if (indexOption < 0) {
                    indexOption = -1 + option.length;
                }
                break;
            }
            case 40: {
                indexOption++;    
                if (indexOption >= option.length) {
                    indexOption = 0;
                }
                break;
            }
            case 13: {
                if (indexOption !== -1) {
                    eleMail.value = eleSelect.value;    
                }
                eleList.style.visibility = "hidden";
                break;
            }
        }        
        option[indexOption] && (option[indexOption].selected = "selected");
    });
    
    document.body.attachEvent("onmouseup", function(event) {
        if (!event) return;
        var target = event.srcElement || event.target;
        if (target && target != eleMail && target.parentNode != eleSelect) {
            eleList.style.visibility = "hidden";
        }
    });
    
    eleMail.fnListReplace.call(eleMail);    
    
    // 选中
    eleList.attachEvent("onclick", function() {
        eleMail.value = eleSelect.value;
        eleList.style.visibility = "hidden";
    });
}

效果:

邮箱: