-
Notifications
You must be signed in to change notification settings - Fork 48
Using type magic
Complementary to #import magic, type magic allows to further improve the readability and shorten the code. It is also used for smart completion and error checking.
First, when you declare a local variable, you can specify its type after a name:
var v:Type;
// or:
var v:Type = value;
// or with #args magic:
#args v:Type, ?z:Type, q:Type = value
// or with function arguments and/or return types in GMS≥2.3:
function name(v:Type, z:Type, q:Type)->Type {
// (z is undefined by default if not provided)
q ??= value;
// ...
}
if the "type" is an #import namespace, you will be able to use any functions from the namespace as variable's "methods":
#import string.* as String
var s:String = "hi";
return s.repeat(2); // -> string_repeat(s, 2) -> "hihi"
if the namespace has a function called "create", you can also use a keyword "new" on the namespace, and it'll translate to that:
#import ds_grid.* as Grid
return new Grid(4, 4); // -> ds_grid_create(4, 4)
Note that type magic only works with local variables. Use @hint or @is to specify types for global/instance variables.
If you specify an enum as a type instead, you can do .field
access with constant names from enum as if it was a lightweight object:
enum Vec2 { x, y, sizeof }
var v:Vec2 = argument0;
v.x = 1; // -> v[@Vec2.x]
return v.y; // -> v[Vec2.y]
if your enum ends with a separate constant to mark the number of other constants inside of it, you can use Type()
to construct an empty copy of it:
enum Vec2 { x, y, sizeof }
var v:Vec2 = Vec2(); // -> array_create(Vec2.sizeof);
and you can import scripts/functions on top of them:
enum Vec2 { x, y, sizeof }
#import vec2.* in Vec2 // where you have vec2_create(x, y), vec2_add(v, x, y)
var v:Vec2 = new Vec2(2, 3); // -> vec2_create(2, 3)
return v.add(new Vec2(4, 5)); // -> vec2_add(v, vec2_create(4, 5))
Since January 2019 update, you can also use #import com.pkg.some in NS:name
syntax to be able to do
#import buffer_* in Buffer:
#import buffer_create in Buffer.create
#import buffer_get_address in Buffer:ptr
var b:Buffer = new Buffer(64, buffer_grow, 1);
some_func(b.ptr(), b.tell());
without turning every non-type-magic buffer_tell(buf)
into Buffer.tell(buf)
- Smart auto-completion
- Types
- JSDoc tags (incl. additional ones)
- @hint tag (mostly 2.3)
- `vals: $v1 $v2` (template strings)
- #args (pre-2.3 named arguments)
- ??= (for pre-GM2022 optional arguments)
- ?? ?. ?[ (pre-GM2022 null-conditional operators)
- #lambda (pre-2.3 function literals)
- => (2.3+ function shorthands)
- #import (namespaces and aliases)
- v:Type (local variable types)
- #mfunc (macros with arguments)
- #gmcr (coroutines)