零基础实现node+express个性化聊天室的示例
本篇文章使用node+express+jquery写一个个性化聊天室,一起来get一下~(源码地址见文章末尾) 效果图 项目结构 实现功能
下面将一一讲解如何实现 前期准备、、 具体实现1、将聊天室部署到服务器先用node搭建一个服务器,部署在localhost:3000端口,先尝试向浏览器发送一个“hello world”,新建server.js文件。 app.get('/',function(req,res){ // 路由为localhost:3000时向客户端响应“hello world”
res.send(' Hello world'); // 发送数据}); http.listen(3000,function(){ // 监听3000端口 打开浏览器输入网址:localhost:3000是这样的 一个node服务器搭建成功。 接下来用express向浏览器返回一个html页面 将server.js的代码改一下: // 路由为/默认www静态文件夹
app.use('/',express.static(__dirname + '/www')); express.static(__dirname + '/www');是将www文件夹托管为静态资源,意味着这个文件夹里的文件(html、css、js)彼此可以用相对路径。在www文件夹中添加index.html文件以及相应的css(相应css代码就不贴了,详情见源码),如下,该页面用了font-awesome小图标
chat
请输入你的昵称 -->
在线人员()
当前无人在线哟~ 打开localhost:3000,会看到如下: 聊天室成功部署到服务器。 2、检测登录在客户端和服务器之间传送消息需要用到socket.io 将server.js改动如下: app.use('/',express.static(__dirname + '/www'));
io.on('connection',function(socket){ // 用户连接时触发 http.listen(3000,function(){ 当打开localhost:3000的时候会触发服务器端io的connection事件,会在服务器打印“a user connected”,但是我们想统计一下连接该服务器的用户人数,如果有用户连接就打印“n users connected”,n为用户人数,怎么办呢? 在server.js设置一个全局数组为user,每当一个用户连接成功就在连接事件中将用户的昵称push进user,打印user.length即可知道已成功连接用户的人数。 等一等。 在用户连接的时输入昵称登录,我们应该检测一下用户的昵称是否已存在,避免昵称相同的情况发生,在服务器监听一个登录事件来判断该情况,由于一切都发生在用户连接之后,所以触发事件应该写在connection事件的回调函数中。 {
// 渲染在线人员
io.emit('disUser',usersInfo);
// 登录,检测用户名 system和disUser事件先不管,之后再说 区分io.emit(foo)、socket.emit(foo)、socket.broadcast.emit(foo) 接下来是客户端代码chat-client.js // 点击输入昵称
$('#nameBtn').click(()=> { var imgN = Math.floor(Math.random()*4)+1; // 随机分配头像 if($('#name').val().trim()!=='') socket.emit('login',{ // 触发服务器端登录事件 name: $('#name').val(),img: 'image/user' + imgN + '.jpg' }); return false; }); // 登录成功,隐藏登录层 socket.on('loginSuc',()=> { $('.name').hide(); }) socket.on('loginError',()=> { alert('用户名已存在,请重新输入!'); $('#name').val(''); }); }); 倘若登录成功,会看到如下页面: 登录检测完成。 3、系统自动提示用户状态(进入/离开)该功能是为了实现上图所示的系统提示“XXX进入聊天室”,在登录成功时触发system事件,向所有用户广播信息,注意此时用的是io.emit而不是socket.emit,客户端代码如下 {
var data = new Date().toTimeString().substr(0,8);
$('#messages').append(`
${data} 4、显示在线用户客户端监听一个显示在线用户的事件disUser,在以下三个时间段服务器端就触发一次该事件重新渲染一次
{
displayUser(usersInfo);
});
// 显示在线人员
function displayUser(users) {
$('#users').text(''); // 每次都要重新渲染
if(!users.length) {
$('.contacts p').show();
} else {
$('.contacts p').hide();
}
$('#num').text(users.length);
for(var i = 0; i < users.length; i++) {
var $html = `
5、支持发送和接收消息用户发送消息时触发服务器端的sendMsg事件,并将消息内容作为参数,服务器端监听到sendMsg事件之后向其他所有用户广播该消息,用的socket.broadcast.emit(foo) {
var img = '';
for(var i = 0; i < usersInfo.length; i++) {
if(usersInfo[i].name == socket.nickname) {
img = usersInfo[i].img;
}
}
socket.broadcast.emit('receiveMsg',{ // 向除了发送者之外的其他用户广播
name: socket.nickname,img: img,msg: data.msg,color: data.color,side: 'left'
});
socket.emit('receiveMsg',{ // 向发送者发送消息,为什么分开发送?因为css样式不同
name: socket.nickname,side: 'right'
});
});
服务器端接受到来自用户的消息后会触发客户端的receiveMsg事件,并将用户发送的消息作为参数传递,该事件会向聊天面板添加聊天内容,以下为chat-client.js代码 {
if(ev.which == 13) {
sendMsg();
}
});
`);
// 滚动条总是在最底部
$('#messages').scrollTop($('#messages')[0].scrollHeight);
});
// 接收消息 ${obj.msg} // 发送消息 6、自定义字体颜色得益于html5的input新特性,可以通过type为color的input调用系统调色板 客户端根据用户选择的颜色渲染内容样式,代码很容易看懂,这里就不赘述了。 7、支持发送表情发送表情其实很简单,将表情图片放在li中,当用户点击li时就将表情的src中的序号解析出来,用[emoji+表情序号]的格式存放在聊天框里,点击发送后再解析为src。就是一个解析加还原的过程,这一过程中我们的服务器代码不变,需要改变的是客户端监听的receiveMsg事件。 // 显示表情选择面板
$('#smile').click(()=> { $('.selectBox').css('display',"block"); }); $('#smile').dblclick((ev)=> { $('.selectBox').css('display',"none"); }); $('#m').click(()=> { $('.selectBox').css('display',"none"); }); // 用户点击发送表情 客户端收到之后将表情序号还原为src,更改如下 // 接收消息
`);
// 滚动条总是在最底部
$('#messages').scrollTop($('#messages')[0].scrollHeight);
});
socket.on('receiveMsg',(obj)=> { // 提取文字中的表情加以渲染 var msg = obj.msg; var content = ''; while(msg.indexOf('[') > -1) { // 其实更建议用正则将[]中的内容提取出来 var start = msg.indexOf('['); var end = msg.indexOf(']');
} $('#messages').append(`
可以成功发送表情了。 8、支持发送图片首先是图片按钮样式,发送图片的按钮是type为file的input。这里有一个改变样式的小技巧,那就是将input的透明度设为0,z-index为5,将你想要得样式放在div中,z-index设为1覆盖在input上。
css:
.edit #file { 完美 接下来是点击按钮发送图片,我们用了fileReader对象,这里有一篇不错的文章讲解了fileReader,fileReader是一个对象,可以将我们选中的文件已64位输出然后将结果存放在reader.result中,我们选中图片之后,reader.result就存放的是图片的src // 用户发送图片
$('#file').change(function() { var file = this.files[0]; // 上传单张图片 var reader = new FileReader(); //文件读取出错的时候触发 由于发送的是图片,所以对页面布局难免有影响,为了页面美观客户端在接收其他用户发送的消息的时候会先判断发送的是文本还是图片,根据不同的结果展示不同布局。判断的方法是在客户发送消息的时候传入一个type,根据type的值来确实发送内容的类型。所以上面发送图片代码中触发了sendMsg事件,传入参数多了一个type属性。 响应的,我们应该在chat-client.js中修改receiveMsg事件监听函数,改为根据传入type做不同操作 {
// 发送为图片
if(obj.type == 'img') {
$('#messages').append(`
`);
$('#messages').scrollTop($('#messages')[0].scrollHeight);
return;
}
// 提取文字中的表情加以渲染 现在我们可以发送图片了 圆满完成一个功能齐全的聊天室! 源码地址:,本文断断续续写了两天,真是写文章比敲代码还累...其实写一个聊天室并不难,这算是node起步作品吧。 以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持编程之家。 (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |