I’m trying to write a function that identifies the four corners of the view frustum (in 2d mode), and use those to instantiate a tile every unity unit within the frustum, effectively populating the entire visible play area with tiles:
Vector3 upperLeftScreen = new Vector3(0, Screen.height, Camera.main.depth);
Vector3 upperRightScreen = new Vector3(Screen.width, Camera.main.depth);
Vector3 lowerLeftScreen = new Vector3(0, 0, Camera.main.depth);
Vector3 lowerRightScreen = new Vector3(Screen.width, 0, Camera.main.depth);
//Corner locations in world coordinates
Vector3 upperLeft = Camera.main.ScreenToWorldPoint(upperLeftScreen);
Vector3 upperRight = Camera.main.ScreenToWorldPoint(upperRightScreen);
Vector3 lowerLeft = Camera.main.ScreenToWorldPoint(lowerLeftScreen);
Vector3 lowerRight = Camera.main.ScreenToWorldPoint(lowerRightScreen);
for (int i = (int)upperLeft.x; i < (int)lowerRight.x; i++)
{
for (int j = (int)upperLeft.y; i < (int)lowerRight.y; j++)
{
Instantiate(TileToDraw, new Vector3(i,j,0), Quaternion.identity);
}
}
However, instead of spawning tiles in a rectangle that matches the view frustum, this draws them straight up in a vertical line. Is there something obviously weird with my math? The only other thing I can think of is that ScreenToWorldPoint might not be returning the frustum’s corners like I think it is.
There are multiple problems in your approach to this thing;
A. Where are you going to draw your tiles?
You don’t show the type of your object, but I guess it’s gameobject? It might be easier to just draw tile sprites to fill the canvas instead of filling camera frustum with gameobjects, unless there is some specific reason to fill actual 3D space camera.
You have to then expect that 2D orthographic camera is used, if you are drawing simple 2D tilemap, like it seems, you are not accounting for camera orientation.
B. Depth. I think you don’t get proper with .depth, maybe should use Camera.main.nearClipPlane… but then again, you can leave it as zero because you are using ortho camera. And upperRightScreen Vector3 is missing one value.
C. Your for loop might not work, I’m generally bad with loops, but I think you should calculate ortho camera width and then divide it by your tile width, then you get your x amount of tiles. Same for Y tile amount. You probably have to add padding to each side, since 4x4 tiles might leave gap on side/top/bottom depending on your screen size, so instead draw 5x5 or 6x6 tiles to add some extra tiles it the screen width isn’t divisible by tile size.
Ooh, that works perfectly, thank you guys! I don’t know why, but vector math just tends to short-circuit my brain in the worst of ways. For anyone else who will find it helpful, to answer your original questions:
The tile is a prefab, it’s a sprite, boxcollider, and monobehavior. The tiles are all of uniform size (64x64 pixels, imported so that 64 pixels = 1 unity unit), viewed through an orthographic camera. Since I set them up to each occupy 1 unit of space, I have the leisure of using the map array’s indices as literal coordinates instead of multiplying them.
It’s for a tiled game, the reason I’m using individual gameobjects instead of a single batch-rendered sprite is because each tile is mutable and can change pretty frequently. To keep from melting the cpu with gameobject/monobehavior overhead, I’m only drawing enough tiles to fit in the frustum, then re-positioning them (and changing their sprite) every time the camera moves.