Computer Science Canada

SDL2 console output

Author:  Raknarg [ Wed May 06, 2015 3:37 pm ]
Post subject:  SDL2 console output

Alright so I'm trying to learn how to use SDL2. I'm using a text editor and command line for it, following LazyFoo's tutorials. However, I'm trying now to introduce SDL_image into the program, and it's crashing now. However I can't figure out where it is crashing, because I can't output anything to console. I've tried reading up on it and apparently it's supposed to redirect stdout to a file, but I can't find such a file anywhere.

You guys have any ideas?

Author:  DemonWasp [ Thu May 07, 2015 8:57 am ]
Post subject:  RE:SDL2 console output

I took a (very brief) look at LazyFoo's tutorials and I'm not seeing anything about redirecting console output. What does your build environment look like (OS, compiler, etc)? How are you compiling and running your program?

Author:  Raknarg [ Thu May 07, 2015 9:00 am ]
Post subject:  RE:SDL2 console output

He never mentions console output redirection because I guess for him it's not a problem, but for me i can't get any output anywhere, at keast none that I can tell.

I'm using the makefile suggested, windows 8, using mingw with g++

Author:  DemonWasp [ Thu May 07, 2015 4:36 pm ]
Post subject:  RE:SDL2 console output

If you're just running the program from a terminal (CMD) then you should just see output from cout or printf() automatically -- by default it goes to the console.

Can you post your code and the exact steps that you're using to run your program?

Author:  Raknarg [ Sat May 09, 2015 12:52 am ]
Post subject:  RE:SDL2 console output

This is my code:

c:

#include <SDL.h>
#include <SDL_image.h>
#include <iostream>
#include <stdio.h>
using namespace std;

const int WIDTH = 500;
const int HEIGHT = 500;

enum Keys {
        KEY_DEFAULT,
        KEY_UP,
        KEY_DOWN,
        KEY_LEFT,
        KEY_RIGHT,
        KEY_TOTAL
};

bool init();
bool loadMedia();
void run();
void close();
SDL_Surface* loadImage(string path);

SDL_Window* gWindow = NULL;
SDL_Surface* gScreenSurface = NULL;
char gKeyPress[KEY_TOTAL][3];
char gBackColor[3];
SDL_Surface* gImage = NULL;

void setColor(char* c, char r, char g, char b) { c[0]=r; c[1]=g; c[2]=b; }
void setColor(char* dest, char* src) { setColor(dest, src[0], src[1], src[2]); }

int main(int argc, char* args[]) {
        printf("HI\n");
        if (init()) {
                if (loadMedia()) {
                        run();
                }
        }

        close();

        return 0;
}

bool init() {
        bool success = true;

        if (SDL_Init(SDL_INIT_VIDEO) < 0) {
                cout << "SDL could not be initialized; SDL_Error: " << SDL_GetError() << endl;
                success = false;
        } else {
                freopen( "CON", "wt", stdout );
                freopen( "CON", "wt", stderr );
                printf("HI\n");
                gWindow = SDL_CreateWindow("My SDL", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, WIDTH, HEIGHT, SDL_WINDOW_SHOWN);
                if (gWindow == NULL) {
                        cout << "Window could not be created; SDL_Error: " << SDL_GetError() << endl;
                        success = false;
                } else {
                        int imgFlags = IMG_INIT_PNG;
                        if (!(IMG_Init(imgFlags) & imgFlags)) {
                                cout << "SDL_image could not initialize; SDL_image Error: " << IMG_GetError() << endl;
                                success = false;
                        } else {
                                gScreenSurface = SDL_GetWindowSurface(gWindow);
                        }
                }
        }

        return success;
}

bool loadMedia() {
        bool success = true;

        setColor(gKeyPress[KEY_DEFAULT], 0x00, 0x00, 0x00);
        setColor(gKeyPress[KEY_UP], 0xff, 0xff, 0xff);
        setColor(gKeyPress[KEY_DOWN], 0xff, 0xff, 0x00);
        setColor(gKeyPress[KEY_LEFT], 0x00, 0xff, 0xff);
        setColor(gKeyPress[KEY_RIGHT], 0xff, 0x00, 0xff);

        string imgPath = "D:/Code/C++/SDL Tutorial/hello.bmp";

        gImage = loadImage(imgPath);
        if (gImage == NULL) {
                success = false;
        }

        return success;
}

