diff --git a/doomsday/libdeng2/src/scriptsys/nameexpression.cpp b/doomsday/libdeng2/src/scriptsys/nameexpression.cpp index 8315412e32..3df91c292c 100644 --- a/doomsday/libdeng2/src/scriptsys/nameexpression.cpp +++ b/doomsday/libdeng2/src/scriptsys/nameexpression.cpp @@ -46,7 +46,7 @@ Value *NameExpression::evaluate(Evaluator &evaluator) const { //LOG_AS("NameExpression::evaluate"); //std::cout << "NameExpression::evaluator: " << _flags.to_string() << "\n"; - //LOG_DEBUG("path = %s, scope = %x") << _path << evaluator.names(); + LOGDEV_SCR_XVERBOSE_DEBUGONLY("evaluating name:\"%s\" flags:%x", _identifier << flags()); // Collect the namespaces to search. Evaluator::Namespaces spaces; diff --git a/doomsday/libdeng2/src/scriptsys/parser.cpp b/doomsday/libdeng2/src/scriptsys/parser.cpp index 926fe6358b..2c0ecf3c77 100644 --- a/doomsday/libdeng2/src/scriptsys/parser.cpp +++ b/doomsday/libdeng2/src/scriptsys/parser.cpp @@ -619,7 +619,7 @@ Expression *Parser::parseExpression(TokenRange const &fullRange, Expression::Fla TokenRange range = fullRange; LOG_AS("parseExpression"); - LOGDEV_SCR_XVERBOSE_DEBUGONLY("", range.asText()); + LOGDEV_SCR_XVERBOSE_DEBUGONLY("%s (flags:%x)", range.asText() << flags); if(!range.size()) { @@ -633,6 +633,21 @@ Expression *Parser::parseExpression(TokenRange const &fullRange, Expression::Fla range = range.shrink(1); } + // Do we have a record declaration in the expression? + if(range.firstToken().type() == Token::KEYWORD && + range.firstToken().equals(ScriptLex::RECORD)) + { + LOGDEV_SCR_XVERBOSE_DEBUGONLY("declaration expression: RECORD %s", range.startingFrom(1).asText()); + + if(range.size() == 1) + { + throw MissingTokenError("Parser::parseDeclarationExpression", + "Expected identifier to follow " + range.firstToken().asText()); + } + return parseExpression(range.startingFrom(1), + flags | Expression::LocalOnly | Expression::NewSubrecord); + } + TokenRange leftSide = range.between(0, 0); TokenRange rightSide = leftSide; @@ -673,7 +688,7 @@ ArrayExpression *Parser::parseArrayExpression(TokenRange const &range) "Expected brackets for the array expression beginning at " + range.firstToken().asText()); } - return parseList(range.between(1, range.size() - 1)); + return parseList(range.shrink(1)); } DictionaryExpression *Parser::parseDictionaryExpression(TokenRange const &range) @@ -791,7 +806,16 @@ OperatorExpression *Parser::parseOperatorExpression(Operator op, TokenRange cons Expression::ByReference : Expression::ByValue); Expression::Flags rightOpFlags = rightFlags; - if(op != MEMBER) rightOpFlags &= ~Expression::ByReference; + if(op == MEMBER) + { + // Don't create new variables for the left side of the member. The only place + // where a new variable is created is on the right. + leftOpFlags &= ~Expression::NewVariable; + } + else + { + rightOpFlags &= ~Expression::ByReference; + } // Binary operation. QScopedPointer leftOperand(parseExpression(leftSide, leftOpFlags)); diff --git a/doomsday/tests/test_script/kitchen_sink.de b/doomsday/tests/test_script/kitchen_sink.de index 7d94ce9665..ae37579d1b 100644 --- a/doomsday/tests/test_script/kitchen_sink.de +++ b/doomsday/tests/test_script/kitchen_sink.de @@ -449,7 +449,7 @@ end # --------------------------------------------------------------------------- sections.begin('RECORDS') -sections.subsection('Creating a record.') +sections.subsection('Creating a record with a statement.') record myrec print len(myrec) print "Alternative way using Record()." @@ -457,6 +457,13 @@ del myrec myrec = Record() print len(myrec) +sections.subsection('Creating a record using an expression.') +del myrec +(record myrec).expressionCreated = True +myrec.(record subexp).alsoExpCreated = True +print myrec +del myrec.subexp + sections.subsection('Creating variables into a record.') myrec.newMember = 100 print len(myrec)