Java-Gaming.org Hi !
 Featured games (83) games approved by the League of Dukes Games in Showcase (523) Games in Android Showcase (127) games submitted by our members Games in WIP (591) games currently in development
 News: Read the Java Gaming Resources, or peek at the official Java tutorials
Pages: [1]
 ignore  |  Print
 Picking Tile in staggered isometric map  (Read 2527 times) 0 Members and 1 Guest are viewing this topic.
Xyle
 « Posted 2012-12-16 11:57:57 »

Hello!
I have been looking and trying for quite a while now, but can't seem to work out an algorithm for figuring out which tile is selected on a staggered isometric map using 64x32 tiles with a diamond shape inside.

Here is a pic of my map...

The first row is drawn, then the x is offset to the right by 32 and the next row is drawn.

Anyone have any good math skills to throw some algorithms my way for this?
Thanks for any help!

PS: My math isn't exactly top notch, so please keep that in mind.

Life is just a game, learn to play!
------------------------------------------
╬-YellzBellz Games!-╬
dapy
 « Reply #1 - Posted 2012-12-16 13:29:06 »

You can indeed solve this with a little maths.
In my isometric games, I use the following code to calculate where to draw a given tile:

 1  2 `int screenx = (int)(TILE_WIDTH * (tilex - tiley)/2.0);int screeny = (int)(TILE_HEIGHT * (tilex + tiley)/2.0);`

- screenx and screeny are the position on screen
- tilex and tiley are the tile position in the game world
- in your case, TILE_WIDTH = 64 and TILE_HEIGHT = 32
- some games may include a camera offset, but in principal they all work the same way

To determine which tile is selected on screen, you can use simultaneous equations to find tilex and tiley. Basically, make tilex the subject of the first equation, and tiley the subject of the second. I can explain this bit in more detail if you like...
Solving the simultaneous equations results in the following code:

 1  2 `int tilex = (int)(screenx/TILE_WIDTH + screeny/TILE_HEIGHT);int tiley = (int)(screeny/TILE_HEIGHT - screenx/TILE_WIDTH);`

Xyle
 « Reply #2 - Posted 2012-12-16 17:17:24 »

Thanks for the input Dapy,

I'm kind of confused on what tileX and tileY are returning in this formula...
int tilex = (int)(screenx/TILE_WIDTH + screeny/TILE_HEIGHT);
int tiley = (int)(screeny/TILE_HEIGHT - screenx/TILE_WIDTH);

are those the coordinates for the tile that was clicked?

I dont have any offsets, so I am starting my drawing at 0,0 on the screen
I am using this for drawing my tiles...
 1  2  3  4  5  6  7  8  9  10  11  12  13 `for (var i = 0; i < rows; ++i) {   for (var j = 0; j < cols; ++j) {      tTile._y = i*16;      // handle odd and even rows differently      if (i % 2) {        // Even Row        tTile._x = (j*64)+32;      } else {        // odd row        tTile._x = j*64;      }   }}`

PS: should also explain that I'm not very good at abstract logic either, hehehe.

Life is just a game, learn to play!
------------------------------------------
╬-YellzBellz Games!-╬
dapy
 « Reply #3 - Posted 2012-12-16 18:25:51 »

Yes - tilex and tiley are the co-ordinates of the clicked tile.

In my game, tile data is stored in a 2-dimensional array, something like this:

 1 `Tile[][] tileData = new Tile[TOTAL_COLUMNS][TOTAL_ROWS];`

Therefore I can access the tile data like this:

 1  2  3  4  5  6  7  8  9 `// find which tile the player has clickedint tilex = (int)(screenx/TILE_WIDTH + screeny/TILE_HEIGHT);int tiley = (int)(screeny/TILE_HEIGHT - screenx/TILE_WIDTH);// respond to the click depending on what is in that tileif (tileData[tiley][tilex] == Tile.BLOB) {  // do something to BLOB tile} else if (...) {  // ... etc etc...`
Xyle
 « Reply #4 - Posted 2012-12-16 19:19:07 »

I create my tiles from a Tile object that has individual fields. I do store the x and y of the tile, but that just references the top left corner of the 64x32 tile, where it will be drawn. Plus I would have to iterate through all tiles until that tile is matched which would still be pointing to the tiles drawing origin.

Of course this is in Flash, but the ideas are still the same. The formula for picking a tile in a diamond shape isometric map that was given by dishmoth in this post...
http://www.java-gaming.org/topics/get-row-and-col-of-mouse-click-on-isometric-map/21914/msg/252507/view.html#msg252507
worked great for the diamond shape isometric map. But trying to chop that up to make it work for a staggered isometric map is proving to be quite a challenge. The issue I believe is in the staggering of the rows.

I will keep staring at it until my eyes fall out in great goobs of goo

Life is just a game, learn to play!
------------------------------------------
╬-YellzBellz Games!-╬
matheus23

JGO Kernel

Medals: 113
Projects: 3

You think about my Avatar right now!

 « Reply #5 - Posted 2012-12-16 19:27:46 »

Danny02, where are you? ^^

See my:
My development Blog:     | Or look at my RPG | Or simply my coding
http://matheusdev.tumblr.comRuins of Revenge  |      On Github
dapy
 « Reply #6 - Posted 2012-12-16 22:28:43 »

