SDL_key

Started by
11 comments, last by rip-off 14 years, 2 months ago
Hi! My first post here. I have a problem with toggling sound on and off (game pause aswell). This is a part of the game loop, the only part that i can't get to work. Game checks if the 's' button is pressed and then, if snd is true, sets it to false (sound is on, make it off) and tells surface msgsnd to tell it's now off, and the other way around. Now i know, that it just runs them both at the same time, so it's ending with sound on all the time, but how can i make it that when i press it once it turns it on, when i press it again, it turns off. Atm the sound is just a bool, nothing more. The same goes with the pause game. Rightnow i've got to use 'up' for entering and 'down' for exitting pause. I can't use 'space' for both. I would appreciate any kind of help, here's the part of code:
Quote:while( SDL_PollEvent( &event ) ) { if( event.type == SDL_KEYDOWN) { if( event.key.keysym.sym == SDLK_s ) { if (snd == true) { snd = false; msgsnd = TTF_RenderText_Solid( font2, "SOUND: OFF", textColor ); } if (snd == false) { snd = true; msgsnd = TTF_RenderText_Solid( font2, "SOUND: ON", textColor ); } } } }
Advertisement
You could fix this by changing:
if (snd == false)
to:
else if (snd == false)
Check this out.

However, a better solution would be something like:

