Complete.Org: Mailing Lists: Archives: freeciv-dev: March 2004:
[Freeciv-Dev] Re: (PR#7667) Wishlist: "load" and "unload" commands
Home

[Freeciv-Dev] Re: (PR#7667) Wishlist: "load" and "unload" commands

[Top] [All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index] [Thread Index]
To: undisclosed-recipients: ;
Subject: [Freeciv-Dev] Re: (PR#7667) Wishlist: "load" and "unload" commands
From: "Jason Short" <jdorje@xxxxxxxxxxxxxxxxxxxxx>
Date: Wed, 31 Mar 2004 00:21:39 -0800
Reply-to: rt@xxxxxxxxxxx

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

And here's a patch.

- Can_unit_transport_unit is renamed as can_unit_load() and moved to 
common/unit.  It also does a few more checks now.

- Find_transporter_for_unit is moved as-is into common/unit.

- can_unit_unload is added to common/unit.

- request_unit_unload is renamed as request_unit_unload_all.  Similar 
with key_unit_unload.

- A new client function request_unit_unload(pcargo) is added.  This does 
exactly what you'd expect.

- A new client function request_unit_load(pcargo, ptrans) is added.  If 
ptrans is NULL a random transporter will be picked by 
find_transporter_for_unit.

- Clients are updated only for the function renaming.

- The GTK2 client is updated to add "Load" (shift-L) and "Unload" 
(shift-U) menu items.  The "worklist" menu item is changed from Shift-L 
to Shift-W.

The result is pretty nice.  Of course a more advanced interface would 
allow the player to control exactly which transport a unit was loaded 
into.  This is a GUI change that becomes possible with this interface.

The patch is 25k in size.  It could be cut into pieces: one piece to 
move functions, a second to implement the core client functionality, a 
third for the gtk2 changes.  This doesn't give any technical benefit 
other than smaller patches.

jason

? cma_weirdness
? data/bak
? data/civ3
? data/womoks
Index: client/control.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/control.c,v
retrieving revision 1.131
diff -u -r1.131 control.c
--- client/control.c    30 Mar 2004 19:00:15 -0000      1.131
+++ client/control.c    31 Mar 2004 07:15:42 -0000
@@ -631,16 +631,35 @@
 /**************************************************************************
 ...
 **************************************************************************/
-void request_unit_unload(struct unit *punit)
+void request_unit_unload_all(struct unit *punit)
 {
+  struct tile *ptile = map_get_tile(punit->x, punit->y);
+  struct unit *plast = NULL;
+
   if(get_transporter_capacity(punit) == 0) {
     append_output_window(_("Game: Only transporter units can be unloaded."));
     return;
   }
 
   request_unit_wait(punit);    /* RP: unfocus the ship */
-  
-  dsend_packet_unit_unload(&aconnection, punit->id);
+
+  unit_list_iterate(ptile->units, pcargo) {
+    if (pcargo->transported_by == punit->id) {
+      request_unit_unload(pcargo);
+
+      if (pcargo->activity == ACTIVITY_SENTRY) {
+       request_new_unit_activity(punit, ACTIVITY_IDLE);
+      }
+
+      plast = pcargo;
+    }
+  } unit_list_iterate_end;
+
+  if (plast) {
+    /* If the above unloading failed this focus will still happen.  That's
+     * probably a feature. */
+    set_unit_focus(plast);
+  }
 }
 
 /**************************************************************************
@@ -811,6 +830,39 @@
   }
 }
 
+/****************************************************************************
+  Send a request to the server that the cargo be loaded into the transporter.
+
+  If ptransporter is NULL a transporter will be picked at random.
+****************************************************************************/
+void request_unit_load(struct unit *pcargo, struct unit *ptrans)
+{
+  if (!ptrans) {
+    ptrans = find_transporter_for_unit(pcargo, pcargo->x, pcargo->y);
+  }
+
+  if (can_client_issue_orders()
+      && can_unit_load(pcargo, ptrans)) {
+    dsend_packet_unit_load(&aconnection, pcargo->id, ptrans->id);
+  }
+}
+
+/****************************************************************************
+  Send a request to the server that the cargo be unloaded from its current
+  transporter.
+****************************************************************************/
+void request_unit_unload(struct unit *pcargo)
+{
+  struct unit *ptrans = find_unit_by_id(pcargo->transported_by);
+
+  if (can_client_issue_orders()
+      && ptrans
+      && can_unit_unload(pcargo, ptrans)
+      && can_unit_survive_at_tile(pcargo, pcargo->x, pcargo->y)) {
+    dsend_packet_unit_unload(&aconnection, pcargo->id, ptrans->id);
+  }
+}
+
 /**************************************************************************
 ...
 **************************************************************************/
@@ -1717,10 +1769,10 @@
 /**************************************************************************
 ...
 **************************************************************************/
-void key_unit_unload(void)
+void key_unit_unload_all(void)
 {
   if (punit_focus) {
-    request_unit_unload(punit_focus);
+    request_unit_unload_all(punit_focus);
   }
 }
 
Index: client/control.h
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/control.h,v
retrieving revision 1.41
diff -u -r1.41 control.h
--- client/control.h    30 Mar 2004 19:00:15 -0000      1.41
+++ client/control.h    31 Mar 2004 07:15:42 -0000
@@ -48,6 +48,8 @@
 void request_new_unit_activity_targeted(struct unit *punit,
                                        enum unit_activity act,
                                        enum tile_special_type tgt);
+void request_unit_load(struct unit *pcargo, struct unit *ptransporter);
+void request_unit_unload(struct unit *pcargo);
 void request_unit_auto(struct unit *punit);
 void request_unit_build_city(struct unit *punit);
 void request_unit_caravan_action(struct unit *punit, enum packet_type action);
@@ -62,7 +64,7 @@
 void request_unit_patrol(void);
 void request_unit_pillage(struct unit *punit);
 void request_unit_sentry(struct unit *punit);
-void request_unit_unload(struct unit *punit);
+void request_unit_unload_all(struct unit *punit);
 void request_unit_airlift(struct unit *punit, struct city *pcity);
 void request_unit_return(struct unit *punit);
 void request_unit_upgrade(struct unit *punit);
@@ -153,7 +155,7 @@
 void key_unit_sentry(void);
 void key_unit_traderoute(void);
 void key_unit_transform(void);
-void key_unit_unload(void);
+void key_unit_unload_all(void);
 void key_unit_wait(void);
 void key_unit_wakeup_others(void);
 
Index: client/packhand.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/packhand.c,v
retrieving revision 1.356
diff -u -r1.356 packhand.c
--- client/packhand.c   30 Mar 2004 19:00:15 -0000      1.356
+++ client/packhand.c   31 Mar 2004 07:15:42 -0000
@@ -1019,13 +1019,14 @@
         refresh_unit_city_dialogs(punit);
       }
 
-      /* These two lines force the menus to be updated as appropriate when
-        the unit activity changes. */
-      if (punit == get_unit_in_focus()) {
-         update_menus();
-      }
     } /*** End of Change in activity or activity's target. ***/
     
+    /* These two lines force the menus to be updated as appropriate when
+     * the focus unit changes. */
+    if (punit == get_unit_in_focus()) {
+      update_menus();
+    }
+
     if (punit->homecity != packet_unit->homecity) {
       /* change homecity */
       struct city *pcity;
Index: client/gui-gtk/menu.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-gtk/menu.c,v
retrieving revision 1.81
diff -u -r1.81 menu.c
--- client/gui-gtk/menu.c       20 Jan 2004 21:52:07 -0000      1.81
+++ client/gui-gtk/menu.c       31 Mar 2004 07:15:43 -0000
@@ -378,7 +378,7 @@
     key_unit_homecity();
     break;
    case MENU_ORDER_UNLOAD:
-    key_unit_unload();
+    key_unit_unload_all();
     break;
    case MENU_ORDER_WAKEUP_OTHERS:
     key_unit_wakeup_others();
Index: client/gui-gtk-2.0/menu.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-gtk-2.0/menu.c,v
retrieving revision 1.26
diff -u -r1.26 menu.c
--- client/gui-gtk-2.0/menu.c   20 Jan 2004 21:52:07 -0000      1.26
+++ client/gui-gtk-2.0/menu.c   31 Mar 2004 07:15:43 -0000
@@ -113,6 +113,8 @@
   MENU_ORDER_SENTRY,
   MENU_ORDER_PILLAGE,
   MENU_ORDER_HOMECITY,
+  MENU_ORDER_UNLOAD_TRANSPORTER,
+  MENU_ORDER_LOAD,
   MENU_ORDER_UNLOAD,
   MENU_ORDER_WAKEUP_OTHERS,
   MENU_ORDER_AUTO_SETTLER,   /* shared with AUTO_ATTACK */
@@ -378,8 +380,14 @@
    case MENU_ORDER_HOMECITY:
     key_unit_homecity();
     break;
-   case MENU_ORDER_UNLOAD:
-    key_unit_unload();
+   case MENU_ORDER_UNLOAD_TRANSPORTER:
+    key_unit_unload_all();
+    break;
+  case MENU_ORDER_LOAD:
+    request_unit_load(get_unit_in_focus(), NULL);
+    break;
+  case MENU_ORDER_UNLOAD:
+    request_unit_unload(get_unit_in_focus());
     break;
    case MENU_ORDER_WAKEUP_OTHERS:
     key_unit_wakeup_others();
@@ -605,7 +613,7 @@
        NULL,                   0,                                      
"<Separator>"   },
   { "/" N_("Kingdom") "/" N_("_Find City"),            "<shift>f",
        kingdom_menu_callback,  MENU_KINGDOM_FIND_CITY                          
        },
-  { "/" N_("Kingdom") "/" N_("Work_lists"),            "<shift>l",
+  { "/" N_("Kingdom") "/" N_("_Worklists"),            "<shift>w",
        kingdom_menu_callback,  MENU_KINGDOM_WORKLISTS                          
        },
   { "/" N_("Kingdom") "/sep2",                         NULL,
        NULL,                   0,                                      
"<Separator>"   },
@@ -699,8 +707,12 @@
        NULL,                   0,                                      
"<Separator>"   },
   { "/" N_("Orders") "/" N_("Make _Homecity"),         "h",
        orders_menu_callback,   MENU_ORDER_HOMECITY                             
        },
-  { "/" N_("Orders") "/" N_("_Unload"),                        "u",
-       orders_menu_callback,   MENU_ORDER_UNLOAD                               
        },
+  { "/" N_("Orders") "/" N_("_Load"), "<shift>L",
+    orders_menu_callback, MENU_ORDER_LOAD},
+  { "/" N_("Orders") "/" N_("_Unload Transporter"),    "u",
+       orders_menu_callback,   MENU_ORDER_UNLOAD_TRANSPORTER                   
                },
+  { "/" N_("Orders") "/" N_("_Unload"), "<shift>U",
+    orders_menu_callback, MENU_ORDER_UNLOAD},
   { "/" N_("Orders") "/" N_("Wake up o_thers"),                "<shift>w",
        orders_menu_callback,   MENU_ORDER_WAKEUP_OTHERS                        
        },
   { "/" N_("Orders") "/sep3",                          NULL,
@@ -1082,7 +1094,7 @@
 
     menus_set_sensitive("<main>/_Kingdom/_Tax Rates",
                        can_client_issue_orders());
-    menus_set_sensitive("<main>/_Kingdom/Work_lists",
+    menus_set_sensitive("<main>/_Kingdom/_Worklists",
                        can_client_issue_orders());
     menus_set_sensitive("<main>/_Kingdom/_Government",
                        can_client_issue_orders());
@@ -1164,8 +1176,14 @@
                          !unit_flag(punit, F_UNDISBANDABLE));
       menus_set_sensitive("<main>/_Orders/Make _Homecity",
                          can_unit_change_homecity(punit));
-      menus_set_sensitive("<main>/_Orders/_Unload",
+      menus_set_sensitive("<main>/_Orders/_Unload Transporter",
                          get_transporter_capacity(punit)>0);
+      menus_set_sensitive("<main>/_Orders/_Load",
+       can_unit_load(punit, find_transporter_for_unit(punit,
+                                                      punit->x, punit->y)));
+      menus_set_sensitive("<main>/_Orders/_Unload",
+       (can_unit_unload(punit, find_unit_by_id(punit->transported_by))
+        && can_unit_exist_at_tile(punit, punit->x, punit->y)));
       menus_set_sensitive("<main>/_Orders/Wake up o_thers", 
                          is_unit_activity_on_tile(ACTIVITY_SENTRY,
                                                    punit->x, punit->y));
Index: client/gui-mui/gui_main.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-mui/gui_main.c,v
retrieving revision 1.81
diff -u -r1.81 gui_main.c
--- client/gui-mui/gui_main.c   24 Jan 2004 02:58:55 -0000      1.81
+++ client/gui-mui/gui_main.c   31 Mar 2004 07:15:43 -0000
@@ -590,7 +590,7 @@
       key_unit_wait();
       break;
     case MENU_ORDER_UNLOAD:
-      key_unit_unload();
+      key_unit_unload_all();
       break;
     case MENU_ORDER_WAKEUP_OTHERS:
       key_unit_wakeup_others();
Index: client/gui-sdl/menu.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-sdl/menu.c,v
retrieving revision 1.24
diff -u -r1.24 menu.c
--- client/gui-sdl/menu.c       20 Jan 2004 21:52:07 -0000      1.24
+++ client/gui-sdl/menu.c       31 Mar 2004 07:15:43 -0000
@@ -141,7 +141,7 @@
     key_unit_homecity();
     break;
   case ID_UNIT_ORDER_UNLOAD:
-    key_unit_unload();
+    key_unit_unload_all();
     break;
   case ID_UNIT_ORDER_WAKEUP_OTHERS:
     key_unit_wakeup_others();
Index: client/gui-win32/menu.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-win32/menu.c,v
retrieving revision 1.17
diff -u -r1.17 menu.c
--- client/gui-win32/menu.c     7 Jul 2003 19:14:37 -0000       1.17
+++ client/gui-win32/menu.c     31 Mar 2004 07:15:45 -0000
@@ -705,7 +705,7 @@
       break;
     case IDM_ORDERS_UNLOAD:
       if(get_unit_in_focus())
-       request_unit_unload(get_unit_in_focus());
+       request_unit_unload_all(get_unit_in_focus());
       break;
     case IDM_ORDERS_WAKEUP:
       if(get_unit_in_focus())
Index: client/gui-xaw/actions.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-xaw/actions.c,v
retrieving revision 1.18
diff -u -r1.18 actions.c
--- client/gui-xaw/actions.c    1 Dec 2003 19:32:04 -0000       1.18
+++ client/gui-xaw/actions.c    31 Mar 2004 07:15:45 -0000
@@ -531,10 +531,10 @@
     key_unit_transform();
 }
 
-static void xaw_key_unit_unload(Widget w, XEvent *event, String *argv, 
Cardinal *argc)
+static void xaw_key_unit_unload_all(Widget w, XEvent *event, String *argv, 
Cardinal *argc)
 {
   if(is_menu_item_active(MENU_ORDER, MENU_ORDER_UNLOAD))
-    key_unit_unload();
+    key_unit_unload_all();
 }
 
 static void xaw_key_unit_wait(Widget w, XEvent *event, String *argv, Cardinal 
*argc)
@@ -679,7 +679,7 @@
   { "key-unit-traderoute", xaw_key_unit_traderoute },
   { "key-unit-sentry", xaw_key_unit_sentry },
   { "key-unit-transform", xaw_key_unit_transform },
-  { "key-unit-unload", xaw_key_unit_unload },
+  { "key-unit-unload-all", xaw_key_unit_unload_all },
   { "key-unit-wait", xaw_key_unit_wait },
   { "key-unit-wakeup-others", xaw_key_unit_wakeup_others },
   { "msg-close-city", xaw_msg_close_city },
Index: client/gui-xaw/menu.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/gui-xaw/menu.c,v
retrieving revision 1.59
diff -u -r1.59 menu.c
--- client/gui-xaw/menu.c       20 Jan 2004 21:52:08 -0000      1.59
+++ client/gui-xaw/menu.c       31 Mar 2004 07:15:45 -0000
@@ -631,7 +631,7 @@
     key_unit_homecity();
     break;
   case MENU_ORDER_UNLOAD:
-    key_unit_unload();
+    key_unit_unload_all();
     break;
   case MENU_ORDER_WAKEUP_OTHERS:
     key_unit_wakeup_others();
Index: common/packets.def
===================================================================
RCS file: /home/freeciv/CVS/freeciv/common/packets.def,v
retrieving revision 1.14
diff -u -r1.14 packets.def
--- common/packets.def  30 Mar 2004 19:00:15 -0000      1.14
+++ common/packets.def  31 Mar 2004 07:15:45 -0000
@@ -211,7 +211,7 @@
   Spaceship
   Ruleset
 
-The last used packet number is 106.
+The last used packet number is 107.
 ****************************************************/
 
 
@@ -687,8 +687,14 @@
   UNIT unit_id;
 end
 
+# Load the given cargo into the transporter.
+PACKET_UNIT_LOAD=107;cs,dsend
+  UNIT cargo_id, transporter_id;
+end
+
+# Unload the given cargo from the transporter.
 PACKET_UNIT_UNLOAD=61;cs,dsend
-  UNIT unit_id;
+  UNIT cargo_id, transporter_id;
 end
 
 PACKET_UNIT_UPGRADE=62;cs,dsend
Index: common/unit.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/common/unit.c,v
retrieving revision 1.201
diff -u -r1.201 unit.c
--- common/unit.c       8 Mar 2004 03:00:22 -0000       1.201
+++ common/unit.c       31 Mar 2004 07:15:45 -0000
@@ -593,6 +593,85 @@
   return text;
 }
 
+/****************************************************************************
+  Return TRUE iff the given unit can be loaded into the transporter.
+****************************************************************************/
+bool can_unit_load(struct unit *pcargo, struct unit *ptrans)
+{
+  /* This function needs to check EVERYTHING. */
+
+  if (!pcargo || !ptrans) {
+    return FALSE;
+  }
+
+  /* Check positions of the units.  Of course you can't load a unit onto
+   * a transporter on a different tile... */
+  if (!same_pos(pcargo->x, pcargo->y, ptrans->x, ptrans->y)) {
+    return FALSE;
+  }
+
+  /* Double-check ownership of the units: you can load into an allied unit
+   * (of course only allied units can be on the same tile). */
+  if (!pplayers_allied(unit_owner(pcargo), unit_owner(ptrans))) {
+    return FALSE;
+  }
+
+  /* Only top-level transporters may be loaded or loaded into. */
+  if (pcargo->transported_by != -1 || ptrans->transported_by != -1) {
+    return FALSE;
+  }
+
+  /* Make sure this transporter can carry this type of unit. */
+  if (is_ground_unit(pcargo)) {
+    if (!is_ground_units_transport(ptrans)) {
+      return FALSE;
+    }
+  } else if (unit_flag(pcargo, F_MISSILE)) {
+    if (!is_air_units_transport(ptrans)) {
+      return FALSE;
+    }
+  } else if (is_air_unit(pcargo) || is_heli_unit(pcargo)) {
+    if (!unit_flag(ptrans, F_CARRIER)) {
+      return FALSE;
+    }
+  } else {
+    return FALSE;
+  }
+
+  /* Make sure there's room in the transporter. */
+  return (get_transporter_occupancy(ptrans)
+         < get_transporter_capacity(ptrans));
+}
+
+/****************************************************************************
+  Return TRUE iff the given unit can be unloaded from its current
+  transporter.
+
+  This function checks everything *except* the legality of the position
+  after the unloading.  The caller may also want to call
+  can_unit_exist_at_tile() to check this, unless the unit is unloading and
+  moving at the same time.
+****************************************************************************/
+bool can_unit_unload(struct unit *pcargo, struct unit *ptrans)
+{
+  if (!pcargo || !ptrans) {
+    return FALSE;
+  }
+
+  /* Make sure the unit's transporter exists and is known. */
+  if (pcargo->transported_by != ptrans->id) {
+    return FALSE;
+  }
+
+  /* Only top-level transporters may be unloaded.  However the unit being
+   * unloaded may be transporting other units. */
+  if (ptrans->transported_by != -1) {
+    return FALSE;
+  }
+
+  return TRUE;
+}
+
 /**************************************************************************
 Return whether the unit can be paradropped.
 That is if the unit is in a friendly city or on an Airbase
@@ -1610,6 +1689,22 @@
   } unit_list_iterate_end;
 
   return occupied;
+}
+
+/****************************************************************************
+  Find a transporter at the given location for the unit.
+****************************************************************************/
+struct unit *find_transporter_for_unit(struct unit *pcargo, int x, int y)
+{ 
+  struct tile *ptile = map_get_tile(x, y);
+
+  unit_list_iterate(ptile->units, ptrans) {
+    if (can_unit_load(pcargo, ptrans)) {
+      return ptrans;
+    }
+  } unit_list_iterate_end;
+
+  return FALSE;
 }
 
 /***************************************************************************
Index: common/unit.h
===================================================================
RCS file: /home/freeciv/CVS/freeciv/common/unit.h,v
retrieving revision 1.112
diff -u -r1.112 unit.h
--- common/unit.h       8 Mar 2004 03:00:22 -0000       1.112
+++ common/unit.h       31 Mar 2004 07:15:45 -0000
@@ -239,6 +239,8 @@
 bool unit_can_airlift_to(struct unit *punit, struct city *pcity);
 bool unit_has_orders(struct unit *punit);
 
+bool can_unit_load(struct unit *punit, struct unit *ptrans);
+bool can_unit_unload(struct unit *punit, struct unit *ptrans);
 bool can_unit_paradrop(struct unit *punit);
 bool can_unit_change_homecity(struct unit *punit);
 bool can_unit_do_connect(struct unit *punit, enum unit_activity activity);
@@ -324,6 +326,7 @@
 void free_unit_orders(struct unit *punit);
 
 int get_transporter_occupancy(struct unit *ptrans);
+struct unit *find_transporter_for_unit(struct unit *pcargo, int x, int y);
 
 enum unit_upgrade_result test_unit_upgrade(struct unit *punit, bool is_free);
 enum unit_upgrade_result get_unit_upgrade_info(char *buf, size_t bufsz,
Index: server/unithand.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/server/unithand.c,v
retrieving revision 1.292
diff -u -r1.292 unithand.c
--- server/unithand.c   30 Mar 2004 19:00:16 -0000      1.292
+++ server/unithand.c   31 Mar 2004 07:15:46 -0000
@@ -1420,42 +1420,49 @@
   }
 }
 
-/**************************************************************************
-...
-**************************************************************************/
-void handle_unit_unload(struct player *pplayer, int unit_id)
+/****************************************************************************
+  Handle a client request to load the given unit into the given transporter.
+****************************************************************************/
+void handle_unit_load(struct player *pplayer, int cargo_id, int trans_id)
 {
-  struct unit *punit = player_find_unit_by_id(pplayer, unit_id);
+  struct unit *pcargo = player_find_unit_by_id(pplayer, cargo_id);
+  struct unit *ptrans = player_find_unit_by_id(pplayer, trans_id);
 
-  if (!punit) {
+  if (!pcargo || !ptrans) {
     return;
   }
 
-  unit_list_iterate(map_get_tile(punit->x, punit->y)->units, punit2) {
-    if (punit != punit2 && punit2->activity == ACTIVITY_SENTRY) {
-      bool wakeup = FALSE;
-
-      if (is_ground_units_transport(punit)) {
-       if (is_ground_unit(punit2))
-         wakeup = TRUE;
-      }
-
-      if (unit_flag(punit, F_MISSILE_CARRIER)) {
-       if (unit_flag(punit2, F_MISSILE))
-         wakeup = TRUE;
-      }
-
-      if (unit_flag(punit, F_CARRIER)) {
-       if (is_air_unit(punit2))
-         wakeup = TRUE;
-      }
-
-      if (wakeup) {
-       set_unit_activity(punit2, ACTIVITY_IDLE);
-       send_unit_info(NULL, punit2);
-      }
-    }
-  } unit_list_iterate_end;
+  if (!can_unit_load(pcargo, ptrans)) {
+    return;
+  }
+
+  /* Load the unit and send out info to clients. */
+  load_unit_onto_transporter(pcargo, ptrans);
+}
+
+/****************************************************************************
+  Handle a client request to unload the given unit from the given
+  transporter.
+****************************************************************************/
+void handle_unit_unload(struct player *pplayer, int cargo_id, int trans_id)
+{
+  struct unit *pcargo = player_find_unit_by_id(pplayer, cargo_id);
+  struct unit *ptrans = player_find_unit_by_id(pplayer, trans_id);
+
+  if (!pcargo || !ptrans) {
+    return;
+  }
+
+  if (!can_unit_unload(pcargo, ptrans)) {
+    return;
+  }
+
+  if (!can_unit_survive_at_tile(pcargo, pcargo->x, pcargo->y)) {
+    return;
+  }
+
+  /* Unload the unit and send out info to clients. */
+  unload_unit_from_transporter(pcargo);
 }
 
 /**************************************************************************
Index: server/unittools.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/server/unittools.c,v
retrieving revision 1.287
diff -u -r1.287 unittools.c
--- server/unittools.c  30 Mar 2004 19:00:16 -0000      1.287
+++ server/unittools.c  31 Mar 2004 07:15:46 -0000
@@ -2514,54 +2514,6 @@
 }
 
 /****************************************************************************
-  Return TRUE iff the given transporter can carry the given unit.
-****************************************************************************/
-static bool can_unit_transport_unit(struct unit *ptrans, struct unit *punit)
-{
-  if (ptrans->transported_by != -1) {
-    /* Only top-level transporters allowed. */
-    return FALSE;
-  }
-
-  /* First check unit types. */
-  if (is_ground_unit(punit)) {
-    if (!is_ground_units_transport(ptrans)) {
-      return FALSE;
-    }
-  } else if (unit_flag(punit, F_MISSILE)) {
-    if (!is_air_units_transport(ptrans)) {
-      return FALSE;
-    }
-  } else if (is_air_unit(punit) || is_heli_unit(punit)) {
-    if (!unit_flag(ptrans, F_CARRIER)) {
-      return FALSE;
-    }
-  } else {
-    return FALSE;
-  }
-
-  /* Then check capacity. */
-  return (get_transporter_occupancy(ptrans)
-         < get_transporter_capacity(ptrans));
-}
-
-/****************************************************************************
-  Find a transporter at the given location for the unit.
-****************************************************************************/
-struct unit *find_transporter_for_unit(struct unit *punit, int x, int y)
-{ 
-  struct tile *ptile = map_get_tile(x, y);
-
-  unit_list_iterate(ptile->units, ptrans) {
-    if (can_unit_transport_unit(ptrans, punit)) {
-      return ptrans;
-    }
-  } unit_list_iterate_end;
-
-  return FALSE;
-}
-
-/****************************************************************************
   Put the unit onto the transporter.  Don't do any other work.
 ****************************************************************************/
 static void put_unit_onto_transporter(struct unit *punit, struct unit *ptrans)
Index: server/unittools.h
===================================================================
RCS file: /home/freeciv/CVS/freeciv/server/unittools.h,v
retrieving revision 1.66
diff -u -r1.66 unittools.h
--- server/unittools.h  30 Mar 2004 19:00:16 -0000      1.66
+++ server/unittools.h  31 Mar 2004 07:15:46 -0000
@@ -80,7 +80,6 @@
 bool try_move_unit(struct unit *punit, int dest_x, int dest_y); 
 bool do_airline(struct unit *punit, struct city *city2);
 bool do_paradrop(struct unit *punit, int dest_x, int dest_y);
-struct unit *find_transporter_for_unit(struct unit *punit, int x, int y);
 void load_unit_onto_transporter(struct unit *punit, struct unit *ptrans);
 void unload_unit_from_transporter(struct unit *punit);
 bool move_unit(struct unit *punit, int dest_x, int dest_y, int move_cost);

[Prev in Thread] Current Thread [Next in Thread]
  • [Freeciv-Dev] Re: (PR#7667) Wishlist: "load" and "unload" commands, Jason Short <=