IMG_Load() doesn't work properly when using with CMake - c++

I'm trying to make a game on vscode with CMake. Everything was fine until I try to show a png image on the screen. I had initialized and linked everything correctly and there are no errors that occur except this:
"Couldn't open ./Images/Mountain.png"
Here is my code:
#include <SDL.h>
#include <SDL_image.h>
#include <iostream>
#undef main
SDL_Window *window;
SDL_Renderer *renderer;
SDL_Texture *tex;
int main(int argc, char const *argv[])
{
if (SDL_Init(SDL_INIT_EVERYTHING) == 0)
{
std::cout << "Initialize SDL" << std::endl;
window = SDL_CreateWindow("SDL2", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 640, 640, SDL_WINDOW_SHOWN);
if (window)
std::cout << "Window created" << std::endl;
renderer = SDL_CreateRenderer(window, -1, 0);
if (renderer)
{
std::cout << "Render created" << std::endl;
SDL_SetRenderDrawColor(renderer, 255, 255, 255, 255);
}
SDL_Surface *tempSurface = IMG_Load("./Images/Mountain.png");
if (!tempSurface)
std::cout << "Can't load image! Error: " << IMG_GetError() << std::endl;
tex = SDL_CreateTextureFromSurface(renderer, tempSurface);
SDL_FreeSurface(tempSurface);
}
SDL_DestroyWindow(window);
SDL_DestroyRenderer(renderer);
SDL_Quit();
return 0;
}
And here is my CMakeLists.txt:
cmake_minimum_required(VERSION 3.19)
project(SDL2 VERSION 1.0.0)
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} ${CMAKE_CURRENT_SOURCE_DIR}/cmake)
set(SDL2_PATH "E:\\Code\\SDL2")
set(SDL2_IMAGE_PATH "E:\\Code\\SDL2")
set(SDL2_TTF_PATH "E:\\Code\\SDL2")
find_package(SDL2 REQUIRED)
find_package(SDL2_image REQUIRED)
find_package(SDL2_ttf REQUIRED)
include_directories(
${SDL2_INCLUDE_DIR}
${SDL2_IMAGE_INCLUDE_DIRS}
${SDL2_TTF_INCLUDE_DIR})
set(SOURCES
src/main.cpp
)
add_executable(${PROJECT_NAME} ${SOURCES})
target_link_libraries(
${PROJECT_NAME}
${SDL2_LIBRARY}
${SDL2_IMAGE_LIBRARIES}
${SDL2_TTF_LIBRARIES}
)
I use Visual Studio Build Tools 2019 Release - x86 kit for CMake and build it successfully with CMake extension. The error only appears when I run the program although my path is correct.

Related

Error : "SDL could not initialize! SDL_Error: dsp: No such audio device"

I'm currently working on a personnal project and I have an issue with SDL_mixer or Audio
I can compile without any problems but when I try to execute the program I got this error:
"SDL could not initialize! SDL_Error: dsp: No such audio device"
I'm compiling with cmake, this is my CMakeList.txt :
cmake_minimum_required(VERSION 3.0)
set(CMAKE_BUILD_TYPE Debug)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++14")
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/cmake/")
project(R-TYPE)
find_package(SDL2 REQUIRED)
find_package(SDL2_image REQUIRED)
find_package(SDL2_ttf REQUIRED)
find_package(SDL2_mixer REQUIRED)
include_directories(${SDL2_INCLUDE_DIRS} ${SDL2_IMAGE_INCLUDE_DIRS} ${SDL2_TTF_INCLUDE_DIRS} ${SDL2_MIXER_INCLUDE_DIRS})
add_executable(
R-TYPE
main.cpp
Render/renderWindow.cpp
Menu/menu.cpp
)
target_link_libraries(R-TYPE ${SDL2_LIBRARIES} ${SDL2_IMAGE_LIBRARIES} ${SDL2_TTF_LIBRARIES} ${SDL2_MIXER_LIBRARIES})
this is the function where I got the error from :
int main(int argc, char* args[])
{
if (SDL_Init(SDL_INIT_EVERYTHING) < 0)
{
std::cout << "SDL could not initialize! SDL_Error: " << SDL_GetError() << std::endl;
return 84;
}
RenderWindow window("R-TYPE", 1920, 1080);
while (gameRunning)
{
game(window);
}
window.cleanUp();
SDL_Quit();
TTF_Quit();
return 0;
}
I'm on UBUNTU, how can I fix this?
I already tried to install libasound2-dev libpulse-dev but that didn't work
This is caused by manually building SDL2 and/or SDL2_mixer (without having all required dependencies installed).
Installing them from apt instead fixes the issue. The self-built versions had to be purged from /usr/local.

