From f321e549a4bb4af4bae0bf6a37e4b5a558156681 Mon Sep 17 00:00:00 2001 From: Marc Zinnschlag Date: Mon, 4 Apr 2011 15:10:37 +0200 Subject: [PATCH 1/5] added instruction GetPCCell --- apps/openmw/mwscript/cellextensions.cpp | 34 +++++++++++++++++++++++++ apps/openmw/mwscript/docs/vmformat.txt | 3 ++- 2 files changed, 36 insertions(+), 1 deletion(-) diff --git a/apps/openmw/mwscript/cellextensions.cpp b/apps/openmw/mwscript/cellextensions.cpp index 9c756e11f..bb5263203 100644 --- a/apps/openmw/mwscript/cellextensions.cpp +++ b/apps/openmw/mwscript/cellextensions.cpp @@ -102,10 +102,42 @@ namespace MWScript } }; + class OpGetPCCell : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + InterpreterContext& context + = static_cast (runtime.getContext()); + + std::string name = runtime.getStringLiteral (runtime[0].mInteger); + runtime.pop(); + + const ESM::Cell *cell = context.getWorld().getPlayer().getPlayer().getCell()->cell; + + std::string current = cell->name; + + if (!(cell->data.flags & ESM::Cell::Interior) && current.empty()) + { + const ESM::Region *region = + context.getWorld().getStore().regions.find (cell->region); + + current = region->name; + } + + bool match = current.length()>=name.length() && + current.substr (0, name.length())==name; + + runtime.push (match ? 1 : 0); + } + }; + const int opcodeCellChanged = 0x2000000; const int opcodeCOC = 0x2000026; const int opcodeCOE = 0x200008e; const int opcodeGetInterior = 0x2000131; + const int opcodeGetPCCell = 0x2000136; void registerExtensions (Compiler::Extensions& extensions) { @@ -115,6 +147,7 @@ namespace MWScript extensions.registerInstruction ("coe", "ll", opcodeCOE); extensions.registerInstruction ("centeronexterior", "ll", opcodeCOE); extensions.registerFunction ("getinterior", 'l', "", opcodeGetInterior); + extensions.registerFunction ("getpccell", 'l', "c", opcodeGetPCCell); } void installOpcodes (Interpreter::Interpreter& interpreter) @@ -123,6 +156,7 @@ namespace MWScript interpreter.installSegment5 (opcodeCOC, new OpCOC); interpreter.installSegment5 (opcodeCOE, new OpCOE); interpreter.installSegment5 (opcodeGetInterior, new OpGetInterior); + interpreter.installSegment5 (opcodeGetPCCell, new OpGetPCCell); } } } diff --git a/apps/openmw/mwscript/docs/vmformat.txt b/apps/openmw/mwscript/docs/vmformat.txt index 90962f56b..fcebaae2b 100644 --- a/apps/openmw/mwscript/docs/vmformat.txt +++ b/apps/openmw/mwscript/docs/vmformat.txt @@ -107,4 +107,5 @@ op 0x2000132: ToggleCollsionDebug op 0x2000133: Journal op 0x2000134: SetJournalIndex op 0x2000135: GetJournalIndex -opcodes 0x2000136-0x3ffffff unused +op 0x2000136: GetPCCell +opcodes 0x2000137-0x3ffffff unused From 53e0e3886242511804dbf1454892b139342beee5 Mon Sep 17 00:00:00 2001 From: Marc Zinnschlag Date: Wed, 6 Apr 2011 09:49:00 +0200 Subject: [PATCH 2/5] added missing TCL instruction --- apps/openmw/mwscript/controlextensions.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/apps/openmw/mwscript/controlextensions.cpp b/apps/openmw/mwscript/controlextensions.cpp index f5a5c08a4..e687b1352 100644 --- a/apps/openmw/mwscript/controlextensions.cpp +++ b/apps/openmw/mwscript/controlextensions.cpp @@ -74,6 +74,7 @@ namespace MWScript } extensions.registerInstruction ("togglecollision", "", opcodeToggleCollision); + extensions.registerInstruction ("tcl", "", opcodeToggleCollision); } void installOpcodes (Interpreter::Interpreter& interpreter) From f52e6bd5ef9dad530134a39ba1446b64caab6755 Mon Sep 17 00:00:00 2001 From: Marc Zinnschlag Date: Tue, 26 Apr 2011 21:38:21 +0200 Subject: [PATCH 3/5] made toggle-type script instructions more verbose --- apps/openmw/mwrender/mwscene.cpp | 13 +++-- apps/openmw/mwrender/mwscene.hpp | 6 ++- apps/openmw/mwscript/controlextensions.cpp | 4 +- apps/openmw/mwscript/miscextensions.cpp | 6 ++- apps/openmw/mwscript/skyextensions.cpp | 55 +++++++++++----------- apps/openmw/mwworld/world.cpp | 12 +++-- apps/openmw/mwworld/world.hpp | 9 ++-- 7 files changed, 63 insertions(+), 42 deletions(-) diff --git a/apps/openmw/mwrender/mwscene.cpp b/apps/openmw/mwrender/mwscene.cpp index 890bf2cd6..e4d449bf2 100644 --- a/apps/openmw/mwrender/mwscene.cpp +++ b/apps/openmw/mwrender/mwscene.cpp @@ -191,7 +191,7 @@ void MWScene::scaleObject (const std::string& handle, float scale) } -void MWScene::toggleCollisionMode() +bool MWScene::toggleCollisionMode() { for(std::map::iterator it = eng->PhysicActorMap.begin(); it != eng->PhysicActorMap.end();it++) { @@ -203,6 +203,7 @@ void MWScene::toggleCollisionMode() act->setGravity(0.); act->setVerticalVelocity(0); mFreeFly = true; + return false; } else { @@ -210,11 +211,15 @@ void MWScene::toggleCollisionMode() act->enableCollisions(true); act->setGravity(4.); act->setVerticalVelocity(0); + return true; } } + + return false; // This should never happen, but it shall not bother us now, since + // this part of the code needs a rewrite anyway. } -void MWScene::toggleRenderMode (int mode) +bool MWScene::toggleRenderMode (int mode) { switch (mode) { @@ -223,6 +228,8 @@ void MWScene::toggleRenderMode (int mode) // TODO use a proper function instead of accessing the member variable // directly. eng->setDebugRenderingMode (!eng->isDebugCreated); - break; + return eng->isDebugCreated; } + + return false; } diff --git a/apps/openmw/mwrender/mwscene.hpp b/apps/openmw/mwrender/mwscene.hpp index fd14fcce0..7429ff21e 100644 --- a/apps/openmw/mwrender/mwscene.hpp +++ b/apps/openmw/mwrender/mwscene.hpp @@ -91,12 +91,14 @@ namespace MWRender /// Toggle collision mode for player. If disabled player object should ignore /// collisions and gravity. - void toggleCollisionMode(); + /// \return Resulting mode + bool toggleCollisionMode(); /// Toggle render mode /// \todo Using an int instead of a enum here to avoid cyclic includes. Will be fixed /// when the mw*-refactoring is done. - void toggleRenderMode (int mode); + /// \return Resulting mode + bool toggleRenderMode (int mode); }; } diff --git a/apps/openmw/mwscript/controlextensions.cpp b/apps/openmw/mwscript/controlextensions.cpp index e687b1352..3d65c5705 100644 --- a/apps/openmw/mwscript/controlextensions.cpp +++ b/apps/openmw/mwscript/controlextensions.cpp @@ -46,7 +46,9 @@ namespace MWScript InterpreterContext& context = static_cast (runtime.getContext()); - context.getWorld().toggleCollisionMode(); + bool enabled = context.getWorld().toggleCollisionMode(); + + context.messageBox (enabled ? "Collsion -> On" : "Collision -> Off"); } }; diff --git a/apps/openmw/mwscript/miscextensions.cpp b/apps/openmw/mwscript/miscextensions.cpp index 9bfb8774d..e1c9eae3b 100644 --- a/apps/openmw/mwscript/miscextensions.cpp +++ b/apps/openmw/mwscript/miscextensions.cpp @@ -99,7 +99,11 @@ namespace MWScript InterpreterContext& context = static_cast (runtime.getContext()); - context.getWorld().toggleRenderMode (MWWorld::World::Render_CollisionDebug); + bool enabled = + context.getWorld().toggleRenderMode (MWWorld::World::Render_CollisionDebug); + + context.messageBox (enabled ? + "Collsion Mesh Rendering -> On" : "Collision Mesh Rendering -> Off"); } }; diff --git a/apps/openmw/mwscript/skyextensions.cpp b/apps/openmw/mwscript/skyextensions.cpp index f53168240..1a761e3bb 100644 --- a/apps/openmw/mwscript/skyextensions.cpp +++ b/apps/openmw/mwscript/skyextensions.cpp @@ -16,68 +16,70 @@ namespace MWScript class OpToggleSky : public Interpreter::Opcode0 { public: - + virtual void execute (Interpreter::Runtime& runtime) { InterpreterContext& context = static_cast (runtime.getContext()); - - context.getWorld().toggleSky(); - } - }; - + + bool enabled = context.getWorld().toggleSky(); + + context.messageBox (enabled ? "Sky -> On" : "Sky -> Off"); + } + }; + class OpTurnMoonWhite : public Interpreter::Opcode0 { public: - + virtual void execute (Interpreter::Runtime& runtime) { InterpreterContext& context = static_cast (runtime.getContext()); - + context.getWorld().setMoonColour (false); - } - }; + } + }; class OpTurnMoonRed : public Interpreter::Opcode0 { public: - + virtual void execute (Interpreter::Runtime& runtime) { InterpreterContext& context = static_cast (runtime.getContext()); - + context.getWorld().setMoonColour (true); - } - }; - + } + }; + class OpGetMasserPhase : public Interpreter::Opcode0 { public: - + virtual void execute (Interpreter::Runtime& runtime) { InterpreterContext& context = static_cast (runtime.getContext()); - + runtime.push (context.getWorld().getMasserPhase()); - } - }; + } + }; class OpGetSecundaPhase : public Interpreter::Opcode0 { public: - + virtual void execute (Interpreter::Runtime& runtime) { InterpreterContext& context = static_cast (runtime.getContext()); - + runtime.push (context.getWorld().getSecundaPhase()); - } - }; - + } + }; + const int opcodeToggleSky = 0x2000021; const int opcodeTurnMoonWhite = 0x2000022; const int opcodeTurnMoonRed = 0x2000023; @@ -93,7 +95,7 @@ namespace MWScript extensions.registerFunction ("getmasserphase", 'l', "", opcodeGetMasserPhase); extensions.registerFunction ("getsecundaphase", 'l', "", opcodeGetSecundaPhase); } - + void installOpcodes (Interpreter::Interpreter& interpreter) { interpreter.installSegment5 (opcodeToggleSky, new OpToggleSky); @@ -101,7 +103,6 @@ namespace MWScript interpreter.installSegment5 (opcodeTurnMoonRed, new OpTurnMoonRed); interpreter.installSegment5 (opcodeGetMasserPhase, new OpGetMasserPhase); interpreter.installSegment5 (opcodeGetSecundaPhase, new OpGetSecundaPhase); - } + } } } - diff --git a/apps/openmw/mwworld/world.cpp b/apps/openmw/mwworld/world.cpp index 63019349c..a4001169d 100644 --- a/apps/openmw/mwworld/world.cpp +++ b/apps/openmw/mwworld/world.cpp @@ -645,12 +645,13 @@ namespace MWWorld mSkyManager->setDate (mGlobalVariables->getInt ("day"), month); } - void World::toggleSky() + bool World::toggleSky() { if (mSky) { mSky = false; mSkyManager->disable(); + return false; } else { @@ -660,6 +661,7 @@ namespace MWWorld mSkyManager->setDate (mGlobalVariables->getInt ("day"), mGlobalVariables->getInt ("month")); mSkyManager->enable(); + return true; } } @@ -853,13 +855,13 @@ namespace MWWorld mScene.doPhysics (duration, *this, actors); } - void World::toggleCollisionMode() + bool World::toggleCollisionMode() { - mScene.toggleCollisionMode(); + return mScene.toggleCollisionMode(); } - void World::toggleRenderMode (RenderMode mode) + bool World::toggleRenderMode (RenderMode mode) { - mScene.toggleRenderMode (mode); + return mScene.toggleRenderMode (mode); } } diff --git a/apps/openmw/mwworld/world.hpp b/apps/openmw/mwworld/world.hpp index 6965aebc6..739353394 100644 --- a/apps/openmw/mwworld/world.hpp +++ b/apps/openmw/mwworld/world.hpp @@ -147,7 +147,8 @@ namespace MWWorld void setDay (int day); - void toggleSky(); + bool toggleSky(); + ///< \return Resulting mode int getMasserPhase() const; @@ -185,12 +186,14 @@ namespace MWWorld float duration); ///< Run physics simulation and modify \a world accordingly. - void toggleCollisionMode(); + bool toggleCollisionMode(); ///< Toggle collision mode for player. If disabled player object should ignore /// collisions and gravity. + ///< \return Resulting mode - void toggleRenderMode (RenderMode mode); + bool toggleRenderMode (RenderMode mode); ///< Toggle a render mode. + ///< \return Resulting mode }; } From 125319c441559378993437059756236c78236a8a Mon Sep 17 00:00:00 2001 From: Marc Zinnschlag Date: Tue, 26 Apr 2011 21:48:13 +0200 Subject: [PATCH 4/5] splitting off console output from messageBox channel --- apps/openmw/mwgui/console.cpp | 7 ++++ apps/openmw/mwscript/controlextensions.cpp | 2 +- apps/openmw/mwscript/interpretercontext.cpp | 5 +++ apps/openmw/mwscript/interpretercontext.hpp | 4 ++ apps/openmw/mwscript/miscextensions.cpp | 2 +- apps/openmw/mwscript/skyextensions.cpp | 2 +- components/interpreter/context.hpp | 42 ++++++++++----------- 7 files changed, 40 insertions(+), 24 deletions(-) diff --git a/apps/openmw/mwgui/console.cpp b/apps/openmw/mwgui/console.cpp index 836a0f0db..0421dc370 100644 --- a/apps/openmw/mwgui/console.cpp +++ b/apps/openmw/mwgui/console.cpp @@ -17,6 +17,8 @@ namespace MWGui ConsoleInterpreterContext (Console& console, MWWorld::Environment& environment, MWWorld::Ptr reference); + + virtual void report (const std::string& message); }; ConsoleInterpreterContext::ConsoleInterpreterContext (Console& console, @@ -26,6 +28,11 @@ namespace MWGui mConsole (console) {} + void ConsoleInterpreterContext::report (const std::string& message) + { + mConsole.printOK (message); + } + bool Console::compile (const std::string& cmd, Compiler::Output& output) { try diff --git a/apps/openmw/mwscript/controlextensions.cpp b/apps/openmw/mwscript/controlextensions.cpp index 3d65c5705..893af259f 100644 --- a/apps/openmw/mwscript/controlextensions.cpp +++ b/apps/openmw/mwscript/controlextensions.cpp @@ -48,7 +48,7 @@ namespace MWScript bool enabled = context.getWorld().toggleCollisionMode(); - context.messageBox (enabled ? "Collsion -> On" : "Collision -> Off"); + context.report (enabled ? "Collsion -> On" : "Collision -> Off"); } }; diff --git a/apps/openmw/mwscript/interpretercontext.cpp b/apps/openmw/mwscript/interpretercontext.cpp index cb6ecb218..77a71a1d4 100644 --- a/apps/openmw/mwscript/interpretercontext.cpp +++ b/apps/openmw/mwscript/interpretercontext.cpp @@ -110,6 +110,11 @@ namespace MWScript mEnvironment.mWindowManager->messageBox (message, buttons); } + void InterpreterContext::report (const std::string& message) + { + messageBox (message); + } + bool InterpreterContext::menuMode() { return mEnvironment.mWindowManager->isGuiMode(); diff --git a/apps/openmw/mwscript/interpretercontext.hpp b/apps/openmw/mwscript/interpretercontext.hpp index aebfc620e..35b4a169d 100644 --- a/apps/openmw/mwscript/interpretercontext.hpp +++ b/apps/openmw/mwscript/interpretercontext.hpp @@ -57,9 +57,13 @@ namespace MWScript virtual void setLocalFloat (int index, float value); using Interpreter::Context::messageBox; + virtual void messageBox (const std::string& message, const std::vector& buttons); + virtual void report (const std::string& message); + ///< By default echo via messageBox. + virtual bool menuMode(); virtual int getGlobalShort (const std::string& name) const; diff --git a/apps/openmw/mwscript/miscextensions.cpp b/apps/openmw/mwscript/miscextensions.cpp index e1c9eae3b..d8dfbdde4 100644 --- a/apps/openmw/mwscript/miscextensions.cpp +++ b/apps/openmw/mwscript/miscextensions.cpp @@ -102,7 +102,7 @@ namespace MWScript bool enabled = context.getWorld().toggleRenderMode (MWWorld::World::Render_CollisionDebug); - context.messageBox (enabled ? + context.report (enabled ? "Collsion Mesh Rendering -> On" : "Collision Mesh Rendering -> Off"); } }; diff --git a/apps/openmw/mwscript/skyextensions.cpp b/apps/openmw/mwscript/skyextensions.cpp index 1a761e3bb..caa07c095 100644 --- a/apps/openmw/mwscript/skyextensions.cpp +++ b/apps/openmw/mwscript/skyextensions.cpp @@ -24,7 +24,7 @@ namespace MWScript bool enabled = context.getWorld().toggleSky(); - context.messageBox (enabled ? "Sky -> On" : "Sky -> Off"); + context.report (enabled ? "Sky -> On" : "Sky -> Off"); } }; diff --git a/components/interpreter/context.hpp b/components/interpreter/context.hpp index 0d77903f4..973b22d35 100644 --- a/components/interpreter/context.hpp +++ b/components/interpreter/context.hpp @@ -18,21 +18,23 @@ namespace Interpreter virtual float getLocalFloat (int index) const = 0; - virtual void setLocalShort (int index, int value) = 0; + virtual void setLocalShort (int index, int value) = 0; - virtual void setLocalLong (int index, int value) = 0; + virtual void setLocalLong (int index, int value) = 0; virtual void setLocalFloat (int index, float value) = 0; - + virtual void messageBox (const std::string& message, - const std::vector& buttons) = 0; - + const std::vector& buttons) = 0; + void messageBox (const std::string& message) { std::vector empty; messageBox (message, empty); } - + + virtual void report (const std::string& message) = 0; + virtual bool menuMode() = 0; virtual int getGlobalShort (const std::string& name) const = 0; @@ -41,31 +43,29 @@ namespace Interpreter virtual float getGlobalFloat (const std::string& name) const = 0; - virtual void setGlobalShort (const std::string& name, int value) = 0; + virtual void setGlobalShort (const std::string& name, int value) = 0; - virtual void setGlobalLong (const std::string& name, int value) = 0; + virtual void setGlobalLong (const std::string& name, int value) = 0; + + virtual void setGlobalFloat (const std::string& name, float value) = 0; - virtual void setGlobalFloat (const std::string& name, float value) = 0; - virtual bool isScriptRunning (const std::string& name) const = 0; - + virtual void startScript (const std::string& name) = 0; - + virtual void stopScript (const std::string& name) = 0; - + virtual float getDistance (const std::string& name, const std::string& id = "") const - = 0; - + = 0; + virtual float getSecondsPassed() const = 0; - + virtual bool isDisabled (const std::string& id = "") const = 0; - + virtual void enable (const std::string& id = "") = 0; - - virtual void disable (const std::string& id = "") = 0; + + virtual void disable (const std::string& id = "") = 0; }; } #endif - - From 861dc6a16e7f52d44e8877c11f581929b1ad43bb Mon Sep 17 00:00:00 2001 From: Marc Zinnschlag Date: Tue, 26 Apr 2011 22:07:27 +0200 Subject: [PATCH 5/5] redirecting output of expression evalutation to new report channel --- components/compiler/generator.cpp | 13 +++ components/compiler/generator.hpp | 2 + components/compiler/lineparser.cpp | 4 +- components/interpreter/docs/vmformat.txt | 6 +- components/interpreter/installopcodes.cpp | 2 +- components/interpreter/miscopcodes.hpp | 135 +++++++++++++--------- 6 files changed, 103 insertions(+), 59 deletions(-) diff --git a/components/compiler/generator.cpp b/components/compiler/generator.cpp index 3d3b21d65..ee9876a14 100644 --- a/components/compiler/generator.cpp +++ b/components/compiler/generator.cpp @@ -125,6 +125,11 @@ namespace code.push_back (Compiler::Generator::segment3 (0, buttons)); } + void opReport (Compiler::Generator::CodeContainer& code) + { + code.push_back (Compiler::Generator::segment5 (58)); + } + void opFetchLocalShort (Compiler::Generator::CodeContainer& code) { code.push_back (Compiler::Generator::segment5 (21)); @@ -516,6 +521,14 @@ namespace Compiler opMessageBox (code, buttons); } + void report (CodeContainer& code, Literals& literals, const std::string& message) + { + int index = literals.addString (message); + + opPushInt (code, index); + opReport (code); + } + void fetchLocal (CodeContainer& code, char localType, int localIndex) { opPushInt (code, localIndex); diff --git a/components/compiler/generator.hpp b/components/compiler/generator.hpp index 5671949f2..fd1f954ca 100644 --- a/components/compiler/generator.hpp +++ b/components/compiler/generator.hpp @@ -81,6 +81,8 @@ namespace Compiler void message (CodeContainer& code, Literals& literals, const std::string& message, int buttons); + void report (CodeContainer& code, Literals& literals, const std::string& message); + void fetchLocal (CodeContainer& code, char localType, int localIndex); void jump (CodeContainer& code, int offset); diff --git a/components/compiler/lineparser.cpp b/components/compiler/lineparser.cpp index 5462f7788..834cd27b4 100644 --- a/components/compiler/lineparser.cpp +++ b/components/compiler/lineparser.cpp @@ -30,12 +30,12 @@ namespace Compiler { case 'l': - Generator::message (mCode, mLiterals, "%g", 0); + Generator::report (mCode, mLiterals, "%g"); break; case 'f': - Generator::message (mCode, mLiterals, "%f", 0); + Generator::report (mCode, mLiterals, "%f"); break; default: diff --git a/components/interpreter/docs/vmformat.txt b/components/interpreter/docs/vmformat.txt index 6619fc30a..3e513aa44 100644 --- a/components/interpreter/docs/vmformat.txt +++ b/components/interpreter/docs/vmformat.txt @@ -117,5 +117,9 @@ op 55: explicit reference = stack[0]; pop; disable explicit reference op 56: explicit reference = stack[0]; pop; push 1, if explicit reference is disabled, 0 else op 57: explicit reference = stack[0]; pop; replace stack[0] with distance between explicit reference and a reference of ID stack[0] -opcodes 58-33554431 unused +op 58: report string literal index in stack[0]; + additional arguments (if any) in stack[n]..stack[1]; + n is determined according to the message string + all arguments are removed from stack +opcodes 59-33554431 unused opcodes 33554432-67108863 reserved for extensions diff --git a/components/interpreter/installopcodes.cpp b/components/interpreter/installopcodes.cpp index f383ff47c..556477af2 100644 --- a/components/interpreter/installopcodes.cpp +++ b/components/interpreter/installopcodes.cpp @@ -95,6 +95,7 @@ namespace Interpreter interpreter.installSegment5 (54, new OpEnableExplicit); interpreter.installSegment5 (55, new OpDisableExplicit); interpreter.installSegment5 (56, new OpGetDisabledExplicit); + interpreter.installSegment5 (58, new OpReport); // script control interpreter.installSegment5 (46, new OpScriptRunning); @@ -106,4 +107,3 @@ namespace Interpreter interpreter.installSegment5 (57, new OpGetDistanceExplicit); } } - diff --git a/components/interpreter/miscopcodes.hpp b/components/interpreter/miscopcodes.hpp index fbee0aa26..37c38fc30 100644 --- a/components/interpreter/miscopcodes.hpp +++ b/components/interpreter/miscopcodes.hpp @@ -13,6 +13,66 @@ namespace Interpreter { + inline std::string formatMessage (const std::string& message, Runtime& runtime) + { + std::string formattedMessage; + + for (std::size_t i=0; i