~ubuntu-branches/debian/squeeze/freeciv/squeeze

« back to all changes in this revision

Viewing changes to common/map.c

  • Committer: Bazaar Package Importer
  • Author(s): Jordi Mallach
  • Date: 2008-07-08 18:34:23 UTC
  • mfrom: (5.1.9 intrepid)
  • Revision ID: james.westby@ubuntu.com-20080708183423-c80u1h25xmj6h9s0
Tags: 2.1.5-2
Export datarootdir=/usr/share in debian/rules, so make calls can
have a correct value for LOCALEDIR (closes: #489455). Thanks Loïc Minier
for the help to solve this.

Show diffs side-by-side

added added

removed removed

Lines of Context:
14
14
#ifdef HAVE_CONFIG_H
15
15
#include <config.h>
16
16
#endif
17
 
 
18
17
#include <assert.h>
19
18
#include <string.h>             /* strlen */
20
19
 
21
20
#include "city.h"
22
21
#include "fcintl.h"
 
22
#include "game.h"
23
23
#include "log.h"
24
24
#include "mem.h"
 
25
#include "movement.h"
25
26
#include "packets.h"
26
27
#include "rand.h"
27
28
#include "shared.h"
28
29
#include "support.h"
29
30
#include "unit.h"
 
31
#include "unitlist.h"
30
32
 
31
33
#include "map.h"
32
34
 
54
56
const int DIR_DX[8] = { -1, 0, 1, -1, 1, -1, 0, 1 };
55
57
const int DIR_DY[8] = { -1, -1, -1, 0, 0, 1, 1, 1 };
56
58
 
57
 
/* Names of specials.
58
 
 * (These must correspond to enum tile_special_type in terrain.h.)
59
 
 */
60
 
static const char *tile_special_type_names[] =
61
 
{
62
 
  N_("Special1"),
63
 
  N_("Road"),
64
 
  N_("Irrigation"),
65
 
  N_("Railroad"),
66
 
  N_("Mine"),
67
 
  N_("Pollution"),
68
 
  N_("Hut"),
69
 
  N_("Fortress"),
70
 
  N_("Special2"),
71
 
  N_("River"),
72
 
  N_("Farmland"),
73
 
  N_("Airbase"),
74
 
  N_("Fallout")
75
 
};
76
 
 
77
59
/****************************************************************************
78
60
  Return a bitfield of the specials on the tile that are infrastructure.
79
61
****************************************************************************/
80
 
enum tile_special_type get_tile_infrastructure_set(const struct tile *ptile)
81
 
{
82
 
  return (ptile->special
83
 
          & (S_ROAD | S_RAILROAD | S_IRRIGATION | S_FARMLAND | S_MINE
84
 
             | S_FORTRESS | S_AIRBASE));
85
 
}
86
 
 
87
 
/***************************************************************
88
 
  Return a (static) string with terrain name;
89
 
  eg: "Hills"
90
 
  eg: "Hills (Coals)"
91
 
  eg: "Hills (Coals) [Pollution]"
92
 
***************************************************************/
93
 
const char *map_get_tile_info_text(const struct tile *ptile)
94
 
{
95
 
  static char s[64];
96
 
  bool first;
97
 
  struct tile_type *ptype = get_tile_type(ptile->terrain);
98
 
 
99
 
  sz_strlcpy(s, ptype->terrain_name);
100
 
  if (tile_has_special(ptile, S_RIVER)) {
101
 
    sz_strlcat(s, "/");
102
 
    sz_strlcat(s, get_special_name(S_RIVER));
103
 
  }
104
 
 
105
 
  first = TRUE;
106
 
  if (tile_has_special(ptile, S_SPECIAL_1)) {
107
 
    if (first) {
108
 
      first = FALSE;
109
 
      sz_strlcat(s, " (");
110
 
    } else {
111
 
      sz_strlcat(s, "/");
112
 
    }
113
 
    sz_strlcat(s, ptype->special_1_name);
114
 
  }
115
 
  if (tile_has_special(ptile, S_SPECIAL_2)) {
116
 
    if (first) {
117
 
      first = FALSE;
118
 
      sz_strlcat(s, " (");
119
 
    } else {
120
 
      sz_strlcat(s, "/");
121
 
    }
122
 
    sz_strlcat(s, ptype->special_2_name);
123
 
  }
124
 
  if (!first) {
125
 
    sz_strlcat(s, ")");
126
 
  }
127
 
 
128
 
  first = TRUE;
129
 
  if (tile_has_special(ptile, S_POLLUTION)) {
130
 
    if (first) {
131
 
      first = FALSE;
132
 
      sz_strlcat(s, " [");
133
 
    } else {
134
 
      sz_strlcat(s, "/");
135
 
    }
136
 
    sz_strlcat(s, get_special_name(S_POLLUTION));
137
 
  }
138
 
  if (tile_has_special(ptile, S_FALLOUT)) {
139
 
    if (first) {
140
 
      first = FALSE;
141
 
      sz_strlcat(s, " [");
142
 
    } else {
143
 
      sz_strlcat(s, "/");
144
 
    }
145
 
    sz_strlcat(s, get_special_name(S_FALLOUT));
146
 
  }
147
 
  if (!first) {
148
 
    sz_strlcat(s, "]");
149
 
  }
150
 
 
151
 
  return s;
 
62
bv_special get_tile_infrastructure_set(const struct tile *ptile,
 
63
                                          int *pcount)
 
64
{
 
65
  bv_special pspresent;
 
66
  int i, count = 0;
 
67
 
 
68
  BV_CLR_ALL(pspresent);
 
69
  for (i = 0; infrastructure_specials[i] != S_LAST; i++) {
 
70
    if (tile_has_special(ptile, infrastructure_specials[i])) {
 
71
      BV_SET(pspresent, infrastructure_specials[i]);
 
72
      count++;
 
73
    }
 
74
  }
 
75
  if (pcount) {
 
76
    *pcount = count;
 
77
  }
 
78
  return pspresent;
152
79
}
153
80
 
154
81
/***************************************************************
192
119
  map.num_continents        = 0;
193
120
  map.num_oceans            = 0;
194
121
  map.num_start_positions   = 0;
195
 
  map.have_specials         = FALSE;
 
122
  map.have_resources = FALSE;
196
123
  map.have_rivers_overlay   = FALSE;
197
124
  map.have_huts             = FALSE;
198
125
}
306
233
 
307
234
  if (!set_sizes) {
308
235
    /* Set map.size based on map.xsize and map.ysize. */
309
 
    map.size = (float)(map.xsize * map.ysize) / 1000.0 + 0.5;
 
236
    map.size = (float)(map_num_tiles()) / 1000.0 + 0.5;
310
237
  }
311
238
  
312
239
  /* sanity check for iso topologies*/
340
267
***************************************************************/
341
268
static void tile_init(struct tile *ptile)
342
269
{
 
270
  ptile->continent = 0;
 
271
 
 
272
  BV_CLR_ALL(ptile->tile_known);
 
273
  vision_layer_iterate(v) {
 
274
    BV_CLR_ALL(ptile->tile_seen[v]);
 
275
  } vision_layer_iterate_end;
 
276
 
 
277
  tile_clear_all_specials (ptile);
 
278
  ptile->resource = NULL;
343
279
  ptile->terrain  = T_UNKNOWN;
344
 
  ptile->special  = S_NO_SPECIAL;
345
 
  ptile->known    = 0;
346
 
  ptile->continent = 0;
347
280
  ptile->city     = NULL;
348
 
  unit_list_init(&ptile->units);
 
281
  ptile->units    = unit_list_new();
349
282
  ptile->worked   = NULL; /* pointer to city working tile */
350
 
  ptile->assigned = 0; /* bitvector */
351
283
  ptile->owner    = NULL; /* Tile not claimed by any nation. */
352
 
  ptile->client.hilite = HILITE_NONE; /* Area Selection in client. */
 
284
  ptile->owner_source = NULL;
353
285
  ptile->spec_sprite = NULL;
354
286
}
355
287
 
435
367
    return NULL;
436
368
  }
