作为学习实验的一部分,我想制作网络应用程序。我还在学习多线程,我做了一个简单的多线程“游戏”,它涉及在屏幕上绘制精灵,玩家可以移动它们。
对于这个新项目,我想做一些简单的事情,仅仅是为了体验和学习。我想创建一个服务器,多个客户端可以连接到它。服务器将包含“游戏对象”,它只是一个包含x和y位置的对象,一个字符串名称,一个用于标识它的ID和一个速度(dx和dy)。
“服务器”应用程序将以工作者线程更新对象位置(使用其速度)为特征,并且还将向客户端发送所有游戏对象的“状态”,以便客户端可以绘制它们球员要看。
只要玩家按下键盘上的按钮并生成KeyEvent,客户端也会发送服务器数据。服务器将读取此数据并通过更新播放器的游戏对象来处理它。例如,如果玩家按下左箭头键,客户端将发送指示左键被按下的服务器数据,服务器将找到与客户端关联的游戏对象(也许我会将对象存储在地图中? )
问题是如何做到这一点。我以前从未做过这种规模的网络。到目前为止,我所做的最多的是一个有缺陷的2人tic tac toe游戏。由于这是基于回合制的,因此我正在尝试制作的应用程序非常不同。作为研究,我阅读了关于Oracle的整个Concurrency课程。我还在NIO上阅读了本教程。我之前从未使用过NIO,但我被多人推荐使用它。通过阅读代码并弄清楚它是如何工作的,我学到了很多关于多线程和并发的知识。
由于SocketChannels使用ByteBuffers进行通信,我想到的一个策略是获取GameObjects列表并将其序列化为字节数组。然后使用ByteArray创建一个ByteBuffer并将其发送到客户端。然后,客户端将获取服务器中加载的所有GameObject,并能够根据其类型和状态绘制所有GameObject。这样做的一个问题是字节数组可能变得非常大。我用256个GameObjects测试了它,得到了一个高达9KB的字节数组。如果我压缩字节数组,则大小约为96字节。不过,我不知道这是不是太大了,不能每秒发送给客户15次。
我知道的另一个选择是逐字节发送信息。例如,发送的第一个字节可以识别我发送的游戏对象类型(例如:cat,car,person),接下来的两个字节可以识别X位置,然后接下来的两个Y位置,然后是最后使用的字节识别对象的状态。使用此数据,客户端只需在收到的位置上绘制一个精灵。
我所说的一个大问题是客户端无法与任何对象进行交互。客户端只能向服务器发送简单的命令,并在其位置“查看”游戏对象的精灵。如果服务器想告诉游戏对象做一个特定的动作,就很难画它,因为我只是将静态精灵画到屏幕上,而不是与精灵交互。
我也不确定NIO是否是最好的主意。我讨论过的大多数人都推荐它,但我不太明白实现非阻塞NIO服务器和多线程常规java.net。*服务器之间的实际区别。我的猜测是非阻塞服务器比多线程服务器具有更好的性能,而且我只会遇到1个线程而不是每个连接多个线程的问题。
最后,我得到了关于是否使用TCP或UDP的混合建议。我之前从未使用过UDP。一些人强烈建议使用TCP,而其他人强烈建议使用UDP。
正如你所看到的,我很无组织,不知道该怎么做。我觉得我已经阅读了很多关于网络和并发性的知识,而且我已经对Swing做了很多关于制作图形游戏的知识。我只是不知道怎么把它们放在一起。
答案 0 :(得分:0)
或许考虑使用Netty。我发现它对于快速应用程序开发非常有用,对于大多数服务器和客户端应用程序来说足够快使用Java NIO实现反应堆设计模式的原始实现可以更快,但是需要更多的工作和代码才能进行调试。