Author: sveinung
Date: Sat May  6 22:58:54 2017
New Revision: 35424

URL: http://svn.gna.org/viewcvs/freeciv?rev=35424&view=rev
Log:
Non Spy consumption: use action shared system.

Have the actions where units without the Spy unit type flag always are
consumed and units with the Spy utype flag has a chance to escape use the
shared action system when consuming non spies.

Using the system common to actions makes the auto help system aware that non
Spy units will be consumed.

By using the general action consumes actor system it becomes possible to
split those actions in a unit consuming and a unit escaping version in the
future.

See hrm Feature #657674

Modified:
    trunk/common/unittype.c
    trunk/server/diplomats.c

Modified: trunk/common/unittype.c
URL: 
http://svn.gna.org/viewcvs/freeciv/trunk/common/unittype.c?rev=35424&r1=35423&r2=35424&view=diff
==============================================================================
--- trunk/common/unittype.c     (original)
+++ trunk/common/unittype.c     Sat May  6 22:58:54 2017
@@ -850,8 +850,30 @@
 bool utype_is_consumed_by_action(const struct action *paction,
                                  const struct unit_type *utype)
 {
-  /* Only care about the action it self for now. */
-  return paction->actor_consuming_always;
+  if (paction->actor_consuming_always) {
+    /* This action will always consume the unit no matter who it is. */
+    return TRUE;
+  }
+
+  /* FIXME: Since the actions listed below can be predicted to always
+   * consume the actor unit based on unit type alone they should probably
+   * be split in an actor consuming and a non actor consuming version. */
+  switch (paction->id) {
+  case ACTION_SPY_POISON:
+  case ACTION_SPY_SABOTAGE_UNIT:
+  case ACTION_SPY_STEAL_TECH:
+  case ACTION_SPY_TARGETED_STEAL_TECH:
+  case ACTION_SPY_INCITE_CITY:
+  case ACTION_SPY_SABOTAGE_CITY:
+  case ACTION_SPY_TARGETED_SABOTAGE_CITY:
+  case ACTION_SPY_STEAL_GOLD:
+  case ACTION_STEAL_MAPS:
+  case ACTION_SPY_NUKE:
+    /* A Spy has a chance to escape after performing the action. */
+    return !utype_has_flag(utype, UTYF_SPY);
+  default:
+    return FALSE;
+  }
 }
 
 /****************************************************************************

Modified: trunk/server/diplomats.c
URL: 
http://svn.gna.org/viewcvs/freeciv/trunk/server/diplomats.c?rev=35424&r1=35423&r2=35424&view=diff
==============================================================================
--- trunk/server/diplomats.c    (original)
+++ trunk/server/diplomats.c    Sat May  6 22:58:54 2017
@@ -69,12 +69,14 @@
                                 struct player *tgt_player,
                                 const struct action *act);
 static void diplomat_escape(struct player *pplayer, struct unit *pdiplomat,
-                            const struct city *pcity);
+                            const struct city *pcity,
+                            const struct action *paction);
 static void diplomat_escape_full(struct player *pplayer,
                                  struct unit *pdiplomat,
                                  bool city_related,
                                  struct tile *ptile,
-                                 const char *vlink);
+                                 const char *vlink,
+                                 const struct action *paction);
 
 /******************************************************************************
   Poison a city's water supply.
@@ -155,7 +157,7 @@
   action_consequence_success(paction, pplayer, cplayer, ctile, clink);
 
   /* Now lets see if the spy survives. */
-  diplomat_escape_full(pplayer, pdiplomat, TRUE, ctile, clink);
+  diplomat_escape_full(pplayer, pdiplomat, TRUE, ctile, clink, paction);
 
   return TRUE;
 }
@@ -436,7 +438,7 @@
                              unit_tile(pvictim), victim_link);
 
   /* Now lets see if the spy survives. */
-  diplomat_escape(pplayer, pdiplomat, NULL);
+  diplomat_escape(pplayer, pdiplomat, NULL, paction);
 
   return TRUE;
 }
@@ -763,8 +765,8 @@
   action_consequence_success(paction, pplayer, cplayer,
                              city_tile(pcity), city_link(pcity));
 
-  /* Check if a spy survives her mission. Diplomats never do. */
-  diplomat_escape(pplayer, pdiplomat, pcity);
+  /* Check if a spy survives her mission. */
+  diplomat_escape(pplayer, pdiplomat, pcity, paction);
 
   return TRUE;
 }
