AS3 Custom Depth Control - actionscript-3

I am trying to create a way of controlling movieclip depths, which movieclip is show above another, so that I can set the depth of a movieclip to any number and they will be displayed with higher values above lower values.
I was thinking of creating a MovieClipDepth class that extends MovieClip with the added property depth, and a Container class that extends DisplayObjectContainer which all objects will be placed inside of.
The Container class will override the addChild method to update the child display order when a child is added.
What I need help with is how do I reorder the children according to
their depth value?

As you can read in the comment below your question, there are several methods for this.
But actually, what you asked "set the depth of a movieclip to any number" can't really be done in AS3. If i'm correct, you could do this in AS2, so...
... how was it ...
_root.createEmptyMovieClip("mc", -1000);
or
_root.createEmptyMovieClip("mc1", 1);
_root.createEmptyMovieClip("mc2", 10);
worked, but does not work in AS3. In AS3 depth starts with 0 and you can't force a DisplayObject to sit on a level what is not continous from zero.
So the depths' of 3 movieclips in a container is only possible with these values: 0, 1, 2.
Depth can't be a negative number for example.
Now, if you want to build a custom depth manager, you can do that, but you have to consider these facts.
So to say, you could create virtual depths.
So I guess, you could override the addChildAt method for example. At the moment, if you would give a wrong number: negative, or higher then the number of children, flash would give back the error:
RangeError: Error #2006: The supplied index is out of bounds.
So mc.addChildAt(newchild, -1000) gives an arror.
But with overriding the method, you could make a trick, so you could store the depths in an array. You could store any numbers and then transform that order for the needs of AS3.
Like pairing the depths with the added children, sorting the array by the depths, then manage the children according to the order.
If you have more questions, feel free to ask, hope this gets you closer to the solution.

I suggest you take a look at this tutorial :
A Tour of Depths Management Methods on the website http://www.flashandmath.com/. I presume you not a newbie .
The link is this:
http://www.flashandmath.com/intermediate/depths/index.html

Related

How to detect if there is a drawing/graphic drawn on a movie clip in AS3?

I am a newbie to AS3. I have a movie clip.I want to know if there is a drawing/graphic drawn over movie clip at all?
Simple, check the width and height of the MovieClip. Assuming you mean the MovieClip itself contains the drawing/graphic.
After seeing Fygo's comment
I did some testing and found out that the scale properties of the MovieClip will change depending on whether or not it has any graphics.
Meaning if you set the width and height to zero, the corresponding scaleX and scaleY will also be set to zero. So what you can do is check the scale AND the dimensions of the MovieClip. If both scales are 1:1 and both dimensions are 0:0, that means you didn't mess with the dimensions and it truly is graphic-less.
trace (awd.scaleX, awd.scaleY, awd.width, awd.height);
//If you get 1 1 0 0 as the output, the MovieClip is empty
Use readGraphicsData(). I assume that if it's empty it means there is nothing drawn there :)
It's not perfect though, read the reference
Maybe you just mean collision detection? To detect if two movieClips are touching...?
For that you need either:
HitTestObject - (checks if two objects touching by their box boundaries) - Link:
or HitTestPoint - (read description carefully) - Link:
A good tutorial explaining both methods is here: - Link:
example code:
if ( MC_one.hitTestObject(MC_two) )
{
trace("MovieClip One is touching/over MovieClip Two");
//add code needed to happen when touching/over. example below
//MC_two.gotoAndStop(2); //example tells touched MC_two to change frame to 2
}

nested collision starling as3

