00:00
00:00
Newgrounds Background Image Theme

Someone gifted MetalSlayer69 supporter status!

We need you on the team, too.

Support Newgrounds and get tons of perks for just $2.99!

Create a Free Account and then..

Become a Supporter!

AS2 Vectors 2023-06-06 15:59:19


So I lucked out while digging for old Actionscript tutorials and found what appears to be a complete guide for coding vectors. It miraculously has a bunch of source flas you can download and open using Flash MX 2004 or higher. You can visit the guide here via the Wayback Machine.


I tried learning from it myself and came up with this. I'm not sure if what I did is correct and would like someone with more experience than me to review my fla and tell me what I should be doing differently.


[1] - [2]

Response to AS2 Vectors 2023-06-29 13:55:47


Just gonna'...bump this...


[1] - [2]

Response to AS2 Vectors 2023-06-30 00:43:41


Sorry, I don't have flash on my new computer at the moment. I'll probably install it over the weekend and take a look. Had been meaning to do this earlier but I just ended up forgetting at one point.


Slint approves of me! | "This is Newgrounds.com, not Disney.com" - WadeFulp

"Sit look rub panda" - Alan Davies

BBS Signature

Response to AS2 Vectors 2023-06-30 02:17:21


At 6/30/23 12:43 AM, Gimmick wrote: Sorry, I don't have flash on my new computer at the moment. I'll probably install it over the weekend and take a look. Had been meaning to do this earlier but I just ended up forgetting at one point.


Oh, um, no worries. I'm kind of surprised it's you again. Your dedication to this forum is astounding.


[1] - [2]

Response to AS2 Vectors 2023-07-01 15:23:10


At 6/30/23 02:17 AM, Nabella wrote:
At 6/30/23 12:43 AM, Gimmick wrote: Sorry, I don't have flash on my new computer at the moment. I'll probably install it over the weekend and take a look. Had been meaning to do this earlier but I just ended up forgetting at one point.
Oh, um, no worries. I'm kind of surprised it's you again. Your dedication to this forum is astounding.


No worries, I like doing this stuff. Certainly more productive than spending hours on reddit in any case :D


So going through your code, I know that you probably didn't intend on creating it as anything more than a test, so I'm not going to hold the variable naming scheme against you (since I do that a lot on my throwaway code as well). But if you're intending to make a project out of it, then I would suggest you do either of the following:


  • throw away the code and start again, or
  • clean up the code.


The first option is supposed to be a common practice in software engineering because the prototype is supposed to be a proof of concept -- that is, now that you know how to do it, then you can start again afresh with a clean slate. In practice though it's far too costly and/or boring/tedious (for personal projects) to start from scratch, so most people just clean up the code instead. That's what I've done with the FLA, and you can probably pick up a few hints as to the process that I go through of cleaning up. I've listed them below just as a summary, though:


  • Find any code that could go into separate functions. For example, the code that wraps the movieclip around the stage.
  • Use the official classes where possible. For example, you're dealing with "x" and "y" objects, use the Point class.
import flash.geom.Point;

//instead of...
// var pt = {x: 0, y: 0}
//prefer...
var pt: Point = new Point(0, 0);
pt.x += 20;
pt.y += 20;
  • Try to determine if there are alternative ways of accomplishing the same things. For example, rather than adding the deceleration to the acceleration, it is probably better to just add the two together and return a separate object to determine the impact on the velocity.
  • Rename your variables to be more readable and then condense into classes where applicable. For example, dclx can be "decelerationX", which itself can be converted to a Point containing both the X and Y deceleration:
//instead of...
// var dclX:Number = 0
// var dclY:Number = 0
//prefer...
var deceleration:Point = new Point(0, 0)


Use type hints wherever possible, it helps Flash help you. For example,

var velocity: Point = augh.velocity

If you then type "velocity." then it'll show you all the methods and properties available for the "velocity" object. Meanwhile if you try typing "augh.velocity." it won't show anything even though it's a Point, because the IDE doesn't know that it's a point (all the type information is stripped for properties of "dynamic" classes like MovieClip, meaning that whenever you do "mc.variable = value" it treats it as though it could be anything -- numbers, strings, etc. -- so it doesn't even try loading any hints. This is as true for AS2 as it is for AS3.)


