Freeciv-3.2: /fast/freeciv/nightly/S3_2/client/gui-gtk-3.22/gui_main.c Source File

Freeciv-3.2

Loading...
Searching...
No Matches
gui_main.c
Go to the documentation of this file.
1/***********************************************************************
2 Freeciv - Copyright (C) 1996 - A Kjeldberg, L Gregersen, P Unold
3 This program is free software; you can redistribute it and/or modify
4 it under the terms of the GNU General Public License as published by
5 the Free Software Foundation; either version 2, or (at your option)
6 any later version.
7
8 This program is distributed in the hope that it will be useful,
9 but WITHOUT ANY WARRANTY; without even the implied warranty of
10 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 GNU General Public License for more details.
12***********************************************************************/
13
14#ifdef HAVE_CONFIG_H
15#include <fc_config.h>
16#endif
17
18#ifdef AUDIO_SDL
19/* Though it would happily compile without this include,
20 * it is needed for sound to work.
21 * It defines "main" macro to rename our main() so that
22 * it can install SDL's own. */
23#ifdef SDL2_PLAIN_INCLUDE
24#include <SDL.h>
25#else /* PLAIN_INCLUDE */
26#include <SDL2/SDL.h>
27#endif /* PLAIN_INCLUDE */
28#endif /* AUDIO_SDL */
29
30#ifdef HAVE_LOCALE_H
31#include <locale.h>
32#endif
33#include <stdarg.h>
34#include <stdio.h>
35#include <stdlib.h>
36#include <string.h>
37#include <time.h>
38
39#ifdef HAVE_UNISTD_H
40#include <unistd.h>
41#endif
42
43#include <gtk/gtk.h>
44#include <gdk/gdkkeysyms.h>
45
46/* utility */
47#include "fc_cmdline.h"
48#include "fciconv.h"
49#include "fcintl.h"
50#include "log.h"
51#include "mem.h"
52#include "support.h"
53
54/* common */
55#include "dataio.h"
56#include "featured_text.h"
57#include "game.h"
58#include "government.h"
59#include "map.h"
60#include "unitlist.h"
61#include "version.h"
62
63/* client */
64#include "audio.h"
65#include "client_main.h"
66#include "climisc.h"
67#include "clinet.h"
68#include "colors.h"
69#include "connectdlg_common.h"
70#include "control.h"
71#include "editor.h"
72#include "options.h"
73#include "text.h"
74#include "tilespec.h"
75#include "zoom.h"
76
77/* client/gui-gtk-3.22 */
78#include "chatline.h"
79#include "citizensinfo.h"
80#include "connectdlg.h"
81#include "cma_fe.h"
82#include "dialogs.h"
83#include "diplodlg.h"
84#include "editgui.h"
85#include "gotodlg.h"
86#include "graphics.h"
87#include "gui_stuff.h"
88#include "happiness.h"
89#include "helpdlg.h"
90#include "inteldlg.h"
91#include "mapctrl.h"
92#include "mapview.h"
93#include "menu.h"
94#include "messagewin.h"
95#include "optiondlg.h"
96#include "pages.h"
97#include "plrdlg.h"
98#include "luaconsole.h"
99#include "spaceshipdlg.h"
100#include "repodlgs.h"
101#include "voteinfo_bar.h"
102
103#include "gui_main.h"
104
105 const char *client_string = GUI_NAME_FULL;
106
107 GtkWidget *map_canvas; /* GtkDrawingArea */
108 GtkWidget *map_horizontal_scrollbar;
109 GtkWidget *map_vertical_scrollbar;
110
111 GtkWidget *overview_canvas; /* GtkDrawingArea */
112 GtkWidget *overview_scrolled_window; /* GtkScrolledWindow */
113/* The two values below define the width and height of the map overview. The
114 * first set of values (2*62, 2*46) define the size for a netbook display. For
115 * bigger displays the values are doubled (default). */
116#define OVERVIEW_CANVAS_STORE_WIDTH_NETBOOK (2 * 64)
117#define OVERVIEW_CANVAS_STORE_HEIGHT_NETBOOK (2 * 46)
118#define OVERVIEW_CANVAS_STORE_WIDTH \
119 (2 * OVERVIEW_CANVAS_STORE_WIDTH_NETBOOK)
120#define OVERVIEW_CANVAS_STORE_HEIGHT \
121 (2 * OVERVIEW_CANVAS_STORE_HEIGHT_NETBOOK)
122 int overview_canvas_store_width = OVERVIEW_CANVAS_STORE_WIDTH;
123 int overview_canvas_store_height = OVERVIEW_CANVAS_STORE_HEIGHT;
124
125 GtkWidget *toplevel;
126 GdkWindow *root_window;
127 GtkWidget *toplevel_tabs;
128 GtkWidget *top_vbox;
129 GtkWidget *top_notebook, *bottom_notebook, *right_notebook;
130 GtkWidget *map_widget;
131 static GtkWidget *bottom_hpaned;
132
133 PangoFontDescription *city_names_style = NULL;
134 PangoFontDescription *city_productions_style = NULL;
135 PangoFontDescription *reqtree_text_style = NULL;
136
137 GtkWidget *main_frame_civ_name;
138 GtkWidget *main_label_info;
139
140 GtkWidget *avbox, *ahbox, *conn_box;
141 GtkWidget* scroll_panel;
142
143 GtkWidget *econ_label[10];
144 GtkWidget *bulb_label;
145 GtkWidget *sun_label;
146 GtkWidget *flake_label;
147 GtkWidget *government_label;
148 GtkWidget *timeout_label;
149 GtkWidget *turn_done_button;
150
151 GtkWidget *unit_info_label;
152 GtkWidget *unit_info_box;
153 GtkWidget *unit_info_frame;
154
155 GtkWidget *econ_ebox;
156 GtkWidget *bulb_ebox;
157 GtkWidget *sun_ebox;
158 GtkWidget *flake_ebox;
159 GtkWidget *government_ebox;
160
161 const char *const gui_character_encoding = "UTF-8";
162 const bool gui_use_transliteration = FALSE;
163
164 static GtkWidget *main_menubar;
165 static GtkWidget *unit_image_table;
166 static GtkWidget *unit_image;
167 static GtkWidget *unit_image_button;
168 static GtkWidget *unit_below_image[MAX_NUM_UNITS_BELOW];
169 static GtkWidget *unit_below_image_button[MAX_NUM_UNITS_BELOW];
170 static GtkWidget *more_arrow_pixmap;
171 static GtkWidget *more_arrow_pixmap_button;
172 static GtkWidget *more_arrow_pixmap_container;
173
174 static int unit_id_top;
175 static int unit_ids[MAX_NUM_UNITS_BELOW]; /* ids of the units icons in
176 * information display: (or 0) */
177 GtkTextView *main_message_area;
178 GtkTextBuffer *message_buffer = NULL;
179 static GtkWidget *allied_chat_toggle_button;
180
181 static gint timer_id; /* ditto */
182 static GIOChannel *srv_channel;
183 static guint srv_id;
184 gint cur_x, cur_y;
185
186 static bool gui_up = FALSE;
187
188 static bool audio_paused = FALSE;
189 static bool client_focus = TRUE;
190
191 static struct video_mode vmode = { -1, -1 };
192
193static void set_g_log_callbacks(void);
194
195static gboolean show_info_button_release(GtkWidget *w, GdkEventButton *ev, gpointer data);
196static gboolean show_info_popup(GtkWidget *w, GdkEventButton *ev, gpointer data);
197
198static void end_turn_callback(GtkWidget *w, gpointer data);
199static gboolean get_net_input(GIOChannel *source, GIOCondition condition,
200 gpointer data);
201static void set_wait_for_writable_socket(struct connection *pc,
202 bool socket_writable);
203
204static void print_usage(void);
205static bool parse_options(int argc, char **argv);
206static gboolean toplevel_key_press_handler(GtkWidget *w, GdkEventKey *ev, gpointer data);
207static gboolean toplevel_key_release_handler(GtkWidget *w, GdkEventKey *ev, gpointer data);
208static gboolean mouse_scroll_mapcanvas(GtkWidget *w, GdkEventScroll *ev);
209
210static void tearoff_callback(GtkWidget *b, gpointer data);
211static GtkWidget *detached_widget_new(void);
212static GtkWidget *detached_widget_fill(GtkWidget *tearbox);
213
214static gboolean select_unit_image_callback(GtkWidget *w, GdkEvent *ev,
215 gpointer data);
216static gboolean select_more_arrow_pixmap_callback(GtkWidget *w, GdkEvent *ev,
217 gpointer data);
218static gboolean quit_dialog_callback(void);
219
220static void allied_chat_button_toggled(GtkToggleButton *button,
221 gpointer user_data);
222
223static void free_unit_table(void);
224
225static void adjust_default_options(void);
226
227/**********************************************************************/
230 static void log_callback_utf8(enum log_level level, const char *message,
231 bool file_too)
232{
233 if (!file_too || level <= LOG_FATAL) {
234 fc_fprintf(stderr, "%d: %s\n", level, message);
235 }
236}
237
238/**********************************************************************/
242 static gboolean timer_callback(gpointer data)
243{
244 double seconds = real_timer_callback();
245
246 if (gui_options.silent_when_not_in_focus) {
247 if (!audio_paused && !client_focus) {
248 audio_pause();
249 audio_paused = TRUE;
250 } else if (audio_paused && client_focus) {
251 audio_resume();
252 audio_paused = FALSE;
253 }
254 }
255
256 timer_id = g_timeout_add(seconds * 1000, timer_callback, NULL);
257
258 return FALSE;
259}
260
261/**********************************************************************/
265 static void print_usage(void)
266{
267 /* add client-specific usage information here */
268 fc_fprintf(stderr,
269 _("This client accepts the standard Gtk command-line options\n"
270 "after '--'. See the Gtk documentation.\n\n"));
271
272 fc_fprintf(stderr,
273 _("Other gui-specific options are:\n"));
274
275 fc_fprintf(stderr,
276 _("-r, --resolution WIDTHxHEIGHT\tAssume given resolution "
277 "screen\n"));
278
279#ifdef EXP_ZOOM_LEVELS
280 fc_fprintf(stderr,
281 /* TRANS: Keep word 'default' untranslated */
282 _("-z, --zoom LEVEL\tSet zoom level; use value 'default' "
283 "to reset\n\n"));
284#else
285 fc_fprintf(stderr, "\n");
286#endif /* EXP_ZOOM_LEVELS */
287
288 /* TRANS: No full stop after the URL, could cause confusion. */
289 fc_fprintf(stderr, _("Report bugs at %s\n"), BUG_URL);
290}
291
292/**********************************************************************/
295 static bool parse_options(int argc, char **argv)
296{
297 int i = 1;
298
299 while (i < argc) {
300 char *option = NULL;
301
302 if (is_option("--help", argv[i])) {
303 print_usage();
304
305 return FALSE;
306
307#ifdef EXP_ZOOM_LEVELS
308 } else if ((option = get_option_malloc("--zoom", argv, &i, argc, FALSE))) {
309 char *endptr;
310
311 if (strcmp("default", option)) {
312 gui_options.zoom_set = TRUE;
313 gui_options.zoom_default_level = strtof(option, &endptr);
314 } else {
315 gui_options.zoom_set = FALSE;
316 }
317 free(option);
318#endif /* EXP_ZOOM_LEVELS */
319
320 } else if ((option = get_option_malloc("--resolution", argv, &i, argc, FALSE))) {
321 if (!string_to_video_mode(option, &vmode)) {
322 fc_fprintf(stderr, _("Illegal video mode '%s'\n"), option);
323 exit(EXIT_FAILURE);
324 }
325 free(option);
326 }
327 /* Can't check against unknown options, as those might be gtk options */
328
329 i++;
330 }
331
332 return TRUE;
333}
334
335/**********************************************************************/
338 static gboolean toplevel_focus(GtkWidget *w, GtkDirectionType arg)
339{
340 switch (arg) {
341 case GTK_DIR_TAB_FORWARD:
342 case GTK_DIR_TAB_BACKWARD:
343
344 if (!gtk_widget_get_can_focus(w)) {
345 return FALSE;
346 }
347
348 if (!gtk_widget_is_focus(w)) {
349 gtk_widget_grab_focus(w);
350 return TRUE;
351 }
352 break;
353
354 default:
355 break;
356 }
357 return FALSE;
358}
359
360/**********************************************************************/
365 static void main_message_area_size_allocate(GtkWidget *widget,
366 GtkAllocation *allocation,
367 gpointer data)
368{
369 static int old_width = 0, old_height = 0;
370
371 if (allocation->width != old_width
372 || allocation->height != old_height) {
373 chatline_scroll_to_bottom(TRUE);
374 old_width = allocation->width;
375 old_height = allocation->height;
376 }
377}
378
379/**********************************************************************/
382 gboolean map_canvas_focus(void)
383{
384 gtk_window_present(GTK_WINDOW(toplevel));
385 gtk_notebook_set_current_page(GTK_NOTEBOOK(top_notebook), 0);
386 gtk_widget_grab_focus(map_canvas);
387 return TRUE;
388}
389
390/**********************************************************************/
399 static gboolean toplevel_handler(GtkWidget *w, GdkEvent *ev, gpointer data)
400{
401 GtkWidget *focus;
402
403 focus = gtk_window_get_focus(GTK_WINDOW(toplevel));
404 if (focus) {
405 if (GTK_IS_ENTRY(focus)
406 || (GTK_IS_TEXT_VIEW(focus)
407 && gtk_text_view_get_editable(GTK_TEXT_VIEW(focus)))) {
408 /* Propagate event to currently focused entry widget. */
409 if (gtk_widget_event(focus, ev)) {
410 /* Do not propagate event to our children. */
411 return TRUE;
412 }
413 }
414 }
415
416 /* Continue propagating event to our children. */
417 return FALSE;
418}
419
420/**********************************************************************/
423 static gboolean key_press_map_canvas(GtkWidget *w, GdkEventKey *ev,
424 gpointer data)
425{
426 if ((ev->state & GDK_SHIFT_MASK)) {
427 switch (ev->keyval) {
428
429 case GDK_KEY_Left:
430 scroll_mapview(DIR8_WEST);
431 return TRUE;
432
433 case GDK_KEY_Right:
434 scroll_mapview(DIR8_EAST);
435 return TRUE;
436
437 case GDK_KEY_Up:
438 scroll_mapview(DIR8_NORTH);
439 return TRUE;
440
441 case GDK_KEY_Down:
442 scroll_mapview(DIR8_SOUTH);
443 return TRUE;
444
445 case GDK_KEY_Home:
446 key_center_capital();
447 return TRUE;
448
449 case GDK_KEY_Page_Up:
450 g_signal_emit_by_name(main_message_area, "move_cursor",
451 GTK_MOVEMENT_PAGES, -1, FALSE);
452 return TRUE;
453
454 case GDK_KEY_Page_Down:
455 g_signal_emit_by_name(main_message_area, "move_cursor",
456 GTK_MOVEMENT_PAGES, 1, FALSE);
457 return TRUE;
458
459 default:
460 break;
461 }
462 } else if (!(ev->state & GDK_CONTROL_MASK)) {
463 switch (ev->keyval) {
464 default:
465 break;
466 }
467 }
468
469 if (ev->state & GDK_SHIFT_MASK) {
470 bool volchange = FALSE;
471
472 switch (ev->keyval) {
473 case GDK_KEY_plus:
474 case GDK_KEY_KP_Add:
475 gui_options.sound_effects_volume += 10;
476 volchange = TRUE;
477 break;
478
479 case GDK_KEY_minus:
480 case GDK_KEY_KP_Subtract:
481 gui_options.sound_effects_volume -= 10;
482 volchange = TRUE;
483 break;
484
485 default:
486 break;
487 }
488
489 if (volchange) {
490 struct option *poption = optset_option_by_name(client_optset, "sound_effects_volume");
491
492 gui_options.sound_effects_volume = CLIP(0, gui_options.sound_effects_volume, 100);
493 option_changed(poption);
494
495 return TRUE;
496 }
497 } else if (!(ev->state & GDK_CONTROL_MASK)) {
498 switch (ev->keyval) {
499 case GDK_KEY_plus:
500 case GDK_KEY_KP_Add:
501 zoom_step_up();
502 return TRUE;
503
504 case GDK_KEY_minus:
505 case GDK_KEY_KP_Subtract:
506 zoom_step_down();
507 return TRUE;
508
509 default:
510 break;
511 }
512 }
513
514 /* Return here if observer */
515 if (client_is_observer()) {
516 return FALSE;
517 }
518
519 switch (ev->keyval) {
520
521 case GDK_KEY_KP_Up:
522 case GDK_KEY_KP_8:
523 case GDK_KEY_Up:
524 case GDK_KEY_8:
525 key_unit_move(DIR8_NORTH);
526 return TRUE;
527
528 case GDK_KEY_KP_Page_Up:
529 case GDK_KEY_KP_9:
530 case GDK_KEY_Page_Up:
531 case GDK_KEY_9:
532 key_unit_move(DIR8_NORTHEAST);
533 return TRUE;
534
535 case GDK_KEY_KP_Right:
536 case GDK_KEY_KP_6:
537 case GDK_KEY_Right:
538 case GDK_KEY_6:
539 key_unit_move(DIR8_EAST);
540 return TRUE;
541
542 case GDK_KEY_KP_Page_Down:
543 case GDK_KEY_KP_3:
544 case GDK_KEY_Page_Down:
545 case GDK_KEY_3:
546 key_unit_move(DIR8_SOUTHEAST);
547 return TRUE;
548
549 case GDK_KEY_KP_Down:
550 case GDK_KEY_KP_2:
551 case GDK_KEY_Down:
552 case GDK_KEY_2:
553 key_unit_move(DIR8_SOUTH);
554 return TRUE;
555
556 case GDK_KEY_KP_End:
557 case GDK_KEY_KP_1:
558 case GDK_KEY_End:
559 case GDK_KEY_1:
560 key_unit_move(DIR8_SOUTHWEST);
561 return TRUE;
562
563 case GDK_KEY_KP_Left:
564 case GDK_KEY_KP_4:
565 case GDK_KEY_Left:
566 case GDK_KEY_4:
567 key_unit_move(DIR8_WEST);
568 return TRUE;
569
570 case GDK_KEY_KP_Home:
571 case GDK_KEY_KP_7:
572 case GDK_KEY_Home:
573 case GDK_KEY_7:
574 key_unit_move(DIR8_NORTHWEST);
575 return TRUE;
576
577 case GDK_KEY_KP_Begin:
578 case GDK_KEY_KP_5:
579 case GDK_KEY_5:
580 key_recall_previous_focus_unit();
581 return TRUE;
582
583 case GDK_KEY_Escape:
584 key_cancel_action();
585 return TRUE;
586
587 case GDK_KEY_b:
588 if (tiles_hilited_cities) {
589 buy_production_in_selected_cities();
590 return TRUE;
591 }
592 break;
593
594 default:
595 break;
596 };
597
598 return FALSE;
599}
600
601/**********************************************************************/
604 static gboolean toplevel_key_release_handler(GtkWidget *w, GdkEventKey *ev,
605 gpointer data)
606{
607 /* inputline history code */
608 if (!gtk_widget_get_mapped(top_vbox) || inputline_has_focus()) {
609 return FALSE;
610 }
611
612 if (editor_is_active()) {
613 return handle_edit_key_release(ev);
614 }
615
616 return FALSE;
617}
618
619/**********************************************************************/
622 static gboolean toplevel_key_press_handler(GtkWidget *w, GdkEventKey *ev,
623 gpointer data)
624{
625 if (inputline_has_focus()) {
626 return FALSE;
627 }
628
629 if (ev->keyval == GDK_KEY_apostrophe) {
630 /* Allow this even if not in main map view; chatline is present on
631 * some other pages too */
632
633 /* Make the chatline visible if it's not currently.
634 * FIXME: should find the correct window, even when detached, from any
635 * other window; should scroll to the bottom automatically showing the
636 * latest text from other players; MUST NOT make spurious text windows
637 * at the bottom of other dialogs. */
638 if (gtk_widget_get_mapped(top_vbox)) {
639 /* The main game view is visible. May need to switch notebook. */
640 if (GUI_GTK_OPTION(message_chat_location) == GUI_GTK_MSGCHAT_MERGED) {
641 gtk_notebook_set_current_page(GTK_NOTEBOOK(top_notebook), 1);
642 } else {
643 gtk_notebook_set_current_page(GTK_NOTEBOOK(bottom_notebook), 0);
644 }
645 }
646
647 /* If the chatline is (now) visible, focus it. */
648 if (inputline_is_visible()) {
649 inputline_grab_focus();
650 return TRUE;
651 }
652 }
653
654 if (!gtk_widget_get_mapped(top_vbox)
655 || !can_client_change_view()) {
656 return FALSE;
657 }
658
659 if (editor_is_active()) {
660 if (handle_edit_key_press(ev)) {
661 return TRUE;
662 }
663 }
664
665 if (ev->state & GDK_SHIFT_MASK) {
666 switch (ev->keyval) {
667
668 case GDK_KEY_Return:
669 case GDK_KEY_KP_Enter:
670 key_end_turn();
671 return TRUE;
672
673 default:
674 break;
675 }
676 }
677
678 if (0 == gtk_notebook_get_current_page(GTK_NOTEBOOK(top_notebook))) {
679 /* 0 means the map view is focused. */
680 return key_press_map_canvas(w, ev, data);
681 }
682
683#if 0
684 /* We are focused some other dialog, tab, or widget. */
685 if ((ev->state & GDK_CONTROL_MASK)) {
686 } else if ((ev->state & GDK_SHIFT_MASK)) {
687 } else {
688 switch (ev->keyval) {
689
690 case GDK_KEY_F4:
691 map_canvas_focus();
692 return TRUE;
693
694 default:
695 break;
696 };
697 }
698#endif /* 0 */
699
700 return FALSE;
701}
702
703/**********************************************************************/
706 static gboolean mouse_scroll_mapcanvas(GtkWidget *w, GdkEventScroll *ev)
707{
708 int scroll_x, scroll_y, xstep, ystep;
709
710 if (!can_client_change_view()) {
711 return FALSE;
712 }
713
714 get_mapview_scroll_pos(&scroll_x, &scroll_y);
715 get_mapview_scroll_step(&xstep, &ystep);
716
717 switch (ev->direction) {
718 case GDK_SCROLL_UP:
719 scroll_y -= ystep*2;
720 break;
721 case GDK_SCROLL_DOWN:
722 scroll_y += ystep*2;
723 break;
724 case GDK_SCROLL_RIGHT:
725 scroll_x += xstep*2;
726 break;
727 case GDK_SCROLL_LEFT:
728 scroll_x -= xstep*2;
729 break;
730 default:
731 return FALSE;
732 };
733
734 set_mapview_scroll_pos(scroll_x, scroll_y, mouse_zoom);
735
736 /* Emulating mouse move now */
737 if (!gtk_widget_has_focus(map_canvas)) {
738 gtk_widget_grab_focus(map_canvas);
739 }
740
741 update_line(ev->x, ev->y);
742 if (rbutton_down && (ev->state & GDK_BUTTON3_MASK)) {
743 update_selection_rectangle(ev->x, ev->y);
744 }
745
746 if (keyboardless_goto_button_down && hover_state == HOVER_NONE) {
747 maybe_activate_keyboardless_goto(cur_x, cur_y);
748 }
749
750 control_mouse_cursor(canvas_pos_to_tile(cur_x, cur_y, mouse_zoom));
751
752 return TRUE;
753}
754
755/**********************************************************************/
758 gboolean fc_lost_focus(GtkWidget *w, GdkEventKey *ev, gpointer data)
759{
760 client_focus = FALSE;
761
762 return TRUE;
763}
764
765/**********************************************************************/
768 gboolean fc_gained_focus(GtkWidget *w, GdkEventKey *ev, gpointer data)
769{
770 client_focus = TRUE;
771
772 return TRUE;
773}
774
775/**********************************************************************/
778 static void tearoff_destroy(GtkWidget *w, gpointer data)
779{
780 GtkWidget *p, *b, *box;
781 GtkWidget *old_parent;
782
783 box = GTK_WIDGET(data);
784 old_parent = gtk_widget_get_parent(box);
785 p = g_object_get_data(G_OBJECT(w), "parent");
786 b = g_object_get_data(G_OBJECT(w), "toggle");
787 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(b), FALSE);
788
789 gtk_widget_hide(w);
790
791 g_object_ref(box); /* Make sure reference count stays above 0
792 * during the transition to new parent. */
793 gtk_container_remove(GTK_CONTAINER(old_parent), box);
794 gtk_container_add(GTK_CONTAINER(p), box);
795 g_object_unref(box);
796}
797
798/**********************************************************************/
801 static gboolean propagate_keypress(GtkWidget *w, GdkEvent *ev)
802{
803 gtk_widget_event(toplevel, ev);
804
805 return FALSE;
806}
807
808/**********************************************************************/
812 static void tearoff_callback(GtkWidget *b, gpointer data)
813{
814 GtkWidget *box = GTK_WIDGET(data);
815
816 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(b))) {
817 GtkWidget *old_parent;
818 GtkWidget *w;
819 GtkWidget *temp_hide;
820
821 old_parent = gtk_widget_get_parent(box);
822 w = gtk_window_new(GTK_WINDOW_TOPLEVEL);
823 setup_dialog(w, toplevel);
824 gtk_widget_set_name(w, "Freeciv");
825 gtk_window_set_title(GTK_WINDOW(w), _("Freeciv"));
826 gtk_window_set_position(GTK_WINDOW(w), GTK_WIN_POS_MOUSE);
827 g_signal_connect(w, "destroy", G_CALLBACK(tearoff_destroy), box);
828 g_signal_connect(w, "key_press_event",
829 G_CALLBACK(propagate_keypress), NULL);
830
831 g_object_set_data(G_OBJECT(w), "parent", gtk_widget_get_parent(box));
832 g_object_set_data(G_OBJECT(w), "toggle", b);
833
834 temp_hide = g_object_get_data(G_OBJECT(box), "hide-over-reparent");
835 if (temp_hide != NULL) {
836 gtk_widget_hide(temp_hide);
837 }
838
839 g_object_ref(box); /* Make sure reference count stays above 0
840 * during the transition to new parent. */
841 gtk_container_remove(GTK_CONTAINER(old_parent), box);
842 gtk_container_add(GTK_CONTAINER(w), box);
843 g_object_unref(box);
844 gtk_widget_show(w);
845
846 if (temp_hide != NULL) {
847 gtk_widget_show(temp_hide);
848 }
849 } else {
850 gtk_widget_destroy(gtk_widget_get_parent(box));
851 }
852}
853
854/**********************************************************************/
857 static GtkWidget *detached_widget_new(void)
858{
859 GtkWidget *hgrid = gtk_grid_new();
860 gtk_grid_set_column_spacing(GTK_GRID(hgrid), 2);
861 return hgrid;
862}
863
864/**********************************************************************/
868 static GtkWidget *detached_widget_fill(GtkWidget *tearbox)
869{
870 GtkWidget *b, *fillbox;
871 static GtkCssProvider *detach_button_provider = NULL;
872
873 if (detach_button_provider == NULL) {
874 detach_button_provider = gtk_css_provider_new();
875
876 /* These toggle buttons run vertically down the side of many UI
877 * elements, so they need to be thin horizontally. */
878 gtk_css_provider_load_from_data(detach_button_provider,
879 ".detach_button {\n"
880 " padding: 0px 0px 0px 0px;\n"
881 " min-width: 6px;\n"
882 "}",
883 -1, NULL);
884 }
885
886 b = gtk_toggle_button_new();
887 gtk_style_context_add_provider(gtk_widget_get_style_context(b),
888 GTK_STYLE_PROVIDER(detach_button_provider),
889 GTK_STYLE_PROVIDER_PRIORITY_APPLICATION);
890 gtk_style_context_add_class(gtk_widget_get_style_context(b),
891 "detach_button");
892
893 gtk_container_add(GTK_CONTAINER(tearbox), b);
894 g_signal_connect(b, "toggled", G_CALLBACK(tearoff_callback), tearbox);
895
896 fillbox = gtk_grid_new();
897 gtk_orientable_set_orientation(GTK_ORIENTABLE(fillbox),
898 GTK_ORIENTATION_VERTICAL);
899
900 gtk_container_add(GTK_CONTAINER(tearbox), fillbox);
901
902 return fillbox;
903}
904
905/**********************************************************************/
912 static void populate_unit_image_table(void)
913{
914 int i, width;
915 GtkWidget *table = unit_image_table;
916 GdkPixbuf *pix;
917 int ttw;
918
919 /* Get width of the overview window */
920 width = (overview_canvas_store_width > GUI_GTK_OVERVIEW_MIN_XSIZE)
921 ? overview_canvas_store_width
922 : GUI_GTK_OVERVIEW_MIN_XSIZE;
923
924 ttw = tileset_tile_width(tileset);
925
926 if (GUI_GTK_OPTION(small_display_layout)) {
927 /* We want arrow to appear if there is other units in addition
928 to active one in tile. Active unit is not counted, so there
929 can be 0 other units to not to display arrow. */
930 num_units_below = 1 - 1;
931 } else {
932 num_units_below = width / ttw;
933 num_units_below = CLIP(1, num_units_below, MAX_NUM_UNITS_BELOW);
934 }
935
936 /* Top row: the active unit. */
937 /* Note, we ref this and other widgets here so that we can unref them
938 * in reset_unit_table. */
939 unit_image = gtk_image_new();
940 gtk_widget_add_events(unit_image, GDK_BUTTON_PRESS_MASK);
941 g_object_ref(unit_image);
942 unit_image_button = gtk_event_box_new();
943 gtk_widget_set_size_request(unit_image_button, ttw, -1);
944 gtk_event_box_set_visible_window(GTK_EVENT_BOX(unit_image_button), FALSE);
945 g_object_ref(unit_image_button);
946 gtk_container_add(GTK_CONTAINER(unit_image_button), unit_image);
947 gtk_grid_attach(GTK_GRID(table), unit_image_button, 0, 0, 1, 1);
948 g_signal_connect(unit_image_button, "button_press_event",
949 G_CALLBACK(select_unit_image_callback),
950 GINT_TO_POINTER(-1));
951
952 if (!GUI_GTK_OPTION(small_display_layout)) {
953 /* Bottom row: other units in the same tile. */
954 for (i = 0; i < num_units_below; i++) {
955 unit_below_image[i] = gtk_image_new();
956 g_object_ref(unit_below_image[i]);
957 gtk_widget_add_events(unit_below_image[i], GDK_BUTTON_PRESS_MASK);
958 unit_below_image_button[i] = gtk_event_box_new();
959 g_object_ref(unit_below_image_button[i]);
960 gtk_widget_set_size_request(unit_below_image_button[i], ttw, -1);
961 gtk_event_box_set_visible_window(GTK_EVENT_BOX(unit_below_image_button[i]),
962 FALSE);
963 gtk_container_add(GTK_CONTAINER(unit_below_image_button[i]),
964 unit_below_image[i]);
965 g_signal_connect(unit_below_image_button[i],
966 "button_press_event",
967 G_CALLBACK(select_unit_image_callback),
968 GINT_TO_POINTER(i));
969
970 gtk_grid_attach(GTK_GRID(table), unit_below_image_button[i],
971 i, 1, 1, 1);
972 }
973 }
974
975 /* Create arrow (popup for all units on the selected tile) */
976 pix = sprite_get_pixbuf(get_arrow_sprite(tileset, ARROW_RIGHT));
977 more_arrow_pixmap = gtk_image_new_from_pixbuf(pix);
978 g_object_ref(more_arrow_pixmap);
979 more_arrow_pixmap_button = gtk_event_box_new();
980 g_object_ref(more_arrow_pixmap_button);
981 gtk_event_box_set_visible_window(GTK_EVENT_BOX(more_arrow_pixmap_button),
982 FALSE);
983 gtk_container_add(GTK_CONTAINER(more_arrow_pixmap_button),
984 more_arrow_pixmap);
985 g_signal_connect(more_arrow_pixmap_button,
986 "button_press_event",
987 G_CALLBACK(select_more_arrow_pixmap_callback), NULL);
988 /* An extra layer so that we can hide the clickable button but keep
989 * an explicit size request to avoid the layout jumping around */
990 more_arrow_pixmap_container = gtk_frame_new(NULL);
991 gtk_frame_set_shadow_type(GTK_FRAME(more_arrow_pixmap_container), GTK_SHADOW_NONE);
992 gtk_widget_set_halign(more_arrow_pixmap_container, GTK_ALIGN_CENTER);
993 gtk_widget_set_valign(more_arrow_pixmap_container, GTK_ALIGN_CENTER);
994 g_object_ref(more_arrow_pixmap_container);
995 gtk_container_add(GTK_CONTAINER(more_arrow_pixmap_container),
996 more_arrow_pixmap_button);
997 gtk_widget_set_size_request(more_arrow_pixmap_container,
998 gdk_pixbuf_get_width(pix), -1);
999 g_object_unref(G_OBJECT(pix));
1000
1001 if (!GUI_GTK_OPTION(small_display_layout)) {
1002 /* Display on bottom row. */
1003 gtk_grid_attach(GTK_GRID(table), more_arrow_pixmap_container,
1004 num_units_below, 1, 1, 1);
1005 } else {
1006 /* Display on top row (there is no bottom row). */
1007 gtk_grid_attach(GTK_GRID(table), more_arrow_pixmap_container,
1008 1, 0, 1, 1);
1009 }
1010
1011 gtk_widget_show_all(table);
1012}
1013
1014/**********************************************************************/
1017 static void free_unit_table(void)
1018{
1019 if (unit_image_button) {
1020 gtk_container_remove(GTK_CONTAINER(unit_image_table),
1021 unit_image_button);
1022 g_object_unref(unit_image);
1023 g_object_unref(unit_image_button);
1024 if (!GUI_GTK_OPTION(small_display_layout)) {
1025 int i;
1026
1027 for (i = 0; i < num_units_below; i++) {
1028 gtk_container_remove(GTK_CONTAINER(unit_image_table),
1029 unit_below_image_button[i]);
1030 g_object_unref(unit_below_image[i]);
1031 g_object_unref(unit_below_image_button[i]);
1032 }
1033 }
1034 gtk_container_remove(GTK_CONTAINER(unit_image_table),
1035 more_arrow_pixmap_container);
1036 g_object_unref(more_arrow_pixmap);
1037 g_object_unref(more_arrow_pixmap_button);
1038 g_object_unref(more_arrow_pixmap_container);
1039 }
1040}
1041
1042/**********************************************************************/
1045 void reset_unit_table(void)
1046{
1047 /* Unreference all of the widgets that we're about to reallocate, thus
1048 * avoiding a memory leak. Remove them from the container first, just
1049 * to be safe. Note, the widgets are ref'd in
1050 * populate_unit_image_table. */
1051 free_unit_table();
1052
1053 populate_unit_image_table();
1054
1055 /* We have to force a redraw of the units. And we explicitly have
1056 * to force a redraw of the focus unit, which is normally only
1057 * redrawn when the focus changes. We also have to force the 'more'
1058 * arrow to go away, both by expicitly hiding it and telling it to
1059 * do so (this will be reset immediately afterwards if necessary,
1060 * but we have to make the *internal* state consistent). */
1061 gtk_widget_hide(more_arrow_pixmap_button);
1062 set_unit_icons_more_arrow(FALSE);
1063 if (get_num_units_in_focus() == 1) {
1064 set_unit_icon(-1, head_of_units_in_focus());
1065 } else {
1066 set_unit_icon(-1, NULL);
1067 }
1068 update_unit_pix_label(get_units_in_focus());
1069}
1070
1071/**********************************************************************/
1074 void enable_menus(bool enable)
1075{
1076 if (enable) {
1077 main_menubar = setup_menus(toplevel);
1078 /* Ensure the menus are really created before performing any operations
1079 * on them. */
1080 while (gtk_events_pending()) {
1081 gtk_main_iteration();
1082 }
1083 gtk_grid_attach_next_to(GTK_GRID(top_vbox), main_menubar, NULL, GTK_POS_TOP, 1, 1);
1084 menus_init();
1085 gtk_widget_show_all(main_menubar);
1086 } else {
1087 gtk_widget_destroy(main_menubar);
1088 }
1089}
1090
1091/**********************************************************************/
1097 static gboolean right_notebook_button_release(GtkWidget *widget,
1098 GdkEventButton *event)
1099{
1100 if (event->type != GDK_BUTTON_RELEASE) {
1101 return FALSE;
1102 }
1103
1104 if (!GTK_IS_NOTEBOOK(widget)
1105 || -1 == gtk_notebook_get_current_page(GTK_NOTEBOOK(widget))) {
1106 /* Make sure the default gtk handler
1107 * does NOT get called in this case. */
1108 return TRUE;
1109 }
1110
1111 return FALSE;
1112}
1113
1114/**********************************************************************/
1117#if 0
1118static void setup_canvas_color_for_state(GtkStateFlags state)
1119{
1120 gtk_widget_override_background_color(GTK_WIDGET(overview_canvas), state,
1121 &get_color(tileset, COLOR_OVERVIEW_UNKNOWN)->color);
1122 gtk_widget_override_background_color(GTK_WIDGET(map_canvas), state,
1123 &get_color(tileset, COLOR_OVERVIEW_UNKNOWN)->color);
1124}
1125#endif
1126
1127/**********************************************************************/
1130 void update_turn_done_tooltip(void)
1131{
1132 struct option *opt = optset_option_by_name(server_optset, "fixedlength");
1133
1134 if (opt != NULL && option_bool_get(opt)) {
1135 gtk_widget_set_tooltip_text(turn_done_button,
1136 _("Fixed length turns"));
1137 } else {
1138 char buf[256];
1139
1140 fc_snprintf(buf, sizeof(buf), "%s:\n%s",
1141 _("Turn Done"), _("Shift+Return"));
1142 gtk_widget_set_tooltip_text(turn_done_button, buf);
1143 }
1144}
1145
1146/**********************************************************************/
1149 static void setup_widgets(void)
1150{
1151 GtkWidget *page, *ebox, *hgrid, *hgrid2, *label;
1152 GtkWidget *frame, *table, *table2, *paned, *sw, *text;
1153 GtkWidget *button, *view, *vgrid, *right_vbox = NULL;
1154 int i;
1155 GtkWidget *notebook, *statusbar;
1156 GtkWidget *dtach_lowbox = NULL;
1157 struct sprite *spr;
1158
1159 message_buffer = gtk_text_buffer_new(NULL);
1160
1161 notebook = gtk_notebook_new();
1162
1163 /* Stop mouse wheel notebook page switching. */
1164 g_signal_connect(notebook, "scroll_event",
1165 G_CALLBACK(gtk_true), NULL);
1166
1167 toplevel_tabs = notebook;
1168 gtk_notebook_set_show_tabs(GTK_NOTEBOOK(notebook), FALSE);
1169 gtk_notebook_set_show_border(GTK_NOTEBOOK(notebook), FALSE);
1170 vgrid = gtk_grid_new();
1171 gtk_orientable_set_orientation(GTK_ORIENTABLE(vgrid),
1172 GTK_ORIENTATION_VERTICAL);
1173 gtk_grid_set_row_spacing(GTK_GRID(vgrid), 4);
1174 gtk_container_add(GTK_CONTAINER(toplevel), vgrid);
1175 gtk_container_add(GTK_CONTAINER(vgrid), notebook);
1176 statusbar = create_statusbar();
1177 gtk_container_add(GTK_CONTAINER(vgrid), statusbar);
1178
1179 gtk_notebook_append_page(GTK_NOTEBOOK(notebook),
1180 create_main_page(), NULL);
1181 gtk_notebook_append_page(GTK_NOTEBOOK(notebook),
1182 create_start_page(), NULL);
1183 gtk_notebook_append_page(GTK_NOTEBOOK(notebook),
1184 create_scenario_page(), NULL);
1185 gtk_notebook_append_page(GTK_NOTEBOOK(notebook),
1186 create_load_page(), NULL);
1187 gtk_notebook_append_page(GTK_NOTEBOOK(notebook),
1188 create_network_page(), NULL);
1189
1190 editgui_create_widgets();
1191
1192 ingame_votebar = voteinfo_bar_new(FALSE);
1193 g_object_set(ingame_votebar, "margin", 2, NULL);
1194
1195 /* *** everything in the top *** */
1196
1197 page = gtk_scrolled_window_new(NULL, NULL);
1198 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(page),
1199 GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC);
1200 gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(page),
1201 GTK_SHADOW_ETCHED_IN);
1202 gtk_notebook_append_page(GTK_NOTEBOOK(notebook), page, NULL);
1203
1204 top_vbox = gtk_grid_new();
1205 gtk_orientable_set_orientation(GTK_ORIENTABLE(top_vbox),
1206 GTK_ORIENTATION_VERTICAL);
1207 gtk_grid_set_row_spacing(GTK_GRID(top_vbox), 5);
1208 hgrid = gtk_grid_new();
1209
1210 if (GUI_GTK_OPTION(small_display_layout)) {
1211 /* The window is divided into two horizontal panels: overview +
1212 * civinfo + unitinfo, main view + message window. */
1213 right_vbox = gtk_grid_new();
1214 gtk_orientable_set_orientation(GTK_ORIENTABLE(right_vbox),
1215 GTK_ORIENTATION_VERTICAL);
1216 gtk_container_add(GTK_CONTAINER(hgrid), right_vbox);
1217
1218 paned = gtk_paned_new(GTK_ORIENTATION_HORIZONTAL);
1219 gtk_container_add(GTK_CONTAINER(page), top_vbox);
1220 gtk_container_add(GTK_CONTAINER(top_vbox), hgrid);
1221 gtk_container_add(GTK_CONTAINER(right_vbox), paned);
1222 gtk_container_add(GTK_CONTAINER(right_vbox), ingame_votebar);
1223
1224 /* Overview size designed for small displays (netbooks). */
1225 overview_canvas_store_width = OVERVIEW_CANVAS_STORE_WIDTH_NETBOOK;
1226 overview_canvas_store_height = OVERVIEW_CANVAS_STORE_HEIGHT_NETBOOK;
1227 } else {
1228 /* The window is divided into two vertical panes: overview +
1229 * + civinfo + unitinfo + main view, message window. */
1230 paned = gtk_paned_new(GTK_ORIENTATION_VERTICAL);
1231 gtk_container_add(GTK_CONTAINER(page), paned);
1232 gtk_paned_pack1(GTK_PANED(paned), top_vbox, TRUE, FALSE);
1233 gtk_container_add(GTK_CONTAINER(top_vbox), hgrid);
1234
1235 /* Overview size designed for big displays (desktops). */
1236 overview_canvas_store_width = OVERVIEW_CANVAS_STORE_WIDTH;
1237 overview_canvas_store_height = OVERVIEW_CANVAS_STORE_HEIGHT;
1238 }
1239
1240 /* this holds the overview canvas, production info, etc. */
1241 vgrid = gtk_grid_new();
1242 gtk_orientable_set_orientation(GTK_ORIENTABLE(vgrid),
1243 GTK_ORIENTATION_VERTICAL);
1244 gtk_grid_set_column_spacing(GTK_GRID(vgrid), 3);
1245 /* Put vgrid to the left of anything else in hgrid -- right_vbox is either
1246 * the chat/messages pane, or NULL which is OK */
1247 gtk_grid_attach_next_to(GTK_GRID(hgrid), vgrid, right_vbox,
1248 GTK_POS_LEFT, 1, 1);
1249
1250 /* Overview canvas */
1251 ahbox = detached_widget_new();
1252 gtk_widget_set_hexpand(ahbox, FALSE);
1253 gtk_widget_set_vexpand(ahbox, FALSE);
1254 gtk_container_add(GTK_CONTAINER(vgrid), ahbox);
1255 avbox = detached_widget_fill(ahbox);
1256
1257 overview_scrolled_window = gtk_scrolled_window_new(NULL, NULL);
1258 gtk_container_set_border_width(GTK_CONTAINER (overview_scrolled_window), 1);
1259 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW (overview_scrolled_window),
1260 GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC);
1261
1262 overview_canvas = gtk_drawing_area_new();
1263 gtk_widget_set_halign(overview_canvas, GTK_ALIGN_CENTER);
1264 gtk_widget_set_valign(overview_canvas, GTK_ALIGN_CENTER);
1265 gtk_widget_set_size_request(overview_canvas, overview_canvas_store_width,
1266 overview_canvas_store_height);
1267 gtk_widget_set_size_request(overview_scrolled_window, overview_canvas_store_width,
1268 overview_canvas_store_height);
1269 gtk_widget_set_hexpand(overview_canvas, TRUE);
1270 gtk_widget_set_vexpand(overview_canvas, TRUE);
1271
1272 gtk_widget_add_events(overview_canvas, GDK_EXPOSURE_MASK
1273 |GDK_BUTTON_PRESS_MASK
1274 |GDK_POINTER_MOTION_MASK);
1275 gtk_container_add(GTK_CONTAINER(avbox), overview_scrolled_window);
1276
1277 gtk_container_add(GTK_CONTAINER(overview_scrolled_window),
1278 overview_canvas);
1279
1280 g_signal_connect(overview_canvas, "draw",
1281 G_CALLBACK(overview_canvas_draw), NULL);
1282
1283 g_signal_connect(overview_canvas, "motion_notify_event",
1284 G_CALLBACK(move_overviewcanvas), NULL);
1285
1286 g_signal_connect(overview_canvas, "button_press_event",
1287 G_CALLBACK(butt_down_overviewcanvas), NULL);
1288
1289 /* The rest */
1290
1291 ahbox = detached_widget_new();
1292 gtk_container_add(GTK_CONTAINER(vgrid), ahbox);
1293 gtk_widget_set_hexpand(ahbox, FALSE);
1294 avbox = detached_widget_fill(ahbox);
1295 gtk_widget_set_vexpand(avbox, TRUE);
1296 gtk_widget_set_valign(avbox, GTK_ALIGN_FILL);
1297
1298 /* Info on player's civilization, when game is running. */
1299 frame = gtk_frame_new("");
1300 gtk_container_add(GTK_CONTAINER(avbox), frame);
1301
1302 main_frame_civ_name = frame;
1303
1304 vgrid = gtk_grid_new();
1305 gtk_orientable_set_orientation(GTK_ORIENTABLE(vgrid),
1306 GTK_ORIENTATION_VERTICAL);
1307 gtk_container_add(GTK_CONTAINER(frame), vgrid);
1308 gtk_widget_set_hexpand(vgrid, TRUE);
1309
1310 ebox = gtk_event_box_new();
1311 gtk_widget_add_events(ebox, GDK_BUTTON_PRESS_MASK);
1312 gtk_event_box_set_visible_window(GTK_EVENT_BOX(ebox), FALSE);
1313 g_signal_connect(ebox, "button_press_event",
1314 G_CALLBACK(show_info_popup), NULL);
1315 gtk_container_add(GTK_CONTAINER(vgrid), ebox);
1316
1317 label = gtk_label_new(NULL);
1318 gtk_widget_set_halign(label, GTK_ALIGN_START);
1319 gtk_widget_set_valign(label, GTK_ALIGN_CENTER);
1320 gtk_widget_set_margin_start(label, 2);
1321 gtk_widget_set_margin_end(label, 2);
1322 gtk_widget_set_margin_top(label, 2);
1323 gtk_widget_set_margin_bottom(label, 2);
1324 gtk_container_add(GTK_CONTAINER(ebox), label);
1325 main_label_info = label;
1326
1327 /* Production status */
1328 table = gtk_grid_new();
1329 gtk_widget_set_halign(table, GTK_ALIGN_CENTER);
1330 gtk_grid_set_column_homogeneous(GTK_GRID(table), TRUE);
1331 gtk_container_add(GTK_CONTAINER(avbox), table);
1332
1333 /* Citizens for taxrates */
1334 ebox = gtk_event_box_new();
1335 gtk_event_box_set_visible_window(GTK_EVENT_BOX(ebox), FALSE);
1336 gtk_grid_attach(GTK_GRID(table), ebox, 0, 0, 10, 1);
1337 econ_ebox = ebox;
1338
1339 table2 = gtk_grid_new();
1340 gtk_container_add(GTK_CONTAINER(ebox), table2);
1341
1342 for (i = 0; i < 10; i++) {
1343 ebox = gtk_event_box_new();
1344 gtk_event_box_set_visible_window(GTK_EVENT_BOX(ebox), FALSE);
1345 gtk_widget_add_events(ebox, GDK_BUTTON_PRESS_MASK);
1346
1347 gtk_grid_attach(GTK_GRID(table2), ebox, i, 0, 1, 1);
1348
1349 g_signal_connect(ebox, "button_press_event",
1350 G_CALLBACK(taxrates_callback), GINT_TO_POINTER(i));
1351
1352 spr = i < 5 ? get_tax_sprite(tileset, O_SCIENCE) : get_tax_sprite(tileset, O_GOLD);
1353 econ_label[i] = gtk_image_new_from_surface(spr->surface);
1354 gtk_container_add(GTK_CONTAINER(ebox), econ_label[i]);
1355 }
1356
1357 /* Science, environmental, govt, timeout */
1358 spr = client_research_sprite();
1359 if (spr != NULL) {
1360 bulb_label = gtk_image_new_from_surface(spr->surface);
1361 } else {
1362 bulb_label = gtk_image_new();
1363 }
1364
1365 spr = client_warming_sprite();
1366 if (spr != NULL) {
1367 sun_label = gtk_image_new_from_surface(spr->surface);
1368 } else {
1369 sun_label = gtk_image_new();
1370 }
1371
1372 spr = client_cooling_sprite();
1373 if (spr != NULL) {
1374 flake_label = gtk_image_new_from_surface(spr->surface);
1375 } else {
1376 flake_label = gtk_image_new();
1377 }
1378
1379 spr = client_government_sprite();
1380 if (spr != NULL) {
1381 government_label = gtk_image_new_from_surface(spr->surface);
1382 } else {
1383 government_label = gtk_image_new();
1384 }
1385
1386 for (i = 0; i < 4; i++) {
1387 GtkWidget *w;
1388
1389 ebox = gtk_event_box_new();
1390 gtk_event_box_set_visible_window(GTK_EVENT_BOX(ebox), FALSE);
1391
1392 switch (i) {
1393 case 0:
1394 w = bulb_label;
1395 bulb_ebox = ebox;
1396 break;
1397 case 1:
1398 w = sun_label;
1399 sun_ebox = ebox;
1400 break;
1401 case 2:
1402 w = flake_label;
1403 flake_ebox = ebox;
1404 break;
1405 default:
1406 case 3:
1407 w = government_label;
1408 government_ebox = ebox;
1409 break;
1410 }
1411
1412 gtk_widget_set_halign(w, GTK_ALIGN_START);
1413 gtk_widget_set_valign(w, GTK_ALIGN_START);
1414 gtk_widget_set_margin_start(w, 0);
1415 gtk_widget_set_margin_end(w, 0);
1416 gtk_widget_set_margin_top(w, 0);
1417 gtk_widget_set_margin_bottom(w, 0);
1418 gtk_container_add(GTK_CONTAINER(ebox), w);
1419 gtk_grid_attach(GTK_GRID(table), ebox, i, 1, 1, 1);
1420 }
1421
1422 timeout_label = gtk_label_new("");
1423
1424 frame = gtk_frame_new(NULL);
1425 gtk_grid_attach(GTK_GRID(table), frame, 4, 1, 6, 1);
1426 gtk_container_add(GTK_CONTAINER(frame), timeout_label);
1427
1428
1429 /* Turn done */
1430 turn_done_button = gtk_button_new_with_label(_("Turn Done"));
1431
1432 gtk_grid_attach(GTK_GRID(table), turn_done_button, 0, 2, 10, 1);
1433
1434 g_signal_connect(turn_done_button, "clicked",
1435 G_CALLBACK(end_turn_callback), NULL);
1436 update_turn_done_tooltip();
1437
1438 /* Selected unit status */
1439
1440 unit_info_box = gtk_grid_new();
1441 gtk_widget_set_hexpand(unit_info_box, FALSE);
1442 gtk_orientable_set_orientation(GTK_ORIENTABLE(unit_info_box),
1443 GTK_ORIENTATION_VERTICAL);
1444 gtk_container_add(GTK_CONTAINER(avbox), unit_info_box);
1445
1446 /* In edit mode the unit_info_box widget is replaced by the
1447 * editinfobox, so we need to add a ref here so that it is
1448 * not destroyed when removed from its container.
1449 * See editinfobox_refresh(). */
1450 g_object_ref(unit_info_box);
1451
1452 unit_info_frame = gtk_frame_new("");
1453 gtk_container_add(GTK_CONTAINER(unit_info_box), unit_info_frame);
1454
1455 sw = gtk_scrolled_window_new(NULL, NULL);
1456 gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw),
1457 GTK_SHADOW_OUT);
1458 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw),
1459 GTK_POLICY_AUTOMATIC, GTK_POLICY_NEVER);
1460 gtk_container_add(GTK_CONTAINER(unit_info_frame), sw);
1461
1462 label = gtk_label_new(NULL);
1463 gtk_widget_set_hexpand(label, TRUE);
1464 gtk_widget_set_halign(label, GTK_ALIGN_START);
1465 gtk_widget_set_valign(label, GTK_ALIGN_CENTER);
1466 gtk_widget_set_margin_start(label, 2);
1467 gtk_widget_set_margin_end(label, 2);
1468 gtk_widget_set_margin_top(label, 2);
1469 gtk_widget_set_margin_bottom(label, 2);
1470 gtk_container_add(GTK_CONTAINER(sw), label);
1471 unit_info_label = label;
1472
1473 hgrid2 = gtk_grid_new();
1474 gtk_container_add(GTK_CONTAINER(unit_info_box), hgrid2);
1475
1476 table = gtk_grid_new();
1477 g_object_set(table, "margin", 5, NULL);
1478 gtk_container_add(GTK_CONTAINER(hgrid2), table);
1479
1480 gtk_grid_set_row_spacing(GTK_GRID(table), 2);
1481 gtk_grid_set_column_spacing(GTK_GRID(table), 2);
1482
1483 unit_image_table = table;
1484
1485 /* Map canvas, editor toolbar, and scrollbars */
1486
1487 /* The top notebook containing the map view and dialogs. */
1488
1489 top_notebook = gtk_notebook_new();
1490 gtk_notebook_set_tab_pos(GTK_NOTEBOOK(top_notebook), GTK_POS_BOTTOM);
1491 gtk_notebook_set_scrollable(GTK_NOTEBOOK(top_notebook), TRUE);
1492
1493
1494 if (GUI_GTK_OPTION(small_display_layout)) {
1495 gtk_paned_pack1(GTK_PANED(paned), top_notebook, TRUE, FALSE);
1496 } else if (GUI_GTK_OPTION(message_chat_location) == GUI_GTK_MSGCHAT_MERGED) {
1497 right_vbox = gtk_grid_new();
1498 gtk_orientable_set_orientation(GTK_ORIENTABLE(right_vbox),
1499 GTK_ORIENTATION_VERTICAL);
1500
1501 gtk_container_add(GTK_CONTAINER(right_vbox), top_notebook);
1502 gtk_container_add(GTK_CONTAINER(right_vbox), ingame_votebar);
1503 gtk_container_add(GTK_CONTAINER(hgrid), right_vbox);
1504 } else {
1505 gtk_container_add(GTK_CONTAINER(hgrid), top_notebook);
1506 }
1507
1508 map_widget = gtk_grid_new();
1509
1510 vgrid = gtk_grid_new();
1511 gtk_orientable_set_orientation(GTK_ORIENTABLE(vgrid),
1512 GTK_ORIENTATION_VERTICAL);
1513 gtk_container_add(GTK_CONTAINER(vgrid), map_widget);
1514
1515 gtk_container_add(GTK_CONTAINER(vgrid), editgui_get_editbar()->widget);
1516 g_object_set(editgui_get_editbar()->widget, "margin", 4, NULL);
1517
1518 label = gtk_label_new(Q_("?noun:View"));
1519 gtk_notebook_append_page(GTK_NOTEBOOK(top_notebook), vgrid, label);
1520
1521 frame = gtk_frame_new(NULL);
1522 gtk_grid_attach(GTK_GRID(map_widget), frame, 0, 0, 1, 1);
1523
1524 map_canvas = gtk_drawing_area_new();
1525 gtk_widget_set_hexpand(map_canvas, TRUE);
1526 gtk_widget_set_vexpand(map_canvas, TRUE);
1527 gtk_widget_set_size_request(map_canvas, 300, 300);
1528 gtk_widget_set_can_focus(map_canvas, TRUE);
1529
1530#if 0
1531 setup_canvas_color_for_state(GTK_STATE_FLAG_NORMAL);
1532 setup_canvas_color_for_state(GTK_STATE_FLAG_ACTIVE);
1533 setup_canvas_color_for_state(GTK_STATE_FLAG_PRELIGHT);
1534 setup_canvas_color_for_state(GTK_STATE_FLAG_SELECTED);
1535 setup_canvas_color_for_state(GTK_STATE_FLAG_INSENSITIVE);
1536 setup_canvas_color_for_state(GTK_STATE_FLAG_INCONSISTENT);
1537 setup_canvas_color_for_state(GTK_STATE_FLAG_FOCUSED);
1538 setup_canvas_color_for_state(GTK_STATE_FLAG_BACKDROP);
1539#endif /* 0 */
1540
1541 gtk_widget_add_events(map_canvas, GDK_EXPOSURE_MASK
1542 |GDK_BUTTON_PRESS_MASK
1543 |GDK_BUTTON_RELEASE_MASK
1544 |GDK_KEY_PRESS_MASK
1545 |GDK_POINTER_MOTION_MASK
1546 |GDK_SCROLL_MASK);
1547
1548 gtk_container_add(GTK_CONTAINER(frame), map_canvas);
1549
1550 map_horizontal_scrollbar =
1551 gtk_scrollbar_new(GTK_ORIENTATION_HORIZONTAL, NULL);
1552 gtk_grid_attach(GTK_GRID(map_widget), map_horizontal_scrollbar, 0, 1, 1, 1);
1553
1554 map_vertical_scrollbar =
1555 gtk_scrollbar_new(GTK_ORIENTATION_VERTICAL, NULL);
1556 gtk_grid_attach(GTK_GRID(map_widget), map_vertical_scrollbar, 1, 0, 1, 1);
1557
1558 g_signal_connect(map_canvas, "draw",
1559 G_CALLBACK(map_canvas_draw), NULL);
1560
1561 g_signal_connect(map_canvas, "configure_event",
1562 G_CALLBACK(map_canvas_configure), NULL);
1563
1564 g_signal_connect(map_canvas, "motion_notify_event",
1565 G_CALLBACK(move_mapcanvas), NULL);
1566
1567 g_signal_connect(toplevel, "enter_notify_event",
1568 G_CALLBACK(leave_mapcanvas), NULL);
1569
1570 g_signal_connect(map_canvas, "button_press_event",
1571 G_CALLBACK(butt_down_mapcanvas), NULL);
1572
1573 g_signal_connect(map_canvas, "button_release_event",
1574 G_CALLBACK(butt_release_mapcanvas), NULL);
1575
1576 g_signal_connect(map_canvas, "scroll_event",
1577 G_CALLBACK(mouse_scroll_mapcanvas), NULL);
1578
1579 g_signal_connect(toplevel, "key_press_event",
1580 G_CALLBACK(toplevel_key_press_handler), NULL);
1581
1582 g_signal_connect(toplevel, "key_release_event",
1583 G_CALLBACK(toplevel_key_release_handler), NULL);
1584
1585 /* *** The message window -- this is a detachable widget *** */
1586
1587 if (GUI_GTK_OPTION(message_chat_location) == GUI_GTK_MSGCHAT_MERGED) {
1588 bottom_hpaned = paned;
1589 right_notebook = bottom_notebook = top_notebook;
1590 } else {
1591 GtkWidget *hpaned;
1592
1593 dtach_lowbox = detached_widget_new();
1594 gtk_paned_pack2(GTK_PANED(paned), dtach_lowbox, FALSE, TRUE);
1595 avbox = detached_widget_fill(dtach_lowbox);
1596
1597 vgrid = gtk_grid_new();
1598 gtk_orientable_set_orientation(GTK_ORIENTABLE(vgrid),
1599 GTK_ORIENTATION_VERTICAL);
1600 if (!GUI_GTK_OPTION(small_display_layout)) {
1601 gtk_container_add(GTK_CONTAINER(vgrid), ingame_votebar);
1602 }
1603 gtk_container_add(GTK_CONTAINER(avbox), vgrid);
1604
1605 if (GUI_GTK_OPTION(small_display_layout)) {
1606 hpaned = gtk_paned_new(GTK_ORIENTATION_VERTICAL);
1607 } else {
1608 hpaned = gtk_paned_new(GTK_ORIENTATION_HORIZONTAL);
1609 }
1610 gtk_container_add(GTK_CONTAINER(vgrid), hpaned);
1611 g_object_set(hpaned, "margin", 4, NULL);
1612 bottom_hpaned = hpaned;
1613
1614 bottom_notebook = gtk_notebook_new();
1615 gtk_notebook_set_tab_pos(GTK_NOTEBOOK(bottom_notebook), GTK_POS_TOP);
1616 gtk_notebook_set_scrollable(GTK_NOTEBOOK(bottom_notebook), TRUE);
1617 gtk_paned_pack1(GTK_PANED(hpaned), bottom_notebook, TRUE, TRUE);
1618
1619 right_notebook = gtk_notebook_new();
1620 g_object_ref(right_notebook);
1621 gtk_notebook_set_tab_pos(GTK_NOTEBOOK(right_notebook), GTK_POS_TOP);
1622 gtk_notebook_set_scrollable(GTK_NOTEBOOK(right_notebook), TRUE);
1623 g_signal_connect(right_notebook, "button-release-event",
1624 G_CALLBACK(right_notebook_button_release), NULL);
1625 if (GUI_GTK_OPTION(message_chat_location) == GUI_GTK_MSGCHAT_SPLIT) {
1626 gtk_paned_pack2(GTK_PANED(hpaned), right_notebook, TRUE, TRUE);
1627 }
1628 }
1629
1630 vgrid = gtk_grid_new();
1631 gtk_orientable_set_orientation(GTK_ORIENTABLE(vgrid),
1632 GTK_ORIENTATION_VERTICAL);
1633
1634 sw = gtk_scrolled_window_new(NULL, NULL);
1635 gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(sw),
1636 GTK_SHADOW_ETCHED_IN);
1637 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(sw), GTK_POLICY_AUTOMATIC,
1638 GTK_POLICY_ALWAYS);
1639 gtk_container_add(GTK_CONTAINER(vgrid), sw);
1640
1641 label = gtk_label_new(_("Chat"));
1642 gtk_notebook_append_page(GTK_NOTEBOOK(bottom_notebook), vgrid, label);
1643
1644 text = gtk_text_view_new_with_buffer(message_buffer);
1645 gtk_widget_set_hexpand(text, TRUE);
1646 gtk_widget_set_vexpand(text, TRUE);
1647 set_message_buffer_view_link_handlers(text);
1648 gtk_text_view_set_editable(GTK_TEXT_VIEW(text), FALSE);
1649 gtk_container_add(GTK_CONTAINER(sw), text);
1650 g_signal_connect(text, "size-allocate",
1651 G_CALLBACK(main_message_area_size_allocate), NULL);
1652
1653 gtk_widget_set_name(text, "chatline");
1654
1655 gtk_text_view_set_wrap_mode(GTK_TEXT_VIEW(text), GTK_WRAP_WORD);
1656 gtk_widget_realize(text);
1657 gtk_text_view_set_left_margin(GTK_TEXT_VIEW(text), 5);
1658
1659 main_message_area = GTK_TEXT_VIEW(text);
1660 if (dtach_lowbox != NULL) {
1661 g_object_set_data(G_OBJECT(dtach_lowbox), "hide-over-reparent", main_message_area);
1662 }
1663
1664 chat_welcome_message(TRUE);
1665
1666 /* the chat line */
1667 view = inputline_toolkit_view_new();
1668 gtk_container_add(GTK_CONTAINER(vgrid), view);
1669 g_object_set(view, "margin", 3, NULL);
1670
1671 button = gtk_check_button_new_with_label(_("Allies Only"));
1672 gtk_widget_set_focus_on_click(button, FALSE);
1673 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button),
1674 GUI_GTK_OPTION(allied_chat_only));
1675 g_signal_connect(button, "toggled",
1676 G_CALLBACK(allied_chat_button_toggled), NULL);
1677 inputline_toolkit_view_append_button(view, button);
1678 allied_chat_toggle_button = button;
1679
1680 button = gtk_button_new_with_label(_("Clear links"));
1681 g_signal_connect(button, "clicked",
1682 G_CALLBACK(link_marks_clear_all), NULL);
1683 inputline_toolkit_view_append_button(view, button);
1684
1685 /* Other things to take care of */
1686
1687 gtk_widget_show_all(gtk_bin_get_child(GTK_BIN(toplevel)));
1688
1689 if (GUI_GTK_OPTION(enable_tabs)) {
1690 meswin_dialog_popup(FALSE);
1691 }
1692
1693 gtk_notebook_set_current_page(GTK_NOTEBOOK(top_notebook), 0);
1694 gtk_notebook_set_current_page(GTK_NOTEBOOK(bottom_notebook), 0);
1695
1696 if (!GUI_GTK_OPTION(map_scrollbars)) {
1697 gtk_widget_hide(map_horizontal_scrollbar);
1698 gtk_widget_hide(map_vertical_scrollbar);
1699 }
1700}
1701
1702/**********************************************************************/
1705 static void g_log_to_freelog_cb(const gchar *log_domain,
1706 GLogLevelFlags log_level,
1707 const gchar *message,
1708 gpointer user_data)
1709{
1710 enum log_level fllvl = LOG_ERROR;
1711
1712 switch (log_level) {
1713 case G_LOG_LEVEL_DEBUG:
1714 fllvl = LOG_DEBUG;
1715 break;
1716 case G_LOG_LEVEL_WARNING:
1717 fllvl = LOG_WARN;
1718 break;
1719 default:
1720 break;
1721 }
1722
1723 if (log_domain != NULL) {
1724 log_base(fllvl, "%s: %s", log_domain, message);
1725 } else {
1726 log_base(fllvl, "%s", message);
1727 }
1728}
1729
1730/**********************************************************************/
1733 static GLogWriterOutput g_log_writer_to_freelog_cb(GLogLevelFlags log_level,
1734 const GLogField *fields,
1735 gsize n_fields,
1736 gpointer user_data)
1737{
1738 /* No need to have formatter of our own - let's use glib's default one. */
1739 gchar *out = g_log_writer_format_fields(log_level, fields, n_fields, FALSE);
1740
1741 g_log_to_freelog_cb(NULL, log_level, out, NULL);
1742
1743 return G_LOG_WRITER_HANDLED;
1744}
1745
1746/**********************************************************************/
1749 static void set_g_log_callback_domain(const char *domain)
1750{
1751 g_log_set_handler(domain,
1752 G_LOG_LEVEL_CRITICAL | G_LOG_LEVEL_ERROR | G_LOG_LEVEL_WARNING
1753 | G_LOG_LEVEL_MASK
1754 | G_LOG_FLAG_FATAL | G_LOG_FLAG_RECURSION,
1755 g_log_to_freelog_cb, NULL);
1756}
1757
1758/**********************************************************************/
1761 static void set_g_log_callbacks(void)
1762{
1763 /* Old API, still used by many log producers */
1764 g_log_set_default_handler(g_log_to_freelog_cb, NULL);
1765
1766 set_g_log_callback_domain("Gtk");
1767 set_g_log_callback_domain("Gdk");
1768 set_g_log_callback_domain("Glib");
1769
1770 /* glib >= 2.50 API */
1771 g_log_set_writer_func(g_log_writer_to_freelog_cb, NULL, NULL);
1772}
1773
1774/**********************************************************************/
1777 void ui_init(void)
1778{
1779 log_set_callback(log_callback_utf8);
1780 set_g_log_callbacks();
1781 set_frame_by_frame_animation();
1782}
1783
1784/**********************************************************************/
1787 int main(int argc, char **argv)
1788{
1789 return client_main(argc, argv, FALSE);
1790}
1791
1792/**********************************************************************/
1795 static void migrate_options_from_gtk2(void)
1796{
1797 log_normal(_("Migrating options from gtk2 to gtk3 client"));
1798
1799#define MIGRATE_OPTION(opt) gui_options.gui_gtk3_##opt = gui_options.gui_gtk2_##opt;
1800#define MIGRATE_STR_OPTION(opt) \
1801 strncpy(gui_options.gui_gtk3_##opt, gui_options.gui_gtk2_##opt, \
1802 sizeof(gui_options.gui_gtk3_##opt));
1803
1804 /* Default theme name is never migrated */
1805 /* 'fullscreen', 'small_display_layout', and 'message_chat_location'
1806 * not migrated, as (unlike Gtk2), Gtk3-client tries to pick better
1807 * defaults for these in fresh installations based on screen size (see
1808 * adjust_default_options()); so user is probably better served by
1809 * getting these adaptive defaults than whatever they had for Gtk2.
1810 * Since 'fullscreen' isn't migrated, we don't need to worry about
1811 * preserving gui_gtk2_migrated_from_2_5 either. */
1812 MIGRATE_OPTION(map_scrollbars);
1813 MIGRATE_OPTION(dialogs_on_top);
1814 MIGRATE_OPTION(show_task_icons);
1815 MIGRATE_OPTION(enable_tabs);
1816 MIGRATE_OPTION(show_chat_message_time);
1817 MIGRATE_OPTION(new_messages_go_to_top);
1818 MIGRATE_OPTION(show_message_window_buttons);
1819 MIGRATE_OPTION(metaserver_tab_first);
1820 MIGRATE_OPTION(allied_chat_only);
1821 MIGRATE_OPTION(mouse_over_map_focus);
1822 MIGRATE_OPTION(chatline_autocompletion);
1823 MIGRATE_OPTION(citydlg_xsize);
1824 MIGRATE_OPTION(citydlg_ysize);
1825 MIGRATE_OPTION(popup_tech_help);
1826
1827 MIGRATE_STR_OPTION(font_city_label);
1828 MIGRATE_STR_OPTION(font_notify_label);
1829 MIGRATE_STR_OPTION(font_spaceship_label);
1830 MIGRATE_STR_OPTION(font_help_label);
1831 MIGRATE_STR_OPTION(font_help_link);
1832 MIGRATE_STR_OPTION(font_help_text);
1833 MIGRATE_STR_OPTION(font_chatline);
1834 MIGRATE_STR_OPTION(font_beta_label);
1835 MIGRATE_STR_OPTION(font_small);
1836 MIGRATE_STR_OPTION(font_comment_label);
1837 MIGRATE_STR_OPTION(font_city_names);
1838 MIGRATE_STR_OPTION(font_city_productions);
1839 MIGRATE_STR_OPTION(font_reqtree_text);
1840
1841#undef MIGRATE_OPTION
1842#undef MIGRATE_STR_OPTION
1843
1844 gui_options.gui_gtk3_migrated_from_gtk2 = TRUE;
1845}
1846
1847/**********************************************************************/
1850 static void migrate_options_from_gtk3(void)
1851{
1852 log_normal(_("Migrating options from gtk3 to gtk3.22 client"));
1853
1854#define MIGRATE_OPTION(opt) GUI_GTK_OPTION(opt) = gui_options.gui_gtk3_##opt;
1855#define MIGRATE_STR_OPTION(opt) \
1856 strncpy(GUI_GTK_OPTION(opt), gui_options.gui_gtk3_##opt, \
1857 sizeof(GUI_GTK_OPTION(opt)));
1858
1859 /* Default theme name is never migrated */
1860
1861 /* Simulate gui-gtk3's migrate_options_from_2_5() */
1862 if (!gui_options.gui_gtk3_migrated_from_2_5) {
1863 log_normal(_("Migrating gtk3-client options from freeciv-2.5 options."));
1864 gui_options.gui_gtk3_fullscreen = gui_options.migrate_fullscreen;
1865 gui_options.gui_gtk3_migrated_from_2_5 = TRUE;
1866 }
1867
1868 MIGRATE_OPTION(fullscreen);
1869 MIGRATE_OPTION(map_scrollbars);
1870 MIGRATE_OPTION(dialogs_on_top);
1871 MIGRATE_OPTION(show_task_icons);
1872 MIGRATE_OPTION(enable_tabs);
1873 MIGRATE_OPTION(show_chat_message_time);
1874 MIGRATE_OPTION(new_messages_go_to_top);
1875 MIGRATE_OPTION(show_message_window_buttons);
1876 MIGRATE_OPTION(metaserver_tab_first);
1877 MIGRATE_OPTION(allied_chat_only);
1878 MIGRATE_OPTION(message_chat_location);
1879 MIGRATE_OPTION(small_display_layout);
1880 MIGRATE_OPTION(mouse_over_map_focus);
1881 MIGRATE_OPTION(chatline_autocompletion);
1882 MIGRATE_OPTION(citydlg_xsize);
1883 MIGRATE_OPTION(citydlg_ysize);
1884 MIGRATE_OPTION(popup_tech_help);
1885
1886 MIGRATE_STR_OPTION(font_city_label);
1887 MIGRATE_STR_OPTION(font_notify_label);
1888 MIGRATE_STR_OPTION(font_spaceship_label);
1889 MIGRATE_STR_OPTION(font_help_label);
1890 MIGRATE_STR_OPTION(font_help_link);
1891 MIGRATE_STR_OPTION(font_help_text);
1892 MIGRATE_STR_OPTION(font_chatline);
1893 MIGRATE_STR_OPTION(font_beta_label);
1894 MIGRATE_STR_OPTION(font_small);
1895 MIGRATE_STR_OPTION(font_comment_label);
1896 MIGRATE_STR_OPTION(font_city_names);
1897 MIGRATE_STR_OPTION(font_city_productions);
1898 MIGRATE_STR_OPTION(font_reqtree_text);
1899
1900#undef MIGRATE_OPTION
1901#undef MIGRATE_STR_OPTION
1902
1903 GUI_GTK_OPTION(migrated_from_gtk3) = TRUE;
1904}
1905
1906/**********************************************************************/
1909 int ui_main(int argc, char **argv)
1910{
1911 PangoFontDescription *toplevel_font_name;
1912 guint sig;
1913
1914 if (parse_options(argc, argv)) {
1915 char window_name[1024];
1916
1917 /* The locale has already been set in init_nls() and the windows-specific
1918 * locale logic in gtk_init() causes problems with zh_CN (see PR#39475) */
1919 gtk_disable_setlocale();
1920
1921 /* GTK withdraw gtk options. Process GTK arguments */
1922 if (!gtk_init_check(&argc, &argv)) {
1923 log_fatal(_("Failed to open graphical mode."));
1924 return EXIT_FAILURE;
1925 }
1926
1927 help_system_init();
1928
1929 dlg_tab_provider_prepare();
1930
1931 toplevel = gtk_window_new(GTK_WINDOW_TOPLEVEL);
1932 gtk_window_set_position(GTK_WINDOW(toplevel), GTK_WIN_POS_CENTER);
1933 if (vmode.width > 0 && vmode.height > 0) {
1934 gtk_window_resize(GTK_WINDOW(toplevel), vmode.width, vmode.height);
1935 }
1936 g_signal_connect(toplevel, "key_press_event",
1937 G_CALLBACK(toplevel_handler), NULL);
1938
1939 g_signal_connect(toplevel, "focus_out_event",
1940 G_CALLBACK(fc_lost_focus), NULL);
1941 g_signal_connect(toplevel, "focus_in_event",
1942 G_CALLBACK(fc_gained_focus), NULL);
1943
1944 gtk_window_set_role(GTK_WINDOW(toplevel), "toplevel");
1945 gtk_widget_realize(toplevel);
1946 gtk_widget_set_name(toplevel, "Freeciv");
1947 root_window = gtk_widget_get_window(toplevel);
1948
1949 if (gui_options.first_boot) {
1950 adjust_default_options();
1951 /* We're using fresh defaults for this version of this client,
1952 * so prevent any future migrations from other clients / versions */
1953 GUI_GTK_OPTION(migrated_from_gtk3) = TRUE;
1954 /* Avoid also marking gtk3 as migrated, so that it can have its own
1955 * run of its adjust_default_options() if it is ever run (as a
1956 * side effect of Gtk2->Gtk3 migration). */
1957 } else {
1958 if (!GUI_GTK_OPTION(migrated_from_gtk3)) {
1959 if (!gui_options.gui_gtk3_migrated_from_gtk2) {
1960 migrate_options_from_gtk2();
1961 /* We want a fresh look at screen-size-related options after Gtk2 */
1962 adjust_default_options();
1963 /* We don't ever want to consider pre-2.6 fullscreen option again
1964 * (even for gui-gtk3) */
1965 gui_options.gui_gtk3_migrated_from_2_5 = TRUE;
1966 }
1967 migrate_options_from_gtk3();
1968 }
1969 }
1970
1971 if (GUI_GTK_OPTION(fullscreen)) {
1972 gtk_window_fullscreen(GTK_WINDOW(toplevel));
1973 }
1974
1975 fc_snprintf(window_name, sizeof(window_name), _("Freeciv (%s)"), GUI_NAME_SHORT);
1976 gtk_window_set_title(GTK_WINDOW(toplevel), window_name);
1977
1978 g_signal_connect(toplevel, "delete_event",
1979 G_CALLBACK(quit_dialog_callback), NULL);
1980
1981 /* Disable GTK+ cursor key focus movement */
1982 sig = g_signal_lookup("focus", GTK_TYPE_WIDGET);
1983 g_signal_handlers_disconnect_matched(toplevel, G_SIGNAL_MATCH_ID, sig,
1984 0, 0, 0, 0);
1985 g_signal_connect(toplevel, "focus", G_CALLBACK(toplevel_focus), NULL);
1986
1987 options_iterate(client_optset, poption) {
1988 if (OT_FONT == option_type(poption)) {
1989 /* Force to call the appropriate callback. */
1990 option_changed(poption);
1991 }
1992 } options_iterate_end;
1993
1994 toplevel_font_name = pango_context_get_font_description(
1995 gtk_widget_get_pango_context(toplevel));
1996
1997 if (NULL == city_names_style) {
1998 city_names_style = pango_font_description_copy(toplevel_font_name);
1999 log_error("city_names_style should have been set by options.");
2000 }
2001 if (NULL == city_productions_style) {
2002 city_productions_style = pango_font_description_copy(toplevel_font_name);
2003 log_error("city_productions_style should have been set by options.");
2004 }
2005 if (NULL == reqtree_text_style) {
2006 reqtree_text_style = pango_font_description_copy(toplevel_font_name);
2007 log_error("reqtree_text_style should have been set by options.");
2008 }
2009
2010 tileset_init(tileset);
2011 tileset_load_tiles(tileset);
2012
2013 /* Keep the icon of the executable on Windows (see PR#36491) */
2014#ifndef FREECIV_MSWINDOWS
2015 {
2016 GdkPixbuf *pixbuf = sprite_get_pixbuf(get_icon_sprite(tileset, ICON_FREECIV));
2017
2018 /* Only call this after tileset_load_tiles is called. */
2019 gtk_window_set_icon(GTK_WINDOW(toplevel), pixbuf);
2020 g_object_unref(pixbuf);
2021 }
2022#endif /* FREECIV_MSWINDOWS */
2023
2024 setup_widgets();
2025 load_cursors();
2026 cma_fe_init();
2027 diplomacy_dialog_init();
2028 luaconsole_dialog_init();
2029 happiness_dialog_init();
2030 citizens_dialog_init();
2031 intel_dialog_init();
2032 spaceship_dialog_init();
2033 chatline_init();
2034 init_mapcanvas_and_overview();
2035
2036 tileset_use_preferred_theme(tileset);
2037
2038 gtk_widget_show(toplevel);
2039
2040 /* Assumes toplevel showing */
2041 set_client_state(C_S_DISCONNECTED);
2042
2043 /* Assumes client_state is set */
2044 timer_id = g_timeout_add(TIMER_INTERVAL, timer_callback, NULL);
2045
2046 gui_up = TRUE;
2047 gtk_main();
2048 gui_up = FALSE;
2049
2050 destroy_server_scans();
2051 free_mapcanvas_and_overview();
2052 spaceship_dialog_done();
2053 intel_dialog_done();
2054 citizens_dialog_done();
2055 luaconsole_dialog_done();
2056 happiness_dialog_done();
2057 diplomacy_dialog_done();
2058 cma_fe_done();
2059 free_unit_table();
2060
2061 /* We have extra ref for unit_info_box that has protected
2062 * it from getting destroyed when editinfobox_refresh()
2063 * moves widgets around. Free that extra ref here. */
2064 g_object_unref(unit_info_box);
2065
2066 editgui_free();
2067 gtk_widget_destroy(toplevel_tabs);
2068 gtk_widget_destroy(toplevel);
2069 menus_free();
2070 message_buffer = NULL; /* Result of destruction of everything */
2071 tileset_free_tiles(tileset);
2072 }
2073
2074 return EXIT_SUCCESS;
2075}
2076
2077/**********************************************************************/
2080 bool is_gui_up(void)
2081{
2082 return gui_up;
2083}
2084
2085/**********************************************************************/
2088 void ui_exit(void)
2089{
2090 if (message_buffer != NULL) {
2091 g_object_unref(message_buffer);
2092 message_buffer = NULL;
2093 }
2094}
2095
2096/**********************************************************************/
2099 enum gui_type get_gui_type(void)
2100{
2101 return GUI_GTK3_22;
2102}
2103
2104/**********************************************************************/
2107 void sound_bell(void)
2108{
2109 gdk_display_beep(gdk_display_get_default());
2110}
2111
2112/**********************************************************************/
2118 void set_unit_icon(int idx, struct unit *punit)
2119{
2120 GtkWidget *w;
2121
2122 fc_assert_ret(idx >= -1 && idx < num_units_below);
2123
2124 if (idx == -1) {
2125 w = unit_image;
2126 unit_id_top = punit ? punit->id : 0;
2127 } else {
2128 w = unit_below_image[idx];
2129 unit_ids[idx] = punit ? punit->id : 0;
2130 }
2131
2132 if (!w) {
2133 return;
2134 }
2135
2136 if (punit) {
2137 put_unit_image(punit, GTK_IMAGE(w), -1);
2138 } else {
2139 gtk_image_clear(GTK_IMAGE(w));
2140 }
2141}
2142
2143/**********************************************************************/
2148 void set_unit_icons_more_arrow(bool onoff)
2149{
2150 static bool showing = FALSE;
2151
2152 if (!more_arrow_pixmap_button) {
2153 return;
2154 }
2155
2156 if (onoff && !showing) {
2157 gtk_widget_show(more_arrow_pixmap_button);
2158 showing = TRUE;
2159 } else if (!onoff && showing) {
2160 gtk_widget_hide(more_arrow_pixmap_button);
2161 showing = FALSE;
2162 }
2163}
2164
2165/**********************************************************************/
2171 void real_focus_units_changed(void)
2172{
2173 goto_dialog_focus_units_changed();
2174}
2175
2176/**********************************************************************/
2180 static gboolean select_unit_image_callback(GtkWidget *w, GdkEvent *ev,
2181 gpointer data)
2182{
2183 int i = GPOINTER_TO_INT(data);
2184 struct unit *punit;
2185
2186 if (i == -1) {
2187 punit = game_unit_by_number(unit_id_top);
2188 if (punit && unit_is_in_focus(punit)) {
2189 /* Clicking on the currently selected unit will center it. */
2190 center_tile_mapcanvas(unit_tile(punit));
2191 }
2192 return TRUE;
2193 }
2194
2195 if (unit_ids[i] == 0) /* no unit displayed at this place */
2196 return TRUE;
2197
2198 punit = game_unit_by_number(unit_ids[i]);
2199 if (NULL != punit && unit_owner(punit) == client.conn.playing) {
2200 /* Unit shouldn't be NULL but may be owned by an ally. */
2201 unit_focus_set(punit);
2202 }
2203
2204 return TRUE;
2205}
2206
2207/**********************************************************************/
2211 static gboolean select_more_arrow_pixmap_callback(GtkWidget *w, GdkEvent *ev,
2212 gpointer data)
2213{
2214 struct unit *punit = game_unit_by_number(unit_id_top);
2215
2216 if (punit) {
2217 unit_select_dialog_popup(unit_tile(punit));
2218 }
2219
2220 return TRUE;
2221}
2222
2223/**********************************************************************/
2226 static gboolean show_info_button_release(GtkWidget *w, GdkEventButton *ev,
2227 gpointer data)
2228{
2229 gtk_grab_remove(w);
2230 gdk_seat_ungrab(gdk_device_get_seat(ev->device));
2231 gtk_widget_destroy(w);
2232
2233 return FALSE;
2234}
2235
2236/**********************************************************************/
2239 static gboolean show_info_popup(GtkWidget *w, GdkEventButton *ev, gpointer data)
2240{
2241 if (ev->button == 1) {
2242 GtkWidget *p;
2243
2244 p = gtk_window_new(GTK_WINDOW_POPUP);
2245 gtk_container_set_border_width(GTK_CONTAINER(p), 4);
2246 gtk_window_set_transient_for(GTK_WINDOW(p), GTK_WINDOW(toplevel));
2247 gtk_window_set_position(GTK_WINDOW(p), GTK_WIN_POS_MOUSE);
2248
2249 gtk_widget_new(GTK_TYPE_LABEL, "GtkWidget::parent", p,
2250 "GtkLabel::label", get_info_label_text_popup(),
2251 "GtkWidget::visible", TRUE,
2252 NULL);
2253 gtk_widget_show(p);
2254
2255 gdk_seat_grab(gdk_device_get_seat(ev->device), gtk_widget_get_window(p),
2256 GDK_SEAT_CAPABILITY_ALL_POINTING,
2257 TRUE, NULL, (GdkEvent *)ev, NULL, NULL);
2258 gtk_grab_add(p);
2259
2260 g_signal_connect_after(p, "button_release_event",
2261 G_CALLBACK(show_info_button_release), NULL);
2262 }
2263
2264 return TRUE;
2265}
2266
2267/**********************************************************************/
2270 static void end_turn_callback(GtkWidget *w, gpointer data)
2271{
2272 gtk_widget_set_sensitive(turn_done_button, FALSE);
2273 user_ended_turn();
2274}
2275
2276/**********************************************************************/
2279 static gboolean get_net_input(GIOChannel *source, GIOCondition condition,
2280 gpointer data)
2281{
2282 input_from_server(g_io_channel_unix_get_fd(source));
2283
2284 return TRUE;
2285}
2286
2287/**********************************************************************/
2290 static void set_wait_for_writable_socket(struct connection *pc,
2291 bool socket_writable)
2292{
2293 static bool previous_state = FALSE;
2294
2295 fc_assert_ret(pc == &client.conn);
2296
2297 if (previous_state == socket_writable)
2298 return;
2299
2300 log_debug("set_wait_for_writable_socket(%d)", socket_writable);
2301
2302 g_source_remove(srv_id);
2303 srv_id = g_io_add_watch(srv_channel,
2304 G_IO_IN | (socket_writable ? G_IO_OUT : 0) | G_IO_ERR,
2305 get_net_input,
2306 NULL);
2307
2308 previous_state = socket_writable;
2309}
2310
2311/**********************************************************************/
2315 void add_net_input(int sock)
2316{
2317#ifdef FREECIV_MSWINDOWS
2318 srv_channel = g_io_channel_win32_new_socket(sock);
2319#else
2320 srv_channel = g_io_channel_unix_new(sock);
2321#endif
2322 srv_id = g_io_add_watch(srv_channel,
2323 G_IO_IN | G_IO_ERR,
2324 get_net_input,
2325 NULL);
2326 client.conn.notify_of_writable_data = set_wait_for_writable_socket;
2327}
2328
2329/**********************************************************************/
2333 void remove_net_input(void)
2334{
2335 g_source_remove(srv_id);
2336 g_io_channel_unref(srv_channel);
2337 gdk_window_set_cursor(root_window, NULL);
2338}
2339
2340/**********************************************************************/
2344 static void quit_dialog_response(GtkWidget *dialog, gint response)
2345{
2346 gtk_widget_destroy(dialog);
2347 if (response == GTK_RESPONSE_YES) {
2348 start_quitting();
2349 if (client.conn.used) {
2350 disconnect_from_server(FALSE);
2351 }
2352 quit_gtk_main();
2353 }
2354}
2355
2356/**********************************************************************/
2359 void quit_gtk_main(void)
2360{
2361 /* Quit gtk main loop. After this it will return to finish
2362 * ui_main() */
2363
2364 gtk_main_quit();
2365}
2366
2367/**********************************************************************/
2371 void popup_quit_dialog(void)
2372{
2373 static GtkWidget *dialog;
2374
2375 if (!dialog) {
2376 dialog = gtk_message_dialog_new(NULL,
2377 0,
2378 GTK_MESSAGE_WARNING,
2379 GTK_BUTTONS_YES_NO,
2380 _("Are you sure you want to quit?"));
2381 setup_dialog(dialog, toplevel);
2382
2383 gtk_window_set_position(GTK_WINDOW(dialog), GTK_WIN_POS_MOUSE);
2384
2385 g_signal_connect(dialog, "response",
2386 G_CALLBACK(quit_dialog_response), NULL);
2387 g_signal_connect(dialog, "destroy",
2388 G_CALLBACK(gtk_widget_destroyed), &dialog);
2389 }
2390
2391 gtk_window_present(GTK_WINDOW(dialog));
2392}
2393
2394/**********************************************************************/
2397 static gboolean quit_dialog_callback(void)
2398{
2399 popup_quit_dialog();
2400 /* Stop emission of event. */
2401 return TRUE;
2402}
2403
2404 struct callback {
2405 void (*callback)(void *data);
2406 void *data;
2407};
2408
2409/**********************************************************************/
2412 static gboolean idle_callback_wrapper(gpointer data)
2413{
2414 struct callback *cb = data;
2415
2416 (cb->callback)(cb->data);
2417 free(cb);
2418
2419 return FALSE;
2420}
2421
2422/**********************************************************************/
2427 void add_idle_callback(void (callback)(void *), void *data)
2428{
2429 struct callback *cb = fc_malloc(sizeof(*cb));
2430
2431 cb->callback = callback;
2432 cb->data = data;
2433 g_idle_add(idle_callback_wrapper, cb);
2434}
2435
2436/**********************************************************************/
2440 static void allied_chat_only_callback(struct option *poption)
2441{
2442 GtkWidget *button;
2443
2444 button = allied_chat_toggle_button;
2445 fc_assert_ret(button != NULL);
2446 fc_assert_ret(GTK_IS_TOGGLE_BUTTON(button));
2447
2448 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button),
2449 option_bool_get(poption));
2450}
2451
2452/**********************************************************************/
2455 void fullscreen_opt_refresh(struct option *poption)
2456{
2457 if (GUI_GTK_OPTION(fullscreen)) {
2458 gtk_window_fullscreen(GTK_WINDOW(toplevel));
2459 } else {
2460 gtk_window_unfullscreen(GTK_WINDOW(toplevel));
2461 }
2462}
2463
2464/**********************************************************************/
2467 static void apply_city_names_font(struct option *poption)
2468{
2469 gui_update_font_full(option_font_target(poption),
2470 option_font_get(poption),
2471 &city_names_style);
2472 update_city_descriptions();
2473}
2474
2475/**********************************************************************/
2478 static void apply_city_productions_font(struct option *poption)
2479{
2480 gui_update_font_full(option_font_target(poption),
2481 option_font_get(poption),
2482 &city_productions_style);
2483 update_city_descriptions();
2484}
2485
2486/**********************************************************************/
2489 static void apply_reqtree_text_font(struct option *poption)
2490{
2491 gui_update_font_full(option_font_target(poption),
2492 option_font_get(poption),
2493 &reqtree_text_style);
2494 science_report_dialog_redraw();
2495}
2496
2497/**********************************************************************/
2501 void options_extra_init(void)
2502{
2503 struct option *poption;
2504
2505#define option_var_set_callback(var, callback) \
2506 if ((poption = optset_option_by_name(client_optset, \
2507 GUI_GTK_OPTION_STR(var)))) { \
2508 option_set_changed_callback(poption, callback); \
2509 } else { \
2510 log_error("Didn't find option %s!", GUI_GTK_OPTION_STR(var)); \
2511 }
2512
2513 option_var_set_callback(allied_chat_only,
2514 allied_chat_only_callback);
2515 option_var_set_callback(fullscreen,
2516 fullscreen_opt_refresh);
2517
2518 option_var_set_callback(font_city_names,
2519 apply_city_names_font);
2520 option_var_set_callback(font_city_productions,
2521 apply_city_productions_font);
2522 option_var_set_callback(font_reqtree_text,
2523 apply_reqtree_text_font);
2524#undef option_var_set_callback
2525}
2526
2527/**********************************************************************/
2531 void refresh_chat_buttons(void)
2532{
2533 GtkWidget *button;
2534
2535 button = allied_chat_toggle_button;
2536 fc_assert_ret(button != NULL);
2537 fc_assert_ret(GTK_IS_TOGGLE_BUTTON(button));
2538
2539 /* Hide the "Allies Only" button for local games. */
2540 if (is_server_running()) {
2541 gtk_widget_hide(button);
2542 } else {
2543 gtk_widget_show(button);
2544 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button),
2545 GUI_GTK_OPTION(allied_chat_only));
2546 }
2547}
2548
2549/**********************************************************************/
2552 static void allied_chat_button_toggled(GtkToggleButton *button,
2553 gpointer user_data)
2554{
2555 GUI_GTK_OPTION(allied_chat_only) = gtk_toggle_button_get_active(button);
2556}
2557
2558/**********************************************************************/
2561 void insert_client_build_info(char *outbuf, size_t outlen)
2562{
2563 cat_snprintf(outbuf, outlen, _("\nBuilt against gtk+ %d.%d.%d, using %d.%d.%d"
2564 "\nBuilt against glib %d.%d.%d, using %d.%d.%d"),
2565 GTK_MAJOR_VERSION, GTK_MINOR_VERSION, GTK_MICRO_VERSION,
2566 gtk_get_major_version(), gtk_get_minor_version(), gtk_get_micro_version(),
2567 GLIB_MAJOR_VERSION, GLIB_MINOR_VERSION, GLIB_MICRO_VERSION,
2568 glib_major_version, glib_minor_version, glib_micro_version);
2569}
2570
2571/**********************************************************************/
2575 static bool monitor_size(GdkRectangle *rect_p)
2576{
2577 GdkDisplay *display;
2578 GdkMonitor *monitor;
2579
2580 display = gdk_display_get_default();
2581 if (!display) {
2582 return FALSE;
2583 }
2584
2585 monitor = gdk_display_get_primary_monitor(display);
2586 if (!monitor) {
2587 return FALSE;
2588 }
2589
2590 gdk_monitor_get_geometry(monitor, rect_p);
2591 return TRUE;
2592}
2593
2594/**********************************************************************/
2597 int screen_width(void)
2598{
2599 GdkRectangle rect;
2600
2601 if (vmode.width > 0) {
2602 return vmode.width;
2603 }
2604
2605 if (monitor_size(&rect)) {
2606 return rect.width;
2607 } else {
2608 return 0;
2609 }
2610}
2611
2612/**********************************************************************/
2615 int screen_height(void)
2616{
2617 GdkRectangle rect;
2618
2619 if (vmode.height > 0) {
2620 return vmode.height;
2621 }
2622
2623 if (monitor_size(&rect)) {
2624 return rect.height;
2625 } else {
2626 return 0;
2627 }
2628}
2629
2630/**********************************************************************/
2633 struct video_mode *resolution_request_get(void)
2634{
2635 if (vmode.width > 0 && vmode.height > 0) {
2636 return &vmode;
2637 }
2638
2639 return NULL;
2640}
2641
2642/**********************************************************************/
2645 static void adjust_default_options(void)
2646{
2647 int scr_height = screen_height();
2648
2649 if (scr_height > 0) {
2650 /* Adjust these options only if we do know the screen height. */
2651
2652 if (scr_height <= 480) {
2653 /* Freeciv is practically unusable outside fullscreen mode in so
2654 * small display */
2655 log_verbose("Changing default to fullscreen due to very small screen");
2656 GUI_GTK_OPTION(fullscreen) = TRUE;
2657 }
2658 if (scr_height < 1024) {
2659 /* This is a small display */
2660 log_verbose("Defaulting to small widget layout due to small screen");
2661 GUI_GTK_OPTION(small_display_layout) = TRUE;
2662 log_verbose("Defaulting to merged messages/chat due to small screen");
2663 GUI_GTK_OPTION(message_chat_location) = GUI_GTK_MSGCHAT_MERGED;
2664 }
2665 }
2666}
audio_pause
void audio_pause(void)
Definition audio.c:606
audio_resume
void audio_resume(void)
Definition audio.c:614
audio.h
width
struct canvas int int struct sprite int int int width
Definition canvas_g.h:44
chat_welcome_message
void chat_welcome_message(bool gui_has_copying_mitem)
Definition chatline_common.c:177
client_is_observer
bool client_is_observer(void)
Definition client_main.c:1083
real_timer_callback
double real_timer_callback(void)
Definition client_main.c:1182
client_main
int client_main(int argc, char *argv[], bool postpone_tileset)
Definition client_main.c:351
user_ended_turn
void user_ended_turn(void)
Definition client_main.c:798
client
struct civclient client
Definition client_main.c:150
start_quitting
void start_quitting(void)
Definition client_main.c:1644
set_client_state
void set_client_state(enum client_states newstate)
Definition client_main.c:844
can_client_change_view
bool can_client_change_view(void)
Definition client_main.c:1312
client_main.h
TIMER_INTERVAL
#define TIMER_INTERVAL
Definition client_main.h:30
C_S_DISCONNECTED
@ C_S_DISCONNECTED
Definition client_main.h:45
buy_production_in_selected_cities
void buy_production_in_selected_cities(void)
Definition climisc.c:1305
client_warming_sprite
struct sprite * client_warming_sprite(void)
Definition climisc.c:377
client_cooling_sprite
struct sprite * client_cooling_sprite(void)
Definition climisc.c:394
client_research_sprite
struct sprite * client_research_sprite(void)
Definition climisc.c:354
client_government_sprite
struct sprite * client_government_sprite(void)
Definition climisc.c:412
climisc.h
disconnect_from_server
void disconnect_from_server(bool leaving_sound)
Definition clinet.c:306
input_from_server
void input_from_server(int fd)
Definition clinet.c:411
clinet.h
get_color
struct color * get_color(const struct tileset *t, enum color_std stdcolor)
Definition colors_common.c:100
incite_cost
char * incite_cost
Definition comments.c:74
is_server_running
bool is_server_running(void)
Definition connectdlg_common.c:124
connectdlg_common.h
key_recall_previous_focus_unit
void key_recall_previous_focus_unit(void)
Definition control.c:3291
unit_is_in_focus
bool unit_is_in_focus(const struct unit *punit)
Definition control.c:383
key_cancel_action
void key_cancel_action(void)
Definition control.c:3229
num_units_below
int num_units_below
Definition control.c:76
unit_focus_set
void unit_focus_set(struct unit *punit)
Definition control.c:501
get_units_in_focus
struct unit_list * get_units_in_focus(void)
Definition control.c:177
key_end_turn
void key_end_turn(void)
Definition control.c:3283
update_unit_pix_label
void update_unit_pix_label(struct unit_list *punitlist)
Definition control.c:967
key_unit_move
void key_unit_move(enum direction8 gui_dir)
Definition control.c:3312
hover_state
enum cursor_hover_state hover_state
Definition control.c:89
head_of_units_in_focus
struct unit * head_of_units_in_focus(void)
Definition control.c:405
get_num_units_in_focus
int get_num_units_in_focus(void)
Definition control.c:185
control_mouse_cursor
void control_mouse_cursor(struct tile *ptile)
Definition control.c:1189
key_center_capital
void key_center_capital(void)
Definition control.c:3266
control.h
MAX_NUM_UNITS_BELOW
#define MAX_NUM_UNITS_BELOW
Definition control.h:295
HOVER_NONE
@ HOVER_NONE
Definition control.h:26
dataio.h
punit
struct unit struct city struct unit struct tile struct extra_type const struct act_prob *act_probs int actor_unit_id struct unit struct unit * punit
Definition dialogs_g.h:74
editor_is_active
bool editor_is_active(void)
Definition editor.c:346
editor.h
event
enum event_type event
Definition events.c:81
is_option
bool is_option(const char *option_name, char *option)
Definition fc_cmdline.c:112
get_option_malloc
char * get_option_malloc(const char *option_name, char **argv, int *i, int argc, bool gc)
Definition fc_cmdline.c:50
fc_cmdline.h
O_SCIENCE
@ O_SCIENCE
Definition fc_types.h:101
O_GOLD
@ O_GOLD
Definition fc_types.h:101
fciconv.h
fc_fprintf
void fc_fprintf(FILE *stream, const char *format,...) fc__attribute((__format__(__printf__
fcintl.h
Q_
#define Q_(String)
Definition fcintl.h:70
_
#define _(String)
Definition fcintl.h:67
featured_text.h
game_unit_by_number
struct unit * game_unit_by_number(int id)
Definition game.c:116
game.h
government.h
inputline_has_focus
bool inputline_has_focus(void)
Definition chatline.c:71
inputline_toolkit_view_append_button
void inputline_toolkit_view_append_button(GtkWidget *toolkit_view, GtkWidget *button)
Definition chatline.c:1292
inputline_toolkit_view_new
GtkWidget * inputline_toolkit_view_new(void)
Definition chatline.c:1270
set_message_buffer_view_link_handlers
void set_message_buffer_view_link_handlers(GtkWidget *view)
Definition chatline.c:744
inputline_is_visible
bool inputline_is_visible(void)
Definition chatline.c:87
chatline_init
void chatline_init(void)
Definition chatline.c:1302
inputline_grab_focus
void inputline_grab_focus(void)
Definition chatline.c:79
chatline_scroll_to_bottom
void chatline_scroll_to_bottom(bool delayed)
Definition chatline.c:1006
citizens_dialog_init
void citizens_dialog_init(void)
Definition citizensinfo.c:269
citizens_dialog_done
void citizens_dialog_done(void)
Definition citizensinfo.c:277
cma_fe_init
void cma_fe_init(void)
Definition cma_fe.c:88
cma_fe_done
void cma_fe_done(void)
Definition cma_fe.c:96
unit_select_dialog_popup
void unit_select_dialog_popup(struct tile *ptile)
Definition dialogs.c:377
taxrates_callback
gboolean taxrates_callback(GtkWidget *w, GdkEventButton *ev, gpointer data)
Definition dialogs.c:1425
diplomacy_dialog_init
void diplomacy_dialog_init(void)
Definition diplodlg.c:1204
diplomacy_dialog_done
void diplomacy_dialog_done(void)
Definition diplodlg.c:1213
handle_edit_key_release
gboolean handle_edit_key_release(GdkEventKey *ev)
Definition editgui.c:1780
handle_edit_key_press
gboolean handle_edit_key_press(GdkEventKey *ev)
Definition editgui.c:1662
editgui_create_widgets
void editgui_create_widgets(void)
Definition editgui.c:1822
editgui_get_editbar
struct editbar * editgui_get_editbar(void)
Definition editgui.c:1788
editgui_free
void editgui_free(void)
Definition editgui.c:1835
goto_dialog_focus_units_changed
void goto_dialog_focus_units_changed(void)
Definition gotodlg.c:541
source
static GtkWidget * source
Definition gotodlg.c:58
load_cursors
void load_cursors(void)
Definition graphics.c:78
map_vertical_scrollbar
GtkWidget * map_vertical_scrollbar
Definition gui_main.c:109
ui_main
int ui_main(int argc, char **argv)
Definition gui_main.c:1909
client_string
const char * client_string
Definition gui_main.c:105
message_buffer
GtkTextBuffer * message_buffer
Definition gui_main.c:178
quit_dialog_response
static void quit_dialog_response(GtkWidget *dialog, gint response)
Definition gui_main.c:2344
real_focus_units_changed
void real_focus_units_changed(void)
Definition gui_main.c:2171
set_unit_icons_more_arrow
void set_unit_icons_more_arrow(bool onoff)
Definition gui_main.c:2148
print_usage
static void print_usage(void)
Definition gui_main.c:265
OVERVIEW_CANVAS_STORE_WIDTH_NETBOOK
#define OVERVIEW_CANVAS_STORE_WIDTH_NETBOOK
Definition gui_main.c:116
option_var_set_callback
#define option_var_set_callback(var, callback)
select_unit_image_callback
static gboolean select_unit_image_callback(GtkWidget *w, GdkEvent *ev, gpointer data)
Definition gui_main.c:2180
quit_dialog_callback
static gboolean quit_dialog_callback(void)
Definition gui_main.c:2397
srv_channel
static GIOChannel * srv_channel
Definition gui_main.c:182
main_label_info
GtkWidget * main_label_info
Definition gui_main.c:138
monitor_size
static bool monitor_size(GdkRectangle *rect_p)
Definition gui_main.c:2575
bottom_notebook
GtkWidget * bottom_notebook
Definition gui_main.c:129
unit_info_label
GtkWidget * unit_info_label
Definition gui_main.c:151
timer_callback
static gboolean timer_callback(gpointer data)
Definition gui_main.c:242
resolution_request_get
struct video_mode * resolution_request_get(void)
Definition gui_main.c:2633
set_unit_icon
void set_unit_icon(int idx, struct unit *punit)
Definition gui_main.c:2118
unit_ids
static int unit_ids[MAX_NUM_UNITS_BELOW]
Definition gui_main.c:175
timeout_label
GtkWidget * timeout_label
Definition gui_main.c:148
gui_up
static bool gui_up
Definition gui_main.c:186
srv_id
static guint srv_id
Definition gui_main.c:183
mouse_scroll_mapcanvas
static gboolean mouse_scroll_mapcanvas(GtkWidget *w, GdkEventScroll *ev)
Definition gui_main.c:706
city_productions_style
PangoFontDescription * city_productions_style
Definition gui_main.c:134
overview_scrolled_window
GtkWidget * overview_scrolled_window
Definition gui_main.c:112
more_arrow_pixmap
static GtkWidget * more_arrow_pixmap
Definition gui_main.c:170
detached_widget_fill
static GtkWidget * detached_widget_fill(GtkWidget *tearbox)
Definition gui_main.c:868
enable_menus
void enable_menus(bool enable)
Definition gui_main.c:1074
select_more_arrow_pixmap_callback
static gboolean select_more_arrow_pixmap_callback(GtkWidget *w, GdkEvent *ev, gpointer data)
Definition gui_main.c:2211
top_notebook
GtkWidget * top_notebook
Definition gui_main.c:129
propagate_keypress
static gboolean propagate_keypress(GtkWidget *w, GdkEvent *ev)
Definition gui_main.c:801
MIGRATE_STR_OPTION
#define MIGRATE_STR_OPTION(opt)
econ_ebox
GtkWidget * econ_ebox
Definition gui_main.c:155
unit_info_box
GtkWidget * unit_info_box
Definition gui_main.c:152
fc_lost_focus
gboolean fc_lost_focus(GtkWidget *w, GdkEventKey *ev, gpointer data)
Definition gui_main.c:758
ui_exit
void ui_exit(void)
Definition gui_main.c:2088
get_gui_type
enum gui_type get_gui_type(void)
Definition gui_main.c:2099
detached_widget_new
static GtkWidget * detached_widget_new(void)
Definition gui_main.c:857
cur_y
gint cur_y
Definition gui_main.c:184
main
int main(int argc, char **argv)
Definition gui_main.c:1787
fullscreen_opt_refresh
void fullscreen_opt_refresh(struct option *poption)
Definition gui_main.c:2455
main_message_area_size_allocate
static void main_message_area_size_allocate(GtkWidget *widget, GtkAllocation *allocation, gpointer data)
Definition gui_main.c:365
toplevel_handler
static gboolean toplevel_handler(GtkWidget *w, GdkEvent *ev, gpointer data)
Definition gui_main.c:399
ui_init
void ui_init(void)
Definition gui_main.c:1777
unit_below_image_button
static GtkWidget * unit_below_image_button[MAX_NUM_UNITS_BELOW]
Definition gui_main.c:169
free_unit_table
static void free_unit_table(void)
Definition gui_main.c:1017
idle_callback_wrapper
static gboolean idle_callback_wrapper(gpointer data)
Definition gui_main.c:2412
apply_city_names_font
static void apply_city_names_font(struct option *poption)
Definition gui_main.c:2467
apply_city_productions_font
static void apply_city_productions_font(struct option *poption)
Definition gui_main.c:2478
fc_gained_focus
gboolean fc_gained_focus(GtkWidget *w, GdkEventKey *ev, gpointer data)
Definition gui_main.c:768
unit_below_image
static GtkWidget * unit_below_image[MAX_NUM_UNITS_BELOW]
Definition gui_main.c:168
tearoff_destroy
static void tearoff_destroy(GtkWidget *w, gpointer data)
Definition gui_main.c:778
government_label
GtkWidget * government_label
Definition gui_main.c:147
sun_label
GtkWidget * sun_label
Definition gui_main.c:145
city_names_style
PangoFontDescription * city_names_style
Definition gui_main.c:133
refresh_chat_buttons
void refresh_chat_buttons(void)
Definition gui_main.c:2531
map_canvas_focus
gboolean map_canvas_focus(void)
Definition gui_main.c:382
turn_done_button
GtkWidget * turn_done_button
Definition gui_main.c:149
bottom_hpaned
static GtkWidget * bottom_hpaned
Definition gui_main.c:131
timer_id
static gint timer_id
Definition gui_main.c:181
main_menubar
static GtkWidget * main_menubar
Definition gui_main.c:164
screen_width
int screen_width(void)
Definition gui_main.c:2597
scroll_panel
GtkWidget * scroll_panel
Definition gui_main.c:141
end_turn_callback
static void end_turn_callback(GtkWidget *w, gpointer data)
Definition gui_main.c:2270
OVERVIEW_CANVAS_STORE_HEIGHT_NETBOOK
#define OVERVIEW_CANVAS_STORE_HEIGHT_NETBOOK
Definition gui_main.c:117
log_callback_utf8
static void log_callback_utf8(enum log_level level, const char *message, bool file_too)
Definition gui_main.c:230
add_idle_callback
void add_idle_callback(void(callback)(void *), void *data)
Definition gui_main.c:2427
show_info_popup
static gboolean show_info_popup(GtkWidget *w, GdkEventButton *ev, gpointer data)
Definition gui_main.c:2239
set_g_log_callbacks
static void set_g_log_callbacks(void)
Definition gui_main.c:1761
reset_unit_table
void reset_unit_table(void)
Definition gui_main.c:1045
key_press_map_canvas
static gboolean key_press_map_canvas(GtkWidget *w, GdkEventKey *ev, gpointer data)
Definition gui_main.c:423
unit_info_frame
GtkWidget * unit_info_frame
Definition gui_main.c:153
options_extra_init
void options_extra_init(void)
Definition gui_main.c:2501
top_vbox
GtkWidget * top_vbox
Definition gui_main.c:128
allied_chat_only_callback
static void allied_chat_only_callback(struct option *poption)
Definition gui_main.c:2440
root_window
GdkWindow * root_window
Definition gui_main.c:126
adjust_default_options
static void adjust_default_options(void)
Definition gui_main.c:2645
set_wait_for_writable_socket
static void set_wait_for_writable_socket(struct connection *pc, bool socket_writable)
Definition gui_main.c:2290
more_arrow_pixmap_button
static GtkWidget * more_arrow_pixmap_button
Definition gui_main.c:171
ahbox
GtkWidget * ahbox
Definition gui_main.c:140
apply_reqtree_text_font
static void apply_reqtree_text_font(struct option *poption)
Definition gui_main.c:2489
show_info_button_release
static gboolean show_info_button_release(GtkWidget *w, GdkEventButton *ev, gpointer data)
Definition gui_main.c:2226
is_gui_up
bool is_gui_up(void)
Definition gui_main.c:2080
toplevel_focus
static gboolean toplevel_focus(GtkWidget *w, GtkDirectionType arg)
Definition gui_main.c:338
reqtree_text_style
PangoFontDescription * reqtree_text_style
Definition gui_main.c:135
sun_ebox
GtkWidget * sun_ebox
Definition gui_main.c:157
bulb_ebox
GtkWidget * bulb_ebox
Definition gui_main.c:156
flake_label
GtkWidget * flake_label
Definition gui_main.c:146
g_log_to_freelog_cb
static void g_log_to_freelog_cb(const gchar *log_domain, GLogLevelFlags log_level, const gchar *message, gpointer user_data)
Definition gui_main.c:1705
avbox
GtkWidget * avbox
Definition gui_main.c:140
cur_x
gint cur_x
Definition gui_main.c:184
insert_client_build_info
void insert_client_build_info(char *outbuf, size_t outlen)
Definition gui_main.c:2561
unit_image_button
static GtkWidget * unit_image_button
Definition gui_main.c:167
unit_image_table
static GtkWidget * unit_image_table
Definition gui_main.c:165
right_notebook_button_release
static gboolean right_notebook_button_release(GtkWidget *widget, GdkEventButton *event)
Definition gui_main.c:1097
set_g_log_callback_domain
static void set_g_log_callback_domain(const char *domain)
Definition gui_main.c:1749
bulb_label
GtkWidget * bulb_label
Definition gui_main.c:144
overview_canvas
GtkWidget * overview_canvas
Definition gui_main.c:111
toplevel
GtkWidget * toplevel
Definition gui_main.c:125
setup_widgets
static void setup_widgets(void)
Definition gui_main.c:1149
OVERVIEW_CANVAS_STORE_WIDTH
#define OVERVIEW_CANVAS_STORE_WIDTH
Definition gui_main.c:118
toplevel_key_release_handler
static gboolean toplevel_key_release_handler(GtkWidget *w, GdkEventKey *ev, gpointer data)
Definition gui_main.c:604
remove_net_input
void remove_net_input(void)
Definition gui_main.c:2333
map_horizontal_scrollbar
GtkWidget * map_horizontal_scrollbar
Definition gui_main.c:108
map_canvas
GtkWidget * map_canvas
Definition gui_main.c:107
toplevel_key_press_handler
static gboolean toplevel_key_press_handler(GtkWidget *w, GdkEventKey *ev, gpointer data)
Definition gui_main.c:622
sound_bell
void sound_bell(void)
Definition gui_main.c:2107
migrate_options_from_gtk2
static void migrate_options_from_gtk2(void)
Definition gui_main.c:1795
econ_label
GtkWidget * econ_label[10]
Definition gui_main.c:143
government_ebox
GtkWidget * government_ebox
Definition gui_main.c:159
popup_quit_dialog
void popup_quit_dialog(void)
Definition gui_main.c:2371
migrate_options_from_gtk3
static void migrate_options_from_gtk3(void)
Definition gui_main.c:1850
gui_character_encoding
const char *const gui_character_encoding
Definition gui_main.c:161
unit_id_top
static int unit_id_top
Definition gui_main.c:174
get_net_input
static gboolean get_net_input(GIOChannel *source, GIOCondition condition, gpointer data)
Definition gui_main.c:2279
audio_paused
static bool audio_paused
Definition gui_main.c:188
more_arrow_pixmap_container
static GtkWidget * more_arrow_pixmap_container
Definition gui_main.c:172
map_widget
GtkWidget * map_widget
Definition gui_main.c:130
client_focus
static bool client_focus
Definition gui_main.c:189
right_notebook
GtkWidget * right_notebook
Definition gui_main.c:129
quit_gtk_main
void quit_gtk_main(void)
Definition gui_main.c:2359
allied_chat_button_toggled
static void allied_chat_button_toggled(GtkToggleButton *button, gpointer user_data)
Definition gui_main.c:2552
vmode
static struct video_mode vmode
Definition gui_main.c:191
add_net_input
void add_net_input(int sock)
Definition gui_main.c:2315
g_log_writer_to_freelog_cb
static GLogWriterOutput g_log_writer_to_freelog_cb(GLogLevelFlags log_level, const GLogField *fields, gsize n_fields, gpointer user_data)
Definition gui_main.c:1733
toplevel_tabs
GtkWidget * toplevel_tabs
Definition gui_main.c:127
allied_chat_toggle_button
static GtkWidget * allied_chat_toggle_button
Definition gui_main.c:179
flake_ebox
GtkWidget * flake_ebox
Definition gui_main.c:158
overview_canvas_store_width
int overview_canvas_store_width
Definition gui_main.c:122
update_turn_done_tooltip
void update_turn_done_tooltip(void)
Definition gui_main.c:1130
tearoff_callback
static void tearoff_callback(GtkWidget *b, gpointer data)
Definition gui_main.c:812
unit_image
static GtkWidget * unit_image
Definition gui_main.c:166
main_message_area
GtkTextView * main_message_area
Definition gui_main.c:177
overview_canvas_store_height
int overview_canvas_store_height
Definition gui_main.c:123
screen_height
int screen_height(void)
Definition gui_main.c:2615
parse_options
static bool parse_options(int argc, char **argv)
Definition gui_main.c:295
conn_box
GtkWidget * conn_box
Definition gui_main.c:140
OVERVIEW_CANVAS_STORE_HEIGHT
#define OVERVIEW_CANVAS_STORE_HEIGHT
Definition gui_main.c:120
main_frame_civ_name
GtkWidget * main_frame_civ_name
Definition gui_main.c:137
MIGRATE_OPTION
#define MIGRATE_OPTION(opt)
gui_use_transliteration
const bool gui_use_transliteration
Definition gui_main.c:162
populate_unit_image_table
static void populate_unit_image_table(void)
Definition gui_main.c:912
GUI_NAME_FULL
#define GUI_NAME_FULL
Definition gui_main.h:22
GUI_NAME_SHORT
#define GUI_NAME_SHORT
Definition gui_main.h:23
GUI_GTK_OPTION
#define GUI_GTK_OPTION(optname)
Definition gui_main.h:25
dlg_tab_provider_prepare
void dlg_tab_provider_prepare(void)
Definition gui_stuff.c:1155
setup_dialog
void setup_dialog(GtkWidget *shell, GtkWidget *parent)
Definition gui_stuff.c:287
gui_update_font_full
void gui_update_font_full(const char *font_name, const char *font_value, PangoFontDescription **font_desc)
Definition gui_stuff.c:1073
happiness_dialog_init
void happiness_dialog_init(void)
Definition happiness.c:86
happiness_dialog_done
void happiness_dialog_done(void)
Definition happiness.c:94
help_system_init
void help_system_init(void)
Definition helpdlg.c:157
intel_dialog_done
void intel_dialog_done(void)
Definition inteldlg.c:128
intel_dialog_init
void intel_dialog_init(void)
Definition inteldlg.c:119
luaconsole_dialog_init
void luaconsole_dialog_init(void)
Definition luaconsole.c:83
luaconsole_dialog_done
void luaconsole_dialog_done(void)
Definition luaconsole.c:101
butt_release_mapcanvas
gboolean butt_release_mapcanvas(GtkWidget *w, GdkEventButton *ev, gpointer data)
Definition mapctrl.c:221
move_overviewcanvas
gboolean move_overviewcanvas(GtkWidget *w, GdkEventMotion *ev, gpointer data)
Definition mapctrl.c:463
butt_down_overviewcanvas
gboolean butt_down_overviewcanvas(GtkWidget *w, GdkEventButton *ev, gpointer data)
Definition mapctrl.c:473
butt_down_mapcanvas
gboolean butt_down_mapcanvas(GtkWidget *w, GdkEventButton *ev, gpointer data)
Definition mapctrl.c:242
move_mapcanvas
gboolean move_mapcanvas(GtkWidget *w, GdkEventMotion *ev, gpointer data)
Definition mapctrl.c:406
leave_mapcanvas
gboolean leave_mapcanvas(GtkWidget *widget, GdkEventCrossing *event)
Definition mapctrl.c:435
update_city_descriptions
void update_city_descriptions(void)
Definition mapview.c:488
map_canvas_draw
gboolean map_canvas_draw(GtkWidget *w, cairo_t *cr, gpointer data)
Definition mapview.c:424
map_canvas_configure
gboolean map_canvas_configure(GtkWidget *w, GdkEventConfigure *ev, gpointer data)
Definition mapview.c:403
put_unit_image
void put_unit_image(struct unit *punit, GtkImage *p, int height)
Definition mapview.c:496
overview_canvas_draw
gboolean overview_canvas_draw(GtkWidget *w, cairo_t *cr, gpointer data)
Definition mapview.c:356
setup_menus
GtkWidget * setup_menus(GtkWidget *window)
Definition menu.c:2147
menus_free
void menus_free(void)
Definition menu.c:3215
meswin_dialog_popup
void meswin_dialog_popup(bool raise)
Definition messagewin.c:417
create_start_page
GtkWidget * create_start_page(void)
Definition pages.c:2607
create_network_page
GtkWidget * create_network_page(void)
Definition pages.c:1185
create_scenario_page
GtkWidget * create_scenario_page(void)
Definition pages.c:3169
statusbar
static GtkWidget * statusbar
Definition pages.c:89
destroy_server_scans
void destroy_server_scans(void)
Definition pages.c:752
create_load_page
GtkWidget * create_load_page(void)
Definition pages.c:2888
create_statusbar
GtkWidget * create_statusbar(void)
Definition pages.c:893
create_main_page
GtkWidget * create_main_page(void)
Definition pages.c:229
science_report_dialog_redraw
void science_report_dialog_redraw(void)
Definition repodlgs.c:761
spaceship_dialog_init
void spaceship_dialog_init(void)
Definition spaceshipdlg.c:87
spaceship_dialog_done
void spaceship_dialog_done(void)
Definition spaceshipdlg.c:95
sprite_get_pixbuf
GdkPixbuf * sprite_get_pixbuf(struct sprite *sprite)
Definition sprite.c:402
ingame_votebar
GtkWidget * ingame_votebar
Definition voteinfo_bar.c:50
voteinfo_bar_new
GtkWidget * voteinfo_bar_new(bool split_bar)
Definition voteinfo_bar.c:92
citizensinfo.h
editgui.h
gui_stuff.h
happiness.h
enable
#define enable(id)
Definition widget.h:223
cma_fe.h
chatline.h
colors.h
connectdlg.h
dialogs.h
diplodlg.h
gotodlg.h
graphics.h
gui_main.h
helpdlg.h
inteldlg.h
luaconsole.h
mapctrl.h
mapview.h
menu.h
messagewin.h
optiondlg.h
pages.h
plrdlg.h
repodlgs.h
spaceshipdlg.h
voteinfo_bar.h
log_set_callback
log_callback_fn log_set_callback(log_callback_fn callback)
Definition log.c:290
log.h
fc_assert_ret
#define fc_assert_ret(condition)
Definition log.h:191
log_verbose
#define log_verbose(message,...)
Definition log.h:109
log_fatal
#define log_fatal(message,...)
Definition log.h:100
log_debug
#define log_debug(message,...)
Definition log.h:115
log_normal
#define log_normal(message,...)
Definition log.h:107
log_base
#define log_base(level, message,...)
Definition log.h:94
log_level
log_level
Definition log.h:28
LOG_ERROR
@ LOG_ERROR
Definition log.h:30
LOG_DEBUG
@ LOG_DEBUG
Definition log.h:34
LOG_FATAL
@ LOG_FATAL
Definition log.h:29
LOG_WARN
@ LOG_WARN
Definition log.h:31
log_error
#define log_error(message,...)
Definition log.h:103
map.h
update_line
void update_line(int canvas_x, int canvas_y)
Definition mapctrl_common.c:666
maybe_activate_keyboardless_goto
void maybe_activate_keyboardless_goto(int canvas_x, int canvas_y)
Definition mapctrl_common.c:508
rbutton_down
bool rbutton_down
Definition mapctrl_common.c:55
tiles_hilited_cities
bool tiles_hilited_cities
Definition mapctrl_common.c:60
scroll_mapview
void scroll_mapview(enum direction8 gui_dir)
Definition mapctrl_common.c:553
keyboardless_goto_button_down
bool keyboardless_goto_button_down
Definition mapctrl_common.c:69
update_selection_rectangle
void update_selection_rectangle(float canvas_x, float canvas_y)
Definition mapctrl_common.c:201
init_mapcanvas_and_overview
void init_mapcanvas_and_overview(void)
Definition mapview_common.c:3698
canvas_pos_to_tile
struct tile * canvas_pos_to_tile(float canvas_x, float canvas_y, float zoom)
Definition mapview_common.c:763
free_mapcanvas_and_overview
void free_mapcanvas_and_overview(void)
Definition mapview_common.c:3707
get_mapview_scroll_pos
void get_mapview_scroll_pos(int *scroll_x, int *scroll_y)
Definition mapview_common.c:1206
get_mapview_scroll_step
void get_mapview_scroll_step(int *xstep, int *ystep)
Definition mapview_common.c:1192
set_mapview_scroll_pos
void set_mapview_scroll_pos(int scroll_x, int scroll_y, float zoom)
Definition mapview_common.c:1215
center_tile_mapcanvas
void center_tile_mapcanvas(const struct tile *ptile)
Definition mapview_common.c:1237
set_frame_by_frame_animation
void set_frame_by_frame_animation(void)
Definition mapview_common.c:4106
link_marks_clear_all
void link_marks_clear_all(void)
Definition mapview_common.c:3977
mem.h
fc_malloc
#define fc_malloc(sz)
Definition mem.h:34
menus_init
void menus_init(void)
Definition update_queue.c:554
option_changed
void option_changed(struct option *poption)
Definition options.c:747
server_optset
const struct option_set * server_optset
Definition options.c:4019
client_optset
const struct option_set * client_optset
Definition options.c:1279
option_bool_get
bool option_bool_get(const struct option *poption)
Definition options.c:796
option_type
enum option_type option_type(const struct option *poption)
Definition options.c:657
option_font_target
const char * option_font_target(const struct option *poption)
Definition options.c:1162
string_to_video_mode
bool string_to_video_mode(const char *buf, struct video_mode *mode)
Definition options.c:6508
gui_options
struct client_options gui_options
Definition options.c:71
option_font_get
const char * option_font_get(const struct option *poption)
Definition options.c:1140
optset_option_by_name
struct option * optset_option_by_name(const struct option_set *poptset, const char *name)
Definition options.c:430
options.h
GUI_GTK_OVERVIEW_MIN_XSIZE
#define GUI_GTK_OVERVIEW_MIN_XSIZE
Definition options.h:598
options_iterate
#define options_iterate(poptset, poption)
Definition options.h:551
GUI_GTK_MSGCHAT_MERGED
@ GUI_GTK_MSGCHAT_MERGED
Definition options.h:69
GUI_GTK_MSGCHAT_SPLIT
@ GUI_GTK_MSGCHAT_SPLIT
Definition options.h:67
options_iterate_end
#define options_iterate_end
Definition options.h:556
get_info_label_text_popup
const char * get_info_label_text_popup(void)
Definition text.c:969
level
struct setting_list * level[OLEVELS_NUM]
Definition settings.c:190
CLIP
#define CLIP(lower, current, upper)
Definition shared.h:57
callback
Definition gui_main.c:2404
callback::data
void * data
Definition gui_main.c:2406
callback::callback
void(* callback)(void *data)
Definition gui_main.c:2405
civclient::conn
struct connection conn
Definition client_main.h:96
client_options::silent_when_not_in_focus
bool silent_when_not_in_focus
Definition options.h:191
client_options::gui_gtk3_migrated_from_2_5
bool gui_gtk3_migrated_from_2_5
Definition options.h:139
client_options::zoom_set
bool zoom_set
Definition options.h:230
client_options::sound_effects_volume
int sound_effects_volume
Definition options.h:190
client_options::first_boot
bool first_boot
Definition options.h:128
client_options::zoom_default_level
float zoom_default_level
Definition options.h:231
client_options::gui_gtk3_fullscreen
bool gui_gtk3_fullscreen
Definition options.h:266
client_options::migrate_fullscreen
bool migrate_fullscreen
Definition options.h:145
client_options::gui_gtk3_migrated_from_gtk2
bool gui_gtk3_migrated_from_gtk2
Definition options.h:133
color
Definition colors.h:21
connection
Definition connection.h:136
connection::playing
struct player * playing
Definition connection.h:151
connection::notify_of_writable_data
void(* notify_of_writable_data)(struct connection *pc, bool data_available_and_socket_full)
Definition connection.h:181
connection::used
bool used
Definition connection.h:139
message
Definition messagewin_common.h:29
option
Definition options.c:478
sprite
Definition sprite.h:22
tileset
Definition tilespec.c:481
unit
Definition unit.h:138
unit::id
int id
Definition unit.h:145
video_mode
Definition options.h:46
video_mode::height
int height
Definition options.h:48
video_mode::width
int width
Definition options.h:47
view
Definition mapview_common.h:36
widget
Definition widget.h:112
fc_snprintf
int fc_snprintf(char *str, size_t n, const char *format,...)
Definition support.c:974
cat_snprintf
int cat_snprintf(char *str, size_t n, const char *format,...)
Definition support.c:1000
support.h
TRUE
#define TRUE
Definition support.h:46
FALSE
#define FALSE
Definition support.h:47
text.h
tileset_load_tiles
void tileset_load_tiles(struct tileset *t)
Definition tilespec.c:3632
tileset_free_tiles
void tileset_free_tiles(struct tileset *t)
Definition tilespec.c:6608
tileset_use_preferred_theme
void tileset_use_preferred_theme(const struct tileset *t)
Definition tilespec.c:7073
get_icon_sprite
struct sprite * get_icon_sprite(const struct tileset *t, enum icon_type icon)
Definition tilespec.c:6983
tileset_init
void tileset_init(struct tileset *t)
Definition tilespec.c:7130
get_arrow_sprite
struct sprite * get_arrow_sprite(const struct tileset *t, enum arrow_type arrow)
Definition tilespec.c:6872
get_tax_sprite
struct sprite * get_tax_sprite(const struct tileset *t, Output_type_id otype)
Definition tilespec.c:6883
tileset_tile_width
int tileset_tile_width(const struct tileset *t)
Definition tilespec.c:753
tilespec.h
ARROW_RIGHT
@ ARROW_RIGHT
Definition tilespec.h:200
ICON_FREECIV
@ ICON_FREECIV
Definition tilespec.h:313
unit_tile
#define unit_tile(_pu)
Definition unit.h:390
unit_owner
#define unit_owner(_pu)
Definition unit.h:389
unitlist.h
version.h
mouse_zoom
float mouse_zoom
Definition zoom.c:28
zoom_step_down
void zoom_step_down(void)
Definition zoom.c:134
zoom_step_up
void zoom_step_up(void)
Definition zoom.c:110
zoom.h