Sprite hitting an invisible platform - actionscript-3

Hi there I'm currently making a platform game and I'm having trouble where the sprite starts at the very bottom of the stage:
Like this:
and if I try to jump, it stays on an invisible platform:
Here's my external code so far :
import flash.display.*;
import flash.events.*;
import flash.ui.*;
public class codes extends MovieClip
{
public function codes(){
chara.stop();
stage.addEventListener (KeyboardEvent.KEY_DOWN, keydown);
stage.addEventListener (KeyboardEvent.KEY_UP, keyup);
stage.addEventListener (Event.ENTER_FRAME, gameloop);
}
var mspeed:Number=0;
var sy:Number=2;
var gv:Number=1;
var jumped:Boolean=false;
function keydown (e:KeyboardEvent){
if (e.keyCode==Keyboard.LEFT){
mspeed=-10;
chara.gotoAndStop(2);
}
if (e.keyCode==Keyboard.RIGHT){
mspeed=10;
chara.gotoAndStop(1);
}
if (e.keyCode==Keyboard.SPACE) {
if (!jumped){
sy=-20;
jumped=true;
}
}
}
function keyup (e:KeyboardEvent){
if (e.keyCode==Keyboard.LEFT){
mspeed=-0;
}
if (e.keyCode==Keyboard.RIGHT){
mspeed=0;
}
}
function gameloop (e:Event) {
chara.x += mspeed;
if (chara.x<0) {
chara.x=0;
}
if (chara.x>950) {
chara.x=950;
}
sy+=gv;
if (!jump.hitTestPoint(chara.x,chara.y,true)) {
chara.y+=sy;
}
for (var i=0;i<10;i++) {
if (jump.hitTestPoint (chara.x, chara.y, true)) {
chara.y--;
sy=0;
jumped=false;
}
}
}
}

It looks like he is standing on the platform with his face! Are you sure that's not what's happening?
It's not bug. It's doing what you told it to. It may be as simple as making sure that the character has his feet at the origin point of the movie clip (the little white dot when you edit the movie clip)

Related

Removing the own MovieClip through its class block