I am using starling and tweenMax frameworks in my project.
The trouble I am running into is this:
For the purpose of animating along different paths, I am using tweenmax.
There is one _leaderEnemy that animates along a path and I am pushing several other _shooterEnemy (they are of the same class) into it.
public function createEnemies(enemyNo:int, path:Array, offset:int):void
{
for(var i:uint=1;i<=enemyNo;i++){
if (i==1){
_leaderCount++;
_leaderEnemy = new ShooterEnemy();
_leaderEnemy.x=600;
_leaderEnemy.y=300;
_leaderEnemy.name="_shooterEnemy"+_leaderCount;
this.addChild(_leaderEnemy);
leaderEnemyArray.push(_leaderEnemy);
}
else
{
_leaderCount++;
_shooterEnemy= new ShooterEnemy();
_shooterEnemy.x=0;
_shooterEnemy.y=(offset*(i-1));
_shooterEnemy.name="_shooterEnemy"+_leaderCount;
trace("no: "+_shooterEnemy.name);
leaderEnemyArray.push(_shooterEnemy);
_leaderEnemy.addChild(_shooterEnemy);
}
}
Now I want to check for collision using starling between each of the _leaderEnemy and the _shooterEnemy inside it with _shooterHero.
Running this array successfully checks collision with the whole group i.e. _leaderEnemy but not the individual ones inside it.
Technically, I should be able to do this just by:
var Track:Object;
for(var i:uint=0;i<leaderEnemyArray.length;i++) {
Track=leaderEnemyArray[i];
if (Track.bounds.intersects(_shooterHero.bounds)){
Track.rotation=deg2rad(70);
}
}
It may be something stupid I am doing. But I have not been able to solve this.
Any help on this would be appreciated.
Some other questions I have:
Can I check for collision with _shooterHero from inside the _shooterEnemy's class?
I have tried:
if (this.bounds.intersects(stage.getChildByName("_hero"))){
}
although it did not work.
Can I check for collision of one Enemy with everything on stage, so I can assign individual functions for his each contact?
For example: hit with hero: die; hit with another enemy: turn around
If you need more info, I will be happy to provide it.
Thank You.
Can I check for collision of one Enemy with everything on stage, so I can assign individual functions for his each contact? For example: hit with hero: die; hit with another enemy: turn around
Of course you can. You should! This is approximatively how collision engines works.
Running this array successfully checks collision with the whole group i.e. _leaderEnemy but not the individual ones inside it.
Nope. It won't work. Because the bounds property use the parent coordinates.
Meaning you can intersect each child display (of same container) with each other.
But you shouldn't intersect a child display of A with a child display of B.
Except if you convert every bounds coordinates (which are local) to global.
http://doc.starling-framework.org/core/starling/display/DisplayObject.html#localToGlobal()
Using Track.bounds.intersects is one way of checking collosions. Another would be to use hitTest method of starling.displayDisplayObject
You could also check the distance of your hero and other enemies calculated by a pythagorean theorem type calculation.
Are you checking enemies against each other? If you have many enemies you might want to look into "flocking" algorithms. Keith Petes covers this subject nicely in his book Advanced Actionscript Animation.

AS3: weird getBounds() result

EDIT2: It seems that the big numbers are created because the movieclip doesnt hold any bipmapdata, but Im yet not sure about it, but my real mistake was that I just forgot "this" infront of one "getBounds" ... project size was to big and I couldnt find the bug =)
EDIT: tried to use seperate containers, for the movieclips, and did all this in the root class ... everything worked fine, when I used seperate containers and attached everything to the charakter class it got screwd up again
OLD:
Hey I am making a game right now and I want to get the bounds of the charakter body.
To understand how I did set the whole thing up I explain the hirarchy.
The class of my flash document is "game.as". "game.as" adds a Child of the class Charakter
my Charakterclass has a Movieclip for every body part, for example the "head"
every bodypart has a movieclip which contains the picture of the bodypart, in this case "head".
When I now try to use the getBounds(head.mc) inside the "head" class I get really weird results. ussualy something around x=64001, y=64001, width = 0, height = 0;
I found a way how to solve this problem by simply using the getBounds(head.mc) function not inside the head, but inside the Charakter class .... but this is not what I actually want to do, I would like to use the getBounds(head.mc) function inside the head class.
Any ideas why the results are so weird or what I have to do? Im very thankfull for every opinion, because this doesnt seem logical to me xD
getBounds() is inaccurate. Please read the following posts to understand the issue.
getBounds "wrong" results (Source)
When getting bounds of an object relative to it's OWN coordinate system,
those values will NOT be scaled.
getBounds() returning incorrect height (Source)
From inside head_mc, try getBounds(this.parent); (you may want to test to see if the parent exists first) - this should give you the bounds of your head_mc as its container sees it, which I think is what you want, but called from inside head_mc, as you request.
bitmapdata is right, though - getBounds() can sometimes give some odd results. It looks to me like you might be asking the question before you add head_mc to the stage, and are therefore getting the undefined values for width/height/x/y.

