NO

Author Topic: Array of GpImage objects in GDI+  (Read 2052 times)

Offline iwrbc

  • Member
  • *
  • Posts: 16
Array of GpImage objects in GDI+
« on: September 22, 2020, 11:17:01 PM »
Hi,
I am pretty new to C. One of my first projects is to convert an existing program written in another language to Pelles C. I am now trying to create an array of GpImage (so GDI+) objects and display the one which is selected by the user. At design time I do not know how many pictures the user will select and which one. What I managed so far: initialise GDI+, load the jpg-file using GdipLoadImageFromFile and display the file using GdipDrawImageRect in a WM_PAINT event of a subclassed static control. FYI, the code looks like this. I got a global variable:

Code: [Select]
GpImage  *pP;
I load a file:

Code: [Select]
  GpStatus st;

  st = GdipLoadImageFromFile(Pict[1].FileName, (GpImage**)&pP);

and draw it:

Code: [Select]
LRESULT BigStaticProc(HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam) {

  RECT RC;

  switch (Msg) {
    case WM_PAINT:
      GetClientRect(hStaticBig, &RC);
      GdipDrawImageRect(pGraphObjectBigStat, pP, 0, 0, RC.right, RC.bottom);
  }

  return DefSubclassProc(hWnd, Msg, wParam, lParam);

};

This works.

Now when I try to implement the global dynamic array of GpImage objects, I change to:

Code: [Select]
GpImage             *pPict;
Then I allocate memory for an array:

Code: [Select]
pPict=(GpImage*)calloc((Plant.NumPictures), sizeof(GpImage*));
(This approach works for me for integer and structure arrays.)
In this line sizeof(GpImage*) returns 8 which is correct.

Then when I try to load the array I use this code:

Code: [Select]
  long i;
  GpStatus st;

  pPict=(GpImage*)calloc((Plant.NumPictures), sizeof(GpImage*));

  for (i = 0; i < Plant.NumPictures; i = i +1) {
    st = GdipLoadImageFromFile(Pict[i].FileName, (GpImage**)&pPict[i]);
    if(st==Ok){
      MessageBox(NULL, L"was OK", L"Message", MB_OK);}
    else {
      MessageBox(NULL, L"was NOT OK", L"Message", MB_OK);
    }
  }

And then I get the error message at the line with 'GdipLoadImageFromFile': "error #2153: Unknown size for type 'GpImage (aka (incomplete) struct tagGpImage)'."

First of all I do not understand the message because a few lines up the compiler DOES know the size of GpImage. Secondly, I do not know how to get this code working. Thirdly, how to change the code in the WM_PAINT event?

I guess it is something stupid but I have been trying for days now so I hope someone here is willing and able to help me.
Any help is appreciated.

Offline frankie

  • Global Moderator
  • Member
  • *****
  • Posts: 2113
Re: Array of GpImage objects in GDI+
« Reply #1 on: September 23, 2020, 02:03:18 PM »
The problem is due to the abuse of unnecessary casting, that in the specific case trigger the error.
The GpImage is defined as an incomplete structure, therefore its size is unknown, and known only by its address in memory, the pointer to the structure.
So you have to create a pointer to an array of pointers:
Code: [Select]
GpImage **pPict;
Then access each element (a pointer to a structure) as follows:
Code: [Select]
void tst(void)
{
long i;
GpStatus st;

pPict = calloc((Plant.NumPictures), sizeof(GpImage *));

for (i = 0; i < Plant.NumPictures; i = i + 1)
{
st = GdipLoadImageFromFile(Pict[i].FileName, &pPict[i]);
if (st == Ok)
{
MessageBox(NULL, L"was OK", L"Message", MB_OK);
}
else
{
MessageBox(NULL, L"was NOT OK", L"Message", MB_OK);
}
}
}

Note the line
Code: [Select]
st = GdipLoadImageFromFile(Pict[i].FileName, &pPict[i]);where the function GdipLoadImageFromFile assign to a pointer to structure the freshly allocated picture. Here we pass the address of the i-eth element of the array &pPict.

In your code:
Code: [Select]
GpImage **pPict;

st = GdipLoadImageFromFile(Pict[i].FileName, (GpImage**)&pPict[i]);
You declared a pointer to the incomplete structure GpImage, then using the index operator pPict[] try to extract from the pointer the structure itself dereferencing the element. Then the error.
« Last Edit: September 23, 2020, 02:06:22 PM by frankie »
"It is better to be hated for what you are than to be loved for what you are not." - Andre Gide

Offline iwrbc

  • Member
  • *
  • Posts: 16
Re: Array of GpImage objects in GDI+
« Reply #2 on: September 23, 2020, 03:53:43 PM »
Thank you for your explanation. It now works as I want it. :)