SDL2 Clion executable unable to start correctly 0xc000007b

I'm trying to run the executable of my application made with CLion and I get the error 0xc000007b (STATUS_INVALID_IMAGE_FORMAT).
If I launch the program from CLion the application start normally without any error, the problem occurs only if I try to launch the EXE.
I use SDL2, SDL2_image and SDL2_ttf. I always had this problem with SDL.
Project structure:
./cmake-build-debug
/SDL2.dll, SDL2_image.dll, SDL2_ttf.dll
/myProgram.exe
./include
/SDL2/
/*.a
./lib
/SDL2/
/*.h
./src
/main.cpp
main.cpp:
#include <iostream>
#include <SDL.h>
#include <SDL_image.h>
#include <SDL_ttf.h>
int main(int argc, char** argv) {
SDL_Init(SDL_INIT_VIDEO);
SDL_Window *window = SDL_CreateWindow(
"GameEngine",
SDL_WINDOWPOS_UNDEFINED,
SDL_WINDOWPOS_UNDEFINED,
640,
480,
0
);
SDL_Renderer *renderer = SDL_CreateRenderer(window, -1, SDL_RENDERER_SOFTWARE);
SDL_SetRenderDrawColor(renderer, 0, 0, 0, SDL_ALPHA_OPAQUE);
SDL_RenderClear(renderer);
SDL_RenderPresent(renderer);
bool should_quit = false;
while (!should_quit) {
SDL_Event event;
while (SDL_PollEvent(&event)) {
switch (event.type) {
case SDL_QUIT:
should_quit = true;
break;
}
break;
}
}
SDL_DestroyWindow(window);
SDL_Quit();
return 0;
}
CMakeList.txt:
cmake_minimum_required(VERSION 3.21)
project(GameEngine)
set(CMAKE_CXX_STANDARD 20)
set(SDL2_INCLUDE_DIR ${CMAKE_SOURCE_DIR}/include/SDL2)
set(SDL2_LIB_DIR ${CMAKE_SOURCE_DIR}/lib/SDL2)
include_directories(${SDL2_INCLUDE_DIR})
link_directories(${SDL2_LIB_DIR})
file(GLOB_RECURSE SOURCES
${PROJECT_SOURCE_DIR}/src/*.cpp
)
add_executable(${PROJECT_NAME} ${SOURCES})
target_link_libraries(${PROJECT_NAME} mingw32 SDL2main SDL2 SDL2_image SDL2_ttf)

CLion, SDL2, CMake: No available video device

I am trying to start using SDL2 (with CLion as my IDE), but I'm running into errors. I'm on Pop!_OS 19.10 (based on ubuntu)
Here are the relevant project files:
CMakeLists.txt
cmake_minimum_required(VERSION 3.13)
project(sdlpractice)
set(CMAKE_CXX_STANDARD 20)
find_package(SDL2 REQUIRED)
include_directories(${SDL2_INCLUDE_DIRS})
add_executable(sdlpractice main.cpp)
target_link_libraries(sdlpractice ${SDL2_LIBRARIES})
Main.cpp
#include "SDL2/SDL.h"
#include "stdio.h"
const int SCREEN_WIDTH = 640;
const int SCREEN_HEIGHT = 480;
int main(int argc, char* args[]) {
// The window we will be rendering to
SDL_Window * ptrWindow = NULL;
// The surface contained by the window
SDL_Surface * ptrScreenSurface = NULL;
// Initialize SDL
if (SDL_Init(SDL_INIT_VIDEO) < 0) {
printf("SDL could not initialize! SDL_Error: %s\n", SDL_GetError());
} else {
// Create window
ptrWindow = SDL_CreateWindow("SDL Practice",
SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED,
SCREEN_WIDTH, SCREEN_HEIGHT, SDL_WINDOW_SHOWN);
if (ptrWindow == nullptr) {
printf("Window creation failed: %s\n", SDL_GetError());
}
// Get window surface
ptrScreenSurface = SDL_GetWindowSurface(ptrWindow);
// Fill the surface white
SDL_FillRect(ptrScreenSurface, NULL, SDL_MapRGB(ptrScreenSurface->format, 0xFF, 0xFF, 0xFF));
// Update the surface
SDL_UpdateWindowSurface(ptrWindow);
// Wait 2 seconds
SDL_Delay(2000);
// Destroy window, quit SDL subsystems
SDL_DestroyWindow(ptrWindow);
SDL_Quit();
return 0;
}
}
I get the following error:
SDL could not initialize! SDL_Error: No available video device
I have tried setting DISPLAY=:0.0 in CLion's run configurations. Same error results. Futhermore, I ran
echo $DISPLAY
:1
and tried using :1 as well, same error persists.
Removing /usr/local/bin/sdl2-config,/usr/local/include/SDL2 and /usr/local/lib/libSDL2* (as suggested by Botje) solved the problem due to the self-built version of SDL2 missing the required video headers.

SDL_image Can't load .png file with IMG_LoadTexture()

While trying to load a .png file with IMG_LoadTexture(renderer, "idle.png")
SDL_GetError() says: "Couldn't open idle.png"
There are no compiler errors, just a black window appears.
This is my main.cpp
#include <stdlib.h>
#include <SDL2/SDL.h>
#include <SDL2/SDL_image.h>
#include <iostream>
int main(int argc, char** argv) {
SDL_Event event;
SDL_Renderer *renderer = NULL;
SDL_Texture *texture = NULL;
SDL_Window *window = NULL;
SDL_Init(SDL_INIT_TIMER | SDL_INIT_VIDEO);
SDL_CreateWindowAndRenderer(
800, 600,
0, &window, &renderer
);
IMG_Init(IMG_INIT_PNG);
texture = IMG_LoadTexture(renderer, "idle.png");
std::cout << SDL_GetError();
while (1) {
SDL_RenderCopy(renderer, texture, NULL, NULL);
SDL_RenderPresent(renderer);
if (SDL_PollEvent(&event) && event.type == SDL_QUIT)
break;
}
SDL_DestroyTexture(texture);
IMG_Quit();
SDL_DestroyRenderer(renderer);
SDL_DestroyWindow(window);
SDL_Quit();
return EXIT_SUCCESS;
}
But I guess the problem is the way I link the library. I installed sdl2, sdl2_image and libpng.
CMakeLists.txt:
cmake_minimum_required(VERSION 3.12)
project(untitled)
set(CMAKE_CXX_STANDARD 17)
add_executable(untitled main.cpp)
INCLUDE(FindPkgConfig)
PKG_SEARCH_MODULE(SDL2 REQUIRED sdl2)
PKG_SEARCH_MODULE(SDL2IMAGE REQUIRED SDL2_image>=2.0.0)
INCLUDE_DIRECTORIES(${SDL2_INCLUDE_DIRS} ${SDL2IMAGE_INCLUDE_DIRS})
TARGET_LINK_LIBRARIES(untitled ${SDL2_LIBRARIES} ${SDL2IMAGE_LIBRARIES})
You are loading the image from the current working directory (CWD) of your application. That is not necessarily the same directory as your executable is in (it depends on how it is launched), which you seem to assume.
3 easy ways to fix:
change the cwd at runtime to where the file is and load as you do now.
provide an absolute path to the file when loading, so cwd is irrelevant.
obtain the path to the executable at runtime and then construct a path to the file relative to where the executable is. (best option in my opinion since it's robust against moving your project around/installing to a different location).

‘IMG_Load’ was not declared in this scope SDL 2

I'm trying to make an application with SDL and I would like to add an icon on my window but when I compile I get this error :
error: ‘IMG_Load’ was not declared in this scope
SDL_Surface * icon_surface = IMG_Load(icon);
^
I'am using cmake and make for the compilation, here is the CMakeLists.txt
cmake_minimum_required (VERSION 2.6)
set(PROJECT_NAME "Engine")
project (${PROJECT_NAME})
SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=c++0x")
if( CMAKE_SIZEOF_VOID_P EQUAL 8 )
MESSAGE( "64 bits compiler detected" )
SET( EX_PLATFORM 64 )
SET( EX_PLATFORM_NAME "x64" )
SET( EXECUTABLE_NAME ${PROJECT_NAME}-x64 )
else( CMAKE_SIZEOF_VOID_P EQUAL 8 )
MESSAGE( "32 bits compiler detected" )
SET( EX_PLATFORM 32 )
SET( EX_PLATFORM_NAME "x86" )
SET( EXECUTABLE_NAME ${PROJECT_NAME}-x86 )
endif( CMAKE_SIZEOF_VOID_P EQUAL 8 )
# The executable file will be generate in the bin/ directory
set(EXECUTABLE_OUTPUT_PATH bin/${CMAKE_BUILD_TYPE})
# All .h files are in the include/ directory
include_directories(
../include/
)
# All .cpp files are in the src/ directory
file(
GLOB_RECURSE
SOURCE_FILES
../src/*
)
add_executable(
${EXECUTABLE_NAME}
${HEADER_FILES}
${SOURCE_FILES}
)
target_link_libraries(
${EXECUTABLE_NAME}
GL
GLEW
SDL2
)
and here the main.cpp
#include <stdio.h>
#include <stdlib.h>
#include <GL/glew.h>
#include <SDL2/SDL.h>
#include <glm/glm.hpp>
using namespace glm;
using namespace std;
SDL_Window * CreateWindow(
const char * title,
int x,
int y,
int w,
int h,
Uint32 flags,
const char * icon
);
SDL_Renderer * CreateRenderer(
SDL_Window * window,
Uint32 flags,
int r,
int g,
int b
);
void Init(Uint32 flags);
int main(void)
{
Init(SDL_INIT_EVERYTHING);
SDL_Window * window = CreateWindow("Prism", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 800, 600, /*SDL_WINDOW_FULLSCREEN_DESKTOP*/ SDL_WINDOW_SHOWN | SDL_WINDOW_OPENGL, "../../assets/icon.png");
SDL_Renderer * renderer = CreateRenderer(window, SDL_RENDERER_ACCELERATED | SDL_RENDERER_PRESENTVSYNC, 0, 0, 0);
bool end = false;
SDL_Event events;
while(!end) {
SDL_WaitEvent(&events);
if(events.window.event == SDL_WINDOWEVENT_CLOSE)
end = true;
SDL_RenderClear(renderer); // On nettoie l'écran
SDL_RenderPresent(renderer); // Et on effectue le rendu
}
SDL_DestroyWindow(window);
SDL_Quit();
return(EXIT_SUCCESS);
}
void Init(Uint32 flags){
if(SDL_Init(flags) < 0){
printf("Erreur lors de l'initialisation de la SDL : %s\n", SDL_GetError());
exit(EXIT_FAILURE);
}
}
SDL_Window * CreateWindow(const char * title, int x, int y, int w, int h, Uint32 flags, const char * icon)
{
SDL_Window * window = SDL_CreateWindow(title, x, y, w, h, flags);
if(window == NULL){
printf("Erreur lors de la création de la fenêtre : %s\n", SDL_GetError());
exit(EXIT_FAILURE);
}
SDL_Surface * icon_surface = IMG_Load(icon);
if(icon_surface == NULL){
printf("Erreur lors de la récupération de l'icone : %s\n", SDL_GetError());
exit(EXIT_FAILURE);
}
SDL_SetWindowIcon(window, icon_surface);
SDL_FreeSurface(icon_surface);
SDL_ShowCursor(SDL_DISABLE);
return window;
}
SDL_Renderer * CreateRenderer(SDL_Window * window, Uint32 flags, int r, int g, int b)
{
SDL_Renderer * renderer = SDL_CreateRenderer(window, -1, flags);
if(renderer == NULL){
printf("Erreur lors de la création du renderer : %s\n", SDL_GetError());
exit(EXIT_FAILURE);
}
if(SDL_SetRenderDrawColor(renderer, r, g, b, 255) < 0){
printf("Erreur lors de la modification de la couleur de fond du renderer : %s\n", SDL_GetError());
exit(EXIT_FAILURE);
}
return renderer;
}
I tried to add SDL_image.h in the include directory but I get an error because the compiler isn't able to find the SDL.h specified in the SDL_image.h...
Thank you for your helps !
Hmm... not sure, but maybe try this?
#include <SDL2/SDL.h>
#include <SDL2/SDL_image.h>
Include both headers, in that order.
Aside from include <SDL2/SDL_image.h> as suggested by Justin Time, you would also have to supply the library (SDL2_image) to link against your executable in your cmake file, like so;
target_link_libraries(
${EXECUTABLE_NAME}
GL
GLEW
SDL2
SDL2_image
)
I just tested your code and it runs fine with above modification. Make sure your "../../assets/icon.png" is accessible to your executable. Hope that helps.
Ok
So I'm an idiot because I didn't install libsdl2-image-2.0-0... I looked at what you sent me Gestrong and I changed my CMakeList.txt to the following :
cmake_minimum_required (VERSION 2.6)
SET(PROJECT_NAME "Engine")
PROJECT(${PROJECT_NAME})
SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=c++0x")
INCLUDE(FindPkgConfig)
INCLUDE(FindOpenGL REQUIRED)
INCLUDE(FindGLEW REQUIRED)
INCLUDE(FindSDL REQUIRED)
PKG_SEARCH_MODULE(SDL2 REQUIRED sdl2)
PKG_SEARCH_MODULE(SDL2IMAGE REQUIRED SDL2_image)
INCLUDE_DIRECTORIES(${OPENGL_INCLUDE_DIR})
INCLUDE_DIRECTORIES(${GLEW_INCLUDE_DIR})
SET(EXECUTABLE_OUTPUT_PATH bin/)
INCLUDE_DIRECTORIES(../include/)
INCLUDE_DIRECTORIES(${SDL2_INCLUDE_DIRS})
INCLUDE_DIRECTORIES(${SDL2IMAGE_INCLUDE_DIRS})
FILE(
GLOB_RECURSE
SOURCE_FILES
../src/*
)
ADD_EXECUTABLE(
${PROJECT_NAME}
${SOURCE_FILES}
)
TARGET_LINK_LIBRARIES(
${PROJECT_NAME}
${SDL2_LIBRARIES}
${SDL2IMAGE_LIBRARIES}
${OPENGL_LIBRARIES}
${GLEW_LIBRARIES}
)
I added #include <SDL2/SDL_image.h> in my code and now it WORKS :) thank you !