/* gdialog.c - Created by Giampiero Caprino This file is part of Train Director Train Director is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2, or (at your option) any later version. Train Director is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with Train Director; see the file COPYING. If not, write to the Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ #include #include #include #include #include #if !defined(__unix) #include #endif #include "trsim.h" #include "gtkui.h" #include "ask.h" extern grid *current_grid, *field_grid, *tools_grid; struct trk_vars { Track *trk; GtkWidget *dname; GtkWidget *length; GtkWidget *speed; GtkWidget *station; GtkWidget *distance; GtkWidget *wlink; GtkWidget *elink; GtkWidget *nopenalty; GtkWidget *signalx; GtkWidget *fixedred; } tvars; GtkWidget *Combo; static gboolean combo_changed(GtkWidget *widget) { gchar *string; string = gtk_entry_get_text (GTK_ENTRY (GTK_COMBO (Combo)->entry)); gtk_entry_set_text(GTK_ENTRY(tvars.station), string); return TRUE; } static gboolean cmw_destroy_cb(GtkWidget *widget) { /* This is needed to get out of gtk_main */ gtk_main_quit(); return FALSE; } static gboolean track_dialogue_close(GtkWidget *widget) { char *len; char *speed; char *station; char *distance; char *wlink, *elink; int i; Track *t; t = tvars.trk; len = gtk_entry_get_text(GTK_ENTRY(tvars.length)); speed = gtk_entry_get_text(GTK_ENTRY(tvars.speed)); station = gtk_entry_get_text(GTK_ENTRY(tvars.station)); distance = gtk_entry_get_text(GTK_ENTRY(tvars.distance)); wlink = gtk_entry_get_text(GTK_ENTRY(tvars.wlink)); elink = gtk_entry_get_text(GTK_ENTRY(tvars.elink)); if(set_track_properties(t, len, station, speed, distance, wlink, elink)) repaint_field(); /* This is needed to get out of gtk_main */ gtk_widget_destroy(widget); repaint_all(); return FALSE; } void gtk_track_properties_dialog(Track *t) { GtkWidget *window = NULL; GtkWidget *box1,*box2; GtkWidget *frame1; GtkWidget *btnColor,*btnFile,*btnClose; GtkWidget *child; char buff[256]; tvars.trk = t; /* Create modal window (Here you can use any window descendent )*/ window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_window_set_title(GTK_WINDOW(window), L("Track properties")); /* Set window as modal */ gtk_window_set_modal(GTK_WINDOW(window),TRUE); /* Create widgets */ box1 = gtk_vbox_new(FALSE,5); gtk_container_add(GTK_CONTAINER(window), box1); sprintf(buff, L("Track %d,%d"), t->x, t->y); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box1), child, TRUE, TRUE, 4); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L("Length :")); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); sprintf(buff, "%d", t->length); gtk_entry_set_text(GTK_ENTRY(child), buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.length = child; box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L("Speed :")); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); sprintf(buff, "%d/%d/%d/%d", t->speed[0], t->speed[1], t->speed[2], t->speed[3]); gtk_entry_set_text(GTK_ENTRY(child), buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.speed = child; box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L("Station :")); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); buff[0] = 0; if(t->station) strcpy(buff, t->station); gtk_entry_set_text(GTK_ENTRY(child), buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.station = child; box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); child = gtk_label_new("Km. : "); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); if(t->km) { sprintf(buff, "%d.%d", t->km / 1000, t->km % 1000); gtk_entry_set_text(GTK_ENTRY(child), buff); } gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.distance = child; box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L(t->type != TSIGNAL && t->type != SWITCH ? L("Linked to west") : L("Controls"))); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); sprintf(buff, "%d,%d", t->wlinkx, t->wlinky); gtk_entry_set_text(GTK_ENTRY(child), buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.wlink = child; if(t->type != TSIGNAL && t->type != SWITCH) { box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L("Linked to east :")); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); sprintf(buff, "%d,%d", t->elinkx, t->elinky); gtk_entry_set_text(GTK_ENTRY(child), buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.elink = child; } gtk_box_pack_start(GTK_BOX(box1), gtk_hseparator_new(), FALSE, FALSE, 4); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); if(editing) { btnClose = gtk_button_new_with_label(L("Ok")); gtk_box_pack_start(GTK_BOX(box2), btnClose, FALSE, FALSE, 4); gtk_signal_connect_object(GTK_OBJECT(btnClose), "clicked", GTK_SIGNAL_FUNC(track_dialogue_close), GTK_OBJECT(window)); GTK_WIDGET_SET_FLAGS(btnClose, GTK_CAN_DEFAULT); gtk_widget_grab_default(btnClose); btnClose = gtk_button_new_with_label(L("Cancel")); } else btnClose = gtk_button_new_with_label(L("Close")); gtk_box_pack_start(GTK_BOX(box2), btnClose, FALSE, FALSE, 4); gtk_signal_connect_object(GTK_OBJECT(btnClose), "clicked", GTK_SIGNAL_FUNC(gtk_widget_destroy), GTK_OBJECT(window)); gtk_signal_connect(GTK_OBJECT(window), "destroy", GTK_SIGNAL_FUNC(cmw_destroy_cb),NULL); gtk_widget_show_all(window); gtk_main(); } gboolean trigger_dialogue_close(GtkWidget *widget) { char *station; char *wlink, *elink; char *len; int i; Track *t; t = tvars.trk; station = gtk_entry_get_text(GTK_ENTRY(tvars.station)); wlink = gtk_entry_get_text(GTK_ENTRY(tvars.wlink)); if(set_track_properties(t, "0", station, "0", "0", wlink, "0")) repaint_field(); /* This is needed to get out of gtk_main */ gtk_widget_destroy(widget); repaint_all(); return FALSE; } /* trigger properties */ void gtk_trigger_properties_dialog(Track *t) { GtkWidget *window = NULL; GtkWidget *box1,*box2; GtkWidget *frame1; GtkWidget *btnColor,*btnFile,*btnClose; GtkWidget *child,*combo; GList *items = NULL; char buff[256]; tvars.trk = t; /* Create modal window (Here you can use any window descendent )*/ window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_window_set_title(GTK_WINDOW(window), L("Trigger properties")); /* Set window as modal */ gtk_window_set_modal(GTK_WINDOW(window),TRUE); /* Create widgets */ box1 = gtk_vbox_new(FALSE,5); gtk_container_add(GTK_CONTAINER(window), box1); sprintf(buff, L("Trigger at %d,%d"), t->x, t->y); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box1), child, TRUE, TRUE, 4); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); child = gtk_label_new(L("Action :")); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_label_new(L("'@' in action = name of triggering train")); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); items = g_list_append (items, " "); items = g_list_append (items, "click x,y"); items = g_list_append (items, "fast"); items = g_list_append (items, "slow"); items = g_list_append (items, "shunt train"); items = g_list_append (items, "reverse train"); items = g_list_append (items, "traininfo train"); items = g_list_append (items, "stationinfo train"); items = g_list_append (items, "accelerate speed train"); items = g_list_append (items, "decelerate speed train"); combo = gtk_combo_new(); gtk_combo_set_popdown_strings(GTK_COMBO(combo), items); gtk_box_pack_start(GTK_BOX(box2), GTK_WIDGET(combo), TRUE, TRUE, 4); Combo = combo; gtk_signal_connect(GTK_OBJECT(GTK_COMBO(combo)->list), "selection-changed", GTK_SIGNAL_FUNC(combo_changed), combo); child = gtk_entry_new(); buff[0] = 0; if(t->station) sprintf(buff, "%s", t->station); gtk_entry_set_text(GTK_ENTRY(child), buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.station = child; box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L("Linked to track at coord:")); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); sprintf(buff, "%d,%d", t->wlinkx, t->wlinky); gtk_entry_set_text(GTK_ENTRY(child), buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.wlink = child; box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L("Probabilities for action :")); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); sprintf(buff, "%d/%d/%d/%d", t->speed[0], t->speed[1], t->speed[2], t->speed[3]); gtk_entry_set_text(GTK_ENTRY(child), buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.speed = child; gtk_box_pack_start(GTK_BOX(box1), gtk_hseparator_new(), FALSE, FALSE, 4); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); if(editing) { btnClose = gtk_button_new_with_label(L("Ok")); gtk_box_pack_start(GTK_BOX(box2), btnClose, FALSE, FALSE, 4); gtk_signal_connect_object(GTK_OBJECT(btnClose), "clicked", GTK_SIGNAL_FUNC(trigger_dialogue_close), GTK_OBJECT(window)); GTK_WIDGET_SET_FLAGS(btnClose, GTK_CAN_DEFAULT); gtk_widget_grab_default(btnClose); btnClose = gtk_button_new_with_label(L("Cancel")); } else btnClose = gtk_button_new_with_label(L("Close")); gtk_box_pack_start(GTK_BOX(box2), btnClose, FALSE, FALSE, 4); gtk_signal_connect_object(GTK_OBJECT(btnClose), "clicked", GTK_SIGNAL_FUNC(gtk_widget_destroy), GTK_OBJECT(window)); gtk_signal_connect(GTK_OBJECT(window), "destroy", GTK_SIGNAL_FUNC(cmw_destroy_cb),NULL); gtk_widget_show_all(window); gtk_main(); } gboolean signal_dialogue_close(GtkWidget *widget) { char *station; char *wlink, *elink; char *len; int i; Track *t; t = tvars.trk; t->signalx = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(tvars.signalx)); t->fixedred = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(tvars.fixedred)); t->nopenalty = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(tvars.nopenalty)); station = gtk_entry_get_text(GTK_ENTRY(tvars.station)); wlink = gtk_entry_get_text(GTK_ENTRY(tvars.wlink)); elink = gtk_entry_get_text(GTK_ENTRY(tvars.elink)); if(set_track_properties(t,"0", station,"0","0" , wlink, elink)) repaint_field(); /* This is needed to get out of gtk_main */ gtk_widget_destroy(widget); repaint_all(); return FALSE; } /* Signal properties dialog */ void gtk_signal_properties_dialog(Track *t) { GtkWidget *window = NULL; GtkWidget *box1,*box2; GtkWidget *frame1; GtkWidget *btnColor,*btnFile,*btnClose; GtkWidget *child; char buff[256]; tvars.trk = t; /* Create modal window (Here you can use any window descendent )*/ window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_window_set_title(GTK_WINDOW(window), L("Signal properties")); /* Set window as modal */ gtk_window_set_modal(GTK_WINDOW(window),TRUE); /* Create widgets */ box1 = gtk_vbox_new(FALSE,5); gtk_container_add(GTK_CONTAINER(window), box1); sprintf(buff, L("Signal at %d,%d"), t->x, t->y); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box1), child, TRUE, TRUE, 4); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L("Signal Name :")); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); buff[0] = 0; if(t-> station) sprintf(buff, "%s", t->station); gtk_entry_set_text(GTK_ENTRY(child), buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.station = child; box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L("Linked to east :")); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); sprintf(buff, "%d,%d", t->elinkx, t->elinky); gtk_entry_set_text(GTK_ENTRY(child), buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.elink = child; box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L("Linked to west :")); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); sprintf(buff, "%d,%d", t->wlinkx, t->wlinky); gtk_entry_set_text(GTK_ENTRY(child), buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); tvars.wlink = child; box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); tvars.fixedred = gtk_check_button_new_with_label(L("Signal is always red")); gtk_box_pack_start(GTK_BOX(box2), tvars.fixedred, TRUE, TRUE, 4); if (t->fixedred == 1) { gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(tvars.fixedred), TRUE); } box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); tvars.signalx = gtk_check_button_new_with_label(L("Signal has square frame")); gtk_box_pack_start(GTK_BOX(box2), tvars.signalx, TRUE, TRUE, 4); if (t->signalx == 1) { gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(tvars.signalx), TRUE); } box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); tvars.nopenalty = gtk_check_button_new_with_label(L("No penalty for train stopping at this signal")); gtk_box_pack_start(GTK_BOX(box2), tvars.nopenalty, TRUE, TRUE, 4); if (t->nopenalty == 1) { gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(tvars.nopenalty), TRUE); } gtk_box_pack_start(GTK_BOX(box1), gtk_hseparator_new(), FALSE, FALSE, 4); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); if(editing) { btnClose = gtk_button_new_with_label(L("Ok")); gtk_box_pack_start(GTK_BOX(box2), btnClose, FALSE, FALSE, 4); gtk_signal_connect_object(GTK_OBJECT(btnClose), "clicked", GTK_SIGNAL_FUNC(signal_dialogue_close), GTK_OBJECT(window)); GTK_WIDGET_SET_FLAGS(btnClose, GTK_CAN_DEFAULT); gtk_widget_grab_default(btnClose); btnClose = gtk_button_new_with_label(L("Cancel")); } else btnClose = gtk_button_new_with_label(L("Close")); gtk_box_pack_start(GTK_BOX(box2), btnClose, FALSE, FALSE, 4); gtk_signal_connect_object(GTK_OBJECT(btnClose), "clicked", GTK_SIGNAL_FUNC(gtk_widget_destroy), GTK_OBJECT(window)); gtk_signal_connect(GTK_OBJECT(window), "destroy", GTK_SIGNAL_FUNC(cmw_destroy_cb),NULL); gtk_widget_show_all(window); gtk_main(); } /* * * INFO WINDOW * * */ static GtkWidget *info_window; static void do_update(gpointer data) { GtkText *txt; TextList *tl, *tlast; char buff[512]; char *p; unsigned int i; unsigned int len; while((tl = track_info)) { track_info = tl->next; free(tl->txt); free(tl); } tlast = 0; txt = GTK_TEXT(data); len = gtk_text_get_length(txt); p = buff; for(i = 0; i < len; ++i) { if(GTK_TEXT_INDEX(txt, i) == '\n') { *p = 0; tl = (TextList *)malloc(sizeof(TextList)); tl->txt = strdup(buff); p = buff; if(tlast) tlast->next = tl; else track_info = tl; tlast = tl; tl->next = 0; continue; } *p++ = GTK_TEXT_INDEX(txt, i); } if(p != buff) { *p = 0; tl = (TextList *)malloc(sizeof(TextList)); tl->txt = strdup(buff); p = buff; if(tlast) tlast->next = tl; else track_info = tl; tl->next = 0; } } static void print_info_clicked(gpointer button, gpointer data) { do_update(data); print_track_info(); } static void update_info_clicked(gpointer button, gpointer data) { do_update(data); if(info_window) gtk_widget_destroy(info_window); info_window = 0; } void track_info_dialogue() { GtkWidget *window, *scrolled_window; GtkWidget *text; GdkFont *font; TextList *tl; GtkWidget *box1, *box2, *hbox; GtkWidget *saveb; char buff[512]; window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_widget_set_usize(window, 400, 300); gtk_window_set_policy(GTK_WINDOW(window), TRUE, TRUE, FALSE); gtk_window_set_title(GTK_WINDOW(window), L("Territory Information")); gtk_container_set_border_width(GTK_CONTAINER(window), 0); box1 = gtk_vbox_new(FALSE, 0); gtk_container_add(GTK_CONTAINER(window), box1); gtk_widget_show(box1); box2 = gtk_vbox_new(FALSE, 10); gtk_container_set_border_width(GTK_CONTAINER(box2), 10); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 0); gtk_widget_show(box2); scrolled_window = gtk_scrolled_window_new(NULL, NULL); gtk_box_pack_start(GTK_BOX(box2), scrolled_window, TRUE, TRUE, 0); gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scrolled_window), GTK_POLICY_NEVER, GTK_POLICY_ALWAYS); gtk_widget_show(scrolled_window); text = gtk_text_new(NULL, NULL); gtk_text_set_editable(GTK_TEXT(text), TRUE); gtk_text_set_word_wrap(GTK_TEXT(text), FALSE); gtk_container_add(GTK_CONTAINER(scrolled_window), text); gtk_widget_show(text); gtk_text_freeze(GTK_TEXT(text)); font = gdk_font_load("-adobe-courier-medium-r-normal--*-120-*-*-*-*-*-*"); for(tl = track_info; tl; tl = tl->next) gtk_text_insert(GTK_TEXT(text), font, NULL, NULL, tl->txt, -1); gdk_font_unref(font); gtk_text_thaw(GTK_TEXT(text)); hbox = gtk_hbutton_box_new(); gtk_box_pack_start(GTK_BOX(box2), hbox, FALSE, FALSE, 0); gtk_widget_show(hbox); saveb = gtk_button_new_with_label(L("Update")); gtk_signal_connect(GTK_OBJECT(saveb), "clicked", GTK_SIGNAL_FUNC(update_info_clicked), text); gtk_box_pack_start(GTK_BOX(hbox), saveb, TRUE, TRUE, 0); gtk_widget_show(saveb); saveb = gtk_button_new_with_label(L("Print")); gtk_signal_connect(GTK_OBJECT(saveb), "clicked", GTK_SIGNAL_FUNC(print_info_clicked), NULL); gtk_box_pack_start(GTK_BOX(hbox), saveb, TRUE, TRUE, 0); gtk_widget_show(saveb); gtk_widget_show(window); gtk_widget_grab_focus(text); info_window = window; } /* * * DAY SELECTION DIALOG * */ struct DayData { GtkWidget *window; GtkWidget *buttons[8]; int which; }; static struct DayData day_data; static char *days[] = { "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday", 0 }; static void day_selected(gpointer button, gpointer data) { int i; for(i = 0; i < 7; ++i) if(data == day_data.buttons[i]) break; if(i == 7) day_data.which = 0; else day_data.which = i + 1; } static void day_continue(gpointer button, gpointer data) { if(!day_data.window) return; gtk_widget_destroy(day_data.window); day_data.window = 0; if(day_data.which) run_day = 1 << (day_data.which - 1); else run_day = 0; gtk_main_quit(); } void gtk_select_day_dialog(void) { GtkWidget *window = NULL; GtkWidget *box1, *box2; GtkWidget *separator; GtkWidget *button; char buff[256]; int i; window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_window_set_title(GTK_WINDOW(window), L("Day Selection")); gtk_window_set_modal(GTK_WINDOW(window),TRUE); box1 = gtk_vbox_new(FALSE,5); gtk_container_add(GTK_CONTAINER(window), box1); box2 = gtk_vbox_new (FALSE, 10); gtk_container_set_border_width (GTK_CONTAINER (box2), 10); gtk_box_pack_start (GTK_BOX (box1), box2, TRUE, TRUE, 0); separator = gtk_label_new(L("Not all trains run every day of the week.\nWhich day do you want to simulate?")); gtk_box_pack_start (GTK_BOX (box2), separator, TRUE, TRUE, 0); button = gtk_radio_button_new_with_label (NULL, days[0]); gtk_box_pack_start (GTK_BOX (box2), button, TRUE, TRUE, 0); day_data.buttons[0] = button; day_data.which = 1; /* default is first day */ for(i = 0; days[i]; ++i) { button = gtk_radio_button_new_with_label ( gtk_radio_button_group (GTK_RADIO_BUTTON (button)), L(days[i])); gtk_signal_connect_object (GTK_OBJECT (button), "clicked", GTK_SIGNAL_FUNC(day_selected), GTK_OBJECT (button)); gtk_box_pack_start (GTK_BOX (box2), button, TRUE, TRUE, 0); day_data.buttons[i] = button; } separator = gtk_hseparator_new (); gtk_box_pack_start (GTK_BOX (box1), separator, FALSE, TRUE, 0); box2 = gtk_vbox_new (FALSE, 10); gtk_container_set_border_width (GTK_CONTAINER (box2), 10); gtk_box_pack_start (GTK_BOX (box1), box2, FALSE, TRUE, 0); button = gtk_button_new_with_label (L("Ok")); gtk_signal_connect_object (GTK_OBJECT (button), "clicked", GTK_SIGNAL_FUNC(day_continue), GTK_OBJECT (window)); gtk_box_pack_start (GTK_BOX (box2), button, TRUE, TRUE, 0); GTK_WIDGET_SET_FLAGS (button, GTK_CAN_DEFAULT); gtk_widget_grab_default (button); day_data.window = window; gtk_widget_show_all(window); gtk_main(); } /* * * PREFERENCES DIALOG * */ static struct _opt { GtkWidget *sig; GtkWidget *blocks; GtkWidget *speeds; GtkWidget *alert; GtkWidget *enter; GtkWidget *seconds; GtkWidget *statustop; GtkWidget *terse; GtkWidget *grid; GtkWidget *siglink; GtkWidget *window; GtkWidget *hard; GtkWidget *saveprefs; } opts; static void opts_default(void) { default_prefs(); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.terse), terse_status); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.statustop), status_on_top); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.alert), beep_on_alert); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.enter), beep_on_enter); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.speeds), show_speeds); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.siglink), auto_link); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.grid), show_grid); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.seconds), show_seconds); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.sig), signal_traditional); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.hard), hard_counters); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.saveprefs), save_prefs); if(ask(L("Write default prefs to ini file?"))) save_ini_file(); } static void opts_continue(gpointer button, gpointer data) { if(!opts.window) return; signal_traditional = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.sig)) == FALSE; show_blocks = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.blocks)) == TRUE; beep_on_alert = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.alert)) == TRUE; beep_on_enter = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.enter)) == TRUE; show_speeds = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.speeds)) == TRUE; show_seconds = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.seconds)) == TRUE; status_on_top = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.statustop)) == TRUE; terse_status = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.terse)) == FALSE; show_grid = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.grid)) == TRUE; auto_link = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.siglink)) == TRUE; hard_counters = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.hard)) == TRUE; save_prefs = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(opts.saveprefs)) == TRUE; gtk_widget_destroy(opts.window); opts.window = 0; gtk_main_quit(); } void gtk_options_dialog(void) { GtkWidget *window = NULL; GtkWidget *box, *box1,*box2; GtkWidget *button,*button1; GtkWidget *child; char buff[256]; /* Create modal window (Here you can use any window descendent )*/ window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_window_set_title(GTK_WINDOW(window), L("Preferences")); /* Set window as modal */ gtk_window_set_modal(GTK_WINDOW(window), TRUE); /* Create widgets */ box = gtk_vbox_new(FALSE, 5); gtk_container_add(GTK_CONTAINER(window), box); gtk_container_set_border_width (GTK_CONTAINER (box), 10); box1 = gtk_vbox_new(FALSE, 5); gtk_container_add(GTK_CONTAINER(box), box1); gtk_container_set_border_width (GTK_CONTAINER (box1), 10); opts.terse = gtk_check_button_new_with_label(L("Full status info")); gtk_box_pack_start(GTK_BOX(box1), opts.terse, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.terse), !terse_status); opts.statustop = gtk_check_button_new_with_label(L("Status line at top of window")); gtk_box_pack_start(GTK_BOX(box1), opts.statustop, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.statustop), status_on_top); opts.alert = gtk_check_button_new_with_label(L("Alert sound on")); gtk_box_pack_start(GTK_BOX(box1), opts.alert, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.alert), beep_on_alert); opts.enter = gtk_check_button_new_with_label(L("Beep on train entering scenario")); gtk_box_pack_start(GTK_BOX(box1), opts.enter, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.enter), beep_on_enter); opts.speeds = gtk_check_button_new_with_label(L("View speed limits")); gtk_box_pack_start(GTK_BOX(box1), opts.speeds, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.speeds), show_speeds); opts.siglink = gtk_check_button_new_with_label(L("Automatically link signals")); gtk_box_pack_start(GTK_BOX(box1), opts.siglink, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.siglink), auto_link); opts.grid = gtk_check_button_new_with_label(L("Show grid")); gtk_box_pack_start(GTK_BOX(box1), opts.grid, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.grid), show_grid); opts.blocks = gtk_check_button_new_with_label(L("View long blocks")); gtk_box_pack_start(GTK_BOX(box1), opts.blocks, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.blocks), show_blocks); opts.seconds = gtk_check_button_new_with_label(L("Show seconds on clock")); gtk_box_pack_start(GTK_BOX(box1), opts.seconds, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.seconds), show_seconds); opts.sig = gtk_check_button_new_with_label(L("Italian signals")); gtk_box_pack_start(GTK_BOX(box1), opts.sig, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.sig), !signal_traditional); opts.hard = gtk_check_button_new_with_label(L("Hard performance tracking")); gtk_box_pack_start(GTK_BOX(box1), opts.hard, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.hard), hard_counters); opts.saveprefs = gtk_check_button_new_with_label(L("Save preferences on exit")); gtk_box_pack_start(GTK_BOX(box1), opts.saveprefs, TRUE, TRUE, 4); gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(opts.saveprefs), save_prefs); gtk_box_pack_start(GTK_BOX(box1), gtk_hseparator_new(), TRUE, TRUE, 0); box2 = gtk_hbox_new(FALSE, 5); gtk_container_add(GTK_CONTAINER(box), box2); gtk_container_set_border_width (GTK_CONTAINER (box2), 10); button = gtk_button_new_with_label (L("Ok")); gtk_signal_connect_object (GTK_OBJECT (button), "clicked", GTK_SIGNAL_FUNC(opts_continue), GTK_OBJECT (box2)); gtk_box_pack_start (GTK_BOX (box2), button, TRUE, TRUE, 0); button1 = gtk_button_new_with_label (L("Default")); gtk_signal_connect_object (GTK_OBJECT (button1), "clicked", GTK_SIGNAL_FUNC(opts_default), GTK_OBJECT (box2)); gtk_box_pack_start (GTK_BOX (box2), button1, TRUE, TRUE, 0); GTK_WIDGET_SET_FLAGS (button, GTK_CAN_DEFAULT); gtk_widget_grab_default (button); opts.window = window; gtk_widget_show_all(window); gtk_main(); } /* * ITINERARY DIALOG */ struct it_vars { Itinerary *it; GtkWidget *name; GtkWidget *nextitin; } itvars; static gboolean itinerary_close(GtkWidget *widget) { char *p, *p1; int i; Itinerary *it, *it1, *it2; it = itvars.it; p1 = gtk_entry_get_text(GTK_ENTRY(itvars.name)); p = gtk_entry_get_text(GTK_ENTRY(itvars.nextitin)); if(!set_itin_name(it, p1, p)) return FALSE; itvars.it = 0; /* This is needed to get out of gtk_main */ gtk_widget_destroy(widget); show_itinerary(); repaint_all(); return FALSE; } static gboolean itinerary_remove(GtkWidget *widget) { Itinerary *it; it = itvars.it; if(it) { itineraries = it->next; if(it->name) free(it->name); if(it->signame) free(it->signame); free(it); } cmw_destroy_cb(widget); return FALSE; } void gtk_itinerary_dialog(Itinerary *it) { GtkWidget *window = NULL; GtkWidget *box1,*box2; GtkWidget *btnColor,*btnFile,*btnClose; GtkWidget *child; char buff[256]; itvars.it = it; /* Create modal window (Here you can use any window descendent )*/ window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_window_set_title(GTK_WINDOW(window), L("Itinerary")); /* Set window as modal */ gtk_window_set_modal(GTK_WINDOW(window),TRUE); /* Create widgets */ box1 = gtk_vbox_new(FALSE,5); gtk_container_add(GTK_CONTAINER(window), box1); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L("Name :")); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); if(it->name) gtk_entry_set_text(GTK_ENTRY(child), it->name); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); itvars.name = child; sprintf(buff, L("From signal '%s'"), it->signame); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box1), child, TRUE, TRUE, 4); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); strcpy(buff, L("Next itinerary : ")); strcat(buff, " "); child = gtk_label_new(buff); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); child = gtk_entry_new(); if(it->nextitin) gtk_entry_set_text(GTK_ENTRY(child), it->nextitin); gtk_box_pack_start(GTK_BOX(box2), child, TRUE, TRUE, 4); itvars.nextitin = child; gtk_box_pack_start(GTK_BOX(box1), gtk_hseparator_new(), FALSE, FALSE, 4); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); btnClose = gtk_button_new_with_label(L("Ok")); gtk_box_pack_start(GTK_BOX(box2), btnClose, FALSE, FALSE, 4); gtk_signal_connect_object(GTK_OBJECT(btnClose), "clicked", GTK_SIGNAL_FUNC(itinerary_close), GTK_OBJECT(window)); GTK_WIDGET_SET_FLAGS(btnClose, GTK_CAN_DEFAULT); gtk_widget_grab_default(btnClose); /* btnClose = gtk_button_new_with_label("Remove"); gtk_box_pack_start(GTK_BOX(box2), btnClose, FALSE, FALSE, 4); gtk_signal_connect_object(GTK_OBJECT(btnClose), "clicked", GTK_SIGNAL_FUNC(itinerary_remove), GTK_OBJECT(window)); */ gtk_signal_connect(GTK_OBJECT(window), "destroy", GTK_SIGNAL_FUNC(itinerary_remove),NULL); gtk_widget_show_all(window); gtk_main(); } static int ycnt; static void add_perf_line(GtkWidget *box1, char *txt, long tot, long vals) { GtkWidget *box2; GtkWidget *child; char buff[256]; sprintf(buff, "%s ", L(txt)); box2 = gtk_label_new(txt); gtk_misc_set_alignment(GTK_MISC(box2), 0.0, 0.5); gtk_table_attach_defaults(GTK_TABLE(box1), box2, 0, 1, ycnt, ycnt + 1); gtk_widget_show (box1); sprintf(buff, "%6d x %3d = %d", tot, vals, tot * vals); box2 = gtk_label_new(buff); gtk_misc_set_alignment(GTK_MISC(box2), 0.0, 0.5); gtk_table_attach_defaults(GTK_TABLE(box1), box2, 1, 2, ycnt, ycnt + 1); gtk_widget_show (box1); ++ycnt; } void gtk_performance_dialog(void) { GtkWidget *window = NULL; GtkWidget *box1,*box2; GtkWidget *table; GtkWidget *btnColor,*btnFile,*btnClose; GtkWidget *child; char buff[256]; /* Create modal window (Here you can use any window descendent )*/ window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_window_set_title(GTK_WINDOW(window), L("Performance status")); /* Set window as modal */ gtk_window_set_modal(GTK_WINDOW(window),TRUE); box1 = gtk_vbox_new(FALSE, 5); gtk_container_set_border_width(GTK_CONTAINER(box1), 10); gtk_container_add(GTK_CONTAINER(window), box1); ycnt = 0; table = gtk_table_new(2, 9, FALSE); gtk_box_pack_start(GTK_BOX(box1), table, FALSE, FALSE, 0); add_perf_line(table, L("Wrong destinations :"), perf_tot.wrong_dest, perf_vals.wrong_dest); add_perf_line(table, L("Late trains :"), perf_tot.late_trains, perf_vals.late_trains); add_perf_line(table, L("Thrown switches :"), perf_tot.thrown_switch, perf_vals.thrown_switch); add_perf_line(table, L("Cleared signals :"), perf_tot.cleared_signal, perf_vals.cleared_signal); add_perf_line(table, L("Turned trains :"), perf_tot.turned_train, perf_vals.turned_train); add_perf_line(table, L("Trains stopped at sig.:"), perf_tot.waiting_train, perf_vals.waiting_train); add_perf_line(table, L("Wrong platforms :"), perf_tot.wrong_platform, perf_vals.wrong_platform); add_perf_line(table, L("Commands denied :"), perf_tot.denied, perf_vals.denied); add_perf_line(table, L("Wrong stock assignments :"), perf_tot.wrong_assign, perf_vals.wrong_assign); gtk_box_pack_start(GTK_BOX(box1), gtk_hseparator_new(), FALSE, FALSE, 4); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); btnClose = gtk_button_new_with_label(L("Ok")); gtk_box_pack_start(GTK_BOX(box2), btnClose, TRUE, TRUE, 4); gtk_signal_connect_object(GTK_OBJECT(btnClose), "clicked", GTK_SIGNAL_FUNC(gtk_widget_destroy), GTK_OBJECT(window)); GTK_WIDGET_SET_FLAGS (btnClose, GTK_CAN_DEFAULT); gtk_widget_grab_default(btnClose); gtk_signal_connect(GTK_OBJECT(window), "destroy", GTK_SIGNAL_FUNC(cmw_destroy_cb),NULL); gtk_widget_show_all(window); gtk_main(); } static void add_about_line(GtkWidget *box1, char *text) { GtkWidget *child; child = gtk_label_new(text); gtk_box_pack_start(GTK_BOX(box1), child, TRUE, TRUE, 4); } void gtk_about_dialog(void) { GtkWidget *window = NULL; GtkWidget *box1,*box2; GtkWidget *btnClose; char buff[64]; /* Create modal window (Here you can use any window descendent )*/ window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_window_set_title(GTK_WINDOW(window), L("About Train Director")); /* Set window as modal */ gtk_window_set_modal(GTK_WINDOW(window),TRUE); box1 = gtk_vbox_new(FALSE, 5); gtk_container_set_border_width(GTK_CONTAINER(box1), 10); gtk_container_add(GTK_CONTAINER(window), box1); sprintf(buff, "Train Director %s %s", version, host); add_about_line(box1, buff); gtk_box_pack_start(GTK_BOX(box1), gtk_hseparator_new(), FALSE, FALSE, 4); strcpy(buff, L("Created by")); strcat(buff, " Giampiero Caprino\nSunnyvale, California"); add_about_line(box1, buff); add_about_line(box1, L("This is a game, and is not intended to\nbe used to actually control train traffic.")); add_about_line(box1, L("This is free software, released under the\nGNU General Public License.\n" "The author declines any responsibility for any damage\nthat might occur from the use of this program.")); gtk_box_pack_start(GTK_BOX(box1), gtk_hseparator_new(), FALSE, FALSE, 4); box2 = gtk_hbox_new(FALSE, 5); gtk_box_pack_start(GTK_BOX(box1), box2, TRUE, TRUE, 4); btnClose = gtk_button_new_with_label(L("Ok")); gtk_box_pack_start(GTK_BOX(box2), btnClose, TRUE, TRUE, 4); gtk_signal_connect_object(GTK_OBJECT(btnClose), "clicked", GTK_SIGNAL_FUNC(gtk_widget_destroy), GTK_OBJECT(window)); GTK_WIDGET_SET_FLAGS (btnClose, GTK_CAN_DEFAULT); gtk_widget_grab_default(btnClose); gtk_signal_connect(GTK_OBJECT(window), "destroy", GTK_SIGNAL_FUNC(cmw_destroy_cb),NULL); gtk_widget_show_all(window); gtk_main(); } extern void gtk_train_info_dialog(Train *); extern void gtk_assign_dialog(Train *); extern void gtk_station_sched_dialog(char *); void init_gtk_dialogs(void) { if(!performance_dialog) performance_dialog = gtk_performance_dialog; if(!options_dialog) options_dialog = gtk_options_dialog; #if defined(__unix__) if(!trigger_properties_dialog) trigger_properties_dialog = gtk_trigger_properties_dialog; if(!signal_properties_dialog) signal_properties_dialog = gtk_signal_properties_dialog; #endif if(!track_properties_dialog) track_properties_dialog = gtk_track_properties_dialog; if(!select_day_dialog) select_day_dialog = gtk_select_day_dialog; if(!train_info_dialog) train_info_dialog = gtk_train_info_dialog; if(!assign_dialog || getenv("USEGTKDLG")) assign_dialog = gtk_assign_dialog; if(!station_sched_dialog) station_sched_dialog = gtk_station_sched_dialog; if(!itinerary_dialog) itinerary_dialog = gtk_itinerary_dialog; if(!about_dialog) about_dialog = gtk_about_dialog; } #if defined(__unix__) void enter_beep(void) { gdk_beep(); } #endif