Danke für die klasse Zusammenarbeit!



  • Moin,

    wenn dir Mathe liegt und du nicht unbedingt das machen möchtest, was dein Lehrer vorgeschlagen hat, könntest du ja auch einen grafische Ausgabe von Mathe Funktionen machen. (z.b. Sinus kurven)

    Dazu müsstest du dich auch nicht so stark mit dem Grafiksystem auseinander setzen, sondern kannst mit deinen Formeln punkten. 😉

    Ich weiss noch, das wir vor Jahren auch solche Sachen in der Schule programmiert haben... War lustig. 🙂



  • Hallo,

    ja da hast du Recht! Aber ich denke, dass ich bei dem Projekt "Bilder spiegeln" festhalten werde.
    Sicherlich würde es mir (so wie du gesagt hast) leichter fallen, irgendwas zu machen, bei dem der Schwerpunkt eher im Mathematischen liegt. Mein schulisches Projekt zielt aber hauptsächlich auf die Programmierung.
    Klar: Das Spiegeln von Bildpunkten an einer Achse ist auch ein "mathematisches Problem" doch bei dem Thema liegt die Schwierigkeit eher im Programmieren.

    Zur Info: Sitz seit dem Mittagessen (13:00) an meinem Microsoft Visual 2005 und habe keine nennenswerte Erfolge. 😃

    Grüße



  • Zeig doch mal, was du bislang hast.



  • Hey servus,

    also zu aller erst hab ich mir mal das Problem bzw. dann die Lösung verbildlicht:

    Ich bleib aber am Ball...

    Grüße



  • Hallo Leute,

    ich komm leider nicht weiter.
    Bisher hab ich mir überlegt, dass das Programm 2 Schleifen benötigt.
    Es soll jeden senkrechten in einer Spalte verschieben bis zum Ende des Bildes. Dann soll das Programm die Spalte verschieben und wieder die Bildpunkte verschieben. Bis das gesamte Bild gespiegelt ist.

    Mein Hauptproblem ist aber, dass ich überhaupt nicht weiß, wie ich ein "Pixel" auswählen kann.

    Ich hoffe auf Hilfe und sorry, wenn ich jemanden mit meiner "Unfähigkeit" nerve

    Grüße



  • Ich kenn mich ehrlich gesagt mit VC++ nicht aus aber dort sollte es eine GUI Komponente geben "Image" oder sowas in der Art die dir die entsprechenden Funktionen zur Verfügung stellt. Alternativ kannst du auch selber einen Windows Bitmap Loader basteln, ist nicht sonderlich schwer, siehe Doku auf Wikipedia.



  • Also ich benutze den Typ IplImage aus der OpenCV, aber du kannst auch mit WinAPI-Funktionen arbeiten. Woran ich mich spontan noch erinnere (alles ohne Gewähr 😉 ): wenn du ein Bitmap (Stichwort HBITMAP, guck mal nach LoadBitmap oder LoadImage) geladen hast, kannst du, glaube ich, mit GetBitmapBits direkt auf die Bilddaten zugreifen. Da liegt dein 2D-Bild dann hintereinander im eindimensionalen Speicher, so dass du eine Position x,y mit y*breite+x ansteuern kannst. Zu dem Zweck kannst du dir eine kleine Funktion oder ein Makro basteln. Das Spiegeln ist dir dann ja klar. Einfach Pixel links und rechts bzw. oben und unten tauschen.



  • Guten Morgen!

    also Leute ich sag euch ganz ehrlich: Ich habe grade keinen Durchblick mehr 🙂

    Aber zu erst nochmal etwas anderes:
    Ich glaube es gab ein Missverständnis! Ich schreibe dieses Programm in Microsoft Visual C++ 2005 Express Edition ABER in C und nicht in C++ . In C++ kenne ich auch diesen Weg des Bildaufrufes aber in "reinem" C ist alles ja sehr maschinennah.

    Oder funktioniert es dort genau gleich und ich bin einfach zu blöd? :p

    Also machts gut!



  • Es gab kein Missverständnis. Die WinAPI-Funktionen haben alle C-Interface, da brauchst du nix C++-spezifisches zu verwenden (wenn du nur Standard-ANSI-C nutzen willst, also komplett ohne Windows-Funktionen, ist das natürlich was anderes). Mein Vorschlag wäre, mal deinen bisherigen Stand zu posten. Dann kann man auch leichter helfen.



  • Hallo Matze,

    danke für deine Antwort! Das mit dem C-Interface wusste ich nicht... aber ich weiß so vieles nicht 😃

    Also ich post euch mal wie weit ich bin^^ (Ist ein Gemisch aus C und Text :-))

    /* Datei: Spiegeln.c */
    #include<stdio.h>
    #include<math.h> /*enthält mathematische Formeln */

    int main (void)

    {

    int d /* Abstand als integer Zahl Local Var. /
    int x /
    X-Koordinate als integer Zahl Local Var. /
    int y /
    Y-Koordinate als integer Zahl Local Var.*/
    /* man muss hier noch die Breite des Bildes also d abfragen */

    {
    do
    { /* */
    while d>0

    for (d=0)
    {/* eine Reihe nach unten und dann wieder do-while schleife*/

    }

    return 0;

    }

    Also Leute ich entschuldige mich schon mal hier für meine Unfähigkeit 🤡
    Aber ich hoffe ihr nehmt es mir nicht übel und helft mir. Ich hab noch nicht so lang C.

    Grüße



  • Hast Du den Code 1:1 geposted? Sagt Dir das Wort Semikolon etwas?
    Ansonsten sind Code Tags nicht schlecht und Selbsterniedrigung

    stuttgart schrieb:

    ich entschuldige mich schon mal hier für meine Unfähigkeit

    bringt Dich auch nicht weiter.



  • Ich habe dir ja ein paar Funktionsnamen genannt. Mach dich mal in der Richtung schlau (Google, msdn.com, das Forum hier; man findet in kurzer Zeit jede Menge zum Thema...). Ein Anfang wäre, mal eine Bitmap-Datei zu laden. Dann kannst du sehen, wie du auf die Bilddaten zugreifen kannst. Und so kannst du dich Stück für Stück an die Lösung herantasten. Bei Teilproblemen melde dich einfach.

    Ich habe, wie gesagt, auch nicht viel Erfahrung damit, da ich OpenCV benutze, und kann (und da so jeder Lerneffekt fehlen würden, will) dir nicht aus dem Stehgreif eine komplette Lösung posten.



  • Hallo Leute,

    ich meld mich mal wieder 😉

    War mehr oder weniger erfolgreich. Hab auf der Suche nach den Begriffen (Nochmal Danke an Matze) einige ganz coole Programme entdeckt!
    Am eigentlichen Problem bin ich leider nicht wirklich weiter gekommen.

    Ich denke dies hier wird der Knackpunkt sein: (Hab es mal probiert aber es klappt nicht wirklich:

    #inlude<stdio.h>

    int main(void)

    {

    HBITMAP hBmp =
    (HBITMAP)LoadImage(NULL,"Spiegeln.bmp",IMAGE_BITMAP,0,0,LR_LOADFROMFILE);

    return 0;

    }

    Grüße aus Stuttgart



  • Stuttgart schrieb:

    Hab es mal probiert aber es klappt nicht wirklich:

    Du musst dir angewöhnen, sowas besser zu beschreiben. Was klappt nicht und wie äußert sich das (Compiler- oder Linker-Fehler, oder zur Runtime)? Kommt eine Fehlermeldung? Wenn ja, welche (genauer Fehlertext und u.U. auch -code)?

    In deinem Beispiel dürfte der Compiler vermutlich sagen, dass er die Funktion LoadImage nicht kennt, da du windows.h einbinden musst. Richtig?

    Und "#inlude" ist sicher nur ein Tippfehler (warum auch immer du das abtippst, statt es per C&P zu machen 😉 ) und kommt in deinem Code nicht vor, oder?



  • Abend Matze und natürlich Hallo an alle!

    also zuerst mal zu dem Copy & Paste Thema. Ich programmier immer in Microsoft Visual 2008 und dann kopier ich den Quellcode nicht einfach hier rein sondern schreib ihn ohne noch mal in das Programm zu schauen hier hinein! Ich will da einfach was lernen :p . Aber ich poste ab sofort den "orginal" Quellcode und beschreib meine Fehler mehr.-> Versprochen

    Also ich hab das jetzt so mal reingeschrieben:

    #include<stdio.h>
    #include<windows.h>

    int main(void)

    {

    HBITMAP hBmp =
    (HBITMAP)LoadImage(NULL,"Spiegeln.bmp",IMAGE_BITMAP,0,0,LR_LOADFROMFILE);

    return 0;

    }

    Der Tipp mit der Headerdatei war genau der Richtige! Weil woher soll das Programm die Funktion LoadImage kennen?
    Ich bekomme keine Fehlermeldung und es scheint zu klappen.

    Nun hab ich noch Fragen:

    1. Woher kommt denn die, bis jetzt fiktive, Datei "Spiegeln.bmp" ? Müsste ich nicht eine Adresse wie C:\Dokumente und Einstellungen\.... angeben?

    2. Wie geht es denn jetzt weiter? Jetzt hätte ich ja mal ein Bild "geladen".

    Ich denke (war ja wieder ein Tipp von Matze 😉 ) es hat was damit zu tun:

    GetBitmapBits("Spiegln.bmp",LONG cb, LPVOID lpvBit);

    Die Funktion ist mir aber ganz unklar!

    Herzliche Grüße



    1. Jeder Prozess hat ein "current directory". Wenn kein absoluter Pfad angegeben wird, dann sucht das OS Dateien immer relativ zu diesem "current directory".

    2. Wenn dir unklar ist wie man an die Bitmap Bits kommt, und wie du von dort weitermachen sollst, und wenn dir die MSDN nicht weiterhilft ... dann such dir halt Beispiele im Netz.
      Wenn man mit Google nichts brauchbares findet, ist Google Code Search meist einen Versuch Wert.

    http://www.google.com/codesearch



  • Ob es klappt, siehst du am Rückgabewert von LoadImage (den solltest du prüfen). Da die Datei (noch) nicht existiert, wird NULL zurückgegeben. Das könntest du so machen:

    HBITMAP hBmp = 
    (HBITMAP)LoadImage(NULL,"Spiegeln.bmp",IMAGE_BITMAP,0,0,LR_LOADFROMFILE);
    if(!hBmp) {  //wenn hBmp 0 ist
      //eventuell Fehlermeldung ausgeben
      return 0;  //Programm beenden
    }
    

    Einen Pfad kannst du angeben, wenn das nötig ist (s. hustbaers Post). Dabei musst du ihn so angeben: "C:\\myDir\\myFile.bmp". Doppelte Backslashes (Stichwort Escapesequenzen), sonst klappt es nicht.

    Ich hab mir GetBitmapBits mal kurz angesehen. Das funktioniert so, dass du dir die Bilddaten in einen Puffer (den du selbst erzeugen musst, Stichwort malloc/free) kopierst (ich dachte, du kriegst einfach einen Pointer...). Dann führst du dein Spiegeln durch und kopierst den ganzen Quatsch wieder mit SetBitmapBits zurück.

    Ich würde vorschlagen, unternimm mal zumindest folgende Schritte:
    - BMP-Datei besorgen und mit LoadImage laden
    - Puffer mit malloc erzeugen, der soviele Bytes hat, wie im BMP an Daten sind (Länge*Breite*4 Bytes pro Pixel). Da du nicht in den Farbkanälen rumpfuschen willst, kann das ruhig direkt ein int-Puffer sein.
    - Bilddaten mit GetBitmapBits in deinen Puffer kopieren.

    Das solltest du mit allen genannten Stichwörtern und entsprechendem googlen schaffen. Ansonsten meld dich.



  • Guten Tag!

    Also ich hab mal noch rumprobiert und hab mit Hilfe deiner Stichworte die Malloc-Geschichte auf jeden Fall verstanden! 💡

    So weit wir jetzt sind:

    #include<stdio.h>
    #include<windows.h>

    int main(void)

    {

    int*Speicher;

    HBITMAP hBmp =
    (HBITMAP)LoadImage(NULL,"C:\\Desktop\\Spiegeln.bmp",IMAGE_BITMAP,0,0,LR_LOADFROMFILE);

    if(!hBmp)
    { printf("Fehler beim Ladevorgang\n");
    }
    else
    {printf("Laden war erfolgreich\n");
    }

    Speicher=malloc(sizeof(int));

    GetBitmapBits(HBITMAP hBmp,LONG cSize, void * lpvBits);

    free(Speicher);

    return 0;

    }

    Also das Laden der Bmp funktioniert ganz gut!

    Fragen:

    1. Muss ich bei sizeof(int) nicht irgendwie vorher sagen, dass des Bild eben 100 Pixel lang und 200 Pixel breit ist? Dazu habe ich leider nichts gefunden. Aber so gibt malloc ja nur für "int" Speicher frei. Oder war das richtig?

    Da du nicht in den Farbkanälen rumpfuschen willst, kann das ruhig direkt ein int-Puffer sein.

    2. GetBitmapBits Fehlermeldung:
    Nicht genügend Argumente für Aufruf
    Die Funktion habe ich aber vom Aufbau her auch noch nicht begriffen!

    Grüße aus dem sonnigen Stuttgart



  • Bitte benutze in Zukunft cpp-Tags, um deinen Code schön leserlich mit Syntaxhighlighting darzustellen. Dazu umschließt du deinen Code mit [cpp] und [/cpp].

    Stuttgart schrieb:

    Speicher=malloc(sizeof(int));
    

    Hier reservierst du nur 4 Bytes (unter einem 32-Bit-OS). malloc nimmt einfach einen Zahlenwert, der die Anzahl an zu allozierenden Bytes darstellt. Wenn du also für jeden Pixel 4 Bytes anfordern willst, dann musst du einfach sizeof(int)*Breite*Höhe übergeben ("Speicher=malloc(sizeof(int)*width*height)").

    Ich finde es sogar besser, wenn man hier 4 statt sizeof(int) übergibt (vielleicht in Form einer Präprozessor-Konstante oder in einem weiter fortgeschrittenen Programm als zuweisbaren Member einer Struktur oder Klasse). Vielleicht ändert sich sizeof(int) ja unter einem anderen OS/Compiler, du willst aber weiterhin 32 Bit pro Pixel verarbeiten. Aber egal...

    Übrigens gut, dass du auch ans free gedacht hast. Sonst hättest du direkt ein Speicherleck...

    Stuttgart schrieb:

    2. GetBitmapBits Fehlermeldung:
    Nicht genügend Argumente für Aufruf
    Die Funktion habe ich aber vom Aufbau her auch noch nicht begriffen!

    Du übergibst ja hier auch nix, das ist einfach der Kopf der Funktion aus der Hilfe kopiert. Also...

    1. Parameter: Dein Bitmap-Handle, dass von LoadImage kommt.
    2. Parameter: Anzahl zu kopierender Bytes (also hier wieder Breite*Höhe*4, eben soviel Speicher wie du angefordert hast und im Bitmap an Daten vorhanden ist).
    3. Parameter: void-Pointer auf den Puffer, in den die Daten reinkopiert werden sollen. Speicher ist ein int-Pointer, der muss gecastet werden. Das wäre wohl "(void*)Speicher".

    Wenn das ganze Vorgeplänkel dann passt, bist du kurz davor, endlich mal im Bildspeicher rumpfuschen zu können... 🙂



  • Super vielen Dank für die schnelle Antwort!

    Mein Problem ist noch, dass ich nicht weiß wie ich die Höhe und Breite des Bildes auslesen kann? Gibt es da sowas in C wie getimagesize() ?

    Grüße


Anmelden zum Antworten