Exemplo n.º 1
0
        private void MoveBetweenContainers()
        {
            IItem extraItem;
            var   updatedItem = Thing as IItem;

            if (FromContainer == null || ToContainer == null || updatedItem == null || Requestor == null)
            {
                return;
            }

            // attempt to remove from the source container
            if (!FromContainer.RemoveContent(updatedItem.Type.TypeId, FromIndex, Count, out extraItem))
            {
                return;
            }

            if (extraItem != null)
            {
                updatedItem = extraItem;
            }

            // successfully removed thing from the source container
            // attempt to add to the dest container
            if (ToContainer.AddContent(updatedItem, ToIndex))
            {
                return;
            }

            // failed to add to the dest container (whole or partial)
            // attempt to add again to the source at any index.
            if (FromContainer.AddContent(updatedItem, 0xFF))
            {
                return;
            }

            // and we somehow failed to re-add it to the source container...
            // throw to the ground.
            IThing thing = updatedItem;

            Requestor.Tile.AddThing(ref thing, updatedItem.Count);

            // notify all spectator players of that tile.
            Game.Instance.NotifySpectatingPlayers(conn => new TileUpdatedNotification(conn, Requestor.Location, Game.Instance.GetMapTileDescription(conn.PlayerId, Requestor.Location)), Requestor.Location);

            // and handle collision.
            if (!Requestor.Tile.HandlesCollision)
            {
                return;
            }

            foreach (var itemWithCollision in Requestor.Tile.ItemsWithCollision)
            {
                var collisionEvents = Game.Instance.EventsCatalog[ItemEventType.Collision].Cast <CollisionItemEvent>();

                var candidate = collisionEvents.FirstOrDefault(e => e.ThingIdOfCollision == itemWithCollision.Type.TypeId && e.Setup(itemWithCollision, thing) && e.CanBeExecuted);

                // Execute all actions.
                candidate?.Execute();
            }
        }
Exemplo n.º 2
0
        private void MoveSlotToContainer()
        {
            if (Item == null || Requestor == null)
            {
                return;
            }

            bool partialRemove;

            // attempt to remove the item from the inventory
            var movingItem = Requestor.Inventory?.Remove(FromSlot, Count, out partialRemove);

            if (movingItem == null)
            {
                return;
            }

            // successfully removed thing from the source container
            // attempt to add to the dest container
            if (ToContainer.AddContent(movingItem, ToIndex))
            {
                return;
            }

            // failed to add to the slot, add again to the source slot
            if (!Requestor.Inventory.Add(movingItem, out movingItem, FromSlot, movingItem.Count))
            {
                // and we somehow failed to re-add it to the source container...
                // throw to the ground.
                IThing thing = movingItem;
                Requestor.Tile.AddThing(ref thing, movingItem.Count);

                // notify all spectator players of that tile.
                Game.Instance.NotifySpectatingPlayers(conn => new TileUpdatedNotification(conn, Requestor.Location, Game.Instance.GetMapTileDescription(conn.PlayerId, Requestor.Location)), Requestor.Location);

                // call any collision events again.
                if (Requestor.Tile.HandlesCollision)
                {
                    foreach (var itemWithCollision in Requestor.Tile.ItemsWithCollision)
                    {
                        var collisionEvents = Game.Instance.EventsCatalog[ItemEventType.Collision].Cast <CollisionItemEvent>();

                        var candidate =
                            collisionEvents.FirstOrDefault(
                                e => e.ThingIdOfCollision == itemWithCollision.Type.TypeId &&
                                e.Setup(itemWithCollision, thing) && e.CanBeExecuted);

                        // Execute all actions.
                        candidate?.Execute();
                    }
                }
            }
        }
        private void PickupToContainer()
        {
            var thingAsItem = Thing as IItem;

            if (FromTile == null || ToContainer == null || Thing == null || thingAsItem == null)
            {
                return;
            }

            var thingAtTile = FromTile.GetThingAtStackPosition(FromStackPos);

            if (thingAtTile == null)
            {
                return;
            }

            var thing = Thing;

            FromTile.RemoveThing(ref thing, Count);

            // notify all spectator players of that tile.
            Game.Instance.NotifySpectatingPlayers(conn => new TileUpdatedNotification(conn, FromTile.Location, Game.Instance.GetMapTileDescription(conn.PlayerId, FromTile.Location)), FromTile.Location);

            if (thing != Thing)
            {
                // item got split cause we removed less than the total amount.
                // update the thing we're adding to the container.
                thingAsItem = thing as IItem;
            }

            // attempt to add the item to the container.
            if (thingAsItem == null || ToContainer.AddContent(thingAsItem, ToIndex))
            {
                // and call any separation events.
                if (FromTile.HandlesSeparation) // TODO: what happens on separation of less than required quantity, etc?
                {
                    foreach (var itemWithSeparation in FromTile.ItemsWithSeparation)
                    {
                        var separationEvents = Game.Instance.EventsCatalog[ItemEventType.Separation].Cast <SeparationItemEvent>();

                        var candidate = separationEvents.FirstOrDefault(e => e.ThingIdOfSeparation == itemWithSeparation.Type.TypeId && e.Setup(itemWithSeparation, thing, Requestor as IPlayer) && e.CanBeExecuted);

                        // Execute all actions.
                        candidate?.Execute();
                    }
                }

                return;
            }

            // failed to add to the dest container (whole or partial)
            // add again to the source tile
            IThing itemAsThing = thingAsItem;

            FromTile.AddThing(ref itemAsThing, thingAsItem.Count);

            // notify all spectator players of that tile.
            Game.Instance.NotifySpectatingPlayers(conn => new TileUpdatedNotification(conn, FromTile.Location, Game.Instance.GetMapTileDescription(conn.PlayerId, FromTile.Location)), FromTile.Location);

            // call any collision events again.
            if (!FromTile.HandlesCollision)
            {
                return;
            }

            foreach (var itemWithCollision in FromTile.ItemsWithCollision)
            {
                var collisionEvents = Game.Instance.EventsCatalog[ItemEventType.Collision].Cast <CollisionItemEvent>();

                var candidate = collisionEvents.FirstOrDefault(e => e.ThingIdOfCollision == itemWithCollision.Type.TypeId && e.Setup(itemWithCollision, Thing) && e.CanBeExecuted);

                // Execute all actions.
                candidate?.Execute();
            }
        }