437
369
 
438
 
  if (index >= 0 && index < MAX_MAP_INDEX) {
 
370
  if (index >= 0 && index < MAP_INDEX_SIZE) {
439
371
    return map.tiles + index;
440
372
  } else {
441
373
    /* Unwrapped index coordinates are impossible, so the best we can do is
444
376
  }
445
377
}
446
378
 
447
 
/**************************************************************************
448
 
  Return the player who owns this tile (or NULL if none).
449
 
**************************************************************************/
450
 
struct player *map_get_owner(const struct tile *ptile)
451
 
{
452
 
  return ptile->owner;
453
 
}
454
 
 
455
 
/**************************************************************************
456
 
  Set the owner of a tile (may be NULL).
457
 
**************************************************************************/
458
 
void map_set_owner(struct tile *ptile, struct player *owner)
459
 
{
460
 
  ptile->owner = owner;
461
 
}
462
 
 
463
379
/***************************************************************
464
380
...
465
381
***************************************************************/
466
382
static void tile_free(struct tile *ptile)
467
383
{
468
 
  unit_list_unlink_all(&ptile->units);
 
384
  unit_list_unlink_all(ptile->units);
 
385
  unit_list_free(ptile->units);
469
386
  if (ptile->spec_sprite) {
470
387
    free(ptile->spec_sprite);
471
388
    ptile->spec_sprite = NULL;
479
396
void map_allocate(void)
480
397
{
481
398
  freelog(LOG_DEBUG, "map_allocate (was %p) (%d,%d)",
482
 
          map.tiles, map.xsize, map.ysize);
 
399
          (void *)map.tiles, map.xsize, map.ysize);
483
400
 
484
401
  assert(map.tiles == NULL);
485
 
  map.tiles = fc_malloc(map.xsize * map.ysize * sizeof(struct tile));
 
402
  map.tiles = fc_malloc(MAP_INDEX_SIZE * sizeof(*map.tiles));
 
403
 
 
404
  /* Note this use of whole_map_iterate may be a bit sketchy, since the
 
405
   * tile values (ptile->index, etc.) haven't been set yet.  It might be
 
406
   * better to do a manual loop here. */
486
407
  whole_map_iterate(ptile) {
487
 
    int index, nat_x, nat_y, map_x, map_y;
488
 
 
489
 
    index = ptile - map.tiles;
490
 
    index_to_native_pos(&nat_x, &nat_y, index);
491
 
    index_to_map_pos(&map_x, &map_y, index);
492
 
    CHECK_INDEX(index);
493
 
    CHECK_MAP_POS(map_x, map_y);
494
 
    CHECK_NATIVE_POS(nat_x, nat_y);
495
 
 
496
 
    /* HACK: these fields are declared const to keep anyone from changing
497
 
     * them.  But we have to set them somewhere!  This should be the only
498
 
     * place. */
499
 
    *(int *)&ptile->index = index;
500
 
    *(int *)&ptile->x = map_x;
501
 
    *(int *)&ptile->y = map_y;
502
 
    *(int *)&ptile->nat_x = nat_x;
503
 
    *(int *)&ptile->nat_y = nat_y;
 
408
    ptile->index = ptile - map.tiles;
 
409
    index_to_map_pos(&ptile->x, &ptile->y, ptile->index);
 
410
    index_to_native_pos(&ptile->nat_x, &ptile->nat_y, ptile->index);
 
411
    CHECK_INDEX(ptile->index);
 
412
    CHECK_MAP_POS(ptile->x, ptile->y);
 
413
    CHECK_NATIVE_POS(ptile->nat_x, ptile->nat_y);
504
414
 
505
415
    tile_init(ptile);
506
416
  } whole_map_iterate_end;
526
436
  }
527
437
}
528
438
 
529
 
/***************************************************************
530
 
...
531
 
***************************************************************/
532
 
enum tile_special_type get_special_by_name(const char * name)
533
 
{
534
 
  int i;
535
 
  enum tile_special_type st = 1;
536
 
 
537
 
  for (i = 0; i < ARRAY_SIZE(tile_special_type_names); i++) {
538
 
    if (0 == strcmp(name, tile_special_type_names[i]))
539
 
      return st;
540
 
      
541
 
    st <<= 1;
542
 
  }
543
 
 
544
 
  return S_NO_SPECIAL;
545
 
}
546
 
 
547
 
/***************************************************************
548
 
...
549
 
***************************************************************/
550
 
const char *get_special_name(enum tile_special_type type)
551
 
{
552
 
  int i;
553
 
 
554
 
  for (i = 0; i < ARRAY_SIZE(tile_special_type_names); i++) {
555
 
    if ((type & 0x1) == 1) {
556
 
      return _(tile_special_type_names[i]);
557
 
    }
558
 
    type >>= 1;
559
 
  }
560
 
 
561
 
  return NULL;
562
 
}
563
 
 
564
439
/****************************************************************************
565
440
  Return the "distance" (which is really the Manhattan distance, and should
566
441
  rarely be used) for a given vector.
581
456
****************************************************************************/
582
457
int map_vector_to_real_distance(int dx, int dy)
583
458
{
 
459
  const int absdx = abs(dx), absdy = abs(dy);
 
460
 
584
461
  if (topo_has_flag(TF_HEX)) {
585
462
    if (topo_has_flag(TF_ISO)) {
586
463
      /* Iso-hex: you can't move NE or SW. */
588
465
          || (dx > 0 && dy < 0)) {
589
466
        /* Diagonal moves in this direction aren't allowed, so it will take
590
467
         * the full number of moves. */
591
 
        return abs(dx) + abs(dy);
 
468
        return absdx + absdy;
592
469
      } else {
593
470
        /* Diagonal moves in this direction *are* allowed. */
594
 
        return MAX(abs(dx), abs(dy));
 
471
        return MAX(absdx, absdy);
595
472
      }
596
473
    } else {
597
474
      /* Hex: you can't move SE or NW. */
599
476
          || (dx < 0 && dy < 0)) {
600
477
        /* Diagonal moves in this direction aren't allowed, so it will take
601
478
         * the full number of moves. */
602
 
        return abs(dx) + abs(dy);
 
479
        return absdx + absdy;
603
480
      } else {
604
481
        /* Diagonal moves in this direction *are* allowed. */
605
 
        return MAX(abs(dx), abs(dy));
 
482
        return MAX(absdx, absdy);
606
483
      }
607
484
    }
608
485
  } else {
609
 
    return MAX(abs(dx), abs(dy));
 
486
    return MAX(absdx, absdy);
610
487
  }
611
488
}
612
489
 
