on windows too: call resize callback only in response to WM message
[freeglut] / src / fg_main.c
index c3bccdc..2bc8435 100644 (file)
@@ -74,14 +74,6 @@ static void fghReshapeWindow ( SFG_Window *window, int width, int height )
 
        fgPlatformReshapeWindow ( window, width, height );
 
-    if( FETCH_WCB( *window, Reshape ) )
-        INVOKE_WCB( *window, Reshape, ( width, height ) );
-    else
-    {
-        fgSetWindow( window );
-        glViewport( 0, 0, width, height );
-    }
-
     /*
      * Force a window redraw.  In Windows at least this is only a partial
      * solution:  if the window is increasing in size in either dimension,
@@ -172,15 +164,21 @@ static void fghDisplayAll( void )
 static void fghcbCheckJoystickPolls( SFG_Window *window,
                                      SFG_Enumerator *enumerator )
 {
-    fg_time_t checkTime = fgElapsedTime( );
-
-    if( window->State.JoystickLastPoll + window->State.JoystickPollRate <=
-        checkTime )
+    fg_time_t checkTime;
+    
+    if (window->State.JoystickPollRate > 0 && FETCH_WCB( *window, Joystick ))
     {
+        /* This window has a joystick to be polled (if pollrate <= 0, user needs to poll manually with glutForceJoystickFunc */
+        checkTime= fgElapsedTime( );
+
+        if( window->State.JoystickLastPoll + window->State.JoystickPollRate <=
+            checkTime )
+        {
 #if !defined(_WIN32_WCE)
-        fgJoystickPollWindow( window );
+            fgJoystickPollWindow( window );
 #endif /* !defined(_WIN32_WCE) */
-        window->State.JoystickLastPoll = checkTime;
+            window->State.JoystickLastPoll = checkTime;
+        }
     }
 
     fgEnumSubWindows( window, fghcbCheckJoystickPolls, enumerator );
@@ -188,6 +186,10 @@ static void fghcbCheckJoystickPolls( SFG_Window *window,
 
 /*
  * Check all windows for joystick polling
+ * 
+ * The real way to do this is to make use of the glutTimer() API
+ * to more cleanly re-implement the joystick API.  Then, this code
+ * and all other "joystick timer" code can be yanked.
  */
 static void fghCheckJoystickPolls( void )
 {
@@ -211,6 +213,7 @@ static void fghCheckTimers( void )
         SFG_Timer *timer = fgState.Timers.First;
 
         if( timer->TriggerTime > checkTime )
+            /* XXX: are timers always sorted by triggerTime? If not, this and fghNextTimer are wrong */
             break;
 
         fgListRemove( &fgState.Timers, &timer->Node );
@@ -224,12 +227,8 @@ static void fghCheckTimers( void )
 /* Platform-dependent time in milliseconds, as an unsigned 64-bit integer.
  * This doesn't overflow in any reasonable time, so no need to worry about
  * that. The GLUT API return value will however overflow after 49.7 days,
- * and on Windows we (currently) do not have access to a 64-bit timestamp,
- * which means internal time will still get in trouble when running the
+ * which means you will still get in trouble when running the
  * application for more than 49.7 days.
- * This value wraps every 49.7 days, but integer overflows cancel
- * when subtracting an initial start time, unless the total time exceeds
- * 32-bit, where the GLUT API return value is also overflowed.
  */  
 fg_time_t fgSystemTime(void)
 {
@@ -261,7 +260,7 @@ void fgError( const char *fmt, ... )
         va_end( ap );
 
     } else {
-
+#if FREEGLUT_ERRORS
         va_start( ap, fmt );
 
         fprintf( stderr, "freeglut ");
@@ -271,6 +270,7 @@ void fgError( const char *fmt, ... )
         fprintf( stderr, "\n" );
 
         va_end( ap );
+#endif
 
         if ( fgState.Initialised )
             fgDeinitialize ();
@@ -293,7 +293,7 @@ void fgWarning( const char *fmt, ... )
         va_end( ap );
 
     } else {
-
+#if FREEGLUT_WARNINGS
         va_start( ap, fmt );
 
         fprintf( stderr, "freeglut ");
@@ -303,46 +303,25 @@ void fgWarning( const char *fmt, ... )
         fprintf( stderr, "\n" );
 
         va_end( ap );
+#endif
     }
 }
 
 
 /*
- * Indicates whether Joystick events are being used by ANY window.
+ * Indicates whether a redisplay is pending for ANY window.
  *
  * The current mechanism is to walk all of the windows and ask if
- * there is a joystick callback.  We have a short-circuit early
- * return if we find any joystick handler registered.
- *
- * The real way to do this is to make use of the glutTimer() API
- * to more cleanly re-implement the joystick API.  Then, this code
- * and all other "joystick timer" code can be yanked.
- *
+ * a redisplay is pending. We have a short-circuit early
+ * return if we find any.
  */
-static void fghCheckJoystickCallback( SFG_Window* w, SFG_Enumerator* e)
-{
-    if( FETCH_WCB( *w, Joystick ) )
-    {
-        e->found = GL_TRUE;
-        e->data = w;
-    }
-    fgEnumSubWindows( w, fghCheckJoystickCallback, e );
-}
-static int fghHaveJoystick( void )
-{
-    SFG_Enumerator enumerator;
-
-    enumerator.found = GL_FALSE;
-    enumerator.data = NULL;
-    fgEnumWindows( fghCheckJoystickCallback, &enumerator );
-    return !!enumerator.data;
-}
 static void fghHavePendingRedisplaysCallback( SFG_Window* w, SFG_Enumerator* e)
 {
     if( w->State.Redisplay && w->State.Visible )
     {
         e->found = GL_TRUE;
         e->data = w;
+        return;
     }
     fgEnumSubWindows( w, fghHavePendingRedisplaysCallback, e );
 }
@@ -355,6 +334,7 @@ static int fghHavePendingRedisplays (void)
     fgEnumWindows( fghHavePendingRedisplaysCallback, &enumerator );
     return !!enumerator.data;
 }
