Windows Phone Gesture Detection - windows-phone-7

I'm creating a game where the player will use Drag gestures to "slash" an enemy, swiping their finger across the screen to kill them.
I have a feeling this should be easier than it is, but currently the code I have to detect this is:
while (TouchPanel.IsGestureAvailable)
{
GestureSample gs = TouchPanel.ReadGesture();
if (gs.GestureType == GestureType.FreeDrag ||
gs.GestureType == GestureType.HorizontalDrag ||
gs.GestureType == GestureType.VerticalDrag)
{
Current_Start = gs.Position;
Current_End = Current_Start + gs.Delta;
}
if (gs.GestureType == GestureType.DragComplete)
{
DragEnded = true;
}
}
This isn't quite working, though. I need the two vectors of:
Where the drag started
Where the drag ended
What is wrong, and how would I get this to work?

I would try using the onmousedown and onmouseup events to get the start and end points and go from there.

Related

How to write KeyBindings

I am developing a Java 2D Game, in which I have used a KeyListener, but as you probably can guess, it has focusing issues, mainly when the Player is running and you keep the same key pressed for long, for example pressing "W" to run forward, but after some seconds of keep pressing W, the KeyListener dies and no key works, I want to use KeyBindings, as most people suggest it for game development, but I cannot find any usefull tutorials, most of them use some form of Buttons, and other useless features for my game, so how can i avoid the KeyListener from losing focus, or how can I write a simple KeyBinding code, that only moves the player, and other simple stuff used in a game.
This is the kind of Key Binding that I want, I KNOW IT DOES NOT WORK, it is an example:
component.getInputMap().put(KeyStroke.getKeyStroke(VK_W),
"move forward")
component.getActionMap().put("released",
releasedAction);
if(releasedAction == true){
Player.playerSpeedY = 7;
} else{
Player.playerSpeedY = 0;
}
FWI: this is the current KeyListener code:
if(HUD.PlayerHealth > 0){
if(key == KeyEvent.VK_W) {Player.playerSpeedY = -5; keyDown[0]= true;}
if(key == KeyEvent.VK_S) {Player.playerSpeedY = 5; keyDown [1]= true;}
if(key == KeyEvent.VK_A) {Player.playerSpeedX = -5; keyDown [2]= true;}
if(key == KeyEvent.VK_D) {Player.playerSpeedX = 5; keyDown [3]= true;}
}
I keep looking for Actions and Input maps tutorials, or KeyBinding ones, and I just don't find anything useful, another dough, the component in action and input map, what is it for?, should my entire code be based on that, and is there any way to only make the action map move the player, and only that?
Try something like this:
this.getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_D, 0, false), "right");
this.getActionMap().put("right", new AbstractAction() {
public void actionPerformed(ActionEvent e) {
//Do Something Here
Player.playerSpeedX = 5;
}
});
How to use KeyBindings

GDScript: How to play an animation while key is preessed?

I am very new to coding and I'm still trying different languages out, I started off with GameMaker Studio and changed to Godot due to its compatibility with Mac I might as well learn something newer since GameMaker has been out for quite some time.
I want to create a RPG game and apply animation to each direction the character moves but the animation only plays after the key is pressed AND lifted. This means that while my key is pressed, the animation stops, and the animation only plays while my character is standing still, which is the complete opposite of what I want. The script looked really straight forward, but doesn't seem to be working.
I would tag this as the GDScript language instead of Python, but I guess I'm not reputable enough to make a new tag, so I tagged it under python because it is the most similar.
#variables
extends KinematicBody2D
const spd = 100
var direction = Vector2()
var anim_player = null
func _ready():
set_fixed_process(true)
anim_player = get_node("move/ani_move")
#movement and sprite change
func _fixed_process(delta):
if (Input.is_action_pressed("ui_left")) :
direction.x = -spd
anim_player.play("ani_player_left")
elif (Input.is_action_pressed("ui_right")):
direction.x = spd
anim_player.play("ani_player_right")
else:
direction.x = 0
if (Input.is_action_pressed("ui_up")) :
direction.y = -spd
anim_player.play("ani_player_up")
elif (Input.is_action_pressed("ui_down")):
direction.y = (spd)
anim_player.play("ani_player_down")
else:
direction.y = 0
if (Input.is_action_pressed("ui_right")) and (Input.is_action_pressed("ui_left")):
direction.x = 0
if (Input.is_action_pressed("ui_up")) and (Input.is_action_pressed("ui_down")) :
direction.y = 0
# move
var motion = direction * delta
move(motion)
As you check the input in _fixed_process, you call anim_player.play() several times a frame, which always seems to restart the animation, and thus, keeps the very first frame of the animation visible all the time.
As soon as you release the key, anim_player.play() stops resetting the animation back to start, and it can actually proceed to play the following frames.
A simple straight-forward solution would be to remember the last animation you played, and only call play() as soon as it changes.
You need to know if the animation has changed
First you need to put these variables in your code:
var currentAnim = ""
var newAnim = ""
And then you add this in your _fixed process:
if newAnim != anim:
anim = newAnim
anim_player.play(newAnim)
To change the animation you use:
newAnim = "new animation here"

