Strike Force Heroes 2
The explosive sequel to the hit game Strike Force Heroes!
3.97 / 5.00 8,473 ViewsObsolescence
Defeat the enormous mechanical beasts--and become one of them.
4.01 / 5.00 42,206 ViewsAS:Constant Distance
AS:Main
Saw there wasn't one of these yet, so decided to make one. Any errors/mistakes please alert me straight away.
Ever wanted to ensure 2 points (e.g movie clip co ordinates) are always a constant distance from eachother?
We can do this using trigonometry through Kinematics (or Inverse Kinematics)
Required reading:
-AS:Trigonometry by BleeBlap
-Basic knowledge of most AS:Main topics
Kinematics is the process of finding a point in space when given the length and angle of an armature.
Kinematics can be used to achieve effects such as a ragdoll, or to bind wheels on a car/bike together during gameplay.
I’m just going over the VERY BASICS in this tutorial; the possibilities for application of the concept are near endless. However going into detail here would be unnecessary and over complicated.
The Trig
First take a look at the example diagram .
Try dragging point 2 (bottom one) with the mouse, you will see that point 1 (top one) is pushed away to always keep a constant distance.
We work with the points as a triangle, with the distance between their _x co ordinates acting as side X, and the distance between their _y co ordinates acting as side Y.
Place your two point mc’s on stage, give them instance names point1_mc and point2_mc.
In our example, point 2 is made draggable when clicked, and will have authority over point 1, force changing its _x and _y values to always maintain a constant distance away.
This means our kinematics code will just be applied to point 1, as point 2 isn’t being affected.
(Bear in mind Flash works with radians instead of degrees while performing trigonometric equations)
I’m coding on the frame itself for simplicity purposes during the tutorial, but you can easily change yours to be placed onto the movie clips themselves.
var hypotenuse:Number = 170;
//Our defined hypotenuse side length (see diagram)
//This is important for finding the allowed X and Y sides of the triangle, and determines the distance the points will always be from eachother
_root.onEnterFrame = function() {
//Manipulates values every frame (example is running at 30 fps)
point2_mc.xDist = point1_mc._x-point2_mc._x;
//Finds the length of side X in the diagram by subtracting point 2's _x from point 1's
point2_mc.yDist = point1_mc._y-point2_mc._y;
//Finds the length of side Y in the diagram by doing the same with _y co ordinates
point2_mc.angle = Math.atan2(point2_mc.yDist, _root.point2_mc.xDist);
//Finds the Angle marked in the diagram using tangent (opposite side (Y) / adjacent side (X)
point1_mc._x = point2_mc._x + (Math.cos(point2_mc.angle)*hypotenuse);
// In triangles ,we know that an angles Cosine value is equal to the result of dividing the side adjacent to it (side X in the diagram) by the Hypotenuse side.
We can work this formula backwards to find the allowed value of side X when both the Angle and the Hypotenuse already have values.
We first find the cosine of the angle, using Math.cos()
We then multiply this value by the hypotenuse, to get side X. (remember Cosine = Side X / Hypotenuse). So side X is given a value based on the values of the Hypotenuse and the Angle.
As the Hypotenuse is always constant, the X value will be lengthened or shortened depending on the angle, and the effect will be that when the _y distance between the points become greater, the _x distance will become shorter in ratio.
We then have to add side X onto the _x co ordinate of point 2, to get point 1’s allowed _x co ordinate.
point1_mc._y = point2_mc._y + (Math.sin(point2_mc.angle)*hypotenuse);
This is basically the same method, but finds side Y instead of side X (because The Sine value of an angle = opposite side (side Y in diagram ) / hypotenuse).
Side Y is then added onto point 2’s _y co ordinate value to get point 1’s allowed _y value.
point2_mc.onPress = function() {
point2_mc.startDrag();
};
//Makes point 2 draggable when clicked
point2_mc.onRelease = function() {
point2_mc.stopDrag();
};
//Makes point 2 stay put when released
};
//End of enterFrame handler
Complete code on Frame
var hypotenuse:Number = 170;
_root.onEnterFrame = function() {
point2_mc.xDist = point1_mc._x-point2_mc._x;
point2_mc.yDist = point1_mc._y-point2_mc._y;
point2_mc.angle = Math.atan2(point2_mc.yDist, _root.point2_mc.xDist);
point1_mc._x = point2_mc._x+(Math.cos(point2_mc.angle)*hy
potenuse);
point1_mc._y = point2_mc._y+(Math.sin(point2_mc.angle)*hy
potenuse);
point2_mc.onPress = function() {
point2_mc.startDrag();
};
point2_mc.onRelease = function() {
point2_mc.stopDrag();
};
};
Examples and other Tutorials
-GotoAndPlay.it - slightly more in-depth and complex
-Something for the hardcore people
Very useful for Artificial intelligence.
Extremely detailed and well explained.
Good job :D
At 10/1/05 07:46 AM, -Toast- wrote: Very useful for Artificial intelligence.
Yeah I guess, it would be for realistic attacks and damage
Extremely detailed and well explained.
Thanks, glad there aren't any errors spotted yet cos I really screwed the last one of these I did up
Good job :D
<3
Yeah, I started learning this stuff a few weeks ago, and I have to say it's very fun to work with.
Pretty decent tutorial too.
Maybe you could show a example of the what the AS can do. Could you?
At 10/1/05 07:51 AM, bigexplosions wrote: Maybe you could show a example of the what the AS can do. Could you?
Lol, I posted a couple at the bottom.
At 10/1/05 07:51 AM, bigexplosions wrote: Maybe you could show a example of the what the AS can do. Could you?
umm yeah he did plus he posted a bunch of links which expand on this alot more
And tost how would this be good for AI exactly?
- Matt, Rustyarcade.com
At 10/1/05 07:51 AM, bigexplosions wrote: Maybe you could show a example of the what the AS can do. Could you?
If you learn IK (Inverse Kinematics) REALLY well, you can make stuff like this. But I wouldn't expect you to learn it that well. You can also do stuff like bone structure, or the simplest IK technique, IK chains.
At 10/1/05 07:56 AM, Rantzien wrote:At 10/1/05 07:51 AM, bigexplosions wrote: Maybe you could show a example of the what the AS can do. Could you?If you learn IK (Inverse Kinematics) REALLY well, you can make stuff like this. But I wouldn't expect you to learn it that well. You can also do stuff like bone structure, or the simplest IK technique, IK chains.
Yeah I dont see why people have such orgasms over that fucking file. I mean www.teagames.com has a shit load of games using just as impressive realism (true physics) as that so why the wetness over it?
- Matt, Rustyarcade.com
Yeah flade owns, Its really hard to do stuff where you have multiple points affecting eachother at the same time without the structure just shooting off screen.
That also have complex physics stuff like weighted colision with circles and really good friction simulation.
Its one of my favorite effects so far, got a few ideas for uses after me and NC finish priority 1
At 10/1/05 07:59 AM, Ninja-Chicken wrote: Yeah I dont see why people have such orgasms over that fucking file. I mean www.teagames.com has a shit load of games using just as impressive realism (true physics) as that so why the wetness over it?
Because it's open source ^^
Very nice but I don't see how to add physical simulation to kinematic'ed points.
At 10/1/05 08:02 AM, F-13 wrote: Very nice but I don't see how to add physical simulation to kinematic'ed points.
Well I only really wanted to cover the basics here. I was going to mention at the bottom that you can assemble heirarchies from points, and use parent/child style labeling and put it into some sort of assesment function to see which one/s should be affected.
Thats where it starts to get complecated, I've only really experimented with stuff like that.
Nice tutorial, I might have a go at making something later. I'm impressed.
<3
Sup, bitches :)
Yeah I origionally made a kinematics tutorial but my fucking computer crashed (again) and I lost it all
- Matt, Rustyarcade.com
At 10/1/05 09:03 AM, Ninja-Chicken wrote: Yeah I origionally made a kinematics tutorial but my fucking computer crashed (again) and I lost it all
Yeah I felt bad for you while writing it <3
This one is Dedicated to NC's lost tut.
At 10/1/05 09:04 AM, T-H wrote:At 10/1/05 09:03 AM, Ninja-Chicken wrote: Yeah I origionally made a kinematics tutorial but my fucking computer crashed (again) and I lost it allYeah I felt bad for you while writing it <3
This one is Dedicated to NC's lost tut.
lol maybe Ill make AS: Penetration (do you get it?)
no
okay Ill just go over here then
- Matt, Rustyarcade.com
Very good tutorial. The diagrams are what did it for me. As people have already said this could be the start of NG's own ragdoll physics. I'm going to add some code for limiting the range of motion (ie set a limiting angle) between the two points and either write another tutorial or just spit the code back out in a FOSS. I have two full post it notes of little things like this I've been meaning to do though so no guarentees about a time frame. Damn, another thing I've been meaning to do is an AS: Kinematics like ninja mentioned. Or if I really want to kill myself AS: Newtonian Mechanics. Anyway, good tutorial and I hope I can add to it sometime soonish.
At 10/1/05 12:41 PM, BleeBlap wrote: Very good tutorial.........
That would be great, I'm no master of this stuff, I've not tried limiting angles yet, but build a heirarchy of points into half a doll.
A more advanced version of this would be extremely cool, "newtonian mechanics" heh, has me enthraled already.
And yeah I think this would be undesipherable without the diagram, thats why I linked to it about every other line heh.
Thanks
Well I made some progress. link At the moment the heiarchy is hardcoded and I'm going to convert it all to loops, draw a few diagrams and write a follow up tut but I thought I would post and ask for some suggestions first.
At 10/2/05 03:25 PM, BleeBlap wrote: thought I would post and ask for some suggestions first.
None as such, looking good so far.
If you can anchor the leftmost point then you will have yourself an arm
This actually rocks. GREAT tutorial man.
You learn something new every day.
*Bookmarked*
"Actually, the server timed out trying to remove all your posts..."
-TomFulp
How do you make both points dragable?
At 12/15/05 08:49 AM, Creeepy wrote: How do you make both points dragable?
anyone?
i dont think many gonna see this, so i might make a new topic about it or something! i mean... Come On guys!
You would have to do something like:
var hypotenuse:Number = 170;
onEnterFrame = function() {
xDist = dragee._x - dragger._x;
yDist = dragee._y - dragger._y;
angle = Math.atan2 (yDist, xDist);
dragee._x = dragger._x + (Math.cos (angle) * hypotenuse);
dragee._y = dragger._y + (Math.sin (angle) * hypotenuse);
};
point1_mc.onPress = function() {
this.startDrag();
dragger = this;
dragee = point2_mc;
};
point2_mc.onPress = function() {
this.startDrag();
dragger = this;
dragee = point1_mc;
};
point1_mc.onRelease = point2_mc.onRelease = function() {
stopDrag();
};
At 12/15/05 09:22 AM, Santazien wrote: You would have to do something like:
var hypotenuse:Number = 170;
onEnterFrame = function() {
xDist = dragee._x - dragger._x;
yDist = dragee._y - dragger._y;
angle = Math.atan2 (yDist, xDist);
dragee._x = dragger._x + (Math.cos (angle) * hypotenuse);
dragee._y = dragger._y + (Math.sin (angle) * hypotenuse);
};
point1_mc.onPress = function() {
this.startDrag();
dragger = this;
dragee = point2_mc;
};
point2_mc.onPress = function() {
this.startDrag();
dragger = this;
dragee = point1_mc;
};
point1_mc.onRelease = point2_mc.onRelease = function() {
stopDrag();
};
thank you ( but my engine still doesnt look exactly like i wanted!)
take alook here: http://img234.images..gintolooknice2wi.swf
nice tut, but i prefer the non trigonometry approach to IK, its faster although depending on your knowledge, possible more or less complicated
the trigometric approach here takes the angle between the two points, and then using sine and cosine finds the new position
the vector approach takes the vector between the two points, normalizes it, then scales it to the required distance to find the new position
xd = x1-x2; //where x1 is the x-coordinate of the parent point and x2 is of the point being moved
yd = y1-y2; //where y1 is the y-coordinate of the parent point and y2 is of the point being moved
d = Math.sqrt(xd*xd+yd*yd);
xd = (xd/d)*(d-5);
yd = (yd/d)*(d-5);
x2 += xd;
y2 += yd;
the advantages of this other the trigometric method is its faster
trig. method: atan2, sin, cos for each point
vec. method: sqrt for each point
id draw an image but i cant be bothered, basicly, its a way of finding out how much the point has to move along the x and y axis to be withing 5 pixels of the other point without using trigonometry, you can obviously change the '5' to however far the point should be
I didnt really read it properly so I dont know if this is basically what you are doing but...
The other day I had an idea for this. I though if I calculated distance then if it wasnt the exact distance I wanted then I could make the second ball move towards it. So I came up with this
onClipEvent (enterFrame) {
while (Math.round (Math.sqrt(Math.pow(_root.b1._x-this._x, 2)+Math.pow(_root.b1._y-this._y, 2)))>100) {
ang = Math.atan2(this._x-_root.b1._x, this._y-_root.b1._y);
this._x -= Math.sin(ang);
this._y -= Math.cos(ang);
}
while (Math.round (Math.sqrt(Math.pow(_root.b1._x-this._x, 2)+Math.pow(_root.b1._y-this._y, 2)))<100) {
ang = Math.atan2(this._x-_root.b1._x, this._y-_root.b1._y);
this._x += Math.sin(ang);
this._y += Math.cos(ang);
}
}
The same effect.
Dont know how useful this is but I thought I'd post it
- Matt, Rustyarcade.com
At 12/15/05 12:18 PM, -dELta- wrote: ...
Basically Pythagors then? I tried that way once, but it doesnt work very well for movement on slopes by two linked objects, but it is indeed a lot less intense and far simpler.
And NC, yeah that was pretty much the same but with less variables.
yeah cool
Also check this out
make a symbol and give it linkage name "ball"
add this to frame 1
for (i=0; i<21; i++) {
_root.attachMovie("ball", "b"+i, i, {_x:200, _y:200, parent:i+1, dist:10});
_root["b"+i].onEnterFrame = function() {
while (Math.round(Math.sqrt(Math.pow(_root["b"+t
his.parent]._x-this._x, 2)+Math.pow(_root["b"+this.parent]._y-this
._y, 2)))>this.dist) {
this.ang = Math.atan2(this._x-_root["b"+this.parent].
_x, this._y-_root["b"+this.parent]._y);
this._x -= Math.sin(this.ang);
this._y -= Math.cos(this.ang);
}
while (Math.round(Math.sqrt(Math.pow(_root["b"+t
his.parent]._x-this._x, 2)+Math.pow(_root["b"+this.parent]._y-this
._y, 2)))<this.dist) {
this.ang = Math.atan2(this._x-_root["b"+this.parent].
_x, this._y-_root["b"+this.parent]._y);
this._x += Math.sin(this.ang);
this._y += Math.cos(this.ang);
}
};
}
_root.attachMovie("ball", "b"+21, 21, {_x:500, _y:200});
_root.b21.onPress = function() {
this.startDrag(true);
};
_root.b21.onRelease = function() {
this.stopDrag ()
};
Does it lag for anyone??
- Matt, Rustyarcade.com