Network traffic reduced. Changes!

Bugs:
- Character rotation?
This commit is contained in:
EntenKoeniq
2021-12-23 22:03:01 +01:00
parent 013a71a1ed
commit b9a1089fd0
16 changed files with 3824 additions and 1502 deletions

106
Client/BitReader.cs Normal file
View File

@ -0,0 +1,106 @@
using System;
using System.Text;
using System.Linq;
namespace CoopClient
{
internal class BitReader
{
public int CurrentIndex { get; set; }
private byte[] ResultArray;
public BitReader(byte[] array)
{
CurrentIndex = 0;
ResultArray = array;
}
~BitReader()
{
ResultArray = null;
}
public bool CanRead(int bytes)
{
return ResultArray.Length >= CurrentIndex + bytes;
}
public bool ReadBool()
{
bool value = BitConverter.ToBoolean(ResultArray, CurrentIndex);
CurrentIndex += 1;
return value;
}
public float ReadFloat()
{
float value = BitConverter.ToSingle(ResultArray, CurrentIndex);
CurrentIndex += 4;
return value;
}
public byte ReadByte()
{
byte value = ResultArray[CurrentIndex];
CurrentIndex += 1;
return value;
}
public byte[] ReadByteArray(int length)
{
byte[] value = ResultArray.Skip(CurrentIndex).Take(length).ToArray();
CurrentIndex += length;
return value;
}
public short ReadShort()
{
short value = BitConverter.ToInt16(ResultArray, CurrentIndex);
CurrentIndex += 2;
return value;
}
public ushort ReadUShort()
{
ushort value = BitConverter.ToUInt16(ResultArray, CurrentIndex);
CurrentIndex += 2;
return value;
}
public int ReadInt()
{
int value = BitConverter.ToInt32(ResultArray, CurrentIndex);
CurrentIndex += 4;
return value;
}
public uint ReadUInt()
{
uint value = BitConverter.ToUInt32(ResultArray, CurrentIndex);
CurrentIndex += 4;
return value;
}
public long ReadLong()
{
long value = BitConverter.ToInt64(ResultArray, CurrentIndex);
CurrentIndex += 8;
return value;
}
public ulong ReadULong()
{
ulong value = BitConverter.ToUInt64(ResultArray, CurrentIndex);
CurrentIndex += 8;
return value;
}
public string ReadString(int index)
{
string value = Encoding.UTF8.GetString(ResultArray.Skip(CurrentIndex).Take(index).ToArray());
CurrentIndex += index;
return value;
}
}
}

View File

@ -132,7 +132,7 @@ namespace CoopClient
switch (keyChar[0]) switch (keyChar[0])
{ {
case (char)8: case (char)8:
if (CurrentInput.Length > 0) if (CurrentInput?.Length > 0)
{ {
CurrentInput = CurrentInput.Remove(CurrentInput.Length - 1); CurrentInput = CurrentInput.Remove(CurrentInput.Length - 1);
MainScaleForm.CallFunction("DELETE_TEXT"); MainScaleForm.CallFunction("DELETE_TEXT");

View File

@ -51,9 +51,6 @@
<SpecificVersion>False</SpecificVersion> <SpecificVersion>False</SpecificVersion>
<HintPath>..\Libs\Release\scripts\Newtonsoft.Json.dll</HintPath> <HintPath>..\Libs\Release\scripts\Newtonsoft.Json.dll</HintPath>
</Reference> </Reference>
<Reference Include="protobuf-net">
<HintPath>..\Libs\Release\scripts\protobuf-net.dll</HintPath>
</Reference>
<Reference Include="ScriptHookVDotNet3, Version=3.3.2.0, Culture=neutral, processorArchitecture=AMD64"> <Reference Include="ScriptHookVDotNet3, Version=3.3.2.0, Culture=neutral, processorArchitecture=AMD64">
<SpecificVersion>False</SpecificVersion> <SpecificVersion>False</SpecificVersion>
<HintPath>..\Libs\Release\ScriptHookVDotNet3.dll</HintPath> <HintPath>..\Libs\Release\ScriptHookVDotNet3.dll</HintPath>
@ -74,6 +71,7 @@
<Reference Include="System.Xml" /> <Reference Include="System.Xml" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<Compile Include="BitReader.cs" />
<Compile Include="Chat.cs" /> <Compile Include="Chat.cs" />
<Compile Include="COOPAPI.cs" /> <Compile Include="COOPAPI.cs" />
<Compile Include="Entities\EntitiesPed.cs" /> <Compile Include="Entities\EntitiesPed.cs" />

View File

@ -40,10 +40,6 @@ namespace CoopClient.Entities
/// </summary> /// </summary>
public Vehicle MainVehicle { get; internal set; } public Vehicle MainVehicle { get; internal set; }
/// <summary> /// <summary>
/// The latest vehicle position (may not have been applied yet)
/// </summary>
public Vector3 VehiclePosition { get; internal set; }
/// <summary>
/// The latest vehicle rotation (may not have been applied yet) /// The latest vehicle rotation (may not have been applied yet)
/// </summary> /// </summary>
public Quaternion VehicleRotation { get; internal set; } public Quaternion VehicleRotation { get; internal set; }
@ -72,10 +68,7 @@ namespace CoopClient.Entities
internal byte VehLandingGear { get; set; } internal byte VehLandingGear { get; set; }
internal bool VehRoofOpened { get; set; } internal bool VehRoofOpened { get; set; }
internal bool VehIsSireneActive { get; set; } internal bool VehIsSireneActive { get; set; }
private VehicleDoors[] LastVehDoors; internal VehicleDamageModel VehDamageModel { get; set; }
internal VehicleDoors[] VehDoors { get; set; }
private int LastVehTires;
internal int VehTires { get; set; }
#endregion #endregion
private void DisplayInVehicle() private void DisplayInVehicle()
@ -125,7 +118,7 @@ namespace CoopClient.Entities
return; return;
} }
MainVehicle = World.CreateVehicle(vehicleModel, VehiclePosition); MainVehicle = World.CreateVehicle(vehicleModel, Position);
vehicleModel.MarkAsNoLongerNeeded(); vehicleModel.MarkAsNoLongerNeeded();
if (NPCVehHandle != 0) if (NPCVehHandle != 0)
{ {
@ -295,69 +288,7 @@ namespace CoopClient.Entities
if (LastSyncWasFull) if (LastSyncWasFull)
{ {
if (VehDoors != null && VehDoors != LastVehDoors) MainVehicle.SetVehicleDamageModel(VehDamageModel);
{
int doorLength = VehDoors.Length;
if (VehDoors.Length != 0)
{
for (int i = 0; i < (doorLength - 1); i++)
{
VehicleDoor door = MainVehicle.Doors[(VehicleDoorIndex)i];
VehicleDoors aDoor = VehDoors[i];
if (aDoor.Broken)
{
if (!door.IsBroken)
{
door.Break();
}
continue;
}
else if (!aDoor.Broken && door.IsBroken)
{
// Repair?
//MainVehicle.Repair();
}
if (aDoor.FullyOpen)
{
if (!door.IsFullyOpen)
{
door.Open(false, true);
}
continue;
}
else if (aDoor.Open)
{
if (!door.IsOpen)
{
door.Open();
}
door.AngleRatio = aDoor.AngleRatio;
continue;
}
door.Close(true);
}
}
LastVehDoors = VehDoors;
}
if (VehTires != default && LastVehTires != VehTires)
{
foreach (var wheel in MainVehicle.Wheels.GetAllWheels())
{
if ((VehTires & 1 << (int)wheel.BoneId) != 0)
{
wheel.Puncture();
wheel.Burst();
}
}
LastVehTires = VehTires;
}
} }
} }
} }
@ -368,25 +299,25 @@ namespace CoopClient.Entities
} }
// Good enough for now, but we need to create a better sync // Good enough for now, but we need to create a better sync
if (CurrentVehicleSpeed > 0.05f && MainVehicle.IsInRange(VehiclePosition, 7.0f)) if (CurrentVehicleSpeed > 0.05f && MainVehicle.IsInRange(Position, 7.0f))
{ {
int forceMultiplier = (Game.Player.Character.IsInVehicle() && MainVehicle.IsTouching(Game.Player.Character.CurrentVehicle)) ? 1 : 3; int forceMultiplier = (Game.Player.Character.IsInVehicle() && MainVehicle.IsTouching(Game.Player.Character.CurrentVehicle)) ? 1 : 3;
MainVehicle.Velocity = VehicleVelocity + forceMultiplier * (VehiclePosition - MainVehicle.Position); MainVehicle.Velocity = VehicleVelocity + forceMultiplier * (Position - MainVehicle.Position);
MainVehicle.Quaternion = Quaternion.Slerp(MainVehicle.Quaternion, VehicleRotation, 0.5f); MainVehicle.Quaternion = Quaternion.Slerp(MainVehicle.Quaternion, VehicleRotation, 0.5f);
VehicleStopTime = Util.GetTickCount64(); VehicleStopTime = Util.GetTickCount64();
} }
else if ((Util.GetTickCount64() - VehicleStopTime) <= 1000) else if ((Util.GetTickCount64() - VehicleStopTime) <= 1000)
{ {
Vector3 posTarget = Util.LinearVectorLerp(MainVehicle.Position, VehiclePosition + (VehiclePosition - MainVehicle.Position), Util.GetTickCount64() - VehicleStopTime, 1000); Vector3 posTarget = Util.LinearVectorLerp(MainVehicle.Position, Position + (Position - MainVehicle.Position), Util.GetTickCount64() - VehicleStopTime, 1000);
MainVehicle.PositionNoOffset = posTarget; MainVehicle.PositionNoOffset = posTarget;
MainVehicle.Quaternion = Quaternion.Slerp(MainVehicle.Quaternion, VehicleRotation, 0.5f); MainVehicle.Quaternion = Quaternion.Slerp(MainVehicle.Quaternion, VehicleRotation, 0.5f);
} }
else else
{ {
MainVehicle.PositionNoOffset = VehiclePosition; MainVehicle.PositionNoOffset = Position;
MainVehicle.Quaternion = VehicleRotation; MainVehicle.Quaternion = VehicleRotation;
} }
#endregion #endregion

View File