+
 /*
  * Returns the number of GLUT ticks (milliseconds) till the next timer event.
  */
@@ -376,13 +356,13 @@ static void fghSleepForEvents( void )
 {
     fg_time_t msec;
 
-    if( fgState.IdleCallback || fghHavePendingRedisplays( ) )
+    if( fghHavePendingRedisplays( ) )
         return;
 
     msec = fghNextTimer( );
-    /* XXX Use GLUT timers for joysticks... */
+    /* XXX Should use GLUT timers for joysticks... */
     /* XXX Dumb; forces granularity to .01sec */
-    if( fghHaveJoystick( ) && ( msec > 10 ) )     
+    if( fgState.NumActiveJoysticks>0 && ( msec > 10 ) )     
         msec = 10;
 
        fgPlatformSleepForEvents ( msec );
@@ -400,7 +380,8 @@ void FGAPIENTRY glutMainLoopEvent( void )
 
     if( fgState.Timers.First )
         fghCheckTimers( );
-    fghCheckJoystickPolls( );
+    if (fgState.NumActiveJoysticks>0)   /* If zero, don't poll joysticks */
+        fghCheckJoystickPolls( );
     fghDisplayAll( );
 
     fgCloseWindows( );
@@ -416,6 +397,9 @@ void FGAPIENTRY glutMainLoop( void )
 
     FREEGLUT_EXIT_IF_NOT_INITIALISED ( "glutMainLoop" );
 
+    if (!fgStructure.Windows.First)
+        fgError(" ERROR:  glutMainLoop called with no windows created.");
+
        fgPlatformMainLoopPreliminaryWork ();
 
     fgState.ExecState = GLUT_EXEC_STATE_RUNNING ;
@@ -446,8 +430,8 @@ void FGAPIENTRY glutMainLoop( void )
                     fgSetWindow( window );
                 fgState.IdleCallback( );
             }
-
-            fghSleepForEvents( );
+            else
+                fghSleepForEvents( );
         }
     }