一个仿微博登陆邮箱提示框js开发案例


Posted in Javascript onJuly 28, 2016

最近在好好的研究JS,通过一个仿邮箱登录提示框的案例加深下对面向对象的理解!啥都别说,先上图:

一个仿微博登陆邮箱提示框js开发案例

功能:实现正则匹配显示相符的内容、键盘事件、鼠标事件

简单布局:

<div id="login">
  <h2>仿微博登录</h2>
  <div class="detail">
    <input type="text" placeholder='邮箱/会员账号/手机号' autocomplete='off' class='name' id='nameInput' maxlength='18'>
  </div>
  <div class="detail">
    <input type="password" placeholder='请输入密码' autocomplete='off' class='password'>
  </div>
  <ul id='suggest'>
    <li class="note">请选择邮箱类型:</li>
    <li class="item" email=""></li>
    <li class="item" email="@sina.com">@sina.com</li>
    <li class="item" email="@163.com">@163.com</li>
    <li class="item" email="@qq.com">@qq.com</li>
    <li class="item" email="@126.com">@126.com</li>
    <li class="item" email="@sina.cn">@sina.cn</li>
    <li class="item" email="@139.com">@139.com</li>
  </ul>
</div>

CSS代码:

body,ul,li,h2{margin:0;padding:0;color:#ccc;}
ul{list-style-type: none;}
#login{width:250px;background:#fff;border:1px solid #ccc;text-align: center;margin:10px auto;position:relative;}
#login h2{background:#FA7D3C;color:#fff;line-height:40px; }
.detail{}
.detail input{width:220px;height:30px;margin:10px auto;border:1px solid #ccc;padding-left:5px;}
#suggest{width:225px;height:auto;background:#fff;border:1px solid #ccc;position:absolute;top:84px;left:12px;display: none;}
#suggest li{width:225px;height:25px;line-height:25px;text-align: left;cursor: pointer;}
#suggest li.note{color:#989090;}
#suggest li.active{background:#eee;}

JS代码:

window.onload=function(){
  var s1=new Suggest();
  s1.init();
};
function Suggest(){
  this.oInput=document.getElementById('nameInput');
  this.oUl=document.getElementById('suggest');
  this.aLi=this.oUl.getElementsByTagName('li');
}
Suggest.prototype={
  init:function(){
    this.toChange();
    this.toBlur();
  },
  toChange:function(){
    //ie:onpropertychange
    //标准:oninput
    /*判断IE浏览器最短方法:var isIE = !-[1,]*/
    var ie=!-[1,];
    //存this指向,this指向问题
    var This=this;
    if(ie){
      this.oInput.onpropertychange=function(){
        if(This.oInput.value==''){
          This.tips();//?解决ie下空值时li新增内容不置空情况
          return;
        }

        This.showUl();
        This.tips();
        This.sel(1);//选中第一条
      };
    }else{
      this.oInput.oninput=function(){
        This.showUl();
        This.tips();
        This.sel(1);//选中第一条
      }
    }
  },
  showUl:function(){
    this.oUl.style.display='block';
  },
  toBlur:function(){
    var This=this;
    this.oInput.onblur=function(){
      This.oUl.style.display='none';
    }
  },
  tips:function(){

    var value=this.oInput.value;
    //正则匹配
    var re=new RegExp('@'+value.substring(value.indexOf('@')+1)+'');
    // console.log(re);
    //bug修复:全部内容一次性清空仍可出现提示
    for(var i=1;i<this.aLi.length;i++){
      this.aLi[i].style.display='block';
    }
    if(re.test(value)){//匹配@输入后情况
      for(var i=1;i<this.aLi.length;i++){
        var oEmail=this.aLi[i].getAttribute('email');
        if(i==1){
          this.aLi[i].innerHTML=value;
        }else{

          if(re.test(oEmail)){//匹配项显示,否则隐藏
            this.aLi[i].style.display='block';
          }else{
            this.aLi[i].style.display='none';
          }
        }
      }
    }else{//未输入@之前
      for(var i=1;i<this.aLi.length;i++){
        var oEmail=this.aLi[i].getAttribute('email');
        if(!oEmail){
          this.aLi[i].innerHTML=value;
        }else{
          this.aLi[i].innerHTML=value+oEmail;
        }
      }
    }

  },
  sel:function(iNow){//传入当前索引

    var This=this;
    //每次改变重新设置类型,不会重复
    for(var i=1;i<this.aLi.length;i++){
      this.aLi[i].className='item';
    }

    if(this.oInput.value==''){
      this.aLi[iNow].className='item';
    }else{
      this.aLi[iNow].className='active';
    }

    for(var i=1;i<this.aLi.length;i++){
      this.aLi[i].index=i;
      this.aLi[i].onmouseover=function(){
        for(var i=1;i<This.aLi.length;i++){
          This.aLi[i].className='item';
        }
        this.className='active';
        iNow=this.index;//当前索引
      };
      //鼠标点击事件:
      this.aLi[i].onmousedown=function(){
        This.oInput.value=this.innerHTML;
      }
    }
    //键盘事件:
    this.oInput.onkeydown=function(e){
      var e=e||window.event;
      if(e.keyCode==38){//上

        if(iNow==1){
          iNow=This.aLi.length-1;
        }else{
          iNow--;
        }
        for(var i=1;i<This.aLi.length;i++){
          This.aLi[i].className='item';
        }
        This.aLi[iNow].className='active';

      }else if(e.keyCode==40){//下

        if(iNow==This.aLi.length-1){
          iNow=1;
        }else{
          iNow++;
        }
        for(var i=1;i<This.aLi.length;i++){
          This.aLi[i].className='item';
        }
        This.aLi[iNow].className='active';

      }else if(e.keyCode==13){//回车
        This.oInput.value=This.aLi[iNow].innerHTML;
        This.oInput.blur();//回车后触发blur事件隐藏ul层
      }
    }
  }

}

需要处理好多个分支情况,处理好小细节,也感觉面向对象中比较常遇到是this指向的问题,通过这个案例好好地理解了下this。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
传智播客学习之JavaScript基础篇
Nov 13 Javascript
js下写一个事件队列操作函数
Jul 19 Javascript
jQuery EasyUI API 中文文档 - Menu菜单
Oct 03 Javascript
使用AngularJS实现表单向导的方法
Jun 19 Javascript
再谈Javascript中的异步以及如何异步
Aug 19 Javascript
浅谈jQuery的bind和unbind事件(绑定和解绑事件)
Mar 02 Javascript
Node.js中的require.resolve方法使用简介
Apr 23 Javascript
Angular2使用Angular-CLI快速搭建工程(二)
May 21 Javascript
Vue自定义toast组件的实例代码
Aug 15 Javascript
详解puppeteer使用代理
Dec 27 Javascript
使用ESLint禁止项目导入特定模块的方法步骤
Mar 04 Javascript
在nuxt中使用路由重定向的实例
Nov 06 Javascript
利用JS实现数字增长
Jul 28 #Javascript
灵活使用数组制作图片切换js实现
Jul 28 #Javascript
AngularJS 中文API参考手册
Jul 28 #Javascript
AngularJS 简单应用实例
Jul 28 #Javascript
AngularJS 路由详解和简单实例
Jul 28 #Javascript
AngularJS 依赖注入详解和简单实例
Jul 28 #Javascript
AngularJS中实现动画效果的方法
Jul 28 #Javascript
You might like
实用函数2
2007/11/08 PHP
一些php项目中比较通用的php自建函数的详解
2013/06/06 PHP
关于zend studio 出现乱码问题的总结
2013/06/23 PHP
PHP使用Mysql事务实例解析
2014/09/08 PHP
thinkphp3.2中Lite文件替换框架入口文件或应用入口文件的方法
2015/05/21 PHP
隐藏Nginx或Apache以及PHP的版本号的方法
2016/01/03 PHP
全面解析JavaScript中的valueOf与toString方法(推荐)
2016/06/14 Javascript
JS中innerHTML和pasteHTML的区别实例分析
2016/06/22 Javascript
给easyui datebox扩展一个清空的实例
2016/11/09 Javascript
NPM 安装cordova时警告:npm WARN deprecated minimatch@2.0.10: Please update to minimatch 3.0.2 or higher to
2016/12/20 Javascript
js实现hashtable的赋值、取值、遍历操作实例详解
2016/12/25 Javascript
浅析vue中常见循环遍历指令的使用 v-for
2018/04/18 Javascript
vue兄弟组件传递数据的实例
2018/09/06 Javascript
微信小程序实现蒙版弹出窗功能
2019/09/17 Javascript
JS实现“全选”和&quot;全不选&quot;功能代码实例
2020/02/06 Javascript
jquery实现简易验证插件封装
2020/09/13 jQuery
vue 使用饿了么UI仿写teambition的筛选功能
2021/03/01 Vue.js
[56:00]2018DOTA2亚洲邀请赛 4.6 淘汰赛 VP vs TNC 第二场
2018/04/10 DOTA
[06:07]DOTA2-DPC中国联赛3月5日Recap集锦
2021/03/11 DOTA
Python 元组(Tuple)操作详解
2014/03/11 Python
Python入门篇之面向对象
2014/10/20 Python
关于python的list相关知识(推荐)
2017/08/30 Python
python实现知乎高颜值图片爬取
2019/08/12 Python
Django--权限Permissions的例子
2019/08/28 Python
python PIL模块的基本使用
2020/09/29 Python
Manjaro、pip、conda更换国内源的方法
2020/11/17 Python
详解CSS3选择器的使用方法汇总
2015/11/24 HTML / CSS
HTML5 canvas画矩形时出现边框样式不一致的解决方法
2013/10/14 HTML / CSS
StubHub智利:购买和出售您的门票
2016/11/23 全球购物
Agoda台湾官网:国内外订房2折起
2018/03/20 全球购物
2014年党员创先争优承诺书
2014/05/29 职场文书
民主生活会汇报材料
2014/12/15 职场文书
优秀党员先进材料
2014/12/18 职场文书
2015年优质护理服务工作总结
2015/04/08 职场文书
2016年幼儿园教研活动总结
2016/04/05 职场文书
如何使用vue3打造一个物料库
2021/05/08 Vue.js