[C++/WinApi] Bitmap Ladebalken

posi90

Erfahrenes Mitglied
Hallo,

Ich programmiere gerade an einem File-Updater und will den aktuellen Download-Status via Ladebalken anzeigen. Dieser Ladebalken sollte folgendermaßen aussehn:

Voller Balken:
loadx.png


Balken mitten drinnen:
load2x.png


Meine Grundidee: Man könnte doch einen Layer machen in dem der volle Balken vorhanden ist. Im Layer wird dann immer eine "Maske" nach Rechts gezogen und somit der Ladevorgang gezeigt.

Hat das schon einmal jemand gemacht? Wie gehe ich das am besten an?

mfg. Poseidon
 
Zuletzt bearbeitet:
Hey,

ich habe schon mal einen Ladeblaken selbst geschrieben. Allerdings war es kein wirklich guter, aber er machte seine arbeit^^. Es war eigentlich nur ein einfaches Fenster was pixel für pixel mit farbe ausgefüllt wurde. Hatte aber den nachteil dass ich einen Thread machen musste der des Fenster immer wieder neu zeichnete, da die Funktion "neu zeichenen" in einer schleife nicht funktionierte.
Falls du auf eine andere/bessere Lösung kommst, kannst sie ja posten...
Bzw. falls einer weiß wie man einen schönen "Windows-Ladebalken" erzeugt. Ich habe damals nichts gefunden :(.

gruß
 
Den nomalen Ladebalken von Windows hab ich mir bereits angeschaut, gibt es auch zig Beispiele im Netz. Gibt es hier evtl. wieder einen Style zum selbstzeichnen? siehe BS_OWNERDRAW bei den buttons

mfg. Poseidon
 
Ich kenne mich nicht sehr gut in der WinAPI aus, aber zumindest steht in der MSDN (Link) nichts spezielles von so einem Style.
 
Zuletzt bearbeitet:
Danke.

Habe nun den ganzen Balken in Segmente unterteilt und versucht diese selbst zu zeichnen. Wundere mich, warum bei der WM_PAINT message das nächste Segment nicht ausgegeben wird.

Code:
	case WM_PAINT:
		hdc = BeginPaint(hWnd, &ps);
		for(i=0;i<position;i++)
		{
			hdcMem = CreateCompatibleDC(hdc);
			SelectObject(hdcMem, hbmp_segment);
			BitBlt(hdc, i*bmp_segment.bmWidth, 0, bmp_segment.bmWidth, bmp_segment.bmHeight, hdcMem, 0, 0, SRCCOPY);
			DeleteDC(hdcMem);
		}
		MessageBox(0,L"paint",0,0);
		EndPaint(hWnd, &ps);
		break;

Mit einem Button zähl ich dann die Variable "position" um ein Segment rauf. Zum "repaint" habe ich schon folgende Funktion probiert:

Code:
SendMessage(hWnd, WM_PAINT, 0, 0);

Wenn ich vor dem Debuggen die Variable position setzt, funktioniert der Paint schon, jedoch bei erzwungenem Aufruf von WM_PAINT via SendMessage nicht. Bei Minimierung und anschließender Maximierung des Fensters werden die Segmente aber gezeichnet.

Hat jemand dieses Problem schon einmal gehabt?

mfg. Poseidon
 
Zuletzt bearbeitet:
Das liegt vermutlich daran, dass das Fenster nicht neu gezeichnet wird. Beim minimieren bzw. maximieren dann schon wieder. Du musst die Funktion InvalitadeRect verwenden. Allerdings zeichnet die Funktion auch nur neu wenn dann irgendwann return 0 kommt. So war es bei mir zumindest. Deshalb hab ich einen eigenen Thread dafür machen müssen zum neuzeichnen, und starte den dann immer. Is zwar ein Umweg, aber so gehts es wenigstens.

grüße
 
Die Sache mit dem Laden/Animieren funktioniert schon ganz gut.

Habe nun das Problem, dass es noch manchmal zum Flackern kommt. Wirklich nicht oft, nur halt manchmal.

Mein Zeichenvorgang sieht folgendermaßen aus:

Code:
	hdc = BeginPaint(hwnd, &ps);

		hdcMem = CreateCompatibleDC(hdc);
		SelectObject(hdcMem, hBmpLoadingbar);
		BitBlt(hdc, 0, 0, position, bmploadingbar.bmHeight, hdcMem, 0, 0, SRCCOPY);
		DeleteDC(hdcMem);

	EndPaint(hwnd, &ps);

Mit einem Timer wird die Variable position raufgezählt und mit InvalidateRect der Bereich im Prinzip neu gezeichnet.

Code:
		case WM_TIMER:
			if(wParam==IDT_TIMER1) 
			{
				if(position==363)//zurücksetzen
				{
					position=0;
					InvalidateRect (hWnd, &inval_load_1_rect, TRUE);//Bereich löschen
				}
				else
				{
					InvalidateRect (hWnd, &inval_load_1_rect, FALSE);//Bereich neu zeichnen
					position++;					
				}
			}
			break;

Das Bitmap wird halt immer neu gezeichnet, kann man das auch mit einer Maske machen, die am Ladebalken drauf liegt, und nachgezogen wird? Der Hintergrund ist nämlich auch ein Bitmap.

Brauchte ein paar Ansätze dazu.

mfg. Poseidon
 
Zurück