Thanks so much!For that, simply put your WorldGen code in the CheckDead() or NPCLoot() methods of your NPC.
int size = 10;
//Assuming building is placed from left to right, starting on the way left.
int doorX = position.X;
WorldGen.PlaceObject(/* Forgot what goes here. But you know. :P */);
//Assuming building is placed right to left, starting on the way right.
doorX = position.X + size;
WorldGen.PlaceObject(/* etc. */);
//Assuming building is placed from middle.
doorX = position.X - (size / 2); //On left.
doorX = position.X + (size / 2); //On right.
WorldGen.PlaceTile(k + -1, l + 2, 10, true, false, 0, 4);
HI! Thanks For guide, it helps so much! but how I can transform my biome to something like beehive? (with clear space inside) cuz right now it's looking like this:
And if i can ask, can you add to your guide how to make custom structure that spawns inside biome? Like Abeemination in hive. or jungle shrines.
Thanks a lot!
Ok finally an update - I could not get the door to work by the code given above It spawns doors but they are not attached to the walls around them so they drop when interacted with.
This did work, for placing specific type of door(in this case a cactus door). But it's not consistent(sometimes there is a door, most times not) and I can't figure out why.
PlaceObject might have a random placement chance, and so mayn't place sometimes. Not sure. Code please (post on http://hastebin.com or http://pastebin.com)
I believe this is a somewhat outdated tutorial.For the comet example,Code:getSurface does not exist in the current context
Hello people!
It seems that there has been an explosion of World Generation in mods, and, well, I want to make it bigger/I'm bored.
Note: This tutorial is a bit complicated. You should know how to at least make a basic NPC before you read this. Or be crazy and read it anyways.
So, here will be a basic tutorial on how to make simple lines/passageways, blobs of block, or pools/mini biomes, which will come later.
Ok, let's start off now
First off, it'd be useful to have something to base off, so ExampleMod has a decent example (duh) with it's Well. Use that and tinker for a bit, change the water to dirt, as to get a feel for it.
Basic Blob Making
Then, once you're done turning a well into a blob, we can begin.
Go into your ModWorld.cs file add a method called ModifyWorldGenTasks()
The full method is here:
Code:public override void ModifyWorldGenTasks(List<GenPass> tasks, ref float totalWeight)
Obviously, put {} around it. Now, let's start with a blobbecause I'm lazy.
Code:public override void ModifyWorldGenTasks(List<GenPass> tasks, ref float totalWeight) { int genIndex = tasks.FindIndex(genpass => genpass.Name.Equals("Micro Biomes")); tasks.Insert(genIndex + 1, new PassLegacy("Dirt Blob", delegate (GenerationProgress progress) { WorldGen.TileRunner(Main.spawnTileX, Main.spawnTileY + -46, 6, Main.rand.Next(1, 3), TileID.Dirt, true, 0f, 0f, true, true); })); }
Here's an explanation of what's in the TileRunner method.
So, I and J is X and Y, respectively. Strength decides how big it is (I can't understand the code enough to give a presise measurement.) Type is the type of tile, in TileID, int, or mod.tiletype. Add Tile checks if you're adding tiles or replacing them. SpeedX and Y sets the direction it goes is (also don't understand the code). noYChange is just that. It doesn't change Y. overRide means it can override other tiles.Code:TileRunner(int i, int j, double strength, int steps, int type, bool addTile = false, float speedX = 0f, float speedY = 0f, bool noYChange = false, bool overRide = true)
That should place a blob of dirt above the player. You can replace the TileID with any other ID or mod.TileType("") if you wish.
That is the simplest of the things you can possibly do.
I'll keep the above code for future inserts, so I don't have to re-write it over. And over. And over again
So when I say something of this sort: Add code into your existing method, it means add the code into the Dirt Blob thing
Making a Line
Now for something a bit less...blobby.
I personally did this in a method as to make it easier to randomize, but you may do whatever you want.
So, there is a method in WorldGen called PlaceTile. It's a more precise way of using TileRunner.
Here is the method.
Please note that it places in tile positions, so if you want to place it in game at, say, npc.position.X, do npc.position.X / 16.Code:WorldGen.PlaceTile(int X, int Y, int TileType);
So, we use a for loop to make a straight line, like this:
Code:for (int i = 0; i < 10; i++) { WorldGen.PlaceTile(Main.spawnTileX + i, Main.spawnTileY - 30, TileID.Iron); }
If you add that, it should make a 10 block long iron ore thing. I might've gotten the TileID wrong, but you get the point.
View attachment 131880
Now let's get to the really fun stuff
Overriding a Biome
Are you tired of having Jungles in your world? Don't Jungle Bats bother you when you're setting up your mud hut? Well, I got the fix for you! Code. yay?
Anyways, yes, you can remove biomes and put a bunch of whatever there.
So now you should have no jungle (if I remembered the name correctly) and an extra blob of dirt, but below you. Do not put this is the same code block (These: { }) as the previous dirt blob, that will give an error. Still needs verifacation.Code:int jungleGen = tasks.FindIndex(genpass => genpass.Name.Equals("Jungle")); tasks[jungleGen] = new PassLegacy("More Dirt Blobs", delegate (GenerationProgress progress) { WorldGen.TileRunner(Main.spawnTileX, Main.spawnTileY + 12, 6, Main.rand.Next(1, 3), TileID.Dirt, true, 0f, 0f, true, true); });
How to Place Multi blocks
As shown above, people want to know how to place something such as a Table or Chair.
So, you have to use the WorldGen.PlaceTile method.
This, without testing, should place an Example Chair 10 blocks away from the player.Code://PlaceObject(int x, int y, int type, bool mute = false, int style = 0, int alternate = 0, int random = -1, int direction = -1)[code] That's an explanation of the args.[/SPOILER] So, this will place a modded chair in the X and Y: [code] WorldGen.PlaceObject(Main.spawnTileX + 10, Main.spawnTileY, mod.TileType("ExampleChair"), false, 0, 0, -1, 1);
Placing a Chest
I've barely explored this concept; you could make a "starter chest" near spawn with some good lewt. Or, just a Meowmere. Either work.
So, you can't place chests with PlaceObject (for some reason) so you need PlaceChest. Code shown below.
So, basic explanation of what those do: X and Y is duh. Type is what chest type. notNearOtherChests makes it so you can't place a chest there if it's near another. Style is what frame.X is should be at, used for placing locked chests.Code:WorldGen.PlaceChest(int X, int Y, int type, bool noNearOtherChests = false, int style = 0);
So, just dofor a chest to appear next to the player. Not sure what chest though, the chest tilesheet is the longest thing ever. (Needs testing)Code:WorldGen.PlaceChest(Main.spawnTileX - 10, Main.spawnTileY, 21, false, 2);
Making a Meteor-like biome
Easy enough
So, here is a method that makes a 'comet' out of any pre-hardmode ore, except Demonite, Hellstone and Crimtane. It places this anywhere above ground, with it initially spawning above the world, and doesn't place until it hits a block. This method won't do anything alone, though, you'll place it in the Kill method of a projectile, which is easiest. The projectile should call Kill OnTileCollide(). Code:Code:public void OreComet() { int x = Main.rand.Next(0, Main.maxTilesX); int y = Main.worldSurface - 200; int[] tileIDs = { 6, 7, 8, 9 , 166, 167, 168, 169}; if (Main.tile[x, y].type <= -1) { y--; } else { WorldGen.TileRunner(x, y, 2, 4, tileIDs[Main.rand.Next(tileIDs.Length)], false, 0f, 0f, true, true); return; } }
That should have a 0.1% chance to spawn every frame.Code:public override void Kill() { OreComet(); }
Have fun!
Floating Islands
Let's spam us some candy cane w/ red team block floating islands.
As suggested by @Jenosis
Anyways, I'll be using a method named (by me, since I'm creative) BlockLining.
This will make a "lining" of blocks either as tall as Max or a random of Min, Max.Code:public int BlockLining(double x, double y, int repeats, int tileType, bool random, int max, int min = 3) { for (double i = x; i < x + repeats; i++) { if (random) { for (double k = y; k < y + Main.rand.Next(min, max); k++) { WorldGen.PlaceTile((int)i, (int)k, tileType); } } else { for (double k = y; k < y + max; k++) { WorldGen.PlaceTile((int)i, (int)k, tileType); } } } return repeats; }
Now for the actual island. I used it in an inefficient way, but it makes it easier to read.
Basically, it makes an "outline" of clouds out of BlockLinings and then places Mushroom Grass and Mud in the center.Code:public void MiniIsland() { double X = WorldGen.genRand.Next(0, Main.maxTilesX); double Y = (double)Main.worldSurface - Main.rand.Next(255, 270); for (int i = 0; i < 13; i++) { if (i == 0) { BlockLining(X, Y - 4, 4, TileID.Cloud, true, 6); } else if (i == 1) { BlockLining(X + 4, Y - 3, 4, TileID.Cloud, true, 6); } else if (i == 2) { BlockLining(X + 8, Y - 2, 4, TileID.Cloud, true, 6); } else if (i == 3) { BlockLining(X + 12, Y - 1, 5, TileID.Cloud, true, 6); } else if (i == 4) { BlockLining(X + 17, Y, 5, TileID.Cloud, true, 6); } else if (i == 5) { BlockLining(X + 21, Y + 1, 6, TileID.Cloud, true, 6); } else if (i == 6) { BlockLining(X + 27, Y + 2, 6, TileID.Cloud, true, 6); } else if (i == 7) { BlockLining(X + 33, Y + 1, 7, TileID.Cloud, true, 6); } else if (i == 8) { BlockLining(X + 40, Y, 5, TileID.Cloud, true, 6); } else if (i == 9) { BlockLining(X + 45, Y - 1, 5, TileID.Cloud, true, 6); } else if (i == 10) { BlockLining(X + 49, Y - 2, 4, TileID.Cloud, true, 6); } else if (i == 11) { BlockLining(X + 53, Y - 3, 4, TileID.Cloud, true, 6); } else if (i == 12) { BlockLining(X + 57, Y - 4, 4, TileID.Cloud, true, 6); }//z else if (i == 13) { BlockLining(X + 61, Y - 5, 4, TileID.Cloud, true, 6); } } for (double i = X + 4; i < X + 57; i++) WorldGen.PlaceTile((int)i, (int)Y - 4, TileID.MushroomGrass); for (double i = X + 8; i < X + 53; i++) WorldGen.PlaceTile((int)i, (int)Y - 3, TileID.Mud); for (double i = X + 12; i < X + 49; i++) WorldGen.PlaceTile((int)i, (int)Y - 2, TileID.Mud); for (double i = X + 16; i < X + 45; i++) WorldGen.PlaceTile((int)i, (int)Y - 1, TileID.Mud); for (double i = X + 21; i < X + 40; i++) WorldGen.PlaceTile((int)i, (int)Y, TileID.Mud); for (double i = X + 26; i < X + 33; i++) WorldGen.PlaceTile((int)i, (int)Y + 1, TileID.Mud); }
View attachment 144435
Change any of the TileIDs to your liking. Have fun!
Placing a Tree, and growing the Tree
This one is pretty simple, really. I'll just slap in some code and done
do that as a base. Make it 3 wide, so the tree will go properly.Code:WorldGen.PlaceTile(X, Y, TileID.Dirt);
Then:
This will grow the MagicSapling if it can. Otherwise, it'll simply place a sapling.Code:WorldGen.PlaceObject(X, Y - 1, mod.TileType("MagicSapling)); WorldGen.GrowTree(X, Y - 1);
Notify me on this thread/my profile page if this doesn't work. Thanks!
Placing Walls
It's basically the same as placing a tile. But with walls. Woah.
Here's two:orCode:WorldGen.PlaceTile(int i, int j, int type)
Simple enoughCode:Main.tile[i, j].wall = WallID.MudUnsafe;
Changing Tile Slopes
Also simple.
From what I know, it goes from 0 to 12. Tell me if I'm wrong.Code:Main.tile[i, j].slope(0);
TileIDs can be found here: https://github.com/bluemagic123/tModLoader/wiki/Vanilla-Tile-IDs
Some useful (ints) things for WorldGen are Main.maxTilesY, same thing but with X, Main.spawnTileY, and X.
Main.spawnTileX +/- 300-400 is the Snow/Desert biome. Main.maxTilesY - 200 is the top of the Underworld.
The amount of derps done here: 9 so far.
I will expand this upon user request, though I won't do your WorldGen for you.
Anyways, that'll be it for now. Leave any comments/questions/suggestions below
Credits
Thanks to @Graydee for being helpful with worldgen on occasion
Thanks to @EchoNex for the first WorldGen code he gave me.
Thanks to @jopojelly for random helps
I request that anyone who uses this tutorial and publishes it in any way, Mod Browser or not, gives me any sort of credit. Either it be a link to this thread, a link to me, a simple "thanks to gabe for some worldgen stuff", please do it
Ok, so i just need this and the grass seed item and it will work on standard dirt?https://hastebin.com/bodeqifava.cs
Thanks to @Dan Yami for the original code, I just edited it a bunch.