I am trying to make a character (char) jump in stages in a game using a for loop to jump a part of the way each time the loop run. The loop never initializes.
Jump starting is traced to the output console but the jump No. does not get traced.
Why is this?
JumpHeight == 25
stage.addEventListener(KeyboardEvent.KEY_DOWN, keyPressed);
stage.addEventListener(Event.ENTER_FRAME, loop);
function loop(event:Event):void
{
if (jumping == false && char.hitTestObject(floor) == false)
{
char.y += gravity
}
}
function keyPressed(event:KeyboardEvent):void
{
if (event.keyCode == jumpKey)
{
jump()
}
}
function jump()
{
if (char.y >= groundY)
{
trace("Jump Starting")
jumping = true
for (jCycle = 0; jCycle == jumpHeight; jCycle++)
{
char.y -= gravity
trace("Jump No. " + jCycle)
}
jumping = false
}
}
Your problem is that for condition is always false (jCycle == 0 !=jumpHeight) and body is unreachable.
Try this:
for (var jCycle:int = 0; jCycle <= jumpHeight; jCycle++)
{
//body
}
You have an error in the for loop condition: jCycle == jumpHeight should be jCycle < jumpHeight (or jCycle <= jumpHeight).
Related
I am making a platform game where the main character moves right and left and jumps however my character jumps and does not return to the ground but stays on top of the stage.My characters movie-clip symbol is called 'naruto' and my ground symbol is called 'ground'.
Here is my code:
import flash.events.KeyboardEvent;
import flash.ui.Keyboard;
import flash.display.MovieClip;
import flash.events.Event;
import flash.display.Stage;
naruto.gotoAndStop("stance");
var rightPressed:Boolean = new Boolean(false);
var leftPressed:Boolean = new Boolean(false);
var upPressed:Boolean = new Boolean(false);
var downPressed:Boolean = new Boolean(false);
var narutoSpeed:Number = 10;
stage.addEventListener(KeyboardEvent.KEY_DOWN,keyDownHandler);
stage.addEventListener(KeyboardEvent.KEY_UP,keyUpHandler);
stage.addEventListener(Event.ENTER_FRAME,gameLoop);
function keyDownHandler(keyEvent:KeyboardEvent):void
{
if (keyEvent.keyCode == Keyboard.RIGHT)
{
rightPressed = true;
}
else if(keyEvent.keyCode == Keyboard.LEFT)
{
leftPressed = true;
}
else if(keyEvent.keyCode == Keyboard.UP)
{
upPressed = true;
}else if(keyEvent.keyCode == Keyboard.DOWN)
{
downPressed = true;
}
}
function keyUpHandler(keyEvent:KeyboardEvent):void
{
if (keyEvent.keyCode == Keyboard.RIGHT)
{
rightPressed = false;
naruto.gotoAndStop("standright")
}
else if(keyEvent.keyCode == Keyboard.LEFT)
{
leftPressed = false;
naruto.gotoAndStop("standleft")
}
else if(keyEvent.keyCode == Keyboard.UP)
{
upPressed = false;
naruto.gotoAndStop("stance")
}else if(keyEvent.keyCode == Keyboard.DOWN)
{
downPressed = false;
naruto.gotoAndStop("stance")
}
}
function gameLoop(loopEvent: Event): void {
//If the right key is pressed, and the left key is NOT pressed
if (rightPressed && !leftPressed) {
naruto.x += narutoSpeed;
naruto.gotoAndStop("right");
}
if(leftPressed && !rightPressed) {
naruto.x -= narutoSpeed;
naruto.gotoAndStop("left");
}
var jumpHeight =0;
var defaultJumpSpeed = 20;
var jumpSpeed = 20;
if(upPressed && naruto.hitTestObject(ground))
{
trace("HELLO!");
naruto.y -= jumpSpeed;
jumpSpeed-= 4;
}
if(upPressed)
{
trace("HELLO!");
jumpHeight++;
naruto.y -= jumpSpeed;
if(jumpHeight>10)
jumpSpeed -= 4;
}
if(naruto.hitTestObject(ground))
{
trace("HELLO!");
jumpHeight =0;
jumpSpeed = defaultJumpSpeed;
}
}
Here is the link for my work: https://www.mediafire.com/?8d5opy49fuqmup5
Here is the problem:
The main issue, is in your current code, the player can only possible be in 3 positions:
Whatever the ground position is
16 (up is pressed and the character was not touching the ground
12 (up is pressed and the character was touching the ground)
Please see the code comments next to your original code to explain what is happening:
//you have this var inside the game loop, so every loop it resets to 20
var jumpSpeed = 20;
//so here, if up is pressed and the character is touching the ground
//you initiate a jump
if(upPressed && naruto.hitTestObject(ground))
{
trace("HELLO!");
naruto.y -= jumpSpeed;
jumpSpeed-= 4; //since you reset jumpSpeed to 20 every loop, this value will always just be 16
}
if(upPressed)
{
trace("HELLO!");
jumpHeight++;
//if naruto is touching the ground
//you are subtracting jumpSpeed above and right here again.
//so now the y position is 12 if touching the ground (or 16 if not touching the ground)
//since you reset jumpSpeed to 20 every loop, it always be one of those two values
naruto.y -= jumpSpeed;
if(jumpHeight>10)
jumpSpeed -= 4; //this serves no purpose, as your not using the value again and it gets reset to 20 next time the game loop runs
}
//this hit test will succeed in addition to the first one above when your jump starts.
if(naruto.hitTestObject(ground))
{
trace("HELLO!");
jumpHeight =0;
jumpSpeed = defaultJumpSpeed;
}
To remedy your jumping, you'll need to do something along these lines:
//initialize these vars outside of the game-loop for efficient and proper scoping (so their values don't reset every frame)
var isJumping:Boolean = false; //a flag to know if a jump is in progress
var jumpSpeed:Number = 0; //the current velocity of the jump
var defaultJumpSpeed:Number = 20; //the initial force (speed) of a jump
var jumpGravity:Number = 2; //subtract this from the speed every frame to slow the jump over time and fall
var onGround:Boolean = false; //a helper var for efficiency
function gameLoop(loopEvent: Event): void {
//If the right key is pressed, and the left key is NOT pressed
if (rightPressed && !leftPressed) {
naruto.x += narutoSpeed;
naruto.gotoAndStop("right");
}
if (leftPressed && !rightPressed) {
naruto.x -= narutoSpeed;
naruto.gotoAndStop("left");
}
//only do the hit test once per frame for efficiency (store the result)
onGround = naruto.hitTestObject(ground);
if (upPressed && onGround) {
trace("START JUMP");
isJumping = true;
jumpSpeed = defaultJumpSpeed; //set the initial jump velocity
}
if(isJumping){ //if jumping
naruto.y -= jumpSpeed; //move the player based off the current jump velocity
jumpSpeed -= jumpGravity; //slow the jump every frame (eventually causing it to be negative making the player fall)
}
//touching the ground and the up key is not pressed
//it's very important to put !upPressed so this doesn't run at the time as the initial jump above
if (!upPressed && onGround) {
//stop any jump motion
jumpSpeed = 0;
isJumping = false;
//you probably also want to snap the player to the ground
naruto.y = ground.y - naruto.height + 2; //the plus 2 ensures that the ground and the player touch so the hit test succeeds
}
}
I'm scripting a game with Actionscript 3.0 in Flash Professional CS5.5, but I get an error.
Scene 1, Layer 'as2', Frame 153, Line 4 1151: A conflict exists with definition leftIdle1 in namespace internal.
(I get these with the other Variables too.)
Now it's a platform game, and I am going to put cutscenes throughout in the game and I need to switch from frames and put the code in another frame. But it gives that error, I turned off the 'Automatic Declare stage instances' function, now I checked this website and Googled it, people get it with their Movieclips, I get it with my variables.
This is my script:
var leftKeyDown1:Boolean = false;
var rightKeyDown1:Boolean = false;
var spaceKeyDown1:Boolean = false;
var leftIdle1:Boolean = false;
var rightIdle1:Boolean = true;
var mainSpeed1:Number = 4;
player.addEventListener(Event.ENTER_FRAME, moveChar);
function moveChar(event:Event)
{
if (leftKeyDown1)
{
player.x -= mainSpeed1;
leftIdle1 = true;
rightIdle1 = false;
player.gotoAndStop("walk_left");
}
if (rightKeyDown1)
{
player.x += mainSpeed1;
rightIdle1 = true;
leftIdle1 = false;
player.gotoAndStop("walk_right");
}
if (rightIdle1 && !rightKeyDown1 && !leftKeyDown1)
{
player.gotoAndStop("idle_right");
}
else if (leftIdle1 && !rightKeyDown1 && !leftKeyDown1)
{
player.gotoAndStop("idle_left");
}
if (collide.hitTestObject(player))
{
player.x = player.x + mainSpeed1;
}
if (trigger1.hitTestObject(player))
{
son1.gotoAndStop("walkRight");
trigger1.gotoAndStop(2);
son1.x += 2;
}
if (trigger2.hitTestObject(player))
{
gotoAndPlay(4);
}
}
stage.addEventListener(KeyboardEvent.KEY_DOWN, checkKeysDown);
function checkKeysDown(event:KeyboardEvent)
{
if (event.keyCode == 37 || event.keyCode == 65)
{
leftKeyDown1 = true;
}
if (event.keyCode == 39 || event.keyCode == 68)
{
rightKeyDown1 = true;
}
if (event.keyCode == 32)
{
spaceKeyDown1 = true;
}
}
stage.addEventListener(KeyboardEvent.KEY_UP, checkKeysU1);
function checkKeysUp(event:KeyboardEvent)
{
if (event.keyCode == 37 || event.keyCode == 65)
{
leftKeyDown1 = false;
}
if (event.keyCode == 32)
{
spaceKeyDown1 = false;
}
if (event.keyCode == 39 || event.keyCode == 68)
{
rightKeyDown1 = false;
}
}
It's probably coded in a weird way, but whatever.
I have no idea what to do at this point.
Help would be really appreciated.
EDIT:
Oh I got another error too. It's with Duplicate function, and I can't seem to fix it but to rename those, and it will take a long time to rename them every-time. So if someone has something for that, thanks!
you have duplicated definitions.
For example:
var leftIdle1:Boolean
exists multiple times - remove the duplicates
Good Evening,
I can't seem to get my code to only add one instance of an object to the stage. It seems to add atleast 3 instances of the object to the stage. The objects added is r2, r3 and r4.
stop();
import flash.events.Event;
stage.focus=stage;
var upKeyDown5:Boolean = false;
var rightKeyDown5:Boolean = false;
var downKeyDown5:Boolean = false;
var leftKeyDown5:Boolean = false;
var enterkey:Boolean = false;
var interaction:Boolean = false;
p5.addEventListener(Event.ENTER_FRAME, moveChar5);
stage.addEventListener(KeyboardEvent.KEY_DOWN, checkKeysDown5);
stage.addEventListener(KeyboardEvent.KEY_UP, checkKeysUp5);
Mouse.hide();
function moveChar5(e:Event):void{
if(downKeyDown5 && !upKeyDown5 && !rightKeyDown5 && !leftKeyDown5)
{
p5.gotoAndStop("walk_down");
if(p5.y < 492.75)
p5.y += 6;
}
if(upKeyDown5 && !downKeyDown5 && !rightKeyDown5 && !leftKeyDown5)
{
p5.gotoAndStop("walk_up");
if(p5.y > 202.85)
p5.y -= 6;
}
if(rightKeyDown5 && !upKeyDown5 && !downKeyDown5 && !leftKeyDown5)
{
p5.gotoAndStop("walk_right");
if(p5.x < 871.5)
p5.x += 6;
}
if(leftKeyDown5 && !upKeyDown5 && !rightKeyDown5 && !downKeyDown5)
{
p5.gotoAndStop("walk_left");
if(p5.x > 203.65)
p5.x -= 6;
}
if(enterkey && interaction && p5.hitTestObject(c1)){
if (!(Boolean(stage.getChildByName('r2')))) {
var rat2:r2;
rat2 = new r2();
addChild(rat2);
rat2.y=38;
rat2.x=32;
}
}
if(enterkey && interaction && p5.hitTestObject(c2)){
if (!(Boolean(stage.getChildByName('r3')))) {
var rat3:r3;
rat3 = new r3();
addChild(rat3);
rat3.y=38;
rat3.x=32;
}
}
if(enterkey && interaction && p5.hitTestObject(c3)){
if (!(Boolean(stage.getChildByName('r4')))) {
var rat4:r4;
rat4 = new r4();
addChild(rat4);
rat4.y=38;
rat4.x=32;
}
}
}
function checkKeysDown5(event:KeyboardEvent):void{
if(event.keyCode == 87){
upKeyDown5 = true;
}
if(event.keyCode == 68){
rightKeyDown5 = true;
}
if(event.keyCode == 83){
downKeyDown5 = true;
}
if(event.keyCode == 65){
leftKeyDown5 = true;
}
if (event.keyCode == 13){
enterkey = true;
}
}
function checkKeysUp5(event:KeyboardEvent):void{
if(event.keyCode == 87){
upKeyDown5 = false;
p5.gotoAndStop("still_up");
}
if(event.keyCode == 68){
rightKeyDown5 = false;
p5.gotoAndStop("still_right");
}
if(event.keyCode == 65){
leftKeyDown5 = false;
p5.gotoAndStop("still_left");
}
if(event.keyCode == 83){
downKeyDown5 = false;
p5.gotoAndStop("still_down");
}
if (event.keyCode == 13){
enterkey = false;
}
if(p5.hitTestObject(c1) || p5.hitTestObject(c2) || p5.hitTestObject(c3)){
p5.gotoAndStop("interaction");
interaction = true;
}
else
interaction = false;
}
Thanks in advance
It would be more efficient and cleaner to use a switch statement instead all those if statements (if you only ever want one and only one of those conditions to be met)
You're issue I think has to do with the way you're tracking your rats - eg. using the stage.getChildByName.
Below is an example, plus some commented notes on some of your other potential issues.
switch(true){
case (enterkey && interaction && p5.hitTestObject(c1)):
if (!(Boolean(stage.getChildByName('r2')))) { //your not giving your rat a name so this will always return false, plus you're not adding the rat to the stage but to this class
var rat2:r2;
rat2 = new r2();
addChild(rat2); //use stage.addChild if you want the above check (stage.getChildByName) to work
rat2.y=38;
rat2.x=32;
rat2.name = "r2"; //if you want the above check to work
break; //break out of the switch if you don't want any of the others evaluate since this rat got added
}
//do a case for your other blocks
}
It would be better to not use stage.getChidByName at all, and instead create a method like this:
function checkRatExists(ratClass:Class):Boolean {
var tmp:DisplayObject;
var i:int = numChildren;
while(i--){
tmp = getChildAt(i);
if(tmp is ratClass){
return true;
}
}
return false;
}
Then use that new function instead of stage.getChildByName:
if (!checkRatExists(r2)) //r2 is the class of rat you want to check
As an aside from your issue, it would be much cleaner to create a method/function to do your rat positioning and adding instead of duplicated the code over and over and over...
function addRat(rat:RatCommonBaseClass, ratName:String):void {
addChild(rat);
rat.y=38;
rat.x=32;
rat.name = ratName;
}
//now you can just do this for all your rats:
addRat(new r2(),"r2);
You don't have an else condition for the your statements where you add the objects, so most likely what is happening is that all the statements are satisfying the condition at once. Adding an else statement should prevent this from happening:
if(enterkey && interaction && p5.hitTestObject(c1)){
if (!(Boolean(stage.getChildByName('r2')))) {
var rat2:r2;
rat2 = new r2();
addChild(rat2);
rat2.y=38;
rat2.x=32;
}
}
else if(enterkey && interaction && p5.hitTestObject(c2)){
if (!(Boolean(stage.getChildByName('r3')))) {
var rat3:r3;
rat3 = new r3();
addChild(rat3);
rat3.y=38;
rat3.x=32;
}
}
else if(enterkey && interaction && p5.hitTestObject(c3)){
if (!(Boolean(stage.getChildByName('r4')))) {
var rat4:r4;
rat4 = new r4();
addChild(rat4);
rat4.y=38;
rat4.x=32;
}
}
This way it will first check to see if p5 has hit c1 and only if it hasn't will it check if it has hit c2 and then the same thing for c3.
Some troubles to make my new flash game(i used AS3,CS5.5):
I just try to make my character(hatt) walk and jump, but I can't make it at the same time, well, idk how... Furthermore, I don't know how make my character recognize the ground.
And at last this thing here:
"Scene 1, Layer 'hatt', Frame 1, Line 6 Warning: 1090: Migration issue: The onKeyDown event handler is not triggered automatically by Flash Player at run time in ActionScript 3.0. You must first register this handler for the event using addEventListener ( 'keyDown', callback_handler)."
Plz help me and give some hints plz... Thanks.
Here's the code:
var grav:Number = 10;
var jumping:Boolean = false;
var jumpPow:Number = 0;
stage.addEventListener(KeyboardEvent.KEY_DOWN, onKeyDown);
stage.addEventListener(Event.ENTER_FRAME, update);
function onKeyDown(evt:KeyboardEvent):void
{
if (evt.keyCode == Keyboard.UP)
{
if (jumping != true)
{
jumpPow = -25;
jumping = true;
}
}
}
function update(evt:Event):void
{
if (jumping)
{
hatt.y += jumpPow;
jumpPow += grav;
if (hatt.y >= stage.stageHeight)
{
jumping = false;
hatt.y = stage.stageHeight;
}
}
}
stage.addEventListener (KeyboardEvent.KEY_DOWN, myFunction) ;
function myFunction (event: KeyboardEvent){
if(event.keyCode == Keyboard.LEFT) {
hatt.x -= 5
}
if(event.keyCode == Keyboard.RIGHT) {
hatt.x += 5
}
}
remove this line:
stage.addEventListener(KeyboardEvent.KEY_DOWN, onKeyDown);
remove function onKeyDown:
function onKeyDown(evt:KeyboardEvent):void
{
if (evt.keyCode == Keyboard.UP)
{
if (jumping != true)
{
jumpPow = -25;
jumping = true;
}
}
}
replace myFunction with this:
function myFunction (event: KeyboardEvent)
{
if(event.keyCode == Keyboard.LEFT)
hatt.x -= 5;
if(event.keyCode == Keyboard.RIGHT)
hatt.x += 5;
if(event.keyCode == Keyboard.UP && jumping != true)
{
jumpPow = -25;
jumping = true;
}
}
I am a student working on a project with flash. I am simply trying to make a flash game using Actionscript 3 in Adobe Flash CS5. Everything is working fine, i can walk and jump, but I want the game to restart if the Main character touches an object and dies (like spikes in a pit). I have a main menu in frame 1 and the first level on frame 2. The main character is called "player_mc" and the object that kills him is called "dies". Help and tips is very much appreciated.
Code:
//The Code For The Character (Player_mc)
import flash.events.KeyboardEvent;
import flash.events.Event;
var KeyThatIsPressed:uint;
var rightKeyIsDown:Boolean = false;
var leftKeyIsDown:Boolean = false;
var upKeyIsDown:Boolean = false;
var downKeyIsDown:Boolean = false;
var playerSpeed:Number = 20;
var gravity:Number = 1;
var yVelocity:Number = 0;
var canJump:Boolean = false;
var canDoubleJump:Boolean = false;
stage.addEventListener(KeyboardEvent.KEY_DOWN, PressAKey);
stage.addEventListener(KeyboardEvent.KEY_UP, ReleaseAKey);
//This two functions cllapsed is the keybindings that the game uses
function PressAKey(event:KeyboardEvent):void
{
if(event.keyCode == Keyboard.D)
{
rightKeyIsDown = true;
}
if(event.keyCode == Keyboard.A)
{
leftKeyIsDown = true;
}
if(event.keyCode == Keyboard.SPACE)
{
upKeyIsDown = true;
}
if(event.keyCode == Keyboard.S)
{
downKeyIsDown = true;
}
}
function ReleaseAKey(event:KeyboardEvent):void
{
if(event.keyCode == Keyboard.D)
{
rightKeyIsDown = false;
}
if(event.keyCode == Keyboard.A)
{
leftKeyIsDown = false;
}
if(event.keyCode == Keyboard.SPACE)
{
upKeyIsDown = false;
}
if(event.keyCode == Keyboard.S)
{
downKeyIsDown = false;
}
}
//Player animations
player_mc.addEventListener(Event.ENTER_FRAME, moveThePlayer);
function moveThePlayer(event:Event):void
{
if(!canJump || rightKeyIsDown && !canJump || leftKeyIsDown && !canJump)
{
player_mc.gotoAndStop(3);
}
if(!upKeyIsDown && !rightKeyIsDown && !leftKeyIsDown && canJump)
{
player_mc.gotoAndStop(1);
}
if(rightKeyIsDown && canJump || leftKeyIsDown && canJump)
{
player_mc.gotoAndStop(2);
}
//Animation stops here
if(rightKeyIsDown)
{
floor_mc.x -= playerSpeed;
dies.x -= playerSpeed;
player_mc.scaleX = 0.3;
}
if(leftKeyIsDown)
{
floor_mc.x += playerSpeed;
dies.x += playerSpeed;
player_mc.scaleX = -0.3;
}
if(upKeyIsDown && canJump)
{
yVelocity = -18;
canJump = false;
canDoubleJump = true;
}
if(upKeyIsDown && canDoubleJump && yVelocity > -2)
{
yVelocity =-13;
canDoubleJump = false;
}
if(!rightKeyIsDown && !leftKeyIsDown && !upKeyIsDown)
{
player_mc.gotoAndStop(1);
}
yVelocity +=gravity
if(! floor_mc.hitTestPoint(player_mc.x, player_mc.y, true))
{
player_mc.y+=yVelocity;
}
if(yVelocity > 20)
{
yVelocity =20;
}
for (var i:int = 0; i<10; i++)
{
if(floor_mc.hitTestPoint(player_mc.x, player_mc.y, true))
{
player_mc.y--;
yVelocity = 0;
canJump = true;
}
}
}
If I understand this right, when you die, you want to restart the level. To do this, you could save all your initial variables like player position, floor position, etc in an array, then on death, restore those variables to their corresponding object. However, when you get more complex and have lots and lots of objects, it could become tricky.
A simpler solution is to display a death screen of some sorts on another frame (lets call it frame 3) when you hit the dies object, and on that death screen when you press a restart button or after a certain time delay, it then goes back to frame 2 and restarts the level.
Example:
Put this in your moveThePlayer function:
if(dies.hitTestPoint(player_mc.x, player_mc.y, true))
{
// remove all the event listeners
player_mc.removeEventListener(Event.ENTER_FRAME, moveThePlayer);
stage.removeEventListener(KeyboardEvent.KEY_DOWN, PressAKey);
stage.removeEventListener(KeyboardEvent.KEY_UP, ReleaseAKey);
gotoAndStop(3); // this has your "dead" screen on it.
}
And on frame 3, have something like:
import flash.events.MouseEvent;
retry_button.addEventListener(MouseEvent.CLICK, retry);
function retry(e:MouseEvent) {
retry_button.removeEventListener(MouseEvent.CLICK, retry);
// back to the level
gotoAndStop(2);
}
You could also do something like storing a variable on which frame you want to go back to, so you have a single retry frame which can go to whatever level you were just on.
A good habit that you should develop is having an endGame() or similar method that you update as you work on the game.
For example:
function endGame():void
{
// nothing here yet
}
Now lets say you create a player. The player is initially set up like this:
player.health = 100;
player.dead = false;
You'll want to update your endGame() method to reflect this.
function endGame():void
{
player.health = 100;
player.dead = false;
}
Got some variables related to the game engine itself?
var score:int = 0;
var lives:int = 3;
Add those too:
function endGame():void
{
player.health = 100;
player.dead = false;
score = 0;
lives = 3;
}
Now endGame() should reset the game back to its original state. It's much easier to work this way (as you code the game) rather than leaving it until last and trying to make sure you cover everything off, which is unlikely.