Flixel Game Over Screen

I am new to game development but familiar with programming languages. I have started using Flixel and have a working Breakout game with score and lives.
I am just stuck on how I can create a new screen/game over screen if a player runs out of lives. I would like the process to be like following:
Check IF lives are equal to 0
Pause the game and display a new screen (probably transparent) that says 'Game Over'
When a user clicks or hits ENTER restart the level
Here is the function I currently have to update the lives:
private function loseLive(_ball:FlxObject, _bottomWall:FlxObject):void
{
// check for game over
if (lives_count == 0)
{
}
else
{
FlxG:lives_count -= 1;
lives.text = 'Lives: ' + lives_count.toString()
}
}
Here is my main game.as:
package
{
import org.flixel.*;
public class Game extends FlxGame
{
private const resolution:FlxPoint = new FlxPoint(640, 480);
private const zoom:uint = 2;
private const fps:uint = 60;
public function Game()
{
super(resolution.x / zoom, resolution.y / zoom, PlayState, zoom);
FlxG.flashFramerate = fps;
}
}
}
There are multiple ways to go about doing this...
You could use different FlxStates, like I described in the answer to your other post: Creating user UI using Flixel, although you'll have to get smart with passing the score or whatever around, or use a Registry-type setup
If you want it to actually work like you described above, with a transparent-overlay screen, you can try something like this (keep in mind, the exact details may differ for your project, I'm just trying to give you an idea):
First, make sure you have good logic for starting a level, lets say it's a function called StartLevel.
You'll want to define a flag - just a Boolean - that tracks whether or not the game is still going on or not: private var _isGameOver:Boolean; At the very end of StartLevel(), set this to false.
In your create() function for your PlayState, build a new FlxGroup which has all the things you want on your Game Over screen - some text, an image, and something that says "Press ENTER to Restart" (or whatever). Then set it to visible = false. The code for that might look something like:
grpGameOver = new FlxGroup();
grpGameOver.add(new FlxSprite(10,10).makeGraphic(FlxG.Width-20,FlxG.Height-20,0x66000000)); // just a semi-transparent black box to cover your game screen.
grpGameOver.add(new FlxText(...)); // whatever you want to add to the group...
grpGameOver.visible = false;
add(grpGameOver); // add the group to your State.
Depending on how your game is setup, you may also want to set the objects in your group's scrollFactor to 0 - if your game screen scrolls at all:
grpGameOver.setAll("scrollFactor", new FlxPoint(0,0));
In your update() function, you'll need to split it into 2 parts: one for when the game is over, and one for if the game is still going on:
if (_isGameOver)
{
if (FlxG.keys.justReleased("ENTER"))
{
grpGameOver.visible = false;
StartLevel();
}
}
else
{
... the rest of your game logic that you already have ...
}
super.update();
Keep in mind, if you have things that respond to user input anywhere else - like a player object or something, you might need to change their update() functions to check for that flag as well.
Then, the last thing you need to do is in your loseLive() logic:
if (lives_count == 0)
{
_isGameOver = true;
grpGameOver.visible = true;
}
else
...
That should do it!
I would highly recommend spending some time with different tutorials and sample projects to kind of get a better feel for Flixel in general. Photon Storm has some great material to play with (even though he's jumped over to HTML5 games)
I also want to note that if you get comfortable with the way Flixel handles updates, you can get really smart with your state's update() function and have it only call update on the grpGameOver objects, instead of having to change all your other objects updates individually. Pretty advanced stuff, but can be worth it to learn it.

wp7 xna touch. I want the user to keep tapping, not hold

Trying to make an xna game, where the user needs to tap to stop a bar going down. The simulation is like what we see in a WWE PS3/xbox game, the give up bar.
Anyway, the way i have done it, serves the purpose. However, if the user holds the touch, touch values keep incrementing.
What I want is, if the user taps it, only 1 point will be scored. And when he taps again, he will get 1 point more. At the moment what is happening is, if the user holds it, it keeps incrementing, kind of like in a keyboard (if u hold a button, keypresses keeps going on).
foreach (TouchLocation location in TouchPanel.GetState())
{
if (location.State == TouchLocationState.Moved)
{
touchPoints++;
break;
}
}
Change from TouchLocationState.Moved to TouchLocationState.Pressed. That should only occur with each new touch.
foreach (TouchLocation location in TouchPanel.GetState())
{
TouchLocation prevLocation;
bool prevLocationAvailable = location.TryGetPreviousLocation(out prevLocation);
if (location.State == TouchLocationState.Pressed && prevLocation.State != TouchLocationState.Pressed)
{
touchPoints++;
break;
}
}
And for the future, if you're doing Keyboard input and want each press of the keyboard to increment the value but to be ignored if the player is holding down the space, you just have to store the previous state of the keyboard. Then you compare if the current keyboard state the key is being pressed and the previous keyboard state the key wasn't pressed.
(didn't actually code in compiler so there could be some code issues with the below)
KeyboardState currentKeyboardState = Keyboard.GetState();
if (currentKeyboardState.IsKeyDown(Keys.Space) && !previousKeyboardState.IsKeyDown(Keys.Space) {
//Do whatever it is you want to do with the press of the space key
}
previousKeyboardState = currentKeyboardState;
This is a snippet of my code of how i got each touch to be a individual value.
The system.diagnostics line is the test that will show you in your output box.
TouchCollection touch = TouchPanel.GetState();
foreach (TouchLocation touchLocation in touch)
{
if (touchLocation.State == TouchLocationState.Pressed)
{
base.InputPointX = touchLocation.Position.X;
base.InputPointY = touchLocation.Position.Y;
System.Diagnostics.Debug.WriteLine("X: " + base.InputPointX + \
", Y: " + base.InputPointY);
base.Update();
return true;
}
}

ManipulationDelta event only fires after a threshold is passed

I am trying to write some code that will allow the user to draw on the touch screen.
When using either GestureService or ManipulationStarted/Delta, there's a "pause" that occurs when the user starts moving their finger - only when the finger is far enough from the point in which it started, only then do you start getting ManipulationDelta events (and like I said, same deal is true for GestureService).
What can I do to avoid this threshold? It really does not work well with drawing code.
Just blogged about it as I have come across similar questions on AppHub Forum.
https://invokeit.wordpress.com/2012/04/27/high-performance-touch-interface-wpdev-wp7dev/
Manipulation Delta and Gesture services are high level touch interfaces. If you want performance, consider using low level interfaces: Touch and an event called TouchReported. I tend to use them mostly (for drawing / position detection) in many of my projects
The event you want to plug in to detech touch is
Touch.FrameReported += Touch_FrameReported;
You can do this in Loaded event. Here's the implementation of the Touch_FrameReported handler. WorkArea is Canvas in this. I have also used this in conjugation with WritableBitmap
private void Touch_FrameReported(object sender, TouchFrameEventArgs e)
{
try
{
// Determine if finger / mouse is down
point = e.GetPrimaryTouchPoint(this.workArea);
if (point.Position.X < 0 || point.Position.Y < 0)
return;
if (point.Position.X > this.workArea.Width || point.Position.Y > this.workArea.Height)
return;
if (this.lbLetter.SelectedIndex == -1)
return;
switch (point.Action)
{
case TouchAction.Down:
draw = true;
old_point = point;
goto default;
case TouchAction.Up:
draw = false;
break;
default:
Draw();
break;
}
}
catch
{
MessageBox.Show("Application encountered error processing last request.");
}
}
This works lot better than high level interfaces.

Resources