670
547
*************************************************************************/
671
548
bool is_cardinally_adj_to_ocean(const struct tile *ptile)
672
549
{
673
 
  cardinal_adjc_iterate(ptile, tile1) {
674
 
    if (is_ocean(map_get_terrain(tile1))) {
675
 
      return TRUE;
676
 
    }
677
 
  } cardinal_adjc_iterate_end;
678
 
 
679
 
  return FALSE;
 
550
  return count_terrain_flag_near_tile(ptile, TRUE, FALSE, TER_OCEANIC) > 0;
680
551
}
681
552
 
682
553
/****************************************************************************
684
555
****************************************************************************/
685
556
bool is_safe_ocean(const struct tile *ptile)
686
557
{
687
 
  adjc_iterate(ptile, tile1) {
688
 
    Terrain_type_id ter = map_get_terrain(tile1);
689
 
    if (!terrain_has_flag(ter, TER_UNSAFE_COAST) && ter != T_UNKNOWN) {
690
 
      return TRUE;
691
 
    }
692
 
  } adjc_iterate_end;
693
 
 
694
 
  return FALSE;
695
 
}
696
 
 
697
 
/***************************************************************
698
 
Returns whether you can put a city on land near enough to use
699
 
the tile.
700
 
***************************************************************/
701
 
bool is_sea_usable(const struct tile *ptile)
702
 
{
703
 
  map_city_radius_iterate(ptile, tile1) {
704
 
    if (!is_ocean(map_get_terrain(tile1))) {
705
 
      return TRUE;
706
 
    }
707
 
  } map_city_radius_iterate_end;
708
 
 
709
 
  return FALSE;
710
 
}
711
 
 
712
 
/***************************************************************
713
 
...
714
 
***************************************************************/
715
 
int get_tile_food_base(const struct tile *ptile)
716
 
{
717
 
  if (tile_has_special(ptile, S_SPECIAL_1)) 
718
 
    return get_tile_type(ptile->terrain)->food_special_1;
719
 
  else if (tile_has_special(ptile, S_SPECIAL_2))
720
 
    return get_tile_type(ptile->terrain)->food_special_2;
721
 
  else
722
 
    return get_tile_type(ptile->terrain)->food;
723
 
}
724
 
 
725
 
/***************************************************************
726
 
...
727
 
***************************************************************/
728
 
int get_tile_shield_base(const struct tile *ptile)
729
 
{
730
 
  if (tile_has_special(ptile, S_SPECIAL_1))
731
 
    return get_tile_type(ptile->terrain)->shield_special_1;
732
 
  else if(tile_has_special(ptile, S_SPECIAL_2))
733
 
    return get_tile_type(ptile->terrain)->shield_special_2;
734
 
  else
735
 
    return get_tile_type(ptile->terrain)->shield;
736
 
}
737
 
 
738
 