Simplifying the code in the above manner also makes it easier to eliminate duplicates. For example, it seems as though you checked whether the velocity crossed the maximum twice, first at the beginning of the onEnterFrame and then right after you press a key. It doesn't need to be done this way - as long as you check it right before you apply the changes, you should be fine. By that, I mean, since your velocity is used to determine how much to move your character by, it's fine if it exceeds the maximum as long as it's limited right before you change the character's position. This is easier to spot if you have it boxed in functions like "limitVelocity", that way if you see it being called twice there's probably some reason for doing some investigation.


I also prefer returning new objects rather than modifying existing ones, at least for personal projects. That's why I create a new Point rather than just modifying the "x" and "y" directly - I generally do that if there's a strong need to do so, as in, when I know that the main reason I'm getting slowdowns is because of that. I understand it's wasteful on some level to create new objects each frame, and using Points was slower than using direct properties in the Flash player of old -- but because you're most likely going to run it in Ruffle, these shouldn't be (as much of) a problem now since browser engines are very good at handling this sort of stuff.


On another note, I should've probably mentioned that it's best to decide on a convention that you'll be using. That is, rather than using acceleration and deceleration, both of which can be affected by the player depending on the key they're pressing, it might be better to decide that "acceleration" as being "caused by the forces a player exerts" (e.g. pressing a key), and "deceleration" as "caused by the environment" (e.g. friction, gravity, etc.). In this light, it makes it easier to manage the code, but you'll also have to rename the variables to make it make sense (gravity isn't a deceleration!).


Lastly, I much prefer using the variable name for dynamic textboxes and updating them manually rather than using the "variable" setting in the properties panel, which can be rather finicky.


Here's the final FLA with the changes described above. It may look nothing like your original code, and that's fine - this is moreso so you can try and understand how it should be for larger projects. I'm not an absolutist insofar as this is "the" correct way, but moreso that you should try and take away whatever patterns you can find from it.


In hindsight, it would've been better to have the entire code transformation recorded so that you can see the process in real-time...oh well. I know that there are videos like those on youtube, just search for "Let's refactor code" or something like that and you should (hopefully) see plenty of videos that do the same thing that I just did, and maybe you can glean something from those -- the "big picture" stuff like thought processes and so on.


Slint approves of me! | "This is Newgrounds.com, not Disney.com" - WadeFulp

"Sit look rub panda" - Alan Davies

BBS Signature

Response to AS2 Vectors 2023-07-25 12:26:25


At 7/1/23 03:23 PM, Gimmick wrote:
No worries, I like doing this stuff. Certainly more productive than spending hours on reddit in any case :D

So going through your code, I know that you probably didn't intend on creating it as anything more than a test, so I'm not going to hold the variable naming scheme against you (since I do that a lot on my throwaway code as well). But if you're intending to make a project out of it, then I would suggest you do either of the following:

The first option is supposed to be a common practice in software engineering because the prototype is supposed to be a proof of concept -- that is, now that you know how to do it, then you can start again afresh with a clean slate. In practice though it's far too costly and/or boring/tedious (for personal projects) to start from scratch, so most people just clean up the code instead. That's what I've done with the FLA, and you can probably pick up a few hints as to the process that I go through of cleaning up. I've listed them below just as a summary, though:

Use type hints wherever possible, it helps Flash help you. For example,
If you then type "velocity." then it'll show you all the methods and properties available for the "velocity" object. Meanwhile if you try typing "augh.velocity." it won't show anything even though it's a Point, because the IDE doesn't know that it's a point (all the type information is stripped for properties of "dynamic" classes like MovieClip, meaning that whenever you do "mc.variable = value" it treats it as though it could be anything -- numbers, strings, etc. -- so it doesn't even try loading any hints. This is as true for AS2 as it is for AS3.)

