Skip to content

Commit

Permalink
Add tooled and icon support of ecmascript
Browse files Browse the repository at this point in the history
Update typescript api documentation
  • Loading branch information
Geequlim committed Dec 13, 2019
1 parent 8d0262e commit 706d39a
Show file tree
Hide file tree
Showing 3 changed files with 55 additions and 4 deletions.
26 changes: 22 additions & 4 deletions misc/godot.builtin.d.ts
Original file line number Diff line number Diff line change
@@ -1,27 +1,37 @@
declare module godot {


type GodotClass = new() => godot.Object;

/**
* Export class to godot
*
* @param target The class extends from `godot.Object`
* @param name The class name
*/
function register_class(target: Function, name: string);
function register_class(target: GodotClass, name: string);

/**
* Register signal to class
* @param target The class of the signal
* @param name signal name
*/
function register_signal(target: Function|object, name: string);
function register_signal(target: GodotClass | godot.Object, name: string);

/**
* Register property to class
* @param target The class of the property
* @param name The name of the property
* @param value The default value of the property
*/
function register_property(target: Function|object, name: string, value: any);
function register_property(target: GodotClass | godot.Object, name: string, value: any);

/**
* The meta data of an script
* @param target The script class
* @param tool is tooled of this class
* @param icon The icon of the class
*/
function set_script_meta(target: GodotClass, tool: boolean, icon?: string);

/**
* Returns the internal type of the given `Variant` object, using the `godot.TYPE_*`
Expand All @@ -38,6 +48,14 @@ declare module godot {
* ```*/
function load(path: string): Resource;


/**
* Wait a signal of an object
* @param target The owner of the signal to wait
* @param signal The signal to wait
*/
function yield(target: godot.Object, signal: string): Promise<any[]>;

const E: 2.7182818284590452353602874714;
const LN2: 0.6931471805599453094172321215;
const SQRT2: 1.4142135623730950488016887242;
Expand Down
30 changes: 30 additions & 0 deletions quickjs/quickjs_binder.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -755,6 +755,9 @@ void QuickJSBinder::add_godot_globals() {
// godot.register_property
JSValue js_func_register_property = JS_NewCFunction(ctx, godot_register_property, "register_property", 3);
JS_DefinePropertyValueStr(ctx, godot_object, "register_property", js_func_register_property, PROP_DEF_DEFAULT);
// godot.set_script_meta
JSValue js_func_set_script_meta = JS_NewCFunction(ctx, godot_set_script_metadata, "set_script_meta", 3);
JS_DefinePropertyValueStr(ctx, godot_object, "set_script_meta", js_func_set_script_meta, PROP_DEF_DEFAULT);
// godot.get_type
JSValue js_get_type = JS_NewCFunction(ctx, godot_get_type, "get_type", 1);
JS_DefinePropertyValueStr(ctx, godot_object, "get_type", js_get_type, PROP_DEF_DEFAULT);
Expand Down Expand Up @@ -805,6 +808,8 @@ void QuickJSBinder::initialize() {
js_key_godot_classid = JS_NewAtom(ctx, JS_HIDDEN_SYMBOL("cls"));
js_key_godot_exports = JS_NewAtom(ctx, JS_HIDDEN_SYMBOL("exports"));
js_key_godot_signals = JS_NewAtom(ctx, JS_HIDDEN_SYMBOL("signals"));
js_key_godot_tooled = JS_NewAtom(ctx, JS_HIDDEN_SYMBOL("tool"));
js_key_godot_icon_path = JS_NewAtom(ctx, JS_HIDDEN_SYMBOL("icon"));
JS_DefinePropertyValueStr(ctx, global_object, GODOT_OBJECT_NAME, godot_object, PROP_DEF_DEFAULT);
// godot.GodotOrigin
add_godot_origin();
Expand Down Expand Up @@ -856,6 +861,8 @@ void QuickJSBinder::uninitialize() {
module_cache.clear();

JS_FreeAtom(ctx, js_key_godot_classid);
JS_FreeAtom(ctx, js_key_godot_tooled);
JS_FreeAtom(ctx, js_key_godot_icon_path);
JS_FreeAtom(ctx, js_key_godot_exports);
JS_FreeAtom(ctx, js_key_godot_signals);
JS_FreeValue(ctx, empty_function);
Expand Down Expand Up @@ -1072,6 +1079,8 @@ const ECMAClassInfo *QuickJSBinder::register_ecma_class(const JSValue &p_constru
QuickJSBinder *binder = get_context_binder(ctx);
JSValue prototype = JS_UNDEFINED;
JSValue classid = JS_UNDEFINED;
JSValue tooled = JS_UNDEFINED;
JSValue icon = JS_UNDEFINED;
JSClassID id = 0;

if (!JS_IsFunction(ctx, p_constructor)) {
Expand All @@ -1081,6 +1090,9 @@ const ECMAClassInfo *QuickJSBinder::register_ecma_class(const JSValue &p_constru

prototype = JS_GetProperty(ctx, p_constructor, QuickJSBinder::JS_ATOM_prototype);
classid = JS_GetProperty(ctx, prototype, js_key_godot_classid);
tooled = JS_GetProperty(ctx, p_constructor, js_key_godot_tooled);
icon = JS_GetProperty(ctx, p_constructor, js_key_godot_icon_path);

if (JS_IsUndefined(classid)) {
JS_ThrowTypeError(ctx, "ECMAClass class expected: %s", p_path.utf8().ptr());
goto fail;
Expand All @@ -1102,6 +1114,10 @@ const ECMAClassInfo *QuickJSBinder::register_ecma_class(const JSValue &p_constru
ecma_class.class_name = class_name;
ecma_class.prototype.ecma_object = JS_VALUE_GET_PTR(prototype);
ecma_class.constructor.ecma_object = JS_VALUE_GET_PTR(p_constructor);
ecma_class.tool = JS_ToBool(ctx, tooled);
if (JS_IsString(icon)) {
ecma_class.icon_path = js_to_string(ctx, icon);
}

// signals
JSValue signals = JS_GetProperty(ctx, prototype, js_key_godot_signals);
Expand Down Expand Up @@ -1149,6 +1165,8 @@ const ECMAClassInfo *QuickJSBinder::register_ecma_class(const JSValue &p_constru
fail:
JS_FreeValue(ctx, classid);
JS_FreeValue(ctx, prototype);
JS_FreeValue(ctx, icon);
JS_FreeValue(ctx, tooled);
return binder->ecma_classes.getptr(p_path);
}

Expand Down Expand Up @@ -1213,6 +1231,18 @@ JSValue QuickJSBinder::godot_register_property(JSContext *ctx, JSValue this_val,
return JS_UNDEFINED;
}

JSValue QuickJSBinder::godot_set_script_metadata(JSContext *ctx, JSValue this_val, int argc, JSValue *argv) {
ERR_FAIL_COND_V(argc < 2, JS_ThrowTypeError(ctx, "Two or more arguments expected"))
ERR_FAIL_COND_V(!JS_IsFunction(ctx, argv[0]), JS_ThrowTypeError(ctx, "godot class expected for argument #0"));
JSValue constructor = argv[0];
QuickJSBinder *binder = get_context_binder(ctx);
JS_SetProperty(ctx, constructor, binder->js_key_godot_tooled, JS_DupValue(ctx, argv[1]));
if (argc >= 3 && JS_IsString(argv[2])) {
JS_SetProperty(ctx, constructor, binder->js_key_godot_tooled, JS_DupValue(ctx, argv[2]));
}
return JS_UNDEFINED;
}

int QuickJSBinder::get_js_array_length(JSContext *ctx, JSValue p_val) {
if (!JS_IsArray(ctx, p_val)) return -1;
JSValue ret = JS_GetProperty(ctx, p_val, JS_ATOM_length);
Expand Down
3 changes: 3 additions & 0 deletions quickjs/quickjs_binder.h
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,8 @@ class QuickJSBinder : public ECMAScriptBinder {
JSValue godot_object;
JSValue empty_function;
JSAtom js_key_godot_classid;
JSAtom js_key_godot_tooled;
JSAtom js_key_godot_icon_path;
JSAtom js_key_godot_exports;
JSAtom js_key_godot_signals;
Vector<JSValue> godot_singletons;
Expand Down Expand Up @@ -119,6 +121,7 @@ class QuickJSBinder : public ECMAScriptBinder {
static JSValue godot_register_class(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv);
static JSValue godot_register_signal(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv);
static JSValue godot_register_property(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv);
static JSValue godot_set_script_metadata(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv);

_FORCE_INLINE_ static JSValue js_empty_func(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv) { return JS_UNDEFINED; }
_FORCE_INLINE_ static JSValue js_empty_consturctor(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv) { return JS_NewObject(ctx); }
Expand Down

0 comments on commit 706d39a

Please sign in to comment.