symbian-qemu-0.9.1-12/libsdl-trunk/src/video/photon/SDL_ph_modes.c
changeset 1 2fb8b9db1c86
equal deleted inserted replaced
0:ffa851df0825 1:2fb8b9db1c86
       
     1 /*
       
     2     SDL - Simple DirectMedia Layer
       
     3     Copyright (C) 1997-2006 Sam Lantinga
       
     4 
       
     5     This library is free software; you can redistribute it and/or
       
     6     modify it under the terms of the GNU Lesser General Public
       
     7     License as published by the Free Software Foundation; either
       
     8     version 2.1 of the License, or (at your option) any later version.
       
     9 
       
    10     This library is distributed in the hope that it will be useful,
       
    11     but WITHOUT ANY WARRANTY; without even the implied warranty of
       
    12     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
       
    13     Lesser General Public License for more details.
       
    14 
       
    15     You should have received a copy of the GNU Lesser General Public
       
    16     License along with this library; if not, write to the Free Software
       
    17     Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
       
    18 
       
    19     Sam Lantinga
       
    20     slouken@libsdl.org
       
    21 */
       
    22 #include "SDL_config.h"
       
    23 
       
    24 #include "SDL_ph_modes_c.h"
       
    25 
       
    26 static PgVideoModeInfo_t mode_info;
       
    27 static PgVideoModes_t mode_list;
       
    28 
       
    29 /* The current list of available video modes */
       
    30 SDL_Rect  SDL_modelist[PH_MAX_VIDEOMODES];
       
    31 SDL_Rect* SDL_modearray[PH_MAX_VIDEOMODES];
       
    32 
       
    33 static int compare_modes_by_res(const void* mode1, const void* mode2)
       
    34 {
       
    35     PgVideoModeInfo_t mode1_info;
       
    36     PgVideoModeInfo_t mode2_info;
       
    37 
       
    38     if (PgGetVideoModeInfo(*(unsigned short*)mode1, &mode1_info) < 0)
       
    39     {
       
    40         return 0;
       
    41     }
       
    42 
       
    43     if (PgGetVideoModeInfo(*(unsigned short*)mode2, &mode2_info) < 0)
       
    44     {
       
    45         return 0;
       
    46     }
       
    47 
       
    48     if (mode1_info.width == mode2_info.width)
       
    49     {
       
    50         return mode2_info.height - mode1_info.height;
       
    51     }
       
    52     else
       
    53     {
       
    54         return mode2_info.width - mode1_info.width;
       
    55     }
       
    56 }
       
    57 
       
    58 SDL_Rect **ph_ListModes(_THIS, SDL_PixelFormat *format, Uint32 flags)
       
    59 {
       
    60     int i = 0;
       
    61     int j = 0;
       
    62     SDL_Rect Amodelist[PH_MAX_VIDEOMODES];
       
    63 
       
    64     for (i=0; i<PH_MAX_VIDEOMODES; i++)
       
    65     {
       
    66         SDL_modearray[i]=&SDL_modelist[i];
       
    67     }
       
    68 
       
    69     if (PgGetVideoModeList(&mode_list) < 0)
       
    70     {
       
    71        SDL_SetError("ph_ListModes(): PgGetVideoModeList() function failed !\n");
       
    72        return NULL;
       
    73     }
       
    74 
       
    75     mode_info.bits_per_pixel = 0;
       
    76 
       
    77     for (i=0; i < mode_list.num_modes; i++) 
       
    78     {
       
    79         if (PgGetVideoModeInfo(mode_list.modes[i], &mode_info) < 0)
       
    80         {
       
    81             SDL_SetError("ph_ListModes(): PgGetVideoModeInfo() function failed on mode: 0x%X.\n", mode_list.modes[i]);
       
    82             return NULL;
       
    83         }
       
    84         if(mode_info.bits_per_pixel == format->BitsPerPixel)
       
    85         {
       
    86             Amodelist[j].w = mode_info.width;
       
    87             Amodelist[j].h = mode_info.height;
       
    88             Amodelist[j].x = 0;
       
    89             Amodelist[j].y = 0;
       
    90             j++;	
       
    91         }
       
    92     }
       
    93 	
       
    94     /* reorder biggest for smallest, assume width dominates */
       
    95 
       
    96     for(i=0; i<j; i++)
       
    97     {
       
    98         SDL_modelist[i].w = Amodelist[j - i - 1].w;
       
    99         SDL_modelist[i].h = Amodelist[j - i - 1].h;
       
   100         SDL_modelist[i].x = Amodelist[j - i - 1].x;
       
   101         SDL_modelist[i].y = Amodelist[j - i - 1].y;
       
   102     }
       
   103     SDL_modearray[j]=NULL;
       
   104 	
       
   105     return SDL_modearray;
       
   106 }
       
   107 
       
   108 void ph_FreeVideoModes(_THIS)
       
   109 {
       
   110    return;
       
   111 }
       
   112 
       
   113 /* return the mode associated with width, height and bpp */
       
   114 /* if there is no mode then zero is returned             */
       
   115 int ph_GetVideoMode(int width, int height, int bpp)
       
   116 {
       
   117     int i;
       
   118     int modestage=0;
       
   119     int closestmode=0;
       
   120 
       
   121     if (PgGetVideoModeList(&mode_list) < 0)
       
   122     {
       
   123         return -1;
       
   124     }
       
   125 
       
   126     /* special case for the double-sized 320x200 mode */
       
   127     if ((width==640) && (height==400))
       
   128     {
       
   129        modestage=1;
       
   130     }
       
   131 
       
   132     /* search list for exact match */
       
   133     for (i=0; i<mode_list.num_modes; i++)
       
   134     {
       
   135         if (PgGetVideoModeInfo(mode_list.modes[i], &mode_info) < 0)
       
   136         {
       
   137             return 0;
       
   138         }
       
   139 
       
   140         if ((mode_info.width == width) && (mode_info.height == height) && 
       
   141             (mode_info.bits_per_pixel == bpp))
       
   142         {
       
   143             return mode_list.modes[i];
       
   144         }
       
   145         else
       
   146         {
       
   147            if ((modestage) && (mode_info.width == width) && (mode_info.height == height+80) && 
       
   148                (mode_info.bits_per_pixel == bpp))
       
   149            {
       
   150               modestage=2;
       
   151               closestmode=mode_list.modes[i];
       
   152            }
       
   153         }
       
   154     }
       
   155 
       
   156     /* if we are here, then no 640x400xbpp mode found and we'll emulate it via 640x480xbpp mode */
       
   157     if (modestage==2)
       
   158     {
       
   159        return closestmode;
       
   160     }
       
   161 
       
   162     return (i == mode_list.num_modes) ? 0 : mode_list.modes[i];
       
   163 }
       
   164 
       
   165 /* return the mode associated with width, height and bpp               */
       
   166 /* if requested bpp is not found the mode with closest bpp is returned */
       
   167 int get_mode_any_format(int width, int height, int bpp)
       
   168 {
       
   169     int i, closest, delta, min_delta;
       
   170 
       
   171     if (PgGetVideoModeList(&mode_list) < 0)
       
   172     {
       
   173         return -1;
       
   174     }
       
   175 
       
   176     SDL_qsort(mode_list.modes, mode_list.num_modes, sizeof(unsigned short), compare_modes_by_res);
       
   177 
       
   178     for(i=0;i<mode_list.num_modes;i++)
       
   179     {
       
   180         if (PgGetVideoModeInfo(mode_list.modes[i], &mode_info) < 0)
       
   181         {
       
   182             return 0;
       
   183         }
       
   184         if ((mode_info.width == width) && (mode_info.height == height))
       
   185         {
       
   186            break;
       
   187         }
       
   188     }
       
   189 
       
   190     if (i<mode_list.num_modes)
       
   191     {
       
   192         /* get closest bpp */
       
   193         closest = i++;
       
   194         if (mode_info.bits_per_pixel == bpp)
       
   195         {
       
   196             return mode_list.modes[closest];
       
   197         }
       
   198 
       
   199         min_delta = abs(mode_info.bits_per_pixel - bpp);
       
   200 
       
   201         while(1)
       
   202         {
       
   203             if (PgGetVideoModeInfo(mode_list.modes[i], &mode_info) < 0)
       
   204             {
       
   205                 return 0;
       
   206             }
       
   207 
       
   208             if ((mode_info.width != width) || (mode_info.height != height))
       
   209             {
       
   210                 break;
       
   211             }
       
   212             else
       
   213             {
       
   214                 if (mode_info.bits_per_pixel == bpp)
       
   215                 {
       
   216                     closest = i;
       
   217                     break;
       
   218                 }
       
   219                 else
       
   220                 {
       
   221                     delta = abs(mode_info.bits_per_pixel - bpp);
       
   222                     if (delta < min_delta)
       
   223                     {
       
   224                         closest = i;
       
   225                         min_delta = delta;
       
   226                     }
       
   227                     i++;
       
   228                 }
       
   229             }
       
   230         }
       
   231         return mode_list.modes[closest];
       
   232     }
       
   233 
       
   234     return 0;
       
   235 }
       
   236 
       
   237 int ph_ToggleFullScreen(_THIS, int on)
       
   238 {
       
   239     return -1;
       
   240 }
       
   241 
       
   242 int ph_EnterFullScreen(_THIS, SDL_Surface* screen, int fmode)
       
   243 {
       
   244     PgDisplaySettings_t settings;
       
   245     int mode;
       
   246     char* refreshrate;
       
   247     int refreshratenum;
       
   248 
       
   249     if (!currently_fullscreen)
       
   250     {
       
   251         /* Get the video mode and set it */
       
   252         if (screen->flags & SDL_ANYFORMAT)
       
   253         {
       
   254             if ((mode = get_mode_any_format(screen->w, screen->h, screen->format->BitsPerPixel)) == 0)
       
   255             {
       
   256                 SDL_SetError("ph_EnterFullScreen(): can't find appropriate video mode !\n");
       
   257                 return 0;
       
   258             }
       
   259         }
       
   260         else
       
   261         {
       
   262             if ((mode = ph_GetVideoMode(screen->w, screen->h, screen->format->BitsPerPixel)) == 0)
       
   263             {
       
   264                 SDL_SetError("ph_EnterFullScreen(): can't find appropriate video mode !\n");
       
   265                 return 0;
       
   266             }
       
   267             if (PgGetVideoModeInfo(mode, &mode_info) < 0)
       
   268             {
       
   269                 SDL_SetError("ph_EnterFullScreen(): can't get video mode capabilities !\n");
       
   270                 return 0;
       
   271             }
       
   272             if (mode_info.height != screen->h)
       
   273             {
       
   274                if ((mode_info.height==480) && (screen->h==400))
       
   275                {
       
   276                   videomode_emulatemode=1;
       
   277                }
       
   278             }
       
   279             else
       
   280             {
       
   281                videomode_emulatemode=0;
       
   282             }
       
   283         }
       
   284 
       
   285         /* save old video mode caps */
       
   286         PgGetVideoMode(&settings);
       
   287         old_video_mode=settings.mode;
       
   288         old_refresh_rate=settings.refresh;
       
   289 
       
   290         /* setup new video mode */
       
   291         settings.mode = mode;
       
   292         settings.refresh = 0;
       
   293         settings.flags = 0;
       
   294 
       
   295         refreshrate=SDL_getenv("SDL_PHOTON_FULLSCREEN_REFRESH");
       
   296         if (refreshrate!=NULL)
       
   297         {
       
   298            if (SDL_sscanf(refreshrate, "%d", &refreshratenum)==1)
       
   299            {
       
   300                settings.refresh = refreshratenum;
       
   301            }
       
   302         }
       
   303 
       
   304         if (PgSetVideoMode(&settings) < 0)
       
   305         {
       
   306             SDL_SetError("ph_EnterFullScreen(): PgSetVideoMode() call failed !\n");
       
   307             return 0;
       
   308         }
       
   309 
       
   310         if (this->screen)
       
   311         {
       
   312             if ((this->screen->flags & SDL_OPENGL)==SDL_OPENGL)
       
   313             {
       
   314 #if !SDL_VIDEO_OPENGL || (_NTO_VERSION < 630)
       
   315                 return 0; /* 6.3.0 */
       
   316 #endif
       
   317             }
       
   318         }
       
   319 
       
   320         if (fmode==0)
       
   321         {
       
   322             if (OCImage.direct_context==NULL)
       
   323             {
       
   324                 OCImage.direct_context=(PdDirectContext_t*)PdCreateDirectContext();
       
   325                 if (!OCImage.direct_context)
       
   326                 {
       
   327                     SDL_SetError("ph_EnterFullScreen(): Can't create direct context !\n");
       
   328                     ph_LeaveFullScreen(this);
       
   329                     return 0;
       
   330                 }
       
   331             }
       
   332             OCImage.oldDC=PdDirectStart(OCImage.direct_context);
       
   333         }
       
   334 
       
   335         currently_fullscreen = 1;
       
   336     }
       
   337     PgFlush();
       
   338 
       
   339     return 1;
       
   340 }
       
   341 
       
   342 int ph_LeaveFullScreen(_THIS)
       
   343 {
       
   344     PgDisplaySettings_t oldmode_settings;
       
   345        
       
   346     if (currently_fullscreen)
       
   347     {
       
   348         if ((this->screen) && ((this->screen->flags & SDL_OPENGL)==SDL_OPENGL))
       
   349         {
       
   350 #if !SDL_VIDEO_OPENGL || (_NTO_VERSION < 630)
       
   351             return 0;
       
   352 #endif
       
   353         }
       
   354 
       
   355         /* release routines starts here */
       
   356         {
       
   357             if (OCImage.direct_context)
       
   358             {
       
   359                 PdDirectStop(OCImage.direct_context);
       
   360                 PdReleaseDirectContext(OCImage.direct_context);
       
   361                 OCImage.direct_context=NULL;
       
   362             }
       
   363             if (OCImage.oldDC)
       
   364             {
       
   365                 PhDCSetCurrent(OCImage.oldDC);
       
   366                 OCImage.oldDC=NULL;
       
   367             }
       
   368 
       
   369             currently_fullscreen=0;
       
   370 
       
   371             /* Restore old video mode */
       
   372             if (old_video_mode != -1)
       
   373             {
       
   374                 oldmode_settings.mode = (unsigned short) old_video_mode;
       
   375                 oldmode_settings.refresh = (unsigned short) old_refresh_rate;
       
   376                 oldmode_settings.flags = 0;
       
   377                 
       
   378                 if (PgSetVideoMode(&oldmode_settings) < 0)
       
   379                 {
       
   380                     SDL_SetError("Ph_LeaveFullScreen(): PgSetVideoMode() function failed !\n");
       
   381                     return 0;
       
   382                 }
       
   383             }
       
   384 
       
   385             old_video_mode=-1;
       
   386             old_refresh_rate=-1;
       
   387         }
       
   388     }
       
   389     return 1;
       
   390 }