Ah, now I understand!
The technique I described is pretty much the same as dishmoth's - it works for 'diamond' isometric, but not for 'staggered'.

The following link explains how you might solve the problem for 'staggered' isometric maps:

http://www.gamedev.net/page/resources/_/technical/game-programming/isometric-n-hexagonal-maps-part-i-r747

Look for the heading 'Mouse Matters'.
Xyle
 « Reply #7 - Posted 2012-12-19 04:58:03 »

I appreciate the help. It being the work week, I didn't get a chance to really put some time into any solution and I definitely am not going to post the embarassing hack I was attempting.

I did get a plug and play solution involving some math equations that are quite a bit beyond me that I will post for anyone running into the same situation. It works great!

dawsonk
Maybe try something like this...

 1  2  3  4  5  6  7  8  9  10  11  12  13  14  15  16  17  18  19  20  21  22  23  24  25  26  27  28  29  30  31  32  33  34  35  36  37  38  39  40  41  42  43  44  45  46  47  48  49  50  51  52  53  54  55  56  57 `        var tileW = 64;    var tileH = 32;    var rows = 8;    var cols = 4;    for (var i = 0; i < rows; ++i) {            for (var j = 0; j < cols; ++j) {                    tTile = _root.attachMovie("Tile", "R" + i + "C" + j, _root.getNextHighestDepth());                    tTile._x = (tileW * j) + ((i % 2 == 1) ? 32 : 0);                    tTile._y = (tileH / 2) * i;            }    }    onMouseDown = function () {            var ax, ay, bx, by;            var cx = _xmouse;            var cy = _ymouse;            var posX = (_xmouse / 32) >> 0;            var posY = (_ymouse / 16) >> 0;            if ((posX % 2) == (posY % 2)) {                    ax = (posX) * 32;                    ay = (posY + 1) * 16;                    bx = (posX + 1) * 32;                    by = (posY) * 16;                    if (getPos(ax, ay, bx, by, cx, cy) < 0) {                            trace(((posY / 1 >> 0) - 1) + " : " + ((posX / 2 >>0) + ((((posY / 1 >> 0) - 1) % 2 == 0) ? 0 : -1)));                    } else {                            trace((posY / 1 >> 0) + " : " + (posX / 2 >> 0));                    }            } else {                    ax = (posX) * 32;                    ay = (posY) * 16;                    bx = (posX + 1) * 32;                    by = (posY + 1) * 16;                    if (getPos(ax, ay, bx, by, cx, cy) < 0) {                            trace(((posY / 1 >> 0) - 1) + " : " + (posX / 2 >>0));                    } else {                            trace((posY / 1 >> 0) + " : " + ((posX / 2 >> 0) +((((posY / 1 >> 0) - 1) % 2 == 0) ? -1 : 0)));                    }            }    };    function getPos(\$ax, \$ay, \$bx, \$by, \$cx, \$cy) {            // below = 1, above = -1, on = 0;            var slope = (\$by - \$ay) / (\$bx - \$ax);            var yIntercept = \$ay - \$ax * slope;            var cSolution = (slope * \$cx) + yIntercept;            if (slope != 0) {                    if (\$cy > cSolution) {                            return \$bx > \$ax ? 1 : -1;                    }                    if (\$cy < cSolution) {                            return \$bx > \$ax ? -1 : 1;                    }                    return 0;            }            return 0;    }`

Life is just a game, learn to play!
------------------------------------------
╬-YellzBellz Games!-╬
Pages: [1]
 ignore  |  Print

You cannot reply to this message, because it is very, very old.

 Add your game by posting it in the WIP section, or publish it in Showcase. The first screenshot will be displayed as a thumbnail.
 Gibbo3771 (10 views) 2014-11-24 19:59:16 trollwarrior1 (35 views) 2014-11-22 12:13:56 xFryIx (73 views) 2014-11-13 12:34:49 digdugdiggy (52 views) 2014-11-12 21:11:50 digdugdiggy (46 views) 2014-11-12 21:10:15 digdugdiggy (40 views) 2014-11-12 21:09:33 kovacsa (66 views) 2014-11-07 19:57:14 TehJavaDev (70 views) 2014-11-03 22:04:50 BurntPizza (68 views) 2014-11-03 18:54:52 moogie (83 views) 2014-11-03 06:22:04
 basil_ 29x theagentd 28x HeroesGraveDev 25x BurntPizza 20x Spasi 19x Riven 18x KevinWorkman 15x princec 13x SHC 12x LiquidNitrogen 11x gouessej 11x Gibbo3771 11x kevglass 11x CopyableCougar4 10x kpars 10x Longarmx 9x
 Understanding relations between setOrigin, setScale and setPosition in libGdx2014-10-09 22:35:00Definite guide to supporting multiple device resolutions on Android (2014)2014-10-02 22:36:02List of Learning Resources2014-08-16 10:40:00List of Learning Resources2014-08-05 19:33:27Resources for WIP games2014-08-01 16:20:17Resources for WIP games2014-08-01 16:19:50List of Learning Resources2014-07-31 16:29:50List of Learning Resources2014-07-31 16:26:06
 java-gaming.org is not responsible for the content posted by its members, including references to external websites, and other references that may or may not have a relation with our primarily gaming and game production oriented community. inquiries and complaints can be sent via email to the info‑account of the company managing the website of java‑gaming.org