首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >多人游戏同步球

多人游戏同步球
EN

Stack Overflow用户
提问于 2015-12-10 12:09:44
回答 2查看 1.7K关注 0票数 2

我正在开发一个非常简单的游戏在HTML5与惊人的phaser.io。游戏非常简单: 1vs1截击游戏在2D.实际上,它是伟大的“皮卡丘截击”(http://imagenes.es.sftcdn.net/es/scrn/12000/12531/pikachu-volleyball-2.jpg)的‘复制’。

就像我说的,游戏很简单,我有:

  • Player1
  • Player2
  • 静态元素

我只需要控制:-球员的动作-球的动作(实际上是由拱门物理控制的)-球员-球碰撞

我只是为了好玩,把朋友的脸加到球员身上。这个游戏运行得很好,我和朋友玩得很开心。所以我想,为什么不让它在线多人玩,这样我们就可以在不同的地方远程玩了?

在阅读了有关多人HTML5游戏的文章之后,我开始使用具有nodeJS服务器的websocket(socket.io)开发它。socket.io的实现非常简单,通信也很好。

问题是要使游戏实际上是可玩的。

这些是我现在的脚步:

在客户端连接上,它被创建:

  • Player1(我自己)
  • 静态元素

客户端等待一个新的客户端对分,以创建:

  • 远程播放器

因此,在连接两个客户端之后,在每个客户端上:

  • OwnPlayer
  • RemotePlayer
  • 静态元素

然后游戏开始..。在这个舞台上,这是不公平的,因为远程球员,它根本没有移动。因此,为了让远程播放器移动(经过一些尝试),我决定实现一种权威的服务器,这样的工作。

  • 本地播放器移动(已注册输入) ->客户端将输入发送到服务器->服务器将输入发送给两个客户端->每个客户端应用移动(通过改变速度)

这个技工使球员的动作在过去工作,但“同步”(等待时间是可以接受的)。

这看起来很棒,每个客户都在移动他们的玩家,还有另一个玩家被一个远程客户端移动。

问题是球..。

每个客户都有一个球,移动与拱门物理(反弹在网或在每个球员的头部).所以在很少的动作后,由于球员位置的同步不完美,每个客户的球位都不一样。

如何实现球同步?

我在想一些选择:

  • 定期将球位置发送到服务器->服务器,将球位置发送给客户端,->客户端更新球位置(通过一些插值)
  • 只在一个客户端(主客户端)启用球物理,然后定期将球的位置从“主客户端”发送到“从客户端”(可能使用webRTC )。
  • 重新开始,做一个真正的“权威服务器”,在服务器上安装Arcade物理(如果可能的话),并在客户端上进行插值?
EN

回答 2

Stack Overflow用户

发布于 2016-01-10 16:45:52

为了解决您的问题,您可以采取一种简单的方式,您可以转移到服务器,即正在附加的播放器的攻击状态,现在,所有玩家从服务器订阅攻击信息和现在的“斜线”必须呈现子弹。

这里有一个小小的代码示例

Part1:发布数据

代码语言:javascript
运行
复制
            transferData = [
            {
                id: id,
                name: Player.name,
                position: Player.position,
                facing: Player.facing,
                hitFacing: Player.hitFacing,
                health: Player.health,
                energie: Player.energie,
                healtbar: {width: Player.healthbar.width},
                energiebar: {width: Player.energiebar.width},
                isAttacking: Attack.isAttacking
            }
        ];

        session.publish('org.example.character.data', transferData);
        Attack.isAttacking = false;

Part2:订阅数据

代码语言:javascript
运行
复制
 // get player position
    session.subscribe('org.example.character.data',function (args) {
        var player = args[0];
        var exists = false;
        for (var i = 0; i < onlinePlayer.length; i++) {

            if (onlinePlayer[i].uid == player.uid) {
                var tmp = onlinePlayer[i];
                player.sprite = tmp.sprite;
                player.label = tmp.label;
                player.status = tmp.status;


                if (player.isAttacking && player.sprite != undefined) {
                    // HERE RENDER THE BALL
                    renderBall(player, this.game);
                }

                onlinePlayer[i] = player;
                exists = true;
            }
        }

        if (!exists)
            onlinePlayer.push(player);

    }).then(
        function (sub) {
            //console.log('subscribed to topic');
        },
        function (err) {
            console.log('failed to subscribe to topic', err);
        }
    );

这个例子是针对websocket服务器的,比如crossbar.io和autobahn.js在节点基础上。

http://crossbar.io/docs/Quick-Start/,但您也可以使用其他服务器实现它。

票数 1
EN

Stack Overflow用户

发布于 2015-12-10 12:40:20

你的问题让我想起了我过去的一个问题,那就是微笑。我在网上做地图应用程序。对所有客户端来说,Map对象必须是相同的(同步)。

我解决这个问题的方法是将类库移到服务器端,并使map对象单例化。看看单例模式。单例对象不能不止一次实例化。我的意思是,每一场比赛都会有一个球,客户会用它更新他们的本地对象。

这是维基百科的网页:pattern

在此之后,客户端要做的第一件事是获取映射的最近实例(即在您的例子中的球),修改和更新服务器。

另一点是,不止一个客户端可能希望在sime时间更新服务器上的共享对象。这将导致一致性问题。许多实现包括对变量的锁以限制访问。其他客户端则等待锁的释放和更新。

无论如何,在客户端拥有同一个对象的多个实例并不是一个好方法。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/34201558

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档