if( event.key.keysym.sym == SDLK_s ){    snd = !snd; // toggle snd    msgsnd = TTF_RenderText_Solid( font2, snd ? "SOUND: ON" : "SOUND: OFF", textColor ); // is this really the best place to render this string?}
if (snd == true){   snd = false;   msgsnd = TTF_RenderText_Solid( font2, "SOUND: OFF", textColor );}if(snd == false){   snd = true;   msgsnd = TTF_RenderText_Solid( font2, "SOUND: ON", textColor );}

Your code is equivalent to:
if (snd == true){   msgsnd = TTF_RenderText_Solid( font2, "SOUND: OFF", textColor );}snd = true;msgsnd = TTF_RenderText_Solid( font2, "SOUND: ON", textColor );

Try using if...else... to express such conditions. Also, you should probably be de-allocating the original msgsnd surface, or else you will leak memory.
SDL_FreeSurface(soundMessage);if(sound){    sound = false;    soundMessage = TTF_RenderText_Solid( font2, "SOUND: OFF", textColor );}else{    sound = true;    soundMessage = TTF_RenderText_Solid( font2, "SOUND: ON", textColor );}

Note that you should avoid compressing your variable names, it makes your code harder to read.
With this code:
if (snd == true){    snd = false;    msgsnd = TTF_RenderText_Solid( font2, "SOUND: OFF", textColor );}if (snd == false){    snd = true;    msgsnd = TTF_RenderText_Solid( font2, "SOUND: ON", textColor );}
If snd is true, it will be set to false, but then of course the next block of code will be executed immediately and it'll be set back to true, which isn't what you want. You can fix the problem by using an if-else statement (rather than two consecutive 'if' statements). You could also toggle the 'snd' variable like this:
snd = !snd;
And then set the message text as appropriate depending on the new value of 'snd'.

[Too slow...]
Thanks for all the replies, i just added 'else'. Didnt seem to think of it myself.
Quote:Also, you should probably be de-allocating the original msgsnd surface, or else you will leak memory.

What do you mean by that?
Every time you call TTF_RenderText_*(), memory is allocated. If you don't free it, your program will consume more and more memory over time. This will cause it to slow down or crash if it is a long running process (imagine a game server running 24/7). This is why I included a call to "SDL_FreeSurface()" in my example.
I am too slow typing. I just had to delete my whole post since it's already been said....

One important thing to note: if SDL_EnableKeyRepeat is enabled, then you will have repeating key down events, thus toggling snd back and forth while the key is pressed.

And the other nit-pick is:
if ( snd ){    ...}if ( !snd ){    ...}


is easier to read than:
if ( snd == true ){    ...}if ( snd == false ){    ...}
This is what i'm making - http://yy.lv/upload/index.php?ACT=4&f=108708&ext=RAR
SPACE - pause
Mouse controls player 1
1 - beginner AI
2 - expert AI
r - reset
s - sound

When the game is in pause mode (basically it's a 'while(...)' loop) sound button works nicely, but when it's in the main loop it act's like it's held down.
And i can't get out of pause mode by tapping space again.
Everything else seems to work nicely.
We'll need to see some code to be able to diagnose that. Could you post the event handling code in question?

Use [source]..[/source] tags to keep it tidy.
I'm latvian, so some ofthe variables are in latvian aswell.
This is the main loop:

int loop(){	while(!quit)       {           while( SDL_PollEvent( &event ) )           {			       			}            SDL_Delay(1);            if( event.type == SDL_KEYDOWN )			{                         if( event.key.keysym.sym == SDLK_s )                         {                             if (snd)                             {                              snd = false;                              msgsnd = TTF_RenderText_Solid( font2,  "SOUND: OFF", textColor );                             }                             else if (!snd)                             {                              snd = true;                              msgsnd = TTF_RenderText_Solid( font2,  "SOUND: ON", textColor );                             }                         }           }	            if (sp2lvl == 1)			   {                   vsp2 = 0.30;                   msglvl = TTF_RenderText_Solid( font2,  "BEGINNER", textColor );                }                if (sp2lvl == 2)                {                       vsp2 = 0.40;                       msglvl = TTF_RenderText_Solid( font2,  "EXPERT", textColor );                }                if (snd)                {                           msgsnd = TTF_RenderText_Solid( font2,  "SOUND: ON", textColor );                }                if (!snd)                {                           msgsnd = TTF_RenderText_Solid( font2,  "SOUND: OFF", textColor );                }				ball_fizika();				Speletaji_fizika();				Punkti();				Speletaji();                SDL_FillRect(screen , NULL , 0x38A2CF);				apply_surface( 318, 0, middle, screen );				apply_surface( 0, 0, side1, screen );				apply_surface( 0, 394, side2, screen );				apply_surface( xball, yball, ball, screen );				apply_surface( xsp1, ysp1, SP1, screen );				apply_surface( xsp2, ysp2, SP2, screen );				if (Points1 <= 9)				{				 apply_surface( SCREEN_WIDTH/2-19, 2, msgPoints1, screen );                }                if (Points1 > 9)                {                   apply_surface( SCREEN_WIDTH/2-28, 2, msgPoints1, screen );                }                if (Points1 > 99)                {                   apply_surface( SCREEN_WIDTH/2-53, 2, msgPoints1, screen );                }                if (Points2 <= 9)				{				 apply_surface( SCREEN_WIDTH/2+5, 2, msgPoints2, screen );                }                if (Points2 > 9)                {                   apply_surface( SCREEN_WIDTH/2+5, 2, msgPoints2, screen );                }				apply_surface( 2, 3, msglvl, screen );				apply_surface( 2, 13, msgsnd, screen );				apply_surface( 0, SCREEN_HEIGHT-20, msgcredits, screen );				if( event.type == SDL_KEYDOWN )					{						switch( event.key.keysym.sym )					{						case SDLK_SPACE: pauze(); bpauze = true;  break;						case SDLK_q: quit = true; break;						case SDLK_ESCAPE: quit = true; break;						case SDLK_2: sp2lvl = 2; break;						case SDLK_1: sp2lvl = 1; break;						case SDLK_r: greset(); reset = true; break;					}				}                    if( SDL_Flip( screen ) == -1 )                {                return 1;                    }                if( event.type == SDL_QUIT )				{                quit = true;				}       }}

This is pause loop:
void pauze(){     while( bpauze == true )       {            msgPauze = TTF_RenderText_Solid( font,  "PAUSE", textColor );            msginstr4 = TTF_RenderText_Solid( font2,  "S: SOUND", textColor );            msginstr3 = TTF_RenderText_Solid( font2,  "R: RESET", textColor );	        msginstr2 = TTF_RenderText_Solid( font2,  "2: EXPERT", textColor );	        msginstr1 = TTF_RenderText_Solid( font2,  "1: BEGINNER", textColor );	        SDL_FillRect(screen , NULL , 0x38A2CF);	        apply_surface( SCREEN_WIDTH/2+4, SCREEN_HEIGHT/2, msgPauze, screen );            apply_surface( SCREEN_WIDTH/2+4, SCREEN_HEIGHT/2-9, msginstr1, screen );            apply_surface( SCREEN_WIDTH/2+4, SCREEN_HEIGHT/2-8-12, msginstr2, screen );            apply_surface( SCREEN_WIDTH/2+4, SCREEN_HEIGHT/2-8-10-13, msginstr3, screen );            apply_surface( SCREEN_WIDTH/2+4, SCREEN_HEIGHT/2-8-10-10-14, msginstr4, screen );            apply_surface( 2, 3, msglvl, screen );				apply_surface( 318, 0, middle, screen );				apply_surface( 0, 0, side1, screen );				apply_surface( 0, 394, side2, screen );				apply_surface( xball, yball, ball, screen );				apply_surface( xsp1, ysp1, SP1, screen );				apply_surface( xsp2, ysp2, SP2, screen );				apply_surface( 2, 13, msgsnd, screen );				apply_surface( 0, SCREEN_HEIGHT-20, msgcredits, screen );				if (Points1 <= 9)				{				 apply_surface( SCREEN_WIDTH/2-19, 2, msgPoints1, screen );                }                if (Points1 > 9)                {                   apply_surface( SCREEN_WIDTH/2-28, 2, msgPoints1, screen );                }                if (Points1 > 99)                {                   apply_surface( SCREEN_WIDTH/2-53, 2, msgPoints1, screen );                }                if (Points2 <= 9)				{				 apply_surface( SCREEN_WIDTH/2+5, 2, msgPoints2, screen );                }                if (Points2 > 9)                {                   apply_surface( SCREEN_WIDTH/2+5, 2, msgPoints2, screen );                }				            SDL_Flip( screen );            while( SDL_PollEvent( &event ) )            {                   		           if( event.type == SDL_KEYDOWN)                   {                         if( event.key.keysym.sym == SDLK_SPACE )                         {                              bpauze = false;                              break;                         }                              if( event.key.keysym.sym == SDLK_r )                         {                              bpauze = false;                              reset = true;                              greset();                         }                         if( event.key.keysym.sym == SDLK_s )                         {                             if (snd)                             {                              snd = false;                              msgsnd = TTF_RenderText_Solid( font2,  "SOUND: OFF", textColor );                             }                             else if (!snd)                             {                             snd = true;                              msgsnd = TTF_RenderText_Solid( font2,  "SOUND: ON", textColor );                             }                         }                         if( event.key.keysym.sym == SDLK_1 )                         {                             sp2lvl = 1;                             msglvl = TTF_RenderText_Solid( font2,  "BEGINNER", textColor );                         }                         if( event.key.keysym.sym == SDLK_2 )                         {                             sp2lvl = 2;                             msglvl = TTF_RenderText_Solid( font2,  "EXPERT", textColor );                         }                                            }                                                         if( event.type == SDL_QUIT )		           {                    quit = true;                    bpauze = false;		           }            }       }      }

I know, that my code is a mess, but this is my first SDL game and one of the first c++ app's aswell. But i hope, you can help me.
The only problems I have, as I mentioned - is getting out of pause, without any problems and when i press 's' it doesn't act like it's being held down.

This topic is closed to new replies.

Advertisement