/***************************************************************
739
 
...
740
 
***************************************************************/
741
 
int get_tile_trade_base(const struct tile *ptile)
742
 
{
743
 
  if (tile_has_special(ptile, S_SPECIAL_1))
744
 
    return get_tile_type(ptile->terrain)->trade_special_1;
745
 
  else if (tile_has_special(ptile, S_SPECIAL_2))
746
 
    return get_tile_type(ptile->terrain)->trade_special_2;
747
 
  else
748
 
    return get_tile_type(ptile->terrain)->trade;
749
 
}
750
 
 
751
 
/***************************************************************
752
 
  Return a (static) string with special(s) name(s);
753
 
  eg: "Mine"
754
 
  eg: "Road/Farmland"
755
 
***************************************************************/
756
 
const char *map_get_infrastructure_text(enum tile_special_type spe)
757
 
{
758
 
  static char s[64];
759
 
  char *p;
760
 
  
761
 
  s[0] = '\0';
762
 
 
763
 
  /* Since railroad requires road, Road/Railroad is redundant */
764
 
  if (contains_special(spe, S_RAILROAD))
765
 
    cat_snprintf(s, sizeof(s), "%s/", _("Railroad"));
766
 
  else if (contains_special(spe, S_ROAD))
767
 
    cat_snprintf(s, sizeof(s), "%s/", _("Road"));
768
 
 
769
 
  /* Likewise for farmland on irrigation */
770
 
  if (contains_special(spe, S_FARMLAND))
771
 
    cat_snprintf(s, sizeof(s), "%s/", _("Farmland"));
772
 
  else if (contains_special(spe, S_IRRIGATION))
773
 
    cat_snprintf(s, sizeof(s), "%s/", _("Irrigation"));
774
 
 
775
 
  if (contains_special(spe, S_MINE))
776
 
    cat_snprintf(s, sizeof(s), "%s/", _("Mine"));
777
 
 
778
 
  if (contains_special(spe, S_FORTRESS))
779
 
    cat_snprintf(s, sizeof(s), "%s/", _("Fortress"));
780
 
 
781
 
  if (contains_special(spe, S_AIRBASE))
782
 
    cat_snprintf(s, sizeof(s), "%s/", _("Airbase"));
783
 
 
784
 
  p = s + strlen(s) - 1;
785
 
  if (*p == '/')
786
 
    *p = '\0';
787
 
 
788
 
  return s;
789
 
}
790
 
 
791
 
/****************************************************************************
792
 
  Return the prerequesites needed before building the given infrastructure.
793
 
****************************************************************************/
794
 
enum tile_special_type map_get_infrastructure_prerequisite(enum tile_special_type spe)
795
 
{
796
 
  enum tile_special_type prereq = S_NO_SPECIAL;
797
 
 
798
 
  if (contains_special(spe, S_RAILROAD)) {
799
 
    prereq |= S_ROAD;
800
 
  }
801
 
  if (contains_special(spe, S_FARMLAND)) {
802
 
    prereq |= S_IRRIGATION;
803
 
  }
804
 
 
805
 
  return prereq;
806
 
}
807
 
 
808
 
/***************************************************************
809
 
...
810
 
***************************************************************/
811
 
enum tile_special_type get_preferred_pillage(enum tile_special_type pset)
812
 
{
813
 
  if (contains_special(pset, S_FARMLAND))
814
 
    return S_FARMLAND;
815
 
  if (contains_special(pset, S_IRRIGATION))
816
 
    return S_IRRIGATION;
817
 
  if (contains_special(pset, S_MINE))
818
 
    return S_MINE;
819
 
  if (contains_special(pset, S_FORTRESS))
820
 
    return S_FORTRESS;
821
 
  if (contains_special(pset, S_AIRBASE))
822
 
    return S_AIRBASE;
823
 
  if (contains_special(pset, S_RAILROAD))
824
 
    return S_RAILROAD;
825
 
  if (contains_special(pset, S_ROAD))
826
 
    return S_ROAD;
827
 
  return S_NO_SPECIAL;
 
558
  return count_terrain_flag_near_tile(ptile, FALSE, TRUE,
 
559
                                      TER_UNSAFE_COAST) < 100;
828
560
}
829
561
 
830
562
/***************************************************************
832
564
***************************************************************/
833
565
bool is_water_adjacent_to_tile(const struct tile *ptile)
834
566
{
835
 
  if (is_ocean(ptile->terrain)
836
 
      || tile_has_special(ptile, S_RIVER)
837
 
      || tile_has_special(ptile, S_IRRIGATION))
 
567
  if (ptile->terrain != T_UNKNOWN
 
568
      && (is_ocean(ptile->terrain)
 
569
          || tile_has_special(ptile, S_RIVER)
 
570
          || tile_has_special(ptile, S_IRRIGATION))) {
838
571
    return TRUE;
 
572
  }
839
573
 
840
574
  cardinal_adjc_iterate(ptile, tile1) {
841
 
    if (is_ocean(tile1->terrain)
842
 
        || tile_has_special(tile1, S_RIVER)
843
 
        || tile_has_special(tile1, S_IRRIGATION))
 
575
    if (ptile->terrain != T_UNKNOWN
 
576
        && (is_ocean(tile1->terrain)
 
577
            || tile_has_special(tile1, S_RIVER)
 
578
            || tile_has_special(tile1, S_IRRIGATION))) {
844
579
      return TRUE;
 
580
    }
845
581
  } cardinal_adjc_iterate_end;
846
582
 
847
583
  return FALSE;
848
584
}
849
585
 
850
 
/***************************************************************
851
 
...
852
 
***************************************************************/
853
 
