1 Commits
main ... 3.x

Author SHA1 Message Date
435c16942c hook -> GodotHook 2022-08-19 05:16:20 +03:00
5 changed files with 41 additions and 65 deletions

View File

@ -9,7 +9,6 @@
## Compilation ## Compilation
- Download GodotHook and place it to the Godot `modules` folder. - Download GodotHook and place it to the Godot `modules` folder.
- Rename `GodotHook-master` to `GodotHook`
- Compile Godot like usual using one of [these guides](https://docs.godotengine.org/en/stable/development/compiling/index.html). - Compile Godot like usual using one of [these guides](https://docs.godotengine.org/en/stable/development/compiling/index.html).
Example compilation `Windows` command: `scons p=windows tools=yes -j4` Example compilation `Windows` command: `scons p=windows tools=yes -j4`
@ -17,8 +16,8 @@ Example compilation `Windows` command: `scons p=windows tools=yes -j4`
## Methods ## Methods
```gdscript ```gdscript
hook.GetTable() hook.GetTable()
hook.Add(event: String, uid: String, function: Callable) hook.Add(event: String, uid: String, function: FuncRef)
hook.Call(event: String, args: Array = [], defer: bool = false) hook.Call(event: String, args: Array)
hook.Remove(event: String, uid: String) hook.Remove(event: String, uid: String)
``` ```
@ -28,7 +27,7 @@ hook.Remove(event: String, uid: String)
```gdscript ```gdscript
# autorun.gd # autorun.gd
@onready var hook: Hook = Hook.new() var hook: Hook = Hook.new()
func printHookOutput1(a: String, b: String): func printHookOutput1(a: String, b: String):
print(a, " ", b) print(a, " ", b)
@ -36,15 +35,14 @@ func printHookOutput1(a: String, b: String):
func printHookOutput2(a: String, b: String): func printHookOutput2(a: String, b: String):
print(a, " ", b) print(a, " ", b)
hook.Add("OnReady", "UniqueName1", Callable(self, "printHookOutput1")) hook.Add("OnReady", "UniqueName1", funcref(self, "printHookOutput1"))
hook.Add("OnReady", "UniqueName2", Callable(self, "printHookOutput2")) hook.Add("OnReady", "UniqueName2", funcref(self, "printHookOutput2"))
``` ```
```gdscript ```gdscript
# any node script # any node script
func _ready(): func _ready():
hook.Call("OnReady", ["Hey!", "It's OnReady hook!"]) hook.Call("OnReady", ["Hey!", "It's OnReady hook!"])
hook.Call("OnReady", ["Hey!", "It's OnReady hook, but deferred!"], true)
``` ```
`hook.Remove` removes any listening event by its name and type: `hook.Remove` removes any listening event by its name and type:
@ -62,7 +60,3 @@ hook.Remove("OnReady", "UniqueName")
var hookTable: Dictionary = hook.GetTable() var hookTable: Dictionary = hook.GetTable()
``` ```
## Star History
[![Star History Chart](https://api.star-history.com/svg?repos=Mestima/GodotHook&type=Date)](https://star-history.com/#Mestima/GodotHook&Date)

View File

@ -6,42 +6,30 @@ Dictionary Hook::GetTable() {
return table; return table;
} }
void Hook::Add(String event, String uid, Callable function) { void Hook::Add(String event, String uid, Ref<FuncRef> function) {
Dictionary tmp = table.get(event, Dictionary()); Dictionary tmp = table.get(event, Dictionary());
tmp[uid] = function; tmp[uid] = function;
table[event] = tmp; table[event] = tmp;
} }
void Hook::Call(String event, Array args = Array(), bool defer = false) { void Hook::Call(String event, Array args = Array()) {
const Variant **argptrs = nullptr; for (int i = 0; i < table.size(); i++) {
if (args.size() > 0) {
argptrs = (const Variant **)alloca(sizeof(Variant *) * args.size());
for (int i = 0; i < args.size(); i++) {
argptrs[i] = &args[i];
}
}
Dictionary tmp = table.get(event, Dictionary()); Dictionary tmp = table.get(event, Dictionary());
if (!tmp.is_empty()) { if (!tmp.empty()) {
Array keys = tmp.keys(); Array keys = tmp.keys();
for (int key_i = 0; key_i < keys.size(); key_i++) { for (int key_i = 0; key_i < keys.size(); key_i++) {
Callable function = tmp[keys[key_i]]; Ref<FuncRef> function = tmp[keys[key_i]];
if (!defer) { function->call_funcv(args);
Callable::CallError call_error;
Variant r_return_variant = Variant();
function.callp(argptrs, args.size(), r_return_variant, call_error);
} else {
function.call_deferredp(argptrs, args.size());
}
} }
} else { } else {
ERR_PRINT("Hook event '" + event + "' cannot be found or empty."); ERR_PRINT("Hook event '" + event + "' cannot be found or empty.");
} }
}
} }
void Hook::Remove(String event, String uid) { void Hook::Remove(String event, String uid) {
Dictionary tmp = table.get(event, Dictionary()); Dictionary tmp = table.get(event, Dictionary());
if (!tmp.is_empty()) { if (!tmp.empty()) {
if (tmp.erase(uid)) { if (tmp.erase(uid)) {
table[event] = tmp; table[event] = tmp;
} else { } else {
@ -55,7 +43,7 @@ void Hook::Remove(String event, String uid) {
void Hook::_bind_methods() { void Hook::_bind_methods() {
ClassDB::bind_method(D_METHOD("GetTable"), &Hook::GetTable); ClassDB::bind_method(D_METHOD("GetTable"), &Hook::GetTable);
ClassDB::bind_method(D_METHOD("Add", "event", "uid", "function"), &Hook::Add); ClassDB::bind_method(D_METHOD("Add", "event", "uid", "function"), &Hook::Add);
ClassDB::bind_method(D_METHOD("Call", "event", "args", "defer"), &Hook::Call, DEFVAL(Array()), DEFVAL(false)); ClassDB::bind_method(D_METHOD("Call", "event", "args"), &Hook::Call);
ClassDB::bind_method(D_METHOD("Remove", "event", "uid"), &Hook::Remove); ClassDB::bind_method(D_METHOD("Remove", "event", "uid"), &Hook::Remove);
}; };

19
hook.h
View File

@ -3,15 +3,14 @@
#ifndef HOOK_H #ifndef HOOK_H
#define HOOK_H #define HOOK_H
#include "core/object/ref_counted.h" #include "core/reference.h"
#include "core/string/ustring.h" #include "core/func_ref.h"
#include "core/variant/variant.h" #include "core/ustring.h"
#include "core/variant/callable.h" #include "core/dictionary.h"
#include "core/variant/array.h" #include "core/array.h"
#include "core/variant/dictionary.h"
class Hook : public RefCounted { class Hook : public Reference {
GDCLASS(Hook, RefCounted); GDCLASS(Hook, Reference);
Dictionary table; Dictionary table;
@ -20,8 +19,8 @@ protected:
public: public:
Dictionary GetTable(); Dictionary GetTable();
void Add(String event, String uid, Callable function); void Add(String event, String uid, Ref<FuncRef> function);
void Call(String event, Array args, bool defer); void Call(String event, Array args);
void Remove(String event, String uid); void Remove(String event, String uid);
Hook(); Hook();
}; };

View File

@ -1,17 +1,14 @@
/* register_types.cpp */ /* register_types.cpp */
#include "register_types.h" #include "register_types.h"
#include "core/object/class_db.h"
#include "core/class_db.h"
#include "hook.h" #include "hook.h"
void initialize_GodotHook_module(ModuleInitializationLevel p_level) { void register_GodotHook_types() {
if (p_level == MODULE_INITIALIZATION_LEVEL_SCENE) {
ClassDB::register_class<Hook>(); ClassDB::register_class<Hook>();
}
} }
void uninitialize_GodotHook_module(ModuleInitializationLevel p_level) { void unregister_GodotHook_types() {
if (p_level != MODULE_INITIALIZATION_LEVEL_SCENE) { // Nothing to do here in this example.
return;
}
} }

View File

@ -1,7 +1,5 @@
/* register_types.h */ /* register_types.h */
#include "modules/register_module_types.h" void register_GodotHook_types();
void unregister_GodotHook_types();
void initialize_GodotHook_module(ModuleInitializationLevel p_level);
void uninitialize_GodotHook_module(ModuleInitializationLevel p_level);
/* yes, the word in the middle must be the same as the module folder name */ /* yes, the word in the middle must be the same as the module folder name */