I've been following LazyFoo's tutorial for a while. But I haven't been able to get this to initialize a week a go. I went back to it recently, after error checking, I found it that the window initializes properly, but the images won't load. What is the reason for it?
#include "SDL/SDL.h"
#include <string>
//setting screen info
const int SCH=640;
const int SCW=480;
const int BBP=32;
const char* name = "TEHGAEM";
// sprite height and width
const int SPH=45;
const int SPW=45;
//initilize event
SDL_Event event;
//loading surfaces for screen, sprite, and temp sprite
SDL_Surface *screen=NULL;
SDL_Surface *sprite=NULL;
SDL_Surface *temp = NULL;
//making class for movable objects
class Player
{
private:
int x,y;
int xVel,yVel;
public:
Player();
void show();
void move();
void handle_input();
};
//initializing variables
Player::Player()
{
x=0;
y=0;
xVel=0;
yVel=0;
}
//intended to show player picture
void Player::show()
{
SDL_Rect pos;
pos.x=x;
pos.y=y;
SDL_BlitSurface(sprite, NULL, screen, &pos);
SDL_UpdateRects(screen, 1, &pos);
}
//setting input
void Player::handle_input()
{
if (event.type ==SDL_KEYDOWN)
{
switch (event.key.keysym.sym)
{
case SDLK_UP: yVel -= SPH /2; break;
case SDLK_DOWN: yVel += SPH /2; break;
case SDLK_LEFT: xVel -=SPW /2; break;
case SDLK_RIGHT: xVel +=SPW /2; break;
}
}
if (event.type == SDL_KEYUP)
{
switch(event.key.keysym.sym)
{
case SDLK_UP: yVel += SPH /2; break;
case SDLK_DOWN: yVel -= SPH /2; break;
case SDLK_LEFT: xVel +=SPW /2; break;
case SDLK_RIGHT: xVel -=SPW /2; break;
}
}
}
void Player::move()
{
x=+xVel;
y=+yVel;
if (x >= SCW)
{
x-10;
}
if (y >= SCH)
{
y-10;
}
}
//initializing program
bool init()
{
if (SDL_Init(SDL_INIT_EVERYTHING)==-1)
{
return false;
}
screen = SDL_SetVideoMode(SCH,SCW,BBP, SDL_SWSURFACE);
if (screen == NULL)
{
return false;
}
SDL_WM_SetCaption(name, NULL);
return true;
}
//loading images
bool somethings()
{
temp = SDL_LoadBMP("sprite.bmp");
if (temp == NULL)
{
return false;
}
sprite = SDL_DisplayFormat (temp);
if (sprite ==NULL)
{
return false;
}
SDL_FreeSurface(temp);
return true;
}
//clean up function
void clean()
{
SDL_FreeSurface(sprite);
SDL_Quit();
}
int main(int argc, char* args[])
{
Player P1;
bool quit;
if (init() == false)
{
return 1;
}
if (somethings() ==false)
{
return 1;
}
while (quit ==false)
{
while (SDL_PollEvent(&event))
{
P1.handle_input();
if (event.type == SDL_QUIT)
{
quit == true;
}
}
if (SDL_Flip(screen) ==-1)
{
return 1;
}
P1.move();
P1.show();
}
clean();
return 0;
}
This isn't completely related to your problem but the varible bool quit; isn't defined as true or false before the main while( quit == false ) { ... }loop. This could produce undefined while loop behavior.
int main(int argc, char* args[])
{
Player P1;
bool quit = false; // CHANGE THIS AND SEE WHAT HAPPENS
if (init() == false)
{
return 1;
}
if (somethings() ==false)
{
return 1;
}
while (quit ==false)
{
while (SDL_PollEvent(&event))
{
P1.handle_input();
if (event.type == SDL_QUIT)
{
quit == true;
}
}
if (SDL_Flip(screen) ==-1)
{
return 1;
}
P1.move();
P1.show();
}
clean();
return 0;
}
About the images not loading, step through your program with a debugger and watch your somethings()function and follow the variables temp and sprite.
Make sure your "sprite.bmp" file is located in the running directory of this program. I tested it and it works for me.
Also this has no effect:
if (x >= SCW)
{
x-10;
}
if (y >= SCH)
{
y-10;
}
You probably wanted to say x -= 10; and y -= 10;.
This makes your 'player' jump back to the original position immediately:
if (event.type == SDL_KEYUP)
{
switch(event.key.keysym.sym)
{
case SDLK_UP: yVel += SPH /2; break;
case SDLK_DOWN: yVel -= SPH /2; break;
case SDLK_LEFT: xVel +=SPW /2; break;
case SDLK_RIGHT: xVel -=SPW /2; break;
}
}
You probably only need to handle SDL_KEYDOWN event.
Hope that helps.
There are big chances that you aren't loading the bitmap. But anything that you are trying to print on the screen and wasn't loaded can terminate the app.
Related
Using sdl2 I managed to construct "soon-to-be-spaghetti" classes for a game. However when it came to using a function of a class I stumble upon this weirdness.
class Player{
public:
Player();
const SDL_Rect *getPositionPtr() const { return &position; }
const SDL_Rect * getClip(){ return &clip; }
void eventHandle(SDL_Event & e);
void move();
private:
SDL_Rect position;
SDL_Rect clip;
float velocity;
bool leftkeydown;
bool rightkeydown;
};
Player::Player(){
position = {100, 300, 64, 64};
clip = {0, 0, 64, 64};
velocity = 0.3;
leftkeydown = false;
rightkeydown = false;
}
void Player::eventHandle(SDL_Event & e){
if( e.type == SDL_KEYDOWN && e.key.repeat == 0 ){
switch( e.key.keysym.sym ){
case SDLK_a:
leftkeydown = true;
break;
case SDLK_d:
rightkeydown = true;
break;
}
}
else if( e.type == SDL_KEYUP && e.key.repeat == 0 ){
//Adjust the velocity
switch( e.key.keysym.sym ){
case SDLK_a:
leftkeydown = false;
break;
case SDLK_d:
rightkeydown = false;
break;
}
}
}
void Player::move(){
if(leftkeydown) position.x -= velocity;
if(rightkeydown) position.x += velocity; // <----- problem here
}
leftkeydown seems to work as expected but rightkeydown doesn't do anything to the position.x variable.
Any ideas why it is not incrementing?
as #keltar commended it happens because at int + (float < 0) the int stays the same because it converts the result (100.3) from float to int (100) (thats because one of the values is int) so the position x will stay the same unless you make the velocity int or bigger than 0.
I am trying to write a program which allows users to draw using the mouse. I have been trying many different ways to appropriately update the display using an object of sf::RenderWindow to call display() without much success. My loop where the drawing is occurring is calling display so fast it's causing massive flickering (confirmed that through testing). If I add a way to slow the call to display(), like using sf::Clock, then the drawing is only updated on the same delay as display() resulting in a stuttering effect. What I need is a way to update the display often enough to show drawing updates while also not causing a screen flicker.
Currently, I've got the display on a delay (at the bottom of the event polling switch statement) so flickering doesn't occur, but adding mainWindow.display(); to the void MainWindow::draw() function causes flickering as it updates too quickly. I had the drawing occurring on sf::Event::MouseMoved, but I tried changing it to see if that would help, and it did not.
Here's where all the drawing and event detection occurs:
MainWindow.h
#pragma once
#include "GraphPaper.h"
#include "stdafx.h"
class MainWindow
{
public:
MainWindow(short, short);
void close();
void start();
void moveCamera(sf::Keyboard::Key);
void draw(sf::Event);
void displayWindow(sf::Vector2i&);
private:
bool leftMousePressed, rightMousePressed, isExiting;
int r, g, b, mouseX, mouseY;
short height, width;
const short DRAWING_CRICLE_RADIUS = 10;
GraphPaper paper;
//DrawingBrush brush;
const sf::Color WHITE = sf::Color(255, 255, 255);
const sf::Color BLACK = sf::Color(0, 0, 0);
sf::CircleShape circle;
sf::Mouse cursor;
sf::Vector2i windowCenter;
sf::RenderWindow mainWindow;
sf::View view;
};
MainWindow.cpp:
#include "MainWindow.h"
#include "GraphPaper.h"
#include "stdafx.h"
MainWindow::MainWindow(short height, short width)
{
this->height = height;
this->width = width;
circle.setRadius(DRAWING_CRICLE_RADIUS);
circle.setFillColor(BLACK);
}
void MainWindow::start()
{
sf::Clock clock;
mainWindow.create(sf::VideoMode(height, width, 32), "Test");
sf::View view(sf::FloatRect(0,0,height,width));
mainWindow.setView(view);
leftMousePressed, rightMousePressed, isExiting = false;
sf::Event currentEvent;
sf::Vector2i windowCenter(mainWindow.getPosition().x + (mainWindow.getSize().x / 2), mainWindow.getPosition().y + (mainWindow.getSize().y / 2));
displayWindow(windowCenter);
while (!isExiting)
{
sf::Clock clock;
while (mainWindow.pollEvent(currentEvent))
{
switch (currentEvent.type)
{
case sf::Event::MouseMoved:
{
if (rightMousePressed == true)
{
std::cout << "Mouse Panned\n";
}
if (leftMousePressed == true)
{
draw(currentEvent);
}
break;
}
case sf::Event::MouseButtonPressed:
{
std::cout << "Mouse Pressed\n";
mouseX = currentEvent.mouseButton.x;
mouseY = currentEvent.mouseButton.y;
if (currentEvent.mouseButton.button == sf::Mouse::Left)
{
while (currentEvent.type != sf::Event::MouseButtonReleased)
{
std::cout << "Mouse is Drawing\n";
draw(currentEvent);
mainWindow.pollEvent(currentEvent);
}
}
else if (currentEvent.mouseButton.button == sf::Mouse::Right)
{
rightMousePressed = true;
}
break;
}
case sf::Event::MouseButtonReleased:
{
std::cout << "Mouse Released\n";
if (currentEvent.mouseButton.button == sf::Mouse::Left)
{
leftMousePressed = false;
}
else if(currentEvent.mouseButton.button == sf::Mouse::Right)
{
rightMousePressed = false;
}
break;
}
case sf::Event::KeyPressed:
{
sf::Keyboard::Key keyPressed = currentEvent.key.code;
if(keyPressed == sf::Keyboard::Escape)
{
close();
}
else if(keyPressed == sf::Keyboard::Left || sf::Keyboard::Right ||
sf::Keyboard::Down || sf::Keyboard::Up ||
sf::Keyboard::A || sf::Keyboard::S ||
sf::Keyboard::D || sf::Keyboard::W)
{
moveCamera(keyPressed);
displayWindow(windowCenter);
}
break;
}
case sf::Event::Closed:
{
close();
break;
}
case sf::Event::Resized:
{
windowCenter = sf::Vector2i(mainWindow.getPosition().x + (mainWindow.getSize().x / 2), mainWindow.getPosition().y + (mainWindow.getSize().y / 2));
displayWindow(windowCenter);
break;
}
}
if (clock.getElapsedTime().asMilliseconds() >= 500)
{
clock.restart();
mainWindow.display();
}
}
}
}
void MainWindow::moveCamera(sf::Keyboard::Key keyPressed)
{
view = mainWindow.getView();
switch (keyPressed)
{
case sf::Keyboard::A:
case sf::Keyboard::Left:
{
view.move(-50, 0);
break;
}
case sf::Keyboard::D:
case sf::Keyboard::Right:
{
view.move(50, 0);
break;
}
case sf::Keyboard::W:
case sf::Keyboard::Up:
{
view.move(0, 50);
break;
}
case sf::Keyboard::S:
case sf::Keyboard::Down:
{
view.move(0, -50);
break;
}
}
mainWindow.setView(view);
}
void MainWindow::draw(sf::Event mouse)
{
circle.setPosition(mainWindow.mapPixelToCoords(sf::Vector2i(mouse.mouseMove.x, mouse.mouseMove.y)));
mainWindow.draw(circle);
}
void MainWindow::close()
{
std::cout << "Closing...\n";
mainWindow.close();
isExiting = true;
}
void MainWindow::displayWindow(sf::Vector2i& windowCenter)
{
mainWindow.clear(WHITE);
mainWindow.draw(paper.getSprite());
mainWindow.display();
cursor.setPosition(windowCenter);
}
You are missing an important part of the rendering loop. You should draw all parts every loop iteration. Right now you are only drawing your circle when it's changed.
Your code should look like this:
change circle position based on input
clear window
draw circle
display
I'm making a simple top down 2D shooter, where you move with WASD and shoot in the direction you're looking at with space. I can move and shoot just fine, but I can't do them both at the same time. For example if I'm shooting and start moving, my character will stop shooting until I release and press space again, and if I then start moving in another direction I have to release and press space again.
Here's my main method:
int main(int argc, char* args[])
{
if (!init())
{
log("Failed to initialize!\n");
}
else
{
log("Initialized SDL and SDL subsystems. \nLoading assets:\n");
if (!loadAssets())
{
printf("Failed to load assets!\n");
}
else
{
log("All assets loaded successfully.\n");
bool running = true;
SDL_Event e;
std::vector<Shot> shots;
LTimer shotTimer;
float cooldown = 250.0f;
float previousCooldown = 0.0f;
Player player;
log("Game running.\n");
shotTimer.start();
while (running)
{
while (SDL_PollEvent(&e) != 0)
{
if (e.type == SDL_QUIT)
{
log("SDL_QUIT event triggered.\n");
running = false;
}
else if (e.type == SDL_KEYDOWN)
{
switch (e.key.keysym.sym)
{
case SDLK_ESCAPE:
{
running = false;
break;
}
}
}
player.handleEvent(e);
if (SDL_GetTicks() - previousCooldown > cooldown)
{
previousCooldown = SDL_GetTicks();
shots = shoot(e, player, shots);
}
}
player.move();
for (int i = 0; i < shots.size(); i++)
{
shots[i].move();
}
/*if (shotTimer.getTicks() >= cooldown)
shotTimer.restart();*/
SDL_SetRenderDrawColor(renderer, 0xff, 0xff, 0xff, 0xff);
SDL_RenderClear(renderer);
background.render(0, 0);
for (int i = 0; i < shots.size(); i++)
{
shots[i].render();
}
player.render();
SDL_RenderPresent(renderer);
}
}
}
close();
return 0;
}
Here's my shoot() function, which is probably what's causing this:
std::vector<Shot> shoot(SDL_Event& e, Player player, std::vector<Shot> shots)
{
bool shoot = false;
if (e.type = SDL_KEYDOWN && e.key.repeat == 1)
{
switch (e.key.keysym.sym)
{
case SDLK_SPACE:
{
shoot = true;
break;
}
}
}
else if (e.type = SDL_KEYUP && e.key.repeat == 1)
{
switch (e.key.keysym.sym)
{
case SDLK_SPACE:
{
shoot = false;
break;
}
}
}
if (shoot)
{
Shot newShot(player.getDir(), player);
shots.push_back(newShot);
}
return shots;
}
And this is how I move the player
void Player::handleEvent(SDL_Event& e)
{
if (e.type == SDL_KEYDOWN && e.key.repeat == 0)
{
switch (e.key.keysym.sym)
{
case SDLK_w: mVelY -= PLAYER_VEL; mDir = 0; break;
case SDLK_s: mVelY += PLAYER_VEL; mDir = 1; break;
case SDLK_d: mVelX += PLAYER_VEL; mDir = 2; break;
case SDLK_a: mVelX -= PLAYER_VEL; mDir = 3; break;
}
}
else if (e.type == SDL_KEYUP && e.key.repeat == 0)
{
switch (e.key.keysym.sym)
{
case SDLK_w: mVelY += PLAYER_VEL; break;
case SDLK_s: mVelY -= PLAYER_VEL; break;
case SDLK_d: mVelX -= PLAYER_VEL; break;
case SDLK_a: mVelX += PLAYER_VEL; break;
}
}
}
Separate your event polling from the rest of the game logic.
Poll all events once per frame in a separate function and store the state of the keystates into an array. Then, when you need the state, simply check the array.
You can also use SDL_GetKeyboardState to sample the surrent state of the keys, without having to handle the key events yourself.
I'm self learning programming using various online tutorials and a couple of books. Currently it's C++. I've done a bit of OpenGL and SDL in the last few days.
I have a small program that creates a wall to stop a small square from passing through it.
Here's my code:
//
// main.cpp
// SDL_Template
//
// The headers
#include <stdlib.h>
#include <string>
// SDL headers
#include <SDL/SDL.h>
#include "SDL_image/SDL_image.h"
//#include "SDL/SDL_ttf.h"
//#include "SDL/SDL_mixer.h"
// Other headers
#include <OpenGL/gl3.h>
// Screen attributes
const int SCREEN_WIDTH = 640;
const int SCREEN_HEIGHT = 480;
const int SCREEN_BPP = 32;
// The frame rate
const int FRAMES_PER_SECOND = 20;
// The attributes of the square
const int SQUARE_WIDTH = 20;
const int SQUARE_HEIGHT = 20;
// The surfaces
SDL_Surface *square = NULL;
SDL_Surface *screen = NULL;
// The event structure
SDL_Event event;
// The wall
SDL_Rect wall;
// The square
class Square
{
private:
// The collision box of the square
SDL_Rect box;
// The velocity of the square
int xVel, yVel;
public:
// Initializes the variables
Square();
// Takes key presses and adjusts the square's velocity
void handle_input();
// Moves the square
void move();
// Shows the square on the screen
void show();
};
//The timer
class Timer
{
private:
// The clock time when the timer started
int startTicks;
// The ticks stored when the timer was paused
int pausedTicks;
// The timer status
bool paused;
bool started;
public:
// Initializes variables
Timer();
// The various clock actions
void start();
void stop();
void pause();
void unpause();
// Gets the timer's time
int get_ticks();
// Checks the status of the timer
bool is_started();
bool is_paused();
};
SDL_Surface *load_image(std::string filename)
{
// The image that's loaded
SDL_Surface* loadedImage = NULL;
// The optimized surface that will be used
SDL_Surface* optimizedImage = NULL;
// Load the image
loadedImage = IMG_Load(filename.c_str());
// If the image loaded
if (loadedImage != NULL)
{
// Create an optimized surface
optimizedImage = SDL_DisplayFormat(loadedImage);
// Free the old surface
SDL_FreeSurface(loadedImage);
// If the surface was optimized
if (optimizedImage != NULL)
{
// Color key surface
SDL_SetColorKey(optimizedImage, SDL_SRCCOLORKEY, SDL_MapRGB(optimizedImage->format, 0, 0xFF, 0xFF));
}
}
// Return the optimized surface
return optimizedImage;
}
void apply_surface(int x, int y, SDL_Surface* source, SDL_Surface* destination, SDL_Rect* clip = NULL)
{
// Holds offsets
SDL_Rect offset;
// Get offsets
offset.x = x;
offset.y = y;
// Blit
SDL_BlitSurface(source, clip, destination, &offset);
}
bool check_collision(SDL_Rect A, SDL_Rect B)
{
// The sides of the rectangles
int leftA, leftB;
int rightA, rightB;
int topA, topB;
int bottomA, bottomB;
// Calculate the sides of rect A
leftA = A.x;
rightA = A.x + A.w;
topA = A.y;
bottomA = A.y + A.h;
// Calculate the sides of rect B
leftB = B.x;
rightB = B.x + B.w;
topB = B.y;
bottomB = B.y + B.h;
// If any of the sides from A are outside of B
if( bottomA <= topB )
{
return false;
}
if( topA >= bottomB )
{
return false;
}
if( rightA <= leftB )
{
return false;
}
if( leftA >= rightB )
{
return false;
}
// If none of the sides from A are outside B
return true;
}
bool init()
{
// Initialize all SDL subsystems
if (SDL_Init( SDL_INIT_EVERYTHING ) == -1)
{
return false;
}
// Set up the screen
screen = SDL_SetVideoMode(SCREEN_WIDTH, SCREEN_HEIGHT, SCREEN_BPP, SDL_SWSURFACE);
// If there was an error in setting up the screen
if (screen == NULL)
{
return false;
}
// Set the window caption
SDL_WM_SetCaption("Move the Square", NULL);
// If everything initialized fine
return true;
}
bool load_files()
{
// Load the square image
square = load_image("square.bmp");
// If there was a problem in loading the square
if (square == NULL)
{
return false;
}
// If everything loaded fine
return true;
}
void clean_up()
{
// Free the surface
SDL_FreeSurface(square);
// Quit SDL
SDL_Quit();
}
Square::Square()
{
// Initialize the offsets
box.x = 0;
box.y = 0;
// Set the square's dimentions
box.w = SQUARE_WIDTH;
box.h = SQUARE_HEIGHT;
// Initialize the velocity
xVel = 0;
yVel = 0;
}
void Square::handle_input()
{
// If a key was pressed
if (event.type == SDL_KEYDOWN)
{
//Adjust the velocity
switch (event.key.keysym.sym)
{
case SDLK_UP: yVel -= SQUARE_HEIGHT / 2; break;
case SDLK_DOWN: yVel += SQUARE_HEIGHT / 2; break;
case SDLK_LEFT: xVel -= SQUARE_WIDTH / 2; break;
case SDLK_RIGHT: xVel += SQUARE_WIDTH / 2; break;
}
}
// If a key was released
else if (event.type == SDL_KEYUP)
{
//Adjust the velocity
switch (event.key.keysym.sym)
{
case SDLK_UP: yVel += SQUARE_HEIGHT / 2; break;
case SDLK_DOWN: yVel -= SQUARE_HEIGHT / 2; break;
case SDLK_LEFT: xVel += SQUARE_WIDTH / 2; break;
case SDLK_RIGHT: xVel -= SQUARE_WIDTH / 2; break;
}
}
}
void Square::move()
{
// Move the square left or right
box.x += xVel;
// If the square went too far to the left or right or has collided with the wall
if (( box.x < 0 ) || ( box.x + SQUARE_WIDTH > SCREEN_WIDTH ) || ( check_collision(box, wall)))
{
// Move back
box.x -= xVel;
}
// Move the square up or down
box.y += yVel;
// If the square went too far up or down or has collided with the wall
if (( box.y < 0 ) || ( box.y + SQUARE_HEIGHT > SCREEN_HEIGHT) || (check_collision(box, wall)))
{
// Move back
box.y -= yVel;
}
}
void Square::show()
{
// Show the square
apply_surface(box.x, box.y, square, screen);
}
Timer::Timer()
{
// Initialize the variables
startTicks = 0;
pausedTicks = 0;
paused = false;
started = false;
}
void Timer::start()
{
// Start the timer
started = true;
// Unpause the timer
paused = false;
// Get the current clock time
startTicks = SDL_GetTicks();
}
void Timer::stop()
{
// Stop the timer
started = false;
// Unpause the timer
paused = false;
}
void Timer::pause()
{
// If the timer is running and isn't already paused
if ((started == true) && (paused == false))
{
// Pause the timer
paused = true;
// Calculate the paused ticks
pausedTicks = SDL_GetTicks() - startTicks;
}
}
void Timer::unpause()
{
// If the timer is paused
if (paused == true)
{
// Unpause the timer
paused = false;
// Reset the starting ticks
startTicks = SDL_GetTicks() - pausedTicks;
// Reset the paused ticks
pausedTicks = 0;
}
}
int Timer::get_ticks()
{
// If the timer is running
if (started == true)
{
// If the timer is paused
if (paused == true)
{
// Return the number of ticks when the timer was paused
return pausedTicks;
}
else
{
// Return the current time minus the start time
return SDL_GetTicks() - startTicks;
}
}
// If the timer isn't running
return 0;
}
bool Timer::is_started()
{
return started;
}
bool Timer::is_paused()
{
return paused;
}
int main(int argc, char* args[])
{
// Quit flag
bool quit = false;
// The square
Square mySquare;
// The frame rate regulator
Timer fps;
// Initialize
if( init() == false )
{
return 1;
}
// Load the files
if (load_files() == false)
{
return 1;
}
// Set the wall
wall.x = 300;
wall.y = 40;
wall.w = 40;
wall.h = 400;
// While the user hasn't quit
while (quit == false)
{
// Start the frame timer
fps.start();
// While there are events to handle
while (SDL_PollEvent(&event))
{
// Handle events for the square
mySquare.handle_input();
// If the user has Xed out the window
if (event.type == SDL_QUIT)
{
// Quit the program
quit = true;
}
}
// Move the square
mySquare.move();
// Fill the screen white
SDL_FillRect(screen, &screen->clip_rect, SDL_MapRGB(screen->format, 0xFF, 0xFF, 0xFF));
// Show the wall
SDL_FillRect (screen, &wall, SDL_MapRGB(screen->format, 0x77, 0x77, 0x77));
// Show the square on the screen
mySquare.show();
// Update the screen
if (SDL_Flip(screen) == -1)
{
return 1;
}
// Cap the frame rate
if (fps.get_ticks() < 1000 / FRAMES_PER_SECOND)
{
SDL_Delay((1000 / FRAMES_PER_SECOND) - fps.get_ticks());
}
}
// Clean up
clean_up();
return 0;
}
I completely understand how this site works, so I'm not asking you to check my code. My code compiles in both Xcode 4.5 and Visual Studio 2010. In Xcode it compiles, but throws some warnings up (although it still builds), but nothing happens when it's run. However in Visual Studio 2012, it compiles, with no warnings and runs successfully.
I have searched here and the C++/SDL forums/help pages, but I haven't found any similar cases.
Why may this be? Seems it runs in Visual Studio 2010, I'm confident it isn't the code...
In case you were wondering the warnings flagged up in Xcode are:
229 enumeration values not handled in switch: 'SDLK_UNKNOWN','SDLK_BACKSPACE','SDLK_TAB'...
This is highlighted on the switch (event.key.keysym.sym) line of code.
So my questions are:
What kind of problems could case this warning error?
Are there any commonly know issues with programs working in Visual Studio and not Xcode?
I'm guessing (it seems I can't find anything about it) it's a setting somewhere that I haven't spotted...
I apologise for the length of this.
You are not handling all the possible choices in your switch statement. If this is what you intended then you can remove the warning by using the default case like the following:
switch (event.key.keysym.sym)
{
case SDLK_UP: yVel -= SQUARE_HEIGHT / 2; break;
case SDLK_DOWN: yVel += SQUARE_HEIGHT / 2; break;
case SDLK_LEFT: xVel -= SQUARE_WIDTH / 2; break;
case SDLK_RIGHT: xVel += SQUARE_WIDTH / 2; break;
default: break;
}
Xcode is simply warning you that you are not handling all possible values for the event.key.keysym.sym enumeration. Since I doubt you want to handle ever single different type of key press, this isn't a problem, as I would maybe see if I could turn down the warning level to suppress these warnings.
As for the program not running successfully when built by Xcode, I don't know. Perhaps SDL is set up in a different way?
I am trying to catch the event for F1 key in SDL in C++.
But,somehow i cannot see any changes after pressing the F1 key.But,when i wnat to toggle my animation objects on the screen i make use SDL_t case to do so,and it is executing fine.
Just not geting why is it not taking the F1 key.
Here is the switch case for handling key press events:
SDL_Event event;
bool done = false;
bool keyPress = false;
while ( not done ) {
draw();
SDL_Flip(screen);
SDL_PollEvent(&event);
if (event.type == SDL_QUIT) { break; }
if(event.type == SDL_KEYUP) { keyCatch = false; }
if(event.type == SDL_KEYDOWN) {
switch ( event.key.keysym.sym ) {
case SDLK_ESCAPE : done = true; break;
case SDLK_q : done = true; break;
case SDLK_F1 : {
if(!keyCatch){
keyPress=true;
//this method is from another class.
io.printMessageAt("F1 is selected:",50,10);
currentOrb = (currentOrb+1) % orbs.size();
}
break;
}
case SDLK_t : case SDLK_SPACE :
if ( !keyPress ) {
//something
}
break;
case SDLK_p : {
if (!keyPress) {
keyPress = true;
//something
}
break;
}
default : break;
}
}
}
NOTE: i cannot give the entire code here.The above is my part what i am trying to do.
Double-check that your window manager or a hotkey daemon isn't consuming your F1's before they hit your process.
This works fine (F1 closes the program) on my system:
#include <SDL.h>
int main( int, char** )
{
SDL_Init(SDL_INIT_EVERYTHING);
SDL_Surface* screen = SDL_SetVideoMode(640, 480, 32, SDL_ANYFORMAT);
SDL_Event event;
bool done = false;
bool keyPress = false;
while ( !done )
{
SDL_Flip(screen);
SDL_PollEvent(&event);
if(event.type == SDL_QUIT)
{
break;
}
if(event.type == SDL_KEYUP)
{
keyPress = false;
}
if(event.type == SDL_KEYDOWN)
{
switch ( event.key.keysym.sym )
{
case SDLK_ESCAPE:
case SDLK_q:
done = true;
break;
case SDLK_F1:
if(!keyPress)
{
keyPress=true;
done = true;
}
break;
case SDLK_t:
case SDLK_SPACE:
if ( !keyPress )
{
//something
}
break;
case SDLK_p:
if (!keyPress)
{
keyPress = true;
//something
}
break;
default:
break;
}
}
}
SDL_Quit();
return 0;
}
I did notice that keyCatch was undefined. I replaced it with keyPress.