diff options
author | Bojidar Marinov <bojidar.marinov.bg@gmail.com> | 2016-08-26 14:15:45 +0300 |
---|---|---|
committer | Bojidar Marinov <bojidar.marinov.bg@gmail.com> | 2016-08-27 15:27:02 +0300 |
commit | 4ee82a2c38c57fb980df1ed4727d47959ba9e983 (patch) | |
tree | ef393dfafdeb9dbd34ea6299f9d19139bbef0c08 /modules | |
parent | 41a58f7935ecd0c91ae55a5e5b84425aadc51840 (diff) |
Adds enums to GDScript
Fixes #2966
Diffstat (limited to 'modules')
-rw-r--r-- | modules/gdscript/gd_parser.cpp | 88 | ||||
-rw-r--r-- | modules/gdscript/gd_tokenizer.cpp | 2 | ||||
-rw-r--r-- | modules/gdscript/gd_tokenizer.h | 1 |
3 files changed, 91 insertions, 0 deletions
diff --git a/modules/gdscript/gd_parser.cpp b/modules/gdscript/gd_parser.cpp index e5a8dc0152..ed3bfd7ce2 100644 --- a/modules/gdscript/gd_parser.cpp +++ b/modules/gdscript/gd_parser.cpp @@ -3157,6 +3157,94 @@ void GDParser::_parse_class(ClassNode *p_class) { } } break; + case GDTokenizer::TK_PR_ENUM: { + //mutiple constant declarations.. + + int last_assign = -1; // Incremented by 1 right before the assingment. + + tokenizer->advance(); + if (tokenizer->get_token()!=GDTokenizer::TK_CURLY_BRACKET_OPEN) { + _set_error("Expected '{' in enum declaration"); + return; + } + tokenizer->advance(); + + while(true) { + if(tokenizer->get_token()==GDTokenizer::TK_NEWLINE) { + + tokenizer->advance(); // Ignore newlines + } else if (tokenizer->get_token()==GDTokenizer::TK_CURLY_BRACKET_CLOSE) { + + tokenizer->advance(); + break; // End of enum + } else if (tokenizer->get_token()!=GDTokenizer::TK_IDENTIFIER) { + + if(tokenizer->get_token()==GDTokenizer::TK_EOF) { + _set_error("Unexpected end of file."); + } else { + _set_error(String("Unexpected ") + GDTokenizer::get_token_name(tokenizer->get_token()) + ", expected identifier"); + } + + return; + } else { // tokenizer->get_token()==GDTokenizer::TK_IDENTIFIER + ClassNode::Constant constant; + + constant.identifier=tokenizer->get_token_identifier(); + + tokenizer->advance(); + + if (tokenizer->get_token()==GDTokenizer::TK_OP_ASSIGN) { + tokenizer->advance(); + + Node *subexpr=NULL; + + subexpr = _parse_and_reduce_expression(p_class,true,true); + if (!subexpr) { + if (_recover_from_completion()) { + break; + } + return; + } + + if (subexpr->type!=Node::TYPE_CONSTANT) { + _set_error("Expected constant expression"); + } + + const ConstantNode *subexpr_const = static_cast<const ConstantNode*>(subexpr); + + if(subexpr_const->value.get_type() != Variant::INT) { + _set_error("Expected an int value for enum"); + } + + last_assign = subexpr_const->value; + + constant.expression=subexpr; + + } else { + last_assign = last_assign + 1; + ConstantNode *cn = alloc_node<ConstantNode>(); + cn->value = last_assign; + constant.expression = cn; + } + + if(tokenizer->get_token()==GDTokenizer::TK_COMMA) { + tokenizer->advance(); + } + + p_class->constant_expressions.push_back(constant); + } + + } + + if (!_end_statement()) { + _set_error("Expected end of statement (enum)"); + return; + } + + + + + } break; default: { diff --git a/modules/gdscript/gd_tokenizer.cpp b/modules/gdscript/gd_tokenizer.cpp index 47e740b227..072a7e26a0 100644 --- a/modules/gdscript/gd_tokenizer.cpp +++ b/modules/gdscript/gd_tokenizer.cpp @@ -95,6 +95,7 @@ const char* GDTokenizer::token_names[TK_MAX]={ "setget", "const", "var", +"enum", "preload", "assert", "yield", @@ -874,6 +875,7 @@ void GDTokenizerText::_advance() { {TK_PR_SLAVE,"slave"}, {TK_PR_SYNC,"sync"}, {TK_PR_CONST,"const"}, + {TK_PR_ENUM,"enum"}, //controlflow {TK_CF_IF,"if"}, {TK_CF_ELIF,"elif"}, diff --git a/modules/gdscript/gd_tokenizer.h b/modules/gdscript/gd_tokenizer.h index 1815f82894..b91229ab1e 100644 --- a/modules/gdscript/gd_tokenizer.h +++ b/modules/gdscript/gd_tokenizer.h @@ -102,6 +102,7 @@ public: TK_PR_SETGET, TK_PR_CONST, TK_PR_VAR, + TK_PR_ENUM, TK_PR_PRELOAD, TK_PR_ASSERT, TK_PR_YIELD, |