Variable not changing state despite being volatile - c++

I am checking for pressing of a switch(negative logic) inside the condition of a while loop. But the variable in which I store the input button press does not change state if I press the button. If I keep pressing the switch and reset the Arduino board, the press is recognized.
I tried making the variable volatile but I don't understand why it still don't work? I also tried to read from register instead of digitalRead but in vain.
volatile char ok_btn;
ok_btn= digitalRead(10);
while(ok_btn!=0)
{
Serial.println("ok button not pressed/n");
delay(200);
}
Serial.println("ok button pressed/n");
It seems the variable ok_btn is just reading once and storing it for ever!

You need to move the digitalread function inside the while loop.
If you are using a physical switch, you need to have some sort of debounce mechanism for the switch. Look at Simple Debounce Routine for some ideas.

as long as ok_btn isn´t 0 it won´t leave your while loop so it doesn´t read the button, it´s better to check the value of ok_btn in a if/else

Related

Creating a loop inside GtkDialog

I have a GtkDialog set up like this:
GtkWidget *dialog;
dialog = gtk_message_dialog_new(GTK_WINDOW(window),
GTK_DIALOG_DESTROY_WITH_PARENT,
GTK_MESSAGE_INFO,
GTK_BUTTONS_OK,
"Information");
gtk_window_set_title(GTK_WINDOW(dialog), "Information");
gtk_dialog_run(GTK_DIALOG(dialog));
gtk_widget_destroy(dialog);
However, when the dialog is open I want to have an infinite loop, which would be exited when the OK button is pressed. Is something like that possible to achieve?
Just run gtk_dialog_run in a do/while loop and test its return value in the while. That return value tells you which button has been pressed (most probably GTK_RESPONSE_ACCEPT in your case).
Please read the documentation for gtk_dialog_run, that's explained there.

What signal should I capture to grab the text of Gtk::Entry before it is changed?

I am writing an application using gtkmm 3 (running Ubuntu 12.04 LTS) and working right now with the Gtk::Entry control.
I cannot find the correct signal to capture so that I can grab the Gtk::Entry buffer text before it is changed, and persist it to maintain a record of changes. I know that in some other tool-kits, there is a hook provided that facilitates such. (I believe using a "shadow buffer".)
What signal do I have to grab to do this? What is the slot's signature for this signal? Is this functionality supported at all?
Since you are changing the behaviour, it's better to inherit from Gtk::Entry:
class ValidatedEntry : public Gtk::Entry {
Glib::ustring last_valid;
virtual void on_changed()
{
Glib::ustring text = get_text();
if (... validation here ...)
set_text(last_valid); // WARNING: will call this on_changed() again
else
last_valid = text;
Gtk::Entry::on_changed(); // propagate down
}
};
BUT
This goes against usability, that's why it's not a built-in behaviour. Users won't like the text reverting back just because they miss-typed something; they might hit backspace before they realize the entry threw the wrong character away.
You should at least wait until the user presses the Enter key (i.e. signal_activate or override on_activate()), or do something less drastic, like showing a warning icon.
You could give a try to GObject's "notify" signal. It is used in conjunction with the property to spy. Connecting to "notify::text" will call your callback for each modification of the "text" property, but the first change may be the setter that will set the initial value, that you could then store. Worth a try.
Otherwise, you could try to store it on the first triggering of the "insert-text" or "delete-text" signals. Please give use some feedback if that seems to work.
I also agree with DanielKO: on an usability point of view, modifying user input is just annoying and bad practice. Better to tell her which field is wrong, put the focus there, and/or have a button to reset to defaults, but not enforce any change on user input.

Jump function on a character

