Complete.Org: Mailing Lists: Archives: freeciv-dev: April 2004:
[Freeciv-Dev] (PR#8507) generalized tile boundaries
Home

[Freeciv-Dev] (PR#8507) generalized tile boundaries

[Top] [All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index] [Thread Index]
To: undisclosed-recipients: ;
Subject: [Freeciv-Dev] (PR#8507) generalized tile boundaries
From: "Jason Short" <jdorje@xxxxxxxxxxxxxxxxxxxxx>
Date: Tue, 13 Apr 2004 13:14:57 -0700
Reply-to: rt@xxxxxxxxxxx

<URL: http://rt.freeciv.org/Ticket/Display.html?id=8507 >

Currently there are a lot of places that draw boundary lines:

   - The map grid.
   - Borders.
   - Coastlines.
   - City selection rectangles.
   - Unavailable city tiles.

Each of these hard-codes not just the locations of the tile borders but 
also how many borders there are.  It is not easily extensible - for 
instance to use a hex tileset you have to add lots of new code all over 
the place.

My proposal is that a function is created to return the positions of 
each tile boundary:

static bool get_tile_boundaries(enum direction8 dir,
                                int inset, int width,
                                 enum draw_type draw,
                                int *start_x, int *start_y,
                                int *end_x, int *end_y)

this function finds the starting and ending position for a line along 
the boundary.

   - dir specifies the direction of the boundary.  Currently only
     cardinal directions have boundaries.  (With hex tiles diagonals
     may as well).
   - inset specifies how far the line is to be inset from the side.  For
     instance the map grid isn't inset at all but the unavailable city
     tiles "red frame" and the city selection rectangles are generally
     inset by 1 pixel.
   - width specifies the width of the line.  Borders have width 2, all
     other current lines have width 1.  This must be handled separately
     because we have to move the line to account for its width.  Also
     width 2 lines do not overlap at the boundaries (like the map grid
     does).
   - draw specifies the draw_type of this tile.  For iso-view if you're
     only drawing part of the tile not all boundaries are visible.
   - start_x, start_y, end_x, end_y give the position of the line.

The return value specifies whether the line is visible on the tile. 
This may be FALSE if:

   - The direction is invalid (for instance northeast).
   - The line is on another tile (the eastern map grid line is actually
     on the adjacent tile, and so isn't drawn as part of this tile).
   - The draw_type is such that the line isn't visible.

All in all, this function is very nice.

However some users do run into a significant problem: In iso-view we 
can't cleanly draw at the south and east of our tile, because when the 
tiles below/right of the current tile are drawn their terrain will cover 
the lines.  Therefore for borders and the selection rectangle we have to 
draw the lines as a part of those south/east tiles rather than as a part 
of this tile.  It is ugly.  The only sure way to fix this is to use a 
layered drawing algorithm - first drawing _all_ terrain, then _all_ 
gridlines, then _all_ units and cities.  In cityview this is basically 
what is done.

(Another way to fix this is to change the tilesets to match the 
mathematical tile boundaries, or change the math to match tile tileset's 
tile boundaries.  Either will be error-prone.)

jason

? foo.png
Index: client/mapview_common.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/mapview_common.c,v
retrieving revision 1.100
diff -u -r1.100 mapview_common.c
--- client/mapview_common.c     13 Apr 2004 16:05:08 -0000      1.100
+++ client/mapview_common.c     13 Apr 2004 20:13:48 -0000
@@ -738,37 +738,127 @@
 }
 
 /****************************************************************************
+  Return the vertices of the given edge of the tile.  This will return
+  FALSE if the edge doesn't exist (or if it does exist but is part of an
+  adjacent tile).
+
+  The result is intended to be used to draw lines via canvas_put_line.
+
+  inset specifies how many pixels inward the boundary is to be inset.  This
+  is generally 0 or 1.
+
+  width specifies the width of the boundary - generally 1 or 2.  For
+  instance if the boundary is 2 pixels wide then the right and bottom
+  positions must be translated so it's drawn in the right location.
+****************************************************************************/
+static bool get_tile_boundaries(enum direction8 dir,
+                               int inset, int width, enum draw_type draw,
+                               int *start_x, int *start_y,
+                               int *end_x, int *end_y)
+{
+  const int W = NORMAL_TILE_WIDTH, H = NORMAL_TILE_HEIGHT;
+  const int overlap = (width > 1) ? 1 : 0;
+
+  assert(inset >= 0);
+  assert(width >= 1);
+
+  width--;
+
+  /* Note that the boundary (with inset 0) may actually cover some adjacent
+   * tiles, since the left boundary for this tile is equivalent to the right
+   * boundary for the tile to our left.  The north and west boundaries will
+   * be on this tile while the south and east boundaries must be drawn as
+   * part of the adjacent tiles. */
+
+  if (is_isometric) {
+    switch (dir) {
+    case DIR8_NORTH:
+      /* Top right. */
+      *start_x = W / 2;
+      *end_x = W - inset;
+      *start_y = inset + width;
+      *end_y = H / 2 + width;
+      return (draw & D_M_R);
+    case DIR8_SOUTH:
+      /* Bottom left. */
+      *start_x = inset;
+      *end_x = W / 2;
+      *start_y = H / 2 - overlap;
+      *end_y = H - inset - overlap;
+      return (draw & D_B_L) && (inset + overlap) > 0;
+    case DIR8_EAST:
+      /* Bottom right. */
+      *start_x = W - inset;
+      *end_x = W / 2;
+      *start_y = H / 2 - overlap;
+      *end_y = H - inset - overlap;
+      return (draw & D_B_R) && (inset + overlap) > 0;
+    case DIR8_WEST:
+      /* Top left. */
+      *start_x = inset;
+      *end_x = W / 2;
+      *start_y = H / 2 + width;
+      *end_y = inset + width;
+      return (draw & D_M_L);
+    case DIR8_NORTHEAST:
+    case DIR8_SOUTHEAST:
+    case DIR8_SOUTHWEST:
+    case DIR8_NORTHWEST:
+      return FALSE;
+    }
+  } else {
+    switch (dir) {
+    case DIR8_NORTH:
+      *start_x = inset;
+      *end_x = W - inset;
+      *start_y = *end_y = inset + width;
+      return TRUE;
+    case DIR8_SOUTH:
+      *start_x = inset;
+      *end_x = W - inset;
+      *start_y = *end_y = H - inset - overlap;
+      return inset + overlap > 0;
+    case DIR8_EAST:
+      *start_x = *end_x = W - inset - overlap;
+      *start_y = inset;
+      *end_y = H - inset;
+      return inset + overlap > 0;
+    case DIR8_WEST:
+      *start_x = *end_x = inset + width;
+      *start_y = inset;
+      *end_y = H - inset;
+      return TRUE;
+    case DIR8_NORTHEAST:
+    case DIR8_SOUTHEAST:
+    case DIR8_SOUTHWEST:
+    case DIR8_NORTHWEST:
+      return FALSE;
+    }
+  }
+
+  assert(0);
+  return FALSE;
+}
+
+
+/****************************************************************************
   Draw a red frame around the tile.  (canvas_x, canvas_y) is the tile origin.
 ****************************************************************************/
 void put_red_frame_tile(struct canvas *pcanvas,
                        int canvas_x, int canvas_y)
 {
-  if (is_isometric) {
-    canvas_put_line(pcanvas, COLOR_STD_RED, LINE_TILE_FRAME,
-                   canvas_x + NORMAL_TILE_WIDTH / 2 - 1, canvas_y,
-                   NORMAL_TILE_WIDTH / 2, NORMAL_TILE_HEIGHT / 2 - 1);
-    canvas_put_line(pcanvas, COLOR_STD_RED, LINE_TILE_FRAME,
-                   canvas_x + NORMAL_TILE_WIDTH - 1,
-                   canvas_y + NORMAL_TILE_HEIGHT / 2 - 1,
-                   -NORMAL_TILE_WIDTH / 2, NORMAL_TILE_HEIGHT / 2);
-    canvas_put_line(pcanvas, COLOR_STD_RED, LINE_TILE_FRAME,
-                   canvas_x + NORMAL_TILE_WIDTH / 2 - 1,
-                   canvas_y + NORMAL_TILE_HEIGHT - 1,
-                   -(NORMAL_TILE_WIDTH / 2 - 1), -NORMAL_TILE_HEIGHT / 2);
-    canvas_put_line(pcanvas, COLOR_STD_RED, LINE_TILE_FRAME,
-                   canvas_x, canvas_y + NORMAL_TILE_HEIGHT / 2 - 1,
-                   NORMAL_TILE_WIDTH / 2 - 1, -(NORMAL_TILE_HEIGHT / 2 - 1));
-  } else {
-    canvas_put_line(pcanvas, COLOR_STD_RED, LINE_NORMAL,
-                   canvas_x, canvas_y, NORMAL_TILE_WIDTH - 1, 0);
-    canvas_put_line(pcanvas, COLOR_STD_RED, LINE_NORMAL,
-                   canvas_x + NORMAL_TILE_WIDTH - 1, canvas_y,
-                   0, NORMAL_TILE_HEIGHT - 1);
-    canvas_put_line(pcanvas, COLOR_STD_RED, LINE_NORMAL,
-                   canvas_x, canvas_y, 0, NORMAL_TILE_HEIGHT - 1);
-    canvas_put_line(pcanvas, COLOR_STD_RED, LINE_NORMAL,
-                   canvas_x, canvas_y + NORMAL_TILE_HEIGHT - 1,
-                   NORMAL_TILE_WIDTH - 1, 0);
+  enum direction8 dir;
+
+  for (dir = 0; dir < 8; dir++) {
+    int start_x, start_y, end_x, end_y;
+
+    if (get_tile_boundaries(dir, 1, 1, D_FULL,
+                           &start_x, &start_y, &end_x, &end_y)) {
+      canvas_put_line(pcanvas, COLOR_STD_RED, LINE_NORMAL,
+                     canvas_x + start_x, canvas_y + start_y,
+                     end_x - start_x, end_y - start_y);
+
+    }
   }
 }
 
@@ -807,51 +897,52 @@
 **************************************************************************/
 static void tile_draw_borders(struct canvas *pcanvas,
                              int map_x, int map_y,
-                             int canvas_x, int canvas_y)
+                             int canvas_x, int canvas_y,
+                             enum draw_type draw)
 {
   struct player *this_owner = map_get_owner(map_x, map_y), *adjc_owner;
-  int x1, y1;
+  int start_x, start_y, end_x, end_y;
 
-  if (!draw_borders || game.borders == 0) {
+  if (!draw_borders || game.borders == 0 || !this_owner) {
     return;
   }
 
-  /* left side */
-  if (MAPSTEP(x1, y1, map_x, map_y, DIR8_WEST)
-      && this_owner != (adjc_owner = map_get_owner(x1, y1))
-      && tile_get_known(x1, y1)
-      && this_owner) {
-    canvas_put_line(pcanvas, player_color(this_owner), LINE_BORDER,
-                   canvas_x + 1, canvas_y + 1, 0, NORMAL_TILE_HEIGHT - 1);
-  }
-
-  /* top side */
-  if (MAPSTEP(x1, y1, map_x, map_y, DIR8_NORTH)
-      && this_owner != (adjc_owner = map_get_owner(x1, y1))
-      && tile_get_known(x1, y1)
-      && this_owner) {
-    canvas_put_line(pcanvas, player_color(this_owner), LINE_BORDER,
-                   canvas_x + 1, canvas_y + 1, NORMAL_TILE_WIDTH - 1, 0);
-  }
-
-  /* right side */
-  if (MAPSTEP(x1, y1, map_x, map_y, DIR8_EAST)
-      && this_owner != (adjc_owner = map_get_owner(x1, y1))
-      && tile_get_known(x1, y1)
-      && this_owner) {
-    canvas_put_line(pcanvas, player_color(this_owner), LINE_BORDER,
-                   canvas_x + NORMAL_TILE_WIDTH - 1, canvas_y + 1,
-                   0, NORMAL_TILE_HEIGHT - 1);
-  }
-
-  /* bottom side */
-  if (MAPSTEP(x1, y1, map_x, map_y, DIR8_SOUTH)
-      && this_owner != (adjc_owner = map_get_owner(x1, y1))
-      && tile_get_known(x1, y1)
-      && this_owner) {
-    canvas_put_line(pcanvas, player_color(this_owner), LINE_BORDER,
-                   canvas_x + 1, canvas_y + NORMAL_TILE_HEIGHT - 1,
-                   NORMAL_TILE_WIDTH - 1, 0);
+  if (is_isometric) {
+    /* Isometric must be done differently or the borders will get overwritten
+     * by other terrain graphics.  Of course this means the borders may
+     * themselves overwrite units and cities.  The only real solution is
+     * to do the drawing in layers rather than per-tile.  In the meantime
+     * we use this hack. */
+    adjc_dir_iterate(map_x, map_y, adjc_x, adjc_y, dir) {
+      if (dir < 4
+         && get_tile_boundaries(dir, 0, BORDER_WIDTH, draw,
+                                 &start_x, &start_y, &end_x, &end_y)
+         && tile_get_known(adjc_x, adjc_y)
+         && this_owner != (adjc_owner = map_get_owner(adjc_x, adjc_y))) {
+       if (this_owner) {
+         canvas_put_line(pcanvas, player_color(this_owner), LINE_BORDER,
+                         canvas_x + start_x, canvas_y + start_y,
+                         end_x - start_x, end_y - start_y);
+       }
+       if (adjc_owner) {
+         canvas_put_line(pcanvas, player_color(adjc_owner), LINE_BORDER,
+                         canvas_x + start_x,
+                         canvas_y + start_y - BORDER_WIDTH,
+                         end_x - start_x, end_y - start_y);
+       }
+      }
+    } adjc_dir_iterate_end;
+  } else {
+    adjc_dir_iterate(map_x, map_y, adjc_x, adjc_y, dir) {
+      if (get_tile_boundaries(dir, 0, BORDER_WIDTH, draw,
+                             &start_x, &start_y, &end_x, &end_y)
+         && tile_get_known(adjc_x, adjc_y)
+         && this_owner != (adjc_owner = map_get_owner(adjc_x, adjc_y))) {
+       canvas_put_line(pcanvas, player_color(this_owner), LINE_BORDER,
+                       canvas_x + start_x, canvas_y + start_y,
+                       end_x - start_x, end_y - start_y);
+      }
+    } adjc_dir_iterate_end;
   }
 }
 
@@ -888,71 +979,9 @@
       }
     }
 
-    /** Area Selection hiliting **/
-    if (!citymode &&
-        map_get_tile(map_x, map_y)->client.hilite == HILITE_CITY) {
-      const enum color_std hilitecolor = COLOR_STD_YELLOW;
-
-      if (!draw_map_grid) { /* it would be overwritten below */
-        /* left side... */
-        canvas_put_line(pcanvas, hilitecolor, LINE_NORMAL,
-                       canvas_x, canvas_y, 0, NORMAL_TILE_HEIGHT - 1);
-
-        /* top side... */
-        canvas_put_line(pcanvas, hilitecolor, LINE_NORMAL,
-                       canvas_x, canvas_y, NORMAL_TILE_WIDTH - 1, 0);
-      }
-
-      /* right side... */
-      canvas_put_line(pcanvas, hilitecolor, LINE_NORMAL,
-                     canvas_x + NORMAL_TILE_WIDTH - 1, canvas_y,
-                     0, NORMAL_TILE_HEIGHT - 1);
-
-      /* bottom side... */
-      canvas_put_line(pcanvas, hilitecolor, LINE_NORMAL,
-                     canvas_x, canvas_y + NORMAL_TILE_HEIGHT - 1,
-                     NORMAL_TILE_WIDTH - 1, 0);
-    }
-
-    if (draw_map_grid && !citymode) {
-      /* left side... */
-      canvas_put_line(pcanvas,
-                     get_grid_color(map_x, map_y, map_x - 1, map_y),
-                     LINE_NORMAL,
-                     canvas_x, canvas_y, 0, NORMAL_TILE_HEIGHT);
-
-      /* top side... */
-      canvas_put_line(pcanvas,
-                     get_grid_color(map_x, map_y, map_x, map_y - 1),
-                     LINE_NORMAL,
-                     canvas_x, canvas_y, NORMAL_TILE_WIDTH, 0);
-    }
-
-    /* Draw national borders. */
-    tile_draw_borders(pcanvas, map_x, map_y, canvas_x, canvas_y);
-
-    if (draw_coastline && !draw_terrain) {
-      enum tile_terrain_type t1 = map_get_terrain(map_x, map_y), t2;
-      int x1, y1;
-
-      /* left side */
-      if (MAPSTEP(x1, y1, map_x, map_y, DIR8_WEST)) {
-       t2 = map_get_terrain(x1, y1);
-       if (is_ocean(t1) ^ is_ocean(t2)) {
-         canvas_put_line(pcanvas, COLOR_STD_OCEAN, LINE_NORMAL,
-                         canvas_x, canvas_y, 0, NORMAL_TILE_HEIGHT);
-       }
-      }
-
-      /* top side */
-      if (MAPSTEP(x1, y1, map_x, map_y, DIR8_NORTH)) {
-       t2 = map_get_terrain(x1, y1);
-       if (is_ocean(t1) ^ is_ocean(t2)) {
-         canvas_put_line(pcanvas, COLOR_STD_OCEAN, LINE_NORMAL,
-                         canvas_x, canvas_y, NORMAL_TILE_WIDTH, 0);
-       }
-      }
-    }
+    /*** Grid (map grid, borders, coastline, etc.) ***/
+    tile_draw_grid(pcanvas, map_x, map_y, canvas_x, canvas_y,
+                  D_FULL, citymode);
   } else {
     /* tile is unknown */
     canvas_put_rectangle(pcanvas, COLOR_STD_BLACK,
@@ -1002,128 +1031,109 @@
 }
 
 /****************************************************************************
-   Draw the map grid around the given map tile at the given canvas position
-   in isometric view.
+   Draw the map grid around the given map tile at the given canvas position.
 ****************************************************************************/
-static void tile_draw_map_grid_iso(struct canvas *pcanvas,
-                                  int map_x, int map_y,
-                                  int canvas_x, int canvas_y,
-                                  enum draw_type draw)
+static void tile_draw_map_grid(struct canvas *pcanvas,
+                              int map_x, int map_y,
+                              int canvas_x, int canvas_y,
+                              enum draw_type draw)
 {
-  if (!draw_map_grid
-      || map_get_tile(map_x, map_y)->client.hilite != HILITE_NONE) {
+  enum direction8 dir;
+
+  if (!draw_map_grid) {
     return;
   }
 
-  /* we draw the 2 lines on top of the tile; the buttom lines will be
-   * drawn by the tiles underneath. */
-  if (draw & D_M_R) {
-    canvas_put_line(pcanvas, get_grid_color(map_x, map_y, map_x, map_y - 1),
-                   LINE_NORMAL, canvas_x + NORMAL_TILE_WIDTH / 2, canvas_y,
-                   NORMAL_TILE_WIDTH / 2, NORMAL_TILE_HEIGHT / 2);
-  }
+  for (dir = 0; dir < 8; dir++) {
+    int start_x, start_y, end_x, end_y, dx, dy;
 
-  if (draw & D_M_L) {
-    canvas_put_line(pcanvas, get_grid_color(map_x, map_y, map_x - 1, map_y),
-                   LINE_NORMAL, canvas_x, canvas_y + NORMAL_TILE_HEIGHT / 2,
-                   NORMAL_TILE_WIDTH / 2, -NORMAL_TILE_HEIGHT / 2);
+    if (get_tile_boundaries(dir, 0, 1, draw,
+                           &start_x, &start_y, &end_x, &end_y)) {
+      DIRSTEP(dx, dy, dir);
+      canvas_put_line(pcanvas,
+                     get_grid_color(map_x, map_y, map_x + dx, map_y + dy),
+                     LINE_NORMAL,
+                     canvas_x + start_x, canvas_y + start_y,
+                     end_x - start_x, end_y - start_y);
+    }
   }
 }
 
-/**************************************************************************
-   Draw the borders of the given map tile at the given canvas position
-   in isometric view.
-**************************************************************************/
-static void tile_draw_borders_iso(struct canvas *pcanvas,
-                                 int map_x, int map_y,
-                                 int canvas_x, int canvas_y,
-                                 enum draw_type draw)
+/****************************************************************************
+   Draw the coastline of the given map tile at the given canvas position.
+****************************************************************************/
+static void tile_draw_coastline(struct canvas *pcanvas,
+                               int map_x, int map_y,
+                               int canvas_x, int canvas_y,
+                               enum draw_type draw)
 {
-  struct player *this_owner = map_get_owner(map_x, map_y), *adjc_owner;
-  int x1, y1;
+  enum tile_terrain_type t1 = map_get_terrain(map_x, map_y), t2;
 
-  if (!draw_borders || game.borders == 0) {
+  if (!draw_coastline || draw_terrain || t1 == T_UNKNOWN) {
     return;
   }
 
-  /* left side */
-  if ((draw & D_M_L) && MAPSTEP(x1, y1, map_x, map_y, DIR8_WEST)
-      && this_owner != (adjc_owner = map_get_owner(x1, y1))
-      && tile_get_known(x1, y1)) {
-    if (adjc_owner) {
-      canvas_put_line(pcanvas, player_color(adjc_owner), LINE_BORDER,
-                     canvas_x, canvas_y + NORMAL_TILE_HEIGHT / 2 - 1,
-                     NORMAL_TILE_WIDTH / 2, -NORMAL_TILE_HEIGHT / 2);
-    }
-    if (this_owner) {
-      canvas_put_line(pcanvas, player_color(this_owner), LINE_BORDER,
-                     canvas_x, canvas_y + NORMAL_TILE_HEIGHT / 2 + 1,
-                     NORMAL_TILE_WIDTH / 2, -NORMAL_TILE_HEIGHT / 2);
-    }
-  }
+  adjc_dir_iterate(map_x, map_y, adjc_x, adjc_y, dir) {
+    int start_x, start_y, end_x, end_y;
 
-  /* top side */
-  if ((draw & D_M_R) && MAPSTEP(x1, y1, map_x, map_y, DIR8_NORTH)
-      && this_owner != (adjc_owner = map_get_owner(x1, y1))
-      && tile_get_known(x1, y1)) {
-    if (adjc_owner) {
-      canvas_put_line(pcanvas, player_color(adjc_owner), LINE_BORDER,
-                     canvas_x + NORMAL_TILE_WIDTH / 2, canvas_y - 1,
-                     NORMAL_TILE_WIDTH / 2, NORMAL_TILE_HEIGHT / 2);
-    }
-    if (this_owner) {
-      canvas_put_line(pcanvas, player_color(this_owner), LINE_BORDER,
-                     canvas_x + NORMAL_TILE_WIDTH / 2, canvas_y + 1,
-                     NORMAL_TILE_WIDTH / 2, NORMAL_TILE_HEIGHT / 2);
+    if (get_tile_boundaries(dir, 0, 1, draw,
+                           &start_x, &start_y, &end_x, &end_y)) {
+      t2 = map_get_terrain(adjc_x, adjc_y);
+      if (t2 != T_UNKNOWN && (is_ocean(t1) ^ is_ocean(t2))) {
+       canvas_put_line(pcanvas, COLOR_STD_OCEAN, LINE_NORMAL,
+                       canvas_x + start_x, canvas_y + start_y,
+                       end_x - start_x, end_y - start_y);
+      }
     }
-  }
+  } adjc_dir_iterate_end;
 }
 
 /****************************************************************************
-   Draw the coastline of the given map tile at the given canvas position
-   in isometric view.
+   Draw the selection rectangle the given map tile at the given canvas
+   position.
 ****************************************************************************/
-static void tile_draw_coastline_iso(struct canvas *pcanvas,
-                                   int map_x, int map_y,
-                                   int canvas_x, int canvas_y,
-                                   enum draw_type draw)
+static void tile_draw_selection(struct canvas *pcanvas,
+                               int map_x, int map_y,
+                               int canvas_x, int canvas_y,
+                               enum draw_type draw, bool citymode)
 {
-  enum tile_terrain_type t1 = map_get_terrain(map_x, map_y), t2;
-  int adjc_x, adjc_y;
+  const int inset = (is_isometric ? 0 : 1);
 
-  if (!draw_coastline || draw_terrain || t1 == T_UNKNOWN) {
+  if (citymode) {
     return;
   }
 
-  if ((draw & D_M_R) && MAPSTEP(adjc_x, adjc_y, map_x, map_y, DIR8_NORTH)) {
-    t2 = map_get_terrain(adjc_x, adjc_y);
-    if (t2 != T_UNKNOWN        && (is_ocean(t1) ^ is_ocean(t2))) {
-      canvas_put_line(pcanvas, COLOR_STD_OCEAN, LINE_NORMAL,
-                     canvas_x + NORMAL_TILE_WIDTH / 2, canvas_y,
-                     NORMAL_TILE_WIDTH / 2, NORMAL_TILE_HEIGHT / 2);
-    }
-  }
+  adjc_dir_iterate(map_x, map_y, adjc_x, adjc_y, dir) {
+    int start_x, start_y, end_x, end_y;
 
-  if ((draw & D_M_L) && MAPSTEP(adjc_x, adjc_y, map_x, map_y, DIR8_WEST)) {
-    t2 = map_get_terrain(adjc_x, adjc_y);
-    if (t2 != T_UNKNOWN        && (is_ocean(t1) ^ is_ocean(t2))) {
-      canvas_put_line(pcanvas, COLOR_STD_OCEAN, LINE_NORMAL,
-                     canvas_x, canvas_y + NORMAL_TILE_HEIGHT / 2,
-                     NORMAL_TILE_WIDTH / 2, -NORMAL_TILE_HEIGHT / 2);
+    if ((!is_isometric || dir < 4)
+       && get_tile_boundaries(dir, inset, 1, draw,
+                              &start_x, &start_y, &end_x, &end_y)) {
+      if (map_get_tile(map_x, map_y)->client.hilite == HILITE_CITY
+         || (is_isometric
+             && map_get_tile(adjc_x, adjc_y)->client.hilite == HILITE_CITY)) {
+       canvas_put_line(pcanvas, COLOR_STD_YELLOW, LINE_NORMAL,
+                       canvas_x + start_x, canvas_y + start_y,
+                       end_x - start_x, end_y - start_y);
+      }
     }
-  }
+  } adjc_dir_iterate_end;
 }
 
+
 /****************************************************************************
    Draw the grid lines of the given map tile at the given canvas position
    in isometric view.  (This include the map grid, borders, and coastline).
 ****************************************************************************/
-void tile_draw_grid_iso(struct canvas *pcanvas, int map_x, int map_y,
-                       int canvas_x, int canvas_y, enum draw_type draw)
+void tile_draw_grid(struct canvas *pcanvas, int map_x, int map_y,
+                       int canvas_x, int canvas_y,
+                   enum draw_type draw, bool citymode)
 {
-  tile_draw_map_grid_iso(pcanvas, map_x, map_y, canvas_x, canvas_y, draw);
-  tile_draw_borders_iso(pcanvas, map_x, map_y, canvas_x, canvas_y, draw);
-  tile_draw_coastline_iso(pcanvas, map_x, map_y, canvas_x, canvas_y, draw);
+  tile_draw_map_grid(pcanvas, map_x, map_y, canvas_x, canvas_y, draw);
+  tile_draw_borders(pcanvas, map_x, map_y, canvas_x, canvas_y, draw);
+  tile_draw_coastline(pcanvas, map_x, map_y, canvas_x, canvas_y, draw);
+  tile_draw_selection(pcanvas, map_x, map_y, canvas_x, canvas_y,
+                     draw, citymode);
 }
 
 /**************************************************************************
Index: client/mapview_common.h
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/mapview_common.h,v
retrieving revision 1.55
diff -u -r1.55 mapview_common.h
--- client/mapview_common.h     13 Apr 2004 16:05:08 -0000      1.55
+++ client/mapview_common.h     13 Apr 2004 20:13:48 -0000
@@ -132,6 +132,8 @@
   D_MB_LR = D_M_L | D_M_R | D_B_L | D_B_R
 };
 
+#define BORDER_WIDTH 2
+
 enum update_type {
   /* Masks */
   UPDATE_NONE = 0,
@@ -180,8 +182,9 @@
 
 void put_one_tile(struct canvas *pcanvas, int map_x, int map_y,
                  int canvas_x, int canvas_y, bool citymode);
-void tile_draw_grid_iso(struct canvas *pcanvas, int map_x, int map_y,
-                       int canvas_x, int canvas_y, enum draw_type draw);
+void tile_draw_grid(struct canvas *pcanvas, int map_x, int map_y,
+                   int canvas_x, int canvas_y,
+                   enum draw_type draw, bool citymode);
 
 void update_map_canvas(int x, int y, int width, int height,
                       bool write_to_screen);
Index: client/gui-gtk/gui_main.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-gtk/gui_main.c,v
retrieving revision 1.147
diff -u -r1.147 gui_main.c
--- client/gui-gtk/gui_main.c   8 Mar 2004 02:24:35 -0000       1.147
+++ client/gui-gtk/gui_main.c   13 Apr 2004 20:13:49 -0000
@@ -896,7 +896,7 @@
                             GDK_LINE_SOLID,
                             GDK_CAP_NOT_LAST,
                             GDK_JOIN_MITER);
-  gdk_gc_set_line_attributes(border_line_gc, 2,
+  gdk_gc_set_line_attributes(border_line_gc, BORDER_WIDTH,
                             GDK_LINE_ON_OFF_DASH,
                             GDK_CAP_NOT_LAST,
                             GDK_JOIN_MITER);
Index: client/gui-gtk/mapview.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-gtk/mapview.c,v
retrieving revision 1.213
diff -u -r1.213 mapview.c
--- client/gui-gtk/mapview.c    13 Apr 2004 16:05:08 -0000      1.213
+++ client/gui-gtk/mapview.c    13 Apr 2004 20:13:49 -0000
@@ -1055,44 +1055,8 @@
       freelog(LOG_ERROR, "sprite is NULL");
   }
 
-  /*** Area Selection hiliting ***/
-  if (tile_hilited) {
-    gdk_gc_set_foreground(thin_line_gc, colors_standard[COLOR_STD_YELLOW]);
-
-    if (draw & D_M_R) {
-      gdk_draw_line(pm, thin_line_gc,
-            canvas_x + NORMAL_TILE_WIDTH / 2,
-            canvas_y,
-            canvas_x + NORMAL_TILE_WIDTH - 1,
-            canvas_y + NORMAL_TILE_HEIGHT / 2 - 1);
-    }
-    if (draw & D_M_L) {
-      gdk_draw_line(pm, thin_line_gc,
-            canvas_x,
-            canvas_y + NORMAL_TILE_HEIGHT / 2 - 1,
-            canvas_x + NORMAL_TILE_WIDTH / 2 - 1,
-            canvas_y);
-    }
-    /* The lower lines do not quite reach the tile's bottom;
-     * they would be too obscured by overlapping tiles' terrain. */
-    if (draw & D_B_R) {
-      gdk_draw_line(pm, thin_line_gc,
-            canvas_x + NORMAL_TILE_WIDTH / 2,
-            canvas_y + NORMAL_TILE_HEIGHT - 3,
-            canvas_x + NORMAL_TILE_WIDTH - 1,
-            canvas_y + NORMAL_TILE_HEIGHT / 2 - 1);
-    }
-    if (draw & D_B_L) {
-      gdk_draw_line(pm, thin_line_gc,
-            canvas_x,
-            canvas_y + NORMAL_TILE_HEIGHT / 2 - 1,
-            canvas_x + NORMAL_TILE_WIDTH / 2 - 1,
-            canvas_y + NORMAL_TILE_HEIGHT - 3);
-    }
-  }
-
   /*** Grid (map grid, borders, coastline, etc.) ***/
-  tile_draw_grid_iso(&canvas_store, x, y, canvas_x, canvas_y, draw);
+  tile_draw_grid(&canvas_store, x, y, canvas_x, canvas_y, draw, citymode);
 
   /*** City and various terrain improvements ***/
   if (pcity && draw_cities) {
Index: client/gui-gtk-2.0/gui_main.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-gtk-2.0/gui_main.c,v
retrieving revision 1.70
diff -u -r1.70 gui_main.c
--- client/gui-gtk-2.0/gui_main.c       3 Apr 2004 01:57:22 -0000       1.70
+++ client/gui-gtk-2.0/gui_main.c       13 Apr 2004 20:13:49 -0000
@@ -1140,7 +1140,7 @@
                             GDK_LINE_SOLID,
                             GDK_CAP_NOT_LAST,
                             GDK_JOIN_MITER);
-  gdk_gc_set_line_attributes(border_line_gc, 2,
+  gdk_gc_set_line_attributes(border_line_gc, BORDER_WIDTH,
                             GDK_LINE_ON_OFF_DASH,
                             GDK_CAP_NOT_LAST,
                             GDK_JOIN_MITER);
Index: client/gui-gtk-2.0/mapview.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-gtk-2.0/mapview.c,v
retrieving revision 1.118
diff -u -r1.118 mapview.c
--- client/gui-gtk-2.0/mapview.c        13 Apr 2004 16:05:08 -0000      1.118
+++ client/gui-gtk-2.0/mapview.c        13 Apr 2004 20:13:49 -0000
@@ -1167,44 +1167,8 @@
       freelog(LOG_ERROR, "sprite is NULL");
   }
 
-  /*** Area Selection hiliting ***/
-  if (tile_hilited) {
-    gdk_gc_set_foreground(thin_line_gc, colors_standard[COLOR_STD_YELLOW]);
-
-    if (draw & D_M_R) {
-      gdk_draw_line(pm, thin_line_gc,
-            canvas_x + NORMAL_TILE_WIDTH / 2,
-            canvas_y,
-            canvas_x + NORMAL_TILE_WIDTH - 1,
-            canvas_y + NORMAL_TILE_HEIGHT / 2 - 1);
-    }
-    if (draw & D_M_L) {
-      gdk_draw_line(pm, thin_line_gc,
-            canvas_x,
-            canvas_y + NORMAL_TILE_HEIGHT / 2 - 1,
-            canvas_x + NORMAL_TILE_WIDTH / 2 - 1,
-            canvas_y);
-    }
-    /* The lower lines do not quite reach the tile's bottom;
-     * they would be too obscured by overlapping tiles' terrain. */
-    if (draw & D_B_R) {
-      gdk_draw_line(pm, thin_line_gc,
-            canvas_x + NORMAL_TILE_WIDTH / 2,
-            canvas_y + NORMAL_TILE_HEIGHT - 3,
-            canvas_x + NORMAL_TILE_WIDTH - 1,
-            canvas_y + NORMAL_TILE_HEIGHT / 2 - 1);
-    }
-    if (draw & D_B_L) {
-      gdk_draw_line(pm, thin_line_gc,
-            canvas_x,
-            canvas_y + NORMAL_TILE_HEIGHT / 2 - 1,
-            canvas_x + NORMAL_TILE_WIDTH / 2 - 1,
-            canvas_y + NORMAL_TILE_HEIGHT - 3);
-    }
-  }
-
   /*** Grid (map grid, borders, coastline, etc.) ***/
-  tile_draw_grid_iso(&canvas_store, x, y, canvas_x, canvas_y, draw);
+  tile_draw_grid(&canvas_store, x, y, canvas_x, canvas_y, draw, citymode);
 
   /*** City and various terrain improvements ***/
   if (pcity && draw_cities) {
Index: client/gui-win32/mapview.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-win32/mapview.c,v
retrieving revision 1.110
diff -u -r1.110 mapview.c
--- client/gui-win32/mapview.c  13 Apr 2004 16:05:08 -0000      1.110
+++ client/gui-win32/mapview.c  13 Apr 2004 20:13:49 -0000
@@ -1002,7 +1002,7 @@
   }
 
   /*** Grid (map grid, borders, coastline, etc.) ***/
-  tile_draw_grid_iso(&canvas_store, x, y, canvas_x, canvas_y, draw);
+  tile_draw_grid(&canvas_store, x, y, canvas_x, canvas_y, draw, citymode);
 
   if (draw_coastline && !draw_terrain) {
     enum tile_terrain_type t1 = map_get_terrain(x, y), t2;
Index: client/gui-xaw/gui_main.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-xaw/gui_main.c,v
retrieving revision 1.90
diff -u -r1.90 gui_main.c
--- client/gui-xaw/gui_main.c   8 Mar 2004 07:20:50 -0000       1.90
+++ client/gui-xaw/gui_main.c   13 Apr 2004 20:13:49 -0000
@@ -368,7 +368,7 @@
                            
GCForeground|GCBackground|GCFont|GCGraphicsExposures,
                            &values);
 
-    values.line_width = 2;
+    values.line_width = BORDER_WIDTH;
     values.line_style = LineOnOffDash;
     values.cap_style = CapNotLast;
     values.join_style = JoinMiter;

[Prev in Thread] Current Thread [Next in Thread]
  • [Freeciv-Dev] (PR#8507) generalized tile boundaries, Jason Short <=