Sign in to follow this  
Vincent Torri

writing image (as RGBA data) in a surface

Recommended Posts

hello, I'm trying to port the engine of a canvas library [1] from Linux to Windows. I precise that I'm not at all an expert of the Windows API's (I'm a Linux coder). What I want to do is the following: I have created a window, and I have a image as a pointer to a uint32_t data (4 bytes, unsigned), of size w, h. I want to put that image to the coordinates (x,y) on the window. As speed is important, I would like a blit of my data as fast as possible. I've already looked a bit at what exists in Windows APi's, and I think that DirectDraw is better than GDI. So, I've created a surface and now, I would like to retrieve a pointer to the data of my surface and to do a good old linux memcpy from my data to that pointer. Here are my quesitons: 1) Is it possible to get that pointer ? 2) Is it the best solution ? ('best' being : no other solution is faster) 3) If not, which solution(s) do you advice ? 4) Can overlays be helpful here ? thank you very much [1] Evas : http://www.enlightenment.org

Share this post


Link to post
Share on other sites
in fact, I think that I have found out how to do that. I can just create another surface from my buffer :

http://msdn.microsoft.com/archive/d...ddover_6bzr.asp

and then, I bilt it with BltFast on my destination surface.

I've written a code to test the creation of such surface:

#include <stdlib.h>
#include <stdio.h>

#include <windows.h>
#include <ddraw.h>


LRESULT CALLBACK MainWndProc(HWND, UINT, WPARAM, LPARAM);

int APIENTRY
WinMain (HINSTANCE hinstance,
HINSTANCE hPrevInstance,
LPSTR lpCmdLine,
int nCmdShow)
{
HWND window;
WNDCLASS wc;
MSG msg;
int width;
int height;
int running;

/* Create the main window */
width = 320;
height = 200;

wc.style = 0;
wc.lpfnWndProc = MainWndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hinstance;
wc.hIcon = LoadIcon (NULL, IDI_APPLICATION);
wc.hCursor = LoadCursor (NULL, IDC_ARROW);
wc.hbrBackground = (HBRUSH)(1 + COLOR_BTNFACE);
wc.lpszMenuName = NULL;
wc.lpszClassName = "MaWinClass";

if(!RegisterClass(&wc)) return -1;

window = CreateWindow("MaWinClass", "Titre",
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, CW_USEDEFAULT,
width, height,
NULL, NULL, hinstance, NULL);
if (!window) return -1;

ShowWindow(window, nCmdShow);
UpdateWindow(window);

{
LPDIRECTDRAW lpDD;
HRESULT res;
DDSURFACEDESC ddsd;
LPDIRECTDRAWSURFACE lpDDS;
int *surf, *tmp;
int w, h, depth, pitch, r, g;

res = DirectDrawCreate (NULL, &lpDD, NULL);
if (FAILED (DD_OK)) {
printf ("DirectDrawCreate fails\n");
return EXIT_FAILURE;
}

res = lpDD->SetCooperativeLevel (window, DDSCL_NORMAL);
if (FAILED (res)) {
printf ("SetCooperativeLevel fails\n");
lpDD->Release ();
return EXIT_FAILURE;
}

w = 64;
h = 64;
depth = 3;
pitch = depth * w;
surf = (int *)malloc (sizeof (int) * depth * w * h);
if (!surf) {
lpDD->Release ();
return EXIT_FAILURE;
}

ZeroMemory (surf, depth * w * h * sizeof (int));

tmp = surf;
for (r = 0; r < w; r++) {
for (g = 0; g < h; g++, tmp += 3) {
tmp[0] = (r * 2) % 256;
tmp[1] = g % 256;
tmp[2] = (w - 1 - g) * 4;
}
}

ZeroMemory (&ddsd, sizeof (DDSURFACEDESC));
ddsd.dwSize = sizeof(ddsd);
ddsd.dwFlags = DDSD_WIDTH | DDSD_HEIGHT | DDSD_LPSURFACE |
DDSD_PITCH | DDSD_PIXELFORMAT | DDSD_CAPS;
ddsd.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN |
DDSCAPS_SYSTEMMEMORY;
ddsd.dwWidth = w;
ddsd.dwHeight= h;
ddsd.lPitch = pitch;
ddsd.lpSurface = surf;

// Set up the pixel format for 24-bit RGB (8-8-8).
ZeroMemory (&ddsd.ddpfPixelFormat, sizeof (DDPIXELFORMAT));
ddsd.ddpfPixelFormat.dwSize = sizeof(DDPIXELFORMAT);
ddsd.ddpfPixelFormat.dwFlags= DDPF_RGB;
ddsd.ddpfPixelFormat.dwRGBBitCount = (DWORD)depth * 8;
ddsd.ddpfPixelFormat.dwRBitMask = 0x00FF0000;
ddsd.ddpfPixelFormat.dwGBitMask = 0x0000FF00;
ddsd.ddpfPixelFormat.dwBBitMask = 0x000000FF;

// Create the surface
res = lpDD->CreateSurface(&ddsd, &lpDDS, NULL);
if (FAILED (res))
{
printf ("Damned\n");
lpDD->Release ();
free (surf);
return EXIT_SUCCESS;
}
}


/* the main loop */
running = 1;
while (running) {
while (PeekMessage (&msg, window, 0, 0, PM_NOREMOVE)) {
int res;

res = GetMessage (&msg, NULL, 0, 0);
TranslateMessage (&msg);
DispatchMessage (&msg);
if (res == 0)
running = 0;
}
}

return 0;
}

LRESULT CALLBACK
MainWndProc(HWND hwnd,
UINT uMsg,
WPARAM wParam,
LPARAM lParam)
{
switch (uMsg)
{
case WM_CREATE:

return 0;

case WM_DESTROY:
PostQuitMessage(0);
return 0;

default:
return DefWindowProc(hwnd, uMsg, wParam, lParam);
}
}


but the creation of the surface returns the error code : DDERR_INVALIDPARAMS

Does someone see where my error(s) is(are) ?

thank you

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this