Blogger Information
Blog 5
fans 2
comment 1
visits 4636
Popular Tutorials
More>
Latest Downloads
More>
Web Effects
Website Source Code
Website Materials
Front End Template
原生JS仿微信聊天
zhihuanwang的博客
Original
1124 people have browsed it

   终于有点时间写点博客了,最近在忙着找工作的事情。在进入正题之前,我必须得感谢下PHP中文网的所有老师,他们让我对前端有了更清晰的理解。不管什么问题,一个人很难考虑的很全面,但是多个人就不一样了,每个人的出发点不同,思考方式或也不尽相同,人数多了想到的自然会很全面,一个项目的完成如果包含了很多人的努力,那么用户体验、业务逻辑等肯定会很棒。前端这个圈子说大不大,感谢大家给我一个温馨的大家庭。大家在一起学习,聊聊技术,彼此相互照应,挺好。闲话不多说了,且进入正题。

        1.首先预览下页面效果:

20171218_115717.gif

    2.布局的HTML文档没什么好说的,消息区域用无序列表。

index.html


<!DOCTYPE html>
<html>
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <title>聊天室</title>
  <link rel="stylesheet" href="css/style.css">
  <script src="js/move3.js" charset="utf-8"></script>
  <script src="js/javascript.js" charset="utf-8"></script>
</head>
<body>
<div>
  <div>
    <div>仿微信聊天</div>
    <span id="time">00:00:00</span>
  </div>
  <ul id="chatContent">
  </ul>
  <div>
    <input type="text" id="txt1"name="" value="" placeholder="请输入...">
    <input type="button" id="btn" name="" value="发送">
  </div>
</div>
</body>
</html>


3.层叠样式表部分,浮动和绝对定位混合使用来定位

style.css 


html,body,ul,li {
  margin: 0;
  padding: 0;
  list-style: none;
}
  .chat {
    width: 450px;
    height: 770px;
    background: #eee;
    margin: 20px auto 0;
    box-shadow: 20px 20px 55px #777;
  }
  .chat .head {
    width: 450px;
    height: 45px;
    background-color: #000000;
    position: relative;
  }
  .chat .head .center {
    display: inline-block;
    position: absolute;
    left: 90px;
    width: 60%;
    height: 45px;
    text-align: center;
    color: #FFEFE4;
    line-height: 45px;
    font-weight: bolder;
  }
  .chat .head span {
    display: block;
    line-height: 45px;
    float: right;
    color: white;
  }
  .chat #chatContent {
    width: 450px;
    height: 660px;
    overflow: auto;
  }
  .chat .bottom{
    width:434px;
    height: 49px;
    padding: 8px;
    background-color: #666666;
  }
  .chat .bottom #txt1{
    width: 330px;
    height: 44px;
    /*outline: solid 1px;*/
    border-radius: 6px;
    font-size: 20px;
  }
  .chat .bottom #btn {
    width: 80px;
    height: 47px;
    color: white;
    font-size: 22px;
    border-radius: 6px;
    /*background-color:#7DFC00;*/
    background-color: #19AD17;
    border:0px;
  }
  .chat #chatContent li >img{
    width: 30px;
    height: 30px;
    display: inline-block;
    border-radius: 50%;
    /*float: right;*/
  }
  .chat #chatContent li>span {
    padding: 10px;
    /*float: right;*/
    display: inline-block;
    margin: 6px 10px 0 10px;
    /*important*/
    max-width: 310px;
    border: 1px solid #ccc;
    box-shadow: 0 0 3px #ccc;
    background-color: #7DFC00;
    border-radius: 6px;
    padding: 10px;
  }
  .chat #chatContent li {
    margin-top: 10px;
    padding-left: 10px;
    width: 412px;
    margin: 2px 0;
    display: block;
    clear: both;
    overflow: hidden;
  }
  .clear {
    clear: both;
  }
.fl {
  float: left;
}
.fr {
  float: right;
}


4.最重要的部分到了,原生JS实现人机交互和页面动态,具体的功能说明代码中我都加了注释

javascript.js