int map_build_road_time(const struct tile *ptile)
854
 
{
855
 
  return get_tile_type(ptile->terrain)->road_time * ACTIVITY_FACTOR;
856
 
}
857
 
 
858
 
/***************************************************************
859
 
...
860
 
***************************************************************/
861
 
int map_build_irrigation_time(const struct tile *ptile)
862
 
{
863
 
  return get_tile_type(ptile->terrain)->irrigation_time * ACTIVITY_FACTOR;
864
 
}
865
 
 
866
 
/***************************************************************
867
 
...
868
 
***************************************************************/
869
 
int map_build_mine_time(const struct tile *ptile)
870
 
{
871
 
  return get_tile_type(ptile->terrain)->mining_time * ACTIVITY_FACTOR;
872
 
}
873
 
 
874
 
/***************************************************************
875
 
...
876
 
***************************************************************/
877
 
int map_transform_time(const struct tile *ptile)
878
 
{
879
 
  return get_tile_type(ptile->terrain)->transform_time * ACTIVITY_FACTOR;
880
 
}
881
 
 
882
 
/***************************************************************
883
 
...
884
 
***************************************************************/
885
 
int map_build_rail_time(const struct tile *ptile)
886
 
{
887
 
  return get_tile_type(ptile->terrain)->rail_time * ACTIVITY_FACTOR;
888
 
}
889
 
 
890
 
/***************************************************************
891
 
...
892
 
***************************************************************/
893
 
int map_build_airbase_time(const struct tile *ptile)
894
 
{
895
 
  return get_tile_type(ptile->terrain)->airbase_time * ACTIVITY_FACTOR;
896
 
}
897
 
 
898
 
/***************************************************************
899
 
...
900
 
***************************************************************/
901
 
int map_build_fortress_time(const struct tile *ptile)
902
 
{
903
 
  return get_tile_type(ptile->terrain)->fortress_time * ACTIVITY_FACTOR;
904
 
}
905
 
 
906
 
/***************************************************************
907
 
...
908
 
***************************************************************/
909
 
int map_clean_pollution_time(const struct tile *ptile)
910
 
{
911
 
  return get_tile_type(ptile->terrain)->clean_pollution_time * ACTIVITY_FACTOR;
912
 
}
913
 
 
914
 
/***************************************************************
915
 
...
916
 
***************************************************************/
917
 
int map_clean_fallout_time(const struct tile *ptile)
918
 
{
919
 
  return get_tile_type(ptile->terrain)->clean_fallout_time * ACTIVITY_FACTOR;
920
 
}
921
 
 
922
 
/***************************************************************
923
 
  Time to complete given activity on given tile.
924
 
***************************************************************/
925
 
int map_activity_time(enum unit_activity activity, const struct tile *ptile)
926
 
{
927
 
  switch (activity) {
928
 
  case ACTIVITY_POLLUTION:
929
 
    return map_clean_pollution_time(ptile);
930
 
  case ACTIVITY_ROAD:
931
 
    return map_build_road_time(ptile);
932
 
  case ACTIVITY_MINE:
933
 
    return map_build_mine_time(ptile);
934
 
  case ACTIVITY_IRRIGATE:
935
 
    return map_build_irrigation_time(ptile);
936
 
  case ACTIVITY_FORTRESS:
937
 
    return map_build_fortress_time(ptile);
938
 
  case ACTIVITY_RAILROAD:
939
 
    return map_build_rail_time(ptile);
940
 
  case ACTIVITY_TRANSFORM:
941
 
    return map_transform_time(ptile);
942
 
  case ACTIVITY_AIRBASE:
943
 
    return map_build_airbase_time(ptile);
944
 
  case ACTIVITY_FALLOUT:
945
 
    return map_clean_fallout_time(ptile);
946
 
  default:
947
 
    return 0;
948
 
  }
949
 
}
950
 
 
951
 
/***************************************************************
952
 
...
953
 
***************************************************************/
954
 
static void clear_infrastructure(struct tile *ptile)
955
 
{
956
 
  map_clear_special(ptile, S_INFRASTRUCTURE_MASK);
957
 
}
958
 
 
959
 
/***************************************************************
960
 
...
961
 
***************************************************************/
962
 
static void clear_dirtiness(struct tile *ptile)
963
 
{
964
 
  map_clear_special(ptile, S_POLLUTION | S_FALLOUT);
965
 
}
966
 
 
967
 
/***************************************************************
968
 
...
969
 
***************************************************************/
970
 
void map_irrigate_tile(struct tile *ptile)
971
 
{
972
 
  Terrain_type_id now, result;
973
 
  
974
 
  now = ptile->terrain;
975
 
  result = get_tile_type(now)->irrigation_result;
976
 
 
977
 
  if (now == result) {
978
 
    if (map_has_special(ptile, S_IRRIGATION)) {
979
 
      map_set_special(ptile, S_FARMLAND);
980
 
    } else {
981
 
      map_set_special(ptile, S_IRRIGATION);
982
 
    }
983
 
  } else if (result != T_NONE) {
984
 
    map_set_terrain(ptile, result);
985
 
    if (is_ocean(result)) {
986
 
      clear_infrastructure(ptile);
987
 
      clear_dirtiness(ptile);
988
 
 
989
 
      /* FIXME: When rest of code can handle
990
 
       * rivers in oceans, don't clear this! */
991
 
      map_clear_special(ptile, S_RIVER);
992
 
    }
993
 
    reset_move_costs(ptile);
994
 
  }
995
 
  map_clear_special(ptile, S_MINE);
996
 
}
997
 
 
998
 
/***************************************************************
999
 
...
1000
 
***************************************************************/
1001
 
void map_mine_tile(struct tile *ptile)
1002
 
