static void mouse_cb( int button, int state, int x, int y ) { #ifdef __APPLE__ if (g_game.practicing && !g_game.race_aborted && g_game.race.name!=NULL && did_player_beat_best_results() && g_game.rankings_displayed==false) { //Notify that a new best result is for the moment unsaved //dirtyScores(); } if (!did_player_beat_best_results() && !plyrWantsToDisplayRankingsAfterRace()) { g_game.rankings_displayed=true; } if (!g_game.race_aborted && g_game.practicing && plyrWantsToSaveOrDisplayRankingsAfterRace() && g_game.rankings_displayed==false) { saveAndDisplayRankings(); } else { //set landscape resolution setparam_x_resolution(320); setparam_y_resolution(480); //rotate screen turnScreenToPortrait(); set_game_mode( NEXT_MODE ); winsys_post_redisplay(); } #else set_game_mode( NEXT_MODE ); winsys_post_redisplay(); #endif }
void GameOver::loop(float timeStep) { int width, height; width = getparam_x_resolution(); height = getparam_y_resolution(); /* Check joystick */ if ( is_joystick_active() ) { update_joystick(); if ( is_joystick_continue_button_down() ) { if ( gameMgr->gametype != GameMgr::PRACTICING ) { set_game_mode( EVENT_RACE_SELECT ); }else{ set_game_mode( RACE_SELECT ); } winsys_post_redisplay(); return; } } fpsCounter.update(); update_audio(); clear_rendering_context(); fogPlane.setup(); update_player_pos( players[0], 0 ); update_view( players[0], 0 ); setup_view_frustum( players[0], NEAR_CLIP_DIST, getparam_forward_clip_distance() ); draw_sky(players[0].view.pos); draw_fog_plane(); set_course_clipping( true ); set_course_eye_point( players[0].view.pos ); setup_course_lighting(); render_course(); draw_trees(); if ( getparam_draw_particles() ) { draw_particles( players[0] ); } ModelHndl->draw_tux(); draw_tux_shadow(); set_gl_options( GUI ); UIMgr.setupDisplay(); UIMgr.draw(); HUD1.draw(players[0]); reshape( width, height ); winsys_swap_buffers(); }
bool GameOver::keyPressEvent(SDLKey key) { if ( gameMgr->gametype!=GameMgr::PRACTICING ) { set_game_mode( EVENT_RACE_SELECT ); }else{ set_game_mode( RACE_SELECT ); } winsys_post_redisplay(); return true; }
/*! Callback called when back button is clicked \author jfpatry \date Created: 2000-09-24 \date Modified: 2000-09-24 */ static void back_click_cb( button_t *button, void *userdata ) { check_assertion( userdata == NULL, "userdata is not null" ); if ( g_game.practicing ) { set_game_mode( GAME_TYPE_SELECT ); } else { set_game_mode( EVENT_SELECT ); } ui_set_dirty(); }
bool GameOver::mouseButtonEvent(int button, int x, int y, bool pressed) { if ( gameMgr->gametype!=GameMgr::PRACTICING ) { set_game_mode( EVENT_RACE_SELECT ); }else{ set_game_mode( RACE_SELECT ); } winsys_post_redisplay(); return true; }
bool Paused::keyPressEvent(SDLKey key) { if(key=='q') { Paused::quit(); } else { if(Benchmark::getMode() == Benchmark::PAUSED){ set_game_mode( GAME_OVER ); }else{ set_game_mode( RACING ); } } winsys_post_redisplay(); return true; }
static void start_race() { if (buy_or_play_course()) { #ifdef __ANDROID__ buy_course_pack(); #else // TODO: Implement In-App-Purchase here #endif } else { race_select_loop( 0 ); update_race_data(); //Select the starting step if (!strcmp(g_game.race.name,"Basic tutorial")) init_starting_tutorial_step(0); if (!strcmp(g_game.race.name,"Jump tutorial")) init_starting_tutorial_step(10); winsys_reset_js_bindings(); set_game_mode( LOADING ); } }
static void back() { if ( g_game.practicing ) { #ifdef SPEED_MODE set_game_mode( RACING_MODE_SELECT ); #else set_game_mode( GAME_TYPE_SELECT ); #endif } else { set_game_mode( GAME_TYPE_SELECT ); } winsys_reset_js_bindings(); ui_set_dirty(); }
END_KEYBOARD_CB START_KEYBOARD_CB( reset_cb ) { if ( release ) return; set_game_mode( RESET ); }
END_KEYBOARD_CB START_KEYBOARD_CB( pause_cb ) { if ( release ) return; set_game_mode( PAUSED ); }
static void save_click_cb( button_t *button, void *userdata ) { check_assertion( userdata == NULL, "userdata is not null" ); cur_sound = listbox_get_current_item( sound_listbox ); int snd = *((int*) get_list_elem_data( cur_sound )); cur_video = listbox_get_current_item( video_listbox ); int vid = *((int*) get_list_elem_data( cur_video )); setparam_sound_enabled(snd); if (getparam_music_enabled() == 1 && snd == 0) stopMusic(); setparam_music_enabled (snd); saveparamSoundEnabled(snd); setparam_video_quality (vid); set_video_quality(vid); saveparamVideoQuality(vid); set_game_mode( GAME_TYPE_SELECT ); ui_set_dirty(); }
static void chancel_click_cb( button_t *button, void *userdata ) { check_assertion( userdata == NULL, "userdata is not null" ); set_game_mode( GAME_TYPE_SELECT ); ui_set_dirty(); }
void credits_click_cb( button_t *button, void *userdata ) { check_assertion( userdata == NULL, "userdata is not null" ); set_game_mode( CREDITS ); ui_set_dirty(); }
void preference_click_cb( button_t *button, void *userdata ) { check_assertion( userdata == NULL, "userdata is not null" ); set_game_mode( PREFERENCE ); ui_set_dirty(); }
void help_click_cb( button_t *button, void *userdata ) { check_assertion( userdata == NULL, "userdata is not null" ); set_game_mode( HELP ); ui_set_dirty(); }
/*! Callback called when start button is clicked \author jfpatry \date Created: 2000-09-24 \date Modified: 2000-09-24 */ static void start_click_cb( button_t *button, void *userdata ) { check_assertion( userdata == NULL, "userdata is not null" ); button_set_highlight( start_btn, True ); race_select_loop( 0 ); update_race_data(); set_game_mode( LOADING ); }
void enter_event_click_cb( button_t* button, void *userdata ) { check_assertion( userdata == NULL, "userdata is not null" ); g_game.current_event = NULL; g_game.current_cup = NULL; g_game.current_race = -1; g_game.practicing = False; set_game_mode( EVENT_SELECT ); ui_set_dirty(); }
bool Racing::keyPressEvent(SDLKey key) { switch(key){ case 'q': gameMgr->abortRace(); set_game_mode( GAME_OVER ); return true; case SDLK_ESCAPE: set_game_mode( PAUSED ); return true; case '1': set_view_mode( players[0], ABOVE ); setparam_view_mode( ABOVE ); return true; case '2': set_view_mode( players[0], FOLLOW ); setparam_view_mode( FOLLOW ); return true; case '3': set_view_mode( players[0], BEHIND ); setparam_view_mode( BEHIND ); return true; case 's': screenshot(); return true; case 'p': set_game_mode( PAUSED ); return true; default: if(key==getparam_reset_key()){ set_game_mode( RESET ); return true; } } return false; }
//wich is in this version the "world challenge click callback void practice_click_cb( button_t *button, void *userdata ) { check_assertion( userdata == NULL, "userdata is not null" ); g_game.current_event = NULL; g_game.current_cup = NULL; g_game.current_race = -1; g_game.practicing = True; #ifdef __APPLE__ //usefull for score saving g_game.race.name=NULL; #endif set_game_mode( RACE_SELECT ); ui_set_dirty(); }
static void continue_click_cb( button_t *button, void *userdata ) { cup_data_t *cup_data; player_data_t *plyr = get_player_data( local_player() ); check_assertion( userdata == NULL, "userdata is not null" ); cur_event = listbox_get_current_item( event_listbox ); event_data = (event_data_t*) get_list_elem_data( cur_event ); cur_cup = listbox_get_current_item( cup_listbox ); cup_data = (cup_data_t*) get_list_elem_data( cur_cup ); g_game.current_event = get_event_name( event_data ); g_game.current_cup = get_cup_name( cup_data ); plyr->lives = INIT_NUM_LIVES; set_game_mode( RACE_SELECT ); ui_set_dirty(); }
/*! Callback called when start button is clicked \author jfpatry \date Created: 2000-09-24 \date Modified: 2000-09-24 */ static void start_click_cb( button_t *button, void *userdata ) { check_assertion( userdata == NULL, "userdata is not null" ); button_set_highlight( start_btn, True ); race_select_loop( 0 ); update_race_data(); #ifdef __APPLE__ //set landscape resolution setparam_x_resolution(480); setparam_y_resolution(320); //rotate screen turnScreenToLandscape(); #endif //Select the starting step if (!strcmp(g_game.race.name,"Basic tutorial")) init_starting_tutorial_step(0); if (!strcmp(g_game.race.name,"Jump tutorial")) init_starting_tutorial_step(10); set_game_mode( LOADING ); }
/*! Returns to the game type select screen \author jfpatry \date Created: 2000-09-27 \date Modified: 2000-09-27 */ static void go_back() { set_game_mode( GAME_TYPE_SELECT ); winsys_set_joystick_button_func(NULL); winsys_post_redisplay(); }
/*! Returns to the game type select screen \author jfpatry \date Created: 2000-09-27 \date Modified: 2000-09-27 */ static void go_back() { set_game_mode( GAME_TYPE_SELECT ); winsys_post_redisplay(); }
void Racing::loop(float timeStep) { int width, height; bool joy_left_turn = false; bool joy_right_turn = false; double joy_turn_fact = 0.0; bool joy_paddling = false; bool joy_braking = false; bool joy_tricks = false; bool joy_charging = false; bool airborne; pp::Vec3d dir; float speed; float terrain_weights[NUM_TERRAIN_TYPES]; int new_terrain = 0; int slide_volume; unsigned int i; if (Benchmark::getMode() == Benchmark::AUTO){ m_paddling = true; } dir = players[0].vel; speed = dir.normalize(); //set max_speed if (speed > players[0].max_speed) players[0].max_speed=int(speed); airborne = (bool) ( players[0].pos.y > ( find_y_coord(players[0].pos.x, players[0].pos.z) + JUMP_MAX_START_HEIGHT ) ); width = getparam_x_resolution(); height = getparam_y_resolution(); fpsCounter.update(); update_audio(); clear_rendering_context(); fogPlane.setup(); // Joystick if ( is_joystick_active() ) { float joy_x; float joy_y; update_joystick(); joy_x = get_joystick_x_axis(); joy_y = get_joystick_y_axis(); if ( joy_x > 0.1 ) { joy_right_turn = true; joy_turn_fact = joy_x; } else if ( joy_x < -0.1 ) { joy_left_turn = true; joy_turn_fact = joy_x; } if ( getparam_joystick_brake_button() >= 0 ) { joy_braking = is_joystick_button_down( getparam_joystick_brake_button() ); } if ( !joy_braking ) { joy_braking = (bool) ( joy_y > 0.5 ); } if ( getparam_joystick_paddle_button() >= 0 ) { joy_paddling = is_joystick_button_down( getparam_joystick_paddle_button() ); } if ( !joy_paddling ) { joy_paddling = (bool) ( joy_y < -0.5 ); } if ( getparam_joystick_jump_button() >= 0 ) { joy_charging = is_joystick_button_down( getparam_joystick_jump_button() ); } if ( getparam_joystick_trick_button() >= 0 ) { joy_tricks = is_joystick_button_down( getparam_joystick_trick_button() ); } } // Update braking players[0].control.is_braking = (bool) ( m_braking || joy_braking ); if ( airborne ) { new_terrain = (1<<4); // Tricks if ( m_trickModifier || joy_tricks ) { if ( m_leftTurn || joy_left_turn ) { players[0].control.barrel_roll_left = true; } if ( m_rightTurn || joy_right_turn ) { players[0].control.barrel_roll_right = true; } if ( m_paddling || joy_paddling ) { players[0].control.front_flip = true; } if ( players[0].control.is_braking ) { players[0].control.back_flip = true; } } for(i=0;i<num_terrains;i++){ if ( !terrain_texture[i].sound.empty() && terrain_texture[i].soundactive==true) { halt_sound( terrain_texture[i].sound.c_str() ); terrain_texture[i].soundactive=false; } } } else { get_surface_type(players[0].pos.x, players[0].pos.z, terrain_weights); //Play sliding sound slide_volume = int(MIN( (((pow(players[0].control.turn_fact, 2)*128)) + (players[0].control.is_braking?128:0) + (players[0].control.jumping?128:0) + 20) * (speed/10), 128 )); for(i=0;i<num_terrains;i++){ if ( !terrain_texture[i].sound.empty() ) { if (terrain_weights[i] > 0 ){ set_sound_volume(terrain_texture[i].sound.c_str(), int(slide_volume * terrain_weights[i])); if (terrain_texture[i].soundactive==false){ play_sound(terrain_texture[i].sound.c_str() , -1 ); terrain_texture[i].soundactive=true; } } else if (terrain_texture[i].soundactive==true){ halt_sound( terrain_texture[i].sound.c_str() ); terrain_texture[i].soundactive=false; } } } } // Jumping calcJumpAmt( timeStep ); if ( ( m_charging || joy_charging ) && !players[0].control.jump_charging && !players[0].control.jumping ) { players[0].control.jump_charging = true; m_chargeStartTime = gameMgr->time; } if ( ( !m_charging && !joy_charging ) && players[0].control.jump_charging ) { players[0].control.jump_charging = false; players[0].control.begin_jump = true; } // Turning if ( ( m_leftTurn || joy_left_turn ) ^ (m_rightTurn || joy_right_turn ) ) { bool turning_left = (bool) ( m_leftTurn || joy_left_turn ); if ( joy_left_turn || joy_right_turn ) { players[0].control.turn_fact = joy_turn_fact; } else { players[0].control.turn_fact = (turning_left?-1:1); } players[0].control.turn_animation += (turning_left?-1:1) * 0.15 * timeStep / 0.05; players[0].control.turn_animation = MIN(1.0, MAX(-1.0, players[0].control.turn_animation)); } else { players[0].control.turn_fact = 0; // Decay turn animation if ( timeStep < ROLL_DECAY_TIME_CONSTANT ) { players[0].control.turn_animation *= 1.0 - timeStep/ROLL_DECAY_TIME_CONSTANT; } else { players[0].control.turn_animation = 0.0; } } //Paddling if ( ( m_paddling || joy_paddling ) && players[0].control.is_paddling == false ) { players[0].control.is_paddling = true; players[0].control.paddle_time = gameMgr->time; } //Play flying sound if (new_terrain & (1<<4)) { set_sound_volume("flying_sound", int(MIN(128, speed*2))); if (!(m_lastTerrain & (1<<4))) { play_sound( "flying_sound", -1 ); } } else { if (m_lastTerrain & (1<<4)) { halt_sound( "flying_sound" ); } } m_lastTerrain = new_terrain; //Tricks if ( players[0].control.barrel_roll_left || players[0].control.barrel_roll_right ) { players[0].control.barrel_roll_factor += ( players[0].control.barrel_roll_left ? -1 : 1 ) * 0.15 * timeStep / 0.05; if ( (players[0].control.barrel_roll_factor > 1) || (players[0].control.barrel_roll_factor < -1) ) { players[0].control.barrel_roll_factor = 0; players[0].control.barrel_roll_left = players[0].control.barrel_roll_right = false; } } if ( players[0].control.front_flip || players[0].control.back_flip ) { players[0].control.flip_factor += ( players[0].control.back_flip ? -1 : 1 ) * 0.15 * timeStep / 0.05; if ( (players[0].control.flip_factor > 1) || (players[0].control.flip_factor < -1) ) { players[0].control.flip_factor = 0; players[0].control.front_flip = players[0].control.back_flip = false; } } update_player_pos( players[0], timeStep ); //Track Marks add_track_mark( players[0] ); update_view( players[0], timeStep ); setup_view_frustum( players[0], NEAR_CLIP_DIST, getparam_forward_clip_distance() ); draw_sky(players[0].view.pos); draw_fog_plane(); set_course_clipping( true ); set_course_eye_point( players[0].view.pos ); setup_course_lighting(); render_course(); //Draw snow update_snow( timeStep, false, players[0].view.pos ); draw_snow(players[0].view.pos); draw_trees(); if ( getparam_draw_particles() ) { update_particles( timeStep ); draw_particles( players[0] ); } ModelHndl->draw_tux(); draw_tux_shadow(); HUD1.draw(players[0]); reshape( width, height ); winsys_swap_buffers(); gameMgr->time += timeStep; if (airborne) gameMgr->airbornetime += timeStep; if(Benchmark::getMode() == Benchmark::PAUSED){ set_game_mode(PAUSED); } }
int main( int argc, char **argv ) { /* Print copyright notice */ fprintf( stderr, "Tux Rider World Challenge -- http://www.barlow-server.com\n" "a fork from:\n" "Tux Racer " VERSION " -- a Sunspire Studios Production " "(http://www.sunspirestudios.com)\n" "(c) 1999-2000 Jasmin F. Patry " "<*****@*****.**>\n" "\"Tux Racer\" is a trademark of Jasmin F. Patry\n" "Tux Rider World Challenge comes with ABSOLUTELY NO WARRANTY. " "This is free software,\nand you are welcome to redistribute " "it under certain conditions.\n" "See http://www.gnu.org/copyleft/gpl.html for details.\n\n" ); /* Init the game clock */ g_game.secs_since_start = 0; /* Seed the random number generator */ srand( time(NULL) ); /* * Set up the game configuration */ /* Don't support multiplayer, yet... */ g_game.num_players = 2; /* Create a Tcl interpreter */ g_game.tcl_interp = Tcl_CreateInterp(); if ( g_game.tcl_interp == NULL ) { handle_error( 1, "cannot create Tcl interpreter" ); } /* Setup the configuration variables and read the ~/.tuxracer/options file */ init_game_configuration(); read_config_file(); /* Set up the debugging modes */ init_debug(); /* Setup diagnostic log if requested */ if ( getparam_write_diagnostic_log() ) { setup_diagnostic_log(); } /* * Setup Tcl stdout and stderr channels to point to C stdout and stderr * streams */ setup_tcl_std_channels(); /* * Initialize rendering context, create window */ winsys_init( &argc, argv, WINDOW_TITLE, WINDOW_TITLE ); /* Ingore key-repeat messages */ winsys_enable_key_repeat(0); /* Set up a function to clean up when program exits */ winsys_atexit( cleanup ); /* * Initial OpenGL settings */ glBlendFunc( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA ); init_opengl_extensions(); /* Print OpenGL debugging information if requested */ if ( debug_mode_is_active( DEBUG_GL_INFO ) ) { print_debug( DEBUG_GL_INFO, "OpenGL information:" ); print_gl_info(); } /* * Load the game data and initialize game state */ register_game_config_callbacks( g_game.tcl_interp ); register_course_load_tcl_callbacks( g_game.tcl_interp ); register_key_frame_callbacks( g_game.tcl_interp ); register_fog_callbacks( g_game.tcl_interp ); register_course_light_callbacks( g_game.tcl_interp ); register_particle_callbacks( g_game.tcl_interp ); register_texture_callbacks( g_game.tcl_interp ); register_font_callbacks( g_game.tcl_interp ); register_sound_tcl_callbacks( g_game.tcl_interp ); register_sound_data_tcl_callbacks( g_game.tcl_interp ); register_course_manager_callbacks( g_game.tcl_interp ); init_saved_games(); load_tux(); init_textures(); init_fonts(); init_audio_data(); init_audio(); init_ui_manager(); init_course_manager(); init_joystick(); /* Read the tuxracer_init.tcl file */ read_game_init_script(); /* Need to set up an initial view position for select_course (quadtree simplification) */ //Player 0 = classic mode player ; Player 1 = Speed Only Mode Player g_game.player[0].view.pos = make_point( 0., 0., 0. ); g_game.player[1].view.pos = make_point( 0., 0., 0. ); /* Placeholder name until we give players way to enter name */ g_game.player[0].name = "noname"; g_game.player[1].name = "nonameSpeedOnly"; init_preview(); splash_screen_register(); intro_register(); racing_register(); game_over_register(); paused_register(); reset_register(); game_type_select_register(); racing_mode_select_register(); event_select_register(); race_select_register(); credits_register(); loading_register(); g_game.mode = NO_MODE; set_game_mode( SPLASH ); g_game.difficulty = DIFFICULTY_LEVEL_NORMAL; init_keyboard(); winsys_show_cursor( False ); /* We use this to "prime" the GLUT loop */ winsys_set_idle_func( main_loop ); /* * ...and off we go! */ winsys_process_events(); return 0; }
void Paused::configuration() { set_game_mode( CONFIGURATION ); UIMgr.setDirty(); }
void Paused::quit() { gameMgr->abortRace(); set_game_mode( GAME_OVER ); }
void Paused::resume() { set_game_mode( RACING ); winsys_post_redisplay(); }
void update_key_frame( player_data_t *plyr, scalar_t dt ) { int idx; scalar_t frac; point_t pos; scalar_t v; matrixgl_t cob_mat, rot_mat; char *root; char *lsh; char *rsh; char *lhp; char *rhp; char *lkn; char *rkn; char *lank; char *rank; char *head; char *neck; char *tail; root = get_tux_root_node(); lsh = get_tux_left_shoulder_joint(); rsh = get_tux_right_shoulder_joint(); lhp = get_tux_left_hip_joint(); rhp = get_tux_right_hip_joint(); lkn = get_tux_left_knee_joint(); rkn = get_tux_right_knee_joint(); lank = get_tux_left_ankle_joint(); rank = get_tux_right_ankle_joint(); head = get_tux_head(); neck = get_tux_neck(); tail = get_tux_tail_joint(); keyTime += dt; for (idx = 1; idx < numFrames; idx ++) { if ( keyTime < frames[idx].time ) break; } if ( idx == numFrames || numFrames == 0 ) { set_game_mode( RACING ); return; } reset_scene_node( root ); reset_scene_node( lsh ); reset_scene_node( rsh ); reset_scene_node( lhp ); reset_scene_node( rhp ); reset_scene_node( lkn ); reset_scene_node( rkn ); reset_scene_node( lank ); reset_scene_node( rank ); reset_scene_node( head ); reset_scene_node( neck ); reset_scene_node( tail ); check_assertion( idx > 0, "invalid keyframe index" ); if ( fabs( frames[idx-1].time - frames[idx].time ) < EPS ) { frac = 1.; } else { frac = (keyTime - frames[idx].time) / ( frames[idx-1].time - frames[idx].time ); } pos.x = interp( frac, frames[idx-1].pos.x, frames[idx].pos.x ); pos.z = interp( frac, frames[idx-1].pos.z, frames[idx].pos.z ); pos.y = interp( frac, frames[idx-1].pos.y, frames[idx].pos.y ); pos.y += find_y_coord( pos.x, pos.z ); set_tux_pos( plyr, pos ); make_identity_matrix( cob_mat ); v = interp( frac, frames[idx-1].yaw, frames[idx].yaw ); rotate_scene_node( root, 'y', v ); make_rotation_matrix( rot_mat, v, 'y' ); multiply_matrices( cob_mat, cob_mat, rot_mat ); v = interp( frac, frames[idx-1].pitch, frames[idx].pitch ); rotate_scene_node( root, 'x', v ); make_rotation_matrix( rot_mat, v, 'x' ); multiply_matrices( cob_mat, cob_mat, rot_mat ); v = interp( frac, frames[idx-1].l_shldr, frames[idx].l_shldr ); rotate_scene_node( lsh, 'z', v ); v = interp( frac, frames[idx-1].r_shldr, frames[idx].r_shldr ); rotate_scene_node( rsh, 'z', v ); v = interp( frac, frames[idx-1].l_hip, frames[idx].l_hip ); rotate_scene_node( lhp, 'z', v ); v = interp( frac, frames[idx-1].r_hip, frames[idx].r_hip ); rotate_scene_node( rhp, 'z', v ); /* Set orientation */ plyr->orientation = make_quaternion_from_matrix( cob_mat ); plyr->orientation_initialized = True; }
void game_over_loop( scalar_t time_step ) { player_data_t *plyr = get_player_data( local_player() ); int width, height; width = getparam_x_resolution(); height = getparam_y_resolution(); check_gl_error(); /* Check joystick */ if ( is_joystick_active() ) { update_joystick(); if ( is_joystick_continue_button_down() ) { set_game_mode( NEXT_MODE ); winsys_post_redisplay(); return; } } new_frame_for_fps_calc(); update_audio(); clear_rendering_context(); setup_fog(); update_player_pos( plyr, 0 ); update_view( plyr, 0 ); setup_view_frustum( plyr, NEAR_CLIP_DIST, getparam_forward_clip_distance() ); draw_sky(plyr->view.pos); draw_fog_plane(); set_course_clipping( True ); set_course_eye_point( plyr->view.pos ); setup_course_lighting(); render_course(); draw_trees(); if ( getparam_draw_particles() ) { draw_particles( plyr ); } draw_tux(); draw_tux_shadow(); set_gl_options( GUI ); ui_setup_display(); draw_game_over_text(); #ifndef __APPLE__ draw_hud( plyr ); #endif draw_hud_training(plyr); reshape( width, height ); winsys_swap_buffers(); }