1using Microsoft.Xna.Framework;
2using Microsoft.Xna.Framework.Graphics;
4using System.Collections.Generic;
6using Terraria.ObjectData;
32 internal static readonly IList<ModTile> tiles =
new List<ModTile>();
33 internal static readonly IList<GlobalTile> globalTiles =
new List<GlobalTile>();
34 internal static readonly IDictionary<int, ModTree> trees =
new Dictionary<int, ModTree>();
35 internal static readonly IDictionary<int, ModPalmTree> palmTrees =
new Dictionary<int, ModPalmTree>();
36 internal static readonly IDictionary<int, ModCactus> cacti =
new Dictionary<int, ModCactus>();
41 private static readonly
int vanillaDoorCount = TileID.Sets.RoomNeeds.CountsAsDoor.Length;
44 private delegate
void DelegateNumDust(
int i,
int j,
int type,
bool fail, ref
int num);
48 private delegate
void DelegateDropCritterChance(
int i,
int j,
int type, ref
int wormChance, ref
int grassHopperChance, ref
int jungleGrubChance);
50 private static Func<int, int, int, bool>[]
HookDrop;
53 private delegate
void DelegateKillTile(
int i,
int j,
int type, ref
bool fail, ref
bool effectOnly, ref
bool noItem);
57 private delegate
void DelegateModifyLight(
int i,
int j,
int type, ref
float r, ref
float g, ref
float b);
63 private static Func<int, int, int, SpriteBatch, bool>[]
HookPreDraw;
64 private delegate
void DelegateDrawEffects(
int i,
int j,
int type, SpriteBatch spriteBatch, ref Color drawColor, ref
int nextSpecialDrawIndex);
69 private delegate
bool DelegateTileFrame(
int i,
int j,
int type, ref
bool resetFrame, ref
bool noBreak);
79 private static Func<int, int, int, bool>[]
HookSlope;
87 internal static int ReserveTileID() {
103 return type >= TileID.Count && type <
TileCount ? tiles[type - TileID.Count] :
null;
107 int dim1 = array.GetLength(0);
108 int dim2 = array.GetLength(1);
109 T[,] newArray =
new T[newSize, dim2];
110 for (
int j = 0; j < newSize && j < dim1; j++) {
111 for (
int k = 0; k < dim2; k++) {
112 newArray[j, k] = array[j, k];
118 internal static void ResizeArrays(
bool unloading =
false) {
119 Array.Resize(ref Main.tileSetsLoaded,
nextTile);
120 for (
int k = TileID.Count; k <
nextTile; k++) {
121 Main.tileSetsLoaded[k] =
true;
123 Array.Resize(ref Main.highlightMaskTexture,
nextTile);
124 Resize2DArray(ref Main.tileAltTexture,
nextTile);
125 Resize2DArray(ref Main.tileAltTextureInit,
nextTile);
126 Resize2DArray(ref Main.tileAltTextureDrawn,
nextTile);
127 Array.Resize(ref Main.tileTexture,
nextTile);
128 Array.Resize(ref Main.tileLighted,
nextTile);
129 Array.Resize(ref Main.tileMergeDirt,
nextTile);
130 Array.Resize(ref Main.tileCut,
nextTile);
131 Array.Resize(ref Main.tileAlch,
nextTile);
132 Array.Resize(ref Main.tileShine,
nextTile);
133 Array.Resize(ref Main.tileShine2,
nextTile);
134 Array.Resize(ref Main.tileStone,
nextTile);
135 Array.Resize(ref Main.tileAxe,
nextTile);
136 Array.Resize(ref Main.tileHammer,
nextTile);
137 Array.Resize(ref Main.tileWaterDeath,
nextTile);
138 Array.Resize(ref Main.tileLavaDeath,
nextTile);
139 Array.Resize(ref Main.tileTable,
nextTile);
140 Array.Resize(ref Main.tileBlockLight,
nextTile);
141 Array.Resize(ref Main.tileNoSunLight,
nextTile);
142 Array.Resize(ref Main.tileDungeon,
nextTile);
143 Array.Resize(ref Main.tileSpelunker,
nextTile);
144 Array.Resize(ref Main.tileSolidTop,
nextTile);
145 Array.Resize(ref Main.tileSolid,
nextTile);
146 Array.Resize(ref Main.tileBouncy,
nextTile);
147 Array.Resize(ref Main.tileValue,
nextTile);
148 Array.Resize(ref Main.tileLargeFrames,
nextTile);
149 Array.Resize(ref Main.tileRope,
nextTile);
150 Array.Resize(ref Main.tileBrick,
nextTile);
151 Array.Resize(ref Main.tileMoss,
nextTile);
152 Array.Resize(ref Main.tileNoAttach,
nextTile);
153 Array.Resize(ref Main.tileNoFail,
nextTile);
154 Array.Resize(ref Main.tileObsidianKill,
nextTile);
155 Array.Resize(ref Main.tileFrameImportant,
nextTile);
156 Array.Resize(ref Main.tilePile,
nextTile);
157 Array.Resize(ref Main.tileBlendAll,
nextTile);
158 Array.Resize(ref Main.tileGlowMask,
nextTile);
159 Array.Resize(ref Main.tileContainer,
nextTile);
160 Array.Resize(ref Main.tileSign,
nextTile);
161 Array.Resize(ref Main.tileMerge,
nextTile);
164 Array.Resize(ref Main.tileMerge[k],
nextTile);
166 Array.Resize(ref Main.tileSand,
nextTile);
167 Array.Resize(ref Main.tileFlame,
nextTile);
168 Array.Resize(ref Main.tileFrame,
nextTile);
169 Array.Resize(ref Main.tileFrameCounter,
nextTile);
170 Array.Resize(ref Main.screenTileCounts,
nextTile);
171 Array.Resize(ref WorldGen.tileCounts,
nextTile);
172 Array.Resize(ref WorldGen.houseTile,
nextTile);
173 Array.Resize(ref GameContent.Biomes.CaveHouseBiome._blacklistedTiles,
nextTile);
174 Array.Resize(ref GameContent.Biomes.CorruptionPitBiome.ValidTiles,
nextTile);
175 Array.Resize(ref TileID.Sets.Conversion.Grass,
nextTile);
176 Array.Resize(ref TileID.Sets.Conversion.Stone,
nextTile);
177 Array.Resize(ref TileID.Sets.Conversion.Ice,
nextTile);
178 Array.Resize(ref TileID.Sets.Conversion.Sand,
nextTile);
179 Array.Resize(ref TileID.Sets.Conversion.HardenedSand,
nextTile);
180 Array.Resize(ref TileID.Sets.Conversion.Sandstone,
nextTile);
181 Array.Resize(ref TileID.Sets.Conversion.Thorn,
nextTile);
182 Array.Resize(ref TileID.Sets.Conversion.Moss,
nextTile);
183 Array.Resize(ref TileID.Sets.ForAdvancedCollision.ForSandshark,
nextTile);
184 Array.Resize(ref TileID.Sets.Platforms,
nextTile);
185 Array.Resize(ref TileID.Sets.DrawsWalls,
nextTile);
186 Array.Resize(ref TileID.Sets.GemsparkFramingTypes,
nextTile);
187 Array.Resize(ref TileID.Sets.TeamTiles,
nextTile);
188 Array.Resize(ref TileID.Sets.ConveyorDirection,
nextTile);
189 Array.Resize(ref TileID.Sets.HasSlopeFrames,
nextTile);
190 Array.Resize(ref TileID.Sets.TileInteractRead,
nextTile);
191 Array.Resize(ref TileID.Sets.HasOutlines,
nextTile);
192 Array.Resize(ref TileID.Sets.AllTiles,
nextTile);
193 Array.Resize(ref TileID.Sets.Stone,
nextTile);
194 Array.Resize(ref TileID.Sets.Grass,
nextTile);
195 Array.Resize(ref TileID.Sets.Mud,
nextTile);
196 Array.Resize(ref TileID.Sets.Snow,
nextTile);
197 Array.Resize(ref TileID.Sets.Ices,
nextTile);
198 Array.Resize(ref TileID.Sets.IcesSlush,
nextTile);
199 Array.Resize(ref TileID.Sets.IcesSnow,
nextTile);
200 Array.Resize(ref TileID.Sets.GrassSpecial,
nextTile);
201 Array.Resize(ref TileID.Sets.JungleSpecial,
nextTile);
202 Array.Resize(ref TileID.Sets.HellSpecial,
nextTile);
203 Array.Resize(ref TileID.Sets.Leaves,
nextTile);
204 Array.Resize(ref TileID.Sets.GeneralPlacementTiles,
nextTile);
205 Array.Resize(ref TileID.Sets.BasicChest,
nextTile);
206 Array.Resize(ref TileID.Sets.BasicChestFake,
nextTile);
207 Array.Resize(ref TileID.Sets.CanBeClearedDuringGeneration,
nextTile);
208 Array.Resize(ref TileID.Sets.CanBeClearedDuringOreRunner,
nextTile);
209 Array.Resize(ref TileID.Sets.Corrupt,
nextTile);
210 Array.Resize(ref TileID.Sets.Hallow,
nextTile);
211 Array.Resize(ref TileID.Sets.Crimson,
nextTile);
212 Array.Resize(ref TileID.Sets.BlocksStairs,
nextTile);
213 Array.Resize(ref TileID.Sets.BlocksStairsAbove,
nextTile);
214 Array.Resize(ref TileID.Sets.NotReallySolid,
nextTile);
215 Array.Resize(ref TileID.Sets.NeedsGrassFraming,
nextTile);
216 Array.Resize(ref TileID.Sets.NeedsGrassFramingDirt,
nextTile);
217 Array.Resize(ref TileID.Sets.ChecksForMerge,
nextTile);
218 Array.Resize(ref TileID.Sets.FramesOnKillWall,
nextTile);
219 Array.Resize(ref TileID.Sets.AvoidedByNPCs,
nextTile);
220 Array.Resize(ref TileID.Sets.InteractibleByNPCs,
nextTile);
221 Array.Resize(ref TileID.Sets.HousingWalls,
nextTile);
222 Array.Resize(ref TileID.Sets.BreakableWhenPlacing,
nextTile);
223 Array.Resize(ref TileID.Sets.TouchDamageVines,
nextTile);
224 Array.Resize(ref TileID.Sets.TouchDamageSands,
nextTile);
225 Array.Resize(ref TileID.Sets.TouchDamageHot,
nextTile);
226 Array.Resize(ref TileID.Sets.TouchDamageOther,
nextTile);
227 Array.Resize(ref TileID.Sets.Falling,
nextTile);
228 Array.Resize(ref TileID.Sets.Ore,
nextTile);
229 Array.Resize(ref TileID.Sets.ForceObsidianKill,
nextTile);
230 for (
int k = TileID.Count; k <
nextTile; k++) {
231 TileID.Sets.AllTiles[k] =
true;
232 TileID.Sets.GeneralPlacementTiles[k] =
true;
233 TileID.Sets.CanBeClearedDuringGeneration[k] =
true;
235 while (TileObjectData._data.Count <
nextTile) {
236 TileObjectData._data.Add(
null);
239 ModLoader.BuildGlobalHook(ref
HookKillSound, globalTiles, g => g.KillSound);
240 ModLoader.BuildGlobalHook(ref
HookNumDust, globalTiles, g => g.NumDust);
241 ModLoader.BuildGlobalHook(ref
HookCreateDust, globalTiles, g => g.CreateDust);
243 ModLoader.BuildGlobalHook(ref
HookDrop, globalTiles, g => g.Drop);
244 ModLoader.BuildGlobalHook(ref
HookCanKillTile, globalTiles, g => g.CanKillTile);
245 ModLoader.BuildGlobalHook(ref
HookKillTile, globalTiles, g => g.KillTile);
246 ModLoader.BuildGlobalHook(ref
HookCanExplode, globalTiles, g => g.CanExplode);
247 ModLoader.BuildGlobalHook(ref
HookNearbyEffects, globalTiles, g => g.NearbyEffects);
248 ModLoader.BuildGlobalHook(ref
HookModifyLight, globalTiles, g => g.ModifyLight);
249 ModLoader.BuildGlobalHook(ref
HookDangersense, globalTiles, g => g.Dangersense);
251 ModLoader.BuildGlobalHook(ref
HookAnimateTile, globalTiles, g => g.AnimateTile);
252 ModLoader.BuildGlobalHook(ref
HookPreDraw, globalTiles, g => g.PreDraw);
253 ModLoader.BuildGlobalHook(ref
HookDrawEffects, globalTiles, g => g.DrawEffects);
254 ModLoader.BuildGlobalHook(ref
HookPostDraw, globalTiles, g => g.PostDraw);
255 ModLoader.BuildGlobalHook(ref
HookSpecialDraw, globalTiles, g => g.SpecialDraw);
256 ModLoader.BuildGlobalHook(ref
HookRandomUpdate, globalTiles, g => g.RandomUpdate);
257 ModLoader.BuildGlobalHook(ref
HookTileFrame, globalTiles, g => g.TileFrame);
258 ModLoader.BuildGlobalHook(ref
HookCanPlace, globalTiles, g => g.CanPlace);
259 ModLoader.BuildGlobalHook(ref
HookAdjTiles, globalTiles, g => g.AdjTiles);
260 ModLoader.BuildGlobalHook(ref
HookRightClick, globalTiles, g => g.RightClick);
261 ModLoader.BuildGlobalHook(ref
HookMouseOver, globalTiles, g => g.MouseOver);
262 ModLoader.BuildGlobalHook(ref
HookMouseOverFar, globalTiles, g => g.MouseOverFar);
263 ModLoader.BuildGlobalHook(ref
HookAutoSelect, globalTiles, g => g.AutoSelect);
264 ModLoader.BuildGlobalHook(ref
HookPreHitWire, globalTiles, g => g.PreHitWire);
265 ModLoader.BuildGlobalHook(ref
HookHitWire, globalTiles, g => g.HitWire);
266 ModLoader.BuildGlobalHook(ref
HookSlope, globalTiles, g => g.Slope);
267 ModLoader.BuildGlobalHook(ref
HookFloorVisuals, globalTiles, g => g.FloorVisuals);
270 ModLoader.BuildGlobalHook(ref
HookPlaceInWorld, globalTiles, g => g.PlaceInWorld);
277 internal static void Unload() {
289 while (TileObjectData._data.Count > TileID.Count) {
290 TileObjectData._data.RemoveAt(TileObjectData._data.Count - 1);
298 if (WorldGen.destroyObject) {
301 TileObjectData tileData = TileObjectData.GetTileData(type, 0, 0);
302 if (tileData ==
null) {
305 int frameX = Main.tile[i, j].frameX;
306 int frameY = Main.tile[i, j].frameY;
307 int subX = frameX / tileData.CoordinateFullWidth;
308 int subY = frameY / tileData.CoordinateFullHeight;
309 int wrap = tileData.StyleWrapLimit;
313 int subTile = tileData.StyleHorizontal ? subY * wrap + subX : subX * wrap + subY;
314 int style = subTile / tileData.StyleMultiplier;
315 int alternate = subTile % tileData.StyleMultiplier;
316 for (
int k = 0; k < tileData.AlternatesCount; k++) {
317 if (alternate >= tileData.Alternates[k].Style && alternate <= tileData.Alternates[k].Style + tileData.RandomStyleRange) {
322 tileData = TileObjectData.GetTileData(type, style, alternate + 1);
323 int partFrameX = frameX % tileData.CoordinateFullWidth;
324 int partFrameY = frameY % tileData.CoordinateFullHeight;
325 int partX = partFrameX / (tileData.CoordinateWidth + tileData.CoordinatePadding);
327 int remainingFrameY = partFrameY;
328 while (remainingFrameY > 0) {
329 remainingFrameY -= tileData.CoordinateHeights[partY] + tileData.CoordinatePadding;
334 int originX = i + tileData.Origin.X;
335 int originY = j + tileData.Origin.Y;
336 TileObject objectData;
337 bool partiallyDestroyed =
false;
338 for (
int x = i; x < i + tileData.Width; x++) {
339 for (
int y = j; y < j + tileData.Height; y++) {
340 if (!Main.tile[x, y].active() || Main.tile[x, y].type != type) {
341 partiallyDestroyed =
true;
345 if (partiallyDestroyed) {
349 if (partiallyDestroyed || !TileObject.CanPlace(originX, originY, type, style, 0, out objectData,
true,
true)) {
350 WorldGen.destroyObject =
true;
351 for (
int x = i; x < i + tileData.Width; x++) {
352 for (
int y = j; y < j + tileData.Height; y++) {
353 if (Main.tile[x, y].type == type && Main.tile[x, y].active()) {
354 WorldGen.KillTile(x, y,
false,
false,
false);
358 KillMultiTile(i, j, frameX - partFrameX, frameY - partFrameY, type);
359 WorldGen.destroyObject =
false;
360 for (
int x = i - 1; x < i + tileData.Width + 2; x++) {
361 for (
int y = j - 1; y < j + tileData.Height + 2; y++) {
362 WorldGen.TileFrame(x, y,
false,
false);
366 TileObject.objectPreview.Active =
false;
372 if (modTile !=
null) {
381 if (modTile !=
null) {
391 if (modTile !=
null) {
394 if (tile.type == TileID.ClosedDoor && (tile.frameY < 594 || tile.frameY > 646 || tile.frameX >= 54)) {
395 return TileID.OpenDoor;
405 if (modTile !=
null) {
408 if (tile.type == TileID.OpenDoor) {
409 return TileID.ClosedDoor;
415 if (modTile !=
null) {
416 return modTile.openDoorID > -1;
418 return tile.type == TileID.ClosedDoor;
423 if (modTile !=
null) {
424 return modTile.
chest;
430 if (type == TileID.Dressers) {
438 if (modTile !=
null) {
446 if (modTile ==
null) {
454 if (modTile ==
null) {
455 return type == TileID.Torches;
457 return modTile.
torch;
462 if (modTile ==
null) {
463 return type == TileID.Saplings;
469 return SoundLoader.tileToMusic.ContainsKey(tile.type)
470 &&
SoundLoader.tileToMusic[tile.type].ContainsKey(tile.frameY / 36 * 36);
474 internal static void SetDefaults(
ModTile tile) {
476 if (TileObjectData.newTile.Width > 1 || TileObjectData.newTile.Height > 1) {
477 TileObjectData.FixNewTile();
478 throw new Exception(
"It appears that you have an error surrounding TileObjectData.AddTile in " + tile.GetType().FullName) { HelpLink =
"https://github.com/tModLoader/tModLoader/wiki/Basic-tModLoader-Modding-FAQ#tileobjectdataaddtile-issues" };
480 if (Main.tileLavaDeath[tile.
Type]) {
481 Main.tileObsidianKill[tile.
Type] =
true;
483 if (Main.tileSolid[tile.
Type]) {
484 Main.tileNoSunLight[tile.
Type] =
true;
493 public static void FixSmartInteractCoords(
int type, ref
int width, ref
int height, ref
int frameWidth, ref
int frameHeight, ref
int extraX, ref
int extraY) {
495 if (modTile !=
null) {
496 TileObjectData data = TileObjectData.GetTileData(type, 0);
498 height = data.Height;
499 frameWidth = data.CoordinateWidth + data.CoordinatePadding;
500 frameHeight = data.CoordinateHeights[0] + data.CoordinatePadding;
501 extraY = data.CoordinateFullHeight % frameHeight;
508 if (!hook(i, j, type)) {
513 if (modTile !=
null) {
524 public static void NumDust(
int i,
int j,
int type,
bool fail, ref
int numDust) {
528 hook(i, j, type, fail, ref numDust);
533 public static bool CreateDust(
int i,
int j,
int type, ref
int dustType) {
535 if (!hook(i, j, type, ref dustType)) {
543 public static void DropCritterChance(
int i,
int j,
int type, ref
int wormChance, ref
int grassHopperChance, ref
int jungleGrubChance) {
547 hook(i, j, type, ref wormChance, ref grassHopperChance, ref jungleGrubChance);
553 public static bool Drop(
int i,
int j,
int type) {
555 if (!hook(i, j, type)) {
560 if (modTile !=
null) {
561 if (!modTile.
Drop(i, j)) {
564 if (modTile.
drop > 0) {
565 Item.NewItem(i * 16, j * 16, 16, 16, modTile.
drop, 1,
false, -1);
573 public static bool CanKillTile(
int i,
int j,
int type, ref
bool blockDamaged) {
575 if (!hook(i, j, type, ref blockDamaged)) {
583 public static void KillTile(
int i,
int j,
int type, ref
bool fail, ref
bool effectOnly, ref
bool noItem) {
587 hook(i, j, type, ref fail, ref effectOnly, ref noItem);
591 public static void KillMultiTile(
int i,
int j,
int frameX,
int frameY,
int type) {
596 int type = Main.tile[i, j].type;
598 if (modTile !=
null && !modTile.
CanExplode(i, j)) {
602 if (!hook(i, j, type)) {
614 hook(i, j, type, closer);
619 public static void ModifyLight(
int i,
int j,
int type, ref
float r, ref
float g, ref
float b) {
620 if (!Main.tileLighted[type]) {
626 hook(i, j, type, ref r, ref g, ref b);
630 public static bool Dangersense(
int i,
int j,
int type, Player player) {
632 if (modTile !=
null && modTile.
Dangersense(i, j, player)) {
636 if (hook(i, j, type, player)) {
644 public static void SetSpriteEffects(
int i,
int j,
int type, ref SpriteEffects spriteEffects) {
648 hook(i, j, type, ref spriteEffects);
653 public static void SetDrawPositions(
int i,
int j, ref
int width, ref
int offsetY, ref
int height) {
654 Tile tile = Main.tile[i, j];
655 if (tile.type >= TileID.Count) {
656 TileObjectData tileData = TileObjectData.GetTileData(tile.type, 0, 0);
657 if (tileData !=
null) {
658 int partFrameY = tile.frameY % tileData.CoordinateFullHeight;
660 while (partFrameY > 0) {
661 partFrameY -= tileData.CoordinateHeights[partY] + tileData.CoordinatePadding;
664 width = tileData.CoordinateWidth;
665 offsetY = tileData.DrawYOffset;
666 height = tileData.CoordinateHeights[partY];
674 for (
int i = 0; i < tiles.Count; i++) {
676 modTile.
AnimateTile(ref Main.tileFrame[modTile.
Type], ref Main.tileFrameCounter[modTile.
Type]);
694 public static void SetAnimationFrame(
int type,
int i,
int j, ref
int frameXOffset, ref
int frameYOffset) {
696 if (modTile !=
null) {
697 frameYOffset = modTile.animationFrameHeight * Main.tileFrame[type];
705 public static bool PreDraw(
int i,
int j,
int type, SpriteBatch spriteBatch) {
707 if (!hook(i, j, type, spriteBatch)) {
714 public static void DrawEffects(
int i,
int j,
int type, SpriteBatch spriteBatch, ref Color drawColor, ref
int nextSpecialDrawIndex) {
715 GetTile(type)?.
DrawEffects(i, j, spriteBatch, ref drawColor, ref nextSpecialDrawIndex);
717 hook(i, j, type, spriteBatch, ref drawColor, ref nextSpecialDrawIndex);
722 public static void PostDraw(
int i,
int j,
int type, SpriteBatch spriteBatch) {
726 hook(i, j, type, spriteBatch);
733 public static void SpecialDraw(
int type,
int specX,
int specY, SpriteBatch spriteBatch) {
737 hook(specX, specY, type, spriteBatch);
745 if (!Main.tile[i, j].active()) {
756 public static bool TileFrame(
int i,
int j,
int type, ref
bool resetFrame, ref
bool noBreak) {
759 if (modTile !=
null) {
760 flag = modTile.
TileFrame(i, j, ref resetFrame, ref noBreak);
763 flag &= hook(i, j, type, ref resetFrame, ref noBreak);
771 public static void MineDamage(
int minePower, ref
int damage) {
772 Tile target = Main.tile[Player.tileTargetX, Player.tileTargetY];
774 damage += modTile !=
null ? (int)(minePower / modTile.
mineResist) : minePower;
780 if (modTile !=
null && pickPower < modTile.
minPick) {
786 public static bool CanPlace(
int i,
int j,
int type) {
788 if (!hook(i, j, type)) {
796 public static void AdjTiles(Player player,
int type) {
798 if (modTile !=
null) {
799 foreach (
int k
in modTile.
adjTiles) {
800 player.adjTile[k] =
true;
804 int[] adjTiles = hook(type);
805 foreach (
int k
in adjTiles) {
806 player.adjTile[k] =
true;
813 bool returnValue =
false;
814 int type = Main.tile[i, j].type;
816 if (
GetTile(type)?.NewRightClick(i, j) ??
false)
827 int type = Main.tile[i, j].type;
836 int type = Main.tile[i, j].type;
845 if (!Main.tile[i, j].active()) {
848 int type = Main.tile[i, j].type;
850 for (
int k = 0; k < 50; k++) {
851 Item item = player.inventory[k];
852 if (item.type == 0 || item.stack == 0) {
855 if (modTile !=
null && modTile.
AutoSelect(i, j, item)) {
859 if (hook(i, j, type, item)) {
869 if (!hook(i, j, type)) {
879 public static void HitWire(
int i,
int j,
int type) {
896 public static bool Slope(
int i,
int j,
int type) {
898 if (!hook(i, j, type)) {
909 public static void WalkDust(
int type, ref
int dustType, ref
bool makeDust, ref Color color) {
916 hook(type, ref style);
921 int originalType = saplingType;
922 int originalStyle = style;
925 if (modTile !=
null) {
928 originalType = saplingType;
929 originalStyle = style;
933 saplingType = originalType;
934 style = originalStyle;
938 saplingType = hook(type, ref style);
940 originalType = saplingType;
941 originalStyle = style;
945 saplingType = originalType;
946 style = originalStyle;
953 return trees.ContainsKey(type);
956 public static void TreeDust(Tile tile, ref
int dust) {
957 if (tile.active() && trees.ContainsKey(tile.type)) {
958 dust = trees[tile.type].CreateDust();
963 if (trees.ContainsKey(type)) {
964 gore = trees[type].GrowthFXGore();
969 return trees.ContainsKey(type) ? trees[type].CanDropAcorn() :
false;
973 if (trees.ContainsKey(type)) {
974 wood = trees[type].DropWood();
979 return tile.active() && trees.ContainsKey(tile.type) ? trees[tile.type].GetTexture() :
null;
983 ref
int frameWidth, ref
int frameHeight, ref
int xOffsetLeft, ref
int yOffset) {
984 return trees.ContainsKey(type) ? trees[type].GetTopTextures(i, j, ref frame,
985 ref frameWidth, ref frameHeight, ref xOffsetLeft, ref yOffset) :
null;
989 return trees.ContainsKey(type) ? trees[type].GetBranchTextures(i, j, trunkOffset, ref frame) :
null;
993 return palmTrees.ContainsKey(type);
997 if (tile.active() && palmTrees.ContainsKey(tile.type)) {
998 dust = palmTrees[tile.type].CreateDust();
1003 if (palmTrees.ContainsKey(type)) {
1004 gore = palmTrees[type].GrowthFXGore();
1009 if (palmTrees.ContainsKey(type)) {
1010 wood = palmTrees[type].DropWood();
1015 return tile.active() && palmTrees.ContainsKey(tile.type) ? palmTrees[tile.type].GetTexture() :
null;
1019 return palmTrees.ContainsKey(type) ? palmTrees[type].GetTopTextures() :
null;
1023 return cacti.ContainsKey(type);
1027 return cacti.ContainsKey(type) ? cacti[type].GetTexture() :
null;
1031 int type = item.createTile;
1046 public static bool UnlockChest(
int i,
int j,
int type, ref
short frameXAdjustment, ref
int dustType, ref
bool manual) {
1047 return GetTile(type)?.
UnlockChest(i, j, ref frameXAdjustment, ref dustType, ref manual) ??
false;
static bool AllowVanillaClients
This class represents a type of tile that can be added by a mod. Only one instance of this class will...
virtual void RandomUpdate(int i, int j)
Called whenever the world randomly decides to update this tile in a given tick. Useful for things suc...
virtual void MouseOver(int i, int j)
Allows you to make something happen when the mouse hovers over this tile. Useful for showing item ico...
virtual void MouseOverFar(int i, int j)
Allows you to make something happen when the mouse hovers over this tile, even when the player is far...
virtual void SetDefaults()
Allows you to set the properties of this tile. Many properties are stored as arrays throughout Terrar...
bool disableSmartCursor
Whether or not the smart cursor function is disabled when the cursor hovers above this tile....
int soundType
The default type of sound made when this tile is hit. Defaults to 0.
virtual void NearbyEffects(int i, int j, bool closer)
Allows you to make things happen when this tile is within a certain range of the player (around the s...
virtual bool UnlockChest(int i, int j, ref short frameXAdjustment, ref int dustType, ref bool manual)
Allows customization of how a chest unlock is accomplished. By default, frameXAdjustment will be -36,...
string dresser
Same as chest, except use this if your block is a dresser (has a size of 3x2 instead of 2x2).
ushort Type
The internal ID of this type of tile.
virtual bool AutoSelect(int i, int j, Item item)
Allows you to determine whether the given item can become selected when the cursor is hovering over t...
bool bed
Whether or not this tile is a valid spawn point. Defaults to false. If you set this to true,...
virtual void ModifyLight(int i, int j, ref float r, ref float g, ref float b)
Allows you to determine how much light this block emits. Make sure you set Main.tileLighted[Type] to ...
virtual bool Dangersense(int i, int j, Player player)
Allows you to determine whether this block glows red when the given player has the Dangersense buff.
bool sapling
Whether or not this tile is a sapling, which can grow into a modded tree or palm tree.
virtual void WalkDust(ref int dustType, ref bool makeDust, ref Color color)
Allows you to modify the dust created when the player walks on this tile. The makeDust parameter is w...
int drop
The default type of item dropped when this tile is killed. Defaults to 0, which means no item.
int[] adjTiles
An array of the IDs of tiles that this tile can be considered as when looking for crafting stations.
virtual void AnimateIndividualTile(int type, int i, int j, ref int frameXOffset, ref int frameYOffset)
Animates an individual tile. i and j are the coordinates of the Tile in question. frameXOffset and fr...
virtual void HitWire(int i, int j)
Allows you to make something happen when a wire current passes through this tile.
virtual bool KillSound(int i, int j)
Allows you to customize which sound you want to play when the tile at the given coordinates is hit....
virtual bool Drop(int i, int j)
Allows you to customize which items the tile at the given coordinates drops. Remember that the x,...
virtual void NumDust(int i, int j, bool fail, ref int num)
Allows you to change how many dust particles are created when the tile at the given coordinates is hi...
int openDoorID
The ID of the tile that this door transforms into when it is opened. Defaults to -1,...
virtual bool PreDraw(int i, int j, SpriteBatch spriteBatch)
Allows you to draw things behind the tile at the given coordinates. Return false to stop the game fro...
int closeDoorID
The ID of the tile that this door transforms into when it is closed. Defaults to -1,...
virtual void AnimateTile(ref int frame, ref int frameCounter)
Allows you to animate your tile. Use frameCounter to keep track of how long the current frame has bee...
virtual void DrawEffects(int i, int j, SpriteBatch spriteBatch, ref Color drawColor, ref int nextSpecialDrawIndex)
Allows you to make stuff happen whenever the tile at the given coordinates is drawn....
virtual bool IsLockedChest(int i, int j)
Return true if this Tile corresponds to a chest that is locked. Prevents Quick Stacking items into th...
virtual void SetSpriteEffects(int i, int j, ref SpriteEffects spriteEffects)
Allows you to determine whether or not the tile will draw itself flipped in the world.
virtual void SetDrawPositions(int i, int j, ref int width, ref int offsetY, ref int height)
Allows you to customize the position in which this tile is drawn. Width refers to the width of one fr...
virtual void KillMultiTile(int i, int j, int frameX, int frameY)
This hook is called exactly once whenever a block encompassing multiple tiles is destroyed....
int soundStyle
The default style of sound made when this tile is hit. Defaults to 1.
virtual bool HasSmartInteract()
Whether or not the smart interact function can select this tile. Useful for things like chests....
virtual void KillTile(int i, int j, ref bool fail, ref bool effectOnly, ref bool noItem)
Allows you to determine what happens when the tile at the given coordinates is killed or hit with a p...
virtual void DropCritterChance(int i, int j, ref int wormChance, ref int grassHopperChance, ref int jungleGrubChance)
Allows you to modify the chance the tile at the given coordinates has of spawning a certain critter w...
virtual void RightClick(int i, int j)
Allows you to make something happen when this tile is right-clicked by the player.
virtual bool CreateDust(int i, int j, ref int type)
Allows you to modify the default type of dust created when the tile at the given coordinates is hit....
virtual void PostSetDefaults()
Allows you to override some default properties of this tile, such as Main.tileNoSunLight and Main....
virtual bool HasWalkDust()
Whether or not this tile creates dust when the player walks on it. Returns false by default.
virtual bool CanPlace(int i, int j)
Allows you to stop this tile from being placed at the given coordinates. Return false to block the ti...
virtual void SpecialDraw(int i, int j, SpriteBatch spriteBatch)
Special Draw. Only called if coordinates are placed in Main.specX/Y during DrawEffects....
virtual void FloorVisuals(Player player)
Allows you to make something happen when a player stands on this type of tile. For example,...
float mineResist
A multiplier describing how much this block resists harvesting. Higher values will make it take longe...
virtual bool CanExplode(int i, int j)
Whether or not the tile at the given coordinates can be killed by an explosion (ie....
bool disableSmartInteract
Whether or not the smart tile interaction function is disabled when the cursor hovers above this tile...
int minPick
The minimum pickaxe power required for pickaxes to mine this block. Defaults to 0.
virtual void PostDraw(int i, int j, SpriteBatch spriteBatch)
Allows you to draw things in front of the tile at the given coordinates. This can also be used to do ...
string chest
The default name of this chest that is displayed when this 2x2 chest is open. Defaults to the empty s...
virtual void PlaceInWorld(int i, int j, Item item)
Allows you to do something when this tile is placed. Called on the local Client and Single Player.
virtual bool CanKillTile(int i, int j, ref bool blockDamaged)
Allows you to determine whether or not the tile at the given coordinates can be hit by anything....
virtual bool Slope(int i, int j)
Allows you to control how hammers slope this tile. Return true to allow it to slope normally....
virtual int SaplingGrowthType(ref int style)
Allows this tile to support a sapling that can eventually grow into a tree. The type of the sapling s...
virtual void ChangeWaterfallStyle(ref int style)
Allows you to change the style of waterfall that passes through or over this type of tile.
virtual bool TileFrame(int i, int j, ref bool resetFrame, ref bool noBreak)
Called whenever this tile updates due to being placed or being next to a tile that is changed....
bool torch
Whether or not this tile behaves like a torch. If you are making a torch tile, then setting this to t...
This class is used to keep track of and support the existence of custom sounds that have been added t...
This serves as the central class from which tile-related functions are supported and carried out.
static void PalmTreeGrowthFXGore(int type, ref int gore)
static ModTile GetTile(int type)
Gets the ModTile instance with the given type. If no ModTile with the given type exists,...
static Action< int, int, int >[] HookMouseOverFar
static bool UnlockChest(int i, int j, int type, ref short frameXAdjustment, ref int dustType, ref bool manual)
static void TreeGrowthFXGore(int type, ref int gore)
static void HitWire(int i, int j, int type)
static readonly int vanillaChairCount
static void DropTreeWood(int type, ref int wood)
static void WalkDust(int type, ref int dustType, ref bool makeDust, ref Color color)
static Action< int, int, int, SpriteBatch >[] HookPostDraw
static DelegateTileFrame[] HookTileFrame
static Texture2D GetPalmTreeTopTextures(int type)
static DelegateCanKillTile[] HookCanKillTile
static Func< int, int, int, SpriteBatch, bool >[] HookPreDraw
static bool CanPlace(int i, int j, int type)
static bool IsLockedChest(int i, int j, int type)
static Func< int, int, int, bool >[] HookDrop
static Func< int, int[]>[] HookAdjTiles
static Action< int, int, int >[] HookMouseOver
static void TreeDust(Tile tile, ref int dust)
static bool IsDresser(int type)
static bool SaplingGrowthType(int type, ref int saplingType, ref int style)
static readonly int vanillaTorchCount
static Texture2D GetCactusTexture(int type)
static void MouseOverFar(int i, int j)
static Action< int, int, Item >[] HookPlaceInWorld
delegate void DelegateSetSpriteEffects(int i, int j, int type, ref SpriteEffects spriteEffects)
static void MouseOver(int i, int j)
static DelegateNumDust[] HookNumDust
static Texture2D GetTreeTopTextures(int type, int i, int j, ref int frame, ref int frameWidth, ref int frameHeight, ref int xOffsetLeft, ref int yOffset)
static void NumDust(int i, int j, int type, bool fail, ref int numDust)
static void PalmTreeDust(Tile tile, ref int dust)
static Action< int, int, int >[] HookRightClick
static string ModChestName(int type)
static DelegateDropCritterChance[] HookDropCritterChance
static void KillMultiTile(int i, int j, int frameX, int frameY, int type)
static string ModDresserName(int type)
static bool IsTorch(int type)
static void FloorVisuals(int type, Player player)
static Texture2D GetPalmTreeTexture(Tile tile)
static Func< int, int, int, bool >[] HookKillSound
static Texture2D GetTreeBranchTextures(int type, int i, int j, int trunkOffset, ref int frame)
static bool IsModMusicBox(Tile tile)
static bool PreDraw(int i, int j, int type, SpriteBatch spriteBatch)
static void SetDrawPositions(int i, int j, ref int width, ref int offsetY, ref int height)
static void DropPalmTreeWood(int type, ref int wood)
static void SetSpriteEffects(int i, int j, int type, ref SpriteEffects spriteEffects)
static int AutoSelect(int i, int j, Player player)
delegate void DelegateDropCritterChance(int i, int j, int type, ref int wormChance, ref int grassHopperChance, ref int jungleGrubChance)
static DelegateModifyLight[] HookModifyLight
static Func< int, int, int, bool >[] HookSlope
static Action< int, int, int, SpriteBatch >[] HookSpecialDraw
static void FixSmartInteractCoords(int type, ref int width, ref int height, ref int frameWidth, ref int frameHeight, ref int extraX, ref int extraY)
static void DropCritterChance(int i, int j, int type, ref int wormChance, ref int grassHopperChance, ref int jungleGrubChance)
static Texture2D GetTreeTexture(Tile tile)
delegate void DelegateDrawEffects(int i, int j, int type, SpriteBatch spriteBatch, ref Color drawColor, ref int nextSpecialDrawIndex)
static bool Drop(int i, int j, int type)
static bool HasWalkDust(int type)
static bool CanDropAcorn(int type)
static bool CreateDust(int i, int j, int type, ref int dustType)
static bool CanGrowModTree(int type)
static Action[] HookAnimateTile
static Func< int, int, int, Player, bool >[] HookDangersense
delegate void DelegateModifyLight(int i, int j, int type, ref float r, ref float g, ref float b)
static void KillTile(int i, int j, int type, ref bool fail, ref bool effectOnly, ref bool noItem)
static int OpenDoorID(Tile tile)
static void AdjTiles(Player player, int type)
static DelegateDrawEffects[] HookDrawEffects
delegate void DelegateKillTile(int i, int j, int type, ref bool fail, ref bool effectOnly, ref bool noItem)
static bool Dangersense(int i, int j, int type, Player player)
static void Resize2DArray< T >(ref T[,] array, int newSize)
static void RandomUpdate(int i, int j, int type)
delegate bool DelegateCanKillTile(int i, int j, int type, ref bool blockDamaged)
static void SetAnimationFrame(int type, int i, int j, ref int frameXOffset, ref int frameYOffset)
Sets the animation frame. Sets frameYOffset = modTile.animationFrameHeight * Main....
static Action< int, int, int, bool >[] HookNearbyEffects
delegate bool DelegateCreateDust(int i, int j, int type, ref int dustType)
static bool IsModBed(int type)
delegate int DelegateSaplingGrowthType(int type, ref int style)
static void MineDamage(int minePower, ref int damage)
static int CloseDoorID(Tile tile)
static void CheckModTile(int i, int j, int type)
static bool KillSound(int i, int j, int type)
static void PlaceInWorld(int i, int j, Item item)
static bool IsClosedDoor(Tile tile)
static bool Slope(int i, int j, int type)
static void NearbyEffects(int i, int j, int type, bool closer)
static bool CanGrowModCactus(int type)
static void ModifyLight(int i, int j, int type, ref float r, ref float g, ref float b)
static bool HasSmartInteract(int type)
static Action< int, int, int >[] HookHitWire
static bool PreHitWire(int i, int j, int type)
static Func< int, int, int, bool >[] HookPreHitWire
delegate void DelegateNumDust(int i, int j, int type, bool fail, ref int num)
static DelegateSetSpriteEffects[] HookSetSpriteEffects
static void PickPowerCheck(Tile target, int pickPower, ref int damage)
static DelegateKillTile[] HookKillTile
static readonly int vanillaTableCount
static void DisableSmartCursor(Tile tile, ref bool disable)
static void PostDraw(int i, int j, int type, SpriteBatch spriteBatch)
static bool CanKillTile(int i, int j, int type, ref bool blockDamaged)
static Func< int, int, int, Item, bool >[] HookAutoSelect
static bool TileFrame(int i, int j, int type, ref bool resetFrame, ref bool noBreak)
static DelegateChangeWaterfallStyle[] HookChangeWaterfallStyle
static DelegateCreateDust[] HookCreateDust
static DelegateSaplingGrowthType[] HookSaplingGrowthType
static Action< int, Player >[] HookFloorVisuals
static Action< int, int, int >[] HookRandomUpdate
static bool RightClick(int i, int j)
static Func< int, int, int, bool >[] HookCanExplode
static void AnimateTiles()
delegate void DelegateChangeWaterfallStyle(int type, ref int style)
static readonly int vanillaDoorCount
static void ChangeWaterfallStyle(int type, ref int style)
static void SpecialDraw(int type, int specX, int specY, SpriteBatch spriteBatch)
Special Draw calls ModTile and GlobalTile SpecialDraw methods. Special Draw is called from DrawTiles ...
static void DrawEffects(int i, int j, int type, SpriteBatch spriteBatch, ref Color drawColor, ref int nextSpecialDrawIndex)
static void DisableSmartInteract(Tile tile, ref bool disable)
static bool CanGrowModPalmTree(int type)
static bool CanExplode(int i, int j)
static bool IsSapling(int type)
delegate bool DelegateTileFrame(int i, int j, int type, ref bool resetFrame, ref bool noBreak)
static Func< int, int, int, bool >[] HookCanPlace