{
1003
 
  Terrain_type_id now, result;
1004
 
  
1005
 
  now = ptile->terrain;
1006
 
  result = get_tile_type(now)->mining_result;
1007
 
  
1008
 
  if (now == result) {
1009
 
    map_set_special(ptile, S_MINE);
1010
 
  } else if (result != T_NONE) {
1011
 
    map_set_terrain(ptile, result);
1012
 
    if (is_ocean(result)) {
1013
 
      clear_infrastructure(ptile);
1014
 
      clear_dirtiness(ptile);
1015
 
 
1016
 
      /* FIXME: When rest of code can handle
1017
 
       * rivers in oceans, don't clear this! */
1018
 
      map_clear_special(ptile, S_RIVER);
1019
 
    }
1020
 
    reset_move_costs(ptile);
1021
 
  }
1022
 
  map_clear_special(ptile, S_FARMLAND);
1023
 
  map_clear_special(ptile, S_IRRIGATION);
1024
 
}
1025
 
 
1026
 
/***************************************************************
1027
 
...
1028
 
***************************************************************/
1029
 
void change_terrain(struct tile *ptile, Terrain_type_id type)
1030
 
{
1031
 
  map_set_terrain(ptile, type);
1032
 
  if (is_ocean(type)) {
1033
 
    clear_infrastructure(ptile);
1034
 
    clear_dirtiness(ptile);
1035
 
    map_clear_special(ptile, S_RIVER);  /* FIXME: When rest of code can handle
1036
 
                                           rivers in oceans, don't clear this! */
1037
 
  }
1038
 
 
1039
 
  reset_move_costs(ptile);
1040
 
 
1041
 
  /* Clear mining/irrigation if resulting terrain type cannot support
1042
 
     that feature.  (With current rules, this should only clear mines,
1043
 
     but I'm including both cases in the most general form for possible
1044
 
     future ruleset expansion. -GJW) */
1045
 
  
1046
 
  if (get_tile_type(type)->mining_result != type)
1047
 
    map_clear_special(ptile, S_MINE);
1048
 
 
1049
 
  if (get_tile_type(type)->irrigation_result != type)
1050
 
    map_clear_special(ptile, S_FARMLAND | S_IRRIGATION);
1051
 
}
1052
 
 
1053
 
/***************************************************************
1054
 
...
1055
 
***************************************************************/
1056
 
void map_transform_tile(struct tile *ptile)
1057
 
{
1058
 
  Terrain_type_id now, result;
1059
 
  
1060
 
  now = ptile->terrain;
1061
 
  result = get_tile_type(now)->transform_result;
1062
 
  
1063
 
  if (result != T_NONE) {
1064
 
    change_terrain(ptile, result);
1065
 
  }
1066
 
}
1067
 
 
1068
586
/**************************************************************************
1069
587
This function returns true if the tile at the given location can be
1070
588
"reclaimed" from ocean into land.  This is the case only when there are
1102
620
                               const struct tile *t1, const struct tile *t2)
1103
621
{
1104
622
  bool cardinal_move;
1105
 
 
1106
 
  if (game.slow_invasions
 
623
  struct unit_class *pclass = NULL;
 
624
  bool native = TRUE;
 
625
 
 
626
  if (punit) {
 
627
    pclass = unit_class(punit);
 
628
    native = is_native_terrain(punit, t2->terrain);
 
629
  }
 
630
 
 
631
  if (game.info.slow_invasions
1107
632
      && punit 
1108
633
      && is_ground_unit(punit) 
1109
634
      && is_ocean(t1->terrain)
1112
637
     * if "slowinvasions" server option is turned on. */
1113
638
    return punit->moves_left;
1114
639
  }
1115
 
  if (punit && !is_ground_unit(punit))
 
640
 
 
641
  if (punit && !pclass->move.terrain_affects) {
1116
642
    return SINGLE_MOVE;
1117
 
  if (tile_has_special(t1, S_RAILROAD) && tile_has_special(t2, S_RAILROAD))
 
643
  }
 
644
 
 
645
  /* Railroad check has to be before F_IGTER check so that F_IGTER
 
646
   * units are not penalized. F_IGTER affects also entering and
 
647
   * leaving ships, so F_IGTER check has to be before native terrain
 
648
   * check. We want to give railroad bonus only to native units. */
 
649
  if (tile_has_special(t1, S_RAILROAD) && tile_has_special(t2, S_RAILROAD)
 
650
      && native) {
1118
651
    return MOVE_COST_RAIL;
1119
 
/* return (unit_move_rate(punit)/RAIL_MAX) */
1120
 
  if (punit && unit_flag(punit, F_IGTER))
 
652
  }
 
653
  if (punit && unit_has_type_flag(punit, F_IGTER)) {
1121
654
    return SINGLE_MOVE/3;
1122
 
  if (tile_has_special(t1, S_ROAD) && tile_has_special(t2, S_ROAD))
 
655
  }
 
656
  if (!native) {
 
657
    return SINGLE_MOVE;
 
658
  }
 
659
  if (tile_has_special(t1, S_ROAD) && tile_has_special(t2, S_ROAD)) {
1123
660
    return MOVE_COST_ROAD;
 
661
  }
1124
662
 
1125
663
  if (tile_has_special(t1, S_RIVER) && tile_has_special(t2, S_RIVER)) {
1126
664
    cardinal_move = is_move_cardinal(t1, t2);
1143
681
    }
1144
682
  }
1145
683
 
1146
 
  return(get_tile_type(t2->terrain)->movement_cost*SINGLE_MOVE);
 
684
  return t2->terrain->movement_cost * SINGLE_MOVE;
1147
685
}
1148
686
 
1149
 