void run() {
        bool running = true;
        SDL_Event e;
        setColor(gBackColor, gKeyPress[KEY_DEFAULT]);

        while (running) {
                while(SDL_PollEvent(&e) != 0) {
                        if (e.type == SDL_QUIT) {
                                running = false;
                        } else if (e.type = SDL_KEYDOWN) {
                                switch(e.key.keysym.sym) {
                                        case SDLK_UP:
                                                setColor(gBackColor, gKeyPress[KEY_UP]);
                                                break;
                                        case SDLK_DOWN:
                                                setColor(gBackColor, gKeyPress[KEY_DOWN]);
                                                break;
                                        case SDLK_LEFT:
                                                setColor(gBackColor, gKeyPress[KEY_LEFT]);
                                                break;
                                        case SDLK_RIGHT:
                                                setColor(gBackColor, gKeyPress[KEY_RIGHT]);
                                                break;
                                        default:
                                                setColor(gBackColor, gKeyPress[KEY_DEFAULT]);
                                }
                        }
                }

                SDL_FillRect(gScreenSurface, NULL, SDL_MapRGB(gScreenSurface->format, gBackColor[0], gBackColor[1], gBackColor[2]));
                       
                SDL_Rect rect;
                rect.x = 50;
                rect.y = 50;
                rect.w = 300;
                rect.h = 200;
                SDL_BlitScaled(gImage, NULL, gScreenSurface, &rect);
               
                SDL_UpdateWindowSurface(gWindow);
        }
}

void close() {
        SDL_FreeSurface(gImage);
        gImage = NULL;

        SDL_DestroyWindow(gWindow);
        gWindow = NULL;

        SDL_Quit();
}

SDL_Surface* loadImage(string path) {
        SDL_Surface* optimizedImage = NULL;
        SDL_Surface* newImage = SDL_LoadBMP(path.c_str());
        if (newImage == NULL) {
                cout << "Unable to load image " << path << "; SDL_image Error: " << IMG_GetError() << endl;
        } else {
                optimizedImage = SDL_ConvertSurface(newImage, gScreenSurface->format, NULL);
                if (optimizedImage == NULL) {
                        cout << "Unable to optimize image; SDL Error: " << SDL_GetError() << endl;
                }
                SDL_FreeSurface(newImage);
        }

        return optimizedImage;
}



This is my makefile:
code:

#OBJS specifies which files to compile as part of the project
OBJS = 06_sdl_image.cc

#CC specifies which compiler we're using
CC = g++

#INCLUDE_PATHS specifies the additional include paths we'll need
INCLUDE_PATHS = -ID:/Code/C++/SDL/include/SDL2

#LIBRARY_PATHS specifies the additional library paths we'll need
LIBRARY_PATHS = -LD:/Code/C++/SDL/lib

#COMPILER_FLAGS specifies the additional compilation options we're using
# -w suppresses all warnings
# -Wl,-subsystem,windows gets rid of the console window
COMPILER_FLAGS = -w -Wl,-subsystem,windows

#LINKER_FLAGS specifies the libraries we're linking against
LINKER_FLAGS = -lmingw32 -lSDL2main -lSDL2 -lSDL2_image

#OBJ_NAME specifies the name of our exectuable
OBJ_NAME = 06_sdl_image

#This is the target that compiles our executable
all : $(OBJS)
        $(CC) $(OBJS) $(INCLUDE_PATHS) $(LIBRARY_PATHS) $(COMPILER_FLAGS) $(LINKER_FLAGS) -o $(OBJ_NAME)

Author:  Raknarg [ Sat May 09, 2015 12:53 am ]
Post subject:  RE:SDL2 console output

Note that both SDL and SDL_image are in the same lib and include folders, I figured they should be together anyways cause they're more or less part of the same program and don't have names that match up anywhere

Also those freeopen lines there are from me trying out some solutions I found online, idk if they're doing anything

Author:  DemonWasp [ Sat May 09, 2015 8:43 am ]
Post subject:  RE:SDL2 console output

Output redirection happens here:

code:

freopen( "CON", "wt", stdout );
freopen( "CON", "wt", stderr );


That will redirect stdout (cout) to a file called "CON". The reason you don't see that file is that Windows reserves dozens of filenames and 'con' is one of them. See this: http://superuser.com/questions/86999/unable-to-rename-a-folder-or-a-file-as-con

I bet if you comment out those lines, you will suddenly have console output.

Author:  Raknarg [ Sat May 09, 2015 11:21 am ]
Post subject:  RE:SDL2 console output

Tbats what my second comment was for. I was trying that out because it wasn't working. Evem without those lines it doesn't work.

Author:  DemonWasp [ Sat May 09, 2015 12:56 pm ]
Post subject:  RE:SDL2 console output

I don't have an environment where I can build SDL2, so my only suggestion now is to start removing stuff. If you comment out everything in main() except the printf() statement, recompile and rerun, do you at least see HI in the cmd prompt?

Author:  Raknarg [ Sat May 09, 2015 1:19 pm ]
Post subject:  RE:SDL2 console output

think I just figured it out. This line on my makefile:

-Wl,-subsystem,windows

Got rid of that and now it gives me console output

Author:  DemonWasp [ Sat May 09, 2015 7:50 pm ]
Post subject:  RE:SDL2 console output

Interesting. Apparently -Wl is used to pass arguments to the linker. In this case, you're passing --subsystem windows , which apparently tells the linker to (somehow) omit console output.

That's pretty weird. Usually programs have console output even if they also have a GUI -- it's usually just hidden.

Author:  Raknarg [ Sat May 09, 2015 9:30 pm ]
Post subject:  RE:SDL2 console output

Interesting. Of course now I have to figure out why SDL_image os crashing in the first place, but it's a start


: