From a84d8c44e4053aa4210bb18e7235199a3d91e45d Mon Sep 17 00:00:00 2001 From: Eugene Sandulenko Date: Wed, 13 Jul 2016 07:42:44 +0200 Subject: DIRECTOR: Lingo: Initial code for splitting factory and method input --- engines/director/lingo/lingo.cpp | 39 ++++++++++++++++++++++++++++++++++++--- engines/director/lingo/lingo.h | 5 +++++ 2 files changed, 41 insertions(+), 3 deletions(-) diff --git a/engines/director/lingo/lingo.cpp b/engines/director/lingo/lingo.cpp index ccbb66898d..837dfa0b67 100644 --- a/engines/director/lingo/lingo.cpp +++ b/engines/director/lingo/lingo.cpp @@ -94,6 +94,8 @@ Lingo::Lingo(DirectorEngine *vm) : _vm(vm) { _hadError = false; + _inFactory = false; + _floatPrecision = 4; _floatPrecisionFormat = "%.4f"; @@ -103,6 +105,28 @@ Lingo::Lingo(DirectorEngine *vm) : _vm(vm) { Lingo::~Lingo() { } +const char *Lingo::findNextDefinition(const char *s) { + const char *res; + + if ((res = strstr(s, "\nmacro "))) { + return res; + } else if ((res = strstr(s, "\nfactory "))) { + return res; + } else if (_inFactory && (res = strstr(s, "method "))) { + if (s == res) + return res; + + // Check that this is the first token on the line + const char *tres = res; + while (tres > s && (*tres == ' ' || *tres == '\t') && *tres != '\n') + tres--; + if (*tres == '\n') + return res; + } + + return nullptr; +} + void Lingo::addCode(const char *code, ScriptType type, uint16 id) { debug(2, "Add code \"%s\" for type %d with id %d", code, type, id); @@ -119,19 +143,26 @@ void Lingo::addCode(const char *code, ScriptType type, uint16 id) { const char *begin, *end; - // macros have conflicting grammar. Thus we ease life for the parser. - if ((begin = strstr(code, "\nmacro "))) { + // macros and factories have conflicting grammar. Thus we ease life for the parser. + if ((begin = findNextDefinition(code))) { bool first = true; begin += 1; - while ((end = strstr(begin, "\nmacro "))) { + while ((end = findNextDefinition(begin))) { if (first) { begin = code; first = false; } Common::String chunk(begin, end + 1); + if (chunk.hasPrefix("factory") || chunk.hasPrefix("method")) + _inFactory = true; + else if (chunk.hasPrefix("macro")) + _inFactory = false; + else + _inFactory = false; + debug(2, "Code chunk\n#####\n%s#####", chunk.c_str()); parse(chunk.c_str()); @@ -149,6 +180,8 @@ void Lingo::addCode(const char *code, ScriptType type, uint16 id) { code1(STOP); } + _inFactory = false; + if (_currentScript->size() && !_hadError) Common::hexdump((byte *)&_currentScript->front(), _currentScript->size() * sizeof(inst)); } diff --git a/engines/director/lingo/lingo.h b/engines/director/lingo/lingo.h index 254cf76ce7..462b14d6b6 100644 --- a/engines/director/lingo/lingo.h +++ b/engines/director/lingo/lingo.h @@ -150,6 +150,9 @@ public: void runTests(); +private: + const char *findNextDefinition(const char *s); + public: void execute(int pc); void pushContext(); @@ -284,6 +287,8 @@ public: bool _hadError; + bool _inFactory; + private: int parse(const char *code); void push(Datum d); -- cgit v1.2.3