Implemented gamma correction on Windows. SDL-1.3
authorSam Lantinga <slouken@libsdl.org>
Sun, 09 Jul 2006 09:02:26 +0000
branchSDL-1.3
changeset 17330b1070f2f94d
parent 1732 fd65f12b6de6
child 1734 f7c667ded87d
Implemented gamma correction on Windows.
Added general code to restore the video mode and gamma when windows lose focus.
include/SDL_video.h
src/SDL_compat.c
src/events/SDL_windowevents.c
src/video/SDL_gamma.c
src/video/SDL_sysvideo.h
src/video/SDL_video.c
src/video/win32/SDL_win32events.c
src/video/win32/SDL_win32gamma.c
src/video/win32/SDL_win32gamma.h
src/video/win32/SDL_win32modes.c
src/video/win32/SDL_win32modes.h
src/video/win32/SDL_win32video.c
src/video/win32/SDL_win32video.h
src/video/win32/SDL_win32window.c
test/testsprite2.c
test/testwm2.c
     1.1 --- a/include/SDL_video.h	Sat Jul 08 20:55:39 2006 +0000
     1.2 +++ b/include/SDL_video.h	Sun Jul 09 09:02:26 2006 +0000
     1.3 @@ -98,6 +98,7 @@
     1.4   * \sa SDL_RaiseWindow()
     1.5   * \sa SDL_RestoreWindow()
     1.6   * \sa SDL_SetWindowData()
     1.7 + * \sa SDL_SetWindowFullscreen()
     1.8   * \sa SDL_SetWindowGrab()
     1.9   * \sa SDL_SetWindowIcon()
    1.10   * \sa SDL_SetWindowPosition()
    1.11 @@ -474,15 +475,28 @@
    1.12                                                                     * closest);
    1.13  
    1.14  /**
    1.15 - * \fn int SDL_SetDisplayMode(const SDL_DisplayMode *mode)
    1.16 + * \fn int SDL_SetFullscreenDisplayMode(const SDL_DisplayMode *mode)
    1.17   *
    1.18 - * \brief Set up the closest available mode on the current display.
    1.19 + * \brief Set the display mode used when a fullscreen window is visible
    1.20 + *        on the currently selected display.
    1.21   *
    1.22 - * \param mode The desired display mode, or NULL to set the desktop mode.
    1.23 + * \param mode The mode to use, or NULL for the desktop mode.
    1.24   *
    1.25   * \return 0 on success, or -1 if setting the display mode failed.
    1.26 + *
    1.27 + * \sa SDL_SetWindowFullscreen()
    1.28   */
    1.29 -extern DECLSPEC int SDLCALL SDL_SetDisplayMode(const SDL_DisplayMode * mode);
    1.30 +extern DECLSPEC int SDLCALL SDL_SetFullscreenDisplayMode(const SDL_DisplayMode
    1.31 +                                                         * mode);
    1.32 +
    1.33 +/**
    1.34 + * \fn const SDL_DisplayMode *SDL_GetFullscreenDisplayMode(void)
    1.35 + *
    1.36 + * \brief Query the display mode used when a fullscreen window is visible
    1.37 + *        on the currently selected display.
    1.38 + */
    1.39 +extern DECLSPEC const SDL_DisplayMode *SDLCALL
    1.40 +SDL_GetFullscreenDisplayMode(void);
    1.41  
    1.42  /**
    1.43   * \fn int SDL_SetDisplayPalette(const SDL_Color *colors, int firstcolor, int ncolors)
    1.44 @@ -507,6 +521,57 @@
    1.45                                                    int ncolors);
    1.46  
    1.47  /**
    1.48 + * \fn int SDL_SetGamma(float red, float green, float blue)
    1.49 + *
    1.50 + * \brief Set the gamma correction for each of the color channels on the currently selected display.
    1.51 + *
    1.52 + * \return 0 on success, or -1 if setting the gamma isn't supported.
    1.53 + *
    1.54 + * \sa SDL_SetGammaRamp()
    1.55 + */
    1.56 +extern DECLSPEC int SDLCALL SDL_SetGamma(float red, float green, float blue);
    1.57 +
    1.58 +/**
    1.59 + * \fn int SDL_SetGammaRamp(const Uint16 * red, const Uint16 * green, const Uint16 * blue)
    1.60 + *
    1.61 + * \brief Set the gamma ramp for the currently selected display.
    1.62 + *
    1.63 + * \param red The translation table for the red channel, or NULL
    1.64 + * \param green The translation table for the green channel, or NULL
    1.65 + * \param blue The translation table for the blue channel, or NULL
    1.66 + *
    1.67 + * \return 0 on success, or -1 if gamma ramps are unsupported.
    1.68 + *
    1.69 + * Set the gamma translation table for the red, green, and blue channels
    1.70 + * of the video hardware.  Each table is an array of 256 16-bit quantities,
    1.71 + * representing a mapping between the input and output for that channel.
    1.72 + * The input is the index into the array, and the output is the 16-bit
    1.73 + * gamma value at that index, scaled to the output color precision.
    1.74 + * 
    1.75 + * \sa SDL_GetGammaRamp()
    1.76 + */
    1.77 +extern DECLSPEC int SDLCALL SDL_SetGammaRamp(const Uint16 * red,
    1.78 +                                             const Uint16 * green,
    1.79 +                                             const Uint16 * blue);
    1.80 +
    1.81 +/**
    1.82 + * \fn int SDL_GetGammaRamp(Uint16 * red, Uint16 * green, Uint16 * blue)
    1.83 + *
    1.84 + * \brief Get the gamma ramp for the currently selected display.
    1.85 + *
    1.86 + * \param red A pointer to a 256 element array of 16-bit quantities to hold the translation table for the red channel, or NULL.
    1.87 + * \param green A pointer to a 256 element array of 16-bit quantities to hold the translation table for the green channel, or NULL.
    1.88 + * \param blue A pointer to a 256 element array of 16-bit quantities to hold the translation table for the blue channel, or NULL.
    1.89 + * 
    1.90 + * \return 0 on success, or -1 if gamma ramps are unsupported.
    1.91 + *
    1.92 + * \sa SDL_SetGammaRamp()
    1.93 + */
    1.94 +extern DECLSPEC int SDLCALL SDL_GetGammaRamp(Uint16 * red, Uint16 * green,
    1.95 +                                             Uint16 * blue);
    1.96 +
    1.97 +
    1.98 +/**
    1.99   * \fn SDL_WindowID SDL_CreateWindow(const char *title, int x, int y, int w, int h, Uint32 flags)
   1.100   *
   1.101   * \brief Create a window with the specified position, dimensions, and flags.
   1.102 @@ -516,7 +581,7 @@
   1.103   * \param y The y position of the window
   1.104   * \param w The width of the window
   1.105   * \param h The height of the window
   1.106 - * \param flags The flags for the window
   1.107 + * \param flags The flags for the window, a mask of any of the following: SDL_WINDOW_FULLSCREEN, SDL_WINDOW_OPENGL, SDL_WINDOW_SHOWN, SDL_WINDOW_BORDERLESS, SDL_WINDOW_RESIZABLE, SDL_WINDOW_MAXIMIZED, SDL_WINDOW_MINIMIZED, SDL_WINDOW_INPUT_GRABBED
   1.108   *
   1.109   * \return The id of the window created, or zero if window creation failed.
   1.110   *
   1.111 @@ -702,13 +767,24 @@
   1.112  extern DECLSPEC void SDLCALL SDL_RestoreWindow(SDL_WindowID windowID);
   1.113  
   1.114  /**
   1.115 + * \fn int SDL_SetWindowFullscreen(SDL_WindowID windowID, int fullscreen)
   1.116 + *
   1.117 + * \brief Set the window's fullscreen state.
   1.118 + *
   1.119 + * \return 0 on success, or -1 if setting the display mode failed.
   1.120 + *
   1.121 + * \sa SDL_SetFullscreenDisplayMode()
   1.122 + */
   1.123 +extern DECLSPEC int SDLCALL SDL_SetWindowFullscreen(SDL_WindowID windowID,
   1.124 +                                                    int fullscreen);
   1.125 +
   1.126 +/**
   1.127   * \fn void SDL_SetWindowGrab(SDL_WindowID windowID, int mode)
   1.128   *
   1.129   * \brief Set the window's input grab mode.
   1.130   *
   1.131   * \param mode This is 1 to grab input, and 0 to release input.
   1.132   *
   1.133 - * \sa SDL_GrabMode
   1.134   * \sa SDL_GetWindowGrab()
   1.135   */
   1.136  extern DECLSPEC void SDLCALL SDL_SetWindowGrab(SDL_WindowID windowID,
   1.137 @@ -721,7 +797,6 @@
   1.138   *
   1.139   * \return This returns 1 if input is grabbed, and 0 otherwise.
   1.140   *
   1.141 - * \sa SDL_GrabMode
   1.142   * \sa SDL_SetWindowGrab()
   1.143   */
   1.144  extern DECLSPEC int SDLCALL SDL_GetWindowGrab(SDL_WindowID windowID);
   1.145 @@ -1070,44 +1145,6 @@
   1.146  extern DECLSPEC void SDLCALL SDL_DestroyRenderer(SDL_WindowID windowID);
   1.147  
   1.148  /*
   1.149 - * Set the gamma correction for each of the color channels.
   1.150 - * The gamma values range (approximately) between 0.1 and 10.0
   1.151 - * 
   1.152 - * If this function isn't supported directly by the hardware, it will
   1.153 - * be emulated using gamma ramps, if available.  If successful, this
   1.154 - * function returns 0, otherwise it returns -1.
   1.155 - */
   1.156 -extern DECLSPEC int SDLCALL SDL_SetGamma(float red, float green, float blue);
   1.157 -
   1.158 -/*
   1.159 - * Set the gamma translation table for the red, green, and blue channels
   1.160 - * of the video hardware.  Each table is an array of 256 16-bit quantities,
   1.161 - * representing a mapping between the input and output for that channel.
   1.162 - * The input is the index into the array, and the output is the 16-bit
   1.163 - * gamma value at that index, scaled to the output color precision.
   1.164 - * 
   1.165 - * You may pass NULL for any of the channels to leave it unchanged.
   1.166 - * If the call succeeds, it will return 0.  If the display driver or
   1.167 - * hardware does not support gamma translation, or otherwise fails,
   1.168 - * this function will return -1.
   1.169 - */
   1.170 -extern DECLSPEC int SDLCALL SDL_SetGammaRamp(const Uint16 * red,
   1.171 -                                             const Uint16 * green,
   1.172 -                                             const Uint16 * blue);
   1.173 -
   1.174 -/*
   1.175 - * Retrieve the current values of the gamma translation tables.
   1.176 - * 
   1.177 - * You must pass in valid pointers to arrays of 256 16-bit quantities.
   1.178 - * Any of the pointers may be NULL to ignore that channel.
   1.179 - * If the call succeeds, it will return 0.  If the display driver or
   1.180 - * hardware does not support gamma translation, or otherwise fails,
   1.181 - * this function will return -1.
   1.182 - */
   1.183 -extern DECLSPEC int SDLCALL SDL_GetGammaRamp(Uint16 * red, Uint16 * green,
   1.184 -                                             Uint16 * blue);
   1.185 -
   1.186 -/*
   1.187   * Maps an RGB triple to an opaque pixel value for a given pixel format
   1.188   */
   1.189  extern DECLSPEC Uint32 SDLCALL SDL_MapRGB
     2.1 --- a/src/SDL_compat.c	Sat Jul 08 20:55:39 2006 +0000
     2.2 +++ b/src/SDL_compat.c	Sun Jul 09 09:02:26 2006 +0000
     2.3 @@ -360,9 +360,8 @@
     2.4      if (flags & SDL_NOFRAME) {
     2.5          window_flags |= SDL_WINDOW_BORDERLESS;
     2.6      }
     2.7 -    if (SDL_getenv("SDL_WINDOW_POS")) {
     2.8 -    }
     2.9      GetEnvironmentWindowPosition(width, height, &window_x, &window_y);
    2.10 +    SDL_SetFullscreenDisplayMode(NULL);
    2.11      SDL_VideoWindow =
    2.12          SDL_CreateWindow(wm_title, window_x, window_y, width, height,
    2.13                           window_flags);
    2.14 @@ -427,21 +426,9 @@
    2.15  
    2.16      /* Set the desired display mode */
    2.17      if (flags & SDL_FULLSCREEN) {
    2.18 -        if (!SDL_GetClosestDisplayMode(&mode, &mode)) {
    2.19 +        if (SDL_SetFullscreenDisplayMode(&mode) < 0) {
    2.20              return NULL;
    2.21          }
    2.22 -    } else {
    2.23 -        if (desktop_format) {
    2.24 -            mode.format = desktop_format;
    2.25 -        }
    2.26 -        if (desktop_mode->w && desktop_mode->h) {
    2.27 -            mode.w = desktop_mode->w;
    2.28 -            mode.h = desktop_mode->h;
    2.29 -        }
    2.30 -        mode.refresh_rate = desktop_mode->refresh_rate;
    2.31 -    }
    2.32 -    if (SDL_SetDisplayMode(&mode) < 0) {
    2.33 -        return NULL;
    2.34      }
    2.35  
    2.36      /* If we're in OpenGL mode, just create a stub surface and we're done! */
     3.1 --- a/src/events/SDL_windowevents.c	Sat Jul 08 20:55:39 2006 +0000
     3.2 +++ b/src/events/SDL_windowevents.c	Sun Jul 09 09:02:26 2006 +0000
     3.3 @@ -44,19 +44,27 @@
     3.4              return 0;
     3.5          }
     3.6          window->flags |= SDL_WINDOW_SHOWN;
     3.7 +        SDL_OnWindowShown(window);
     3.8          break;
     3.9      case SDL_WINDOWEVENT_HIDDEN:
    3.10          if (!(window->flags & SDL_WINDOW_SHOWN)) {
    3.11              return 0;
    3.12          }
    3.13          window->flags &= ~SDL_WINDOW_SHOWN;
    3.14 +        SDL_OnWindowHidden(window);
    3.15          break;
    3.16      case SDL_WINDOWEVENT_MOVED:
    3.17 +        if (window->flags & SDL_WINDOW_FULLSCREEN) {
    3.18 +            return 0;
    3.19 +        }
    3.20          if (data1 == window->x && data2 == window->y) {
    3.21              return 0;
    3.22          }
    3.23          break;
    3.24      case SDL_WINDOWEVENT_RESIZED:
    3.25 +        if (window->flags & SDL_WINDOW_FULLSCREEN) {
    3.26 +            return 0;
    3.27 +        }
    3.28          if (data1 == window->w && data2 == window->h) {
    3.29              return 0;
    3.30          }
    3.31 @@ -96,12 +104,14 @@
    3.32              return 0;
    3.33          }
    3.34          window->flags |= SDL_WINDOW_KEYBOARD_FOCUS;
    3.35 +        SDL_OnWindowFocusGained(window);
    3.36          break;
    3.37      case SDL_WINDOWEVENT_FOCUS_LOST:
    3.38          if (!(window->flags & SDL_WINDOW_KEYBOARD_FOCUS)) {
    3.39              return 0;
    3.40          }
    3.41          window->flags &= ~SDL_WINDOW_KEYBOARD_FOCUS;
    3.42 +        SDL_OnWindowFocusLost(window);
    3.43          break;
    3.44      }
    3.45  
     4.1 --- a/src/video/SDL_gamma.c	Sat Jul 08 20:55:39 2006 +0000
     4.2 +++ b/src/video/SDL_gamma.c	Sun Jul 09 09:02:26 2006 +0000
     4.3 @@ -96,24 +96,13 @@
     4.4  int
     4.5  SDL_SetGamma(float red, float green, float blue)
     4.6  {
     4.7 -    SDL_VideoDevice *_this = SDL_GetVideoDevice();
     4.8 -    int succeeded;
     4.9 +    Uint16 ramp[3][256];
    4.10  
    4.11 -    succeeded = -1;
    4.12 -    /* Prefer using SetGammaRamp(), as it's more flexible */
    4.13 -    {
    4.14 -        Uint16 ramp[3][256];
    4.15 +    CalculateGammaRamp(red, ramp[0]);
    4.16 +    CalculateGammaRamp(green, ramp[1]);
    4.17 +    CalculateGammaRamp(blue, ramp[2]);
    4.18  
    4.19 -        CalculateGammaRamp(red, ramp[0]);
    4.20 -        CalculateGammaRamp(green, ramp[1]);
    4.21 -        CalculateGammaRamp(blue, ramp[2]);
    4.22 -        succeeded = SDL_SetGammaRamp(ramp[0], ramp[1], ramp[2]);
    4.23 -    }
    4.24 -    if ((succeeded < 0) && _this && _this->SetGamma) {
    4.25 -        SDL_ClearError();
    4.26 -        succeeded = _this->SetGamma(_this, red, green, blue);
    4.27 -    }
    4.28 -    return succeeded;
    4.29 +    return SDL_SetGammaRamp(ramp[0], ramp[1], ramp[2]);
    4.30  }
    4.31  
    4.32  /* Calculating the gamma by integrating the gamma ramps isn't exact,
    4.33 @@ -122,24 +111,14 @@
    4.34  int
    4.35  SDL_GetGamma(float *red, float *green, float *blue)
    4.36  {
    4.37 -    SDL_VideoDevice *_this = SDL_GetVideoDevice();
    4.38      int succeeded;
    4.39 +    Uint16 ramp[3][256];
    4.40  
    4.41 -    succeeded = -1;
    4.42 -    /* Prefer using GetGammaRamp(), as it's more flexible */
    4.43 -    {
    4.44 -        Uint16 ramp[3][256];
    4.45 -
    4.46 -        succeeded = SDL_GetGammaRamp(ramp[0], ramp[1], ramp[2]);
    4.47 -        if (succeeded >= 0) {
    4.48 -            CalculateGammaFromRamp(red, ramp[0]);
    4.49 -            CalculateGammaFromRamp(green, ramp[1]);
    4.50 -            CalculateGammaFromRamp(blue, ramp[2]);
    4.51 -        }
    4.52 -    }
    4.53 -    if ((succeeded < 0) && _this && _this->GetGamma) {
    4.54 -        SDL_ClearError();
    4.55 -        succeeded = _this->GetGamma(_this, red, green, blue);
    4.56 +    succeeded = SDL_GetGammaRamp(ramp[0], ramp[1], ramp[2]);
    4.57 +    if (succeeded >= 0) {
    4.58 +        CalculateGammaFromRamp(red, ramp[0]);
    4.59 +        CalculateGammaFromRamp(green, ramp[1]);
    4.60 +        CalculateGammaFromRamp(blue, ramp[2]);
    4.61      }
    4.62      return succeeded;
    4.63  }
    4.64 @@ -152,28 +131,29 @@
    4.65      int succeeded;
    4.66  
    4.67      /* Lazily allocate the gamma tables */
    4.68 -    if (!SDL_CurrentWindow.gamma) {
    4.69 -        SDL_GetGammaRamp(0, 0, 0);
    4.70 +    if (!SDL_CurrentDisplay.gamma) {
    4.71 +        SDL_GetGammaRamp(NULL, NULL, NULL);
    4.72      }
    4.73  
    4.74      /* Fill the gamma table with the new values */
    4.75      if (red) {
    4.76 -        SDL_memcpy(&SDL_CurrentWindow.gamma[0 * 256], red,
    4.77 -                   256 * sizeof(*SDL_CurrentWindow.gamma));
    4.78 +        SDL_memcpy(&SDL_CurrentDisplay.gamma[0 * 256], red,
    4.79 +                   256 * sizeof(*SDL_CurrentDisplay.gamma));
    4.80      }
    4.81      if (green) {
    4.82 -        SDL_memcpy(&SDL_CurrentWindow.gamma[1 * 256], green,
    4.83 -                   256 * sizeof(*SDL_CurrentWindow.gamma));
    4.84 +        SDL_memcpy(&SDL_CurrentDisplay.gamma[1 * 256], green,
    4.85 +                   256 * sizeof(*SDL_CurrentDisplay.gamma));
    4.86      }
    4.87      if (blue) {
    4.88 -        SDL_memcpy(&SDL_CurrentWindow.gamma[2 * 256], blue,
    4.89 -                   256 * sizeof(*SDL_CurrentWindow.gamma));
    4.90 +        SDL_memcpy(&SDL_CurrentDisplay.gamma[2 * 256], blue,
    4.91 +                   256 * sizeof(*SDL_CurrentDisplay.gamma));
    4.92      }
    4.93  
    4.94      /* Try to set the gamma ramp in the driver */
    4.95      succeeded = -1;
    4.96 -    if (_this && _this->SetGammaRamp) {
    4.97 -        succeeded = _this->SetGammaRamp(_this, SDL_CurrentWindow.gamma);
    4.98 +    if (_this && _this->SetDisplayGammaRamp) {
    4.99 +        succeeded =
   4.100 +            _this->SetDisplayGammaRamp(_this, SDL_CurrentDisplay.gamma);
   4.101      } else {
   4.102          SDL_SetError("Gamma ramp manipulation not supported");
   4.103      }
   4.104 @@ -186,38 +166,42 @@
   4.105      SDL_VideoDevice *_this = SDL_GetVideoDevice();
   4.106  
   4.107      /* Lazily allocate the gamma table */
   4.108 -    if (!SDL_CurrentWindow.gamma) {
   4.109 -        SDL_CurrentWindow.gamma =
   4.110 -            SDL_malloc(3 * 256 * sizeof(*SDL_CurrentWindow.gamma));
   4.111 -        if (!SDL_CurrentWindow.gamma) {
   4.112 +    if (!SDL_CurrentDisplay.gamma) {
   4.113 +        size_t rampsize = (3 * 256 * sizeof(*SDL_CurrentDisplay.gamma));
   4.114 +
   4.115 +        SDL_CurrentDisplay.gamma = SDL_malloc(rampsize * 2);
   4.116 +        if (!SDL_CurrentDisplay.gamma) {
   4.117              SDL_OutOfMemory();
   4.118              return -1;
   4.119          }
   4.120 -        if (_this && _this->GetGammaRamp) {
   4.121 +        if (_this && _this->GetDisplayGammaRamp) {
   4.122              /* Get the real hardware gamma */
   4.123 -            _this->GetGammaRamp(_this, SDL_CurrentWindow.gamma);
   4.124 +            _this->GetDisplayGammaRamp(_this, SDL_CurrentDisplay.gamma);
   4.125          } else {
   4.126              /* Assume an identity gamma */
   4.127              int i;
   4.128              for (i = 0; i < 256; ++i) {
   4.129 -                SDL_CurrentWindow.gamma[0 * 256 + i] = (i << 8) | i;
   4.130 -                SDL_CurrentWindow.gamma[1 * 256 + i] = (i << 8) | i;
   4.131 -                SDL_CurrentWindow.gamma[2 * 256 + i] = (i << 8) | i;
   4.132 +                SDL_CurrentDisplay.gamma[0 * 256 + i] = (i << 8) | i;
   4.133 +                SDL_CurrentDisplay.gamma[1 * 256 + i] = (i << 8) | i;
   4.134 +                SDL_CurrentDisplay.gamma[2 * 256 + i] = (i << 8) | i;
   4.135              }
   4.136          }
   4.137 +        SDL_CurrentDisplay.saved_gamma = SDL_CurrentDisplay.gamma + (3 * 256);
   4.138 +        SDL_memcpy(SDL_CurrentDisplay.saved_gamma, SDL_CurrentDisplay.gamma,
   4.139 +                   rampsize);
   4.140      }
   4.141  
   4.142      /* Just copy from our internal table */
   4.143      if (red) {
   4.144 -        SDL_memcpy(red, &SDL_CurrentWindow.gamma[0 * 256],
   4.145 +        SDL_memcpy(red, &SDL_CurrentDisplay.gamma[0 * 256],
   4.146                     256 * sizeof(*red));
   4.147      }
   4.148      if (green) {
   4.149 -        SDL_memcpy(green, &SDL_CurrentWindow.gamma[1 * 256],
   4.150 +        SDL_memcpy(green, &SDL_CurrentDisplay.gamma[1 * 256],
   4.151                     256 * sizeof(*green));
   4.152      }
   4.153      if (blue) {
   4.154 -        SDL_memcpy(blue, &SDL_CurrentWindow.gamma[2 * 256],
   4.155 +        SDL_memcpy(blue, &SDL_CurrentDisplay.gamma[2 * 256],
   4.156                     256 * sizeof(*blue));
   4.157      }
   4.158      return 0;
     5.1 --- a/src/video/SDL_sysvideo.h	Sat Jul 08 20:55:39 2006 +0000
     5.2 +++ b/src/video/SDL_sysvideo.h	Sun Jul 09 09:02:26 2006 +0000
     5.3 @@ -117,14 +117,16 @@
     5.4      int w, h;
     5.5      Uint32 flags;
     5.6  
     5.7 -    Uint16 *gamma;
     5.8 -
     5.9      int display;
    5.10      SDL_Renderer *renderer;
    5.11  
    5.12      void *userdata;
    5.13      void *driverdata;
    5.14  };
    5.15 +#define FULLSCREEN_VISIBLE(W) \
    5.16 +    ((W->flags & SDL_WINDOW_FULLSCREEN) && \
    5.17 +     (W->flags & SDL_WINDOW_SHOWN) && \
    5.18 +     !(W->flags & SDL_WINDOW_MINIMIZED))
    5.19  
    5.20  /* Define the SDL display structure
    5.21     This corresponds to physical monitors attached to the system.
    5.22 @@ -136,8 +138,13 @@
    5.23      SDL_DisplayMode *display_modes;
    5.24      SDL_DisplayMode desktop_mode;
    5.25      SDL_DisplayMode current_mode;
    5.26 +    SDL_DisplayMode desired_mode;
    5.27 +    SDL_DisplayMode *fullscreen_mode;
    5.28      SDL_Palette *palette;
    5.29  
    5.30 +    Uint16 *gamma;
    5.31 +    Uint16 *saved_gamma;        /* (just offset into gamma) */
    5.32 +
    5.33      int num_render_drivers;
    5.34      SDL_RenderDriver *render_drivers;
    5.35  
    5.36 @@ -174,6 +181,12 @@
    5.37      /* * * */
    5.38      /* Display functions
    5.39       */
    5.40 +
    5.41 +    /* Get a list of the available display modes.
    5.42 +     * e.g.  SDL_AddDisplayMode(_this->current_display, mode)
    5.43 +     */
    5.44 +    void (*GetDisplayModes) (_THIS);
    5.45 +
    5.46      /* Setting the display mode is independent of creating windows,
    5.47       * so when the display mode is changed, all existing windows
    5.48       * should have their data updated accordingly, including the
    5.49 @@ -181,12 +194,18 @@
    5.50       */
    5.51      int (*SetDisplayMode) (_THIS, SDL_DisplayMode * mode);
    5.52  
    5.53 -    /* Sets the color entries of the display palette to those in 'colors'.
    5.54 -       The return value is 0 if all entries could be set properly or -1
    5.55 -       otherwise.
    5.56 -     */
    5.57 +    /* Set the color entries of the display palette */
    5.58      int (*SetDisplayPalette) (_THIS, SDL_Palette * palette);
    5.59  
    5.60 +    /* Get the color entries of the display palette */
    5.61 +    int (*GetDisplayPalette) (_THIS, SDL_Palette * palette);
    5.62 +
    5.63 +    /* Set the gamma ramp */
    5.64 +    int (*SetDisplayGammaRamp) (_THIS, Uint16 * ramp);
    5.65 +
    5.66 +    /* Get the gamma ramp */
    5.67 +    int (*GetDisplayGammaRamp) (_THIS, Uint16 * ramp);
    5.68 +
    5.69      /* * * */
    5.70      /* Window functions
    5.71       */
    5.72 @@ -214,21 +233,6 @@
    5.73      void (*VideoQuit) (_THIS);
    5.74  
    5.75      /* * * */
    5.76 -    /* Gamma support */
    5.77 -
    5.78 -    /* Set the gamma correction directly (emulated with gamma ramps) */
    5.79 -    int (*SetGamma) (_THIS, float red, float green, float blue);
    5.80 -
    5.81 -    /* Get the gamma correction directly (emulated with gamma ramps) */
    5.82 -    int (*GetGamma) (_THIS, float *red, float *green, float *blue);
    5.83 -
    5.84 -    /* Set the gamma ramp */
    5.85 -    int (*SetGammaRamp) (_THIS, Uint16 * ramp);
    5.86 -
    5.87 -    /* Get the gamma ramp */
    5.88 -    int (*GetGammaRamp) (_THIS, Uint16 * ramp);
    5.89 -
    5.90 -    /* * * */
    5.91      /* OpenGL support */
    5.92  
    5.93      /* Sets the dll to use for OpenGL and loads it */
    5.94 @@ -405,7 +409,6 @@
    5.95  #endif
    5.96  
    5.97  #define SDL_CurrentDisplay	(_this->displays[_this->current_display])
    5.98 -#define SDL_CurrentWindow	(SDL_CurrentDisplay.windows[0])
    5.99  
   5.100  extern SDL_VideoDevice *SDL_GetVideoDevice();
   5.101  extern int SDL_AddBasicVideoDisplay(const SDL_DisplayMode * desktop_mode);
   5.102 @@ -418,6 +421,11 @@
   5.103  extern SDL_Window *SDL_GetWindowFromID(SDL_WindowID windowID);
   5.104  extern SDL_VideoDisplay *SDL_GetDisplayFromWindow(SDL_Window * window);
   5.105  
   5.106 +extern void SDL_OnWindowShown(SDL_Window * window);
   5.107 +extern void SDL_OnWindowHidden(SDL_Window * window);
   5.108 +extern void SDL_OnWindowFocusGained(SDL_Window * window);
   5.109 +extern void SDL_OnWindowFocusLost(SDL_Window * window);
   5.110 +
   5.111  #endif /* _SDL_sysvideo_h */
   5.112  
   5.113  /* vi: set ts=4 sw=4 expandtab: */
     6.1 --- a/src/video/SDL_video.c	Sat Jul 08 20:55:39 2006 +0000
     6.2 +++ b/src/video/SDL_video.c	Sun Jul 09 09:02:26 2006 +0000
     6.3 @@ -267,13 +267,6 @@
     6.4          return (-1);
     6.5      }
     6.6  
     6.7 -    /* Sort the video modes */
     6.8 -    for (i = 0; i < _this->num_displays; ++i) {
     6.9 -        SDL_qsort(_this->displays[i].display_modes,
    6.10 -                  _this->displays[i].num_display_modes,
    6.11 -                  sizeof(SDL_DisplayMode), cmpmodes);
    6.12 -    }
    6.13 -
    6.14      /* The software renderer is always available */
    6.15      for (i = 0; i < _this->num_displays; ++i) {
    6.16          if (_this->displays[i].num_render_drivers > 0) {
    6.17 @@ -398,7 +391,13 @@
    6.18  SDL_GetNumDisplayModes()
    6.19  {
    6.20      if (_this) {
    6.21 -        return SDL_CurrentDisplay.num_display_modes;
    6.22 +        SDL_VideoDisplay *display = &SDL_CurrentDisplay;
    6.23 +        if (!display->num_display_modes && _this->GetDisplayModes) {
    6.24 +            _this->GetDisplayModes(_this);
    6.25 +            SDL_qsort(display->display_modes, display->num_display_modes,
    6.26 +                      sizeof(SDL_DisplayMode), cmpmodes);
    6.27 +        }
    6.28 +        return display->num_display_modes;
    6.29      }
    6.30      return 0;
    6.31  }
    6.32 @@ -460,7 +459,7 @@
    6.33      }
    6.34  
    6.35      match = NULL;
    6.36 -    for (i = 0; i < SDL_CurrentDisplay.num_display_modes; ++i) {
    6.37 +    for (i = 0; i < SDL_GetNumDisplayModes(); ++i) {
    6.38          current = &SDL_CurrentDisplay.display_modes[i];
    6.39  
    6.40          if ((current->w && current->h) &&
    6.41 @@ -602,7 +601,7 @@
    6.42      /* Move any fullscreen windows into position */
    6.43      for (i = 0; i < display->num_windows; ++i) {
    6.44          SDL_Window *window = &display->windows[i];
    6.45 -        if (window->flags & SDL_WINDOW_FULLSCREEN) {
    6.46 +        if (FULLSCREEN_VISIBLE(window)) {
    6.47              SDL_SetWindowPosition(window->id,
    6.48                                    ((display_mode.w - window->w) / 2),
    6.49                                    ((display_mode.h - window->h) / 2));
    6.50 @@ -613,6 +612,44 @@
    6.51  }
    6.52  
    6.53  int
    6.54 +SDL_SetFullscreenDisplayMode(const SDL_DisplayMode * mode)
    6.55 +{
    6.56 +    SDL_VideoDisplay *display;
    6.57 +    int i;
    6.58 +
    6.59 +    if (!_this) {
    6.60 +        SDL_SetError("Video subsystem has not been initialized");
    6.61 +        return -1;
    6.62 +    }
    6.63 +
    6.64 +    display = &SDL_CurrentDisplay;
    6.65 +    if (mode) {
    6.66 +        SDL_GetClosestDisplayMode(mode, &display->desired_mode);
    6.67 +        display->fullscreen_mode = &display->desired_mode;
    6.68 +    } else {
    6.69 +        display->fullscreen_mode = NULL;
    6.70 +    }
    6.71 +
    6.72 +    /* Actually set the mode if we have a fullscreen window visible */
    6.73 +    for (i = 0; i < display->num_windows; ++i) {
    6.74 +        SDL_Window *window = &display->windows[i];
    6.75 +        if (FULLSCREEN_VISIBLE(window)) {
    6.76 +            return SDL_SetDisplayMode(display->fullscreen_mode);
    6.77 +        }
    6.78 +    }
    6.79 +    return 0;
    6.80 +}
    6.81 +
    6.82 +const SDL_DisplayMode *
    6.83 +SDL_GetFullscreenDisplayMode(void)
    6.84 +{
    6.85 +    if (_this) {
    6.86 +        return SDL_CurrentDisplay.fullscreen_mode;
    6.87 +    }
    6.88 +    return NULL;
    6.89 +}
    6.90 +
    6.91 +int
    6.92  SDL_SetDisplayPalette(const SDL_Color * colors, int firstcolor, int ncolors)
    6.93  {
    6.94      SDL_Palette *palette;
    6.95 @@ -939,7 +976,7 @@
    6.96          return;
    6.97      }
    6.98  
    6.99 -    window->flags |= SDL_WINDOW_SHOWN;
   6.100 +    SDL_SendWindowEvent(window->id, SDL_WINDOWEVENT_SHOWN, 0, 0);
   6.101  
   6.102      if (_this->ShowWindow) {
   6.103          _this->ShowWindow(_this, window);
   6.104 @@ -955,7 +992,7 @@
   6.105          return;
   6.106      }
   6.107  
   6.108 -    window->flags &= ~SDL_WINDOW_SHOWN;
   6.109 +    SDL_SendWindowEvent(window->id, SDL_WINDOWEVENT_HIDDEN, 0, 0);
   6.110  
   6.111      if (_this->HideWindow) {
   6.112          _this->HideWindow(_this, window);
   6.113 @@ -985,7 +1022,7 @@
   6.114          return;
   6.115      }
   6.116  
   6.117 -    window->flags |= SDL_WINDOW_MAXIMIZED;
   6.118 +    SDL_SendWindowEvent(window->id, SDL_WINDOWEVENT_MAXIMIZED, 0, 0);
   6.119  
   6.120      if (_this->MaximizeWindow) {
   6.121          _this->MaximizeWindow(_this, window);
   6.122 @@ -1001,7 +1038,7 @@
   6.123          return;
   6.124      }
   6.125  
   6.126 -    window->flags |= SDL_WINDOW_MINIMIZED;
   6.127 +    SDL_SendWindowEvent(window->id, SDL_WINDOWEVENT_MINIMIZED, 0, 0);
   6.128  
   6.129      if (_this->MinimizeWindow) {
   6.130          _this->MinimizeWindow(_this, window);
   6.131 @@ -1018,7 +1055,7 @@
   6.132          return;
   6.133      }
   6.134  
   6.135 -    window->flags &= ~(SDL_WINDOW_MAXIMIZED | SDL_WINDOW_MINIMIZED);
   6.136 +    SDL_SendWindowEvent(window->id, SDL_WINDOWEVENT_RESTORED, 0, 0);
   6.137  
   6.138      if (_this->RestoreWindow) {
   6.139          _this->RestoreWindow(_this, window);
   6.140 @@ -1058,6 +1095,43 @@
   6.141  }
   6.142  
   6.143  void
   6.144 +SDL_OnWindowShown(SDL_Window * window)
   6.145 +{
   6.146 +}
   6.147 +
   6.148 +void
   6.149 +SDL_OnWindowHidden(SDL_Window * window)
   6.150 +{
   6.151 +}
   6.152 +
   6.153 +void
   6.154 +SDL_OnWindowFocusGained(SDL_Window * window)
   6.155 +{
   6.156 +    SDL_VideoDisplay *display = SDL_GetDisplayFromWindow(window);
   6.157 +
   6.158 +    if (window->flags & SDL_WINDOW_FULLSCREEN) {
   6.159 +        SDL_SetDisplayMode(display->fullscreen_mode);
   6.160 +    }
   6.161 +    if (display->gamma && _this->SetDisplayGammaRamp) {
   6.162 +        _this->SetDisplayGammaRamp(_this, display->gamma);
   6.163 +    }
   6.164 +}
   6.165 +
   6.166 +void
   6.167 +SDL_OnWindowFocusLost(SDL_Window * window)
   6.168 +{
   6.169 +    SDL_VideoDisplay *display = SDL_GetDisplayFromWindow(window);
   6.170 +
   6.171 +    if (window->flags & SDL_WINDOW_FULLSCREEN) {
   6.172 +        SDL_SetDisplayMode(NULL);
   6.173 +        SDL_MinimizeWindow(window->id);
   6.174 +    }
   6.175 +    if (display->gamma && _this->SetDisplayGammaRamp) {
   6.176 +        _this->SetDisplayGammaRamp(_this, display->saved_gamma);
   6.177 +    }
   6.178 +}
   6.179 +
   6.180 +void
   6.181  SDL_DestroyWindow(SDL_WindowID windowID)
   6.182  {
   6.183      int i, j;
   6.184 @@ -1073,6 +1147,12 @@
   6.185              if (window->id != windowID) {
   6.186                  continue;
   6.187              }
   6.188 +            if (window->flags & SDL_WINDOW_FULLSCREEN) {
   6.189 +                SDL_SetDisplayMode(NULL);
   6.190 +            }
   6.191 +            if (display->gamma && _this->SetDisplayGammaRamp) {
   6.192 +                _this->SetDisplayGammaRamp(_this, display->saved_gamma);
   6.193 +            }
   6.194              if (window->flags & SDL_WINDOW_INPUT_GRABBED) {
   6.195                  window->flags &= ~SDL_WINDOW_INPUT_GRABBED;
   6.196                  _this->SetWindowGrab(_this, window);
   6.197 @@ -1086,9 +1166,6 @@
   6.198              if (window->title) {
   6.199                  SDL_free(window->title);
   6.200              }
   6.201 -            if (window->gamma) {
   6.202 -                SDL_free(window->gamma);
   6.203 -            }
   6.204              if (j != display->num_windows - 1) {
   6.205                  SDL_memcpy(&display->windows[i],
   6.206                             &display->windows[i + 1],
   6.207 @@ -1868,6 +1945,12 @@
   6.208              SDL_FreePalette(display->palette);
   6.209              display->palette = NULL;
   6.210          }
   6.211 +        if (display->gamma) {
   6.212 +            SDL_free(display->gamma);
   6.213 +        }
   6.214 +        if (display->driverdata) {
   6.215 +            SDL_free(display->driverdata);
   6.216 +        }
   6.217      }
   6.218      if (_this->displays) {
   6.219          SDL_free(_this->displays);
     7.1 --- a/src/video/win32/SDL_win32events.c	Sat Jul 08 20:55:39 2006 +0000
     7.2 +++ b/src/video/win32/SDL_win32events.c	Sun Jul 09 09:02:26 2006 +0000
     7.3 @@ -421,6 +421,18 @@
     7.4  
     7.5      switch (msg) {
     7.6  
     7.7 +    case WM_SHOWWINDOW:
     7.8 +        {
     7.9 +            if (wParam) {
    7.10 +                SDL_SendWindowEvent(data->windowID, SDL_WINDOWEVENT_SHOWN, 0,
    7.11 +                                    0);
    7.12 +            } else {
    7.13 +                SDL_SendWindowEvent(data->windowID, SDL_WINDOWEVENT_HIDDEN, 0,
    7.14 +                                    0);
    7.15 +            }
    7.16 +        }
    7.17 +        break;
    7.18 +
    7.19      case WM_ACTIVATE:
    7.20          {
    7.21              int index;
    7.22 @@ -452,7 +464,6 @@
    7.23                          ClipCursor(&rect);
    7.24                      }
    7.25                  }
    7.26 -                /* FIXME: Restore mode state (mode, gamma) */
    7.27                  /* FIXME: Update keyboard state */
    7.28              } else {
    7.29                  if (keyboard && keyboard->focus == data->windowID) {
    7.30 @@ -467,7 +478,6 @@
    7.31                      SDL_SendWindowEvent(data->windowID,
    7.32                                          SDL_WINDOWEVENT_MINIMIZED, 0, 0);
    7.33                  }
    7.34 -                /* FIXME: Restore desktop state (mode, gamma) */
    7.35              }
    7.36              return (0);
    7.37          }
     8.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     8.2 +++ b/src/video/win32/SDL_win32gamma.c	Sun Jul 09 09:02:26 2006 +0000
     8.3 @@ -0,0 +1,63 @@
     8.4 +/*
     8.5 +    SDL - Simple DirectMedia Layer
     8.6 +    Copyright (C) 1997-2006 Sam Lantinga
     8.7 +
     8.8 +    This library is free software; you can redistribute it and/or
     8.9 +    modify it under the terms of the GNU Lesser General Public
    8.10 +    License as published by the Free Software Foundation; either
    8.11 +    version 2.1 of the License, or (at your option) any later version.
    8.12 +
    8.13 +    This library is distributed in the hope that it will be useful,
    8.14 +    but WITHOUT ANY WARRANTY; without even the implied warranty of
    8.15 +    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
    8.16 +    Lesser General Public License for more details.
    8.17 +
    8.18 +    You should have received a copy of the GNU Lesser General Public
    8.19 +    License along with this library; if not, write to the Free Software
    8.20 +    Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
    8.21 +
    8.22 +    Sam Lantinga
    8.23 +    slouken@libsdl.org
    8.24 +*/
    8.25 +#include "SDL_config.h"
    8.26 +
    8.27 +#include "SDL_win32video.h"
    8.28 +
    8.29 +
    8.30 +int
    8.31 +WIN_SetDisplayGammaRamp(_THIS, Uint16 * ramp)
    8.32 +{
    8.33 +    SDL_DisplayData *data = (SDL_DisplayData *) SDL_CurrentDisplay.driverdata;
    8.34 +    HDC hdc;
    8.35 +    BOOL succeeded = FALSE;
    8.36 +
    8.37 +    hdc = CreateDC(data->DeviceName, NULL, NULL, NULL);
    8.38 +    if (hdc) {
    8.39 +        succeeded = SetDeviceGammaRamp(hdc, ramp);
    8.40 +        if (!succeeded) {
    8.41 +            WIN_SetError("SetDeviceGammaRamp()");
    8.42 +        }
    8.43 +        DeleteDC(hdc);
    8.44 +    }
    8.45 +    return succeeded ? 0 : -1;
    8.46 +}
    8.47 +
    8.48 +int
    8.49 +WIN_GetDisplayGammaRamp(_THIS, Uint16 * ramp)
    8.50 +{
    8.51 +    SDL_DisplayData *data = (SDL_DisplayData *) SDL_CurrentDisplay.driverdata;
    8.52 +    HDC hdc;
    8.53 +    BOOL succeeded = FALSE;
    8.54 +
    8.55 +    hdc = CreateDC(data->DeviceName, NULL, NULL, NULL);
    8.56 +    if (hdc) {
    8.57 +        succeeded = GetDeviceGammaRamp(hdc, ramp);
    8.58 +        if (!succeeded) {
    8.59 +            WIN_SetError("GetDeviceGammaRamp()");
    8.60 +        }
    8.61 +        DeleteDC(hdc);
    8.62 +    }
    8.63 +    return succeeded ? 0 : -1;
    8.64 +}
    8.65 +
    8.66 +/* vi: set ts=4 sw=4 expandtab: */
     9.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     9.2 +++ b/src/video/win32/SDL_win32gamma.h	Sun Jul 09 09:02:26 2006 +0000
     9.3 @@ -0,0 +1,32 @@
     9.4 +/*
     9.5 +    SDL - Simple DirectMedia Layer
     9.6 +    Copyright (C) 1997-2006 Sam Lantinga
     9.7 +
     9.8 +    This library is free software; you can redistribute it and/or
     9.9 +    modify it under the terms of the GNU Lesser General Public
    9.10 +    License as published by the Free Software Foundation; either
    9.11 +    version 2.1 of the License, or (at your option) any later version.
    9.12 +
    9.13 +    This library is distributed in the hope that it will be useful,
    9.14 +    but WITHOUT ANY WARRANTY; without even the implied warranty of
    9.15 +    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
    9.16 +    Lesser General Public License for more details.
    9.17 +
    9.18 +    You should have received a copy of the GNU Lesser General Public
    9.19 +    License along with this library; if not, write to the Free Software
    9.20 +    Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
    9.21 +
    9.22 +    Sam Lantinga
    9.23 +    slouken@libsdl.org
    9.24 +*/
    9.25 +#include "SDL_config.h"
    9.26 +
    9.27 +#ifndef _SDL_win32gamma_h
    9.28 +#define _SDL_win32gamma_h
    9.29 +
    9.30 +extern int WIN_SetDisplayGammaRamp(_THIS, Uint16 * ramp);
    9.31 +extern int WIN_GetDisplayGammaRamp(_THIS, Uint16 * ramp);
    9.32 +
    9.33 +#endif /* _SDL_win32gamma_h */
    9.34 +
    9.35 +/* vi: set ts=4 sw=4 expandtab: */
    10.1 --- a/src/video/win32/SDL_win32modes.c	Sat Jul 08 20:55:39 2006 +0000
    10.2 +++ b/src/video/win32/SDL_win32modes.c	Sun Jul 09 09:02:26 2006 +0000
    10.3 @@ -24,12 +24,6 @@
    10.4  #include "SDL_win32video.h"
    10.5  
    10.6  
    10.7 -typedef struct
    10.8 -{
    10.9 -    TCHAR DeviceName[32];
   10.10 -    DEVMODE DeviceMode;
   10.11 -} SDL_DisplayModeData;
   10.12 -
   10.13  /* FIXME: Each call to EnumDisplaySettings() takes about 6 ms on my laptop.
   10.14            With 500 or so modes, this takes almost 3 seconds to run!
   10.15  */
   10.16 @@ -123,7 +117,7 @@
   10.17  WIN_InitModes(_THIS)
   10.18  {
   10.19      SDL_VideoData *data = (SDL_VideoData *) _this->driverdata;
   10.20 -    DWORD i, j, k;
   10.21 +    DWORD i, j;
   10.22      DISPLAY_DEVICE device;
   10.23  
   10.24      device.cb = sizeof(device);
   10.25 @@ -143,6 +137,7 @@
   10.26          for (j = 0;; ++j) {
   10.27              int index;
   10.28              SDL_VideoDisplay display;
   10.29 +            SDL_DisplayData *displaydata;
   10.30              SDL_DisplayMode mode;
   10.31  
   10.32              if (!EnumDisplayDevices(DeviceName, j, &device, 0)) {
   10.33 @@ -157,19 +152,37 @@
   10.34              if (!WIN_GetDisplayMode(DeviceName, ENUM_CURRENT_SETTINGS, &mode)) {
   10.35                  break;
   10.36              }
   10.37 +
   10.38 +            displaydata =
   10.39 +                (SDL_DisplayData *) SDL_malloc(sizeof(*displaydata));
   10.40 +            if (!displaydata) {
   10.41 +                continue;
   10.42 +            }
   10.43 +            SDL_memcpy(displaydata->DeviceName, DeviceName,
   10.44 +                       sizeof(DeviceName));
   10.45 +
   10.46              SDL_zero(display);
   10.47              display.desktop_mode = mode;
   10.48              display.current_mode = mode;
   10.49 -            index = SDL_AddVideoDisplay(&display);
   10.50 +            display.driverdata = displaydata;
   10.51 +            SDL_AddVideoDisplay(&display);
   10.52 +        }
   10.53 +    }
   10.54 +}
   10.55  
   10.56 -            for (k = 0;; ++k) {
   10.57 -                if (!WIN_GetDisplayMode(DeviceName, k, &mode)) {
   10.58 -                    break;
   10.59 -                }
   10.60 -                if (!SDL_AddDisplayMode(index, &mode)) {
   10.61 -                    SDL_free(mode.driverdata);
   10.62 -                }
   10.63 -            }
   10.64 +void
   10.65 +WIN_GetDisplayModes(_THIS)
   10.66 +{
   10.67 +    SDL_DisplayData *data = (SDL_DisplayData *) SDL_CurrentDisplay.driverdata;
   10.68 +    DWORD i;
   10.69 +    SDL_DisplayMode mode;
   10.70 +
   10.71 +    for (i = 0;; ++i) {
   10.72 +        if (!WIN_GetDisplayMode(data->DeviceName, i, &mode)) {
   10.73 +            break;
   10.74 +        }
   10.75 +        if (!SDL_AddDisplayMode(_this->current_display, &mode)) {
   10.76 +            SDL_free(mode.driverdata);
   10.77          }
   10.78      }
   10.79  }
    11.1 --- a/src/video/win32/SDL_win32modes.h	Sat Jul 08 20:55:39 2006 +0000
    11.2 +++ b/src/video/win32/SDL_win32modes.h	Sun Jul 09 09:02:26 2006 +0000
    11.3 @@ -24,7 +24,19 @@
    11.4  #ifndef _SDL_win32modes_h
    11.5  #define _SDL_win32modes_h
    11.6  
    11.7 +typedef struct
    11.8 +{
    11.9 +    TCHAR DeviceName[32];
   11.10 +} SDL_DisplayData;
   11.11 +
   11.12 +typedef struct
   11.13 +{
   11.14 +    TCHAR DeviceName[32];
   11.15 +    DEVMODE DeviceMode;
   11.16 +} SDL_DisplayModeData;
   11.17 +
   11.18  extern void WIN_InitModes(_THIS);
   11.19 +extern void WIN_GetDisplayModes(_THIS);
   11.20  extern int WIN_SetDisplayMode(_THIS, SDL_DisplayMode * mode);
   11.21  extern void WIN_QuitModes(_THIS);
   11.22  
    12.1 --- a/src/video/win32/SDL_win32video.c	Sat Jul 08 20:55:39 2006 +0000
    12.2 +++ b/src/video/win32/SDL_win32video.c	Sun Jul 09 09:02:26 2006 +0000
    12.3 @@ -84,11 +84,11 @@
    12.4  #if SDL_VIDEO_RENDER_D3D
    12.5      data->d3dDLL = LoadLibrary(TEXT("D3D9.DLL"));
    12.6      if (data->d3dDLL) {
    12.7 -        IDirect3D9 *WINAPI(*D3DCreate) (UINT SDKVersion);
    12.8 +        IDirect3D9 *(WINAPI * D3DCreate) (UINT SDKVersion);
    12.9  
   12.10          D3DCreate =
   12.11 -            (IDirect3D9 * WINAPI(*)(UINT)) GetProcAddress(data->d3dDLL,
   12.12 -                                                          "Direct3DCreate9");
   12.13 +            (IDirect3D9 * (WINAPI *) (UINT)) GetProcAddress(data->d3dDLL,
   12.14 +                                                            "Direct3DCreate9");
   12.15          if (D3DCreate) {
   12.16              data->d3d = D3DCreate(D3D_SDK_VERSION);
   12.17          }
   12.18 @@ -101,7 +101,10 @@
   12.19  
   12.20      /* Set the function pointers */
   12.21      device->VideoInit = WIN_VideoInit;
   12.22 +    device->GetDisplayModes = WIN_GetDisplayModes;
   12.23      device->SetDisplayMode = WIN_SetDisplayMode;
   12.24 +    device->SetDisplayGammaRamp = WIN_SetDisplayGammaRamp;
   12.25 +    device->GetDisplayGammaRamp = WIN_GetDisplayGammaRamp;
   12.26      device->VideoQuit = WIN_VideoQuit;
   12.27      device->PumpEvents = WIN_PumpEvents;
   12.28  
    13.1 --- a/src/video/win32/SDL_win32video.h	Sat Jul 08 20:55:39 2006 +0000
    13.2 +++ b/src/video/win32/SDL_win32video.h	Sun Jul 09 09:02:26 2006 +0000
    13.3 @@ -36,6 +36,7 @@
    13.4  #endif
    13.5  
    13.6  #include "SDL_win32events.h"
    13.7 +#include "SDL_win32gamma.h"
    13.8  #include "SDL_win32keyboard.h"
    13.9  #include "SDL_win32modes.h"
   13.10  #include "SDL_win32mouse.h"
    14.1 --- a/src/video/win32/SDL_win32window.c	Sat Jul 08 20:55:39 2006 +0000
    14.2 +++ b/src/video/win32/SDL_win32window.c	Sun Jul 09 09:02:26 2006 +0000
    14.3 @@ -22,6 +22,7 @@
    14.4  #include "SDL_config.h"
    14.5  
    14.6  #include "../SDL_sysvideo.h"
    14.7 +#include "../../events/SDL_keyboard_c.h"
    14.8  
    14.9  #include "SDL_win32video.h"
   14.10  
   14.11 @@ -110,6 +111,14 @@
   14.12          int index = data->videodata->keyboard;
   14.13          window->flags |= SDL_WINDOW_KEYBOARD_FOCUS;
   14.14          SDL_SetKeyboardFocus(index, data->windowID);
   14.15 +
   14.16 +        if (window->flags & SDL_WINDOW_INPUT_GRABBED) {
   14.17 +            RECT rect;
   14.18 +            GetClientRect(hwnd, &rect);
   14.19 +            ClientToScreen(hwnd, (LPPOINT) & rect);
   14.20 +            ClientToScreen(hwnd, (LPPOINT) & rect + 1);
   14.21 +            ClipCursor(&rect);
   14.22 +        }
   14.23      }
   14.24  
   14.25      /* All done! */
    15.1 --- a/test/testsprite2.c	Sat Jul 08 20:55:39 2006 +0000
    15.2 +++ b/test/testsprite2.c	Sun Jul 09 09:02:26 2006 +0000
    15.3 @@ -162,14 +162,7 @@
    15.4          SDL_zero(fullscreen_mode);
    15.5          fullscreen_mode.w = window_w;
    15.6          fullscreen_mode.h = window_h;
    15.7 -        mode = &fullscreen_mode;
    15.8 -    } else {
    15.9 -        /* Set the desktop mode, we don't care what it is */
   15.10 -        mode = NULL;
   15.11 -    }
   15.12 -    if (SDL_SetDisplayMode(mode) < 0) {
   15.13 -        fprintf(stderr, "Couldn't set display mode: %s\n", SDL_GetError());
   15.14 -        quit(2);
   15.15 +        SDL_SetFullscreenDisplayMode(&fullscreen_mode);
   15.16      }
   15.17  
   15.18      /* Create the windows, initialize the renderers, and load the textures */
    16.1 --- a/test/testwm2.c	Sat Jul 08 20:55:39 2006 +0000
    16.2 +++ b/test/testwm2.c	Sun Jul 09 09:02:26 2006 +0000
    16.3 @@ -49,12 +49,6 @@
    16.4          }
    16.5      }
    16.6  
    16.7 -    /* Set the desktop mode, we don't care what it is */
    16.8 -    if (SDL_SetDisplayMode(NULL) < 0) {
    16.9 -        fprintf(stderr, "Couldn't set display mode: %s\n", SDL_GetError());
   16.10 -        quit(2);
   16.11 -    }
   16.12 -
   16.13      /* Create the windows */
   16.14      windows = (SDL_WindowID *) SDL_malloc(num_windows * sizeof(*windows));
   16.15      if (!windows) {