From 7375035fef34fee75085dcab850f9467c25fe945 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Mon, 9 Jul 2012 17:54:15 -0400 Subject: [PATCH 01/84] Counter changed back to 10 --- libs/openengine/bullet/pmove.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libs/openengine/bullet/pmove.cpp b/libs/openengine/bullet/pmove.cpp index e13e9e6c07..924812c29f 100644 --- a/libs/openengine/bullet/pmove.cpp +++ b/libs/openengine/bullet/pmove.cpp @@ -527,7 +527,7 @@ int PM_StepSlideMove( bool gravity ) delta = pm->ps.origin.z - start_o.z; if ( delta > 2 ) { - pm->ps.counter = 5; + pm->ps.counter = 10; /* if (gravity) From 7d6ad6ad9477e0644cc7f1e671f08ccfb79d9df1 Mon Sep 17 00:00:00 2001 From: gugus Date: Fri, 3 Aug 2012 18:14:05 +0200 Subject: [PATCH 02/84] setPos and getPos Script instructions. Cell-crossing is not tested yet. --- .../mwscript/transformationextensions.cpp | 71 +++++++++++++++++++ 1 file changed, 71 insertions(+) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 2ea80c0d88..42ef16ed9c 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -108,6 +108,67 @@ namespace MWScript } }; + template + class OpGetPos : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + MWWorld::Ptr ptr = R()(runtime); + + std::string axis = runtime.getStringLiteral (runtime[0].mInteger); + runtime.pop(); + + if(axis == "X") + { + runtime.push(ptr.getRefData().getPosition().pos[0]); + } + if(axis == "Y") + { + runtime.push(ptr.getRefData().getPosition().pos[1]); + } + if(axis == "Z") + { + runtime.push(ptr.getRefData().getPosition().pos[2]); + } + } + }; + + template + class OpSetPos : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + MWWorld::Ptr ptr = R()(runtime); + + std::string axis = runtime.getStringLiteral (runtime[0].mInteger); + runtime.pop(); + Interpreter::Type_Float pos = runtime[0].mFloat; + runtime.pop(); + + float ax = ptr.getRefData().getPosition().pos[0]; + float ay = ptr.getRefData().getPosition().pos[1]; + float az = ptr.getRefData().getPosition().pos[2]; + std::cout << "setPos"; + + if(axis == "X") + { + MWBase::Environment::get().getWorld()->moveObject(ptr,pos,ay,az); + } + if(axis == "Y") + { + MWBase::Environment::get().getWorld()->moveObject(ptr,ax,pos,az); + } + if(axis == "Z") + { + MWBase::Environment::get().getWorld()->moveObject(ptr,ax,ay,pos); + } + } + }; + const int opcodeSetScale = 0x2000164; const int opcodeSetScaleExplicit = 0x2000165; const int opcodeSetAngle = 0x2000166; @@ -116,6 +177,10 @@ namespace MWScript const int opcodeGetScaleExplicit = 0x2000169; const int opcodeGetAngle = 0x200016a; const int opcodeGetAngleExplicit = 0x200016b; + const int opcodeGetPos = 0x200016c; + const int opcodeGetPosExplicit = 0x200016d; + const int opcodeSetPos = 0x200016e; + const int opcodeSetPosExplicit = 0x200016f; void registerExtensions (Compiler::Extensions& extensions) { @@ -123,6 +188,8 @@ namespace MWScript extensions.registerFunction("getscale",'f',"",opcodeGetScale,opcodeGetScaleExplicit); extensions.registerInstruction("setangle","Sf",opcodeSetAngle,opcodeSetAngleExplicit); extensions.registerFunction("getangle",'f',"S",opcodeGetAngle,opcodeGetAngleExplicit); + extensions.registerInstruction("setpos","Sf",opcodeSetPos,opcodeSetPosExplicit); + extensions.registerFunction("getpos",'f',"S",opcodeGetPos,opcodeGetPosExplicit); } void installOpcodes (Interpreter::Interpreter& interpreter) @@ -135,6 +202,10 @@ namespace MWScript interpreter.installSegment5(opcodeGetScaleExplicit,new OpGetScale); interpreter.installSegment5(opcodeGetAngle,new OpGetAngle); interpreter.installSegment5(opcodeGetAngleExplicit,new OpGetAngle); + interpreter.installSegment5(opcodeGetPos,new OpGetPos); + interpreter.installSegment5(opcodeGetPosExplicit,new OpGetPos); + interpreter.installSegment5(opcodeSetPos,new OpSetPos); + interpreter.installSegment5(opcodeSetPosExplicit,new OpSetPos); } } } From b2ce1dfd1ab10f1a12f42576d9611cca8a570b29 Mon Sep 17 00:00:00 2001 From: gugus Date: Fri, 3 Aug 2012 18:20:51 +0200 Subject: [PATCH 03/84] getStartingPos --- .../mwscript/transformationextensions.cpp | 32 +++++++++++++++++++ 1 file changed, 32 insertions(+) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 42ef16ed9c..1eb53e8f38 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -169,6 +169,33 @@ namespace MWScript } }; + template + class OpGetStartingPos : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + MWWorld::Ptr ptr = R()(runtime); + + std::string axis = runtime.getStringLiteral (runtime[0].mInteger); + runtime.pop(); + + if(axis == "X") + { + runtime.push(ptr.getCellRef().pos.pos[0]); + } + if(axis == "Y") + { + runtime.push(ptr.getCellRef().pos.pos[1]); + } + if(axis == "Z") + { + runtime.push(ptr.getCellRef().pos.pos[2]); + } + } + }; + const int opcodeSetScale = 0x2000164; const int opcodeSetScaleExplicit = 0x2000165; const int opcodeSetAngle = 0x2000166; @@ -181,6 +208,8 @@ namespace MWScript const int opcodeGetPosExplicit = 0x200016d; const int opcodeSetPos = 0x200016e; const int opcodeSetPosExplicit = 0x200016f; + const int opcodeGetStartingPos = 0x2000170; + const int opcodeGetStartingPosExplicit = 0x2000171; void registerExtensions (Compiler::Extensions& extensions) { @@ -190,6 +219,7 @@ namespace MWScript extensions.registerFunction("getangle",'f',"S",opcodeGetAngle,opcodeGetAngleExplicit); extensions.registerInstruction("setpos","Sf",opcodeSetPos,opcodeSetPosExplicit); extensions.registerFunction("getpos",'f',"S",opcodeGetPos,opcodeGetPosExplicit); + extensions.registerFunction("getstartingpos",'f',"S",opcodeGetStartingPos,opcodeGetStartingPosExplicit); } void installOpcodes (Interpreter::Interpreter& interpreter) @@ -206,6 +236,8 @@ namespace MWScript interpreter.installSegment5(opcodeGetPosExplicit,new OpGetPos); interpreter.installSegment5(opcodeSetPos,new OpSetPos); interpreter.installSegment5(opcodeSetPosExplicit,new OpSetPos); + interpreter.installSegment5(opcodeGetStartingPos,new OpGetStartingPos); + interpreter.installSegment5(opcodeGetStartingPosExplicit,new OpGetStartingPos); } } } From cacf0bd10dca7efd216f823976404b0be273fd95 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Sat, 4 Aug 2012 15:43:33 -0400 Subject: [PATCH 04/84] Basic collision with npcs --- apps/openmw/mwclass/npc.cpp | 2 +- apps/openmw/mwrender/npcanimation.cpp | 2 +- apps/openmw/mwworld/physicssystem.cpp | 18 +++++++++++++----- components/nifbullet/bullet_nif_loader.cpp | 21 +++++++++++++++++---- components/nifbullet/bullet_nif_loader.hpp | 1 + libs/openengine/bullet/physic.cpp | 4 +++- libs/openengine/bullet/pmove.cpp | 2 +- libs/openengine/bullet/pmove.h | 2 +- libs/openengine/bullet/trace.cpp | 13 ++++++++----- libs/openengine/bullet/trace.h | 1 - 10 files changed, 46 insertions(+), 20 deletions(-) diff --git a/apps/openmw/mwclass/npc.cpp b/apps/openmw/mwclass/npc.cpp index ab4e2d5e6c..72565abda3 100644 --- a/apps/openmw/mwclass/npc.cpp +++ b/apps/openmw/mwclass/npc.cpp @@ -140,7 +140,7 @@ namespace MWClass std::string smodel = "meshes\\base_anim.nif"; if(beast) smodel = "meshes\\base_animkna.nif"; - physics.insertActorPhysics(ptr, smodel); + physics.insertObjectPhysics(ptr, smodel); MWBase::Environment::get().getMechanicsManager()->addActor (ptr); diff --git a/apps/openmw/mwrender/npcanimation.cpp b/apps/openmw/mwrender/npcanimation.cpp index fa88b72777..3cc0589f0a 100644 --- a/apps/openmw/mwrender/npcanimation.cpp +++ b/apps/openmw/mwrender/npcanimation.cpp @@ -161,7 +161,7 @@ NpcAnimation::NpcAnimation(const MWWorld::Ptr& ptr, OEngine::Render::OgreRendere textmappings = NIFLoader::getSingletonPtr()->getTextIndices(smodel); insert->attachObject(base); - + if(isFemale) insert->scale(race->data.height.female, race->data.height.female, race->data.height.female); else diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index 9848efe6eb..86268567a7 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -156,10 +156,11 @@ namespace MWWorld act->setWalkDirection(btVector3(0,0,0)); } playerMove::playercmd& pm_ref = playerphysics->cmd; - + //playerphysics->ps.snappingImplemented = false; pm_ref.rightmove = 0; pm_ref.forwardmove = 0; pm_ref.upmove = 0; + //playerphysics->ps.move_type = PM_NOCLIP; for (std::vector >::const_iterator iter (actors.begin()); @@ -175,12 +176,14 @@ namespace MWWorld Ogre::Quaternion yawQuat = yawNode->getOrientation(); Ogre::Quaternion pitchQuat = pitchNode->getOrientation(); + playerphysics->ps.viewangles.x = pitchQuat.getPitch().valueDegrees(); - playerphysics->ps.viewangles.y = yawQuat.getYaw().valueDegrees() *-1 + 90; - + playerphysics->ps.viewangles.y = yawQuat.getYaw().valueDegrees() * -1 + 90; + if(playerphysics->ps.viewangles.y < 0) + playerphysics->ps.viewangles.y += 360; Ogre::Quaternion quat = yawNode->getOrientation(); Ogre::Vector3 dir1(iter->second.x,iter->second.z,-iter->second.y); @@ -213,7 +216,7 @@ namespace MWWorld Ogre::Vector3 coord(newPos.x(), newPos.y(), newPos.z()); if(it->first == "player"){ - coord = playerphysics->ps.origin; + coord = playerphysics->ps.origin ; } @@ -242,7 +245,12 @@ namespace MWWorld OEngine::Physic::RigidBody* body = mEngine->createRigidBody(mesh,handle,scale); mEngine->addRigidBody(body); btTransform tr; - tr.setOrigin(btVector3(position.x,position.y,position.z)); + btBoxShape* box = dynamic_cast(body->getCollisionShape()); + if(box != NULL){ + tr.setOrigin(btVector3(position.x,position.y,position.z + box->getHalfExtentsWithMargin().getZ())); + } + else + tr.setOrigin(btVector3(position.x,position.y,position.z)); tr.setRotation(btQuaternion(rotation.x,rotation.y,rotation.z,rotation.w)); body->setWorldTransform(tr); } diff --git a/components/nifbullet/bullet_nif_loader.cpp b/components/nifbullet/bullet_nif_loader.cpp index 17c5f18aca..e0215fe195 100644 --- a/components/nifbullet/bullet_nif_loader.cpp +++ b/components/nifbullet/bullet_nif_loader.cpp @@ -136,6 +136,7 @@ void ManualBulletShapeLoader::loadResource(Ogre::Resource *resource) cShape = static_cast(resource); resourceName = cShape->getName(); cShape->collide = false; + mBoundingBox = NULL; mTriMesh = new btTriangleMesh(); @@ -199,9 +200,13 @@ void ManualBulletShapeLoader::loadResource(Ogre::Resource *resource) delete m_meshInterface; } }; - - currentShape = new TriangleMeshShape(mTriMesh,true); - cShape->Shape = currentShape; + if(mBoundingBox != NULL) + cShape->Shape = mBoundingBox; + else + { + currentShape = new TriangleMeshShape(mTriMesh,true); + cShape->Shape = currentShape; + } } bool ManualBulletShapeLoader::hasRootCollisionNode(Nif::Node* node) @@ -289,7 +294,15 @@ void ManualBulletShapeLoader::handleNode(Nif::Node *node, int flags, final.scale *= trafo->scale; } - + if(node->hasBounds) + { + btVector3 getHalf = getbtVector(*(node->boundXYZ)); + //getHalf.setX(getHalf.getX() / 2); + //getHalf.setY(getHalf.getY() / 2); + //getHalf.setZ(getHalf.getZ() / 2); + const btVector3 boxsize = getHalf; + mBoundingBox = new btBoxShape(boxsize); + } // For NiNodes, loop through children if (node->recType == Nif::RC_NiNode) diff --git a/components/nifbullet/bullet_nif_loader.hpp b/components/nifbullet/bullet_nif_loader.hpp index 488a7a42b0..93809ff7d7 100644 --- a/components/nifbullet/bullet_nif_loader.hpp +++ b/components/nifbullet/bullet_nif_loader.hpp @@ -126,6 +126,7 @@ private: BulletShape* cShape;//current shape btTriangleMesh *mTriMesh; + btBoxShape *mBoundingBox; btBvhTriangleMeshShape* currentShape;//the shape curently under construction }; diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 904747afa9..8c07d6e2cf 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -344,7 +344,9 @@ namespace Physic BulletShapeManager::getSingletonPtr()->load(outputstring,"General"); BulletShapePtr shape = BulletShapeManager::getSingleton().getByName(outputstring,"General"); shape->Shape->setLocalScaling( btVector3(scale,scale,scale)); - //btScaledBvhTriangleMeshShape* scaled = new btScaledBvhTriangleMeshShape(dynamic_cast (shape->Shape), btVector3(scale,scale,scale)); + + + // //create the motionState CMotionState* newMotionState = new CMotionState(this,name); diff --git a/libs/openengine/bullet/pmove.cpp b/libs/openengine/bullet/pmove.cpp index 924812c29f..4c70971a3f 100644 --- a/libs/openengine/bullet/pmove.cpp +++ b/libs/openengine/bullet/pmove.cpp @@ -449,7 +449,7 @@ int PM_StepSlideMove( bool gravity ) //pm->trace (&trace, start_o, pm->mins, pm->maxs, down, pm->ps->clientNum, pm->tracemask); //tracefunc(&trace, start_o, down, , 0, pml.scene); //tracefunc(&trace, *(const D3DXVECTOR3* const)&start_o, *(const D3DXVECTOR3* const)&down, D3DXVECTOR3(0.0f, -STEPSIZE, 0.0f), 0, pml.traceObj); - newtrace(&trace, start_o, down, halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); + newtrace(&trace, down, start_o, halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); // up = vec3(0, 0, 1) //VectorSet(up, 0, 0, 1); diff --git a/libs/openengine/bullet/pmove.h b/libs/openengine/bullet/pmove.h index aea63d1dbd..a0fec3d1c8 100644 --- a/libs/openengine/bullet/pmove.h +++ b/libs/openengine/bullet/pmove.h @@ -55,7 +55,7 @@ static const Ogre::Vector3 halfExtents(14.64f * 2, 14.24f * 2, 33.25f * 2); #define CONTENTS_FOG 64 static const float pm_accelerate = 10.0f; static const float pm_stopspeed = 100.0f; -static const float pm_friction = 12.0f; +static const float pm_friction = 6.0f; static const float pm_flightfriction = 3.0f; static const float pm_waterfriction = 1.0f; static const float pm_airaccelerate = 1.0f; diff --git a/libs/openengine/bullet/trace.cpp b/libs/openengine/bullet/trace.cpp index 2d18aaa4da..6d2166baac 100644 --- a/libs/openengine/bullet/trace.cpp +++ b/libs/openengine/bullet/trace.cpp @@ -13,7 +13,8 @@ void newtrace(traceResults* const results, const Ogre::Vector3& start, const Ogre::Vector3& end, const Ogre::Vector3& BBHalfExtents, const float rotation, bool isInterior, OEngine::Physic::PhysicEngine* enginePass) //Traceobj was a Aedra Object { - + static float lastyaw = 0.0f; + static float lastpitch = 0.0f; //if (!traceobj) // return; @@ -21,10 +22,12 @@ void newtrace(traceResults* const results, const Ogre::Vector3& start, const Ogr // return; const Ogre::Vector3 rayDir = end - start; + + + - // Nudge starting point backwards - //const Position3D nudgestart = start + (rayDir * -0.1f); // by 10% (isn't that too much?) - //const Position3D nudgestart = start; + + NewPhysTraceResults out; //std::cout << "Starting trace\n"; @@ -32,7 +35,7 @@ void newtrace(traceResults* const results, const Ogre::Vector3& start, const Ogr //Ogre::Vector3 endReplace = startReplace; //endReplace.z -= .25; - const bool hasHit = NewPhysicsTrace(&out, start, end, BBHalfExtents, Ogre::Vector3(0.0f, 0.0, rotation), isInterior, enginePass); + const bool hasHit = NewPhysicsTrace(&out, start, end, BBHalfExtents, Ogre::Vector3(0.0f, 0.0f,0.0f), isInterior, enginePass); if (out.fraction < 0.001f) results->startsolid = true; diff --git a/libs/openengine/bullet/trace.h b/libs/openengine/bullet/trace.h index 076baf56ef..bd554031a5 100644 --- a/libs/openengine/bullet/trace.h +++ b/libs/openengine/bullet/trace.h @@ -9,7 +9,6 @@ #include - enum traceWorldType { collisionWorldTrace = 1, From d850a3ee49bf31b4b301695a6023d56c9bd29566 Mon Sep 17 00:00:00 2001 From: gugus Date: Sun, 5 Aug 2012 16:21:53 +0200 Subject: [PATCH 05/84] some correction --- .../mwscript/transformationextensions.cpp | 36 +++++++++---------- 1 file changed, 18 insertions(+), 18 deletions(-) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 1eb53e8f38..432482e480 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -66,15 +66,15 @@ namespace MWScript float ay = Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees(); float az = Ogre::Radian(ptr.getRefData().getPosition().rot[2]).valueDegrees(); - if(axis == "X") + if(axis == "x") { MWBase::Environment::get().getWorld()->rotateObject(ptr,angle,ay,az); } - if(axis == "Y") + if(axis == "y") { MWBase::Environment::get().getWorld()->rotateObject(ptr,ax,angle,az); } - if(axis == "Z") + if(axis == "z") { MWBase::Environment::get().getWorld()->rotateObject(ptr,ax,ay,angle); } @@ -93,15 +93,15 @@ namespace MWScript std::string axis = runtime.getStringLiteral (runtime[0].mInteger); runtime.pop(); - if(axis == "X") + if(axis == "x") { runtime.push(Ogre::Radian(ptr.getRefData().getPosition().rot[0]).valueDegrees()); } - if(axis == "Y") + if(axis == "y") { runtime.push(Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees()); } - if(axis == "Z") + if(axis == "z") { runtime.push(Ogre::Radian(ptr.getRefData().getPosition().rot[2]).valueDegrees()); } @@ -120,15 +120,15 @@ namespace MWScript std::string axis = runtime.getStringLiteral (runtime[0].mInteger); runtime.pop(); - if(axis == "X") + if(axis == "x") { runtime.push(ptr.getRefData().getPosition().pos[0]); } - if(axis == "Y") + if(axis == "y") { runtime.push(ptr.getRefData().getPosition().pos[1]); } - if(axis == "Z") + if(axis == "z") { runtime.push(ptr.getRefData().getPosition().pos[2]); } @@ -154,15 +154,15 @@ namespace MWScript float az = ptr.getRefData().getPosition().pos[2]; std::cout << "setPos"; - if(axis == "X") + if(axis == "x") { MWBase::Environment::get().getWorld()->moveObject(ptr,pos,ay,az); } - if(axis == "Y") + if(axis == "y") { MWBase::Environment::get().getWorld()->moveObject(ptr,ax,pos,az); } - if(axis == "Z") + if(axis == "z") { MWBase::Environment::get().getWorld()->moveObject(ptr,ax,ay,pos); } @@ -181,15 +181,15 @@ namespace MWScript std::string axis = runtime.getStringLiteral (runtime[0].mInteger); runtime.pop(); - if(axis == "X") + if(axis == "x") { runtime.push(ptr.getCellRef().pos.pos[0]); } - if(axis == "Y") + if(axis == "y") { runtime.push(ptr.getCellRef().pos.pos[1]); } - if(axis == "Z") + if(axis == "z") { runtime.push(ptr.getCellRef().pos.pos[2]); } @@ -217,9 +217,9 @@ namespace MWScript extensions.registerFunction("getscale",'f',"",opcodeGetScale,opcodeGetScaleExplicit); extensions.registerInstruction("setangle","Sf",opcodeSetAngle,opcodeSetAngleExplicit); extensions.registerFunction("getangle",'f',"S",opcodeGetAngle,opcodeGetAngleExplicit); - extensions.registerInstruction("setpos","Sf",opcodeSetPos,opcodeSetPosExplicit); - extensions.registerFunction("getpos",'f',"S",opcodeGetPos,opcodeGetPosExplicit); - extensions.registerFunction("getstartingpos",'f',"S",opcodeGetStartingPos,opcodeGetStartingPosExplicit); + extensions.registerInstruction("setpos","cf",opcodeSetPos,opcodeSetPosExplicit); + extensions.registerFunction("getpos",'f',"c",opcodeGetPos,opcodeGetPosExplicit); + extensions.registerFunction("getstartingpos",'f',"c",opcodeGetStartingPos,opcodeGetStartingPosExplicit); } void installOpcodes (Interpreter::Interpreter& interpreter) From 8a485e213b78ef280807d1b91845cf50dee168bb Mon Sep 17 00:00:00 2001 From: gugus Date: Sun, 5 Aug 2012 16:44:56 +0200 Subject: [PATCH 06/84] first try of the Position script instruction. Still missing: check if overlapp with an object. --- .../mwscript/transformationextensions.cpp | 36 +++++++++++++++++++ 1 file changed, 36 insertions(+) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 432482e480..46cbf781f0 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -196,6 +196,37 @@ namespace MWScript } }; + template + class OpPosition : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + MWWorld::Ptr ptr = R()(runtime); + + Interpreter::Type_Float x = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float y = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float z = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float zRot = runtime[0].mFloat; + runtime.pop(); + + MWBase::Environment::get().getWorld()->moveObject(ptr,x,y,z); + float ax = Ogre::Radian(ptr.getRefData().getPosition().rot[0]).valueDegrees(); + float ay = Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees(); + if(ptr.getTypeName() == "struct ESM::NPC")//some morrowind oddity + { + ax = ax/60.; + ay = ay/60.; + zRot = zRot/60.; + } + MWBase::Environment::get().getWorld()->rotateObject(ptr,ax,ay,zRot); + } + }; + const int opcodeSetScale = 0x2000164; const int opcodeSetScaleExplicit = 0x2000165; const int opcodeSetAngle = 0x2000166; @@ -210,6 +241,8 @@ namespace MWScript const int opcodeSetPosExplicit = 0x200016f; const int opcodeGetStartingPos = 0x2000170; const int opcodeGetStartingPosExplicit = 0x2000171; + const int opcodePosition = 0x2000172; + const int opcodePositionExplicit = 0x2000173; void registerExtensions (Compiler::Extensions& extensions) { @@ -220,6 +253,7 @@ namespace MWScript extensions.registerInstruction("setpos","cf",opcodeSetPos,opcodeSetPosExplicit); extensions.registerFunction("getpos",'f',"c",opcodeGetPos,opcodeGetPosExplicit); extensions.registerFunction("getstartingpos",'f',"c",opcodeGetStartingPos,opcodeGetStartingPosExplicit); + extensions.registerInstruction("position","ffff",opcodePosition,opcodePositionExplicit); } void installOpcodes (Interpreter::Interpreter& interpreter) @@ -238,6 +272,8 @@ namespace MWScript interpreter.installSegment5(opcodeSetPosExplicit,new OpSetPos); interpreter.installSegment5(opcodeGetStartingPos,new OpGetStartingPos); interpreter.installSegment5(opcodeGetStartingPosExplicit,new OpGetStartingPos); + interpreter.installSegment5(opcodePosition,new OpPosition); + interpreter.installSegment5(opcodePositionExplicit,new OpPosition); } } } From cb5b69104d18be0383c901a86758b49600fcc354 Mon Sep 17 00:00:00 2001 From: gugus Date: Thu, 9 Aug 2012 23:45:06 +0200 Subject: [PATCH 07/84] PositionCell --- .../mwscript/transformationextensions.cpp | 38 +++++++++++++++++++ 1 file changed, 38 insertions(+) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 46cbf781f0..f47a1829a8 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -196,6 +196,39 @@ namespace MWScript } }; + template + class OpPositionCell : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + MWWorld::Ptr ptr = R()(runtime); + + Interpreter::Type_Float x = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float y = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float z = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float zRot = runtime[0].mFloat; + runtime.pop(); + std::string cellID = runtime.getStringLiteral (runtime[0].mInteger); + runtime.pop(); + + MWBase::Environment::get().getWorld()->moveObjectToCell(ptr,cellID,x,y,z); + float ax = Ogre::Radian(ptr.getRefData().getPosition().rot[0]).valueDegrees(); + float ay = Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees(); + if(ptr.getTypeName() == "struct ESM::NPC")//some morrowind oddity + { + ax = ax/60.; + ay = ay/60.; + zRot = zRot/60.; + } + MWBase::Environment::get().getWorld()->rotateObject(ptr,ax,ay,zRot); + } + }; + template class OpPosition : public Interpreter::Opcode0 { @@ -243,6 +276,8 @@ namespace MWScript const int opcodeGetStartingPosExplicit = 0x2000171; const int opcodePosition = 0x2000172; const int opcodePositionExplicit = 0x2000173; + const int opcodePositionCell = 0x2000174; + const int opcodePositionCellExplicit = 0x2000175; void registerExtensions (Compiler::Extensions& extensions) { @@ -254,6 +289,7 @@ namespace MWScript extensions.registerFunction("getpos",'f',"c",opcodeGetPos,opcodeGetPosExplicit); extensions.registerFunction("getstartingpos",'f',"c",opcodeGetStartingPos,opcodeGetStartingPosExplicit); extensions.registerInstruction("position","ffff",opcodePosition,opcodePositionExplicit); + extensions.registerInstruction("positioncell","ffffS",opcodePositionCell,opcodePositionCellExplicit); } void installOpcodes (Interpreter::Interpreter& interpreter) @@ -274,6 +310,8 @@ namespace MWScript interpreter.installSegment5(opcodeGetStartingPosExplicit,new OpGetStartingPos); interpreter.installSegment5(opcodePosition,new OpPosition); interpreter.installSegment5(opcodePositionExplicit,new OpPosition); + interpreter.installSegment5(opcodePositionCell,new OpPositionCell); + interpreter.installSegment5(opcodePositionCellExplicit,new OpPositionCell); } } } From 38c2c5d480d7f159ebeb1566628f60dea577ca9a Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Thu, 9 Aug 2012 18:09:11 -0400 Subject: [PATCH 08/84] Creatures now use object physics --- apps/openmw/mwclass/creature.cpp | 2 +- components/files/ogreplugin.hpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/apps/openmw/mwclass/creature.cpp b/apps/openmw/mwclass/creature.cpp index 0f3141f5c6..620f809e7d 100644 --- a/apps/openmw/mwclass/creature.cpp +++ b/apps/openmw/mwclass/creature.cpp @@ -89,7 +89,7 @@ namespace MWClass { const std::string model = getModel(ptr); if(!model.empty()){ - physics.insertActorPhysics(ptr, model); + physics.insertObjectPhysics(ptr, model); } MWBase::Environment::get().getMechanicsManager()->addActor (ptr); } diff --git a/components/files/ogreplugin.hpp b/components/files/ogreplugin.hpp index c5292b3a21..2d56bfb47a 100644 --- a/components/files/ogreplugin.hpp +++ b/components/files/ogreplugin.hpp @@ -32,7 +32,7 @@ namespace Ogre { class Root; } -#if (BOOST_VERSION <= 104300) +#if (BOOST_VERSION <= 104500) namespace boost { namespace filesystem { inline path absolute(const path& p, const path& base=current_path()) { From 56c9c4dbd95270b8b0b98691bd188d961c490815 Mon Sep 17 00:00:00 2001 From: greye Date: Fri, 10 Aug 2012 21:03:46 +0400 Subject: [PATCH 09/84] remove some redundant code --- apps/openmw/mwworld/scene.cpp | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/apps/openmw/mwworld/scene.cpp b/apps/openmw/mwworld/scene.cpp index ec557e35c7..40d0a634a4 100644 --- a/apps/openmw/mwworld/scene.cpp +++ b/apps/openmw/mwworld/scene.cpp @@ -140,19 +140,18 @@ namespace MWWorld const ESM::Position& pos, bool adjustPlayerPos) { - MWBase::Environment::get().getWorld()->getPlayer().setCell (cell); - bool hasWater = cell->cell->data.flags & cell->cell->HasWater; mPhysics->setCurrentWater(hasWater, cell->cell->water); MWBase::World *world = MWBase::Environment::get().getWorld(); MWWorld::Ptr player = world->getPlayer().getPlayer(); + world->getPlayer().setCell(cell); + if (adjustPlayerPos) { world->moveObject(player, pos.pos[0], pos.pos[1], pos.pos[2]); world->rotateObject(player, pos.rot[0], pos.rot[1], pos.rot[2]); } - world->getPlayer().setCell(cell); MWMechanics::MechanicsManager *mechMgr = MWBase::Environment::get().getMechanicsManager(); From bed6545e45e9d456eeda474d2a0ac8327e6c0c13 Mon Sep 17 00:00:00 2001 From: greye Date: Fri, 10 Aug 2012 21:06:09 +0400 Subject: [PATCH 10/84] still fix assertion fail --- apps/openmw/mwworld/scene.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/apps/openmw/mwworld/scene.cpp b/apps/openmw/mwworld/scene.cpp index 40d0a634a4..531546a576 100644 --- a/apps/openmw/mwworld/scene.cpp +++ b/apps/openmw/mwworld/scene.cpp @@ -144,10 +144,10 @@ namespace MWWorld mPhysics->setCurrentWater(hasWater, cell->cell->water); MWBase::World *world = MWBase::Environment::get().getWorld(); - MWWorld::Ptr player = world->getPlayer().getPlayer(); - world->getPlayer().setCell(cell); + MWWorld::Ptr player = world->getPlayer().getPlayer(); + if (adjustPlayerPos) { world->moveObject(player, pos.pos[0], pos.pos[1], pos.pos[2]); world->rotateObject(player, pos.rot[0], pos.rot[1], pos.rot[2]); From 0042020385b7303d20490e810e49e9b6f8e97b0c Mon Sep 17 00:00:00 2001 From: greye Date: Fri, 10 Aug 2012 21:24:07 +0400 Subject: [PATCH 11/84] should fix 'north direction' bug not even compiled --- apps/openmw/mwrender/renderingmanager.cpp | 29 ++++++++++++----------- 1 file changed, 15 insertions(+), 14 deletions(-) diff --git a/apps/openmw/mwrender/renderingmanager.cpp b/apps/openmw/mwrender/renderingmanager.cpp index 8719557ca3..4534fee2c7 100644 --- a/apps/openmw/mwrender/renderingmanager.cpp +++ b/apps/openmw/mwrender/renderingmanager.cpp @@ -254,27 +254,28 @@ RenderingManager::rotateObject( Ogre::Vector3 &rot, bool adjust) { - if (ptr.getRefData().getHandle() == "player") { - if (adjust) { - return mPlayer->adjustRotation(rot); - } else { - return mPlayer->setRotation(rot); - } + bool isPlayer = ptr.getRefData().getHandle() == "player"; + bool force = true; + + if (isPlayer) { + force = (adjust) ? mPlayer->adjustRotation(rot) : mPlayer->setRotation(rot); } MWWorld::Class::get(ptr).adjustRotation(ptr, rot.x, rot.y, rot.z); - if (adjust) { float *f = ptr.getRefData().getPosition().rot; - rot.x += f[0], rot.y += f[1], rot.z += f[2]; + rot.x += Ogre::Radian(f[0]).valueDegrees(); + rot.y += Ogre::Radian(f[1]).valueDegrees(); + rot.z += Ogre::Radian(f[2]).valueDegrees(); } + if (!isPlayer) { + Ogre::Quaternion xr(Ogre::Degree(rot.x), Ogre::Vector3::UNIT_X); + Ogre::Quaternion yr(Ogre::Degree(rot.y), Ogre::Vector3::UNIT_Y); + Ogre::Quaternion zr(Ogre::Degree(rot.z), Ogre::Vector3::UNIT_Z); - Ogre::Quaternion xr(Ogre::Degree(rot.x), Ogre::Vector3::UNIT_X); - Ogre::Quaternion yr(Ogre::Degree(rot.y), Ogre::Vector3::UNIT_Y); - Ogre::Quaternion zr(Ogre::Degree(rot.z), Ogre::Vector3::UNIT_Z); - - ptr.getRefData().getBaseNode()->setOrientation(xr * yr * zr); + ptr.getRefData().getBaseNode()->setOrientation(xr * yr * zr); + } - return true; + return force; } void From 7fa1dc93d7837b86ecbdc176468475af28df5d4b Mon Sep 17 00:00:00 2001 From: gugus Date: Sat, 11 Aug 2012 09:52:49 +0200 Subject: [PATCH 12/84] 2nd try: position/ PositionCell --- .../mwscript/transformationextensions.cpp | 32 +++++++++++++------ 1 file changed, 23 insertions(+), 9 deletions(-) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 50897278f7..5d9de6baf8 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -249,16 +249,29 @@ namespace MWScript std::string cellID = runtime.getStringLiteral (runtime[0].mInteger); runtime.pop(); - MWBase::Environment::get().getWorld()->moveObjectToCell(ptr,cellID,x,y,z); - float ax = Ogre::Radian(ptr.getRefData().getPosition().rot[0]).valueDegrees(); - float ay = Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees(); - if(ptr.getTypeName() == "struct ESM::NPC")//some morrowind oddity + + MWWorld::CellStore* store = MWBase::Environment::get().getWorld()->getInterior(cellID); + if(!store) { - ax = ax/60.; - ay = ay/60.; - zRot = zRot/60.; + ESM::Cell cell = MWBase::Environment::get().getWorld()->getExterior(cellID); + if(cell) + { + store = MWBase::Environment::get().getWorld()->getExterior(cell.getGridX(),cell.getGridY()); + } + } + if(store) + { + MWBase::Environment::get().getWorld()->moveObject(ptr,store,x,y,z); + float ax = Ogre::Radian(ptr.getRefData().getPosition().rot[0]).valueDegrees(); + float ay = Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees(); + if(ptr.getTypeName() == "struct ESM::NPC")//some morrowind oddity + { + ax = ax/60.; + ay = ay/60.; + zRot = zRot/60.; + } + MWBase::Environment::get().getWorld()->rotateObject(ptr,ax,ay,zRot); } - MWBase::Environment::get().getWorld()->rotateObject(ptr,ax,ay,zRot); } }; @@ -280,7 +293,8 @@ namespace MWScript Interpreter::Type_Float zRot = runtime[0].mFloat; runtime.pop(); - MWBase::Environment::get().getWorld()->moveObject(ptr,x,y,z); + MWBase::Environment::get().getWorld()->moveObject(ptr, + MWBase::Environment::get().getWorld()->getExterior(x,y),x,y,z); float ax = Ogre::Radian(ptr.getRefData().getPosition().rot[0]).valueDegrees(); float ay = Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees(); if(ptr.getTypeName() == "struct ESM::NPC")//some morrowind oddity From eaf6a8df94822a6bb2b58b44b2b2341bba87ace2 Mon Sep 17 00:00:00 2001 From: gugus Date: Sat, 11 Aug 2012 14:06:58 +0200 Subject: [PATCH 13/84] some correction --- apps/openmw/mwscript/transformationextensions.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 5d9de6baf8..8576ac22e0 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -253,15 +253,15 @@ namespace MWScript MWWorld::CellStore* store = MWBase::Environment::get().getWorld()->getInterior(cellID); if(!store) { - ESM::Cell cell = MWBase::Environment::get().getWorld()->getExterior(cellID); + const ESM::Cell* cell = MWBase::Environment::get().getWorld()->getExterior(cellID); if(cell) { - store = MWBase::Environment::get().getWorld()->getExterior(cell.getGridX(),cell.getGridY()); + store = MWBase::Environment::get().getWorld()->getExterior(cell->getGridX(),cell->getGridY()); } } if(store) { - MWBase::Environment::get().getWorld()->moveObject(ptr,store,x,y,z); + MWBase::Environment::get().getWorld()->moveObject(ptr,*store,x,y,z); float ax = Ogre::Radian(ptr.getRefData().getPosition().rot[0]).valueDegrees(); float ay = Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees(); if(ptr.getTypeName() == "struct ESM::NPC")//some morrowind oddity @@ -294,7 +294,7 @@ namespace MWScript runtime.pop(); MWBase::Environment::get().getWorld()->moveObject(ptr, - MWBase::Environment::get().getWorld()->getExterior(x,y),x,y,z); + *MWBase::Environment::get().getWorld()->getExterior(x,y),x,y,z); float ax = Ogre::Radian(ptr.getRefData().getPosition().rot[0]).valueDegrees(); float ay = Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees(); if(ptr.getTypeName() == "struct ESM::NPC")//some morrowind oddity From 0bc48cc5eaaa23793fbeb644c20a747e2fb969fd Mon Sep 17 00:00:00 2001 From: gugus Date: Sat, 11 Aug 2012 18:07:20 +0200 Subject: [PATCH 14/84] little fix (thanks greye!) --- apps/openmw/mwscript/transformationextensions.cpp | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 8576ac22e0..cc0444f86a 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -292,9 +292,10 @@ namespace MWScript runtime.pop(); Interpreter::Type_Float zRot = runtime[0].mFloat; runtime.pop(); - + int cx,cy; + MWBase::Environment::get().getWorld()->positionToIndex(x,y,cx,cy); MWBase::Environment::get().getWorld()->moveObject(ptr, - *MWBase::Environment::get().getWorld()->getExterior(x,y),x,y,z); + *MWBase::Environment::get().getWorld()->getExterior(cx,cy),x,y,z); float ax = Ogre::Radian(ptr.getRefData().getPosition().rot[0]).valueDegrees(); float ay = Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees(); if(ptr.getTypeName() == "struct ESM::NPC")//some morrowind oddity From 0c8045d60661b615a4b7089898c294d1e710453d Mon Sep 17 00:00:00 2001 From: gugus Date: Sat, 11 Aug 2012 19:16:00 +0200 Subject: [PATCH 15/84] allow exterior cell for positioncell. Crash! --- apps/openmw/mwscript/transformationextensions.cpp | 14 +++++++++++--- 1 file changed, 11 insertions(+), 3 deletions(-) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index cc0444f86a..f3d22f6702 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -249,13 +249,21 @@ namespace MWScript std::string cellID = runtime.getStringLiteral (runtime[0].mInteger); runtime.pop(); - - MWWorld::CellStore* store = MWBase::Environment::get().getWorld()->getInterior(cellID); - if(!store) + bool interior = true; + MWWorld::CellStore* store; + try + { + MWWorld::CellStore* store = MWBase::Environment::get().getWorld()->getInterior(cellID); + } + catch(std::exception &e) { + std::cout << "trying exterior"; const ESM::Cell* cell = MWBase::Environment::get().getWorld()->getExterior(cellID); if(cell) { + std::cout << "exteriorfffffffffffffffffmZEJFB"; + //cell->getGridX(); + //MWBase::Environment::get().getWorld()->getExterior(cell->getGridX(),cell->getGridY()); store = MWBase::Environment::get().getWorld()->getExterior(cell->getGridX(),cell->getGridY()); } } From fb91f76a2b70bf10366d8f8f97b53d4aa3c0acfd Mon Sep 17 00:00:00 2001 From: gugus Date: Sat, 11 Aug 2012 22:08:04 +0200 Subject: [PATCH 16/84] fixed a crash --- apps/openmw/mwscript/transformationextensions.cpp | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index f3d22f6702..3f1cff7e7d 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -249,21 +249,16 @@ namespace MWScript std::string cellID = runtime.getStringLiteral (runtime[0].mInteger); runtime.pop(); - bool interior = true; - MWWorld::CellStore* store; + MWWorld::CellStore* store = 0; try { MWWorld::CellStore* store = MWBase::Environment::get().getWorld()->getInterior(cellID); } catch(std::exception &e) { - std::cout << "trying exterior"; const ESM::Cell* cell = MWBase::Environment::get().getWorld()->getExterior(cellID); if(cell) { - std::cout << "exteriorfffffffffffffffffmZEJFB"; - //cell->getGridX(); - //MWBase::Environment::get().getWorld()->getExterior(cell->getGridX(),cell->getGridY()); store = MWBase::Environment::get().getWorld()->getExterior(cell->getGridX(),cell->getGridY()); } } From e7329d5f8bc36f29578304c6a111f9518e0623dd Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Sun, 12 Aug 2012 00:36:49 -0400 Subject: [PATCH 17/84] Creatures now have a properly positioned box shape --- apps/openmw/mwworld/physicssystem.cpp | 13 ++----------- components/nifbullet/bullet_nif_loader.cpp | 8 +++++++- components/nifbullet/bullet_nif_loader.hpp | 2 ++ libs/openengine/bullet/BulletShapeLoader.h | 3 ++- libs/openengine/bullet/physic.cpp | 15 ++++++++++++++- libs/openengine/bullet/physic.hpp | 2 +- 6 files changed, 28 insertions(+), 15 deletions(-) diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index 7f773b5cbd..3bdf76bcd5 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -173,7 +173,7 @@ namespace MWWorld act->setWalkDirection(btVector3(0,0,0)); } playerMove::playercmd& pm_ref = playerphysics->cmd; - //playerphysics->ps.snappingImplemented = false; + pm_ref.rightmove = 0; pm_ref.forwardmove = 0; pm_ref.upmove = 0; @@ -259,17 +259,8 @@ namespace MWWorld const Ogre::Quaternion& rotation, float scale, const Ogre::Vector3& position) { handleToMesh[handle] = mesh; - OEngine::Physic::RigidBody* body = mEngine->createRigidBody(mesh,handle,scale); + OEngine::Physic::RigidBody* body = mEngine->createAndAdjustRigidBody(mesh,handle,scale, position, rotation); mEngine->addRigidBody(body); - btTransform tr; - btBoxShape* box = dynamic_cast(body->getCollisionShape()); - if(box != NULL){ - tr.setOrigin(btVector3(position.x,position.y,position.z + box->getHalfExtentsWithMargin().getZ())); - } - else - tr.setOrigin(btVector3(position.x,position.y,position.z)); - tr.setRotation(btQuaternion(rotation.x,rotation.y,rotation.z,rotation.w)); - body->setWorldTransform(tr); } void PhysicsSystem::addActor (const std::string& handle, const std::string& mesh, diff --git a/components/nifbullet/bullet_nif_loader.cpp b/components/nifbullet/bullet_nif_loader.cpp index 13c2cbbb7f..7af56d04c3 100644 --- a/components/nifbullet/bullet_nif_loader.cpp +++ b/components/nifbullet/bullet_nif_loader.cpp @@ -73,6 +73,7 @@ void ManualBulletShapeLoader::loadResource(Ogre::Resource *resource) resourceName = cShape->getName(); cShape->collide = false; mBoundingBox = NULL; + boxTranslation = Ogre::Vector3(0,0,0); mTriMesh = new btTriangleMesh(); @@ -126,8 +127,10 @@ void ManualBulletShapeLoader::loadResource(Ogre::Resource *resource) delete m_meshInterface; } }; + cShape->boxTranslation = boxTranslation; if(mBoundingBox != NULL) cShape->Shape = mBoundingBox; + else { currentShape = new TriangleMeshShape(mTriMesh,true); @@ -220,8 +223,11 @@ void ManualBulletShapeLoader::handleNode(Nif::Node *node, int flags, if(node->hasBounds) { - btVector3 boxsize = getbtVector((node->boundXYZ)); + + btVector3 boxsize = getbtVector((node->boundXYZ)); + boxTranslation = node->boundPos; + mBoundingBox = new btBoxShape(boxsize); } diff --git a/components/nifbullet/bullet_nif_loader.hpp b/components/nifbullet/bullet_nif_loader.hpp index 8bf91d127c..beb4274b0c 100644 --- a/components/nifbullet/bullet_nif_loader.hpp +++ b/components/nifbullet/bullet_nif_loader.hpp @@ -102,6 +102,8 @@ private: std::string resourceName; std::string resourceGroup; + Ogre::Vector3 boxTranslation; + BulletShape* cShape;//current shape btTriangleMesh *mTriMesh; btBoxShape *mBoundingBox; diff --git a/libs/openengine/bullet/BulletShapeLoader.h b/libs/openengine/bullet/BulletShapeLoader.h index 316ee523c2..c09f0dc7e9 100644 --- a/libs/openengine/bullet/BulletShapeLoader.h +++ b/libs/openengine/bullet/BulletShapeLoader.h @@ -4,7 +4,7 @@ #include #include #include - +#include //For some reason, Ogre Singleton cannot be used in another namespace, that's why there is no namespace here. //But the risk of name collision seems pretty low here. @@ -31,6 +31,7 @@ public: virtual ~BulletShape(); btCollisionShape* Shape; + Ogre::Vector3 boxTranslation; //this flag indicate if the shape is used for collision or if it's for raycasting only. bool collide; }; diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 743024c40c..9d0a290e9e 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -332,7 +332,7 @@ namespace Physic mHeightFieldMap.erase(name); } - RigidBody* PhysicEngine::createRigidBody(std::string mesh,std::string name,float scale) + RigidBody* PhysicEngine::createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation) { std::string sid = (boost::format("%07.3f") % scale).str(); std::string outputstring = mesh + sid; @@ -354,6 +354,19 @@ namespace Physic btRigidBody::btRigidBodyConstructionInfo CI = btRigidBody::btRigidBodyConstructionInfo(0,newMotionState,shape->Shape); RigidBody* body = new RigidBody(CI,name); body->collide = shape->collide; + + btTransform tr; + btBoxShape* box = dynamic_cast(body->getCollisionShape()); + if(box != NULL){ + Ogre::Vector3 transrot = rotation * (shape->boxTranslation * scale); + Ogre::Vector3 newPosition = transrot + position; + tr.setOrigin(btVector3(newPosition.x, newPosition.y, newPosition.z)); + } + else + tr.setOrigin(btVector3(position.x,position.y,position.z)); + tr.setRotation(btQuaternion(rotation.x,rotation.y,rotation.z,rotation.w)); + body->setWorldTransform(tr); + return body; } diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index 9ae8e76077..42f6487662 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -146,7 +146,7 @@ namespace Physic * Create a RigidBody.It does not add it to the simulation, but it does add it to the rigidBody Map, * so you can get it with the getRigidBody function. */ - RigidBody* createRigidBody(std::string mesh,std::string name,float scale); + RigidBody* createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation); /** * Add a HeightField to the simulation From 1f5bc229e0ef5c7e5d72b1f721bc0eb7c5e90e75 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Tue, 14 Aug 2012 18:04:58 -0400 Subject: [PATCH 18/84] Separate adjustRigidBody function --- apps/openmw/mwworld/physicssystem.cpp | 24 ++++++++++--------- apps/openmw/mwworld/physicssystem.hpp | 6 ++--- apps/openmw/mwworld/worldimp.cpp | 6 ++--- components/nifbullet/bullet_nif_loader.cpp | 2 +- libs/openengine/bullet/physic.cpp | 28 +++++++++++++--------- libs/openengine/bullet/physic.hpp | 2 ++ libs/openengine/bullet/trace.cpp | 5 +++- 7 files changed, 43 insertions(+), 30 deletions(-) diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index 3bdf76bcd5..faacc5b060 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -193,8 +193,8 @@ namespace MWWorld Ogre::Quaternion pitchQuat = pitchNode->getOrientation(); + //playerphysics->ps.snappingImplemented = false; - playerphysics->ps.viewangles.x = pitchQuat.getPitch().valueDegrees(); @@ -280,19 +280,20 @@ namespace MWWorld mEngine->deleteRigidBody(handle); } - void PhysicsSystem::moveObject (const std::string& handle, const Ogre::Vector3& position) + void PhysicsSystem::moveObject (const std::string& handle, Ogre::SceneNode* node) { if (OEngine::Physic::RigidBody* body = mEngine->getRigidBody(handle)) { // TODO very dirty hack to avoid crash during setup -> needs cleaning up to allow // start positions others than 0, 0, 0 btTransform tr = body->getWorldTransform(); + Ogre::Vector3 position = node->getPosition(); tr.setOrigin(btVector3(position.x,position.y,position.z)); body->setWorldTransform(tr); } if (OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle)) { - // TODO very dirty hack to avoid crash during setup -> needs cleaning up to allow + /*// TODO very dirty hack to avoid crash during setup -> needs cleaning up to allow // start positions others than 0, 0, 0 if (handle == "player") { @@ -301,31 +302,32 @@ namespace MWWorld else { act->setPosition(btVector3(position.x,position.y,position.z)); - } + }*/ } } - void PhysicsSystem::rotateObject (const std::string& handle, const Ogre::Quaternion& rotation) + void PhysicsSystem::rotateObject (const std::string& handle, Ogre::SceneNode* node) { - if (OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle)) + /*if (OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle)) { act->setRotation(btQuaternion(rotation.x, rotation.y, rotation.z, rotation.w)); - } + }*/ if (OEngine::Physic::RigidBody* body = mEngine->getRigidBody(handle)) { + Ogre::Quaternion rotation = node->getOrientation(); body->getWorldTransform().setRotation(btQuaternion(rotation.x, rotation.y, rotation.z, rotation.w)); } } - void PhysicsSystem::scaleObject (const std::string& handle, float scale) + void PhysicsSystem::scaleObject (const std::string& handle, Ogre::SceneNode* node) { if(handleToMesh.find(handle) != handleToMesh.end()) { - btTransform transform = mEngine->getRigidBody(handle)->getWorldTransform(); removeObject(handle); - Ogre::Quaternion quat = Ogre::Quaternion(transform.getRotation().getW(), transform.getRotation().getX(), transform.getRotation().getY(), transform.getRotation().getZ()); - Ogre::Vector3 vec = Ogre::Vector3(transform.getOrigin().getX(), transform.getOrigin().getY(), transform.getOrigin().getZ()); + float scale = node->getScale().x; + Ogre::Quaternion quat = node->getOrientation(); + Ogre::Vector3 vec = node->getPosition(); addObject(handle, handleToMesh[handle], quat, scale, vec); } } diff --git a/apps/openmw/mwworld/physicssystem.hpp b/apps/openmw/mwworld/physicssystem.hpp index e42fa536b9..4ed8d59f60 100644 --- a/apps/openmw/mwworld/physicssystem.hpp +++ b/apps/openmw/mwworld/physicssystem.hpp @@ -34,11 +34,11 @@ namespace MWWorld void removeObject (const std::string& handle); - void moveObject (const std::string& handle, const Ogre::Vector3& position); + void moveObject (const std::string& handle, Ogre::SceneNode* node); - void rotateObject (const std::string& handle, const Ogre::Quaternion& rotation); + void rotateObject (const std::string& handle, Ogre::SceneNode* node); - void scaleObject (const std::string& handle, float scale); + void scaleObject (const std::string& handle, Ogre::SceneNode* node); bool toggleCollisionMode(); diff --git a/apps/openmw/mwworld/worldimp.cpp b/apps/openmw/mwworld/worldimp.cpp index 8fb7b1ba7d..d5046db2d4 100644 --- a/apps/openmw/mwworld/worldimp.cpp +++ b/apps/openmw/mwworld/worldimp.cpp @@ -585,7 +585,7 @@ namespace MWWorld { moveObjectImp(ptr, x, y, z); - mPhysics->moveObject (ptr.getRefData().getHandle(), Ogre::Vector3 (x, y, z)); + mPhysics->moveObject (ptr.getRefData().getHandle(), ptr.getRefData().getBaseNode()); } void World::scaleObject (const Ptr& ptr, float scale) @@ -595,7 +595,7 @@ namespace MWWorld ptr.getCellRef().scale = scale; //scale = scale/ptr.getRefData().getBaseNode()->getScale().x; ptr.getRefData().getBaseNode()->setScale(scale,scale,scale); - mPhysics->scaleObject( ptr.getRefData().getHandle(), scale ); + mPhysics->scaleObject( ptr.getRefData().getHandle(), ptr.getRefData().getBaseNode()); } void World::rotateObject (const Ptr& ptr,float x,float y,float z) @@ -610,7 +610,7 @@ namespace MWWorld Ogre::Quaternion roty(Ogre::Degree(-y),Ogre::Vector3::UNIT_Y); Ogre::Quaternion rotz(Ogre::Degree(-z),Ogre::Vector3::UNIT_Z); ptr.getRefData().getBaseNode()->setOrientation(rotx*roty*rotz); - mPhysics->rotateObject(ptr.getRefData().getHandle(),ptr.getRefData().getBaseNode()->getOrientation()); + mPhysics->rotateObject(ptr.getRefData().getHandle(),ptr.getRefData().getBaseNode()); } void World::indexToPosition (int cellX, int cellY, float &x, float &y, bool centre) const diff --git a/components/nifbullet/bullet_nif_loader.cpp b/components/nifbullet/bullet_nif_loader.cpp index 7af56d04c3..fc7fb5ec26 100644 --- a/components/nifbullet/bullet_nif_loader.cpp +++ b/components/nifbullet/bullet_nif_loader.cpp @@ -129,7 +129,7 @@ void ManualBulletShapeLoader::loadResource(Ogre::Resource *resource) }; cShape->boxTranslation = boxTranslation; if(mBoundingBox != NULL) - cShape->Shape = mBoundingBox; + cShape->Shape = mBoundingBox; else { diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 9d0a290e9e..af73a42a6a 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -332,6 +332,20 @@ namespace Physic mHeightFieldMap.erase(name); } + void PhysicEngine::adjustRigidBody(BulletShapePtr shape, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation){ + btTransform tr; + btBoxShape* box = dynamic_cast(body->getCollisionShape()); + if(box != NULL){ + Ogre::Vector3 transrot = rotation * (shape->boxTranslation * scale); + Ogre::Vector3 newPosition = transrot + position; + tr.setOrigin(btVector3(newPosition.x, newPosition.y, newPosition.z)); + } + else + tr.setOrigin(btVector3(position.x,position.y,position.z)); + tr.setRotation(btQuaternion(rotation.x,rotation.y,rotation.z,rotation.w)); + body->setWorldTransform(tr); + } + RigidBody* PhysicEngine::createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation) { std::string sid = (boost::format("%07.3f") % scale).str(); @@ -355,17 +369,9 @@ namespace Physic RigidBody* body = new RigidBody(CI,name); body->collide = shape->collide; - btTransform tr; - btBoxShape* box = dynamic_cast(body->getCollisionShape()); - if(box != NULL){ - Ogre::Vector3 transrot = rotation * (shape->boxTranslation * scale); - Ogre::Vector3 newPosition = transrot + position; - tr.setOrigin(btVector3(newPosition.x, newPosition.y, newPosition.z)); - } - else - tr.setOrigin(btVector3(position.x,position.y,position.z)); - tr.setRotation(btQuaternion(rotation.x,rotation.y,rotation.z,rotation.w)); - body->setWorldTransform(tr); + //Pass in BulletShape, RigidBody, scale, position, rotation + + adjustRigidBody(shape, body, scale, position, rotation); return body; diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index 42f6487662..fc52ad127a 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -148,6 +148,8 @@ namespace Physic */ RigidBody* createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation); + void adjustRigidBody(BulletShapePtr shape, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation); + /** * Add a HeightField to the simulation */ diff --git a/libs/openengine/bullet/trace.cpp b/libs/openengine/bullet/trace.cpp index 6d2166baac..2329ed652c 100644 --- a/libs/openengine/bullet/trace.cpp +++ b/libs/openengine/bullet/trace.cpp @@ -21,6 +21,7 @@ void newtrace(traceResults* const results, const Ogre::Vector3& start, const Ogr //if (!traceobj->incellptr) // return; + const Ogre::Vector3 rayDir = end - start; @@ -34,6 +35,7 @@ void newtrace(traceResults* const results, const Ogre::Vector3& start, const Ogr //Ogre::Vector3 startReplace = Ogre::Vector3(650,950, 45); //Ogre::Vector3 endReplace = startReplace; //endReplace.z -= .25; + const bool hasHit = NewPhysicsTrace(&out, start, end, BBHalfExtents, Ogre::Vector3(0.0f, 0.0f,0.0f), isInterior, enginePass); @@ -104,7 +106,8 @@ const bool NewPhysicsTrace(NewPhysTraceResults* const out, const Ogre::Vector3& const btVector3 btend(end.x, end.y, end.z); const btQuaternion btrot(rotation.y, rotation.x, rotation.z); //y, x, z - const btBoxShape newshape(btVector3(BBHalfExtents.x, BBHalfExtents.y, BBHalfExtents.z)); + const btBoxShape newshape(btVector3(BBHalfExtents.x, BBHalfExtents.y, BBHalfExtents.z)); + //const btCapsuleShapeZ newshape(BBHalfExtents.x, BBHalfExtents.z * 2 - BBHalfExtents.x * 2); const btTransform from(btrot, btstart); const btTransform to(btrot, btend); From 7b8b4c366d5de40e148b780b86e409544975385d Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Tue, 14 Aug 2012 20:29:48 -0400 Subject: [PATCH 19/84] Set angle now working for npcs and creatures --- apps/openmw/mwclass/npc.cpp | 3 +-- apps/openmw/mwworld/physicssystem.cpp | 16 ++++++++++++---- libs/openengine/bullet/physic.cpp | 12 ++++++++++++ libs/openengine/bullet/physic.hpp | 2 +- 4 files changed, 26 insertions(+), 7 deletions(-) diff --git a/apps/openmw/mwclass/npc.cpp b/apps/openmw/mwclass/npc.cpp index 72501e8acf..217d920254 100644 --- a/apps/openmw/mwclass/npc.cpp +++ b/apps/openmw/mwclass/npc.cpp @@ -379,8 +379,7 @@ namespace MWClass void Npc::adjustRotation(const MWWorld::Ptr& ptr,float& x,float& y,float& z) const { - y = 0; - x = 0; + } MWWorld::Ptr diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index faacc5b060..3d4a08c69f 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -286,10 +286,15 @@ namespace MWWorld { // TODO very dirty hack to avoid crash during setup -> needs cleaning up to allow // start positions others than 0, 0, 0 - btTransform tr = body->getWorldTransform(); Ogre::Vector3 position = node->getPosition(); - tr.setOrigin(btVector3(position.x,position.y,position.z)); - body->setWorldTransform(tr); + + if(dynamic_cast(body->getCollisionShape()) == NULL){ + btTransform tr = body->getWorldTransform(); + tr.setOrigin(btVector3(position.x,position.y,position.z)); + body->setWorldTransform(tr); + } + else + mEngine->boxAdjustExternal(handleToMesh[handle], body, node->getScale().x, position, node->getOrientation()); } if (OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle)) { @@ -315,7 +320,10 @@ namespace MWWorld if (OEngine::Physic::RigidBody* body = mEngine->getRigidBody(handle)) { Ogre::Quaternion rotation = node->getOrientation(); - body->getWorldTransform().setRotation(btQuaternion(rotation.x, rotation.y, rotation.z, rotation.w)); + if(dynamic_cast(body->getCollisionShape()) == NULL) + body->getWorldTransform().setRotation(btQuaternion(rotation.x, rotation.y, rotation.z, rotation.w)); + else + mEngine->boxAdjustExternal(handleToMesh[handle], body, node->getScale().x, node->getPosition(), rotation); } } diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index af73a42a6a..2f06244709 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -345,6 +345,18 @@ namespace Physic tr.setRotation(btQuaternion(rotation.x,rotation.y,rotation.z,rotation.w)); body->setWorldTransform(tr); } + void PhysicEngine::boxAdjustExternal(std::string mesh, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation){ + std::string sid = (boost::format("%07.3f") % scale).str(); + std::string outputstring = mesh + sid; + //std::cout << "The string" << outputstring << "\n"; + + //get the shape from the .nif + mShapeLoader->load(outputstring,"General"); + BulletShapeManager::getSingletonPtr()->load(outputstring,"General"); + BulletShapePtr shape = BulletShapeManager::getSingleton().getByName(outputstring,"General"); + + adjustRigidBody(shape, body, scale, position, rotation); + } RigidBody* PhysicEngine::createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation) { diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index fc52ad127a..088bbc465c 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -149,7 +149,7 @@ namespace Physic RigidBody* createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation); void adjustRigidBody(BulletShapePtr shape, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation); - + void boxAdjustExternal(std::string mesh, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation); /** * Add a HeightField to the simulation */ From 8762f4a47abfd873acc036e70f24859105d0a6f7 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Wed, 15 Aug 2012 16:47:26 -0400 Subject: [PATCH 20/84] boxrotation nif field; commented functions --- apps/openmw/mwworld/physicssystem.cpp | 2 +- components/nifbullet/bullet_nif_loader.cpp | 6 +++--- components/nifbullet/bullet_nif_loader.hpp | 2 +- libs/openengine/bullet/BulletShapeLoader.h | 1 + libs/openengine/bullet/physic.cpp | 3 ++- libs/openengine/bullet/physic.hpp | 9 +++++++++ libs/openengine/bullet/pmove.cpp | 5 ++++- 7 files changed, 21 insertions(+), 7 deletions(-) diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index 3d4a08c69f..d1e39c8b7b 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -194,7 +194,7 @@ namespace MWWorld //playerphysics->ps.snappingImplemented = false; - + //playerphysics->ps.speed = 240; playerphysics->ps.viewangles.x = pitchQuat.getPitch().valueDegrees(); diff --git a/components/nifbullet/bullet_nif_loader.cpp b/components/nifbullet/bullet_nif_loader.cpp index fc7fb5ec26..6fec6241fb 100644 --- a/components/nifbullet/bullet_nif_loader.cpp +++ b/components/nifbullet/bullet_nif_loader.cpp @@ -73,7 +73,7 @@ void ManualBulletShapeLoader::loadResource(Ogre::Resource *resource) resourceName = cShape->getName(); cShape->collide = false; mBoundingBox = NULL; - boxTranslation = Ogre::Vector3(0,0,0); + cShape->boxTranslation = Ogre::Vector3(0,0,0); mTriMesh = new btTriangleMesh(); @@ -127,7 +127,6 @@ void ManualBulletShapeLoader::loadResource(Ogre::Resource *resource) delete m_meshInterface; } }; - cShape->boxTranslation = boxTranslation; if(mBoundingBox != NULL) cShape->Shape = mBoundingBox; @@ -226,7 +225,8 @@ void ManualBulletShapeLoader::handleNode(Nif::Node *node, int flags, btVector3 boxsize = getbtVector((node->boundXYZ)); - boxTranslation = node->boundPos; + cShape->boxTranslation = node->boundPos; + cShape->boxRotation = node->boundRot; mBoundingBox = new btBoxShape(boxsize); } diff --git a/components/nifbullet/bullet_nif_loader.hpp b/components/nifbullet/bullet_nif_loader.hpp index beb4274b0c..82ac227a0f 100644 --- a/components/nifbullet/bullet_nif_loader.hpp +++ b/components/nifbullet/bullet_nif_loader.hpp @@ -102,7 +102,7 @@ private: std::string resourceName; std::string resourceGroup; - Ogre::Vector3 boxTranslation; + BulletShape* cShape;//current shape btTriangleMesh *mTriMesh; diff --git a/libs/openengine/bullet/BulletShapeLoader.h b/libs/openengine/bullet/BulletShapeLoader.h index c09f0dc7e9..8640fd54f0 100644 --- a/libs/openengine/bullet/BulletShapeLoader.h +++ b/libs/openengine/bullet/BulletShapeLoader.h @@ -32,6 +32,7 @@ public: btCollisionShape* Shape; Ogre::Vector3 boxTranslation; + Ogre::Quaternion boxRotation; //this flag indicate if the shape is used for collision or if it's for raycasting only. bool collide; }; diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 2f06244709..0845864ef2 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -336,9 +336,10 @@ namespace Physic btTransform tr; btBoxShape* box = dynamic_cast(body->getCollisionShape()); if(box != NULL){ - Ogre::Vector3 transrot = rotation * (shape->boxTranslation * scale); + Ogre::Vector3 transrot = rotation * shape->boxRotation * (shape->boxTranslation * scale); Ogre::Vector3 newPosition = transrot + position; tr.setOrigin(btVector3(newPosition.x, newPosition.y, newPosition.z)); + rotation = rotation * shape->boxRotation; } else tr.setOrigin(btVector3(position.x,position.y,position.z)); diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index 088bbc465c..403af6c6cf 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -145,10 +145,19 @@ namespace Physic /** * Create a RigidBody.It does not add it to the simulation, but it does add it to the rigidBody Map, * so you can get it with the getRigidBody function. + + After created, the body is set to the correct rotation, position, and scale */ RigidBody* createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation); + /** + * Adjusts a rigid body to the right position and rotation + */ + void adjustRigidBody(BulletShapePtr shape, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation); + /** + Mainly used to (but not limited to) adjust rigid bodies based on box shapes to the right position and rotation. + */ void boxAdjustExternal(std::string mesh, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation); /** * Add a HeightField to the simulation diff --git a/libs/openengine/bullet/pmove.cpp b/libs/openengine/bullet/pmove.cpp index 4c70971a3f..32a11179fb 100644 --- a/libs/openengine/bullet/pmove.cpp +++ b/libs/openengine/bullet/pmove.cpp @@ -657,10 +657,11 @@ static void PM_Accelerate( Ogre::Vector3& wishdir, float wishspeed, float accel // int i; float addspeed, accelspeed, currentspeed; + // currentspeed = pm->ps->velocity dot wishdir //currentspeed = DotProduct (pm->ps->velocity, wishdir); currentspeed = pm->ps.velocity.dotProduct(wishdir); - + addspeed = wishspeed - currentspeed; if (addspeed <= 0) return; @@ -675,6 +676,8 @@ static void PM_Accelerate( Ogre::Vector3& wishdir, float wishspeed, float accel //for (i=0 ; i<3 ; i++) //pm->ps->velocity[i] += accelspeed * wishdir[i]; pm->ps.velocity += (wishdir * accelspeed); + //pm->ps.velocity = wishdir * wishspeed; //New, for instant acceleration + } static bool PM_CheckJump(void) From 63a40e9ba320b4ca44413c72d4aabcafe482b465 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Thu, 16 Aug 2012 15:41:42 -0400 Subject: [PATCH 21/84] npc xy disabled --- apps/openmw/mwclass/npc.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/apps/openmw/mwclass/npc.cpp b/apps/openmw/mwclass/npc.cpp index 217d920254..72501e8acf 100644 --- a/apps/openmw/mwclass/npc.cpp +++ b/apps/openmw/mwclass/npc.cpp @@ -379,7 +379,8 @@ namespace MWClass void Npc::adjustRotation(const MWWorld::Ptr& ptr,float& x,float& y,float& z) const { - + y = 0; + x = 0; } MWWorld::Ptr From f2d080d0913a2ebcddce5d2740658d908bb9cf5a Mon Sep 17 00:00:00 2001 From: gugus Date: Sat, 18 Aug 2012 10:50:58 +0200 Subject: [PATCH 22/84] bugfix --- .../mwscript/transformationextensions.cpp | 18 +++++++++++------- 1 file changed, 11 insertions(+), 7 deletions(-) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 3f1cff7e7d..18054374c0 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -185,7 +185,7 @@ namespace MWScript float ax = ptr.getRefData().getPosition().pos[0]; float ay = ptr.getRefData().getPosition().pos[1]; float az = ptr.getRefData().getPosition().pos[2]; - std::cout << "setPos"; + if(axis == "x") { @@ -252,28 +252,32 @@ namespace MWScript MWWorld::CellStore* store = 0; try { - MWWorld::CellStore* store = MWBase::Environment::get().getWorld()->getInterior(cellID); + store = MWBase::Environment::get().getWorld()->getInterior(cellID); } catch(std::exception &e) { - const ESM::Cell* cell = MWBase::Environment::get().getWorld()->getExterior(cellID); + /*const ESM::Cell* cell = MWBase::Environment::get().getWorld()->getExterior(cellID); if(cell) { store = MWBase::Environment::get().getWorld()->getExterior(cell->getGridX(),cell->getGridY()); - } + }*/ } if(store) { MWBase::Environment::get().getWorld()->moveObject(ptr,*store,x,y,z); float ax = Ogre::Radian(ptr.getRefData().getPosition().rot[0]).valueDegrees(); float ay = Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees(); - if(ptr.getTypeName() == "struct ESM::NPC")//some morrowind oddity + if(ptr.getTypeName() == typeid(ESM::NPC).name())//some morrowind oddity { ax = ax/60.; ay = ay/60.; zRot = zRot/60.; } - MWBase::Environment::get().getWorld()->rotateObject(ptr,ax,ay,zRot); + //MWBase::Environment::get().getWorld()->rotateObject(ptr,ax,ay,zRot); + } + else + { + throw std::runtime_error ("unknown cell"); } } }; @@ -301,7 +305,7 @@ namespace MWScript *MWBase::Environment::get().getWorld()->getExterior(cx,cy),x,y,z); float ax = Ogre::Radian(ptr.getRefData().getPosition().rot[0]).valueDegrees(); float ay = Ogre::Radian(ptr.getRefData().getPosition().rot[1]).valueDegrees(); - if(ptr.getTypeName() == "struct ESM::NPC")//some morrowind oddity + if(ptr.getTypeName() == typeid(ESM::NPC).name())//some morrowind oddity { ax = ax/60.; ay = ay/60.; From 165065d37891be204f67f9cc89de3780a0982b92 Mon Sep 17 00:00:00 2001 From: gugus Date: Tue, 21 Aug 2012 19:54:42 +0200 Subject: [PATCH 23/84] fix a bug with case sensitivity: when searching for a cell which is already loaded,but with another case, the cell get loaded twice, which is bad :p --- apps/openmw/mwworld/cells.cpp | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) diff --git a/apps/openmw/mwworld/cells.cpp b/apps/openmw/mwworld/cells.cpp index 822aa78d6e..dd2339eeb5 100644 --- a/apps/openmw/mwworld/cells.cpp +++ b/apps/openmw/mwworld/cells.cpp @@ -8,6 +8,17 @@ #include "class.hpp" #include "containerstore.hpp" +//helper function +std::string toLower (const std::string& name) +{ + std::string lowerCase; + + std::transform (name.begin(), name.end(), std::back_inserter (lowerCase), + (int(*)(int)) std::tolower); + + return lowerCase; +} + MWWorld::Ptr::CellStore *MWWorld::Cells::getCellStore (const ESM::Cell *cell) { if (cell->data.flags & ESM::Cell::Interior) @@ -129,13 +140,14 @@ MWWorld::Ptr::CellStore *MWWorld::Cells::getExterior (int x, int y) MWWorld::Ptr::CellStore *MWWorld::Cells::getInterior (const std::string& name) { - std::map::iterator result = mInteriors.find (name); + std::string nName = toLower(name); + std::map::iterator result = mInteriors.find (nName); if (result==mInteriors.end()) { - const ESM::Cell *cell = mStore.cells.findInt (name); + const ESM::Cell *cell = mStore.cells.findInt (nName); - result = mInteriors.insert (std::make_pair (name, Ptr::CellStore (cell))).first; + result = mInteriors.insert (std::make_pair (nName, Ptr::CellStore (cell))).first; } if (result->second.mState!=Ptr::CellStore::State_Loaded) From ed607a625913cd175f0d12f5c2c5f911769fcdad Mon Sep 17 00:00:00 2001 From: Michael Mc Donnell Date: Wed, 22 Aug 2012 15:00:07 -0400 Subject: [PATCH 24/84] Use char literals in UTF 8 conversion to fix 798 warnings The data type is specified as char but the literals are unsigned char. This results in 798 truncation warnings in vs2010. The literals were converted with a simple python script to signed char while taking two's complement and the overflow into account. --- components/to_utf8/tables_gen.hpp | 1536 ++++++++++++++--------------- 1 file changed, 768 insertions(+), 768 deletions(-) diff --git a/components/to_utf8/tables_gen.hpp b/components/to_utf8/tables_gen.hpp index 1084ca28f9..9c32f0427d 100644 --- a/components/to_utf8/tables_gen.hpp +++ b/components/to_utf8/tables_gen.hpp @@ -10,785 +10,785 @@ namespace ToUTF8 /// Serbian (Latin script), Romanian and Albanian. static char windows_1250[] = { - (char)0x1, (char)0x0, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x8, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x9, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xa, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xb, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xc, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xd, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xe, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xf, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x10, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x11, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x12, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x13, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x14, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x15, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x16, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x17, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x18, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x19, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x21, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x22, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x23, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x24, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x25, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x26, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x27, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x28, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x29, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x30, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x31, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x32, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x33, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x34, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x35, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x36, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x37, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x38, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x39, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x40, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x41, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x42, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x43, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x44, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x45, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x46, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x47, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x48, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x49, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x50, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x51, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x52, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x53, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x54, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x55, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x56, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x57, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x58, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x59, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x60, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x61, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x62, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x63, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x64, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x65, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x66, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x67, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x68, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x69, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x70, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x71, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x72, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x73, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x74, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x75, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x76, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x77, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x78, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x79, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x82, (char)0xac, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, // not part of this charset - (char)0x3, (char)0xe2, (char)0x80, (char)0x9a, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, // not part of this charset - (char)0x3, (char)0xe2, (char)0x80, (char)0x9e, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa6, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa1, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, // not part of this charset - (char)0x3, (char)0xe2, (char)0x80, (char)0xb0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xa0, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xb9, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x9a, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xa4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xbd, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xb9, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, // not part of this charset - (char)0x3, (char)0xe2, (char)0x80, (char)0x98, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x99, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x9c, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x9d, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa2, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x93, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x94, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, // not part of this charset - (char)0x3, (char)0xe2, (char)0x84, (char)0xa2, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xa1, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xba, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x9b, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xa5, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xbe, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xba, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xcb, (char)0x87, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xcb, (char)0x98, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x81, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x84, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa6, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa8, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa9, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x9e, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xab, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xac, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xad, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xae, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xbb, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb1, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xcb, (char)0x9b, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x82, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb5, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb6, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb8, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x85, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x9f, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xbb, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0xbd, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xcb, (char)0x9d, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0xbe, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xbc, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x94, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x81, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x82, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x82, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x84, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0xb9, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x86, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x87, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x8c, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x89, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x98, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x8b, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x9a, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x8d, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x8e, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x8e, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x90, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x83, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x87, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x93, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x94, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x90, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x96, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x97, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x98, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xae, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x9a, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xb0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x9c, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x9d, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xa2, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x9f, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x95, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa1, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa2, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x83, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0xba, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x87, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x8d, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa9, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x99, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xab, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x9b, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xad, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xae, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x8f, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc4, (char)0x91, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x84, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x88, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb3, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x91, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb6, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x99, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xaf, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xba, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xb1, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xbc, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xbd, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xa3, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xcb, (char)0x99, (char)0x0, (char)0x0, (char)0x0 + 1, 0, 0, 0, 0, 0, + 1, 1, 0, 0, 0, 0, + 1, 2, 0, 0, 0, 0, + 1, 3, 0, 0, 0, 0, + 1, 4, 0, 0, 0, 0, + 1, 5, 0, 0, 0, 0, + 1, 6, 0, 0, 0, 0, + 1, 7, 0, 0, 0, 0, + 1, 8, 0, 0, 0, 0, + 1, 9, 0, 0, 0, 0, + 1, 10, 0, 0, 0, 0, + 1, 11, 0, 0, 0, 0, + 1, 12, 0, 0, 0, 0, + 1, 13, 0, 0, 0, 0, + 1, 14, 0, 0, 0, 0, + 1, 15, 0, 0, 0, 0, + 1, 16, 0, 0, 0, 0, + 1, 17, 0, 0, 0, 0, + 1, 18, 0, 0, 0, 0, + 1, 19, 0, 0, 0, 0, + 1, 20, 0, 0, 0, 0, + 1, 21, 0, 0, 0, 0, + 1, 22, 0, 0, 0, 0, + 1, 23, 0, 0, 0, 0, + 1, 24, 0, 0, 0, 0, + 1, 25, 0, 0, 0, 0, + 1, 26, 0, 0, 0, 0, + 1, 27, 0, 0, 0, 0, + 1, 28, 0, 0, 0, 0, + 1, 29, 0, 0, 0, 0, + 1, 30, 0, 0, 0, 0, + 1, 31, 0, 0, 0, 0, + 1, 32, 0, 0, 0, 0, + 1, 33, 0, 0, 0, 0, + 1, 34, 0, 0, 0, 0, + 1, 35, 0, 0, 0, 0, + 1, 36, 0, 0, 0, 0, + 1, 37, 0, 0, 0, 0, + 1, 38, 0, 0, 0, 0, + 1, 39, 0, 0, 0, 0, + 1, 40, 0, 0, 0, 0, + 1, 41, 0, 0, 0, 0, + 1, 42, 0, 0, 0, 0, + 1, 43, 0, 0, 0, 0, + 1, 44, 0, 0, 0, 0, + 1, 45, 0, 0, 0, 0, + 1, 46, 0, 0, 0, 0, + 1, 47, 0, 0, 0, 0, + 1, 48, 0, 0, 0, 0, + 1, 49, 0, 0, 0, 0, + 1, 50, 0, 0, 0, 0, + 1, 51, 0, 0, 0, 0, + 1, 52, 0, 0, 0, 0, + 1, 53, 0, 0, 0, 0, + 1, 54, 0, 0, 0, 0, + 1, 55, 0, 0, 0, 0, + 1, 56, 0, 0, 0, 0, + 1, 57, 0, 0, 0, 0, + 1, 58, 0, 0, 0, 0, + 1, 59, 0, 0, 0, 0, + 1, 60, 0, 0, 0, 0, + 1, 61, 0, 0, 0, 0, + 1, 62, 0, 0, 0, 0, + 1, 63, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 1, 65, 0, 0, 0, 0, + 1, 66, 0, 0, 0, 0, + 1, 67, 0, 0, 0, 0, + 1, 68, 0, 0, 0, 0, + 1, 69, 0, 0, 0, 0, + 1, 70, 0, 0, 0, 0, + 1, 71, 0, 0, 0, 0, + 1, 72, 0, 0, 0, 0, + 1, 73, 0, 0, 0, 0, + 1, 74, 0, 0, 0, 0, + 1, 75, 0, 0, 0, 0, + 1, 76, 0, 0, 0, 0, + 1, 77, 0, 0, 0, 0, + 1, 78, 0, 0, 0, 0, + 1, 79, 0, 0, 0, 0, + 1, 80, 0, 0, 0, 0, + 1, 81, 0, 0, 0, 0, + 1, 82, 0, 0, 0, 0, + 1, 83, 0, 0, 0, 0, + 1, 84, 0, 0, 0, 0, + 1, 85, 0, 0, 0, 0, + 1, 86, 0, 0, 0, 0, + 1, 87, 0, 0, 0, 0, + 1, 88, 0, 0, 0, 0, + 1, 89, 0, 0, 0, 0, + 1, 90, 0, 0, 0, 0, + 1, 91, 0, 0, 0, 0, + 1, 92, 0, 0, 0, 0, + 1, 93, 0, 0, 0, 0, + 1, 94, 0, 0, 0, 0, + 1, 95, 0, 0, 0, 0, + 1, 96, 0, 0, 0, 0, + 1, 97, 0, 0, 0, 0, + 1, 98, 0, 0, 0, 0, + 1, 99, 0, 0, 0, 0, + 1, 100, 0, 0, 0, 0, + 1, 101, 0, 0, 0, 0, + 1, 102, 0, 0, 0, 0, + 1, 103, 0, 0, 0, 0, + 1, 104, 0, 0, 0, 0, + 1, 105, 0, 0, 0, 0, + 1, 106, 0, 0, 0, 0, + 1, 107, 0, 0, 0, 0, + 1, 108, 0, 0, 0, 0, + 1, 109, 0, 0, 0, 0, + 1, 110, 0, 0, 0, 0, + 1, 111, 0, 0, 0, 0, + 1, 112, 0, 0, 0, 0, + 1, 113, 0, 0, 0, 0, + 1, 114, 0, 0, 0, 0, + 1, 115, 0, 0, 0, 0, + 1, 116, 0, 0, 0, 0, + 1, 117, 0, 0, 0, 0, + 1, 118, 0, 0, 0, 0, + 1, 119, 0, 0, 0, 0, + 1, 120, 0, 0, 0, 0, + 1, 121, 0, 0, 0, 0, + 1, 122, 0, 0, 0, 0, + 1, 123, 0, 0, 0, 0, + 1, 124, 0, 0, 0, 0, + 1, 125, 0, 0, 0, 0, + 1, 126, 0, 0, 0, 0, + 1, 127, 0, 0, 0, 0, + 3, -30, -126, -84, 0, 0, + 1, 32, 0, 0, 0, 0, // not part of this charset + 3, -30, -128, -102, 0, 0, + 1, 32, 0, 0, 0, 0, // not part of this charset + 3, -30, -128, -98, 0, 0, + 3, -30, -128, -90, 0, 0, + 3, -30, -128, -96, 0, 0, + 3, -30, -128, -95, 0, 0, + 1, 32, 0, 0, 0, 0, // not part of this charset + 3, -30, -128, -80, 0, 0, + 2, -59, -96, 0, 0, 0, + 3, -30, -128, -71, 0, 0, + 2, -59, -102, 0, 0, 0, + 2, -59, -92, 0, 0, 0, + 2, -59, -67, 0, 0, 0, + 2, -59, -71, 0, 0, 0, + 1, 32, 0, 0, 0, 0, // not part of this charset + 3, -30, -128, -104, 0, 0, + 3, -30, -128, -103, 0, 0, + 3, -30, -128, -100, 0, 0, + 3, -30, -128, -99, 0, 0, + 3, -30, -128, -94, 0, 0, + 3, -30, -128, -109, 0, 0, + 3, -30, -128, -108, 0, 0, + 1, 32, 0, 0, 0, 0, // not part of this charset + 3, -30, -124, -94, 0, 0, + 2, -59, -95, 0, 0, 0, + 3, -30, -128, -70, 0, 0, + 2, -59, -101, 0, 0, 0, + 2, -59, -91, 0, 0, 0, + 2, -59, -66, 0, 0, 0, + 2, -59, -70, 0, 0, 0, + 2, -62, -96, 0, 0, 0, + 2, -53, -121, 0, 0, 0, + 2, -53, -104, 0, 0, 0, + 2, -59, -127, 0, 0, 0, + 2, -62, -92, 0, 0, 0, + 2, -60, -124, 0, 0, 0, + 2, -62, -90, 0, 0, 0, + 2, -62, -89, 0, 0, 0, + 2, -62, -88, 0, 0, 0, + 2, -62, -87, 0, 0, 0, + 2, -59, -98, 0, 0, 0, + 2, -62, -85, 0, 0, 0, + 2, -62, -84, 0, 0, 0, + 2, -62, -83, 0, 0, 0, + 2, -62, -82, 0, 0, 0, + 2, -59, -69, 0, 0, 0, + 2, -62, -80, 0, 0, 0, + 2, -62, -79, 0, 0, 0, + 2, -53, -101, 0, 0, 0, + 2, -59, -126, 0, 0, 0, + 2, -62, -76, 0, 0, 0, + 2, -62, -75, 0, 0, 0, + 2, -62, -74, 0, 0, 0, + 2, -62, -73, 0, 0, 0, + 2, -62, -72, 0, 0, 0, + 2, -60, -123, 0, 0, 0, + 2, -59, -97, 0, 0, 0, + 2, -62, -69, 0, 0, 0, + 2, -60, -67, 0, 0, 0, + 2, -53, -99, 0, 0, 0, + 2, -60, -66, 0, 0, 0, + 2, -59, -68, 0, 0, 0, + 2, -59, -108, 0, 0, 0, + 2, -61, -127, 0, 0, 0, + 2, -61, -126, 0, 0, 0, + 2, -60, -126, 0, 0, 0, + 2, -61, -124, 0, 0, 0, + 2, -60, -71, 0, 0, 0, + 2, -60, -122, 0, 0, 0, + 2, -61, -121, 0, 0, 0, + 2, -60, -116, 0, 0, 0, + 2, -61, -119, 0, 0, 0, + 2, -60, -104, 0, 0, 0, + 2, -61, -117, 0, 0, 0, + 2, -60, -102, 0, 0, 0, + 2, -61, -115, 0, 0, 0, + 2, -61, -114, 0, 0, 0, + 2, -60, -114, 0, 0, 0, + 2, -60, -112, 0, 0, 0, + 2, -59, -125, 0, 0, 0, + 2, -59, -121, 0, 0, 0, + 2, -61, -109, 0, 0, 0, + 2, -61, -108, 0, 0, 0, + 2, -59, -112, 0, 0, 0, + 2, -61, -106, 0, 0, 0, + 2, -61, -105, 0, 0, 0, + 2, -59, -104, 0, 0, 0, + 2, -59, -82, 0, 0, 0, + 2, -61, -102, 0, 0, 0, + 2, -59, -80, 0, 0, 0, + 2, -61, -100, 0, 0, 0, + 2, -61, -99, 0, 0, 0, + 2, -59, -94, 0, 0, 0, + 2, -61, -97, 0, 0, 0, + 2, -59, -107, 0, 0, 0, + 2, -61, -95, 0, 0, 0, + 2, -61, -94, 0, 0, 0, + 2, -60, -125, 0, 0, 0, + 2, -61, -92, 0, 0, 0, + 2, -60, -70, 0, 0, 0, + 2, -60, -121, 0, 0, 0, + 2, -61, -89, 0, 0, 0, + 2, -60, -115, 0, 0, 0, + 2, -61, -87, 0, 0, 0, + 2, -60, -103, 0, 0, 0, + 2, -61, -85, 0, 0, 0, + 2, -60, -101, 0, 0, 0, + 2, -61, -83, 0, 0, 0, + 2, -61, -82, 0, 0, 0, + 2, -60, -113, 0, 0, 0, + 2, -60, -111, 0, 0, 0, + 2, -59, -124, 0, 0, 0, + 2, -59, -120, 0, 0, 0, + 2, -61, -77, 0, 0, 0, + 2, -61, -76, 0, 0, 0, + 2, -59, -111, 0, 0, 0, + 2, -61, -74, 0, 0, 0, + 2, -61, -73, 0, 0, 0, + 2, -59, -103, 0, 0, 0, + 2, -59, -81, 0, 0, 0, + 2, -61, -70, 0, 0, 0, + 2, -59, -79, 0, 0, 0, + 2, -61, -68, 0, 0, 0, + 2, -61, -67, 0, 0, 0, + 2, -59, -93, 0, 0, 0, + 2, -53, -103, 0, 0, 0 }; /// Cyrillic alphabet such as Russian, Bulgarian, Serbian Cyrillic /// and other languages static char windows_1251[] = { - (char)0x1, (char)0x0, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x8, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x9, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xa, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xb, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xc, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xd, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xe, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xf, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x10, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x11, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x12, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x13, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x14, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x15, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x16, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x17, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x18, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x19, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x21, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x22, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x23, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x24, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x25, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x26, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x27, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x28, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x29, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x30, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x31, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x32, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x33, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x34, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x35, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x36, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x37, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x38, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x39, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x40, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x41, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x42, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x43, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x44, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x45, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x46, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x47, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x48, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x49, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x50, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x51, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x52, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x53, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x54, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x55, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x56, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x57, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x58, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x59, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x60, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x61, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x62, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x63, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x64, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x65, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x66, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x67, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x68, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x69, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x70, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x71, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x72, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x73, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x74, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x75, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x76, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x77, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x78, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x79, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x82, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x83, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x9a, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x93, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x9e, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa6, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa1, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x82, (char)0xac, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xb0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x89, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xb9, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x8a, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x8c, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x8b, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x8f, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x92, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x98, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x99, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x9c, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x9d, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa2, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x93, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x94, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, // not part of this charset - (char)0x3, (char)0xe2, (char)0x84, (char)0xa2, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x99, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xba, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x9a, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x9c, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x9b, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x9f, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x8e, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x9e, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x88, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd2, (char)0x90, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa6, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x81, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa9, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x84, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xab, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xac, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xad, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xae, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x87, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb1, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x86, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x96, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd2, (char)0x91, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb5, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb6, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x91, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x84, (char)0x96, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x94, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xbb, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x98, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x85, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x95, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x97, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x90, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x91, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x92, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x93, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x94, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x95, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x96, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x97, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x98, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x99, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x9a, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x9b, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x9c, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x9d, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x9e, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0x9f, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xa0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xa1, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xa2, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xa3, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xa4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xa5, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xa6, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xa7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xa8, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xa9, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xaa, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xab, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xac, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xad, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xae, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xaf, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xb0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xb1, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xb2, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xb3, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xb4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xb5, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xb6, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xb7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xb8, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xb9, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xba, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xbb, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xbc, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xbd, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xbe, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd0, (char)0xbf, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x80, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x81, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x82, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x83, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x84, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x85, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x86, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x87, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x88, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x89, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x8a, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x8b, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x8c, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x8d, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x8e, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xd1, (char)0x8f, (char)0x0, (char)0x0, (char)0x0 + 1, 0, 0, 0, 0, 0, + 1, 1, 0, 0, 0, 0, + 1, 2, 0, 0, 0, 0, + 1, 3, 0, 0, 0, 0, + 1, 4, 0, 0, 0, 0, + 1, 5, 0, 0, 0, 0, + 1, 6, 0, 0, 0, 0, + 1, 7, 0, 0, 0, 0, + 1, 8, 0, 0, 0, 0, + 1, 9, 0, 0, 0, 0, + 1, 10, 0, 0, 0, 0, + 1, 11, 0, 0, 0, 0, + 1, 12, 0, 0, 0, 0, + 1, 13, 0, 0, 0, 0, + 1, 14, 0, 0, 0, 0, + 1, 15, 0, 0, 0, 0, + 1, 16, 0, 0, 0, 0, + 1, 17, 0, 0, 0, 0, + 1, 18, 0, 0, 0, 0, + 1, 19, 0, 0, 0, 0, + 1, 20, 0, 0, 0, 0, + 1, 21, 0, 0, 0, 0, + 1, 22, 0, 0, 0, 0, + 1, 23, 0, 0, 0, 0, + 1, 24, 0, 0, 0, 0, + 1, 25, 0, 0, 0, 0, + 1, 26, 0, 0, 0, 0, + 1, 27, 0, 0, 0, 0, + 1, 28, 0, 0, 0, 0, + 1, 29, 0, 0, 0, 0, + 1, 30, 0, 0, 0, 0, + 1, 31, 0, 0, 0, 0, + 1, 32, 0, 0, 0, 0, + 1, 33, 0, 0, 0, 0, + 1, 34, 0, 0, 0, 0, + 1, 35, 0, 0, 0, 0, + 1, 36, 0, 0, 0, 0, + 1, 37, 0, 0, 0, 0, + 1, 38, 0, 0, 0, 0, + 1, 39, 0, 0, 0, 0, + 1, 40, 0, 0, 0, 0, + 1, 41, 0, 0, 0, 0, + 1, 42, 0, 0, 0, 0, + 1, 43, 0, 0, 0, 0, + 1, 44, 0, 0, 0, 0, + 1, 45, 0, 0, 0, 0, + 1, 46, 0, 0, 0, 0, + 1, 47, 0, 0, 0, 0, + 1, 48, 0, 0, 0, 0, + 1, 49, 0, 0, 0, 0, + 1, 50, 0, 0, 0, 0, + 1, 51, 0, 0, 0, 0, + 1, 52, 0, 0, 0, 0, + 1, 53, 0, 0, 0, 0, + 1, 54, 0, 0, 0, 0, + 1, 55, 0, 0, 0, 0, + 1, 56, 0, 0, 0, 0, + 1, 57, 0, 0, 0, 0, + 1, 58, 0, 0, 0, 0, + 1, 59, 0, 0, 0, 0, + 1, 60, 0, 0, 0, 0, + 1, 61, 0, 0, 0, 0, + 1, 62, 0, 0, 0, 0, + 1, 63, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 1, 65, 0, 0, 0, 0, + 1, 66, 0, 0, 0, 0, + 1, 67, 0, 0, 0, 0, + 1, 68, 0, 0, 0, 0, + 1, 69, 0, 0, 0, 0, + 1, 70, 0, 0, 0, 0, + 1, 71, 0, 0, 0, 0, + 1, 72, 0, 0, 0, 0, + 1, 73, 0, 0, 0, 0, + 1, 74, 0, 0, 0, 0, + 1, 75, 0, 0, 0, 0, + 1, 76, 0, 0, 0, 0, + 1, 77, 0, 0, 0, 0, + 1, 78, 0, 0, 0, 0, + 1, 79, 0, 0, 0, 0, + 1, 80, 0, 0, 0, 0, + 1, 81, 0, 0, 0, 0, + 1, 82, 0, 0, 0, 0, + 1, 83, 0, 0, 0, 0, + 1, 84, 0, 0, 0, 0, + 1, 85, 0, 0, 0, 0, + 1, 86, 0, 0, 0, 0, + 1, 87, 0, 0, 0, 0, + 1, 88, 0, 0, 0, 0, + 1, 89, 0, 0, 0, 0, + 1, 90, 0, 0, 0, 0, + 1, 91, 0, 0, 0, 0, + 1, 92, 0, 0, 0, 0, + 1, 93, 0, 0, 0, 0, + 1, 94, 0, 0, 0, 0, + 1, 95, 0, 0, 0, 0, + 1, 96, 0, 0, 0, 0, + 1, 97, 0, 0, 0, 0, + 1, 98, 0, 0, 0, 0, + 1, 99, 0, 0, 0, 0, + 1, 100, 0, 0, 0, 0, + 1, 101, 0, 0, 0, 0, + 1, 102, 0, 0, 0, 0, + 1, 103, 0, 0, 0, 0, + 1, 104, 0, 0, 0, 0, + 1, 105, 0, 0, 0, 0, + 1, 106, 0, 0, 0, 0, + 1, 107, 0, 0, 0, 0, + 1, 108, 0, 0, 0, 0, + 1, 109, 0, 0, 0, 0, + 1, 110, 0, 0, 0, 0, + 1, 111, 0, 0, 0, 0, + 1, 112, 0, 0, 0, 0, + 1, 113, 0, 0, 0, 0, + 1, 114, 0, 0, 0, 0, + 1, 115, 0, 0, 0, 0, + 1, 116, 0, 0, 0, 0, + 1, 117, 0, 0, 0, 0, + 1, 118, 0, 0, 0, 0, + 1, 119, 0, 0, 0, 0, + 1, 120, 0, 0, 0, 0, + 1, 121, 0, 0, 0, 0, + 1, 122, 0, 0, 0, 0, + 1, 123, 0, 0, 0, 0, + 1, 124, 0, 0, 0, 0, + 1, 125, 0, 0, 0, 0, + 1, 126, 0, 0, 0, 0, + 1, 127, 0, 0, 0, 0, + 2, -48, -126, 0, 0, 0, + 2, -48, -125, 0, 0, 0, + 3, -30, -128, -102, 0, 0, + 2, -47, -109, 0, 0, 0, + 3, -30, -128, -98, 0, 0, + 3, -30, -128, -90, 0, 0, + 3, -30, -128, -96, 0, 0, + 3, -30, -128, -95, 0, 0, + 3, -30, -126, -84, 0, 0, + 3, -30, -128, -80, 0, 0, + 2, -48, -119, 0, 0, 0, + 3, -30, -128, -71, 0, 0, + 2, -48, -118, 0, 0, 0, + 2, -48, -116, 0, 0, 0, + 2, -48, -117, 0, 0, 0, + 2, -48, -113, 0, 0, 0, + 2, -47, -110, 0, 0, 0, + 3, -30, -128, -104, 0, 0, + 3, -30, -128, -103, 0, 0, + 3, -30, -128, -100, 0, 0, + 3, -30, -128, -99, 0, 0, + 3, -30, -128, -94, 0, 0, + 3, -30, -128, -109, 0, 0, + 3, -30, -128, -108, 0, 0, + 1, 32, 0, 0, 0, 0, // not part of this charset + 3, -30, -124, -94, 0, 0, + 2, -47, -103, 0, 0, 0, + 3, -30, -128, -70, 0, 0, + 2, -47, -102, 0, 0, 0, + 2, -47, -100, 0, 0, 0, + 2, -47, -101, 0, 0, 0, + 2, -47, -97, 0, 0, 0, + 2, -62, -96, 0, 0, 0, + 2, -48, -114, 0, 0, 0, + 2, -47, -98, 0, 0, 0, + 2, -48, -120, 0, 0, 0, + 2, -62, -92, 0, 0, 0, + 2, -46, -112, 0, 0, 0, + 2, -62, -90, 0, 0, 0, + 2, -62, -89, 0, 0, 0, + 2, -48, -127, 0, 0, 0, + 2, -62, -87, 0, 0, 0, + 2, -48, -124, 0, 0, 0, + 2, -62, -85, 0, 0, 0, + 2, -62, -84, 0, 0, 0, + 2, -62, -83, 0, 0, 0, + 2, -62, -82, 0, 0, 0, + 2, -48, -121, 0, 0, 0, + 2, -62, -80, 0, 0, 0, + 2, -62, -79, 0, 0, 0, + 2, -48, -122, 0, 0, 0, + 2, -47, -106, 0, 0, 0, + 2, -46, -111, 0, 0, 0, + 2, -62, -75, 0, 0, 0, + 2, -62, -74, 0, 0, 0, + 2, -62, -73, 0, 0, 0, + 2, -47, -111, 0, 0, 0, + 3, -30, -124, -106, 0, 0, + 2, -47, -108, 0, 0, 0, + 2, -62, -69, 0, 0, 0, + 2, -47, -104, 0, 0, 0, + 2, -48, -123, 0, 0, 0, + 2, -47, -107, 0, 0, 0, + 2, -47, -105, 0, 0, 0, + 2, -48, -112, 0, 0, 0, + 2, -48, -111, 0, 0, 0, + 2, -48, -110, 0, 0, 0, + 2, -48, -109, 0, 0, 0, + 2, -48, -108, 0, 0, 0, + 2, -48, -107, 0, 0, 0, + 2, -48, -106, 0, 0, 0, + 2, -48, -105, 0, 0, 0, + 2, -48, -104, 0, 0, 0, + 2, -48, -103, 0, 0, 0, + 2, -48, -102, 0, 0, 0, + 2, -48, -101, 0, 0, 0, + 2, -48, -100, 0, 0, 0, + 2, -48, -99, 0, 0, 0, + 2, -48, -98, 0, 0, 0, + 2, -48, -97, 0, 0, 0, + 2, -48, -96, 0, 0, 0, + 2, -48, -95, 0, 0, 0, + 2, -48, -94, 0, 0, 0, + 2, -48, -93, 0, 0, 0, + 2, -48, -92, 0, 0, 0, + 2, -48, -91, 0, 0, 0, + 2, -48, -90, 0, 0, 0, + 2, -48, -89, 0, 0, 0, + 2, -48, -88, 0, 0, 0, + 2, -48, -87, 0, 0, 0, + 2, -48, -86, 0, 0, 0, + 2, -48, -85, 0, 0, 0, + 2, -48, -84, 0, 0, 0, + 2, -48, -83, 0, 0, 0, + 2, -48, -82, 0, 0, 0, + 2, -48, -81, 0, 0, 0, + 2, -48, -80, 0, 0, 0, + 2, -48, -79, 0, 0, 0, + 2, -48, -78, 0, 0, 0, + 2, -48, -77, 0, 0, 0, + 2, -48, -76, 0, 0, 0, + 2, -48, -75, 0, 0, 0, + 2, -48, -74, 0, 0, 0, + 2, -48, -73, 0, 0, 0, + 2, -48, -72, 0, 0, 0, + 2, -48, -71, 0, 0, 0, + 2, -48, -70, 0, 0, 0, + 2, -48, -69, 0, 0, 0, + 2, -48, -68, 0, 0, 0, + 2, -48, -67, 0, 0, 0, + 2, -48, -66, 0, 0, 0, + 2, -48, -65, 0, 0, 0, + 2, -47, -128, 0, 0, 0, + 2, -47, -127, 0, 0, 0, + 2, -47, -126, 0, 0, 0, + 2, -47, -125, 0, 0, 0, + 2, -47, -124, 0, 0, 0, + 2, -47, -123, 0, 0, 0, + 2, -47, -122, 0, 0, 0, + 2, -47, -121, 0, 0, 0, + 2, -47, -120, 0, 0, 0, + 2, -47, -119, 0, 0, 0, + 2, -47, -118, 0, 0, 0, + 2, -47, -117, 0, 0, 0, + 2, -47, -116, 0, 0, 0, + 2, -47, -115, 0, 0, 0, + 2, -47, -114, 0, 0, 0, + 2, -47, -113, 0, 0, 0 }; /// Latin alphabet used by English and some other Western languages static char windows_1252[] = { - (char)0x1, (char)0x0, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x8, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x9, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xa, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xb, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xc, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xd, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xe, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0xf, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x10, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x11, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x12, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x13, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x14, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x15, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x16, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x17, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x18, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x19, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x1f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x21, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x22, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x23, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x24, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x25, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x26, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x27, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x28, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x29, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x2f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x30, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x31, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x32, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x33, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x34, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x35, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x36, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x37, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x38, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x39, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x3f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x40, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x41, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x42, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x43, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x44, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x45, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x46, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x47, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x48, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x49, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x4f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x50, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x51, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x52, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x53, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x54, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x55, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x56, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x57, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x58, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x59, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x5f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x60, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x61, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x62, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x63, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x64, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x65, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x66, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x67, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x68, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x69, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x6f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x70, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x71, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x72, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x73, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x74, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x75, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x76, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x77, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x78, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x79, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7a, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7b, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7c, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7d, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7e, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x7f, (char)0x0, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x82, (char)0xac, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, // not part of this charset - (char)0x3, (char)0xe2, (char)0x80, (char)0x9a, (char)0x0, (char)0x0, - (char)0x2, (char)0xc6, (char)0x92, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x9e, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa6, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa1, (char)0x0, (char)0x0, - (char)0x2, (char)0xcb, (char)0x86, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xb0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xa0, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xb9, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x92, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, // not part of this charset - (char)0x2, (char)0xc5, (char)0xbd, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, // not part of this charset - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, // not part of this charset - (char)0x3, (char)0xe2, (char)0x80, (char)0x98, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x99, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x9c, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x9d, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xa2, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x93, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0x94, (char)0x0, (char)0x0, - (char)0x2, (char)0xcb, (char)0x9c, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x84, (char)0xa2, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xa1, (char)0x0, (char)0x0, (char)0x0, - (char)0x3, (char)0xe2, (char)0x80, (char)0xba, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0x93, (char)0x0, (char)0x0, (char)0x0, - (char)0x1, (char)0x20, (char)0x0, (char)0x0, (char)0x0, (char)0x0, // not part of this charset - (char)0x2, (char)0xc5, (char)0xbe, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc5, (char)0xb8, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa1, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa2, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa3, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa5, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa6, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa8, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xa9, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xaa, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xab, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xac, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xad, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xae, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xaf, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb1, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb2, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb3, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb5, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb6, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb8, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xb9, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xba, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xbb, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xbc, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xbd, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xbe, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc2, (char)0xbf, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x80, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x81, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x82, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x83, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x84, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x85, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x86, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x87, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x88, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x89, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x8a, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x8b, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x8c, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x8d, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x8e, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x8f, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x90, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x91, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x92, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x93, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x94, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x95, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x96, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x97, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x98, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x99, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x9a, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x9b, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x9c, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x9d, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x9e, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0x9f, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa1, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa2, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa3, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa5, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa6, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa8, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xa9, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xaa, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xab, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xac, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xad, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xae, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xaf, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb0, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb1, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb2, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb3, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb4, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb5, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb6, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb7, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb8, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xb9, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xba, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xbb, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xbc, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xbd, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xbe, (char)0x0, (char)0x0, (char)0x0, - (char)0x2, (char)0xc3, (char)0xbf, (char)0x0, (char)0x0, (char)0x0 + 1, 0, 0, 0, 0, 0, + 1, 1, 0, 0, 0, 0, + 1, 2, 0, 0, 0, 0, + 1, 3, 0, 0, 0, 0, + 1, 4, 0, 0, 0, 0, + 1, 5, 0, 0, 0, 0, + 1, 6, 0, 0, 0, 0, + 1, 7, 0, 0, 0, 0, + 1, 8, 0, 0, 0, 0, + 1, 9, 0, 0, 0, 0, + 1, 10, 0, 0, 0, 0, + 1, 11, 0, 0, 0, 0, + 1, 12, 0, 0, 0, 0, + 1, 13, 0, 0, 0, 0, + 1, 14, 0, 0, 0, 0, + 1, 15, 0, 0, 0, 0, + 1, 16, 0, 0, 0, 0, + 1, 17, 0, 0, 0, 0, + 1, 18, 0, 0, 0, 0, + 1, 19, 0, 0, 0, 0, + 1, 20, 0, 0, 0, 0, + 1, 21, 0, 0, 0, 0, + 1, 22, 0, 0, 0, 0, + 1, 23, 0, 0, 0, 0, + 1, 24, 0, 0, 0, 0, + 1, 25, 0, 0, 0, 0, + 1, 26, 0, 0, 0, 0, + 1, 27, 0, 0, 0, 0, + 1, 28, 0, 0, 0, 0, + 1, 29, 0, 0, 0, 0, + 1, 30, 0, 0, 0, 0, + 1, 31, 0, 0, 0, 0, + 1, 32, 0, 0, 0, 0, + 1, 33, 0, 0, 0, 0, + 1, 34, 0, 0, 0, 0, + 1, 35, 0, 0, 0, 0, + 1, 36, 0, 0, 0, 0, + 1, 37, 0, 0, 0, 0, + 1, 38, 0, 0, 0, 0, + 1, 39, 0, 0, 0, 0, + 1, 40, 0, 0, 0, 0, + 1, 41, 0, 0, 0, 0, + 1, 42, 0, 0, 0, 0, + 1, 43, 0, 0, 0, 0, + 1, 44, 0, 0, 0, 0, + 1, 45, 0, 0, 0, 0, + 1, 46, 0, 0, 0, 0, + 1, 47, 0, 0, 0, 0, + 1, 48, 0, 0, 0, 0, + 1, 49, 0, 0, 0, 0, + 1, 50, 0, 0, 0, 0, + 1, 51, 0, 0, 0, 0, + 1, 52, 0, 0, 0, 0, + 1, 53, 0, 0, 0, 0, + 1, 54, 0, 0, 0, 0, + 1, 55, 0, 0, 0, 0, + 1, 56, 0, 0, 0, 0, + 1, 57, 0, 0, 0, 0, + 1, 58, 0, 0, 0, 0, + 1, 59, 0, 0, 0, 0, + 1, 60, 0, 0, 0, 0, + 1, 61, 0, 0, 0, 0, + 1, 62, 0, 0, 0, 0, + 1, 63, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 1, 65, 0, 0, 0, 0, + 1, 66, 0, 0, 0, 0, + 1, 67, 0, 0, 0, 0, + 1, 68, 0, 0, 0, 0, + 1, 69, 0, 0, 0, 0, + 1, 70, 0, 0, 0, 0, + 1, 71, 0, 0, 0, 0, + 1, 72, 0, 0, 0, 0, + 1, 73, 0, 0, 0, 0, + 1, 74, 0, 0, 0, 0, + 1, 75, 0, 0, 0, 0, + 1, 76, 0, 0, 0, 0, + 1, 77, 0, 0, 0, 0, + 1, 78, 0, 0, 0, 0, + 1, 79, 0, 0, 0, 0, + 1, 80, 0, 0, 0, 0, + 1, 81, 0, 0, 0, 0, + 1, 82, 0, 0, 0, 0, + 1, 83, 0, 0, 0, 0, + 1, 84, 0, 0, 0, 0, + 1, 85, 0, 0, 0, 0, + 1, 86, 0, 0, 0, 0, + 1, 87, 0, 0, 0, 0, + 1, 88, 0, 0, 0, 0, + 1, 89, 0, 0, 0, 0, + 1, 90, 0, 0, 0, 0, + 1, 91, 0, 0, 0, 0, + 1, 92, 0, 0, 0, 0, + 1, 93, 0, 0, 0, 0, + 1, 94, 0, 0, 0, 0, + 1, 95, 0, 0, 0, 0, + 1, 96, 0, 0, 0, 0, + 1, 97, 0, 0, 0, 0, + 1, 98, 0, 0, 0, 0, + 1, 99, 0, 0, 0, 0, + 1, 100, 0, 0, 0, 0, + 1, 101, 0, 0, 0, 0, + 1, 102, 0, 0, 0, 0, + 1, 103, 0, 0, 0, 0, + 1, 104, 0, 0, 0, 0, + 1, 105, 0, 0, 0, 0, + 1, 106, 0, 0, 0, 0, + 1, 107, 0, 0, 0, 0, + 1, 108, 0, 0, 0, 0, + 1, 109, 0, 0, 0, 0, + 1, 110, 0, 0, 0, 0, + 1, 111, 0, 0, 0, 0, + 1, 112, 0, 0, 0, 0, + 1, 113, 0, 0, 0, 0, + 1, 114, 0, 0, 0, 0, + 1, 115, 0, 0, 0, 0, + 1, 116, 0, 0, 0, 0, + 1, 117, 0, 0, 0, 0, + 1, 118, 0, 0, 0, 0, + 1, 119, 0, 0, 0, 0, + 1, 120, 0, 0, 0, 0, + 1, 121, 0, 0, 0, 0, + 1, 122, 0, 0, 0, 0, + 1, 123, 0, 0, 0, 0, + 1, 124, 0, 0, 0, 0, + 1, 125, 0, 0, 0, 0, + 1, 126, 0, 0, 0, 0, + 1, 127, 0, 0, 0, 0, + 3, -30, -126, -84, 0, 0, + 1, 32, 0, 0, 0, 0, // not part of this charset + 3, -30, -128, -102, 0, 0, + 2, -58, -110, 0, 0, 0, + 3, -30, -128, -98, 0, 0, + 3, -30, -128, -90, 0, 0, + 3, -30, -128, -96, 0, 0, + 3, -30, -128, -95, 0, 0, + 2, -53, -122, 0, 0, 0, + 3, -30, -128, -80, 0, 0, + 2, -59, -96, 0, 0, 0, + 3, -30, -128, -71, 0, 0, + 2, -59, -110, 0, 0, 0, + 1, 32, 0, 0, 0, 0, // not part of this charset + 2, -59, -67, 0, 0, 0, + 1, 32, 0, 0, 0, 0, // not part of this charset + 1, 32, 0, 0, 0, 0, // not part of this charset + 3, -30, -128, -104, 0, 0, + 3, -30, -128, -103, 0, 0, + 3, -30, -128, -100, 0, 0, + 3, -30, -128, -99, 0, 0, + 3, -30, -128, -94, 0, 0, + 3, -30, -128, -109, 0, 0, + 3, -30, -128, -108, 0, 0, + 2, -53, -100, 0, 0, 0, + 3, -30, -124, -94, 0, 0, + 2, -59, -95, 0, 0, 0, + 3, -30, -128, -70, 0, 0, + 2, -59, -109, 0, 0, 0, + 1, 32, 0, 0, 0, 0, // not part of this charset + 2, -59, -66, 0, 0, 0, + 2, -59, -72, 0, 0, 0, + 2, -62, -96, 0, 0, 0, + 2, -62, -95, 0, 0, 0, + 2, -62, -94, 0, 0, 0, + 2, -62, -93, 0, 0, 0, + 2, -62, -92, 0, 0, 0, + 2, -62, -91, 0, 0, 0, + 2, -62, -90, 0, 0, 0, + 2, -62, -89, 0, 0, 0, + 2, -62, -88, 0, 0, 0, + 2, -62, -87, 0, 0, 0, + 2, -62, -86, 0, 0, 0, + 2, -62, -85, 0, 0, 0, + 2, -62, -84, 0, 0, 0, + 2, -62, -83, 0, 0, 0, + 2, -62, -82, 0, 0, 0, + 2, -62, -81, 0, 0, 0, + 2, -62, -80, 0, 0, 0, + 2, -62, -79, 0, 0, 0, + 2, -62, -78, 0, 0, 0, + 2, -62, -77, 0, 0, 0, + 2, -62, -76, 0, 0, 0, + 2, -62, -75, 0, 0, 0, + 2, -62, -74, 0, 0, 0, + 2, -62, -73, 0, 0, 0, + 2, -62, -72, 0, 0, 0, + 2, -62, -71, 0, 0, 0, + 2, -62, -70, 0, 0, 0, + 2, -62, -69, 0, 0, 0, + 2, -62, -68, 0, 0, 0, + 2, -62, -67, 0, 0, 0, + 2, -62, -66, 0, 0, 0, + 2, -62, -65, 0, 0, 0, + 2, -61, -128, 0, 0, 0, + 2, -61, -127, 0, 0, 0, + 2, -61, -126, 0, 0, 0, + 2, -61, -125, 0, 0, 0, + 2, -61, -124, 0, 0, 0, + 2, -61, -123, 0, 0, 0, + 2, -61, -122, 0, 0, 0, + 2, -61, -121, 0, 0, 0, + 2, -61, -120, 0, 0, 0, + 2, -61, -119, 0, 0, 0, + 2, -61, -118, 0, 0, 0, + 2, -61, -117, 0, 0, 0, + 2, -61, -116, 0, 0, 0, + 2, -61, -115, 0, 0, 0, + 2, -61, -114, 0, 0, 0, + 2, -61, -113, 0, 0, 0, + 2, -61, -112, 0, 0, 0, + 2, -61, -111, 0, 0, 0, + 2, -61, -110, 0, 0, 0, + 2, -61, -109, 0, 0, 0, + 2, -61, -108, 0, 0, 0, + 2, -61, -107, 0, 0, 0, + 2, -61, -106, 0, 0, 0, + 2, -61, -105, 0, 0, 0, + 2, -61, -104, 0, 0, 0, + 2, -61, -103, 0, 0, 0, + 2, -61, -102, 0, 0, 0, + 2, -61, -101, 0, 0, 0, + 2, -61, -100, 0, 0, 0, + 2, -61, -99, 0, 0, 0, + 2, -61, -98, 0, 0, 0, + 2, -61, -97, 0, 0, 0, + 2, -61, -96, 0, 0, 0, + 2, -61, -95, 0, 0, 0, + 2, -61, -94, 0, 0, 0, + 2, -61, -93, 0, 0, 0, + 2, -61, -92, 0, 0, 0, + 2, -61, -91, 0, 0, 0, + 2, -61, -90, 0, 0, 0, + 2, -61, -89, 0, 0, 0, + 2, -61, -88, 0, 0, 0, + 2, -61, -87, 0, 0, 0, + 2, -61, -86, 0, 0, 0, + 2, -61, -85, 0, 0, 0, + 2, -61, -84, 0, 0, 0, + 2, -61, -83, 0, 0, 0, + 2, -61, -82, 0, 0, 0, + 2, -61, -81, 0, 0, 0, + 2, -61, -80, 0, 0, 0, + 2, -61, -79, 0, 0, 0, + 2, -61, -78, 0, 0, 0, + 2, -61, -77, 0, 0, 0, + 2, -61, -76, 0, 0, 0, + 2, -61, -75, 0, 0, 0, + 2, -61, -74, 0, 0, 0, + 2, -61, -73, 0, 0, 0, + 2, -61, -72, 0, 0, 0, + 2, -61, -71, 0, 0, 0, + 2, -61, -70, 0, 0, 0, + 2, -61, -69, 0, 0, 0, + 2, -61, -68, 0, 0, 0, + 2, -61, -67, 0, 0, 0, + 2, -61, -66, 0, 0, 0, + 2, -61, -65, 0, 0, 0 }; } From b7697a62adcbf5df4fa1d23e35292b4330719a18 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Wed, 29 Aug 2012 18:35:39 -0400 Subject: [PATCH 25/84] Position set back to zero --- libs/openengine/bullet/pmove.cpp | 2 +- libs/openengine/bullet/pmove.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/libs/openengine/bullet/pmove.cpp b/libs/openengine/bullet/pmove.cpp index 32a11179fb..3d2462ab5b 100644 --- a/libs/openengine/bullet/pmove.cpp +++ b/libs/openengine/bullet/pmove.cpp @@ -301,7 +301,7 @@ bool PM_SlideMove( bool gravity ) if(planes[i].x >= .70) { - pm->ps.velocity = Ogre::Vector3(0,0,0); + pm->ps.velocity.z = 0; return true; } // see how hard we are hitting things diff --git a/libs/openengine/bullet/pmove.h b/libs/openengine/bullet/pmove.h index a0fec3d1c8..aa10a6bff5 100644 --- a/libs/openengine/bullet/pmove.h +++ b/libs/openengine/bullet/pmove.h @@ -92,7 +92,7 @@ struct playerMove { playerStruct() : gravity(800.0f), speed(480.0f), pmove_framecount(20), groundEntityNum(ENTITYNUM_NONE), commandTime(40), move_type(PM_NOCLIP), pm_time(0), snappingImplemented(true), bSnap(false), counter(-1) { - origin = Ogre::Vector3(733.164f,900.0f, 839.432f); + origin = Ogre::Vector3(0.0f, 0.0f, 0.0f); velocity = Ogre::Vector3(0.0f, 0.0f, 0.0f); viewangles = Ogre::Vector3(0.0f, 0.0f, 0.0f); From 3c3737ed78a81d05a0243687a12a1089d80c2994 Mon Sep 17 00:00:00 2001 From: Michael Mc Donnell Date: Wed, 29 Aug 2012 19:38:33 -0400 Subject: [PATCH 26/84] Write error message for exception and fix warning Provides details of what went wrong when reading the .esp and also fixes a warning on vs2010. --- apps/launcher/datafilespage.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/apps/launcher/datafilespage.cpp b/apps/launcher/datafilespage.cpp index 8545be835f..7ff2ce44c5 100644 --- a/apps/launcher/datafilespage.cpp +++ b/apps/launcher/datafilespage.cpp @@ -351,6 +351,7 @@ bool DataFilesPage::setupDataFiles() } catch(std::runtime_error &e) { // An error occurred while reading the .esp + std::cerr << "Error reading .esp: " << e.what() << std::endl; continue; } } From fa9f2b268b0869b3203789098a3226ef2de1c9fe Mon Sep 17 00:00:00 2001 From: gugus Date: Sun, 2 Sep 2012 17:57:03 +0200 Subject: [PATCH 27/84] PlaceItem,PlaceItemCell,PlaceAtPC,PlaceAtMe --- apps/openmw/mwbase/world.hpp | 3 + .../mwscript/transformationextensions.cpp | 209 +++++++++++++++++- 2 files changed, 208 insertions(+), 4 deletions(-) diff --git a/apps/openmw/mwbase/world.hpp b/apps/openmw/mwbase/world.hpp index 8b809d399a..b0ce261f1e 100644 --- a/apps/openmw/mwbase/world.hpp +++ b/apps/openmw/mwbase/world.hpp @@ -122,6 +122,9 @@ namespace MWBase virtual MWWorld::Ptr getPtrViaHandle (const std::string& handle) = 0; ///< Return a pointer to a liveCellRef with the given Ogre handle. + virtual void + copyObjectToCell(const MWWorld::Ptr &ptr, MWWorld::CellStore &cell, const ESM::Position &pos) = 0; + /// \todo enable reference in the OGRE scene virtual void enable (const MWWorld::Ptr& ptr) = 0; diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 18054374c0..c82108f8bb 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -16,6 +16,11 @@ #include "ref.hpp" #include "OgreSceneNode.h" + +#include "../mwworld/player.hpp" +#include "components\esm\loadcell.hpp" + +#include "OgreMath.h" namespace MWScript { namespace Transformation @@ -256,11 +261,13 @@ namespace MWScript } catch(std::exception &e) { - /*const ESM::Cell* cell = MWBase::Environment::get().getWorld()->getExterior(cellID); + const ESM::Cell* cell = MWBase::Environment::get().getWorld()->getExterior(cellID); if(cell) { - store = MWBase::Environment::get().getWorld()->getExterior(cell->getGridX(),cell->getGridY()); - }*/ + int cx,cy; + MWBase::Environment::get().getWorld()->positionToIndex(x,y,cx,cy); + store = MWBase::Environment::get().getWorld()->getExterior(cx,cy); + } } if(store) { @@ -273,7 +280,7 @@ namespace MWScript ay = ay/60.; zRot = zRot/60.; } - //MWBase::Environment::get().getWorld()->rotateObject(ptr,ax,ay,zRot); + MWBase::Environment::get().getWorld()->rotateObject(ptr,ax,ay,zRot); } else { @@ -315,6 +322,185 @@ namespace MWScript } }; + template + class OpPlaceItemCell : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + //MWWorld::Ptr ptr = R()(runtime); + + std::string itemID = runtime.getStringLiteral (runtime[0].mInteger); + runtime.pop(); + std::string cellID = runtime.getStringLiteral (runtime[0].mInteger); + runtime.pop(); + + Interpreter::Type_Float x = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float y = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float z = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float zRot = runtime[0].mFloat; + runtime.pop(); + + MWWorld::CellStore* store = 0; + try + { + store = MWBase::Environment::get().getWorld()->getInterior(cellID); + } + catch(std::exception &e) + { + const ESM::Cell* cell = MWBase::Environment::get().getWorld()->getExterior(cellID); + if(cell) + { + int cx,cy; + MWBase::Environment::get().getWorld()->positionToIndex(x,y,cx,cy); + store = MWBase::Environment::get().getWorld()->getExterior(cx,cy); + } + } + if(store) + { + ESM::Position pos; + pos.pos[0] = x; + pos.pos[1] = y; + pos.pos[2] = z; + pos.rot[0] = pos.rot[1] = 0; + pos.rot[2] = zRot; + MWWorld::Ptr ptr = MWBase::Environment::get().getWorld()->getPtr(itemID,false); + MWBase::Environment::get().getWorld()->copyObjectToCell(ptr,*store,pos); + } + else + { + throw std::runtime_error ("unknown cell"); + } + } + }; + + template + class OpPlaceItem : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + //MWWorld::Ptr ptr = R()(runtime); + + std::string itemID = runtime.getStringLiteral (runtime[0].mInteger); + runtime.pop(); + + Interpreter::Type_Float x = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float y = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float z = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Float zRot = runtime[0].mFloat; + runtime.pop(); + + MWWorld::CellStore* store = 0; + int cx,cy; + MWBase::Environment::get().getWorld()->positionToIndex(x,y,cx,cy); + store = MWBase::Environment::get().getWorld()->getExterior(cx,cy); + if(store) + { + ESM::Position pos; + pos.pos[0] = x; + pos.pos[1] = y; + pos.pos[2] = z; + pos.rot[0] = pos.rot[1] = 0; + pos.rot[2] = zRot; + MWWorld::Ptr ptr = MWBase::Environment::get().getWorld()->getPtr(itemID,false); + MWBase::Environment::get().getWorld()->copyObjectToCell(ptr,*store,pos); + } + else + { + throw std::runtime_error ("unknown cell"); + } + } + }; + + template + class OpPlaceAtPc : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + std::string itemID = runtime.getStringLiteral (runtime[0].mInteger); + runtime.pop(); + + Interpreter::Type_Integer count = runtime[0].mInteger; + runtime.pop(); + Interpreter::Type_Float distance = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Integer direction = runtime[0].mInteger; + runtime.pop(); + + ESM::Position ipos = MWBase::Environment::get().getWorld()->getPlayer().getPlayer().getRefData().getPosition(); + Ogre::Vector3 pos(ipos.pos[0],ipos.pos[1],ipos.pos[2]); + Ogre::Quaternion rot(Ogre::Radian(ipos.rot[2]), Ogre::Vector3::UNIT_Z); + if(direction == 0) pos = pos + distance*rot.yAxis(); + else if(direction == 1) pos = pos - distance*rot.yAxis(); + else if(direction == 2) pos = pos - distance*rot.xAxis(); + else if(direction == 3) pos = pos + distance*rot.xAxis(); + else throw std::runtime_error ("direction must be 0,1,2 or 3"); + + ipos.pos[0] = pos.x; + ipos.pos[1] = pos.y; + ipos.pos[2] = pos.z; + MWWorld::CellStore* store = MWBase::Environment::get().getWorld()->getPlayer().getPlayer().getCell(); + MWWorld::Ptr ptr = MWBase::Environment::get().getWorld()->getPtr(itemID,false); + int icount = ptr.getRefData().getCount(); + ptr.getRefData().setCount(count); + MWBase::Environment::get().getWorld()->copyObjectToCell(ptr,*store,ipos); + ptr.getRefData().setCount(icount); + //store->ge + } + }; + + template + class OpPlaceAtMe : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + MWWorld::Ptr me = R()(runtime); + + std::string itemID = runtime.getStringLiteral (runtime[0].mInteger); + runtime.pop(); + + Interpreter::Type_Integer count = runtime[0].mInteger; + runtime.pop(); + Interpreter::Type_Float distance = runtime[0].mFloat; + runtime.pop(); + Interpreter::Type_Integer direction = runtime[0].mInteger; + runtime.pop(); + + ESM::Position ipos = me.getRefData().getPosition(); + Ogre::Vector3 pos(ipos.pos[0],ipos.pos[1],ipos.pos[2]); + Ogre::Quaternion rot(Ogre::Radian(ipos.rot[2]), Ogre::Vector3::UNIT_Z); + if(direction == 0) pos = pos + distance*rot.yAxis(); + else if(direction == 1) pos = pos - distance*rot.yAxis(); + else if(direction == 2) pos = pos - distance*rot.xAxis(); + else if(direction == 3) pos = pos + distance*rot.xAxis(); + else throw std::runtime_error ("direction must be 0,1,2 or 3"); + + ipos.pos[0] = pos.x; + ipos.pos[1] = pos.y; + ipos.pos[2] = pos.z; + MWWorld::CellStore* store = me.getCell(); + MWWorld::Ptr ptr = MWBase::Environment::get().getWorld()->getPtr(itemID,false); + int icount = ptr.getRefData().getCount(); + ptr.getRefData().setCount(count); + MWBase::Environment::get().getWorld()->copyObjectToCell(ptr,*store,ipos); + ptr.getRefData().setCount(icount); + //store->ge + } + }; + const int opcodeSetScale = 0x2000164; const int opcodeSetScaleExplicit = 0x2000165; const int opcodeSetAngle = 0x2000166; @@ -334,6 +520,12 @@ namespace MWScript const int opcodePositionCell = 0x2000174; const int opcodePositionCellExplicit = 0x2000175; + const int opcodePlaceItemCell = 0x2000176; + const int opcodePlaceItem = 0x2000177; + const int opcodePlaceAtPc = 0x2000178; + const int opcodePlaceAtMe = 0x2000179; + const int opcodePlaceAtMeExplicit = 0x200017a; + void registerExtensions (Compiler::Extensions& extensions) { extensions.registerInstruction("setscale","f",opcodeSetScale,opcodeSetScaleExplicit); @@ -345,6 +537,10 @@ namespace MWScript extensions.registerFunction("getstartingpos",'f',"c",opcodeGetStartingPos,opcodeGetStartingPosExplicit); extensions.registerInstruction("position","ffff",opcodePosition,opcodePositionExplicit); extensions.registerInstruction("positioncell","ffffS",opcodePositionCell,opcodePositionCellExplicit); + extensions.registerInstruction("placeitemcell","ccffff",opcodePlaceItemCell); + extensions.registerInstruction("placeitem","cffff",opcodePlaceItem); + extensions.registerInstruction("placeatpc","clfl",opcodePlaceAtPc); + extensions.registerInstruction("placeatme","clfl",opcodePlaceAtMe,opcodePlaceAtMeExplicit); } void installOpcodes (Interpreter::Interpreter& interpreter) @@ -367,6 +563,11 @@ namespace MWScript interpreter.installSegment5(opcodePositionExplicit,new OpPosition); interpreter.installSegment5(opcodePositionCell,new OpPositionCell); interpreter.installSegment5(opcodePositionCellExplicit,new OpPositionCell); + interpreter.installSegment5(opcodePlaceItemCell,new OpPlaceItemCell); + interpreter.installSegment5(opcodePlaceItem,new OpPlaceItem); + interpreter.installSegment5(opcodePlaceAtPc,new OpPlaceAtPc); + interpreter.installSegment5(opcodePlaceAtMe,new OpPlaceAtPc); + interpreter.installSegment5(opcodePlaceAtMeExplicit,new OpPlaceAtPc); } } } From 99885e8ca411ff4e06fd8c77c64fda722301610f Mon Sep 17 00:00:00 2001 From: gugus Date: Sun, 2 Sep 2012 18:04:36 +0200 Subject: [PATCH 28/84] Revert "fix a bug with case sensitivity: when searching for a cell which is already loaded,but with another case, the cell get loaded twice, which is bad :p" This reverts commit 165065d37891be204f67f9cc89de3780a0982b92. --- apps/openmw/mwworld/cells.cpp | 18 +++--------------- 1 file changed, 3 insertions(+), 15 deletions(-) diff --git a/apps/openmw/mwworld/cells.cpp b/apps/openmw/mwworld/cells.cpp index dd2339eeb5..822aa78d6e 100644 --- a/apps/openmw/mwworld/cells.cpp +++ b/apps/openmw/mwworld/cells.cpp @@ -8,17 +8,6 @@ #include "class.hpp" #include "containerstore.hpp" -//helper function -std::string toLower (const std::string& name) -{ - std::string lowerCase; - - std::transform (name.begin(), name.end(), std::back_inserter (lowerCase), - (int(*)(int)) std::tolower); - - return lowerCase; -} - MWWorld::Ptr::CellStore *MWWorld::Cells::getCellStore (const ESM::Cell *cell) { if (cell->data.flags & ESM::Cell::Interior) @@ -140,14 +129,13 @@ MWWorld::Ptr::CellStore *MWWorld::Cells::getExterior (int x, int y) MWWorld::Ptr::CellStore *MWWorld::Cells::getInterior (const std::string& name) { - std::string nName = toLower(name); - std::map::iterator result = mInteriors.find (nName); + std::map::iterator result = mInteriors.find (name); if (result==mInteriors.end()) { - const ESM::Cell *cell = mStore.cells.findInt (nName); + const ESM::Cell *cell = mStore.cells.findInt (name); - result = mInteriors.insert (std::make_pair (nName, Ptr::CellStore (cell))).first; + result = mInteriors.insert (std::make_pair (name, Ptr::CellStore (cell))).first; } if (result->second.mState!=Ptr::CellStore::State_Loaded) From 95c27723f7733f02a8d753d229d52e829c9c4913 Mon Sep 17 00:00:00 2001 From: gugus Date: Sun, 2 Sep 2012 18:12:13 +0200 Subject: [PATCH 29/84] fixed a bug (see commit reverted) --- apps/openmw/mwworld/worldimp.cpp | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/apps/openmw/mwworld/worldimp.cpp b/apps/openmw/mwworld/worldimp.cpp index 8ace54378b..d9c4fe3212 100644 --- a/apps/openmw/mwworld/worldimp.cpp +++ b/apps/openmw/mwworld/worldimp.cpp @@ -541,6 +541,16 @@ namespace MWWorld } } + std::string toLower (const std::string& name) + { + std::string lowerCase; + + std::transform (name.begin(), name.end(), std::back_inserter (lowerCase), + (int(*)(int)) std::tolower); + + return lowerCase; + } + void World::moveObject(const Ptr &ptr, CellStore &newCell, float x, float y, float z) { ESM::Position &pos = ptr.getRefData().getPosition(); @@ -550,11 +560,10 @@ namespace MWWorld CellStore *currCell = ptr.getCell(); bool isPlayer = ptr == mPlayer->getPlayer(); bool haveToMove = mWorldScene->isCellActive(*currCell) || isPlayer; - if (*currCell != newCell) { if (isPlayer) { if (!newCell.isExterior()) { - changeToInteriorCell(newCell.cell->name, pos); + changeToInteriorCell(toLower(newCell.cell->name), pos); } else { int cellX = newCell.cell->data.gridX; int cellY = newCell.cell->data.gridY; From d2612638241e86a5a1a007b4e9b3d12626a1cdc0 Mon Sep 17 00:00:00 2001 From: gugus Date: Sun, 2 Sep 2012 21:09:07 +0200 Subject: [PATCH 30/84] oups forgot vmformat --- apps/openmw/mwscript/docs/vmformat.txt | 19 +++++++++++++++++-- 1 file changed, 17 insertions(+), 2 deletions(-) diff --git a/apps/openmw/mwscript/docs/vmformat.txt b/apps/openmw/mwscript/docs/vmformat.txt index 1ea5f8e3ec..ac8e5d01db 100644 --- a/apps/openmw/mwscript/docs/vmformat.txt +++ b/apps/openmw/mwscript/docs/vmformat.txt @@ -31,7 +31,7 @@ op 0x2000e: PCGetRank implicit op 0x2000f: PCGetRank explicit op 0x20010: AiWander op 0x20011: AiWander, explicit reference -opcodes 0x20012-0x3ffff unused +op s 0x20012-0x3ffff unused Segment 4: (not implemented yet) @@ -181,4 +181,19 @@ op 0x2000170: user4, explicit reference (console only, requires --script-console op 0x2000171: user4 (implicit reference, console only, requires --script-console switch) op 0x2000172: GetStartingAngle op 0x2000173: GetStartingAngle, explicit reference -opcodes 0x2000174-0x3ffffff unused +op 0x200016c: GetPos +op 0x200016d: GetPosExplicit +op 0x200016e: SetPos +op 0x200016f: SetPosExplicit +op 0x2000170: GetStartingPos +op 0x2000171: GetStartingPosExplicit +op 0x2000172: Position +op 0x2000173: Position Explicit +op 0x2000174: PositionCell +op 0x2000175: PositionCell Explicit +op 0x2000176: PlaceItemCell +op 0x2000177: PlaceItem +op 0x2000178: PlaceAtPc +op 0x2000179: PlaceAtMe +op 0x200017a: PlaceAtMe Explicit +opcodes 0x200017b-0x3ffffff unused From 2efceba1fca6e5d430a5e285016a8937503ad9ec Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Mon, 3 Sep 2012 20:32:20 -0400 Subject: [PATCH 31/84] Tearing apart PhysicActor --- apps/openmw/mwworld/physicssystem.cpp | 22 +++--- apps/openmw/mwworld/physicssystem.hpp | 2 +- apps/openmw/mwworld/worldimp.cpp | 2 +- libs/openengine/bullet/physic.cpp | 106 +++++++------------------- libs/openengine/bullet/physic.hpp | 30 ++++---- 5 files changed, 53 insertions(+), 109 deletions(-) diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index 0af9511cf7..7b75ff948a 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -254,12 +254,12 @@ namespace MWWorld } void PhysicsSystem::addActor (const std::string& handle, const std::string& mesh, - const Ogre::Vector3& position) + const Ogre::Vector3& position, float scale, const Ogre::Quaternion& rotation) { //TODO:optimize this. Searching the std::map isn't very efficient i think. - mEngine->addCharacter(handle); + mEngine->addCharacter(handle, mesh, position, scale, rotation); OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle); - act->setPosition(btVector3(position.x,position.y,position.z)); + } void PhysicsSystem::removeObject (const std::string& handle) @@ -272,11 +272,12 @@ namespace MWWorld void PhysicsSystem::moveObject (const std::string& handle, Ogre::SceneNode* node) { + Ogre::Vector3 position = node->getPosition(); if (OEngine::Physic::RigidBody* body = mEngine->getRigidBody(handle)) { // TODO very dirty hack to avoid crash during setup -> needs cleaning up to allow // start positions others than 0, 0, 0 - Ogre::Vector3 position = node->getPosition(); + if(dynamic_cast(body->getCollisionShape()) == NULL){ btTransform tr = body->getWorldTransform(); @@ -288,7 +289,7 @@ namespace MWWorld } if (OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle)) { - /*// TODO very dirty hack to avoid crash during setup -> needs cleaning up to allow + // TODO very dirty hack to avoid crash during setup -> needs cleaning up to allow // start positions others than 0, 0, 0 if (handle == "player") { @@ -297,19 +298,20 @@ namespace MWWorld else { act->setPosition(btVector3(position.x,position.y,position.z)); - }*/ + } } } void PhysicsSystem::rotateObject (const std::string& handle, Ogre::SceneNode* node) { - /*if (OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle)) + Ogre::Quaternion rotation = node->getOrientation(); + if (OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle)) { + //Needs to be changed act->setRotation(btQuaternion(rotation.x, rotation.y, rotation.z, rotation.w)); - }*/ + } if (OEngine::Physic::RigidBody* body = mEngine->getRigidBody(handle)) { - Ogre::Quaternion rotation = node->getOrientation(); if(dynamic_cast(body->getCollisionShape()) == NULL) body->getWorldTransform().setRotation(btQuaternion(rotation.x, rotation.y, rotation.z, rotation.w)); else @@ -380,7 +382,7 @@ namespace MWWorld void PhysicsSystem::insertActorPhysics(const MWWorld::Ptr& ptr, const std::string model){ Ogre::SceneNode* node = ptr.getRefData().getBaseNode(); - addActor (node->getName(), model, node->getPosition()); + addActor (node->getName(), model, node->getPosition(), node->getScale().x, node->getOrientation()); } bool PhysicsSystem::getObjectAABB(const MWWorld::Ptr &ptr, Ogre::Vector3 &min, Ogre::Vector3 &max) diff --git a/apps/openmw/mwworld/physicssystem.hpp b/apps/openmw/mwworld/physicssystem.hpp index 949aa9d452..1427060f6a 100644 --- a/apps/openmw/mwworld/physicssystem.hpp +++ b/apps/openmw/mwworld/physicssystem.hpp @@ -24,7 +24,7 @@ namespace MWWorld const Ogre::Quaternion& rotation, float scale, const Ogre::Vector3& position); void addActor (const std::string& handle, const std::string& mesh, - const Ogre::Vector3& position); + const Ogre::Vector3& position, float scale, const Ogre::Quaternion& rotation); void addHeightField (float* heights, int x, int y, float yoffset, diff --git a/apps/openmw/mwworld/worldimp.cpp b/apps/openmw/mwworld/worldimp.cpp index 73efdd8164..7b1c4e8190 100644 --- a/apps/openmw/mwworld/worldimp.cpp +++ b/apps/openmw/mwworld/worldimp.cpp @@ -189,7 +189,7 @@ namespace MWWorld mPlayer = new MWWorld::Player (mStore.npcs.find ("player"), *this); mRendering->attachCameraTo(mPlayer->getPlayer()); - mPhysics->addActor (mPlayer->getPlayer().getRefData().getHandle(), "", Ogre::Vector3 (0, 0, 0)); + mPhysics->addActor (mPlayer->getPlayer().getRefData().getHandle(), "", Ogre::Vector3 (0, 0, 0), 0, Ogre::Quaternion::ZERO); // global variables mGlobalVariables = new Globals (mStore); diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 0845864ef2..584c3db759 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -26,111 +26,71 @@ namespace Physic COL_RAYCASTING = BIT(3) }; - PhysicActor::PhysicActor(std::string name) + PhysicActor::PhysicActor(std::string name, std::string mesh, PhysicEngine* engine, Ogre::Vector3 position, Ogre::Quaternion rotation, float scale): + mName(name), mEngine(engine), mMesh(mesh), mBoxTranslation(Ogre::Vector3::ZERO), mBoxRotation(Ogre::Quaternion::ZERO), mBody(0) { - mName = name; // The capsule is at the origin btTransform transform; transform.setIdentity(); - // External capsule - externalGhostObject = new PairCachingGhostObject(name); - externalGhostObject->setWorldTransform( transform ); - - btScalar externalCapsuleHeight = 120; - btScalar externalCapsuleWidth = 19; - - externalCollisionShape = new btCapsuleShapeZ( externalCapsuleWidth, externalCapsuleHeight ); - externalCollisionShape->setMargin( 0.1 ); - - externalGhostObject->setCollisionShape( externalCollisionShape ); - externalGhostObject->setCollisionFlags( btCollisionObject::CF_CHARACTER_OBJECT ); - - // Internal capsule - internalGhostObject = new PairCachingGhostObject(name); - internalGhostObject->setWorldTransform( transform ); - //internalGhostObject->getBroadphaseHandle()->s - btScalar internalCapsuleHeight = 110; - btScalar internalCapsuleWidth = 17; - - internalCollisionShape = new btCapsuleShapeZ( internalCapsuleWidth, internalCapsuleHeight ); - internalCollisionShape->setMargin( 0.1 ); - - internalGhostObject->setCollisionShape( internalCollisionShape ); - internalGhostObject->setCollisionFlags( btCollisionObject::CF_CHARACTER_OBJECT ); - - mCharacter = new btKinematicCharacterController( externalGhostObject,internalGhostObject,btScalar( 40 ),1,4,20,9.8,0.2 ); - mCharacter->setUpAxis(btKinematicCharacterController::Z_AXIS); - mCharacter->setUseGhostSweepTest(false); - - mCharacter->mCollision = false; - setGravity(0); - - mTranslation = btVector3(0,0,70); } PhysicActor::~PhysicActor() { - delete mCharacter; - delete internalGhostObject; - delete internalCollisionShape; - delete externalGhostObject; - delete externalCollisionShape; + if(mBody){ + mEngine->dynamicsWorld->removeRigidBody(mBody); + delete mBody; + } } void PhysicActor::setGravity(float gravity) { - mCharacter->setGravity(gravity); - //mCharacter-> + } void PhysicActor::enableCollisions(bool collision) { - mCharacter->mCollision = collision; + } void PhysicActor::setVerticalVelocity(float z) { - mCharacter->setVerticalVelocity(z); + } bool PhysicActor::getCollisionMode() { - return mCharacter->mCollision; + return false; } void PhysicActor::setWalkDirection(const btVector3& mvt) { - mCharacter->setWalkDirection( mvt ); + } - void PhysicActor::Rotate(const btQuaternion& quat) - { - externalGhostObject->getWorldTransform().setRotation( externalGhostObject->getWorldTransform().getRotation() * quat ); - internalGhostObject->getWorldTransform().setRotation( internalGhostObject->getWorldTransform().getRotation() * quat ); - } + void PhysicActor::setRotation(const btQuaternion& quat) { - externalGhostObject->getWorldTransform().setRotation( quat ); - internalGhostObject->getWorldTransform().setRotation( quat ); + //externalGhostObject->getWorldTransform().setRotation( quat ); + //internalGhostObject->getWorldTransform().setRotation( quat ); } btVector3 PhysicActor::getPosition(void) { - return internalGhostObject->getWorldTransform().getOrigin() -mTranslation; + return btVector3(0,0,0);//return internalGhostObject->getWorldTransform().getOrigin() -mTranslation; } btQuaternion PhysicActor::getRotation(void) { - return internalGhostObject->getWorldTransform().getRotation(); + return btQuaternion(0,0,0);//return btQuaternion::internalGhostObject->getWorldTransform().getRotation(); } void PhysicActor::setPosition(const btVector3& pos) { - internalGhostObject->getWorldTransform().setOrigin(pos+mTranslation); - externalGhostObject->getWorldTransform().setOrigin(pos+mTranslation); + //internalGhostObject->getWorldTransform().setOrigin(pos+mTranslation); + //externalGhostObject->getWorldTransform().setOrigin(pos+mTranslation); } //////////////////////////////////////////////////////////////////////////////////////////////////////////////// @@ -247,9 +207,7 @@ namespace Physic { if (pa_it->second != NULL) { - dynamicsWorld->removeCollisionObject(pa_it->second->externalGhostObject); - dynamicsWorld->removeCollisionObject(pa_it->second->internalGhostObject); - dynamicsWorld->removeAction(pa_it->second->mCharacter); + delete pa_it->second; pa_it->second = NULL; @@ -477,16 +435,17 @@ namespace Physic } } - void PhysicEngine::addCharacter(std::string name) + void PhysicEngine::addCharacter(std::string name, std::string mesh, + Ogre::Vector3 position, float scale, Ogre::Quaternion rotation) { // Remove character with given name, so we don't make memory // leak when character would be added twice removeCharacter(name); - PhysicActor* newActor = new PhysicActor(name); - dynamicsWorld->addCollisionObject( newActor->externalGhostObject, COL_ACTOR_EXTERNAL, COL_WORLD |COL_ACTOR_EXTERNAL ); - dynamicsWorld->addCollisionObject( newActor->internalGhostObject, COL_ACTOR_INTERNAL, COL_WORLD |COL_ACTOR_INTERNAL ); - dynamicsWorld->addAction( newActor->mCharacter ); + PhysicActor* newActor = new PhysicActor(name, mesh, this, position, rotation, scale); + + + //dynamicsWorld->addAction( newActor->mCharacter ); PhysicActorMap[name] = newActor; } @@ -499,20 +458,7 @@ namespace Physic PhysicActor* act = it->second; if(act != NULL) { - /*broadphase->getOverlappingPairCache()->removeOverlappingPairsContainingProxy(act->externalGhostObject->getBroadphaseHandle(),dispatcher); - broadphase->getOverlappingPairCache()->removeOverlappingPairsContainingProxy(act->internalGhostObject->getBroadphaseHandle(),dispatcher); - PhysicActorContainer::iterator it2 = PhysicActorMap.begin(); - for(;it2!=PhysicActorMap.end();it++) - { - it->second->internalGhostObject->getOverlappingPairCache()->removeOverlappingPairsContainingProxy(act->externalGhostObject->getBroadphaseHandle(),dispatcher); - it->second->externalGhostObject->getOverlappingPairCache()->removeOverlappingPairsContainingProxy(act->externalGhostObject->getBroadphaseHandle(),dispatcher); - it->second->internalGhostObject->getOverlappingPairCache()->removeOverlappingPairsContainingProxy(act->internalGhostObject->getBroadphaseHandle(),dispatcher); - it->second->externalGhostObject->getOverlappingPairCache()->removeOverlappingPairsContainingProxy(act->internalGhostObject->getBroadphaseHandle(),dispatcher); - }*/ - //act->externalGhostObject-> - dynamicsWorld->removeCollisionObject(act->externalGhostObject); - dynamicsWorld->removeCollisionObject(act->internalGhostObject); - dynamicsWorld->removeAction(act->mCharacter); + delete act; } PhysicActorMap.erase(it); diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index 403af6c6cf..af4d56e33b 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -15,7 +15,6 @@ class btDefaultCollisionConfiguration; class btSequentialImpulseConstraintSolver; class btCollisionDispatcher; class btDiscreteDynamicsWorld; -class btKinematicCharacterController; class btHeightfieldTerrainShape; namespace BtOgre @@ -33,6 +32,8 @@ namespace Physic { class CMotionState; struct PhysicEvent; + class PhysicEngine; + class RigidBody; /** *This is just used to be able to name objects. @@ -55,7 +56,7 @@ namespace Physic class PhysicActor { public: - PhysicActor(std::string name); + PhysicActor(std::string name, std::string mesh, PhysicEngine *engine, Ogre::Vector3 position, Ogre::Quaternion rotation, float scale); ~PhysicActor(); @@ -66,8 +67,6 @@ namespace Physic */ void setWalkDirection(const btVector3& mvt); - void Rotate(const btQuaternion& quat); - void setRotation(const btQuaternion& quat); void setGravity(float gravity); @@ -84,21 +83,17 @@ namespace Physic void setPosition(const btVector3& pos); - btKinematicCharacterController* mCharacter; - - PairCachingGhostObject* internalGhostObject; - btCollisionShape* internalCollisionShape; - - PairCachingGhostObject* externalGhostObject; - btCollisionShape* externalCollisionShape; + std::string mName; - /** - *NPC scenenode is located on there feet, and you can't simply translate a btShape, so this vector is used - *each time get/setposition is called. - */ - btVector3 mTranslation; + + private: + OEngine::Physic::RigidBody* mBody; + Ogre::Vector3 mBoxTranslation; + Ogre::Quaternion mBoxRotation; + std::string mMesh; + PhysicEngine* mEngine; }; /** @@ -195,7 +190,8 @@ namespace Physic /** * Create and add a character to the scene, and add it to the ActorMap. */ - void addCharacter(std::string name); + void addCharacter(std::string name, std::string mesh, + Ogre::Vector3 position, float scale, Ogre::Quaternion rotation); /** * Remove a character from the scene. TODO:delete it! for now, a small memory leak^^ done? From 23777033fdcf94fc83479af7fdc71c1e0718a8dd Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Wed, 5 Sep 2012 17:44:11 -0400 Subject: [PATCH 32/84] Starting to implement new PhysicActor --- apps/openmw/mwclass/creature.cpp | 2 +- apps/openmw/mwclass/npc.cpp | 4 +-- apps/openmw/mwrender/renderingmanager.cpp | 4 ++- apps/openmw/mwworld/physicssystem.cpp | 8 +++-- apps/openmw/mwworld/worldimp.cpp | 4 ++- libs/openengine/bullet/physic.cpp | 44 +++++++++++++---------- libs/openengine/bullet/physic.hpp | 15 ++++---- libs/openengine/bullet/trace.cpp | 5 ++- 8 files changed, 49 insertions(+), 37 deletions(-) diff --git a/apps/openmw/mwclass/creature.cpp b/apps/openmw/mwclass/creature.cpp index f03c0fdb19..7c60216528 100644 --- a/apps/openmw/mwclass/creature.cpp +++ b/apps/openmw/mwclass/creature.cpp @@ -89,7 +89,7 @@ namespace MWClass { const std::string model = getModel(ptr); if(!model.empty()){ - physics.insertObjectPhysics(ptr, model); + physics.insertActorPhysics(ptr, model); } MWBase::Environment::get().getMechanicsManager()->addActor (ptr); } diff --git a/apps/openmw/mwclass/npc.cpp b/apps/openmw/mwclass/npc.cpp index c9b16ae1e3..851cf050b0 100644 --- a/apps/openmw/mwclass/npc.cpp +++ b/apps/openmw/mwclass/npc.cpp @@ -125,7 +125,7 @@ namespace MWClass void Npc::insertObject(const MWWorld::Ptr& ptr, MWWorld::PhysicsSystem& physics) const { - physics.insertObjectPhysics(ptr, getModel(ptr)); + physics.insertActorPhysics(ptr, getModel(ptr)); MWBase::Environment::get().getMechanicsManager()->addActor(ptr); } @@ -294,7 +294,7 @@ namespace MWClass { Ogre::Vector3 vector (0, 0, 0); - vector.x = - getMovementSettings (ptr).mLeftRight * 127; + vector.x = getMovementSettings (ptr).mLeftRight * 127; vector.y = getMovementSettings (ptr).mForwardBackward * 127; vector.z = getMovementSettings(ptr).mUpDown * 127; diff --git a/apps/openmw/mwrender/renderingmanager.cpp b/apps/openmw/mwrender/renderingmanager.cpp index edeb0fe127..bec84e0c95 100644 --- a/apps/openmw/mwrender/renderingmanager.cpp +++ b/apps/openmw/mwrender/renderingmanager.cpp @@ -266,13 +266,15 @@ RenderingManager::rotateObject( float *f = ptr.getRefData().getPosition().rot; rot.x += f[0], rot.y += f[1], rot.z += f[2]; } + if (!isPlayer && isActive) { Ogre::Quaternion xr(Ogre::Radian(rot.x), Ogre::Vector3::UNIT_X); Ogre::Quaternion yr(Ogre::Radian(rot.y), Ogre::Vector3::UNIT_Y); Ogre::Quaternion zr(Ogre::Radian(rot.z), Ogre::Vector3::UNIT_Z); - + ptr.getRefData().getBaseNode()->setOrientation(xr * yr * zr); } + return force; } diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index 7b75ff948a..4285eeb18c 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -201,8 +201,7 @@ namespace MWWorld playerphysics->ps.viewangles.y = Ogre::Radian(mPlayerData.yaw).valueDegrees() + 90; - - pm_ref.rightmove = -iter->second.x; + pm_ref.rightmove = iter->second.x; pm_ref.forwardmove = -iter->second.y; pm_ref.upmove = iter->second.z; } @@ -214,6 +213,7 @@ namespace MWWorld const std::vector >& actors) { Pmove(playerphysics); + std::vector< std::pair > response; for(std::map::iterator it = mEngine->PhysicActorMap.begin(); it != mEngine->PhysicActorMap.end();it++) @@ -224,6 +224,7 @@ namespace MWWorld if(it->first == "player"){ coord = playerphysics->ps.origin ; + } @@ -257,8 +258,9 @@ namespace MWWorld const Ogre::Vector3& position, float scale, const Ogre::Quaternion& rotation) { //TODO:optimize this. Searching the std::map isn't very efficient i think. + std::cout << "NPC position" << position << "\n"; mEngine->addCharacter(handle, mesh, position, scale, rotation); - OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle); + } diff --git a/apps/openmw/mwworld/worldimp.cpp b/apps/openmw/mwworld/worldimp.cpp index 7b1c4e8190..55c2f4161e 100644 --- a/apps/openmw/mwworld/worldimp.cpp +++ b/apps/openmw/mwworld/worldimp.cpp @@ -189,7 +189,9 @@ namespace MWWorld mPlayer = new MWWorld::Player (mStore.npcs.find ("player"), *this); mRendering->attachCameraTo(mPlayer->getPlayer()); - mPhysics->addActor (mPlayer->getPlayer().getRefData().getHandle(), "", Ogre::Vector3 (0, 0, 0), 0, Ogre::Quaternion::ZERO); + std::string playerCollisionFile = "meshes\\base_anim.nif"; //This is used to make a collision shape for our player + //We will need to support the 1st person file too in the future + mPhysics->addActor (mPlayer->getPlayer().getRefData().getHandle(), playerCollisionFile, Ogre::Vector3 (0, 0, 0), 1, Ogre::Quaternion::ZERO); // global variables mGlobalVariables = new Globals (mStore); diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 584c3db759..7db0b154b7 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -27,12 +27,12 @@ namespace Physic }; PhysicActor::PhysicActor(std::string name, std::string mesh, PhysicEngine* engine, Ogre::Vector3 position, Ogre::Quaternion rotation, float scale): - mName(name), mEngine(engine), mMesh(mesh), mBoxTranslation(Ogre::Vector3::ZERO), mBoxRotation(Ogre::Quaternion::ZERO), mBody(0) + mName(name), mEngine(engine), mMesh(mesh), mBoxTranslation(Ogre::Vector3::ZERO), mBoxRotation(Ogre::Quaternion::ZERO), mBody(0), collisionMode(false) { - - // The capsule is at the origin - btTransform transform; - transform.setIdentity(); + Ogre::Vector3 test; + mBody = mEngine->createAndAdjustRigidBody(mesh, mName, scale, position, rotation, &test); + std::cout << "Test" << test << "\n"; + mEngine->addRigidBody(mBody, false); //Add rigid body to dynamics world, but do not add to object map } @@ -51,7 +51,7 @@ namespace Physic void PhysicActor::enableCollisions(bool collision) { - + collisionMode = collision; } void PhysicActor::setVerticalVelocity(float z) @@ -61,7 +61,7 @@ namespace Physic bool PhysicActor::getCollisionMode() { - return false; + return collisionMode; } void PhysicActor::setWalkDirection(const btVector3& mvt) @@ -79,12 +79,12 @@ namespace Physic btVector3 PhysicActor::getPosition(void) { - return btVector3(0,0,0);//return internalGhostObject->getWorldTransform().getOrigin() -mTranslation; + return mBody->getWorldTransform().getOrigin();//return internalGhostObject->getWorldTransform().getOrigin() -mTranslation; } btQuaternion PhysicActor::getRotation(void) { - return btQuaternion(0,0,0);//return btQuaternion::internalGhostObject->getWorldTransform().getRotation(); + return mBody->getWorldTransform().getRotation();//return btQuaternion::internalGhostObject->getWorldTransform().getRotation(); } void PhysicActor::setPosition(const btVector3& pos) @@ -290,7 +290,8 @@ namespace Physic mHeightFieldMap.erase(name); } - void PhysicEngine::adjustRigidBody(BulletShapePtr shape, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation){ + void PhysicEngine::adjustRigidBody(BulletShapePtr shape, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, + Ogre::Vector3 scaledBoxPosition, Ogre::Quaternion boxRotation){ btTransform tr; btBoxShape* box = dynamic_cast(body->getCollisionShape()); if(box != NULL){ @@ -317,8 +318,11 @@ namespace Physic adjustRigidBody(shape, body, scale, position, rotation); } - RigidBody* PhysicEngine::createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation) + RigidBody* PhysicEngine::createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, + Ogre::Vector3* scaledBoxPosition, Ogre::Quaternion* boxRotation) { + if(scaledBoxPosition != 0) + *scaledBoxPosition = Ogre::Vector3(0, 5, 0); std::string sid = (boost::format("%07.3f") % scale).str(); std::string outputstring = mesh + sid; //std::cout << "The string" << outputstring << "\n"; @@ -348,7 +352,7 @@ namespace Physic } - void PhysicEngine::addRigidBody(RigidBody* body) + void PhysicEngine::addRigidBody(RigidBody* body, bool addToMap) { if(body) { @@ -361,14 +365,16 @@ namespace Physic dynamicsWorld->addRigidBody(body,COL_RAYCASTING,COL_RAYCASTING|COL_WORLD); } body->setActivationState(DISABLE_DEACTIVATION); - RigidBody* oldBody = RigidBodyMap[body->mName]; - if (oldBody != NULL) - { - dynamicsWorld->removeRigidBody(oldBody); - delete oldBody; + if(addToMap){ + RigidBody* oldBody = RigidBodyMap[body->mName]; + if (oldBody != NULL) + { + dynamicsWorld->removeRigidBody(oldBody); + delete oldBody; + } + + RigidBodyMap[body->mName] = body; } - - RigidBodyMap[body->mName] = body; } } diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index af4d56e33b..f223804831 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -92,6 +92,7 @@ namespace Physic OEngine::Physic::RigidBody* mBody; Ogre::Vector3 mBoxTranslation; Ogre::Quaternion mBoxRotation; + bool collisionMode; std::string mMesh; PhysicEngine* mEngine; }; @@ -138,18 +139,18 @@ namespace Physic ~PhysicEngine(); /** - * Create a RigidBody.It does not add it to the simulation, but it does add it to the rigidBody Map, - * so you can get it with the getRigidBody function. - - After created, the body is set to the correct rotation, position, and scale + * Creates a RigidBody. It does not add it to the simulation. + * After created, the body is set to the correct rotation, position, and scale */ - RigidBody* createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation); + RigidBody* createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, + Ogre::Vector3* scaledBoxPosition = 0, Ogre::Quaternion* boxRotation = 0); /** * Adjusts a rigid body to the right position and rotation */ - void adjustRigidBody(BulletShapePtr shape, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation); + void adjustRigidBody(BulletShapePtr shape, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, + Ogre::Vector3 scaledBoxPosition = Ogre::Vector3::ZERO, Ogre::Quaternion boxRotation = Ogre::Quaternion::ZERO); /** Mainly used to (but not limited to) adjust rigid bodies based on box shapes to the right position and rotation. */ @@ -169,7 +170,7 @@ namespace Physic /** * Add a RigidBody to the simulation */ - void addRigidBody(RigidBody* body); + void addRigidBody(RigidBody* body, bool addToMap = true); /** * Remove a RigidBody from the simulation. It does not delete it, and does not remove it from the RigidBodyMap. diff --git a/libs/openengine/bullet/trace.cpp b/libs/openengine/bullet/trace.cpp index 57b729db10..474d87ee95 100644 --- a/libs/openengine/bullet/trace.cpp +++ b/libs/openengine/bullet/trace.cpp @@ -35,9 +35,8 @@ void newtrace(traceResults* const results, const Ogre::Vector3& start, const Ogr //Ogre::Vector3 startReplace = Ogre::Vector3(650,950, 45); //Ogre::Vector3 endReplace = startReplace; //endReplace.z -= .25; - - const bool hasHit = NewPhysicsTrace(&out, start, end, BBHalfExtents, Ogre::Vector3(0.0f, 0.0f,0.0f), isInterior, enginePass); + const bool hasHit = NewPhysicsTrace(&out, start, end, BBHalfExtents, Ogre::Vector3(0.0f, 0.0f, 0.0f), isInterior, enginePass); if (out.fraction < 0.001f) results->startsolid = true; @@ -100,7 +99,7 @@ const bool NewPhysicsTrace(NewPhysTraceResults* const out, const Ogre::Vector3& //if(enginePass->dynamicsWorld->getCollisionObjectArray().at(60)->getCollisionShape()->isConvex()) // std::cout << "It's convex\n"; - + const btVector3 btstart(start.x, start.y, start.z + BBHalfExtents.z); const btVector3 btend(end.x, end.y, end.z + BBHalfExtents.z); From 3e3437f9c3e2ed0bdf36bf4496a04d6d76f578ea Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Thu, 6 Sep 2012 20:11:59 -0400 Subject: [PATCH 33/84] Revised create and adjust rigid body functions --- libs/openengine/bullet/physic.cpp | 38 ++++++++++++++++--------------- libs/openengine/bullet/physic.hpp | 6 ++--- 2 files changed, 23 insertions(+), 21 deletions(-) diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 7db0b154b7..f453915c81 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -290,18 +290,13 @@ namespace Physic mHeightFieldMap.erase(name); } - void PhysicEngine::adjustRigidBody(BulletShapePtr shape, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, - Ogre::Vector3 scaledBoxPosition, Ogre::Quaternion boxRotation){ + void PhysicEngine::adjustRigidBody(RigidBody* body, Ogre::Vector3 position, Ogre::Quaternion rotation, + Ogre::Vector3 scaledBoxTranslation, Ogre::Quaternion boxRotation){ btTransform tr; - btBoxShape* box = dynamic_cast(body->getCollisionShape()); - if(box != NULL){ - Ogre::Vector3 transrot = rotation * shape->boxRotation * (shape->boxTranslation * scale); - Ogre::Vector3 newPosition = transrot + position; - tr.setOrigin(btVector3(newPosition.x, newPosition.y, newPosition.z)); - rotation = rotation * shape->boxRotation; - } - else - tr.setOrigin(btVector3(position.x,position.y,position.z)); + rotation = rotation * boxRotation; + Ogre::Vector3 transrot = rotation * scaledBoxTranslation; + Ogre::Vector3 newPosition = transrot + position; + tr.setOrigin(btVector3(newPosition.x, newPosition.y, newPosition.z)); tr.setRotation(btQuaternion(rotation.x,rotation.y,rotation.z,rotation.w)); body->setWorldTransform(tr); } @@ -315,14 +310,18 @@ namespace Physic BulletShapeManager::getSingletonPtr()->load(outputstring,"General"); BulletShapePtr shape = BulletShapeManager::getSingleton().getByName(outputstring,"General"); - adjustRigidBody(shape, body, scale, position, rotation); + btBoxShape* box = dynamic_cast(shape->Shape); + if(box != NULL) + adjustRigidBody(body, position, rotation, shape->boxTranslation * scale, shape->boxRotation); + else + adjustRigidBody(body, position, rotation); } RigidBody* PhysicEngine::createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, - Ogre::Vector3* scaledBoxPosition, Ogre::Quaternion* boxRotation) + Ogre::Vector3* scaledBoxTranslation, Ogre::Quaternion* boxRotation) { - if(scaledBoxPosition != 0) - *scaledBoxPosition = Ogre::Vector3(0, 5, 0); + if(scaledBoxTranslation != 0) + *scaledBoxTranslation = Ogre::Vector3(0, 5, 0); std::string sid = (boost::format("%07.3f") % scale).str(); std::string outputstring = mesh + sid; //std::cout << "The string" << outputstring << "\n"; @@ -332,6 +331,7 @@ namespace Physic BulletShapeManager::getSingletonPtr()->load(outputstring,"General"); BulletShapePtr shape = BulletShapeManager::getSingleton().getByName(outputstring,"General"); shape->Shape->setLocalScaling( btVector3(scale,scale,scale)); + // @@ -344,9 +344,11 @@ namespace Physic RigidBody* body = new RigidBody(CI,name); body->collide = shape->collide; - //Pass in BulletShape, RigidBody, scale, position, rotation - - adjustRigidBody(shape, body, scale, position, rotation); + btBoxShape* box = dynamic_cast(shape->Shape); + if(box != NULL) + adjustRigidBody(body, position, rotation, shape->boxTranslation * scale, shape->boxRotation); + else + adjustRigidBody(body, position, rotation); return body; diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index f223804831..f699b7d440 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -143,14 +143,14 @@ namespace Physic * After created, the body is set to the correct rotation, position, and scale */ RigidBody* createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, - Ogre::Vector3* scaledBoxPosition = 0, Ogre::Quaternion* boxRotation = 0); + Ogre::Vector3* scaledBoxTranslation = 0, Ogre::Quaternion* boxRotation = 0); /** * Adjusts a rigid body to the right position and rotation */ - void adjustRigidBody(BulletShapePtr shape, RigidBody* body, float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, - Ogre::Vector3 scaledBoxPosition = Ogre::Vector3::ZERO, Ogre::Quaternion boxRotation = Ogre::Quaternion::ZERO); + void adjustRigidBody(RigidBody* body, Ogre::Vector3 position, Ogre::Quaternion rotation, + Ogre::Vector3 scaledBoxTranslation = Ogre::Vector3::ZERO, Ogre::Quaternion boxRotation = Ogre::Quaternion::IDENTITY); /** Mainly used to (but not limited to) adjust rigid bodies based on box shapes to the right position and rotation. */ From c5b25ef70b9264c2a9036bcbb04da7fb50336b25 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Mon, 10 Sep 2012 20:29:24 -0400 Subject: [PATCH 34/84] Very basic actor physics (no set scale/rotate functions) --- apps/openmw/mwrender/npcanimation.cpp | 1 + components/nifbullet/bullet_nif_loader.cpp | 1 + libs/openengine/bullet/physic.cpp | 46 +++++++++++----------- libs/openengine/bullet/physic.hpp | 7 ++-- 4 files changed, 28 insertions(+), 27 deletions(-) diff --git a/apps/openmw/mwrender/npcanimation.cpp b/apps/openmw/mwrender/npcanimation.cpp index e509bd1704..e0304e06ee 100644 --- a/apps/openmw/mwrender/npcanimation.cpp +++ b/apps/openmw/mwrender/npcanimation.cpp @@ -122,6 +122,7 @@ NpcAnimation::NpcAnimation(const MWWorld::Ptr& ptr, OEngine::Render::OgreRendere } + if(isFemale) mInsert->scale(race->data.height.female, race->data.height.female, race->data.height.female); else diff --git a/components/nifbullet/bullet_nif_loader.cpp b/components/nifbullet/bullet_nif_loader.cpp index 6fec6241fb..1dc22a0d36 100644 --- a/components/nifbullet/bullet_nif_loader.cpp +++ b/components/nifbullet/bullet_nif_loader.cpp @@ -74,6 +74,7 @@ void ManualBulletShapeLoader::loadResource(Ogre::Resource *resource) cShape->collide = false; mBoundingBox = NULL; cShape->boxTranslation = Ogre::Vector3(0,0,0); + cShape->boxRotation = Ogre::Quaternion::IDENTITY; mTriMesh = new btTriangleMesh(); diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index f453915c81..8fa7681f53 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -27,13 +27,10 @@ namespace Physic }; PhysicActor::PhysicActor(std::string name, std::string mesh, PhysicEngine* engine, Ogre::Vector3 position, Ogre::Quaternion rotation, float scale): - mName(name), mEngine(engine), mMesh(mesh), mBoxTranslation(Ogre::Vector3::ZERO), mBoxRotation(Ogre::Quaternion::ZERO), mBody(0), collisionMode(false) + mName(name), mEngine(engine), mMesh(mesh), mBoxScaledTranslation(0,0,0), mBoxRotationInverse(0,0,0,0), mBody(0), collisionMode(false), mBoxRotation(0,0,0,0) { - Ogre::Vector3 test; - mBody = mEngine->createAndAdjustRigidBody(mesh, mName, scale, position, rotation, &test); - std::cout << "Test" << test << "\n"; + mBody = mEngine->createAndAdjustRigidBody(mesh, mName, scale, position, rotation, &mBoxScaledTranslation, &mBoxRotation, &mBoxRotationInverse); mEngine->addRigidBody(mBody, false); //Add rigid body to dynamics world, but do not add to object map - } PhysicActor::~PhysicActor() @@ -79,12 +76,17 @@ namespace Physic btVector3 PhysicActor::getPosition(void) { - return mBody->getWorldTransform().getOrigin();//return internalGhostObject->getWorldTransform().getOrigin() -mTranslation; + btVector3 vec = mBody->getWorldTransform().getOrigin(); + Ogre::Quaternion rotation = Ogre::Quaternion(mBody->getWorldTransform().getRotation().getW(), mBody->getWorldTransform().getRotation().getX(), + mBody->getWorldTransform().getRotation().getY(), mBody->getWorldTransform().getRotation().getZ()); + Ogre::Vector3 transrot = rotation * mBoxScaledTranslation; + btVector3 visualPosition = vec - btVector3(transrot.x, transrot.y, transrot.z); + return visualPosition; } btQuaternion PhysicActor::getRotation(void) { - return mBody->getWorldTransform().getRotation();//return btQuaternion::internalGhostObject->getWorldTransform().getRotation(); + return mBody->getWorldTransform().getRotation() * mBoxRotationInverse; } void PhysicActor::setPosition(const btVector3& pos) @@ -296,6 +298,7 @@ namespace Physic rotation = rotation * boxRotation; Ogre::Vector3 transrot = rotation * scaledBoxTranslation; Ogre::Vector3 newPosition = transrot + position; + tr.setOrigin(btVector3(newPosition.x, newPosition.y, newPosition.z)); tr.setRotation(btQuaternion(rotation.x,rotation.y,rotation.z,rotation.w)); body->setWorldTransform(tr); @@ -310,21 +313,14 @@ namespace Physic BulletShapeManager::getSingletonPtr()->load(outputstring,"General"); BulletShapePtr shape = BulletShapeManager::getSingleton().getByName(outputstring,"General"); - btBoxShape* box = dynamic_cast(shape->Shape); - if(box != NULL) - adjustRigidBody(body, position, rotation, shape->boxTranslation * scale, shape->boxRotation); - else - adjustRigidBody(body, position, rotation); + adjustRigidBody(body, position, rotation, shape->boxTranslation * scale, shape->boxRotation); } RigidBody* PhysicEngine::createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, - Ogre::Vector3* scaledBoxTranslation, Ogre::Quaternion* boxRotation) + Ogre::Vector3* scaledBoxTranslation, btQuaternion* boxRotation, btQuaternion* boxRotationInverse) { - if(scaledBoxTranslation != 0) - *scaledBoxTranslation = Ogre::Vector3(0, 5, 0); std::string sid = (boost::format("%07.3f") % scale).str(); std::string outputstring = mesh + sid; - //std::cout << "The string" << outputstring << "\n"; //get the shape from the .nif mShapeLoader->load(outputstring,"General"); @@ -332,9 +328,6 @@ namespace Physic BulletShapePtr shape = BulletShapeManager::getSingleton().getByName(outputstring,"General"); shape->Shape->setLocalScaling( btVector3(scale,scale,scale)); - - - // //create the motionState CMotionState* newMotionState = new CMotionState(this,name); @@ -344,11 +337,16 @@ namespace Physic RigidBody* body = new RigidBody(CI,name); body->collide = shape->collide; - btBoxShape* box = dynamic_cast(shape->Shape); - if(box != NULL) - adjustRigidBody(body, position, rotation, shape->boxTranslation * scale, shape->boxRotation); - else - adjustRigidBody(body, position, rotation); + if(scaledBoxTranslation != 0) + *scaledBoxTranslation = shape->boxTranslation * scale; + if(boxRotation != 0) + *boxRotation = btQuaternion(shape->boxRotation.x, shape->boxRotation.y, shape->boxRotation.z,shape->boxRotation.w); + if(boxRotationInverse != 0){ + Ogre::Quaternion inverse = shape->boxRotation.Inverse(); + *boxRotationInverse = btQuaternion(inverse.x,inverse.y,inverse.z,inverse.w); + } + + adjustRigidBody(body, position, rotation, shape->boxTranslation * scale, shape->boxRotation); return body; diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index f699b7d440..1ff7061463 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -90,8 +90,9 @@ namespace Physic private: OEngine::Physic::RigidBody* mBody; - Ogre::Vector3 mBoxTranslation; - Ogre::Quaternion mBoxRotation; + Ogre::Vector3 mBoxScaledTranslation; + btQuaternion mBoxRotationInverse; + btQuaternion mBoxRotation; bool collisionMode; std::string mMesh; PhysicEngine* mEngine; @@ -143,7 +144,7 @@ namespace Physic * After created, the body is set to the correct rotation, position, and scale */ RigidBody* createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, - Ogre::Vector3* scaledBoxTranslation = 0, Ogre::Quaternion* boxRotation = 0); + Ogre::Vector3* scaledBoxTranslation = 0, btQuaternion* boxRotation = 0, btQuaternion* boxRotationInverse = 0); /** * Adjusts a rigid body to the right position and rotation From a1a773373007ff4f63d63cf92df07165c53f25dc Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Wed, 12 Sep 2012 18:30:32 -0400 Subject: [PATCH 35/84] Set scale implemented --- apps/openmw/mwworld/physicssystem.cpp | 9 +++++++-- libs/openengine/bullet/physic.cpp | 27 ++++++++++++++++++++++----- libs/openengine/bullet/physic.hpp | 6 +++--- 3 files changed, 32 insertions(+), 10 deletions(-) diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index 4285eeb18c..243ec61baa 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -218,9 +218,8 @@ namespace MWWorld std::vector< std::pair > response; for(std::map::iterator it = mEngine->PhysicActorMap.begin(); it != mEngine->PhysicActorMap.end();it++) { - btVector3 newPos = it->second->getPosition(); - Ogre::Vector3 coord(newPos.x(), newPos.y(), newPos.z()); + Ogre::Vector3 coord = it->second->getPosition(); if(it->first == "player"){ coord = playerphysics->ps.origin ; @@ -332,6 +331,12 @@ namespace MWWorld Ogre::Vector3 vec = node->getPosition(); addObject(handle, handleToMesh[handle], quat, scale, vec); } + + if (OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle)) + { + float scale = node->getScale().x; + act->setScale(scale); + } } bool PhysicsSystem::toggleCollisionMode() diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 8fa7681f53..2824da4ca5 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -29,7 +29,7 @@ namespace Physic PhysicActor::PhysicActor(std::string name, std::string mesh, PhysicEngine* engine, Ogre::Vector3 position, Ogre::Quaternion rotation, float scale): mName(name), mEngine(engine), mMesh(mesh), mBoxScaledTranslation(0,0,0), mBoxRotationInverse(0,0,0,0), mBody(0), collisionMode(false), mBoxRotation(0,0,0,0) { - mBody = mEngine->createAndAdjustRigidBody(mesh, mName, scale, position, rotation, &mBoxScaledTranslation, &mBoxRotation, &mBoxRotationInverse); + mBody = mEngine->createAndAdjustRigidBody(mMesh, mName, scale, position, rotation, &mBoxScaledTranslation, &mBoxRotation, &mBoxRotationInverse); mEngine->addRigidBody(mBody, false); //Add rigid body to dynamics world, but do not add to object map } @@ -74,19 +74,20 @@ namespace Physic //internalGhostObject->getWorldTransform().setRotation( quat ); } - btVector3 PhysicActor::getPosition(void) + Ogre::Vector3 PhysicActor::getPosition(void) { btVector3 vec = mBody->getWorldTransform().getOrigin(); Ogre::Quaternion rotation = Ogre::Quaternion(mBody->getWorldTransform().getRotation().getW(), mBody->getWorldTransform().getRotation().getX(), mBody->getWorldTransform().getRotation().getY(), mBody->getWorldTransform().getRotation().getZ()); Ogre::Vector3 transrot = rotation * mBoxScaledTranslation; - btVector3 visualPosition = vec - btVector3(transrot.x, transrot.y, transrot.z); + Ogre::Vector3 visualPosition = Ogre::Vector3(vec.getX(), vec.getY(), vec.getZ()) - transrot; return visualPosition; } - btQuaternion PhysicActor::getRotation(void) + Ogre::Quaternion PhysicActor::getRotation(void) { - return mBody->getWorldTransform().getRotation() * mBoxRotationInverse; + btQuaternion quat = mBody->getWorldTransform().getRotation() * mBoxRotationInverse; + return Ogre::Quaternion(quat.getW(), quat.getX(), quat.getY(), quat.getZ()); } void PhysicActor::setPosition(const btVector3& pos) @@ -95,6 +96,22 @@ namespace Physic //externalGhostObject->getWorldTransform().setOrigin(pos+mTranslation); } + void PhysicActor::setScale(float scale){ + std::cout << "Trying to set scale to " << scale << "\n"; + Ogre::Vector3 position = getPosition(); + Ogre::Quaternion rotation = getRotation(); + //We only need to change the scaled box translation, box rotations remain the same. + mBoxScaledTranslation = mBoxScaledTranslation / mBody->getCollisionShape()->getLocalScaling().getX(); + mBoxScaledTranslation *= scale; + if(mBody){ + mEngine->dynamicsWorld->removeRigidBody(mBody); + delete mBody; + } + //Create the newly scaled rigid body + mBody = mEngine->createAndAdjustRigidBody(mMesh, mName, scale, position, rotation); + mEngine->addRigidBody(mBody, false); //Add rigid body to dynamics world, but do not add to object map + } + //////////////////////////////////////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////////////////////////////////////// diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index 1ff7061463..2568cc36f5 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -77,13 +77,13 @@ namespace Physic bool getCollisionMode(); - btVector3 getPosition(void); + Ogre::Vector3 getPosition(void); - btQuaternion getRotation(void); + Ogre::Quaternion getRotation(void); void setPosition(const btVector3& pos); - + void setScale(float scale); std::string mName; From b76a28f69ce5357b60501b1fd2f6aca6b9c8469a Mon Sep 17 00:00:00 2001 From: scrawl Date: Fri, 14 Sep 2012 19:44:00 +0200 Subject: [PATCH 36/84] beginnings of the gui --- apps/openmw/CMakeLists.txt | 2 +- apps/openmw/mwgui/levelupdialog.cpp | 63 ++++++++ apps/openmw/mwgui/levelupdialog.hpp | 30 ++++ apps/openmw/mwgui/mode.hpp | 2 + apps/openmw/mwgui/windowmanagerimp.cpp | 3 + apps/openmw/mwgui/windowmanagerimp.hpp | 2 + files/mygui/CMakeLists.txt | 5 +- .../{openmw.font.xml => openmw_font.xml} | 0 files/mygui/openmw_levelup_dialog.layout | 146 ++++++++++++++++++ ...{openmw.pointer.xml => openmw_pointer.xml} | 0 10 files changed, 250 insertions(+), 3 deletions(-) create mode 100644 apps/openmw/mwgui/levelupdialog.cpp create mode 100644 apps/openmw/mwgui/levelupdialog.hpp rename files/mygui/{openmw.font.xml => openmw_font.xml} (100%) create mode 100644 files/mygui/openmw_levelup_dialog.layout rename files/mygui/{openmw.pointer.xml => openmw_pointer.xml} (100%) diff --git a/apps/openmw/CMakeLists.txt b/apps/openmw/CMakeLists.txt index b9ea8041d6..1870a93f82 100644 --- a/apps/openmw/CMakeLists.txt +++ b/apps/openmw/CMakeLists.txt @@ -29,7 +29,7 @@ add_openmw_dir (mwgui map_window window_pinnable_base cursorreplace tooltips scrollwindow bookwindow list formatting inventorywindow container hud countdialog tradewindow settingswindow confirmationdialog alchemywindow referenceinterface spellwindow mainmenu quickkeysmenu - itemselection spellbuyingwindow loadingscreen + itemselection spellbuyingwindow loadingscreen levelupdialog ) add_openmw_dir (mwdialogue diff --git a/apps/openmw/mwgui/levelupdialog.cpp b/apps/openmw/mwgui/levelupdialog.cpp new file mode 100644 index 0000000000..9f57a2bdde --- /dev/null +++ b/apps/openmw/mwgui/levelupdialog.cpp @@ -0,0 +1,63 @@ +#include "levelupdialog.hpp" + +#include + +#include "../mwbase/windowmanager.hpp" +#include "../mwbase/environment.hpp" + +namespace MWGui +{ + + LevelupDialog::LevelupDialog(MWBase::WindowManager &parWindowManager) + : WindowBase("openmw_levelup_dialog.layout", parWindowManager) + { + getWidget(mOkButton, "OkButton"); + getWidget(mClassImage, "ClassImage"); + getWidget(mLevelText, "LevelText"); + + mOkButton->eventMouseButtonClick += MyGUI::newDelegate(this, &LevelupDialog::onOkButtonClicked); + + for (int i=1; i<9; ++i) + { + MyGUI::TextBox* t; + getWidget(t, "AttribVal" + boost::lexical_cast(i)); + + MyGUI::Button* b; + getWidget(b, "Attrib" + boost::lexical_cast(i)); + b->setUserData (i-1); + b->eventMouseButtonClick += MyGUI::newDelegate(this, &LevelupDialog::onAttributeClicked); + + mAttributeValues.push_back(t); + + getWidget(t, "AttribMultiplier" + boost::lexical_cast(i)); + + t->setCaption("x2"); + mAttributeMultipliers.push_back(t); + } + + center(); + + open(); + } + + void LevelupDialog::open() + { + center(); + + mClassImage->setImageTexture ("textures\\levelup\\acrobat.dds"); + + /// \todo replace this with INI-imported texts + int level = 2; + mLevelText->setCaptionWithReplacing("#{sLevelUpMenu1} " + boost::lexical_cast(level)); + } + + void LevelupDialog::onOkButtonClicked (MyGUI::Widget* sender) + { + MWBase::Environment::get().getWindowManager ()->messageBox("#{sNotifyMessage36}", std::vector()); + } + + void LevelupDialog::onAttributeClicked (MyGUI::Widget *sender) + { + int index = *sender->getUserData(); + } +} diff --git a/apps/openmw/mwgui/levelupdialog.hpp b/apps/openmw/mwgui/levelupdialog.hpp new file mode 100644 index 0000000000..181868e9ec --- /dev/null +++ b/apps/openmw/mwgui/levelupdialog.hpp @@ -0,0 +1,30 @@ +#ifndef MWGUI_LEVELUPDIALOG_H +#define MWGUI_LEVELUPDIALOG_H + +#include "window_base.hpp" + +namespace MWGui +{ + + class LevelupDialog : public WindowBase + { + public: + LevelupDialog(MWBase::WindowManager& parWindowManager); + + virtual void open(); + + private: + MyGUI::Button* mOkButton; + MyGUI::ImageBox* mClassImage; + MyGUI::TextBox* mLevelText; + + std::vector mAttributeValues; + std::vector mAttributeMultipliers; + + void onOkButtonClicked (MyGUI::Widget* sender); + void onAttributeClicked (MyGUI::Widget* sender); + }; + +} + +#endif diff --git a/apps/openmw/mwgui/mode.hpp b/apps/openmw/mwgui/mode.hpp index 7e1adcf8bd..eb2c52b26f 100644 --- a/apps/openmw/mwgui/mode.hpp +++ b/apps/openmw/mwgui/mode.hpp @@ -22,6 +22,8 @@ namespace MWGui GM_Rest, GM_SpellBuying, + GM_Levelup, + // Startup character creation dialogs GM_Name, GM_Race, diff --git a/apps/openmw/mwgui/windowmanagerimp.cpp b/apps/openmw/mwgui/windowmanagerimp.cpp index 99f476574c..670f6122e2 100644 --- a/apps/openmw/mwgui/windowmanagerimp.cpp +++ b/apps/openmw/mwgui/windowmanagerimp.cpp @@ -44,6 +44,7 @@ #include "spellwindow.hpp" #include "quickkeysmenu.hpp" #include "loadingscreen.hpp" +#include "levelupdialog.hpp" using namespace MWGui; @@ -147,6 +148,7 @@ WindowManager::WindowManager( mAlchemyWindow = new AlchemyWindow(*this); mSpellWindow = new SpellWindow(*this); mQuickKeysMenu = new QuickKeysMenu(*this); + mLevelupDialog = new LevelupDialog(*this); mLoadingScreen = new LoadingScreen(mOgre->getScene (), mOgre->getWindow (), *this); mLoadingScreen->onResChange (w,h); @@ -200,6 +202,7 @@ WindowManager::~WindowManager() delete mAlchemyWindow; delete mSpellWindow; delete mLoadingScreen; + delete mLevelupDialog; cleanupGarbage(); diff --git a/apps/openmw/mwgui/windowmanagerimp.hpp b/apps/openmw/mwgui/windowmanagerimp.hpp index e16b03e43d..09d2f0c7d6 100644 --- a/apps/openmw/mwgui/windowmanagerimp.hpp +++ b/apps/openmw/mwgui/windowmanagerimp.hpp @@ -62,6 +62,7 @@ namespace MWGui class AlchemyWindow; class QuickKeysMenu; class LoadingScreen; + class LevelupDialog; class WindowManager : public MWBase::WindowManager { @@ -224,6 +225,7 @@ namespace MWGui SpellWindow* mSpellWindow; QuickKeysMenu* mQuickKeysMenu; LoadingScreen* mLoadingScreen; + LevelupDialog* mLevelupDialog; CharacterCreation* mCharGen; diff --git a/files/mygui/CMakeLists.txt b/files/mygui/CMakeLists.txt index fdf447e690..55230fa76a 100644 --- a/files/mygui/CMakeLists.txt +++ b/files/mygui/CMakeLists.txt @@ -35,7 +35,7 @@ set(MYGUI_FILES openmw_dialogue_window.layout openmw_dialogue_window_skin.xml openmw_edit.skin.xml - openmw.font.xml + openmw_font.xml openmw_hud_box.skin.xml openmw_hud_energybar.skin.xml openmw_hud.layout @@ -51,7 +51,7 @@ set(MYGUI_FILES openmw_map_window.layout openmw_map_window_skin.xml openmw_messagebox.layout - openmw.pointer.xml + openmw_pointer.xml openmw_progress.skin.xml openmw_resources.xml openmw_scroll.layout @@ -72,6 +72,7 @@ set(MYGUI_FILES openmw_magicselection_dialog.layout openmw_spell_buying_window.layout openmw_loading_screen.layout + openmw_levelup_dialog.layout smallbars.png VeraMono.ttf markers.png diff --git a/files/mygui/openmw.font.xml b/files/mygui/openmw_font.xml similarity index 100% rename from files/mygui/openmw.font.xml rename to files/mygui/openmw_font.xml diff --git a/files/mygui/openmw_levelup_dialog.layout b/files/mygui/openmw_levelup_dialog.layout new file mode 100644 index 0000000000..6525a1e410 --- /dev/null +++ b/files/mygui/openmw_levelup_dialog.layout @@ -0,0 +1,146 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/files/mygui/openmw.pointer.xml b/files/mygui/openmw_pointer.xml similarity index 100% rename from files/mygui/openmw.pointer.xml rename to files/mygui/openmw_pointer.xml From 76b494100e367ecbe5ae80d5cf67f710fd235f6d Mon Sep 17 00:00:00 2001 From: scrawl Date: Sat, 15 Sep 2012 17:12:42 +0200 Subject: [PATCH 37/84] finished? --- apps/openmw/mwbase/windowmanager.hpp | 2 +- apps/openmw/mwgui/charactercreation.cpp | 8 +- apps/openmw/mwgui/charactercreation.hpp | 14 +-- apps/openmw/mwgui/hud.cpp | 2 +- apps/openmw/mwgui/hud.hpp | 2 +- apps/openmw/mwgui/levelupdialog.cpp | 145 +++++++++++++++++++++- apps/openmw/mwgui/levelupdialog.hpp | 9 ++ apps/openmw/mwgui/review.cpp | 6 +- apps/openmw/mwgui/review.hpp | 6 +- apps/openmw/mwgui/stats_window.cpp | 16 ++- apps/openmw/mwgui/stats_window.hpp | 2 +- apps/openmw/mwgui/windowmanagerimp.cpp | 7 +- apps/openmw/mwgui/windowmanagerimp.hpp | 4 +- apps/openmw/mwinput/inputmanagerimp.cpp | 9 ++ apps/openmw/mwinput/inputmanagerimp.hpp | 1 + apps/openmw/mwmechanics/actors.cpp | 2 +- apps/openmw/mwmechanics/creaturestats.cpp | 35 ++++-- apps/openmw/mwmechanics/creaturestats.hpp | 29 +++-- apps/openmw/mwmechanics/npcstats.cpp | 70 ++++++++++- apps/openmw/mwmechanics/npcstats.hpp | 11 ++ apps/openmw/mwscript/docs/vmformat.txt | 6 +- apps/openmw/mwscript/statsextensions.cpp | 50 ++++++++ files/mygui/openmw_levelup_dialog.layout | 10 +- 23 files changed, 380 insertions(+), 66 deletions(-) diff --git a/apps/openmw/mwbase/windowmanager.hpp b/apps/openmw/mwbase/windowmanager.hpp index 58fe180e91..6e4c106251 100644 --- a/apps/openmw/mwbase/windowmanager.hpp +++ b/apps/openmw/mwbase/windowmanager.hpp @@ -118,7 +118,7 @@ namespace MWBase /// Set value for the given ID. virtual void setValue (const std::string& id, const MWMechanics::Stat& value) = 0; virtual void setValue (int parSkill, const MWMechanics::Stat& value) = 0; - virtual void setValue (const std::string& id, const MWMechanics::DynamicStat& value) = 0; + virtual void setValue (const std::string& id, const MWMechanics::DynamicStat& value) = 0; virtual void setValue (const std::string& id, const std::string& value) = 0; virtual void setValue (const std::string& id, int value) = 0; diff --git a/apps/openmw/mwgui/charactercreation.cpp b/apps/openmw/mwgui/charactercreation.cpp index 7d63f69220..0005b78ad4 100644 --- a/apps/openmw/mwgui/charactercreation.cpp +++ b/apps/openmw/mwgui/charactercreation.cpp @@ -151,7 +151,7 @@ void CharacterCreation::setValue (const std::string& id, const MWMechanics::Stat } } -void CharacterCreation::setValue (const std::string& id, const MWMechanics::DynamicStat& value) +void CharacterCreation::setValue (const std::string& id, const MWMechanics::DynamicStat& value) { if (mReviewDialog) { @@ -294,17 +294,17 @@ void CharacterCreation::spawnDialog(const char id) } } -void CharacterCreation::setPlayerHealth (const MWMechanics::DynamicStat& value) +void CharacterCreation::setPlayerHealth (const MWMechanics::DynamicStat& value) { mPlayerHealth = value; } -void CharacterCreation::setPlayerMagicka (const MWMechanics::DynamicStat& value) +void CharacterCreation::setPlayerMagicka (const MWMechanics::DynamicStat& value) { mPlayerMagicka = value; } -void CharacterCreation::setPlayerFatigue (const MWMechanics::DynamicStat& value) +void CharacterCreation::setPlayerFatigue (const MWMechanics::DynamicStat& value) { mPlayerFatigue = value; } diff --git a/apps/openmw/mwgui/charactercreation.hpp b/apps/openmw/mwgui/charactercreation.hpp index d65763d0cd..28ced2e70a 100644 --- a/apps/openmw/mwgui/charactercreation.hpp +++ b/apps/openmw/mwgui/charactercreation.hpp @@ -35,14 +35,14 @@ namespace MWGui //Show a dialog void spawnDialog(const char id); - void setPlayerHealth (const MWMechanics::DynamicStat& value); + void setPlayerHealth (const MWMechanics::DynamicStat& value); - void setPlayerMagicka (const MWMechanics::DynamicStat& value); + void setPlayerMagicka (const MWMechanics::DynamicStat& value); - void setPlayerFatigue (const MWMechanics::DynamicStat& value); + void setPlayerFatigue (const MWMechanics::DynamicStat& value); void setValue (const std::string& id, const MWMechanics::Stat& value); - void setValue (const std::string& id, const MWMechanics::DynamicStat& value); + void setValue (const std::string& id, const MWMechanics::DynamicStat& value); void setValue(const ESM::Skill::SkillEnum parSkill, const MWMechanics::Stat& value); void configureSkills (const SkillList& major, const SkillList& minor); @@ -65,9 +65,9 @@ namespace MWGui std::string mPlayerRaceId; std::string mPlayerBirthSignId; ESM::Class mPlayerClass; - MWMechanics::DynamicStat mPlayerHealth; - MWMechanics::DynamicStat mPlayerMagicka; - MWMechanics::DynamicStat mPlayerFatigue; + MWMechanics::DynamicStat mPlayerHealth; + MWMechanics::DynamicStat mPlayerMagicka; + MWMechanics::DynamicStat mPlayerFatigue; //Class generation vars unsigned mGenerateClassStep; // Keeps track of current step in Generate Class dialog diff --git a/apps/openmw/mwgui/hud.cpp b/apps/openmw/mwgui/hud.cpp index b148335537..72dc0c7fbe 100644 --- a/apps/openmw/mwgui/hud.cpp +++ b/apps/openmw/mwgui/hud.cpp @@ -161,7 +161,7 @@ void HUD::setEffect(const char *img) mEffect1->setImageTexture(img); } -void HUD::setValue(const std::string& id, const MWMechanics::DynamicStat& value) +void HUD::setValue(const std::string& id, const MWMechanics::DynamicStat& value) { static const char *ids[] = { diff --git a/apps/openmw/mwgui/hud.hpp b/apps/openmw/mwgui/hud.hpp index de4228e87c..013ad59f05 100644 --- a/apps/openmw/mwgui/hud.hpp +++ b/apps/openmw/mwgui/hud.hpp @@ -14,7 +14,7 @@ namespace MWGui public: HUD(int width, int height, int fpsLevel, DragAndDrop* dragAndDrop); void setEffect(const char *img); - void setValue (const std::string& id, const MWMechanics::DynamicStat& value); + void setValue (const std::string& id, const MWMechanics::DynamicStat& value); void setFPS(float fps); void setTriangleCount(unsigned int count); void setBatchCount(unsigned int count); diff --git a/apps/openmw/mwgui/levelupdialog.cpp b/apps/openmw/mwgui/levelupdialog.cpp index 9f57a2bdde..610c22bf78 100644 --- a/apps/openmw/mwgui/levelupdialog.cpp +++ b/apps/openmw/mwgui/levelupdialog.cpp @@ -4,6 +4,17 @@ #include "../mwbase/windowmanager.hpp" #include "../mwbase/environment.hpp" +#include "../mwbase/world.hpp" + +#include "../mwworld/player.hpp" +#include "../mwworld/class.hpp" + +#include "../mwmechanics/creaturestats.hpp" +#include "../mwmechanics/npcstats.hpp" +#include "../mwmechanics/stat.hpp" + +#include +#include namespace MWGui { @@ -26,6 +37,7 @@ namespace MWGui getWidget(b, "Attrib" + boost::lexical_cast(i)); b->setUserData (i-1); b->eventMouseButtonClick += MyGUI::newDelegate(this, &LevelupDialog::onAttributeClicked); + mAttributes.push_back(b); mAttributeValues.push_back(t); @@ -35,29 +47,152 @@ namespace MWGui mAttributeMultipliers.push_back(t); } + int curX = mMainWidget->getWidth()/2 - (16 + 2) * 1.5; + for (int i=0; i<3; ++i) + { + MyGUI::ImageBox* image = mMainWidget->createWidget("ImageBox", MyGUI::IntCoord(curX,250,16,16), MyGUI::Align::Default); + image->setImageTexture ("icons\\tx_goldicon.dds"); + curX += 24+2; + mCoins.push_back(image); + } + center(); + } + + void LevelupDialog::setAttributeValues() + { + MWWorld::Ptr player = MWBase::Environment::get().getWorld ()->getPlayer().getPlayer(); + MWMechanics::CreatureStats& creatureStats = MWWorld::Class::get(player).getCreatureStats (player); + MWMechanics::NpcStats& pcStats = MWWorld::Class::get(player).getNpcStats (player); + + for (int i=0; i<8; ++i) + { + int val = creatureStats.getAttribute (i).getBase (); + if (std::find(mSpentAttributes.begin(), mSpentAttributes.end(), i) != mSpentAttributes.end()) + { + val += pcStats.getLevelupAttributeMultiplier (i); + } + + if (val >= 100) + val = 100; + + mAttributeValues[i]->setCaption(boost::lexical_cast(val)); + } + } + + + void LevelupDialog::resetCoins () + { + int curX = mMainWidget->getWidth()/2 - (16 + 2) * 1.5; + for (int i=0; i<3; ++i) + { + MyGUI::ImageBox* image = mCoins[i]; + image->setCoord(MyGUI::IntCoord(curX,250,16,16)); + curX += 24+2; + } + } + + void LevelupDialog::assignCoins () + { + resetCoins(); + for (unsigned int i=0; igetCaption() == "" ? 0 : 30; + + MyGUI::IntPoint pos = mAttributes[attribute]->getAbsolutePosition() - mMainWidget->getAbsolutePosition() - MyGUI::IntPoint(24+xdiff,-4); + image->setPosition(pos); + } - open(); + setAttributeValues(); } void LevelupDialog::open() { + MWWorld::Ptr player = MWBase::Environment::get().getWorld ()->getPlayer().getPlayer(); + MWMechanics::CreatureStats& creatureStats = MWWorld::Class::get(player).getCreatureStats (player); + MWMechanics::NpcStats& pcStats = MWWorld::Class::get(player).getNpcStats (player); + center(); - mClassImage->setImageTexture ("textures\\levelup\\acrobat.dds"); + mSpentAttributes.clear(); + resetCoins(); + + setAttributeValues(); + + // set class image + const ESM::Class& playerClass = MWBase::Environment::get().getWorld ()->getPlayer ().getClass (); + // retrieve the ID to this class + std::string classId; + std::map list = MWBase::Environment::get().getWorld()->getStore ().classes.list; + for (std::map::iterator it = list.begin(); it != list.end(); ++it) + { + if (playerClass.name == it->second.name) + classId = it->first; + } + mClassImage->setImageTexture ("textures\\levelup\\" + classId + ".dds"); /// \todo replace this with INI-imported texts - int level = 2; + int level = creatureStats.getLevel ()+1; mLevelText->setCaptionWithReplacing("#{sLevelUpMenu1} " + boost::lexical_cast(level)); + + for (int i=0; i<8; ++i) + { + MyGUI::TextBox* text = mAttributeMultipliers[i]; + int mult = pcStats.getLevelupAttributeMultiplier (i); + text->setCaption(mult <= 1 ? "" : "x" + boost::lexical_cast(mult)); + } } void LevelupDialog::onOkButtonClicked (MyGUI::Widget* sender) { - MWBase::Environment::get().getWindowManager ()->messageBox("#{sNotifyMessage36}", std::vector()); + MWWorld::Ptr player = MWBase::Environment::get().getWorld ()->getPlayer().getPlayer(); + MWMechanics::CreatureStats& creatureStats = MWWorld::Class::get(player).getCreatureStats (player); + MWMechanics::NpcStats& pcStats = MWWorld::Class::get(player).getNpcStats (player); + + if (mSpentAttributes.size() < 3) + MWBase::Environment::get().getWindowManager ()->messageBox("#{sNotifyMessage36}", std::vector()); + else + { + // increase attributes + for (int i=0; i<3; ++i) + { + MWMechanics::Stat& attribute = creatureStats.getAttribute(mSpentAttributes[i]); + attribute.setBase (attribute.getBase () + pcStats.getLevelupAttributeMultiplier (mSpentAttributes[i])); + + if (attribute.getBase() >= 100) + attribute.setBase(100); + } + + // "When you gain a level, in addition to increasing three primary attributes, your Health + // will automatically increase by 10% of your Endurance attribute. If you increased Endurance this level, + // the Health increase is calculated from the increased Endurance" + creatureStats.increaseLevelHealthBonus (creatureStats.getAttribute(ESM::Attribute::Endurance).getBase() * 0.1f); + + creatureStats.setLevel (creatureStats.getLevel()+1); + pcStats.levelUp (); + + mWindowManager.removeGuiMode (GM_Rest); + } + } void LevelupDialog::onAttributeClicked (MyGUI::Widget *sender) { - int index = *sender->getUserData(); + int attribute = *sender->getUserData(); + + std::vector::iterator found = std::find(mSpentAttributes.begin(), mSpentAttributes.end(), attribute); + if (found != mSpentAttributes.end()) + mSpentAttributes.erase (found); + else + { + if (mSpentAttributes.size() == 3) + mSpentAttributes[2] = attribute; + else + mSpentAttributes.push_back(attribute); + } + assignCoins(); } } diff --git a/apps/openmw/mwgui/levelupdialog.hpp b/apps/openmw/mwgui/levelupdialog.hpp index 181868e9ec..f5b24530d1 100644 --- a/apps/openmw/mwgui/levelupdialog.hpp +++ b/apps/openmw/mwgui/levelupdialog.hpp @@ -18,11 +18,20 @@ namespace MWGui MyGUI::ImageBox* mClassImage; MyGUI::TextBox* mLevelText; + std::vector mAttributes; std::vector mAttributeValues; std::vector mAttributeMultipliers; + std::vector mCoins; + + std::vector mSpentAttributes; void onOkButtonClicked (MyGUI::Widget* sender); void onAttributeClicked (MyGUI::Widget* sender); + + void assignCoins(); + void resetCoins(); + + void setAttributeValues(); }; } diff --git a/apps/openmw/mwgui/review.cpp b/apps/openmw/mwgui/review.cpp index 76b211b18e..411fead089 100644 --- a/apps/openmw/mwgui/review.cpp +++ b/apps/openmw/mwgui/review.cpp @@ -134,21 +134,21 @@ void ReviewDialog::setBirthSign(const std::string& signId) } } -void ReviewDialog::setHealth(const MWMechanics::DynamicStat& value) +void ReviewDialog::setHealth(const MWMechanics::DynamicStat& value) { mHealth->setValue(value.getCurrent(), value.getModified()); std::string valStr = boost::lexical_cast(value.getCurrent()) + "/" + boost::lexical_cast(value.getModified()); mHealth->setUserString("Caption_HealthDescription", "#{sHealthDesc}\n" + valStr); } -void ReviewDialog::setMagicka(const MWMechanics::DynamicStat& value) +void ReviewDialog::setMagicka(const MWMechanics::DynamicStat& value) { mMagicka->setValue(value.getCurrent(), value.getModified()); std::string valStr = boost::lexical_cast(value.getCurrent()) + "/" + boost::lexical_cast(value.getModified()); mMagicka->setUserString("Caption_HealthDescription", "#{sIntDesc}\n" + valStr); } -void ReviewDialog::setFatigue(const MWMechanics::DynamicStat& value) +void ReviewDialog::setFatigue(const MWMechanics::DynamicStat& value) { mFatigue->setValue(value.getCurrent(), value.getModified()); std::string valStr = boost::lexical_cast(value.getCurrent()) + "/" + boost::lexical_cast(value.getModified()); diff --git a/apps/openmw/mwgui/review.hpp b/apps/openmw/mwgui/review.hpp index 058e3cff38..2b0740234e 100644 --- a/apps/openmw/mwgui/review.hpp +++ b/apps/openmw/mwgui/review.hpp @@ -35,9 +35,9 @@ namespace MWGui void setClass(const ESM::Class& class_); void setBirthSign (const std::string &signId); - void setHealth(const MWMechanics::DynamicStat& value); - void setMagicka(const MWMechanics::DynamicStat& value); - void setFatigue(const MWMechanics::DynamicStat& value); + void setHealth(const MWMechanics::DynamicStat& value); + void setMagicka(const MWMechanics::DynamicStat& value); + void setFatigue(const MWMechanics::DynamicStat& value); void setAttribute(ESM::Attribute::AttributeID attributeId, const MWMechanics::Stat& value); diff --git a/apps/openmw/mwgui/stats_window.cpp b/apps/openmw/mwgui/stats_window.cpp index ffbfd7d78e..88bc3dc903 100644 --- a/apps/openmw/mwgui/stats_window.cpp +++ b/apps/openmw/mwgui/stats_window.cpp @@ -95,6 +95,7 @@ void StatsWindow::setBar(const std::string& name, const std::string& tname, int getWidget(pt, name); pt->setProgressRange(max); pt->setProgressPosition(val); + std::cout << "set bar " << name << val << " " << max << std::endl; std::stringstream out; out << val << "/" << max; @@ -137,7 +138,7 @@ void StatsWindow::setValue (const std::string& id, const MWMechanics::Stat& } } -void StatsWindow::setValue (const std::string& id, const MWMechanics::DynamicStat& value) +void StatsWindow::setValue (const std::string& id, const MWMechanics::DynamicStat& value) { static const char *ids[] = { @@ -150,7 +151,7 @@ void StatsWindow::setValue (const std::string& id, const MWMechanics::DynamicSta if (ids[i]==id) { std::string id (ids[i]); - setBar (id, id + "T", value.getCurrent(), value.getModified()); + setBar (id, id + "T", static_cast(value.getCurrent()), static_cast(value.getModified())); // health, magicka, fatigue tooltip MyGUI::Widget* w; @@ -236,12 +237,21 @@ void StatsWindow::configureSkills (const std::vector& major, const std::vec void StatsWindow::onFrame () { - if (mMainWidget->getVisible()) + if (!mMainWidget->getVisible()) return; MWWorld::Ptr player = MWBase::Environment::get().getWorld()->getPlayer().getPlayer(); MWMechanics::NpcStats PCstats = MWWorld::Class::get(player).getNpcStats(player); + // level progress + MyGUI::Widget* levelWidget; + for (int i=0; i<2; ++i) + { + getWidget(levelWidget, i==0 ? "Level_str" : "LevelText"); + levelWidget->setUserString("RangePosition_LevelProgress", boost::lexical_cast(PCstats.getLevelProgress())); + levelWidget->setUserString("Caption_LevelProgressText", boost::lexical_cast(PCstats.getLevelProgress()) + "/10"); + } + setFactions(PCstats.getFactionRanks()); setBirthSign(MWBase::Environment::get().getWorld()->getPlayer().getBirthsign()); diff --git a/apps/openmw/mwgui/stats_window.hpp b/apps/openmw/mwgui/stats_window.hpp index 73c4706dd9..75f8c568bf 100644 --- a/apps/openmw/mwgui/stats_window.hpp +++ b/apps/openmw/mwgui/stats_window.hpp @@ -32,7 +32,7 @@ namespace MWGui /// Set value for the given ID. void setValue (const std::string& id, const MWMechanics::Stat& value); - void setValue (const std::string& id, const MWMechanics::DynamicStat& value); + void setValue (const std::string& id, const MWMechanics::DynamicStat& value); void setValue (const std::string& id, const std::string& value); void setValue (const std::string& id, int value); void setValue(const ESM::Skill::SkillEnum parSkill, const MWMechanics::Stat& value); diff --git a/apps/openmw/mwgui/windowmanagerimp.cpp b/apps/openmw/mwgui/windowmanagerimp.cpp index 670f6122e2..465f2c239f 100644 --- a/apps/openmw/mwgui/windowmanagerimp.cpp +++ b/apps/openmw/mwgui/windowmanagerimp.cpp @@ -250,6 +250,7 @@ void WindowManager::updateVisible() mAlchemyWindow->setVisible(false); mSpellWindow->setVisible(false); mQuickKeysMenu->setVisible(false); + mLevelupDialog->setVisible(false); mHud->setVisible(true); @@ -301,6 +302,9 @@ void WindowManager::updateVisible() case GM_Alchemy: mAlchemyWindow->setVisible(true); break; + case GM_Rest: + mLevelupDialog->setVisible(true); + break; case GM_Name: case GM_Race: case GM_Class: @@ -398,8 +402,9 @@ void WindowManager::setValue (int parSkill, const MWMechanics::Stat& valu mPlayerSkillValues[parSkill] = value; } -void WindowManager::setValue (const std::string& id, const MWMechanics::DynamicStat& value) +void WindowManager::setValue (const std::string& id, const MWMechanics::DynamicStat& value) { + std::cout << " set value " << id << value.getModified () << std::endl; mStatsWindow->setValue (id, value); mHud->setValue (id, value); mCharGen->setValue(id, value); diff --git a/apps/openmw/mwgui/windowmanagerimp.hpp b/apps/openmw/mwgui/windowmanagerimp.hpp index 09d2f0c7d6..131029ed47 100644 --- a/apps/openmw/mwgui/windowmanagerimp.hpp +++ b/apps/openmw/mwgui/windowmanagerimp.hpp @@ -118,7 +118,7 @@ namespace MWGui ///< Set value for the given ID. virtual void setValue (const std::string& id, const MWMechanics::Stat& value); virtual void setValue (int parSkill, const MWMechanics::Stat& value); - virtual void setValue (const std::string& id, const MWMechanics::DynamicStat& value); + virtual void setValue (const std::string& id, const MWMechanics::DynamicStat& value); virtual void setValue (const std::string& id, const std::string& value); virtual void setValue (const std::string& id, int value); @@ -243,7 +243,7 @@ namespace MWGui std::map > mPlayerAttributes; SkillList mPlayerMajorSkills, mPlayerMinorSkills; std::map > mPlayerSkillValues; - MWMechanics::DynamicStat mPlayerHealth, mPlayerMagicka, mPlayerFatigue; + MWMechanics::DynamicStat mPlayerHealth, mPlayerMagicka, mPlayerFatigue; MyGUI::Gui *mGui; // Gui diff --git a/apps/openmw/mwinput/inputmanagerimp.cpp b/apps/openmw/mwinput/inputmanagerimp.cpp index b198785d2f..724dccd8eb 100644 --- a/apps/openmw/mwinput/inputmanagerimp.cpp +++ b/apps/openmw/mwinput/inputmanagerimp.cpp @@ -190,6 +190,9 @@ namespace MWInput case A_ToggleWeapon: toggleWeapon (); break; + case A_Rest: + rest(); + break; case A_ToggleSpell: toggleSpell (); break; @@ -543,6 +546,12 @@ namespace MWInput } } + void InputManager::rest() + { + if (!mWindows.isGuiMode ()) + mWindows.pushGuiMode (MWGui::GM_Rest); + } + void InputManager::screenshot() { mEngine.screenshot(); diff --git a/apps/openmw/mwinput/inputmanagerimp.hpp b/apps/openmw/mwinput/inputmanagerimp.hpp index 7d03f1d5bf..5e6169f689 100644 --- a/apps/openmw/mwinput/inputmanagerimp.hpp +++ b/apps/openmw/mwinput/inputmanagerimp.hpp @@ -168,6 +168,7 @@ namespace MWInput void toggleWalking(); void toggleAutoMove(); void exitNow(); + void rest(); void quickKey (int index); void showQuickKeysMenu(); diff --git a/apps/openmw/mwmechanics/actors.cpp b/apps/openmw/mwmechanics/actors.cpp index bd037df9f0..b4cc40fec2 100644 --- a/apps/openmw/mwmechanics/actors.cpp +++ b/apps/openmw/mwmechanics/actors.cpp @@ -68,7 +68,7 @@ namespace MWMechanics creatureStats.getMagicEffects().get (EffectKey (84)).mMagnitude * 0.1 + 0.5; creatureStats.getHealth().setBase( - static_cast (0.5 * (strength + endurance))); + static_cast (0.5 * (strength + endurance)) + creatureStats.getLevelHealthBonus ()); creatureStats.getMagicka().setBase( static_cast (intelligence + magickaFactor * intelligence)); diff --git a/apps/openmw/mwmechanics/creaturestats.cpp b/apps/openmw/mwmechanics/creaturestats.cpp index 91a9225fec..fc05231412 100644 --- a/apps/openmw/mwmechanics/creaturestats.cpp +++ b/apps/openmw/mwmechanics/creaturestats.cpp @@ -9,6 +9,21 @@ namespace MWMechanics { + CreatureStats::CreatureStats() + : mLevelHealthBonus(0.f) + { + } + + void CreatureStats::increaseLevelHealthBonus (float value) + { + mLevelHealthBonus += value; + } + + float CreatureStats::getLevelHealthBonus () const + { + return mLevelHealthBonus; + } + const AiSequence& CreatureStats::getAiSequence() const { return mAiSequence; @@ -40,17 +55,17 @@ namespace MWMechanics return mAttributes[index]; } - const DynamicStat &CreatureStats::getHealth() const + const DynamicStat &CreatureStats::getHealth() const { return mDynamic[0]; } - const DynamicStat &CreatureStats::getMagicka() const + const DynamicStat &CreatureStats::getMagicka() const { return mDynamic[1]; } - const DynamicStat &CreatureStats::getFatigue() const + const DynamicStat &CreatureStats::getFatigue() const { return mDynamic[2]; } @@ -103,22 +118,22 @@ namespace MWMechanics return mAttributes[index]; } - DynamicStat &CreatureStats::getHealth() + DynamicStat &CreatureStats::getHealth() { return mDynamic[0]; } - DynamicStat &CreatureStats::getMagicka() + DynamicStat &CreatureStats::getMagicka() { return mDynamic[1]; } - DynamicStat &CreatureStats::getFatigue() + DynamicStat &CreatureStats::getFatigue() { return mDynamic[2]; } - DynamicStat &CreatureStats::getDynamic(int index) + DynamicStat &CreatureStats::getDynamic(int index) { if (index < 0 || index > 2) { throw std::runtime_error("dynamic stat index is out of range"); @@ -154,17 +169,17 @@ namespace MWMechanics mAttributes[index] = value; } - void CreatureStats::setHealth(const DynamicStat &value) + void CreatureStats::setHealth(const DynamicStat &value) { mDynamic[0] = value; } - void CreatureStats::setMagicka(const DynamicStat &value) + void CreatureStats::setMagicka(const DynamicStat &value) { mDynamic[1] = value; } - void CreatureStats::setFatigue(const DynamicStat &value) + void CreatureStats::setFatigue(const DynamicStat &value) { mDynamic[2] = value; } diff --git a/apps/openmw/mwmechanics/creaturestats.hpp b/apps/openmw/mwmechanics/creaturestats.hpp index a6fb6779af..7a1e46f56e 100644 --- a/apps/openmw/mwmechanics/creaturestats.hpp +++ b/apps/openmw/mwmechanics/creaturestats.hpp @@ -19,7 +19,7 @@ namespace MWMechanics class CreatureStats { Stat mAttributes[8]; - DynamicStat mDynamic[3]; // health, magicka, fatigue + DynamicStat mDynamic[3]; // health, magicka, fatigue int mLevel; Spells mSpells; ActiveSpells mActiveSpells; @@ -30,15 +30,18 @@ namespace MWMechanics int mAlarm; AiSequence mAiSequence; + float mLevelHealthBonus; + public: + CreatureStats(); const Stat & getAttribute(int index) const; - const DynamicStat & getHealth() const; + const DynamicStat & getHealth() const; - const DynamicStat & getMagicka() const; + const DynamicStat & getMagicka() const; - const DynamicStat & getFatigue() const; + const DynamicStat & getFatigue() const; const Spells & getSpells() const; @@ -59,13 +62,13 @@ namespace MWMechanics Stat & getAttribute(int index); - DynamicStat & getHealth(); + DynamicStat & getHealth(); - DynamicStat & getMagicka(); + DynamicStat & getMagicka(); - DynamicStat & getFatigue(); + DynamicStat & getFatigue(); - DynamicStat & getDynamic(int index); + DynamicStat & getDynamic(int index); Spells & getSpells(); @@ -76,11 +79,11 @@ namespace MWMechanics void setAttribute(int index, const Stat &value); - void setHealth(const DynamicStat &value); + void setHealth(const DynamicStat &value); - void setMagicka(const DynamicStat &value); + void setMagicka(const DynamicStat &value); - void setFatigue(const DynamicStat &value); + void setFatigue(const DynamicStat &value); void setSpells(const Spells &spells); @@ -104,6 +107,10 @@ namespace MWMechanics float getFatigueTerm() const; ///< Return effective fatigue + + // small hack to allow the fact that Health permanently increases by 10% of endurance on each level up + void increaseLevelHealthBonus(float value); + float getLevelHealthBonus() const; }; } diff --git a/apps/openmw/mwmechanics/npcstats.cpp b/apps/openmw/mwmechanics/npcstats.cpp index d2908e26e2..fc99c44a8f 100644 --- a/apps/openmw/mwmechanics/npcstats.cpp +++ b/apps/openmw/mwmechanics/npcstats.cpp @@ -12,10 +12,16 @@ #include "../mwbase/environment.hpp" #include "../mwbase/world.hpp" +#include "../mwbase/windowmanager.hpp" MWMechanics::NpcStats::NpcStats() : mMovementFlags (0), mDrawState (DrawState_Nothing) -{} +, mLevelProgress(0) +{ + mSkillIncreases.resize (ESM::Attribute::Length); + for (int i=0; i (base)!=level) + { + // skill leveled up base = level+1; + // if this is a major or minor skill of the class, increase level progress + //bool levelProgress = false; + bool levelProgress = true; + for (int i=0; i<2; ++i) + for (int j=0; j<5; ++j) + { + int skill = class_.data.skills[j][i]; + if (skill == skillIndex) + levelProgress = true; + } + + if (!levelProgress) + std::cout <<"This is not a level skilL" << std::endl; + + mLevelProgress += levelProgress; + + // check the attribute this skill belongs to + const ESM::Skill* skill = MWBase::Environment::get().getWorld ()->getStore ().skills.find(skillIndex); + ++mSkillIncreases[skill->data.attribute]; + + if (mLevelProgress >= 10) + { + // levelup is possible now + MWBase::Environment::get().getWindowManager ()->messageBox ("#{sLevelUpMsg}", std::vector()); + } + } + getSkill (skillIndex).setBase (base); } + +int MWMechanics::NpcStats::getLevelProgress () const +{ + return mLevelProgress; +} + +void MWMechanics::NpcStats::levelUp() +{ + mLevelProgress -= 10; + for (int i=0; i #include #include +#include #include "stat.hpp" #include "drawstate.hpp" @@ -45,6 +46,10 @@ namespace MWMechanics unsigned int mMovementFlags; Stat mSkill[27]; + int mLevelProgress; // 0-10 + + std::vector mSkillIncreases; // number of skill increases for each attribute + public: NpcStats(); @@ -73,6 +78,12 @@ namespace MWMechanics void useSkill (int skillIndex, const ESM::Class& class_, int usageType = -1); ///< Increase skill by usage. + + int getLevelProgress() const; + + int getLevelupAttributeMultiplier(int attribute) const; + + void levelUp(); }; } diff --git a/apps/openmw/mwscript/docs/vmformat.txt b/apps/openmw/mwscript/docs/vmformat.txt index 59b9bca35b..8052c6a082 100644 --- a/apps/openmw/mwscript/docs/vmformat.txt +++ b/apps/openmw/mwscript/docs/vmformat.txt @@ -183,4 +183,8 @@ op 0x2000172: GetStartingAngle op 0x2000173: GetStartingAngle, explicit reference op 0x2000174: ToggleVanityMode op 0x2000175-0x200018B: Get controls disabled -opcodes 0x200018C-0x3ffffff unused +op 0x200018C: GetLevel +op 0x200018D: GetLevel, explicit reference +op 0x200018E: SetLevel +op 0x200018F: SetLevel, explicit reference +opcodes 0x200018F-0x3ffffff unused diff --git a/apps/openmw/mwscript/statsextensions.cpp b/apps/openmw/mwscript/statsextensions.cpp index 5113c9dbff..f49d684a5d 100644 --- a/apps/openmw/mwscript/statsextensions.cpp +++ b/apps/openmw/mwscript/statsextensions.cpp @@ -32,6 +32,42 @@ namespace MWScript { namespace Stats { + template + class OpGetLevel : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + MWWorld::Ptr ptr = R()(runtime); + + Interpreter::Type_Integer value = + MWWorld::Class::get (ptr) + .getCreatureStats (ptr) + .getLevel(); + + runtime.push (value); + } + }; + + template + class OpSetLevel : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + MWWorld::Ptr ptr = R()(runtime); + + Interpreter::Type_Integer value = runtime[0].mInteger; + runtime.pop(); + + MWWorld::Class::get (ptr) + .getCreatureStats (ptr) + .setLevel(value); + } + }; + template class OpGetAttribute : public Interpreter::Opcode0 { @@ -592,6 +628,11 @@ namespace MWScript const int opcodeModDisposition = 0x200014d; const int opcodeModDispositionExplicit = 0x200014e; + const int opcodeGetLevel = 0x200018c; + const int opcodeGetLevelExplicit = 0x200018d; + const int opcodeSetLevel = 0x200018e; + const int opcodeSetLevelExplicit = 0x200018f; + void registerExtensions (Compiler::Extensions& extensions) { static const char *attributes[numberOfAttributes] = @@ -674,6 +715,9 @@ namespace MWScript extensions.registerInstruction("moddisposition","l",opcodeModDisposition, opcodeModDispositionExplicit); extensions.registerFunction("getpcrank",'l',"/S",opcodeGetPCRank,opcodeGetPCRankExplicit); + + extensions.registerInstruction("setlevel", "l", opcodeSetLevel, opcodeSetLevelExplicit); + extensions.registerFunction("getlevel", 'l', "", opcodeGetLevel, opcodeGetLevelExplicit); } void installOpcodes (Interpreter::Interpreter& interpreter) @@ -745,6 +789,12 @@ namespace MWScript interpreter.installSegment5(opcodeModDispositionExplicit,new OpModDisposition); interpreter.installSegment3(opcodeGetPCRank,new OpGetPCRank); interpreter.installSegment3(opcodeGetPCRankExplicit,new OpGetPCRank); + + interpreter.installSegment5 (opcodeGetLevel, new OpGetLevel); + interpreter.installSegment5 (opcodeGetLevelExplicit, new OpGetLevel); + interpreter.installSegment5 (opcodeSetLevel, new OpSetLevel); + interpreter.installSegment5 (opcodeSetLevelExplicit, new OpSetLevel); + } } } diff --git a/files/mygui/openmw_levelup_dialog.layout b/files/mygui/openmw_levelup_dialog.layout index 6525a1e410..86e65e99a9 100644 --- a/files/mygui/openmw_levelup_dialog.layout +++ b/files/mygui/openmw_levelup_dialog.layout @@ -4,7 +4,7 @@ - + @@ -31,7 +31,6 @@ - @@ -45,7 +44,6 @@ - @@ -59,7 +57,6 @@ - @@ -73,7 +70,6 @@ - @@ -88,7 +84,6 @@ - @@ -102,7 +97,6 @@ - @@ -116,7 +110,6 @@ - @@ -130,7 +123,6 @@ - From b34b894d6a743bbc423321f3ba72ce19f520a3eb Mon Sep 17 00:00:00 2001 From: scrawl Date: Sat, 15 Sep 2012 17:20:47 +0200 Subject: [PATCH 38/84] removed some debug stuff --- apps/openmw/mwgui/levelupdialog.cpp | 1 - apps/openmw/mwgui/stats_window.cpp | 1 - apps/openmw/mwgui/windowmanagerimp.cpp | 1 - apps/openmw/mwmechanics/npcstats.cpp | 11 ++--------- 4 files changed, 2 insertions(+), 12 deletions(-) diff --git a/apps/openmw/mwgui/levelupdialog.cpp b/apps/openmw/mwgui/levelupdialog.cpp index 610c22bf78..3616283d97 100644 --- a/apps/openmw/mwgui/levelupdialog.cpp +++ b/apps/openmw/mwgui/levelupdialog.cpp @@ -43,7 +43,6 @@ namespace MWGui getWidget(t, "AttribMultiplier" + boost::lexical_cast(i)); - t->setCaption("x2"); mAttributeMultipliers.push_back(t); } diff --git a/apps/openmw/mwgui/stats_window.cpp b/apps/openmw/mwgui/stats_window.cpp index 88bc3dc903..701c39b0d6 100644 --- a/apps/openmw/mwgui/stats_window.cpp +++ b/apps/openmw/mwgui/stats_window.cpp @@ -95,7 +95,6 @@ void StatsWindow::setBar(const std::string& name, const std::string& tname, int getWidget(pt, name); pt->setProgressRange(max); pt->setProgressPosition(val); - std::cout << "set bar " << name << val << " " << max << std::endl; std::stringstream out; out << val << "/" << max; diff --git a/apps/openmw/mwgui/windowmanagerimp.cpp b/apps/openmw/mwgui/windowmanagerimp.cpp index 465f2c239f..8f7c0d17a7 100644 --- a/apps/openmw/mwgui/windowmanagerimp.cpp +++ b/apps/openmw/mwgui/windowmanagerimp.cpp @@ -404,7 +404,6 @@ void WindowManager::setValue (int parSkill, const MWMechanics::Stat& valu void WindowManager::setValue (const std::string& id, const MWMechanics::DynamicStat& value) { - std::cout << " set value " << id << value.getModified () << std::endl; mStatsWindow->setValue (id, value); mHud->setValue (id, value); mCharGen->setValue(id, value); diff --git a/apps/openmw/mwmechanics/npcstats.cpp b/apps/openmw/mwmechanics/npcstats.cpp index fc99c44a8f..2980aed59a 100644 --- a/apps/openmw/mwmechanics/npcstats.cpp +++ b/apps/openmw/mwmechanics/npcstats.cpp @@ -128,10 +128,7 @@ float MWMechanics::NpcStats::getSkillGain (int skillIndex, const ESM::Class& cla throw std::runtime_error ("invalid skill specialisation factor"); } - //return 1.0 / (level +1) * (1.0 / (skillFactor)) * typeFactor * specialisationFactor; - - ///FIXME: TEST FOR FASTER LEVELLING - return 1.0 / (level +1) * (1.0 / (skillFactor/100)) * typeFactor * specialisationFactor; + return 1.0 / (level +1) * (1.0 / (skillFactor)) * typeFactor * specialisationFactor; } void MWMechanics::NpcStats::useSkill (int skillIndex, const ESM::Class& class_, int usageType) @@ -148,8 +145,7 @@ void MWMechanics::NpcStats::useSkill (int skillIndex, const ESM::Class& class_, base = level+1; // if this is a major or minor skill of the class, increase level progress - //bool levelProgress = false; - bool levelProgress = true; + bool levelProgress = false; for (int i=0; i<2; ++i) for (int j=0; j<5; ++j) { @@ -158,9 +154,6 @@ void MWMechanics::NpcStats::useSkill (int skillIndex, const ESM::Class& class_, levelProgress = true; } - if (!levelProgress) - std::cout <<"This is not a level skilL" << std::endl; - mLevelProgress += levelProgress; // check the attribute this skill belongs to From 234f8fa5d57b41f40347250cbebead2f6f5b8253 Mon Sep 17 00:00:00 2001 From: scrawl Date: Sat, 15 Sep 2012 18:35:59 +0200 Subject: [PATCH 39/84] added the missing sound & notification for skill increase --- apps/openmw/mwmechanics/npcstats.cpp | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/apps/openmw/mwmechanics/npcstats.cpp b/apps/openmw/mwmechanics/npcstats.cpp index 2980aed59a..2c8cc06dee 100644 --- a/apps/openmw/mwmechanics/npcstats.cpp +++ b/apps/openmw/mwmechanics/npcstats.cpp @@ -4,6 +4,8 @@ #include #include +#include + #include #include #include @@ -13,6 +15,7 @@ #include "../mwbase/environment.hpp" #include "../mwbase/world.hpp" #include "../mwbase/windowmanager.hpp" +#include "../mwbase/soundmanager.hpp" MWMechanics::NpcStats::NpcStats() : mMovementFlags (0), mDrawState (DrawState_Nothing) @@ -160,6 +163,16 @@ void MWMechanics::NpcStats::useSkill (int skillIndex, const ESM::Class& class_, const ESM::Skill* skill = MWBase::Environment::get().getWorld ()->getStore ().skills.find(skillIndex); ++mSkillIncreases[skill->data.attribute]; + // Play sound & skill progress notification + /// \todo check if character is the player, if levelling is ever implemented for NPCs + MWBase::Environment::get().getSoundManager ()->playSound ("skillraise", 1, 1); + + std::stringstream message; + message << boost::format(MWBase::Environment::get().getWindowManager ()->getGameSettingString ("sNotifyMessage39", "")) + % std::string("#{" + ESM::Skill::sSkillNameIds[skillIndex] + "}") + % base; + MWBase::Environment::get().getWindowManager ()->messageBox(message.str(), std::vector()); + if (mLevelProgress >= 10) { // levelup is possible now From f5237ff1a65e7b56b54750c826173ad4bfec5312 Mon Sep 17 00:00:00 2001 From: scrawl Date: Sat, 15 Sep 2012 19:06:56 +0200 Subject: [PATCH 40/84] skill gain from books --- apps/openmw/mwmechanics/npcstats.cpp | 74 +++++++++++++++++----------- apps/openmw/mwmechanics/npcstats.hpp | 2 + apps/openmw/mwworld/actionread.cpp | 24 +++++++++ 3 files changed, 70 insertions(+), 30 deletions(-) diff --git a/apps/openmw/mwmechanics/npcstats.cpp b/apps/openmw/mwmechanics/npcstats.cpp index 2c8cc06dee..0f5d2c95ea 100644 --- a/apps/openmw/mwmechanics/npcstats.cpp +++ b/apps/openmw/mwmechanics/npcstats.cpp @@ -145,40 +145,54 @@ void MWMechanics::NpcStats::useSkill (int skillIndex, const ESM::Class& class_, if (static_cast (base)!=level) { // skill leveled up + increaseSkill(skillIndex, class_, false); + } + else + getSkill (skillIndex).setBase (base); +} + +void MWMechanics::NpcStats::increaseSkill(int skillIndex, const ESM::Class &class_, bool preserveProgress) +{ + float base = getSkill (skillIndex).getBase(); + + int level = static_cast (base); + + if (preserveProgress) + base += 1; + else base = level+1; - // if this is a major or minor skill of the class, increase level progress - bool levelProgress = false; - for (int i=0; i<2; ++i) - for (int j=0; j<5; ++j) - { - int skill = class_.data.skills[j][i]; - if (skill == skillIndex) - levelProgress = true; - } - - mLevelProgress += levelProgress; - - // check the attribute this skill belongs to - const ESM::Skill* skill = MWBase::Environment::get().getWorld ()->getStore ().skills.find(skillIndex); - ++mSkillIncreases[skill->data.attribute]; - - // Play sound & skill progress notification - /// \todo check if character is the player, if levelling is ever implemented for NPCs - MWBase::Environment::get().getSoundManager ()->playSound ("skillraise", 1, 1); - - std::stringstream message; - message << boost::format(MWBase::Environment::get().getWindowManager ()->getGameSettingString ("sNotifyMessage39", "")) - % std::string("#{" + ESM::Skill::sSkillNameIds[skillIndex] + "}") - % base; - MWBase::Environment::get().getWindowManager ()->messageBox(message.str(), std::vector()); - - if (mLevelProgress >= 10) + // if this is a major or minor skill of the class, increase level progress + bool levelProgress = false; + for (int i=0; i<2; ++i) + for (int j=0; j<5; ++j) { - // levelup is possible now - MWBase::Environment::get().getWindowManager ()->messageBox ("#{sLevelUpMsg}", std::vector()); + int skill = class_.data.skills[j][i]; + if (skill == skillIndex) + levelProgress = true; } - } + + mLevelProgress += levelProgress; + + // check the attribute this skill belongs to + const ESM::Skill* skill = MWBase::Environment::get().getWorld ()->getStore ().skills.find(skillIndex); + ++mSkillIncreases[skill->data.attribute]; + + // Play sound & skill progress notification + /// \todo check if character is the player, if levelling is ever implemented for NPCs + MWBase::Environment::get().getSoundManager ()->playSound ("skillraise", 1, 1); + + std::stringstream message; + message << boost::format(MWBase::Environment::get().getWindowManager ()->getGameSettingString ("sNotifyMessage39", "")) + % std::string("#{" + ESM::Skill::sSkillNameIds[skillIndex] + "}") + % base; + MWBase::Environment::get().getWindowManager ()->messageBox(message.str(), std::vector()); + + if (mLevelProgress >= 10) + { + // levelup is possible now + MWBase::Environment::get().getWindowManager ()->messageBox ("#{sLevelUpMsg}", std::vector()); + } getSkill (skillIndex).setBase (base); } diff --git a/apps/openmw/mwmechanics/npcstats.hpp b/apps/openmw/mwmechanics/npcstats.hpp index ea8f926096..7c3055783d 100644 --- a/apps/openmw/mwmechanics/npcstats.hpp +++ b/apps/openmw/mwmechanics/npcstats.hpp @@ -79,6 +79,8 @@ namespace MWMechanics void useSkill (int skillIndex, const ESM::Class& class_, int usageType = -1); ///< Increase skill by usage. + void increaseSkill (int skillIndex, const ESM::Class& class_, bool preserveProgress); + int getLevelProgress() const; int getLevelupAttributeMultiplier(int attribute) const; diff --git a/apps/openmw/mwworld/actionread.cpp b/apps/openmw/mwworld/actionread.cpp index 7fb2b23e70..d049bf5b59 100644 --- a/apps/openmw/mwworld/actionread.cpp +++ b/apps/openmw/mwworld/actionread.cpp @@ -2,10 +2,18 @@ #include "../mwbase/environment.hpp" #include "../mwbase/windowmanager.hpp" +#include "../mwbase/world.hpp" + +#include "../mwworld/player.hpp" +#include "../mwworld/class.hpp" + +#include "../mwmechanics/npcstats.hpp" #include "../mwgui/bookwindow.hpp" #include "../mwgui/scrollwindow.hpp" +#include + namespace MWWorld { ActionRead::ActionRead (const MWWorld::Ptr& object) : Action (false, object) @@ -26,5 +34,21 @@ namespace MWWorld MWBase::Environment::get().getWindowManager()->pushGuiMode(MWGui::GM_Book); MWBase::Environment::get().getWindowManager()->getBookWindow()->open(getTarget()); } + + if (ref->base->data.skillID >= 0 && ref->base->data.skillID < ESM::Skill::Length) + { + MWWorld::Ptr player = MWBase::Environment::get().getWorld ()->getPlayer().getPlayer(); + MWMechanics::NpcStats& npcStats = MWWorld::Class::get(player).getNpcStats (player); + MWWorld::LiveCellRef *playerRef = player.get(); + const ESM::Class *class_ = MWBase::Environment::get().getWorld()->getStore().classes.find ( + playerRef->base->cls); + + npcStats.increaseSkill (ref->base->data.skillID, *class_, true); + + // Remove skill from the book + /// \todo This will have to be changed later + const_cast(ref->base)->data.skillID = -1; + } + } } From 0dc242c60318896730243c6c292d27f92d272b11 Mon Sep 17 00:00:00 2001 From: scrawl Date: Sat, 15 Sep 2012 19:10:48 +0200 Subject: [PATCH 41/84] don't increase skill beyond 100 --- apps/openmw/mwmechanics/npcstats.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/apps/openmw/mwmechanics/npcstats.cpp b/apps/openmw/mwmechanics/npcstats.cpp index 0f5d2c95ea..f2b7df6cb5 100644 --- a/apps/openmw/mwmechanics/npcstats.cpp +++ b/apps/openmw/mwmechanics/npcstats.cpp @@ -157,6 +157,9 @@ void MWMechanics::NpcStats::increaseSkill(int skillIndex, const ESM::Class &clas int level = static_cast (base); + if (level == 100) + return; + if (preserveProgress) base += 1; else From cf358fa79d1e401b4025f6db39b9252192fe63a2 Mon Sep 17 00:00:00 2001 From: scrawl Date: Sat, 15 Sep 2012 19:20:13 +0200 Subject: [PATCH 42/84] >= instead of == --- apps/openmw/mwmechanics/npcstats.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/openmw/mwmechanics/npcstats.cpp b/apps/openmw/mwmechanics/npcstats.cpp index f2b7df6cb5..5e3896af21 100644 --- a/apps/openmw/mwmechanics/npcstats.cpp +++ b/apps/openmw/mwmechanics/npcstats.cpp @@ -157,7 +157,7 @@ void MWMechanics::NpcStats::increaseSkill(int skillIndex, const ESM::Class &clas int level = static_cast (base); - if (level == 100) + if (level >= 100) return; if (preserveProgress) From 02bca98e9f45e0d13157d031f67593e069e55800 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Sat, 15 Sep 2012 13:23:49 -0400 Subject: [PATCH 43/84] Setrotate working --- apps/openmw/mwworld/physicssystem.cpp | 5 +---- libs/openengine/bullet/physic.cpp | 20 +++++++++----------- libs/openengine/bullet/physic.hpp | 11 ++++++++--- 3 files changed, 18 insertions(+), 18 deletions(-) diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index 243ec61baa..5e58f61a3f 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -257,10 +257,7 @@ namespace MWWorld const Ogre::Vector3& position, float scale, const Ogre::Quaternion& rotation) { //TODO:optimize this. Searching the std::map isn't very efficient i think. - std::cout << "NPC position" << position << "\n"; mEngine->addCharacter(handle, mesh, position, scale, rotation); - - } void PhysicsSystem::removeObject (const std::string& handle) @@ -309,7 +306,7 @@ namespace MWWorld if (OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle)) { //Needs to be changed - act->setRotation(btQuaternion(rotation.x, rotation.y, rotation.z, rotation.w)); + act->setRotation(rotation); } if (OEngine::Physic::RigidBody* body = mEngine->getRigidBody(handle)) { diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 2824da4ca5..f3cebfb402 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -29,7 +29,9 @@ namespace Physic PhysicActor::PhysicActor(std::string name, std::string mesh, PhysicEngine* engine, Ogre::Vector3 position, Ogre::Quaternion rotation, float scale): mName(name), mEngine(engine), mMesh(mesh), mBoxScaledTranslation(0,0,0), mBoxRotationInverse(0,0,0,0), mBody(0), collisionMode(false), mBoxRotation(0,0,0,0) { - mBody = mEngine->createAndAdjustRigidBody(mMesh, mName, scale, position, rotation, &mBoxScaledTranslation, &mBoxRotation, &mBoxRotationInverse); + mBody = mEngine->createAndAdjustRigidBody(mMesh, mName, scale, position, rotation, &mBoxScaledTranslation, &mBoxRotation); + Ogre::Quaternion inverse = mBoxRotation.Inverse(); + mBoxRotationInverse = btQuaternion(inverse.x, inverse.y, inverse.z,inverse.w); mEngine->addRigidBody(mBody, false); //Add rigid body to dynamics world, but do not add to object map } @@ -68,10 +70,11 @@ namespace Physic - void PhysicActor::setRotation(const btQuaternion& quat) + void PhysicActor::setRotation(const Ogre::Quaternion quat) { - //externalGhostObject->getWorldTransform().setRotation( quat ); - //internalGhostObject->getWorldTransform().setRotation( quat ); + if(!quat.equals(getRotation(), Ogre::Radian(0))){ + mEngine->adjustRigidBody(mBody, getPosition(), quat, mBoxScaledTranslation, mBoxRotation); + } } Ogre::Vector3 PhysicActor::getPosition(void) @@ -97,7 +100,6 @@ namespace Physic } void PhysicActor::setScale(float scale){ - std::cout << "Trying to set scale to " << scale << "\n"; Ogre::Vector3 position = getPosition(); Ogre::Quaternion rotation = getRotation(); //We only need to change the scaled box translation, box rotations remain the same. @@ -334,7 +336,7 @@ namespace Physic } RigidBody* PhysicEngine::createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, - Ogre::Vector3* scaledBoxTranslation, btQuaternion* boxRotation, btQuaternion* boxRotationInverse) + Ogre::Vector3* scaledBoxTranslation, Ogre::Quaternion* boxRotation) { std::string sid = (boost::format("%07.3f") % scale).str(); std::string outputstring = mesh + sid; @@ -357,11 +359,7 @@ namespace Physic if(scaledBoxTranslation != 0) *scaledBoxTranslation = shape->boxTranslation * scale; if(boxRotation != 0) - *boxRotation = btQuaternion(shape->boxRotation.x, shape->boxRotation.y, shape->boxRotation.z,shape->boxRotation.w); - if(boxRotationInverse != 0){ - Ogre::Quaternion inverse = shape->boxRotation.Inverse(); - *boxRotationInverse = btQuaternion(inverse.x,inverse.y,inverse.z,inverse.w); - } + *boxRotation = shape->boxRotation; adjustRigidBody(body, position, rotation, shape->boxTranslation * scale, shape->boxRotation); diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index 2568cc36f5..7ea6a323d3 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -67,7 +67,12 @@ namespace Physic */ void setWalkDirection(const btVector3& mvt); - void setRotation(const btQuaternion& quat); + /** + * This adjusts the rotation of a PhysicActor + * If we have any problems with this (getting stuck in pmove) we should change it + * from setting the visual orientation to setting the orientation of the rigid body directly. + */ + void setRotation(const Ogre::Quaternion quat); void setGravity(float gravity); @@ -92,7 +97,7 @@ namespace Physic OEngine::Physic::RigidBody* mBody; Ogre::Vector3 mBoxScaledTranslation; btQuaternion mBoxRotationInverse; - btQuaternion mBoxRotation; + Ogre::Quaternion mBoxRotation; bool collisionMode; std::string mMesh; PhysicEngine* mEngine; @@ -144,7 +149,7 @@ namespace Physic * After created, the body is set to the correct rotation, position, and scale */ RigidBody* createAndAdjustRigidBody(std::string mesh,std::string name,float scale, Ogre::Vector3 position, Ogre::Quaternion rotation, - Ogre::Vector3* scaledBoxTranslation = 0, btQuaternion* boxRotation = 0, btQuaternion* boxRotationInverse = 0); + Ogre::Vector3* scaledBoxTranslation = 0, Ogre::Quaternion* boxRotation = 0); /** * Adjusts a rigid body to the right position and rotation From 3e5ab069a64d1a4cf5c1eec5f4aa5d8dde0aaca7 Mon Sep 17 00:00:00 2001 From: scrawl Date: Sat, 15 Sep 2012 19:52:18 +0200 Subject: [PATCH 44/84] remove the const cast --- apps/openmw/mwworld/actionread.cpp | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/apps/openmw/mwworld/actionread.cpp b/apps/openmw/mwworld/actionread.cpp index d049bf5b59..f21fd35ec0 100644 --- a/apps/openmw/mwworld/actionread.cpp +++ b/apps/openmw/mwworld/actionread.cpp @@ -45,9 +45,8 @@ namespace MWWorld npcStats.increaseSkill (ref->base->data.skillID, *class_, true); - // Remove skill from the book - /// \todo This will have to be changed later - const_cast(ref->base)->data.skillID = -1; + /// \todo Remove skill from the book. Right now you can read as many times as you want + /// and the skill will still increase. } } From 9cf1cbc89b514b744f6e9d667bfba76bd45beef4 Mon Sep 17 00:00:00 2001 From: scrawl Date: Sat, 15 Sep 2012 20:03:53 +0200 Subject: [PATCH 45/84] remove book skill gain --- apps/openmw/mwworld/actionread.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/apps/openmw/mwworld/actionread.cpp b/apps/openmw/mwworld/actionread.cpp index f21fd35ec0..fe5e2d58fb 100644 --- a/apps/openmw/mwworld/actionread.cpp +++ b/apps/openmw/mwworld/actionread.cpp @@ -35,6 +35,8 @@ namespace MWWorld MWBase::Environment::get().getWindowManager()->getBookWindow()->open(getTarget()); } + /* + // Skill gain from books if (ref->base->data.skillID >= 0 && ref->base->data.skillID < ESM::Skill::Length) { MWWorld::Ptr player = MWBase::Environment::get().getWorld ()->getPlayer().getPlayer(); @@ -48,6 +50,7 @@ namespace MWWorld /// \todo Remove skill from the book. Right now you can read as many times as you want /// and the skill will still increase. } + */ } } From 896428c129124d64f8479380881f1b1bd4568847 Mon Sep 17 00:00:00 2001 From: scrawl Date: Sat, 15 Sep 2012 20:18:41 +0200 Subject: [PATCH 46/84] enableRestMenu & enableLevelupMenu --- apps/openmw/mwbase/windowmanager.hpp | 3 +++ apps/openmw/mwgui/windowmanagerimp.cpp | 1 + apps/openmw/mwgui/windowmanagerimp.hpp | 5 +++++ apps/openmw/mwinput/inputmanagerimp.cpp | 7 +++++-- apps/openmw/mwscript/guiextensions.cpp | 16 +++++++++++----- 5 files changed, 25 insertions(+), 7 deletions(-) diff --git a/apps/openmw/mwbase/windowmanager.hpp b/apps/openmw/mwbase/windowmanager.hpp index 6e4c106251..0fd78225ab 100644 --- a/apps/openmw/mwbase/windowmanager.hpp +++ b/apps/openmw/mwbase/windowmanager.hpp @@ -219,6 +219,9 @@ namespace MWBase virtual void setLoadingProgress (const std::string& stage, int depth, int current, int total) = 0; virtual void loadingDone() = 0; + + virtual void enableRest() = 0; + virtual bool getRestEnabled() = 0; }; } diff --git a/apps/openmw/mwgui/windowmanagerimp.cpp b/apps/openmw/mwgui/windowmanagerimp.cpp index 8f7c0d17a7..0241cc734a 100644 --- a/apps/openmw/mwgui/windowmanagerimp.cpp +++ b/apps/openmw/mwgui/windowmanagerimp.cpp @@ -85,6 +85,7 @@ WindowManager::WindowManager( , mGarbageDialogs() , mShown(GW_ALL) , mAllowed(newGame ? GW_None : GW_ALL) + , mRestAllowed(newGame ? false : true) , mShowFPSLevel(fpsLevel) , mFPS(0.0f) , mTriangleCount(0) diff --git a/apps/openmw/mwgui/windowmanagerimp.hpp b/apps/openmw/mwgui/windowmanagerimp.hpp index 131029ed47..a02aa17b57 100644 --- a/apps/openmw/mwgui/windowmanagerimp.hpp +++ b/apps/openmw/mwgui/windowmanagerimp.hpp @@ -200,6 +200,9 @@ namespace MWGui virtual void setLoadingProgress (const std::string& stage, int depth, int current, int total); virtual void loadingDone(); + virtual void enableRest() { mRestAllowed = true; } + virtual bool getRestEnabled() { return mRestAllowed; } + private: OEngine::GUI::MyGUIManager *mGuiManager; HUD *mHud; @@ -260,6 +263,8 @@ namespace MWGui allow() and disableAll(). */ GuiWindow mAllowed; + // is the rest window allowed? + bool mRestAllowed; void updateVisible(); // Update visibility of all windows based on mode, shown and allowed settings diff --git a/apps/openmw/mwinput/inputmanagerimp.cpp b/apps/openmw/mwinput/inputmanagerimp.cpp index 724dccd8eb..c3e1314402 100644 --- a/apps/openmw/mwinput/inputmanagerimp.cpp +++ b/apps/openmw/mwinput/inputmanagerimp.cpp @@ -548,8 +548,11 @@ namespace MWInput void InputManager::rest() { - if (!mWindows.isGuiMode ()) - mWindows.pushGuiMode (MWGui::GM_Rest); + if (!mWindows.getRestEnabled () || mWindows.isGuiMode ()) + return; + + /// \todo check if resting is currently allowed (enemies nearby?) + mWindows.pushGuiMode (MWGui::GM_Rest); } void InputManager::screenshot() diff --git a/apps/openmw/mwscript/guiextensions.cpp b/apps/openmw/mwscript/guiextensions.cpp index d740e5feba..7f3b9777b0 100644 --- a/apps/openmw/mwscript/guiextensions.cpp +++ b/apps/openmw/mwscript/guiextensions.cpp @@ -30,6 +30,16 @@ namespace MWScript } }; + class OpEnableRest : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + MWBase::Environment::get().getWindowManager()->enableRest(); + } + }; + class OpShowDialogue : public Interpreter::Opcode0 { MWGui::GuiMode mDialogue; @@ -146,12 +156,8 @@ opcodeEnableStatsReviewMenu); interpreter.installSegment5 (opcodeEnableStatsMenu, new OpEnableWindow (MWGui::GW_Stats)); - /* Not done yet. Enabling rest mode is not really a gui - issue, it's a gameplay issue. - interpreter.installSegment5 (opcodeEnableRest, - new OpEnableDialogue (MWGui::GM_Rest)); - */ + new OpEnableRest ()); interpreter.installSegment5 (opcodeShowRestMenu, new OpShowDialogue (MWGui::GM_Rest)); From c161a3850fe2ef9806dbbfcc780c819d2de589b7 Mon Sep 17 00:00:00 2001 From: Michael Mc Donnell Date: Sat, 15 Sep 2012 15:36:22 -0400 Subject: [PATCH 47/84] Use correct type for iterator Fixes building on Windows with vs2010. --- libs/openengine/ogre/selectionbuffer.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libs/openengine/ogre/selectionbuffer.cpp b/libs/openengine/ogre/selectionbuffer.cpp index 3ecb99f3b4..8dd12b6535 100644 --- a/libs/openengine/ogre/selectionbuffer.cpp +++ b/libs/openengine/ogre/selectionbuffer.cpp @@ -73,7 +73,7 @@ namespace Render int id = Ogre::any_cast(subEntity->getParent ()->getUserObjectBindings().getUserAny()); bool found = false; Ogre::ColourValue colour; - for (std::map::iterator it = mColourMap.begin(); it != mColourMap.end(); ++it) + for (std::map::iterator it = mColourMap.begin(); it != mColourMap.end(); ++it) { if (it->second == id) { From f21faf197c0be14d82b25ccd425c1547a36ba7aa Mon Sep 17 00:00:00 2001 From: Edmondo Tommasina Date: Sat, 15 Sep 2012 22:19:44 +0200 Subject: [PATCH 48/84] =?UTF-8?q?selectionbuffer.cpp:=20fix=20=E2=80=98run?= =?UTF-8?q?time=5Ferror=E2=80=99=20is=20not=20a=20member=20of=20=E2=80=98s?= =?UTF-8?q?td=E2=80=99?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- libs/openengine/ogre/selectionbuffer.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/libs/openengine/ogre/selectionbuffer.cpp b/libs/openengine/ogre/selectionbuffer.cpp index 3ecb99f3b4..cb7f41a1c3 100644 --- a/libs/openengine/ogre/selectionbuffer.cpp +++ b/libs/openengine/ogre/selectionbuffer.cpp @@ -4,6 +4,7 @@ #include #include #include +#include #include From 256dff0a29c4cc9030384f49ee1c3e228a024095 Mon Sep 17 00:00:00 2001 From: Michael Mc Donnell Date: Sat, 15 Sep 2012 16:21:07 -0400 Subject: [PATCH 49/84] Disable warning 4800 for Visual Studio Visual Studio 2010 complains about constructs such as: int myInt = 1; bool myBool = myInt; Which are fine with most compilers. It would instead like: int myInt = 1; bool myBool = (myInt != 0); Warning 4800 is just an optimization warning and is therefore safe to disable. This patch disables warning 4800. --- CMakeLists.txt | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index e01b3d26b1..0a24998d15 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -513,6 +513,7 @@ if (WIN32) 4309 # Variable overflow, trying to store 128 in a signed char for example 4355 # Using 'this' in member initialization list 4701 # Potentially uninitialized local variable used + 4800 # Boolean optimization warning, e.g. myBool = (myInt != 0) instead of myBool = myInt ) foreach(d ${WARNINGS_DISABLE}) @@ -524,6 +525,7 @@ if (WIN32) set_target_properties(omwlauncher PROPERTIES COMPILE_FLAGS ${WARNINGS}) endif (BUILD_LAUNCHER) set_target_properties(openmw PROPERTIES COMPILE_FLAGS ${WARNINGS}) + set_target_properties(esmtool PROPERTIES COMPILE_FLAGS ${WARNINGS}) endif(MSVC) # Same for MinGW From f586f53a42e3ab3c4f10745c0ca2dc9b11298948 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Sat, 15 Sep 2012 16:45:50 -0400 Subject: [PATCH 50/84] positioning --- apps/openmw/mwworld/physicssystem.cpp | 7 +++++-- apps/openmw/mwworld/worldimp.cpp | 2 +- libs/openengine/bullet/physic.cpp | 5 ++--- libs/openengine/bullet/physic.hpp | 22 +++++++++++++++++++--- 4 files changed, 27 insertions(+), 9 deletions(-) diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index 5e58f61a3f..d0291b01a3 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -282,8 +282,11 @@ namespace MWWorld tr.setOrigin(btVector3(position.x,position.y,position.z)); body->setWorldTransform(tr); } - else + else{ + //For objects that contain a box shape. + //Do any such objects exist? Perhaps animated objects? mEngine->boxAdjustExternal(handleToMesh[handle], body, node->getScale().x, position, node->getOrientation()); + } } if (OEngine::Physic::PhysicActor* act = mEngine->getCharacter(handle)) { @@ -295,7 +298,7 @@ namespace MWWorld } else { - act->setPosition(btVector3(position.x,position.y,position.z)); + act->setPosition(position); } } } diff --git a/apps/openmw/mwworld/worldimp.cpp b/apps/openmw/mwworld/worldimp.cpp index 55c2f4161e..3ad58dc7d1 100644 --- a/apps/openmw/mwworld/worldimp.cpp +++ b/apps/openmw/mwworld/worldimp.cpp @@ -637,7 +637,7 @@ namespace MWWorld rot.x = Ogre::Degree(x).valueRadians(); rot.y = Ogre::Degree(y).valueRadians(); rot.z = Ogre::Degree(z).valueRadians(); - + if (mRendering->rotateObject(ptr, rot, adjust)) { float *objRot = ptr.getRefData().getPosition().rot; objRot[0] = rot.x, objRot[1] = rot.y, objRot[2] = rot.z; diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index f3cebfb402..9c387e140d 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -93,10 +93,9 @@ namespace Physic return Ogre::Quaternion(quat.getW(), quat.getX(), quat.getY(), quat.getZ()); } - void PhysicActor::setPosition(const btVector3& pos) + void PhysicActor::setPosition(const Ogre::Vector3 pos) { - //internalGhostObject->getWorldTransform().setOrigin(pos+mTranslation); - //externalGhostObject->getWorldTransform().setOrigin(pos+mTranslation); + mEngine->adjustRigidBody(mBody, pos, getRotation(), mBoxScaledTranslation, mBoxRotation); } void PhysicActor::setScale(float scale){ diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index 7ea6a323d3..1598d3e870 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -51,7 +51,8 @@ namespace Physic }; /** - * A physic Actor use a modifed KinematicCharacterController taken in the bullet forum. + * A physic actor uses a rigid body based on box shapes. + * Pmove is used to move the physic actor around the dynamic world. */ class PhysicActor { @@ -82,15 +83,29 @@ namespace Physic bool getCollisionMode(); + /** + * This returns the visual position of the PhysicActor (used to position a scenenode). + * Note - this is different from the position of the contained mBody. + */ Ogre::Vector3 getPosition(void); + /** + * Returns the visual orientation of the PhysicActor + */ Ogre::Quaternion getRotation(void); - void setPosition(const btVector3& pos); + /** + * Sets the position of mBody from a visual position input. + * For most cases this should not be used. We should instead let pmove move the PhysicActor around for us + */ + void setPosition(const Ogre::Vector3 pos); + /** + * Sets the scale of the PhysicActor + */ void setScale(float scale); - std::string mName; + private: @@ -101,6 +116,7 @@ namespace Physic bool collisionMode; std::string mMesh; PhysicEngine* mEngine; + std::string mName; }; /** From f6384574dae1c31acb0dd7adc96e98838a589ac7 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Sat, 15 Sep 2012 18:17:42 -0400 Subject: [PATCH 51/84] Starting to introduce pmove --- libs/openengine/bullet/physic.cpp | 28 +++++++++++++++------------- libs/openengine/bullet/physic.hpp | 10 +++++++++- libs/openengine/bullet/trace.h | 2 +- 3 files changed, 25 insertions(+), 15 deletions(-) diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 9c387e140d..a9f483aa4a 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -2,6 +2,7 @@ #include #include #include +#include "pmove.h" #include #include "CMotionState.h" #include "OgreRoot.h" @@ -33,6 +34,7 @@ namespace Physic Ogre::Quaternion inverse = mBoxRotation.Inverse(); mBoxRotationInverse = btQuaternion(inverse.x, inverse.y, inverse.z,inverse.w); mEngine->addRigidBody(mBody, false); //Add rigid body to dynamics world, but do not add to object map + pmove = new playerMove; } PhysicActor::~PhysicActor() @@ -41,6 +43,7 @@ namespace Physic mEngine->dynamicsWorld->removeRigidBody(mBody); delete mBody; } + delete pmove; } void PhysicActor::setGravity(float gravity) @@ -210,8 +213,8 @@ namespace Physic delete hf_it->second.mBody; } - RigidBodyContainer::iterator rb_it = RigidBodyMap.begin(); - for (; rb_it != RigidBodyMap.end(); ++rb_it) + RigidBodyContainer::iterator rb_it = ObjectMap.begin(); + for (; rb_it != ObjectMap.end(); ++rb_it) { if (rb_it->second != NULL) { @@ -380,22 +383,22 @@ namespace Physic } body->setActivationState(DISABLE_DEACTIVATION); if(addToMap){ - RigidBody* oldBody = RigidBodyMap[body->mName]; + RigidBody* oldBody = ObjectMap[body->mName]; if (oldBody != NULL) { dynamicsWorld->removeRigidBody(oldBody); delete oldBody; } - RigidBodyMap[body->mName] = body; + ObjectMap[body->mName] = body; } } } void PhysicEngine::removeRigidBody(std::string name) { - RigidBodyContainer::iterator it = RigidBodyMap.find(name); - if (it != RigidBodyMap.end() ) + RigidBodyContainer::iterator it = ObjectMap.find(name); + if (it != ObjectMap.end() ) { RigidBody* body = it->second; if(body != NULL) @@ -414,8 +417,8 @@ namespace Physic void PhysicEngine::deleteRigidBody(std::string name) { - RigidBodyContainer::iterator it = RigidBodyMap.find(name); - if (it != RigidBodyMap.end() ) + RigidBodyContainer::iterator it = ObjectMap.find(name); + if (it != ObjectMap.end() ) { RigidBody* body = it->second; //btScaledBvhTriangleMeshShape* scaled = dynamic_cast (body->getCollisionShape()); @@ -428,16 +431,16 @@ namespace Physic { delete scaled; }*/ - RigidBodyMap.erase(it); + ObjectMap.erase(it); } } RigidBody* PhysicEngine::getRigidBody(std::string name) { - RigidBodyContainer::iterator it = RigidBodyMap.find(name); - if (it != RigidBodyMap.end() ) + RigidBodyContainer::iterator it = ObjectMap.find(name); + if (it != ObjectMap.end() ) { - RigidBody* body = RigidBodyMap[name]; + RigidBody* body = ObjectMap[name]; return body; } else @@ -483,7 +486,6 @@ namespace Physic } PhysicActorMap.erase(it); } - //std::cout << "ok"; } PhysicActor* PhysicEngine::getCharacter(std::string name) diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index 1598d3e870..f516753989 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -9,6 +9,8 @@ #include "BulletShapeLoader.h" #include "BulletCollision/CollisionShapes/btScaledBvhTriangleMeshShape.h" + + class btRigidBody; class btBroadphaseInterface; class btDefaultCollisionConfiguration; @@ -16,6 +18,7 @@ class btSequentialImpulseConstraintSolver; class btCollisionDispatcher; class btDiscreteDynamicsWorld; class btHeightfieldTerrainShape; +struct playerMove; namespace BtOgre { @@ -27,6 +30,7 @@ namespace MWWorld class World; } + namespace OEngine { namespace Physic { @@ -109,6 +113,7 @@ namespace Physic private: + OEngine::Physic::RigidBody* mBody; Ogre::Vector3 mBoxScaledTranslation; btQuaternion mBoxRotationInverse; @@ -117,6 +122,8 @@ namespace Physic std::string mMesh; PhysicEngine* mEngine; std::string mName; + playerMove* pmove; + }; /** @@ -284,7 +291,7 @@ namespace Physic HeightFieldContainer mHeightFieldMap; typedef std::map RigidBodyContainer; - RigidBodyContainer RigidBodyMap; + RigidBodyContainer ObjectMap; typedef std::map PhysicActorContainer; PhysicActorContainer PhysicActorMap; @@ -293,6 +300,7 @@ namespace Physic BtOgre::DebugDrawer* mDebugDrawer; bool isDebugCreated; bool mDebugActive; + }; diff --git a/libs/openengine/bullet/trace.h b/libs/openengine/bullet/trace.h index bd554031a5..1bfe0c7178 100644 --- a/libs/openengine/bullet/trace.h +++ b/libs/openengine/bullet/trace.h @@ -5,8 +5,8 @@ #include #include #include -#include #include +#include "pmove.h" enum traceWorldType From 97326ffdbf62009c3e2e6ae6734676c402372430 Mon Sep 17 00:00:00 2001 From: Pieter van der Kloet Date: Sun, 16 Sep 2012 03:01:48 +0200 Subject: [PATCH 52/84] Fixed data-local directory handling in the launcher --- apps/launcher/datafilespage.cpp | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/apps/launcher/datafilespage.cpp b/apps/launcher/datafilespage.cpp index 64816fae56..69ed6defad 100644 --- a/apps/launcher/datafilespage.cpp +++ b/apps/launcher/datafilespage.cpp @@ -208,12 +208,10 @@ bool DataFilesPage::setupDataFiles() std::string local = variables["data-local"].as(); if (!local.empty()) { - mDataLocal.push_back(Files::PathContainer::value_type(local)); + mDataDirs.push_back(Files::PathContainer::value_type(local)); + mDataLocal.push_back(Files::PathContainer::value_type(local)); // For config writing } - if (mDataDirs.size()>1) - mDataDirs.resize (1); - mCfgMgr.processPaths(mDataDirs); while (mDataDirs.empty()) { From 4bcc34f4f963cfdd8319a74611c9d96cf07c2e73 Mon Sep 17 00:00:00 2001 From: Pieter van der Kloet Date: Sun, 16 Sep 2012 04:28:51 +0200 Subject: [PATCH 53/84] Re-enabled and fixed multiple data directory handling in the launcher --- apps/launcher/datafilespage.cpp | 154 ++++++++++++++++++-------------- apps/launcher/datafilespage.hpp | 1 + 2 files changed, 86 insertions(+), 69 deletions(-) diff --git a/apps/launcher/datafilespage.cpp b/apps/launcher/datafilespage.cpp index 69ed6defad..266a381019 100644 --- a/apps/launcher/datafilespage.cpp +++ b/apps/launcher/datafilespage.cpp @@ -189,71 +189,8 @@ void DataFilesPage::setupConfig() } -bool DataFilesPage::setupDataFiles() +void DataFilesPage::addDataFiles(Files::Collections &fileCollections, const QString &encoding) { - // We use the Configuration Manager to retrieve the configuration values - boost::program_options::variables_map variables; - boost::program_options::options_description desc; - - desc.add_options() - ("data", boost::program_options::value()->default_value(Files::PathContainer(), "data")->multitoken()) - ("data-local", boost::program_options::value()->default_value("")) - ("fs-strict", boost::program_options::value()->implicit_value(true)->default_value(false)) - ("encoding", boost::program_options::value()->default_value("win1252")); - - mCfgMgr.readConfiguration(variables, desc); - - // Put the paths in a boost::filesystem vector to use with Files::Collections - mDataDirs = Files::PathContainer(variables["data"].as()); - - std::string local = variables["data-local"].as(); - if (!local.empty()) { - mDataDirs.push_back(Files::PathContainer::value_type(local)); - mDataLocal.push_back(Files::PathContainer::value_type(local)); // For config writing - } - - mCfgMgr.processPaths(mDataDirs); - - while (mDataDirs.empty()) { - QMessageBox msgBox; - msgBox.setWindowTitle("Error detecting Morrowind installation"); - msgBox.setIcon(QMessageBox::Warning); - msgBox.setStandardButtons(QMessageBox::Cancel); - msgBox.setText(tr("
Could not find the Data Files location

\ - The directory containing the data files was not found.

\ - Press \"Browse...\" to specify the location manually.
")); - - QAbstractButton *dirSelectButton = - msgBox.addButton(tr("B&rowse..."), QMessageBox::ActionRole); - - msgBox.exec(); - - if (msgBox.clickedButton() == dirSelectButton) { - - // Show a custom dir selection dialog which only accepts valid dirs - QString selectedDir = FileDialog::getExistingDirectory( - this, tr("Select Data Files Directory"), - QDir::currentPath(), - QFileDialog::ShowDirsOnly | QFileDialog::DontResolveSymlinks); - - // Add the user selected data directory - if (!selectedDir.isEmpty()) { - mDataDirs.push_back(Files::PathContainer::value_type(selectedDir.toStdString())); - mCfgMgr.processPaths(mDataDirs); - } else { - // Cancel from within the dir selection dialog - return false; - } - - } else { - // Cancel - return false; - } - } - - // Create a file collection for the data dirs - Files::Collections fileCollections(mDataDirs, !variables["fs-strict"].as()); - // First we add all the master files const Files::MultiDirCollection &esm = fileCollections.getCollection(".esm"); unsigned int i = 0; // Row number @@ -281,7 +218,7 @@ bool DataFilesPage::setupDataFiles() ESMReader fileReader; QStringList availableMasters; // Will contain all found masters - fileReader.setEncoding(variables["encoding"].as()); + fileReader.setEncoding(encoding.toStdString()); fileReader.open(iter->second.string()); // First we fill the availableMasters and the mMastersWidget @@ -352,6 +289,81 @@ bool DataFilesPage::setupDataFiles() } } + +} + + +bool DataFilesPage::setupDataFiles() +{ + // We use the Configuration Manager to retrieve the configuration values + boost::program_options::variables_map variables; + boost::program_options::options_description desc; + + desc.add_options() + ("data", boost::program_options::value()->default_value(Files::PathContainer(), "data")->multitoken()) + ("data-local", boost::program_options::value()->default_value("")) + ("fs-strict", boost::program_options::value()->implicit_value(true)->default_value(false)) + ("encoding", boost::program_options::value()->default_value("win1252")); + + mCfgMgr.readConfiguration(variables, desc); + + // Put the paths in a boost::filesystem vector to use with Files::Collections + mDataDirs = Files::PathContainer(variables["data"].as()); + + std::string local = variables["data-local"].as(); + if (!local.empty()) { + mDataLocal.push_back(Files::PathContainer::value_type(local)); + } + + mCfgMgr.processPaths(mDataDirs); + mCfgMgr.processPaths(mDataLocal); + + while (mDataDirs.empty()) { + QMessageBox msgBox; + msgBox.setWindowTitle("Error detecting Morrowind installation"); + msgBox.setIcon(QMessageBox::Warning); + msgBox.setStandardButtons(QMessageBox::Cancel); + msgBox.setText(tr("
Could not find the Data Files location

\ + The directory containing the data files was not found.

\ + Press \"Browse...\" to specify the location manually.
")); + + QAbstractButton *dirSelectButton = + msgBox.addButton(tr("B&rowse..."), QMessageBox::ActionRole); + + msgBox.exec(); + + if (msgBox.clickedButton() == dirSelectButton) { + + // Show a custom dir selection dialog which only accepts valid dirs + QString selectedDir = FileDialog::getExistingDirectory( + this, tr("Select Data Files Directory"), + QDir::currentPath(), + QFileDialog::ShowDirsOnly | QFileDialog::DontResolveSymlinks); + + // Add the user selected data directory + if (!selectedDir.isEmpty()) { + mDataDirs.push_back(Files::PathContainer::value_type(selectedDir.toStdString())); + mCfgMgr.processPaths(mDataDirs); + } else { + // Cancel from within the dir selection dialog + return false; + } + + } else { + // Cancel + return false; + } + } + + // Add the plugins in the data directories + Files::Collections dataCollections(mDataDirs, !variables["fs-strict"].as()); + Files::Collections dataLocalCollections(mDataLocal, !variables["fs-strict"].as()); + + addDataFiles(dataCollections, QString::fromStdString(variables["encoding"].as())); + addDataFiles(dataLocalCollections, QString::fromStdString(variables["encoding"].as())); + + mDataFilesModel->sort(0); + readConfig(); return true; } @@ -1137,11 +1149,13 @@ void DataFilesPage::writeConfig(QString profile) path = QString::fromStdString(it->string()); path.remove(QChar('\"')); + QDir dir(path); + // Make sure the string is quoted when it contains spaces if (path.contains(" ")) { - gameConfig << "data=\"" << path << "\"" << endl; + gameConfig << "data=\"" << dir.absolutePath() << "\"" << endl; } else { - gameConfig << "data=" << path << endl; + gameConfig << "data=" << dir.absolutePath() << endl; } } @@ -1150,10 +1164,12 @@ void DataFilesPage::writeConfig(QString profile) path = QString::fromStdString(mDataLocal.front().string()); path.remove(QChar('\"')); + QDir dir(path); + if (path.contains(" ")) { - gameConfig << "data-local=\"" << path << "\"" << endl; + gameConfig << "data-local=\"" << dir.absolutePath() << "\"" << endl; } else { - gameConfig << "data-local=" << path << endl; + gameConfig << "data-local=" << dir.absolutePath() << endl; } } diff --git a/apps/launcher/datafilespage.hpp b/apps/launcher/datafilespage.hpp index 5078f64288..83b3186772 100644 --- a/apps/launcher/datafilespage.hpp +++ b/apps/launcher/datafilespage.hpp @@ -89,6 +89,7 @@ private: const QStringList checkedPlugins(); const QStringList selectedMasters(); + void addDataFiles(Files::Collections &fileCollections, const QString &encoding); void addPlugins(const QModelIndex &index); void removePlugins(const QModelIndex &index); void uncheckPlugins(); From 76f2a8288498910dd1f271dd43f4317b2785adeb Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Sat, 15 Sep 2012 22:48:24 -0400 Subject: [PATCH 54/84] More pmove stuff; Turned off broadphase, we could not fall in exteriors --- apps/openmw/mwworld/physicssystem.cpp | 8 ++++---- libs/openengine/bullet/physic.cpp | 17 ++++++++++++++--- libs/openengine/bullet/physic.hpp | 4 +++- libs/openengine/bullet/pmove.cpp | 2 +- libs/openengine/bullet/pmove.h | 4 ++-- libs/openengine/bullet/trace.cpp | 3 ++- 6 files changed, 26 insertions(+), 12 deletions(-) diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index d0291b01a3..27bff68c67 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -96,6 +96,10 @@ namespace MWWorld if(hasWater){ playerphysics->waterHeight = waterHeight; } + for(std::map::iterator it = mEngine->PhysicActorMap.begin(); it != mEngine->PhysicActorMap.end();it++) + { + it->second->setCurrentWater(hasWater, waterHeight); + } } @@ -356,8 +360,6 @@ namespace MWWorld if(cmode) { act->enableCollisions(false); - act->setGravity(0.); - act->setVerticalVelocity(0); mFreeFly = true; return false; } @@ -365,8 +367,6 @@ namespace MWWorld { mFreeFly = false; act->enableCollisions(true); - act->setGravity(4.); - act->setVerticalVelocity(0); return true; } } diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index a9f483aa4a..181aa62b57 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -46,19 +46,30 @@ namespace Physic delete pmove; } + void PhysicActor::setCurrentWater(bool hasWater, int waterHeight){ + pmove->hasWater = hasWater; + if(hasWater){ + pmove->waterHeight = waterHeight; + } + } + void PhysicActor::setGravity(float gravity) { - + pmove->ps.gravity = gravity; } void PhysicActor::enableCollisions(bool collision) { collisionMode = collision; + if(collisionMode) + pmove->ps.move_type=PM_NORMAL; + else + pmove->ps.move_type=PM_NOCLIP; } - void PhysicActor::setVerticalVelocity(float z) + void PhysicActor::setJumpVelocity(float velocity) { - + pmove->ps.jump_velocity = velocity; } bool PhysicActor::getCollisionMode() diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index f516753989..481fa2ed81 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -65,6 +65,8 @@ namespace Physic ~PhysicActor(); + void setCurrentWater(bool hasWater, int waterHeight); + /** * This function set the walkDirection. This is not relative to the actor orientation. * I think it's also needed to take time into account. A typical call should look like this: @@ -81,7 +83,7 @@ namespace Physic void setGravity(float gravity); - void setVerticalVelocity(float z); + void setJumpVelocity(float velocity); void enableCollisions(bool collision); diff --git a/libs/openengine/bullet/pmove.cpp b/libs/openengine/bullet/pmove.cpp index 3d2462ab5b..f3e1a470a4 100644 --- a/libs/openengine/bullet/pmove.cpp +++ b/libs/openengine/bullet/pmove.cpp @@ -704,7 +704,7 @@ static bool PM_CheckJump(void) //pm->ps->pm_flags |= PMF_JUMP_HELD; pm->ps.groundEntityNum = ENTITYNUM_NONE; - pm->ps.velocity.z = JUMP_VELOCITY; + pm->ps.velocity.z = pm->ps.jump_velocity; pm->ps.bSnap = false; //PM_AddEvent( EV_JUMP ); diff --git a/libs/openengine/bullet/pmove.h b/libs/openengine/bullet/pmove.h index aef028ba4b..63d03f86a9 100644 --- a/libs/openengine/bullet/pmove.h +++ b/libs/openengine/bullet/pmove.h @@ -42,7 +42,6 @@ static const Ogre::Vector3 halfExtents(14.64f * 2, 14.24f * 2, 33.25f * 2); #define ENTITYNUM_NONE (MAX_GENTITIES - 1) #define ENTITYNUM_WORLD (MAX_GENTITIES - 2) #define MIN_WALK_NORMAL .7f // can't walk on very steep slopes -#define JUMP_VELOCITY (270) #define PS_PMOVEFRAMECOUNTBITS 6 #define MINS_Z -24 #define DEFAULT_VIEWHEIGHT 26 @@ -90,7 +89,7 @@ struct playerMove { struct playerStruct { - playerStruct() : gravity(800.0f), speed(480.0f), pmove_framecount(20), groundEntityNum(ENTITYNUM_NONE), commandTime(40), move_type(PM_NOCLIP), pm_time(0), snappingImplemented(true), bSnap(false), counter(-1) + playerStruct() : gravity(800.0f), speed(480.0f), jump_velocity(270), pmove_framecount(20), groundEntityNum(ENTITYNUM_NONE), commandTime(40), move_type(PM_NOCLIP), pm_time(0), snappingImplemented(true), bSnap(false), counter(-1) { origin = Ogre::Vector3(0.0f, 0.0f, 0.0f); velocity = Ogre::Vector3(0.0f, 0.0f, 0.0f); @@ -122,6 +121,7 @@ struct playerMove int counter; float gravity; // default = 800 float speed; // default = 320 + float jump_velocity; //default = 270 int commandTime; // the time at which this command was issued (in milliseconds) diff --git a/libs/openengine/bullet/trace.cpp b/libs/openengine/bullet/trace.cpp index 474d87ee95..03ed4ffb14 100644 --- a/libs/openengine/bullet/trace.cpp +++ b/libs/openengine/bullet/trace.cpp @@ -181,7 +181,8 @@ const bool NewPhysicsTrace(NewPhysTraceResults* const out, const Ogre::Vector3& if (!TestPointAgainstAabb2(aabbMin, aabbMax, *(const btVector3* const)&(start) ) ) { //We're solid - out->startSolid = true; + //THIS NEEDS TO BE TURNED OFF IF WE WANT FALLING IN EXTERIORS TO WORK CORRECTLY!!!!!!! + //out->startSolid = true; } } } From 192d6340985bd8b97e36dd241572fa972cfdce51 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Sun, 16 Sep 2012 13:19:38 -0400 Subject: [PATCH 55/84] Movement keys; View angles --- apps/openmw/mwworld/physicssystem.cpp | 4 ++-- libs/openengine/bullet/physic.cpp | 22 ++++++++++++++++++++-- libs/openengine/bullet/physic.hpp | 17 +++++++++++++---- 3 files changed, 35 insertions(+), 8 deletions(-) diff --git a/apps/openmw/mwworld/physicssystem.cpp b/apps/openmw/mwworld/physicssystem.cpp index 27bff68c67..8de415980e 100644 --- a/apps/openmw/mwworld/physicssystem.cpp +++ b/apps/openmw/mwworld/physicssystem.cpp @@ -176,11 +176,11 @@ namespace MWWorld //set the DebugRenderingMode. To disable it,set it to 0 //eng->setDebugRenderingMode(1); - //set the walkdirection to 0 (no movement) for every actor) + //set the movement keys to 0 (no movement) for every actor) for(std::map::iterator it = mEngine->PhysicActorMap.begin(); it != mEngine->PhysicActorMap.end();it++) { OEngine::Physic::PhysicActor* act = it->second; - act->setWalkDirection(btVector3(0,0,0)); + act->setMovement(0,0,0); } playerMove::playercmd& pm_ref = playerphysics->cmd; diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 181aa62b57..ca7709c2c5 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -35,6 +35,7 @@ namespace Physic mBoxRotationInverse = btQuaternion(inverse.x, inverse.y, inverse.z,inverse.w); mEngine->addRigidBody(mBody, false); //Add rigid body to dynamics world, but do not add to object map pmove = new playerMove; + pmove->mEngine = mEngine; } PhysicActor::~PhysicActor() @@ -77,9 +78,18 @@ namespace Physic return collisionMode; } - void PhysicActor::setWalkDirection(const btVector3& mvt) + void PhysicActor::setMovement(signed char rightmove, signed char forwardmove, signed char upmove) { - + playerMove::playercmd& pm_ref = pmove->cmd; + pm_ref.rightmove = rightmove; + pm_ref.forwardmove = forwardmove; + pm_ref.upmove = upmove; + } + + void PhysicActor::setPmoveViewAngles(float pitch, float yaw, float roll){ + pmove->ps.viewangles.x = pitch; + pmove->ps.viewangles.y = yaw; + pmove->ps.viewangles.z = roll; } @@ -110,6 +120,8 @@ namespace Physic void PhysicActor::setPosition(const Ogre::Vector3 pos) { mEngine->adjustRigidBody(mBody, pos, getRotation(), mBoxScaledTranslation, mBoxRotation); + btVector3 vec = mBody->getWorldTransform().getOrigin(); + pmove->ps.origin = Ogre::Vector3(vec.getX(), vec.getY(), vec.getZ()); } void PhysicActor::setScale(float scale){ @@ -127,6 +139,12 @@ namespace Physic mEngine->addRigidBody(mBody, false); //Add rigid body to dynamics world, but do not add to object map } + void PhysicActor::runPmove(){ + Pmove(pmove); + Ogre::Vector3 newpos = pmove->ps.origin; + mBody->getWorldTransform().setOrigin(btVector3(newpos.x, newpos.y, newpos.z)); + } + //////////////////////////////////////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////////////////////////////////////// diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index 481fa2ed81..56b7f1fb79 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -68,11 +68,9 @@ namespace Physic void setCurrentWater(bool hasWater, int waterHeight); /** - * This function set the walkDirection. This is not relative to the actor orientation. - * I think it's also needed to take time into account. A typical call should look like this: - * setWalkDirection( mvt * orientation * dt) + * This function sets the movement keys for pmove */ - void setWalkDirection(const btVector3& mvt); + void setMovement(signed char rightmove, signed char forwardmove, signed char upmove); /** * This adjusts the rotation of a PhysicActor @@ -106,11 +104,22 @@ namespace Physic */ void setPosition(const Ogre::Vector3 pos); + /** + * Sets the view angles for pmove directly. + * Remember, add 90 for yaw. Set roll to 0. + */ + void setPmoveViewAngles(float pitch, float yaw, float roll); + /** * Sets the scale of the PhysicActor */ void setScale(float scale); + /** + * Runs pmove for this PhysicActor + */ + void runPmove(); + From 42d25c0af001c80ea7c17364e3aee07959725d62 Mon Sep 17 00:00:00 2001 From: scrawl Date: Sun, 16 Sep 2012 20:56:49 +0200 Subject: [PATCH 56/84] fix resources, I renamed those in the last commit, but only in one place --- files/mygui/core.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/files/mygui/core.xml b/files/mygui/core.xml index e1fb1b5e21..ea16278757 100644 --- a/files/mygui/core.xml +++ b/files/mygui/core.xml @@ -4,8 +4,8 @@ - - + + From 0fa1dea6c1cdd9c5a02b185db253a39896513dd0 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Sun, 16 Sep 2012 17:29:16 -0400 Subject: [PATCH 57/84] Box size set; Set speed --- libs/openengine/bullet/physic.cpp | 13 +++++++++++++ libs/openengine/bullet/physic.hpp | 2 ++ libs/openengine/bullet/pmove.cpp | 20 ++++++++++---------- libs/openengine/bullet/pmove.h | 5 +++-- 4 files changed, 28 insertions(+), 12 deletions(-) diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index ca7709c2c5..4ced2db904 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -36,6 +36,10 @@ namespace Physic mEngine->addRigidBody(mBody, false); //Add rigid body to dynamics world, but do not add to object map pmove = new playerMove; pmove->mEngine = mEngine; + btBoxShape* box = static_cast (mBody->getCollisionShape()); + btVector3 size = box->getHalfExtentsWithMargin(); + Ogre::Vector3 halfExtents = Ogre::Vector3(size.getX(), size.getY(), size.getZ()); + pmove->ps.halfExtents = halfExtents; } PhysicActor::~PhysicActor() @@ -58,6 +62,11 @@ namespace Physic { pmove->ps.gravity = gravity; } + + void PhysicActor::setSpeed(float speed) + { + pmove->ps.speed = speed; + } void PhysicActor::enableCollisions(bool collision) { @@ -137,6 +146,10 @@ namespace Physic //Create the newly scaled rigid body mBody = mEngine->createAndAdjustRigidBody(mMesh, mName, scale, position, rotation); mEngine->addRigidBody(mBody, false); //Add rigid body to dynamics world, but do not add to object map + btBoxShape* box = static_cast (mBody->getCollisionShape()); + btVector3 size = box->getHalfExtentsWithMargin(); + Ogre::Vector3 halfExtents = Ogre::Vector3(size.getX(), size.getY(), size.getZ()); + pmove->ps.halfExtents = halfExtents; } void PhysicActor::runPmove(){ diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index 56b7f1fb79..a69d80e534 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -81,6 +81,8 @@ namespace Physic void setGravity(float gravity); + void setSpeed(float speed); + void setJumpVelocity(float velocity); void enableCollisions(bool collision); diff --git a/libs/openengine/bullet/pmove.cpp b/libs/openengine/bullet/pmove.cpp index f3e1a470a4..645abf205b 100644 --- a/libs/openengine/bullet/pmove.cpp +++ b/libs/openengine/bullet/pmove.cpp @@ -231,7 +231,7 @@ bool PM_SlideMove( bool gravity ) // see if we can make it there //pm->trace ( &trace, pm->ps->origin, pm->mins, pm->maxs, end, pm->ps->clientNum, pm->tracemaskg); //tracefunc(&trace, *(const D3DXVECTOR3* const)&(pm->ps.origin), *(const D3DXVECTOR3* const)&(end), *(const D3DXVECTOR3* const)&(pm->ps.velocity), 0, pml.traceObj); - newtrace(&trace, pm->ps.origin, end, halfExtents, Ogre::Math::DegreesToRadians (pm->ps.viewangles.y), pm->isInterior, pm->mEngine); + newtrace(&trace, pm->ps.origin, end, pm->ps.halfExtents, Ogre::Math::DegreesToRadians (pm->ps.viewangles.y), pm->isInterior, pm->mEngine); if (trace.allsolid) { @@ -449,7 +449,7 @@ int PM_StepSlideMove( bool gravity ) //pm->trace (&trace, start_o, pm->mins, pm->maxs, down, pm->ps->clientNum, pm->tracemask); //tracefunc(&trace, start_o, down, , 0, pml.scene); //tracefunc(&trace, *(const D3DXVECTOR3* const)&start_o, *(const D3DXVECTOR3* const)&down, D3DXVECTOR3(0.0f, -STEPSIZE, 0.0f), 0, pml.traceObj); - newtrace(&trace, down, start_o, halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); + newtrace(&trace, down, start_o, pm->ps.halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); // up = vec3(0, 0, 1) //VectorSet(up, 0, 0, 1); @@ -479,7 +479,7 @@ int PM_StepSlideMove( bool gravity ) // test the player position if they were a stepheight higher //pm->trace (&trace, start_o, pm->mins, pm->maxs, up, pm->ps->clientNum, pm->tracemask); //tracefunc(&trace, *(const D3DXVECTOR3* const)&start_o, *(const D3DXVECTOR3* const)&up, D3DXVECTOR3(0.0f, STEPSIZE, 0.0f), 0, pml.traceObj); - newtrace(&trace, start_o, up, halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); + newtrace(&trace, start_o, up, pm->ps.halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); if ( trace.allsolid ) { //if ( pm->debugLevel ) @@ -510,7 +510,7 @@ int PM_StepSlideMove( bool gravity ) //pm->trace (&trace, pm->ps->origin, pm->mins, pm->maxs, down, pm->ps->clientNum, pm->tracemask); //tracefunc(&trace, *(const D3DXVECTOR3* const)&(pm->ps.origin), *(const D3DXVECTOR3* const)&down, D3DXVECTOR3(0.0f, -STEPSIZE, 0.0f), 0, pml.traceObj); - newtrace(&trace, pm->ps.origin, down, halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); + newtrace(&trace, pm->ps.origin, down, pm->ps.halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); if ( !trace.allsolid ) //VectorCopy (trace.endpos, pm->ps->origin); pm->ps.origin = trace.endpos; @@ -902,7 +902,7 @@ static void PM_WalkMove( playerMove* const pmove ) if (pmove->hasWater ) { const float waterHeight = pmove->waterHeight; - const float waterSoundStepHeight = waterHeight + halfExtents.y; + const float waterSoundStepHeight = waterHeight + pm->ps.halfExtents.y; if (pmove->ps.origin.y < waterSoundStepHeight) step_underwater = true; } @@ -1182,7 +1182,7 @@ void PM_GroundTraceMissed() //pm->trace (&trace, pm->ps->origin, pm->mins, pm->maxs, point, pm->ps->clientNum, pm->tracemask); //tracefunc(&trace, *(const D3DXVECTOR3* const)&(pm->ps.origin), *(const D3DXVECTOR3* const)&point, D3DXVECTOR3(0.0f, -64.0f, 0.0f), 0, pml.traceObj); - newtrace(&trace, pm->ps.origin, point, halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); + newtrace(&trace, pm->ps.origin, point, pm->ps.halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); //It hit the ground below if ( trace.fraction < 1.0 && pm->ps.origin.z > trace.endpos.z) { @@ -1228,7 +1228,7 @@ static bool PM_CorrectAllSolid(traceResults* const trace) //pm->trace (trace, point, pm->mins, pm->maxs, point, pm->ps->clientNum, pm->tracemask); //tracefunc(trace, *(const D3DXVECTOR3* const)&point, *(const D3DXVECTOR3* const)&point, D3DXVECTOR3(0.0f, 0.0f, 0.0f), 0, pml.traceObj); - newtrace(trace, point, point, halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); + newtrace(trace, point, point, pm->ps.halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); if ( !trace->allsolid ) { @@ -1240,7 +1240,7 @@ static bool PM_CorrectAllSolid(traceResults* const trace) //pm->trace (trace, pm->ps->origin, pm->mins, pm->maxs, point, pm->ps->clientNum, pm->tracemask); //tracefunc(trace, *(const D3DXVECTOR3* const)&(pm->ps.origin), *(const D3DXVECTOR3* const)&point, D3DXVECTOR3(0.0f, -0.25f, 0.0f), 0, pml.traceObj); - newtrace(trace, pm->ps.origin, point, halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); + newtrace(trace, pm->ps.origin, point, pm->ps.halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); pml.groundTrace = *trace; return true; } @@ -1341,7 +1341,7 @@ static void PM_CrashLand( void ) { const float waterHeight = pm->waterHeight; - const float waterHeightSplash = waterHeight + halfExtents.y; + const float waterHeightSplash = waterHeight + pm->ps.halfExtents.y; if (pm->ps.origin.z < waterHeightSplash) { splashSound = true; @@ -1416,7 +1416,7 @@ static void PM_GroundTrace( void ) //pm->trace (&trace, pm->ps->origin, pm->mins, pm->maxs, point, pm->ps->clientNum, pm->tracemask); //tracefunc(&trace, *(const D3DXVECTOR3* const)&(pm->ps.origin), *(const D3DXVECTOR3* const)&point, D3DXVECTOR3(0.0f, -0.25f, 0.0f), 0, pml.traceObj); - newtrace(&trace, pm->ps.origin, point, halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); + newtrace(&trace, pm->ps.origin, point, pm->ps.halfExtents, Ogre::Math::DegreesToRadians(pm->ps.viewangles.y), pm->isInterior, pm->mEngine); pml.groundTrace = trace; // do something corrective if the trace starts in a solid... diff --git a/libs/openengine/bullet/pmove.h b/libs/openengine/bullet/pmove.h index 63d03f86a9..fa303184e5 100644 --- a/libs/openengine/bullet/pmove.h +++ b/libs/openengine/bullet/pmove.h @@ -23,7 +23,7 @@ Quake 3 Arena is copyright (C) 1999-2005 Id Software, Inc. extern SceneInstance* global_lastscene; #endif*/ -static const Ogre::Vector3 halfExtents(14.64f * 2, 14.24f * 2, 33.25f * 2); +static const Ogre::Vector3 halfExtentsDefault(14.64f * 2, 14.24f * 2, 33.25f * 2); #define MAX_CLIP_PLANES 5 #define OVERCLIP 1.001f @@ -89,7 +89,7 @@ struct playerMove { struct playerStruct { - playerStruct() : gravity(800.0f), speed(480.0f), jump_velocity(270), pmove_framecount(20), groundEntityNum(ENTITYNUM_NONE), commandTime(40), move_type(PM_NOCLIP), pm_time(0), snappingImplemented(true), bSnap(false), counter(-1) + playerStruct() : gravity(800.0f), speed(480.0f), jump_velocity(270), pmove_framecount(20), groundEntityNum(ENTITYNUM_NONE), commandTime(40), move_type(PM_NOCLIP), pm_time(0), snappingImplemented(true), bSnap(false), counter(-1), halfExtents(halfExtentsDefault) { origin = Ogre::Vector3(0.0f, 0.0f, 0.0f); velocity = Ogre::Vector3(0.0f, 0.0f, 0.0f); @@ -116,6 +116,7 @@ struct playerMove Ogre::Vector3 velocity; Ogre::Vector3 origin; + Ogre::Vector3 halfExtents; bool bSnap; bool snappingImplemented; int counter; From 05687c120fc5692bf04cbff89ab5230bd7ab78d7 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Sun, 16 Sep 2012 17:48:18 -0400 Subject: [PATCH 58/84] protection for null cast --- libs/openengine/bullet/physic.cpp | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index 4ced2db904..b52c09edac 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -37,9 +37,11 @@ namespace Physic pmove = new playerMove; pmove->mEngine = mEngine; btBoxShape* box = static_cast (mBody->getCollisionShape()); - btVector3 size = box->getHalfExtentsWithMargin(); - Ogre::Vector3 halfExtents = Ogre::Vector3(size.getX(), size.getY(), size.getZ()); - pmove->ps.halfExtents = halfExtents; + if(box != NULL){ + btVector3 size = box->getHalfExtentsWithMargin(); + Ogre::Vector3 halfExtents = Ogre::Vector3(size.getX(), size.getY(), size.getZ()); + pmove->ps.halfExtents = halfExtents; + } } PhysicActor::~PhysicActor() @@ -147,9 +149,11 @@ namespace Physic mBody = mEngine->createAndAdjustRigidBody(mMesh, mName, scale, position, rotation); mEngine->addRigidBody(mBody, false); //Add rigid body to dynamics world, but do not add to object map btBoxShape* box = static_cast (mBody->getCollisionShape()); - btVector3 size = box->getHalfExtentsWithMargin(); - Ogre::Vector3 halfExtents = Ogre::Vector3(size.getX(), size.getY(), size.getZ()); - pmove->ps.halfExtents = halfExtents; + if(box != NULL){ + btVector3 size = box->getHalfExtentsWithMargin(); + Ogre::Vector3 halfExtents = Ogre::Vector3(size.getX(), size.getY(), size.getZ()); + pmove->ps.halfExtents = halfExtents; + } } void PhysicActor::runPmove(){ From ff54508633b75518387958ce624c0dde854307a1 Mon Sep 17 00:00:00 2001 From: Brother Brick Date: Mon, 17 Sep 2012 11:57:29 +0200 Subject: [PATCH 59/84] during cleanup we now delete all plugins created --- libs/openengine/ogre/renderer.cpp | 29 ++++++++++++++++++++++++++++- libs/openengine/ogre/renderer.hpp | 4 +++- 2 files changed, 31 insertions(+), 2 deletions(-) diff --git a/libs/openengine/ogre/renderer.cpp b/libs/openengine/ogre/renderer.cpp index daf82b9dac..9251e5683e 100644 --- a/libs/openengine/ogre/renderer.cpp +++ b/libs/openengine/ogre/renderer.cpp @@ -44,8 +44,10 @@ void OgreRenderer::cleanup() delete mFader; mFader = NULL; - OGRE_DELETE mRoot; + delete mRoot; mRoot = NULL; + + unloadPlugins(); } void OgreRenderer::start() @@ -103,6 +105,31 @@ bool OgreRenderer::loadPlugins() return true; } +bool OgreRenderer::unloadPlugins() +{ + #ifdef ENABLE_PLUGIN_GL + delete mGLPlugin; + mGLPlugin = NULL; + #endif + #ifdef ENABLE_PLUGIN_Direct3D9 + delete mD3D9Plugin; + mD3D9Plugin = NULL; + #endif + #ifdef ENABLE_PLUGIN_CgProgramManager + delete mCgPlugin; + mCgPlugin = NULL; + #endif + #ifdef ENABLE_PLUGIN_OctreeSceneManager + delete mOctreePlugin; + mOctreePlugin = NULL; + #endif + #ifdef ENABLE_PLUGIN_ParticleFX + delete mParticleFXPlugin; + mParticleFXPlugin = NULL; + #endif + return true; +} + void OgreRenderer::update(float dt) { mFader->update(dt); diff --git a/libs/openengine/ogre/renderer.hpp b/libs/openengine/ogre/renderer.hpp index 00e094b4dc..b71da90202 100644 --- a/libs/openengine/ogre/renderer.hpp +++ b/libs/openengine/ogre/renderer.hpp @@ -151,7 +151,9 @@ namespace OEngine /// Start the main rendering loop void start(); - bool loadPlugins() ; + bool loadPlugins(); + + bool unloadPlugins(); void update(float dt); From 032ff7c879e2b80423f21576f508edc8e8753776 Mon Sep 17 00:00:00 2001 From: gugus Date: Mon, 17 Sep 2012 13:36:48 +0200 Subject: [PATCH 60/84] Clean-up. There is still a little bug. --- apps/openmw/mwbase/world.hpp | 3 ++ .../mwscript/transformationextensions.cpp | 36 ++++++++++--------- apps/openmw/mwworld/worldimp.cpp | 5 +++ apps/openmw/mwworld/worldimp.hpp | 3 ++ 4 files changed, 31 insertions(+), 16 deletions(-) diff --git a/apps/openmw/mwbase/world.hpp b/apps/openmw/mwbase/world.hpp index b0ce261f1e..ef4e6a5b85 100644 --- a/apps/openmw/mwbase/world.hpp +++ b/apps/openmw/mwbase/world.hpp @@ -187,6 +187,9 @@ namespace MWBase virtual void rotateObject(const MWWorld::Ptr& ptr,float x,float y,float z, bool adjust = false) = 0; + virtual void safePlaceObject(const MWWorld::Ptr& ptr,MWWorld::CellStore &Cell,ESM::Position pos) = 0; + ///< place an object in a "safe" location (ie not in the void, etc). Makes a copy of the Ptr. + virtual void indexToPosition (int cellX, int cellY, float &x, float &y, bool centre = false) const = 0; ///< Convert cell numbers to position. diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index c82108f8bb..e40390a635 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -19,6 +19,7 @@ #include "../mwworld/player.hpp" #include "components\esm\loadcell.hpp" +#include "../mwworld/manualref.hpp" #include "OgreMath.h" namespace MWScript @@ -369,7 +370,7 @@ namespace MWScript pos.rot[0] = pos.rot[1] = 0; pos.rot[2] = zRot; MWWorld::Ptr ptr = MWBase::Environment::get().getWorld()->getPtr(itemID,false); - MWBase::Environment::get().getWorld()->copyObjectToCell(ptr,*store,pos); + MWBase::Environment::get().getWorld()->safePlaceObject(ptr,*store,pos); } else { @@ -412,7 +413,7 @@ namespace MWScript pos.rot[0] = pos.rot[1] = 0; pos.rot[2] = zRot; MWWorld::Ptr ptr = MWBase::Environment::get().getWorld()->getPtr(itemID,false); - MWBase::Environment::get().getWorld()->copyObjectToCell(ptr,*store,pos); + MWBase::Environment::get().getWorld()->safePlaceObject(ptr,*store,pos); } else { @@ -450,13 +451,14 @@ namespace MWScript ipos.pos[0] = pos.x; ipos.pos[1] = pos.y; ipos.pos[2] = pos.z; + ipos.rot[0] = 0; + ipos.rot[1] = 0; + ipos.rot[2] = 0; + MWWorld::CellStore* store = MWBase::Environment::get().getWorld()->getPlayer().getPlayer().getCell(); - MWWorld::Ptr ptr = MWBase::Environment::get().getWorld()->getPtr(itemID,false); - int icount = ptr.getRefData().getCount(); - ptr.getRefData().setCount(count); - MWBase::Environment::get().getWorld()->copyObjectToCell(ptr,*store,ipos); - ptr.getRefData().setCount(icount); - //store->ge + MWWorld::ManualRef ref(MWBase::Environment::get().getWorld()->getStore(),itemID); + ref.getPtr().getRefData().setCount(count); + MWBase::Environment::get().getWorld()->safePlaceObject(ref.getPtr(),*store,ipos); } }; @@ -491,13 +493,15 @@ namespace MWScript ipos.pos[0] = pos.x; ipos.pos[1] = pos.y; ipos.pos[2] = pos.z; + ipos.rot[0] = 0; + ipos.rot[1] = 0; + ipos.rot[2] = 0; + MWWorld::CellStore* store = me.getCell(); - MWWorld::Ptr ptr = MWBase::Environment::get().getWorld()->getPtr(itemID,false); - int icount = ptr.getRefData().getCount(); - ptr.getRefData().setCount(count); - MWBase::Environment::get().getWorld()->copyObjectToCell(ptr,*store,ipos); - ptr.getRefData().setCount(icount); - //store->ge + MWWorld::ManualRef ref(MWBase::Environment::get().getWorld()->getStore(),itemID); + ref.getPtr().getRefData().setCount(count); + MWBase::Environment::get().getWorld()->safePlaceObject(ref.getPtr(),*store,ipos); + } }; @@ -566,8 +570,8 @@ namespace MWScript interpreter.installSegment5(opcodePlaceItemCell,new OpPlaceItemCell); interpreter.installSegment5(opcodePlaceItem,new OpPlaceItem); interpreter.installSegment5(opcodePlaceAtPc,new OpPlaceAtPc); - interpreter.installSegment5(opcodePlaceAtMe,new OpPlaceAtPc); - interpreter.installSegment5(opcodePlaceAtMeExplicit,new OpPlaceAtPc); + interpreter.installSegment5(opcodePlaceAtMe,new OpPlaceAtMe); + interpreter.installSegment5(opcodePlaceAtMeExplicit,new OpPlaceAtMe); } } } diff --git a/apps/openmw/mwworld/worldimp.cpp b/apps/openmw/mwworld/worldimp.cpp index d9c4fe3212..fb475f3615 100644 --- a/apps/openmw/mwworld/worldimp.cpp +++ b/apps/openmw/mwworld/worldimp.cpp @@ -656,6 +656,11 @@ namespace MWWorld } } + void World::safePlaceObject(const MWWorld::Ptr& ptr,MWWorld::CellStore &Cell,ESM::Position pos) + { + copyObjectToCell(ptr,Cell,pos); + } + void World::indexToPosition (int cellX, int cellY, float &x, float &y, bool centre) const { const int cellSize = 8192; diff --git a/apps/openmw/mwworld/worldimp.hpp b/apps/openmw/mwworld/worldimp.hpp index 4031a180a8..acf63b54a0 100644 --- a/apps/openmw/mwworld/worldimp.hpp +++ b/apps/openmw/mwworld/worldimp.hpp @@ -214,6 +214,9 @@ namespace MWWorld /// \param adjust indicates rotation should be set or adjusted virtual void rotateObject (const Ptr& ptr,float x,float y,float z, bool adjust = false); + virtual void safePlaceObject(const MWWorld::Ptr& ptr,MWWorld::CellStore &Cell,ESM::Position pos); + ///< place an object in a "safe" location (ie not in the void, etc). Makes a copy of the Ptr. + virtual void indexToPosition (int cellX, int cellY, float &x, float &y, bool centre = false) const; ///< Convert cell numbers to position. From b96485284a64dcf005d6b43aeafff2d919f4783f Mon Sep 17 00:00:00 2001 From: Marc Zinnschlag Date: Mon, 17 Sep 2012 13:41:15 +0200 Subject: [PATCH 61/84] removed some unneeded return values --- libs/openengine/ogre/renderer.cpp | 6 ++---- libs/openengine/ogre/renderer.hpp | 4 ++-- 2 files changed, 4 insertions(+), 6 deletions(-) diff --git a/libs/openengine/ogre/renderer.cpp b/libs/openengine/ogre/renderer.cpp index 8cff0f9e00..65911df342 100644 --- a/libs/openengine/ogre/renderer.cpp +++ b/libs/openengine/ogre/renderer.cpp @@ -80,7 +80,7 @@ void OgreRenderer::start() #endif } -bool OgreRenderer::loadPlugins() +void OgreRenderer::loadPlugins() { #ifdef ENABLE_PLUGIN_GL mGLPlugin = new Ogre::GLPlugin(); @@ -102,10 +102,9 @@ bool OgreRenderer::loadPlugins() mParticleFXPlugin = new Ogre::ParticleFXPlugin(); mRoot->installPlugin(mParticleFXPlugin); #endif - return true; } -bool OgreRenderer::unloadPlugins() +void OgreRenderer::unloadPlugins() { #ifdef ENABLE_PLUGIN_GL delete mGLPlugin; @@ -127,7 +126,6 @@ bool OgreRenderer::unloadPlugins() delete mParticleFXPlugin; mParticleFXPlugin = NULL; #endif - return true; } void OgreRenderer::update(float dt) diff --git a/libs/openengine/ogre/renderer.hpp b/libs/openengine/ogre/renderer.hpp index b71da90202..95bcac3b87 100644 --- a/libs/openengine/ogre/renderer.hpp +++ b/libs/openengine/ogre/renderer.hpp @@ -151,9 +151,9 @@ namespace OEngine /// Start the main rendering loop void start(); - bool loadPlugins(); + void loadPlugins(); - bool unloadPlugins(); + void unloadPlugins(); void update(float dt); From 3c1a9061de1641fa03e4a69c25b050ee89ae7f2a Mon Sep 17 00:00:00 2001 From: gugus Date: Mon, 17 Sep 2012 14:12:27 +0200 Subject: [PATCH 62/84] Fixed a bug of Ptr having a wrong orientation. But that's strange, seems CellRef isn't initialized properly --- apps/openmw/mwscript/transformationextensions.cpp | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index e40390a635..5b43453ebf 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -369,8 +369,9 @@ namespace MWScript pos.pos[2] = z; pos.rot[0] = pos.rot[1] = 0; pos.rot[2] = zRot; - MWWorld::Ptr ptr = MWBase::Environment::get().getWorld()->getPtr(itemID,false); - MWBase::Environment::get().getWorld()->safePlaceObject(ptr,*store,pos); + MWWorld::ManualRef ref(MWBase::Environment::get().getWorld()->getStore(),itemID); + ref.getPtr().getCellRef().pos = pos; + MWBase::Environment::get().getWorld()->safePlaceObject(ref.getPtr(),*store,pos); } else { @@ -412,8 +413,9 @@ namespace MWScript pos.pos[2] = z; pos.rot[0] = pos.rot[1] = 0; pos.rot[2] = zRot; - MWWorld::Ptr ptr = MWBase::Environment::get().getWorld()->getPtr(itemID,false); - MWBase::Environment::get().getWorld()->safePlaceObject(ptr,*store,pos); + MWWorld::ManualRef ref(MWBase::Environment::get().getWorld()->getStore(),itemID); + ref.getPtr().getCellRef().pos = pos; + MWBase::Environment::get().getWorld()->safePlaceObject(ref.getPtr(),*store,pos); } else { @@ -457,6 +459,7 @@ namespace MWScript MWWorld::CellStore* store = MWBase::Environment::get().getWorld()->getPlayer().getPlayer().getCell(); MWWorld::ManualRef ref(MWBase::Environment::get().getWorld()->getStore(),itemID); + ref.getPtr().getCellRef().pos = ipos; ref.getPtr().getRefData().setCount(count); MWBase::Environment::get().getWorld()->safePlaceObject(ref.getPtr(),*store,ipos); } @@ -499,6 +502,7 @@ namespace MWScript MWWorld::CellStore* store = me.getCell(); MWWorld::ManualRef ref(MWBase::Environment::get().getWorld()->getStore(),itemID); + ref.getPtr().getCellRef().pos = ipos; ref.getPtr().getRefData().setCount(count); MWBase::Environment::get().getWorld()->safePlaceObject(ref.getPtr(),*store,ipos); From f01aae138f1fc88f3358b4d31c2b024f52b60413 Mon Sep 17 00:00:00 2001 From: Jason Hooks Date: Mon, 17 Sep 2012 17:23:26 -0400 Subject: [PATCH 63/84] Removing void --- libs/openengine/bullet/physic.cpp | 4 ++-- libs/openengine/bullet/physic.hpp | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/libs/openengine/bullet/physic.cpp b/libs/openengine/bullet/physic.cpp index b52c09edac..74352b358b 100644 --- a/libs/openengine/bullet/physic.cpp +++ b/libs/openengine/bullet/physic.cpp @@ -112,7 +112,7 @@ namespace Physic } } - Ogre::Vector3 PhysicActor::getPosition(void) + Ogre::Vector3 PhysicActor::getPosition() { btVector3 vec = mBody->getWorldTransform().getOrigin(); Ogre::Quaternion rotation = Ogre::Quaternion(mBody->getWorldTransform().getRotation().getW(), mBody->getWorldTransform().getRotation().getX(), @@ -122,7 +122,7 @@ namespace Physic return visualPosition; } - Ogre::Quaternion PhysicActor::getRotation(void) + Ogre::Quaternion PhysicActor::getRotation() { btQuaternion quat = mBody->getWorldTransform().getRotation() * mBoxRotationInverse; return Ogre::Quaternion(quat.getW(), quat.getX(), quat.getY(), quat.getZ()); diff --git a/libs/openengine/bullet/physic.hpp b/libs/openengine/bullet/physic.hpp index a69d80e534..e4e71706f7 100644 --- a/libs/openengine/bullet/physic.hpp +++ b/libs/openengine/bullet/physic.hpp @@ -93,12 +93,12 @@ namespace Physic * This returns the visual position of the PhysicActor (used to position a scenenode). * Note - this is different from the position of the contained mBody. */ - Ogre::Vector3 getPosition(void); + Ogre::Vector3 getPosition(); /** * Returns the visual orientation of the PhysicActor */ - Ogre::Quaternion getRotation(void); + Ogre::Quaternion getRotation(); /** * Sets the position of mBody from a visual position input. From 408c5b8bd46214e685792aab4750d19688418776 Mon Sep 17 00:00:00 2001 From: Marc Zinnschlag Date: Tue, 18 Sep 2012 10:49:51 +0200 Subject: [PATCH 64/84] some cleanup --- .../mwscript/transformationextensions.cpp | 24 +++++++++---------- 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 4ce1c7cdfe..cd979e2ecb 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -1,6 +1,9 @@ #include +#include + #include +#include #include @@ -11,18 +14,13 @@ #include "../mwbase/environment.hpp" #include "../mwworld/class.hpp" +#include "../mwworld/player.hpp" +#include "../mwworld/manualref.hpp" #include "interpretercontext.hpp" #include "ref.hpp" #include "OgreSceneNode.h" - -#include "../mwworld/player.hpp" -#include -#include "../mwworld/manualref.hpp" - -#include "OgreMath.h" - namespace MWScript { namespace Transformation @@ -172,6 +170,8 @@ namespace MWScript { runtime.push(ptr.getRefData().getPosition().pos[2]); } + else + throw std::runtime_error ("invalid rotation axis: " + axis); } }; @@ -192,7 +192,6 @@ namespace MWScript float ax = ptr.getRefData().getPosition().pos[0]; float ay = ptr.getRefData().getPosition().pos[1]; float az = ptr.getRefData().getPosition().pos[2]; - if(axis == "x") { @@ -206,6 +205,8 @@ namespace MWScript { MWBase::Environment::get().getWorld()->moveObject(ptr,ax,ay,pos); } + else + throw std::runtime_error ("invalid axis: " + axis); } }; @@ -233,6 +234,8 @@ namespace MWScript { runtime.push(ptr.getCellRef().pos.pos[2]); } + else + throw std::runtime_error ("invalid axis: " + axis); } }; @@ -331,8 +334,6 @@ namespace MWScript virtual void execute (Interpreter::Runtime& runtime) { - //MWWorld::Ptr ptr = R()(runtime); - std::string itemID = runtime.getStringLiteral (runtime[0].mInteger); runtime.pop(); std::string cellID = runtime.getStringLiteral (runtime[0].mInteger); @@ -402,10 +403,9 @@ namespace MWScript Interpreter::Type_Float zRot = runtime[0].mFloat; runtime.pop(); - MWWorld::CellStore* store = 0; int cx,cy; MWBase::Environment::get().getWorld()->positionToIndex(x,y,cx,cy); - store = MWBase::Environment::get().getWorld()->getExterior(cx,cy); + MWWorld::CellStore* store = MWBase::Environment::get().getWorld()->getExterior(cx,cy); if(store) { ESM::Position pos; From ea8eab4f34f2d0b16050cd4ae33dd1bdd7bce82c Mon Sep 17 00:00:00 2001 From: Marc Zinnschlag Date: Tue, 18 Sep 2012 11:06:19 +0200 Subject: [PATCH 65/84] more cleanup --- apps/openmw/mwbase/world.hpp | 7 ++----- apps/openmw/mwscript/transformationextensions.cpp | 4 +--- 2 files changed, 3 insertions(+), 8 deletions(-) diff --git a/apps/openmw/mwbase/world.hpp b/apps/openmw/mwbase/world.hpp index 9d432c5b6a..b841e5427a 100644 --- a/apps/openmw/mwbase/world.hpp +++ b/apps/openmw/mwbase/world.hpp @@ -142,9 +142,6 @@ namespace MWBase virtual MWWorld::Ptr getPtrViaHandle (const std::string& handle) = 0; ///< Return a pointer to a liveCellRef with the given Ogre handle. - virtual void - copyObjectToCell(const MWWorld::Ptr &ptr, MWWorld::CellStore &cell, const ESM::Position &pos) = 0; - /// \todo enable reference in the OGRE scene virtual void enable (const MWWorld::Ptr& ptr) = 0; @@ -208,7 +205,7 @@ namespace MWBase virtual void rotateObject(const MWWorld::Ptr& ptr,float x,float y,float z, bool adjust = false) = 0; virtual void safePlaceObject(const MWWorld::Ptr& ptr,MWWorld::CellStore &Cell,ESM::Position pos) = 0; - ///< place an object in a "safe" location (ie not in the void, etc). Makes a copy of the Ptr. + ///< place an object in a "safe" location (ie not in the void, etc). virtual void indexToPosition (int cellX, int cellY, float &x, float &y, bool centre = false) const = 0; @@ -224,7 +221,7 @@ namespace MWBase virtual bool toggleCollisionMode() = 0; ///< Toggle collision mode for player. If disabled player object should ignore /// collisions and gravity. - ///< \return Resulting mode + /// \return Resulting mode virtual bool toggleRenderMode (RenderMode mode) = 0; ///< Toggle a render mode. diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index cd979e2ecb..570b8e0811 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -1,6 +1,7 @@ #include #include +#include #include #include @@ -19,7 +20,6 @@ #include "interpretercontext.hpp" #include "ref.hpp" -#include "OgreSceneNode.h" namespace MWScript { @@ -389,8 +389,6 @@ namespace MWScript virtual void execute (Interpreter::Runtime& runtime) { - //MWWorld::Ptr ptr = R()(runtime); - std::string itemID = runtime.getStringLiteral (runtime[0].mInteger); runtime.pop(); From fcda3b6ca8a87c26d25aea387f6a68b51851c633 Mon Sep 17 00:00:00 2001 From: Marc Zinnschlag Date: Tue, 18 Sep 2012 11:09:54 +0200 Subject: [PATCH 66/84] fixed some script argument types --- apps/openmw/mwscript/transformationextensions.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 570b8e0811..5db5571741 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -537,13 +537,13 @@ namespace MWScript { extensions.registerInstruction("setscale","f",opcodeSetScale,opcodeSetScaleExplicit); extensions.registerFunction("getscale",'f',"",opcodeGetScale,opcodeGetScaleExplicit); - extensions.registerInstruction("setangle","Sf",opcodeSetAngle,opcodeSetAngleExplicit); - extensions.registerFunction("getangle",'f',"S",opcodeGetAngle,opcodeGetAngleExplicit); + extensions.registerInstruction("setangle","cf",opcodeSetAngle,opcodeSetAngleExplicit); + extensions.registerFunction("getangle",'f',"c",opcodeGetAngle,opcodeGetAngleExplicit); extensions.registerInstruction("setpos","cf",opcodeSetPos,opcodeSetPosExplicit); extensions.registerFunction("getpos",'f',"c",opcodeGetPos,opcodeGetPosExplicit); extensions.registerFunction("getstartingpos",'f',"c",opcodeGetStartingPos,opcodeGetStartingPosExplicit); extensions.registerInstruction("position","ffff",opcodePosition,opcodePositionExplicit); - extensions.registerInstruction("positioncell","ffffS",opcodePositionCell,opcodePositionCellExplicit); + extensions.registerInstruction("positioncell","ffffc",opcodePositionCell,opcodePositionCellExplicit); extensions.registerInstruction("placeitemcell","ccffff",opcodePlaceItemCell); extensions.registerInstruction("placeitem","cffff",opcodePlaceItem); extensions.registerInstruction("placeatpc","clfl",opcodePlaceAtPc); From 747a4e1123c244671356655930ce510b86c82db5 Mon Sep 17 00:00:00 2001 From: Marc Zinnschlag Date: Tue, 18 Sep 2012 11:19:21 +0200 Subject: [PATCH 67/84] increased version number and updated readme --- CMakeLists.txt | 2 +- readme.txt | 35 ++++++++++++++++++++++++++++++++++- 2 files changed, 35 insertions(+), 2 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 0a24998d15..aee073d3ef 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -15,7 +15,7 @@ include (OpenMWMacros) # Version set (OPENMW_VERSION_MAJOR 0) -set (OPENMW_VERSION_MINOR 17) +set (OPENMW_VERSION_MINOR 18) set (OPENMW_VERSION_RELEASE 0) set (OPENMW_VERSION "${OPENMW_VERSION_MAJOR}.${OPENMW_VERSION_MINOR}.${OPENMW_VERSION_RELEASE}") diff --git a/readme.txt b/readme.txt index a254e2672b..20aff18aef 100644 --- a/readme.txt +++ b/readme.txt @@ -3,7 +3,7 @@ OpenMW: A reimplementation of The Elder Scrolls III: Morrowind OpenMW is an attempt at recreating the engine for the popular role-playing game Morrowind by Bethesda Softworks. You need to own and install the original game for OpenMW to work. -Version: 0.17.0 +Version: 0.18.0 License: GPL (see GPL3.txt for more information) Website: http://www.openmw.org @@ -97,6 +97,39 @@ Allowed options: CHANGELOG +0.18.0 + +Bug #310: Button of the "preferences menu" are too small +Bug #361: Hand-to-hand skill is always 100 +Bug #365: NPC and creature animation is jerky; Characters float around when they are not supposed to +Bug #372: playSound3D uses original coordinates instead of current coordinates. +Bug #373: Static OGRE build faulty +Bug #375: Alt-tab toggle view +Bug #376: Screenshots are disable +Bug #378: Exception when drinking self-made potions +Bug #380: Cloth visibility problem +Bug #384: Weird character on doors tooltip. +Bug #398: Some objects do not collide in MW, but do so in OpenMW +Feature #22: Implement level-up +Feature #36: Hide Marker +Feature #88: Hotkey Window +Feature #91: Level-Up Dialogue +Feature #118: Keyboard and Mouse-Button bindings +Feature #119: Spell Buying Window +Feature #133: Handle resources across multiple data directories +Feature #134: Generate a suitable default-value for --data-local +Feature #292: Object Movement/Creation Script Instructions +Feature #340: AIPackage data structures +Feature #356: Ingredients use +Feature #358: Input system rewrite +Feature #370: Target handling in actions +Feature #379: Door markers on the local map +Feature #389: AI framework +Feature #395: Using keys to open doors / containers +Feature #396: Loading screens +Feature #397: Inventory avatar image and race selection head preview +Task #339: Move sounds into Action + 0.17.0 Bug #225: Valgrind reports about 40MB of leaked memory From 0ba996f290eefb21ae11e93f81ef0f6421426dea Mon Sep 17 00:00:00 2001 From: scrawl Date: Tue, 18 Sep 2012 18:29:03 +0200 Subject: [PATCH 68/84] dialog layout --- apps/openmw/CMakeLists.txt | 2 +- apps/openmw/mwgui/waitdialog.cpp | 12 ++ apps/openmw/mwgui/waitdialog.hpp | 19 +++ apps/openmw/mwgui/widgets.cpp | 166 ++++++++++++++++++++++--- apps/openmw/mwgui/widgets.hpp | 19 ++- apps/openmw/mwgui/windowmanagerimp.cpp | 9 +- apps/openmw/mwgui/windowmanagerimp.hpp | 2 + files/mygui/CMakeLists.txt | 1 + files/mygui/openmw_wait_dialog.layout | 45 +++++++ 9 files changed, 257 insertions(+), 18 deletions(-) create mode 100644 apps/openmw/mwgui/waitdialog.cpp create mode 100644 apps/openmw/mwgui/waitdialog.hpp create mode 100644 files/mygui/openmw_wait_dialog.layout diff --git a/apps/openmw/CMakeLists.txt b/apps/openmw/CMakeLists.txt index 2542ef350e..bcd5fc8530 100644 --- a/apps/openmw/CMakeLists.txt +++ b/apps/openmw/CMakeLists.txt @@ -29,7 +29,7 @@ add_openmw_dir (mwgui map_window window_pinnable_base cursorreplace tooltips scrollwindow bookwindow list formatting inventorywindow container hud countdialog tradewindow settingswindow confirmationdialog alchemywindow referenceinterface spellwindow mainmenu quickkeysmenu - itemselection spellbuyingwindow loadingscreen levelupdialog + itemselection spellbuyingwindow loadingscreen levelupdialog waitdialog ) add_openmw_dir (mwdialogue diff --git a/apps/openmw/mwgui/waitdialog.cpp b/apps/openmw/mwgui/waitdialog.cpp new file mode 100644 index 0000000000..5b491a4f26 --- /dev/null +++ b/apps/openmw/mwgui/waitdialog.cpp @@ -0,0 +1,12 @@ +#include "waitdialog.hpp" + +namespace MWGui +{ + + WaitDialog::WaitDialog(MWBase::WindowManager &parWindowManager) + : WindowBase("openmw_wait_dialog.layout", parWindowManager) + { + center(); + } + +} diff --git a/apps/openmw/mwgui/waitdialog.hpp b/apps/openmw/mwgui/waitdialog.hpp new file mode 100644 index 0000000000..3c68c1249b --- /dev/null +++ b/apps/openmw/mwgui/waitdialog.hpp @@ -0,0 +1,19 @@ +#ifndef MWGUI_WAIT_DIALOG_H +#define MWGUI_WAIT_DIALOG_H + +#include "window_base.hpp" + +namespace MWGui +{ + + class WaitDialog : public WindowBase + { + public: + WaitDialog(MWBase::WindowManager& parWindowManager); + + + }; + +} + +#endif diff --git a/apps/openmw/mwgui/widgets.cpp b/apps/openmw/mwgui/widgets.cpp index 97a5b2eb5b..e8cee21412 100644 --- a/apps/openmw/mwgui/widgets.cpp +++ b/apps/openmw/mwgui/widgets.cpp @@ -869,29 +869,33 @@ void AutoSizedButton::setPropertyOverride(const std::string& _key, const std::st Box::Box() : mSpacing(4) + , mPadding(0) + , mAutoResize(false) { } -void Box::setPropertyOverride(const std::string& _key, const std::string& _value) -{ - if (_key == "Spacing") - { - mSpacing = MyGUI::utility::parseValue(_value); - } -} - void Box::notifyChildrenSizeChanged () { align(); } +void Box::_setPropertyImpl(const std::string& _key, const std::string& _value) +{ + if (_key == "Spacing") + mSpacing = MyGUI::utility::parseValue(_value); + else if (_key == "Padding") + mPadding = MyGUI::utility::parseValue(_value); + else if (_key == "AutoResize") + mAutoResize = MyGUI::utility::parseValue(_value); +} void HBox::align () { unsigned int count = getChildCount (); size_t h_stretched_count = 0; int total_width = 0; + int total_height = 0; std::vector< std::pair > sizes; for (unsigned int i = 0; i < count; ++i) @@ -904,28 +908,43 @@ void HBox::align () { sizes.push_back(std::make_pair(aw->getRequestedSize (), hstretch)); total_width += aw->getRequestedSize ().width; + total_height = std::max(total_height, aw->getRequestedSize ().height); } else { - if (!hstretch) h_stretched_count ++; - sizes.push_back (std::make_pair(MyGUI::IntSize(0,0), true)); + sizes.push_back (std::make_pair(w->getSize(), hstretch)); + total_width += w->getSize().width; } if (i != count-1) total_width += mSpacing; } + if (mAutoResize && (total_width+mPadding*2 != getSize().width || total_height+mPadding*2 != getSize().height)) + { + setSize(MyGUI::IntSize(total_width+mPadding*2, total_height+mPadding*2)); + return; + } + + int curX = 0; for (unsigned int i = 0; i < count; ++i) { + if (i == 0) + curX += mPadding; + MyGUI::Widget* w = getChildAt(i); + + bool vstretch = w->getUserString ("VStretch") == "true"; + int height = vstretch ? total_height : sizes[i].first.height; + MyGUI::IntCoord widgetCoord; widgetCoord.left = curX; - widgetCoord.top = (getSize().height - sizes[i].first.height) / 2; - int width = sizes[i].second ? sizes[i].first.width + (getSize().width - total_width)/h_stretched_count + widgetCoord.top = mPadding + (getSize().height-mPadding*2 - height) / 2; + int width = sizes[i].second ? sizes[i].first.width + (getSize().width-mPadding*2 - total_width)/h_stretched_count : sizes[i].first.width; widgetCoord.width = width; - widgetCoord.height = sizes[i].first.height; + widgetCoord.height = height; w->setCoord(widgetCoord); curX += width; @@ -934,12 +953,33 @@ void HBox::align () } } +void HBox::setPropertyOverride(const std::string& _key, const std::string& _value) +{ + Box::_setPropertyImpl (_key, _value); +} + void HBox::setSize (const MyGUI::IntSize& _value) { MyGUI::Widget::setSize (_value); align(); } +void HBox::setCoord (const MyGUI::IntCoord& _value) +{ + MyGUI::Widget::setCoord (_value); + align(); +} + +void HBox::onWidgetCreated(MyGUI::Widget* _widget) +{ + align(); +} + +void HBox::onWidgetDestroy(MyGUI::Widget* _widget) +{ + align(); +} + MyGUI::IntSize HBox::getRequestedSize () { MyGUI::IntSize size(0,0); @@ -954,6 +994,16 @@ MyGUI::IntSize HBox::getRequestedSize () if (i != getChildCount()-1) size.width += mSpacing; } + else + { + MyGUI::IntSize requested = getChildAt(i)->getSize (); + size.height = std::max(size.height, requested.height); + size.width = size.width + requested.width; + if (i != getChildCount()-1) + size.width += mSpacing; + } + size.height += mPadding*2; + size.width += mPadding*2; } return size; } @@ -963,7 +1013,69 @@ MyGUI::IntSize HBox::getRequestedSize () void VBox::align () { - // not yet implemented + unsigned int count = getChildCount (); + size_t v_stretched_count = 0; + int total_height = 0; + int total_width = 0; + std::vector< std::pair > sizes; + for (unsigned int i = 0; i < count; ++i) + { + MyGUI::Widget* w = getChildAt(i); + bool vstretch = w->getUserString ("VStretch") == "true"; + v_stretched_count += vstretch; + AutoSizedWidget* aw = dynamic_cast(w); + if (aw) + { + sizes.push_back(std::make_pair(aw->getRequestedSize (), vstretch)); + total_height += aw->getRequestedSize ().height; + total_width = std::max(total_width, aw->getRequestedSize ().width); + } + else + { + sizes.push_back (std::make_pair(w->getSize(), vstretch)); + total_height += w->getSize().height; + } + + if (i != count-1) + total_height += mSpacing; + } + + if (mAutoResize && (total_width+mPadding*2 != getSize().width || total_height+mPadding*2 != getSize().height)) + { + setSize(MyGUI::IntSize(total_width+mPadding*2, total_height+mPadding*2)); + return; + } + + + int curY = 0; + for (unsigned int i = 0; i < count; ++i) + { + if (i==0) + curY += mPadding; + + MyGUI::Widget* w = getChildAt(i); + + bool hstretch = w->getUserString ("HStretch") == "true"; + int width = hstretch ? total_width : sizes[i].first.width; + + MyGUI::IntCoord widgetCoord; + widgetCoord.top = curY; + widgetCoord.left = mPadding + (getSize().width-mPadding*2 - width) / 2; + int height = sizes[i].second ? sizes[i].first.height + (getSize().height-mPadding*2 - total_height)/v_stretched_count + : sizes[i].first.height; + widgetCoord.height = height; + widgetCoord.width = width; + w->setCoord(widgetCoord); + curY += height; + + if (i != count-1) + curY += mSpacing; + } +} + +void VBox::setPropertyOverride(const std::string& _key, const std::string& _value) +{ + Box::_setPropertyImpl (_key, _value); } void VBox::setSize (const MyGUI::IntSize& _value) @@ -972,6 +1084,12 @@ void VBox::setSize (const MyGUI::IntSize& _value) align(); } +void VBox::setCoord (const MyGUI::IntCoord& _value) +{ + MyGUI::Widget::setCoord (_value); + align(); +} + MyGUI::IntSize VBox::getRequestedSize () { MyGUI::IntSize size(0,0); @@ -986,6 +1104,26 @@ MyGUI::IntSize VBox::getRequestedSize () if (i != getChildCount()-1) size.height += mSpacing; } + else + { + MyGUI::IntSize requested = getChildAt(i)->getSize (); + size.width = std::max(size.width, requested.width); + size.height = size.height + requested.height; + if (i != getChildCount()-1) + size.height += mSpacing; + } + size.height += mPadding*2; + size.width += mPadding*2; } return size; } + +void VBox::onWidgetCreated(MyGUI::Widget* _widget) +{ + align(); +} + +void VBox::onWidgetDestroy(MyGUI::Widget* _widget) +{ + align(); +} diff --git a/apps/openmw/mwgui/widgets.hpp b/apps/openmw/mwgui/widgets.hpp index 16c2adec95..6298ea77d7 100644 --- a/apps/openmw/mwgui/widgets.hpp +++ b/apps/openmw/mwgui/widgets.hpp @@ -357,10 +357,13 @@ namespace MWGui protected: virtual void align() = 0; - virtual void setPropertyOverride(const std::string& _key, const std::string& _value); - + virtual void _setPropertyImpl(const std::string& _key, const std::string& _value); int mSpacing; // how much space to put between elements + + int mPadding; // outer padding + + bool mAutoResize; // auto resize the box so that it exactly fits all elements }; class HBox : public Box, public MyGUI::Widget @@ -369,10 +372,16 @@ namespace MWGui public: virtual void setSize (const MyGUI::IntSize &_value); + virtual void setCoord (const MyGUI::IntCoord &_value); protected: virtual void align(); virtual MyGUI::IntSize getRequestedSize(); + + virtual void setPropertyOverride(const std::string& _key, const std::string& _value); + + virtual void onWidgetCreated(MyGUI::Widget* _widget); + virtual void onWidgetDestroy(MyGUI::Widget* _widget); }; class VBox : public Box, public MyGUI::Widget @@ -381,10 +390,16 @@ namespace MWGui public: virtual void setSize (const MyGUI::IntSize &_value); + virtual void setCoord (const MyGUI::IntCoord &_value); protected: virtual void align(); virtual MyGUI::IntSize getRequestedSize(); + + virtual void setPropertyOverride(const std::string& _key, const std::string& _value); + + virtual void onWidgetCreated(MyGUI::Widget* _widget); + virtual void onWidgetDestroy(MyGUI::Widget* _widget); }; } } diff --git a/apps/openmw/mwgui/windowmanagerimp.cpp b/apps/openmw/mwgui/windowmanagerimp.cpp index 0241cc734a..5efd2b47a8 100644 --- a/apps/openmw/mwgui/windowmanagerimp.cpp +++ b/apps/openmw/mwgui/windowmanagerimp.cpp @@ -45,6 +45,7 @@ #include "quickkeysmenu.hpp" #include "loadingscreen.hpp" #include "levelupdialog.hpp" +#include "waitdialog.hpp" using namespace MWGui; @@ -71,6 +72,8 @@ WindowManager::WindowManager( , mSpellWindow(NULL) , mLoadingScreen(NULL) , mCharGen(NULL) + , mLevelupDialog(NULL) + , mWaitDialog(NULL) , mPlayerClass() , mPlayerName() , mPlayerRaceId() @@ -150,6 +153,7 @@ WindowManager::WindowManager( mSpellWindow = new SpellWindow(*this); mQuickKeysMenu = new QuickKeysMenu(*this); mLevelupDialog = new LevelupDialog(*this); + mWaitDialog = new WaitDialog(*this); mLoadingScreen = new LoadingScreen(mOgre->getScene (), mOgre->getWindow (), *this); mLoadingScreen->onResChange (w,h); @@ -204,6 +208,7 @@ WindowManager::~WindowManager() delete mSpellWindow; delete mLoadingScreen; delete mLevelupDialog; + delete mWaitDialog; cleanupGarbage(); @@ -252,6 +257,7 @@ void WindowManager::updateVisible() mSpellWindow->setVisible(false); mQuickKeysMenu->setVisible(false); mLevelupDialog->setVisible(false); + mWaitDialog->setVisible(false); mHud->setVisible(true); @@ -304,7 +310,8 @@ void WindowManager::updateVisible() mAlchemyWindow->setVisible(true); break; case GM_Rest: - mLevelupDialog->setVisible(true); + //mLevelupDialog->setVisible(true); + mWaitDialog->setVisible(true); break; case GM_Name: case GM_Race: diff --git a/apps/openmw/mwgui/windowmanagerimp.hpp b/apps/openmw/mwgui/windowmanagerimp.hpp index a02aa17b57..15c9c66313 100644 --- a/apps/openmw/mwgui/windowmanagerimp.hpp +++ b/apps/openmw/mwgui/windowmanagerimp.hpp @@ -63,6 +63,7 @@ namespace MWGui class QuickKeysMenu; class LoadingScreen; class LevelupDialog; + class WaitDialog; class WindowManager : public MWBase::WindowManager { @@ -229,6 +230,7 @@ namespace MWGui QuickKeysMenu* mQuickKeysMenu; LoadingScreen* mLoadingScreen; LevelupDialog* mLevelupDialog; + WaitDialog* mWaitDialog; CharacterCreation* mCharGen; diff --git a/files/mygui/CMakeLists.txt b/files/mygui/CMakeLists.txt index 55230fa76a..44235fa0e9 100644 --- a/files/mygui/CMakeLists.txt +++ b/files/mygui/CMakeLists.txt @@ -73,6 +73,7 @@ set(MYGUI_FILES openmw_spell_buying_window.layout openmw_loading_screen.layout openmw_levelup_dialog.layout + openmw_wait_dialog.layout smallbars.png VeraMono.ttf markers.png diff --git a/files/mygui/openmw_wait_dialog.layout b/files/mygui/openmw_wait_dialog.layout new file mode 100644 index 0000000000..527d5158da --- /dev/null +++ b/files/mygui/openmw_wait_dialog.layout @@ -0,0 +1,45 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + From 4d4ba6698abdd8e968fd98dc2386b748b19aa6a0 Mon Sep 17 00:00:00 2001 From: scrawl Date: Tue, 18 Sep 2012 19:00:20 +0200 Subject: [PATCH 69/84] fix character preview destruction; don't allow empty names in name dialog --- apps/openmw/mwgui/text_input.cpp | 16 ++++++++++++++-- apps/openmw/mwrender/characterpreview.cpp | 2 ++ 2 files changed, 16 insertions(+), 2 deletions(-) diff --git a/apps/openmw/mwgui/text_input.cpp b/apps/openmw/mwgui/text_input.cpp index 9d5ba98963..3dbe751659 100644 --- a/apps/openmw/mwgui/text_input.cpp +++ b/apps/openmw/mwgui/text_input.cpp @@ -47,10 +47,22 @@ void TextInputDialog::open() void TextInputDialog::onOkClicked(MyGUI::Widget* _sender) { - eventDone(this); + if (mTextEdit->getCaption() == "") + { + mWindowManager.messageBox ("#{sNotifyMessage37}", std::vector()); + MyGUI::InputManager::getInstance ().setKeyFocusWidget (mTextEdit); + } + else + eventDone(this); } void TextInputDialog::onTextAccepted(MyGUI::Edit* _sender) { - eventDone(this); + if (mTextEdit->getCaption() == "") + { + mWindowManager.messageBox ("#{sNotifyMessage37}", std::vector()); + MyGUI::InputManager::getInstance ().setKeyFocusWidget (mTextEdit); + } + else + eventDone(this); } diff --git a/apps/openmw/mwrender/characterpreview.cpp b/apps/openmw/mwrender/characterpreview.cpp index 01c5d594a7..c8852bff52 100644 --- a/apps/openmw/mwrender/characterpreview.cpp +++ b/apps/openmw/mwrender/characterpreview.cpp @@ -72,6 +72,8 @@ namespace MWRender CharacterPreview::~CharacterPreview () { Ogre::TextureManager::getSingleton().remove(mName); + mSceneMgr->destroyCamera (mName); + delete mAnimation; } From ab698bb401ad668f9c6713471a49ee45d73d571c Mon Sep 17 00:00:00 2001 From: scrawl Date: Tue, 18 Sep 2012 20:53:32 +0200 Subject: [PATCH 70/84] date time label --- apps/openmw/mwbase/world.hpp | 5 ++ apps/openmw/mwgui/waitdialog.cpp | 101 ++++++++++++++++++++++++++ apps/openmw/mwgui/waitdialog.hpp | 16 ++++ apps/openmw/mwgui/widgets.cpp | 10 ++- apps/openmw/mwworld/worldimp.cpp | 20 +++++ apps/openmw/mwworld/worldimp.hpp | 5 ++ files/mygui/openmw_wait_dialog.layout | 11 +-- 7 files changed, 159 insertions(+), 9 deletions(-) diff --git a/apps/openmw/mwbase/world.hpp b/apps/openmw/mwbase/world.hpp index b841e5427a..05b31b3df9 100644 --- a/apps/openmw/mwbase/world.hpp +++ b/apps/openmw/mwbase/world.hpp @@ -160,6 +160,9 @@ namespace MWBase virtual void setDay (int day) = 0; ///< Set in-game time day. + virtual int getDay() = 0; + virtual int getMonth() = 0; + virtual MWWorld::TimeStamp getTimeStamp() const = 0; ///< Return current in-game time stamp. @@ -281,6 +284,8 @@ namespace MWBase virtual void renderPlayer() = 0; virtual void setupExternalRendering (MWRender::ExternalRendering& rendering) = 0; + + virtual bool canRest() = 0; }; } diff --git a/apps/openmw/mwgui/waitdialog.cpp b/apps/openmw/mwgui/waitdialog.cpp index 5b491a4f26..622191566e 100644 --- a/apps/openmw/mwgui/waitdialog.cpp +++ b/apps/openmw/mwgui/waitdialog.cpp @@ -1,12 +1,113 @@ #include "waitdialog.hpp" +#include + +#include + +#include "../mwbase/windowmanager.hpp" +#include "../mwbase/world.hpp" +#include "../mwbase/environment.hpp" + +#include "../mwworld/timestamp.hpp" + +#include "widgets.hpp" + + namespace MWGui { WaitDialog::WaitDialog(MWBase::WindowManager &parWindowManager) : WindowBase("openmw_wait_dialog.layout", parWindowManager) { + getWidget(mDateTimeText, "DateTimeText"); + getWidget(mRestText, "RestText"); + getWidget(mHourText, "HourText"); + getWidget(mHourSlider, "HourSlider"); + getWidget(mUntilHealedButton, "UntilHealedButton"); + getWidget(mWaitButton, "WaitButton"); + getWidget(mCancelButton, "CancelButton"); + + mCancelButton->eventMouseButtonClick += MyGUI::newDelegate(this, &WaitDialog::onCancelButtonClicked); + mUntilHealedButton->eventMouseButtonClick += MyGUI::newDelegate(this, &WaitDialog::onUntilHealedButtonClicked); + mWaitButton->eventMouseButtonClick += MyGUI::newDelegate(this, &WaitDialog::onWaitButtonClicked); + + mHourSlider->eventScrollChangePosition += MyGUI::newDelegate(this, &WaitDialog::onHourSliderChangedPosition); + } + + void WaitDialog::open() + { + setCanRest(MWBase::Environment::get().getWorld ()->canRest ()); + + onHourSliderChangedPosition(mHourSlider, 0); + mHourSlider->setScrollPosition (0); + + // http://www.uesp.net/wiki/Lore:Calendar + std::string month; + int m = MWBase::Environment::get().getWorld ()->getMonth (); + if (m == 0) + month = "#{sMonthMorningstar}"; + else if (m == 1) + month = "#{sMonthSunsdawn}"; + else if (m == 2) + month = "#{sMonthFirstseed}"; + else if (m == 3) + month = "#{sMonthRainshand}"; + else if (m == 4) + month = "#{sMonthSecondseed}"; + else if (m == 5) + month = "#{sMonthMidyear}"; + else if (m == 6) + month = "#{sMonthSunsheight}"; + else if (m == 7) + month = "#{sMonthLastseed}"; + else if (m == 8) + month = "#{sMonthHeartfire}"; + else if (m == 9) + month = "#{sMonthFrostfall}"; + else if (m == 10) + month = "#{sMonthSunsdusk}"; + else if (m == 11) + month = "#{sMonthEveningstar}"; + + int hour = MWBase::Environment::get().getWorld ()->getTimeStamp ().getHour (); + bool pm = hour >= 12; + if (hour >= 13) hour -= 12; + + std::string dateTimeText = + boost::lexical_cast(MWBase::Environment::get().getWorld ()->getDay ()+1) + " " + + month + " (#{sDay} " + boost::lexical_cast(MWBase::Environment::get().getWorld ()->getTimeStamp ().getDay ()+1) + + ") " + boost::lexical_cast(hour) + " " + (pm ? "#{sSaveMenuHelp05}" : "#{sSaveMenuHelp04}"); + + mDateTimeText->setCaptionWithReplacing (dateTimeText); + center(); } + void WaitDialog::onUntilHealedButtonClicked(MyGUI::Widget* sender) + { + + } + + void WaitDialog::onWaitButtonClicked(MyGUI::Widget* sender) + { + //MWBase::Environment::get().getWorld ()->getFader ()->fadeOut(1); + } + + void WaitDialog::onCancelButtonClicked(MyGUI::Widget* sender) + { + mWindowManager.removeGuiMode (GM_Rest); + } + + void WaitDialog::onHourSliderChangedPosition(MyGUI::ScrollBar* sender, size_t position) + { + mHourText->setCaptionWithReplacing (boost::lexical_cast(position+1) + " #{sRestMenu2}"); + } + + void WaitDialog::setCanRest (bool canRest) + { + mUntilHealedButton->setVisible(canRest); + mWaitButton->setCaptionWithReplacing (canRest ? "#{sRest}" : "#{sWait}"); + mRestText->setCaptionWithReplacing (canRest ? "#{sRestMenu3}" : "#{sRestIllegal}"); + } + } diff --git a/apps/openmw/mwgui/waitdialog.hpp b/apps/openmw/mwgui/waitdialog.hpp index 3c68c1249b..040779819c 100644 --- a/apps/openmw/mwgui/waitdialog.hpp +++ b/apps/openmw/mwgui/waitdialog.hpp @@ -11,7 +11,23 @@ namespace MWGui public: WaitDialog(MWBase::WindowManager& parWindowManager); + virtual void open(); + protected: + MyGUI::TextBox* mDateTimeText; + MyGUI::TextBox* mRestText; + MyGUI::TextBox* mHourText; + MyGUI::ScrollBar* mHourSlider; + MyGUI::Button* mUntilHealedButton; + MyGUI::Button* mWaitButton; + MyGUI::Button* mCancelButton; + + void onUntilHealedButtonClicked(MyGUI::Widget* sender); + void onWaitButtonClicked(MyGUI::Widget* sender); + void onCancelButtonClicked(MyGUI::Widget* sender); + void onHourSliderChangedPosition(MyGUI::ScrollBar* sender, size_t position); + + void setCanRest(bool canRest); }; } diff --git a/apps/openmw/mwgui/widgets.cpp b/apps/openmw/mwgui/widgets.cpp index e8cee21412..4f7ecb7757 100644 --- a/apps/openmw/mwgui/widgets.cpp +++ b/apps/openmw/mwgui/widgets.cpp @@ -998,7 +998,10 @@ MyGUI::IntSize HBox::getRequestedSize () { MyGUI::IntSize requested = getChildAt(i)->getSize (); size.height = std::max(size.height, requested.height); - size.width = size.width + requested.width; + + if (getChildAt(i)->getUserString("HStretch") != "true") + size.width = size.width + requested.width; + if (i != getChildCount()-1) size.width += mSpacing; } @@ -1108,7 +1111,10 @@ MyGUI::IntSize VBox::getRequestedSize () { MyGUI::IntSize requested = getChildAt(i)->getSize (); size.width = std::max(size.width, requested.width); - size.height = size.height + requested.height; + + if (getChildAt(i)->getUserString("VStretch") != "true") + size.height = size.height + requested.height; + if (i != getChildCount()-1) size.height += mSpacing; } diff --git a/apps/openmw/mwworld/worldimp.cpp b/apps/openmw/mwworld/worldimp.cpp index 8316116186..af0a536556 100644 --- a/apps/openmw/mwworld/worldimp.cpp +++ b/apps/openmw/mwworld/worldimp.cpp @@ -450,6 +450,16 @@ namespace MWWorld mRendering->skySetDate (mGlobalVariables->getInt ("day"), month); } + int World::getDay() + { + return mGlobalVariables->getInt("day"); + } + + int World::getMonth() + { + return mGlobalVariables->getInt("month"); + } + TimeStamp World::getTimeStamp() const { return TimeStamp (mGlobalVariables->getFloat ("gamehour"), @@ -1241,4 +1251,14 @@ namespace MWWorld { mRendering->setupExternalRendering (rendering); } + + bool World::canRest () + { + Ptr::CellStore *currentCell = mWorldScene->getCurrentCell(); + assert (currentCell); + if (currentCell->cell->data.flags & ESM::Cell::NoSleep) + return false; + else + return true; + } } diff --git a/apps/openmw/mwworld/worldimp.hpp b/apps/openmw/mwworld/worldimp.hpp index d48a0ec814..e918a85e01 100644 --- a/apps/openmw/mwworld/worldimp.hpp +++ b/apps/openmw/mwworld/worldimp.hpp @@ -179,6 +179,9 @@ namespace MWWorld virtual void setDay (int day); ///< Set in-game time day. + virtual int getDay(); + virtual int getMonth(); + virtual TimeStamp getTimeStamp() const; ///< Return current in-game time stamp. @@ -312,6 +315,8 @@ namespace MWWorld virtual void renderPlayer(); virtual void setupExternalRendering (MWRender::ExternalRendering& rendering); + + virtual bool canRest(); }; } diff --git a/files/mygui/openmw_wait_dialog.layout b/files/mygui/openmw_wait_dialog.layout index 527d5158da..66e0ec22f0 100644 --- a/files/mygui/openmw_wait_dialog.layout +++ b/files/mygui/openmw_wait_dialog.layout @@ -6,22 +6,19 @@ - + - - + - - + - - + From 4829f47a4f86234658cc1a11406b761636d34151 Mon Sep 17 00:00:00 2001 From: scrawl Date: Tue, 18 Sep 2012 21:04:43 +0200 Subject: [PATCH 71/84] rewrote the fader to use Rectangle2d instead of overlay, in order to not cover the UI --- libs/openengine/ogre/fader.cpp | 61 +++++++++++++------------- libs/openengine/ogre/fader.hpp | 72 +++++++++++++++---------------- libs/openengine/ogre/renderer.cpp | 2 +- 3 files changed, 66 insertions(+), 69 deletions(-) diff --git a/libs/openengine/ogre/fader.cpp b/libs/openengine/ogre/fader.cpp index 41b7773ea3..498b659eec 100644 --- a/libs/openengine/ogre/fader.cpp +++ b/libs/openengine/ogre/fader.cpp @@ -1,52 +1,49 @@ #include "fader.hpp" -#include -#include -#include #include #include #include #include +#include +#include -#define FADE_OVERLAY_NAME "FadeInOutOverlay" -#define FADE_OVERLAY_PANEL_NAME "FadeInOutOverlayPanel" -#define FADE_MATERIAL_NAME "FadeInOutMaterial" using namespace Ogre; using namespace OEngine::Render; -Fader::Fader() : - mMode(FadingMode_In), - mRemainingTime(0.f), - mTargetTime(0.f), - mTargetAlpha(0.f), - mCurrentAlpha(0.f), - mStartAlpha(0.f) +Fader::Fader(Ogre::SceneManager* sceneMgr) + : mSceneMgr(sceneMgr) + , mMode(FadingMode_In) + , mRemainingTime(0.f) + , mTargetTime(0.f) + , mTargetAlpha(0.f) + , mCurrentAlpha(0.f) + , mStartAlpha(0.f) { - // Create the fading material - MaterialPtr material = MaterialManager::getSingleton().create( FADE_MATERIAL_NAME, ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME ); + MaterialPtr material = MaterialManager::getSingleton().create("FadeInOutMaterial", ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME ); Pass* pass = material->getTechnique(0)->getPass(0); pass->setSceneBlending(SBT_TRANSPARENT_ALPHA); mFadeTextureUnit = pass->createTextureUnitState(); mFadeTextureUnit->setColourOperationEx(LBX_SOURCE1, LBS_MANUAL, LBS_CURRENT, ColourValue(0.f, 0.f, 0.f)); // always black colour - // Create the overlay - OverlayManager& ovm = OverlayManager::getSingleton(); + mRectangle = new Ogre::Rectangle2D(true); + mRectangle->setCorners(-1.0, 1.0, 1.0, -1.0); + mRectangle->setMaterial("FadeInOutMaterial"); + mRectangle->setRenderQueueGroup(Ogre::RENDER_QUEUE_OVERLAY-1); + // Use infinite AAB to always stay visible + Ogre::AxisAlignedBox aabInf; + aabInf.setInfinite(); + mRectangle->setBoundingBox(aabInf); + // Attach background to the scene + Ogre::SceneNode* node = mSceneMgr->getRootSceneNode()->createChildSceneNode(); + node->attachObject(mRectangle); + mRectangle->setVisible(false); +} - mOverlay = ovm.create( FADE_OVERLAY_NAME ); - - OverlayContainer* overlay_panel; - overlay_panel = (OverlayContainer*)ovm.createOverlayElement("Panel", FADE_OVERLAY_PANEL_NAME); - - // position it over the whole screen - overlay_panel->_setPosition(0, 0); - overlay_panel->_setDimensions(1, 1); - - overlay_panel->setMaterialName( FADE_MATERIAL_NAME ); - overlay_panel->show(); - mOverlay->add2D(overlay_panel); - mOverlay->hide(); +Fader::~Fader() +{ + delete mRectangle; } void Fader::update(float dt) @@ -69,12 +66,12 @@ void Fader::update(float dt) mRemainingTime -= dt; } - if (mCurrentAlpha == 0.f) mOverlay->hide(); + if (mCurrentAlpha == 0.f) mRectangle->setVisible(false); } void Fader::applyAlpha() { - mOverlay->show(); + mRectangle->setVisible(true); mFadeTextureUnit->setAlphaOperation(LBX_SOURCE1, LBS_MANUAL, LBS_CURRENT, mCurrentAlpha); } diff --git a/libs/openengine/ogre/fader.hpp b/libs/openengine/ogre/fader.hpp index efb12a5d2d..bddf5dc919 100644 --- a/libs/openengine/ogre/fader.hpp +++ b/libs/openengine/ogre/fader.hpp @@ -4,52 +4,52 @@ /* A class that handles fading in the screen from black or fading it out to black. - To achieve this, it uses a full-screen Ogre::Overlay - - inspired by http://www.ogre3d.org/tikiwiki/FadeEffectOverlay (heavily adjusted) + To achieve this, it uses a full-screen Rectangle2d */ namespace Ogre { class TextureUnitState; - class Overlay; + class Rectangle2D; + class SceneManager; } namespace OEngine { namespace Render { - class Fader - { - public: - Fader(); - - void update(float dt); - - void fadeIn(const float time); - void fadeOut(const float time); - void fadeTo(const int percent, const float time); - - private: - enum FadingMode + class Fader { - FadingMode_In, - FadingMode_Out + public: + Fader(Ogre::SceneManager* sceneMgr); + ~Fader(); + + void update(float dt); + + void fadeIn(const float time); + void fadeOut(const float time); + void fadeTo(const int percent, const float time); + + private: + enum FadingMode + { + FadingMode_In, + FadingMode_Out + }; + + void applyAlpha(); + + Ogre::TextureUnitState* mFadeTextureUnit; + Ogre::Rectangle2D* mRectangle; + + FadingMode mMode; + + float mRemainingTime; + float mTargetTime; + float mTargetAlpha; + float mCurrentAlpha; + float mStartAlpha; + + Ogre::SceneManager* mSceneMgr; }; - - void applyAlpha(); - - Ogre::TextureUnitState* mFadeTextureUnit; - Ogre::Overlay* mOverlay; - - FadingMode mMode; - - float mRemainingTime; - float mTargetTime; - float mTargetAlpha; - float mCurrentAlpha; - float mStartAlpha; - - protected: - }; -}} + }} #endif diff --git a/libs/openengine/ogre/renderer.cpp b/libs/openengine/ogre/renderer.cpp index 65911df342..ec68c37ab8 100644 --- a/libs/openengine/ogre/renderer.cpp +++ b/libs/openengine/ogre/renderer.cpp @@ -243,7 +243,7 @@ void OgreRenderer::createScene(const std::string& camName, float fov, float near // Alter the camera aspect ratio to match the viewport mCamera->setAspectRatio(Real(mView->getActualWidth()) / Real(mView->getActualHeight())); - mFader = new Fader(); + mFader = new Fader(mScene); } void OgreRenderer::adjustViewport() From bf5e30b24fc22c3d68126ae6f159a40787633240 Mon Sep 17 00:00:00 2001 From: scrawl Date: Wed, 19 Sep 2012 02:53:06 +0200 Subject: [PATCH 72/84] everything done except health/mana restore --- apps/openmw/mwbase/world.hpp | 7 +- apps/openmw/mwgui/levelupdialog.cpp | 2 +- apps/openmw/mwgui/mode.hpp | 1 + apps/openmw/mwgui/race.cpp | 2 +- apps/openmw/mwgui/waitdialog.cpp | 112 +++++++++++++++++- apps/openmw/mwgui/waitdialog.hpp | 29 +++++ apps/openmw/mwgui/widgets.cpp | 1 - apps/openmw/mwgui/windowmanagerimp.cpp | 10 +- apps/openmw/mwscript/guiextensions.cpp | 2 +- apps/openmw/mwworld/worldimp.cpp | 24 +++- apps/openmw/mwworld/worldimp.hpp | 7 +- files/mygui/CMakeLists.txt | 1 + files/mygui/openmw_alchemy_window.layout | 5 +- files/mygui/openmw_chargen_birth.layout | 4 +- files/mygui/openmw_chargen_class.layout | 4 +- .../mygui/openmw_chargen_create_class.layout | 4 +- ...penmw_chargen_generate_class_result.layout | 4 +- files/mygui/openmw_chargen_race.layout | 5 +- files/mygui/openmw_chargen_review.layout | 4 +- files/mygui/openmw_confirmation_dialog.layout | 4 +- files/mygui/openmw_container_window.layout | 4 +- files/mygui/openmw_count_window.layout | 4 +- files/mygui/openmw_trade_window.layout | 4 +- .../openmw_wait_dialog_progressbar.layout | 13 ++ libs/openengine/ogre/fader.cpp | 1 + 25 files changed, 228 insertions(+), 30 deletions(-) create mode 100644 files/mygui/openmw_wait_dialog_progressbar.layout diff --git a/apps/openmw/mwbase/world.hpp b/apps/openmw/mwbase/world.hpp index 05b31b3df9..521bbb988e 100644 --- a/apps/openmw/mwbase/world.hpp +++ b/apps/openmw/mwbase/world.hpp @@ -285,7 +285,12 @@ namespace MWBase virtual void setupExternalRendering (MWRender::ExternalRendering& rendering) = 0; - virtual bool canRest() = 0; + virtual int canRest() = 0; + ///< check if the player is allowed to rest \n + /// 0 - yes \n + /// 1 - only waiting \n + /// 2 - player is underwater \n + /// 3 - enemies are nearby (not implemented) }; } diff --git a/apps/openmw/mwgui/levelupdialog.cpp b/apps/openmw/mwgui/levelupdialog.cpp index 3616283d97..980a9e13ba 100644 --- a/apps/openmw/mwgui/levelupdialog.cpp +++ b/apps/openmw/mwgui/levelupdialog.cpp @@ -173,7 +173,7 @@ namespace MWGui creatureStats.setLevel (creatureStats.getLevel()+1); pcStats.levelUp (); - mWindowManager.removeGuiMode (GM_Rest); + mWindowManager.removeGuiMode (GM_Levelup); } } diff --git a/apps/openmw/mwgui/mode.hpp b/apps/openmw/mwgui/mode.hpp index eb2c52b26f..64aa1dc216 100644 --- a/apps/openmw/mwgui/mode.hpp +++ b/apps/openmw/mwgui/mode.hpp @@ -20,6 +20,7 @@ namespace MWGui GM_Dialogue, // NPC interaction GM_Barter, GM_Rest, + GM_RestBed, GM_SpellBuying, GM_Levelup, diff --git a/apps/openmw/mwgui/race.cpp b/apps/openmw/mwgui/race.cpp index 3fe70d959b..5cb73e682f 100644 --- a/apps/openmw/mwgui/race.cpp +++ b/apps/openmw/mwgui/race.cpp @@ -40,7 +40,7 @@ RaceDialog::RaceDialog(MWBase::WindowManager& parWindowManager) getWidget(mHeadRotate, "HeadRotate"); mHeadRotate->setScrollRange(50); - mHeadRotate->setScrollPosition(20); + mHeadRotate->setScrollPosition(25); mHeadRotate->setScrollViewPage(10); mHeadRotate->eventScrollChangePosition += MyGUI::newDelegate(this, &RaceDialog::onHeadRotate); diff --git a/apps/openmw/mwgui/waitdialog.cpp b/apps/openmw/mwgui/waitdialog.cpp index 622191566e..cc9019f2be 100644 --- a/apps/openmw/mwgui/waitdialog.cpp +++ b/apps/openmw/mwgui/waitdialog.cpp @@ -9,6 +9,11 @@ #include "../mwbase/environment.hpp" #include "../mwworld/timestamp.hpp" +#include "../mwworld/player.hpp" +#include "../mwworld/ptr.hpp" +#include "../mwworld/class.hpp" + +#include "../mwmechanics/npcstats.hpp" #include "widgets.hpp" @@ -16,8 +21,34 @@ namespace MWGui { + WaitDialogProgressBar::WaitDialogProgressBar(MWBase::WindowManager &parWindowManager) + : WindowBase("openmw_wait_dialog_progressbar.layout", parWindowManager) + { + getWidget(mProgressBar, "ProgressBar"); + getWidget(mProgressText, "ProgressText"); + } + + void WaitDialogProgressBar::open() + { + center(); + } + + void WaitDialogProgressBar::setProgress (int cur, int total) + { + mProgressBar->setProgressRange (total); + mProgressBar->setProgressPosition (cur); + mProgressText->setCaption(boost::lexical_cast(cur) + "/" + boost::lexical_cast(total)); + } + + // --------------------------------------------------------------------------------------------------------- + WaitDialog::WaitDialog(MWBase::WindowManager &parWindowManager) : WindowBase("openmw_wait_dialog.layout", parWindowManager) + , mProgressBar(parWindowManager) + , mWaiting(false) + , mSleeping(false) + , mHours(1) + , mRemainingTime(0.05) { getWidget(mDateTimeText, "DateTimeText"); getWidget(mRestText, "RestText"); @@ -32,11 +63,27 @@ namespace MWGui mWaitButton->eventMouseButtonClick += MyGUI::newDelegate(this, &WaitDialog::onWaitButtonClicked); mHourSlider->eventScrollChangePosition += MyGUI::newDelegate(this, &WaitDialog::onHourSliderChangedPosition); + + mProgressBar.setVisible (false); } void WaitDialog::open() { - setCanRest(MWBase::Environment::get().getWorld ()->canRest ()); + if (!MWBase::Environment::get().getWindowManager ()->getRestEnabled ()) + { + mWindowManager.popGuiMode (); + } + + int canRest = MWBase::Environment::get().getWorld ()->canRest (); + + if (canRest == 2) + { + // resting underwater or mid-air not allowed + mWindowManager.messageBox ("#{sNotifyMessage1}", std::vector()); + mWindowManager.popGuiMode (); + } + + setCanRest(canRest == 0); onHourSliderChangedPosition(mHourSlider, 0); mHourSlider->setScrollPosition (0); @@ -79,28 +126,38 @@ namespace MWGui + ") " + boost::lexical_cast(hour) + " " + (pm ? "#{sSaveMenuHelp05}" : "#{sSaveMenuHelp04}"); mDateTimeText->setCaptionWithReplacing (dateTimeText); - - center(); } void WaitDialog::onUntilHealedButtonClicked(MyGUI::Widget* sender) { - + startWaiting(); } void WaitDialog::onWaitButtonClicked(MyGUI::Widget* sender) { - //MWBase::Environment::get().getWorld ()->getFader ()->fadeOut(1); + startWaiting(); + } + + void WaitDialog::startWaiting () + { + MWBase::Environment::get().getWorld ()->getFader ()->fadeOut(0.2); + setVisible(false); + mProgressBar.setVisible (true); + mWaiting = true; + mCurHour = 0; + mRemainingTime = 0.05; + mProgressBar.setProgress (0, mHours); } void WaitDialog::onCancelButtonClicked(MyGUI::Widget* sender) { - mWindowManager.removeGuiMode (GM_Rest); + mWindowManager.popGuiMode (); } void WaitDialog::onHourSliderChangedPosition(MyGUI::ScrollBar* sender, size_t position) { mHourText->setCaptionWithReplacing (boost::lexical_cast(position+1) + " #{sRestMenu2}"); + mHours = position+1; } void WaitDialog::setCanRest (bool canRest) @@ -108,6 +165,49 @@ namespace MWGui mUntilHealedButton->setVisible(canRest); mWaitButton->setCaptionWithReplacing (canRest ? "#{sRest}" : "#{sWait}"); mRestText->setCaptionWithReplacing (canRest ? "#{sRestMenu3}" : "#{sRestIllegal}"); + + mSleeping = canRest; + + dynamic_cast(mMainWidget)->notifyChildrenSizeChanged(); + center(); + } + + void WaitDialog::onFrame(float dt) + { + if (!mWaiting) + return; + + mRemainingTime -= dt; + + if (mRemainingTime < 0) + { + mRemainingTime = 0.05; + ++mCurHour; + mProgressBar.setProgress (mCurHour, mHours); + + if (mCurHour <= mHours) + MWBase::Environment::get().getWorld ()->advanceTime (1); + } + + if (mCurHour > mHours) + stopWaiting(); + } + + void WaitDialog::stopWaiting () + { + MWBase::Environment::get().getWorld ()->getFader ()->fadeIn(0.2); + mProgressBar.setVisible (false); + mWindowManager.popGuiMode (); + mWaiting = false; + + MWWorld::Ptr player = MWBase::Environment::get().getWorld()->getPlayer().getPlayer(); + MWMechanics::NpcStats pcstats = MWWorld::Class::get(player).getNpcStats(player); + + // trigger levelup if possible + if (mSleeping && pcstats.getLevelProgress () >= 10) + { + mWindowManager.pushGuiMode (GM_Levelup); + } } } diff --git a/apps/openmw/mwgui/waitdialog.hpp b/apps/openmw/mwgui/waitdialog.hpp index 040779819c..1d079a8aa4 100644 --- a/apps/openmw/mwgui/waitdialog.hpp +++ b/apps/openmw/mwgui/waitdialog.hpp @@ -6,6 +6,20 @@ namespace MWGui { + class WaitDialogProgressBar : public WindowBase + { + public: + WaitDialogProgressBar(MWBase::WindowManager& parWindowManager); + + virtual void open(); + + void setProgress(int cur, int total); + + protected: + MyGUI::ProgressBar* mProgressBar; + MyGUI::TextBox* mProgressText; + }; + class WaitDialog : public WindowBase { public: @@ -13,6 +27,10 @@ namespace MWGui virtual void open(); + void onFrame(float dt); + + void bedActivated() { setCanRest(true); } + protected: MyGUI::TextBox* mDateTimeText; MyGUI::TextBox* mRestText; @@ -22,12 +40,23 @@ namespace MWGui MyGUI::Button* mWaitButton; MyGUI::Button* mCancelButton; + bool mWaiting; + bool mSleeping; + int mCurHour; + int mHours; + float mRemainingTime; + + WaitDialogProgressBar mProgressBar; + void onUntilHealedButtonClicked(MyGUI::Widget* sender); void onWaitButtonClicked(MyGUI::Widget* sender); void onCancelButtonClicked(MyGUI::Widget* sender); void onHourSliderChangedPosition(MyGUI::ScrollBar* sender, size_t position); void setCanRest(bool canRest); + + void startWaiting(); + void stopWaiting(); }; } diff --git a/apps/openmw/mwgui/widgets.cpp b/apps/openmw/mwgui/widgets.cpp index 4f7ecb7757..3138205340 100644 --- a/apps/openmw/mwgui/widgets.cpp +++ b/apps/openmw/mwgui/widgets.cpp @@ -795,7 +795,6 @@ void MWDynamicStat::initialiseOverride() // --------------------------------------------------------------------------------------------------------------------- - void AutoSizedWidget::notifySizeChange (MyGUI::Widget* w) { if (w->getParent () != 0) diff --git a/apps/openmw/mwgui/windowmanagerimp.cpp b/apps/openmw/mwgui/windowmanagerimp.cpp index 5efd2b47a8..5de35367a6 100644 --- a/apps/openmw/mwgui/windowmanagerimp.cpp +++ b/apps/openmw/mwgui/windowmanagerimp.cpp @@ -310,9 +310,15 @@ void WindowManager::updateVisible() mAlchemyWindow->setVisible(true); break; case GM_Rest: - //mLevelupDialog->setVisible(true); mWaitDialog->setVisible(true); break; + case GM_RestBed: + mWaitDialog->setVisible(true); + mWaitDialog->bedActivated(); + break; + case GM_Levelup: + mLevelupDialog->setVisible(true); + break; case GM_Name: case GM_Race: case GM_Class: @@ -547,6 +553,8 @@ void WindowManager::onFrame (float frameDuration) mStatsWindow->onFrame(); + mWaitDialog->onFrame(frameDuration); + mHud->onFrame(frameDuration); mDialogueWindow->checkReferenceAvailable(); diff --git a/apps/openmw/mwscript/guiextensions.cpp b/apps/openmw/mwscript/guiextensions.cpp index 7f3b9777b0..6e5540fa8f 100644 --- a/apps/openmw/mwscript/guiextensions.cpp +++ b/apps/openmw/mwscript/guiextensions.cpp @@ -160,7 +160,7 @@ opcodeEnableStatsReviewMenu); new OpEnableRest ()); interpreter.installSegment5 (opcodeShowRestMenu, - new OpShowDialogue (MWGui::GM_Rest)); + new OpShowDialogue (MWGui::GM_RestBed)); interpreter.installSegment5 (opcodeGetButtonPressed, new OpGetButtonPressed); diff --git a/apps/openmw/mwworld/worldimp.cpp b/apps/openmw/mwworld/worldimp.cpp index af0a536556..dae95255e9 100644 --- a/apps/openmw/mwworld/worldimp.cpp +++ b/apps/openmw/mwworld/worldimp.cpp @@ -1252,13 +1252,27 @@ namespace MWWorld mRendering->setupExternalRendering (rendering); } - bool World::canRest () + int World::canRest () { Ptr::CellStore *currentCell = mWorldScene->getCurrentCell(); - assert (currentCell); + + Ogre::Vector3 playerPos; + float* pos = mPlayer->getPlayer ().getRefData ().getPosition ().pos; + playerPos.x = pos[0]; + playerPos.y = pos[1]; + playerPos.z = pos[2]; + + std::pair hit = + mPhysics->castRay(playerPos, Ogre::Vector3(0,0,-1), 50); + bool isOnGround = (hit.first ? (hit.second.distance (playerPos) < 25) : false); + + if (!isOnGround || isUnderwater (*currentCell->cell, playerPos)) + return 2; + if (currentCell->cell->data.flags & ESM::Cell::NoSleep) - return false; - else - return true; + return 1; + + return 0; + } } diff --git a/apps/openmw/mwworld/worldimp.hpp b/apps/openmw/mwworld/worldimp.hpp index e918a85e01..90cd2151b6 100644 --- a/apps/openmw/mwworld/worldimp.hpp +++ b/apps/openmw/mwworld/worldimp.hpp @@ -316,7 +316,12 @@ namespace MWWorld virtual void setupExternalRendering (MWRender::ExternalRendering& rendering); - virtual bool canRest(); + virtual int canRest(); + ///< check if the player is allowed to rest \n + /// 0 - yes \n + /// 1 - only waiting \n + /// 2 - player is underwater \n + /// 3 - enemies are nearby (not implemented) }; } diff --git a/files/mygui/CMakeLists.txt b/files/mygui/CMakeLists.txt index 44235fa0e9..ae8d3afbed 100644 --- a/files/mygui/CMakeLists.txt +++ b/files/mygui/CMakeLists.txt @@ -74,6 +74,7 @@ set(MYGUI_FILES openmw_loading_screen.layout openmw_levelup_dialog.layout openmw_wait_dialog.layout + openmw_wait_dialog_progressbar.layout smallbars.png VeraMono.ttf markers.png diff --git a/files/mygui/openmw_alchemy_window.layout b/files/mygui/openmw_alchemy_window.layout index 458d24b2c6..8471f69df0 100644 --- a/files/mygui/openmw_alchemy_window.layout +++ b/files/mygui/openmw_alchemy_window.layout @@ -77,8 +77,9 @@ - - + + + diff --git a/files/mygui/openmw_chargen_birth.layout b/files/mygui/openmw_chargen_birth.layout index 5edec72d3c..f4b8c518d4 100644 --- a/files/mygui/openmw_chargen_birth.layout +++ b/files/mygui/openmw_chargen_birth.layout @@ -15,7 +15,9 @@ - + + + diff --git a/files/mygui/openmw_chargen_class.layout b/files/mygui/openmw_chargen_class.layout index baa36b24a7..00e3793bcc 100644 --- a/files/mygui/openmw_chargen_class.layout +++ b/files/mygui/openmw_chargen_class.layout @@ -61,7 +61,9 @@ - + + + diff --git a/files/mygui/openmw_chargen_create_class.layout b/files/mygui/openmw_chargen_create_class.layout index 5e08db6e51..54f73f2211 100644 --- a/files/mygui/openmw_chargen_create_class.layout +++ b/files/mygui/openmw_chargen_create_class.layout @@ -59,7 +59,9 @@ - + + + diff --git a/files/mygui/openmw_chargen_generate_class_result.layout b/files/mygui/openmw_chargen_generate_class_result.layout index 65dbf016c1..aa4a89d28c 100644 --- a/files/mygui/openmw_chargen_generate_class_result.layout +++ b/files/mygui/openmw_chargen_generate_class_result.layout @@ -21,7 +21,9 @@ - + + + diff --git a/files/mygui/openmw_chargen_race.layout b/files/mygui/openmw_chargen_race.layout index b690738992..a9ec9905da 100644 --- a/files/mygui/openmw_chargen_race.layout +++ b/files/mygui/openmw_chargen_race.layout @@ -57,7 +57,10 @@ - + + + + diff --git a/files/mygui/openmw_chargen_review.layout b/files/mygui/openmw_chargen_review.layout index dbe7a4780b..97e32cfe28 100644 --- a/files/mygui/openmw_chargen_review.layout +++ b/files/mygui/openmw_chargen_review.layout @@ -112,7 +112,9 @@ - + + + diff --git a/files/mygui/openmw_confirmation_dialog.layout b/files/mygui/openmw_confirmation_dialog.layout index fe7f7cbf6e..46b477407c 100644 --- a/files/mygui/openmw_confirmation_dialog.layout +++ b/files/mygui/openmw_confirmation_dialog.layout @@ -14,7 +14,9 @@ - + + + diff --git a/files/mygui/openmw_container_window.layout b/files/mygui/openmw_container_window.layout index 896566fdd0..94e9458a5b 100644 --- a/files/mygui/openmw_container_window.layout +++ b/files/mygui/openmw_container_window.layout @@ -12,7 +12,9 @@ - + + + diff --git a/files/mygui/openmw_count_window.layout b/files/mygui/openmw_count_window.layout index a021d7df9a..5812ec7fd9 100644 --- a/files/mygui/openmw_count_window.layout +++ b/files/mygui/openmw_count_window.layout @@ -22,7 +22,9 @@ - + + + diff --git a/files/mygui/openmw_trade_window.layout b/files/mygui/openmw_trade_window.layout index 7de6c85e60..d38377f987 100644 --- a/files/mygui/openmw_trade_window.layout +++ b/files/mygui/openmw_trade_window.layout @@ -56,7 +56,9 @@ - + + + diff --git a/files/mygui/openmw_wait_dialog_progressbar.layout b/files/mygui/openmw_wait_dialog_progressbar.layout new file mode 100644 index 0000000000..93793fd8e0 --- /dev/null +++ b/files/mygui/openmw_wait_dialog_progressbar.layout @@ -0,0 +1,13 @@ + + + + + + + + + + + + + diff --git a/libs/openengine/ogre/fader.cpp b/libs/openengine/ogre/fader.cpp index 498b659eec..ba532b5273 100644 --- a/libs/openengine/ogre/fader.cpp +++ b/libs/openengine/ogre/fader.cpp @@ -39,6 +39,7 @@ Fader::Fader(Ogre::SceneManager* sceneMgr) Ogre::SceneNode* node = mSceneMgr->getRootSceneNode()->createChildSceneNode(); node->attachObject(mRectangle); mRectangle->setVisible(false); + mRectangle->setVisibilityFlags (0x01); } Fader::~Fader() From be44810623c8c970defb65bebe6c8c292cf0b79e Mon Sep 17 00:00:00 2001 From: scrawl Date: Wed, 19 Sep 2012 03:11:23 +0200 Subject: [PATCH 73/84] implemented GetPCSleep --- apps/openmw/mwbase/windowmanager.hpp | 2 ++ apps/openmw/mwgui/waitdialog.hpp | 2 ++ apps/openmw/mwgui/windowmanagerimp.cpp | 5 +++++ apps/openmw/mwgui/windowmanagerimp.hpp | 2 ++ apps/openmw/mwscript/docs/vmformat.txt | 3 ++- apps/openmw/mwscript/miscextensions.cpp | 14 ++++++++++++++ 6 files changed, 27 insertions(+), 1 deletion(-) diff --git a/apps/openmw/mwbase/windowmanager.hpp b/apps/openmw/mwbase/windowmanager.hpp index 0fd78225ab..49f1f95b0e 100644 --- a/apps/openmw/mwbase/windowmanager.hpp +++ b/apps/openmw/mwbase/windowmanager.hpp @@ -222,6 +222,8 @@ namespace MWBase virtual void enableRest() = 0; virtual bool getRestEnabled() = 0; + + virtual bool getPlayerSleeping() = 0; }; } diff --git a/apps/openmw/mwgui/waitdialog.hpp b/apps/openmw/mwgui/waitdialog.hpp index 1d079a8aa4..4a401c0c6d 100644 --- a/apps/openmw/mwgui/waitdialog.hpp +++ b/apps/openmw/mwgui/waitdialog.hpp @@ -31,6 +31,8 @@ namespace MWGui void bedActivated() { setCanRest(true); } + bool getSleeping() { return mWaiting && mSleeping; } + protected: MyGUI::TextBox* mDateTimeText; MyGUI::TextBox* mRestText; diff --git a/apps/openmw/mwgui/windowmanagerimp.cpp b/apps/openmw/mwgui/windowmanagerimp.cpp index 5de35367a6..9d4aaf7492 100644 --- a/apps/openmw/mwgui/windowmanagerimp.cpp +++ b/apps/openmw/mwgui/windowmanagerimp.cpp @@ -946,3 +946,8 @@ void WindowManager::loadingDone () { mLoadingScreen->loadingDone (); } + +bool WindowManager::getPlayerSleeping () +{ + return mWaitDialog->getSleeping(); +} diff --git a/apps/openmw/mwgui/windowmanagerimp.hpp b/apps/openmw/mwgui/windowmanagerimp.hpp index 15c9c66313..0ed5e1feaa 100644 --- a/apps/openmw/mwgui/windowmanagerimp.hpp +++ b/apps/openmw/mwgui/windowmanagerimp.hpp @@ -204,6 +204,8 @@ namespace MWGui virtual void enableRest() { mRestAllowed = true; } virtual bool getRestEnabled() { return mRestAllowed; } + virtual bool getPlayerSleeping(); + private: OEngine::GUI::MyGUIManager *mGuiManager; HUD *mHud; diff --git a/apps/openmw/mwscript/docs/vmformat.txt b/apps/openmw/mwscript/docs/vmformat.txt index d58045a0ab..a9f2cd1435 100644 --- a/apps/openmw/mwscript/docs/vmformat.txt +++ b/apps/openmw/mwscript/docs/vmformat.txt @@ -202,5 +202,6 @@ op 0x200019b: PlaceItem op 0x200019c: PlaceAtPc op 0x200019d: PlaceAtMe op 0x200019e: PlaceAtMe Explicit -opcodes 0x200019f-0x3ffffff unused +op 0x200019f: GetPcSleep +opcodes 0x20001a0-0x3ffffff unused diff --git a/apps/openmw/mwscript/miscextensions.cpp b/apps/openmw/mwscript/miscextensions.cpp index 864c1a1eed..a869f882b1 100644 --- a/apps/openmw/mwscript/miscextensions.cpp +++ b/apps/openmw/mwscript/miscextensions.cpp @@ -10,6 +10,7 @@ #include #include "../mwbase/environment.hpp" +#include "../mwbase/windowmanager.hpp" #include "../mwworld/class.hpp" @@ -20,6 +21,16 @@ namespace MWScript { namespace Misc { + class OpGetPcSleep : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + runtime.push (MWBase::Environment::get().getWindowManager ()->getPlayerSleeping()); + } + }; + class OpXBox : public Interpreter::Opcode0 { public: @@ -249,6 +260,7 @@ namespace MWScript const int opcodeTogglePathgrid = 0x2000146; const int opcodeDontSaveObject = 0x2000153; const int opcodeToggleVanityMode = 0x2000174; + const int opcodeGetPcSleep = 0x200019f; void registerExtensions (Compiler::Extensions& extensions) { @@ -273,6 +285,7 @@ namespace MWScript extensions.registerInstruction ("dontsaveobject", "", opcodeDontSaveObject); extensions.registerInstruction ("togglevanitymode", "", opcodeToggleVanityMode); extensions.registerInstruction ("tvm", "", opcodeToggleVanityMode); + extensions.registerFunction ("getpcsleep", 'l', "", opcodeGetPcSleep); } void installOpcodes (Interpreter::Interpreter& interpreter) @@ -293,6 +306,7 @@ namespace MWScript interpreter.installSegment5 (opcodeToggleWater, new OpToggleWater); interpreter.installSegment5 (opcodeDontSaveObject, new OpDontSaveObject); interpreter.installSegment5 (opcodeToggleVanityMode, new OpToggleVanityMode); + interpreter.installSegment5 (opcodeGetPcSleep, new OpGetPcSleep); } } } From 4b5706d65292a627c528cf573a79eee73c4fdc0b Mon Sep 17 00:00:00 2001 From: Nikolay Kasyanov Date: Wed, 19 Sep 2012 11:16:13 +0400 Subject: [PATCH 74/84] Fixed packaging on OS X --- CMakeLists.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index aee073d3ef..614a840c4a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -633,7 +633,7 @@ if (APPLE) include(CPack) endif (APPLE) -if (NOT WIN32 AND NOT DPKG_PROGRAM) +if (NOT WIN32 AND NOT DPKG_PROGRAM AND NOT APPLE) ## Non Debian based Linux building # paths set(BINDIR "${CMAKE_INSTALL_PREFIX}/usr/bin" CACHE PATH "Where to install binaries") @@ -664,4 +664,4 @@ if (NOT WIN32 AND NOT DPKG_PROGRAM) # Install resources INSTALL(DIRECTORY "${OpenMW_BINARY_DIR}/resources" DESTINATION "${DATADIR}" ) INSTALL(FILES "${OpenMW_BINARY_DIR}/launcher.qss" DESTINATION "${DATADIR}/resources" ) -endif(NOT WIN32 AND NOT DPKG_PROGRAM) +endif(NOT WIN32 AND NOT DPKG_PROGRAM AND NOT APPLE) From 32de090079690f683d7c38db50b5f61669d1c98e Mon Sep 17 00:00:00 2001 From: scrawl Date: Wed, 19 Sep 2012 19:34:02 +0200 Subject: [PATCH 75/84] Allow changing OpenGL RTT mode, useful for example if the driver reports incorrect capabilities --- apps/openmw/engine.cpp | 1 + files/settings-default.cfg | 4 ++++ libs/openengine/ogre/renderer.cpp | 4 ++++ libs/openengine/ogre/renderer.hpp | 1 + 4 files changed, 10 insertions(+) diff --git a/apps/openmw/engine.cpp b/apps/openmw/engine.cpp index db6edf397d..d10ae99794 100644 --- a/apps/openmw/engine.cpp +++ b/apps/openmw/engine.cpp @@ -299,6 +299,7 @@ void OMW::Engine::go() mOgre->configure( mCfgMgr.getLogPath().string(), renderSystem, + Settings::Manager::getString("opengl rtt mode", "Video"), false); // This has to be added BEFORE MyGUI is initialized, as it needs diff --git a/files/settings-default.cfg b/files/settings-default.cfg index 8fab98da24..6a77b7fc06 100644 --- a/files/settings-default.cfg +++ b/files/settings-default.cfg @@ -24,6 +24,10 @@ antialiasing = none vsync = false +# opengl render to texture mode, valid options: +# PBuffer, FBO, Copy +opengl rtt mode = FBO + [GUI] # 1 is fully opaque menu transparency = 0.84 diff --git a/libs/openengine/ogre/renderer.cpp b/libs/openengine/ogre/renderer.cpp index 65911df342..5f3435c52a 100644 --- a/libs/openengine/ogre/renderer.cpp +++ b/libs/openengine/ogre/renderer.cpp @@ -145,6 +145,7 @@ float OgreRenderer::getFPS() void OgreRenderer::configure(const std::string &logPath, const std::string& renderSystem, + const std::string& rttMode, bool _logging) { // Set up logging first @@ -198,6 +199,9 @@ void OgreRenderer::configure(const std::string &logPath, if (rs == 0) throw std::runtime_error ("RenderSystem with name " + renderSystem + " not found, make sure the plugins are loaded"); mRoot->setRenderSystem(rs); + + if (rs->getName().find("OpenGL") != std::string::npos) + rs->setConfigOption ("RTT Preferred Mode", rttMode); } void OgreRenderer::createWindow(const std::string &title, const WindowSettings& settings) diff --git a/libs/openengine/ogre/renderer.hpp b/libs/openengine/ogre/renderer.hpp index 95bcac3b87..a8788dfcaf 100644 --- a/libs/openengine/ogre/renderer.hpp +++ b/libs/openengine/ogre/renderer.hpp @@ -132,6 +132,7 @@ namespace OEngine void configure( const std::string &logPath, // Path to directory where to store log files const std::string &renderSystem, + const std::string &rttMode, bool _logging); // Enable or disable logging /// Create a window with the given title From d9f6072f02b279963b6e1929dfe519fb5580f999 Mon Sep 17 00:00:00 2001 From: scrawl Date: Wed, 19 Sep 2012 23:25:07 +0200 Subject: [PATCH 76/84] gamma correct rendering & adjustment setting --- apps/openmw/mwrender/renderingmanager.cpp | 2 ++ files/materials/core.h | 4 ++++ files/materials/objects.shader | 14 +++++++++----- files/materials/terrain.shader | 16 ++++++++++------ files/settings-default.cfg | 2 ++ 5 files changed, 27 insertions(+), 11 deletions(-) diff --git a/apps/openmw/mwrender/renderingmanager.cpp b/apps/openmw/mwrender/renderingmanager.cpp index 308a016888..5fffa30d3a 100644 --- a/apps/openmw/mwrender/renderingmanager.cpp +++ b/apps/openmw/mwrender/renderingmanager.cpp @@ -129,6 +129,8 @@ RenderingManager::RenderingManager (OEngine::Render::OgreRenderer& _rend, const sh::Factory::getInstance ().setSharedParameter ("waterTimer", sh::makeProperty(new sh::FloatValue(0))); sh::Factory::getInstance ().setSharedParameter ("windDir_windSpeed", sh::makeProperty(new sh::Vector3(0.5, -0.8, 0.2))); sh::Factory::getInstance ().setSharedParameter ("waterSunFade_sunHeight", sh::makeProperty(new sh::Vector2(1, 0.6))); + sh::Factory::getInstance ().setSharedParameter ("gammaCorrection", sh::makeProperty(new sh::FloatValue( + Settings::Manager::getFloat ("gamma", "Video")))); applyCompositors(); diff --git a/files/materials/core.h b/files/materials/core.h index cba7167770..e9577bbf3c 100644 --- a/files/materials/core.h +++ b/files/materials/core.h @@ -1,3 +1,7 @@ +#define gammaCorrectRead(v) pow(v, float3(gammaCorrection,gammaCorrection,gammaCorrection)) +#define gammaCorrectOutput(v) pow(v, float3(1.f/gammaCorrection,1.f/gammaCorrection,1.f/gammaCorrection)) + + #if SH_HLSL == 1 || SH_CG == 1 #define shTexture2D sampler2D diff --git a/files/materials/objects.shader b/files/materials/objects.shader index 8e5cbf76ef..45f33774db 100644 --- a/files/materials/objects.shader +++ b/files/materials/objects.shader @@ -112,6 +112,8 @@ shUniform(float, far) @shAutoConstant(far, far_clip_distance) #endif + shUniform(float, gammaCorrection) @shSharedParameter(gammaCorrection, gammaCorrection) + #if LIGHTING shInput(float3, normalPassthrough) shInput(float3, objSpacePositionPassthrough) @@ -173,7 +175,8 @@ SH_START_PROGRAM { shOutputColour(0) = shSample(diffuseMap, UV); - + shOutputColour(0).xyz = gammaCorrectRead(shOutputColour(0).xyz); + #if LIGHTING float3 normal = normalize(normalPassthrough); float3 lightDir; @@ -259,7 +262,7 @@ // regular fog only if fragment is above water if (worldPos.y > waterLevel) #endif - shOutputColour(0).xyz = shLerp (shOutputColour(0).xyz, fogColour, fogValue); + shOutputColour(0).xyz = shLerp (shOutputColour(0).xyz, gammaCorrectRead(fogColour), fogValue); #endif // prevent negative colour output (for example with negative lights) @@ -274,12 +277,11 @@ float waterSunGradient = dot(eyeVec, -normalize(lightDirectionWS0.xyz)); waterSunGradient = shSaturate(pow(waterSunGradient*0.7+0.3,2.0)); - float3 waterSunColour = float3(0.0,1.0,0.85)*waterSunGradient * 0.5; + float3 waterSunColour = gammaCorrectRead(float3(0.0,1.0,0.85)) *waterSunGradient * 0.5; float waterGradient = dot(eyeVec, float3(0.0,-1.0,0.0)); waterGradient = clamp((waterGradient*0.5+0.5),0.2,1.0); - float3 watercolour = (float3(0.0078, 0.5176, 0.700)+waterSunColour)*waterGradient*2.0; - float3 waterext = float3(0.6, 0.9, 1.0);//water extinction + float3 watercolour = ( gammaCorrectRead(float3(0.0078, 0.5176, 0.700))+waterSunColour)*waterGradient*2.0; watercolour = shLerp(watercolour*0.3*waterSunFade_sunHeight.x, watercolour, shSaturate(1.0-exp(-waterSunFade_sunHeight.y*SUN_EXT))); watercolour = (cameraPos.y <= waterLevel) ? watercolour : watercolour*0.3; @@ -292,6 +294,8 @@ shOutputColour(0).xyz = shLerp (shOutputColour(0).xyz, watercolour, fogAmount * isUnderwater * waterEnabled); #endif + shOutputColour(0).xyz = gammaCorrectOutput(shOutputColour(0).xyz); + #if MRT shOutputColour(1) = float4(depthPassthrough / far,1,1,1); #endif diff --git a/files/materials/terrain.shader b/files/materials/terrain.shader index 7ef26d0359..9183595e34 100644 --- a/files/materials/terrain.shader +++ b/files/materials/terrain.shader @@ -137,6 +137,8 @@ shSampler2D(normalMap) // global normal map + shUniform(float, gammaCorrection) @shSharedParameter(gammaCorrection, gammaCorrection) + @shForeach(@shPropertyString(num_blendmaps)) shSampler2D(blendMap@shIterator) @@ -247,9 +249,9 @@ #if IS_FIRST_PASS == 1 && @shIterator == 0 // first layer of first pass doesn't need a blend map - albedo = shSample(diffuseMap0, UV * 10).rgb; + albedo = gammaCorrectRead(shSample(diffuseMap0, UV * 10).rgb); #else - albedo = shLerp(albedo, shSample(diffuseMap@shIterator, UV * 10).rgb, blendValues@shPropertyString(blendmap_component_@shIterator)); + albedo = shLerp(albedo, gammaCorrectRead(shSample(diffuseMap@shIterator, UV * 10).rgb), blendValues@shPropertyString(blendmap_component_@shIterator)); #endif @shEndForeach @@ -336,7 +338,7 @@ // regular fog only if fragment is above water if (worldPos.y > waterLevel) #endif - shOutputColour(0).xyz = shLerp (shOutputColour(0).xyz, fogColour, fogValue); + shOutputColour(0).xyz = shLerp (shOutputColour(0).xyz, gammaCorrectRead(fogColour), fogValue); #endif // prevent negative colour output (for example with negative lights) @@ -351,12 +353,12 @@ float waterSunGradient = dot(eyeVec, -normalize(lightDirectionWS0.xyz)); waterSunGradient = shSaturate(pow(waterSunGradient*0.7+0.3,2.0)); - float3 waterSunColour = float3(0.0,1.0,0.85)*waterSunGradient * 0.5; + float3 waterSunColour = gammaCorrectRead(float3(0.0,1.0,0.85))*waterSunGradient * 0.5; float waterGradient = dot(eyeVec, float3(0.0,-1.0,0.0)); waterGradient = clamp((waterGradient*0.5+0.5),0.2,1.0); - float3 watercolour = (float3(0.0078, 0.5176, 0.700)+waterSunColour)*waterGradient*2.0; - float3 waterext = float3(0.6, 0.9, 1.0);//water extinction + float3 watercolour = (gammaCorrectRead(float3(0.0078, 0.5176, 0.700))+waterSunColour)*waterGradient*2.0; + float3 waterext = gammaCorrectRead(float3(0.6, 0.9, 1.0));//water extinction watercolour = shLerp(watercolour*0.3*waterSunFade_sunHeight.x, watercolour, shSaturate(1.0-exp(-waterSunFade_sunHeight.y*SUN_EXT))); watercolour = (cameraPos.y <= waterLevel) ? watercolour : watercolour*0.3; @@ -369,6 +371,8 @@ shOutputColour(0).xyz = shLerp (shOutputColour(0).xyz, watercolour, fogAmount * isUnderwater); #endif + shOutputColour(0).xyz = gammaCorrectOutput(shOutputColour(0).xyz); + #if MRT shOutputColour(1) = float4(depth / far,1,1,1); diff --git a/files/settings-default.cfg b/files/settings-default.cfg index 6a77b7fc06..1768b2f5ec 100644 --- a/files/settings-default.cfg +++ b/files/settings-default.cfg @@ -28,6 +28,8 @@ vsync = false # PBuffer, FBO, Copy opengl rtt mode = FBO +gamma = 2.2 + [GUI] # 1 is fully opaque menu transparency = 0.84 From b9a3f8e8d74e2fc97fc48c1ad6e613d6f4d5b280 Mon Sep 17 00:00:00 2001 From: scrawl Date: Wed, 19 Sep 2012 23:47:42 +0200 Subject: [PATCH 77/84] gamma slider --- apps/openmw/mwgui/settingswindow.cpp | 19 +++++++++++++++++ apps/openmw/mwgui/settingswindow.hpp | 1 + apps/openmw/mwrender/renderingmanager.cpp | 5 +++++ files/mygui/openmw_settings_window.layout | 25 +++++++++++++++++++---- 4 files changed, 46 insertions(+), 4 deletions(-) diff --git a/apps/openmw/mwgui/settingswindow.cpp b/apps/openmw/mwgui/settingswindow.cpp index d1e206a957..cdfe4d2b68 100644 --- a/apps/openmw/mwgui/settingswindow.cpp +++ b/apps/openmw/mwgui/settingswindow.cpp @@ -122,6 +122,7 @@ namespace MWGui getWidget(mInvertYButton, "InvertYButton"); getWidget(mUISensitivitySlider, "UISensitivitySlider"); getWidget(mCameraSensitivitySlider, "CameraSensitivitySlider"); + getWidget(mGammaSlider, "GammaSlider"); mSubtitlesButton->eventMouseButtonClick += MyGUI::newDelegate(this, &SettingsWindow::onButtonToggled); mCrosshairButton->eventMouseButtonClick += MyGUI::newDelegate(this, &SettingsWindow::onButtonToggled); @@ -143,6 +144,7 @@ namespace MWGui mViewDistanceSlider->eventScrollChangePosition += MyGUI::newDelegate(this, &SettingsWindow::onSliderChangePosition); mResolutionList->eventListChangePosition += MyGUI::newDelegate(this, &SettingsWindow::onResolutionSelected); mAnisotropySlider->eventScrollChangePosition += MyGUI::newDelegate(this, &SettingsWindow::onSliderChangePosition); + mGammaSlider->eventScrollChangePosition += MyGUI::newDelegate(this, &SettingsWindow::onSliderChangePosition); mShadowsEnabledButton->eventMouseButtonClick += MyGUI::newDelegate(this, &SettingsWindow::onButtonToggled); mShadowsLargeDistance->eventMouseButtonClick += MyGUI::newDelegate(this, &SettingsWindow::onButtonToggled); @@ -200,6 +202,14 @@ namespace MWGui getWidget(fovText, "FovText"); fovText->setCaption("Field of View (" + boost::lexical_cast(int(Settings::Manager::getFloat("field of view", "General"))) + ")"); + float gammaVal = (Settings::Manager::getFloat("gamma", "Video")-0.1f)/(3.f-0.1f); + mGammaSlider->setScrollPosition(gammaVal * (mGammaSlider->getScrollRange()-1)); + MyGUI::TextBox* gammaText; + getWidget(gammaText, "GammaText"); + std::stringstream gamma; + gamma << std::setprecision (2) << Settings::Manager::getFloat("gamma", "Video"); + gammaText->setCaption("Gamma (" + gamma.str() + ")"); + float anisotropyVal = Settings::Manager::getInt("anisotropy", "General") / 16.0; mAnisotropySlider->setScrollPosition(anisotropyVal * (mAnisotropySlider->getScrollRange()-1)); std::string tf = Settings::Manager::getString("texture filtering", "General"); @@ -511,6 +521,15 @@ namespace MWGui fovText->setCaption("Field of View (" + boost::lexical_cast(int((1-val) * sFovMin + val * sFovMax)) + ")"); Settings::Manager::setFloat("field of view", "General", (1-val) * sFovMin + val * sFovMax); } + else if (scroller == mGammaSlider) + { + Settings::Manager::setFloat("gamma", "Video", (1-val) * 0.1f + val * 3.f); + MyGUI::TextBox* gammaText; + getWidget(gammaText, "GammaText"); + std::stringstream gamma; + gamma << std::setprecision (2) << Settings::Manager::getFloat("gamma", "Video"); + gammaText->setCaption("Gamma (" + gamma.str() + ")"); + } else if (scroller == mAnisotropySlider) { mAnisotropyLabel->setCaption("Anisotropy (" + boost::lexical_cast(int(val*16)) + ")"); diff --git a/apps/openmw/mwgui/settingswindow.hpp b/apps/openmw/mwgui/settingswindow.hpp index d1f35ed710..e878d0abea 100644 --- a/apps/openmw/mwgui/settingswindow.hpp +++ b/apps/openmw/mwgui/settingswindow.hpp @@ -40,6 +40,7 @@ namespace MWGui MyGUI::Button* mFPSButton; MyGUI::ScrollBar* mViewDistanceSlider; MyGUI::ScrollBar* mFOVSlider; + MyGUI::ScrollBar* mGammaSlider; MyGUI::ScrollBar* mAnisotropySlider; MyGUI::Button* mTextureFilteringButton; MyGUI::TextBox* mAnisotropyLabel; diff --git a/apps/openmw/mwrender/renderingmanager.cpp b/apps/openmw/mwrender/renderingmanager.cpp index 5fffa30d3a..d63f9c2fc7 100644 --- a/apps/openmw/mwrender/renderingmanager.cpp +++ b/apps/openmw/mwrender/renderingmanager.cpp @@ -749,6 +749,11 @@ void RenderingManager::processChangedSettings(const Settings::CategorySettingVec sh::Factory::getInstance ().setShadersEnabled (Settings::Manager::getBool("shaders", "Objects")); mObjects.rebuildStaticGeometry (); } + else if (it->second == "gamma" && it->first == "Video") + { + sh::Factory::getInstance ().setSharedParameter ("gammaCorrection", sh::makeProperty(new sh::FloatValue( + Settings::Manager::getFloat ("gamma", "Video")))); + } else if (it->second == "shader mode" && it->first == "General") { sh::Language lang; diff --git a/files/mygui/openmw_settings_window.layout b/files/mygui/openmw_settings_window.layout index 38d2786e51..2f9b5a67f1 100644 --- a/files/mygui/openmw_settings_window.layout +++ b/files/mygui/openmw_settings_window.layout @@ -157,7 +157,7 @@ - + @@ -174,20 +174,37 @@ - + - + - + + + + + + + + + + + + + + + + + + From 86cfc91ef357988564105fa60d254059c6e09b37 Mon Sep 17 00:00:00 2001 From: scrawl Date: Thu, 20 Sep 2012 13:56:37 +0200 Subject: [PATCH 78/84] global map rendering --- apps/openmw/CMakeLists.txt | 2 +- apps/openmw/engine.cpp | 3 + apps/openmw/mwbase/world.hpp | 1 + apps/openmw/mwgui/map_window.cpp | 26 +++- apps/openmw/mwgui/map_window.hpp | 3 + apps/openmw/mwrender/globalmap.cpp | 145 ++++++++++++++++++++++ apps/openmw/mwrender/globalmap.hpp | 23 ++++ apps/openmw/mwrender/renderingmanager.cpp | 14 ++- apps/openmw/mwrender/renderingmanager.hpp | 5 + apps/openmw/mwworld/worldimp.cpp | 5 + apps/openmw/mwworld/worldimp.hpp | 1 + components/esm/loadland.cpp | 6 +- components/esm/loadland.hpp | 2 +- files/mygui/openmw_map_window.layout | 15 ++- 14 files changed, 231 insertions(+), 20 deletions(-) create mode 100644 apps/openmw/mwrender/globalmap.cpp create mode 100644 apps/openmw/mwrender/globalmap.hpp diff --git a/apps/openmw/CMakeLists.txt b/apps/openmw/CMakeLists.txt index 2542ef350e..95d15f1184 100644 --- a/apps/openmw/CMakeLists.txt +++ b/apps/openmw/CMakeLists.txt @@ -16,7 +16,7 @@ source_group(game FILES ${GAME} ${GAME_HEADER}) add_openmw_dir (mwrender renderingmanager debugging sky player animation npcanimation creatureanimation actors objects renderinginterface localmap occlusionquery terrain terrainmaterial water shadows - compositors characterpreview externalrendering + compositors characterpreview externalrendering globalmap ) add_openmw_dir (mwinput diff --git a/apps/openmw/engine.cpp b/apps/openmw/engine.cpp index d10ae99794..b526d8e0d4 100644 --- a/apps/openmw/engine.cpp +++ b/apps/openmw/engine.cpp @@ -307,6 +307,8 @@ void OMW::Engine::go() //addResourcesDirectory(mResDir); + addResourcesDirectory(mCfgMgr.getCachePath ().string()); + addResourcesDirectory(mResDir / "mygui"); addResourcesDirectory(mResDir / "water"); addResourcesDirectory(mResDir / "gbuffer"); @@ -367,6 +369,7 @@ void OMW::Engine::go() pos.pos[2] = 0; mEnvironment.getWorld()->renderPlayer(); + mEnvironment.getWorld()->renderGlobalMap(); if (const ESM::Cell *exterior = MWBase::Environment::get().getWorld()->getExterior (mCellName)) { diff --git a/apps/openmw/mwbase/world.hpp b/apps/openmw/mwbase/world.hpp index b841e5427a..a725d389de 100644 --- a/apps/openmw/mwbase/world.hpp +++ b/apps/openmw/mwbase/world.hpp @@ -279,6 +279,7 @@ namespace MWBase virtual void togglePlayerLooking(bool enable) = 0; virtual void renderPlayer() = 0; + virtual void renderGlobalMap() = 0; virtual void setupExternalRendering (MWRender::ExternalRendering& rendering) = 0; }; diff --git a/apps/openmw/mwgui/map_window.cpp b/apps/openmw/mwgui/map_window.cpp index f92e4ee4fc..b2b8538ba3 100644 --- a/apps/openmw/mwgui/map_window.cpp +++ b/apps/openmw/mwgui/map_window.cpp @@ -3,6 +3,7 @@ #include #include +#include #include "../mwbase/windowmanager.hpp" #include "../mwbase/world.hpp" @@ -254,8 +255,11 @@ MapWindow::MapWindow(MWBase::WindowManager& parWindowManager) : getWidget(mLocalMap, "LocalMap"); getWidget(mGlobalMap, "GlobalMap"); + getWidget(mGlobalMapImage, "GlobalMapImage"); getWidget(mPlayerArrow, "Compass"); + mGlobalMap->setVisible (false); + getWidget(mButton, "WorldButton"); mButton->eventMouseButtonClick += MyGUI::newDelegate(this, &MapWindow::onWorldButtonClicked); mButton->setCaptionWithReplacing("#{sWorld}"); @@ -276,21 +280,22 @@ void MapWindow::setCellName(const std::string& cellName) void MapWindow::onDragStart(MyGUI::Widget* _sender, int _left, int _top, MyGUI::MouseButton _id) { if (_id!=MyGUI::MouseButton::Left) return; - if (!mGlobal) - mLastDragPos = MyGUI::IntPoint(_left, _top); + mLastDragPos = MyGUI::IntPoint(_left, _top); } void MapWindow::onMouseDrag(MyGUI::Widget* _sender, int _left, int _top, MyGUI::MouseButton _id) { if (_id!=MyGUI::MouseButton::Left) return; + MyGUI::IntPoint diff = MyGUI::IntPoint(_left, _top) - mLastDragPos; + if (!mGlobal) - { - MyGUI::IntPoint diff = MyGUI::IntPoint(_left, _top) - mLastDragPos; mLocalMap->setViewOffset( mLocalMap->getViewOffset() + diff ); + else + mGlobalMap->setViewOffset( mGlobalMap->getViewOffset() + diff ); - mLastDragPos = MyGUI::IntPoint(_left, _top); - } + + mLastDragPos = MyGUI::IntPoint(_left, _top); } void MapWindow::onWorldButtonClicked(MyGUI::Widget* _sender) @@ -307,3 +312,12 @@ void MapWindow::onPinToggled() { mWindowManager.setMinimapVisibility(!mPinned); } + +void MapWindow::open() +{ + mGlobalMapImage->setImageTexture("GlobalMap.png"); + + Ogre::TexturePtr tex = Ogre::TextureManager::getSingleton ().getByName("GlobalMap.png"); + mGlobalMap->setCanvasSize (tex->getWidth(), tex->getHeight()); + mGlobalMapImage->setSize(tex->getWidth(), tex->getHeight()); +} diff --git a/apps/openmw/mwgui/map_window.hpp b/apps/openmw/mwgui/map_window.hpp index 1203233bf9..abb6a06536 100644 --- a/apps/openmw/mwgui/map_window.hpp +++ b/apps/openmw/mwgui/map_window.hpp @@ -62,12 +62,15 @@ namespace MWGui void setCellName(const std::string& cellName); + virtual void open(); + private: void onDragStart(MyGUI::Widget* _sender, int _left, int _top, MyGUI::MouseButton _id); void onMouseDrag(MyGUI::Widget* _sender, int _left, int _top, MyGUI::MouseButton _id); void onWorldButtonClicked(MyGUI::Widget* _sender); MyGUI::ScrollView* mGlobalMap; + MyGUI::ImageBox* mGlobalMapImage; MyGUI::ImageBox* mPlayerArrow; MyGUI::Button* mButton; MyGUI::IntPoint mLastDragPos; diff --git a/apps/openmw/mwrender/globalmap.cpp b/apps/openmw/mwrender/globalmap.cpp new file mode 100644 index 0000000000..2edd325958 --- /dev/null +++ b/apps/openmw/mwrender/globalmap.cpp @@ -0,0 +1,145 @@ +#include "globalmap.hpp" + +#include +#include +#include +#include +#include + +#include "../mwbase/environment.hpp" +#include "../mwbase/world.hpp" + +#include +#include + +namespace MWRender +{ + + GlobalMap::GlobalMap(const std::string &cacheDir) + : mCacheDir(cacheDir) + { + } + + + void GlobalMap::render () + { + + Ogre::TexturePtr tex = Ogre::TextureManager::getSingleton ().getByName ("GlobalMap.png"); + + if (tex.isNull ()) + { + + int cellSize = 24; + + Ogre::Image image; + + int width = cellSize*61; + int height = cellSize*61; + + Ogre::uchar data[width * height * 3]; + + for (int x = -30; x <= 30; ++x) + { + for (int y = -30; y <= 30; ++y) + { + ESM::Land* land = MWBase::Environment::get().getWorld ()->getStore ().lands.search (x,y); + + if (land) + { + if (!land->dataLoaded) + { + land->loadData(); + } + } + + for (int cellY=0; cellYlandData->heights[vertexY * ESM::Land::LAND_SIZE + vertexX]; + + + if (landHeight >= 0) + { + if (landHeight >= hillHeight) + { + float factor = std::min(1.f, float(landHeight-hillHeight)/mountainHeight); + r = (hillColour.r * (1-factor) + mountainColour.r * factor) * 255; + g = (hillColour.g * (1-factor) + mountainColour.g * factor) * 255; + b = (hillColour.b * (1-factor) + mountainColour.b * factor) * 255; + } + else + { + float factor = std::min(1.f, float(landHeight)/hillHeight); + r = (groundColour.r * (1-factor) + hillColour.r * factor) * 255; + g = (groundColour.g * (1-factor) + hillColour.g * factor) * 255; + b = (groundColour.b * (1-factor) + hillColour.b * factor) * 255; + } + } + else + { + if (landHeight >= -100) + { + float factor = std::min(1.f, -1*landHeight/100.f); + r = (((waterShallowColour+groundColour)/2).r * (1-factor) + waterShallowColour.r * factor) * 255; + g = (((waterShallowColour+groundColour)/2).g * (1-factor) + waterShallowColour.g * factor) * 255; + b = (((waterShallowColour+groundColour)/2).b * (1-factor) + waterShallowColour.b * factor) * 255; + } + else + { + float factor = std::min(1.f, -1*(landHeight-100)/1000.f); + r = (waterShallowColour.r * (1-factor) + waterDeepColour.r * factor) * 255; + g = (waterShallowColour.g * (1-factor) + waterDeepColour.g * factor) * 255; + b = (waterShallowColour.b * (1-factor) + waterDeepColour.b * factor) * 255; + } + } + + } + else + { + r = waterDeepColour.r * 255; + g = waterDeepColour.g * 255; + b = waterDeepColour.b * 255; + } + + data[texelY * height * 3 + texelX * 3] = r; + data[texelY * height * 3 + texelX * 3+1] = g; + data[texelY * height * 3 + texelX * 3+2] = b; + } + assert(0); + } + } + } + + image.loadDynamicImage (data, width, height, Ogre::PF_B8G8R8); + + image.save (mCacheDir + "/GlobalMap.png"); + + tex = Ogre::TextureManager::getSingleton ().createManual ("GlobalMap.png", Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME, + Ogre::TEX_TYPE_2D, width, height, 0, Ogre::PF_B8G8R8, Ogre::TU_DEFAULT); + tex->loadImage(image); + } + tex->load(); + } + +} diff --git a/apps/openmw/mwrender/globalmap.hpp b/apps/openmw/mwrender/globalmap.hpp new file mode 100644 index 0000000000..b7c199dcf0 --- /dev/null +++ b/apps/openmw/mwrender/globalmap.hpp @@ -0,0 +1,23 @@ +#ifndef _GAME_RENDER_GLOBALMAP_H +#define _GAME_RENDER_GLOBALMAP_H + +#include + +namespace MWRender +{ + + class GlobalMap + { + public: + GlobalMap(const std::string& cacheDir); + + void render(); + + private: + std::string mCacheDir; + }; + +} + +#endif + diff --git a/apps/openmw/mwrender/renderingmanager.cpp b/apps/openmw/mwrender/renderingmanager.cpp index 308a016888..603d2e16c2 100644 --- a/apps/openmw/mwrender/renderingmanager.cpp +++ b/apps/openmw/mwrender/renderingmanager.cpp @@ -35,6 +35,7 @@ #include "compositors.hpp" #include "npcanimation.hpp" #include "externalrendering.hpp" +#include "globalmap.hpp" using namespace MWRender; using namespace Ogre; @@ -43,7 +44,7 @@ namespace MWRender { RenderingManager::RenderingManager (OEngine::Render::OgreRenderer& _rend, const boost::filesystem::path& resDir, const boost::filesystem::path& cacheDir, OEngine::Physic::PhysicEngine* engine) - :mRendering(_rend), mObjects(mRendering), mActors(mRendering), mAmbientMode(0), mSunEnabled(0), mPhysicsEngine(engine) + : mRendering(_rend), mObjects(mRendering), mActors(mRendering), mAmbientMode(0), mSunEnabled(0), mPhysicsEngine(engine) { // select best shader mode bool openGL = (Ogre::Root::getSingleton ().getRenderSystem ()->getName().find("OpenGL") != std::string::npos); @@ -100,7 +101,8 @@ RenderingManager::RenderingManager (OEngine::Render::OgreRenderer& _rend, const MaterialManager::getSingleton().setDefaultTextureFiltering(tfo); MaterialManager::getSingleton().setDefaultAnisotropy( (filter == "anisotropic") ? Settings::Manager::getInt("anisotropy", "General") : 1 ); - // Load resources + ResourceGroupManager::getSingleton ().declareResource ("GlobalMap.png", "Texture", ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME); + ResourceGroupManager::getSingleton().initialiseAllResourceGroups(); // causes light flicker in opengl when moving.. @@ -160,6 +162,8 @@ RenderingManager::RenderingManager (OEngine::Render::OgreRenderer& _rend, const mDebugging = new Debugging(mMwRoot, engine); mLocalMap = new MWRender::LocalMap(&mRendering, this); + mGlobalMap = new GlobalMap(cacheDir.string()); + setMenuTransparency(Settings::Manager::getFloat("menu transparency", "GUI")); } @@ -176,6 +180,7 @@ RenderingManager::~RenderingManager () delete mOcclusionQuery; delete mCompositors; delete mWater; + delete mGlobalMap; } MWRender::SkyManager* RenderingManager::getSkyManager() @@ -887,4 +892,9 @@ void RenderingManager::setupExternalRendering (MWRender::ExternalRendering& rend rendering.setup (mRendering.getScene()); } +void RenderingManager::renderGlobalMap () +{ + mGlobalMap->render (); +} + } // namespace diff --git a/apps/openmw/mwrender/renderingmanager.hpp b/apps/openmw/mwrender/renderingmanager.hpp index e994e4909c..24ec8b15b4 100644 --- a/apps/openmw/mwrender/renderingmanager.hpp +++ b/apps/openmw/mwrender/renderingmanager.hpp @@ -44,6 +44,7 @@ namespace MWRender class Water; class Compositors; class ExternalRendering; + class GlobalMap; class RenderingManager: private RenderingInterface, public Ogre::WindowEventListener { @@ -194,6 +195,8 @@ class RenderingManager: private RenderingInterface, public Ogre::WindowEventList void setupExternalRendering (MWRender::ExternalRendering& rendering); + void renderGlobalMap(); + protected: virtual void windowResized(Ogre::RenderWindow* rw); virtual void windowClosed(Ogre::RenderWindow* rw); @@ -218,6 +221,8 @@ class RenderingManager: private RenderingInterface, public Ogre::WindowEventList MWRender::Water *mWater; + GlobalMap* mGlobalMap; + OEngine::Render::OgreRenderer &mRendering; MWRender::Objects mObjects; diff --git a/apps/openmw/mwworld/worldimp.cpp b/apps/openmw/mwworld/worldimp.cpp index 8316116186..592f2b4b62 100644 --- a/apps/openmw/mwworld/worldimp.cpp +++ b/apps/openmw/mwworld/worldimp.cpp @@ -1237,6 +1237,11 @@ namespace MWWorld mRendering->renderPlayer(mPlayer->getPlayer()); } + void World::renderGlobalMap () + { + mRendering->renderGlobalMap (); + } + void World::setupExternalRendering (MWRender::ExternalRendering& rendering) { mRendering->setupExternalRendering (rendering); diff --git a/apps/openmw/mwworld/worldimp.hpp b/apps/openmw/mwworld/worldimp.hpp index d48a0ec814..dfb9238f50 100644 --- a/apps/openmw/mwworld/worldimp.hpp +++ b/apps/openmw/mwworld/worldimp.hpp @@ -310,6 +310,7 @@ namespace MWWorld } virtual void renderPlayer(); + virtual void renderGlobalMap(); virtual void setupExternalRendering (MWRender::ExternalRendering& rendering); }; diff --git a/components/esm/loadland.cpp b/components/esm/loadland.cpp index 96afdf8316..024767e90a 100644 --- a/components/esm/loadland.cpp +++ b/components/esm/loadland.cpp @@ -84,11 +84,7 @@ void Land::loadData() { mEsm->restoreContext(context); - //esm.getHNExact(landData->normals, sizeof(VNML), "VNML"); - if (mEsm->isNextSub("VNML")) - { - mEsm->skipHSubSize(12675); - } + mEsm->getHNExact(landData->normals, sizeof(VNML), "VNML"); VHGT rawHeights; diff --git a/components/esm/loadland.hpp b/components/esm/loadland.hpp index ebc314a280..955fb95181 100644 --- a/components/esm/loadland.hpp +++ b/components/esm/loadland.hpp @@ -60,7 +60,7 @@ struct Land { float heightOffset; float heights[LAND_NUM_VERTS]; - //float normals[LAND_NUM_VERTS * 3]; + float normals[LAND_NUM_VERTS * 3]; uint16_t textures[LAND_NUM_TEXTURES]; bool usingColours; diff --git a/files/mygui/openmw_map_window.layout b/files/mygui/openmw_map_window.layout index 8b64de22e1..2b9b439062 100644 --- a/files/mygui/openmw_map_window.layout +++ b/files/mygui/openmw_map_window.layout @@ -3,10 +3,6 @@ - - - - @@ -15,9 +11,18 @@ - + + + + + + + + + + From 5f014f7411be4859243895eb4f6d2b19852f5e98 Mon Sep 17 00:00:00 2001 From: scrawl Date: Thu, 20 Sep 2012 14:04:29 +0200 Subject: [PATCH 79/84] oops, left in a testing assertion --- apps/openmw/mwrender/globalmap.cpp | 1 - 1 file changed, 1 deletion(-) diff --git a/apps/openmw/mwrender/globalmap.cpp b/apps/openmw/mwrender/globalmap.cpp index 2edd325958..90fd25aff3 100644 --- a/apps/openmw/mwrender/globalmap.cpp +++ b/apps/openmw/mwrender/globalmap.cpp @@ -126,7 +126,6 @@ namespace MWRender data[texelY * height * 3 + texelX * 3+1] = g; data[texelY * height * 3 + texelX * 3+2] = b; } - assert(0); } } } From e8bba2b833af9f466ce3b8df63ceb37ad7edca05 Mon Sep 17 00:00:00 2001 From: scrawl Date: Thu, 20 Sep 2012 14:06:30 +0200 Subject: [PATCH 80/84] disabled loading of land normals again, didn't need them after all --- components/esm/loadland.cpp | 6 +++++- components/esm/loadland.hpp | 2 +- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/components/esm/loadland.cpp b/components/esm/loadland.cpp index 024767e90a..05cadae7f9 100644 --- a/components/esm/loadland.cpp +++ b/components/esm/loadland.cpp @@ -84,7 +84,11 @@ void Land::loadData() { mEsm->restoreContext(context); - mEsm->getHNExact(landData->normals, sizeof(VNML), "VNML"); + //mEsm->getHNExact(landData->normals, sizeof(VNML), "VNML"); + if (mEsm->isNextSub("VNML")) + { + mEsm->skipHSubSize(12675); + } VHGT rawHeights; diff --git a/components/esm/loadland.hpp b/components/esm/loadland.hpp index 955fb95181..ebc314a280 100644 --- a/components/esm/loadland.hpp +++ b/components/esm/loadland.hpp @@ -60,7 +60,7 @@ struct Land { float heightOffset; float heights[LAND_NUM_VERTS]; - float normals[LAND_NUM_VERTS * 3]; + //float normals[LAND_NUM_VERTS * 3]; uint16_t textures[LAND_NUM_TEXTURES]; bool usingColours; From e5e3d829d039c5963b45be56f24abf1d0ca16317 Mon Sep 17 00:00:00 2001 From: scrawl Date: Thu, 20 Sep 2012 17:30:09 +0200 Subject: [PATCH 81/84] player arrow & markers --- apps/openmw/mwgui/map_window.cpp | 69 +++++++++++++++++++++++--- apps/openmw/mwgui/map_window.hpp | 11 +++- apps/openmw/mwgui/windowmanagerimp.cpp | 3 ++ files/mygui/openmw_map_window.layout | 10 +++- 4 files changed, 84 insertions(+), 9 deletions(-) diff --git a/apps/openmw/mwgui/map_window.cpp b/apps/openmw/mwgui/map_window.cpp index b2b8538ba3..824e72bd85 100644 --- a/apps/openmw/mwgui/map_window.cpp +++ b/apps/openmw/mwgui/map_window.cpp @@ -4,10 +4,12 @@ #include #include +#include #include "../mwbase/windowmanager.hpp" #include "../mwbase/world.hpp" #include "../mwbase/environment.hpp" +#include "../mwworld/player.hpp" using namespace MWGui; @@ -256,7 +258,8 @@ MapWindow::MapWindow(MWBase::WindowManager& parWindowManager) : getWidget(mLocalMap, "LocalMap"); getWidget(mGlobalMap, "GlobalMap"); getWidget(mGlobalMapImage, "GlobalMapImage"); - getWidget(mPlayerArrow, "Compass"); + getWidget(mPlayerArrowLocal, "CompassLocal"); + getWidget(mPlayerArrowGlobal, "CompassGlobal"); mGlobalMap->setVisible (false); @@ -264,12 +267,14 @@ MapWindow::MapWindow(MWBase::WindowManager& parWindowManager) : mButton->eventMouseButtonClick += MyGUI::newDelegate(this, &MapWindow::onWorldButtonClicked); mButton->setCaptionWithReplacing("#{sWorld}"); - MyGUI::Button* eventbox; - getWidget(eventbox, "EventBox"); - eventbox->eventMouseDrag += MyGUI::newDelegate(this, &MapWindow::onMouseDrag); - eventbox->eventMouseButtonPressed += MyGUI::newDelegate(this, &MapWindow::onDragStart); + getWidget(mEventBoxGlobal, "EventBoxGlobal"); + mEventBoxGlobal->eventMouseDrag += MyGUI::newDelegate(this, &MapWindow::onMouseDrag); + mEventBoxGlobal->eventMouseButtonPressed += MyGUI::newDelegate(this, &MapWindow::onDragStart); + getWidget(mEventBoxLocal, "EventBoxLocal"); + mEventBoxLocal->eventMouseDrag += MyGUI::newDelegate(this, &MapWindow::onMouseDrag); + mEventBoxLocal->eventMouseButtonPressed += MyGUI::newDelegate(this, &MapWindow::onDragStart); - LocalMapBase::init(mLocalMap, mPlayerArrow, this); + LocalMapBase::init(mLocalMap, mPlayerArrowLocal, this); } void MapWindow::setCellName(const std::string& cellName) @@ -277,6 +282,35 @@ void MapWindow::setCellName(const std::string& cellName) setTitle(cellName); } +void MapWindow::addVisitedLocation(const std::string& name, int x, int y) +{ + const int cellSize = 24; + + Ogre::TexturePtr tex = Ogre::TextureManager::getSingleton ().getByName("GlobalMap.png"); + + MyGUI::IntCoord widgetCoord( + (x+30)*cellSize+6, + (tex->getHeight()-1) - (y+30)*cellSize+6, + 12, 12); + + + static int _counter=0; + MyGUI::Button* markerWidget = mGlobalMapImage->createWidget("ButtonImage", + widgetCoord, MyGUI::Align::Default, "Marker" + boost::lexical_cast(_counter)); + markerWidget->setImageResource("DoorMarker"); + markerWidget->setUserString("ToolTipType", "Layout"); + markerWidget->setUserString("ToolTipLayout", "TextToolTip"); + markerWidget->setUserString("Caption_Text", name); + ++_counter; + + markerWidget = mEventBoxGlobal->createWidget("", + widgetCoord, MyGUI::Align::Default); + markerWidget->setNeedMouseFocus (true); + markerWidget->setUserString("ToolTipType", "Layout"); + markerWidget->setUserString("ToolTipLayout", "TextToolTip"); + markerWidget->setUserString("Caption_Text", name); +} + void MapWindow::onDragStart(MyGUI::Widget* _sender, int _left, int _top, MyGUI::MouseButton _id) { if (_id!=MyGUI::MouseButton::Left) return; @@ -320,4 +354,27 @@ void MapWindow::open() Ogre::TexturePtr tex = Ogre::TextureManager::getSingleton ().getByName("GlobalMap.png"); mGlobalMap->setCanvasSize (tex->getWidth(), tex->getHeight()); mGlobalMapImage->setSize(tex->getWidth(), tex->getHeight()); + + for (unsigned int i=0; igetChildCount (); ++i) + { + if (mGlobalMapImage->getChildAt (i)->getName().substr(0,6) == "Marker") + mGlobalMapImage->getChildAt (i)->castType()->setImageResource("DoorMarker"); + } + + Ogre::Vector3 pos = MWBase::Environment::get().getWorld ()->getPlayer ().getPlayer().getRefData ().getBaseNode ()->_getDerivedPosition (); + Ogre::Quaternion orient = MWBase::Environment::get().getWorld ()->getPlayer ().getPlayer().getRefData ().getBaseNode ()->_getDerivedOrientation (); + Ogre::Vector2 dir (orient.yAxis ().x, -orient.yAxis().z); + + float worldX = ((pos.x / 8192.f-0.5) / 30.f+1)/2.f; + float worldY = ((pos.z / 8192.f+1.5) / 30.f+1)/2.f; + + mPlayerArrowGlobal->setPosition(MyGUI::IntPoint(tex->getWidth() * worldX - 16, tex->getHeight() * worldY - 16)); + + MyGUI::ISubWidget* main = mPlayerArrowGlobal->getSubWidgetMain(); + MyGUI::RotatingSkin* rotatingSubskin = main->castType(); + rotatingSubskin->setCenter(MyGUI::IntPoint(16,16)); + float angle = std::atan2(dir.x, dir.y); + rotatingSubskin->setAngle(angle); + + mPlayerArrowGlobal->setImageTexture ("textures\\compass.dds"); } diff --git a/apps/openmw/mwgui/map_window.hpp b/apps/openmw/mwgui/map_window.hpp index abb6a06536..e9c473a299 100644 --- a/apps/openmw/mwgui/map_window.hpp +++ b/apps/openmw/mwgui/map_window.hpp @@ -62,6 +62,8 @@ namespace MWGui void setCellName(const std::string& cellName); + void addVisitedLocation(const std::string& name, int x, int y); // adds the marker to the global map + virtual void open(); private: @@ -71,11 +73,18 @@ namespace MWGui MyGUI::ScrollView* mGlobalMap; MyGUI::ImageBox* mGlobalMapImage; - MyGUI::ImageBox* mPlayerArrow; + MyGUI::ImageBox* mPlayerArrowLocal; + MyGUI::ImageBox* mPlayerArrowGlobal; MyGUI::Button* mButton; MyGUI::IntPoint mLastDragPos; bool mGlobal; + MyGUI::Button* mEventBoxGlobal; + MyGUI::Button* mEventBoxLocal; + + int mGlobalMapSizeX; + int mGlobalMapSizeY; + protected: virtual void onPinToggled(); }; diff --git a/apps/openmw/mwgui/windowmanagerimp.cpp b/apps/openmw/mwgui/windowmanagerimp.cpp index 0241cc734a..728243d5f9 100644 --- a/apps/openmw/mwgui/windowmanagerimp.cpp +++ b/apps/openmw/mwgui/windowmanagerimp.cpp @@ -555,7 +555,10 @@ void WindowManager::changeCell(MWWorld::Ptr::CellStore* cell) { std::string name; if (cell->cell->name != "") + { name = cell->cell->name; + mMap->addVisitedLocation (name, cell->cell->getGridX (), cell->cell->getGridY ()); + } else { const ESM::Region* region = MWBase::Environment::get().getWorld()->getStore().regions.search(cell->cell->region); diff --git a/files/mygui/openmw_map_window.layout b/files/mygui/openmw_map_window.layout index 2b9b439062..20cfbbd6ed 100644 --- a/files/mygui/openmw_map_window.layout +++ b/files/mygui/openmw_map_window.layout @@ -7,10 +7,11 @@ - + + @@ -19,9 +20,14 @@ + + + + + + - From 451a9fd6ac8a03f20462d3d07d674ec3157a9688 Mon Sep 17 00:00:00 2001 From: scrawl Date: Thu, 20 Sep 2012 17:35:30 +0200 Subject: [PATCH 82/84] don't update world arrow position in interior --- apps/openmw/mwgui/map_window.cpp | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/apps/openmw/mwgui/map_window.cpp b/apps/openmw/mwgui/map_window.cpp index 824e72bd85..fe357660dd 100644 --- a/apps/openmw/mwgui/map_window.cpp +++ b/apps/openmw/mwgui/map_window.cpp @@ -368,13 +368,18 @@ void MapWindow::open() float worldX = ((pos.x / 8192.f-0.5) / 30.f+1)/2.f; float worldY = ((pos.z / 8192.f+1.5) / 30.f+1)/2.f; - mPlayerArrowGlobal->setPosition(MyGUI::IntPoint(tex->getWidth() * worldX - 16, tex->getHeight() * worldY - 16)); + // for interiors, we have no choice other than using the last position & direction. + /// \todo save this last position in the savegame? + if (MWBase::Environment::get().getWorld ()->isCellExterior ()) + { + mPlayerArrowGlobal->setPosition(MyGUI::IntPoint(tex->getWidth() * worldX - 16, tex->getHeight() * worldY - 16)); - MyGUI::ISubWidget* main = mPlayerArrowGlobal->getSubWidgetMain(); - MyGUI::RotatingSkin* rotatingSubskin = main->castType(); - rotatingSubskin->setCenter(MyGUI::IntPoint(16,16)); - float angle = std::atan2(dir.x, dir.y); - rotatingSubskin->setAngle(angle); + MyGUI::ISubWidget* main = mPlayerArrowGlobal->getSubWidgetMain(); + MyGUI::RotatingSkin* rotatingSubskin = main->castType(); + rotatingSubskin->setCenter(MyGUI::IntPoint(16,16)); + float angle = std::atan2(dir.x, dir.y); + rotatingSubskin->setAngle(angle); + } mPlayerArrowGlobal->setImageTexture ("textures\\compass.dds"); } From 98c1dc115145ebcf8ce0deb6efc50900e8f82b99 Mon Sep 17 00:00:00 2001 From: scrawl Date: Thu, 20 Sep 2012 18:02:37 +0200 Subject: [PATCH 83/84] ShowMap & FillMap commands, merged next --- apps/openmw/mwbase/windowmanager.hpp | 2 + apps/openmw/mwgui/windowmanagerimp.cpp | 5 +++ apps/openmw/mwgui/windowmanagerimp.hpp | 2 + apps/openmw/mwscript/docs/vmformat.txt | 4 +- apps/openmw/mwscript/guiextensions.cpp | 54 ++++++++++++++++++++++++++ 5 files changed, 66 insertions(+), 1 deletion(-) diff --git a/apps/openmw/mwbase/windowmanager.hpp b/apps/openmw/mwbase/windowmanager.hpp index 49f1f95b0e..4291631363 100644 --- a/apps/openmw/mwbase/windowmanager.hpp +++ b/apps/openmw/mwbase/windowmanager.hpp @@ -189,6 +189,8 @@ namespace MWBase virtual void allowMouse() = 0; virtual void notifyInputActionBound() = 0; + virtual void addVisitedLocation(const std::string& name, int x, int y) = 0; + virtual void removeDialog(OEngine::GUI::Layout* dialog) = 0; ///< Hides dialog and schedules dialog to be deleted. diff --git a/apps/openmw/mwgui/windowmanagerimp.cpp b/apps/openmw/mwgui/windowmanagerimp.cpp index c72ad9854a..c8e56f2c73 100644 --- a/apps/openmw/mwgui/windowmanagerimp.cpp +++ b/apps/openmw/mwgui/windowmanagerimp.cpp @@ -954,3 +954,8 @@ bool WindowManager::getPlayerSleeping () { return mWaitDialog->getSleeping(); } + +void WindowManager::addVisitedLocation(const std::string& name, int x, int y) +{ + mMap->addVisitedLocation (name, x, y); +} diff --git a/apps/openmw/mwgui/windowmanagerimp.hpp b/apps/openmw/mwgui/windowmanagerimp.hpp index 0ed5e1feaa..47461f877a 100644 --- a/apps/openmw/mwgui/windowmanagerimp.hpp +++ b/apps/openmw/mwgui/windowmanagerimp.hpp @@ -172,6 +172,8 @@ namespace MWGui virtual void allowMouse(); virtual void notifyInputActionBound(); + virtual void addVisitedLocation(const std::string& name, int x, int y); + virtual void removeDialog(OEngine::GUI::Layout* dialog); ///< Hides dialog and schedules dialog to be deleted. virtual void messageBox (const std::string& message, const std::vector& buttons); diff --git a/apps/openmw/mwscript/docs/vmformat.txt b/apps/openmw/mwscript/docs/vmformat.txt index a9f2cd1435..a4a9e99fd8 100644 --- a/apps/openmw/mwscript/docs/vmformat.txt +++ b/apps/openmw/mwscript/docs/vmformat.txt @@ -203,5 +203,7 @@ op 0x200019c: PlaceAtPc op 0x200019d: PlaceAtMe op 0x200019e: PlaceAtMe Explicit op 0x200019f: GetPcSleep -opcodes 0x20001a0-0x3ffffff unused +op 0x20001a0: ShowMap +op 0x20001a1: FillMap +opcodes 0x20001a2-0x3ffffff unused diff --git a/apps/openmw/mwscript/guiextensions.cpp b/apps/openmw/mwscript/guiextensions.cpp index 6e5540fa8f..a93de0ede2 100644 --- a/apps/openmw/mwscript/guiextensions.cpp +++ b/apps/openmw/mwscript/guiextensions.cpp @@ -1,12 +1,17 @@ #include "guiextensions.hpp" +#include + #include #include #include #include +#include +#include + #include "../mwbase/environment.hpp" #include "../mwbase/windowmanager.hpp" @@ -91,6 +96,47 @@ namespace MWScript } }; + class OpShowMap : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + std::string cell = (runtime.getStringLiteral (runtime[0].mInteger)); + boost::algorithm::to_lower(cell); + runtime.pop(); + + // "Will match complete or partial cells, so ShowMap, "Vivec" will show cells Vivec and Vivec, Fred's House as well." + // http://www.uesp.net/wiki/Tes3Mod:ShowMap + + const ESMS::CellList::ExtCells& extCells = MWBase::Environment::get().getWorld ()->getStore ().cells.extCells; + for (ESMS::CellList::ExtCells::const_iterator it = extCells.begin(); it != extCells.end(); ++it) + { + std::string name = it->second->name; + boost::algorithm::to_lower(name); + if (name.find(cell) != std::string::npos) + MWBase::Environment::get().getWindowManager()->addVisitedLocation (it->second->name, it->first.first, it->first.second); + } + } + }; + + class OpFillMap : public Interpreter::Opcode0 + { + public: + + virtual void execute (Interpreter::Runtime& runtime) + { + const ESMS::CellList::ExtCells& extCells = MWBase::Environment::get().getWorld ()->getStore ().cells.extCells; + for (ESMS::CellList::ExtCells::const_iterator it = extCells.begin(); it != extCells.end(); ++it) + { + std::string name = it->second->name; + if (name != "") + MWBase::Environment::get().getWindowManager()->addVisitedLocation (name, it->first.first, it->first.second); + } + } + }; + + const int opcodeEnableBirthMenu = 0x200000e; const int opcodeEnableClassMenu = 0x200000f; const int opcodeEnableNameMenu = 0x2000010; @@ -105,6 +151,8 @@ namespace MWScript const int opcodeGetButtonPressed = 0x2000137; const int opcodeToggleFogOfWar = 0x2000145; const int opcodeToggleFullHelp = 0x2000151; + const int opcodeShowMap = 0x20001a0; + const int opcodeFillMap = 0x20001a1; void registerExtensions (Compiler::Extensions& extensions) { @@ -132,6 +180,9 @@ opcodeEnableStatsReviewMenu); extensions.registerInstruction ("togglefullhelp", "", opcodeToggleFullHelp); extensions.registerInstruction ("tfh", "", opcodeToggleFullHelp); + + extensions.registerInstruction ("showmap", "S", opcodeShowMap); + extensions.registerInstruction ("fillmap", "", opcodeFillMap); } void installOpcodes (Interpreter::Interpreter& interpreter) @@ -167,6 +218,9 @@ opcodeEnableStatsReviewMenu); interpreter.installSegment5 (opcodeToggleFogOfWar, new OpToggleFogOfWar); interpreter.installSegment5 (opcodeToggleFullHelp, new OpToggleFullHelp); + + interpreter.installSegment5 (opcodeShowMap, new OpShowMap); + interpreter.installSegment5 (opcodeFillMap, new OpFillMap); } } } From a161b34c67ad41acb412fa3d249457ffb2cd791c Mon Sep 17 00:00:00 2001 From: scrawl Date: Thu, 20 Sep 2012 18:23:27 +0200 Subject: [PATCH 84/84] remove useless member, fix map rendering crash --- apps/openmw/mwgui/map_window.cpp | 13 +++++++------ apps/openmw/mwgui/map_window.hpp | 3 --- apps/openmw/mwrender/globalmap.cpp | 10 +++++++--- 3 files changed, 14 insertions(+), 12 deletions(-) diff --git a/apps/openmw/mwgui/map_window.cpp b/apps/openmw/mwgui/map_window.cpp index fe357660dd..ea7b442593 100644 --- a/apps/openmw/mwgui/map_window.cpp +++ b/apps/openmw/mwgui/map_window.cpp @@ -286,11 +286,11 @@ void MapWindow::addVisitedLocation(const std::string& name, int x, int y) { const int cellSize = 24; - Ogre::TexturePtr tex = Ogre::TextureManager::getSingleton ().getByName("GlobalMap.png"); + int size = 24 * 61; MyGUI::IntCoord widgetCoord( (x+30)*cellSize+6, - (tex->getHeight()-1) - (y+30)*cellSize+6, + (size-1) - (y+30)*cellSize+6, 12, 12); @@ -351,9 +351,10 @@ void MapWindow::open() { mGlobalMapImage->setImageTexture("GlobalMap.png"); - Ogre::TexturePtr tex = Ogre::TextureManager::getSingleton ().getByName("GlobalMap.png"); - mGlobalMap->setCanvasSize (tex->getWidth(), tex->getHeight()); - mGlobalMapImage->setSize(tex->getWidth(), tex->getHeight()); + int size = 24 * 61; + + mGlobalMap->setCanvasSize (size, size); + mGlobalMapImage->setSize(size, size); for (unsigned int i=0; igetChildCount (); ++i) { @@ -372,7 +373,7 @@ void MapWindow::open() /// \todo save this last position in the savegame? if (MWBase::Environment::get().getWorld ()->isCellExterior ()) { - mPlayerArrowGlobal->setPosition(MyGUI::IntPoint(tex->getWidth() * worldX - 16, tex->getHeight() * worldY - 16)); + mPlayerArrowGlobal->setPosition(MyGUI::IntPoint(size * worldX - 16, size * worldY - 16)); MyGUI::ISubWidget* main = mPlayerArrowGlobal->getSubWidgetMain(); MyGUI::RotatingSkin* rotatingSubskin = main->castType(); diff --git a/apps/openmw/mwgui/map_window.hpp b/apps/openmw/mwgui/map_window.hpp index e9c473a299..a8b5b9cb90 100644 --- a/apps/openmw/mwgui/map_window.hpp +++ b/apps/openmw/mwgui/map_window.hpp @@ -82,9 +82,6 @@ namespace MWGui MyGUI::Button* mEventBoxGlobal; MyGUI::Button* mEventBoxLocal; - int mGlobalMapSizeX; - int mGlobalMapSizeY; - protected: virtual void onPinToggled(); }; diff --git a/apps/openmw/mwrender/globalmap.cpp b/apps/openmw/mwrender/globalmap.cpp index 90fd25aff3..72adb75792 100644 --- a/apps/openmw/mwrender/globalmap.cpp +++ b/apps/openmw/mwrender/globalmap.cpp @@ -1,5 +1,7 @@ #include "globalmap.hpp" +#include + #include #include #include @@ -23,10 +25,9 @@ namespace MWRender void GlobalMap::render () { + Ogre::TexturePtr tex; - Ogre::TexturePtr tex = Ogre::TextureManager::getSingleton ().getByName ("GlobalMap.png"); - - if (tex.isNull ()) + if (!boost::filesystem::exists(mCacheDir + "/GlobalMap.png")) { int cellSize = 24; @@ -138,6 +139,9 @@ namespace MWRender Ogre::TEX_TYPE_2D, width, height, 0, Ogre::PF_B8G8R8, Ogre::TU_DEFAULT); tex->loadImage(image); } + else + tex = Ogre::TextureManager::getSingleton ().getByName ("GlobalMap.png"); + tex->load(); }