@ -21,7 +21,7 @@ namespace CoopClient
private bool GameLoaded = false; private bool GameLoaded = false;
internal static readonly string CurrentVersion = "V1_2_0"; internal static readonly string CurrentVersion = "V1_3_0";
internal static bool ShareNPCsWithPlayers = false; internal static bool ShareNPCsWithPlayers = false;
internal static bool DisableTraffic = false; internal static bool DisableTraffic = false;
@ -290,14 +290,14 @@ namespace CoopClient
DebugSyncPed.Health = player.Health; DebugSyncPed.Health = player.Health;
DebugSyncPed.Position = player.Position; DebugSyncPed.Position = player.Position;
byte? flags; ushort? flags;
if (player.IsInVehicle()) if (player.IsInVehicle())
{ {
Vehicle veh = player.CurrentVehicle; Vehicle veh = player.CurrentVehicle;
veh.Opacity = 75; veh.Opacity = 75;
flags = veh.GetVehicleFlags(); flags = player.GetVehicleFlags(veh);
byte secondaryColor; byte secondaryColor;
byte primaryColor; byte primaryColor;
@ -308,7 +308,7 @@ namespace CoopClient
DebugSyncPed.VehicleModelHash = veh.Model.Hash; DebugSyncPed.VehicleModelHash = veh.Model.Hash;
DebugSyncPed.VehicleSeatIndex = (short)player.SeatIndex; DebugSyncPed.VehicleSeatIndex = (short)player.SeatIndex;
DebugSyncPed.VehiclePosition = veh.Position; DebugSyncPed.Position = veh.Position;
DebugSyncPed.VehicleRotation = veh.Quaternion; DebugSyncPed.VehicleRotation = veh.Quaternion;
DebugSyncPed.VehicleEngineHealth = veh.EngineHealth; DebugSyncPed.VehicleEngineHealth = veh.EngineHealth;
DebugSyncPed.VehRPM = veh.CurrentRPM; DebugSyncPed.VehRPM = veh.CurrentRPM;
@ -318,18 +318,17 @@ namespace CoopClient
DebugSyncPed.AimCoords = veh.IsTurretSeat((int)player.SeatIndex) ? Util.GetVehicleAimCoords() : new GTA.Math.Vector3(); DebugSyncPed.AimCoords = veh.IsTurretSeat((int)player.SeatIndex) ? Util.GetVehicleAimCoords() : new GTA.Math.Vector3();
DebugSyncPed.VehicleColors = new byte[] { primaryColor, secondaryColor }; DebugSyncPed.VehicleColors = new byte[] { primaryColor, secondaryColor };
DebugSyncPed.VehicleMods = veh.Mods.GetVehicleMods(); DebugSyncPed.VehicleMods = veh.Mods.GetVehicleMods();
DebugSyncPed.VehDoors = veh.Doors.GetVehicleDoors(); DebugSyncPed.VehDamageModel = veh.GetVehicleDamageModel();
DebugSyncPed.VehTires = veh.Wheels.GetBurstedTires();
DebugSyncPed.LastSyncWasFull = true; DebugSyncPed.LastSyncWasFull = true;
DebugSyncPed.IsInVehicle = true; DebugSyncPed.IsInVehicle = true;
DebugSyncPed.VehIsEngineRunning = (flags.Value & (byte)VehicleDataFlags.IsEngineRunning) > 0; DebugSyncPed.VehIsEngineRunning = (flags.Value & (ushort)VehicleDataFlags.IsEngineRunning) > 0;
DebugSyncPed.VehAreLightsOn = (flags.Value & (byte)VehicleDataFlags.AreLightsOn) > 0; DebugSyncPed.VehAreLightsOn = (flags.Value & (ushort)VehicleDataFlags.AreLightsOn) > 0;
DebugSyncPed.VehAreHighBeamsOn = (flags.Value & (byte)VehicleDataFlags.AreHighBeamsOn) > 0; DebugSyncPed.VehAreHighBeamsOn = (flags.Value & (ushort)VehicleDataFlags.AreHighBeamsOn) > 0;
DebugSyncPed.VehIsSireneActive = (flags.Value & (byte)VehicleDataFlags.IsSirenActive) > 0; DebugSyncPed.VehIsSireneActive = (flags.Value & (ushort)VehicleDataFlags.IsSirenActive) > 0;
DebugSyncPed.VehicleDead = (flags.Value & (byte)VehicleDataFlags.IsDead) > 0; DebugSyncPed.VehicleDead = (flags.Value & (ushort)VehicleDataFlags.IsDead) > 0;
DebugSyncPed.IsHornActive = (flags.Value & (byte)VehicleDataFlags.IsHornActive) > 0; DebugSyncPed.IsHornActive = (flags.Value & (ushort)VehicleDataFlags.IsHornActive) > 0;
DebugSyncPed.Transformed = (flags.Value & (byte)VehicleDataFlags.IsTransformed) > 0; DebugSyncPed.Transformed = (flags.Value & (ushort)VehicleDataFlags.IsTransformed) > 0;
DebugSyncPed.VehRoofOpened = (flags.Value & (byte)VehicleDataFlags.RoofOpened) > 0; DebugSyncPed.VehRoofOpened = (flags.Value & (ushort)VehicleDataFlags.RoofOpened) > 0;
DebugSyncPed.VehLandingGear = veh.IsPlane ? (byte)veh.LandingGearState : (byte)0; DebugSyncPed.VehLandingGear = veh.IsPlane ? (byte)veh.LandingGearState : (byte)0;
if (DebugSyncPed.MainVehicle != null && DebugSyncPed.MainVehicle.Exists() && player.IsInVehicle()) if (DebugSyncPed.MainVehicle != null && DebugSyncPed.MainVehicle.Exists() && player.IsInVehicle())

View File

@ -64,7 +64,7 @@ namespace CoopClient
NetHandle = 0, NetHandle = 0,
Username = Main.MainSettings.Username, Username = Main.MainSettings.Username,
ModVersion = Main.CurrentVersion, ModVersion = Main.CurrentVersion,
NpcsAllowed = false NPCsAllowed = false
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
Client.Connect(ip[0], short.Parse(ip[1]), outgoingMessage); Client.Connect(ip[0], short.Parse(ip[1]), outgoingMessage);
@ -111,13 +111,14 @@ namespace CoopClient
} }
else else
{ {
Packet remoteHailMessagePacket; int len = message.SenderConnection.RemoteHailMessage.ReadInt32();
remoteHailMessagePacket = new HandshakePacket(); byte[] data = message.SenderConnection.RemoteHailMessage.ReadBytes(len);
remoteHailMessagePacket.NetIncomingMessageToPacket(message.SenderConnection.RemoteHailMessage);
HandshakePacket handshakePacket = new HandshakePacket();
handshakePacket.NetIncomingMessageToPacket(data);
HandshakePacket handshakePacket = (HandshakePacket)remoteHailMessagePacket;
Main.LocalNetHandle = handshakePacket.NetHandle; Main.LocalNetHandle = handshakePacket.NetHandle;
Main.NPCsAllowed = handshakePacket.NpcsAllowed; Main.NPCsAllowed = handshakePacket.NPCsAllowed;
Main.MainChat.Init(); Main.MainChat.Init();
@ -154,80 +155,166 @@ namespace CoopClient
case NetIncomingMessageType.Data: case NetIncomingMessageType.Data:
byte packetType = message.ReadByte(); byte packetType = message.ReadByte();
Packet packet;
switch (packetType) switch (packetType)
{ {
case (byte)PacketTypes.PlayerConnectPacket: case (byte)PacketTypes.PlayerConnectPacket:
packet = new PlayerConnectPacket(); {
packet.NetIncomingMessageToPacket(message); int len = message.ReadInt32();
PlayerConnect((PlayerConnectPacket)packet); byte[] data = message.ReadBytes(len);
PlayerConnectPacket packet = new PlayerConnectPacket();
packet.NetIncomingMessageToPacket(data);
PlayerConnect(packet);
}
break; break;
case (byte)PacketTypes.PlayerDisconnectPacket: case (byte)PacketTypes.PlayerDisconnectPacket:
packet = new PlayerDisconnectPacket(); {
packet.NetIncomingMessageToPacket(message); int len = message.ReadInt32();
PlayerDisconnect((PlayerDisconnectPacket)packet); byte[] data = message.ReadBytes(len);
PlayerDisconnectPacket packet = new PlayerDisconnectPacket();
packet.NetIncomingMessageToPacket(data);
PlayerDisconnect(packet);
}
break; break;
case (byte)PacketTypes.FullSyncPlayerPacket: case (byte)PacketTypes.FullSyncPlayerPacket:
packet = new FullSyncPlayerPacket(); {
packet.NetIncomingMessageToPacket(message); int len = message.ReadInt32();
FullSyncPlayer((FullSyncPlayerPacket)packet); byte[] data = message.ReadBytes(len);
FullSyncPlayerPacket packet = new FullSyncPlayerPacket();
packet.NetIncomingMessageToPacket(data);
FullSyncPlayer(packet);
}
break; break;
case (byte)PacketTypes.FullSyncPlayerVehPacket: case (byte)PacketTypes.FullSyncPlayerVehPacket:
packet = new FullSyncPlayerVehPacket(); {
packet.NetIncomingMessageToPacket(message); int len = message.ReadInt32();
FullSyncPlayerVeh((FullSyncPlayerVehPacket)packet); byte[] data = message.ReadBytes(len);
FullSyncPlayerVehPacket packet = new FullSyncPlayerVehPacket();
packet.NetIncomingMessageToPacket(data);
FullSyncPlayerVeh(packet);
}
break; break;
case (byte)PacketTypes.LightSyncPlayerPacket: case (byte)PacketTypes.LightSyncPlayerPacket:
packet = new LightSyncPlayerPacket(); {
packet.NetIncomingMessageToPacket(message); int len = message.ReadInt32();
LightSyncPlayer((LightSyncPlayerPacket)packet); byte[] data = message.ReadBytes(len);
LightSyncPlayerPacket packet = new LightSyncPlayerPacket();
packet.NetIncomingMessageToPacket(data);
LightSyncPlayer(packet);
}
break; break;
case (byte)PacketTypes.LightSyncPlayerVehPacket: case (byte)PacketTypes.LightSyncPlayerVehPacket:
packet = new LightSyncPlayerVehPacket(); {
packet.NetIncomingMessageToPacket(message); int len = message.ReadInt32();
LightSyncPlayerVeh((LightSyncPlayerVehPacket)packet); byte[] data = message.ReadBytes(len);
LightSyncPlayerVehPacket packet = new LightSyncPlayerVehPacket();
packet.NetIncomingMessageToPacket(data);
LightSyncPlayerVeh(packet);
}
break;
case (byte)PacketTypes.SuperLightSyncPacket:
{
int len = message.ReadInt32();
byte[] data = message.ReadBytes(len);
SuperLightSyncPacket packet = new SuperLightSyncPacket();
packet.NetIncomingMessageToPacket(data);
if (Main.Players.ContainsKey(packet.NetHandle))
{
EntitiesPlayer player = Main.Players[packet.NetHandle];
player.Position = packet.Position.ToVector();
player.Latency = packet.Latency.HasValue ? packet.Latency.Value : 0;
}
}
break; break;
case (byte)PacketTypes.FullSyncNpcPacket: case (byte)PacketTypes.FullSyncNpcPacket:
packet = new FullSyncNpcPacket(); {
packet.NetIncomingMessageToPacket(message); int len = message.ReadInt32();
FullSyncNpc((FullSyncNpcPacket)packet); byte[] data = message.ReadBytes(len);
FullSyncNpcPacket packet = new FullSyncNpcPacket();
packet.NetIncomingMessageToPacket(data);
FullSyncNpc(packet);
}
break; break;
case (byte)PacketTypes.FullSyncNpcVehPacket: case (byte)PacketTypes.FullSyncNpcVehPacket:
packet = new FullSyncNpcVehPacket(); {
packet.NetIncomingMessageToPacket(message); int len = message.ReadInt32();
FullSyncNpcVeh((FullSyncNpcVehPacket)packet); byte[] data = message.ReadBytes(len);
break;
case (byte)PacketTypes.SuperLightSyncPlayerPacket: FullSyncNpcVehPacket packet = new FullSyncNpcVehPacket();
packet = new SuperLightSyncPlayerPacket(); packet.NetIncomingMessageToPacket(data);
packet.NetIncomingMessageToPacket(message);
SuperLightSyncPlayer((SuperLightSyncPlayerPacket)packet); FullSyncNpcVeh(packet);
}
break; break;
case (byte)PacketTypes.ChatMessagePacket: case (byte)PacketTypes.ChatMessagePacket:
packet = new ChatMessagePacket();
packet.NetIncomingMessageToPacket(message);
ChatMessagePacket chatMessagePacket = (ChatMessagePacket)packet;
if (!COOPAPI.ChatMessageReceived(chatMessagePacket.Username, chatMessagePacket.Message))
{ {
Main.MainChat.AddMessage(chatMessagePacket.Username, chatMessagePacket.Message); int len = message.ReadInt32();
byte[] data = message.ReadBytes(len);
ChatMessagePacket packet = new ChatMessagePacket();
packet.NetIncomingMessageToPacket(data);
if (!COOPAPI.ChatMessageReceived(packet.Username, packet.Message))
{
Main.MainChat.AddMessage(packet.Username, packet.Message);
}
} }
break; break;
case (byte)PacketTypes.NativeCallPacket: case (byte)PacketTypes.NativeCallPacket:
packet = new NativeCallPacket(); {
packet.NetIncomingMessageToPacket(message); int len = message.ReadInt32();
DecodeNativeCall((NativeCallPacket)packet); byte[] data = message.ReadBytes(len);
NativeCallPacket packet = new NativeCallPacket();
packet.NetIncomingMessageToPacket(data);
DecodeNativeCall(packet);
}
break; break;
case (byte)PacketTypes.NativeResponsePacket: case (byte)PacketTypes.NativeResponsePacket:
packet = new NativeResponsePacket(); {
packet.NetIncomingMessageToPacket(message); try
DecodeNativeResponse((NativeResponsePacket)packet); {
int len = message.ReadInt32();
byte[] data = message.ReadBytes(len);
NativeResponsePacket packet = new NativeResponsePacket();
packet.NetIncomingMessageToPacket(data);
DecodeNativeResponse(packet);
}
catch (Exception ex)
{
GTA.UI.Notification.Show($"{ex.Message}");
}
}
break; break;
case (byte)PacketTypes.ModPacket: case (byte)PacketTypes.ModPacket:
packet = new ModPacket(); {
packet.NetIncomingMessageToPacket(message); int len = message.ReadInt32();
ModPacket modPacket = (ModPacket)packet; byte[] data = message.ReadBytes(len);
COOPAPI.ModPacketReceived(modPacket.NetHandle, modPacket.Mod, modPacket.CustomPacketID, modPacket.Bytes);
ModPacket packet = new ModPacket();
packet.NetIncomingMessageToPacket(data);
COOPAPI.ModPacketReceived(packet.NetHandle, packet.Mod, packet.CustomPacketID, packet.Bytes);
}
break; break;
} }
break; break;
@ -280,14 +367,14 @@ namespace CoopClient
private void FullSyncPlayer(FullSyncPlayerPacket packet) private void FullSyncPlayer(FullSyncPlayerPacket packet)
{ {
if (Main.Players.ContainsKey(packet.Extra.NetHandle)) if (Main.Players.ContainsKey(packet.NetHandle))
{ {
EntitiesPlayer player = Main.Players[packet.Extra.NetHandle]; EntitiesPlayer player = Main.Players[packet.NetHandle];
player.ModelHash = packet.ModelHash; player.ModelHash = packet.ModelHash;
player.Clothes = packet.Clothes; player.Clothes = packet.Clothes;
player.Health = packet.Extra.Health; player.Health = packet.Health;
player.Position = packet.Extra.Position.ToVector(); player.Position = packet.Position.ToVector();
player.Rotation = packet.Rotation.ToVector(); player.Rotation = packet.Rotation.ToVector();
player.Velocity = packet.Velocity.ToVector(); player.Velocity = packet.Velocity.ToVector();
player.Speed = packet.Speed; player.Speed = packet.Speed;
@ -303,24 +390,23 @@ namespace CoopClient
player.IsInVehicle = false; player.IsInVehicle = false;
player.LastSyncWasFull = true; player.LastSyncWasFull = true;
player.Latency = packet.Extra.Latency; player.Latency = packet.Latency.Value;
player.LastUpdateReceived = Util.GetTickCount64(); player.LastUpdateReceived = Util.GetTickCount64();
} }
} }
private void FullSyncPlayerVeh(FullSyncPlayerVehPacket packet) private void FullSyncPlayerVeh(FullSyncPlayerVehPacket packet)
{ {
if (Main.Players.ContainsKey(packet.Extra.NetHandle)) if (Main.Players.ContainsKey(packet.NetHandle))
{ {
EntitiesPlayer player = Main.Players[packet.Extra.NetHandle]; EntitiesPlayer player = Main.Players[packet.NetHandle];
player.ModelHash = packet.ModelHash; player.ModelHash = packet.ModelHash;
player.Clothes = packet.Clothes; player.Clothes = packet.Clothes;
player.Health = packet.Extra.Health; player.Health = packet.Health;
player.Position = packet.Extra.Position.ToVector();
player.VehicleModelHash = packet.VehModelHash; player.VehicleModelHash = packet.VehModelHash;
player.VehicleSeatIndex = packet.VehSeatIndex; player.VehicleSeatIndex = packet.VehSeatIndex;
player.VehiclePosition = packet.VehPosition.ToVector(); player.Position = packet.Position.ToVector();
player.VehicleRotation = packet.VehRotation.ToQuaternion(); player.VehicleRotation = packet.VehRotation.ToQuaternion();
player.VehicleEngineHealth = packet.VehEngineHealth; player.VehicleEngineHealth = packet.VehEngineHealth;
player.VehRPM = packet.VehRPM; player.VehRPM = packet.VehRPM;
@ -330,33 +416,32 @@ namespace CoopClient
player.AimCoords = packet.VehAimCoords.ToVector(); player.AimCoords = packet.VehAimCoords.ToVector();
player.VehicleColors = packet.VehColors; player.VehicleColors = packet.VehColors;
player.VehicleMods = packet.VehMods; player.VehicleMods = packet.VehMods;
player.VehDoors = packet.VehDoors; player.VehDamageModel = packet.VehDamageModel;
player.VehTires = packet.VehTires;
player.VehLandingGear = packet.VehLandingGear; player.VehLandingGear = packet.VehLandingGear;
player.VehIsEngineRunning = (packet.Flag.Value & (byte)VehicleDataFlags.IsEngineRunning) > 0; player.VehIsEngineRunning = (packet.Flag.Value & (ushort)VehicleDataFlags.IsEngineRunning) > 0;
player.VehAreLightsOn = (packet.Flag.Value & (byte)VehicleDataFlags.AreLightsOn) > 0; player.VehAreLightsOn = (packet.Flag.Value & (ushort)VehicleDataFlags.AreLightsOn) > 0;
player.VehAreHighBeamsOn = (packet.Flag.Value & (byte)VehicleDataFlags.AreHighBeamsOn) > 0; player.VehAreHighBeamsOn = (packet.Flag.Value & (ushort)VehicleDataFlags.AreHighBeamsOn) > 0;
player.VehIsSireneActive = (packet.Flag.Value & (byte)VehicleDataFlags.IsSirenActive) > 0; player.VehIsSireneActive = (packet.Flag.Value & (ushort)VehicleDataFlags.IsSirenActive) > 0;
player.VehicleDead = (packet.Flag.Value & (byte)VehicleDataFlags.IsDead) > 0; player.VehicleDead = (packet.Flag.Value & (ushort)VehicleDataFlags.IsDead) > 0;
player.IsHornActive = (packet.Flag.Value & (byte)VehicleDataFlags.IsHornActive) > 0; player.IsHornActive = (packet.Flag.Value & (ushort)VehicleDataFlags.IsHornActive) > 0;
player.Transformed = (packet.Flag.Value & (byte)VehicleDataFlags.IsTransformed) > 0; player.Transformed = (packet.Flag.Value & (ushort)VehicleDataFlags.IsTransformed) > 0;
player.VehRoofOpened = (packet.Flag.Value & (byte)VehicleDataFlags.RoofOpened) > 0; player.VehRoofOpened = (packet.Flag.Value & (ushort)VehicleDataFlags.RoofOpened) > 0;
player.IsInVehicle = true; player.IsInVehicle = true;
player.LastSyncWasFull = true; player.LastSyncWasFull = true;
player.Latency = packet.Extra.Latency; player.Latency = packet.Latency.Value;
player.LastUpdateReceived = Util.GetTickCount64(); player.LastUpdateReceived = Util.GetTickCount64();
} }
} }
private void LightSyncPlayer(LightSyncPlayerPacket packet) private void LightSyncPlayer(LightSyncPlayerPacket packet)
{ {
if (Main.Players.ContainsKey(packet.Extra.NetHandle)) if (Main.Players.ContainsKey(packet.NetHandle))
{ {
EntitiesPlayer player = Main.Players[packet.Extra.NetHandle]; EntitiesPlayer player = Main.Players[packet.NetHandle];
player.Health = packet.Extra.Health; player.Health = packet.Health;
player.Position = packet.Extra.Position.ToVector(); player.Position = packet.Position.ToVector();
player.Rotation = packet.Rotation.ToVector(); player.Rotation = packet.Rotation.ToVector();
player.Velocity = packet.Velocity.ToVector(); player.Velocity = packet.Velocity.ToVector();
player.Speed = packet.Speed; player.Speed = packet.Speed;
@ -371,52 +456,40 @@ namespace CoopClient
player.IsInVehicle = false; player.IsInVehicle = false;
player.LastSyncWasFull = false; player.LastSyncWasFull = false;
player.Latency = packet.Extra.Latency; if (packet.Flag.HasValue)
{
player.Latency = packet.Latency.Value;
}
player.LastUpdateReceived = Util.GetTickCount64(); player.LastUpdateReceived = Util.GetTickCount64();
} }
} }
private void LightSyncPlayerVeh(LightSyncPlayerVehPacket packet) private void LightSyncPlayerVeh(LightSyncPlayerVehPacket packet)
{ {
if (Main.Players.ContainsKey(packet.Extra.NetHandle)) if (Main.Players.ContainsKey(packet.NetHandle))
{ {
EntitiesPlayer player = Main.Players[packet.Extra.NetHandle]; EntitiesPlayer player = Main.Players[packet.NetHandle];
player.Health = packet.Extra.Health; player.Health = packet.Health;
player.Position = packet.Extra.Position.ToVector();
player.VehicleModelHash = packet.VehModelHash; player.VehicleModelHash = packet.VehModelHash;
player.VehicleSeatIndex = packet.VehSeatIndex; player.VehicleSeatIndex = packet.VehSeatIndex;
player.VehiclePosition = packet.VehPosition.ToVector(); player.Position = packet.Position.ToVector();
player.VehicleRotation = packet.VehRotation.ToQuaternion(); player.VehicleRotation = packet.VehRotation.ToQuaternion();
player.VehicleVelocity = packet.VehVelocity.ToVector(); player.VehicleVelocity = packet.VehVelocity.ToVector();
player.VehicleSpeed = packet.VehSpeed; player.VehicleSpeed = packet.VehSpeed;
player.VehicleSteeringAngle = packet.VehSteeringAngle; player.VehicleSteeringAngle = packet.VehSteeringAngle;
player.VehIsEngineRunning = (packet.Flag.Value & (byte)VehicleDataFlags.IsEngineRunning) > 0; player.VehIsEngineRunning = (packet.Flag.Value & (ushort)VehicleDataFlags.IsEngineRunning) > 0;
player.VehAreLightsOn = (packet.Flag.Value & (byte)VehicleDataFlags.AreLightsOn) > 0; player.VehAreLightsOn = (packet.Flag.Value & (ushort)VehicleDataFlags.AreLightsOn) > 0;
player.VehAreHighBeamsOn = (packet.Flag.Value & (byte)VehicleDataFlags.AreHighBeamsOn) > 0; player.VehAreHighBeamsOn = (packet.Flag.Value & (ushort)VehicleDataFlags.AreHighBeamsOn) > 0;
player.VehIsSireneActive = (packet.Flag.Value & (byte)VehicleDataFlags.IsSirenActive) > 0; player.VehIsSireneActive = (packet.Flag.Value & (ushort)VehicleDataFlags.IsSirenActive) > 0;
player.VehicleDead = (packet.Flag.Value & (byte)VehicleDataFlags.IsDead) > 0; player.VehicleDead = (packet.Flag.Value & (ushort)VehicleDataFlags.IsDead) > 0;
player.IsHornActive = (packet.Flag.Value & (byte)VehicleDataFlags.IsHornActive) > 0; player.IsHornActive = (packet.Flag.Value & (ushort)VehicleDataFlags.IsHornActive) > 0;
player.Transformed = (packet.Flag.Value & (byte)VehicleDataFlags.IsTransformed) > 0; player.Transformed = (packet.Flag.Value & (ushort)VehicleDataFlags.IsTransformed) > 0;
player.VehRoofOpened = (packet.Flag.Value & (byte)VehicleDataFlags.RoofOpened) > 0; player.VehRoofOpened = (packet.Flag.Value & (ushort)VehicleDataFlags.RoofOpened) > 0;
player.IsInVehicle = true; player.IsInVehicle = true;
player.LastSyncWasFull = false; player.LastSyncWasFull = false;
player.Latency = packet.Extra.Latency; player.Latency = packet.Latency.Value;
player.LastUpdateReceived = Util.GetTickCount64();
}
}
private void SuperLightSyncPlayer(SuperLightSyncPlayerPacket packet)
{
if (Main.Players.ContainsKey(packet.Extra.NetHandle))
{
EntitiesPlayer player = Main.Players[packet.Extra.NetHandle];
player.Health = packet.Extra.Health;
player.Position = packet.Extra.Position.ToVector();
player.Latency = packet.Extra.Latency;
player.LastUpdateReceived = Util.GetTickCount64(); player.LastUpdateReceived = Util.GetTickCount64();
} }
} }
@ -427,31 +500,32 @@ namespace CoopClient
if (packet.Args != null && packet.Args.Count > 0) if (packet.Args != null && packet.Args.Count > 0)
{ {
packet.Args.ForEach(arg => packet.Args.ForEach(x =>
{ {
Type typeOf = arg.GetType(); Type type = x.GetType();
if (typeOf == typeof(IntArgument)) if (type == typeof(int))
{ {
arguments.Add(((IntArgument)arg).Data); arguments.Add((int)x);
} }
else if (typeOf == typeof(BoolArgument)) else if (type == typeof(bool))
{ {
arguments.Add(((BoolArgument)arg).Data); arguments.Add((bool)x);
} }
else if (typeOf == typeof(FloatArgument)) else if (type == typeof(float))
{ {
arguments.Add(((FloatArgument)arg).Data); arguments.Add((float)x);
} }
else if (typeOf == typeof(StringArgument)) else if (type == typeof(string))
{ {
arguments.Add(((StringArgument)arg).Data); arguments.Add((string)x);
} }
else if (typeOf == typeof(LVector3Argument)) else if (type == typeof(LVector3))
{ {
arguments.Add(((LVector3Argument)arg).Data.X); LVector3 vector = (LVector3)x;
arguments.Add(((LVector3Argument)arg).Data.Y); arguments.Add((float)vector.X);
arguments.Add(((LVector3Argument)arg).Data.Z); arguments.Add((float)vector.Y);
arguments.Add((float)vector.Z);
} }
else else
{ {
@ -471,66 +545,61 @@ namespace CoopClient
if (packet.Args != null && packet.Args.Count > 0) if (packet.Args != null && packet.Args.Count > 0)
{ {
packet.Args.ForEach(arg => packet.Args.ForEach(x =>
{ {
typeOf = arg.GetType(); typeOf = x.GetType();
if (typeOf == typeof(IntArgument)) if (typeOf == typeof(int))
{ {
arguments.Add(((IntArgument)arg).Data); arguments.Add((int)x);
} }
else if (typeOf == typeof(BoolArgument)) else if (typeOf == typeof(bool))
{ {
arguments.Add(((BoolArgument)arg).Data); arguments.Add((bool)x);
} }
else if (typeOf == typeof(FloatArgument)) else if (typeOf == typeof(float))
{ {
arguments.Add(((FloatArgument)arg).Data); arguments.Add((float)x);
} }
else if (typeOf == typeof(StringArgument)) else if (typeOf == typeof(string))
{ {
arguments.Add(((StringArgument)arg).Data); arguments.Add((string)x);
} }
else if (typeOf == typeof(LVector3Argument)) else if (typeOf == typeof(LVector3))
{ {
arguments.Add(((LVector3Argument)arg).Data.X); LVector3 vector = (LVector3)x;
arguments.Add(((LVector3Argument)arg).Data.Y); arguments.Add((float)vector.X);
arguments.Add(((LVector3Argument)arg).Data.Z); arguments.Add((float)vector.Y);
arguments.Add((float)vector.Z);
} }
else else
{ {
GTA.UI.Notification.Show("[DecodeNativeCall][" + packet.Hash + "]: Type of argument not found!"); GTA.UI.Notification.Show("[DecodeNativeResponse][" + packet.Hash + "]: Type of argument not found!");
return; return;
} }
}); });
} }
NativeArgument result = null; object result;
switch (packet.ResultType.Value)
typeOf = packet.Type.GetType();
if (typeOf == typeof(IntArgument))
{ {
result = new IntArgument() { Data = Function.Call<int>((Hash)packet.Hash, arguments.ToArray()) }; case 0x00: // int
} result = Function.Call<int>((Hash)packet.Hash, arguments.ToArray());
else if (typeOf == typeof(BoolArgument)) break;
{ case 0x01: // bool
result = new BoolArgument() { Data = Function.Call<bool>((Hash)packet.Hash, arguments.ToArray()) }; result = Function.Call<bool>((Hash)packet.Hash, arguments.ToArray());
} break;
else if (typeOf == typeof(FloatArgument)) case 0x02: // float
{ result = Function.Call<float>((Hash)packet.Hash, arguments.ToArray());
result = new FloatArgument() { Data = Function.Call<float>((Hash)packet.Hash, arguments.ToArray()) }; break;
} case 0x03: // string
else if (typeOf == typeof(StringArgument)) result = Function.Call<string>((Hash)packet.Hash, arguments.ToArray());
{ break;
result = new StringArgument() { Data = Function.Call<string>((Hash)packet.Hash, arguments.ToArray()) }; case 0x04: // vector3
} result = Function.Call<GTA.Math.Vector3>((Hash)packet.Hash, arguments.ToArray()).ToLVector();
else if (typeOf == typeof(LVector3Argument)) break;
{ default:
result = new LVector3Argument() { Data = Function.Call<GTA.Math.Vector3>((Hash)packet.Hash, arguments.ToArray()).ToLVector() }; GTA.UI.Notification.Show("[DecodeNativeResponse][" + packet.Hash + "]: Type of return not found!");
}
else
{
GTA.UI.Notification.Show("[DecodeNativeResponse][" + packet.Hash + "]: Type of argument not found!");
return; return;
} }
@ -538,11 +607,10 @@ namespace CoopClient
new NativeResponsePacket() new NativeResponsePacket()
{ {
Hash = 0, Hash = 0,
Args = null, Args = new List<object>() { result },
Type = result, ID = packet.ID
NetHandle = packet.NetHandle
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
Client.SendMessage(outgoingMessage, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Native); Client.SendMessage(outgoingMessage, NetDeliveryMethod.ReliableOrdered, (byte)ConnectionChannel.Native);
Client.FlushSendQueue(); Client.FlushSendQueue();
} }
#endregion // -- PLAYER -- #endregion // -- PLAYER --
@ -620,10 +688,9 @@ namespace CoopClient
npc.ModelHash = packet.ModelHash; npc.ModelHash = packet.ModelHash;
npc.Clothes = packet.Clothes; npc.Clothes = packet.Clothes;
npc.Health = packet.Health; npc.Health = packet.Health;
npc.Position = packet.Position.ToVector();
npc.VehicleModelHash = packet.VehModelHash; npc.VehicleModelHash = packet.VehModelHash;
npc.VehicleSeatIndex = packet.VehSeatIndex; npc.VehicleSeatIndex = packet.VehSeatIndex;
npc.VehiclePosition = packet.VehPosition.ToVector(); npc.Position = packet.Position.ToVector();
npc.VehicleRotation = packet.VehRotation.ToQuaternion(); npc.VehicleRotation = packet.VehRotation.ToQuaternion();
npc.VehicleEngineHealth = packet.VehEngineHealth; npc.VehicleEngineHealth = packet.VehEngineHealth;
npc.VehRPM = packet.VehRPM; npc.VehRPM = packet.VehRPM;
@ -631,17 +698,16 @@ namespace CoopClient
npc.VehicleSpeed = packet.VehSpeed; npc.VehicleSpeed = packet.VehSpeed;
npc.VehicleSteeringAngle = packet.VehSteeringAngle; npc.VehicleSteeringAngle = packet.VehSteeringAngle;
npc.VehicleColors = packet.VehColors; npc.VehicleColors = packet.VehColors;
npc.VehDoors = packet.VehDoors; npc.VehDamageModel = packet.VehDamageModel;
npc.VehTires = packet.VehTires;
npc.VehLandingGear = packet.VehLandingGear; npc.VehLandingGear = packet.VehLandingGear;
npc.VehIsEngineRunning = (packet.Flag.Value & (byte)VehicleDataFlags.IsEngineRunning) > 0; npc.VehIsEngineRunning = (packet.Flag.Value & (ushort)VehicleDataFlags.IsEngineRunning) > 0;
npc.VehAreLightsOn = (packet.Flag.Value & (byte)VehicleDataFlags.AreLightsOn) > 0; npc.VehAreLightsOn = (packet.Flag.Value & (ushort)VehicleDataFlags.AreLightsOn) > 0;
npc.VehAreHighBeamsOn = (packet.Flag.Value & (byte)VehicleDataFlags.AreHighBeamsOn) > 0; npc.VehAreHighBeamsOn = (packet.Flag.Value & (ushort)VehicleDataFlags.AreHighBeamsOn) > 0;
npc.VehIsSireneActive = (packet.Flag.Value & (byte)VehicleDataFlags.IsSirenActive) > 0; npc.VehIsSireneActive = (packet.Flag.Value & (ushort)VehicleDataFlags.IsSirenActive) > 0;
npc.VehicleDead = (packet.Flag.Value & (byte)VehicleDataFlags.IsDead) > 0; npc.VehicleDead = (packet.Flag.Value & (ushort)VehicleDataFlags.IsDead) > 0;
npc.IsHornActive = (packet.Flag.Value & (byte)VehicleDataFlags.IsHornActive) > 0; npc.IsHornActive = (packet.Flag.Value & (ushort)VehicleDataFlags.IsHornActive) > 0;
npc.Transformed = (packet.Flag.Value & (byte)VehicleDataFlags.IsTransformed) > 0; npc.Transformed = (packet.Flag.Value & (ushort)VehicleDataFlags.IsTransformed) > 0;
npc.VehRoofOpened = (packet.Flag.Value & (byte)VehicleDataFlags.RoofOpened) > 0; npc.VehRoofOpened = (packet.Flag.Value & (ushort)VehicleDataFlags.RoofOpened) > 0;
npc.IsInVehicle = true; npc.IsInVehicle = true;
npc.LastSyncWasFull = true; npc.LastSyncWasFull = true;
@ -656,10 +722,9 @@ namespace CoopClient
ModelHash = packet.ModelHash, ModelHash = packet.ModelHash,
Clothes = packet.Clothes, Clothes = packet.Clothes,
Health = packet.Health, Health = packet.Health,
Position = packet.Position.ToVector(),
VehicleModelHash = packet.VehModelHash, VehicleModelHash = packet.VehModelHash,
VehicleSeatIndex = packet.VehSeatIndex, VehicleSeatIndex = packet.VehSeatIndex,
VehiclePosition = packet.VehPosition.ToVector(), Position = packet.Position.ToVector(),
VehicleRotation = packet.VehRotation.ToQuaternion(), VehicleRotation = packet.VehRotation.ToQuaternion(),
VehicleEngineHealth = packet.VehEngineHealth, VehicleEngineHealth = packet.VehEngineHealth,
VehRPM = packet.VehRPM, VehRPM = packet.VehRPM,
@ -667,17 +732,16 @@ namespace CoopClient
VehicleSpeed = packet.VehSpeed, VehicleSpeed = packet.VehSpeed,
VehicleSteeringAngle = packet.VehSteeringAngle, VehicleSteeringAngle = packet.VehSteeringAngle,
VehicleColors = packet.VehColors, VehicleColors = packet.VehColors,
VehDoors = packet.VehDoors, VehDamageModel = packet.VehDamageModel,
VehTires = packet.VehTires,
VehLandingGear = packet.VehLandingGear, VehLandingGear = packet.VehLandingGear,
VehIsEngineRunning = (packet.Flag.Value & (byte)VehicleDataFlags.IsEngineRunning) > 0, VehIsEngineRunning = (packet.Flag.Value & (ushort)VehicleDataFlags.IsEngineRunning) > 0,
VehAreLightsOn = (packet.Flag.Value & (byte)VehicleDataFlags.AreLightsOn) > 0, VehAreLightsOn = (packet.Flag.Value & (ushort)VehicleDataFlags.AreLightsOn) > 0,
VehAreHighBeamsOn = (packet.Flag.Value & (byte)VehicleDataFlags.AreHighBeamsOn) > 0, VehAreHighBeamsOn = (packet.Flag.Value & (ushort)VehicleDataFlags.AreHighBeamsOn) > 0,
VehIsSireneActive = (packet.Flag.Value & (byte)VehicleDataFlags.IsSirenActive) > 0, VehIsSireneActive = (packet.Flag.Value & (ushort)VehicleDataFlags.IsSirenActive) > 0,
VehicleDead = (packet.Flag.Value & (byte)VehicleDataFlags.IsDead) > 0, VehicleDead = (packet.Flag.Value & (ushort)VehicleDataFlags.IsDead) > 0,
IsHornActive = (packet.Flag.Value & (byte)VehicleDataFlags.IsHornActive) > 0, IsHornActive = (packet.Flag.Value & (ushort)VehicleDataFlags.IsHornActive) > 0,
Transformed = (packet.Flag.Value & (byte)VehicleDataFlags.IsTransformed) > 0, Transformed = (packet.Flag.Value & (ushort)VehicleDataFlags.IsTransformed) > 0,
VehRoofOpened = (packet.Flag.Value & (byte)VehicleDataFlags.RoofOpened) > 0, VehRoofOpened = (packet.Flag.Value & (ushort)VehicleDataFlags.RoofOpened) > 0,
IsInVehicle = true, IsInVehicle = true,
LastSyncWasFull = true, LastSyncWasFull = true,
@ -697,10 +761,12 @@ namespace CoopClient
NetOutgoingMessage outgoingMessage = Client.CreateMessage(); NetOutgoingMessage outgoingMessage = Client.CreateMessage();
NetDeliveryMethod messageType; NetDeliveryMethod messageType;
int connectionChannel = 0;
if ((Util.GetTickCount64() - LastPlayerFullSync) > 500) if ((Util.GetTickCount64() - LastPlayerFullSync) > 500)
{ {
messageType = NetDeliveryMethod.UnreliableSequenced; messageType = NetDeliveryMethod.UnreliableSequenced;
connectionChannel = (byte)ConnectionChannel.PlayerFull;
if (player.IsInVehicle()) if (player.IsInVehicle())
{ {
@ -714,18 +780,14 @@ namespace CoopClient
} }
new FullSyncPlayerVehPacket() new FullSyncPlayerVehPacket()
{
Extra = new PlayerPacket()
{ {
NetHandle = Main.LocalNetHandle, NetHandle = Main.LocalNetHandle,
Health = player.Health, Health = player.Health,
Position = player.Position.ToLVector()
},
ModelHash = player.Model.Hash, ModelHash = player.Model.Hash,
Clothes = player.GetPedClothes(), Clothes = player.GetPedClothes(),
VehModelHash = veh.Model.Hash, VehModelHash = veh.Model.Hash,
VehSeatIndex = (short)player.SeatIndex, VehSeatIndex = (short)player.SeatIndex,
VehPosition = veh.Position.ToLVector(), Position = veh.Position.ToLVector(),
VehRotation = veh.Quaternion.ToLQuaternion(), VehRotation = veh.Quaternion.ToLQuaternion(),
VehEngineHealth = veh.EngineHealth, VehEngineHealth = veh.EngineHealth,
VehRPM = veh.CurrentRPM, VehRPM = veh.CurrentRPM,
@ -735,24 +797,20 @@ namespace CoopClient
VehAimCoords = veh.IsTurretSeat((int)player.SeatIndex) ? Util.GetVehicleAimCoords().ToLVector() : new LVector3(), VehAimCoords = veh.IsTurretSeat((int)player.SeatIndex) ? Util.GetVehicleAimCoords().ToLVector() : new LVector3(),
VehColors = new byte[] { primaryColor, secondaryColor }, VehColors = new byte[] { primaryColor, secondaryColor },
VehMods = veh.Mods.GetVehicleMods(), VehMods = veh.Mods.GetVehicleMods(),
VehDoors = veh.Doors.GetVehicleDoors(), VehDamageModel = veh.GetVehicleDamageModel(),
VehTires = veh.Wheels.GetBurstedTires(),
VehLandingGear = veh.IsPlane ? (byte)veh.LandingGearState : (byte)0, VehLandingGear = veh.IsPlane ? (byte)veh.LandingGearState : (byte)0,
Flag = veh.GetVehicleFlags() Flag = player.GetVehicleFlags(veh)
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
} }
else else
{ {
new FullSyncPlayerPacket() new FullSyncPlayerPacket()
{
Extra = new PlayerPacket()
{ {
NetHandle = Main.LocalNetHandle, NetHandle = Main.LocalNetHandle,
Health = player.Health, Health = player.Health,
Position = player.Position.ToLVector()
},
ModelHash = player.Model.Hash, ModelHash = player.Model.Hash,
Clothes = player.GetPedClothes(), Clothes = player.GetPedClothes(),
Position = player.Position.ToLVector(),
Rotation = player.Rotation.ToLVector(), Rotation = player.Rotation.ToLVector(),
Velocity = player.Velocity.ToLVector(), Velocity = player.Velocity.ToLVector(),
Speed = player.GetPedSpeed(), Speed = player.GetPedSpeed(),
@ -768,39 +826,33 @@ namespace CoopClient
else else
{ {
messageType = NetDeliveryMethod.ReliableSequenced; messageType = NetDeliveryMethod.ReliableSequenced;
connectionChannel = (byte)ConnectionChannel.PlayerLight;
if (player.IsInVehicle()) if (player.IsInVehicle())
{ {
Vehicle veh = player.CurrentVehicle; Vehicle veh = player.CurrentVehicle;
new LightSyncPlayerVehPacket() new LightSyncPlayerVehPacket()
{
Extra = new PlayerPacket()
{ {
NetHandle = Main.LocalNetHandle, NetHandle = Main.LocalNetHandle,
Health = player.Health, Health = player.Health,
Position = player.Position.ToLVector()
},
VehModelHash = veh.Model.Hash, VehModelHash = veh.Model.Hash,
VehSeatIndex = (short)player.SeatIndex, VehSeatIndex = (short)player.SeatIndex,
VehPosition = veh.Position.ToLVector(), Position = veh.Position.ToLVector(),
VehRotation = veh.Quaternion.ToLQuaternion(), VehRotation = veh.Quaternion.ToLQuaternion(),
VehVelocity = veh.Velocity.ToLVector(), VehVelocity = veh.Velocity.ToLVector(),
VehSpeed = veh.Speed, VehSpeed = veh.Speed,
VehSteeringAngle = veh.SteeringAngle, VehSteeringAngle = veh.SteeringAngle,
Flag = veh.GetVehicleFlags() Flag = player.GetVehicleFlags(veh)
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
} }
else else
{ {
new LightSyncPlayerPacket() new LightSyncPlayerPacket()
{
Extra = new PlayerPacket()
{ {
NetHandle = Main.LocalNetHandle, NetHandle = Main.LocalNetHandle,
Health = player.Health, Health = player.Health,
Position = player.Position.ToLVector() Position = player.Position.ToLVector(),
},
Rotation = player.Rotation.ToLVector(), Rotation = player.Rotation.ToLVector(),
Velocity = player.Velocity.ToLVector(), Velocity = player.Velocity.ToLVector(),
Speed = player.GetPedSpeed(), Speed = player.GetPedSpeed(),
@ -811,7 +863,7 @@ namespace CoopClient
} }
} }
Client.SendMessage(outgoingMessage, messageType, (int)ConnectionChannel.Player); Client.SendMessage(outgoingMessage, messageType, connectionChannel);
Client.FlushSendQueue(); Client.FlushSendQueue();
#if DEBUG #if DEBUG
@ -844,10 +896,9 @@ namespace CoopClient
ModelHash = npc.Model.Hash, ModelHash = npc.Model.Hash,
Clothes = npc.GetPedClothes(), Clothes = npc.GetPedClothes(),
Health = npc.Health, Health = npc.Health,
Position = npc.Position.ToLVector(),
VehModelHash = veh.Model.Hash, VehModelHash = veh.Model.Hash,
VehSeatIndex = (short)npc.SeatIndex, VehSeatIndex = (short)npc.SeatIndex,
VehPosition = veh.Position.ToLVector(), Position = veh.Position.ToLVector(),
VehRotation = veh.Quaternion.ToLQuaternion(), VehRotation = veh.Quaternion.ToLQuaternion(),
VehEngineHealth = veh.EngineHealth, VehEngineHealth = veh.EngineHealth,
VehRPM = veh.CurrentRPM, VehRPM = veh.CurrentRPM,
@ -856,10 +907,9 @@ namespace CoopClient
VehSteeringAngle = veh.SteeringAngle, VehSteeringAngle = veh.SteeringAngle,
VehColors = new byte[] { primaryColor, secondaryColor }, VehColors = new byte[] { primaryColor, secondaryColor },
VehMods = veh.Mods.GetVehicleMods(), VehMods = veh.Mods.GetVehicleMods(),
VehDoors = veh.Doors.GetVehicleDoors(), VehDamageModel = veh.GetVehicleDamageModel(),
VehTires = veh.Wheels.GetBurstedTires(),
VehLandingGear = veh.IsPlane ? (byte)veh.LandingGearState : (byte)0, VehLandingGear = veh.IsPlane ? (byte)veh.LandingGearState : (byte)0,
Flag = veh.GetVehicleFlags() Flag = npc.GetVehicleFlags(veh)
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
} }
else else
@ -880,7 +930,7 @@ namespace CoopClient
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
} }
Client.SendMessage(outgoingMessage, NetDeliveryMethod.Unreliable, (int)ConnectionChannel.NPC); Client.SendMessage(outgoingMessage, NetDeliveryMethod.Unreliable, (byte)ConnectionChannel.NPCFull);
Client.FlushSendQueue(); Client.FlushSendQueue();
#if DEBUG #if DEBUG
@ -894,12 +944,10 @@ namespace CoopClient
internal void SendChatMessage(string message) internal void SendChatMessage(string message)
{ {
NetOutgoingMessage outgoingMessage = Client.CreateMessage(); NetOutgoingMessage outgoingMessage = Client.CreateMessage();
new ChatMessagePacket()
{ new ChatMessagePacket() { Username = Main.MainSettings.Username, Message = message }.PacketToNetOutGoingMessage(outgoingMessage);
Username = Main.MainSettings.Username,
Message = message Client.SendMessage(outgoingMessage, NetDeliveryMethod.ReliableOrdered, (byte)ConnectionChannel.Chat);
}.PacketToNetOutGoingMessage(outgoingMessage);
Client.SendMessage(outgoingMessage, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Chat);
Client.FlushSendQueue(); Client.FlushSendQueue();
#if DEBUG #if DEBUG
@ -921,7 +969,7 @@ namespace CoopClient
CustomPacketID = customID, CustomPacketID = customID,
Bytes = bytes Bytes = bytes
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
Client.SendMessage(outgoingMessage, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Mod); Client.SendMessage(outgoingMessage, NetDeliveryMethod.ReliableOrdered, (byte)ConnectionChannel.Mod);
Client.FlushSendQueue(); Client.FlushSendQueue();
#if DEBUG #if DEBUG

File diff suppressed because it is too large Load Diff

View File

@ -168,48 +168,58 @@ namespace CoopClient
return RaycastEverything(new Vector2(0, 0)); return RaycastEverything(new Vector2(0, 0));
} }
public static byte? GetVehicleFlags(this Vehicle veh) public static ushort? GetVehicleFlags(this Ped ped, Vehicle veh)
{ {
byte? flags = 0; ushort? flags = 0;
if (veh.IsEngineRunning) if (veh.IsEngineRunning)
{ {
flags |= (byte)VehicleDataFlags.IsEngineRunning; flags |= (ushort)VehicleDataFlags.IsEngineRunning;
} }
if (veh.AreLightsOn) if (veh.AreLightsOn)
{ {
flags |= (byte)VehicleDataFlags.AreLightsOn; flags |= (ushort)VehicleDataFlags.AreLightsOn;
} }
if (veh.AreHighBeamsOn) if (veh.AreHighBeamsOn)
{ {
flags |= (byte)VehicleDataFlags.AreHighBeamsOn; flags |= (ushort)VehicleDataFlags.AreHighBeamsOn;
} }
if (veh.IsSirenActive) if (veh.IsSirenActive)
{ {
flags |= (byte)VehicleDataFlags.IsSirenActive; flags |= (ushort)VehicleDataFlags.IsSirenActive;
} }
if (veh.IsDead) if (veh.IsDead)
{ {
flags |= (byte)VehicleDataFlags.IsDead; flags |= (ushort)VehicleDataFlags.IsDead;
} }
if (Function.Call<bool>(Hash.IS_HORN_ACTIVE, veh.Handle)) if (Function.Call<bool>(Hash.IS_HORN_ACTIVE, veh.Handle))
{ {
flags |= (byte)VehicleDataFlags.IsHornActive; flags |= (ushort)VehicleDataFlags.IsHornActive;
} }
if (veh.IsSubmarineCar && Function.Call<bool>(Hash._GET_IS_SUBMARINE_VEHICLE_TRANSFORMED, veh.Handle)) if (veh.IsSubmarineCar && Function.Call<bool>(Hash._GET_IS_SUBMARINE_VEHICLE_TRANSFORMED, veh.Handle))
{ {
flags |= (byte)VehicleDataFlags.IsTransformed; flags |= (ushort)VehicleDataFlags.IsTransformed;
} }
if (veh.HasRoof && (veh.RoofState == VehicleRoofState.Opened || veh.RoofState == VehicleRoofState.Opening)) if (veh.HasRoof && (veh.RoofState == VehicleRoofState.Opened || veh.RoofState == VehicleRoofState.Opening))
{ {
flags |= (byte)VehicleDataFlags.RoofOpened; flags |= (ushort)VehicleDataFlags.RoofOpened;
}
if (veh.IsTurretSeat((int)ped.SeatIndex))
{
flags |= (ushort)VehicleDataFlags.OnTurretSeat;
}
if (veh.IsPlane)
{
flags |= (ushort)VehicleDataFlags.IsPlane;
} }
return flags; return flags;
@ -290,43 +300,103 @@ namespace CoopClient
return result; return result;
} }
public static VehicleDoors[] GetVehicleDoors(this VehicleDoorCollection doors) public static VehicleDamageModel GetVehicleDamageModel(this Vehicle veh)
{ {
int doorLength = doors.ToArray().Length; VehicleDamageModel result = new VehicleDamageModel()
if (doorLength == 0)
{ {
return null; BrokenDoors = 0,
BrokenWindows = 0,
BurstedTires = 0,
PuncturedTires = 0
};
// Broken windows
for (int i = 0; i < 8; i++)
{
if (!veh.Windows[(VehicleWindowIndex)i].IsIntact)
{
result.BrokenWindows |= (byte)(1 << i);
}
} }
VehicleDoors[] result = new VehicleDoors[doorLength]; // Broken doors
for (int i = 0; i < (doorLength - 1); i++) foreach (VehicleDoor door in veh.Doors)
{ {
VehicleDoors currentDoor = new VehicleDoors() if (door.IsBroken)
{ {
AngleRatio = doors[(VehicleDoorIndex)i].AngleRatio, result.BrokenDoors |= (byte)(1 << (byte)door.Index);
Broken = doors[(VehicleDoorIndex)i].IsBroken, }
Open = doors[(VehicleDoorIndex)i].IsOpen, }
FullyOpen = doors[(VehicleDoorIndex)i].IsFullyOpen
}; // Bursted and Punctured tires
result[i] = currentDoor; foreach (VehicleWheel wheel in veh.Wheels.GetAllWheels())
{
if (wheel.IsBursted)
{
result.BurstedTires |= (ushort)(1 << (int)wheel.BoneId);
}
if (wheel.IsPunctured)
{
result.PuncturedTires |= (ushort)(1 << (int)wheel.BoneId);
}
} }
return result; return result;
} }
public static int GetBurstedTires(this VehicleWheelCollection wheels) public static void SetVehicleDamageModel(this Vehicle veh, VehicleDamageModel model, bool leavedoors = true)
{ {
int tireFlag = 0; // Set doors
for (int i = 0; i < 8; i++)
{
if ((model.BrokenDoors & (byte)(1 << i)) != 0)
{
veh.Doors[(VehicleDoorIndex)i].Break(leavedoors);
}
else if (veh.Doors[(VehicleDoorIndex)i].IsBroken)
{
// The vehicle can only fix a door if the vehicle was completely fixed
veh.Repair();
return;
}
foreach (var wheel in wheels.GetAllWheels()) if ((model.BrokenWindows & (byte)(1 << i)) != 0)
{ {
if (wheel.IsBursted) veh.Windows[(VehicleWindowIndex)i].Smash();
}
else if (!veh.Windows[(VehicleWindowIndex)i].IsIntact)
{ {
tireFlag |= (1 << (int)wheel.BoneId); veh.Windows[(VehicleWindowIndex)i].Repair();
} }
} }
return tireFlag; foreach (VehicleWheel wheel in veh.Wheels)
{
if ((model.PuncturedTires & (ushort)(1 << (int)wheel.BoneId)) != 0)
{
if (!wheel.IsPunctured)
{
wheel.Puncture();
}
}
else if (wheel.IsPunctured)
{
wheel.Fix();
}
if ((model.BurstedTires & (ushort)(1 << (int)wheel.BoneId)) != 0)
{
if (!wheel.IsBursted)
{
wheel.Burst();
}
}
else if (wheel.IsBursted)
{
wheel.Fix();
}
}
} }
public static Settings ReadSettings() public static Settings ReadSettings()

106
Server/BitReader.cs Normal file
View File

@ -0,0 +1,106 @@
using System;
using System.Linq;
using System.Text;
namespace CoopServer
{
internal class BitReader
{
public int CurrentIndex { get; set; }
private byte[] ResultArray;
public BitReader(byte[] array)
{
CurrentIndex = 0;
ResultArray = array;
}
~BitReader()
{
ResultArray = null;
}
public bool CanRead(int bytes)
{
return ResultArray.Length >= CurrentIndex + bytes;
}
public bool ReadBool()
{
bool value = BitConverter.ToBoolean(ResultArray, CurrentIndex);
CurrentIndex += 1;
return value;
}
public float ReadFloat()
{
float value = BitConverter.ToSingle(ResultArray, CurrentIndex);
CurrentIndex += 4;
return value;
}
public byte ReadByte()
{
byte value = ResultArray[CurrentIndex];
CurrentIndex += 1;
return value;
}
public byte[] ReadByteArray(int length)
{
byte[] value = ResultArray.Skip(CurrentIndex).Take(length).ToArray();
CurrentIndex += length;
return value;
}
public short ReadShort()
{
short value = BitConverter.ToInt16(ResultArray, CurrentIndex);
CurrentIndex += 2;
return value;
}
public ushort ReadUShort()
{
ushort value = BitConverter.ToUInt16(ResultArray, CurrentIndex);
CurrentIndex += 2;
return value;
}
public int ReadInt()
{
int value = BitConverter.ToInt32(ResultArray, CurrentIndex);
CurrentIndex += 4;
return value;
}
public uint ReadUInt()
{
uint value = BitConverter.ToUInt32(ResultArray, CurrentIndex);
CurrentIndex += 4;
return value;
}
public long ReadLong()
{
long value = BitConverter.ToInt64(ResultArray, CurrentIndex);
CurrentIndex += 8;
return value;
}
public ulong ReadULong()
{
ulong value = BitConverter.ToUInt64(ResultArray, CurrentIndex);
CurrentIndex += 8;
return value;
}
public string ReadString(int index)
{
string value = Encoding.UTF8.GetString(ResultArray.Skip(CurrentIndex).Take(index).ToArray());
CurrentIndex += index;
return value;
}
}
}

View File

@ -65,15 +65,7 @@ namespace CoopServer
return; return;
} }
ChatMessagePacket packet = new() Server.SendChatMessage(from, message, userConnection);
{
Username = from,
Message = message
};
NetOutgoingMessage outgoingMessage = Server.MainNetServer.CreateMessage();
packet.PacketToNetOutGoingMessage(outgoingMessage);
Server.MainNetServer.SendMessage(outgoingMessage, userConnection, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Chat);
} }
catch (Exception e) catch (Exception e)
{ {
@ -81,7 +73,7 @@ namespace CoopServer
} }
} }
public void SendNativeCall(ulong hash, params object[] args) public void SendNativeCall(ulong hash, List<object> args = null)
{ {
try try
{ {
@ -92,27 +84,21 @@ namespace CoopServer
return; return;
} }
List<NativeArgument> arguments = null; if (args != null && args.Count == 0)
if (args != null && args.Length > 0)
{ {
arguments = Util.ParseNativeArguments(args); Logging.Error($"[Client->SendNativeCall(ulong hash, Dictionary<string, object> args)]: Missing arguments!");
if (arguments == null)
{
Logging.Error($"[Client->SendNativeCall(ulong hash, params object[] args)]: Missing arguments!");
return; return;
} }
}
NativeCallPacket packet = new() NativeCallPacket packet = new()
{ {
Hash = hash, Hash = hash,
Args = arguments Args = args ?? new List<object>(),
}; };
NetOutgoingMessage outgoingMessage = Server.MainNetServer.CreateMessage(); NetOutgoingMessage outgoingMessage = Server.MainNetServer.CreateMessage();
packet.PacketToNetOutGoingMessage(outgoingMessage); packet.PacketToNetOutGoingMessage(outgoingMessage);
Server.MainNetServer.SendMessage(outgoingMessage, userConnection, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Native); Server.MainNetServer.SendMessage(outgoingMessage, userConnection, NetDeliveryMethod.ReliableOrdered, (byte)ConnectionChannel.Native);
} }
catch (Exception e) catch (Exception e)
{ {
@ -120,7 +106,7 @@ namespace CoopServer
} }
} }
public void SendNativeResponse(Action<object> callback, ulong hash, Type type, params object[] args) public void SendNativeResponse(Action<object> callback, ulong hash, Type returnType, List<object> args = null)
{ {
try try
{ {
@ -131,59 +117,51 @@ namespace CoopServer
return; return;
} }
NativeArgument returnType = null; if (args != null && args.Count == 0)
Type typeOf = type;
if (typeOf == typeof(int))
{ {
returnType = new IntArgument(); Logging.Error($"[Client->SendNativeCall(ulong hash, Dictionary<string, object> args)]: Missing arguments!");
}
else if (typeOf == typeof(bool))
{
returnType = new BoolArgument();
}
else if (typeOf == typeof(float))
{
returnType = new FloatArgument();
}
else if (typeOf == typeof(string))
{
returnType = new StringArgument();
}
else if (typeOf == typeof(LVector3))
{
returnType = new LVector3Argument();
}
else
{
Logging.Error($"[Client->SendNativeResponse(Action<object> callback, ulong hash, Type type, params object[] args)]: Argument does not exist!");
return; return;
} }
List<NativeArgument> arguments = null;
if (args != null && args.Length > 0)
{
arguments = Util.ParseNativeArguments(args);
if (arguments == null)
{
Logging.Error($"[Client->SendNativeResponse(Action<object> callback, ulong hash, Type type, params object[] args)]: One or more arguments do not exist!");
return;
}
}
long id = 0; long id = 0;
Callbacks.Add(id = Environment.TickCount64, callback); Callbacks.Add(id = Environment.TickCount64, callback);
NativeResponsePacket packet = new() byte returnTypeValue = 0x00;
if (returnType == typeof(int))
{ {
Hash = hash, // NOTHING BECAUSE VALUE IS 0x00
Args = arguments, }
Type = returnType, else if (returnType == typeof(bool))
NetHandle = id {
}; returnTypeValue = 0x01;
}
else if (returnType == typeof(float))
{
returnTypeValue = 0x02;
}
else if (returnType == typeof(string))
{
returnTypeValue = 0x03;
}
else if (returnType == typeof(LVector3))
{
returnTypeValue = 0x04;
}
else
{
Logging.Error($"[Client->SendNativeCall(ulong hash, Dictionary<string, object> args)]: Missing return type!");
return;
}
NetOutgoingMessage outgoingMessage = Server.MainNetServer.CreateMessage(); NetOutgoingMessage outgoingMessage = Server.MainNetServer.CreateMessage();
packet.PacketToNetOutGoingMessage(outgoingMessage); new NativeResponsePacket()
Server.MainNetServer.SendMessage(outgoingMessage, userConnection, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Native); {
Hash = hash,
Args = args ?? new List<object>(),
ResultType = returnTypeValue,
ID = id
}.PacketToNetOutGoingMessage(outgoingMessage);
Server.MainNetServer.SendMessage(outgoingMessage, userConnection, NetDeliveryMethod.ReliableOrdered, (byte)ConnectionChannel.Native);
} }
catch (Exception e) catch (Exception e)
{ {
@ -210,7 +188,7 @@ namespace CoopServer
CustomPacketID = customID, CustomPacketID = customID,
Bytes = bytes Bytes = bytes
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
Server.MainNetServer.SendMessage(outgoingMessage, userConnection, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Mod); Server.MainNetServer.SendMessage(outgoingMessage, userConnection, NetDeliveryMethod.ReliableOrdered, (byte)ConnectionChannel.Mod);
Server.MainNetServer.FlushSendQueue(); Server.MainNetServer.FlushSendQueue();
} }
catch (Exception e) catch (Exception e)

View File

@ -15,9 +15,6 @@
<Reference Include="Newtonsoft.Json"> <Reference Include="Newtonsoft.Json">
<HintPath>..\Libs\Release\scripts\Newtonsoft.Json.dll</HintPath> <HintPath>..\Libs\Release\scripts\Newtonsoft.Json.dll</HintPath>
</Reference> </Reference>
<Reference Include="protobuf-net">
<HintPath>..\Libs\Release\scripts\protobuf-net.dll</HintPath>
</Reference>
</ItemGroup> </ItemGroup>
</Project> </Project>

File diff suppressed because it is too large Load Diff

View File

@ -22,7 +22,7 @@ namespace CoopServer
internal class Server internal class Server
{ {
private static readonly string CompatibleVersion = "V1_2"; private static readonly string CompatibleVersion = "V1_3";
public static readonly Settings MainSettings = Util.Read<Settings>("CoopSettings.xml"); public static readonly Settings MainSettings = Util.Read<Settings>("CoopSettings.xml");
private readonly Blocklist MainBlocklist = Util.Read<Blocklist>("Blocklist.xml"); private readonly Blocklist MainBlocklist = Util.Read<Blocklist>("Blocklist.xml");
@ -237,10 +237,13 @@ namespace CoopServer
{ {
try try
{ {
Packet approvalPacket; int len = message.ReadInt32();
approvalPacket = new HandshakePacket(); byte[] data = message.ReadBytes(len);
approvalPacket.NetIncomingMessageToPacket(message);
GetHandshake(message.SenderConnection, (HandshakePacket)approvalPacket); HandshakePacket packet = new HandshakePacket();
packet.NetIncomingMessageToPacket(data);
GetHandshake(message.SenderConnection, packet);
} }
catch (Exception e) catch (Exception e)
{ {
@ -265,79 +268,111 @@ namespace CoopServer
// Get packet type // Get packet type
byte type = message.ReadByte(); byte type = message.ReadByte();
// Create packet
Packet packet;
switch (type) switch (type)
{ {
case (byte)PacketTypes.FullSyncPlayerPacket: case (byte)PacketTypes.FullSyncPlayerPacket:
{
try try
{ {
packet = new FullSyncPlayerPacket(); int len = message.ReadInt32();
packet.NetIncomingMessageToPacket(message); byte[] data = message.ReadBytes(len);
FullSyncPlayer((FullSyncPlayerPacket)packet);
FullSyncPlayerPacket packet = new FullSyncPlayerPacket();
packet.NetIncomingMessageToPacket(data);
FullSyncPlayer(packet);
} }
catch (Exception e) catch (Exception e)
{ {
message.SenderConnection.Disconnect(e.Message); message.SenderConnection.Disconnect(e.Message);
} }
}
break; break;
case (byte)PacketTypes.FullSyncPlayerVehPacket: case (byte)PacketTypes.FullSyncPlayerVehPacket:
{
try try
{ {
packet = new FullSyncPlayerVehPacket(); int len = message.ReadInt32();
packet.NetIncomingMessageToPacket(message); byte[] data = message.ReadBytes(len);
FullSyncPlayerVeh((FullSyncPlayerVehPacket)packet);
FullSyncPlayerVehPacket packet = new FullSyncPlayerVehPacket();
packet.NetIncomingMessageToPacket(data);
FullSyncPlayerVeh(packet);
} }
catch (Exception e) catch (Exception e)
{ {
message.SenderConnection.Disconnect(e.Message); message.SenderConnection.Disconnect(e.Message);
} }
}
break; break;
case (byte)PacketTypes.LightSyncPlayerPacket: case (byte)PacketTypes.LightSyncPlayerPacket:
{
try try
{ {
packet = new LightSyncPlayerPacket(); int len = message.ReadInt32();
packet.NetIncomingMessageToPacket(message); byte[] data = message.ReadBytes(len);
LightSyncPlayer((LightSyncPlayerPacket)packet);
LightSyncPlayerPacket packet = new LightSyncPlayerPacket();
packet.NetIncomingMessageToPacket(data);
LightSyncPlayer(packet);
} }
catch (Exception e) catch (Exception e)
{ {
message.SenderConnection.Disconnect(e.Message); message.SenderConnection.Disconnect(e.Message);
} }
}
break; break;
case (byte)PacketTypes.LightSyncPlayerVehPacket: case (byte)PacketTypes.LightSyncPlayerVehPacket:
{
try try
{ {
packet = new LightSyncPlayerVehPacket(); int len = message.ReadInt32();
packet.NetIncomingMessageToPacket(message); byte[] data = message.ReadBytes(len);
LightSyncPlayerVeh((LightSyncPlayerVehPacket)packet);
LightSyncPlayerVehPacket packet = new LightSyncPlayerVehPacket();
packet.NetIncomingMessageToPacket(data);
LightSyncPlayerVeh(packet);
} }
catch (Exception e) catch (Exception e)
{ {
message.SenderConnection.Disconnect(e.Message); message.SenderConnection.Disconnect(e.Message);
} }
}
break; break;
case (byte)PacketTypes.ChatMessagePacket: case (byte)PacketTypes.ChatMessagePacket:
{
try try
{ {
packet = new ChatMessagePacket(); int len = message.ReadInt32();
packet.NetIncomingMessageToPacket(message); byte[] data = message.ReadBytes(len);
SendChatMessage((ChatMessagePacket)packet);
ChatMessagePacket packet = new ChatMessagePacket();
packet.NetIncomingMessageToPacket(data);
SendChatMessage(packet);
} }
catch (Exception e) catch (Exception e)
{ {
message.SenderConnection.Disconnect(e.Message); message.SenderConnection.Disconnect(e.Message);
} }
}
break; break;
case (byte)PacketTypes.FullSyncNpcPacket: case (byte)PacketTypes.FullSyncNpcPacket:
{
if (MainSettings.NpcsAllowed) if (MainSettings.NpcsAllowed)
{ {
try try
{ {
packet = new FullSyncNpcPacket(); int len = message.ReadInt32();
packet.NetIncomingMessageToPacket(message); byte[] data = message.ReadBytes(len);
FullSyncNpc(message.SenderConnection, (FullSyncNpcPacket)packet);
FullSyncNpcPacket packet = new FullSyncNpcPacket();
packet.NetIncomingMessageToPacket(data);
FullSyncNpc(message.SenderConnection, packet);
} }
catch (Exception e) catch (Exception e)
{ {
@ -348,15 +383,21 @@ namespace CoopServer
{ {
message.SenderConnection.Disconnect("Npcs are not allowed!"); message.SenderConnection.Disconnect("Npcs are not allowed!");
} }
}
break; break;
case (byte)PacketTypes.FullSyncNpcVehPacket: case (byte)PacketTypes.FullSyncNpcVehPacket:
{
if (MainSettings.NpcsAllowed) if (MainSettings.NpcsAllowed)
{ {
try try
{ {
packet = new FullSyncNpcVehPacket(); int len = message.ReadInt32();
packet.NetIncomingMessageToPacket(message); byte[] data = message.ReadBytes(len);
FullSyncNpcVeh(message.SenderConnection, (FullSyncNpcVehPacket)packet);
FullSyncNpcVehPacket packet = new FullSyncNpcVehPacket();
packet.NetIncomingMessageToPacket(data);
FullSyncNpcVeh(message.SenderConnection, packet);
} }
catch (Exception e) catch (Exception e)
{ {
@ -367,44 +408,25 @@ namespace CoopServer
{ {
message.SenderConnection.Disconnect("Npcs are not allowed!"); message.SenderConnection.Disconnect("Npcs are not allowed!");
} }
}
break; break;
case (byte)PacketTypes.NativeResponsePacket: case (byte)PacketTypes.NativeResponsePacket:
{ {
try try
{ {
packet = new NativeResponsePacket(); int len = message.ReadInt32();
packet.NetIncomingMessageToPacket(message); byte[] data = message.ReadBytes(len);
NativeResponsePacket responsePacket = (NativeResponsePacket)packet;
NativeResponsePacket packet = new NativeResponsePacket();
packet.NetIncomingMessageToPacket(data);
Client client = Clients.Find(x => x.NetHandle == message.SenderConnection.RemoteUniqueIdentifier); Client client = Clients.Find(x => x.NetHandle == message.SenderConnection.RemoteUniqueIdentifier);
if (client != null) if (client != null)
{ {
if (client.Callbacks.ContainsKey(responsePacket.NetHandle)) if (client.Callbacks.ContainsKey(packet.ID))
{ {
object resp = null; client.Callbacks[packet.ID].Invoke(packet.Args[0]);
if (responsePacket.Type is IntArgument argument) client.Callbacks.Remove(packet.ID);
{
resp = argument.Data;
}
else if (responsePacket.Type is StringArgument argument1)
{
resp = argument1.Data;
}
else if (responsePacket.Type is FloatArgument argument2)
{
resp = argument2.Data;
}
else if (responsePacket.Type is BoolArgument argument3)
{
resp = argument3.Data;
}
else if (responsePacket.Type is LVector3Argument argument4)
{
resp = argument4.Data;
}
client.Callbacks[responsePacket.NetHandle].Invoke(resp);
client.Callbacks.Remove(responsePacket.NetHandle);
} }
} }
} }
@ -415,48 +437,51 @@ namespace CoopServer
} }
break; break;
case (byte)PacketTypes.ModPacket: case (byte)PacketTypes.ModPacket:
{
if (MainSettings.ModsAllowed) if (MainSettings.ModsAllowed)
{ {
try try
{ {
packet = new ModPacket(); int len = message.ReadInt32();
packet.NetIncomingMessageToPacket(message); byte[] data = message.ReadBytes(len);
ModPacket modPacket = (ModPacket)packet;
ModPacket packet = new ModPacket();
packet.NetIncomingMessageToPacket(data);
bool resourceResult = false; bool resourceResult = false;
if (Resources.Any()) if (Resources.Any())
{ {
Resources.ForEach(x => Resources.ForEach(x =>
{ {
if (x.InvokeModPacketReceived(modPacket.NetHandle, modPacket.Target, modPacket.Mod, modPacket.CustomPacketID, modPacket.Bytes)) if (x.InvokeModPacketReceived(packet.NetHandle, packet.Target, packet.Mod, packet.CustomPacketID, packet.Bytes))
{ {
resourceResult = true; resourceResult = true;
} }
}); });
} }
if (!resourceResult && modPacket.Target != -1) if (!resourceResult && packet.Target != -1)
{ {
NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage(); NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage();
modPacket.PacketToNetOutGoingMessage(outgoingMessage); packet.PacketToNetOutGoingMessage(outgoingMessage);
if (modPacket.Target != 0) if (packet.Target != 0)
{ {
NetConnection target = MainNetServer.Connections.Find(x => x.RemoteUniqueIdentifier == modPacket.Target); NetConnection target = MainNetServer.Connections.Find(x => x.RemoteUniqueIdentifier == packet.Target);
if (target == null) if (target == null)
{ {
Logging.Error($"[ModPacket] target \"{modPacket.Target}\" not found!"); Logging.Error($"[ModPacket] target \"{packet.Target}\" not found!");
} }
else else
{ {
// Send back to target // Send back to target
MainNetServer.SendMessage(outgoingMessage, target, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Mod); MainNetServer.SendMessage(outgoingMessage, target, NetDeliveryMethod.ReliableOrdered, (byte)ConnectionChannel.Mod);
} }
} }
else else
{ {
// Send back to all players // Send back to all players
MainNetServer.SendMessage(outgoingMessage, MainNetServer.Connections, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Mod); MainNetServer.SendMessage(outgoingMessage, MainNetServer.Connections, NetDeliveryMethod.ReliableOrdered, (byte)ConnectionChannel.Mod);
} }
} }
} }
@ -469,6 +494,7 @@ namespace CoopServer
{ {
message.SenderConnection.Disconnect("Mods are not allowed!"); message.SenderConnection.Disconnect("Mods are not allowed!");
} }
}
break; break;
default: default:
Logging.Error("Unhandled Data / Packet type"); Logging.Error("Unhandled Data / Packet type");
@ -598,7 +624,7 @@ namespace CoopServer
NetHandle = localNetHandle, NetHandle = localNetHandle,
Username = string.Empty, Username = string.Empty,
ModVersion = string.Empty, ModVersion = string.Empty,
NpcsAllowed = MainSettings.NpcsAllowed NPCsAllowed = MainSettings.NpcsAllowed
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
// Accept the connection and send back a new handshake packet with the connection ID // Accept the connection and send back a new handshake packet with the connection ID
@ -697,36 +723,36 @@ namespace CoopServer
private static void FullSyncPlayer(FullSyncPlayerPacket packet) private static void FullSyncPlayer(FullSyncPlayerPacket packet)
{ {
Client client = Util.GetClientByNetHandle(packet.Extra.NetHandle); Client client = Util.GetClientByNetHandle(packet.NetHandle);
if (client == null) if (client == null)
{ {
return; return;
} }
client.Player.Position = packet.Extra.Position; // Save the new data
client.Player.Health = packet.Extra.Health; client.Player.Position = packet.Position;
client.Player.Health = packet.Health;
PlayerPacket playerPacket = packet.Extra; // Override the latency
playerPacket.Latency = client.Latency; packet.Latency = client.Latency;
packet.Extra = playerPacket; MainNetServer.Connections.FindAll(x => x.RemoteUniqueIdentifier != packet.NetHandle).ForEach(x =>
MainNetServer.Connections.FindAll(x => x.RemoteUniqueIdentifier != packet.Extra.NetHandle).ForEach(x =>
{ {
NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage(); NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage();
if (Clients.First(y => y.NetHandle == x.RemoteUniqueIdentifier).Player.IsInRangeOf(packet.Position, 550f))
if (Clients.First(y => y.NetHandle == x.RemoteUniqueIdentifier).Player.IsInRangeOf(packet.Extra.Position, 550f))
{ {
packet.PacketToNetOutGoingMessage(outgoingMessage); packet.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (byte)ConnectionChannel.PlayerFull);
} }
else else
{ {
new SuperLightSyncPlayerPacket() new SuperLightSyncPacket()
{ {
Extra = packet.Extra NetHandle = packet.NetHandle,
Position = packet.Position,
Latency = packet.Latency
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (byte)ConnectionChannel.PlayerSuperLight);
} }
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (int)ConnectionChannel.Player);
}); });
if (Resources.Any()) if (Resources.Any())
@ -737,36 +763,37 @@ namespace CoopServer
private static void FullSyncPlayerVeh(FullSyncPlayerVehPacket packet) private static void FullSyncPlayerVeh(FullSyncPlayerVehPacket packet)
{ {
Client client = Util.GetClientByNetHandle(packet.Extra.NetHandle); Client client = Util.GetClientByNetHandle(packet.NetHandle);
if (client == null) if (client == null)
{ {
return; return;
} }
client.Player.Position = packet.Extra.Position; // Save the new data
client.Player.Health = packet.Extra.Health; client.Player.Position = packet.Position;
client.Player.Health = packet.Health;
PlayerPacket playerPacket = packet.Extra; // Override the latency
playerPacket.Latency = client.Latency; packet.Latency = client.Latency;
packet.Extra = playerPacket; MainNetServer.Connections.FindAll(x => x.RemoteUniqueIdentifier != packet.NetHandle).ForEach(x =>
MainNetServer.Connections.FindAll(x => x.RemoteUniqueIdentifier != packet.Extra.NetHandle).ForEach(x =>
{ {
NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage(); NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage();
if (Clients.First(y => y.NetHandle == x.RemoteUniqueIdentifier).Player.IsInRangeOf(packet.Extra.Position, 550f)) if (Clients.First(y => y.NetHandle == x.RemoteUniqueIdentifier).Player.IsInRangeOf(packet.Position, 550f))
{ {
packet.PacketToNetOutGoingMessage(outgoingMessage); packet.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (byte)ConnectionChannel.PlayerFull);
} }
else else
{ {
new SuperLightSyncPlayerPacket() new SuperLightSyncPacket()
{ {
Extra = packet.Extra NetHandle = packet.NetHandle,
Position = packet.Position,
Latency = packet.Latency
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (byte)ConnectionChannel.PlayerSuperLight);
} }
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (int)ConnectionChannel.Player);
}); });
if (Resources.Any()) if (Resources.Any())
@ -777,36 +804,37 @@ namespace CoopServer
private static void LightSyncPlayer(LightSyncPlayerPacket packet) private static void LightSyncPlayer(LightSyncPlayerPacket packet)
{ {
Client client = Util.GetClientByNetHandle(packet.Extra.NetHandle); Client client = Util.GetClientByNetHandle(packet.NetHandle);
if (client == null) if (client == null)
{ {
return; return;
} }
client.Player.Position = packet.Extra.Position; // Save the new data
client.Player.Health = packet.Extra.Health; client.Player.Position = packet.Position;
client.Player.Health = packet.Health;
PlayerPacket playerPacket = packet.Extra; // Override the latency
playerPacket.Latency = client.Latency; packet.Latency = client.Latency;
packet.Extra = playerPacket; MainNetServer.Connections.FindAll(x => x.RemoteUniqueIdentifier != packet.NetHandle).ForEach(x =>
MainNetServer.Connections.FindAll(x => x.RemoteUniqueIdentifier != packet.Extra.NetHandle).ForEach(x =>
{ {
NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage(); NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage();
if (Clients.First(y => y.NetHandle == x.RemoteUniqueIdentifier).Player.IsInRangeOf(packet.Extra.Position, 550f)) if (Clients.First(y => y.NetHandle == x.RemoteUniqueIdentifier).Player.IsInRangeOf(packet.Position, 550f))
{ {
packet.PacketToNetOutGoingMessage(outgoingMessage); packet.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (byte)ConnectionChannel.PlayerLight);
} }
else else
{ {
new SuperLightSyncPlayerPacket() new SuperLightSyncPacket()
{ {
Extra = packet.Extra NetHandle = packet.NetHandle,
Position = packet.Position,
Latency = packet.Latency
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (byte)ConnectionChannel.PlayerSuperLight);
} }
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (int)ConnectionChannel.Player);
}); });
if (Resources.Any()) if (Resources.Any())
@ -817,36 +845,37 @@ namespace CoopServer
private static void LightSyncPlayerVeh(LightSyncPlayerVehPacket packet) private static void LightSyncPlayerVeh(LightSyncPlayerVehPacket packet)
{ {
Client client = Util.GetClientByNetHandle(packet.Extra.NetHandle); Client client = Util.GetClientByNetHandle(packet.NetHandle);
if (client == null) if (client == null)
{ {
return; return;
} }
client.Player.Position = packet.Extra.Position; // Save the new data
client.Player.Health = packet.Extra.Health; client.Player.Position = packet.Position;
client.Player.Health = packet.Health;
PlayerPacket playerPacket = packet.Extra; // Override the latency
playerPacket.Latency = client.Latency; packet.Latency = client.Latency;
packet.Extra = playerPacket; MainNetServer.Connections.FindAll(x => x.RemoteUniqueIdentifier != packet.NetHandle).ForEach(x =>
MainNetServer.Connections.FindAll(x => x.RemoteUniqueIdentifier != packet.Extra.NetHandle).ForEach(x =>
{ {
NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage(); NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage();
if (Clients.First(y => y.NetHandle == x.RemoteUniqueIdentifier).Player.IsInRangeOf(packet.Extra.Position, 550f)) if (Clients.First(y => y.NetHandle == x.RemoteUniqueIdentifier).Player.IsInRangeOf(packet.Position, 550f))
{ {
packet.PacketToNetOutGoingMessage(outgoingMessage); packet.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (byte)ConnectionChannel.PlayerLight);
} }
else else
{ {
new SuperLightSyncPlayerPacket() new SuperLightSyncPacket()
{ {
Extra = packet.Extra NetHandle = packet.NetHandle,
Position = packet.Position,
Latency = packet.Latency
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (byte)ConnectionChannel.PlayerSuperLight);
} }
MainNetServer.SendMessage(outgoingMessage, x, NetDeliveryMethod.UnreliableSequenced, (int)ConnectionChannel.Player);
}); });
if (Resources.Any()) if (Resources.Any())
@ -858,8 +887,6 @@ namespace CoopServer
// Send a message to targets or all players // Send a message to targets or all players
private static void SendChatMessage(ChatMessagePacket packet, List<NetConnection> targets = null) private static void SendChatMessage(ChatMessagePacket packet, List<NetConnection> targets = null)
{ {
NetOutgoingMessage outgoingMessage;
if (Resources.Any()) if (Resources.Any())
{ {
if (packet.Message.StartsWith('/')) if (packet.Message.StartsWith('/'))
@ -886,13 +913,7 @@ namespace CoopServer
return; return;
} }
outgoingMessage = MainNetServer.CreateMessage(); SendChatMessage("Server", command.Key.Usage, userConnection);
new ChatMessagePacket()
{
Username = "Server",
Message = command.Key.Usage
}.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, userConnection, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Chat);
return; return;
} }
@ -906,13 +927,7 @@ namespace CoopServer
return; return;
} }
outgoingMessage = MainNetServer.CreateMessage(); SendChatMessage("Server", "Command not found!", userConnection);
new ChatMessagePacket()
{
Username = "Server",
Message = "Command not found!"
}.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, userConnection, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Chat);
} }
return; return;
@ -938,12 +953,23 @@ namespace CoopServer
packet.Message = packet.Message.Replace("~", ""); packet.Message = packet.Message.Replace("~", "");
outgoingMessage = MainNetServer.CreateMessage(); SendChatMessage(packet.Username, packet.Message, targets);
packet.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, targets ?? MainNetServer.Connections, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Chat);
Logging.Info(packet.Username + ": " + packet.Message); Logging.Info(packet.Username + ": " + packet.Message);
} }
internal static void SendChatMessage(string username, string message, List<NetConnection> targets = null)
{
NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage();
new ChatMessagePacket() { Username = username, Message = message }.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, targets ?? MainNetServer.Connections, NetDeliveryMethod.ReliableOrdered, (byte)ConnectionChannel.Chat);
}
internal static void SendChatMessage(string username, string message, NetConnection target)
{
SendChatMessage(username, message, new List<NetConnection>() { target });
}
#endregion #endregion
#region -- NPC -- #region -- NPC --
@ -957,7 +983,7 @@ namespace CoopServer
NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage(); NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage();
packet.PacketToNetOutGoingMessage(outgoingMessage); packet.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, clients, NetDeliveryMethod.UnreliableSequenced, (int)ConnectionChannel.NPC); MainNetServer.SendMessage(outgoingMessage, clients, NetDeliveryMethod.UnreliableSequenced, (byte)ConnectionChannel.NPCFull);
} }
private static void FullSyncNpcVeh(NetConnection local, FullSyncNpcVehPacket packet) private static void FullSyncNpcVeh(NetConnection local, FullSyncNpcVehPacket packet)
@ -970,7 +996,7 @@ namespace CoopServer
NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage(); NetOutgoingMessage outgoingMessage = MainNetServer.CreateMessage();
packet.PacketToNetOutGoingMessage(outgoingMessage); packet.PacketToNetOutGoingMessage(outgoingMessage);
MainNetServer.SendMessage(outgoingMessage, clients, NetDeliveryMethod.UnreliableSequenced, (int)ConnectionChannel.NPC); MainNetServer.SendMessage(outgoingMessage, clients, NetDeliveryMethod.UnreliableSequenced, (byte)ConnectionChannel.NPCFull);
} }
#endregion #endregion

View File

@ -261,7 +261,7 @@ namespace CoopServer
CustomPacketID = customID, CustomPacketID = customID,
Bytes = bytes Bytes = bytes
}.PacketToNetOutGoingMessage(outgoingMessage); }.PacketToNetOutGoingMessage(outgoingMessage);
Server.MainNetServer.SendMessage(outgoingMessage, connections, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Mod); Server.MainNetServer.SendMessage(outgoingMessage, connections, NetDeliveryMethod.ReliableOrdered, (byte)ConnectionChannel.Mod);
Server.MainNetServer.FlushSendQueue(); Server.MainNetServer.FlushSendQueue();
} }
catch (Exception e) catch (Exception e)
@ -271,11 +271,12 @@ namespace CoopServer
} }
/// <summary> /// <summary>
/// Send a native call (Function.Call) to all players /// Send a native call (Function.Call) to all players.
/// Keys = int, float, bool, string and lvector3
/// </summary> /// </summary>
/// <param name="hash">The hash (Example: 0x25223CA6B4D20B7F = GET_CLOCK_HOURS)</param> /// <param name="hash">The hash (Example: 0x25223CA6B4D20B7F = GET_CLOCK_HOURS)</param>
/// <param name="args">The arguments (Example: "Function.Call(Hash.SET_TIME_SCALE, args);")</param> /// <param name="args">The arguments (Example: string = int, object = 5)</param>
public static void SendNativeCallToAll(ulong hash, params object[] args) public static void SendNativeCallToAll(ulong hash, List<object> args = null)
{ {
try try
{ {
@ -284,22 +285,21 @@ namespace CoopServer
return; return;
} }
List<NativeArgument> arguments = Util.ParseNativeArguments(args); if (args != null && args.Count == 0)
if (arguments == null)
{ {
Logging.Error($"[ServerScript->SendNativeCallToAll(ulong hash, params object[] args)]: One or more arguments do not exist!"); Logging.Error($"[ServerScript->SendNativeCallToAll(ulong hash, params object[] args)]: args is not null!");
return; return;
} }
NativeCallPacket packet = new() NativeCallPacket packet = new()
{ {
Hash = hash, Hash = hash,
Args = arguments Args = args ?? new List<object>()
}; };
NetOutgoingMessage outgoingMessage = Server.MainNetServer.CreateMessage(); NetOutgoingMessage outgoingMessage = Server.MainNetServer.CreateMessage();
packet.PacketToNetOutGoingMessage(outgoingMessage); packet.PacketToNetOutGoingMessage(outgoingMessage);
Server.MainNetServer.SendMessage(outgoingMessage, Server.MainNetServer.Connections, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Native); Server.MainNetServer.SendMessage(outgoingMessage, Server.MainNetServer.Connections, NetDeliveryMethod.ReliableOrdered, (byte)ConnectionChannel.Native);
} }
catch (Exception e) catch (Exception e)
{ {
@ -354,13 +354,7 @@ namespace CoopServer
? Server.MainNetServer.Connections ? Server.MainNetServer.Connections
: Server.MainNetServer.Connections.FindAll(c => netHandleList.Contains(c.RemoteUniqueIdentifier)); : Server.MainNetServer.Connections.FindAll(c => netHandleList.Contains(c.RemoteUniqueIdentifier));
NetOutgoingMessage outgoingMessage = Server.MainNetServer.CreateMessage(); Server.SendChatMessage(username, message, connections);
new ChatMessagePacket()
{
Username = username,
Message = message
}.PacketToNetOutGoingMessage(outgoingMessage);
Server.MainNetServer.SendMessage(outgoingMessage, connections, NetDeliveryMethod.ReliableOrdered, (int)ConnectionChannel.Chat);
} }
catch (Exception e) catch (Exception e)
{ {

View File

@ -10,48 +10,6 @@ namespace CoopServer
{ {
internal class Util internal class Util
{ {
public static List<NativeArgument> ParseNativeArguments(params object[] args)
{
List<NativeArgument> result = null;
if (args != null && args.Length > 0)
{
result = new();
foreach (object arg in args)
{
Type typeOf = arg.GetType();
if (typeOf == typeof(int))
{
result.Add(new IntArgument() { Data = (int)arg });
}
else if (typeOf == typeof(bool))
{
result.Add(new BoolArgument() { Data = (bool)arg });
}
else if (typeOf == typeof(float))
{
result.Add(new FloatArgument() { Data = (float)arg });
}
else if (typeOf == typeof(string))
{
result.Add(new StringArgument() { Data = (string)arg });
}
else if (typeOf == typeof(LVector3))
{
result.Add(new LVector3Argument() { Data = (LVector3)arg });
}
else
{
return null;
}
}
}
return result;
}
public static Client GetClientByNetHandle(long netHandle) public static Client GetClientByNetHandle(long netHandle)
{ {
Client result = Server.Clients.Find(x => x.NetHandle == netHandle); Client result = Server.Clients.Find(x => x.NetHandle == netHandle);