1 /*
2 * menu_midi.c - MIDI menu for SDL UI.
3 *
4 * Written by
5 * Hannu Nuotio <hannu.nuotio@tut.fi>
6 *
7 * This file is part of VICE, the Versatile Commodore Emulator.
8 * See README for copyright notice.
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 *
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
23 * 02111-1307 USA.
24 *
25 */
26
27 #include "vice.h"
28
29 #ifdef HAVE_MIDI
30
31 #include <stdio.h>
32
33 #include "types.h"
34
35 #include "menu_common.h"
36 #include "menu_midi.h"
37 #include "uimenu.h"
38
39 /* *nix MIDI settings */
40 #if defined(UNIX_COMPILE) && !defined(MACOSX_SUPPORT)
41
sdl_menu_midi_in_free(void)42 void sdl_menu_midi_in_free(void)
43 {
44 }
45
sdl_menu_midi_out_free(void)46 void sdl_menu_midi_out_free(void)
47 {
48 }
49
50 /* only show driver/device items when a midi driver exists */
51 #if defined(USE_OSS) || defined (USE_ALSA)
52 UI_MENU_DEFINE_STRING(MIDIInDev)
53 UI_MENU_DEFINE_STRING(MIDIOutDev)
54 UI_MENU_DEFINE_RADIO(MIDIDriver)
55
56 static const ui_menu_entry_t midi_driver_menu[] = {
57 #ifdef USE_OSS
58 { "OSS",
59 MENU_ENTRY_RESOURCE_RADIO,
60 radio_MIDIDriver_callback,
61 (ui_callback_data_t)0 },
62 #endif
63 #ifdef USE_ALSA
64 { "ALSA",
65 MENU_ENTRY_RESOURCE_RADIO,
66 radio_MIDIDriver_callback,
67 (ui_callback_data_t)1 },
68 #endif
69 SDL_MENU_LIST_END
70 };
71
72 #define VICE_SDL_MIDI_ARCHDEP_ITEMS \
73 SDL_MENU_ITEM_SEPARATOR, \
74 { "Driver", \
75 MENU_ENTRY_SUBMENU, \
76 submenu_radio_callback, \
77 (ui_callback_data_t)midi_driver_menu }, \
78 SDL_MENU_ITEM_SEPARATOR, \
79 SDL_MENU_ITEM_TITLE("OSS driver devices"), \
80 { "MIDI-In", \
81 MENU_ENTRY_RESOURCE_STRING, \
82 string_MIDIInDev_callback, \
83 (ui_callback_data_t)"MIDI-In device" }, \
84 { "MIDI-Out", \
85 MENU_ENTRY_RESOURCE_STRING, \
86 string_MIDIOutDev_callback, \
87 (ui_callback_data_t)"MIDI-Out device" },
88
89 #else
90 #define VICE_SDL_MIDI_ARCHDEP_ITEMS
91 #endif
92
93 #endif /* defined(UNIX_COMPILE) && !defined(MACOSX_SUPPORT) */
94
95 /* OSX MIDI settings */
96 #ifdef MACOSX_SUPPORT
97 UI_MENU_DEFINE_STRING(MIDIName)
UI_MENU_DEFINE_STRING(MIDIInName)98 UI_MENU_DEFINE_STRING(MIDIInName)
99 UI_MENU_DEFINE_STRING(MIDIOutName)
100
101 void sdl_menu_midi_in_free(void)
102 {
103 }
104
sdl_menu_midi_out_free(void)105 void sdl_menu_midi_out_free(void)
106 {
107 }
108
109 #define VICE_SDL_MIDI_ARCHDEP_ITEMS \
110 SDL_MENU_ITEM_SEPARATOR, \
111 { "Client name", \
112 MENU_ENTRY_RESOURCE_STRING, \
113 string_MIDIName_callback, \
114 (ui_callback_data_t)"Name of MIDI client" }, \
115 { "MIDI-In", \
116 MENU_ENTRY_RESOURCE_STRING, \
117 string_MIDIInName_callback, \
118 (ui_callback_data_t)"Name of MIDI-In Port" }, \
119 { "MIDI-Out", \
120 MENU_ENTRY_RESOURCE_STRING, \
121 string_MIDIOutName_callback, \
122 (ui_callback_data_t)"Name of MIDI-Out Port" },
123
124 #endif /* defined(MACOSX_SUPPORT) */
125
126 /* win32 MIDI settings */
127 #ifdef WIN32_COMPILE
128
129 #include <windows.h>
130 #include <mmsystem.h>
131
132 #include "lib.h"
133
134 UI_MENU_DEFINE_RADIO(MIDIInDev)
135 UI_MENU_DEFINE_RADIO(MIDIOutDev)
136
137 static ui_menu_entry_t midi_in_dyn_menu[21];
138 static ui_menu_entry_t midi_out_dyn_menu[21];
139
140 static int midi_in_dyn_menu_init = 0;
141 static int midi_out_dyn_menu_init = 0;
142
sdl_menu_midi_in_free(void)143 void sdl_menu_midi_in_free(void)
144 {
145 int i;
146
147 for (i = 0; midi_in_dyn_menu[i].string != NULL; i++) {
148 lib_free(midi_in_dyn_menu[i].string);
149 }
150 }
151
sdl_menu_midi_out_free(void)152 void sdl_menu_midi_out_free(void)
153 {
154 int i;
155
156 for (i = 0; midi_out_dyn_menu[i].string != NULL; i++) {
157 lib_free(midi_out_dyn_menu[i].string);
158 }
159 }
160
UI_MENU_CALLBACK(MIDIInDev_dynmenu_callback)161 UI_MENU_CALLBACK(MIDIInDev_dynmenu_callback)
162 {
163 MMRESULT ret;
164 MIDIINCAPS mic;
165 int i = 0;
166 int j;
167 int num_in = midiInGetNumDevs();
168
169 /* rebuild menu if it already exists. */
170 if (midi_in_dyn_menu_init != 0) {
171 sdl_menu_midi_in_free();
172 } else {
173 midi_in_dyn_menu_init = 1;
174 }
175
176 if (num_in == 0) {
177 midi_in_dyn_menu[i].string = (char *)lib_strdup("No Devices Present");
178 midi_in_dyn_menu[i].type = MENU_ENTRY_TEXT;
179 midi_in_dyn_menu[i].callback = seperator_callback;
180 midi_in_dyn_menu[i].data = NULL;
181 i++;
182 } else {
183 for (j = 0; (j < num_in) && (i < 20); j++) {
184 ret = midiInGetDevCaps(j, &mic, sizeof(MIDIINCAPS));
185 if (ret == MMSYSERR_NOERROR) {
186 midi_in_dyn_menu[i].string = (char *)lib_strdup(mic.szPname);
187 midi_in_dyn_menu[i].type = MENU_ENTRY_RESOURCE_RADIO;
188 midi_in_dyn_menu[i].callback = radio_MIDIInDev_callback;
189 midi_in_dyn_menu[i].data = (ui_callback_data_t)(int_to_void_ptr(j));
190 i++;
191 }
192 }
193 }
194
195 midi_in_dyn_menu[i].string = NULL;
196 midi_in_dyn_menu[i].type = 0;
197 midi_in_dyn_menu[i].callback = NULL;
198 midi_in_dyn_menu[i].data = NULL;
199
200 return MENU_SUBMENU_STRING;
201 }
202
UI_MENU_CALLBACK(MIDIOutDev_dynmenu_callback)203 UI_MENU_CALLBACK(MIDIOutDev_dynmenu_callback)
204 {
205 MMRESULT ret;
206 MIDIOUTCAPS moc;
207 int i = 0;
208 int j;
209 int num_out = midiOutGetNumDevs();
210
211 /* rebuild menu if it already exists. */
212 if (midi_out_dyn_menu_init != 0) {
213 sdl_menu_midi_out_free();
214 } else {
215 midi_out_dyn_menu_init = 1;
216 }
217
218 if (num_out == 0) {
219 midi_out_dyn_menu[i].string = (char *)lib_strdup("No Devices Present");
220 midi_out_dyn_menu[i].type = MENU_ENTRY_TEXT;
221 midi_out_dyn_menu[i].callback = seperator_callback;
222 midi_out_dyn_menu[i].data = NULL;
223 i++;
224 } else {
225 for (j = 0; (j < num_out) && (i < 20); j++) {
226 ret = midiOutGetDevCaps(j, &moc, sizeof(MIDIOUTCAPS));
227 if (ret == MMSYSERR_NOERROR) {
228 midi_out_dyn_menu[i].string = (char *)lib_strdup(moc.szPname);
229 midi_out_dyn_menu[i].type = MENU_ENTRY_RESOURCE_RADIO;
230 midi_out_dyn_menu[i].callback = radio_MIDIOutDev_callback;
231 midi_out_dyn_menu[i].data = (ui_callback_data_t)(int_to_void_ptr(j));
232 i++;
233 }
234 }
235 }
236
237 midi_out_dyn_menu[i].string = NULL;
238 midi_out_dyn_menu[i].type = 0;
239 midi_out_dyn_menu[i].callback = NULL;
240 midi_out_dyn_menu[i].data = NULL;
241
242 return MENU_SUBMENU_STRING;
243 }
244
245 #define VICE_SDL_MIDI_ARCHDEP_ITEMS \
246 SDL_MENU_ITEM_SEPARATOR, \
247 { "MIDI-In", \
248 MENU_ENTRY_DYNAMIC_SUBMENU, \
249 MIDIInDev_dynmenu_callback, \
250 (ui_callback_data_t)midi_in_dyn_menu }, \
251 { "MIDI-Out", \
252 MENU_ENTRY_DYNAMIC_SUBMENU, \
253 MIDIOutDev_dynmenu_callback, \
254 (ui_callback_data_t)midi_out_dyn_menu },
255
256 #endif /* defined(WIN32_COMPILE) */
257
258 /* Common menus */
259
260 UI_MENU_DEFINE_TOGGLE(MIDIEnable)
261 UI_MENU_DEFINE_RADIO(MIDIMode)
262
263 static const ui_menu_entry_t midi_type_menu[] = {
264 { "Sequential",
265 MENU_ENTRY_RESOURCE_RADIO,
266 radio_MIDIMode_callback,
267 (ui_callback_data_t)0 },
268 { "Passport",
269 MENU_ENTRY_RESOURCE_RADIO,
270 radio_MIDIMode_callback,
271 (ui_callback_data_t)1 },
272 { "DATEL",
273 MENU_ENTRY_RESOURCE_RADIO,
274 radio_MIDIMode_callback,
275 (ui_callback_data_t)2 },
276 { "Namesoft",
277 MENU_ENTRY_RESOURCE_RADIO,
278 radio_MIDIMode_callback,
279 (ui_callback_data_t)3 },
280 { "Maplin",
281 MENU_ENTRY_RESOURCE_RADIO,
282 radio_MIDIMode_callback,
283 (ui_callback_data_t)4 },
284 SDL_MENU_LIST_END
285 };
286
287 const ui_menu_entry_t midi_c64_menu[] = {
288 { "MIDI emulation",
289 MENU_ENTRY_RESOURCE_TOGGLE,
290 toggle_MIDIEnable_callback,
291 NULL },
292 { "MIDI cart type",
293 MENU_ENTRY_SUBMENU,
294 submenu_radio_callback,
295 (ui_callback_data_t)midi_type_menu },
296 VICE_SDL_MIDI_ARCHDEP_ITEMS
297 SDL_MENU_LIST_END
298 };
299
300 const ui_menu_entry_t midi_vic20_menu[] = {
301 { "MIDI emulation",
302 MENU_ENTRY_RESOURCE_TOGGLE,
303 toggle_MIDIEnable_callback,
304 NULL },
305 VICE_SDL_MIDI_ARCHDEP_ITEMS
306 SDL_MENU_LIST_END
307 };
308
309 #endif /* HAVE_MIDI */
310