diff options
author | George Marques <george@gmarqu.es> | 2021-05-26 09:23:17 -0300 |
---|---|---|
committer | George Marques <george@gmarqu.es> | 2021-08-18 18:56:21 -0300 |
commit | 2ba4ee91980511126f5c294a3423121a6ed7a7db (patch) | |
tree | 772a3b0cede9d8318ebf6775bf96ce5b20758f91 /modules/gdscript/gdscript_analyzer.cpp | |
parent | 31dfdcb69eb4d98a399243f5fc93b8e14b2e808a (diff) | |
download | redot-engine-2ba4ee91980511126f5c294a3423121a6ed7a7db.tar.gz |
GDScript: Fix inner classes and preloaded scripts as types
Diffstat (limited to 'modules/gdscript/gdscript_analyzer.cpp')
-rw-r--r-- | modules/gdscript/gdscript_analyzer.cpp | 29 |
1 files changed, 29 insertions, 0 deletions
diff --git a/modules/gdscript/gdscript_analyzer.cpp b/modules/gdscript/gdscript_analyzer.cpp index e925350ba3..d6a2c35ae8 100644 --- a/modules/gdscript/gdscript_analyzer.cpp +++ b/modules/gdscript/gdscript_analyzer.cpp @@ -432,8 +432,28 @@ GDScriptParser::DataType GDScriptAnalyzer::resolve_datatype(GDScriptParser::Type case GDScriptParser::ClassNode::Member::CONSTANT: if (member.constant->get_datatype().is_meta_type) { result = member.constant->get_datatype(); + result.is_meta_type = false; found = true; break; + } else if (Ref<Script>(member.constant->initializer->reduced_value).is_valid()) { + Ref<GDScript> gdscript = member.constant->initializer->reduced_value; + if (gdscript.is_valid()) { + Ref<GDScriptParserRef> ref = get_parser_for(gdscript->get_path()); + if (ref->raise_status(GDScriptParserRef::INTERFACE_SOLVED) != OK) { + push_error(vformat(R"(Could not parse script from "%s".)", gdscript->get_path()), p_type); + return GDScriptParser::DataType(); + } + result = ref->get_parser()->head->get_datatype(); + result.is_meta_type = false; + } else { + Ref<GDScript> script = member.constant->initializer->reduced_value; + result.kind = GDScriptParser::DataType::SCRIPT; + result.builtin_type = Variant::OBJECT; + result.script_type = script; + result.script_path = script->get_path(); + result.native_type = script->get_instance_base_type(); + } + break; } [[fallthrough]]; default: @@ -2129,6 +2149,9 @@ void GDScriptAnalyzer::reduce_call(GDScriptParser::CallNode *p_call, bool is_awa if (is_self && parser->current_function != nullptr && parser->current_function->is_static && !is_static) { push_error(vformat(R"*(Cannot call non-static function "%s()" from static function "%s()".)*", p_call->function_name, parser->current_function->identifier->name), p_call->callee); + } else if (!is_self && base_type.is_meta_type && !is_static) { + base_type.is_meta_type = false; // For `to_string()`. + push_error(vformat(R"*(Cannot call non-static function "%s()" on the class "%s" directly. Make an instance instead.)*", p_call->function_name, base_type.to_string()), p_call->callee); } else if (is_self && !is_static && !lambda_stack.is_empty()) { push_error(vformat(R"*(Cannot call non-static function "%s()" from a lambda function.)*", p_call->function_name), p_call->callee); } @@ -2392,6 +2415,11 @@ void GDScriptAnalyzer::reduce_identifier_from_base(GDScriptParser::IdentifierNod resolve_function_signature(member.function); p_identifier->set_datatype(make_callable_type(member.function->info)); break; + case GDScriptParser::ClassNode::Member::CLASS: + // For out-of-order resolution: + resolve_class_interface(member.m_class); + p_identifier->set_datatype(member.m_class->get_datatype()); + break; default: break; // Type already set. } @@ -3257,6 +3285,7 @@ bool GDScriptAnalyzer::get_function_signature(GDScriptParser::Node *p_source, GD } } r_return_type = found_function->get_datatype(); + r_return_type.is_meta_type = false; r_return_type.is_coroutine = found_function->is_coroutine; return true; |