Linie zeichnen mit C++



  • @HarteWare
    merci viel mal. Ich werde mich mal an SFML versuchen.
    Vielleicht kommen ja noch Fragen.



  • @spatz sagte in Linie zeichnen mit C++:

    Hallo zusammen.
    Ich möchte eine Linie oder ein Kreis zeichnen.

    Wohin, auf welchem System, Gerät?
    (Fenster, Bildschirm, LCD, Drucker, Plotter - Windows, Linux - PC, Mikrocontroller - ...)

    Was mich auch sehr interessiert, wie man einfach einen Punkt (Pixel) setzen kann.

    Im Allgemeinen zeichnet man eine Linie oder Kreis aus mehreren Punkten.

    Habe es mit graphics.h versucht, aber das ging nicht. Ich konnte es gar nicht installieren.

    graphics.h hört sich nach C an.

    Es muss doch möglich sein, mit C++ einfache Grafik zu programmieren.

    C++ an sich kennt keine Grafik.

    Aber es gibt Libraries dafür. Die sind aber (teilweise) Systemabhängig.



  • @spatz sagte in Linie zeichnen mit C++:

    Was mich auch sehr interessiert, wie man einfach einen Punkt (Pixel) setzen kann.

    Hach, vor 20 Jahren hätte ich diese Frage noch mit vielleicht 5 Zeilen Beispielcode beantworten können 😉

    Heute hat man zwar mehr Möglichkeiten, damit sind solche simplen Dinge aber erstmal wesentlich komplizierter und sie verdecken auch erstmal zu einem großen Teil, was Computergrafik hinter den Kulissen wirklich bedeutet.

    Heute schließe ich mich für Anfänger allerdings ebenfalls der SFML-Empfehlung an. OGL/D3D oder Vulkan können im Prinzip nur Dreiecke zeichnen und sind für Anfänger sicher verwirrend und wenig intuitiv (Vulkan und auch D3D >= 11 würde ich sogar nur Experten empfehlen).



  • Hi Spatz,

    Du brauchst vor allem etwas worauf Du zeichnen kannst. Das kann eine zeichenbare Fläche in einem Programm sein, oder auf der Commandozeilenebene im Grafikmodus einfach der Bildschirm. Entweder über Unterprogramme, oder direkt im Graphikmodus über die Adresse angesprochen. Ob das unter Win 10 noch geht weiß ich nicht. müsste aber noch.
    Für das Zeichnen der Linie sieh mal beim Bresenham-Algorithmus nach:
    https://de.wikipedia.org/wiki/Bresenham-Algorithmus

    Viel Erfolg wünscht Mümmel



  • @muemmel

    Hallo Mümmel. Weisst du, das Problem ist bei diesem Bresenham-Algorithmus, ist der Befehl SetPixel. Um den geht es mir ja die ganze Zeit. Aber diese Lumpen haben den Befehl in fast keiner Programmiersprache mehr implementiert. Es ist zum Kotzen.
    Aber ich glaube mit SFML komme ich weiter.
    Oder hast du noch eine Idee, wie es einfacher geht?



  • @spatz sagte in Linie zeichnen mit C++:

    Aber diese Lumpen haben den Befehl in fast keiner Programmiersprache mehr implementiert.

    So ein Befehl gehörte nie (selten) zu irgendeiner Programmiersprache.
    Wenn, war er eine Erweiterung (z.B. BASIC) oder in einer mitgelieferten Bibliothek (z.B. Pascal, C zu DOS-Zeiten)

    Mittlerweile hat sich aber die Computergrafik gewandelt. Man zeichnet nicht mehr auf einem Bildschirm der einem alleine gehört sondern in einem skalierbaren Fenster (von vielen).

    Zudem kommen noch die GUI-Features dazu.
    Darum gibt es jetzt externe oder systemeigene Bibliotheken.
    Aber da muss man sich einarbeiten.


  • Mod

    Bevor du jetzt anfängst, nach Bresenham einzelne Pixel zu setzen, solltest du dich fragen, was denn letztlich dein Ziel ist. Computergrafik heute macht man schlichtweg nicht mehr als Ansammlung einzelner Pixel. Irgendwo ganz am Ende wird zwar natürlich irgendein Algorithmus entscheiden, welcher Pixel auf welche Farbe gesetzt wird, aber die grundlegenden Konzepte, wie man heutzutage über die Grafikdarstellung denkt, sind ganz anders. Daher nützt es dir überhaupt gar nichts, mit einzelnen Pixeln anzufangen, wenn du später dann doch moderne Computergrafik machen möchtest.



  • @spatz sagte in Linie zeichnen mit C++:

    der Befehl SetPixel. Um den geht es mir ja die ganze Zeit. Aber diese Lumpen haben den Befehl in fast keiner Programmiersprache mehr implementiert. Es ist zum Kotzen.

    Ja, furchtbar, alles Verbrecher!!

    Oder hast du noch eine Idee, wie es einfacher geht?

    Ich empfehle dir DOSBox + GW-BASIC.



  • #include <Windows.h>
    
    LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
    
    int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow)
    {
    	static TCHAR szAppName[] = TEXT("Aufgäbe 1");
    	HWND hwnd;
    	MSG msg;
    	WNDCLASS wndclass;
    
    	wndclass.style = CS_HREDRAW | CS_VREDRAW;
    	wndclass.lpfnWndProc = WndProc;
    	wndclass.cbClsExtra = 0;
    	wndclass.cbWndExtra = 0;
    	wndclass.hInstance = hInstance;
    	wndclass.hIcon = LoadIcon(0, IDI_APPLICATION);
    	wndclass.hCursor = LoadCursor(0, IDC_HAND);
    	wndclass.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
    	wndclass.lpszMenuName = 0;
    	wndclass.lpszClassName = szAppName;
    	
    
    	if (!RegisterClass(&wndclass))
    	{
    		MessageBox(0, TEXT("Fehler!"), szAppName, MB_ICONERROR);
    		return 0;
    	}
    
    	hwnd = CreateWindow(szAppName, TEXT("Aufgabe 1"), WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, 0, 0, hInstance, 0);
    
    	ShowWindow(hwnd, iCmdShow);
    	UpdateWindow(hwnd);
    
    	while (GetMessage(&msg, 0, 0, 0))
    	{
    		TranslateMessage(&msg);
    		DispatchMessage(&msg);
    	}
    
    	return msg.wParam;
    }
    
    LRESULT CALLBACK WndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
    {
    	HDC hdc;
    	PAINTSTRUCT ps;
    	RECT rect;	
    
    	switch (message) 
    	{
    	case WM_CREATE:
    		return 0;
    	case WM_PAINT:
    		hdc = BeginPaint(hwnd, &ps);
    
    		GetClientRect(hwnd, &rect);
    
                    MoveToEx(hdc, 10, 10, NULL);
                    LineTo(hdc, 20, 20);
    
    		EndPaint(hwnd, &ps);
    		return 0;
    	case WM_DESTROY:
    		PostQuitMessage(0);
    		return 0;
    	}
    
    	return DefWindowProc(hwnd, message, wParam, lParam);
    }
    


  • @SeppJ

    Hallo Sepp. Mein Ziel ist es, mathematische Funktionen zu zeichnen. Etwa eine Parabel (Quadratfunktion). Dazu muss ich einzelne Pixel setzten können. Es ist mir dies übrigens jetzt mit SFML gelungen auf Linux.
    Juhui!



  • achja wenn du pixel setzen willst, musst du SetPixel(hdc, xcoord, ycoord, RGB(rval, gval, bval)) verwenden. geht doch alles ganz einfach.🙄



  • @Wade1234

    Muss man da noch eine spezielle Bibliothek einbinden? Also für SetPixel?



  • also es funktioniert halt nur unter windows, aber im prinzip kannst du ab zeile 58 ganz normal SetPixel aufrufen. in einem "richtigen" programm würde man das natürlich alles in unterfunktionen auslagern usw., aber wenn du "nur mal ein bisschen malen" möchtest, geht das so. das programm müsstest du einfach so mit copy & paste übernehmen können.



  • @Wade1234

    Also dieser Code funktioniert bei mir in Visual Studio nicht.
    Vielleicht habe ich auch mein VS abgeschossen.



  • @spatz "funktioniert nicht" ist immer sehr ungenau. also ich habs eben getestet mit "Neues Projekt" -> "Windows-Desktopanwendung" (achtung: nicht -Assistent!) -> "Weiter, weiter, weiter" -> vorhandenen quelltext löschen -> meinen code einfügen. wenn du ein leeres projekt erstellst, musst du in den linker-einstellungen das subsystem auf "Windows" ändern.



  • @Wade1234

    Jetzt hat es funktioniert. Da kommt dann ein kleines Strichli, richtig?
    Ich ging drum auf Konsole-Anwendung zuerst.
    Vielen Dank



  • @spatz ja da kommt ein strich von (10, 10) nach (20, 20). die dimensionen bzw. eckpunkte des fensters sind in rect (zeile 48) gespeichert und für linien musst du eben zuerst MoveToEx und dann LineTo aufrufen.



  • Es gibt auch sf::LineStrip. Dann musst Du nur entscheiden, welchen Bereich und mit welcher Abtastrate Du darstellen willst (sprich, Du brauchst (X,Y) Vektoren) und dann werden die Punkte automatisch linear interpoliert).

    Jetzt könnte man natürlich wieder fragen, wozu Du denn Funktionen plotten willst. Dafür gibt es wieder fertige Bibliotheken, oder es geht in anderen Programmiersprachen leichter und schneller. Deshalb solltest Du Deine Fragen eher so stellen z. B. :

    Ich möchte gerne zu Lernzwecken selbst Kurven plotten in C++, wie gehe ich am besten vor?

    Das führt i. d. R. schneller zum Ziel 😉

    Von der WinAPI würde ich hier persönlich abraten:

    • C-Style Interface, mischt sich nicht gut und schön mit C++, kennt kein RAII etc.

    • Windows Only (prinzipiell).

    • Viel Boilerplate Code notwendig, allgemein mehr Aufwand/low-level.

    P.S.:
    Qt oder Qwt können auch plotten, und wenn Du GUI Elemente willst, bist Du auch schon bedient. Es gibt auch GNUPlot, damit habe ich selbst aber noch nie in C++ gearbeitet. Python+Matplotlib ist aber sicherlich einfacher.



  • @HarteWare

    Auf alle Fälle, vielen Dank für eure Hilfe.
    Habe wieder ne Menge dazugelernt.


Anmelden zum Antworten