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

GDScript DocGen: Fix and improve appearance of metatypes and values #82067

Merged
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
12 changes: 6 additions & 6 deletions editor/editor_help.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -462,7 +462,7 @@ void EditorHelp::_add_method(const DocData::MethodDoc &p_method, bool p_overview
class_desc->add_text(" = ");
class_desc->pop();
class_desc->push_color(theme_cache.value_color);
_add_text(_fix_constant(p_method.arguments[j].default_value));
class_desc->add_text(_fix_constant(p_method.arguments[j].default_value));
class_desc->pop();
}

Expand Down Expand Up @@ -1062,7 +1062,7 @@ void EditorHelp::_update_doc() {
class_desc->pop();

class_desc->push_color(theme_cache.value_color);
_add_text(_fix_constant(cd.properties[i].default_value));
class_desc->add_text(_fix_constant(cd.properties[i].default_value));
class_desc->pop();

class_desc->push_color(theme_cache.symbol_color);
Expand Down Expand Up @@ -1238,7 +1238,7 @@ void EditorHelp::_update_doc() {
class_desc->add_text(" [" + TTR("default:") + " ");
class_desc->pop();
class_desc->push_color(theme_cache.value_color);
_add_text(_fix_constant(cd.theme_properties[i].default_value));
class_desc->add_text(_fix_constant(cd.theme_properties[i].default_value));
class_desc->pop();
class_desc->push_color(theme_cache.symbol_color);
class_desc->add_text("]");
Expand Down Expand Up @@ -1454,7 +1454,7 @@ void EditorHelp::_update_doc() {
class_desc->add_text(" = ");
class_desc->pop();
class_desc->push_color(theme_cache.value_color);
_add_text(_fix_constant(enum_list[i].value));
class_desc->add_text(_fix_constant(enum_list[i].value));
class_desc->pop();

if (enum_list[i].is_deprecated) {
Expand Down Expand Up @@ -1530,7 +1530,7 @@ void EditorHelp::_update_doc() {
class_desc->add_text(" = ");
class_desc->pop();
class_desc->push_color(theme_cache.value_color);
_add_text(_fix_constant(constants[i].value));
class_desc->add_text(_fix_constant(constants[i].value));
class_desc->pop();

if (constants[i].is_deprecated) {
Expand Down Expand Up @@ -1711,7 +1711,7 @@ void EditorHelp::_update_doc() {
class_desc->pop(); // color

class_desc->push_color(theme_cache.value_color);
_add_text(_fix_constant(cd.properties[i].default_value));
class_desc->add_text(_fix_constant(cd.properties[i].default_value));
class_desc->pop(); // color

class_desc->push_color(theme_cache.symbol_color);
Expand Down
126 changes: 115 additions & 11 deletions modules/gdscript/editor/gdscript_docgen.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -32,14 +32,11 @@

#include "../gdscript.h"

using GDP = GDScriptParser;
using GDType = GDP::DataType;

static String _get_script_path(const String &p_path) {
String GDScriptDocGen::_get_script_path(const String &p_path) {
return p_path.trim_prefix("res://").quote();
}

static String _get_class_name(const GDP::ClassNode &p_class) {
String GDScriptDocGen::_get_class_name(const GDP::ClassNode &p_class) {
const GDP::ClassNode *curr_class = &p_class;
if (!curr_class->identifier) { // All inner classes have an identifier, so this is the outer class.
return _get_script_path(curr_class->fqcn);
Expand All @@ -56,7 +53,7 @@ static String _get_class_name(const GDP::ClassNode &p_class) {
return full_name;
}

static void _doctype_from_gdtype(const GDType &p_gdtype, String &r_type, String &r_enum, bool p_is_return = false) {
void GDScriptDocGen::_doctype_from_gdtype(const GDType &p_gdtype, String &r_type, String &r_enum, bool p_is_return) {
if (!p_gdtype.is_hard_type()) {
r_type = "Variant";
return;
Expand All @@ -82,9 +79,18 @@ static void _doctype_from_gdtype(const GDType &p_gdtype, String &r_type, String
r_type = Variant::get_type_name(p_gdtype.builtin_type);
return;
case GDType::NATIVE:
if (p_gdtype.is_meta_type) {
//r_type = GDScriptNativeClass::get_class_static();
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Superfluous comment here

r_type = "Object"; // "GDScriptNativeClass" refers to a blank page.
return;
}
r_type = p_gdtype.native_type;
return;
case GDType::SCRIPT:
if (p_gdtype.is_meta_type) {
r_type = p_gdtype.script_type.is_valid() ? p_gdtype.script_type->get_class() : Script::get_class_static();
return;
}
if (p_gdtype.script_type.is_valid()) {
if (p_gdtype.script_type->get_global_name() != StringName()) {
r_type = p_gdtype.script_type->get_global_name();
Expand All @@ -102,9 +108,17 @@ static void _doctype_from_gdtype(const GDType &p_gdtype, String &r_type, String
r_type = "Object";
return;
case GDType::CLASS:
if (p_gdtype.is_meta_type) {
r_type = GDScript::get_class_static();
return;
}
r_type = _get_class_name(*p_gdtype.class_type);
return;
case GDType::ENUM:
if (p_gdtype.is_meta_type) {
r_type = "Dictionary";
return;
}
r_type = "int";
r_enum = String(p_gdtype.native_type).replace("::", ".");
if (r_enum.begins_with("res://")) {
Expand All @@ -123,6 +137,90 @@ static void _doctype_from_gdtype(const GDType &p_gdtype, String &r_type, String
}
}

String GDScriptDocGen::_docvalue_from_variant(const Variant &p_variant, int p_recursion_level) {
constexpr int MAX_RECURSION_LEVEL = 2;

switch (p_variant.get_type()) {
case Variant::STRING:
return String(p_variant).c_escape().quote();
case Variant::OBJECT:
return "<Object>";
case Variant::DICTIONARY: {
const Dictionary dict = p_variant;

if (dict.is_empty()) {
return "{}";
}

if (p_recursion_level > MAX_RECURSION_LEVEL) {
return "{...}";
}

List<Variant> keys;
dict.get_key_list(&keys);
keys.sort();

String data;
for (List<Variant>::Element *E = keys.front(); E; E = E->next()) {
if (E->prev()) {
data += ", ";
}
data += _docvalue_from_variant(E->get(), p_recursion_level + 1) + ": " + _docvalue_from_variant(dict[E->get()], p_recursion_level + 1);
}

return "{" + data + "}";
} break;
case Variant::ARRAY: {
const Array array = p_variant;
String result;

if (array.get_typed_builtin() != Variant::NIL) {
result += "Array[";

Ref<Script> script = array.get_typed_script();
if (script.is_valid()) {
if (script->get_global_name() != StringName()) {
result += script->get_global_name();
} else if (!script->get_path().get_file().is_empty()) {
result += script->get_path().get_file();
} else {
result += array.get_typed_class_name();
}
} else if (array.get_typed_class_name() != StringName()) {
result += array.get_typed_class_name();
} else {
result += Variant::get_type_name((Variant::Type)array.get_typed_builtin());
}

result += "](";
}

if (array.is_empty()) {
result += "[]";
} else if (p_recursion_level > MAX_RECURSION_LEVEL) {
result += "[...]";
} else {
result += "[";
for (int i = 0; i < array.size(); i++) {
if (i > 0) {
result += ", ";
}
result += _docvalue_from_variant(array[i], p_recursion_level + 1);
}
result += "]";
}

if (array.get_typed_builtin() != Variant::NIL) {
result += ")";
}

return result;
} break;
default:
return p_variant.get_construct_string();
}
}

void GDScriptDocGen::generate_docs(GDScript *p_script, const GDP::ClassNode *p_class) {
p_script->_clear_doc();

Expand Down Expand Up @@ -183,7 +281,10 @@ void GDScriptDocGen::generate_docs(GDScript *p_script, const GDP::ClassNode *p_c
p_script->member_lines[const_name] = m_const->start_line;

DocData::ConstantDoc const_doc;
DocData::constant_doc_from_variant(const_doc, const_name, m_const->initializer->reduced_value, m_const->doc_data.description);
const_doc.name = const_name;
const_doc.value = _docvalue_from_variant(m_const->initializer->reduced_value);
const_doc.is_value_valid = true;
const_doc.description = m_const->doc_data.description;
const_doc.is_deprecated = m_const->doc_data.is_deprecated;
const_doc.is_experimental = m_const->doc_data.is_experimental;
doc.constants.push_back(const_doc);
Expand Down Expand Up @@ -217,7 +318,7 @@ void GDScriptDocGen::generate_docs(GDScript *p_script, const GDP::ClassNode *p_c
_doctype_from_gdtype(p->get_datatype(), arg_doc.type, arg_doc.enumeration);
if (p->initializer != nullptr) {
if (p->initializer->is_constant) {
arg_doc.default_value = p->initializer->reduced_value.get_construct_string().replace("\n", "\\n");
arg_doc.default_value = _docvalue_from_variant(p->initializer->reduced_value);
} else {
arg_doc.default_value = "<unknown>";
}
Expand Down Expand Up @@ -286,7 +387,7 @@ void GDScriptDocGen::generate_docs(GDScript *p_script, const GDP::ClassNode *p_c

if (m_var->initializer) {
if (m_var->initializer->is_constant) {
prop_doc.default_value = m_var->initializer->reduced_value.get_construct_string().replace("\n", "\\n");
prop_doc.default_value = _docvalue_from_variant(m_var->initializer->reduced_value);
} else {
prop_doc.default_value = "<unknown>";
}
Expand All @@ -312,7 +413,7 @@ void GDScriptDocGen::generate_docs(GDScript *p_script, const GDP::ClassNode *p_c
for (const GDP::EnumNode::Value &val : m_enum->values) {
DocData::ConstantDoc const_doc;
const_doc.name = val.identifier->name;
const_doc.value = String(Variant(val.value));
const_doc.value = _docvalue_from_variant(val.value);
const_doc.is_value_valid = true;
const_doc.enumeration = name;
const_doc.description = val.doc_data.description;
Expand All @@ -331,8 +432,11 @@ void GDScriptDocGen::generate_docs(GDScript *p_script, const GDP::ClassNode *p_c
p_script->member_lines[name] = m_enum_val.identifier->start_line;

DocData::ConstantDoc const_doc;
DocData::constant_doc_from_variant(const_doc, name, m_enum_val.value, m_enum_val.doc_data.description);
const_doc.name = name;
const_doc.value = _docvalue_from_variant(m_enum_val.value);
const_doc.is_value_valid = true;
const_doc.enumeration = "@unnamed_enums";
const_doc.description = m_enum_val.doc_data.description;
const_doc.is_deprecated = m_enum_val.doc_data.is_deprecated;
const_doc.is_experimental = m_enum_val.doc_data.is_experimental;
doc.constants.push_back(const_doc);
Expand Down
10 changes: 9 additions & 1 deletion modules/gdscript/editor/gdscript_docgen.h
Original file line number Diff line number Diff line change
Expand Up @@ -36,8 +36,16 @@
#include "core/doc_data.h"

class GDScriptDocGen {
using GDP = GDScriptParser;
using GDType = GDP::DataType;

static String _get_script_path(const String &p_path);
static String _get_class_name(const GDP::ClassNode &p_class);
static void _doctype_from_gdtype(const GDType &p_gdtype, String &r_type, String &r_enum, bool p_is_return = false);
static String _docvalue_from_variant(const Variant &p_variant, int p_recursion_level = 1);

public:
static void generate_docs(GDScript *p_script, const GDScriptParser::ClassNode *p_class);
static void generate_docs(GDScript *p_script, const GDP::ClassNode *p_class);
};

#endif // GDSCRIPT_DOCGEN_H