--- ../freeciv-12-23-01/client/gui-gtk/repodlgs.c Sat Dec 22 02:06:13 2001 +++ client/gui-gtk/repodlgs.c Sat Jan 5 17:44:45 2002 @@ -23,6 +23,10 @@ #include #include +#include "common/mem.h" +#include "common/unit.h" + +#include "control.h" #include "fcintl.h" #include "game.h" #include "government.h" @@ -37,6 +41,7 @@ #include "gui_main.h" #include "gui_stuff.h" #include "helpdlg.h" +#include "mapview_g.h" #include "optiondlg.h" #include "repodlgs.h" @@ -83,12 +88,19 @@ void activeunits_refresh_callback(GtkWidget *widget, gpointer data); void activeunits_list_callback(GtkWidget *w, gint row, gint column); void activeunits_list_ucallback(GtkWidget *w, gint row, gint column); +void activeunits_change_prod_callback(GtkWidget *widget, gpointer data); +void activeunits_find_nearest_callback(GtkWidget *widget, gpointer data); +static void awaken_all_callback(GtkWidget *widget, gpointer data); + int activeunits_type[U_LAST]; +int activeunits_change_in_prod_up=0; +int activeunits_starting_find_x,activeunits_starting_find_y; GtkWidget *activeunits_dialog_shell=NULL; GtkWidget *activeunits_label2; GtkWidget *activeunits_list, *activeunits_list_label; -GtkWidget *upgrade_command; +GtkWidget *upgrade_command, *change_prod_command, *find_nearest_command, *awaken_all_command; +GtkWidget *activeunits_lower; int activeunits_dialog_shell_is_modal; /******************************************************************/ @@ -806,7 +818,7 @@ *****************************************************************/ void create_activeunits_report_dialog(int make_modal) { - GtkWidget *close_command, *refresh_command; + GtkWidget *close_command, *refresh_command, *vbox, *upper; static gchar *titles_[AU_COL] = { N_("Unit Type"), N_("U"), N_("In-Prog"), N_("Active"), N_("Shield"), N_("Food") }; @@ -840,23 +852,45 @@ gtk_box_pack_start( GTK_BOX( GTK_DIALOG(activeunits_dialog_shell)->vbox ), activeunits_label2, FALSE, FALSE, 0 ); - close_command = gtk_button_new_with_label(_("Close")); + vbox=gtk_vbox_new(0,0); + upper=gtk_hbox_new(0,0); + activeunits_lower=gtk_hbox_new(0,0); + gtk_box_pack_start( GTK_BOX( GTK_DIALOG(activeunits_dialog_shell)->action_area ), + vbox, TRUE, TRUE, 0 ); + gtk_box_pack_start( GTK_BOX(vbox),upper, TRUE, TRUE, 0 ); + gtk_box_pack_start( GTK_BOX(vbox),activeunits_lower, TRUE, TRUE, 0 ); + + close_command = gtk_button_new_with_label(_("Close")); + gtk_box_pack_start(GTK_BOX(upper), close_command, TRUE, TRUE, 0 ); GTK_WIDGET_SET_FLAGS( close_command, GTK_CAN_DEFAULT ); gtk_widget_grab_default( close_command ); upgrade_command = gtk_button_new_with_label(_("Upgrade")); gtk_widget_set_sensitive(upgrade_command, FALSE); - gtk_box_pack_start( GTK_BOX( GTK_DIALOG(activeunits_dialog_shell)->action_area ), + gtk_box_pack_start( GTK_BOX( upper ), upgrade_command, TRUE, TRUE, 0 ); GTK_WIDGET_SET_FLAGS( upgrade_command, GTK_CAN_DEFAULT ); refresh_command = gtk_button_new_with_label(_("Refresh")); - gtk_box_pack_start( GTK_BOX( GTK_DIALOG(activeunits_dialog_shell)->action_area ), + gtk_box_pack_start( GTK_BOX( upper ), refresh_command, TRUE, TRUE, 0 ); GTK_WIDGET_SET_FLAGS( refresh_command, GTK_CAN_DEFAULT ); + find_nearest_command = gtk_button_new_with_label(_("Find Nearest")); + gtk_box_pack_start( GTK_BOX(activeunits_lower),find_nearest_command, TRUE, TRUE, 0 ); + GTK_WIDGET_SET_FLAGS( find_nearest_command, GTK_CAN_DEFAULT ); + + change_prod_command = gtk_button_new_with_label(_("Change In Progress")); + gtk_box_pack_end( GTK_BOX(activeunits_lower),change_prod_command, TRUE, TRUE, 0 ); + GTK_WIDGET_SET_FLAGS( change_prod_command, GTK_CAN_DEFAULT ); + + awaken_all_command = gtk_button_new_with_label(_("Wake Sentried")); + gtk_box_pack_end( GTK_BOX(activeunits_lower),awaken_all_command, TRUE, TRUE, 0 ); + GTK_WIDGET_SET_FLAGS( awaken_all_command, GTK_CAN_DEFAULT ); + + gtk_signal_connect(GTK_OBJECT(activeunits_list), "select_row", GTK_SIGNAL_FUNC(activeunits_list_callback), NULL); gtk_signal_connect(GTK_OBJECT(activeunits_list), "unselect_row", @@ -867,6 +901,12 @@ GTK_SIGNAL_FUNC(activeunits_upgrade_callback), NULL); gtk_signal_connect(GTK_OBJECT(refresh_command), "clicked", GTK_SIGNAL_FUNC(activeunits_refresh_callback), NULL); + gtk_signal_connect(GTK_OBJECT(change_prod_command), "clicked", + GTK_SIGNAL_FUNC(activeunits_change_prod_callback), NULL); + gtk_signal_connect(GTK_OBJECT(awaken_all_command), "clicked", + GTK_SIGNAL_FUNC(awaken_all_callback), NULL); + gtk_signal_connect(GTK_OBJECT(find_nearest_command), "clicked", + GTK_SIGNAL_FUNC(activeunits_find_nearest_callback), NULL); gtk_widget_show_all( GTK_DIALOG(activeunits_dialog_shell)->vbox ); gtk_widget_show_all( GTK_DIALOG(activeunits_dialog_shell)->action_area ); @@ -882,9 +922,18 @@ *****************************************************************/ void activeunits_list_callback(GtkWidget *w, gint row, gint column) { + char *tmp; if ((unit_type_exists(activeunits_type[row])) && (can_upgrade_unittype(game.player_ptr, activeunits_type[row]) != -1)) gtk_widget_set_sensitive(upgrade_command, TRUE); + gtk_clist_get_text(GTK_CLIST(w),row,2,&tmp); + if (atoi(tmp) && !activeunits_change_in_prod_up) + gtk_widget_set_sensitive(change_prod_command, TRUE); + gtk_clist_get_text(GTK_CLIST(w),row,3,&tmp); + if (atoi(tmp)){ + gtk_widget_set_sensitive(find_nearest_command, TRUE); + gtk_widget_set_sensitive(awaken_all_command, TRUE); + } } /**************************************************************** @@ -893,6 +942,32 @@ void activeunits_list_ucallback(GtkWidget *w, gint row, gint column) { gtk_widget_set_sensitive(upgrade_command, FALSE); + gtk_widget_set_sensitive(change_prod_command, FALSE); + gtk_widget_set_sensitive(awaken_all_command, FALSE); + gtk_widget_destroy(find_nearest_command); + find_nearest_command=gtk_button_new_with_label(_("Find Nearest")); + gtk_box_pack_start(GTK_BOX(activeunits_lower),find_nearest_command,1,1,0); + gtk_signal_connect(GTK_OBJECT(find_nearest_command),"clicked", + GTK_SIGNAL_FUNC(activeunits_find_nearest_callback),NULL); + GTK_WIDGET_SET_FLAGS( find_nearest_command, GTK_CAN_DEFAULT ); + gtk_widget_show(find_nearest_command); + gtk_widget_set_sensitive(find_nearest_command, FALSE); +} + + +/**************************************************************** +... +*****************************************************************/ +static void awaken_all_callback(GtkWidget *w, gpointer data){ + int i,which=activeunits_type[(gint)(GTK_CLIST( activeunits_list )->selection->data)]; + struct unit* nit; + if (which>=U_LAST) + which-=U_LAST; + for(i=0;iunits));i++){ + nit=unit_list_get(&(game.player_ptr->units),i); + if (nit->type==which) + request_unit_wakeup(nit); + } } /**************************************************************** @@ -904,6 +979,247 @@ destroy_message_dialog(w); } + +/**************************************************************** +... +*****************************************************************/ +gint unit_present(Unit_Type_id which,gint x, gint y){ + struct unit_list list; + gint i; + if (!is_normal_map_pos(x,y)) + return(0); + list=map_get_tile(x,y)->units; + for(i=0;itype==which && + unit_list_get(&list,i)->owner==game.player_idx) + return(1); + } + return(0); +} + + +/**************************************************************** +... +*****************************************************************/ +void activeunits_find_next_callback(GtkWidget *w,gpointer data){ + static gint x,y,r,side,which; + which=activeunits_type[(gint)(GTK_CLIST( activeunits_list )->selection->data)]; + if (which>=U_LAST) + which-=U_LAST; + if (data){ + x=activeunits_starting_find_x; + y=activeunits_starting_find_y; + r=0; + side=1; + } + while(1){ + switch (side){ + case 1: + ++y; + if (y-activeunits_starting_find_y>=r) side=2; + break; + case 2: + --x; + if (activeunits_starting_find_x-x>=r) side=3; + break; + case 3: + --y; + if (activeunits_starting_find_y-y>=r) side=4; + break; + case 4: + ++x; + if (x-activeunits_starting_find_x>=r){ + side=1; + ++r; + } + break; + } + if (unit_present(which,x,y)){ + center_tile_mapcanvas(x,y); + put_cross_overlay_tile(x,y); + return; + } + if (r>map.xsize && r>map.ysize){ + r=0; + x=activeunits_starting_find_x; + y=activeunits_starting_find_y; + } + } +} + +/**************************************************************** +... +*****************************************************************/ +void activeunits_find_nearest_callback(GtkWidget *w,gpointer data){ + get_center_tile_mapcanvas(&activeunits_starting_find_x, + &activeunits_starting_find_y); + gtk_widget_destroy(find_nearest_command); + find_nearest_command=gtk_button_new_with_label(_("Find Next")); + gtk_box_pack_start(GTK_BOX(activeunits_lower),find_nearest_command,1,1,0); + gtk_signal_connect(GTK_OBJECT(find_nearest_command),"clicked", + GTK_SIGNAL_FUNC(activeunits_find_next_callback),NULL); + GTK_WIDGET_SET_FLAGS( find_nearest_command, GTK_CAN_DEFAULT ); + gtk_widget_show(find_nearest_command); + activeunits_find_next_callback(w,(gpointer)TRUE); + return; +} + + +/**************************************************************** +... +*****************************************************************/ +void activeunits_change_prod_close_callback(GtkWidget *w, gpointer data){ + activeunits_change_in_prod_up=FALSE; + if (GTK_CLIST(activeunits_list)->selection) + activeunits_list_callback(activeunits_list,(gint)(GTK_CLIST(activeunits_list)->selection->data),0); + free(data); +} + +/**************************************************************** +... +*****************************************************************/ +void activeunits_change_prod_close_button_callback(GtkWidget *w,gpointer data){ + gtk_widget_destroy((GtkWidget*)data); +} + + +/**************************************************************** +... +*****************************************************************/ +void activeunits_change_prod_change_callback(GtkWidget *w, gpointer data){ + gint i; + struct city *pcity; + + gpointer* tofromanddlg; + gint from,row,to; + GtkWidget *tosel,*dlg; + + tofromanddlg=(gpointer*)data; + from=(gint)tofromanddlg[0]; + tosel=(GtkWidget*)tofromanddlg[1]; + dlg=(GtkWidget*)tofromanddlg[2]; + if (!(GTK_CLIST(tosel)->selection)){ + gtk_widget_destroy(dlg); + return; + } + row=(gint)(GTK_CLIST(tosel)->selection->data); + to=(gint)gtk_clist_get_row_data(GTK_CLIST(tosel),row); + + for(i=0,pcity=city_list_get(&game.player_ptr->cities,0); + pcity; + pcity=city_list_get(&game.player_ptr->cities,i++)){ + if ((pcity->is_building_unit) && (pcity->currently_building == from)){ + struct packet_city_request packet; + packet.city_id=pcity->id; + packet.name[0]='\0'; + packet.worklist.name[0] = '\0'; + packet.build_id=to; + packet.is_build_id_unit_id=1; + send_packet_city_request(&aconnection, &packet, PACKET_CITY_CHANGE); + } + } + gtk_clist_unselect_row(GTK_CLIST(activeunits_list),(gint)(GTK_CLIST(activeunits_list)->selection->data),0); + gtk_widget_destroy(dlg); /*the destroy handler will de-allocate data*/ +} + + +/**************************************************************** +... +*****************************************************************/ +int unit_is_obsolete(int id){ + while(unit_type_exists((id = unit_types[id].obsoleted_by))) + if (get_invention(game.player_ptr,unit_types[id].tech_requirement)==TECH_KNOWN) + return(1); + return(0); +} + + +/**************************************************************** +... +*****************************************************************/ +void activeunits_change_prod_callback(GtkWidget *w, gpointer data) +{ + char buf[512]; + int from,i; + GList *selection; + gint row; + GtkWidget *dlg,*lab,*sel,*ok,*canc,*scr; + gchar *rowbuf[1]; + gpointer *passeddata=(gpointer*)fc_malloc(3*sizeof(gpointer)); /*We'll need to send it from, to, and the window to close*/ + + activeunits_change_in_prod_up=TRUE; + gtk_widget_set_sensitive(w,FALSE);/*Don't let it call us twice*/ + + if ( !( selection = GTK_CLIST( activeunits_list )->selection ) ) + return; + + row = (gint)selection->data; + from = activeunits_type[row]; + + + if (from>=U_LAST) + from-=U_LAST; /*if none have been built yet, this is nessesary*/ + if (!(unit_type_exists (from))) + return; + + my_snprintf(buf, sizeof(buf), + _("Convert %s to..."), unit_types[from].name); + + dlg=gtk_dialog_new(); + gtk_window_set_title(GTK_WINDOW(GTK_DIALOG(dlg)),"Change production to..."); + + gtk_signal_connect(GTK_OBJECT(dlg),"destroy", + GTK_SIGNAL_FUNC(activeunits_change_prod_close_callback),passeddata); + + + lab=gtk_label_new(buf); + sel=gtk_clist_new(1); + for(i=0; iaction_area),ok,TRUE,FALSE,0); + passeddata[0]=(gpointer)from; /*And I'm doing it again*/ + passeddata[1]=(gpointer)sel; + passeddata[2]=(gpointer)dlg; + gtk_signal_connect(GTK_OBJECT(ok),"clicked", + GTK_SIGNAL_FUNC(activeunits_change_prod_change_callback), (gpointer)passeddata); + canc=gtk_button_new_with_label("Cancel"); + gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dlg)->action_area),canc,TRUE,FALSE,0); + gtk_signal_connect(GTK_OBJECT(canc),"clicked", + GTK_SIGNAL_FUNC(activeunits_change_prod_close_button_callback),dlg); + + + + scr=gtk_scrolled_window_new(NULL,NULL); + gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scr), + GTK_POLICY_AUTOMATIC, + GTK_POLICY_AUTOMATIC); + gtk_scrolled_window_add_with_viewport(GTK_SCROLLED_WINDOW(scr),sel); + gtk_widget_set_usize(scr,120,160); + gtk_widget_show(sel); + + gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dlg)->vbox),lab,FALSE,FALSE,0); + gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dlg)->vbox),scr,FALSE,FALSE,0); + + gtk_widget_show(lab); + gtk_widget_show(ok); + gtk_widget_show(canc); + gtk_widget_show(scr); + gtk_widget_show(dlg); +} + /**************************************************************** ... *****************************************************************/ @@ -1026,7 +1342,10 @@ gtk_clist_append( GTK_CLIST( activeunits_list ), row ); - activeunits_type[k]=(unitarray[i].active_count > 0) ? i : U_LAST; + activeunits_type[k]=(unitarray[i].active_count > 0) ? i : U_LAST+i; + /*Using U_LAST+i is still + invalid, but it preserves + the information*/ k++; unittotals.active_count += unitarray[i].active_count; unittotals.upkeep_shield += unitarray[i].upkeep_shield;