Exemplo n.º 1
0
        public static void Postfix(SubFire __instance, SubFire.RoomFire startInRoom, bool __state)
        {
            // Spent way too much time trying to get around a bug in dnspy that doesn't allow me to propery edit this method, so I'm going with the hacky solution.
            // Every time a Fire is created, the whole list of SubFire.availableNodes is cleared, then populated with any transforms that have 0 childCount.
            // Next, it chooses a random index, then spawns a fire in that node.
            // We can easily find where it is because it'll be the only Transform in SubFire.availableNodes with a childCount > 0
            if (__state)
            {
                List <Transform> availableNodes = (List <Transform>)__instance.ReflectionGet("availableNodes");
                Dictionary <CyclopsRooms, SubFire.RoomFire> roomFiresDict = (Dictionary <CyclopsRooms, SubFire.RoomFire>)__instance.ReflectionGet("roomFires");

                foreach (Transform transform in availableNodes)
                {
                    if (transform.childCount > 0)
                    {
                        int  nodeIndex = Array.IndexOf(roomFiresDict[startInRoom.roomLinks.room].spawnNodes, transform);
                        Fire fire      = transform.GetComponentInChildren <Fire>();
                        NitroxServiceLocator.LocateService <Fires>().OnCreate(transform.GetComponentInChildren <Fire>(), startInRoom, nodeIndex);
                        return;
                    }
                }
            }
        }
Exemplo n.º 2
0
        /// <summary>
        /// Create a new <see cref="Fire"/>. Majority of code copied from <see cref="SubFire.CreateFire(SubFire.RoomFire)"/>. Currently does not support Fires created outside of a Cyclops
        /// </summary>
        /// <param name="fireGuid">Guid of the Fire. Used for identification when dousing the fire</param>
        /// <param name="subRootGuid">Guid of the Cyclops <see cref="SubRoot"/></param>
        /// <param name="room">The room the Fire will be spawned in</param>
        /// <param name="spawnNodeIndex">Each <see cref="CyclopsRooms"/> has multiple static Fire spawn points called spawnNodes. If the wrong index is provided,
        ///     the clients will see fires in different places from the owner</param>
        public void Create(CyclopsFireData fireData)
        {
            SubFire subFire = GuidHelper.RequireObjectFrom(fireData.CyclopsGuid).GetComponent <SubRoot>().damageManager.subFire;
            Dictionary <CyclopsRooms, SubFire.RoomFire> roomFiresDict = (Dictionary <CyclopsRooms, SubFire.RoomFire>)subFire.ReflectionGet("roomFires");
            // Copied from SubFire_CreateFire_Patch, which copies from SubFire.CreateFire()
            Transform transform2 = roomFiresDict[fireData.Room].spawnNodes[fireData.NodeIndex];

            // If a fire already exists at the node, replace the old Guid with the new one
            if (transform2.childCount > 0)
            {
                Fire existingFire = transform2.GetComponentInChildren <Fire>();

                if (GuidHelper.GetGuid(existingFire.gameObject) != fireData.CyclopsGuid)
                {
                    Log.Error("[Fires.Create Fire already exists at node index " + fireData.NodeIndex
                              + "! Replacing existing Fire Guid " + GuidHelper.GetGuid(existingFire.gameObject)
                              + " with Guid " + fireData.CyclopsGuid
                              + "]");

                    GuidHelper.SetNewGuid(existingFire.gameObject, fireData.CyclopsGuid);
                }

                return;
            }

            List <Transform> availableNodes = (List <Transform>)subFire.ReflectionGet("availableNodes");

            availableNodes.Clear();
            foreach (Transform transform in roomFiresDict[fireData.Room].spawnNodes)
            {
                if (transform.childCount == 0)
                {
                    availableNodes.Add(transform);
                }
            }
            roomFiresDict[fireData.Room].fireValue++;
            PrefabSpawn component = transform2.GetComponent <PrefabSpawn>();

            if (component == null)
            {
                return;
            }
            else
            {
                Log.Error("[FireCreatedProcessor Cannot create new Cyclops fire! PrefabSpawn component could not be found in fire node!"
                          + " Fire Guid: " + fireData.FireGuid
                          + " SubRoot Guid: " + fireData.CyclopsGuid
                          + " Room: " + fireData.Room
                          + " NodeIndex: " + fireData.NodeIndex
                          + "]");
            }
            GameObject gameObject          = component.SpawnManual();
            Fire       componentInChildren = gameObject.GetComponentInChildren <Fire>();

            if (componentInChildren)
            {
                componentInChildren.fireSubRoot = subFire.subRoot;
                GuidHelper.SetNewGuid(componentInChildren.gameObject, fireData.FireGuid);
            }

            subFire.ReflectionSet("roomFires", roomFiresDict);
            subFire.ReflectionSet("availableNodes", availableNodes);
        }
