Ejemplo n.º 1
0
        public int CreateNew(TSPlayer forPlayer, DPoint location, ItemData itemData, bool sendPacket = true)
        {
            int itemIndex = Item.NewItem(
            location.X, location.Y, 0, 0, (int)itemData.Type, itemData.StackSize, true, (int)itemData.Prefix
              );

              if (sendPacket)
            forPlayer.SendData(PacketTypes.ItemDrop, string.Empty, itemIndex);

              return itemIndex;
        }
Ejemplo n.º 2
0
        /// <summary>Sends tile updates for a region border to a client.</summary>
        /// <param name="player">The player to send to.</param>
        public void refresh(TShockAPI.TSPlayer player)
        {
            // Due to the way the Rectangle class works, the Width and Height values are one tile less than the actual dimensions of the region.
            if (this.showArea.Width <= 3 || this.showArea.Height <= 3)
            {
                player.SendData(PacketTypes.TileSendSection, "", this.showArea.Left - 1, this.showArea.Top - 1, this.showArea.Width + 3, this.showArea.Height + 3, 0);
            }
            else
            {
                if (this.showArea.Top == this.area.Top)
                {
                    player.SendData(PacketTypes.TileSendSection, "", this.showArea.Left - 1, this.showArea.Top - 1, this.showArea.Width + 3, 3, 0);
                }
                if (this.showArea.Left == this.area.Left)
                {
                    player.SendData(PacketTypes.TileSendSection, "", this.showArea.Left - 1, this.showArea.Top + 2, 3, this.showArea.Height, 0);
                }
                if (this.showArea.Right == this.area.Right)
                {
                    player.SendData(PacketTypes.TileSendSection, "", this.showArea.Right - 1, this.showArea.Top + 2, 3, this.showArea.Height, 0);
                }
                if (this.showArea.Bottom == this.area.Bottom)
                {
                    player.SendData(PacketTypes.TileSendSection, "", this.showArea.Left + 2, this.showArea.Bottom - 1, this.showArea.Width - 3, 3, 0);
                }
            }

            player.SendData(PacketTypes.TileFrameSection, "", (int)(this.showArea.Left / 200), (int)(this.showArea.Top / 150), (int)(this.showArea.Right / 200), (int)(this.showArea.Bottom / 150), 0);
        }
        public virtual bool HandleQuickStackNearby(TSPlayer player, int playerSlotIndex)
        {
            if (this.IsDisposed)
            return false;

              Item item = player.TPlayer.inventory[playerSlotIndex];
              // TODO: fix this
              //this.PutItemInNearbyChest(player, item, player.TPlayer.Center);

              player.SendData(PacketTypes.PlayerSlot, string.Empty, player.Index, playerSlotIndex, item.prefix);
              return true;
        }
        public virtual bool HandleChestUnlock(TSPlayer player, DPoint chestLocation)
        {
            if (this.IsDisposed)
            return false;

              ProtectionEntry protection = null;
              // Only need the first enumerated entry as we don't need the protections of adjacent blocks.
              foreach (ProtectionEntry enumProtection in this.ProtectionManager.EnumerateProtectionEntries(chestLocation)) {
            protection = enumProtection;
            break;
              }
              if (protection == null)
            return false;

              bool undoUnlock = false;
              if (!this.ProtectionManager.CheckProtectionAccess(protection, player, false)) {
            player.SendErrorMessage("This chest is protected, you can't unlock it.");
            undoUnlock = true;
              }
              if (protection.RefillChestData != null && !this.CheckRefillChestLootability(protection.RefillChestData, player))
            undoUnlock = true;

              if (undoUnlock) {
            bool dummy;
            if (TerrariaUtils.Tiles.GetChestStyle(TerrariaUtils.Tiles[chestLocation], out dummy) == ChestStyle.GoldChest) {
              int itemIndex = Item.NewItem(
            chestLocation.X * TerrariaUtils.TileSize, chestLocation.Y * TerrariaUtils.TileSize, 0, 0, (int)ItemType.GoldenKey
              );
              player.SendData(PacketTypes.ItemDrop, string.Empty, itemIndex);
            }

            player.SendTileSquare(chestLocation, 3);
            return true;
              }

              return false;
        }
        public virtual bool HandleChestRename(TSPlayer player, int chestIndex, string newName)
        {
            if (this.IsDisposed)
            return false;

              IChest chest = this.LastOpenedChest(player);
              if (chest == null)
            return true;

              bool isAllowed = true;
              if (this.CheckProtected(player, chest.Location, true)) {
            player.SendErrorMessage("You have to be the owner of the chest in order to rename it.");
            isAllowed = false;
              }

              if (this.Config.LoginRequiredForChestUsage && !player.IsLoggedIn) {
            player.SendErrorMessage("You have to be logged in in order to rename chests.");
            isAllowed = false;
              }

              if (!isAllowed) {
            string originalName = string.Empty;
            if (chest.IsWorldChest)
              originalName = chest.Name;

            // The name change will already have happened locally for the player, so gotta send the original name back to them.
            player.SendData(PacketTypes.ChestName, originalName, chest.Index, chest.Location.X, chest.Location.Y);
            return true;
              } else {
            // Only world chests can have names, so attempt to convert it into one.
            if (!chest.IsWorldChest && !this.TrySwapChestData(null, chest.Location, out chest)) {
              player.SendErrorMessage("The maximum amount of named chests for this world has been reached.");
              return true;
            }

            chest.Name = newName;
            player.SendData(PacketTypes.ChestName, chest.Name, chest.Index, chest.Location.X, chest.Location.Y);

            return true;
              }
        }
        public bool HandleChestGetContents(TSPlayer player, DPoint location, bool skipInteractions)
        {
            if (this.IsDisposed)
            return false;
              if (!skipInteractions && base.HandleChestGetContents(player, location))
            return true;
              bool isDummyChest = (location.X == 0);
              if (isDummyChest)
            return true;
              if (!TerrariaUtils.Tiles[location].active())
            return true;
              if (this.Config.LoginRequiredForChestUsage && !player.IsLoggedIn) {
            player.SendErrorMessage("You have to be logged in to make use of chests.");
            return true;
              }

              if (this.Config.DungeonChestProtection && !NPC.downedBoss3 && !player.Group.HasPermission(ProtectorPlugin.ProtectionMaster_Permission)) {
            ChestKind kind = TerrariaUtils.Tiles.GuessChestKind(location);
            if (kind == ChestKind.DungeonChest || kind == ChestKind.HardmodeDungeonChest) {
              player.SendErrorMessage("Skeletron has not been defeated yet.");
              return true;
            }
              }

              ProtectionEntry protection = null;
              // Only need the first enumerated entry as we don't need the protections of adjacent blocks.
              foreach (ProtectionEntry enumProtection in this.ProtectionManager.EnumerateProtectionEntries(location)) {
            protection = enumProtection;
            break;
              }

              DPoint chestLocation = TerrariaUtils.Tiles.MeasureObject(location).OriginTileLocation;

              IChest chest = this.ChestManager.ChestFromLocation(chestLocation, player);
              if (chest == null)
            return true;

              if (this.IsChestInUse(player, chest)) {
            player.SendErrorMessage("Another player is already viewing the content of this chest.");
            return true;
              }

              if (protection != null) {
            bool isTradeChest = (protection.TradeChestData != null);
            if (!this.ProtectionManager.CheckProtectionAccess(protection, player)) {
              if (isTradeChest)
            this.InitTrade(player, chest, protection);
              else
            player.SendErrorMessage("This chest is protected.");

              return true;
            }

            if (isTradeChest) {
              Item sellItem = new Item();
              sellItem.netDefaults(protection.TradeChestData.ItemToSellId);
              sellItem.stack = protection.TradeChestData.ItemToSellAmount;
              Item payItem = new Item();
              payItem.netDefaults(protection.TradeChestData.ItemToPayId);
              payItem.stack = protection.TradeChestData.ItemToPayAmount;

              player.SendMessage($"This is a trade chest selling {TShock.Utils.ItemTag(sellItem)} for {TShock.Utils.ItemTag(payItem)}", Color.OrangeRed);
              player.SendMessage("You have access to it, so you can modify it any time.", Color.LightGray);
            }

            if (protection.RefillChestData != null) {
              RefillChestMetadata refillChest = protection.RefillChestData;
              if (this.CheckRefillChestLootability(refillChest, player)) {
            if (refillChest.OneLootPerPlayer)
              player.SendMessage("You can loot this chest a single time only.", Color.OrangeRed);
              } else {
            return true;
              }

              if (refillChest.RefillTime != TimeSpan.Zero) {
            lock (this.ChestManager.RefillTimers) {
              if (this.ChestManager.RefillTimers.IsTimerRunning(refillChest.RefillTimer)) {
                TimeSpan timeLeft = (refillChest.RefillStartTime + refillChest.RefillTime) - DateTime.Now;
                player.SendMessage($"This chest will refill in {timeLeft.ToLongString()}.", Color.OrangeRed);
              } else {
                player.SendMessage("This chest will refill its content.", Color.OrangeRed);
              }
            }
              } else {
            player.SendMessage("This chest will refill its content.", Color.OrangeRed);
              }
            }
              }

              lock (ChestManager.DummyChest) {
            Main.chest[ChestManager.DummyChestIndex] = ChestManager.DummyChest;

            if (chest.IsWorldChest) {
              ChestManager.DummyChest.name = chest.Name;
              player.TPlayer.chest = chest.Index;
            } else {
              player.TPlayer.chest = -1;
            }

            for (int i = 0; i < Chest.maxItems; i++) {
              ChestManager.DummyChest.item[i] = chest.Items[i].ToItem();
              player.SendData(PacketTypes.ChestItem, string.Empty, ChestManager.DummyChestIndex, i);
            }

            ChestManager.DummyChest.x = chestLocation.X;
            ChestManager.DummyChest.y = chestLocation.Y;
            player.SendData(PacketTypes.ChestOpen, string.Empty, ChestManager.DummyChestIndex);
            ChestManager.DummyChest.x = 0;
              }

              DPoint oldChestLocation;
              if (this.PlayerIndexChestDictionary.TryGetValue(player.Index, out oldChestLocation)) {
            this.PlayerIndexChestDictionary.Remove(player.Index);
            this.ChestPlayerIndexDictionary.Remove(oldChestLocation);
              }

              if (!chest.IsWorldChest) {
            this.PlayerIndexChestDictionary[player.Index] = chestLocation;
            this.ChestPlayerIndexDictionary[chestLocation] = player.Index;
              }

              return false;
        }