XNA是微软推出的一个基于DirectX的.net平台游戏开发框架,用来开发XBOX和Windows桌面的游戏,后被移植到了silverlight和windows phone上。内部是一个game loop,不同于事件驱动模式,但也不难掌握,性能方面还是不错的。下面就用XNA创建一个简单的局域网游戏。

网络连接无外乎就是那么几个阶段,连接-发送、接收数据-断开。

用到的几个主要的类是:

        using Microsoft.Xna.Framework.Net;
//网络连接会话类
NetworkSession networkSession;
//发送packet的类
PacketWriter packetWriter = new PacketWriter();
//读取packet的类
PacketReader packetReader = new PacketReader();

游戏开始需要有一个人来创建一个session,然后有人来加入到你创建的游戏当中来。

创建游戏session:

            // 创建一个session,最大人数2
networkSession = NetworkSession.Create(NetworkSessionType.SystemLink, 1, 2);
networkSession.AllowHostMigration = true;
networkSession.AllowJoinInProgress = false;
//绑定join和left时间
networkSession.GamerJoined += GamerJoined;
networkSession.GamerLeft += GamerLeft;

void GamerJoined(object sender, GamerJoinedEventArgs e)
{
//tag是一个object类型的容器,用来保存用户自定义的信息。
e.Gamer.Tag = new entity;
}

void GamerLeft(object sender, GamerLeftEventArgs e)
{
networkSession.Dispose();
networkSession = null;
}

加入游戏:

            // 查找是否存在游戏session
AvailableNetworkSessionCollection sessions =
NetworkSession.Find(NetworkSessionType.SystemLink, 1, null);
if (sessions.Count > 0)
{
//如果session存在,就加入到这个session中
networkSession = NetworkSession.Join(sessions[0]);
//绑定join和left事件,同上
networkSession.GamerJoined += GamerJoined;
networkSession.GamerLeft += GamerLeft;
}

加入到游戏session之后就开是玩家之间进行数据的传输和接收了。

        protected void UpdateLocalPlayer(GameTime gameTime)
{
// 获取本地玩家
LocalNetworkGamer localGamer = networkSession.LocalGamers[0];

// 获取上面绑定到tag中的entity
entity sprite = (entity )localGamer.Tag;

// 写入数据到packetWriter中
packetWriter.Write((int)1);
packetWriter.Write(Vector.Zero);

// 发送数据
localGamer.SendData(packetWriter, SendDataOptions.InOrder);

}
        protected void ProcessIncomingData(GameTime gameTime)
{
// 获取玩家
LocalNetworkGamer localGamer = networkSession.LocalGamers[0];

//是否有数据可读取
while (localGamer.IsDataAvailable)
{
//接收数据
NetworkGamer sender;
localGamer.ReceiveData(packetReader, out sender);

//忽略到自己发送的数据
if (!sender.IsLocal)
{
//读取数据到packetReader中
MessageType messageType = (int)packetReader.ReadInt32();
}
foreach (NetworkGamer gamer in networkSession.AllGamers)
{
if (!gamer.IsLocal)
{
//获取绑定到tag中的实体
entity _e= ((entity)gamer.Tag);

//读取packetReader中的数据
Vector2 Pos = packetReader.ReadVector2();
}

//add some game logic here
}
}
}

在接收到数据之后就可以在Update方法中写游戏逻辑,最后Draw方法也很简单。

            // 循环所有游戏玩家
foreach (NetworkGamer gamer in networkSession.AllGamers)
{
//调用entity中的draw方法
entity sprite = ((entity)gamer.Tag);
sprite.Draw(gameTime, spriteBatch);
}

代码都很简单,一看就懂,感兴趣的朋友可以自己去找些资料来看。






posted on 2011-12-21 20:25  艾克赛尔  阅读(1010)  评论(0编辑  收藏  举报