Classes#
What is a Class#
The concept of a class
is taken mostly from C++ here, although notably simplified down.
By declaring a class
, you declare a template of data to be used repeatedly in creating
objects
, along with some functions associated with that data.
While the order of the parts within a class mostly doesn’t matter to the compiler, you will generally see classes organized in the same general order:[1]
- Data: The variables that make up the class. Can contain arrays, too.
While technically not ‘required’, a class without data has little purpose.
Declared via normal variable declarations. Cannot have initializers.
- Constructor(s): A function or functions to create the class.
Not required- leaving it out is the same as declaring an empty constructor function.
The constructor is declared as a function with the exact same name as the class and no return type.
The parameters may be whatever you like.
- Destructor: A function to destroy the class.
Not required- leaving it out is better for the compiler than declaring an empty destructor function.
A destructor is declared as a function named
~
followed by the exact same name as the class and no return type.The destructor takes no parameters.
- The destructor is automatically called when the object is destroyed by the engine.
Changed in version 3.0: The destructor can no longer manually be triggered with
delete
. This is no longer necessary due to the refcounting + garbage collector.
- Member Functions: Any other functions you like.
All class functions (without the
static
modifier) have a local variable namedthis
, which is a pointer to the object itself.
Note
The order the data is declared in is relevant to existing save files, for any objects saved to the save file. As such, changing the order can break existing save files (in the same way that declaring any new global variable can)
Allocating Objects#
To create an instance of an object, you call its constructor function using the new
keyword[2].
A pointer to the object, whose type is the class itself, will be returned.
Limits
A maximum of 214747
objects can exist at a time, from all (non-internal) classes combined.
If this many objects exist at once, the new
call will fail, returning NULL
.
Object Cleanup#
The program keeps track of all the references to each object, and automatically deletes any object when the last reference to it is lost (calling the destructor, if defined).
There is additionally a garbage collector, which is capable of cleaning up cyclical references (the situation in which the only reference left to two different objects, is inside the other, thus they ‘keep each other alive’ for the reference counting)
Tip
OwnObject grants a single “reference” to the object to whichever entity the function is giving ownership to. If that entity dies, it causes the ownership reference to be ‘lost’.
Tip
GlobalObject marks an object as “global”. Objects that are “global” will be saved to the save file, and cannot be destroyed.
Calling OwnObject marks the object as no longer “global”.
Static Functions#
Declaring a function inside a class with the static
modifier makes the function a static part of
the class, rather than a part of each object. Static functions have a few differences from normal
member functions:
No
this
pointer (meaning no access to any data members from the class)Called similarly to functions inside namespaces, except that a
.
is used after the class name, rather than the scope-resolution operator::
Effectively, they are functions whose only thing to do with the class, is that they are called using the class’s name. One possible use of such functions would be to create ‘named constructors’ for different purposes[3].
Array Data Members#
Declaring an array as a data member of an object creates a special type of array. Notably, you cannot re-assign a different pointer to such an array, and OwnArray/DestroyArray have no effect on these arrays.
These arrays are effectively ‘owned’ by the object, and are destroyed when the object is destroyed. They are also saved to the save file with the object, if the object is global.
Note that this only applies to actual array declarations- declarations of variables with array types that are not array declarations still act as normal.
Not Yet Implemented
Currently, attempting to re-assign a pointer to such an array does not give a compiler error- it simply has no effect. This will likely become a compiler error in the future.