客户端HTML代码优化
页面先分为左右布局,然后左/右里面再分为上中下布局。
很自然,我们想到了flex
布局,Flex是Flexible Box的缩写,意为”弹性布局”,用来为盒状模型提供最大的灵活性。
...
<div class="web-im">
<div class="left">
<div class="aside content">
<div class="header">
...
</div>
<div class="body user-list">
...
</div>
<div class="footer">
...
</div>
</div>
</div>
<div class="right content">
<div class="header">...</div>
<div class="body im-record" id="im-record">
...
</div>
<div class="footer im-input">
...
</div>
</div>
</div>
...
css样式是用stylus书写的,有些初学的小伙伴应该有点点不是很明白,但是大致能懂,就是把嵌套的书写,使其看起来更容易阅读、维护。
如果对flex、和stylus不是很明白的小伙伴,可以留言区留言,后期看情况出更详细的教程,这里就不啰嗦了。
.web-im
display flex
.left
width 220px
.right
flex 1
.content
display: flex;
flex-direction: row;
flex: 1;
box-sizing: border-box;
min-width: 0;
flex-direction: column;
.header
box-shadow 1px -1px 2px 2px #eee
line-height 40px
height 40px
font-size 24px
z-index 10
background #fff
.body
flex 1
overflow-y auto
box-shadow 1px 1px 1px #eee
.footer
box-shadow 1px 1px 8px #eee
height 60px
WebSocket客户端JS
我们主要研究变的地方,没有变的通过…表示。同时,如果您想看完整代码,可以去文章最下方“了解更多”,来获取源码查看。
...
export default {
...
mounted() {
...
// 监听页面刷新,关闭事件,退出聊天室
window.onbeforeunload = function (e) {
vm.socket.send(JSON.stringify({
uid: vm.uid,
type: 2,
nickname: vm.nickname,
bridge: []
}));
}
},
computed: {
// 当前展示的消息列表
currentMessage() {
let vm = this;
let data = vm.messageList.filter(item=>{
if(item.type === 1) {
return item;
} else if(this.groupId) {
return item.groupId === this.groupId
} else if(item.bridge.length){
return item.bridge.sort().join(',') == vm.bridge.sort().join(',')
}
})
data.map(item=>{
item.status = 0
return item;
})
return data;
},
// 当前群组列表
currentGroups() {
let vm = this;
vm.groups.map(group=>{
// 找出群组对应未读消息
group.unread = this.messageList.filter(item=>{
return item.groupId === group.id && item.status === 1
}).length
return group;
})
return vm.groups;
},
// 群组列表是否有未读消息
groupsUnRead(){
return this.messageList.some(item=>{
return item.groupId && item.status === 1
})
},
// 联系人列表是否有未读消息
usersUnRead(){
return this.messageList.some(item=>{
return item.bridge.length && item.status === 1
})
},
// 当前联系人列表
currentUserList() {
let vm = this;
vm.users.map(user=>{
// 找出联系人对应未读消息
user.unread = this.messageList.filter(item=>{
return item.bridge.length && item.uid === user.uid && item.status === 1
}).length
return user;
})
return vm.users;
}
},
methods: {
...
conWebSocket(){
let vm = this;
if(window.WebSocket){
...
socket.onmessage = function(e){
...
// 消息列表滚动条始终在最底部
vm.$nextTick(function(){
var div = document.getElementById('im-record');
div.scrollTop = div.scrollHeight;
})
}
}
}
...
}
}
这次代码优化,主要是在计算属性上面做了大的调整。之前都是用方法来获取未读已读等,现在直接计算属性先一步计算,然后渲染到页面。
WebSocket服务端
...
// 注销
case 2:
delete conns[''+obj.uid+''];
users.map((item, index)=>{
if(item.uid === obj.uid){
item.status = 0;
}
return item;
})
boardcast({
type: 1,
date: moment().format('YYYY-MM-DD HH:mm:ss'),
msg: obj.nickname+'退出了聊天室',
users: users,
groups: groups,
uid: obj.uid,
nickname: obj.nickname,
bridge: []
});
break;
...
服务端主要增加了一个注销功能,用户下线。
同时,之前type=2是发送消息,现在改成了100是发送消息,2是用户下线。
快速预览效果
最后,给大家推荐一个前端学习进阶内推交流群685910553(前端资料分享),不管你在地球哪个方位,
不管你参加工作几年都欢迎你的入驻!(群内会定期免费提供一些群主收藏的免费学习书籍资料以及整理好的面试题和答案文档!)
如果您对这个文章有任何异议,那么请在文章评论处写上你的评论。
如果您觉得这个文章有意思,那么请分享并转发,或者也可以关注一下表示您对我们文章的认可与鼓励。
愿大家都能在编程这条路,越走越远。
网友评论