// DDRestoreCanvas // ---------------------------------------------------------------------------- BOOL DDRestoreCanvas(dd_grs_canvas *canvas) { HRESULT ddresult; Assert(canvas->lpdds != NULL); ddresult = IDirectDrawSurface_Restore(canvas->lpdds); if (ddresult != DD_OK) { if (ddresult != DDERR_WRONGMODE) { logentry("DDRAW::RestoreCanvas::Surface err: %x\n", ddresult); return FALSE; } mprintf((0, "Recreating surfaces:\n")); // Must recreate canvas if (canvas->lpdds == _lpDDSPrimary || canvas->lpdds == _lpDDSBack) { mprintf((0, "DDRestoreCanvas::Screen memory was lost!\n")); exit(1); } if (canvas->sram) { // force sysmem canvas! canvas->lpdds = DDCreateSysMemSurface(canvas->canvas.cv_bitmap.bm_w, canvas->canvas.cv_bitmap.bm_h); } else { canvas->lpdds = DDCreateSurface(canvas->canvas.cv_bitmap.bm_w, canvas->canvas.cv_bitmap.bm_h, _DDSysMemSurfacing); } } return TRUE; }
int GGI_directx_DDChangeMode(struct ggi_visual *vis, ggi_mode *mode) { directx_priv *priv = GGIDIRECTX_PRIV(vis); /* destroy any existing surface */ DDDestroySurface(priv); /* recreate the primary surface and back storage */ if (!DDCreateSurface(priv, mode)) return 0; if (!priv->fullscreen) /* set the new window size */ DDChangeWindow(priv, mode->visible.x, mode->visible.y); /* set a timer to have the window refreshed at regular intervals, and show the window */ if (!(LIBGGI_FLAGS(vis) & GGIFLAG_ASYNC)) priv->timer_id = SetTimer(priv->hWnd, 1, 33, NULL); ShowWindow(priv->hWnd, SW_SHOWNORMAL); if (priv->hParent == NULL) SetForegroundWindow(priv->hWnd); return 1; }
JNIEXPORT void JNICALL Java_sun_awt_windows_Win32OffScreenSurfaceData_initSurface(JNIEnv *env, jobject sData, jint depth, jint width, jint height, jint screen, jboolean isVolatile, jint transparency) { Win32SDOps *wsdo = (Win32SDOps *)SurfaceData_GetOps(env, sData); DTRACE_PRINTLN("Win32OSSD_initSurface"); initOSSD_WSDO(env, wsdo, width, height, screen, transparency); if (!DDCreateSurface(wsdo, isVolatile /* d3d caps desired, if possible */)) { DTRACE_PRINTLN1("Win32OSD.initSurface: Can't create offsc surf tr=%d\n", transparency); SurfaceData_ThrowInvalidPipeException(env, "Can't create offscreen surf"); } else { wsdo->surfacePuntData.lpSurfaceVram = wsdo->lpSurface; if (!D3DEnabled(wsdo)) { // d3d enabled by default for each surface - disable if necessary env->SetBooleanField(sData, localD3dEnabledID, JNI_FALSE); } else { env->SetBooleanField(sData, d3dClippingEnabledID, (DDINSTANCE_USABLE(wsdo->ddInstance) && wsdo->ddInstance->canClipD3dLines)); } } // 8 is somewhat arbitrary; we want the threshhold to represent a // significant portion of the surface area in order to avoid // punting for occasional, small reads wsdo->surfacePuntData.pixelsReadThreshold = width * height / 8; /** * Only enable our punt-to-sysmem-surface scheme for surfaces that are: * - non-transparent (we really only intended this workaround for * back buffers, which are usually opaque) * - volatile (non-volatile images should not even get into the punt * situation since they should not be a rendering destination, but * we check this just to make sure) * And only do so if the user did not specify that punting be disabled */ wsdo->surfacePuntData.disablePunts = (transparency != TR_OPAQUE) || !isVolatile || ddVramForced; }
// DirectDrawSurface2 Calls void DDCreateSurfaceInMemory ( LPDIRECTDRAW2 pExistingDirectDraw, DDSURFACEDESC *pNewSurfaceDesc, BOOLEAN fVideoMemory, LPDIRECTDRAWSURFACE *ppNewSurface1, LPDIRECTDRAWSURFACE2 *ppNewSurface2 ) { DDSURFACEDESC DDSurfaceDesc; BOOLEAN fDestination; Assert ( pExistingDirectDraw != NULL ); Assert ( pNewSurfaceDesc != NULL ); Assert ( ppNewSurface1 != NULL ); Assert ( ppNewSurface2 != NULL ); // copy to a local so we don't change the input parameter memcpy ( &DDSurfaceDesc, pNewSurfaceDesc, sizeof ( DDSURFACEDESC ) ); // must have caps set since we are adding to the ddsCaps element DDSurfaceDesc.dwFlags |= DDSD_CAPS; // If this is a hardware D3D driver, the Z-Buffer MUST end up in video // memory. Otherwise, it MUST end up in system memory. if ( fVideoMemory ) DDSurfaceDesc.ddsCaps.dwCaps |= DDSCAPS_VIDEOMEMORY; else DDSurfaceDesc.ddsCaps.dwCaps |= DDSCAPS_SYSTEMMEMORY; // create the surface DDCreateSurface ( pExistingDirectDraw, &DDSurfaceDesc, ppNewSurface1, ppNewSurface2 ); // get surface information DDGetSurfaceDescription ( *ppNewSurface2, &DDSurfaceDesc ); // was the surface created in video memory? fDestination = ( DDSurfaceDesc.ddsCaps.dwCaps & DDSCAPS_VIDEOMEMORY ) ? TRUE : FALSE; // did we create the surface in the right memory area? if ( fDestination != fVideoMemory ) { // nope we couldn't do it right so release the newly created surface // and pass back a NULL pointer to the user DDReleaseSurface ( ppNewSurface1, ppNewSurface2 ); } }
int DDInitWindowed(int width, int height, int bpp, HWND hwnd) { HRESULT ret; // create object and test for error if (DirectDrawCreate(NULL, &lpDD, NULL) != DD_OK) { return(0); } // set cooperation level to windowed mode normal if (lpDD->SetCooperativeLevel(hwnd, DDSCL_NORMAL) != DD_OK) { return(0); } // set globals screen_height = height; screen_width = width; screen_bpp = bpp; // Create the primary surface memset(&ddsd, 0, sizeof(ddsd)); ddsd.dwSize = sizeof(ddsd); ddsd.dwFlags = DDSD_CAPS; // all we need for windowed mode is access to the primary surface ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE; // create the primary surface ret = lpDD->CreateSurface(&ddsd, &lpDDSPrimary, NULL); // create an offscreen and system mem back surface lpDDSBack = DDCreateSurface(width, height, NULL); lpDD->CreateClipper(0, &lpDDClipper, NULL); lpDDClipper->SetHWnd(0, hwnd); lpDDSPrimary->SetClipper(lpDDClipper); // clear out both primary and secondary surfaces DDFillSurface(lpDDSPrimary, 0); DDFillSurface(lpDDSBack, 0); DDGetRGB16(); return 1; }
bool InitApp(HINSTANCE hInstance, int nCmdShow) { WNDCLASS WinClass; //------------------------------------------------------------------ // Histoire d'avoir un joli fichier log //------------------------------------------------------------------ debug << "---------------------------------------------------------------\n"; debug << "Blip & Blop - (c) LOADED Studio - " << __DATE__ << "\n"; debug << "---------------------------------------------------------------\n"; //------------------------------------------------------------------ // Precalculs mathématiques //------------------------------------------------------------------ preCalcMathsFunctions(); //------------------------------------------------------------------ // FMOD / Sons //------------------------------------------------------------------ if (!FSOUND_Init(22050, CHANNEL_NUMBER, 0)) { Warning("Cannot initialise FMOD. Sound will be turned off."); LOGI("BUG AUDIO"); sound_on = false; music_on = false; } else { // Pour éviter que les musiques ne se fassent écraser par les sons // FSOUND_SetPriority(0, 255); } //------------------------------------------------------------------ // Timer //------------------------------------------------------------------ LInitTimer(); //------------------------------------------------------------------ // Charge la configuration //------------------------------------------------------------------ load_BB3_config(CONFIG_FILE); //------------------------------------------------------------------ // Charge les hi scores //------------------------------------------------------------------ hi_scores.init(); if (!hi_scores.load(HISCORES_FILE)) { debug << "Cannot load hi-scores file. Use default hi-scores\n"; hi_scores.init(); } else { debug << "Using " << HISCORES_FILE << " as hiscores file\n"; } //------------------------------------------------------------------ // Les fichiers textes //------------------------------------------------------------------ if (lang_type == LANG_UK) { if (!loadTxtData("data/uk.dat")) { Bug("Cannot open the file 'data/uk.dat'"); ReleaseAll(); return false; } } else { if (!loadTxtData("data/fr.dat")) { Bug("Cannot open the file 'data/fr.dat'"); ReleaseAll(); return false; } } //------------------------------------------------------------------ // Direct Input //------------------------------------------------------------------ if (!in.open(WinHandle, hInstance)) { Bug("Cannot initialise DirectInput. Make sure DirectX 7 or better is installed."); ReleaseAll(); return false; } debug << "DI Initialized\n"; //------------------------------------------------------------------ // Direct Draw (1ère partie) //------------------------------------------------------------------ LOGI("first"); if (!DDInitDirectDraw()) { Bug("Cannot initialise DirectDraw. Make sure DirectX 7 or better is installed."); ReleaseAll(); return false; } debug << "DD Initialized\n"; active = true; //Activate the game loop LOGI("second"); if (!DDSetCooperativeLevel(WinHandle)) { Bug("Cannot get EXCLUSIVE MODE. Close all other applications and launch Blip'n Blop again"); ReleaseAll(); return false; } debug << "Exclusive mode set\n"; LOGI("third"); static const int BEST_RATE = 85; if (safeMode) { debug << "Safe mode enabled, using default 640x480x16 refresh rate.\n"; winSet = false; if (!DDSetGfxMode(640, 480, 16)) { Bug("Cannot set display mode to 640x480x16. Are you sure your video card meets the requirements ?"); ReleaseAll(); return false; } } else { debug << "Trying to create window\n"; if (!DDSetGfxMode(640, 480, 16)) { Bug("Cannot set display mode to 640x480x16. Are you sure your video card meets the requirements ?"); ReleaseAll(); return false; } debug << "Window creation done\n"; } LOGI("fouth"); //------------------------------------------------------------------ // Direct Draw (suite) //------------------------------------------------------------------ // Crée la surface primaire avec double buffer debug << "Creating primSurface\n"; primSurface = DDCreatePrimary(backSurface); if (primSurface == NULL || backSurface == NULL) { Bug("Cannot get a primary surface. Please reboot your PC and try to launch Blip'n Blop again.\nBe sure you have at least 2 Mb of video memory on your video card."); ReleaseAll(); return false; } debug << "primSurface created\n"; LOGI("fifth"); //------------------------------------------------------------------ // Surface système //------------------------------------------------------------------ debug << "Creating systemSurface\n"; systemSurface = DDCreateSurface(640, 480, DDSURF_SYSTEM); if (systemSurface == NULL) { Bug("Not enough memory. Blip'n Blop needs 32 Mo of free memory. Try to close all other applications and launch Blip'n Blop again."); ReleaseAll(); return false; } debug << "systemSurface created\n"; LOGI("sixth"); //------------------------------------------------------------------ // LGX paker //------------------------------------------------------------------ debug << "Initializing LGXpaker\n"; if (!LGXpaker.init(primSurface)) { Bug("Cannot initialise LGX paker. Please get the latest drivers for your video card."); ReleaseAll(); return false; } debug << "LGXpaker initialized\n"; LOGI("seventh"); //------------------------------------------------------------------ // Scroll buffers //------------------------------------------------------------------ debug << "Creating video buffer of size " << (WANTED_VBUFFER_WIDE) << "..."; videoA = DDCreateSurface(WANTED_VBUFFER_WIDE, 480, DDSURF_VIDEO); if (videoA == NULL) { debug << "Failed\n"; debug << "Creating video buffer of size " << (WANTED_VBUFFER_WIDE - 100) << "..."; videoA = DDCreateSurface(WANTED_VBUFFER_WIDE - 100, 480, DDSURF_VIDEO); if (videoA == NULL) { debug << "Failed\n"; debug << "Creating video buffer (" << (WANTED_VBUFFER_WIDE - 200) << ")..."; videoA = DDCreateSurface(WANTED_VBUFFER_WIDE - 200, 480, DDSURF_VIDEO); if (videoA == NULL) { debug << "Failed\n"; videoA = DDCreateSurface(WANTED_VBUFFER_WIDE, 480, DDSURF_SYSTEM); if (videoA == NULL) { Bug("Not enough memory. Blip'n Blop needs 32 Mo of free memory. Try to close all other applications and launch Blip'n Blop again."); ReleaseAll(); return false; } debug << "Cannot create video buffer. Use system buffer instead.\n"; vbuffer_wide = WANTED_VBUFFER_WIDE; mem_flag = DDSURF_SYSTEM; video_buffer_on = false; } else { debug << "Ok\n"; vbuffer_wide = WANTED_VBUFFER_WIDE - 200; } } else { debug << "Ok\n"; vbuffer_wide = WANTED_VBUFFER_WIDE - 100; } } else { debug << "Ok\n"; vbuffer_wide = WANTED_VBUFFER_WIDE; } LOGI("eighth"); //------------------------------------------------------------------ // Chargement des fontes init //------------------------------------------------------------------ if (!fnt_menu.load("data/menu.lft", mem_flag)) { Bug("Cannot open the file data/menu.lft"); ReleaseAll(); return false; } LOGI("nineth"); if (!fnt_menus.load("data/menus.lft", mem_flag)) { Bug("Cannot open the file data/menus.lft"); ReleaseAll(); return false; } if (!fnt_cool.load("data/cool.lft", mem_flag)) { Bug("Cannot open the file data/cool.lft"); ReleaseAll(); return false; } if (!fnt_rpg.load("data/rpg.lft", mem_flag)) { Bug("Cannot open the file data/rpg.lft"); ReleaseAll(); return false; } LOGI("erz"); //------------------------------------------------------------------ // Chargement de l'interface //------------------------------------------------------------------ if (!pbk_inter.loadGFX("data/inter.gfx", DDSURF_BEST)) { debug << "Cannot load interface.\n"; return false; } else { debug << "Successfully loaded interface.\n"; } if (!mbk_inter.open("data/inter.mbk", false)) { debug << "Cannot load interface musics.\n"; return false; } if (!mbk_interl.open("data/interl.mbk", true)) { debug << "Cannot load interface musics (p2).\n"; return false; } LOGI("END"); //------------------------------------------------------------------ // Mémoire video restante //------------------------------------------------------------------ //------------------------------------------------------------------ // Mise en place du TIMER pour obtenir les FPS //------------------------------------------------------------------ SetTimer(WinHandle, 1, 1000, NULL); return true; // C'est fini! } // Init ---------------------------
BOOL DDCreateScreen(int flags) { DDSCAPS ddscaps; DDCAPS ddcaps, ddcaps2; DDSURFACEDESC ddsd; HRESULT ddresult; memset(&ddcaps, 0, sizeof(ddcaps)); memset(&ddcaps2, 0, sizeof(ddcaps2)); ddcaps.dwSize = sizeof(ddcaps); ddcaps2.dwSize = sizeof(ddcaps); ddresult = IDirectDraw_GetCaps(_lpDD, &ddcaps, &ddcaps2); if (!CheckDDResult(ddresult, "DDCreateScreen::GetCaps")) return FALSE; logentry("DirectDraw HW Caps: %x\nDirectDraw HEL Caps: %x\n",ddcaps.dwCaps,ddcaps2.dwCaps); if (ddcaps.dwCaps & DDCAPS_BANKSWITCHED) { logentry("DirectDraw: Hardware is bank-switched. Using SRAM rendering.\n"); _DDSysMemSurfacing = TRUE; } else { logentry("DirectDraw: Hardware is not bank-switched. Using VRAM rendering.\n"); _DDSysMemSurfacing = FALSE; } // Determine GFX caps. if (ddcaps.dwCaps & DDCAPS_COLORKEYHWASSIST) ddDriverCaps.hwcolorkey = 1; else ddDriverCaps.hwcolorkey = 0; if (ddcaps.dwCaps & DDCAPS_BLTSTRETCH) ddDriverCaps.hwbltstretch = 1; else ddDriverCaps.hwbltstretch = 0; memset(&ddsd, 0, sizeof(ddsd)); ddsd.dwSize = sizeof(ddsd); if (_DDFullScreen && GRMODEINFO(paged)) { // We should use page flipping ddsd.dwFlags = DDSD_CAPS | DDSD_BACKBUFFERCOUNT; ddsd.dwBackBufferCount = 1; ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE | DDSCAPS_FLIP | DDSCAPS_COMPLEX; ddresult = IDirectDraw_CreateSurface(_lpDD, &ddsd, &_lpDDSPrimary, NULL); if (!CheckDDResult(ddresult, "DDCreateScreen::CreateSurface -fullscreen")) return FALSE; ddscaps.dwCaps = DDSCAPS_BACKBUFFER; ddresult = IDirectDrawSurface_GetAttachedSurface(_lpDDSPrimary, &ddscaps, &_lpDDSBack); if (!CheckDDResult(ddresult, "DDCreateScreen::GetAttachedSurface")) return FALSE; } else { // We just create a primary and offscreen buffer if (GRMODEINFO(emul) && !_lpDDSPrimary) { // make sure we don't reinitialize the screen if we already made it // beforehand for windowed version ddsd.dwFlags = DDSD_CAPS; ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE; ddresult = IDirectDraw_CreateSurface(_lpDD, &ddsd, &_lpDDSPrimary, NULL); if (!CheckDDResult(ddresult, "DDCreateScreen::CreateSurface -windowed")) return FALSE; } else if (!GRMODEINFO(emul)) { // If we aren't emulating ddsd.dwFlags = DDSD_CAPS; ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE; ddresult = IDirectDraw_CreateSurface(_lpDD, &ddsd, &_lpDDSPrimary, NULL); if (!CheckDDResult(ddresult, "DDCreateScreen::CreateSurface -windowed")) return FALSE; } if (GRMODEINFO(emul)) { _lpDDSBack = DDCreateSurface(_DDModeList[W95DisplayMode].rw, _DDModeList[W95DisplayMode].rh, 1); if (!_lpDDSBack) { mprintf((0,"Call to create DDSBackBuffer failed.")); return FALSE; } } else _lpDDSBack = NULL; } // Create 8-bit palette { ubyte pal[768]; memset(pal, 0, 768); memset(&ddsd, 0, sizeof(ddsd)); ddsd.dwSize = sizeof(ddsd); IDirectDrawSurface_GetSurfaceDesc(_lpDDSPrimary, &ddsd); logentry("Primary surface pixel format: %x, %d\n", ddsd.ddpfPixelFormat.dwFlags, ddsd.ddpfPixelFormat.dwRGBBitCount); _lpDDPalette = DDCreatePalette(pal); Assert(_lpDDPalette != NULL); DDSetPalette(_lpDDPalette); } return TRUE; }
/* * FadeToSurface: * Fades into a surface from black */ void FadeToSurface(LPDIRECTDRAWSURFACE lpDDS) { int c; // counter variable long i; // incrementing variable WORD *tmp, *ref, *prm; WORD *fasttmp, *fastref; // temporary and destination surface mem pointers RECT SrcRect, DesRect; // Source and destination rectangles int tpitch, rpitch, ppitch; // temporary and destination surface pitch WORD *shade; // Set the source and destination rectangles to the size of the screen SetRect(&SrcRect, 0, 0, 640, 480); SetRect(&DesRect, 0, 0, 640, 480); // Create the surfaces lpDDSTmp = DDCreateSurface(640, 480, DDSCAPS_SYSTEMMEMORY); // the temporary surface lpDDSRef = DDCreateSurface(640, 480, DDSCAPS_SYSTEMMEMORY); // the temporary surface lpDDSRef->Blt(&DesRect, lpDDS, &SrcRect, DDBLT_WAIT, NULL); // blit the desired surface into our destination surface // Lock our surfaces temporary, and destination tmp = DDLockSurface(lpDDSTmp, &tpitch); prm = DDLockSurface(lpDDSPrimary, &ppitch); ref = DDLockSurface(lpDDSRef, &rpitch); // This can be changed, but it worx out nice to do 10 iterations for (c = 1; c <= 30; c++) { // get pointer indexed to the start of the current shade level shade = PixelShade[c]; // "reset" our *fast* surface pointers fasttmp = tmp; fastref = ref; // for every pixel on the screen (640*480=307200) for (i = 0; i < 307200; i++, fasttmp++, fastref++) { // new pixel please..... *fasttmp = shade[*fastref]; } // copy the temp surface to the primary surface // method depends on windowed/full screen #ifdef WINDOWED WORD *fastprm = prm + (g_rcWindow.top * ppitch) + g_rcWindow.left; fasttmp = tmp; for (i = 0; i < 480; i++, fastprm += ppitch, fasttmp += 640) { g_MemCpySys2Vid(fastprm, fasttmp, 1280); // 1280 = 614400 (see below) / 480 } #else // (640*480) = 307200 (words) * 2 = 614400 (bytes) g_MemCpySys2Vid(prm, tmp, 614400); #endif } // unlock the temporary surface and destination surface DDUnlockSurface(lpDDSTmp); DDUnlockSurface(lpDDSPrimary); DDUnlockSurface(lpDDSRef); // blit the actual destination surface to the primary surface so we're sure // the screen is where it should be #ifdef WINDOWED lpDDSPrimary->Blt(&g_rcWindow, lpDDS, &SrcRect, DDBLT_WAIT, NULL); #else lpDDSPrimary->Blt(&DesRect, lpDDS, &SrcRect, DDBLT_WAIT, NULL); #endif // release the temporary and destination surfaces lpDDSTmp->Release(); lpDDSTmp = NULL; lpDDSRef->Release(); lpDDSRef = NULL; }
/* * FadeToBlack: * Fades a screen to black */ void FadeToBlack(void) { RECT SrcRect, DesRect; // Source and Destination Rectangles WORD *tmp; // temporary surface memory pointer WORD *ref; WORD *prm; WORD *fastref, *fasttmp; int c, tpitch, rpitch, ppitch; // incrementing variable, temporary surface pitch long i; // another incrementing variable WORD *shade; // Set source and destination rectangles to size of screen SetRect(&SrcRect, 0, 0, 640, 480); SetRect(&DesRect, 0, 0, 640, 480); // Create our temporary surface lpDDSTmp = DDCreateSurface(640, 480, DDSCAPS_SYSTEMMEMORY); lpDDSRef = DDCreateSurface(640, 480, DDSCAPS_SYSTEMMEMORY); // Blit our primary surface into our temporary SYSTEM MEMORY surface #ifdef WINDOWED lpDDSRef->Blt(&DesRect, lpDDSPrimary, &g_rcWindow, DDBLT_WAIT, NULL); #else lpDDSRef->Blt(&DesRect, lpDDSPrimary, &SrcRect, DDBLT_WAIT, NULL); #endif // Lock our temporary surface tmp = DDLockSurface(lpDDSTmp, &tpitch); ref = DDLockSurface(lpDDSRef, &rpitch); prm = DDLockSurface(lpDDSPrimary, &ppitch); for (c = 30; c >= 1; c--) { // get a pointer indexed to the start of the current shade level shade = PixelShade[c]; // "reset" our *fast* surface pointers fastref = ref; fasttmp = tmp; // for every pixel on the screen (640*480=307200) for (i = 0; i < 307200; i++, fasttmp++, fastref++) { // new pixel please.... *fasttmp = shade[*fastref]; } // copy the temp surface to the primary surface // method depends on windowed/full screen #ifdef WINDOWED WORD *fastprm = prm + (g_rcWindow.top * ppitch) + g_rcWindow.left; fasttmp = tmp; for (i = 0; i < 480; i++, fastprm += ppitch, fasttmp += 640) { g_MemCpySys2Vid(fastprm, fasttmp, 1280); // 1280 = 614400 (see below) / 480 } #else // (640*480) = 307200 (words) * 2 = 614400 (bytes) g_MemCpySys2Vid(prm, tmp, 614400); #endif } // unlock our temporary surface DDUnlockSurface(lpDDSTmp); DDUnlockSurface(lpDDSRef); DDUnlockSurface(lpDDSPrimary); // just to make sure the screen is black when this routine is over, fill it with 0 DDFillSurface(lpDDSPrimary, 0); // release our temporary surface lpDDSTmp->Release(); lpDDSTmp = NULL; lpDDSRef->Release(); lpDDSRef = NULL; }
/* * AlphaTransition: * Does an alpha transition from Src -> Des */ void AlphaTransition(LPDIRECTDRAWSURFACE Src, LPDIRECTDRAWSURFACE Des) { long i; // index into surfaces int alpha; // Holds current alpha value int dpitch, spitch, tpitch, ppitch; // surface pitch for destination, source, temp surfaces WORD *AlphaPTR; // pointer to the current AlphaMap level (Source) WORD *InvAlphaPTR; // the inverted pointer to the current AlphaMap level (Destination) WORD *src, *des, *tmp, *prm; WORD *fastsrc, *fastdes, *fasttmp; // Surface memory pointer for source, destination, and temporary surfaces RECT SrcRect, DesRect; // Source and destination rectangles // Set source and destination rectangles to the screen size SetRect(&SrcRect, 0, 0, 640, 480); SetRect(&DesRect, 0, 0, 640, 480); // Create the three surface we are going to use lpDDSTmp = DDCreateSurface(640, 480, DDSCAPS_SYSTEMMEMORY); // The temporary surface lpDDSSrc = DDCreateSurface(640, 480, DDSCAPS_SYSTEMMEMORY); // The source surface lpDDSDes = DDCreateSurface(640, 480, DDSCAPS_SYSTEMMEMORY); // The destination surface // Blit the transition surfaces into out newly created source/destination surfaces lpDDSSrc->Blt(&DesRect, Src, &SrcRect, DDBLT_WAIT, NULL); // Blit Src->lpDDSSrc lpDDSDes->Blt(&DesRect, Des, &SrcRect, DDBLT_WAIT, NULL); // Blit Des->lpDDSDes // lock all three surfaces temporary, source, and destination des = DDLockSurface(lpDDSDes, &dpitch); src = DDLockSurface(lpDDSSrc, &spitch); tmp = DDLockSurface(lpDDSTmp, &tpitch); prm = DDLockSurface(lpDDSPrimary, &ppitch); // for each alpha level for (alpha = 31; alpha >= 0; alpha--) { // set AlphaMap pointers to appropriate levels AlphaPTR = PixelShade[alpha]; InvAlphaPTR = PixelShade[31 - alpha]; // "reset" the *fast* pointers to the locked surfaces fastsrc = src; fastdes = des; fasttmp = tmp; // loop through every pixel for (i = 0; i < 307200; i++, fasttmp++, fastsrc++, fastdes++) { // Set the new pixel value in temporary surface *fasttmp = AlphaPTR[*fastsrc] + InvAlphaPTR[*fastdes]; } // copy the temp surface to the primary surface // method depends on windowed/full screen #ifdef WINDOWED WORD *fastprm = prm + (g_rcWindow.top * ppitch) + g_rcWindow.left; fasttmp = tmp; for (i = 0; i < 480; i++, fastprm += ppitch, fasttmp += 640) { g_MemCpySys2Vid(fastprm, fasttmp, 1280); // 1280 = 614400 (see below) / 480 } #else // (640*480) = 307200 (words) * 2 = 614400 (bytes) g_MemCpySys2Vid(prm, tmp, 614400); #endif } // Unlock our temporary, source, and destination surfaces DDUnlockSurface(lpDDSPrimary); DDUnlockSurface(lpDDSTmp); DDUnlockSurface(lpDDSDes); DDUnlockSurface(lpDDSSrc); // Release or temporary, source, and destination surfaces lpDDSTmp->Release(); lpDDSTmp = NULL; lpDDSSrc->Release(); lpDDSSrc = NULL; lpDDSDes->Release(); lpDDSDes = NULL; }