Fix multiline array/dictionary match statements
Currently array and dictionary expressions cannot be spread over multiple lines in match statements. Adding mutliline push/pop while parsing the pattern for bracket and brace enables the ability for these to be multiline. This enables more complex patterns to be matched without exceeding line limits. Fixes #90372
This commit is contained in:
parent
b2f425fe68
commit
74177d79c9
5 changed files with 82 additions and 15 deletions
|
@ -2270,11 +2270,13 @@ GDScriptParser::PatternNode *GDScriptParser::parse_match_pattern(PatternNode *p_
|
||||||
break;
|
break;
|
||||||
case GDScriptTokenizer::Token::BRACKET_OPEN: {
|
case GDScriptTokenizer::Token::BRACKET_OPEN: {
|
||||||
// Array.
|
// Array.
|
||||||
|
push_multiline(true);
|
||||||
advance();
|
advance();
|
||||||
pattern->pattern_type = PatternNode::PT_ARRAY;
|
pattern->pattern_type = PatternNode::PT_ARRAY;
|
||||||
|
|
||||||
if (!check(GDScriptTokenizer::Token::BRACKET_CLOSE)) {
|
|
||||||
do {
|
do {
|
||||||
|
if (is_at_end() || check(GDScriptTokenizer::Token::BRACKET_CLOSE)) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
PatternNode *sub_pattern = parse_match_pattern(p_root_pattern != nullptr ? p_root_pattern : pattern);
|
PatternNode *sub_pattern = parse_match_pattern(p_root_pattern != nullptr ? p_root_pattern : pattern);
|
||||||
if (sub_pattern == nullptr) {
|
if (sub_pattern == nullptr) {
|
||||||
continue;
|
continue;
|
||||||
|
@ -2286,12 +2288,13 @@ GDScriptParser::PatternNode *GDScriptParser::parse_match_pattern(PatternNode *p_
|
||||||
}
|
}
|
||||||
pattern->array.push_back(sub_pattern);
|
pattern->array.push_back(sub_pattern);
|
||||||
} while (match(GDScriptTokenizer::Token::COMMA));
|
} while (match(GDScriptTokenizer::Token::COMMA));
|
||||||
}
|
|
||||||
consume(GDScriptTokenizer::Token::BRACKET_CLOSE, R"(Expected "]" to close the array pattern.)");
|
consume(GDScriptTokenizer::Token::BRACKET_CLOSE, R"(Expected "]" to close the array pattern.)");
|
||||||
|
pop_multiline();
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case GDScriptTokenizer::Token::BRACE_OPEN: {
|
case GDScriptTokenizer::Token::BRACE_OPEN: {
|
||||||
// Dictionary.
|
// Dictionary.
|
||||||
|
push_multiline(true);
|
||||||
advance();
|
advance();
|
||||||
pattern->pattern_type = PatternNode::PT_DICTIONARY;
|
pattern->pattern_type = PatternNode::PT_DICTIONARY;
|
||||||
do {
|
do {
|
||||||
|
@ -2334,6 +2337,7 @@ GDScriptParser::PatternNode *GDScriptParser::parse_match_pattern(PatternNode *p_
|
||||||
}
|
}
|
||||||
} while (match(GDScriptTokenizer::Token::COMMA));
|
} while (match(GDScriptTokenizer::Token::COMMA));
|
||||||
consume(GDScriptTokenizer::Token::BRACE_CLOSE, R"(Expected "}" to close the dictionary pattern.)");
|
consume(GDScriptTokenizer::Token::BRACE_CLOSE, R"(Expected "}" to close the dictionary pattern.)");
|
||||||
|
pop_multiline();
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
default: {
|
default: {
|
||||||
|
|
|
@ -0,0 +1,33 @@
|
||||||
|
func foo(x):
|
||||||
|
match x:
|
||||||
|
["value1"]:
|
||||||
|
print('["value1"]')
|
||||||
|
["value1", "value2"]:
|
||||||
|
print('["value1", "value2"]')
|
||||||
|
|
||||||
|
func bar(x):
|
||||||
|
match x:
|
||||||
|
[
|
||||||
|
"value1"
|
||||||
|
]:
|
||||||
|
print('multiline ["value1"]')
|
||||||
|
[
|
||||||
|
"value1",
|
||||||
|
"value2",
|
||||||
|
]:
|
||||||
|
print('multiline ["value1", "value2",]')
|
||||||
|
[
|
||||||
|
"value1",
|
||||||
|
[
|
||||||
|
"value2",
|
||||||
|
..,
|
||||||
|
],
|
||||||
|
]:
|
||||||
|
print('multiline ["value1", ["value2", ..,],]')
|
||||||
|
|
||||||
|
func test():
|
||||||
|
foo(["value1"])
|
||||||
|
foo(["value1", "value2"])
|
||||||
|
bar(["value1"])
|
||||||
|
bar(["value1", "value2"])
|
||||||
|
bar(["value1", ["value2", "value3"]])
|
|
@ -0,0 +1,6 @@
|
||||||
|
GDTEST_OK
|
||||||
|
["value1"]
|
||||||
|
["value1", "value2"]
|
||||||
|
multiline ["value1"]
|
||||||
|
multiline ["value1", "value2",]
|
||||||
|
multiline ["value1", ["value2", ..,],]
|
|
@ -26,6 +26,24 @@ func bar(x):
|
||||||
_:
|
_:
|
||||||
print("wildcard")
|
print("wildcard")
|
||||||
|
|
||||||
|
func baz(x):
|
||||||
|
match x:
|
||||||
|
{
|
||||||
|
"key1": "value1"
|
||||||
|
}:
|
||||||
|
print('multiline {"key1": "value1"}')
|
||||||
|
{
|
||||||
|
"key2": "value2",
|
||||||
|
}:
|
||||||
|
print('multiline {"key2": "value2",}')
|
||||||
|
{
|
||||||
|
"key3": {
|
||||||
|
"key1",
|
||||||
|
..,
|
||||||
|
},
|
||||||
|
}:
|
||||||
|
print('multiline {"key3": {"key1", ..,},}')
|
||||||
|
|
||||||
func test():
|
func test():
|
||||||
foo({"key1": "value1", "key2": "value2"})
|
foo({"key1": "value1", "key2": "value2"})
|
||||||
foo({"key1": "value1", "key2": ""})
|
foo({"key1": "value1", "key2": ""})
|
||||||
|
@ -41,3 +59,6 @@ func test():
|
||||||
bar({1: "1"})
|
bar({1: "1"})
|
||||||
bar({2: "2"})
|
bar({2: "2"})
|
||||||
bar({3: "3"})
|
bar({3: "3"})
|
||||||
|
baz({"key1": "value1"})
|
||||||
|
baz({"key2": "value2"})
|
||||||
|
baz({"key3": {"key1": "value1", "key2": "value2"}})
|
||||||
|
|
|
@ -13,3 +13,6 @@ wildcard
|
||||||
1
|
1
|
||||||
2
|
2
|
||||||
wildcard
|
wildcard
|
||||||
|
multiline {"key1": "value1"}
|
||||||
|
multiline {"key2": "value2",}
|
||||||
|
multiline {"key3": {"key1", ..,},}
|
||||||
|
|
Loading…
Reference in a new issue