Search Unity

2D Mobile Game GameObjects vs Tilemap

Discussion in '2D' started by SunsetKnight, Aug 29, 2021.

  1. SunsetKnight

    SunsetKnight

    Joined:
    Nov 1, 2012
    Posts:
    2
    Hello,
    I have a question about whether to use game objects or a tile map in my situation. I'm building a 2d mobile game where you click cards that are arranged in a grid. I'll need to establish rules like you can only click cards that don't have other cards under them. I'm thinking that I may have up to 100 cards in say a 10x10 grid.

    What are some of the pros/cons with using a tilemap to do this?

    What are some of the pros/cons with spawning gameobjects to do this?

    Is there another way that I'm missing that might be more ideal?

    Thanks
     
  2. Lo-renzo

    Lo-renzo

    Joined:
    Apr 8, 2018
    Posts:
    1,514
    Tilemap is great when you're rendering lots of things that don't need fancy unique data or logic per instance.

    GameObjects are great when you want individualized behavior (e.g. components) for your objects or objects that individually move. They have more overhead (the g.o., the transform, your components) than Tilemap tiles, but are more versatile.

    A mix is often a good strategy. For example, if you imagine a world with trees in the foreground and grass/dirt in the background, the trees may be more appropriate as gameobjects, whereas the grass/dirt could be represented as tiles.

    For your particular case, 100 cards isn't very much so performance is less of a concern. Moreover, since the player could click and drag a card to move, that suggests that GameObjects might be more intuitive. A card is locked into a slot but then when clicked follows the mouse. If you were to accomplish the same with tilemaps, that might be a bit more complicated: spawning a GameObject to represent the card while it is dragged through the air. Finally, it may be useful to encapsulate different behaviors of your card types into components.

    Overall, I think it would be wise to start with GameObjects and components.

    In either case, you'll need some data structure that represents the grid with all the slots that cards can go. Without knowing the rules of your game, it is difficult to speculate how this might work. I imagine one strategy is to keep a Dictionary<Vector2Int, List<Card>> which represents the cards stacked on top of one another in each slot, and on clicking you check the topmost card in that list.

    It still may be helpful to borrow part of the Tilemap, though... the Grid. The grid provides a few nice methods to translate between gridspace - the slot/cell for each card - and worldspace. Methods like grid.WorldToCell and grid.CellToWorld may be useful. If you have the position of a card in the world, you can ask the grid to translate that world position to the correct Vector2Int slot. When placing a card, you translate from its worldspace to register it to the Vector2Int slot.
     
    SunsetKnight likes this.
  3. SunsetKnight

    SunsetKnight

    Joined:
    Nov 1, 2012
    Posts:
    2
    This was my understanding as well, I just wasn't sure where that boundary of logic would be drawn for it being too much for a tilemap.

    This makes a lot of sense, to mix tiles and game objects into the scene depending on what they need to do.

    I think because my cards are going to be interactive, it makes sense like you said to start with game objects. Also a great point on encapsulating the behaviors.

    I originally started with GameObjects and was using raycasting to detect if a card was below it. I eventually moved over to a multidimensional array where I stored the row and column of the grid where the value was the card. That way I could easier detect if a card was below the clicked card. That seemed like a better way to go and is similar to what you suggested with using a Dictionary. I'll have to play around with this structure some more as I build out the game.

    This is actually a great suggestion that I didn't even think about. One of the reasons why I started exploring tilemaps was two fold. For one I stumbled upon a video showing the performance differences between sprites and tilemaps and I was blown away by the difference. I'll put that video down below.

    The other part why I was exploring tilemaps was because I was trying to figure out a way to deal with different device sizes and how to properly draw the screen so everything would fit with an orthographic camera. The grid helped with that where I could use the `cellBounds` to try to change the camera position and orthographicSize that I was having a hard time figuring out how to do with just a bunch of game objects, but maybe using the grid with the game objects would help me with that. Here's how I was doing it with the tilemap:

    Code (CSharp):
    1. float screenRatio = (float)Screen.width / (float)Screen.height;
    2. float targetRatio = (float)tileMap.cellBounds.size.x / (float)tileMap.cellBounds.size.y;
    3.  
    4. if (screenRatio >= targetRatio)
    5. {
    6.     Camera.main.orthographicSize = (float)tileMap.cellBounds.size.y / 2;
    7. }
    8. else
    9. {
    10.     float differenceInSize = targetRatio / screenRatio;
    11.     Camera.main.orthographicSize = ((float)tileMap.cellBounds.size.y / 2) * differenceInSize;
    12. }
    13.  
    14. float newCameraX = Camera.main.aspect * Camera.main.orthographicSize;
    15. float newCameraY = Camera.main.orthographicSize;
    16.  
    17. Camera.main.transform.localPosition = new Vector3(newCameraX - 0.5f, newCameraY, -27f);

    Thank you for your detailed reply!