Hallo allerseits! Dies ist die vierte Lektion in SDL 2. Ich habe beschlossen, die beiden Lektionen zu einer zu kombinieren, da sie im Original klein sind. Aber sie sind
hier und
hier zu finden . Beginnen wir mit der Lektion.
Zuerst werden wir entscheiden, was wir tun werden. Heute lernen wir, wie Sie Bilder einer anderen Erweiterung (nicht BMP) hochladen, nämlich: PNG. Wiederholen Sie das Bild in einem anderen Format, um die Arbeit zu beschleunigen und die Bildgröße zu ändern. Wir werden mit diesem Bild arbeiten:
Installation
Zuerst lernen wir, wie man PNG herunterlädt. Im Standard-SDL 2-Funktionsumfang wird kein Bild ohne BMP-Format hochgeladen. Um ein anderes Format herunterzuladen, müssen Sie die Erweiterung installieren.
Hier sind die Anweisungen:
WindowsSie gehen auf diese
Seite und laden die ZIP- oder TAR.GZ-Archive aus dem Bereich
Entwicklungsbibliotheken herunter. Entpacken Sie sie und werfen Sie sie mit dem Compiler in den Ordner.
LinuxWenn Ihr System Debian verwendet, müssen Sie folgende Befehle eingeben:
apt-cache search libsdl2-image apt-get install libsdl2-image-dev
Wenn Yellowdog Updater, Modified verwendet wird, geben Sie folgende Befehle ein:
yum search SDL2_image-devel yum SDL2_image-devel
Mac OSLaden Sie die DMG-Datei herunter und lesen Sie die Readme-Datei.
Einen Code schreiben
Nach dem Setzen von
SDL_image beginnen
wir mit dem Schreiben von Code. Zuerst werden wir wie immer die Bibliotheken verbinden, die Fenstergrößen festlegen und 3 globale Variablen erstellen.
#include <SDL2/SDL.h> #include <SDL2/SDL_image.h> #include <iostream> const int SCREEN_WIDTH = 640; const int SCREEN_HEIGHT = 480; SDL_Window *win = NULL; SDL_Surface *scr = NULL; SDL_Surface *flower = NULL;
Beachten Sie, dass ich
SDL_image.h separat verbunden
habe , da es sich um eine separate Bibliothek handelt.
Als nächstes schreiben wir 3 uns bekannte Funktionen, in denen wir wie gewohnt etwas hinzufügen und ändern.
Init () bool init() { if (SDL_Init(SDL_INIT_VIDEO) != 0) { std::cout << "Can't init video: " << SDL_GetError() << std::endl; return false; } int flags = IMG_INIT_PNG; if ( !( IMG_Init( flags ) & flags ) ) { std::cout << "Can't init image: " << IMG_GetError() << std::endl; return false; } win = SDL_CreateWindow(" PNG", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, SCREEN_WIDTH, SCREEN_HEIGHT, SDL_WINDOW_SHOWN); if (win == NULL) { std::cout << "Can't create window: " << SDL_GetError() << std::endl; return false; } scr = SDL_GetWindowSurface(win); return true; }
Hier haben wir die Initialisierung des Moduls SDL_image hinzugefügt. Um es zu initialisieren, erstellen Sie zuerst eine
int- Variable, wir haben
Flags und speichern dort alle Flags, die Sie für die Initialisierung verwenden möchten.
Liste aller FlagsSDL_INIT_PNG - initialisiert den PNG-Image-Downloader;
SDL_INIT_JPG - Initialisiert den JPG-Bild-Downloader.
SDL_INIT_TIF - Initialisiert den TIF-Image-Downloader.
Als nächstes schreiben wir diese Bedingung:
if ( !( IMG_Init( flags ) & flags ) )
Die Funktion
IMG_Init () gibt die Flags zurück, die initialisiert werden konnten. Wenn sie die Flaggen zurückgegeben hat, aber die gewünschte fehlte, geben wir einen Fehler zurück. Sehr einfach. Beachten Sie auch, dass ich
IMG_GetError anstelle von
SDL_GetError verwende , da wir nach einem Fehler in der Funktion des
SDL_image- Moduls
suchen , nicht in
SDL .
Ich möchte auch darauf hinweisen, dass ich mich entschieden habe, den
Bool- Typ zu verwenden,
um a zurückzugeben - dies ist ein rationalerer Weg.
Lassen Sie uns unser Programm weiter schreiben, die Funktion
Load () schreiben, in die wir ein PNG-Bild laden und es konvertieren.
Laden bool load() { flower = IMG_Load("flower.png"); if (flower == NULL) { std::cout << "Can't load: " << IMG_GetError() << std::endl; return false; } flower = SDL_ConvertSurface(flower, scr->format, NULL); if (flower == NULL) { std::cout << "Can't convert: " << SDL_GetError() << std::endl; return false; } return true; }
Hier laden wir das Bild mit der neuen Funktion
IMG_Load hoch .
Seine Funktion ist dieselbe wie die von
SDL_LoadBMP und das Ergebnis ist dasselbe - es gibt eine Instanz der
SDL_Surface- Klasse zurück. Um Fehler beim Laden zu finden, verwenden wir auch
IMG_GetError .
Es ist Zeit zu konvertieren. Zunächst eine kleine Theorie. Nur wenige wissen es, aber beim Herunterladen eines Bildes wird es im 24-Bit-Format heruntergeladen, und die meisten modernen Displays sind im 32-Bit-Format. Und jedes Mal, wenn wir das Bild auf dem Bildschirm anzeigten, wurde es zuerst im 32-Bit-Format wiederholt. Für einfache Programme spielt dies keine Rolle, aber wenn Sie ein großes Projekt erstellen, wirkt sich dies stark auf die Leistung aus. Daher nehmen wir Bilder auf und erstellen sie beim Laden im Anzeigeformat neu. Die
SDL_ConvertSurface- Funktion hilft. Es werden 3 Werte benötigt: Die Oberfläche, die wir formatieren möchten, das Format, in das wir formatieren möchten, und die Flags. Wir wollen das
Blumenbild formatieren und ihm den ersten Parameter übergeben. Der zweite Parameter ist das Format der Fensteroberfläche, wir werden keine Flags verwenden. Diese Funktion gibt eine Kopie der Oberfläche zurück, die wir sofort der
Blume zuweisen. Um Fehler zu finden, verwenden wir die Funktion
SDL_GetError () ,
da wir bereits mit Oberflächen arbeiten und diese aus
SDL und nicht aus
SDL_image stammen .
Als nächstes schreiben wir die Quit-Funktion und fügen nur eine Funktion hinzu.
Beenden Sie void quit() { SDL_FreeSurface(flower); SDL_FreeSurface(scr); SDL_DestroyWindow(win); SDL_Quit(); IMG_Quit(); }
Wir haben
IMG_Quit hinzugefügt, um das SDL_image-Modul zu initialisieren.
Haupt
Jetzt bleibt das Einfachste - die Hauptfunktion.
int main (int argc, char ** args) { if (!init()) { system("pause"); quit(); return 1; } if (!load()) { system("pause"); quit(); return 1; }
Initialisieren und erstellen Sie zunächst alles, was Sie benötigen, und laden Sie die erforderlichen Dateien hoch. Wir werden hier nicht aufhören.
SDL_Rect bg_flower; bg_flower.w = SCREEN_WIDTH; bg_flower.h = SCREEN_HEIGHT; bg_flower.x = 0; bg_flower.y = 0;
Erstellen Sie anschließend ein Objekt der Klasse
SDL_Rect . Wir werden es brauchen, um das Bild zu dehnen. Wenn Sie bemerken, ist das Blumenbild viermal kleiner als das Fenster (zweimal dünner und zweimal niedriger), und wir müssen es bis zum Fenster strecken. Schreiben Sie also in die Breite des Rechtecks
bg_flower den Wert der Breite des Fensters und in height - die Höhe des Fensters. Setzen Sie die Koordinaten auf 0, damit das Bild in der oberen linken Ecke angezeigt wird.
Zum Anzeigen von Bildern mit geänderter Größe gibt es eine spezielle Funktion. Es sieht so aus:
SDL_BlitScaled(flower, NULL, scr, &bg_flower);
Es braucht 4 Bedeutungen. Das erste ist das Bild, das wir anzeigen möchten, das zweite ist das Rechteck, das wir aus diesem Bild ausschneiden möchten (wenn wir das gesamte Bild aufnehmen möchten, schreiben wir NULL), das dritte ist die Oberfläche, auf der das Bild angezeigt werden soll, und das vierte ist das gleiche Rechteck, Abmessungen und die Koordinaten, die wir nehmen, um das Bild zu dehnen oder zu komprimieren und anzuzeigen.
Als nächstes aktualisieren Sie einfach die Bildschirmoberfläche, stellen die Verzögerung ein, beenden und geben 0 zurück.
SDL_UpdateWindowSurface(win); SDL_Delay(2000); quit(); return 0; };
Hier endet unser Programm. Um dieses Wunder zu kompilieren, müssen Sie -lSDL2_image als weitere Kompilierungsoption hinzufügen.
Und damit werden wir für heute enden. Hier ist der Code, den wir bekommen haben:
#include <SDL2/SDL.h> #include <SDL2/SDL_image.h> #include <iostream> const int SCREEN_WIDTH = 640; const int SCREEN_HEIGHT = 480; SDL_Window *win = NULL; SDL_Surface *scr = NULL; SDL_Surface *flower = NULL; bool init() { if (SDL_Init(SDL_INIT_VIDEO) != 0) { std::cout << "Can't init video: " << SDL_GetError() << std::endl; return false; } int flags = IMG_INIT_PNG; if ( !( IMG_Init( flags ) & flags ) ) { std::cout << "Can't init image: " << IMG_GetError() << std::endl; return false; } win = SDL_CreateWindow(" PNG", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, SCREEN_WIDTH, SCREEN_HEIGHT, SDL_WINDOW_SHOWN); if (win == NULL) { std::cout << "Can't create window: " << SDL_GetError() << std::endl; return false; } scr = SDL_GetWindowSurface(win); return true; } bool load() { flower = IMG_Load("flower.png"); if (flower == NULL) { std::cout << "Can't load: " << IMG_GetError() << std::endl; return false; } flower = SDL_ConvertSurface(flower, scr->format, NULL); if (flower == NULL) { std::cout << "Can't convert: " << SDL_GetError() << std::endl; return false; } return true; } void quit() { SDL_FreeSurface(flower); SDL_FreeSurface(scr); SDL_DestroyWindow(win); SDL_Quit(); IMG_Quit(); } int main (int argc, char ** args) { if (!init()) { system("pause"); quit(); return 1; } if (!load()) { system("pause"); quit(); return 1; } SDL_Rect bg_flower; bg_flower.w = SCREEN_WIDTH; bg_flower.h = SCREEN_HEIGHT; bg_flower.x = 0; bg_flower.y = 0; SDL_BlitScaled(flower, NULL, scr, &bg_flower); SDL_UpdateWindowSurface(win); SDL_Delay(2000); quit(); return 0; };
Tschüss alle!
<< Vorherige Lektion || Nächste Lektion
>>