Complete.Org: Mailing Lists: Archives: freeciv-dev: October 2003:
[Freeciv-Dev] Re: (PR#6170) Alternative city square utilizations
Home

[Freeciv-Dev] Re: (PR#6170) Alternative city square utilizations

[Top] [All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index] [Thread Index]
To: jdwheeler42@xxxxxxxxx
Subject: [Freeciv-Dev] Re: (PR#6170) Alternative city square utilizations
From: "Remi Bonnet" <remi.bonnet@xxxxxxxxxxx>
Date: Thu, 30 Oct 2003 06:56:32 -0800
Reply-to: rt@xxxxxxxxxxxxxx

Jason Short wrote:

>I recommend developing a complete patch that implements the whole 
>shebang.  But then to get it into CVS this is broken into smaller 
>incremental patches.
>  
>
>>And i don't understand why you want to add this define. Actually,  
>>CITY_MAP_CENTER_X = CITY_MAP_CENTER_Y = CITY_MAP_RADIUS.
>>If you want to add this line, it's even better to call #define 
>>CITY_MAP_CENTER_X CITY_MAP_RADIUS but i still don't see the point.
>>    
>>
>
>Currently CITY_MAP_CENTER_X = CITY_MAP_CENTER_Y = CITY_MAP_RADIUS.  But 
>if MAP_CITY_RADIUS were turned into a server variable then 
>CITY_MAP_RADIUS would/should go away.  Or what if it were redefined as 
>CITY_MAP_RADIUS_SQUARED?
>  
>
I'm definitvely against the squared stuff:
 - complex
 - add no real gameplay change
 - remove realism
 - add no fun
 - (i don't see any use for rulesets)

When MAP_CITY_RADIUS will be replaced by pcity->radius, the coords of 
city center will still be (pcity->radius, pcity->radius) so i still 
don't see any reasons.

>In some alternate universe CITY_MAP_CENTER_X and CITY_MAP_CENTER_Y might 
>not even be the same.  You could have an oval citymap, for instance.
>  
>
You *really* think that's an option? And if there will not be the same, 
i think adding CITY_MAP_RADIUS_{X,Y} is still better

>The point is, CITY_MAP_CENTER_X and CITY_MAP_CENTER_Y have fixed 
>definitions that aren't likely to change.  They should also make the 
>code more readible.
>  
>
Huh? They change when the radius change

>>>This needs a comment: changing this requires adding a new network 
>>>capability and updating CITY_TILES.
>>>      
>>>
>>Yes but looks below for city tiles.
>>    
>>
>
>I don't understand?
>  
>
Oops sorry, my mistake

>
>You can also compare the savegames generated between the two games. 
>They should be identical.
>
The md5sums are different but the map / cities / units are identical.

Here is the patch splitted, with some mistakes fixed.

remove-numbers:
 Remove all hard-coded numbers by appropriate defines. (no real change 
in executable so no speeds issues)

generate-indices:
 The array used by iterate_city_map_outwards() is now dynamically 
generated. (only one time at startup so no real speeds issues)

city-routines:
 Change is_valid_city_coords and some others. (autogames show that the 
slowdown is probably really small)

citymap-network:
 Change the serialization of city maps. Probably no slow down

size-three:
 Change the radius of city_map to three (only for testing, not for cvs)

I tested the patchs when applying them in the order above. Normally, 
every order with remove-numbers first and size-three last may work

Remi

diff -u -r -Xdiff_ignore ../old/common/aicore/cm.c ./common/aicore/cm.c
--- ../old/common/aicore/cm.c   2003-10-29 11:16:14.000000000 +0100
+++ ./common/aicore/cm.c        2003-10-29 11:34:13.000000000 +0100
@@ -148,7 +148,7 @@
 #define DISABLE_CACHE3                                  FALSE
 
 #define NUM_SPECIALISTS_ROLES                          3
-#define MAX_FIELDS_USED                (CITY_MAP_SIZE * CITY_MAP_SIZE - 4 - 1)
+#define MAX_FIELDS_USED                                        (CITY_TILES - 1)
 #define MAX_COMBINATIONS                               150
 
 /* Maps scientists and taxmen to result for a certain combination. */
@@ -1163,11 +1163,14 @@
    */
   root_combination.worker = 0;
   root_combination.production2[FOOD] =
-      base_city_get_food_tile(2, 2, pcity, is_celebrating);
+      base_city_get_food_tile(CITY_MAP_RADIUS, CITY_MAP_RADIUS,
+                             pcity, is_celebrating);
   root_combination.production2[SHIELD] =
-      base_city_get_shields_tile(2, 2, pcity, is_celebrating);
+      base_city_get_shields_tile(CITY_MAP_RADIUS, CITY_MAP_RADIUS, 
+                             pcity, is_celebrating);
   root_combination.production2[TRADE] =
-      base_city_get_trade_tile(2, 2, pcity, is_celebrating);
+      base_city_get_trade_tile(CITY_MAP_RADIUS, CITY_MAP_RADIUS, 
+                            pcity, is_celebrating);
 
   total_tile_trade = root_combination.production2[TRADE];
 
diff -u -r -Xdiff_ignore ../old/common/city.h ./common/city.h
--- ../old/common/city.h        2003-10-02 15:11:10.000000000 +0200
+++ ./common/city.h     2003-10-29 11:34:13.000000000 +0100
@@ -58,10 +58,14 @@
 /* for new city: default auto-attack options all on, others off: */
 #define CITYOPT_DEFAULT (CITYOPT_AUTOATTACK_BITS)
 
+
+/* Changing that requires updating CITY_TILES and network capabilities */
+#define CITY_MAP_RADIUS 2
+
 /* Diameter of the workable city area. Must be an odd number.
    Some places in the code hardcodes this number, fx 
    city_map_iterate_outwards_indices */
-#define CITY_MAP_SIZE 5
+#define CITY_MAP_SIZE (CITY_MAP_RADIUS * 2 + 1) 
 
 /* Number of tiles a city can use */
 #define CITY_TILES (CITY_MAP_SIZE * CITY_MAP_SIZE - 4)
@@ -187,14 +191,14 @@
 
   /* Used for caching when settlers evalueate which tile to improve,
      and when we place workers. */
-  signed short int detox[5][5];
-  signed short int derad[5][5];
-  signed short int mine[5][5];
-  signed short int irrigate[5][5];
-  signed short int road[5][5];
-  signed short int railroad[5][5];
-  signed short int transform[5][5];
-  signed short int tile_value[5][5];
+  signed short int detox[CITY_MAP_SIZE][CITY_MAP_SIZE];
+  signed short int derad[CITY_MAP_SIZE][CITY_MAP_SIZE];
+  signed short int mine[CITY_MAP_SIZE][CITY_MAP_SIZE];
+  signed short int irrigate[CITY_MAP_SIZE][CITY_MAP_SIZE];
+  signed short int road[CITY_MAP_SIZE][CITY_MAP_SIZE];
+  signed short int railroad[CITY_MAP_SIZE][CITY_MAP_SIZE];
+  signed short int transform[CITY_MAP_SIZE][CITY_MAP_SIZE];
+  signed short int tile_value[CITY_MAP_SIZE][CITY_MAP_SIZE];
 
   /* so we can contemplate with warmap fresh and decide later */
   int settler_want, founder_want; /* for builder (F_SETTLERS) and founder 
(F_CITIES) */
--- ../freeciv/client/citydlg_common.c  2003-08-06 09:22:44.000000000 +0200
+++ ./client/citydlg_common.c   2003-10-29 16:38:51.000000000 +0100
@@ -33,9 +33,9 @@
 int get_citydlg_canvas_width(void)
 {
   if (is_isometric) {
-    return 4 * NORMAL_TILE_WIDTH;
+    return (CITY_MAP_SIZE - 1) * NORMAL_TILE_WIDTH;
   } else {
-    return 5 * NORMAL_TILE_WIDTH;
+    return CITY_MAP_SIZE * NORMAL_TILE_WIDTH;
   }
 }
 
@@ -45,9 +45,9 @@
 int get_citydlg_canvas_height(void)
 {
   if (is_isometric) {
-    return 4 * NORMAL_TILE_HEIGHT;
+    return (CITY_MAP_SIZE - 1) * NORMAL_TILE_HEIGHT;
   } else {
-    return 5 * NORMAL_TILE_HEIGHT;
+    return CITY_MAP_SIZE * NORMAL_TILE_HEIGHT;
   }
 }
 
@@ -64,7 +64,7 @@
      * subtract off half a tile in each direction.  For a more
      * rigorous example, see map_pos_to_canvas_pos().
      */
-    int iso_x = (city_x - city_y) - (-4);
+    int iso_x = (city_x - city_y) + (2 * CITY_MAP_RADIUS);
     int iso_y = (city_x + city_y) - (0);
 
     *canvas_x = (iso_x - 1) * NORMAL_TILE_WIDTH / 2;
@@ -103,8 +103,8 @@
 
     /* Add on the offset of the top-left corner to get the final
      * coordinates (like in canvas_to_map_pos). */
-    *city_x -= 2;
-    *city_y += 2;
+    *city_x -= CITY_MAP_RADIUS;
+    *city_y += CITY_MAP_RADIUS;
   } else {
     *city_x = canvas_x / NORMAL_TILE_WIDTH;
     *city_y = canvas_y / NORMAL_TILE_HEIGHT;
diff -u -r -Xdiff_ignore ../old/client/packhand.c ./client/packhand.c
--- ../old/client/packhand.c    2003-10-29 11:16:14.000000000 +0100
+++ ./client/packhand.c 2003-10-29 12:12:52.000000000 +0100
@@ -2525,6 +2525,9 @@
   game.rgame.granary_food_inc = packet->granary_food_inc;
   game.rgame.tech_cost_style = packet->tech_cost_style;
   game.rgame.tech_leakage = packet->tech_leakage;
+
+  /* It is not really from the ruleset but later it will be */
+  generate_city_map_indices(CITY_MAP_RADIUS);
 }
 
 /**************************************************************************
diff -u -r -Xdiff_ignore ../old/common/city.c ./common/city.c
--- ../old/common/city.c        2003-10-02 15:11:10.000000000 +0200
+++ ./common/city.c     2003-10-29 12:28:05.000000000 +0100
@@ -56,21 +56,24 @@
                                      bool asmiths);
 
 /* Iterate a city map, from the center (the city) outwards */
+int** city_map_iterate_outwards_indices;
 
-int city_map_iterate_outwards_indices[CITY_TILES][2] =
-{
-  { 2, 2 },
-
-  { 1, 2 }, { 2, 1 }, { 3, 2 }, { 2, 3 },
-  { 1, 3 }, { 1, 1 }, { 3, 1 }, { 3, 3 },
+/* Unused for the moment. Later maybe... */
+/*int*  available_tiles;*/
 
-  { 0, 2 }, { 2, 0 }, { 4, 2 }, { 2, 4 },
-  { 0, 3 }, { 0, 1 },
-  { 1, 0 }, { 3, 0 },
-  { 4, 1 }, { 4, 3 },
-  { 3, 4 }, { 1, 4 }
+/* Chained list Structure and helper function for generate_city_map_indices */
+struct chained_dists {
+  int dist;
+  int x, y;
+  struct chained_dists *prev;
+  struct chained_dists *next;
 };
 
+#define BIG_DIST (1000 * 1000)
+
+struct chained_dists* insert_chained_dists(struct chained_dists *iter,
+                                          int x, int y, int dist);
+
 struct citystyle *city_styles = NULL;
 
 /**************************************************************************
@@ -152,6 +155,115 @@
 }
 
 /**************************************************************************
+  Insert a new struct chained_dists in the global list. the new one is placed
+ after the iter parameter. Note that iter and iter->next must not be NULL.
+**************************************************************************/
+struct chained_dists* insert_chained_dists(struct chained_dists *iter,
+                                          int x, int y, int dist)
+{
+  struct chained_dists *new_struct = fc_malloc(sizeof(struct chained_dists));
+
+  new_struct->next = iter->next;
+  iter->next->prev = new_struct;
+  new_struct->prev = iter;
+  iter->next = new_struct;
+
+  new_struct->dist = dist;
+  new_struct->x = x;
+  new_struct->y = y;
+
+  return new_struct;
+}
+
+/**************************************************************************
+  Fill the iterate_outwards_indices arrays. The int inside the array are
+ signed. iterate_outwards will later add CITY_MAP_RADIUS to each coord.
+***************************************************************************/
+void generate_city_map_indices(int max_radius)
+{
+  struct chained_dists *iter;
+  int x, y, max_dist = max_radius * max_radius + 1;
+  int dist, i = 0;
+
+  assert(max_radius >= 0);
+
+  /* Create the two bounds */
+  iter = fc_malloc(sizeof(struct chained_dists));
+  iter->next = fc_malloc(sizeof(struct chained_dists));
+  iter->prev = NULL;
+  iter->dist = -1;
+
+  iter->next->next = NULL;
+  iter->next->prev = iter;
+  iter->next->dist = BIG_DIST;
+
+  /* Create the chained list, ordered by ascending dist */
+  for (x = -max_radius; x <= max_radius; x++) {
+    for (y = -max_radius; y <= max_radius; y++) {
+      dist = x * x + y * y;
+      
+      if (dist <= max_dist) {
+       while (1) {
+         if (dist == iter->dist) {
+           iter = insert_chained_dists(iter, x, y, dist);
+           i++;
+           break;
+         }
+         if (dist < iter->dist) {
+           if (dist >= iter->prev->dist) {
+             iter = insert_chained_dists(iter->prev, x, y, dist);
+             i++;
+             break;
+           } else {
+             iter = iter->prev;
+           }
+         } else {
+           if (dist <= iter->next->dist) {
+             iter = insert_chained_dists(iter, x, y, dist);
+             i++;
+             break;
+           } else {
+             iter = iter->next;
+           }
+         }
+       }
+      }
+    }
+  }
+
+  /* Makes iter pointing to the the second iter. First is bound. */
+  while (iter->prev->prev) {
+    iter = iter->prev;
+  }
+
+  /* Is the CITY_TILES define correctly set? */
+  assert(CITY_TILES == i);
+
+  /* Alloc the arrays */
+  city_map_iterate_outwards_indices = fc_malloc(sizeof(int*) * i);
+  /*  available_tiles = fc_malloc(sizeof(int) * (max_radius + 1));*/
+
+  i = 0; 
+  dist = 0;
+ 
+  /* Browse the list and put it into the array */
+  while (iter->next) {
+    /*    if (dist * dist + 1 < iter->dist) {
+      available_tiles[dist] = i;
+      dist++;
+      assert(dist <= max_radius);
+      }*/
+    
+    city_map_iterate_outwards_indices[i] = fc_malloc(2 * sizeof(int));
+    city_map_iterate_outwards_indices[i][0] = iter->x;
+    city_map_iterate_outwards_indices[i][1] = iter->y;
+
+    i++;
+    iter = iter->next;
+  }
+}
+
+/**************************************************************************
   Set the worker on the citymap.  Also sets the worked field in the map.
 **************************************************************************/
 void set_worker_city(struct city *pcity, int city_x, int city_y,
diff -u -r -Xdiff_ignore ../old/common/city.h ./common/city.h
--- ../old/common/city.h        2003-10-29 12:13:06.000000000 +0100
+++ ./common/city.h     2003-10-29 12:12:52.000000000 +0100
@@ -68,7 +68,7 @@
 #define CITY_MAP_SIZE (CITY_MAP_RADIUS * 2 + 1) 
 
 /* Number of tiles a city can use */
-#define CITY_TILES (CITY_MAP_SIZE * CITY_MAP_SIZE - 4)
+#define CITY_TILES 21
 
 #define INCITE_IMPOSSIBLE_COST (1000 * 1000 * 1000)
 
@@ -99,25 +99,27 @@
 
 /* Iterate a city map, from the center (the city) outwards */
 
-extern int city_map_iterate_outwards_indices[CITY_TILES][2];
+extern int** city_map_iterate_outwards_indices;
 
 /* Iterate a city map, from the center (the city) outwards. x and y
    will be elements of [0, CITY_MAP_SIZE). */
-#define city_map_iterate_outwards(x, y) {                                      
\
-  int x, y;                                                                    
\
-  int city_map_iterate_outwards_index;                                         
\
-  for                                                                          
\
-  (                                                                            
\
-    city_map_iterate_outwards_index = 0;                                       
\
-    city_map_iterate_outwards_index < CITY_TILES;                              
\
-    city_map_iterate_outwards_index++                                          
\
-  )                                                                            
\
-  {                                                                            
\
-    x = city_map_iterate_outwards_indices[city_map_iterate_outwards_index][0]; 
\
-    y = city_map_iterate_outwards_indices[city_map_iterate_outwards_index][1];
+#define city_map_iterate_outwards(x, y) {                                     \
+  int x, y;                                                                   \
+  int city_map_iterate_outwards_index;                                        \
+  for                                                                         \
+  (                                                                           \
+    city_map_iterate_outwards_index = 0;                                      \
+    city_map_iterate_outwards_index < CITY_TILES;                             \
+    city_map_iterate_outwards_index++                                         \
+  )                                                                           \
+  {                                                                           \
+    x = CITY_MAP_RADIUS +                                                     \
+      city_map_iterate_outwards_indices[city_map_iterate_outwards_index][0];  \
+    y = CITY_MAP_RADIUS +                                                     \
+      city_map_iterate_outwards_indices[city_map_iterate_outwards_index][1];
 
-#define city_map_iterate_outwards_end                                          
\
-  }                                                                            
\
+#define city_map_iterate_outwards_end                                         \
+  }                                                                           \
 }
 
 /*
@@ -388,6 +390,7 @@
                         int city_map_y);
 bool city_map_to_map(int *map_x, int *map_y, const struct city *const pcity,
                    int city_map_x, int city_map_y);
+void generate_city_map_indices(int max_radius);
 
 /* shield on spot */
 int city_get_shields_tile(int x, int y, struct city *pcity);
diff -u -r -Xdiff_ignore ../old/server/ruleset.c ./server/ruleset.c
--- ../old/server/ruleset.c     2003-10-03 15:28:55.000000000 +0200
+++ ./server/ruleset.c  2003-10-29 12:12:52.000000000 +0100
@@ -2498,6 +2498,9 @@
   lookup_tech_list(&file, "options", "global_init_techs",
                   game.rgame.global_init_techs, filename);
 
+  /* It is not really from the ruleset, but later it will be so do it here */
+  generate_city_map_indices(CITY_MAP_RADIUS);
+
   section_file_check_unused(&file, filename);
   section_file_free(&file);
 }
diff -u -r -Xdiff_ignore ./common/city.c ../goal/common/city.c
--- ./common/city.c     2003-10-22 17:14:46.000000000 +0200
+++ ../goal/common/city.c       2003-10-20 17:50:26.000000000 +0200
@@ -81,15 +81,22 @@
 **************************************************************************/
 bool is_valid_city_coords(const int city_x, const int city_y)
 {
-  if ((city_x == 0 || city_x == CITY_MAP_SIZE-1)
-      && (city_y == 0 || city_y == CITY_MAP_SIZE-1))
-    return FALSE;
-  if (city_x < 0 || city_y < 0
-      || city_x >= CITY_MAP_SIZE
-      || city_y >= CITY_MAP_SIZE)
+  /* Why +1 here? Small schemas:
+   *   Without   |     With
+   *    3               333
+   *  33233            32223  
+   *  32123           3211123
+   * 3210123          3210123 
+   *  32123           3211123  
+   *  33233            32223  
+   *    3               333    */
+  if (CITY_MAP_RADIUS * CITY_MAP_RADIUS + 1>= 
+      (city_x - CITY_MAP_RADIUS) * (city_x - CITY_MAP_RADIUS) +
+      (city_y - CITY_MAP_RADIUS) * (city_y - CITY_MAP_RADIUS)) {
+    return TRUE;
+  } else {
     return FALSE;
-
-  return TRUE;
+  }
 }
 
 /**************************************************************************
@@ -97,8 +104,7 @@
 **************************************************************************/
 bool is_city_center(int city_x, int city_y)
 {
-  return (city_x == (CITY_MAP_SIZE / 2))
-      && (city_y == (CITY_MAP_SIZE / 2));
+  return CITY_MAP_RADIUS == city_x && CITY_MAP_RADIUS == city_y;
 }
 
 /**************************************************************************
@@ -111,8 +117,8 @@
 {
   map_distance_vector(city_map_x, city_map_y,
                      city_center_x, city_center_y, map_x, map_y);
-  *city_map_x += CITY_MAP_SIZE / 2;
-  *city_map_y += CITY_MAP_SIZE / 2;
+  *city_map_x += CITY_MAP_RADIUS;
+  *city_map_y += CITY_MAP_RADIUS;
   return is_valid_city_coords(*city_map_x, *city_map_y);
 }
 
@@ -137,8 +143,8 @@
                         int city_map_x, int city_map_y)
 {
   assert(is_valid_city_coords(city_map_x, city_map_y));
-  *map_x = city_center_x + city_map_x - CITY_MAP_SIZE / 2;
-  *map_y = city_center_y + city_map_y - CITY_MAP_SIZE / 2;
+  *map_x = city_center_x + city_map_x - CITY_MAP_RADIUS;
+  *map_y = city_center_y + city_map_y - CITY_MAP_RADIUS;
   return normalize_map_pos(map_x, map_y);
 }
 
diff -u -r -Xdiff_ignore ./common/city.h ../goal/common/city.h
--- ./common/city.h     2003-10-22 17:14:46.000000000 +0200
+++ ../goal/common/city.h       2003-10-21 17:48:25.000000000 +0200
@@ -86,13 +86,12 @@
 
 /* Iterate a city map */
 
-#define city_map_iterate(x, y)                     \
-{                                                  \
-  int x, y;                                        \
-  for (y = 0; y < CITY_MAP_SIZE; y++)              \
-    for (x = 0; x < CITY_MAP_SIZE; x++)            \
-      if (! ((x == 0 || x == (CITY_MAP_SIZE-1)) && \
-            (y == 0 || y == (CITY_MAP_SIZE-1))) )
+#define city_map_iterate(x, y)                                \
+{                                                             \
+  int x, y;                                                   \
+  for (y = 0; y < CITY_MAP_SIZE; y++)                         \
+    for (x = 0; x < CITY_MAP_SIZE; x++)                       \
+      if (is_valid_city_coords(x, y))
 
 #define city_map_iterate_end                       \
 }
diff -u -r -Xdiff_ignore ../city-sq-pre-freeciv-wo-network/common/dataio.c 
./common/dataio.c
--- ../city-sq-pre-freeciv-wo-network/common/dataio.c   2003-10-29 
10:56:14.000000000 +0100
+++ ./common/dataio.c   2003-10-29 11:02:52.000000000 +0100
@@ -43,6 +43,7 @@
 #endif
 
 #include "capability.h"
+#include "city.h"
 #include "events.h"
 #include "log.h"
 #include "mem.h"
@@ -52,9 +53,7 @@
 
 #include "dataio.h"
 
-static const int city_map_index[20] = {
-  1, 2, 3, 5, 6, 7, 8, 9, 10, 11, 13, 14, 15, 16, 17, 18, 19, 21, 22, 23
-};
+#define citymap_pos_to_indice(x, y) (CITY_MAP_SIZE * y + x)
 
 /**************************************************************************
 ...
@@ -406,14 +405,35 @@
 **************************************************************************/
 void dio_put_city_map(struct data_out *dout, const char *value)
 {
-  int i;
+  int x, y, current_byte, mult;
+
+  mult = 81;
+  current_byte = 0;
+
+  for (y = 0; y < CITY_MAP_SIZE; y++) {
+    for (x = 0; x < CITY_MAP_SIZE; x++) {
+      if (!is_valid_city_coords(x, y)) {
+       continue;
+      }
+
+      if (is_city_center(x, y)) {
+       continue;
+      }
+
+      current_byte += (value[citymap_pos_to_indice(x, y)] - '0') * mult;
+
+      if (mult == 1) {
+       dio_put_uint8(dout, current_byte);
+       current_byte = 0;
+       mult = 81;
+      } else {
+       mult /= 3;
+      }
+    }
+  }
 
-  for (i = 0; i < 20; i += 5) {
-    dio_put_uint8(dout, (value[city_map_index[i]] - '0') * 81 +
-                 (value[city_map_index[i + 1]] - '0') * 27 +
-                 (value[city_map_index[i + 2]] - '0') * 9 +
-                 (value[city_map_index[i + 3]] - '0') * 3 +
-                 (value[city_map_index[i + 4]] - '0') * 1);
+  if (mult != 81) {
+    dio_put_uint8(dout, current_byte);
   }
 }
 
@@ -617,46 +637,58 @@
 **************************************************************************/
 void dio_get_city_map(struct data_in *din, char *dest, size_t max_dest_size)
 {
-  int i;
+  int x, y, modulo, current_byte;
 
   if (dest) {
-    assert(max_dest_size >= 26);
-    dest[0] = '2';
-    dest[4] = '2';
-    dest[12] = '1';
-    dest[20] = '2';
-    dest[24] = '2';
-    dest[25] = '\0';
+    assert(max_dest_size >= CITY_MAP_SIZE * CITY_MAP_SIZE + 1);
+    dest[CITY_MAP_SIZE * CITY_MAP_SIZE] = '\0';
   }
 
   if (!enough_data(din, 4)) {
     if (dest) {
-      for (i = 0; i < 20;) {
-       int j;
-
-       for (j = 0; j < 5; j++) {
-         dest[city_map_index[i++]] = '0';
+      for (y = 0; y < CITY_MAP_SIZE; y++) {
+       for (x = 0; x < CITY_MAP_SIZE; x++) {
+         if (is_city_center(x, y)) {
+           dest[citymap_pos_to_indice(x, y)] = '1';
+           continue;
+         }
+
+         if (!is_valid_city_coords(x, y)) {
+           dest[citymap_pos_to_indice(x, y)] = '2';
+         } else {
+           dest[citymap_pos_to_indice(x, y)] = '0';
+         }
        }
       }
     }
     return;
   }
 
-  for (i = 0; i < 20;) {
-    int j;
+  modulo = 1;
 
-    dio_get_uint8(din, &j);
+  for (y = 0; y < CITY_MAP_SIZE; y++) {
+    for (x = 0; x < CITY_MAP_SIZE; x++) {
+      if (!is_valid_city_coords(x, y)) {
+       dest[citymap_pos_to_indice(x, y)] = '2';
+       continue;
+      }
+      
+      if (is_city_center(x, y)) {
+       dest[citymap_pos_to_indice(x, y)] = '1';
+       continue;
+      }
 
-    if (dest) {
-      dest[city_map_index[i++]] = '0' + j / 81;
-      j %= 81;
-      dest[city_map_index[i++]] = '0' + j / 27;
-      j %= 27;
-      dest[city_map_index[i++]] = '0' + j / 9;
-      j %= 9;
-      dest[city_map_index[i++]] = '0' + j / 3;
-      j %= 3;
-      dest[city_map_index[i++]] = '0' + j;
+      if (modulo == 1) {
+       dio_get_uint8(din, &current_byte);
+       modulo = 81;
+      } else {
+       modulo /= 3;
+      }
+      
+      if (dest) {
+       dest[citymap_pos_to_indice(x, y)] = '0' + current_byte / modulo;
+       current_byte %= modulo;
+      }
     }
   }
 }
--- ../test/common/city.h       2003-10-29 15:00:37.000000000 +0100
+++ ./common/city.h     2003-10-29 15:43:07.000000000 +0100
@@ -60,7 +60,7 @@
 
 
 /* Changing that requires updating CITY_TILES and network capabilities */
-#define CITY_MAP_RADIUS 2
+#define CITY_MAP_RADIUS 3
 
 /* Diameter of the workable city area. Must be an odd number.
    Some places in the code hardcodes this number, fx 
@@ -68,7 +68,7 @@
 #define CITY_MAP_SIZE (CITY_MAP_RADIUS * 2 + 1) 
 
 /* Number of tiles a city can use */
-#define CITY_TILES 21
+#define CITY_TILES 37
 
 #define INCITE_IMPOSSIBLE_COST (1000 * 1000 * 1000)
 
--- ../freeciv/common/capstr.c  2003-10-29 11:16:14.000000000 +0100
+++ ./common/capstr.c   2003-10-30 15:42:52.000000000 +0100
@@ -81,7 +81,7 @@
                    "+diplomacy2 +citizens_style +root_tech auth " \
                    "+nat_ulimit +retake +goto_pack borders dip " \
                    "+packet_short_unit +unit_occupied endgame_rep " \
-                   "+terr_flags +topo_id +goto_pack"
+                   "+terr_flags +topo_id +goto_pack +size3"
 
 /* "+1.14.0" is protocol for 1.14.0 release.
  *
@@ -163,6 +163,8 @@
  * topology is in use.  This value is sent to the client.
  *
  * "goto_pack" means a revised goto packet protocol.
+ *
+ * "size3" means city have now size 3
  */
 
 void init_our_capability(void)

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