GetPixel nur 165 mal ?

AckiB

Mitglied
Hi,
ich versuche die Farbe eines pixels auf dem Desktop zu ermitteln...
Das funktioniert auch mit der untenstehenden Funktion, aber nur 165 mal !!
Danach bekomme ich nur noch Weiß als Farbe (r=FF g=FF b=FF)...
Kann mir bitte jemand erklären was da falsch ist ?
danke, Acki

Code:
void getPixel() {
  static HWND hwnd = GetDesktopWindow();
  HDC ddc = GetDC(hwnd);
  HDC mdc = CreateCompatibleDC(ddc);
  RECT sz;
  GetWindowRect(hwnd, &sz);
  HBITMAP hbmp = CreateCompatibleBitmap(ddc, sz.right, sz.bottom);
  SelectObject(mdc, hbmp);
  BitBlt(mdc, 0, 0, sz.right, sz.bottom, ddc, 0, 0, SRCCOPY);
  COLORREF cref;
  cref = GetPixel(mdc, 512, 384);
  
  // funktioniert nur 165 mal, dann kommt nur noch "FF FF FF"
  static int x = 0;
  printf("%d %02X %02X %02X\n", ++x, GetRValue(cref), GetGValue(cref), GetBValue(cref));
  
  ReleaseDC(hwnd, ddc);
  ReleaseDC(hwnd, mdc);
  DeleteObject(hbmp);
}
 
ok, ich habe die Funktion etwas geändert und jetzt funktioniert es anscheinend...
allerdings bin ich mir nicht sicher, ob das nicht zu "mem leaks" führt, weil ich die Handles (device contexts) nicht mehr frei gebe (die dafür aber jetzt statisch sind)?
Code:
void getPixel() {
  static HWND hwnd = GetDesktopWindow();
  static HDC ddc = GetDC(hwnd);
  static HDC mdc = CreateCompatibleDC(ddc);
  RECT sz;
  GetWindowRect(hwnd, &sz);
  HBITMAP hbmp = CreateCompatibleBitmap(ddc, sz.right, sz.bottom);
  SelectObject(mdc, hbmp);
  BitBlt(mdc, 0, 0, sz.right, sz.bottom, ddc, 0, 0, SRCCOPY);
  COLORREF cref;
  cref = GetPixel(mdc, 512, 384);

  // funktioniert nur 165 mal, dann kommt nur noch "FF FF FF"
  static int x = 0;
  printf("%d %02X %02X %02X\n", ++x, GetRValue(cref), GetGValue(cref), GetBValue(cref));

//  ReleaseDC(hwnd, ddc);
//  ReleaseDC(hwnd, mdc);
  DeleteObject(hbmp);
}
 
Dadurch, dass die static sind,werden die jetzt nur einmal zugewiesen, du behältst aber trotzdem noch zwei HDCs offen. Ist auch nicht ganz sauber.

Du kannst ja zu Beginn deiner GetPixel-Orgie die HDCs einmal zuweisen, danach aber wieder freigeben (Oder zu Beginn und Ende des Programmes, da wird es aber schon wieder heikel). Alle GDI-Handles sollte man nur kurz benutzen und dann wieder freigeben, da es nur eine begrenzte Anzahl davon gibt.
 
Dadurch, dass die static sind,werden die jetzt nur einmal zugewiesen, du behältst aber trotzdem noch zwei HDCs offen. Ist auch nicht ganz sauber.
Das dachte ich mir, aber wenigstens funktionierts jetzt... :lol:

Alle GDI-Handles sollte man nur kurz benutzen und dann wieder freigeben, da es nur eine begrenzte Anzahl davon gibt.
aha, ich denke, dass Das das Problem ist, weshalb nach dem 165sten Aufruf nur noch Weiß ermittelt wird...
Das würde dann aber bedeuten, dass ich im ersten Code etwas nicht richtig frei gebe und so irgendwann das Maximum erreicht wird, oder?

Ich werde auch mal einen Blick auf den Beitrag werfen (danke MCoder ;) )...
Vielleicht bekome ich dann ja einen Geistesblitz... :lol:
 
Beim ersten hast du einen kleinen Fehler: Je nachdem, woher ein HDC kommt, musst du ReleaseDC oder DeleteDC verwenden.

Bei CreateCompatibleDC ist es DeleteDC, bei GetDC ist es ReleaseDC.

Die HBITMAP löschst du schön, aber man muss eigentlich auch die in einen HDC selektieren Objekte wieder rausnehmen. Da das HDC aber sowieso vorher schon zerstört wird, müsste es in dem Fall sogar klappen. Sauberer ist es aber so:

Code:
HBITMAP hbmOld = SelectObject( mdc, hbmp );

.. BitBlt ..

SelectObject( mdc, hbmOld );
 
Zurück