|
@@ -337,311 +337,318 @@ static Variant get_documentation_default_value(const StringName &p_class_name, c
|
|
|
}
|
|
|
|
|
|
void DocTools::generate(bool p_basic_types) {
|
|
|
- List<StringName> classes;
|
|
|
- ClassDB::get_class_list(&classes);
|
|
|
- classes.sort_custom<StringName::AlphCompare>();
|
|
|
- // Move ProjectSettings, so that other classes can register properties there.
|
|
|
- classes.move_to_back(classes.find("ProjectSettings"));
|
|
|
-
|
|
|
- bool skip_setter_getter_methods = true;
|
|
|
-
|
|
|
- while (classes.size()) {
|
|
|
- HashSet<StringName> setters_getters;
|
|
|
-
|
|
|
- String name = classes.front()->get();
|
|
|
- if (!ClassDB::is_class_exposed(name)) {
|
|
|
- print_verbose(vformat("Class '%s' is not exposed, skipping.", name));
|
|
|
- classes.pop_front();
|
|
|
- continue;
|
|
|
- }
|
|
|
-
|
|
|
- String cname = name;
|
|
|
-
|
|
|
- class_list[cname] = DocData::ClassDoc();
|
|
|
- DocData::ClassDoc &c = class_list[cname];
|
|
|
- c.name = cname;
|
|
|
- c.inherits = ClassDB::get_parent_class(name);
|
|
|
+ // Add ClassDB-exposed classes.
|
|
|
+ {
|
|
|
+ List<StringName> classes;
|
|
|
+ ClassDB::get_class_list(&classes);
|
|
|
+ classes.sort_custom<StringName::AlphCompare>();
|
|
|
+ // Move ProjectSettings, so that other classes can register properties there.
|
|
|
+ classes.move_to_back(classes.find("ProjectSettings"));
|
|
|
+
|
|
|
+ bool skip_setter_getter_methods = true;
|
|
|
+
|
|
|
+ // Populate documentation data for each exposed class.
|
|
|
+ while (classes.size()) {
|
|
|
+ String name = classes.front()->get();
|
|
|
+ if (!ClassDB::is_class_exposed(name)) {
|
|
|
+ print_verbose(vformat("Class '%s' is not exposed, skipping.", name));
|
|
|
+ classes.pop_front();
|
|
|
+ continue;
|
|
|
+ }
|
|
|
|
|
|
- List<PropertyInfo> properties;
|
|
|
- List<PropertyInfo> own_properties;
|
|
|
-
|
|
|
- // Special case for editor and project settings, so they can be documented.
|
|
|
- if (name == "EditorSettings") {
|
|
|
- // We don't create the full blown EditorSettings (+ config file) with `create()`,
|
|
|
- // instead we just make a local instance to get default values.
|
|
|
- Ref<EditorSettings> edset = memnew(EditorSettings);
|
|
|
- edset->get_property_list(&properties);
|
|
|
- own_properties = properties;
|
|
|
- } else if (name == "ProjectSettings") {
|
|
|
- ProjectSettings::get_singleton()->get_property_list(&properties);
|
|
|
- own_properties = properties;
|
|
|
- } else {
|
|
|
- ClassDB::get_property_list(name, &properties);
|
|
|
- ClassDB::get_property_list(name, &own_properties, true);
|
|
|
- }
|
|
|
+ String cname = name;
|
|
|
+ // Property setters and getters do not get exposed as individual methods.
|
|
|
+ HashSet<StringName> setters_getters;
|
|
|
|
|
|
- properties.sort();
|
|
|
- own_properties.sort();
|
|
|
+ class_list[cname] = DocData::ClassDoc();
|
|
|
+ DocData::ClassDoc &c = class_list[cname];
|
|
|
+ c.name = cname;
|
|
|
+ c.inherits = ClassDB::get_parent_class(name);
|
|
|
|
|
|
- List<PropertyInfo>::Element *EO = own_properties.front();
|
|
|
- for (const PropertyInfo &E : properties) {
|
|
|
- bool inherited = true;
|
|
|
- if (EO && EO->get() == E) {
|
|
|
- inherited = false;
|
|
|
- EO = EO->next();
|
|
|
- }
|
|
|
+ List<PropertyInfo> properties;
|
|
|
+ List<PropertyInfo> own_properties;
|
|
|
|
|
|
- if (E.usage & PROPERTY_USAGE_GROUP || E.usage & PROPERTY_USAGE_SUBGROUP || E.usage & PROPERTY_USAGE_CATEGORY || E.usage & PROPERTY_USAGE_INTERNAL || (E.type == Variant::NIL && E.usage & PROPERTY_USAGE_ARRAY)) {
|
|
|
- continue;
|
|
|
+ // Special case for editor and project settings, so they can be documented.
|
|
|
+ if (name == "EditorSettings") {
|
|
|
+ // We don't create the full blown EditorSettings (+ config file) with `create()`,
|
|
|
+ // instead we just make a local instance to get default values.
|
|
|
+ Ref<EditorSettings> edset = memnew(EditorSettings);
|
|
|
+ edset->get_property_list(&properties);
|
|
|
+ own_properties = properties;
|
|
|
+ } else if (name == "ProjectSettings") {
|
|
|
+ ProjectSettings::get_singleton()->get_property_list(&properties);
|
|
|
+ own_properties = properties;
|
|
|
+ } else {
|
|
|
+ ClassDB::get_property_list(name, &properties);
|
|
|
+ ClassDB::get_property_list(name, &own_properties, true);
|
|
|
}
|
|
|
|
|
|
- DocData::PropertyDoc prop;
|
|
|
- prop.name = E.name;
|
|
|
- prop.overridden = inherited;
|
|
|
+ properties.sort();
|
|
|
+ own_properties.sort();
|
|
|
|
|
|
- if (inherited) {
|
|
|
- String parent = ClassDB::get_parent_class(c.name);
|
|
|
- while (!ClassDB::has_property(parent, prop.name, true)) {
|
|
|
- parent = ClassDB::get_parent_class(parent);
|
|
|
+ List<PropertyInfo>::Element *EO = own_properties.front();
|
|
|
+ for (const PropertyInfo &E : properties) {
|
|
|
+ bool inherited = true;
|
|
|
+ if (EO && EO->get() == E) {
|
|
|
+ inherited = false;
|
|
|
+ EO = EO->next();
|
|
|
}
|
|
|
- prop.overrides = parent;
|
|
|
- }
|
|
|
-
|
|
|
- bool default_value_valid = false;
|
|
|
- Variant default_value;
|
|
|
|
|
|
- if (name == "EditorSettings") {
|
|
|
- if (E.name == "resource_local_to_scene" || E.name == "resource_name" || E.name == "resource_path" || E.name == "script") {
|
|
|
- // Don't include spurious properties in the generated EditorSettings class reference.
|
|
|
+ if (E.usage & PROPERTY_USAGE_GROUP || E.usage & PROPERTY_USAGE_SUBGROUP || E.usage & PROPERTY_USAGE_CATEGORY || E.usage & PROPERTY_USAGE_INTERNAL || (E.type == Variant::NIL && E.usage & PROPERTY_USAGE_ARRAY)) {
|
|
|
continue;
|
|
|
}
|
|
|
- }
|
|
|
|
|
|
- if (name == "ProjectSettings") {
|
|
|
- // Special case for project settings, so that settings are not taken from the current project's settings
|
|
|
- if (E.name == "script" || !ProjectSettings::get_singleton()->is_builtin_setting(E.name)) {
|
|
|
- continue;
|
|
|
- }
|
|
|
- if (E.usage & PROPERTY_USAGE_EDITOR) {
|
|
|
- if (!ProjectSettings::get_singleton()->get_ignore_value_in_docs(E.name)) {
|
|
|
- default_value = ProjectSettings::get_singleton()->property_get_revert(E.name);
|
|
|
- default_value_valid = true;
|
|
|
+ DocData::PropertyDoc prop;
|
|
|
+ prop.name = E.name;
|
|
|
+ prop.overridden = inherited;
|
|
|
+
|
|
|
+ if (inherited) {
|
|
|
+ String parent = ClassDB::get_parent_class(c.name);
|
|
|
+ while (!ClassDB::has_property(parent, prop.name, true)) {
|
|
|
+ parent = ClassDB::get_parent_class(parent);
|
|
|
}
|
|
|
+ prop.overrides = parent;
|
|
|
}
|
|
|
- } else {
|
|
|
- default_value = get_documentation_default_value(name, E.name, default_value_valid);
|
|
|
- if (inherited) {
|
|
|
- bool base_default_value_valid = false;
|
|
|
- Variant base_default_value = get_documentation_default_value(ClassDB::get_parent_class(name), E.name, base_default_value_valid);
|
|
|
- if (!default_value_valid || !base_default_value_valid || default_value == base_default_value) {
|
|
|
+
|
|
|
+ bool default_value_valid = false;
|
|
|
+ Variant default_value;
|
|
|
+
|
|
|
+ if (name == "EditorSettings") {
|
|
|
+ if (E.name == "resource_local_to_scene" || E.name == "resource_name" || E.name == "resource_path" || E.name == "script") {
|
|
|
+ // Don't include spurious properties in the generated EditorSettings class reference.
|
|
|
continue;
|
|
|
}
|
|
|
}
|
|
|
- }
|
|
|
|
|
|
- if (default_value_valid && default_value.get_type() != Variant::OBJECT) {
|
|
|
- prop.default_value = default_value.get_construct_string().replace("\n", " ");
|
|
|
- }
|
|
|
-
|
|
|
- StringName setter = ClassDB::get_property_setter(name, E.name);
|
|
|
- StringName getter = ClassDB::get_property_getter(name, E.name);
|
|
|
-
|
|
|
- prop.setter = setter;
|
|
|
- prop.getter = getter;
|
|
|
-
|
|
|
- bool found_type = false;
|
|
|
- if (getter != StringName()) {
|
|
|
- MethodBind *mb = ClassDB::get_method(name, getter);
|
|
|
- if (mb) {
|
|
|
- PropertyInfo retinfo = mb->get_return_info();
|
|
|
-
|
|
|
- found_type = true;
|
|
|
- if (retinfo.type == Variant::INT && retinfo.usage & (PROPERTY_USAGE_CLASS_IS_ENUM | PROPERTY_USAGE_CLASS_IS_BITFIELD)) {
|
|
|
- prop.enumeration = retinfo.class_name;
|
|
|
- prop.type = "int";
|
|
|
- } else if (retinfo.class_name != StringName()) {
|
|
|
- prop.type = retinfo.class_name;
|
|
|
- } else if (retinfo.type == Variant::ARRAY && retinfo.hint == PROPERTY_HINT_ARRAY_TYPE) {
|
|
|
- prop.type = retinfo.hint_string + "[]";
|
|
|
- } else if (retinfo.hint == PROPERTY_HINT_RESOURCE_TYPE) {
|
|
|
- prop.type = retinfo.hint_string;
|
|
|
- } else if (retinfo.type == Variant::NIL && retinfo.usage & PROPERTY_USAGE_NIL_IS_VARIANT) {
|
|
|
- prop.type = "Variant";
|
|
|
- } else if (retinfo.type == Variant::NIL) {
|
|
|
- prop.type = "void";
|
|
|
- } else {
|
|
|
- prop.type = Variant::get_type_name(retinfo.type);
|
|
|
+ if (name == "ProjectSettings") {
|
|
|
+ // Special case for project settings, so that settings are not taken from the current project's settings
|
|
|
+ if (E.name == "script" || !ProjectSettings::get_singleton()->is_builtin_setting(E.name)) {
|
|
|
+ continue;
|
|
|
+ }
|
|
|
+ if (E.usage & PROPERTY_USAGE_EDITOR) {
|
|
|
+ if (!ProjectSettings::get_singleton()->get_ignore_value_in_docs(E.name)) {
|
|
|
+ default_value = ProjectSettings::get_singleton()->property_get_revert(E.name);
|
|
|
+ default_value_valid = true;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ default_value = get_documentation_default_value(name, E.name, default_value_valid);
|
|
|
+ if (inherited) {
|
|
|
+ bool base_default_value_valid = false;
|
|
|
+ Variant base_default_value = get_documentation_default_value(ClassDB::get_parent_class(name), E.name, base_default_value_valid);
|
|
|
+ if (!default_value_valid || !base_default_value_valid || default_value == base_default_value) {
|
|
|
+ continue;
|
|
|
+ }
|
|
|
}
|
|
|
}
|
|
|
|
|
|
- setters_getters.insert(getter);
|
|
|
- }
|
|
|
+ if (default_value_valid && default_value.get_type() != Variant::OBJECT) {
|
|
|
+ prop.default_value = default_value.get_construct_string().replace("\n", " ");
|
|
|
+ }
|
|
|
|
|
|
- if (setter != StringName()) {
|
|
|
- setters_getters.insert(setter);
|
|
|
- }
|
|
|
+ StringName setter = ClassDB::get_property_setter(name, E.name);
|
|
|
+ StringName getter = ClassDB::get_property_getter(name, E.name);
|
|
|
+
|
|
|
+ prop.setter = setter;
|
|
|
+ prop.getter = getter;
|
|
|
+
|
|
|
+ bool found_type = false;
|
|
|
+ if (getter != StringName()) {
|
|
|
+ MethodBind *mb = ClassDB::get_method(name, getter);
|
|
|
+ if (mb) {
|
|
|
+ PropertyInfo retinfo = mb->get_return_info();
|
|
|
+
|
|
|
+ found_type = true;
|
|
|
+ if (retinfo.type == Variant::INT && retinfo.usage & (PROPERTY_USAGE_CLASS_IS_ENUM | PROPERTY_USAGE_CLASS_IS_BITFIELD)) {
|
|
|
+ prop.enumeration = retinfo.class_name;
|
|
|
+ prop.type = "int";
|
|
|
+ } else if (retinfo.class_name != StringName()) {
|
|
|
+ prop.type = retinfo.class_name;
|
|
|
+ } else if (retinfo.type == Variant::ARRAY && retinfo.hint == PROPERTY_HINT_ARRAY_TYPE) {
|
|
|
+ prop.type = retinfo.hint_string + "[]";
|
|
|
+ } else if (retinfo.hint == PROPERTY_HINT_RESOURCE_TYPE) {
|
|
|
+ prop.type = retinfo.hint_string;
|
|
|
+ } else if (retinfo.type == Variant::NIL && retinfo.usage & PROPERTY_USAGE_NIL_IS_VARIANT) {
|
|
|
+ prop.type = "Variant";
|
|
|
+ } else if (retinfo.type == Variant::NIL) {
|
|
|
+ prop.type = "void";
|
|
|
+ } else {
|
|
|
+ prop.type = Variant::get_type_name(retinfo.type);
|
|
|
+ }
|
|
|
+ }
|
|
|
|
|
|
- if (!found_type) {
|
|
|
- if (E.type == Variant::OBJECT && E.hint == PROPERTY_HINT_RESOURCE_TYPE) {
|
|
|
- prop.type = E.hint_string;
|
|
|
- } else {
|
|
|
- prop.type = Variant::get_type_name(E.type);
|
|
|
+ setters_getters.insert(getter);
|
|
|
}
|
|
|
- }
|
|
|
|
|
|
- c.properties.push_back(prop);
|
|
|
- }
|
|
|
+ if (setter != StringName()) {
|
|
|
+ setters_getters.insert(setter);
|
|
|
+ }
|
|
|
|
|
|
- List<MethodInfo> method_list;
|
|
|
- ClassDB::get_method_list(name, &method_list, true);
|
|
|
- method_list.sort();
|
|
|
+ if (!found_type) {
|
|
|
+ if (E.type == Variant::OBJECT && E.hint == PROPERTY_HINT_RESOURCE_TYPE) {
|
|
|
+ prop.type = E.hint_string;
|
|
|
+ } else {
|
|
|
+ prop.type = Variant::get_type_name(E.type);
|
|
|
+ }
|
|
|
+ }
|
|
|
|
|
|
- for (const MethodInfo &E : method_list) {
|
|
|
- if (E.name.is_empty() || (E.name[0] == '_' && !(E.flags & METHOD_FLAG_VIRTUAL))) {
|
|
|
- continue; //hidden, don't count
|
|
|
+ c.properties.push_back(prop);
|
|
|
}
|
|
|
|
|
|
- if (skip_setter_getter_methods && setters_getters.has(E.name)) {
|
|
|
- // Don't skip parametric setters and getters, i.e. method which require
|
|
|
- // one or more parameters to define what property should be set or retrieved.
|
|
|
- // E.g. CPUParticles3D::set_param(Parameter param, float value).
|
|
|
- if (E.arguments.size() == 0 /* getter */ || (E.arguments.size() == 1 && E.return_val.type == Variant::NIL /* setter */)) {
|
|
|
- continue;
|
|
|
- }
|
|
|
- }
|
|
|
+ List<MethodInfo> method_list;
|
|
|
+ ClassDB::get_method_list(name, &method_list, true);
|
|
|
+ method_list.sort();
|
|
|
|
|
|
- DocData::MethodDoc method;
|
|
|
- DocData::method_doc_from_methodinfo(method, E, "");
|
|
|
+ for (const MethodInfo &E : method_list) {
|
|
|
+ if (E.name.is_empty() || (E.name[0] == '_' && !(E.flags & METHOD_FLAG_VIRTUAL))) {
|
|
|
+ continue; //hidden, don't count
|
|
|
+ }
|
|
|
|
|
|
- Vector<Error> errs = ClassDB::get_method_error_return_values(name, E.name);
|
|
|
- if (errs.size()) {
|
|
|
- if (!errs.has(OK)) {
|
|
|
- errs.insert(0, OK);
|
|
|
+ if (skip_setter_getter_methods && setters_getters.has(E.name)) {
|
|
|
+ // Don't skip parametric setters and getters, i.e. method which require
|
|
|
+ // one or more parameters to define what property should be set or retrieved.
|
|
|
+ // E.g. CPUParticles3D::set_param(Parameter param, float value).
|
|
|
+ if (E.arguments.size() == 0 /* getter */ || (E.arguments.size() == 1 && E.return_val.type == Variant::NIL /* setter */)) {
|
|
|
+ continue;
|
|
|
+ }
|
|
|
}
|
|
|
- for (int i = 0; i < errs.size(); i++) {
|
|
|
- if (!method.errors_returned.has(errs[i])) {
|
|
|
- method.errors_returned.push_back(errs[i]);
|
|
|
+
|
|
|
+ DocData::MethodDoc method;
|
|
|
+ DocData::method_doc_from_methodinfo(method, E, "");
|
|
|
+
|
|
|
+ Vector<Error> errs = ClassDB::get_method_error_return_values(name, E.name);
|
|
|
+ if (errs.size()) {
|
|
|
+ if (!errs.has(OK)) {
|
|
|
+ errs.insert(0, OK);
|
|
|
+ }
|
|
|
+ for (int i = 0; i < errs.size(); i++) {
|
|
|
+ if (!method.errors_returned.has(errs[i])) {
|
|
|
+ method.errors_returned.push_back(errs[i]);
|
|
|
+ }
|
|
|
}
|
|
|
}
|
|
|
+
|
|
|
+ c.methods.push_back(method);
|
|
|
}
|
|
|
|
|
|
- c.methods.push_back(method);
|
|
|
- }
|
|
|
+ List<MethodInfo> signal_list;
|
|
|
+ ClassDB::get_signal_list(name, &signal_list, true);
|
|
|
|
|
|
- List<MethodInfo> signal_list;
|
|
|
- ClassDB::get_signal_list(name, &signal_list, true);
|
|
|
+ if (signal_list.size()) {
|
|
|
+ for (List<MethodInfo>::Element *EV = signal_list.front(); EV; EV = EV->next()) {
|
|
|
+ DocData::MethodDoc signal;
|
|
|
+ signal.name = EV->get().name;
|
|
|
+ for (int i = 0; i < EV->get().arguments.size(); i++) {
|
|
|
+ const PropertyInfo &arginfo = EV->get().arguments[i];
|
|
|
+ DocData::ArgumentDoc argument;
|
|
|
+ DocData::argument_doc_from_arginfo(argument, arginfo);
|
|
|
|
|
|
- if (signal_list.size()) {
|
|
|
- for (List<MethodInfo>::Element *EV = signal_list.front(); EV; EV = EV->next()) {
|
|
|
- DocData::MethodDoc signal;
|
|
|
- signal.name = EV->get().name;
|
|
|
- for (int i = 0; i < EV->get().arguments.size(); i++) {
|
|
|
- const PropertyInfo &arginfo = EV->get().arguments[i];
|
|
|
- DocData::ArgumentDoc argument;
|
|
|
- DocData::argument_doc_from_arginfo(argument, arginfo);
|
|
|
+ signal.arguments.push_back(argument);
|
|
|
+ }
|
|
|
|
|
|
- signal.arguments.push_back(argument);
|
|
|
+ c.signals.push_back(signal);
|
|
|
}
|
|
|
-
|
|
|
- c.signals.push_back(signal);
|
|
|
}
|
|
|
- }
|
|
|
|
|
|
- List<String> constant_list;
|
|
|
- ClassDB::get_integer_constant_list(name, &constant_list, true);
|
|
|
+ List<String> constant_list;
|
|
|
+ ClassDB::get_integer_constant_list(name, &constant_list, true);
|
|
|
+
|
|
|
+ for (const String &E : constant_list) {
|
|
|
+ DocData::ConstantDoc constant;
|
|
|
+ constant.name = E;
|
|
|
+ constant.value = itos(ClassDB::get_integer_constant(name, E));
|
|
|
+ constant.is_value_valid = true;
|
|
|
+ constant.enumeration = ClassDB::get_integer_constant_enum(name, E);
|
|
|
+ constant.is_bitfield = ClassDB::is_enum_bitfield(name, constant.enumeration);
|
|
|
+ c.constants.push_back(constant);
|
|
|
+ }
|
|
|
|
|
|
- for (const String &E : constant_list) {
|
|
|
- DocData::ConstantDoc constant;
|
|
|
- constant.name = E;
|
|
|
- constant.value = itos(ClassDB::get_integer_constant(name, E));
|
|
|
- constant.is_value_valid = true;
|
|
|
- constant.enumeration = ClassDB::get_integer_constant_enum(name, E);
|
|
|
- constant.is_bitfield = ClassDB::is_enum_bitfield(name, constant.enumeration);
|
|
|
- c.constants.push_back(constant);
|
|
|
- }
|
|
|
+ // Theme items.
|
|
|
+ {
|
|
|
+ List<StringName> l;
|
|
|
+
|
|
|
+ Theme::get_default()->get_color_list(cname, &l);
|
|
|
+ for (const StringName &E : l) {
|
|
|
+ DocData::ThemeItemDoc tid;
|
|
|
+ tid.name = E;
|
|
|
+ tid.type = "Color";
|
|
|
+ tid.data_type = "color";
|
|
|
+ tid.default_value = Variant(Theme::get_default()->get_color(E, cname)).get_construct_string().replace("\n", " ");
|
|
|
+ c.theme_properties.push_back(tid);
|
|
|
+ }
|
|
|
|
|
|
- // Theme items.
|
|
|
- {
|
|
|
- List<StringName> l;
|
|
|
-
|
|
|
- Theme::get_default()->get_color_list(cname, &l);
|
|
|
- for (const StringName &E : l) {
|
|
|
- DocData::ThemeItemDoc tid;
|
|
|
- tid.name = E;
|
|
|
- tid.type = "Color";
|
|
|
- tid.data_type = "color";
|
|
|
- tid.default_value = Variant(Theme::get_default()->get_color(E, cname)).get_construct_string().replace("\n", " ");
|
|
|
- c.theme_properties.push_back(tid);
|
|
|
- }
|
|
|
+ l.clear();
|
|
|
+ Theme::get_default()->get_constant_list(cname, &l);
|
|
|
+ for (const StringName &E : l) {
|
|
|
+ DocData::ThemeItemDoc tid;
|
|
|
+ tid.name = E;
|
|
|
+ tid.type = "int";
|
|
|
+ tid.data_type = "constant";
|
|
|
+ tid.default_value = itos(Theme::get_default()->get_constant(E, cname));
|
|
|
+ c.theme_properties.push_back(tid);
|
|
|
+ }
|
|
|
|
|
|
- l.clear();
|
|
|
- Theme::get_default()->get_constant_list(cname, &l);
|
|
|
- for (const StringName &E : l) {
|
|
|
- DocData::ThemeItemDoc tid;
|
|
|
- tid.name = E;
|
|
|
- tid.type = "int";
|
|
|
- tid.data_type = "constant";
|
|
|
- tid.default_value = itos(Theme::get_default()->get_constant(E, cname));
|
|
|
- c.theme_properties.push_back(tid);
|
|
|
- }
|
|
|
+ l.clear();
|
|
|
+ Theme::get_default()->get_font_list(cname, &l);
|
|
|
+ for (const StringName &E : l) {
|
|
|
+ DocData::ThemeItemDoc tid;
|
|
|
+ tid.name = E;
|
|
|
+ tid.type = "Font";
|
|
|
+ tid.data_type = "font";
|
|
|
+ c.theme_properties.push_back(tid);
|
|
|
+ }
|
|
|
|
|
|
- l.clear();
|
|
|
- Theme::get_default()->get_font_list(cname, &l);
|
|
|
- for (const StringName &E : l) {
|
|
|
- DocData::ThemeItemDoc tid;
|
|
|
- tid.name = E;
|
|
|
- tid.type = "Font";
|
|
|
- tid.data_type = "font";
|
|
|
- c.theme_properties.push_back(tid);
|
|
|
- }
|
|
|
+ l.clear();
|
|
|
+ Theme::get_default()->get_font_size_list(cname, &l);
|
|
|
+ for (const StringName &E : l) {
|
|
|
+ DocData::ThemeItemDoc tid;
|
|
|
+ tid.name = E;
|
|
|
+ tid.type = "int";
|
|
|
+ tid.data_type = "font_size";
|
|
|
+ c.theme_properties.push_back(tid);
|
|
|
+ }
|
|
|
|
|
|
- l.clear();
|
|
|
- Theme::get_default()->get_font_size_list(cname, &l);
|
|
|
- for (const StringName &E : l) {
|
|
|
- DocData::ThemeItemDoc tid;
|
|
|
- tid.name = E;
|
|
|
- tid.type = "int";
|
|
|
- tid.data_type = "font_size";
|
|
|
- c.theme_properties.push_back(tid);
|
|
|
- }
|
|
|
+ l.clear();
|
|
|
+ Theme::get_default()->get_icon_list(cname, &l);
|
|
|
+ for (const StringName &E : l) {
|
|
|
+ DocData::ThemeItemDoc tid;
|
|
|
+ tid.name = E;
|
|
|
+ tid.type = "Texture2D";
|
|
|
+ tid.data_type = "icon";
|
|
|
+ c.theme_properties.push_back(tid);
|
|
|
+ }
|
|
|
|
|
|
- l.clear();
|
|
|
- Theme::get_default()->get_icon_list(cname, &l);
|
|
|
- for (const StringName &E : l) {
|
|
|
- DocData::ThemeItemDoc tid;
|
|
|
- tid.name = E;
|
|
|
- tid.type = "Texture2D";
|
|
|
- tid.data_type = "icon";
|
|
|
- c.theme_properties.push_back(tid);
|
|
|
- }
|
|
|
+ l.clear();
|
|
|
+ Theme::get_default()->get_stylebox_list(cname, &l);
|
|
|
+ for (const StringName &E : l) {
|
|
|
+ DocData::ThemeItemDoc tid;
|
|
|
+ tid.name = E;
|
|
|
+ tid.type = "StyleBox";
|
|
|
+ tid.data_type = "style";
|
|
|
+ c.theme_properties.push_back(tid);
|
|
|
+ }
|
|
|
|
|
|
- l.clear();
|
|
|
- Theme::get_default()->get_stylebox_list(cname, &l);
|
|
|
- for (const StringName &E : l) {
|
|
|
- DocData::ThemeItemDoc tid;
|
|
|
- tid.name = E;
|
|
|
- tid.type = "StyleBox";
|
|
|
- tid.data_type = "style";
|
|
|
- c.theme_properties.push_back(tid);
|
|
|
+ c.theme_properties.sort();
|
|
|
}
|
|
|
|
|
|
- c.theme_properties.sort();
|
|
|
+ classes.pop_front();
|
|
|
}
|
|
|
-
|
|
|
- classes.pop_front();
|
|
|
}
|
|
|
|
|
|
+ // Add a dummy Variant entry.
|
|
|
{
|
|
|
- // So we can document the concept of Variant even if it's not a usable class per se.
|
|
|
+ // This allows us to document the concept of Variant even though
|
|
|
+ // it's not a ClassDB-exposed class.
|
|
|
class_list["Variant"] = DocData::ClassDoc();
|
|
|
class_list["Variant"].name = "Variant";
|
|
|
}
|
|
|
|
|
|
+ // If we don't want to populate basic types, break here.
|
|
|
if (!p_basic_types) {
|
|
|
return;
|
|
|
}
|
|
|
|
|
|
- // Add Variant types.
|
|
|
+ // Add Variant data types.
|
|
|
for (int i = 0; i < Variant::VARIANT_MAX; i++) {
|
|
|
if (i == Variant::NIL) {
|
|
|
continue; // Not exposed outside of 'null', should not be in class list.
|
|
@@ -809,14 +816,14 @@ void DocTools::generate(bool p_basic_types) {
|
|
|
}
|
|
|
}
|
|
|
|
|
|
- //built in constants and functions
|
|
|
-
|
|
|
+ // Add global API (servers, engine singletons, global constants) and Variant utility functions.
|
|
|
{
|
|
|
String cname = "@GlobalScope";
|
|
|
class_list[cname] = DocData::ClassDoc();
|
|
|
DocData::ClassDoc &c = class_list[cname];
|
|
|
c.name = cname;
|
|
|
|
|
|
+ // Global constants.
|
|
|
for (int i = 0; i < CoreConstants::get_global_constant_count(); i++) {
|
|
|
DocData::ConstantDoc cd;
|
|
|
cd.name = CoreConstants::get_global_constant_name(i);
|
|
@@ -830,10 +837,11 @@ void DocTools::generate(bool p_basic_types) {
|
|
|
c.constants.push_back(cd);
|
|
|
}
|
|
|
|
|
|
+ // Servers/engine singletons.
|
|
|
List<Engine::Singleton> singletons;
|
|
|
Engine::get_singleton()->get_singletons(&singletons);
|
|
|
|
|
|
- //servers (this is kind of hackish)
|
|
|
+ // FIXME: this is kind of hackish...
|
|
|
for (const Engine::Singleton &s : singletons) {
|
|
|
DocData::PropertyDoc pd;
|
|
|
if (!s.ptr) {
|
|
@@ -847,13 +855,14 @@ void DocTools::generate(bool p_basic_types) {
|
|
|
c.properties.push_back(pd);
|
|
|
}
|
|
|
|
|
|
+ // Variant utility functions.
|
|
|
List<StringName> utility_functions;
|
|
|
Variant::get_utility_function_list(&utility_functions);
|
|
|
utility_functions.sort_custom<StringName::AlphCompare>();
|
|
|
for (const StringName &E : utility_functions) {
|
|
|
DocData::MethodDoc md;
|
|
|
md.name = E;
|
|
|
- //return
|
|
|
+ // Utility function's return type.
|
|
|
if (Variant::has_utility_function_return_value(E)) {
|
|
|
PropertyInfo pi;
|
|
|
pi.type = Variant::get_utility_function_return_type(E);
|
|
@@ -865,6 +874,7 @@ void DocTools::generate(bool p_basic_types) {
|
|
|
md.return_type = ad.type;
|
|
|
}
|
|
|
|
|
|
+ // Utility function's arguments.
|
|
|
if (Variant::is_utility_function_vararg(E)) {
|
|
|
md.qualifiers = "vararg";
|
|
|
} else {
|
|
@@ -885,11 +895,10 @@ void DocTools::generate(bool p_basic_types) {
|
|
|
}
|
|
|
}
|
|
|
|
|
|
- // Built-in script reference.
|
|
|
- // We only add a doc entry for languages which actually define any built-in
|
|
|
- // methods or constants.
|
|
|
-
|
|
|
+ // Add scripting language built-ins.
|
|
|
{
|
|
|
+ // We only add a doc entry for languages which actually define any built-in
|
|
|
+ // methods, constants, or annotations.
|
|
|
for (int i = 0; i < ScriptServer::get_language_count(); i++) {
|
|
|
ScriptLanguage *lang = ScriptServer::get_language(i);
|
|
|
String cname = "@" + lang->get_name();
|