Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: open .mjs files generated from .ts file inside external editor #211

Merged
merged 4 commits into from
Sep 27, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 5 additions & 16 deletions editor/editor_tools.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,9 @@
};

static Error dump_to_file(const String &p_path, const String &p_content) {
Ref<FileAccess> tsconfig = FileAccess::open(p_path, FileAccess::WRITE);
if (tsconfig.is_valid() && tsconfig->is_open()) {
tsconfig->store_string(p_content);
const Ref<FileAccess> file = FileAccess::open(p_path, FileAccess::WRITE);
if (file.is_valid() && file->is_open()) {
file->store_string(p_content);
return OK;
}
return FAILED;
Expand All @@ -43,8 +43,8 @@
case MainLoop::NOTIFICATION_APPLICATION_FOCUS_IN: {
const HashSet<Ref<JavaScript>> &scripts = JavaScriptLanguage::get_singleton()->get_scripts();
for (const Ref<JavaScript> &s : scripts) {
uint64_t last_time = s->get_last_modified_time();
uint64_t time = FileAccess::get_modified_time(s->get_script_path());
const uint64_t last_time = s->get_last_modified_time();
const uint64_t time = FileAccess::get_modified_time(s->get_script_path());
if (last_time != time) {
JavaScriptLanguage::get_singleton()->reload_tool_script(s, true);
}
Expand All @@ -58,9 +58,6 @@
case MenuItem::ITEM_GEN_DECLARE_FILE:
declaration_file_dialog->popup_centered_ratio();
break;
case MenuItem::ITEM_GEN_TYPESCRIPT_PROJECT:
_generate_typescript_project();
break;
case MenuItem::ITEM_GEN_ENUM_BINDING_SCRIPT:
enumberation_file_dialog->popup_centered_ratio();
break;
Expand All @@ -72,7 +69,6 @@
add_tool_submenu_item(TTR("JavaScript"), menu);
menu->add_item(TTR("Generate TypeScript Declaration File"), ITEM_GEN_DECLARE_FILE);
menu->add_item(TTR("Generate Enumeration Binding Script"), ITEM_GEN_ENUM_BINDING_SCRIPT);
menu->add_item(TTR("Generate TypeScript Project"), ITEM_GEN_TYPESCRIPT_PROJECT);
menu->connect("id_pressed", callable_mp(this, &JavaScriptPlugin::_on_menu_item_pressed));

declaration_file_dialog = memnew(EditorFileDialog);
Expand Down Expand Up @@ -184,15 +180,8 @@
dump_to_file(p_path, file_content);
}

void JavaScriptPlugin::_generate_typescript_project() {
_export_typescript_declare_file("res://godot.d.ts");
dump_to_file("res://tsconfig.json", TSCONFIG_CONTENT);
dump_to_file("res://decorators.ts", TS_DECORATORS_CONTENT);
dump_to_file("res://package.json", PACKAGE_JSON_CONTENT);
}

// The following functions are used to generate a godot.d.ts file out of the docs folder from godot
#pragma region TS declare file

Check warning on line 184 in editor/editor_tools.cpp

View workflow job for this annotation

GitHub Actions / 🐧 Linux / Editor w/ Mono (target=editor)

ignoring #pragma region TS [-Wunknown-pragmas]

static String format_doc_text(const String &p_bbcode, const String &p_indent = "\t") {
String markdown = p_bbcode.strip_edges();
Expand Down Expand Up @@ -727,6 +716,6 @@
}
}

#pragma endregion TS declare file

Check warning on line 719 in editor/editor_tools.cpp

View workflow job for this annotation

GitHub Actions / 🐧 Linux / Editor w/ Mono (target=editor)

ignoring #pragma endregion TS [-Wunknown-pragmas]

#endif // TOOLS_ENABLED
5 changes: 0 additions & 5 deletions editor/editor_tools.h
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,6 @@ class JavaScriptPlugin : public EditorPlugin {

enum MenuItem {
ITEM_GEN_DECLARE_FILE,
ITEM_GEN_TYPESCRIPT_PROJECT,
ITEM_GEN_ENUM_BINDING_SCRIPT,
};

Expand All @@ -24,9 +23,6 @@ class JavaScriptPlugin : public EditorPlugin {
protected:
/* Strings will be generated by ./SCsub from misc directory */
static String BUILTIN_DECLARATION_TEXT;
static String TSCONFIG_CONTENT;
static String TS_DECORATORS_CONTENT;
static String PACKAGE_JSON_CONTENT;

/* Missing declarations, ignoring*/
static Dictionary DECLARATION_CONSTRUCTORS;
Expand All @@ -39,7 +35,6 @@ class JavaScriptPlugin : public EditorPlugin {
void _on_menu_item_pressed(int item);
void _export_typescript_declare_file(const String &p_path);
void _export_enumeration_binding_file(const String &p_path);
void _generate_typescript_project();

public:
virtual String get_name() const override { return "JavaScriptPlugin"; }
Expand Down
File renamed without changes
1 change: 1 addition & 0 deletions javascript.h
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
#define EXT_TSCLASS "ts"
#define EXT_JSMODULE "js"
#define EXT_JSON "json"
#define EXT_GENERATE "//generatedPath="

class JavaScript : public Script {
GDCLASS(JavaScript, Script);
Expand Down
14 changes: 1 addition & 13 deletions misc/generate/editor_tools.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,17 +12,5 @@ def get_editor_tools_files():
"editor/godot.d.ts.gen.cpp": (
"BUILTIN_DECLARATION_TEXT",
"misc/typescript/godot.d.ts",
),
"editor/tsconfig.json.gen.cpp": (
"TSCONFIG_CONTENT",
"misc/typescript/tsconfig.json",
),
"editor/decorators.ts.gen.cpp": (
"TS_DECORATORS_CONTENT",
"misc/typescript/decorators.ts",
),
"editor/package.json.gen.cpp": (
"PACKAGE_JSON_CONTENT",
"misc/typescript/package.json",
),
)
}
10 changes: 0 additions & 10 deletions misc/typescript/package.json

This file was deleted.

17 changes: 0 additions & 17 deletions misc/typescript/tsconfig.json

This file was deleted.

83 changes: 81 additions & 2 deletions src/language/javascript_todo_texteditor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,92 @@

#include "javascript_language.h"

#include <core/config/project_settings.h>
#include <core/io/json.h>

#ifdef TOOLS_ENABLED
#include <editor/editor_settings.h>
#endif

int JavaScriptLanguage::find_function(const String &p_function, const String &p_code) const { return -1; }
String JavaScriptLanguage::make_function(const String &p_class, const String &p_name, const PackedStringArray &p_args) const { return ""; }
void JavaScriptLanguage::auto_indent_code(String &p_code, int p_from_line, int p_to_line) const {}

bool JavaScriptLanguage::supports_documentation() const { return false; }
bool JavaScriptLanguage::can_inherit_from_file() const { return false; }
Error JavaScriptLanguage::open_in_external_editor(const Ref<Script> &p_script, int p_line, int p_col) { return ERR_UNAVAILABLE; }
bool JavaScriptLanguage::overrides_external_editor() { return false; }
Error JavaScriptLanguage::complete_code(const String &p_code, const String &p_path, Object *p_owner, List<ScriptLanguage::CodeCompletionOption> *r_options, bool &r_force, String &r_call_hint) { return ERR_UNAVAILABLE; }
Error JavaScriptLanguage::lookup_code(const String &p_code, const String &p_symbol, const String &p_path, Object *p_owner, ScriptLanguage::LookupResult &r_result) { return ERR_UNAVAILABLE; }

#ifdef TOOLS_ENABLED
Error JavaScriptLanguage::open_in_external_editor(const Ref<Script> &p_script, int p_line, int p_col) {
const Ref<JavaScript> s = p_script;
const String origin_script_path = s->get_script_path();
if (origin_script_path.ends_with(EXT_JSCLASS)) {
const String path = EditorSettings::get_singleton()->get("text_editor/external/exec_path");
String flags = EditorSettings::get_singleton()->get("text_editor/external/exec_flags");

List<String> args;
bool has_file_flag = false;

String resolved_path = origin_script_path;
const String source_code = s->get_source_code();
if (source_code.begins_with(EXT_GENERATE)) {
const Vector<String> found_path = source_code.split("\n", false, 0);
if (found_path.size() > 0) {
resolved_path = found_path[0].replacen(EXT_GENERATE, "");
}
}

const String script_path = ProjectSettings::get_singleton()->globalize_path(resolved_path);
if (flags.size()) {
const String project_path = ProjectSettings::get_singleton()->get_resource_path();
flags = flags.replacen("{line}", itos(p_line > 0 ? p_line : 0));
flags = flags.replacen("{col}", itos(p_col));
flags = flags.strip_edges().replace("\\\\", "\\");
int from = 0;
int num_chars = 0;
bool inside_quotes = false;
for (int i = 0; i < flags.size(); i++) {
if (flags[i] == '"' && (!i || flags[i - 1] != '\\')) {
if (!inside_quotes) {
from++;
}
inside_quotes = !inside_quotes;
} else if (flags[i] == '\0' || (!inside_quotes && flags[i] == ' ')) {
String arg = flags.substr(from, num_chars);
if (arg.find("{file}") != -1) {
has_file_flag = true;
}
// do path replacement here, else there will be issues with spaces and quotes
arg = arg.replacen("{project}", project_path);
arg = arg.replacen("{file}", script_path);
args.push_back(arg);
from = i + 1;
num_chars = 0;
} else {
num_chars++;
}
}
}
// Default to passing script path if no {file} flag is specified.
if (!has_file_flag) {
args.push_back(script_path);
}
const Error err = OS::get_singleton()->execute(path, args);
if (err != OK) {
WARN_PRINT("Couldn't open external text editor, using internal");
}

return err;
}

return OK;
}

bool JavaScriptLanguage::overrides_external_editor() {
return EditorSettings::get_singleton()->get("text_editor/external/use_external_editor");
}
#else
Error JavaScriptLanguage::open_in_external_editor(const Ref<Script> &p_script, int p_line, int p_col) { return ERR_UNAVAILABLE; }
bool JavaScriptLanguage::overrides_external_editor() { return false; }
#endif
Loading