diff options
-rw-r--r-- | backends/wince/findgame.cpp | 5 | ||||
-rw-r--r-- | backends/wince/pocketpc.cpp | 104 | ||||
-rw-r--r-- | backends/wince/screen.cpp | 237 | ||||
-rw-r--r-- | backends/wince/screen.h | 3 |
4 files changed, 314 insertions, 35 deletions
diff --git a/backends/wince/findgame.cpp b/backends/wince/findgame.cpp index e4aa7411f3..1cba8c139c 100644 --- a/backends/wince/findgame.cpp +++ b/backends/wince/findgame.cpp @@ -854,6 +854,11 @@ void handleSelectGame(int x, int y) { x -= _game_selection_X_offset; y -= _game_selection_Y_offset; + if (y < start - 10) { + drawVideoDevice(); + return; + } + /* See if it's a selection */ for (i=0; i<MAX_DISPLAYED_GAMES; i++) { diff --git a/backends/wince/pocketpc.cpp b/backends/wince/pocketpc.cpp index c9bfd1d553..fc011b8afa 100644 --- a/backends/wince/pocketpc.cpp +++ b/backends/wince/pocketpc.cpp @@ -177,8 +177,8 @@ pseudoGAPI availablePseudoGAPI[] = { }, { TEXT("Compaq iPAQ H3600"), /* this is just a test for my device :) */ (void*)0xAC05029E, - 320, 240, + 320, 640, -2, 16, @@ -249,7 +249,7 @@ BOOL defaultSHSipPreference(HWND handle, SIPSTATE state) { /* Default GAPI */ int defaultGXOpenDisplay(HWND hWnd, DWORD dwFlags) { - return 0; + return GAPI_SIMU; } int defaultGXCloseDisplay() { @@ -311,8 +311,8 @@ GameX *gameX; int gameXGXOpenDisplay(HWND hWnd, DWORD dwFlags) { gameX = new GameX(); if (!gameX->OpenGraphics()) { - MessageBox(NULL, TEXT("Couldn't initialize GameX"), TEXT("Error"), MB_OK); - exit(1); + MessageBox(NULL, TEXT("Couldn't initialize GameX. Reverting to GDI graphics"), TEXT("PocketScumm rendering"), MB_OK); + noGAPI = 1; } return 0; } @@ -419,6 +419,8 @@ extern void abortScanPath(); void keypad_init(); +extern char noGAPI; + class OSystem_WINCE3 : public OSystem { public: // Set colors of the palette @@ -707,7 +709,32 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLin //HMODULE SDLAudio_handle; HMODULE GAPI_handle; + /* Create the main window */ + WNDCLASS wcex; + wcex.style = CS_HREDRAW | CS_VREDRAW; + wcex.lpfnWndProc = (WNDPROC)OSystem_WINCE3::WndProc; + wcex.cbClsExtra = 0; + wcex.cbWndExtra = 0; + wcex.hInstance = GetModuleHandle(NULL); + wcex.hIcon = 0; + wcex.hCursor = NULL; + wcex.hbrBackground = (HBRUSH)GetStockObject(BLACK_BRUSH); + wcex.lpszMenuName = 0; + wcex.lpszClassName = TEXT("ScummVM"); + if (!RegisterClass(&wcex)) + Error(TEXT("Cannot register window class!")); + + hWnd_Window = CreateWindow(TEXT("ScummVM"), TEXT("ScummVM"), WS_VISIBLE, + 0, 0, GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN), NULL, NULL, GetModuleHandle(NULL), NULL); + + ShowWindow(hWnd_Window, SW_SHOW); + UpdateWindow(hWnd_Window); + hide_toolbar = false; + noGAPI = 0; + + g_config = new Config("scummvm.ini", "scummvm"); + g_config->set_writing(true); // See if we're running on a Windows CE version supporting aygshell aygshell_handle = LoadLibrary(TEXT("aygshell.dll")); @@ -754,8 +781,16 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLin } if (!availablePseudoGAPI[i].device) { - MessageBox(NULL, TEXT("Cannot find GX.dll and no workaround for this device ! better luck next time ..."), TEXT("GAPI not found"), MB_OK); - exit(1); + noGAPI = 1; + } + else { + if (!g_config->getBool("DirectVideoCheck", false, "wince")) { + if (MessageBox(NULL, TEXT("Direct video support is available for this device. Do you want to use it ?"), TEXT("PocketScumm Rendering"), MB_YESNO|MB_ICONQUESTION|MB_DEFBUTTON1|MB_APPLMODAL) == IDNO) + noGAPI = 1; + MessageBox(NULL, TEXT("Delete scummvm.ini or remove the DirectVideoCheck key if you want to change this setting later"), TEXT("PocketScumm Rendering"), MB_OK|MB_APPLMODAL); + g_config->setBool("DirectVideoCheck", true, "wince"); + g_config->flush(); + } } dynamicGXOpenInput = defaultGXOpenInput; @@ -787,9 +822,6 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLin gfx_mode_switch = false; } - g_config = new Config("scummvm.ini", "scummvm"); - g_config->set_writing(true); - sound = g_config->getBool("Sound", true, "wince"); if (sound) sound_activated = sound; @@ -802,26 +834,7 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLin select_game = true; - /* Create the main window */ - WNDCLASS wcex; - wcex.style = CS_HREDRAW | CS_VREDRAW; - wcex.lpfnWndProc = (WNDPROC)OSystem_WINCE3::WndProc; - wcex.cbClsExtra = 0; - wcex.cbWndExtra = 0; - wcex.hInstance = GetModuleHandle(NULL); - wcex.hIcon = 0; - wcex.hCursor = NULL; - wcex.hbrBackground = (HBRUSH)GetStockObject(BLACK_BRUSH); - wcex.lpszMenuName = 0; - wcex.lpszClassName = TEXT("ScummVM"); - if (!RegisterClass(&wcex)) - Error(TEXT("Cannot register window class!")); - - hWnd_Window = CreateWindow(TEXT("ScummVM"), TEXT("ScummVM"), WS_VISIBLE, - 0, 0, GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN), NULL, NULL, GetModuleHandle(NULL), NULL); - ShowWindow(hWnd_Window, SW_SHOW); - UpdateWindow(hWnd_Window); GraphicsOn(hWnd_Window, gfx_mode_switch); // open GAPI in Portrait mode GAPIKeysInit(); Cls(); @@ -925,10 +938,11 @@ LRESULT CALLBACK OSystem_WINCE3::WndProc(HWND hWnd, UINT message, WPARAM wParam, switch (message) { case WM_CREATE: + memset(&sai, 0, sizeof(sai)); dynamicSHSipPreference(hWnd, SIP_FORCEDOWN); // SHSipPreference(hWnd, SIP_INPUTDIALOG); - + return 0; case WM_DESTROY: @@ -1520,12 +1534,16 @@ OSystem *OSystem_WINCE3::create(int gfx_mode, bool full_screen) { reducePortraitGeometry(); + if ((noGAPI || !gfx_mode_switch) && GetSystemMetrics(SM_CXSCREEN) < 320) + SetScreenMode(1); + Cls(); drawWait(); // Set mode, portrait or landscape display_mode = g_config->get("DisplayMode", "wince"); - if (display_mode) + + if (display_mode && !(noGAPI || !gfx_mode_switch)) SetScreenMode(atoi(display_mode)); return syst; @@ -1799,11 +1817,37 @@ bool OSystem_WINCE3::poll_event(Event *event) { return false; } + +//#define MAX_DEBUG_SOUND 10 void own_soundProc(void *buffer, byte *samples, int len) { +/* + static int debug_sound_counter = 0; + + static FILE *debug_sound = NULL; +*/ + (*real_soundproc)(buffer, samples, len); +/* + if (debug_sound_counter < MAX_DEBUG_SOUND) { + int i; + + for (i=0; i<len; i++) + if (samples[i]) + break; + if (i != len) { + if (!debug_sound_counter) + debug_sound = fopen("\\Carte de stockage\\sound.dmp", "wb"); + fwrite(samples, 1, len, debug_sound); + debug_sound_counter++; + if (debug_sound_counter == MAX_DEBUG_SOUND) + fclose(debug_sound); + } + } +*/ + if (!sound_activated) memset(samples, 0, len); } diff --git a/backends/wince/screen.cpp b/backends/wince/screen.cpp index 14ad6e4c99..36da11fb0e 100644 --- a/backends/wince/screen.cpp +++ b/backends/wince/screen.cpp @@ -118,6 +118,11 @@ int toolbar_available; UBYTE *toolbar = NULL; +UBYTE *noGAPI_video_buffer = NULL; +HDC noGAPI_compat; + +char noGAPI = 0; + /* Using vectorized function to save on branches */ typedef void (*tCls)(); typedef void (*tBlt)(UBYTE*); @@ -127,22 +132,29 @@ typedef void (*tSet_565)(INT16 *buffer, int pitch, int x, int y, int width, int void mono_Cls(); void mono_Blt(UBYTE*); void mono_Blt_part(UBYTE*, int, int, int, int, UBYTE*, int); +void mono_Set_565(INT16*, int, int, int, int, int); + void palette_Cls(); void palette_Blt(UBYTE*); void palette_Blt_part(UBYTE*, int, int, int, int, UBYTE*, int); +void palette_Set_565(INT16*, int, int, int, int, int); + void hicolor_Cls(); void hicolor555_Blt(UBYTE*); void hicolor555_Blt_part(UBYTE*, int, int, int, int, UBYTE*, int); +void hicolor555_Set_565(INT16*, int, int, int, int, int); + void hicolor565_Blt(UBYTE*); void hicolor565_Blt_part(UBYTE*, int, int, int, int, UBYTE*, int); void hicolor565_Get_565(INT16*, int, int, int, int, int); void hicolor565_Set_565(INT16*, int, int, int, int, int); -void hicolor555_Set_565(INT16*, int, int, int, int, int); -void palette_Set_565(INT16*, int, int, int, int, int); -void mono_Set_565(INT16*, int, int, int, int, int); +void noGAPI_Cls(); +void noGAPI_Blt(UBYTE*); +void noGAPI_Blt_part(UBYTE*, int, int, int, int, UBYTE*, int); +void noGAPI_Set_565(INT16*, int, int, int, int, int); void NULL_Get_565(INT16*, int, int, int, int, int); void NULL_Set_565(INT16*, int, int, int, int, int); @@ -188,6 +200,39 @@ static int _saved_geometry_h; HWND hWndMain; +typedef enum { + DEVICE_GAPI = 0, + DEVICE_VIDEO, + DEVICE_GDI +} gfxDevice; + +typedef enum { + VIDEO_565 = 0, + VIDEO_555, + VIDEO_PALETTED, + VIDEO_MONO, + VIDEO_DONT_CARE +} gfxOption; + + +unsigned char* gfx_device_name[] = { + (unsigned char*)"GAPI", + (unsigned char*)"Direct Video", + (unsigned char*)"GDI" +}; + +unsigned char* gfx_device_options_name[] = { + (unsigned char*)"565", + (unsigned char*)"555", + (unsigned char*)"paletted", + (unsigned char*)"mono", + (unsigned char*)"" +}; + +gfxDevice _gfx_device; +gfxOption _gfx_option; + + unsigned char *image_expand(unsigned char *src) { int i = 0; int j; @@ -280,7 +325,11 @@ void RestoreScreenGeometry() { int GraphicsOn(HWND hWndMain_param, bool gfx_mode_switch) { hWndMain = hWndMain_param; - dynamicGXOpenDisplay(hWndMain, GX_FULLSCREEN); + + _gfx_device = DEVICE_GAPI; + + if (dynamicGXOpenDisplay(hWndMain, GX_FULLSCREEN) == GAPI_SIMU) + _gfx_device = DEVICE_VIDEO; _gfx_mode_switch = gfx_mode_switch; @@ -293,6 +342,8 @@ int GraphicsOn(HWND hWndMain_param, bool gfx_mode_switch) _game_selection_Y_offset = 0; } + memset(&gxdp, 0, sizeof(gxdp)); + gxdp = dynamicGXGetDisplayProperties(); // Possible Aero problem @@ -306,7 +357,28 @@ int GraphicsOn(HWND hWndMain_param, bool gfx_mode_switch) gxdp.ffFormat = kfDirect | kfDirect565; } - if(gxdp.ffFormat & kfDirect565) + if(noGAPI) + { + HDC hdc; + + pCls = noGAPI_Cls; + pBlt = noGAPI_Blt; + pBlt_part = noGAPI_Blt_part; + pSet_565 = noGAPI_Set_565; + + toolbar_available = 1; + + // Init GDI + noGAPI_video_buffer = (UBYTE*)malloc(320 * 240 * 2); + + hdc = GetDC(hWndMain); + noGAPI_compat = CreateCompatibleDC(hdc); + ReleaseDC(hWndMain, hdc); + + _gfx_device = DEVICE_GDI; + _gfx_option = VIDEO_DONT_CARE; + } + else if(gxdp.ffFormat & kfDirect565) { pCls = hicolor_Cls; pBlt = hicolor565_Blt; @@ -315,6 +387,8 @@ int GraphicsOn(HWND hWndMain_param, bool gfx_mode_switch) filter_available = 1; smooth_filter = 1; toolbar_available = 1; + + _gfx_option = VIDEO_565; } else if(gxdp.ffFormat & kfDirect555) { @@ -325,6 +399,8 @@ int GraphicsOn(HWND hWndMain_param, bool gfx_mode_switch) filter_available = 1; smooth_filter = 1; toolbar_available = 1; + + _gfx_option = VIDEO_555; } else if((gxdp.ffFormat & kfDirect) && (gxdp.cBPP <= 8)) { @@ -341,6 +417,8 @@ int GraphicsOn(HWND hWndMain_param, bool gfx_mode_switch) filter_available = 1; toolbar_available = 1; + + _gfx_option = VIDEO_MONO; } else if(gxdp.ffFormat & kfPalette) { @@ -350,6 +428,8 @@ int GraphicsOn(HWND hWndMain_param, bool gfx_mode_switch) pSet_565 = palette_Set_565; toolbar_available = 1; + + _gfx_option = VIDEO_PALETTED; } @@ -595,6 +675,14 @@ void drawBlankGameSelection() { pBlt_part(decomp, _game_selection_X_offset, _game_selection_Y_offset, 220, 250, item_startup_colors, 0); } +void drawVideoDevice() { + char video_device[100]; + + sprintf(video_device, "Video device : %s %s", gfx_device_name[_gfx_device], gfx_device_options_name[_gfx_option]); + printString(video_device, 10, 270, 2, 0); + pBlt_part(decomp + (270 * 220), 0, 5, 220, 8, item_startup_colors, 0); +} + void drawCommentString(char *comment) { /* Erase old comment */ memcpy(decomp + (206 * 220), comment_zone, 8 * 220); @@ -1924,6 +2012,145 @@ void hicolor565_Blt_part(UBYTE * scr_ptr, int x, int y, int width, int height, } } +/* ********************************* NO GAPI DISPLAY ********************************* */ + +void noGAPI_Cls() { + HBITMAP old; + RECT rc; + HDC hdc = GetDC(hWndMain); + HBITMAP hb; + + GetWindowRect(hWndMain, &rc); + memset(noGAPI_video_buffer, 0x00, sizeof(noGAPI_video_buffer)); + if (currentScreenMode) + hb = CreateBitmap(320, 240, 1, 16, noGAPI_video_buffer); + else + hb = CreateBitmap(240, 320, 1, 16, noGAPI_video_buffer); + old = (HBITMAP)SelectObject(noGAPI_compat, hb); + if (currentScreenMode) + BitBlt(hdc, 0, 0, 320, 240, noGAPI_compat, 0, 0, SRCCOPY); + else + BitBlt(hdc, 0, 0, 240, 320, noGAPI_compat, 0, 0, SRCCOPY); + SelectObject(noGAPI_compat, old); + ReleaseDC(hWndMain, hdc); + DeleteObject(hb); +} + +void noGAPI_Blt(UBYTE *src_ptr) { + noGAPI_Blt_part(src_ptr, 0, 0, _geometry_w, _geometry_h, NULL, 0); +} + +void noGAPI_Set_565(INT16 *buffer, int pitch, int x, int y, int width, int height) { + HBITMAP old; + RECT rc; + HDC hdc = GetDC(hWndMain); + HBITMAP hb; + UBYTE *work_buffer; + int i; + int j; + long skipmask; + + skipmask = geom[useMode].xSkipMask; + + + GetWindowRect(hWndMain, &rc); + + work_buffer = noGAPI_video_buffer; + unsigned short *work_buffer_2 = (unsigned short*)work_buffer; + if (currentScreenMode) { + + for (i=0; i<width; i++) { + for (j=0; j<height; j++) { + work_buffer_2[i * height + j] = + buffer[(pitch ? pitch : width) * j + (width - i)]; + } + } + } + else { + for (i=0; i<height; i++) { + for (j=0; j<width; j++) { + *(unsigned short*)work_buffer = buffer[j]; + work_buffer += 2; + } + } + } + + if (currentScreenMode) + hb = CreateBitmap(height, width, 1, 16, noGAPI_video_buffer); + else + hb = CreateBitmap(width, height, 1, 16, noGAPI_video_buffer); + old = (HBITMAP)SelectObject(noGAPI_compat, hb); + if (currentScreenMode) + BitBlt(hdc, y , 320 - (x + width), height, width, noGAPI_compat, 0, 0, SRCCOPY); + else + BitBlt(hdc, x, y, width, height, noGAPI_compat, 0, 0, SRCCOPY); + SelectObject(noGAPI_compat, old); + ReleaseDC(hWndMain, hdc); + DeleteObject(hb); +} + +void noGAPI_Blt_part(UBYTE * scr_ptr, int x, int y, int width, int height, + UBYTE * own_palette, int pitch) { + HBITMAP old; + RECT rc; + HDC hdc = GetDC(hWndMain); + HBITMAP hb; + UBYTE *work_buffer; + int i; + int j; + long skipmask; + + skipmask = geom[useMode].xSkipMask; + + + GetWindowRect(hWndMain, &rc); + + work_buffer = noGAPI_video_buffer; + if (currentScreenMode) { + unsigned short *work_buffer_2 = (unsigned short*)work_buffer; + for (i=0; i<width; i++) + for (j=0; j<height; j++) + if (!own_palette) + work_buffer_2[i * height + j] = + pal[scr_ptr[(pitch ? pitch : width) * j + (width - i)]]; + else + work_buffer_2[i * height + j] = + COLORCONV565(own_palette[3 * scr_ptr[(pitch ? pitch : width) * j + (width - i)]], + own_palette[(3 * scr_ptr[(pitch ? pitch : width) * j + (width - i)]) + 1], + own_palette[(3 * scr_ptr[(pitch ? pitch : width) * j + (width - i)]) + 2]); + } + else { + for (i=0; i<height; i++) { + for (j=0; j<width; j++) { + if (!own_palette) + *(unsigned short*)work_buffer = + pal[scr_ptr[(pitch ? pitch : width) * i + j]]; + else + *(unsigned short*)work_buffer = + COLORCONV565(own_palette[3 * scr_ptr[(pitch ? pitch : width) * i + j]], + own_palette[(3 * scr_ptr[(pitch ? pitch : width) * i + j]) + 1], + own_palette[(3 * scr_ptr[(pitch ? pitch : width) * i + j]) + 2]); + + work_buffer += 2; + } + } + } + + if (currentScreenMode) + hb = CreateBitmap(height, width, 1, 16, noGAPI_video_buffer); + else + hb = CreateBitmap(width, height, 1, 16, noGAPI_video_buffer); + old = (HBITMAP)SelectObject(noGAPI_compat, hb); + if (currentScreenMode) + BitBlt(hdc, y , 320 - (x + width), height, width, noGAPI_compat, 0, 0, SRCCOPY); + else + BitBlt(hdc, x, y, width, height, noGAPI_compat, 0, 0, SRCCOPY); + SelectObject(noGAPI_compat, old); + ReleaseDC(hWndMain, hdc); + DeleteObject(hb); +} + + /* ************************** STYLUS TRANSLATION ************************* */ diff --git a/backends/wince/screen.h b/backends/wince/screen.h index 17f27dc86a..47ad51ddae 100644 --- a/backends/wince/screen.h +++ b/backends/wince/screen.h @@ -35,6 +35,8 @@ #define GAME_SELECTION_X_OFFSET 15 #define GAME_SELECTION_Y_OFFSET 25 +#define GAPI_SIMU 0x123456 + void SetScreenGeometry(int w, int h); void LimitScreenGeometry(); void RestoreScreenGeometry(); @@ -55,6 +57,7 @@ void Set_565(INT16 *buffer, int pitch, int x, int y, int width, int height); void SetScreenMode(int mode); int GetScreenMode(); void drawWait(); +void drawVideoDevice(); void drawBlankGameSelection(); void reducePortraitGeometry(); |