aboutsummaryrefslogtreecommitdiffstats
path: root/distrib/sdl-1.2.15/src/video/qtopia/SDL_sysvideo.cc
diff options
context:
space:
mode:
Diffstat (limited to 'distrib/sdl-1.2.15/src/video/qtopia/SDL_sysvideo.cc')
-rw-r--r--distrib/sdl-1.2.15/src/video/qtopia/SDL_sysvideo.cc403
1 files changed, 403 insertions, 0 deletions
diff --git a/distrib/sdl-1.2.15/src/video/qtopia/SDL_sysvideo.cc b/distrib/sdl-1.2.15/src/video/qtopia/SDL_sysvideo.cc
new file mode 100644
index 0000000..0e07874
--- /dev/null
+++ b/distrib/sdl-1.2.15/src/video/qtopia/SDL_sysvideo.cc
@@ -0,0 +1,403 @@
+/*
+ SDL - Simple DirectMedia Layer
+ Copyright (C) 1997-2012 Sam Lantinga
+
+ This library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2.1 of the License, or (at your option) any later version.
+
+ This library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with this library; if not, write to the Free Software
+ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+
+ Sam Lantinga
+ slouken@libsdl.org
+*/
+#include "SDL_config.h"
+
+/* Qtopia based framebuffer implementation */
+
+#include <unistd.h>
+
+#include <qapplication.h>
+#include <qpe/qpeapplication.h>
+
+#include "SDL_timer.h"
+
+#include "SDL_QWin.h"
+
+extern "C" {
+
+#include "../SDL_sysvideo.h"
+#include "../../events/SDL_events_c.h"
+#include "SDL_sysevents_c.h"
+#include "SDL_sysmouse_c.h"
+#include "SDL_syswm_c.h"
+#include "SDL_lowvideo.h"
+
+ //#define QTOPIA_DEBUG
+#define QT_HIDDEN_SIZE 32 /* starting hidden window size */
+
+ /* Name of the environment variable used to invert the screen rotation or not:
+ Possible values:
+ !=0 : Screen is 270° rotated
+ 0: Screen is 90° rotated*/
+#define SDL_QT_ROTATION_ENV_NAME "SDL_QT_INVERT_ROTATION"
+
+ /* Initialization/Query functions */
+ static int QT_VideoInit(_THIS, SDL_PixelFormat *vformat);
+ static SDL_Rect **QT_ListModes(_THIS, SDL_PixelFormat *format, Uint32 flags);
+ static SDL_Surface *QT_SetVideoMode(_THIS, SDL_Surface *current, int width, int height, int bpp, Uint32 flags);
+ static void QT_UpdateMouse(_THIS);
+ static int QT_SetColors(_THIS, int firstcolor, int ncolors, SDL_Color *colors);
+ static void QT_VideoQuit(_THIS);
+
+ /* Hardware surface functions */
+ static int QT_AllocHWSurface(_THIS, SDL_Surface *surface);
+ static int QT_LockHWSurface(_THIS, SDL_Surface *surface);
+ static void QT_UnlockHWSurface(_THIS, SDL_Surface *surface);
+ static void QT_FreeHWSurface(_THIS, SDL_Surface *surface);
+
+ static int QT_ToggleFullScreen(_THIS, int fullscreen);
+
+ static int QT_IconifyWindow(_THIS);
+ static SDL_GrabMode QT_GrabInput(_THIS, SDL_GrabMode mode);
+
+ /* FB driver bootstrap functions */
+
+ static int QT_Available(void)
+ {
+ return(1);
+ }
+
+ static void QT_DeleteDevice(SDL_VideoDevice *device)
+ {
+ SDL_free(device->hidden);
+ SDL_free(device);
+ }
+
+ static SDL_VideoDevice *QT_CreateDevice(int devindex)
+ {
+ SDL_VideoDevice *device;
+
+ /* Initialize all variables that we clean on shutdown */
+ device = (SDL_VideoDevice *)SDL_malloc(sizeof(SDL_VideoDevice));
+ if ( device ) {
+ SDL_memset(device, 0, (sizeof *device));
+ device->hidden = (struct SDL_PrivateVideoData *)
+ SDL_malloc((sizeof *device->hidden));
+ }
+ if ( (device == NULL) || (device->hidden == NULL) ) {
+ SDL_OutOfMemory();
+ if ( device ) {
+ SDL_free(device);
+ }
+ return(0);
+ }
+ SDL_memset(device->hidden, 0, (sizeof *device->hidden));
+
+ /* Set the function pointers */
+ device->VideoInit = QT_VideoInit;
+ device->ListModes = QT_ListModes;
+ device->SetVideoMode = QT_SetVideoMode;
+ device->UpdateMouse = QT_UpdateMouse;
+ device->SetColors = QT_SetColors;
+ device->UpdateRects = NULL;
+ device->VideoQuit = QT_VideoQuit;
+ device->AllocHWSurface = QT_AllocHWSurface;
+ device->CheckHWBlit = NULL;
+ device->FillHWRect = NULL;
+ device->SetHWColorKey = NULL;
+ device->SetHWAlpha = NULL;
+ device->LockHWSurface = QT_LockHWSurface;
+ device->UnlockHWSurface = QT_UnlockHWSurface;
+ device->FlipHWSurface = NULL;
+ device->FreeHWSurface = QT_FreeHWSurface;
+ device->SetIcon = NULL;
+ device->SetCaption = QT_SetWMCaption;
+ device->IconifyWindow = QT_IconifyWindow;
+ device->GrabInput = QT_GrabInput;
+ device->GetWMInfo = NULL;
+ device->FreeWMCursor = QT_FreeWMCursor;
+ device->CreateWMCursor = QT_CreateWMCursor;
+ device->ShowWMCursor = QT_ShowWMCursor;
+ device->WarpWMCursor = QT_WarpWMCursor;
+ device->InitOSKeymap = QT_InitOSKeymap;
+ device->PumpEvents = QT_PumpEvents;
+
+ device->free = QT_DeleteDevice;
+ device->ToggleFullScreen = QT_ToggleFullScreen;
+
+ /* Set the driver flags */
+ device->handles_any_size = 0;
+
+ return device;
+ }
+
+ VideoBootStrap Qtopia_bootstrap = {
+ "qtopia", "Qtopia / QPE graphics",
+ QT_Available, QT_CreateDevice
+ };
+
+ /* Function to sort the display_list */
+ static int CompareModes(const void *A, const void *B)
+ {
+#if 0
+ const display_mode *a = (display_mode *)A;
+ const display_mode *b = (display_mode *)B;
+
+ if ( a->space == b->space ) {
+ return((b->virtual_width*b->virtual_height)-
+ (a->virtual_width*a->virtual_height));
+ } else {
+ return(ColorSpaceToBitsPerPixel(b->space)-
+ ColorSpaceToBitsPerPixel(a->space));
+ }
+#endif
+ return 0;
+ }
+
+ /* Yes, this isn't the fastest it could be, but it works nicely */
+ static int QT_AddMode(_THIS, int index, unsigned int w, unsigned int h)
+ {
+ SDL_Rect *mode;
+ int i;
+ int next_mode;
+
+ /* Check to see if we already have this mode */
+ if ( SDL_nummodes[index] > 0 ) {
+ for ( i=SDL_nummodes[index]-1; i >= 0; --i ) {
+ mode = SDL_modelist[index][i];
+ if ( (mode->w == w) && (mode->h == h) ) {
+ return(0);
+ }
+ }
+ }
+
+ /* Set up the new video mode rectangle */
+ mode = (SDL_Rect *)SDL_malloc(sizeof *mode);
+ if ( mode == NULL ) {
+ SDL_OutOfMemory();
+ return(-1);
+ }
+ mode->x = 0;
+ mode->y = 0;
+ mode->w = w;
+ mode->h = h;
+#ifdef QTOPIA_DEBUG
+ fprintf(stderr, "Adding mode %dx%d at %d bytes per pixel\n", w, h, index+1);
+#endif
+
+ /* Allocate the new list of modes, and fill in the new mode */
+ next_mode = SDL_nummodes[index];
+ SDL_modelist[index] = (SDL_Rect **)
+ SDL_realloc(SDL_modelist[index], (1+next_mode+1)*sizeof(SDL_Rect *));
+ if ( SDL_modelist[index] == NULL ) {
+ SDL_OutOfMemory();
+ SDL_nummodes[index] = 0;
+ SDL_free(mode);
+ return(-1);
+ }
+ SDL_modelist[index][next_mode] = mode;
+ SDL_modelist[index][next_mode+1] = NULL;
+ SDL_nummodes[index]++;
+
+ return(0);
+ }
+
+ int QT_VideoInit(_THIS, SDL_PixelFormat *vformat)
+ {
+ /* Initialize the QPE Application */
+ /* Determine the screen depth */
+ vformat->BitsPerPixel = QPixmap::defaultDepth();
+
+ // For now we hardcode the current depth because anything else
+ // might as well be emulated by SDL rather than by Qtopia.
+
+ QSize desktop_size = qApp->desktop()->size();
+ QT_AddMode(_this, ((vformat->BitsPerPixel+7)/8)-1,
+ desktop_size.width(), desktop_size.height());
+ QT_AddMode(_this, ((vformat->BitsPerPixel+7)/8)-1,
+ desktop_size.height(), desktop_size.width());
+
+ /* Determine the current screen size */
+ _this->info.current_w = desktop_size.width();
+ _this->info.current_h = desktop_size.height();
+
+ /* Create the window / widget */
+ SDL_Win = new SDL_QWin(QSize(QT_HIDDEN_SIZE, QT_HIDDEN_SIZE));
+ ((QPEApplication*)qApp)->showMainWidget(SDL_Win);
+ /* Fill in some window manager capabilities */
+ _this->info.wm_available = 0;
+
+ /* We're done! */
+ return(0);
+ }
+
+ /* We support any dimension at our bit-depth */
+ SDL_Rect **QT_ListModes(_THIS, SDL_PixelFormat *format, Uint32 flags)
+ {
+ SDL_Rect **modes;
+
+ modes = ((SDL_Rect **)0);
+ if ( (flags & SDL_FULLSCREEN) == SDL_FULLSCREEN ) {
+ modes = SDL_modelist[((format->BitsPerPixel+7)/8)-1];
+ } else {
+ if ( format->BitsPerPixel ==
+ _this->screen->format->BitsPerPixel ) {
+ modes = ((SDL_Rect **)-1);
+ }
+ }
+ return(modes);
+ }
+
+ /* Various screen update functions available */
+ static void QT_NormalUpdate(_THIS, int numrects, SDL_Rect *rects);
+
+
+ static int QT_SetFullScreen(_THIS, SDL_Surface *screen, int fullscreen)
+ {
+ return -1;
+ }
+
+ static int QT_ToggleFullScreen(_THIS, int fullscreen)
+ {
+ return -1;
+ }
+
+ /* FIXME: check return values and cleanup here */
+ SDL_Surface *QT_SetVideoMode(_THIS, SDL_Surface *current,
+ int width, int height, int bpp, Uint32 flags)
+ {
+
+ QImage *qimage;
+ QSize desktop_size = qApp->desktop()->size();
+
+
+ current->flags = 0; //SDL_FULLSCREEN; // We always run fullscreen.
+
+ if(width <= desktop_size.width()
+ && height <= desktop_size.height()) {
+ current->w = desktop_size.width();
+ current->h = desktop_size.height();
+ } else if(width <= desktop_size.height() && height <= desktop_size.width()) {
+ // Landscape mode
+ char * envString = SDL_getenv(SDL_QT_ROTATION_ENV_NAME);
+ int envValue = envString ? atoi(envString) : 0;
+ screenRotation = envValue ? SDL_QT_ROTATION_270 : SDL_QT_ROTATION_90;
+ current->h = desktop_size.width();
+ current->w = desktop_size.height();
+ } else {
+ SDL_SetError("Unsupported resolution, %dx%d\n", width, height);
+ }
+ if ( flags & SDL_OPENGL ) {
+ SDL_SetError("OpenGL not supported");
+ return(NULL);
+ }
+ /* Create the QImage framebuffer */
+ qimage = new QImage(current->w, current->h, bpp);
+ if (qimage->isNull()) {
+ SDL_SetError("Couldn't create screen bitmap");
+ delete qimage;
+ return(NULL);
+ }
+ current->pitch = qimage->bytesPerLine();
+ current->pixels = (void *)qimage->bits();
+ SDL_Win->setImage(qimage);
+ _this->UpdateRects = QT_NormalUpdate;
+ SDL_Win->setFullscreen(true);
+ /* We're done */
+ return(current);
+ }
+
+ /* Update the current mouse state and position */
+ void QT_UpdateMouse(_THIS)
+ {
+ QPoint point(-1, -1);
+ if ( SDL_Win->isActiveWindow() ) {
+ point = SDL_Win->mousePos();
+ }
+
+ if ( (point.x() >= 0) && (point.x() < SDL_VideoSurface->w) &&
+ (point.y() >= 0) && (point.y() < SDL_VideoSurface->h) ) {
+ SDL_PrivateAppActive(1, SDL_APPMOUSEFOCUS);
+ SDL_PrivateMouseMotion(0, 0,
+ (Sint16)point.x(), (Sint16)point.y());
+ } else {
+ SDL_PrivateAppActive(0, SDL_APPMOUSEFOCUS);
+ }
+ }
+
+ /* We don't actually allow hardware surfaces other than the main one */
+ static int QT_AllocHWSurface(_THIS, SDL_Surface *surface)
+ {
+ return(-1);
+ }
+ static void QT_FreeHWSurface(_THIS, SDL_Surface *surface)
+ {
+ return;
+ }
+ static int QT_LockHWSurface(_THIS, SDL_Surface *surface)
+ {
+ return(0);
+ }
+ static void QT_UnlockHWSurface(_THIS, SDL_Surface *surface)
+ {
+ return;
+ }
+
+ static void QT_NormalUpdate(_THIS, int numrects, SDL_Rect *rects)
+ {
+ if(SDL_Win->lockScreen()) {
+ for(int i=0; i<numrects; ++i ) {
+ QRect rect(rects[i].x, rects[i].y,
+ rects[i].w, rects[i].h);
+ SDL_Win->repaintRect(rect);
+ }
+ SDL_Win->unlockScreen();
+ }
+ }
+ /* Is the system palette settable? */
+ int QT_SetColors(_THIS, int firstcolor, int ncolors, SDL_Color *colors)
+ {
+ return -1;
+ }
+
+ void QT_VideoQuit(_THIS)
+ {
+ // This is dumb, but if I free this, the app doesn't exit correctly.
+ // Of course, this will leak memory if init video is done more than once.
+ // Sucks but such is life.
+
+ // -- David Hedbor
+ // delete SDL_Win;
+ // SDL_Win = 0;
+ _this->screen->pixels = NULL;
+ QT_GrabInput(_this, SDL_GRAB_OFF);
+ }
+
+ static int QT_IconifyWindow(_THIS) {
+ SDL_Win->hide();
+
+ return true;
+ }
+
+ static SDL_GrabMode QT_GrabInput(_THIS, SDL_GrabMode mode) {
+ if(mode == SDL_GRAB_OFF) {
+ QPEApplication::grabKeyboard();
+ qApp->processEvents();
+ QPEApplication::ungrabKeyboard();
+ } else {
+ QPEApplication::grabKeyboard();
+ }
+ qApp->processEvents();
+ return mode;
+ }
+
+}; /* Extern C */