Complete.Org: Mailing Lists: Archives: freeciv-dev: December 2003:
[Freeciv-Dev] (PR#7179) Request/preliminary patch: nuke affects surround
Home

[Freeciv-Dev] (PR#7179) Request/preliminary patch: nuke affects surround

[Top] [All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index] [Thread Index]
To: undisclosed-recipients: ;
Subject: [Freeciv-Dev] (PR#7179) Request/preliminary patch: nuke affects surrounding infrastructure and reputation
From: "Guest" <rt-guest@xxxxxxxxxxx>
Date: Wed, 31 Dec 2003 11:32:20 -0800
Reply-to: rt@xxxxxxxxxxx

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

I'm not familiar with Civ 2 rules for nukes, so I can't comment on that.
However, I have played Civ 3 and in Civ 3 nukes fill the 8 tiles around
the target with pollution (there's no such thing as 'fallout' in Civ 3),
and destroy all roads and railroads in the surrounding 8 tiles also.
Units in these tiles have a 50% chance of survival. Also, it seemed odd
that there are no non-environmental penalties for using nukes.

Now, I don't have a problem with freeciv's unit nuking behaviour, but I
prefer the Civ 3 system of infrastructure destruction and reputation
loss. I hacked together an edit for server/unittools.c, for the two
functions do_nuclear_explosion() and do_nuke_tile(). This patch is a
patch for the December 29 CVS snapshot
(ftp://www.freeciv.org/pub/freeciv/latest/freeciv-cvs-Dec-29.tar.bz2).

The patch adds these behaviours:

* 66% chance that dropping a nuke will cause a player to lose
(GAME_MAX_REPUTATION * 0.02) units of reputation
* 20% chance of further reputation loss of (GAME_MAX_REPUTATION * 0.03)
* for each surrounding tile railroads and farmland are removed, there's
a 50% chance of irrigation removal and a 33% chance of road removal

All units in surrounding squares still die, and population halving is
still carried out.

It works for me, but since I'm not much of a freeciv hacker, it'd
probably be a good idea for someone with a better handle on the code to
give it a once-over. I'm still not sure whether all those conditional
send_tile_info() calls are all necessary.

Enough babbling, here's the unified diff (also an attachment):

--- unittools.c.orig    2003-12-31 14:35:46.000000000 +0000
+++ unittools.c 2003-12-31 19:30:06.000000000 +0000
@@ -2041,11 +2041,14 @@
 }
 
 /**************************************************************************
-  Nuke a square: 1) remove all units on the square, and 2) halve the 
-  size of the city on the square.
+  Nuke a square: 1) remove all units on the tile and 2) if it's a city,
+  halve its size OTHERWISE 3) remove some amenities on the square.
 
-  If it isn't a city square or an ocean square then with 50% chance add 
-  some fallout, then notify the client about the changes.
+  If it isn't a city tile then take out railroads, farmland, some roads
+  and irrigation. If it's not a city or ocean tile then with 50% chance
+  add fallout.
+  
+  Finally, notify the client about changes.
 **************************************************************************/
 static void do_nuke_tile(struct player *pplayer, int x, int y)
 {
@@ -2082,26 +2085,45 @@
     }
 
     city_reduce_size(pcity, pcity->size / 2);
+  } else {
+    /* not a city tile, get rid of some infrastructure */
+       if (map_has_special(x, y, S_FARMLAND)) {
+         map_clear_special(x, y, S_FARMLAND);
+         send_tile_info(NULL, x, y);
+       }
+       if ((map_has_special(x, y, S_IRRIGATION)) && (myrand(2) == 1)) {
+         map_clear_special(x, y, S_IRRIGATION);
+         send_tile_info(NULL, x, y);
+       }
+       if (map_has_special(x, y, S_RAILROAD)) {
+      map_clear_special(x, y, S_RAILROAD);
+         send_tile_info(NULL, x, y);
+       }
+       if ((map_has_special(x, y, S_ROAD)) && (myrand(3) == 1)) {
+         map_clear_special(x, y, S_ROAD);
+         send_tile_info(NULL, x, y);
+       }
   }
 
   if (!is_ocean(map_get_terrain(x, y)) && myrand(2) == 1) {
     if (game.rgame.nuke_contamination == CONTAMINATION_POLLUTION) {
       if (!map_has_special(x, y, S_POLLUTION)) {
-       map_set_special(x, y, S_POLLUTION);
-       send_tile_info(NULL, x, y);
+           map_set_special(x, y, S_POLLUTION);
+           send_tile_info(NULL, x, y);
       }
     } else {
       if (!map_has_special(x, y, S_FALLOUT)) {
-       map_set_special(x, y, S_FALLOUT);
-       send_tile_info(NULL, x, y);
+           map_set_special(x, y, S_FALLOUT);
+           send_tile_info(NULL, x, y);
       }
     }
   }
 }
 
 /**************************************************************************
-  nuke all the squares in a 3x3 square around the center of the explosion
-  pplayer is the player that caused the explosion.
+  Nuke all the squares in a 3x3 square around the center of the explosion
+  pplayer is the player that caused the explosion. Change rep as
+  appropriate.
 **************************************************************************/
 void do_nuclear_explosion(struct player *pplayer, int x, int y)
 {
@@ -2109,6 +2131,18 @@
     do_nuke_tile(pplayer, x1, y1);
   } square_iterate_end;
 
+  /* Give random reputation penalties to nuke users */
+  if (myrand(3) < 3) {
+    pplayer->reputation -= (GAME_MAX_REPUTATION * 0.02);
+  }
+  if (myrand(5) == 1) {
+    pplayer->reputation -= (GAME_MAX_REPUTATION * 0.03);
+  }
+  if (pplayer->reputation < 0) {
+    pplayer->reputation = 0;
+  }
+  send_player_info(pplayer, NULL);
+
   notify_conn_ex(&game.game_connections, x, y, E_NUKE,
                 _("Game: %s detonated a nuke!"), pplayer->name);
 }

Attachment: nuke_rep_infra_change.diff
Description: Binary data


[Prev in Thread] Current Thread [Next in Thread]
  • [Freeciv-Dev] (PR#7179) Request/preliminary patch: nuke affects surrounding infrastructure and reputation, Guest <=