vid_menu.c (13270B)
1 /* 2 Copyright (C) 1997-2001 Id Software, Inc. 3 4 This program is free software; you can redistribute it and/or 5 modify it under the terms of the GNU General Public License 6 as published by the Free Software Foundation; either version 2 7 of the License, or (at your option) any later version. 8 9 This program is distributed in the hope that it will be useful, 10 but WITHOUT ANY WARRANTY; without even the implied warranty of 11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 12 13 See the GNU General Public License for more details. 14 15 You should have received a copy of the GNU General Public License 16 along with this program; if not, write to the Free Software 17 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 18 19 */ 20 #include "../client/client.h" 21 #include "../client/qmenu.h" 22 23 #define REF_SOFT 0 24 #define REF_OPENGL 1 25 #define REF_3DFX 2 26 #define REF_POWERVR 3 27 #define REF_VERITE 4 28 29 extern cvar_t *vid_ref; 30 extern cvar_t *vid_fullscreen; 31 extern cvar_t *vid_gamma; 32 extern cvar_t *scr_viewsize; 33 34 static cvar_t *gl_mode; 35 static cvar_t *gl_driver; 36 static cvar_t *gl_picmip; 37 static cvar_t *gl_ext_palettedtexture; 38 static cvar_t *gl_finish; 39 40 static cvar_t *sw_mode; 41 static cvar_t *sw_stipplealpha; 42 43 extern void M_ForceMenuOff( void ); 44 45 /* 46 ==================================================================== 47 48 MENU INTERACTION 49 50 ==================================================================== 51 */ 52 #define SOFTWARE_MENU 0 53 #define OPENGL_MENU 1 54 55 static menuframework_s s_software_menu; 56 static menuframework_s s_opengl_menu; 57 static menuframework_s *s_current_menu; 58 static int s_current_menu_index; 59 60 static menulist_s s_mode_list[2]; 61 static menulist_s s_ref_list[2]; 62 static menuslider_s s_tq_slider; 63 static menuslider_s s_screensize_slider[2]; 64 static menuslider_s s_brightness_slider[2]; 65 static menulist_s s_fs_box[2]; 66 static menulist_s s_stipple_box; 67 static menulist_s s_paletted_texture_box; 68 static menulist_s s_finish_box; 69 static menuaction_s s_cancel_action[2]; 70 static menuaction_s s_defaults_action[2]; 71 72 static void DriverCallback( void *unused ) 73 { 74 s_ref_list[!s_current_menu_index].curvalue = s_ref_list[s_current_menu_index].curvalue; 75 76 if ( s_ref_list[s_current_menu_index].curvalue == 0 ) 77 { 78 s_current_menu = &s_software_menu; 79 s_current_menu_index = 0; 80 } 81 else 82 { 83 s_current_menu = &s_opengl_menu; 84 s_current_menu_index = 1; 85 } 86 87 } 88 89 static void ScreenSizeCallback( void *s ) 90 { 91 menuslider_s *slider = ( menuslider_s * ) s; 92 93 Cvar_SetValue( "viewsize", slider->curvalue * 10 ); 94 } 95 96 static void BrightnessCallback( void *s ) 97 { 98 menuslider_s *slider = ( menuslider_s * ) s; 99 100 if ( s_current_menu_index == SOFTWARE_MENU ) 101 s_brightness_slider[1].curvalue = s_brightness_slider[0].curvalue; 102 else 103 s_brightness_slider[0].curvalue = s_brightness_slider[1].curvalue; 104 105 if ( stricmp( vid_ref->string, "soft" ) == 0 ) 106 { 107 float gamma = ( 0.8 - ( slider->curvalue/10.0 - 0.5 ) ) + 0.5; 108 109 Cvar_SetValue( "vid_gamma", gamma ); 110 } 111 } 112 113 static void ResetDefaults( void *unused ) 114 { 115 VID_MenuInit(); 116 } 117 118 static void ApplyChanges( void *unused ) 119 { 120 float gamma; 121 122 /* 123 ** make values consistent 124 */ 125 s_fs_box[!s_current_menu_index].curvalue = s_fs_box[s_current_menu_index].curvalue; 126 s_brightness_slider[!s_current_menu_index].curvalue = s_brightness_slider[s_current_menu_index].curvalue; 127 s_ref_list[!s_current_menu_index].curvalue = s_ref_list[s_current_menu_index].curvalue; 128 129 /* 130 ** invert sense so greater = brighter, and scale to a range of 0.5 to 1.3 131 */ 132 gamma = ( 0.8 - ( s_brightness_slider[s_current_menu_index].curvalue/10.0 - 0.5 ) ) + 0.5; 133 134 Cvar_SetValue( "vid_gamma", gamma ); 135 Cvar_SetValue( "sw_stipplealpha", s_stipple_box.curvalue ); 136 Cvar_SetValue( "gl_picmip", 3 - s_tq_slider.curvalue ); 137 Cvar_SetValue( "vid_fullscreen", s_fs_box[s_current_menu_index].curvalue ); 138 Cvar_SetValue( "gl_ext_palettedtexture", s_paletted_texture_box.curvalue ); 139 Cvar_SetValue( "gl_finish", s_finish_box.curvalue ); 140 Cvar_SetValue( "sw_mode", s_mode_list[SOFTWARE_MENU].curvalue ); 141 Cvar_SetValue( "gl_mode", s_mode_list[OPENGL_MENU].curvalue ); 142 143 switch ( s_ref_list[s_current_menu_index].curvalue ) 144 { 145 case REF_SOFT: 146 Cvar_Set( "vid_ref", "soft" ); 147 break; 148 case REF_OPENGL: 149 Cvar_Set( "vid_ref", "gl" ); 150 Cvar_Set( "gl_driver", "opengl32" ); 151 break; 152 case REF_3DFX: 153 Cvar_Set( "vid_ref", "gl" ); 154 Cvar_Set( "gl_driver", "3dfxgl" ); 155 break; 156 case REF_POWERVR: 157 Cvar_Set( "vid_ref", "gl" ); 158 Cvar_Set( "gl_driver", "pvrgl" ); 159 break; 160 case REF_VERITE: 161 Cvar_Set( "vid_ref", "gl" ); 162 Cvar_Set( "gl_driver", "veritegl" ); 163 break; 164 } 165 166 /* 167 ** update appropriate stuff if we're running OpenGL and gamma 168 ** has been modified 169 */ 170 if ( stricmp( vid_ref->string, "gl" ) == 0 ) 171 { 172 if ( vid_gamma->modified ) 173 { 174 vid_ref->modified = true; 175 if ( stricmp( gl_driver->string, "3dfxgl" ) == 0 ) 176 { 177 char envbuffer[1024]; 178 float g; 179 180 vid_ref->modified = true; 181 182 g = 2.00 * ( 0.8 - ( vid_gamma->value - 0.5 ) ) + 1.0F; 183 Com_sprintf( envbuffer, sizeof(envbuffer), "SSTV2_GAMMA=%f", g ); 184 putenv( envbuffer ); 185 Com_sprintf( envbuffer, sizeof(envbuffer), "SST_GAMMA=%f", g ); 186 putenv( envbuffer ); 187 188 vid_gamma->modified = false; 189 } 190 } 191 192 if ( gl_driver->modified ) 193 vid_ref->modified = true; 194 } 195 196 M_ForceMenuOff(); 197 } 198 199 static void CancelChanges( void *unused ) 200 { 201 extern void M_PopMenu( void ); 202 203 M_PopMenu(); 204 } 205 206 /* 207 ** VID_MenuInit 208 */ 209 void VID_MenuInit( void ) 210 { 211 static const char *resolutions[] = 212 { 213 "[320 240 ]", 214 "[400 300 ]", 215 "[512 384 ]", 216 "[640 480 ]", 217 "[800 600 ]", 218 "[960 720 ]", 219 "[1024 768 ]", 220 "[1152 864 ]", 221 "[1280 960 ]", 222 "[1600 1200]", 223 0 224 }; 225 static const char *refs[] = 226 { 227 "[software ]", 228 "[default OpenGL]", 229 "[3Dfx OpenGL ]", 230 "[PowerVR OpenGL]", 231 // "[Rendition OpenGL]", 232 0 233 }; 234 static const char *yesno_names[] = 235 { 236 "no", 237 "yes", 238 0 239 }; 240 int i; 241 242 if ( !gl_driver ) 243 gl_driver = Cvar_Get( "gl_driver", "opengl32", 0 ); 244 if ( !gl_picmip ) 245 gl_picmip = Cvar_Get( "gl_picmip", "0", 0 ); 246 if ( !gl_mode ) 247 gl_mode = Cvar_Get( "gl_mode", "3", 0 ); 248 if ( !sw_mode ) 249 sw_mode = Cvar_Get( "sw_mode", "0", 0 ); 250 if ( !gl_ext_palettedtexture ) 251 gl_ext_palettedtexture = Cvar_Get( "gl_ext_palettedtexture", "1", CVAR_ARCHIVE ); 252 if ( !gl_finish ) 253 gl_finish = Cvar_Get( "gl_finish", "0", CVAR_ARCHIVE ); 254 255 if ( !sw_stipplealpha ) 256 sw_stipplealpha = Cvar_Get( "sw_stipplealpha", "0", CVAR_ARCHIVE ); 257 258 s_mode_list[SOFTWARE_MENU].curvalue = sw_mode->value; 259 s_mode_list[OPENGL_MENU].curvalue = gl_mode->value; 260 261 if ( !scr_viewsize ) 262 scr_viewsize = Cvar_Get ("viewsize", "100", CVAR_ARCHIVE); 263 264 s_screensize_slider[SOFTWARE_MENU].curvalue = scr_viewsize->value/10; 265 s_screensize_slider[OPENGL_MENU].curvalue = scr_viewsize->value/10; 266 267 if ( strcmp( vid_ref->string, "soft" ) == 0 ) 268 { 269 s_current_menu_index = SOFTWARE_MENU; 270 s_ref_list[0].curvalue = s_ref_list[1].curvalue = REF_SOFT; 271 } 272 else if ( strcmp( vid_ref->string, "gl" ) == 0 ) 273 { 274 s_current_menu_index = OPENGL_MENU; 275 if ( strcmp( gl_driver->string, "3dfxgl" ) == 0 ) 276 s_ref_list[s_current_menu_index].curvalue = REF_3DFX; 277 else if ( strcmp( gl_driver->string, "pvrgl" ) == 0 ) 278 s_ref_list[s_current_menu_index].curvalue = REF_POWERVR; 279 else if ( strcmp( gl_driver->string, "opengl32" ) == 0 ) 280 s_ref_list[s_current_menu_index].curvalue = REF_OPENGL; 281 else 282 // s_ref_list[s_current_menu_index].curvalue = REF_VERITE; 283 s_ref_list[s_current_menu_index].curvalue = REF_OPENGL; 284 } 285 286 s_software_menu.x = viddef.width * 0.50; 287 s_software_menu.nitems = 0; 288 s_opengl_menu.x = viddef.width * 0.50; 289 s_opengl_menu.nitems = 0; 290 291 for ( i = 0; i < 2; i++ ) 292 { 293 s_ref_list[i].generic.type = MTYPE_SPINCONTROL; 294 s_ref_list[i].generic.name = "driver"; 295 s_ref_list[i].generic.x = 0; 296 s_ref_list[i].generic.y = 0; 297 s_ref_list[i].generic.callback = DriverCallback; 298 s_ref_list[i].itemnames = refs; 299 300 s_mode_list[i].generic.type = MTYPE_SPINCONTROL; 301 s_mode_list[i].generic.name = "video mode"; 302 s_mode_list[i].generic.x = 0; 303 s_mode_list[i].generic.y = 10; 304 s_mode_list[i].itemnames = resolutions; 305 306 s_screensize_slider[i].generic.type = MTYPE_SLIDER; 307 s_screensize_slider[i].generic.x = 0; 308 s_screensize_slider[i].generic.y = 20; 309 s_screensize_slider[i].generic.name = "screen size"; 310 s_screensize_slider[i].minvalue = 3; 311 s_screensize_slider[i].maxvalue = 12; 312 s_screensize_slider[i].generic.callback = ScreenSizeCallback; 313 314 s_brightness_slider[i].generic.type = MTYPE_SLIDER; 315 s_brightness_slider[i].generic.x = 0; 316 s_brightness_slider[i].generic.y = 30; 317 s_brightness_slider[i].generic.name = "brightness"; 318 s_brightness_slider[i].generic.callback = BrightnessCallback; 319 s_brightness_slider[i].minvalue = 5; 320 s_brightness_slider[i].maxvalue = 13; 321 s_brightness_slider[i].curvalue = ( 1.3 - vid_gamma->value + 0.5 ) * 10; 322 323 s_fs_box[i].generic.type = MTYPE_SPINCONTROL; 324 s_fs_box[i].generic.x = 0; 325 s_fs_box[i].generic.y = 40; 326 s_fs_box[i].generic.name = "fullscreen"; 327 s_fs_box[i].itemnames = yesno_names; 328 s_fs_box[i].curvalue = vid_fullscreen->value; 329 330 s_defaults_action[i].generic.type = MTYPE_ACTION; 331 s_defaults_action[i].generic.name = "reset to defaults"; 332 s_defaults_action[i].generic.x = 0; 333 s_defaults_action[i].generic.y = 90; 334 s_defaults_action[i].generic.callback = ResetDefaults; 335 336 s_cancel_action[i].generic.type = MTYPE_ACTION; 337 s_cancel_action[i].generic.name = "cancel"; 338 s_cancel_action[i].generic.x = 0; 339 s_cancel_action[i].generic.y = 100; 340 s_cancel_action[i].generic.callback = CancelChanges; 341 } 342 343 s_stipple_box.generic.type = MTYPE_SPINCONTROL; 344 s_stipple_box.generic.x = 0; 345 s_stipple_box.generic.y = 60; 346 s_stipple_box.generic.name = "stipple alpha"; 347 s_stipple_box.curvalue = sw_stipplealpha->value; 348 s_stipple_box.itemnames = yesno_names; 349 350 s_tq_slider.generic.type = MTYPE_SLIDER; 351 s_tq_slider.generic.x = 0; 352 s_tq_slider.generic.y = 60; 353 s_tq_slider.generic.name = "texture quality"; 354 s_tq_slider.minvalue = 0; 355 s_tq_slider.maxvalue = 3; 356 s_tq_slider.curvalue = 3-gl_picmip->value; 357 358 s_paletted_texture_box.generic.type = MTYPE_SPINCONTROL; 359 s_paletted_texture_box.generic.x = 0; 360 s_paletted_texture_box.generic.y = 70; 361 s_paletted_texture_box.generic.name = "8-bit textures"; 362 s_paletted_texture_box.itemnames = yesno_names; 363 s_paletted_texture_box.curvalue = gl_ext_palettedtexture->value; 364 365 s_finish_box.generic.type = MTYPE_SPINCONTROL; 366 s_finish_box.generic.x = 0; 367 s_finish_box.generic.y = 80; 368 s_finish_box.generic.name = "sync every frame"; 369 s_finish_box.curvalue = gl_finish->value; 370 s_finish_box.itemnames = yesno_names; 371 372 Menu_AddItem( &s_software_menu, ( void * ) &s_ref_list[SOFTWARE_MENU] ); 373 Menu_AddItem( &s_software_menu, ( void * ) &s_mode_list[SOFTWARE_MENU] ); 374 Menu_AddItem( &s_software_menu, ( void * ) &s_screensize_slider[SOFTWARE_MENU] ); 375 Menu_AddItem( &s_software_menu, ( void * ) &s_brightness_slider[SOFTWARE_MENU] ); 376 Menu_AddItem( &s_software_menu, ( void * ) &s_fs_box[SOFTWARE_MENU] ); 377 Menu_AddItem( &s_software_menu, ( void * ) &s_stipple_box ); 378 379 Menu_AddItem( &s_opengl_menu, ( void * ) &s_ref_list[OPENGL_MENU] ); 380 Menu_AddItem( &s_opengl_menu, ( void * ) &s_mode_list[OPENGL_MENU] ); 381 Menu_AddItem( &s_opengl_menu, ( void * ) &s_screensize_slider[OPENGL_MENU] ); 382 Menu_AddItem( &s_opengl_menu, ( void * ) &s_brightness_slider[OPENGL_MENU] ); 383 Menu_AddItem( &s_opengl_menu, ( void * ) &s_fs_box[OPENGL_MENU] ); 384 Menu_AddItem( &s_opengl_menu, ( void * ) &s_tq_slider ); 385 Menu_AddItem( &s_opengl_menu, ( void * ) &s_paletted_texture_box ); 386 Menu_AddItem( &s_opengl_menu, ( void * ) &s_finish_box ); 387 388 Menu_AddItem( &s_software_menu, ( void * ) &s_defaults_action[SOFTWARE_MENU] ); 389 Menu_AddItem( &s_software_menu, ( void * ) &s_cancel_action[SOFTWARE_MENU] ); 390 Menu_AddItem( &s_opengl_menu, ( void * ) &s_defaults_action[OPENGL_MENU] ); 391 Menu_AddItem( &s_opengl_menu, ( void * ) &s_cancel_action[OPENGL_MENU] ); 392 393 Menu_Center( &s_software_menu ); 394 Menu_Center( &s_opengl_menu ); 395 s_opengl_menu.x -= 8; 396 s_software_menu.x -= 8; 397 } 398 399 /* 400 ================ 401 VID_MenuDraw 402 ================ 403 */ 404 void VID_MenuDraw (void) 405 { 406 int w, h; 407 408 if ( s_current_menu_index == 0 ) 409 s_current_menu = &s_software_menu; 410 else 411 s_current_menu = &s_opengl_menu; 412 413 /* 414 ** draw the banner 415 */ 416 re.DrawGetPicSize( &w, &h, "m_banner_video" ); 417 re.DrawPic( viddef.width / 2 - w / 2, viddef.height /2 - 110, "m_banner_video" ); 418 419 /* 420 ** move cursor to a reasonable starting position 421 */ 422 Menu_AdjustCursor( s_current_menu, 1 ); 423 424 /* 425 ** draw the menu 426 */ 427 Menu_Draw( s_current_menu ); 428 } 429 430 /* 431 ================ 432 VID_MenuKey 433 ================ 434 */ 435 const char *VID_MenuKey( int key ) 436 { 437 menuframework_s *m = s_current_menu; 438 static const char *sound = "misc/menu1.wav"; 439 440 switch ( key ) 441 { 442 case K_ESCAPE: 443 ApplyChanges( 0 ); 444 return NULL; 445 case K_KP_UPARROW: 446 case K_UPARROW: 447 m->cursor--; 448 Menu_AdjustCursor( m, -1 ); 449 break; 450 case K_KP_DOWNARROW: 451 case K_DOWNARROW: 452 m->cursor++; 453 Menu_AdjustCursor( m, 1 ); 454 break; 455 case K_KP_LEFTARROW: 456 case K_LEFTARROW: 457 Menu_SlideItem( m, -1 ); 458 break; 459 case K_KP_RIGHTARROW: 460 case K_RIGHTARROW: 461 Menu_SlideItem( m, 1 ); 462 break; 463 case K_KP_ENTER: 464 case K_ENTER: 465 if ( !Menu_SelectItem( m ) ) 466 ApplyChanges( NULL ); 467 break; 468 } 469 470 return sound; 471 } 472 473