/***************************************************************
1150
 
  tile_move_cost_ai is used to fill the move_cost array of struct
1151
 
  tile. The cached values of this array are used in server/gotohand.c
1152
 
  and client/goto.c. tile_move_cost_ai returns the move cost as
 
687
/****************************************************************************
 
688
  map_move_cost_ai returns the move cost as
1153
689
  calculated by tile_move_cost_ptrs (with no unit pointer to get
1154
690
  unit-independent results) EXCEPT if either of the source or
1155
691
  destination tile is an ocean tile. Then the result of the method
1156
692
  shows if a ship can take the step from the source position to the
1157
693
  destination position (return value is MOVE_COST_FOR_VALID_SEA_STEP)
1158
 
  or not (return value is maxcost).
 
694
  or not.  An arbitrarily high value will be returned if the move is
 
695
  impossible.
1159
696
 
1160
 
  A ship can take the step if:
1161
 
    - both tiles are ocean or
1162
 
    - one of the tiles is ocean and the other is a city or is unknown
1163
 
***************************************************************/
1164
 
static int tile_move_cost_ai(struct tile *tile0, struct tile *tile1,
1165
 
                             int maxcost)
 
697
  FIXME: this function can't be used for air units because it returns
 
698
  sea<->land moves as impossible.
 
699
****************************************************************************/
 
700
int map_move_cost_ai(const struct tile *tile0, const struct tile *tile1)
1166
701
{
 
702
  const int maxcost = 72; /* Arbitrary. */
 
703
 
1167
704
  assert(!is_server
1168
705
         || (tile0->terrain != T_UNKNOWN && tile1->terrain != T_UNKNOWN));
1169
706
 
 
707
  /* A ship can take the step if:
 
708
   * - both tiles are ocean or
 
709
   * - one of the tiles is ocean and the other is a city or is unknown
 
710
   *
 
711
   * Note tileX->terrain will only be T_UNKNOWN at the client. */
1170
712
  if (is_ocean(tile0->terrain) && is_ocean(tile1->terrain)) {
1171
713
    return MOVE_COST_FOR_VALID_SEA_STEP;
1172
714
  }
1182
724
  }
1183
725
 
1184
726
  if (is_ocean(tile0->terrain) || is_ocean(tile1->terrain)) {
 
727
    /* FIXME: Shouldn't this return MOVE_COST_FOR_VALID_AIR_STEP?
 
728
     * Note that MOVE_COST_FOR_VALID_AIR_STEP is currently equal to
 
729
     * MOVE_COST_FOR_VALID_SEA_STEP. */
1185
730
    return maxcost;
1186
731
  }
1187
732
 
1189
734
}
1190
735
 
1191
736
/***************************************************************
1192
 
 ...
1193
 
***************************************************************/
1194
 
static void debug_log_move_costs(const char *str, struct tile *tile0)
1195
 
{
1196
 
  /* the %x don't work so well for oceans, where
1197
 
     move_cost[]==-3 ,.. --dwp
1198
 
  */
1199
 
  freelog(LOG_DEBUG, "%s (%d, %d) [%x%x%x%x%x%x%x%x]", str,
1200
 
          tile0->x, tile0->y,
1201
 
          tile0->move_cost[0], tile0->move_cost[1],
1202
 
          tile0->move_cost[2], tile0->move_cost[3],
1203
 
          tile0->move_cost[4], tile0->move_cost[5],
1204
 
          tile0->move_cost[6], tile0->move_cost[7]);
1205
 
}
1206
 
 
1207
 
/***************************************************************
1208
 
  Recalculate tile->move_cost[] for (x,y), and for adjacent
1209
 
  tiles in direction back to (x,y).  That is, call this when
1210
 
  something has changed on (x,y), eg roads, city, transform, etc.
1211
 
***************************************************************/
1212
 
void reset_move_costs(struct tile *ptile)
1213
 
{
1214
 
  int maxcost = 72; /* should be big enough without being TOO big */
1215
 
 
1216
 
  debug_log_move_costs("Resetting move costs for", ptile);
1217
 
 
1218
 
  /* trying to move off the screen is the default */
1219
 
  memset(ptile->move_cost, maxcost, sizeof(ptile->move_cost));
1220
 
 
1221
 
  adjc_dir_iterate(ptile, tile1, dir) {
1222
 
    ptile->move_cost[dir] = tile_move_cost_ai(ptile, tile1, maxcost);
1223
 
    /* reverse: not at all obfuscated now --dwp */
1224
 
    tile1->move_cost[DIR_REVERSE(dir)] =
1225
 
        tile_move_cost_ai(tile1, ptile, maxcost);
1226
 
  } adjc_dir_iterate_end;
1227
 
  debug_log_move_costs("Reset move costs for", ptile);
1228
 
}
1229
 
 
1230
 
/***************************************************************
1231
 
  Initialize tile->move_cost[] for all tiles, where move_cost[i]
1232
 
  is the unit-independent cost to move _from_ that tile, to
1233
 
  adjacent tile in direction specified by i.
1234
 
***************************************************************/
1235
 
void initialize_move_costs(void)
1236
 
{
1237
 
  int maxcost = 72; /* should be big enough without being TOO big */
1238
 
 
1239
 
  whole_map_iterate(ptile) {
1240
 
    /* trying to move off the screen is the default */
1241
 
    memset(ptile->move_cost, maxcost, sizeof(ptile->move_cost));
1242
 
 
1243
 
    adjc_dir_iterate(ptile, tile1, dir) {
1244
 
      ptile->move_cost[dir] = tile_move_cost_ai(ptile, tile1, maxcost);
1245
 
    }
1246
 
    adjc_dir_iterate_end;
1247
 
  } whole_map_iterate_end;
1248
 
}
1249
 
 
1250
 
/***************************************************************
1251
737
  The cost to move punit from where it is to tile x,y.
1252
738
  It is assumed the move is a valid one, e.g. the tiles are adjacent.
1253
739
***************************************************************/
1265
751
}
1266
752
 
