Complete.Org: Mailing Lists: Archives: freeciv-dev: August 1999:
Re: [Freeciv-Dev] Hex map implementation
Home

Re: [Freeciv-Dev] Hex map implementation

[Top] [All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index] [Thread Index]
To: Freeciv Dev <freeciv-dev@xxxxxxxxxxxx>
Subject: Re: [Freeciv-Dev] Hex map implementation
From: Falk Hueffner <falk.hueffner@xxxxxxxxxxxxxxxxxxxxxxxx>
Date: 17 Aug 1999 12:25:34 +0200

Artur Biesiadowski <abies@xxxxxxxxx> writes:

> I've started playing with hex map. For now just class in java, generic
> enough it could be used for some wargame if freeciv will not choose
> hexes after all.
> 
> I've decided to use vertically flattened hexes. They fit into square - a
> lot simplier to make calculations/repaint etc. Normal hex should have
> proportions of 2 x sqrt(3) and they have just 2 x 2.
> 
> If somebody thinks that hexes are very simple, here are two routines
> that given the point on screen (actually on map, but it's not important)
> return Point with tile coordinates.

(code snipped)

That can be done easier; the readable variant is

HexCoord PointToHex( int xp, int yp )
{
    // NOTE:  HexCoord(0,0)'s x() and y() just define the origin
    //        for the coordinate system; replace with your own
    //        constants.  (HexCoord(0,0) is the origin in the hex
    //        coordinate system, but it may be offset in the x/y
    //        system; that's why I subtract.)
    double x = 1.0 * ( xp - HexCoord(0,0).x() ) / HexXSpacing;
    double y = 1.0 * ( yp - HexCoord(0,0).y() ) / HexYSpacing;
    double z = -0.5 * x - y;
           y = -0.5 * x + y;
    int ix = floor(x+0.5);
    int iy = floor(y+0.5);
    int iz = floor(z+0.5);
    int s = ix+iy+iz;
    if( s )
    {
        double abs_dx = fabs(ix-x);
        double abs_dy = fabs(iy-y);
        double abs_dz = fabs(iz-z);
        if( abs_dx >= abs_dy && abs_dx >= abs_dz )
            ix -= s;
        else if( abs_dy >= abs_dx && abs_dy >= abs_dz )
            iy -= s;
        else
            iz -= s;
    }
    return HexCoord( ix, ( iy - iz + (1-ix%2) ) / 2 );
}

and the short variant is

HexCoord PointToHex( int xp, int yp )
{
    // NOTE:  First we subtract the origin of the coordinate
    //        system; replace with your own values
    xp -= X_ORIGIN;
    yp -= Y_ORIGIN;
    int row = 1 + yp / 12;
    int col = 1 + xp / 21;
    int diagonal[2][12] = {
        {7,6,6,5,4,4,3,3,2,1,1,0},
        {0,1,1,2,3,3,4,4,5,6,6,7}
    };

    if( diagonal[(row+col)%2][yp%12] >= xp%21 )
        col--;
    return HexCoord( col, (row-(col%2))/2 );
}

(I can dig out where I got this from if somebody is interested, there
is some more stuff about hex tiles.)

I really don't think Hex tiles are difficult in any aspect, especially 
if you're using a language with nice abstract data types. The
difficult thing is to change the thousands of places in the Freeciv
code that depend on squares.

        Falk


[Prev in Thread] Current Thread [Next in Thread]