1 /*
2  *  KCemu -- The emulator for the KC85 homecomputer series and much more.
3  *  Copyright (C) 1997-2010 Torsten Paul
4  *
5  *  This program is free software; you can redistribute it and/or modify
6  *  it under the terms of the GNU General Public License as published by
7  *  the Free Software Foundation; either version 2 of the License, or
8  *  (at your option) any later version.
9  *
10  *  This program is distributed in the hope that it will be useful,
11  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  *  GNU General Public License for more details.
14  *
15  *  You should have received a copy of the GNU General Public License along
16  *  with this program; if not, write to the Free Software Foundation, Inc.,
17  *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18  */
19 
20 #ifndef __ui_gtk_options_h
21 #define __ui_gtk_options_h
22 
23 #include <list>
24 #include <string>
25 
26 #include "kc/system.h"
27 #include "kc/prefs/profile.h"
28 
29 #include "ui/gtk/window.h"
30 
31 using namespace std;
32 
33 class OptionsWindow : public UI_Gtk_Window {
34 private:
35     enum {
36         TREE_INT_COLUMN,
37         TREE_TEXT_COLUMN,
38         TREE_ICON_COLUMN,
39         TREE_CONFIG_NAME_COLUMN,
40 
41         TREE_N_COLUMNS
42     };
43 
44     enum {
45         MODULES_NAME_COLUMN,
46         MODULES_MODIF_COLUMN,
47         MODULES_POINTER_COLUMN,
48 
49         MODULES_N_COLUMNS
50     };
51 
52     enum {
53         ROMS_DESCRIPTION_COLUMN,
54         ROMS_FILENAME_COLUMN,
55         ROMS_TYPE_COLUMN,
56 
57         ROMS_N_COLUMNS
58     };
59 
60     enum {
61         NR_OF_MODULES = 8,
62         NR_OF_ROMS = 8,
63         NR_OF_NETWORK_SETTINGS = 4,
64     };
65 
66     static const char * FILE_CHOOSER_BUTTON_KEY;
67     static const char * FILE_CHOOSER_CLEAR_BUTTON_KEY;
68     static const char * DATA_KEY_CHECK_BUTTON;
69     static const char * PREFERENCES_KEY;
70     static const char * DEFAULT_DIR_KEY;
71     static const char * TARGET_WIDGET1_KEY;
72     static const char * TARGET_WIDGET2_KEY;
73     static const char * TARGET_WIDGET3_KEY;
74 
75     // unfortunately the signature of gtk_tree_path_prev and
76     // gtk_tree_path_next are different. but as we just need to
77     // treat them as void, we cast them to the following type.
78     typedef void (*GtkPathMoveFunc)(GtkTreePath *);
79 
80     typedef void (*GtkIterMoveFunc)(GtkTreeStore *, GtkTreeIter *, GtkTreeIter *);
81 
82     struct {
83         GtkWidget    *treeview;
84         GtkWidget    *b_new;
85         GtkWidget    *b_copy;
86         GtkWidget    *b_delete;
87         GtkWidget    *b_up;
88         GtkWidget    *b_down;
89         GtkWidget    *b_ok;
90         GtkWidget    *b_close;
91         GtkWidget    *b_expand;
92         GtkWidget    *b_collapse;
93 
94         GtkNotebook    *notebook;
95 
96         GtkEntry       *entry_profile_name;
97         GtkComboBox    *combobox_system_type;
98         GtkComboBox    *combobox_system_variant;
99         GtkCheckButton *check_button_system_variant;
100         GtkTextView    *textview_comment;
101         GtkTextBuffer  *textbuffer_comment;
102 
103         GtkCheckButton *check_button_display_scale;
104         GtkCheckButton *check_button_display_effects;
105         GtkCheckButton *check_button_display_mem_access;
106         GtkCheckButton *check_button_display_debug;
107 
108         GtkCheckButton *check_button_d004;
109         GtkCheckButton *check_button_f8_rom;
110         GtkCheckButton *check_button_busdrivers;
111         GtkComboBox    *combobox_d004;
112         GtkComboBox    *combobox_f8_rom;
113         GtkSpinButton  *spin_button_busdrivers;
114 
115         GtkSpinButton  *spin_button_display_scale;
116         GtkComboBox    *combobox_display_effects;
117         GtkComboBox    *combobox_display_mem_access;
118         GtkComboBox    *combobox_display_debug;
119         GtkComboBox    *combobox_module[NR_OF_MODULES];
120         GtkCheckButton *check_button_modules;
121 
122         GtkEntry       *entry_network_ip_address;
123         GtkEntry       *entry_network_netmask;
124         GtkEntry       *entry_network_gateway;
125         GtkEntry       *entry_network_dns_server;
126 
127         GtkLabel         *roms_label[NR_OF_ROMS];
128         GtkComboBoxEntry *roms_comboboxentry[NR_OF_ROMS];
129         GtkButton        *roms_open_button[NR_OF_ROMS];
130         GtkCheckButton   *roms_check_button[NR_OF_ROMS];
131 
132         GtkTreeStore *treestore;
133         GtkListStore *liststore_system;
134         GtkListStore *liststore_modules;
135 
136         GdkPixbuf    *pixbuf_root;
137         GdkPixbuf    *pixbuf_default;
138         GdkPixbuf    *pixbuf_deleted;
139 
140         gint          on_profile_name_changed_id;
141         gint          on_comment_changed_id;
142         gint          on_system_type_changed_id;
143         gint          on_system_variant_changed_id;
144         gint          on_display_scale_value_changed_id;
145         gint          on_display_effects_changed_id;
146         gint          on_display_mem_access_changed_id;
147         gint          on_display_debug_changed_id;
148         gint          on_kc85_d004_changed_id;
149         gint          on_kc85_f8_rom_changed_id;
150         gint          on_kc85_busdrivers_changed_id;
151         gint          on_module_changed_id[NR_OF_MODULES];
152         gint          on_rom_changed_id[NR_OF_ROMS];
153         gint          on_network_changed_id[NR_OF_NETWORK_SETTINGS];
154     } _w;
155 
156     CMD *_cmd;
157     CMD *_cmd_dialog;
158 
159     kc_type_t     _current_kc_type;
160     Profile      *_current_profile;
161     list<string>  _delete_path;
162     char         *_open_rom_last_path;
163 
164 protected:
165     void init(void);
166 
167     bool is_ip_address(const char *addr);
168 
169     GtkTreeStore * get_tree_model(void);
170     GtkListStore * get_system_list_model(void);
171     GtkListStore * get_variant_list_model(kc_variant_t kc_variant, const char *name, ...);
172     GtkListStore * get_modules_list_model(kc_type_t kc_type);
173 
174     GtkTreeModel * get_selected_tree_iter(GtkTreeIter *iter);
175     void expand_and_select(GtkTreeView *treeview, GtkTreeModel *model, GtkTreeIter *iter);
176     ProfileValue * get_current_profile_value(const char *key);
177     const char * get_preferences_key(GObject *object);
178     void set_preferences_key(GObject *object, const char *key);
179 
180     void apply_profile(void);
181     void apply_comment(void);
182     void apply_system_type(void);
183     void apply_kc85_settings(void);
184     void apply_display_settings(void);
185     void apply_network_settings(void);
186     void apply_modules_settings(kc_type_t kc_type);
187     void apply_roms_settings(kc_type_t kc_type, kc_variant_t kc_variant);
188     void apply_system_variant(kc_type_t kc_type, kc_variant_t kc_variant);
189     void apply_filechooserbutton(GtkFileChooser *filechooser);
190     void apply_entry_value(GtkEntry *entry, gint signal_id);
191     void apply_combobox_value(GtkCheckButton *check_button, GtkComboBox *combobox, gint handler_id);
192     void apply_spin_button_value(GtkCheckButton *check_button, GtkSpinButton *spin_button, gint signal_id, int default_value);
193 
194     void expand_tree(void);
195     void collapse_tree(void);
196     void add_system(GtkTreeStore *store, GtkTreeIter *iter, const char *name, const char *config_name, const char *icon_name);
197     void move_row(GtkPathMoveFunc path_func, GtkIterMoveFunc move_func);
198     void set_roms_liststore(int idx, const char *rom_key, SystemROM *rom);
199     bool check_button_toggled(GtkToggleButton *togglebutton);
200     void set_widget_sensitive_by_key(GObject *object, const gchar *key, bool sensitive);
201     void wire_check_button(const char *preferences_key, GtkCheckButton *check_button, GCallback callback, GtkWidget *target1, GtkWidget *target2 = NULL, GtkWidget *target3 = NULL);
202     void wire_check_button(const char *preferences_key, const char *default_dir, const char *check_button_name, const char *filechooser_button_name, const char *button_clear_name);
203 
204     static void on_button_new_clicked(GtkButton *button, gpointer user_data);
205     static void on_button_copy_clicked(GtkButton *button, gpointer user_data);
206     static void on_button_delete_clicked(GtkButton *button, gpointer user_data);
207     static void on_button_up_clicked(GtkButton *button, gpointer user_data);
208     static void on_button_down_clicked(GtkButton *button, gpointer user_data);
209     static void on_button_expand_clicked(GtkButton *button, gpointer user_data);
210     static void on_button_collapse_clicked(GtkButton *button, gpointer user_data);
211     static void on_button_ok_clicked(GtkButton *button, gpointer user_data);
212     static void on_button_close_clicked(GtkButton *button, gpointer user_data);
213     static void on_tree_selection_changed(GtkTreeSelection *selection, gpointer user_data);
214     static void on_media_check_button_toggled(GtkToggleButton *togglebutton, gpointer user_data);
215     static void on_media_clear_button_clicked(GtkButton *button, gpointer user_data);
216     static void on_media_filechooser_file_set(GtkFileChooserButton *filechooserbutton, gpointer user_data);
217 
218     static void on_display_check_button_toggled(GtkToggleButton *togglebutton, gpointer user_data);
219     static void on_display_scale_value_changed(GtkSpinButton *spin_button, gpointer user_data);
220     static void on_display_effects_changed(GtkComboBox *combobox, gpointer user_data);
221     static void on_display_debug_changed(GtkComboBox *combobox, gpointer user_data);
222     static void on_display_mem_access_changed(GtkComboBox *combobox, gpointer user_data);
223 
224     static void on_profile_name_changed(GtkEditable *editable, gpointer user_data);
225     static void on_comment_changed(GtkTextBuffer *textbuffer, gpointer user_data);
226     static void on_system_type_changed(GtkComboBox *combobox, gpointer user_data);
227     static void on_system_variant_changed(GtkComboBox *combobox, gpointer user_data);
228     static void on_system_variant_check_button_toggled(GtkToggleButton *togglebutton, gpointer user_data);
229 
230     static void on_module_changed(GtkComboBox *combobox, gpointer user_data);
231     static void on_modules_check_button_toggled(GtkToggleButton *togglebutton, gpointer user_data);
232 
233     static void on_kc85_settings_check_button_toggled(GtkToggleButton *togglebutton, gpointer user_data);
234     static void on_kc85_d004_changed(GtkComboBox *combobox, gpointer user_data);
235     static void on_kc85_f8_rom_changed(GtkComboBox *combobox, gpointer user_data);
236     static void on_kc85_busdrivers_changed(GtkSpinButton *spin_button, gpointer user_data);
237 
238     static void on_rom_changed(GtkComboBoxEntry *comboboxentry, gpointer user_data);
239     static void on_rom_open_clicked(GtkButton *button, gpointer user_data);
240     static void on_roms_settings_check_button_toggled(GtkToggleButton *togglebutton, gpointer user_data);
241 
242     static void on_network_settings_check_button_toggled(GtkToggleButton *togglebutton, gpointer user_data);
243     static void on_network_changed(GtkEntry *entry, gpointer user_data);
244 
245     static gboolean tree_model_foreach_func_delete(GtkTreeModel *model, GtkTreePath *path, GtkTreeIter *iter, gpointer user_data);
246 
247 public:
248     OptionsWindow(const char *ui_xml_file);
249     virtual ~OptionsWindow(void);
250 
251     void save(void);
252     void reject(void);
253 };
254 
255 #endif /* __ui_gtk_options_h */
256