コード例 #1
0
        public void ApplyWorldState(WorldState ws)
        {
            List <IBaseEntity> tempents = new List <IBaseEntity>();

            {
                BitStream local = Data.Clone();
                local.Cursor = 0;

                TempEntity e = null;
                for (int i = 0; i < EntryCount; i++)
                {
                    double delay = 0;
                    if (local.ReadBool())
                    {
                        delay = local.ReadInt(8) / 100.0;
                    }

                    if (local.ReadBool())
                    {
                        uint classID = local.ReadUInt(ws.ClassBits);

                        ServerClass serverClass = ws.ServerClasses[(int)classID - 1];
                        SendTable   sendTable   = ws.SendTables.Single(st => st.NetTableName == serverClass.DatatableName);
                        var         flattened   = sendTable.FlattenedProps;

                        e = new TempEntity(ws, serverClass, sendTable);
                        EntityCoder.ApplyEntityUpdate(e, local);
                        tempents.Add(e);
                    }
                    else
                    {
                        Debug.Assert(e != null);
                        EntityCoder.ApplyEntityUpdate(e, local);
                    }
                }
            }

            foreach (IBaseEntity te in tempents)
            {
                ws.Listeners.TempEntityCreated.Invoke(te);
            }
        }
コード例 #2
0
        Entity ReadEnterPVS(WorldState ws, BitStream stream, uint entityIndex)
        {
            ServerClass serverClass  = ws.ServerClasses[(int)stream.ReadUInt(ws.ClassBits)];
            SendTable   networkTable = ws.SendTables.Single(st => st.NetTableName == serverClass.DatatableName);
            uint        serialNumber = stream.ReadUInt(SourceConstants.NUM_NETWORKED_EHANDLE_SERIAL_NUMBER_BITS);

            Entity e;
            {
                Entity existing = ws.Entities[entityIndex];
                e = (existing == null || existing.SerialNumber != serialNumber) ?
                    new Entity(ws, serverClass, networkTable, entityIndex, serialNumber) :
                    existing;
            }

            var decodedBaseline = ws.InstanceBaselines[(int)Baseline.Value][entityIndex];

            if (decodedBaseline != null)
            {
                var propertiesToAdd =
                    decodedBaseline
                    .Except(e.Properties, SendPropDefinitionComparer.Instance)
                    .Select(sp => sp.Clone(e));

                foreach (var p2a in propertiesToAdd)
                {
                    e.AddProperty(p2a);
                }
            }
            else
            {
                BitStream baseline = ws.StaticBaselines.SingleOrDefault(bl => bl.Key == e.Class).Value;
                if (baseline != null)
                {
                    baseline.Cursor = 0;
                    EntityCoder.ApplyEntityUpdate(e, baseline);
                    Debug.Assert((baseline.Length - baseline.Cursor) < 8);
                }
            }

            return(e);
        }
コード例 #3
0
        public void ApplyWorldState(WorldState ws)
        {
            if (ws.SignonState.State == ConnectionState.Spawn)
            {
                if (!IsDelta)
                {
                    // We are done with signon sequence.
                    ws.SignonState.State = ConnectionState.Full;
                }
                else
                {
                    throw new InvalidOperationException("eceived delta packet entities while spawing!");
                }
            }

            //ClientFrame newFrame = new ClientFrame(ws.Tick);
            //ws.Frames.Add(newFrame);
            //ClientFrame oldFrame = null;
            if (IsDelta)
            {
                if (ws.Tick == (ulong)DeltaFrom.Value)
                {
                    throw new InvalidDataException("Update self-referencing");
                }

                //oldFrame = ws.Frames.Single(f => f.ServerTick == (ulong)DeltaFrom.Value);
            }

            if (UpdateBaseline)
            {
                if (Baseline.Value == BaselineIndex.Baseline0)
                {
                    ws.InstanceBaselines[(int)BaselineIndex.Baseline1] = ws.InstanceBaselines[(int)BaselineIndex.Baseline0];
                    ws.InstanceBaselines[(int)BaselineIndex.Baseline0] = new IList <SendProp> [SourceConstants.MAX_EDICTS];
                }
                else if (Baseline.Value == BaselineIndex.Baseline1)
                {
                    ws.InstanceBaselines[(int)BaselineIndex.Baseline0] = ws.InstanceBaselines[(int)BaselineIndex.Baseline1];
                    ws.InstanceBaselines[(int)BaselineIndex.Baseline1] = new IList <SendProp> [SourceConstants.MAX_EDICTS];
                }
                else
                {
                    throw new ArgumentOutOfRangeException(nameof(Baseline));
                }
            }

            Data.Seek(0, SeekOrigin.Begin);

            int newEntity = -1;

            for (int i = 0; i < UpdatedEntries; i++)
            {
                newEntity += 1 + (int)EntityCoder.ReadUBitVar(Data);

                // Leave PVS flag
                if (!Data.ReadBool())
                {
                    // Enter PVS flag
                    if (Data.ReadBool())
                    {
                        Entity e = ReadEnterPVS(ws, Data, (uint)newEntity);

                        EntityCoder.ApplyEntityUpdate(e, Data);

                        if (ws.Entities[e.Index] != null && !ReferenceEquals(e, ws.Entities[e.Index]))
                        {
                            ws.Entities[e.Index].Dispose();
                        }

                        ws.Entities[e.Index] = e;

                        if (UpdateBaseline)
                        {
                            ws.InstanceBaselines[Baseline.Value == BaselineIndex.Baseline0 ? 1 : 0][e.Index] = new List <SendProp>(e.Properties.Select(sp => sp.Clone()));
                        }

                        e.InPVS = true;
                    }
                    else
                    {
                        // Preserve/update
                        Entity e = ws.Entities[(uint)newEntity];                        // ws.Entities.Single(ent => ent.Index == newEntity);
                        EntityCoder.ApplyEntityUpdate(e, Data);
                    }
                }
                else
                {
                    bool shouldDelete = Data.ReadBool();

                    Entity e = ws.Entities[newEntity];
                    if (e != null)
                    {
                        e.InPVS = false;
                    }

                    ReadLeavePVS(ws, newEntity, shouldDelete);
                }
            }

            if (IsDelta)
            {
                // Read explicit deletions
                while (Data.ReadBool())
                {
                    uint ent = Data.ReadUInt(SourceConstants.MAX_EDICT_BITS);

                    //Debug.Assert(ws.Entities[ent] != null);
                    if (ws.Entities[ent] != null)
                    {
                        ws.Entities[ent].Dispose();
                    }

                    ws.Entities[ent] = null;
                }
            }

            //Console.WriteLine("Parsed {0}", Description);
        }