Exemplo n.º 3
0
        /// <summary>
        /// Get all of the index locations of all the fires on the <see cref="SubRoot"/>. <see cref="SubFire.RoomFire.spawnNodes"/> contains
        /// a static list of all possible fire nodes.
        /// </summary>
        private IEnumerable <CyclopsFireData> GetActiveRoomFires(SubFire subFire)
        {
            string subRootGuid = GuidHelper.GetGuid(subFire.subRoot.gameObject);
            Dictionary <CyclopsRooms, SubFire.RoomFire> roomFires = (Dictionary <CyclopsRooms, SubFire.RoomFire>)subFire.ReflectionGet("roomFires");

            foreach (KeyValuePair <CyclopsRooms, SubFire.RoomFire> roomFire in roomFires)
            {
                for (int i = 0; i < roomFire.Value.spawnNodes.Length; i++)
                {
                    if (roomFire.Value.spawnNodes[i].childCount > 0)
                    {
                        yield return(new CyclopsFireData(GuidHelper.GetGuid(roomFire.Value.spawnNodes[i].GetComponentInChildren <Fire>().gameObject),
                                                         subRootGuid,
                                                         roomFire.Key,
                                                         i));
                    }
                }
            }
        }
        /// <summary>
        /// Add/remove fires until it matches the <paramref name="roomFires"/> array. Can trigger <see cref="FireDoused"/> packets
        /// </summary>
        private void SetActiveRoomFires(SubRoot subRoot, CyclopsFireData[] roomFires)
        {
            SubFire subFire = subRoot.gameObject.RequireComponent <SubFire>();
            Dictionary <CyclopsRooms, SubFire.RoomFire> roomFiresDict = (Dictionary <CyclopsRooms, SubFire.RoomFire>)subFire.ReflectionGet("roomFires");
            string          subRootGuid = GuidHelper.GetGuid(subRoot.gameObject);
            CyclopsFireData fireNode    = null;

            if (roomFires != null && roomFires.Length > 0)
            {
                // Removing and adding fires will happen in the same loop
                foreach (KeyValuePair <CyclopsRooms, SubFire.RoomFire> keyValuePair in roomFiresDict)
                {
                    for (int nodeIndex = 0; nodeIndex < keyValuePair.Value.spawnNodes.Length; nodeIndex++)
                    {
                        fireNode = roomFires.SingleOrDefault(x => x.Room == keyValuePair.Key && x.NodeIndex == nodeIndex);

                        // If there's a matching node index, add a fire if there isn't one already. Otherwise remove a fire if there is one
                        if (fireNode == null)
                        {
                            if (keyValuePair.Value.spawnNodes[nodeIndex].childCount > 0)
                            {
                                keyValuePair.Value.spawnNodes[nodeIndex].GetComponentInChildren <Fire>().Douse(10000);
                            }
                        }
                        else
                        {
                            if (keyValuePair.Value.spawnNodes[nodeIndex].childCount < 1)
                            {
                                fires.Create(new CyclopsFireData(fireNode.FireGuid, subRootGuid, fireNode.Room, fireNode.NodeIndex));
                            }
                        }
                    }
                }
            }
            // Clear out the fires, there should be none active
            else
            {
                foreach (KeyValuePair <CyclopsRooms, SubFire.RoomFire> keyValuePair in roomFiresDict)
                {
                    for (int nodeIndex = 0; nodeIndex < keyValuePair.Value.spawnNodes.Length; nodeIndex++)
                    {
                        if (keyValuePair.Value.spawnNodes[nodeIndex].childCount > 0)
                        {
                            keyValuePair.Value.spawnNodes[nodeIndex].GetComponentInChildren <Fire>().Douse(10000);
                        }
                    }
                }
            }
        }