c++ - sdl2 - main.cpp:(. text+0x5f): referencia indefinida a
sdl2 2.0 8 zip (2)
Intento recopilar algunos ejercicios de una guía SDL.
Compilo de esta manera:
g++ -o main main.cpp -I/usr/local/include/SDL2 -L/usr/local/lib -lSDL2
y entiendo esto:
/tmp/cci2rYNF.o: In function `main'':
main.cpp:(.text+0x5f): undefined reference to `Game::init(char const*, int, int, int, int, int)''
collect2: error: ld returned 1 exit status
y mi código es:
main.cpp
#include "Game.h"
// our Game object
Game* g_game = 0;
int main(int argc, char* argv[])
{
g_game = new Game();
g_game->init("Chapter 1", 100, 100, 640, 480, 0);
while(g_game->running())
{
g_game->handleEvents();
g_game->update();
g_game->render();
}
g_game->clean();
return 0;
}
Game.h
#ifndef __Game__
#define __Game__
#include <SDL.h>
class Game
{
public:
Game() {}
~Game() {}
bool init(const char* title, int xpos, int ypos, int width, int height, int flags);
void render(){}
void update(){}
void handleEvents(){}
void clean(){}
// a function to access the private running variable
bool running() { return m_bRunning; }
private:
SDL_Window* m_pWindow;
SDL_Renderer* m_pRenderer;
bool m_bRunning;
};
#endif // defined(__Game__) */
Game.cpp
#include "Game.h"
bool Game::init(const char* title, int xpos, int ypos, int width, int height, int flags)
{
// attempt to initialize SDL
if(SDL_Init(SDL_INIT_EVERYTHING) == 0)
{
std::cout << "SDL init success/n";
// init the window
m_pWindow = SDL_CreateWindow(title, xpos, ypos,
width, height, flags);
if(m_pWindow != 0) // window init success
{
std::cout << "window creation success/n";
m_pRenderer = SDL_CreateRenderer(m_pWindow, -1, 0);
if(m_pRenderer != 0) // renderer init success
{
std::cout << "renderer creation success/n";
SDL_SetRenderDrawColor(m_pRenderer,
255,255,255,255);
}
else
{
std::cout << "renderer init fail/n";
return false; // renderer init fail
}
}
else
{
std::cout << "window init fail/n";
return false; // window init fail
}
}
else
{
std::cout << "SDL init fail/n";
return false; // SDL init fail
}
std::cout << "init success/n";
m_bRunning = true; // everything inited successfully, start main loop
return true;
}
void Game::render()
{
SDL_RenderClear(m_pRenderer); // clear the renderer to the draw color
SDL_RenderPresent(m_pRenderer); // draw to the screen
}
void Game::clean()
{
std::cout << "cleaning game/n";
SDL_DestroyWindow(m_pWindow);
SDL_DestroyRenderer(m_pRenderer);
SDL_Quit();
}
void Game::handleEvents()
{
SDL_Event event;
if(SDL_PollEvent(&event))
{
switch (event.type)
{
case SDL_QUIT:
m_bRunning = false;
break;
default:
break;
}
}
}
C y C ++ tienen el concepto de una "unidad de compilación", este es el archivo fuente con el que se invocó el compilador y todo el código que #include
.
GCC, MSVC y la mayoría de los demás compiladores generarán un "archivo objeto" intermedio (.o o .obj) para cada unidad de compilación. Estos deben combinarse juntos, junto con cualquier biblioteca, para formar el ejecutable final, en un paso denominado "vincular".
Con GCC hay algunas formas de hacerlo. Un solo comando:
g++ -o app.exe file1.cpp file2.cpp
Esto compila file1.cpp y file2.cpp por separado (cada uno sigue siendo una sola unidad de compilación) para objetos de archivos y luego vincula los archivos de objetos resultantes a un ejecutable llamado "app.exe" (no necesita la extensión .exe, I estoy usándolo para mayor claridad)
O múltiples comandos:
g++ -o file1.o -c file1.cpp
g++ -o file2.o -c file2.cpp
g++ -o app.exe file1.o file2.o
Esto realiza el paso de compilación en cada cpp individualmente y luego realiza un paso de enlace por separado con ''g ++'' actuando como un front-end para cada paso. Observe la -c
en las primeras dos líneas, que le dice que desea compilar la fuente C / C ++ a .object. La tercera línea, el front-end del compilador reconoce que le está pidiendo que compile archivos de objetos, y se da cuenta de que quiere hacer el paso de enlace.
El primer método es a menudo más fácil para proyectos pequeños, el segundo método es útil cuando se utiliza cualquier tipo de sistema de compilación y las cosas comienzan a complicarse.
No estás compilando Game.cpp
. Tratar:
g++ -o main main.cpp Game.cpp -I/usr/local/include/SDL2 -L/usr/local/lib -lSDL2
El problema es que, aunque #include
Game.h
en main.cpp
, hace referencia a las funciones definidas en Game.cpp
. Sin compilar eso también, el enlazador no tiene las definiciones requeridas para hacer un ejecutable.