Complete.Org: Mailing Lists: Archives: freeciv-dev: November 2002:
[Freeciv-Dev] Re: (PR#2293) Paratroopers jumping into an empty city
Home

[Freeciv-Dev] Re: (PR#2293) Paratroopers jumping into an empty city

[Top] [All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index] [Thread Index]
To: ue80@xxxxxxxxxxxxxxxxxxx
Cc: freeciv-dev@xxxxxxxxxxx
Subject: [Freeciv-Dev] Re: (PR#2293) Paratroopers jumping into an empty city
From: "Davide Pagnin via RT" <rt@xxxxxxxxxxxxxx>
Date: Sat, 16 Nov 2002 12:44:33 -0800
Reply-to: rt@xxxxxxxxxxxxxx

Notable behavior of the patch:

If you try to paradrop in a known_and_seen tile, where exist a city or a
stack of unit, that belong to a player to whom you are in neutral or
cease-fire or peace diplomatic status, then you are not allowed to do
the paradrop and prompted to declare war first.

If you paradrop in a tile where:

- exist a city belonging to a player to whom you are in neutral or
cease-fire or peace diplomatic status

or

- exist a stack of units of player not allied with you

then paradrop is successful, you get the showarea of the paradrop zone
but your unit is killed.

NOTE:
you are allowed to attack a known_and_seen tile where exist units
belonging to players to whom you are in war, tough this will end up in
your paratrooper always killed.

SPECIAL NOTE:
The patch uses pplayer_non_attack() function that consider
non_attackable diplomatic status as: neutral, cease-fire, peace.

This implies that a paradrop in a tile where an empty city owned by a
player to whom you are in no_contact status, is allowed (at the moment).
We should decide who to rule this out.
pplayer_non_attack, reads in the comment, that "you can attack" such a
player, thus there are no reason for not letting the paradrop being
successful...

Patch Attached, If no objection arises I will commit it into stable and
cvs, in 2 days.

        Davide

diff -urN -Xfreeciv/diff_ignore freeciv/server/unittools.c 
freeciv-beta/server/unittools.c
--- freeciv/server/unittools.c  Tue Nov 12 15:09:54 2002
+++ freeciv-beta/server/unittools.c     Sat Nov 16 21:06:41 2002
@@ -2253,24 +2253,35 @@
 **************************************************************************/
 bool do_paradrop(struct unit *punit, int dest_x, int dest_y)
 {
+  struct tile *ptile = map_get_tile(dest_x, dest_y);
+  struct player *pplayer = unit_owner(punit);
+
   if (!unit_flag(punit, F_PARATROOPERS)) {
-    notify_player_ex(unit_owner(punit), punit->x, punit->y, E_NOEVENT,
-                    _("Game: This unit type can not be paradropped."));
+    notify_player_ex(pplayer, punit->x, punit->y, E_NOEVENT,
+                     _("Game: This unit type can not be paradropped."));
     return FALSE;
   }
 
   if (!can_unit_paradrop(punit))
     return FALSE;
 
-  if (!map_get_known(dest_x, dest_y, unit_owner(punit))) {
-    notify_player_ex(unit_owner(punit), dest_x, dest_y, E_NOEVENT,
-                    _("Game: The destination location is not known."));
+  if (!map_get_known(dest_x, dest_y, pplayer)) {
+    notify_player_ex(pplayer, dest_x, dest_y, E_NOEVENT,
+                     _("Game: The destination location is not known."));
     return FALSE;
   }
 
-  if (map_get_player_tile(dest_x, dest_y, unit_owner(punit))->terrain == 
T_OCEAN) {
-    notify_player_ex(unit_owner(punit), dest_x, dest_y, E_NOEVENT,
-                    _("Game: Cannot paradrop into ocean."));
+  if (map_get_player_tile(dest_x, dest_y, pplayer)->terrain == T_OCEAN) {
+    notify_player_ex(pplayer, dest_x, dest_y, E_NOEVENT,
+                     _("Game: Cannot paradrop into ocean."));
+    return FALSE;    
+  }
+
+  if (map_get_known_and_seen(dest_x, dest_y, pplayer) && ((ptile->city
+      && pplayers_non_attack(pplayer, city_owner(ptile->city))) 
+      || is_non_attack_unit_tile(ptile, pplayer))) {
+    notify_player_ex(pplayer, dest_x, dest_y, E_NOEVENT,
+                     _("Game: Cannot attack unless you declare war first."));
     return FALSE;    
   }
 
@@ -2278,34 +2289,34 @@
     int range = unit_type(punit)->paratroopers_range;
     int distance = real_map_distance(punit->x, punit->y, dest_x, dest_y);
     if (distance > range) {
-      notify_player_ex(unit_owner(punit), dest_x, dest_y, E_NOEVENT,
-                      _("Game: The distance to the target (%i) "
-                        "is greater than the unit's range (%i)."),
-                      distance, range);
+      notify_player_ex(pplayer, dest_x, dest_y, E_NOEVENT,
+                       _("Game: The distance to the target (%i) "
+                         "is greater than the unit's range (%i)."),
+                       distance, range);
       return FALSE;
     }
   }
 
   if (map_get_terrain(dest_x, dest_y) == T_OCEAN) {
     int srange = unit_type(punit)->vision_range;
-    show_area(unit_owner(punit), dest_x, dest_y, srange);
+    show_area(pplayer, dest_x, dest_y, srange);
 
-    notify_player_ex(unit_owner(punit), dest_x, dest_y, E_UNIT_LOST,
-                    _("Game: Your %s paradropped into the ocean "
-                      "and was lost."),
-                    unit_type(punit)->name);
+    notify_player_ex(pplayer, dest_x, dest_y, E_UNIT_LOST,
+                     _("Game: Your %s paradropped into the ocean "
+                       "and was lost."),
+                     unit_type(punit)->name);
     server_remove_unit(punit);
     return TRUE;
   }
 
-  if (is_non_allied_unit_tile
-      (map_get_tile(dest_x, dest_y), unit_owner(punit))) {
+  if ((ptile->city && pplayers_non_attack(pplayer, city_owner(ptile->city)))
+      || is_non_allied_unit_tile(ptile, pplayer)) {
     int srange = unit_type(punit)->vision_range;
-    show_area(unit_owner(punit), dest_x, dest_y, srange);
-    notify_player_ex(unit_owner(punit), dest_x, dest_y, E_UNIT_LOST_ATT,
-                    _("Game: Your %s was killed by enemy units at the "
-                      "paradrop destination."),
-                    unit_type(punit)->name);
+    show_area(pplayer, dest_x, dest_y, srange);
+    notify_player_ex(pplayer, dest_x, dest_y, E_UNIT_LOST_ATT,
+                     _("Game: Your %s was killed by enemy units at the "
+                       "paradrop destination."),
+                     unit_type(punit)->name);
     server_remove_unit(punit);
     return TRUE;
   }

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