Simplifying the code in the above manner also makes it easier to eliminate duplicates. For example, it seems as though you checked whether the velocity crossed the maximum twice, first at the beginning of the onEnterFrame and then right after you press a key. It doesn't need to be done this way - as long as you check it right before you apply the changes, you should be fine. By that, I mean, since your velocity is used to determine how much to move your character by, it's fine if it exceeds the maximum as long as it's limited right before you change the character's position. This is easier to spot if you have it boxed in functions like "limitVelocity", that way if you see it being called twice there's probably some reason for doing some investigation.

I also prefer returning new objects rather than modifying existing ones, at least for personal projects. That's why I create a new Point rather than just modifying the "x" and "y" directly - I generally do that if there's a strong need to do so, as in, when I know that the main reason I'm getting slowdowns is because of that. I understand it's wasteful on some level to create new objects each frame, and using Points was slower than using direct properties in the Flash player of old -- but because you're most likely going to run it in Ruffle, these shouldn't be (as much of) a problem now since browser engines are very good at handling this sort of stuff.

On another note, I should've probably mentioned that it's best to decide on a convention that you'll be using. That is, rather than using acceleration and deceleration, both of which can be affected by the player depending on the key they're pressing, it might be better to decide that "acceleration" as being "caused by the forces a player exerts" (e.g. pressing a key), and "deceleration" as "caused by the environment" (e.g. friction, gravity, etc.). In this light, it makes it easier to manage the code, but you'll also have to rename the variables to make it make sense (gravity isn't a deceleration!).

Lastly, I much prefer using the variable name for dynamic textboxes and updating them manually rather than using the "variable" setting in the properties panel, which can be rather finicky.

Here's the final FLA with the changes described above. It may look nothing like your original code, and that's fine - this is moreso so you can try and understand how it should be for larger projects. I'm not an absolutist insofar as this is "the" correct way, but moreso that you should try and take away whatever patterns you can find from it.

In hindsight, it would've been better to have the entire code transformation recorded so that you can see the process in real-time...oh well. I know that there are videos like those on youtube, just search for "Let's refactor code" or something like that and you should (hopefully) see plenty of videos that do the same thing that I just did, and maybe you can glean something from those -- the "big picture" stuff like thought processes and so on.


Okay, very late reply. Please forgive me for that.


I end up restarting coding projects a lot, so don't worry about that.


I finally got a chance to sit down and study your fla today, but it doesn't seem to open. What version of Flash did you use to export it? I'm using Macromedia Flash 8.


Also, thank you again for giving me super insightful programming advice over the internet for practically free. There are lots of videos out there, but it's really nice to just have someone look at what you're working on currently and give you advice about what you should doing differently from there.


[1] - [2]

Response to AS2 Vectors 2023-07-26 20:34:59


At 7/25/23 12:26 PM, Nabella wrote: Okay, very late reply. Please forgive me for that.

I end up restarting coding projects a lot, so don't worry about that.

I finally got a chance to sit down and study your fla today, but it doesn't seem to open. What version of Flash did you use to export it? I'm using Macromedia Flash 8.

Also, thank you again for giving me super insightful programming advice over the internet for practically free. There are lots of videos out there, but it's really nice to just have someone look at what you're working on currently and give you advice about what you should doing differently from there.


