diff --git a/Engine/source/T3D/physics/bullet/btBody.cpp b/Engine/source/T3D/physics/bullet/btBody.cpp index eb722fd17..c71a0cc12 100644 --- a/Engine/source/T3D/physics/bullet/btBody.cpp +++ b/Engine/source/T3D/physics/bullet/btBody.cpp @@ -442,3 +442,25 @@ void BtBody::findContact(SceneObject **contactObject, } } } + +void BtBody::moveKinematicTo(const MatrixF &transform) +{ + AssertFatal(mActor, "BtBody::moveKinematicTo - The actor is null!"); + + U32 bodyflags = mActor->getCollisionFlags(); + const bool isKinematic = bodyflags & BF_KINEMATIC; + if (!isKinematic) + { + Con::errorf("BtBody::moveKinematicTo is only for kinematic bodies."); + return; + } + + if (mCenterOfMass) + { + MatrixF xfm; + xfm.mul(transform, *mCenterOfMass); + mActor->setCenterOfMassTransform(btCast(xfm)); + } + else + mActor->setCenterOfMassTransform(btCast(transform)); +} \ No newline at end of file diff --git a/Engine/source/T3D/physics/bullet/btBody.h b/Engine/source/T3D/physics/bullet/btBody.h index 2de1215d2..2d138e7e1 100644 --- a/Engine/source/T3D/physics/bullet/btBody.h +++ b/Engine/source/T3D/physics/bullet/btBody.h @@ -113,6 +113,8 @@ public: virtual void applyImpulse( const Point3F &origin, const Point3F &force ); virtual void findContact(SceneObject **contactObject, VectorF *contactNormal, Vector *outOverlapObjects) const; + virtual void moveKinematicTo(const MatrixF &xfm); + }; #endif // _T3D_PHYSICS_BTBODY_H_ diff --git a/Engine/source/T3D/physics/bullet/btPlayer.cpp b/Engine/source/T3D/physics/bullet/btPlayer.cpp index 6e22b0cf8..793f6053c 100644 --- a/Engine/source/T3D/physics/bullet/btPlayer.cpp +++ b/Engine/source/T3D/physics/bullet/btPlayer.cpp @@ -71,6 +71,7 @@ void BtPlayer::init( const char *type, mObject = obj; mWorld = (BtWorld*)world; + mSlopeAngle = runSurfaceCos; mStepHeight = stepHeight; //if ( dStricmp( type, "Capsule" ) == 0 ) @@ -102,6 +103,17 @@ Point3F BtPlayer::move( const VectorF &disp, CollisionList &outCol ) { AssertFatal( mGhostObject, "BtPlayer::move - The controller is null!" ); + if (!mWorld->isEnabled()) + { + btTransform currentTrans = mGhostObject->getWorldTransform(); + btVector3 currentPos = currentTrans.getOrigin(); + + Point3F returnPos = btCast(currentPos); + + returnPos.z -= mOriginOffset; + return returnPos; + } + // First recover from any penetrations from the previous tick. U32 numPenetrationLoops = 0; bool touchingContact = false; @@ -305,16 +317,9 @@ bool BtPlayer::_sweep( btVector3 *inOutCurrPos, const btVector3 &disp, Collision col.normal = btCast( callback.m_hitNormalWorld ); col.object = PhysicsUserData::getObject( callback.m_hitCollisionObject->getUserPointer() ); - if (disp.z() < 0.0f) - { - // We're sweeping down as part of the stepping routine. In this - // case we want to have the collision normal only point in the opposite direction. - // i.e. up If we include the sideways part of the normal then the Player class - // velocity calculations using this normal will affect the player's forwards - // momentum. This is especially noticable on stairs as the rounded bottom of - // the capsule slides up the corner of a stair. - col.normal.set(0.0f, 0.0f, 1.0f); - } + F32 vd = col.normal.z; + if (vd < mSlopeAngle) + return false; } return true; diff --git a/Engine/source/T3D/physics/bullet/btPlayer.h b/Engine/source/T3D/physics/bullet/btPlayer.h index 388035431..2ad89a946 100644 --- a/Engine/source/T3D/physics/bullet/btPlayer.h +++ b/Engine/source/T3D/physics/bullet/btPlayer.h @@ -57,6 +57,10 @@ protected: /// F32 mOriginOffset; + /// + F32 mSlopeAngle; + /// + /// F32 mStepHeight; /// diff --git a/Engine/source/T3D/physics/physicsBody.h b/Engine/source/T3D/physics/physicsBody.h index fd8cca089..8d5a3e05f 100644 --- a/Engine/source/T3D/physics/physicsBody.h +++ b/Engine/source/T3D/physics/physicsBody.h @@ -117,6 +117,10 @@ public: virtual void findContact(SceneObject **contactObject, VectorF *contactNormal, Vector *outOverlapObjects) const = 0; + + /// + virtual void moveKinematicTo(const MatrixF &xfm) = 0; + }; diff --git a/Engine/source/T3D/physics/physx3/px3Body.cpp b/Engine/source/T3D/physics/physx3/px3Body.cpp index e36e76d8d..14094e956 100644 --- a/Engine/source/T3D/physics/physx3/px3Body.cpp +++ b/Engine/source/T3D/physics/physx3/px3Body.cpp @@ -468,4 +468,22 @@ void Px3Body::findContact(SceneObject **contactObject, } } -} \ No newline at end of file +}void Px3Body::moveKinematicTo(const MatrixF &transform) +{ + AssertFatal(mActor, "Px3Body::moveKinematicTo - The actor is null!"); + + const bool isKinematic = mBodyFlags & BF_KINEMATIC; + if (!isKinematic) + { + Con::errorf("Px3Body::moveKinematicTo is only for kinematic bodies."); + return; + } + + mWorld->lockScene(); + + physx::PxRigidDynamic *actor = mActor->is(); + actor->setKinematicTarget(px3Cast(transform)); + + mWorld->unlockScene(); +} + diff --git a/Engine/source/T3D/physics/physx3/px3Body.h b/Engine/source/T3D/physics/physx3/px3Body.h index 831d54cde..29b90f343 100644 --- a/Engine/source/T3D/physics/physx3/px3Body.h +++ b/Engine/source/T3D/physics/physx3/px3Body.h @@ -120,6 +120,8 @@ public: virtual void findContact(SceneObject **contactObject, VectorF *contactNormal, Vector *outOverlapObjects) const; + virtual void moveKinematicTo(const MatrixF &xfm); + }; #endif // _PX3BODY_H_ diff --git a/Engine/source/T3D/physics/physx3/px3Player.cpp b/Engine/source/T3D/physics/physx3/px3Player.cpp index e831c939c..10dc65e86 100644 --- a/Engine/source/T3D/physics/physx3/px3Player.cpp +++ b/Engine/source/T3D/physics/physx3/px3Player.cpp @@ -329,3 +329,33 @@ Box3F Px3Player::getWorldBounds() return px3Cast( bounds ); } +bool Px3Player::testSpacials(const Point3F &nPos, const Point3F &nSize) const +{ + F32 offset = nSize.z * 0.5f; + F32 radius = getMax(nSize.x, nSize.y) * 0.5f - mSkinWidth; + F32 height = (nSize.z - (radius * 2.0f)) * 0.5f; + height -= mSkinWidth * 2.0f; + physx::PxCapsuleGeometry geom(radius, height); + + physx::PxVec3 pos(nPos.x, nPos.y, nPos.z + offset); + physx::PxQuat orientation(Float_HalfPi, physx::PxVec3(0.0f, 1.0f, 0.0f)); + + physx::PxOverlapBuffer hit; + physx::PxQueryFilterData queryFilter(physx::PxQueryFlag::eANY_HIT | physx::PxQueryFlag::eSTATIC | physx::PxQueryFlag::eDYNAMIC); + queryFilter.data.word0 = PX3_DEFAULT; + bool hasHit = mWorld->getScene()->overlap(geom, physx::PxTransform(pos, orientation), hit, queryFilter); + + return !hasHit; // Return true if there are no overlapping objects +} + +void Px3Player::setSpacials(const Point3F &nPos, const Point3F &nSize) +{ + mOriginOffset = nSize.z * 0.5f; + F32 radius = getMax(nSize.x, nSize.y) * 0.5f - mSkinWidth; + F32 height = nSize.z - (radius * 2.0f); + height -= mSkinWidth * 2.0f; + + mWorld->releaseWriteLock(); + mController->resize(height); + px3GetFirstShape(mController->getActor())->getCapsuleGeometry(mGeometry); +} \ No newline at end of file diff --git a/Engine/source/T3D/physics/physx3/px3Player.h b/Engine/source/T3D/physics/physx3/px3Player.h index 55a1409cd..bd0546663 100644 --- a/Engine/source/T3D/physics/physx3/px3Player.h +++ b/Engine/source/T3D/physics/physx3/px3Player.h @@ -94,8 +94,8 @@ public: PhysicsWorld *world ); virtual Point3F move( const VectorF &displacement, CollisionList &outCol ); virtual void findContact( SceneObject **contactObject, VectorF *contactNormal, Vector *outOverlapObjects ) const; - virtual bool testSpacials( const Point3F &nPos, const Point3F &nSize ) const { return true; } - virtual void setSpacials( const Point3F &nPos, const Point3F &nSize ) {} + virtual bool testSpacials( const Point3F &nPos, const Point3F &nSize ) const; + virtual void setSpacials( const Point3F &nPos, const Point3F &nSize ); virtual void enableCollision(); virtual void disableCollision(); }; diff --git a/Engine/source/T3D/physics/physx3/px3World.cpp b/Engine/source/T3D/physics/physx3/px3World.cpp index c073423e9..ca5be2302 100644 --- a/Engine/source/T3D/physics/physx3/px3World.cpp +++ b/Engine/source/T3D/physics/physx3/px3World.cpp @@ -62,7 +62,8 @@ Px3World::Px3World(): mScene( NULL ), mIsEnabled( false ), mEditorTimeScale( 1.0f ), mAccumulator( 0 ), - mControllerManager( NULL ) + mControllerManager(NULL), + mIsSceneLocked(false) { } @@ -335,6 +336,62 @@ void Px3World::releaseWriteLock() //AssertFatal( mScene->isWritable(), "PhysX3World::releaseWriteLock() - We should have been writable now!" ); } +void Px3World::lockScenes() +{ + Px3World *world = dynamic_cast(PHYSICSMGR->getWorld("server")); + + if (world) + world->lockScene(); + + world = dynamic_cast(PHYSICSMGR->getWorld("client")); + + if (world) + world->lockScene(); +} + +void Px3World::unlockScenes() +{ + Px3World *world = dynamic_cast(PHYSICSMGR->getWorld("server")); + + if (world) + world->unlockScene(); + + world = dynamic_cast(PHYSICSMGR->getWorld("client")); + + if (world) + world->unlockScene(); +} + +void Px3World::lockScene() +{ + if (!mScene) + return; + + if (mIsSceneLocked) + { + Con::printf("Px3World: Attempting to lock a scene that is already locked."); + return; + } + + mScene->lockWrite(); + mIsSceneLocked = true; +} + +void Px3World::unlockScene() +{ + if (!mScene) + return; + + if (!mIsSceneLocked) + { + Con::printf("Px3World: Attempting to unlock a scene that is not locked."); + return; + } + + mScene->unlockWrite(); + mIsSceneLocked = false; +} + bool Px3World::castRay( const Point3F &startPnt, const Point3F &endPnt, RayInfo *ri, const Point3F &impulse ) { diff --git a/Engine/source/T3D/physics/physx3/px3World.h b/Engine/source/T3D/physics/physx3/px3World.h index a1235d160..9556aac4b 100644 --- a/Engine/source/T3D/physics/physx3/px3World.h +++ b/Engine/source/T3D/physics/physx3/px3World.h @@ -56,6 +56,7 @@ protected: bool mIsEnabled; bool mIsSimulating; bool mIsServer; + bool mIsSceneLocked; U32 mTickCount; ProcessList *mProcessList; F32 mEditorTimeScale; @@ -96,11 +97,15 @@ public: void releaseWriteLock(); bool isServer(){return mIsServer;} physx::PxController* createController( physx::PxControllerDesc &desc ); + void lockScene(); + void unlockScene(); //static static bool restartSDK( bool destroyOnly = false, Px3World *clientWorld = NULL, Px3World *serverWorld = NULL ); static void releaseWriteLocks(); static physx::PxCooking *getCooking(); static void setTiming(F32 stepTime,U32 maxIterations); + static void lockScenes(); + static void unlockScenes(); }; #endif // _PX3WORLD_H_ diff --git a/Engine/source/T3D/vehicles/vehicle.cpp b/Engine/source/T3D/vehicles/vehicle.cpp index 1f18b426f..b6516fc3f 100644 --- a/Engine/source/T3D/vehicles/vehicle.cpp +++ b/Engine/source/T3D/vehicles/vehicle.cpp @@ -46,6 +46,9 @@ #include "gfx/primBuilder.h" #include "gfx/gfxDrawUtil.h" #include "materials/materialDefinition.h" +#include "T3D/physics/physicsPlugin.h" +#include "T3D/physics/physicsBody.h" +#include "T3D/physics/physicsCollision.h" namespace { @@ -203,7 +206,8 @@ VehicleData::VehicleData() dMemset(waterSound, 0, sizeof(waterSound)); collDamageThresholdVel = 20; - collDamageMultiplier = 0.05f; + collDamageMultiplier = 0.05f; + enablePhysicsRep = true; } @@ -315,6 +319,7 @@ void VehicleData::packData(BitStream* stream) stream->write(softSplashSoundVel); stream->write(medSplashSoundVel); stream->write(hardSplashSoundVel); + stream->write(enablePhysicsRep); // write the water sound profiles for(i = 0; i < MaxSounds; i++) @@ -411,6 +416,7 @@ void VehicleData::unpackData(BitStream* stream) stream->read(&softSplashSoundVel); stream->read(&medSplashSoundVel); stream->read(&hardSplashSoundVel); + stream->read(&enablePhysicsRep); // write the water sound profiles for(i = 0; i < MaxSounds; i++) @@ -465,6 +471,11 @@ void VehicleData::unpackData(BitStream* stream) void VehicleData::initPersistFields() { + addGroup("Physics"); + addField("enablePhysicsRep", TypeBool, Offset(enablePhysicsRep, VehicleData), + "@brief Creates a representation of the object in the physics plugin.\n"); + endGroup("Physics"); + addField( "jetForce", TypeF32, Offset(jetForce, VehicleData), "@brief Additional force applied to the vehicle when it is jetting.\n\n" "For WheeledVehicles, the force is applied in the forward direction. For " @@ -682,6 +693,8 @@ Vehicle::Vehicle() mWorkingQueryBox.minExtents.set(-1e9f, -1e9f, -1e9f); mWorkingQueryBox.maxExtents.set(-1e9f, -1e9f, -1e9f); mWorkingQueryBoxCountDown = sWorkingQueryBoxStaleThreshold; + + mPhysicsRep = NULL; } U32 Vehicle::getCollisionMask() @@ -695,6 +708,25 @@ Point3F Vehicle::getVelocity() const return mRigid.linVelocity; } +void Vehicle::_createPhysics() +{ + SAFE_DELETE(mPhysicsRep); + + if (!PHYSICSMGR || !mDataBlock->enablePhysicsRep) + return; + + TSShape *shape = mShapeInstance->getShape(); + PhysicsCollision *colShape = NULL; + colShape = shape->buildColShape(false, getScale()); + + if (colShape) + { + PhysicsWorld *world = PHYSICSMGR->getWorld(isServerObject() ? "server" : "client"); + mPhysicsRep = PHYSICSMGR->createBody(); + mPhysicsRep->init(colShape, 0, PhysicsBody::BF_KINEMATIC, this, world); + mPhysicsRep->setTransform(getTransform()); + } +} //---------------------------------------------------------------------------- bool Vehicle::onAdd() @@ -776,11 +808,15 @@ bool Vehicle::onAdd() mConvex.box.maxExtents.convolve(mObjScale); mConvex.findNodeTransform(); + _createPhysics(); + return true; } void Vehicle::onRemove() { + SAFE_DELETE(mPhysicsRep); + U32 i=0; for( i=0; ienablePhysicsRep is false as mPhysicsRep will be NULL if it is + if (mPhysicsRep) + mPhysicsRep->moveKinematicTo(getTransform()); } } diff --git a/Engine/source/T3D/vehicles/vehicle.h b/Engine/source/T3D/vehicles/vehicle.h index 695c16686..dd8619fd6 100644 --- a/Engine/source/T3D/vehicles/vehicle.h +++ b/Engine/source/T3D/vehicles/vehicle.h @@ -127,6 +127,8 @@ struct VehicleData: public ShapeBaseData F32 splashFreqMod; F32 splashVelEpsilon; + bool enablePhysicsRep; + // VehicleData(); bool preload(bool server, String &errorStr); @@ -142,6 +144,7 @@ struct VehicleData: public ShapeBaseData //---------------------------------------------------------------------------- +class PhysicsBody; class Vehicle: public ShapeBase { @@ -177,6 +180,8 @@ class Vehicle: public ShapeBase Point3F cameraRotVec; }; + PhysicsBody *mPhysicsRep; + StateDelta mDelta; S32 mPredictionCount; ///< Number of ticks to predict VehicleData* mDataBlock; @@ -262,6 +267,8 @@ public: bool onAdd(); void onRemove(); + void _createPhysics(); + /// Interpolates between move ticks @see processTick /// @param dt Change in time between the last call and this call to the function void interpolateTick(F32 dt); diff --git a/Engine/source/materials/materialFeatureTypes.cpp b/Engine/source/materials/materialFeatureTypes.cpp index 85fbd2895..513474c77 100644 --- a/Engine/source/materials/materialFeatureTypes.cpp +++ b/Engine/source/materials/materialFeatureTypes.cpp @@ -30,7 +30,6 @@ ImplementFeatureType( MFT_VertTransform, MFG_Transform, 0, true ); ImplementFeatureType( MFT_TexAnim, MFG_PreTexture, 1.0f, true ); ImplementFeatureType( MFT_Parallax, MFG_PreTexture, 2.0f, true ); -ImplementFeatureType( MFT_DiffuseVertColor, MFG_PreTexture, 3.0f, true ); ImplementFeatureType( MFT_AccuScale, MFG_PreTexture, 4.0f, true ); ImplementFeatureType( MFT_AccuDirection, MFG_PreTexture, 4.0f, true ); @@ -42,6 +41,7 @@ ImplementFeatureType( MFT_DiffuseMap, MFG_Texture, 2.0f, true ); ImplementFeatureType( MFT_OverlayMap, MFG_Texture, 3.0f, true ); ImplementFeatureType( MFT_DetailMap, MFG_Texture, 4.0f, true ); ImplementFeatureType( MFT_DiffuseColor, MFG_Texture, 5.0f, true ); +ImplementFeatureType( MFT_DiffuseVertColor, MFG_Texture, 6.0f, true ); ImplementFeatureType( MFT_AlphaTest, MFG_Texture, 7.0f, true ); ImplementFeatureType( MFT_SpecularMap, MFG_Texture, 8.0f, true ); ImplementFeatureType( MFT_NormalMap, MFG_Texture, 9.0f, true ); diff --git a/Engine/source/materials/processedShaderMaterial.cpp b/Engine/source/materials/processedShaderMaterial.cpp index 6ff609ebe..cd230ef53 100644 --- a/Engine/source/materials/processedShaderMaterial.cpp +++ b/Engine/source/materials/processedShaderMaterial.cpp @@ -1153,7 +1153,8 @@ void ProcessedShaderMaterial::_setShaderConstants(SceneRenderState * state, cons // Deferred Shading: Determine Material Info Flags S32 matInfoFlags = - (mMaterial->mEmissive[stageNum] ? 1 : 0); + (mMaterial->mEmissive[stageNum] ? 1 : 0) | //emissive + (mMaterial->mSubSurface[stageNum] ? 2 : 0); //subsurface mMaterial->mMatInfoFlags[stageNum] = matInfoFlags / 255.0f; shaderConsts->setSafe(handles->mMatInfoFlagsSC, mMaterial->mMatInfoFlags[stageNum]); if( handles->mAccuScaleSC->isValid() ) diff --git a/Engine/source/navigation/navMesh.cpp b/Engine/source/navigation/navMesh.cpp index f029c5deb..db70d1cc3 100644 --- a/Engine/source/navigation/navMesh.cpp +++ b/Engine/source/navigation/navMesh.cpp @@ -145,6 +145,17 @@ DefineConsoleFunction(NavMeshUpdateAroundObject, void, (S32 objid, bool remove), obj->enableCollision(); } + +DefineConsoleFunction(NavMeshIgnore, void, (S32 objid, bool _ignore), (0, true), + "@brief Flag this object as not generating a navmesh result.") +{ + SceneObject *obj; + if(!Sim::findObject(objid, obj)) + return; + + obj->mPathfindingIgnore = _ignore; +} + DefineConsoleFunction(NavMeshUpdateOne, void, (S32 meshid, S32 objid, bool remove), (0, 0, false), "@brief Update all tiles in a given NavMesh that intersect the given object's world box.") { @@ -839,6 +850,7 @@ void NavMesh::buildNextTile() static void buildCallback(SceneObject* object,void *key) { SceneContainer::CallbackInfo* info = reinterpret_cast(key); + if (!object->mPathfindingIgnore) object->buildPolyList(info->context,info->polyList,info->boundingBox,info->boundingSphere); } @@ -861,7 +873,7 @@ unsigned char *NavMesh::buildTileData(const Tile &tile, TileData &data, U32 &dat data.geom.clear(); info.polyList = &data.geom; info.key = this; - getContainer()->findObjects(box, StaticShapeObjectType | TerrainObjectType, buildCallback, &info); + getContainer()->findObjects(box, StaticObjectType | DynamicShapeObjectType, buildCallback, &info); // Parse water objects into the same list, but remember how much geometry was /not/ water. U32 nonWaterVertCount = data.geom.getVertCount(); diff --git a/Engine/source/scene/sceneObject.cpp b/Engine/source/scene/sceneObject.cpp index 1420bac11..1d16377af 100644 --- a/Engine/source/scene/sceneObject.cpp +++ b/Engine/source/scene/sceneObject.cpp @@ -144,6 +144,7 @@ SceneObject::SceneObject() mIsScopeAlways = false; mAccuTex = NULL; + mPathfindingIgnore = false; } //----------------------------------------------------------------------------- diff --git a/Engine/source/scene/sceneObject.h b/Engine/source/scene/sceneObject.h index 42c3c53ed..3985d372c 100644 --- a/Engine/source/scene/sceneObject.h +++ b/Engine/source/scene/sceneObject.h @@ -371,6 +371,7 @@ class SceneObject : public NetObject, private SceneContainer::Link, public Proce SceneObject(); virtual ~SceneObject(); + bool mPathfindingIgnore; /// Triggered when a SceneObject onAdd is called. static Signal< void( SceneObject* ) > smSceneObjectAdd; diff --git a/Engine/source/shaderGen/GLSL/shaderFeatureGLSL.cpp b/Engine/source/shaderGen/GLSL/shaderFeatureGLSL.cpp index 11081125c..e1433c11f 100644 --- a/Engine/source/shaderGen/GLSL/shaderFeatureGLSL.cpp +++ b/Engine/source/shaderGen/GLSL/shaderFeatureGLSL.cpp @@ -1194,7 +1194,10 @@ void DiffuseVertColorFeatureGLSL::processPix( Vector &compon } MultiLine* meta = new MultiLine; - meta->addStatement( new GenOp( " @;\r\n", assignColor( vertColor, Material::Mul ) ) ); + if (fd.features[MFT_isDeferred]) + meta->addStatement(new GenOp(" @;\r\n", assignColor(vertColor, Material::Mul, NULL, ShaderFeature::RenderTarget1))); + else + meta->addStatement(new GenOp(" @;\r\n", assignColor(vertColor, Material::Mul))); output = meta; } diff --git a/Engine/source/shaderGen/HLSL/shaderFeatureHLSL.cpp b/Engine/source/shaderGen/HLSL/shaderFeatureHLSL.cpp index 78e1c3b89..879176a44 100644 --- a/Engine/source/shaderGen/HLSL/shaderFeatureHLSL.cpp +++ b/Engine/source/shaderGen/HLSL/shaderFeatureHLSL.cpp @@ -1258,7 +1258,10 @@ void DiffuseVertColorFeatureHLSL::processPix( Vector &compon } MultiLine* meta = new MultiLine; - meta->addStatement( new GenOp( " @;\r\n", assignColor( vertColor, Material::Mul ) ) ); + if (fd.features[MFT_isDeferred]) + meta->addStatement(new GenOp(" @;\r\n", assignColor(vertColor, Material::Mul, NULL, ShaderFeature::RenderTarget1))); + else + meta->addStatement(new GenOp(" @;\r\n", assignColor(vertColor, Material::Mul))); output = meta; } diff --git a/Templates/Empty/game/tools/materialEditor/scripts/materialEditor.ed.cs b/Templates/Empty/game/tools/materialEditor/scripts/materialEditor.ed.cs index be7d55c39..c1f01f1a7 100644 --- a/Templates/Empty/game/tools/materialEditor/scripts/materialEditor.ed.cs +++ b/Templates/Empty/game/tools/materialEditor/scripts/materialEditor.ed.cs @@ -918,9 +918,6 @@ function MaterialEditorGui::guiSync( %this, %material ) MaterialEditorPropertiesWindow-->vertLitCheckbox.setValue((%material).vertLit[%layer]); MaterialEditorPropertiesWindow-->vertColorSwatch.color = (%material).vertColor[%layer]; MaterialEditorPropertiesWindow-->subSurfaceCheckbox.setValue((%material).subSurface[%layer]); - MaterialEditorPropertiesWindow-->subSurfaceColorSwatch.color = (%material).subSurfaceColor[%layer]; - MaterialEditorPropertiesWindow-->subSurfaceRolloffTextEdit.setText((%material).subSurfaceRolloff[%layer]); - MaterialEditorPropertiesWindow-->minnaertTextEdit.setText((%material).minnaertConstant[%layer]); // Animation properties MaterialEditorPropertiesWindow-->RotationAnimation.setValue(0); diff --git a/Templates/Empty/game/tools/shapeEditor/scripts/shapeEditor.ed.cs b/Templates/Empty/game/tools/shapeEditor/scripts/shapeEditor.ed.cs index 180a9a8ab..391e0b217 100644 --- a/Templates/Empty/game/tools/shapeEditor/scripts/shapeEditor.ed.cs +++ b/Templates/Empty/game/tools/shapeEditor/scripts/shapeEditor.ed.cs @@ -380,7 +380,8 @@ function ShapeEdSelectWindow::navigate( %this, %address ) // Ignore assets in the tools folder %fullPath = makeRelativePath( %fullPath, getMainDotCSDir() ); - %splitPath = strreplace( %fullPath, "/", " " ); + %splitPath = strreplace( %fullPath, " ", "_" ); + %splitPath = strreplace( %splitPath, "/", " " ); if ( getWord( %splitPath, 0 ) $= "tools" ) { %fullPath = findNextFileMultiExpr( %filePatterns ); @@ -393,6 +394,7 @@ function ShapeEdSelectWindow::navigate( %this, %address ) // Add this file's path ( parent folders ) to the // popup menu if it isn't there yet. %temp = strreplace( %pathFolders, " ", "/" ); + %temp = strreplace( %temp, "_", " " ); %r = ShapeEdSelectMenu.findText( %temp ); if ( %r == -1 ) ShapeEdSelectMenu.add( %temp ); diff --git a/Templates/Empty/game/tools/worldEditor/scripts/editors/creator.ed.cs b/Templates/Empty/game/tools/worldEditor/scripts/editors/creator.ed.cs index dc5d7f991..43d4fb65c 100644 --- a/Templates/Empty/game/tools/worldEditor/scripts/editors/creator.ed.cs +++ b/Templates/Empty/game/tools/worldEditor/scripts/editors/creator.ed.cs @@ -318,7 +318,8 @@ function EWCreatorWindow::navigate( %this, %address ) } %fullPath = makeRelativePath( %fullPath, getMainDotCSDir() ); - %splitPath = strreplace( %fullPath, "/", " " ); + %splitPath = strreplace( %fullPath, " ", "_" ); + %splitPath = strreplace( %splitPath, "/", " " ); if( getWord(%splitPath, 0) $= "tools" ) { %fullPath = findNextFileMultiExpr( getFormatExtensions() ); @@ -332,6 +333,7 @@ function EWCreatorWindow::navigate( %this, %address ) // Add this file's path (parent folders) to the // popup menu if it isn't there yet. %temp = strreplace( %pathFolders, " ", "/" ); + %temp = strreplace( %temp, "_", " " ); %r = CreatorPopupMenu.findText( %temp ); if ( %r == -1 ) { @@ -430,7 +432,8 @@ function EWCreatorWindow::navigate( %this, %address ) while ( %fullPath !$= "" ) { %fullPath = makeRelativePath( %fullPath, getMainDotCSDir() ); - %splitPath = strreplace( %fullPath, "/", " " ); + %splitPath = strreplace( %fullPath, " ", "_" ); + %splitPath = strreplace( %splitPath, "/", " " ); if( getWord(%splitPath, 0) $= "tools" ) { %fullPath = findNextFile( %expr ); @@ -444,6 +447,7 @@ function EWCreatorWindow::navigate( %this, %address ) // Add this file's path (parent folders) to the // popup menu if it isn't there yet. %temp = strreplace( %pathFolders, " ", "/" ); + %temp = strreplace( %temp, "_", " " ); %r = CreatorPopupMenu.findText( %temp ); if ( %r == -1 ) { diff --git a/Templates/Full/game/scripts/client/default.bind.cs b/Templates/Full/game/scripts/client/default.bind.cs index d2ca23730..9dcbca96b 100644 --- a/Templates/Full/game/scripts/client/default.bind.cs +++ b/Templates/Full/game/scripts/client/default.bind.cs @@ -618,7 +618,12 @@ GlobalActionMap.bind(keyboard, "ctrl o", bringUpOptions); function showMetrics(%val) { if(%val) - metrics("fps gfx shadow sfx terrain groundcover forest net"); + { + if(!Canvas.isMember(FrameOverlayGui)) + metrics("fps gfx shadow sfx terrain groundcover forest net"); + else + metrics(""); + } } GlobalActionMap.bind(keyboard, "ctrl F2", showMetrics); diff --git a/Templates/Full/game/shaders/common/lighting/advanced/gl/pointLightP.glsl b/Templates/Full/game/shaders/common/lighting/advanced/gl/pointLightP.glsl index 8a1aae3ca..8fe127e04 100644 --- a/Templates/Full/game/shaders/common/lighting/advanced/gl/pointLightP.glsl +++ b/Templates/Full/game/shaders/common/lighting/advanced/gl/pointLightP.glsl @@ -147,6 +147,17 @@ void main() return; } + vec4 colorSample = texture( colorBuffer, uvScene ); + vec3 subsurface = vec3(0.0,0.0,0.0); + if (getFlag( matInfo.r, 1 )) + { + subsurface = colorSample.rgb; + if (colorSample.r>colorSample.g) + subsurface = vec3(0.772549, 0.337255, 0.262745); + else + subsurface = vec3(0.337255, 0.772549, 0.262745); + } + // Sample/unpack the normal/z data vec4 prepassSample = prepassUncondition( prePassBuffer, uvScene ); vec3 normal = prepassSample.rgb; @@ -258,6 +269,5 @@ void main() addToResult = ( 1.0 - shadowed ) * abs(lightMapParams); } - vec4 colorSample = texture( colorBuffer, uvScene ); - OUT_col = AL_DeferredOutput(lightColorOut, colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); + OUT_col = AL_DeferredOutput(lightColorOut+subsurface*(1.0-Sat_NL_Att), colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); } diff --git a/Templates/Full/game/shaders/common/lighting/advanced/gl/spotLightP.glsl b/Templates/Full/game/shaders/common/lighting/advanced/gl/spotLightP.glsl index e7f3e88a7..c6ffa02a0 100644 --- a/Templates/Full/game/shaders/common/lighting/advanced/gl/spotLightP.glsl +++ b/Templates/Full/game/shaders/common/lighting/advanced/gl/spotLightP.glsl @@ -89,6 +89,17 @@ void main() return; } + vec4 colorSample = texture( colorBuffer, uvScene ); + vec3 subsurface = vec3(0.0,0.0,0.0); + if (getFlag( matInfo.r, 1 )) + { + subsurface = colorSample.rgb; + if (colorSample.r>colorSample.g) + subsurface = vec3(0.772549, 0.337255, 0.262745); + else + subsurface = vec3(0.337255, 0.772549, 0.262745); + } + // Sample/unpack the normal/z data vec4 prepassSample = prepassUncondition( prePassBuffer, uvScene ); vec3 normal = prepassSample.rgb; @@ -195,6 +206,5 @@ void main() addToResult = ( 1.0 - shadowed ) * abs(lightMapParams); } - vec4 colorSample = texture( colorBuffer, uvScene ); - OUT_col = AL_DeferredOutput(lightColorOut, colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); + OUT_col = AL_DeferredOutput(lightColorOut+subsurface*(1.0-Sat_NL_Att), colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); } diff --git a/Templates/Full/game/shaders/common/lighting/advanced/gl/vectorLightP.glsl b/Templates/Full/game/shaders/common/lighting/advanced/gl/vectorLightP.glsl index 608524a5a..15e0bf477 100644 --- a/Templates/Full/game/shaders/common/lighting/advanced/gl/vectorLightP.glsl +++ b/Templates/Full/game/shaders/common/lighting/advanced/gl/vectorLightP.glsl @@ -202,6 +202,17 @@ void main() return; } + vec4 colorSample = texture( colorBuffer, uv0 ); + vec3 subsurface = vec3(0.0,0.0,0.0); + if (getFlag( matInfo.r, 1 )) + { + subsurface = colorSample.rgb; + if (colorSample.r>colorSample.g) + subsurface = vec3(0.772549, 0.337255, 0.262745); + else + subsurface = vec3(0.337255, 0.772549, 0.262745); + } + // Sample/unpack the normal/z data vec4 prepassSample = prepassUncondition( prePassBuffer, uv0 ); vec3 normal = prepassSample.rgb; @@ -312,6 +323,5 @@ void main() lightColorOut = debugColor; #endif - vec4 colorSample = texture( colorBuffer, uv0 ); - OUT_col = AL_DeferredOutput(lightColorOut, colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); + OUT_col = AL_DeferredOutput(lightColorOut+subsurface*(1.0-Sat_NL_Att), colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); } diff --git a/Templates/Full/game/shaders/common/lighting/advanced/pointLightP.hlsl b/Templates/Full/game/shaders/common/lighting/advanced/pointLightP.hlsl index 540fd65c7..a8c0ea105 100644 --- a/Templates/Full/game/shaders/common/lighting/advanced/pointLightP.hlsl +++ b/Templates/Full/game/shaders/common/lighting/advanced/pointLightP.hlsl @@ -149,6 +149,16 @@ float4 main( ConvexConnectP IN ) : TORQUE_TARGET0 { return float4(0.0, 0.0, 0.0, 0.0); } + float4 colorSample = TORQUE_TEX2D( colorBuffer, uvScene ); + float3 subsurface = float3(0.0,0.0,0.0); + if (getFlag( matInfo.r, 1 )) + { + subsurface = colorSample.rgb; + if (colorSample.r>colorSample.g) + subsurface = float3(0.772549, 0.337255, 0.262745); + else + subsurface = float3(0.337255, 0.772549, 0.262745); + } // Sample/unpack the normal/z data float4 prepassSample = TORQUE_PREPASS_UNCONDITION( prePassBuffer, uvScene ); @@ -263,6 +273,5 @@ float4 main( ConvexConnectP IN ) : TORQUE_TARGET0 addToResult = ( 1.0 - shadowed ) * abs(lightMapParams); } - float4 colorSample = TORQUE_TEX2D( colorBuffer, uvScene ); - return AL_DeferredOutput(lightColorOut, colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); + return AL_DeferredOutput(lightColorOut+subsurface*(1.0-Sat_NL_Att), colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); } diff --git a/Templates/Full/game/shaders/common/lighting/advanced/spotLightP.hlsl b/Templates/Full/game/shaders/common/lighting/advanced/spotLightP.hlsl index e1f3baf93..5040b15e2 100644 --- a/Templates/Full/game/shaders/common/lighting/advanced/spotLightP.hlsl +++ b/Templates/Full/game/shaders/common/lighting/advanced/spotLightP.hlsl @@ -87,6 +87,17 @@ float4 main( ConvexConnectP IN ) : TORQUE_TARGET0 return float4(0.0, 0.0, 0.0, 0.0); } + float4 colorSample = TORQUE_TEX2D( colorBuffer, uvScene ); + float3 subsurface = float3(0.0,0.0,0.0); + if (getFlag( matInfo.r, 1 )) + { + subsurface = colorSample.rgb; + if (colorSample.r>colorSample.g) + subsurface = float3(0.772549, 0.337255, 0.262745); + else + subsurface = float3(0.337255, 0.772549, 0.262745); + } + // Sample/unpack the normal/z data float4 prepassSample = TORQUE_PREPASS_UNCONDITION( prePassBuffer, uvScene ); float3 normal = prepassSample.rgb; @@ -194,6 +205,5 @@ float4 main( ConvexConnectP IN ) : TORQUE_TARGET0 addToResult = ( 1.0 - shadowed ) * abs(lightMapParams); } - float4 colorSample = TORQUE_TEX2D( colorBuffer, uvScene ); - return AL_DeferredOutput(lightColorOut, colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); + return AL_DeferredOutput(lightColorOut+subsurface*(1.0-Sat_NL_Att), colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); } diff --git a/Templates/Full/game/shaders/common/lighting/advanced/vectorLightP.hlsl b/Templates/Full/game/shaders/common/lighting/advanced/vectorLightP.hlsl index 1a9726171..956227909 100644 --- a/Templates/Full/game/shaders/common/lighting/advanced/vectorLightP.hlsl +++ b/Templates/Full/game/shaders/common/lighting/advanced/vectorLightP.hlsl @@ -202,6 +202,16 @@ float4 main( FarFrustumQuadConnectP IN ) : TORQUE_TARGET0 return float4(1.0, 1.0, 1.0, 0.0); } + float4 colorSample = TORQUE_TEX2D( colorBuffer, IN.uv0 ); + float3 subsurface = float3(0.0,0.0,0.0); + if (getFlag( matInfo.r, 1 )) + { + subsurface = colorSample.rgb; + if (colorSample.r>colorSample.g) + subsurface = float3(0.772549, 0.337255, 0.262745); + else + subsurface = float3(0.337255, 0.772549, 0.262745); + } // Sample/unpack the normal/z data float4 prepassSample = TORQUE_PREPASS_UNCONDITION( prePassBuffer, IN.uv0 ); float3 normal = prepassSample.rgb; @@ -314,6 +324,5 @@ float4 main( FarFrustumQuadConnectP IN ) : TORQUE_TARGET0 lightColorOut = debugColor; #endif - float4 colorSample = TORQUE_TEX2D( colorBuffer, IN.uv0 ); - return AL_DeferredOutput(lightColorOut, colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); + return AL_DeferredOutput(lightColorOut+subsurface*(1.0-Sat_NL_Att), colorSample.rgb, matInfo, addToResult, specular, Sat_NL_Att); } diff --git a/Templates/Full/game/tools/materialEditor/gui/guiMaterialPropertiesWindow.ed.gui b/Templates/Full/game/tools/materialEditor/gui/guiMaterialPropertiesWindow.ed.gui index 63ce28e2a..1e3b98189 100644 --- a/Templates/Full/game/tools/materialEditor/gui/guiMaterialPropertiesWindow.ed.gui +++ b/Templates/Full/game/tools/materialEditor/gui/guiMaterialPropertiesWindow.ed.gui @@ -2240,6 +2240,29 @@ useMouseEvents = "0"; useInactiveState = "0"; }; + new GuiCheckBoxCtrl() { + canSaveDynamicFields = "0"; + internalName = "subSurfaceCheckbox"; + Enabled = "1"; + isContainer = "0"; + Profile = "ToolsGuiCheckBoxProfile"; + HorizSizing = "right"; + VertSizing = "bottom"; + position = "8 46"; + Extent = "79 16"; + MinExtent = "8 2"; + canSave = "1"; + Visible = "1"; + Command = "MaterialEditorGui.updateActiveMaterial(\"subSurface[\" @ MaterialEditorGui.currentLayer @ \"]\", $ThisControl.getValue());"; + tooltipprofile = "ToolsGuiDefaultProfile"; + ToolTip = "Enables the use of subsurface scattering for this layer."; + hovertime = "1000"; + text = "Sub Surface"; + groupNum = "-1"; + buttonType = "ToggleButton"; + useMouseEvents = "0"; + useInactiveState = "0"; + }; }; }; }; diff --git a/Templates/Full/game/tools/materialEditor/scripts/materialEditor.ed.cs b/Templates/Full/game/tools/materialEditor/scripts/materialEditor.ed.cs index be7d55c39..c1f01f1a7 100644 --- a/Templates/Full/game/tools/materialEditor/scripts/materialEditor.ed.cs +++ b/Templates/Full/game/tools/materialEditor/scripts/materialEditor.ed.cs @@ -918,9 +918,6 @@ function MaterialEditorGui::guiSync( %this, %material ) MaterialEditorPropertiesWindow-->vertLitCheckbox.setValue((%material).vertLit[%layer]); MaterialEditorPropertiesWindow-->vertColorSwatch.color = (%material).vertColor[%layer]; MaterialEditorPropertiesWindow-->subSurfaceCheckbox.setValue((%material).subSurface[%layer]); - MaterialEditorPropertiesWindow-->subSurfaceColorSwatch.color = (%material).subSurfaceColor[%layer]; - MaterialEditorPropertiesWindow-->subSurfaceRolloffTextEdit.setText((%material).subSurfaceRolloff[%layer]); - MaterialEditorPropertiesWindow-->minnaertTextEdit.setText((%material).minnaertConstant[%layer]); // Animation properties MaterialEditorPropertiesWindow-->RotationAnimation.setValue(0); diff --git a/Templates/Full/game/tools/shapeEditor/scripts/shapeEditor.ed.cs b/Templates/Full/game/tools/shapeEditor/scripts/shapeEditor.ed.cs index 180a9a8ab..391e0b217 100644 --- a/Templates/Full/game/tools/shapeEditor/scripts/shapeEditor.ed.cs +++ b/Templates/Full/game/tools/shapeEditor/scripts/shapeEditor.ed.cs @@ -380,7 +380,8 @@ function ShapeEdSelectWindow::navigate( %this, %address ) // Ignore assets in the tools folder %fullPath = makeRelativePath( %fullPath, getMainDotCSDir() ); - %splitPath = strreplace( %fullPath, "/", " " ); + %splitPath = strreplace( %fullPath, " ", "_" ); + %splitPath = strreplace( %splitPath, "/", " " ); if ( getWord( %splitPath, 0 ) $= "tools" ) { %fullPath = findNextFileMultiExpr( %filePatterns ); @@ -393,6 +394,7 @@ function ShapeEdSelectWindow::navigate( %this, %address ) // Add this file's path ( parent folders ) to the // popup menu if it isn't there yet. %temp = strreplace( %pathFolders, " ", "/" ); + %temp = strreplace( %temp, "_", " " ); %r = ShapeEdSelectMenu.findText( %temp ); if ( %r == -1 ) ShapeEdSelectMenu.add( %temp ); diff --git a/Templates/Full/game/tools/worldEditor/scripts/editors/creator.ed.cs b/Templates/Full/game/tools/worldEditor/scripts/editors/creator.ed.cs index 1712097ea..9dbfb91bb 100644 --- a/Templates/Full/game/tools/worldEditor/scripts/editors/creator.ed.cs +++ b/Templates/Full/game/tools/worldEditor/scripts/editors/creator.ed.cs @@ -349,7 +349,8 @@ function EWCreatorWindow::navigate( %this, %address ) } %fullPath = makeRelativePath( %fullPath, getMainDotCSDir() ); - %splitPath = strreplace( %fullPath, "/", " " ); + %splitPath = strreplace( %fullPath, " ", "_" ); + %splitPath = strreplace( %splitPath, "/", " " ); if( getWord(%splitPath, 0) $= "tools" ) { %fullPath = findNextFileMultiExpr( getFormatExtensions() ); @@ -363,6 +364,7 @@ function EWCreatorWindow::navigate( %this, %address ) // Add this file's path (parent folders) to the // popup menu if it isn't there yet. %temp = strreplace( %pathFolders, " ", "/" ); + %temp = strreplace( %temp, "_", " " ); %r = CreatorPopupMenu.findText( %temp ); if ( %r == -1 ) { @@ -461,7 +463,8 @@ function EWCreatorWindow::navigate( %this, %address ) while ( %fullPath !$= "" ) { %fullPath = makeRelativePath( %fullPath, getMainDotCSDir() ); - %splitPath = strreplace( %fullPath, "/", " " ); + %splitPath = strreplace( %fullPath, " ", "_" ); + %splitPath = strreplace( %splitPath, "/", " " ); if( getWord(%splitPath, 0) $= "tools" ) { %fullPath = findNextFile( %expr ); @@ -475,6 +478,7 @@ function EWCreatorWindow::navigate( %this, %address ) // Add this file's path (parent folders) to the // popup menu if it isn't there yet. %temp = strreplace( %pathFolders, " ", "/" ); + %temp = strreplace( %temp, "_", " " ); %r = CreatorPopupMenu.findText( %temp ); if ( %r == -1 ) { diff --git a/Templates/Full/game/tools/worldEditor/scripts/menus.ed.cs b/Templates/Full/game/tools/worldEditor/scripts/menus.ed.cs index 102931dec..0916a0065 100644 --- a/Templates/Full/game/tools/worldEditor/scripts/menus.ed.cs +++ b/Templates/Full/game/tools/worldEditor/scripts/menus.ed.cs @@ -262,6 +262,7 @@ function EditorGui::buildMenus(%this) barTitle = "Tools"; item[0] = "Network Graph" TAB "n" TAB "toggleNetGraph();"; + item[1] = "Profiler" TAB "ctrl F2" TAB "showMetrics(true);"; }; %this.menuBar.insert(%toolsMenu, %this.menuBar.getCount()); diff --git a/Tools/CMake/torque3d.cmake b/Tools/CMake/torque3d.cmake index 63a8c9ca9..6a4e4dd31 100644 --- a/Tools/CMake/torque3d.cmake +++ b/Tools/CMake/torque3d.cmake @@ -362,7 +362,7 @@ if(TORQUE_TOOLS) addPath("${srcDir}/forest/editor") addPath("${srcDir}/gui/editor") if(NOT TORQUE_EXPERIMENTAL_EC) - set(BLACKLIST "entityGroup.cpp;entityGroup.h;mountingGroup.cpp;mountingGroup.h" ) + set(BLACKLIST "entityGroup.cpp;entityGroup.h;mountingGroup.cpp;mountingGroup.h;componentGroup.cpp;componentGroup.h" ) endif() addPath("${srcDir}/gui/editor/inspector") set(BLACKLIST "" )