I'm creating this 2D game and I'm having problems with the Jump function. It works, the character jumps up and down, but I would like to be able to jump and then move the character while its in the air,e.g. so it can jump onto a platform. I'm using SDLK...
case SDL_KEYDOWN:
switch (event.key.keysym.sym){
RArrow = (event.button.button = SDLK_RIGHT);
Jump = (event.button.button = SDLK_SPACE);
if((RArrow) && (Jump))
{
if(g->getPlayer()->worldY = GROUND_LEVEL)
{
g->getPlayer()->jump();
g->getPlayer()->move(10);
}
}
break;
This is one of the ways I've tried. I've also tried to make a switch function inside the jump case to navigate left or right but I either didn't code it right or just didn't work.
I'm unfamiliar with SDLK and how this actually is done in real game development.
However one way I've implemented this is to see if both keys are pressed on each game tick. So if w+d is pressed the character would go up and right at the same time. But it's a hackish solution in my opinion.
With the implementation listed, looks like the character will only move right when they are on the ground level. You need to change your code so that every tick, the game checks if the character is jumping and if so, moves the character in the direction it is facing/jumping. This code may need to live outside of your event handler.
Ideally, your keyboard event handler would just set a flag on the character indicating that they are jumping and which direction, then in your game loop you call an update() method which actually handles the jumping (and stops jumping when the character collides with the world geometry, like a floor or wall).
Hope this helps!
EDIT:
Without seeing the rest of your code, I can't say much more. I'm also not great with C++, which I'm assuming this uses. One way you could implement this is:
Replace "g->getPlayer()->jump()" with "g->getPlayer()->setJumping()".
Implement "setJumping()" on the Character to set a jumping flag.
In the game loop, call "g->getPlayer()->updatePos()"
Implement "updatePos()" on the Character to update the character's position. In this, check the jumping flag, and if it's true update the position based on your jumping algorithm.

SDLK Perplexity

How does SDLK_'anykey' work? In my game, a bullet has to be shot when the Ctrl button is pressed, but through breakpoints and test print statements I have realised that even though I press 'ctrl' once, the function is getting called many times. Why is that? And how do I avoid this?
There's nothing much - this is the switch case in the main loop :
case SDLK_p :
s.origin(cat);
break;
where s is an object that calls the origin function of the Shoot class, and passes a frame to it. Using a count variable in the origin function, I now know that the function is called for the number of times equal to the seconds I hold down the 'p' key! How to prevent this?
SDL_PollEvent(&event);
You need to check the return value from SDL_PollEvent. If it's 0 there are no pending events and you shouldn't try to handle it.
According to documentation, you should add this line to the SDL initialization:
SDL_EnableKeyRepeat(0,0);

Button held down by code

I am writing a game and am trying to make a person move with the arrow keys.
I have this code
if (Key_Down(DIK_DOWN))
{movedown(player)}
This works but as I want the player to take four steps every time the key is pressed I created and animation loop. so the player cannot input any more move commands until the animation is over and they have taken four steps I made the code this.
if(player.move == false)
{
if (Key_Down(DIK_DOWN))
{movedown(player)}
}
The problem is that now once a button is pressed the program acts like the button is held down and the player keeps moving until another direction is pressed.
Can anyone explain what the outer loop has done to the code and fix the problem ?
it is programmed in visual c++ 2005 and direct x 9.c
Edit:
If I remove the outer loop then the button press is only registered once so I don't think it is the movedown function.
Simply keep track of the keystate in a variable. So you can reset a move counter. Something like this, combining both:
int MovingDown = 0;
...
if (!Key_Down(DIK_DOWN)) MovingDown = 0;
else if (MovingDown < 4) {
MovingDown++;
movedown(player);
}
Hard to tell without seeing more of your codebase but I would guess that you're not re-setting player.move after you've moved the player. Have you tried sticking some break poins in there to see what is being called and why?
If you remove the if(player.move == false) line does it have the same issue? ..or have you changed something elsewhere? If you could post more of your codebase like the whole movedown function and anythnig else which interacts (e.g. the animation code) it would help us help you...
[Edit] Is movedown a macro? Maybe you've got some peculiar side effect eminating from that? If not, it ought to have a semi colon after the function call.
What does KEY_DOWN return? Is that an API call? Try testing against the exact value you expect it to return?