I'm trying to run this code but it keeps giving me an error.
I copyed SDL2_image.lib in the debug folder but in vain.
I'm at the beggining of programming so please be patient.
Errors:
Error 1 error C3861: 'IMG_LoadTexture': identifier not found
Error 2 IntelliSense: identifier "IMG_LoadTexture" is undefined
#include<SDL/SDL.h>
#include<iostream>
using namespace std;
int main(int argc, char** argv)
{
bool quit = false;
//*Initializing Window;
SDL_Init(SDL_INIT_VIDEO);
SDL_Window* window = NULL;
window = SDL_CreateWindow("Game Test", 100, 100, 640, 480, SDL_WINDOW_SHOWN | SDL_WINDOW_RESIZABLE);
//*If game Crushes;
if (window == NULL)
{
cout << "The game window is not working";
}
//*Creating Update Function
SDL_Renderer* render = NULL;
render = SDL_CreateRenderer(window, -1, SDL_RENDERER_ACCELERATED);
SDL_Event* mainEvent = new SDL_Event();
//*End Update Function
//*Adding Textures;
SDL_Texture* grass_image = NULL;
grass_image = IMG_LoadTexture(render, "grass.bmp");
//*Creating a Sprite;
SDL_Rect grass_rect;
grass_rect.x = 10;
grass_rect.y = 50;
grass_rect.w = 250;
grass_rect.h = 250;
//*Content Of the Window;
while (!quit && mainEvent->type!=SDL_QUIT)
{
SDL_PollEvent(mainEvent);
SDL_RenderClear(render);
SDL_RenderCopy(render, grass_image, NULL, &grass_rect);
SDL_RenderPresent(render);
}
//*End Window Content
//*Memory Cleaning
SDL_DestroyWindow(window);
SDL_DestroyRenderer(render);
delete mainEvent;
//*End Memory Cleaning
return 0;
}
You are missing to include the header that contains the declaration of IMG_LoadTexture():
#include <SDL/SDL_image.h>
It's a separate extension library for SDL, and besides including that header, you'll also need to link that library with your project.
Related
A am trying to compile a simple bgfx program (from this link) and failing, because the window is not updating. Closing the window is fine, so i think the problem is in bgfx. I also tried other tutorials and those didn't work either
Code:
#include <stdio.h>
#include <bgfx/bgfx.h>
#include <bgfx/platform.h>
#include <SDL2/SDL.h>
#include <SDL2/SDL_syswm.h>
SDL_Window* window = NULL;
const int WIDTH = 640;
const int HEIGHT = 480;
int main (int argc, char* args[]) {
// Initialize SDL systems
if(SDL_Init( SDL_INIT_VIDEO ) < 0) {
printf("SDL could not initialize! SDL_Error: %s\n",
SDL_GetError());
}
else {
//Create a window
window = SDL_CreateWindow("BGFX Tutorial",
SDL_WINDOWPOS_UNDEFINED,
SDL_WINDOWPOS_UNDEFINED,
WIDTH, HEIGHT,
SDL_WINDOW_SHOWN);
if(window == NULL) {
printf("Window could not be created! SDL_Error: %s\n",
SDL_GetError());
}
}
// Collect information about the window from SDL
SDL_SysWMinfo wmi;
SDL_VERSION(&wmi.version);
if (!SDL_GetWindowWMInfo(window, &wmi)) {
return 1;
}
bgfx::PlatformData pd;
// and give the pointer to the window to pd
pd.ndt = wmi.info.x11.display;
pd.nwh = (void*)(uintptr_t)wmi.info.x11.window;
// Tell bgfx about the platform and window
bgfx::setPlatformData(pd);
// Render an empty frame
bgfx::renderFrame();
// Initialize bgfx
bgfx::init();
// Reset window
bgfx::reset(WIDTH, HEIGHT, BGFX_RESET_VSYNC);
// Enable debug text.
bgfx::setDebug(BGFX_DEBUG_TEXT /*| BGFX_DEBUG_STATS*/);
// Set view rectangle for 0th view
bgfx::setViewRect(0, 0, 0, uint16_t(WIDTH), uint16_t(HEIGHT));
// Clear the view rect
bgfx::setViewClear(0,
BGFX_CLEAR_COLOR | BGFX_CLEAR_DEPTH,
0x443355FF, 1.0f, 0);
// Set empty primitive on screen
bgfx::touch(0);
// Poll for events and wait till user closes window
bool quit = false;
SDL_Event currentEvent;
while(!quit) {
while(SDL_PollEvent(¤tEvent) != 0) {
if(currentEvent.type == SDL_QUIT) {
quit = true;
}
}
}
// Free up window
SDL_DestroyWindow(window);
// Shutdown SDL
SDL_Quit();
return 0;
}
Why is this happening, and how to fix it?
P.S.: I am using kali linux
I'm doing Lazy Foo's tutorial on SDL (I'm using SDL2-2.0.9), and at the texture rendering part I encountered the following problem: the program compiles and runs as expected, no issue here, but when I close the window, the console doesn't close and the process continues running, so I have to close the console separately.
When I tried to debug it, I found out that the program indeed leaves the main cycle and reaches the "return 0" line in the main function successfully, but then it just hangs like that until I close the console.
The issue is only present when I use the SDL renderer with any option other than SDL_RENDERER_SOFTWARE. If I use SDL_RENDERER_SOFTWARE - the program closes as expected. With other options it stays at "return 0" running other threads (crypt32.dll, ntdll.dll and nvd3dum, in this order in the thread view, meaning that the process is stuck in crypt32).
I'm aware that my main function is not the "real main" as it has been hijacked by SDL, so exit(0) works fine as an ad-hoc solution. But I want to know, why exactly does that happen and is there any other way to fix this, so that I don't have to use exit(0) ?
Here is an example (simplified) code, which demonstrates this issue for me:
#include "SDL.h"
#include <stdio.h>
int main(int argc, char *argv[]) {
SDL_Window *win = NULL;
SDL_Renderer *renderer = NULL;
SDL_Texture *bitmapTex = NULL;
SDL_Surface *bitmapSurface = NULL;
int width = 640, height = 480;
if (SDL_Init(SDL_INIT_VIDEO) < 0)
{
printf("Could not initialize SDL");
return 1;
}
win = SDL_CreateWindow("Hello World", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, width, height, 0);
renderer = SDL_CreateRenderer(win, -1, SDL_RENDERER_ACCELERATED);
bitmapSurface = SDL_LoadBMP("res/x.bmp");
bitmapTex = SDL_CreateTextureFromSurface(renderer, bitmapSurface);
SDL_FreeSurface(bitmapSurface);
bool quit = false;
while (!quit) {
SDL_Event e;
while (SDL_PollEvent(&e) != 0) {
if (e.type == SDL_QUIT) {
quit = true;
}
}
SDL_RenderClear(renderer);
SDL_RenderCopy(renderer, bitmapTex, NULL, NULL);
SDL_RenderPresent(renderer);
}
SDL_DestroyTexture(bitmapTex);
SDL_DestroyRenderer(renderer);
SDL_DestroyWindow(win);
SDL_Quit();
printf("REACHED RETURN 0");
return 0;
}
Works as intended, but after closing the window I see "REACHED RETURN 0" printed in console and that's it, the console stays there. The code can be simplified further, the issue will be present as long as there is an instance of SDL_Renderer created.
UPD: The callstack during the hanging:
> ntdll.dll!_NtWaitForMultipleObjects#20()
KernelBase.dll!_WaitForMultipleObjectsEx#20()
crypt32.dll!ILS_WaitForThreadProc()
kernel32.dll!#BaseThreadInitThunk#12()
ntdll.dll!__RtlUserThreadStart()
ntdll.dll!__RtlUserThreadStart#8()
UPD2: The problem is not with the loop at all, I created the simplest application where I just create a window and a renderer and then return 0, it still gives me a hanging console. Like this:
#include <SDL.h>
int main(int argc, char* args[])
{
if (SDL_Init(SDL_INIT_VIDEO) < 0) return 1;
SDL_Window* window = SDL_CreateWindow("Test", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, 640, 480, 0);
SDL_Renderer* renderer = SDL_CreateRenderer(window, -1, SDL_RENDERER_ACCELERATED);
return 0;
}
Same thing when I destroy them properly. The problem is in the renderer.
UPD3: Here is the Parallel Stack window during the "hanging". There is no "main" thread since I close it successfully, these are the threads which stop the program from closing properly. Other than that, it doesn't give me any understanding of the problem.
I have been trying to make a PNG image appear on-screen to my SDL window. I am using the Eclipse CDT. SDL.h and SDL_image.h both seem to have been correctly linked, in that the functions pop up with colour on the compiler. When I run my code, however, literally nothing happens. There are no errors in the compiler, no comments, nothing. The window doesn't appear. I would really appreciate if anyone could help me out on the matter.
Also, SDL has worked previously on my computer before (without using SDL_image) - in which I ran a particle simulation that worked perfectly fine.
My code:
#include <iostream>
#include "SDL.h"
#include "SDL_image.h"
using namespace std;
SDL_Window *m_window; //Window upon which the game will be displayed.
SDL_Renderer *m_renderer; //Renderer used to draw the objects on the window.
SDL_Texture *playerTex;
int SCREEN_WIDTH = 600;
int SCREEN_HEIGHT = 600;
int main(int argc, char* args[]) {
if (SDL_Init(SDL_INIT_VIDEO) < 0) {
cout << "Video init failed" << endl;
return 1;
}
//Creates the actual SDL-window and stores it in the m_window variable.
m_window = SDL_CreateWindow("Marko Beocanin SDD Project",
SDL_WINDOWPOS_UNDEFINED,
SDL_WINDOWPOS_UNDEFINED, SCREEN_WIDTH, SCREEN_HEIGHT,
SDL_WINDOW_FULLSCREEN);
//Error-checking method that determines if SDL could not create a window - returns false if unsuccessful.
if (m_window == NULL) {
cout << "Window Creation failed" << endl;
SDL_Quit();
IMG_Quit();
return 2;
}
//Creates an SDL-Renderer: a tool used to actually draw objects on the Window
m_renderer = SDL_CreateRenderer(m_window, -1, 0);
//Error-checking method that determines if SDL could not create a renderer - returns false if unsuccessful.
if (m_renderer == NULL) {
cout << "Renderer creation failed." << endl;
SDL_DestroyWindow(m_window);
SDL_Quit();
IMG_Quit();
return 3;
}
SDL_Surface *tmpSurface = IMG_Load("img.png");
playerTex = SDL_CreateTextureFromSurface(m_renderer, tmpSurface);
SDL_FreeSurface(tmpSurface);
SDL_RenderClear(m_renderer);
SDL_RenderCopy(m_renderer, playerTex, NULL, NULL);
SDL_RenderPresent(m_renderer);
SDL_Delay(2000);
SDL_DestroyWindow(m_window);
SDL_Quit();
IMG_Quit();
return 0;
}
The problem I had was a result of me using the wrong SDL_image library - I was using x64 instead of x86, which meant that it didn't throw an error per se, just didn't work properly!
i am currently reentering programming in C++ to write a small game. I am using Visual Studio 2017 and SDL2. I am following a series of tutorials to get into SDL. My problem seems to be related to me not entirely understanding the workings of pointers in c++. I am passing a pointer to a function as an argument and want to use it within this function as an argument to another function which returns a pointer to a SDL_Surface. Following my code:
init SDL:
SDL_Surface* init(SDL_Window *window)
{
SDL_Surface *screenSurface = nullptr;
if (SDL_Init(SDL_INIT_VIDEO) < 0)
{
printf("%s", "Error in init");
}
else
{
screenSurface = SDL_GetWindowSurface(window);
}
return screenSurface;
}
load bmp:
SDL_Surface* loadMedia(const char file[])
{
SDL_Surface *image = SDL_LoadBMP(file);
if (image == nullptr)
{
printf("%s", "Error in loadMedia");
}
return image;
}
main:
int main(int argc, char *argv[])
{
SDL_Window *window = SDL_CreateWindow("xyz", SDL_WINDOWPOS_UNDEFINED,
SDL_WINDOWPOS_UNDEFINED, SCREEN_WIDTH, SCREEN_HEIGHT, SDL_WINDOW_SHOWN);
SDL_Surface *screenSurface = init(window);
if (screenSurface == nullptr)
{
printf("%s", "surface is null");
}
SDL_Surface *image = loadMedia("resources/images/village.bmp");
SDL_BlitSurface(image, NULL, screenSurface, NULL);
SDL_UpdateWindowSurface(window);
SDL_Delay(1000);
SDL_FreeSurface(image);
image = nullptr;
SDL_DestroyWindow(window);
window = nullptr;
SDL_Quit();
return 0;
}
if i create
SDL_Window *window = SDL_CreateWindow("xyz",...)
as a global variable and initialize it within init(), everything works fine and screenSurface is initialized with a valid value. As soon as i do as it is in the code, pass the pointer window to init() to create the surface there and then return screenSurface, screenSurface = SDL_GetWindowSurface(window) returns null.
I have been programming mostly SAS and Java the last years and didnt touch c++ for several years, so im sure its just a minor misunderstanding on my side but i cannot figure out what it is.
Thx in advance :)
I'm trying to load a image("carnero.png") but when I use IMG_LoadTexture(), it returns null;
Game.h
#ifndef GAME_H_
#define GAME_H_
#include <SDL.h>
#include <SDL_image.h>
#include <windows.h>
class Game {
public:
Game();
~Game();
void run();
void initGraphics();
void gameLoop();
private:
SDL_Window* _window = nullptr;
SDL_Renderer* _renderer;
SDL_Surface* _surfaceBMP;
SDL_Texture* _textureScenario;
SDL_Texture* _textureCarnero;
SDL_Rect* _scenarioRect;
SDL_Rect* _carneroRect;
int _width;
int _height;
bool _running;
};
#endif /* SRC_GAME_H_ */
Game.cpp
#include "Game.h"
#include <iostream>
Game::Game(){
_running = true;
run();
}
Game::~Game(){
}
void Game::run(){
initGraphics();
gameLoop();
}
void Game::initGraphics(){
SDL_Init(SDL_INIT_VIDEO);
IMG_Init(IMG_INIT_PNG);
_window = SDL_CreateWindow("Carneiro", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 1024, 768, SDL_WINDOW_SHOWN);
if(_window == nullptr) exit(1);
_renderer = SDL_CreateRenderer(_window, -1, SDL_RENDERER_ACCELERATED);
_surfaceBMP = SDL_LoadBMP("textures/scenario.bmp");
_textureScenario = SDL_CreateTextureFromSurface(_renderer, _surfaceBMP);
SDL_FreeSurface(_surfaceBMP);
_textureCarnero = IMG_LoadTexture(_renderer, "/textures/carnero2.png");
if(_textureCarnero == nullptr) exit(1);
_scenarioRect->x = 0; _scenarioRect->w = 1024;
_scenarioRect->y = 0; _scenarioRect->h = 740;
_carneroRect->x = 20; _carneroRect->w = 150;
_carneroRect->y = 100; _carneroRect->h = 100;
}
void Game::gameLoop(){
while(_running){
Sleep(10);
SDL_Event evnt;
if(SDL_PollEvent(&evnt)){
switch(evnt.type){
case SDL_QUIT:
_running = false;
break;
}
}
SDL_RenderClear(_renderer);
SDL_RenderCopy(_renderer, _textureScenario, nullptr, _scenarioRect);
// SDL_QueryTexture(_textureCarnero, NULL, NULL, &_carneroRect->x, &_carneroRect->y);
SDL_RenderCopy(_renderer, _textureCarnero, nullptr, _carneroRect);
SDL_RenderPresent(_renderer);
}
SDL_DestroyTexture(_textureScenario);
SDL_DestroyTexture(_textureCarnero);
SDL_DestroyRenderer(_renderer);
SDL_DestroyWindow(_window);
SDL_Quit();
IMG_Quit();
}
This function returns null
_textureCarnero = IMG_LoadTexture(_renderer, "/textures/carnero2.png");
But when I use SDL_LoadBMP() to load the background it works. I tried putting my .png in other folders but it doesn't work either. I also tried to load my .png using IMG_LOAD() but i had no sucess.
Your path is incorrect. /textures/carnero2.png will search for a file in C:\textures\carnero2.png, or /textures/carnero2.png on unix.
You can solve this problem as follows:
Use full (absolute) path: C:\Program Files (x86)\MyGame\textures\carnero2.png, /usr/local/share/mygame/textures/carnero2.png
Add a dot ./textures/carnero2.png
Remove the slash: textures/carnero2.png.
The path to your input file is probably incorrect:
/textures/carnero2.png
should probably be
textures/carnero2.png
like in the previous (working) load command.
In the future, I suggest that you test for file existence before trying to load the file. So you can separate "file not found" errors from real format/corrupt file problems.