(skinning) Bitmap wird nicht gezeichnet--
-
Hi! auf basis eines Tutorials über skins habe ich folgenden code fabriziert:
void EntferneCaption(HWND hWnd); //thx to Vander Nunes HRGN TrueRegion(HBITMAP bild, BYTE R,BYTE G,BYTE B); //thx to Vander Nunes BYTE* Get24BitPixels(HBITMAP bild,WORD *breite,WORD *hoehe); //thx to Vander Nunes LRESULT CALLBACK WndProc(HWND hwnd,UINT message,WPARAM wParam,LPARAM lParam) { //------------------------------Deklarationen------------------------------ HRGN WindowRegion; HDC skinDC; HBITMAP skin; //------------------------------Nachrichtenauswertung---------------------- switch(message) { case WM_DESTROY: DeleteObject(WindowRegion); SelectObject(skinDC,skinHOLD); DeleteObject(skinDC); DeleteObject(skinHOLD); PostQuitMessage(0); case WM_CREATE: skin=(HBITMAP) LoadImage(mainHI,"YASAskin.bmp",IMAGE_BITMAP, NULL, NULL, LR_LOADFROMFILE /*LR_CREATEDIBSECTION*/); WindowRegion=TrueRegion(skin,255,255,255); SetWindowRgn(hwnd,WindowRegion,true); EntferneCaption(hwnd); case WM_PAINT: PAINTSTRUCT ps; BeginPaint(hwnd,&ps); skinDC=CreateCompatibleDC(0); SelectObject(skinDC,skin); BitBlt(ps.hdc,0,-20,500,800,skinDC,0,0,SRCCOPY); EndPaint(hwnd,&ps); case WM_LBUTTONDOWN: SendMessage(hwnd,WM_NCLBUTTONDOWN,HTCAPTION,NULL); } return DefWindowProc(hwnd,message,wParam,lParam); } //-------------------------------------------------------------------------- void EntferneCaption(HWND hWnd) { DWORD style; style=GetWindowLong(hWnd,GWL_STYLE); style&=~(WS_CAPTION|WS_SIZEBOX); SetWindowLong(hWnd,GWL_STYLE,style); InvalidateRect(hWnd, NULL, TRUE); SetWindowPos(hWnd, NULL, 0,0,500,800, SWP_NOMOVE|SWP_NOZORDER); // SendMessage(hWnd,WM_PAINT,NULL,NULL); return; } //-------------------------------------------------------------------------- HRGN TrueRegion(HBITMAP bild, BYTE R,BYTE G,BYTE B) { WORD breite,hoehe; HRGN TrueRGN,TmpRGN; BYTE* Pixel=Get24BitPixels(bild,&breite,&hoehe); if(!Pixel) return NULL; TrueRGN=CreateRectRgn(0,0,breite,hoehe); if(!TrueRGN) { delete Pixel; return NULL; } DWORD p=0; for(WORD y=0;y<hoehe;y++) { for(WORD x=0;x<breite;x++) { BYTE rot=Pixel[p+2]; BYTE gruen=Pixel[p+1]; BYTE blau=Pixel[p+0]; if(rot==R && gruen==G && blau==B) { // remove transparent color from region TmpRGN=CreateRectRgn(x,y,x+1,y+1); CombineRgn(TrueRGN,TrueRGN,TmpRGN,RGN_XOR); DeleteObject(TmpRGN); } p+=3; //next pixel } } delete Pixel; return TrueRGN; } //-------------------------------------------------------------------------- BYTE* Get24BitPixels(HBITMAP bild,WORD *breite,WORD *hoehe) { // a bitmap object just to get bitmap width and height BITMAP bmp; // pointer to original bitmap info LPBITMAPINFO pbmiInfo; // bitmap info will hold the new 24bit bitmap info BITMAPINFO bmiInfo; WORD BREITE,HOEHE; GetObject(bild,sizeof(bmp),&bmp); pbmiInfo=(LPBITMAPINFO) &bmp; BREITE=(WORD)pbmiInfo->bmiHeader.biWidth; BREITE-=(BREITE%4); HOEHE=(WORD)pbmiInfo->bmiHeader.biHeight; *breite=BREITE; *hoehe=HOEHE; BYTE* pixel=new BYTE[HOEHE*BREITE*3]; if(!pixel) return NULL; HDC dC=GetWindowDC(NULL); bmiInfo.bmiHeader.biSize=sizeof(BITMAPINFOHEADER); bmiInfo.bmiHeader.biWidth=BREITE; bmiInfo.bmiHeader.biHeight= -HOEHE; bmiInfo.bmiHeader.biPlanes=1; bmiInfo.bmiHeader.biBitCount=24; bmiInfo.bmiHeader.biCompression=BI_RGB; bmiInfo.bmiHeader.biSizeImage=HOEHE*BREITE*3; bmiInfo.bmiHeader.biYPelsPerMeter=0; bmiInfo.bmiHeader.biYPelsPerMeter=0; bmiInfo.bmiHeader.biClrUsed=0; bmiInfo.bmiHeader.biClrImportant=0; // get pixels from the original bitmap converted to 24bits int iRes = GetDIBits(dC,bild,0,HOEHE,(LPVOID)pixel,&bmiInfo,DIB_RGB_COLORS); ReleaseDC(NULL,dC); if(!iRes) { delete pixel; return NULL; }; return pixel; } //--------------------------------------------------------------------------
Die Region wird auch prefekt erstellt und dem Fenster zugewiesen aber das eigentliche Bild wird nicht gezeichnet..
ich sehe nur mein fenster mit der vorgegebenen Hintergrundfarbe in der form, wie ich sie haben will..ohne skin.
weiss einer warum?
-
bei "switch case" fehlen die "break"s !
-
hmm..die breaks, ich weiss nich ob's daran liegt..ich hatte den code auch schonmal mit breaks geschrieben, ist denn ansonsten alles in ordnung?
-
Naja, in WM_PAINT legst du z.B. jedesmal einen DC an, den du aber nur einmal bei WM_DESTROY wieder löscht (und dazu auch noch falsch: DeleteObject statt DeleteDC).
Pack folgendes doch gleich direkt in WM_CREATE:skinDC=CreateCompatibleDC(0); SelectObject(skinDC,skin);
Und was ist dein skinHOLD, was du in WM_DESTROY verwendest
Ich weiß ja nicht welches Tutorial verwendet hast, aber du kannst dir vielleicht auch noch dieses hier anschauen
[ Dieser Beitrag wurde am 23.04.2003 um 22:04 Uhr von flenders editiert. ]
-
Hi flenders! Ja was meinst du woher ich dieses Tut habe
Danke erstmal für deine Tipps..hab leider im mom wenig zeit zum codenmus beim umzug helfen.skinHOLDist ein Überbleibsel von meinen Code schnipseleien..also nicht weiter beachten
also bis den ich werds weiterhin testen
-
JAA! DANKE FLENDERS!
Es lag an dem immer wieder erstellten DC..THX!
-
Wenn du willst, dass die Region schneller erstellt wird, dann schau mal auf meine Homepage (siehe Signatur). Da gibts ne Unit (mehrere Funktionen) namens "Regions", und darin eine Funktion BitmapToRegion(), die um einiges schneller arbeitet, als deins da. Und wenn du's ganz schnell haben willst, dann hol dir (unter Downloads) den RegionBuilder, mit dem Du deine Region speichern und dann in deinem Programm als Resource einbinden kannst (wie das geht, steht da in der Hilfe).
-
Ja danke @webFritzi..ist der region builder der gleiche wie der von Vander Nunes? (link den flanders gepostet hat) ?
-
Original erstellt von <n0Ob>:
ist der region builder der gleiche wie der von Vander Nunes? (link den flanders gepostet hat) ?Ne. Wusste garnicht, dass die auch einen haben. Aber das ist ein Konsolenprogramm und meins ist mit GUI. Außerdem haben die da sicher ihre Funktion reingepackt, die erstens langsamer als meine läuft und zweitens mehr Speicher verbraucht (meine gebauten Regions bestehen aus weniger Rechtecken).
-
aber deine Regions sind auch GENAU? ich werd mal vorbeisurfen und mir angucken wie du das machst
-
Original erstellt von <n0Ob>:
aber deine Regions sind auch GENAU?So GENAU wie die von Vander auch.
ich werd mal vorbeisurfen und mir angucken wie du das machst
Das kann ich dir auch so sagen. Ich erstelle zuerst eine schwarz-weiß-Maske des Bitmaps (wozu RGB?) und scanne diese dann. Das Scannen unterscheidet sich zu Vanders Methode darin, dass ich das ganze in eine RGNDATA schreibe und am Ende erst die Region erstelle, wohingegen er seine Region immer updatet, was um einiges länger dauert.