window.onload=function () {
  var oBtn=document.getElementById('btn');
  var oTxt=document.getElementById('txt1');
  var oUl=document.getElementById('chatContent');
  var oTime=document.getElementById('time');
// 标准化时间
    function toDouble(num) {
      if (num<10) {
        return '0'+num;
      }else {
        return ''+num;
      }
    }
    // 获取并返回时间字符串
    var showTime=function () {
      var oDate=new Date();
      var hour=oDate.getHours();
      var min=oDate.getMinutes();
      var sec=oDate.getSeconds();
      return ''+toDouble(hour)+':'+toDouble(min)+':'+toDouble(sec);
    }
// 设置定时器定时刷新时间
  setInterval(function () {
    oTime.innerHTML=showTime();
  },30);
  // enter键键盘点击事件
  document.onkeydown=function (ev) {
    var oEvent=event||ev;
    if (oEvent.keyCode==13) {
      submit();
    }
  }
  // 实现提交聊天内容
  submit=oBtn.onclick=function () {
    var timeStr=showTime();
    var oLi=document.createElement('li');
    oLi.innerHTML += '<img src="image/me.jpg" class="fr"><span class="fr"><span style="color:yellow;font-size:16px;">'+timeStr+'</span><br>'+oTxt.value+'</span>';
    donghua();
    // oUl.appendChild(oLi);
    oTxt.value='';
    var aData=['你好','吃饭没','吃饱了没','再来一瓶可乐','可以打包吗','您要买什么','我喜欢这条裤子','你要去哪里','这儿附近有饭馆吗'];
    var oLi=document.createElement('li');
    oLi.innerHTML += '<img src="image/github1.jpg" class="fl"><span class="fl" ><span style="color:yellow;font-size:16px;">'+timeStr+'</span><br>'+aData[Math.floor(Math.random()*aData.length)]+'</span>';
    donghua();
    // oUl.appendChild(oLi);
// 实现消息框延时滑出
    function donghua() {
      oUl.appendChild(oLi);
      var iHeight=oLi.offsetHeight;
      oLi.style.height='0';
      startMove(oLi,{height:iHeight},function(){
        // 内容过多时加滚动条
        oUl.scrollTop=oUl.scrollHeight;
        startMove(oLi,{opacity:100});
      });
    }
  }
}




5.消息框延时滑出函数的定义部分

move3.js


function getStyle(obj, name) {
  if (obj.currentStyle) {
    return obj.currentStyle[name];
  }else {
    return getComputedStyle(obj, false)[name];
  }
}
  function startMove(obj, json,fnEnd) {
    clearInterval(obj.timer);
    obj.timer=setInterval(function () {
      // 假设所有的属性值都到达了目标值
      var bStop=true;
      for(var attr in json){
        var cur=0;
        if (attr=='opacity') {
          cur=Math.round(parseFloat(getStyle(obj, attr))*100);
        }else {
          cur=parseInt(getStyle(obj,attr));
        }
        var speed=(json[attr]-cur)/6;
        speed=speed>0?Math.ceil(speed):Math.floor(speed);
        if(cur!=json[attr]){
          bStop=false;
        }
        if (attr=='opacity') {
          obj.style.filter='alpha(opacity:'+(cur+speed)+')';
          obj.style.opacity=(cur+speed)/100;
        }else {
          obj.style[attr]=cur+speed+'px';
        }
      }
      if (bStop) {
        clearInterval(obj.timer);
        // alert('abc');
        if(fnEnd)fnEnd();
      }
    },30);
  }


6.issue与后期改进

经过测试,发现当消息区域的消息满屏后,后面输入的内容会在下面,经过修改后,提交消息时滚动条会先猛的向下一滑,很不自然,然后消息框动画正常显示。第二,aData数组数据内容不够全面,甲发出一条消息后乙的回复是随机的,这样不太好。应该可以做出根据甲的内容,乙的回复符合人类日常用语的逻辑,微软小娜是个不错的好例子,完成这个功能应该需要字符串搜索等的技术的支持。第三,这个还仅仅是一个基于前端的项目,应该拓展一下,加入服务器端的功能,使其可以实现远程聊天。这些我有时间了会去尝试一下,欢迎大家给出好的建议和改进。





Statement of this Website
The copyright of this blog article belongs to the blogger. Please specify the address when reprinting! If there is any infringement or violation of the law, please contact admin@php.cn Report processing!
All comments Speak rationally on civilized internet, please comply with News Comment Service Agreement
1 comments
飞将军 2017-12-18 13:44:35
学习了
1 floor
Author's latest blog post
About us Disclaimer Sitemap
php.cn:Public welfare online PHP training,Help PHP learners grow quickly!