@@ -899,11 +901,11 @@
                               API_TYPE_STRING, "incited");
   }
 
-  /* Check if a spy survives her mission. Diplomats never do.
+  /* Check if a spy survives her mission.
    * _After_ transferring the city, or the city area is first fogged
    * when the diplomat is removed, and then unfogged when the city
    * is transferred. */
-  diplomat_escape_full(pplayer, pdiplomat, TRUE, ctile, clink);
+  diplomat_escape_full(pplayer, pdiplomat, TRUE, ctile, clink, paction);
 
   /* Update the players gold in the client */
   send_player_info_c(pplayer, pplayer->connections);
@@ -1177,8 +1179,8 @@
   action_consequence_success(paction, pplayer, cplayer,
                              city_tile(pcity), city_link(pcity));
 
-  /* Check if a spy survives her mission. Diplomats never do. */
-  diplomat_escape(pplayer, pdiplomat, pcity);
+  /* Check if a spy survives her mission. */
+  diplomat_escape(pplayer, pdiplomat, pcity, paction);
 
   return TRUE;
 }
@@ -1313,7 +1315,7 @@
 
   /* Try to escape. */
   diplomat_escape_full(act_player, act_unit, TRUE,
-                       tgt_tile, tgt_city_link);
+                       tgt_tile, tgt_city_link, paction);
 
   /* Update the players' gold in the client */
   send_player_info_c(act_player, act_player->connections);
@@ -1422,7 +1424,7 @@
 
   /* Try to escape. */
   diplomat_escape_full(act_player, act_unit, TRUE,
-                       tgt_tile, tgt_city_link);
+                       tgt_tile, tgt_city_link, paction);
 
   return TRUE;
 }
@@ -1510,7 +1512,13 @@
 
   /* Try to escape before the blast. */
   diplomat_escape_full(act_player, act_unit, TRUE,
-                       tgt_tile, tgt_city_link);
+                       tgt_tile, tgt_city_link, paction);
+
+  if (utype_is_consumed_by_action(paction, unit_type_get(act_unit))) {
+    /* The unit must be wiped here so it won't be seen as a victim of the
+     * detonation of its own nuke. */
+    wipe_unit(act_unit, ULR_USED, NULL);
+  }
 
   /* TODO: In real life a suitcase nuke is way less powerful than an ICBM.
    * Maybe the size of the suitcase nuke explosion should be ruleset
@@ -1847,7 +1855,8 @@
     - Escapee may become a veteran.
 **************************************************************************/
 static void diplomat_escape(struct player *pplayer, struct unit *pdiplomat,
-                            const struct city *pcity)
+                            const struct city *pcity,
+                            const struct action *paction)
 {
   struct tile *ptile;
   const char *vlink;
@@ -1861,7 +1870,7 @@
   }
 
   return diplomat_escape_full(pplayer, pdiplomat, pcity != NULL,
-                              ptile, vlink);
+                              ptile, vlink, paction);
 }
 
 /**************************************************************************
@@ -1877,7 +1886,8 @@
                                  struct unit *pdiplomat,
                                  bool city_related,
                                  struct tile *ptile,
-                                 const char *vlink)
+                                 const char *vlink,
+                                 const struct action *paction)
 {
   int escapechance;
   struct city *spyhome;
@@ -1899,7 +1909,7 @@
                               FALSE, FALSE, TRUE, FALSE, NULL);
 
   if (spyhome
-      && unit_has_type_flag(pdiplomat, UTYF_SPY)
+      && !utype_is_consumed_by_action(paction, unit_type_get(pdiplomat))
       && (unit_has_type_flag(pdiplomat, UTYF_SUPERSPY)
           || fc_rand (100) < escapechance)) {
     /* Attacking Spy/Diplomat survives. */
@@ -1935,10 +1945,11 @@
     }
   }
 
-  wipe_unit(pdiplomat,
-            /* A non Spy can't escape. It is therefore spent, not caught. */
-            unit_has_type_flag(pdiplomat, UTYF_SPY) ? ULR_CAUGHT : ULR_USED,
-            NULL);
+  if (!utype_is_consumed_by_action(paction, unit_type_get(pdiplomat))) {
+    /* The unit was caught, not spent. It must therefore be deleted by
+     * hand. */
+    wipe_unit(pdiplomat, ULR_CAUGHT, NULL);
+  }
 }
 
 /**************************************************************************


_______________________________________________
Freeciv-commits mailing list
Freeciv-commits@gna.org
https://mail.gna.org/listinfo/freeciv-commits

Reply via email to