1267
753
/***************************************************************
1268
 
...
1269
 
***************************************************************/
1270
 
Continent_id map_get_continent(const struct tile *ptile)
1271
 
{
1272
 
  return ptile->continent;
1273
 
}
1274
 
 
1275
 
/***************************************************************
1276
 
...
1277
 
***************************************************************/
1278
 
void map_set_continent(struct tile *ptile, Continent_id val)
1279
 
{
1280
 
  ptile->continent = val;
1281
 
}
1282
 
 
1283
 
/***************************************************************
1284
 
...
1285
 
***************************************************************/
1286
 
Terrain_type_id map_get_terrain(const struct tile *ptile)
1287
 
{
1288
 
  return ptile->terrain;
1289
 
}
1290
 
 
1291
 
/***************************************************************
1292
 
...
1293
 
***************************************************************/
1294
 
void map_set_terrain(struct tile *ptile, Terrain_type_id ter)
1295
 
{
1296
 
  ptile->terrain = ter;
1297
 
}
1298
 
 
1299
 
/***************************************************************
1300
 
...
1301
 
***************************************************************/
1302
 
enum tile_special_type map_get_special(const struct tile *ptile)
1303
 
{
1304
 
  return ptile->special;
1305
 
}
1306
 
 
1307
 
/***************************************************************
1308
 
 Returns TRUE iff the given special is found at the given map
1309
 
 position.
1310
 
***************************************************************/
1311
 
bool map_has_special(const struct tile *ptile, enum tile_special_type special)
1312
 
{
1313
 
  return contains_special(ptile->special, special);
1314
 
}
1315
 
 
1316
 
/***************************************************************
1317
 
 Returns TRUE iff the given tile has the given special.
1318
 
***************************************************************/
1319
 
bool tile_has_special(const struct tile *ptile,
1320
 
                      enum tile_special_type special)
1321
 
{
1322
 
  return contains_special(ptile->special, special);
1323
 
}
1324
 
  
1325
 
/***************************************************************
1326
 
 Returns TRUE iff the given special is found in the given set.
1327
 
***************************************************************/
1328
 
bool contains_special(enum tile_special_type set,
1329
 
                      enum tile_special_type to_test_for)
1330
 
{
1331
 
  enum tile_special_type masked = set & to_test_for;
1332
 
 
1333
 
  assert(0 == (int) S_NO_SPECIAL);
1334
 
 
1335
 
  /*
1336
 
   * contains_special should only be called with one S_* in
1337
 
   * to_test_for.
1338
 
   */
1339
 
  assert(masked == S_NO_SPECIAL || masked == to_test_for);
1340
 
 
1341
 
  return masked == to_test_for;
1342
 
}
1343
 
 
1344
 
/***************************************************************
1345
 
...
1346
 
***************************************************************/
1347
 
void map_set_special(struct tile *ptile, enum tile_special_type spe)
1348
 
{
1349
 
  ptile->special |= spe;
1350
 
 
1351
 
  if (contains_special(spe, S_ROAD) || contains_special(spe, S_RAILROAD)) {
1352
 
    reset_move_costs(ptile);
1353
 
  }
1354
 
}
1355
 
 
1356
 
/***************************************************************
1357
 
...
1358
 
***************************************************************/
1359
 
void map_clear_special(struct tile *ptile, enum tile_special_type spe)
1360
 
{
1361
 
  ptile->special &= ~spe;
1362
 
 
1363
 
  if (contains_special(spe, S_ROAD) || contains_special(spe, S_RAILROAD)) {
1364
 
    reset_move_costs(ptile);
1365
 
  }
1366
 
}
1367
 
 
1368
 
/***************************************************************
1369
 
  Remove any specials which may exist at these map co-ordinates.
1370
 
***************************************************************/
1371
 
void map_clear_all_specials(struct tile *ptile)
1372
 
{
1373
 
  ptile->special = S_NO_SPECIAL;
1374
 
}
1375
 
 
1376
 
/***************************************************************
1377
 
...
1378
 
***************************************************************/
1379
 
struct city *map_get_city(const struct tile *ptile)
1380
 
{
1381
 
  return ptile->city;
1382
 
}
1383
 
 
1384
 
/***************************************************************
1385
 
...
1386
 
***************************************************************/
1387
 
void map_set_city(struct tile *ptile, struct city *pcity)
1388
 
{
1389
 
  ptile->city = pcity;
1390
 
}
1391
 
 
1392
 
/***************************************************************
1393
754
  Are (x1,y1) and (x2,y2) really the same when adjusted?
1394
755
  This function might be necessary ALOT of places...
1395
756
***************************************************************/
1588
949
{
1589
950
  struct tile *ptile;
1590
951
  int tries = 0;
1591
 
  const int max_tries = map.xsize * map.ysize / ACTIVITY_FACTOR;
 
952
  const int max_tries = MAP_INDEX_SIZE / ACTIVITY_FACTOR;
1592
953
 
1593
954
  /* First do a few quick checks to find a spot.  The limit on number of
1594
955
   * tries could use some tweaking. */
1595
956
  do {
1596
 
    ptile = map.tiles + myrand(map.xsize * map.ysize);
 
957
    ptile = map.tiles + myrand(MAP_INDEX_SIZE);
1597
958
  } while (filter && !filter(ptile, data) && ++tries < max_tries);
1598
959
 
1599
960
  /* If that fails, count all available spots and pick one.
1600
961
   * Slow but reliable. */
1601
962
  if (tries == max_tries) {
1602
 
    int count = 0, positions[map.xsize * map.ysize];
 
963
    int count = 0, positions[MAP_INDEX_SIZE];
1603
964
 
1604
965
    whole_map_iterate(ptile) {
1605
966
      if (filter(ptile, data)) {