I'm trying to make a ship game and I'm having an problem to get opponents fading as well.
Well, these opponents (like ships) has an class. In this class I do a interval to make its children fly to left (changing X per velocity number choosen on fourth argument in the function for adding enemies (addOpponent(opponentX, opponentY, opponentType, opponentVelocity)) and, when any of them has coordinate X smaller than -25, must be removed, through class block of itself.
package {
import flash.display.*
import flash.display.MovieClip;
import flash.utils.setTimeout;
import flash.utils.setInterval;
import flash.utils.clearInterval;
public class opponentNave extends MovieClip {
public function opponentNave(opponentVelocitySet) {
var loopMoveClassicOpponentsNave:uint = setInterval(movingClassicOpponentNave, 58);
function movingClassicOpponentNave() {
if (x < -25) {
clearInterval(loopMoveClassicOpponentsNave);
this.parent.removeChild(this);
} else {
x -= opponentVelocitySet;
}
}
}
}
}
I'm using this.parent.removeChild(this). I'm getting a error when the opponent X is smaller than -25, and it's on that time I want to remove the opponent child.
Here is how I would refactor this: (see code comments)
package
{
import flash.display.MovieClip;
import flash.events.Event;
public class opponentNave extends MovieClip
{
//create a class scoped variable for the velocity
private var velocitySet:Number;
public function opponentNave(opponentVelocitySet)
{
//set the velocity var
velocitySet = opponentVelocitySet;
//wait for this object (opponentNave) to be added to the display before doing anything display oriented
this.addEventListener(Event.ADDED_TO_STAGE, addedToStage, false, 0, true);
}
private function addedToStage(e:Event):void {
//run a function every frame tick of the application's fps
//this is best for things that are display oriented instead of time based ways like Timer or Intervals
this.addEventListener(Event.ENTER_FRAME, enterFrameHandler);
}
private function enterFrameHandler(e:Event):void
{
if (x < -25){
if (this.parent) this.parent.removeChild(this);
this.removeEventListener(Event.ENTER_FRAME, enterFrameHandler);
}
else
{
x -= velocitySet;
}
}
}
}

How do I get Hit Detection to work in Flash?

Ives tried many hit detections and none of them seem to work for me. I've tried hittest hittestobject hitarea. When my object (which is a or b movie-clip goes fully into c movie clip i want c to move 300 x direction. Does not need to be pin point detection just as long as its in the c movie-clip it works.
package {
import flash.display.MovieClip;
import flash.events.MouseEvent;
import flash.events.Event;
import flash.media.Sound;
import flash.ui.Mouse;
public class bakingCake extends MovieClip {
public function bakingCake() {
// constructor code
var object:MovieClip = new MovieClip;
a.addEventListener(MouseEvent.MOUSE_DOWN,objectA);
b.addEventListener(MouseEvent.MOUSE_DOWN,objectB);
if (object.hitArea(c) == true)
{
c.x = 300;
}
function objectA():void
{
object = a;
object.addEventListener(MouseEvent.MOUSE_OVER,objectFun);
}
function objectB():void
{
object = b;
object.addEventListener(MouseEvent.MOUSE_OVER,objectFun);
}
function objectFun(event:MouseEvent):void
{
object.addEventListener(MouseEvent.MOUSE_DOWN,drag);
object.addEventListener(MouseEvent.MOUSE_UP,sDrag);
}
function drag(event:MouseEvent):void
{
object.startDrag();
}
function sDrag(event:MouseEvent):void
{
object.stopDrag();
}
}
}
}
Did you tried getBounds() ?
I suggest condition:
if (c.getBounds(c.parent).containsRect(a.getBounds(c.parent))
|| c.getBounds(c.parent).containsRect(b.getBounds(c.parent))) {
c.x = 300;
}
IMO the best way is check it triggered by ENTER_FRAME event, atached for any of object.

Access of undefined property Keyboard (AS3)

I'm new to Actionscript 3 and I'm wanting to allow a circle to move down using the down arrow on the keyboard. Here's my code:
package {
import flash.display.MovieClip;
import flash.events.KeyboardEvent;
import flash.ui.Keyboard;
public class Circle extends MovieClip {
public function Circle() {
// constructor code
var speed:int = 3;
addEventListener(KeyboardEvent.KEY_DOWN,keyIsDown);
function keyIsDown(event:KeyboardEvent) {
if(event.keyCode == Keyboard.DOWN) {
y = y+=speed;
}
}
}
}
}
When I test it, nothing happens when I press the down key. Anyone know what's wrong with the code?
Try adding KeyBoard events to the stage instead of to the class. Additionally, I would not nest functions like that, bad practice in general. Also the line y = y+=speed; is confusing, shouldn't it just be y += speed; ?
EDIT: Sorry, I guess stage will be null in the constructor, I've added a ADDED event listener.
Try this:
package {
import flash.display.MovieClip;
import flash.events.Event;
import flash.events.KeyboardEvent;
import flash.ui.Keyboard;
public class Circle extends MovieClip {
public function Circle() {
// constructor code
var speed:int = 3;
addEventListener(Event.ADDED, onAdded);
}
private function onAdded(event:Event) {
stage.addEventListener(KeyboardEvent.KEY_DOWN,keyIsDown);
}
private function keyIsDown(event:KeyboardEvent) {
if(event.keyCode == Keyboard.DOWN) {
y += speed;
}
}
}
}

Disabling Nested MovieClips After Removing Parent Movieclip

In some of the level MovieClips I have for my Flash game, there is a certain MovieClip that controls a custom-built camera that I've created. Both the camera and the MovieClip function correctly and smoothly. However, whenever a level is completed and removed from the game, I get an Error #1009 not recognizing the checkCameraZoom function. Also, this MovieClip is not added dynamically with code, but rather placed in the specified level MovieClips from the Library before run-time. Is there any possible way to fix this error?
ZoomOutArea Class:
package com.engine.assetHolders
{
import com.engine.documentClass.*;
import flash.display.*;
import flash.events.*;
public class ZoomOutArea extends MovieClip
{
public function ZoomOutArea():void
{
this.visible = false;
this.addEventListener(Event.ADDED_TO_STAGE, initZoomOutArea);
// constructor code
}
public function initZoomOutArea(event:Event):void
{
this.addEventListener(Event.ENTER_FRAME, checkCameraZoom);
}
public function checkCameraZoom(event:Event):void
{
if (Document.getInstance != null)
{
if (this.hitTestObject(MovieClip(parent.parent).player.playerHitArea))
{
this.hitTestZoom(0.6);
}
if (! this.hitTestObject(MovieClip(parent.parent).player.playerHitArea))
{
this.hitTestZoom(1);
}
}
}
public function hitTestZoom(zoomLevel):Number
{
MovieClip(parent.parent).cameraScale = zoomLevel;
return zoomLevel;
}
}
}
You register the class for ENTER_FRAME events when it's added to the stage, but you never unregister it. So that's why it keeps going even after it has been removed from the stage, and has no parent anymore.
You could add another listener for Event.REMOVED_FROM_STAGE and then remove the checkCameraZoom listener:
public function initZoomOutArea(event:Event):void
{
this.addEventListener(Event.ENTER_FRAME, checkCameraZoom);
this.addEventListener(Event.REMOVED_FROM_STAGE, onRemoved);
}
private function onRemoved(event:Event):void
{
this.removeEventListener(Event.ENTER_FRAME, checkCameraZoom);
}

how to add a limited amount of objects to the stage

So I have a box exported as Box in my library. I have tried :
package {
import flash.display.MovieClip;
import flash.events.*;
public class Main extends MovieClip {
private var _box:Box=new Box ;
private var boxAmount:Number=0;
private var boxLimit:Number=16;
private var _root:Object;
public function Main() {
addEventListener(Event.ENTER_FRAME, eFrame);
addEventListener(MouseEvent.MOUSE_DOWN, mouseclick);
}
private function eFrame(event:Event):void {
if (boxAmount <= boxLimit) {
boxAmount++;
_box.y=Math.random()*stage.stageHeight;
_box.x=Math.random()*stage.stageWidth;
addChild(_box);
} else if (boxAmount >= boxLimit) {
removeEventListener(Event.ENTER_FRAME, eFrame);
} else {
addEventListener(Event.ENTER_FRAME, eFrame);
}
}
}
}
But it did not work as planned.
What I am trying to do is make my box stay on the screen at a random place on the stage and remove it when clicked (but that will come later). This code is for some reason adding the object to the stage and then removing it and adding it again up to 16 times.
Thanks
I it seems like you have created one _box, and re-add it to the timeline on enter frame. It should work if you create a new box instance inside the eFrame function rather than before it, then you keep reassigning to the same variable name, rather than reusing the one object eg:
package {
import flash.display.MovieClip;
import flash.events.*;
public class Main extends MovieClip {
private var boxAmount:Number=0;
private var boxLimit:Number=16;
private var _root:Object;
public function Main() {
addEventListener(Event.ENTER_FRAME, eFrame);
addEventListener(MouseEvent.MOUSE_DOWN, mouseclick);
}
private function eFrame(event:Event):void {
if (boxAmount<=boxLimit) {
boxAmount++;
var _box:Box=new Box ;
_box.y=Math.random()*stage.stageHeight;
_box.x=Math.random()*stage.stageWidth;
addChild(_box);
} else if (boxAmount >= boxLimit) {
removeEventListener(Event.ENTER_FRAME, eFrame);
} else {
addEventListener(Event.ENTER_FRAME, eFrame);
}
}
}
}
In your code you are only ever creating one box. Your enterFrame handler is just assigning it a new random position 16 times. If you want 16 boxes you'll need to create a new box each time in the enterFrame function.
But you don't need to use the ENTER_FRAME event here. You could just use a for loop or a while loop to create the 16 boxes.
Here's some code:
package {
import flash.display.MovieClip;
import flash.events.*;
public class Main extends MovieClip {
private var boxAmount:Number=0;
private var boxLimit:Number=16;
public function Main() {
addBoxes();
}
private function addBoxes():void {
while (boxAmount<=boxLimit) {
boxAmount++;
var box:Box = new Box();
box.y=Math.random()*stage.stageHeight;
box.x=Math.random()*stage.stageWidth;
addChild(box);
// listen for mouse clicks
box.addEventListener(MouseEvent.CLICK, onBoxClick);
}
}
private function onBoxClick(e:MouseEvent):void {
var clickedBox:Box = e.target as Box;
removeChild(clickedBox);
}
}
}
I removed your enterFrame handler and just made a function called addBoxes. I'm using a while loop to crate the boxes. Notice that each time through the loop I'm creating a NEW box, not just reusing the old one. I'm also adding a mouse click event listener to each box so it can be removed from the stage when clicked.
You'll surely want to change some of this to get it to work for your purposes, but it should get you headed in the right direction.
What you have at the moment is just repositioning the same box over and over because you only ever create one Box instance. You need to create multiple instances of Box and add them to the stage individually.
package {
import flash.display.MovieClip;
import flash.events.*;
public class Main extends MovieClip {
private var boxAmount:Number=0;
private var boxLimit:Number=16;
private var _root:Object;
public function Main() {
addEventListener(Event.ENTER_FRAME, eFrame);
addEventListener(MouseEvent.MOUSE_DOWN, mouseclick);
}
private function eFrame(event:Event):void {
if (boxAmount<=boxLimit) {
boxAmount++;
//create a new box instance
var _box:Box = new Box();
_box.y=Math.random()*stage.stageHeight;
_box.x=Math.random()*stage.stageWidth;
addChild(_box);
} else {
removeEventListener(Event.ENTER_FRAME, eFrame);
}
}
}
}
Although the variable boxAmount suggests otherwise, you said you only want one box. So, to do this, you just need to move the following lines into the constructor (Main).
_box.y=Math.random()*stage.stageHeight;
_box.x=Math.random()*stage.stageWidth;
addChild(_box);
Then remove or disable the enter frame event. You don't need it in this case. To check if the box got clicked, attach the listener to the box itself, not to it's parent:
_box.addEventListener(MouseEvent.MOUSE_DOWN, mouseclick);
if (boxAmount<=boxLimit) {
// ...
} else if (boxAmount >= boxLimit) {
// ...
} else {
// ...
}
This part looks really strange. The first condition covers a case that is also covered by the second condition, together they already cover all possible cases. boxAmount is either less or equals to boxLimits or it is greater than it. Checking for equality twice is confusing. There is no need to include the last else statement. It actually has the same behaviour as the following code.
if (boxAmount<=boxLimit) {
// ...
} else if (boxAmount > boxLimit) {
// ...
}