using Barotrauma.Networking; using Microsoft.Xna.Framework; using System; namespace Barotrauma.Items.Components { partial class Wire : ItemComponent, IDrawableComponent, IServerSerializable { private readonly struct ServerEventData : IEventData { public readonly int EventIndex; public ServerEventData(int eventIndex) { EventIndex = eventIndex; } } public void CreateNetworkEvent() { if (GameMain.Server == null) return; //split into multiple events because one might not be enough to fit all the nodes int eventCount = Math.Max((int)Math.Ceiling(nodes.Count / (float)MaxNodesPerNetworkEvent), 1); for (int i = 0; i < eventCount; i++) { item.CreateServerEvent(this, new ServerEventData(i)); } } public override bool ValidateEventData(NetEntityEvent.IData data) => TryExtractEventData(data, out _); public void ServerEventWrite(IWriteMessage msg, Client c, NetEntityEvent.IData extraData = null) { var eventData = ExtractEventData(extraData); int eventIndex = eventData.EventIndex; int nodeStartIndex = eventIndex * MaxNodesPerNetworkEvent; int nodeCount = MathHelper.Clamp(nodes.Count - nodeStartIndex, 0, MaxNodesPerNetworkEvent); msg.WriteRangedInteger(eventIndex, 0, (int)Math.Ceiling(MaxNodeCount / (float)MaxNodesPerNetworkEvent)); msg.WriteRangedInteger(nodeCount, 0, MaxNodesPerNetworkEvent); for (int i = nodeStartIndex; i < nodeStartIndex + nodeCount; i++) { msg.WriteSingle(nodes[i].X); msg.WriteSingle(nodes[i].Y); } } public void ServerEventRead(IReadMessage msg, Client c) { int nodeCount = msg.ReadByte(); Vector2 lastNodePos = Vector2.Zero; if (nodeCount > 0) { lastNodePos = new Vector2(msg.ReadSingle(), msg.ReadSingle()); } if (!item.CanClientAccess(c)) { return; } if (nodes.Count > nodeCount) { nodes.RemoveRange(nodeCount, nodes.Count - nodeCount); } if (nodeCount > 0) { if (nodeCount > nodes.Count) { nodes.Add(lastNodePos); } else { nodes[nodes.Count - 1] = lastNodePos; } } CreateNetworkEvent(); } } }