Children of Children of MovieClip not showing up when MovieClip is added to stage?

This problem seems very simple to me, but I've been unable to fix it, or find an answer anywhere.
This is in a class constructor for a class called block, block_maker is the object that called the constructor, an instance of level.
this.bitmap = new Bitmap(this.bitmap_data);
this.addChild(this.bitmap);
this.block_maker.stage_foreground.addChild(this);
In level, stage_foreground is added to the stage, but nothing appears. trace(stage_foreground.numChildren); shows the correct count of children, and var temp = (this.stage_foreground.getChildAt(0)); trace(temp.numChildren); correctly but the children OF the children don't actually show up, the stage just stays blank.
When I change the above code to
this.bitmap = new Bitmap(this.bitmap_data);
this.block_maker.stage_foreground.addChild(this.bitmap);
the blocks appear on the stage, as children of level_instance.stage_foreground, but with this method, the bitmaps aren't appropriately positioned, as they have no position data. I can simply give this.bitmap x and y positions, and it works, but I am curious as to why it won't work when just adding the bitmap as a child to the block and then adding that as a child to stage_foreground.
I've tried replacing this.bitmap with a number of other object classes, such as a temporary MovieClip I made, or a Shape, but nothing shows up, so I know it has nothing to do with it being a Bitmap.
As you stated
This is in a class constructor for a class called block, block_maker
is the object that called the constructor, an instance of level.
this.bitmap = new Bitmap(this.bitmap_data);
this.addChild(this.bitmap);
this.block_maker.stage_foreground.addChild(this);
The level class needs to to extend a display object for it to show up.
In other words
"this"
has to be a display object or extend it in some form.
The reason this doesn't work.
this.block_maker.stage_foreground.addChild(this);
and this does
this.block_maker.stage_foreground.addChild(this.bitmap);
Is because "this" is not a display object but "this.bitmap" is.
The DisplayObject class is the base class for all objects that can be placed on the display list.
First of all, even though it's not neccesary, I'd suggest to make a classname start with a capital letter, and vars always start with a lower-case letter. It's a common 'rule' in AS3 that's mainly to avoid confusion.
The problem most likely lies within you use of this; what you're doing is adding this into this. It seems to me it's not a proper way of coding.
Also, since all of the other attempts didn't work; have you tried to make the var you want ot add a public static var?

ActionScript Measuring 3D Depth

i'm having a difficult time understanding how to control the z property of display objects in a 3D space. i know how depth works, but what i don't understand is how i can get the maximum depth, or the number at which the display object just disappears into the background.
i assume depth is based on the stage's width and height, and that is why assigning the same depth of the same display object appars mismatched with different stage sizes.
so how can i appropriately measure depth?
You need to consider the childIndex property. There is no Z-index in actionscript.
To get the depth you could use:
// returns the number of direct display children in stage
stage.numChildren;
// returns the number of direct display children in you object
myObj.numChildren;
To set the child Z-index use
//sets the newIndex of child in stage
stage.setChildIndex(child:DisplayObject, newIndex:int):void;
If newIndex is 0 then child is top visible element.
newIndex must be in [0, numChildren-1] else flash will throw errors
Take care.
As of Flash 10, there is a 'z' property.
Checkout this link for a tutorial:
http://www.kirupa.com/developer/as3/intro_3d_as3_pg1.htm
it's explained here: Perspective in Flash