Game Maker:DoAdd:2:undefined value - undefined

Code in Step:
If (keyboard_check(ord("W"))) { phy_position_y -= 4;
}
If (keyboard_check(ord("A"))) { phy_position_x -= 4;
}
If (keyboard_check(ord("S"))) { phy_position_y += 4;
}
If (keyboard_check(ord("D"))) { phy_position_x += 4;
}
Pressing any of the WASD keys produces the above error.

Check if phy_position_y and phy_position_x have been initialised before.
It tries to add 4 to it's value, but it can't do that because it doesn't know it's own value. (Even if it's 0, you should initialise it with 0)
So for example, you can put this in your Create Event:
phy_position_x = 0;
phy_position_y = 0;
Alternatively, assuming you'll decide the objects current position, you can also use the build-in variables x and y:
If (keyboard_check(ord("W"))) { y -= 4;
}
If (keyboard_check(ord("A"))) { x -= 4;
}
If (keyboard_check(ord("S"))) { y += 4;
}
If (keyboard_check(ord("D"))) { x += 4;
}
I think eventually, you'll need to define the x and y anyways if you want to move your object, but understanding custom variables and the need to define them first is a key.

phy_position_x and phy_position_y can only be used if Uses physics flag is checked for the object. Either enable that, or use the regular x and y as Steven suggested.

Related

Moving away object when hit each other

I don't wanna to overlap each other the objects.Also I wanna keep the objects in stage limit.The buttons must move away when hit each other.I tried hitTestObject but buttons move like this.
Sample move code for fish 2 *UPDATE
var fish2x:Number=10;
var fish2y:Number=14;
 
stage.addEventListener(Event.ENTER_FRAME,h42);
function h42(s:Event = null) {
fish2.x+=fish2x;
fish2.y+=fish2y;
if ((fish2.x>=stage.stageWidth-fish2.width/2)|| (fish2.x <= fish2.width/2 )) {
fish2x*=-1;
}
if ((fish2.y>=stage.stageHeight-fish2.height/2)|| (fish2.y <= fish2.height/2 )) {
fish2y*=-1;
}
if (fish2.hitTestObject(fish3)){
fish2y *= -1;
fish3y *= -1;
h42();
}
}
Also I tried in diffrent function
stage.addEventListener(Event.ENTER_FRAME,crash);
function crash(s:Event) {
 
if (fish2.hitTestObject(fish || fish3 )) {
fish2y*=-1;
message.text="crash";
}
}
For more than 2 fish not work.
I set null fish2 and fish 3 than I use this code.
if (fish2.hitTestObject(fish3 || fish4)){
fish2y *= -1;
fish2x *= -1;
h42();
}
I changed hittestoject all off them.All function change like this but it not work.
Update 2
Now it's no error,but not happens when fish3 hit each other.I removed "null" fish and fish 3 just used for fish 2.
if (fish2.hitTestObject(fish || fsih3)){
fish2y *= -1;
fish2x *= -1;
fishy*=-1;
fishx*=-1;
fish3y*=-1;
fish3x*=-1;
}
}
I think it is because they are both moving. When you check collisions between A and B Fishes, if the collision is true, don't just change their speed by *=-1. Instead, also move them one time.
if (A.hitTestObject(B)){
Ay *= -1;
Ax *= -1;
By *= -1;
Bx *= -1;
h42();
}
and add null to your default value like this:
function h42(s:Event = null) {

as3 move object back and forth on iPad or tablet

I am working on a 2d project for iPad where a ball moves back and forth. When it hits the border it has to rotate a bit and roll back in another direction and leaving a child behind that also starts to move and follows a random path. (I made the project in Scratch. See code.)
ball_mc.addEventListener(Event.ENTER_FRAME, moveBall);
function moveBall(e:Event):void {
ball_mc.rotation += 1;
if (ball_mc.x < (stage.stageWidth - 100)) {
//trace('move forward');
ball_mc.x += 2;
} else {
// while(ball_mc.x > 100)?
// trace('move backward');
// how does it roll back?
ball_mc.x += -2;
}
}
}
You need a variable that holds the value of the direction or velocity. This variable should be changed to 2 if the ball passes a left side boundary and changed to -2 if the ball passes a right side boundary. Like this:
var ballSpeed:Number = 0; // this should go where you declare global variables such as at the beginning of your main class before the constructor
ball_mc.addEventListener(Event.ENTER_FRAME, moveBall);
function moveBall(e:Event):void {
ball_mc.rotation += ballSpeed;
if (ball_mc.x < (stage.stageWidth - 100)) {
ballSpeed = 2;
} else if (ball_mc.x > stage.stageWidth){
ballSpeed = -2;
}

How to scale an object so that when it equals 0 it will go to the next frame? AS3

Ok, I've got some script for the Alice in Wonderland scene were she is eating cake and drinking potion to be bigger and smaller. I have been able to link two buttons so that when eat_me is clicked she is made smaller and when drink_me is clicked she is made bigger.
What I want to achieve is for Alice to be given a number like 2 and when you click eat_me it goes down by 1 and when you click drink_me it goes up by 1. I then want AS3 to recognise when Alice is at 0 to then move to the next frame. I have some code but not too sure whether I am close or not.
var alice_size:Number = 2;
drink_me.addEventListener(MouseEvent.MOUSE_DOWN, resizeAlice);
function resizeAlice(event:MouseEvent):void {
sitting_alice.width = sitting_alice.width * 2;
sitting_alice.height = sitting_alice.height * 2;
{if (drink_me.hitTestObject(sitting_alice))
alice_size = alice_size +1;}
}
eat_me.addEventListener(MouseEvent.MOUSE_UP, resizeAlice2);
function resizeAlice2(event:MouseEvent):void {
sitting_alice.width = sitting_alice.width / 2;
sitting_alice.height = sitting_alice.height / 2;
{if (eat_me.hitTestObject(sitting_alice))
alice_size = alice_size -1;}
}
if (alice_size == 0){
gotoAndStop (405)
}
Move alice_size's declaration so that is a member of the current class. I would advise doing the same for resizeAlice() and resizeAlice2(), though you don't have to do it for them. Also drink_me and eat_me are listening for different types of events; make them both either listen for MouseEvent.MOUSE_UP or MouseEvent.CLICK. I'm not sure why hitTestObject() is being used, but the reason may lie in other code you have.
What you have is pretty close.
The event you want is MOUSE_CLICK.
Test for the less than zero condition when you are deciding whether or not to advance the frame -- so you don't 'pass' 0, and never get to the frame you want.
Try to use more descriptive function names.
Get rid of the hit test too, unless there is some other reason you need it there (I left it in).
My version of your code:
var alice_size:Number = 2;
drink_me.addEventListener(MouseEvent.MOUSE_CLICK, growAlice);
function growAlice(event:MouseEvent):void {
sitting_alice.width *= 2;
sitting_alice.height *= 2;
if (drink_me.hitTestObject(sitting_alice)) {
alice_size = alice_size +1;
}
}
eat_me.addEventListener(MouseEvent.MOUSE_CLICK, shrinkAlice);
function shrinkAlice(event:MouseEvent):void {
sitting_alice.width *= 0.5;
sitting_alice.height *= 0.5;
if (eat_me.hitTestObject(sitting_alice)){
alice_size = alice_size -1;
}
}
if (alice_size <= 0){
gotoAndStop (405);
}

Action Script 3. Animation loop forever after gotoAndStop() and have lag during animation when character have collisions

I'm creating simple flash game. I have problem, animation loop forever after I user gotoAndStop() and I have lag when during animation if character have collision with ground or any stage (if character flying on the air don't have any lags)
Here is collision list:
var myCollisionList:CollisionList = new CollisionList(Hero);
myCollisionList.addItem(ground);
myCollisionList.addItem(ground3);
myCollisionList.addItem(ground5);
myCollisionList.addItem(ground4);
And here is my part of code where jumping with animation.
if(Hero.y_speed>0 && myCollisionList.checkCollisions().length > 0 )
{
Hero.y_speed=0;
Hero.x_speed=0;
if(space)
{
if (ground.hitTestPoint(Hero.x + 28, Hero.y+20, true))
{
Hero.gotoAndStop("attack");
stop();
Hero.y_speed = -20;
}
}
}
UPDATE:
Screenshot of the map:
UPDATE 2:
Here is part of code for move character to left (to right side the same) side, I know Its terrible, but I don't know how to make It better.
pakopos - name of CollisionList
fonas - background
var pakopos:CollisionList = new CollisionList(Hero);
pakopos.addItem(ground);
pakopos.addItem(ground3);
pakopos.addItem(ground5);
pakopos.addItem(ground4);
if(left){
Hero.x_speed = -walkspeed;
setDirection(1);
if(pakopos.checkCollisions().length > 0) {
if (ground5.hitTestPoint(Hero.x - 26, Hero.y-120, true)) {
trace("Touching left side - ground5");
ground5.x += 0;
ground4.x += 0;
ground3.x += 0;
fonas.x += 0;
Enemy.x += 0;
}
else if (Enemy.hitTestPoint(Hero.x - 26, Hero.y-120, true)) {
trace("Touching Enemy");
ground5.x += 0;
ground4.x += 0;
ground3.x += 0;
fonas.x += 0;
Enemy.x += 0;
}
else if (ground3.hitTestPoint(Hero.x - 26, Hero.y-120, true)) {
trace("Touching left side - ground3");
ground5.x += 0;
ground4.x += 0;
ground3.x += 0;
fonas.x += 0;
Enemy.x += 0;
}
else if (ground4.hitTestPoint(Hero.x - 26, Hero.y-120, true)) {
trace("Touching left side - ground4");
ground5.x += 0;
ground4.x += 0;
ground3.x += 0;
fonas.x += 0;
Enemy.x += 0;
}else
{
Hero.x_speed = 0;
ground5.x += 4;
ground4.x += 4;
ground3.x += 4;
fonas.x += 4;
Enemy.x += 4;
}}
else {
ground5.x += 4;
ground4.x += 4;
ground3.x += 4;
fonas.x += 4;
Enemy.x += 4;
}}
Your code is very cryptic so it's hard to say what's going on without actually debugging it but my guess is that you're checking collisions multiple times every time your posted code runs. You should check the documentation of the checkCollisions() function that you use since it seems to return an array of results. It likely gives you all collisions that it found among the objects in the collision list so you don't have to call hitTestPoint() directly afterwards.
Edit:
I'm not familiar with CDK that you use in your code but it returns an array of collision results where each result has the colliding objects, their angle and if they're overlapping. For what you're trying to do it seems like an overkill but as I said, I'm not familiar with it - it may be a lot faster then hitTestPoint().
I'd recommend using only one hit test method - either use CDK or use hitTestPoint() but not both. Both will give you pixel perfect detection results. If you use CDK, read the documentation on how checkCollisions() works. You'd have to do something like this:
...
var oResults:Array = pakopos.checkCollisions();
var nCount:int = oResults.length;
if (nCount > 0)
{
for ( var i:int = 0; i <nCount; i++ )
{
var oHit:Object = oResults[i];
// TODO check `oHit.object1` and `oHit.object2` to see which objects
// collided and do something based on that
// You may have multiple results since your hero may collide with
// 'ground' and 'ground4' at the same time.
}
}
Your collision group (pakopos) setup for CDK seems to be off - you won't have to determine if there's a collision between all the objects in your group - I assume you don't care if ground collides with ground4 but you added both to your collision list.
I think (not sure) that checkCollisions() tries to check all objects in the group against all other objects. What you need is check one object (Hero) against a list of objects (the various ground objects). That's a massive difference between the number of checks. This and your extra calls to hitTestPoint() can easily account for your lag.

Flash (AS3) Movieclip Rotation

if (rotCW)
{
tramp1.rotation += 3;
if (tramp1.rotation = 90){
tramp1.rotation += 0;
}
}
I'm trying to make it so that if the movieclip's rotation is 90, its rotation speed is 0.
But every time I press the ' key (which triggers rotCW), the movieclip's rotation just goes to 90.
your problem is assignment within the 2nd condition. you need to use "=="
if (rotCW)
{
tramp1.rotation += 3;
if (tramp1.rotation == 90){
tramp1.rotation += 0;
}
}
edit: the +=3 line you have executes regardless of angle. if you are passing 90 and dont want to, you can test for the opposite condition and increment in that case. eg: if less than 90.
if (rotCW)
{
if (tramp1.rotation < 90){
tramp1.rotation += 3;
}
}