用socket.io简单快速实现H5实时互动

在页游时代,大部分游戏都是经过socket来实现玩家之间的实时通讯互动的,在H5时代,利用websocket,咱们也一样能够达到这个目的,而且目前websocket的浏览器兼容度已经很高,下面记录一下基于socket.io库来实现H5画板功能的过程,很是的简单方便。javascript

socket.io

socket.io是一个基于Node.js的websocket库,能够方便快捷地在web端创建socket通讯。前端

安装

npm install socket.io

启动服务器

安装好socket.io后,咱们创建app.js(服务器的入口程序),添加以下代码:java

var app = require('http').createServer(handler)
var io = require('socket.io')(app);
var fs = require('fs');

// socket端口
app.listen(8080);

// 处理请求
function handler(req, res) {
    res.writeHead(200);
    res.end('Hello World2\n');
}

// 客户端链接的事件处理函数
io.on('connection', function(socket) {
    // todo...
});

上面简单的几行代码已经创建了一个socket服务器,而且能处理客户端的链接与收发消息。web

创建客户端链接

// 链接socket
var socket = io('http://localhost');
// 监听画图消息
socket.on('draw-event', function(data) {
    console.log(data);
    // 处理画图消息
    if (data.type == 'start') {
        onTouchStart(data.x, data.y);
    } else if (data.type == 'move') {
        onTouchMove(data.x, data.y);
    }
});

房间

在同一个房间里的全部用户能够很方便的管理和传递消息,默认状况下,socket.io都是为每一个用户建立一间房间,而且房间id存在socket.id属性中。咱们在第一个用户进入时取到房间号,而后经过二维码方式让后面的用户扫码,后面的用户经过扫码进入时加入到指定的房间。npm

前端逻辑:canvas

socket.on('connect', function() {
    // 判断是经过扫码进入房间仍是房主
    if (isHost) {
        // 生成二维码
        new QRCode(document.getElementById("qrcode"), url + '?r=' + socket.id);
        console.log('url', url + '?r=' + socket.id)
    } else {
        // 发消息给服务器加入房间
        socket.emit('sys', {
            type: 'join',
            roomId: params.r
        });
    }
});

上面的代码用到了QRCode.js这个前端库生成代码。后端

后端逻辑:浏览器

// 处理系统消息
socket.on('sys', function(data) {
    console.log(data);
    if (data.type == 'join') {
        // 猜的一方进入房间
        console.log(socket.id + ' join room: ' + data.roomId);
        socket.join(data.roomId);
        // 通知房间其它用户
        io.in(data.roomId).emit('sys', { type: 'join', roomId: data.roomId });
    }
});

画图消息

画图是用canvas的绘图实现的,核心部分代码:服务器

// 笔触移动
$('#canvas').on('touchmove', function(event) {
    touch = event.touches[0];
    render();
    // 发送到后端
    socket.emit('draw-event', {
        type: 'move',
        x: touch.pageX,
        y: touch.pageY,
    });
}).on('touchstart', function(event) { // 点击屏幕
    event.preventDefault();
    touch = event.touches[0];
    onTouchStart(touch.pageX, touch.pageY);
    isTouched = true;
    // 发送到后端
    socket.emit('draw-event', {
        type: 'start',
        x: touch.pageX,
        y: touch.pageY,
    });
}).on('touchend', function(event) { // 离开屏幕
    event.preventDefault();
    isTouched = false;
    touch = null;
});

...

var render = function() {
    onTouchMove(touch.pageX, touch.pageY);
};

var onTouchStart = function(x, y) {
    context.moveTo(x - canvasOffset.left, y - canvasOffset.top);
};

var onTouchMove = function(x, y) {
    context.lineTo(x, y);
    context.stroke();
    context.moveTo(x - canvasOffset.left, y - canvasOffset.top);
    console.log(x, y)

};

后端转发消息给另外的客户端:websocket

socket.on('draw-event', function(data) {
    console.log(data);
    // 转发画图消息
    socket.to(roomId).emit('draw-event', data);
});

接收方处理消息:

socket.on('draw-event', function(data) {
    console.log(data);
    if (data.type == 'start') {
        onTouchStart(data.x, data.y);
    } else if (data.type == 'move') {
        onTouchMove(data.x, data.y);
    }
});

结语

至此,一个简单的经过websocket进行实时通讯交互的例子实现了,咱们经过扩展细节,能够作成我画你猜的画图游戏,也能够发挥创造力作出更多好玩的交互。

相关文章
相关标签/搜索