NetworkOrderSource.

- Also, fixed the bug where watching a replay that contained non-localplayer production orders crashed.
This commit is contained in:
Bob
2009-11-16 17:26:38 +13:00
parent 5e3f2aa861
commit 99d006c73f
4 changed files with 70 additions and 13 deletions

View File

@@ -10,6 +10,7 @@ using OpenRa.Game.GameRules;
using OpenRa.Game.Graphics; using OpenRa.Game.Graphics;
using OpenRa.Game.Traits; using OpenRa.Game.Traits;
using OpenRa.Game.Support; using OpenRa.Game.Support;
using System.Net.Sockets;
namespace OpenRa.Game namespace OpenRa.Game
{ {
@@ -78,8 +79,10 @@ namespace OpenRa.Game
soundEngine = new ISoundEngine(); soundEngine = new ISoundEngine();
sounds = new Cache<string, ISoundSource>(LoadSound); sounds = new Cache<string, ISoundSource>(LoadSound);
var socket = new TcpClient( "127.0.0.1", 1234 );
orderManager = (Replay == "") orderManager = (Replay == "")
? new OrderManager(new[] { new LocalOrderSource() }, "replay.rep") ? new OrderManager(new[] { new NetworkOrderSource( socket ) }, "replay.rep")
: new OrderManager(new[] { new ReplayOrderSource(Replay) }); : new OrderManager(new[] { new ReplayOrderSource(Replay) });
PlaySound("intro.aud", false); PlaySound("intro.aud", false);

View File

@@ -5,6 +5,7 @@ using System.Text;
using System.IO; using System.IO;
using System.Net; using System.Net;
using IjwFramework.Types; using IjwFramework.Types;
using System.Net.Sockets;
namespace OpenRa.Game namespace OpenRa.Game
{ {
@@ -34,7 +35,7 @@ namespace OpenRa.Game
return false; return false;
foreach( var p in players ) foreach( var p in players )
p.Tick( localOrders ); p.SendLocalOrders( frameNumber, localOrders );
if( savingReplay != null ) if( savingReplay != null )
savingReplay.Write( frameNumber ); savingReplay.Write( frameNumber );
@@ -58,22 +59,23 @@ namespace OpenRa.Game
interface OrderSource interface OrderSource
{ {
void Tick( List<Order> localOrders ); void SendLocalOrders( int localFrame, List<Order> localOrders );
List<Order> OrdersForFrame( int frameNumber ); List<Order> OrdersForFrame( int currentFrame );
} }
class LocalOrderSource : OrderSource class LocalOrderSource : OrderSource
{ {
List<Order> orders; Dictionary<int, List<Order>> orders = new Dictionary<int,List<Order>>();
public void Tick( List<Order> localOrders ) public List<Order> OrdersForFrame( int currentFrame )
{ {
orders = localOrders; // TODO: prune `orders` based on currentFrame.
return orders[ currentFrame ];
} }
public List<Order> OrdersForFrame( int frameNumber ) public void SendLocalOrders( int localFrame, List<Order> localOrders )
{ {
return orders; orders[ localFrame ] = localOrders;
} }
} }
@@ -86,9 +88,7 @@ namespace OpenRa.Game
replayReader.ReadUInt32(); replayReader.ReadUInt32();
} }
public void Tick( List<Order> localOrders ) public void SendLocalOrders( int localFrame, List<Order> localOrders ) { }
{
}
public List<Order> OrdersForFrame( int frameNumber ) public List<Order> OrdersForFrame( int frameNumber )
{ {
@@ -113,5 +113,57 @@ namespace OpenRa.Game
} }
} }
} }
}
class NetworkOrderSource : OrderSource
{
int nextLocalOrderFrame = 0;
TcpClient socket;
BinaryReader reader;
public NetworkOrderSource( TcpClient socket )
{
this.socket = socket;
reader = new BinaryReader( socket.GetStream() );
var nextFrameId = System.BitConverter.GetBytes( nextLocalOrderFrame );
socket.GetStream().Write( nextFrameId, 0, nextFrameId.Length );
}
public List<Order> OrdersForFrame( int currentFrame )
{
if( currentFrame == 0 )
{
var firstFrameNum = reader.ReadInt32();
if( firstFrameNum != 0 )
throw new InvalidOperationException( "Wrong frame number at start of stream" );
}
var ret = new List<Order>();
while( true )
{
var first = reader.ReadUInt32();
if( first == currentFrame + 1 )
return ret;
ret.Add( Order.Deserialize( reader, first ) );
}
}
public void SendLocalOrders( int localFrame, List<Order> localOrders )
{
if( nextLocalOrderFrame != localFrame )
throw new InvalidOperationException( "Attempted time-travel in NetworkOrderSource.SendLocalOrders()" );
foreach( var order in localOrders )
{
var bytes = order.Serialize();
socket.GetStream().Write( bytes, 0, bytes.Length );
}
++nextLocalOrderFrame;
var nextFrameId = System.BitConverter.GetBytes( nextLocalOrderFrame );
socket.GetStream().Write( nextFrameId, 0, nextFrameId.Length );
}
} }
} }

View File

@@ -22,6 +22,9 @@ namespace OpenRa.Game
this.Race = race; this.Race = race;
this.Cash = 10000; this.Cash = 10000;
this.powerProvided = this.powerDrained = 0; this.powerProvided = this.powerDrained = 0;
foreach( var cat in Rules.Categories.Keys )
ProductionInit( cat );
} }
public void ChangePower(int dPower) public void ChangePower(int dPower)

View File

@@ -49,7 +49,6 @@ namespace OpenRa.Game
foreach (string group in groups) foreach (string group in groups)
{ {
player.ProductionInit( group );
clockAnimations.Add( group, new Animation( "clock" ) ); clockAnimations.Add( group, new Animation( "clock" ) );
clockAnimations[ group ].PlayFetchIndex( "idle", ClockAnimFrame( group ) ); clockAnimations[ group ].PlayFetchIndex( "idle", ClockAnimFrame( group ) );
} }