No worries, feel free to ask again in the future if need be (and I'll probably record it the next time around). I saved it using Flash CS5.5, but as a CS4 file. Flash 8 doesn't play nice with my system for some reason, but I can paste the code here if required.


Slint approves of me! | "This is Newgrounds.com, not Disney.com" - WadeFulp

"Sit look rub panda" - Alan Davies

BBS Signature

Response to AS2 Vectors 2023-07-26 21:18:18


At 7/26/23 08:34 PM, Gimmick wrote:
No worries, feel free to ask again in the future if need be (and I'll probably record it the next time around). I saved it using Flash CS5.5, but as a CS4 file. Flash 8 doesn't play nice with my system for some reason, but I can paste the code here if required.


Oooh, okay. I've tried later versions of Flash before but they run a little slow and are prone to crashing on my end. Flash 8 isn't immune to that either, but it feels super rare in comparison to later versions. I'm kind of shocked how they seemingly made something super stable back in 2006 and then slowly crippled it overtime. Is this one of the follies of long term development on a single program, lol?


Don't worry about pasting your code, I think I'll open the file in CS4 (or CS5.5 if it still doesn't work) and hope for the best.


[1] - [2]

Response to AS2 Vectors 2023-07-27 02:39:15


At 7/26/23 09:18 PM, Nabella wrote:
At 7/26/23 08:34 PM, Gimmick wrote:
No worries, feel free to ask again in the future if need be (and I'll probably record it the next time around). I saved it using Flash CS5.5, but as a CS4 file. Flash 8 doesn't play nice with my system for some reason, but I can paste the code here if required.
Oooh, okay. I've tried later versions of Flash before but they run a little slow and are prone to crashing on my end. Flash 8 isn't immune to that either, but it feels super rare in comparison to later versions. I'm kind of shocked how they seemingly made something super stable back in 2006 and then slowly crippled it overtime. Is this one of the follies of long term development on a single program, lol?

Consequences of bloat, perhaps. More and more things got added over time and Flash went on that path after Adobe acquired Macromedia.

Don't worry about pasting your code, I think I'll open the file in CS4 (or CS5.5 if it still doesn't work) and hope for the best.

If you're still having trouble by this weekend, I'll be downloading Flash 8 then and copying it over there by then.


Slint approves of me! | "This is Newgrounds.com, not Disney.com" - WadeFulp

"Sit look rub panda" - Alan Davies

BBS Signature

Response to AS2 Vectors 2023-07-30 02:59:05


At 7/27/23 02:39 AM, Gimmick wrote: Consequences of bloat, perhaps. More and more things got added over time and Flash went on that path after Adobe acquired Macromedia.


I've heard the old story about Adobe wrecking Flash, but even if Macromedia wasn't acquired by Adobe, would it have still gone down the same path?


If you're still having trouble by this weekend, I'll be downloading Flash 8 then and copying it over there by then.


Nah, I got it.


This is really fantastic, by the way. I feel so spoiled by you giving me a full-on graded assessment with notes and everything.


iu_1036408_5508066.png


Awhile back, you explained to me the difference between global variables, local variables, and function parameters. Something that went over my head apparently, now that I'm looking over this, is how valuable the statement 'return' actually is. I'm actually noticing a lot of small things I didn't know I could do previously, like having multiple function parameters (is that limited to ':Point'?) and using something called '.clone'? I'm always learning something new with you.


I'm also realizing I should go back and read some the PDFs listed in AS: Main to learn any basics I might've skimmed over.


[1] - [2]

Response to AS2 Vectors 2023-07-30 15:35:44 (edited 2023-07-30 15:38:32)


At 7/30/23 02:59 AM, Nabella wrote: This is really fantastic, by the way. I feel so spoiled by you giving me a full-on graded assessment with notes and everything.

Happy to help!

Awhile back, you explained to me the difference between global variables, local variables, and function parameters. Something that went over my head apparently, now that I'm looking over this, is how valuable the statement 'return' actually is. I'm actually noticing a lot of small things I didn't know I could do previously, like having multiple function parameters (is that limited to ':Point'?)


Nope! Function parameters can be used with any "type" (class) and there can be as many of them in a function as needed (although for readability purposes, most functions typically have fewer than 4 parameters I'd say). For example, take the following function:


function calculateWeightedAverage(valueA: Number, weightA: Number, valueB: Number, weightB: Number): Number {
    var weightedSum: Number = (valueA * weightA) + (valueB * weightB)
    var totalWeight: Number = (weightA + weightB)
    return weightedSum / totalWeight
}

It's a bit contrived since normally we could use a pair of arrays to accept as many values and weights, but for the purpose of demonstration the above function has 4 parameters, which are all of type Number and return a Number - but it doesn't have to be all the same type. They can be any of the "base" or primitive types defined in the language, which are:

  • String
  • Number (split into int and float in AS3)
  • Boolean

They can also be any custom type (i.e. classes) that you've created yourself, or that are available in the standard library (e.g. Point, BlurFilter, BitmapData, Array, etc.)


And of course, passing function parameters makes things FAR more manageable since you don't have to rely on global variables or undocumented object properties to pass information for use by the function.


You can only return 1 type in a function, but you can return multiple types if you encapsulate / wrap them in a compound type (such as a class or even a simple array):


function getValues(): Array {
    return [2, "Jason"]
}
// and to use...
var returnedValues: Array = getValues()
var numCars: Number = returnedValues[0]
var ownerName: String = returnedValues[1]

Or the more verbose method of declaring a class with the values contained within, along with their type - so that it becomes self-evident when you try and access the object's properties:

//Person.as
public class PersonInfo {
    private var _name:String;
    private var _numCars: Number;
    public function PersonInfo(name: Number, numCars: Number) {
        this._name = name;
        this._numCars = numCars;
    }
    public function get name():String {
        return this._name;
    }
    public function get numCars(): String {
        return this._numCars;
    }
}
//elsewhere
function getValues(): Person {
    return new PersonInfo("Jones", 2);
}
var person: Person = getValues();
var numCars: Number = person.numCars;
var name: String = person.name;

The downside of the above being that (in AS2) you can only define them in their own files, rather than in the FLA. But that's a good practice to do in any case. Regardless, when you try and type "person." then the IDE should automatically tell you that there's two properties, numCars and name belonging to the object pointed to by the variable person. This is unlike if you tried to just return an Array of 2 values, or an Object instead:

function getValues(): Object {
    return {"name": "Jonas", "numCars": 2}
}

which would work equally in a pinch, but wouldn't tell you what was contained within at the type level. You'd have to get the information from elsewhere (e.g. code comments), whereas with a separate class, the IDE and compiler will tell you what you can and can't access - saving time on debugging, e.g. if you made a typo somewhere (I've seen it occur quite a bit in the past, and had it happen to myself as well).


Well, in theory anyway. I think the IDE support for AS2 is quite a bit worse than for AS3, or if you try and develop in AS2 then you might want to try an external IDE such as FlashDevelop. Granted, that comes with its own tradeoffs as well, to a degree.


and using something called '.clone'? I'm always learning something new with you.

"clone" is a function of the Point object, defined as part of the Point class. It's just like "gotoAndStop()" which is a function belonging to the MovieClip class. You can find more information about these methods by looking at the official AS2 documentation (for the Point class, it is on page 1011); it lists the methods (i.e. functions) and properties (i.e. variables*) belonging to a particular class, as well as all the classes that come "out of the box" with Flash.


Side note: you might have noticed that the above PersonInfo class has the function

public function get name():String {
    return this._name;
}

defined, but when we call it then we refer to it directly, like

person.name

instead of

person.name()

as with any other function. And that's because while name is a function, it's a special type of function called a getter. It allows others to treat this as they would any other variable, and the advantage of this is that it makes it less verbose at times while still gating access when required. They also have setters, which are the equivalent of assignment statements; together, you can see how they achieve the "gated" access to a class's variables - e.g. by having a getter (get) but no setter (set), you can prevent others from changing the variable (e.g. you can't change the name property above, it's only created once and that's it), or you can have a write-only property if it's the opposite (e.g. you change a value, but you can't read from it - although this doesn't tend to get used much because it doesn't often make sense to do things this way)


Java doesn't have getters or setters, and their equivalent code is a tad more verbose. Not by much, but it can make things a bit more pleasing to the eye if it were present; just compare the two:

//Java:
//...rest of class... 
public int getAge() {
    return this._age;
}
public void setAge(int age) { 
    this._age = age;
}
//
int age = obj.getAge();
obj.setAge(age + 1);

//AS2
public function get age(): Number {
    return this._age;
}
public function set age(age: Number): Void {
    this._age = age;
}
var age: Number = obj.age;
obj.age = age + 1 // or just obj.age++


There's also a bunch of best practices that you can use with functions, but those are probably for a later time. They have appeared in some way or the other in the original FLA, so you might be able to guess them already.


*properties can be thought of as variables, but they are mostly used to refer to both variables and getters/setters, likely because of the similar syntax.


Slint approves of me! | "This is Newgrounds.com, not Disney.com" - WadeFulp

"Sit look rub panda" - Alan Davies

BBS Signature

Response to AS2 Vectors 2023-07-31 01:00:02


At 7/30/23 03:35 PM, Gimmick wrote:
At 7/30/23 02:59 AM, Nabella wrote: This is really fantastic, by the way. I feel so spoiled by you giving me a full-on graded assessment with notes and everything.
Happy to help!
Awhile back, you explained to me the difference between global variables, local variables, and function parameters. Something that went over my head apparently, now that I'm looking over this, is how valuable the statement 'return' actually is. I'm actually noticing a lot of small things I didn't know I could do previously, like having multiple function parameters (is that limited to ':Point'?)
Nope! Function parameters can be used with any "type" (class) and there can be as many of them in a function as needed (although for readability purposes, most functions typically have fewer than 4 parameters I'd say). For example, take the following function:

It's a bit contrived since normally we could use a pair of arrays to accept as many values and weights, but for the purpose of demonstration the above function has 4 parameters, which are all of type Number and return a Number - but it doesn't have to be all the same type. They can be any of the "base" or primitive types defined in the language, which are:
They can also be any custom type (i.e. classes) that you've created yourself, or that are available in the standard library (e.g. Point, BlurFilter, BitmapData, Array, etc.)

And of course, passing function parameters makes things FAR more manageable since you don't have to rely on global variables or undocumented object properties to pass information for use by the function.

You can only return 1 type in a function, but you can return multiple types if you encapsulate / wrap them in a compound type (such as a class or even a simple array):

Or the more verbose method of declaring a class with the values contained within, along with their type - so that it becomes self-evident when you try and access the object's properties:
The downside of the above being that (in AS2) you can only define them in their own files, rather than in the FLA. But that's a good practice to do in any case. Regardless, when you try and type "person." then the IDE should automatically tell you that there's two properties, numCars and name belonging to the object pointed to by the variable person. This is unlike if you tried to just return an Array of 2 values, or an Object instead:
which would work equally in a pinch, but wouldn't tell you what was contained within at the type level. You'd have to get the information from elsewhere (e.g. code comments), whereas with a separate class, the IDE and compiler will tell you what you can and can't access - saving time on debugging, e.g. if you made a typo somewhere (I've seen it occur quite a bit in the past, and had it happen to myself as well).

Well, in theory anyway. I think the IDE support for AS2 is quite a bit worse than for AS3, or if you try and develop in AS2 then you might want to try an external IDE such as FlashDevelop. Granted, that comes with its own tradeoffs as well, to a degree.

and using something called '.clone'? I'm always learning something new with you.
"clone" is a function of the Point object, defined as part of the Point class. It's just like "gotoAndStop()" which is a function belonging to the MovieClip class. You can find more information about these methods by looking at the official AS2 documentation (for the Point class, it is on page 1011); it lists the methods (i.e. functions) and properties (i.e. variables*) belonging to a particular class, as well as all the classes that come "out of the box" with Flash.

Side note: you might have noticed that the above PersonInfo class has the function
defined, but when we call it then we refer to it directly, like
instead of
as with any other function. And that's because while name is a function, it's a special type of function called a getter. It allows others to treat this as they would any other variable, and the advantage of this is that it makes it less verbose at times while still gating access when required. They also have setters, which are the equivalent of assignment statements; together, you can see how they achieve the "gated" access to a class's variables - e.g. by having a getter (get) but no setter (set), you can prevent others from changing the variable (e.g. you can't change the name property above, it's only created once and that's it), or you can have a write-only property if it's the opposite (e.g. you change a value, but you can't read from it - although this doesn't tend to get used much because it doesn't often make sense to do things this way)

Java doesn't have getters or setters, and their equivalent code is a tad more verbose. Not by much, but it can make things a bit more pleasing to the eye if it were present; just compare the two:

There's also a bunch of best practices that you can use with functions, but those are probably for a later time. They have appeared in some way or the other in the original FLA, so you might be able to guess them already.

*properties can be thought of as variables, but they are mostly used to refer to both variables and getters/setters, likely because of the similar syntax.


This is going to take some time to digest, but I think I'll get it with enough practice. Thank you again for typing all this up, dude, this is nuts.


[1] - [2]