diff options
| author | Anton Novoselov <[email protected]> | 2017-08-14 16:41:28 +0300 |
|---|---|---|
| committer | Anton Novoselov <[email protected]> | 2017-08-14 16:41:28 +0300 |
| commit | 9a1c1d814f3fa0b54b49d90b43130c02bc280f44 (patch) | |
| tree | eae6ead883173c66619c30b6a1ed085f3cb70f4d /tools/ArtistTools/source/BlastPlugin/SampleBase | |
| parent | Updated to CL 22627414: (diff) | |
| download | blast-9a1c1d814f3fa0b54b49d90b43130c02bc280f44.tar.xz blast-9a1c1d814f3fa0b54b49d90b43130c02bc280f44.zip | |
Updated to CL 22661993:
* docs updates
* authoring fixes
* asset view in sample fix
* latest blast_tools_and_samples-windows.zip
Diffstat (limited to 'tools/ArtistTools/source/BlastPlugin/SampleBase')
20 files changed, 814 insertions, 287 deletions
diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastAsset.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastAsset.cpp index c39d927..7bb4f95 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastAsset.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastAsset.cpp @@ -36,10 +36,24 @@ #include "SampleManager.h" // Add By Lixu End - +std::set<int> ExistingAssetIds; BlastAsset::BlastAsset(Renderer& renderer) : m_renderer(renderer), m_bondHealthMax(1.0f), m_supportChunkHealthMax(1.0f) { + for (int id = 0; ; id++) + { + if (ExistingAssetIds.find(id) == ExistingAssetIds.end()) + { + ExistingAssetIds.emplace(id); + mUniqueId = id; + break; + } + } +} + +BlastAsset::~BlastAsset() +{ + ExistingAssetIds.erase(mUniqueId); } void BlastAsset::initialize() diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastAsset.h b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastAsset.h index 5502c5c..feec9e3 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastAsset.h +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastAsset.h @@ -65,7 +65,8 @@ public: //////// ctor //////// BlastAsset(Renderer& renderer); - virtual ~BlastAsset() {} + virtual ~BlastAsset(); + int mUniqueId; //////// desc //////// diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastController.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastController.cpp index 8df665e..950b217 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastController.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastController.cpp @@ -242,6 +242,20 @@ BlastFamily* BlastController::getFamilyByPxActor(const PxActor& actor) return nullptr; } +BlastFamily* BlastController::getFamilyById(int familyId) +{ + BlastFamily* pBlastFamily = nullptr; + for (BlastFamilyPtr p : m_families) + { + if (p->mUniqueId == familyId) + { + pBlastFamily = p; + break; + } + } + return pBlastFamily; +} + std::vector<PxActor*> BlastController::getActor(BlastAsset* asset, int chunkId) { std::vector<PxActor*> actors; diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastController.h b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastController.h index 5e4d269..7a6bcf0 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastController.h +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastController.h @@ -169,6 +169,8 @@ public: // only update unfractured mode mesh void updateModelMeshToProjectParam(const PxActor& actor); + + BlastFamily* getFamilyById(int familyId); // Add By Lixu End float getLastStressDelta() const; diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamily.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamily.cpp index b5afc82..dff2d20 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamily.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamily.cpp @@ -53,6 +53,7 @@ const float RIGIDBODY_DENSITY = 2000.0f; +std::set<int> ExistingFamilyIds; BlastFamily::BlastFamily(PhysXController& physXController, ExtPxManager& pxManager, const BlastAsset& blastAsset) : m_physXController(physXController) , m_pxManager(pxManager) @@ -64,6 +65,16 @@ BlastFamily::BlastFamily(PhysXController& physXController, ExtPxManager& pxManag { m_settings.stressSolverEnabled = false; m_settings.stressDamageEnabled = false; + + for (int id = 0; ; id++) + { + if (ExistingFamilyIds.find(id) == ExistingFamilyIds.end()) + { + ExistingFamilyIds.emplace(id); + mUniqueId = id; + break; + } + } } BlastFamily::~BlastFamily() @@ -76,6 +87,8 @@ BlastFamily::~BlastFamily() m_pxFamily->unsubscribe(m_listener); m_pxFamily->release(); + + ExistingFamilyIds.erase(mUniqueId); } void BlastFamily::initialize(const BlastAsset::ActorDesc& desc) @@ -572,6 +585,7 @@ private: bool BlastFamily::overlap(const PxGeometry& geometry, const PxTransform& pose, std::function<void(ExtPxActor*)> hitCall) { // Add By Lixu Begin + /* const ExtPxAsset* pExtPxAsset = m_blastAsset.getPxAsset(); const TkAsset& tkAsset = pExtPxAsset->getTkAsset(); uint32_t bondCount = tkAsset.getBondCount(); @@ -579,6 +593,7 @@ bool BlastFamily::overlap(const PxGeometry& geometry, const PxTransform& pose, s { return false; } + */ // Add By Lixu End std::set<ExtPxActor*> actorsToDamage; diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamily.h b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamily.h index 356e0c5..9978f20 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamily.h +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamily.h @@ -180,6 +180,7 @@ public: //////// dtor //////// virtual ~BlastFamily(); + int mUniqueId; protected: diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamilyModelSimple.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamilyModelSimple.cpp index 7d2cbe4..4ca8b87 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamilyModelSimple.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/blast/BlastFamilyModelSimple.cpp @@ -157,8 +157,10 @@ void scaleModel(BlastModel& model, PxMat44& scale) class SimpleRenderMesh : public IRenderMesh { public: - SimpleRenderMesh(const SimpleMesh* mesh) : m_mesh(mesh) + SimpleRenderMesh(const SimpleMesh* mesh, int renderableId) : m_mesh(mesh) { + mUniqueId = renderableId; + m_device = GetDeviceManager()->GetDevice(); m_inputDesc.push_back({ "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 }); @@ -242,7 +244,7 @@ public: { context.IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST); - UINT strides[2] = { sizeof(SimpleMesh::Vertex), sizeof(uint32_t) }; + UINT strides[2] = { sizeof(SimpleMesh::Vertex), sizeof(float) }; UINT offsets[2] = { 0 }; ID3D11Buffer* buffers[2] = { m_vertexBuffer, m_healthBuffer }; context.IASetVertexBuffers(0, 2, buffers, strides, offsets); @@ -371,9 +373,12 @@ BlastFamilyModelSimple::BlastFamilyModelSimple(PhysXController& physXController, // Add By Lixu End renderMeshes.resize(meshes.size()); renderables.resize(meshes.size()); + + int renderableId = Renderable::getRenderableId(mUniqueId, chunkIndex); + for (uint32_t i = 0; i < meshes.size(); i++) { - renderMeshes[i] = new SimpleRenderMesh(&meshes[i].mesh); + renderMeshes[i] = new SimpleRenderMesh(&meshes[i].mesh, renderableId); uint32_t materialIndex = model.chunks[chunkIndex].meshes[i].materialIndex; @@ -788,7 +793,7 @@ void BlastFamilyModelSimple::setChunkSelected(uint32_t chunk, bool selected) std::vector<Renderable*>& renderables = m_chunks[chunk].renderables; for (Renderable* r : renderables) { - r->setSelected(select); + r->setSelected(selected); if (!selectionDepthTest && selected) { diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/core/SampleManager.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/core/SampleManager.cpp index 88af3a1..f26fdb3 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/core/SampleManager.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/core/SampleManager.cpp @@ -2686,6 +2686,11 @@ void SampleManager::UpdateCamera() m_renderer->UpdateCamera(); } +void SampleManager::ResetUpDir(bool zup) +{ + m_physXController->ResetUpDir(zup); +} + void SampleManager::_addAssetToProjectParam(BlastAsset* pBlastAsset) { BlastAssetModel* assetModel = dynamic_cast<BlastAssetModel*>(pBlastAsset); diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/core/SampleManager.h b/tools/ArtistTools/source/BlastPlugin/SampleBase/core/SampleManager.h index c16fa25..8daceb4 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/core/SampleManager.h +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/core/SampleManager.h @@ -292,6 +292,7 @@ class SampleManager void refreshAsset(BlastAsset* pBlastAsset); void UpdateCamera(); + void ResetUpDir(bool zup); bool IsSimulating() { return m_simulating; } void EnableSimulating(bool bSimulating); diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/physx/PhysXController.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/physx/PhysXController.cpp index 1cf9e26..ba21a2e 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/physx/PhysXController.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/physx/PhysXController.cpp @@ -60,6 +60,7 @@ // Add By Lixu Begin #include "PxRigidActorExt.h" #include "SimpleScene.h" +#include "GlobalSettings.h" // Add By Lixu End #include <imgui.h> @@ -73,7 +74,6 @@ const DirectX::XMFLOAT4 PLANE_COLOR(1.0f, 1.0f, 1.0f, 1.0f); const DirectX::XMFLOAT4 HOOK_LINE_COLOR(1.0f, 1.0f, 1.0f, 1.0f); const float DEFAULT_FIXED_TIMESTEP = 1.0f / 60.0f; -static Nv::Blast::ExtCustomProfiler gBlastProfiler; PhysXController::PhysXController(PxSimulationFilterShader filterShader) : m_filterShader(filterShader) @@ -126,6 +126,7 @@ void PhysXController::initPhysX() m_pvd = PxCreatePvd(*m_foundation); + static Nv::Blast::ExtCustomProfiler gBlastProfiler; NvBlastProfilerSetCallback(&gBlastProfiler); NvBlastProfilerSetDetail(Nv::Blast::ProfilerDetail::LOW); gBlastProfiler.setPlatformEnabled(false); @@ -451,8 +452,8 @@ LRESULT PhysXController::MsgProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lPa if (m_draggingEnabled && (uMsg == WM_LBUTTONDOWN || uMsg == WM_MOUSEMOVE || uMsg == WM_LBUTTONUP)) { - float mouseX = (short)LOWORD(lParam) / getRenderer().getScreenWidth(); - float mouseY = (short)HIWORD(lParam) / getRenderer().getScreenHeight(); + float mouseX = (short)LOWORD(lParam); + float mouseY = (short)HIWORD(lParam); PxVec3 eyePos, pickDir; getEyePoseAndPickDir(mouseX, mouseY, eyePos, pickDir); @@ -590,7 +591,8 @@ void PhysXController::drawUI() /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // Add By Lixu Begin -PhysXController::Actor* planeActor_Pri = nullptr; +// 0 means GROUND_YUP 1 means GROUND_ZUP +PhysXController::Actor* planeActor_Pri[2] = { nullptr, nullptr }; // Add By Lixu End void PhysXController::initPhysXPrimitives() @@ -609,8 +611,12 @@ void PhysXController::initPhysXPrimitives() plane->setColor(PLANE_COLOR); // Add By Lixu Begin - planeActor_Pri = plane; - planeActor_Pri->setHidden(true); + planeActor_Pri[0] = plane; + planeActor_Pri[0]->setHidden(true); + plane = spawnPhysXPrimitivePlane(PxPlane(PxVec3(0, 0, 1).getNormalized(), 0)); + plane->setColor(PLANE_COLOR); + planeActor_Pri[1] = plane; + planeActor_Pri[1]->setHidden(true); // Add By Lixu End } @@ -657,7 +663,7 @@ PhysXController::Actor* PhysXController::spawnPhysXPrimitiveBox(const PxTransfor PhysXController::Actor* PhysXController::spawnPhysXPrimitivePlane(const PxPlane& plane) { PxRigidStatic* actor = PxCreatePlane(*m_physics, plane, *m_defaultMaterial); - PhysXController::Actor* p = spawnPhysXPrimitive(actor, true, true); + PhysXController::Actor* p = spawnPhysXPrimitive(actor, false, true); return p; } @@ -852,8 +858,8 @@ PxVec3 PhysXController::getMeshScaleForShape(const PxShape* shape) /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // Utils /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// - -PxVec3 unproject(PxMat44& proj, PxMat44& view, float x, float y) +// work right +PxVec3 unprojectRH(PxMat44& proj, PxMat44& view, float x, float y) { PxVec4 screenPoint(x, y, 0, 1); PxVec4 viewPoint = PxVec4(x / proj[0][0], y / proj[1][1], 1, 1); @@ -863,9 +869,55 @@ PxVec3 unproject(PxMat44& proj, PxMat44& view, float x, float y) return PxVec3(nearPoint.x, nearPoint.y, nearPoint.z); } +// work wrong +PxVec3 unprojectRH2(PxMat44& proj, PxMat44& view, float x, float y) +{ + PxMat44 matProj = view * proj; + PxMat44 matInverse = matProj.inverseRT(); + + PxVec4 screenPoint(x, y, 0, 0); + PxVec4 pos = matInverse.transform(screenPoint); + return PxVec3(pos.x, pos.y, pos.z); +} + +// work right +PxVec3 unprojectLH(PxMat44& proj, PxMat44& view, float x, float y) +{ + DirectX::XMMATRIX proj1 = PxMat44ToXMMATRIX(proj); + DirectX::XMMATRIX view1 = PxMat44ToXMMATRIX(view); + DirectX::XMMATRIX invProjectionView = DirectX::XMMatrixInverse(&DirectX::XMMatrixDeterminant(view1 * proj1), (view1 * proj1)); + + DirectX::XMVECTOR mousePosition = DirectX::XMVectorSet(x, y, 0.0f, 0.0f); + DirectX::XMVECTOR mouseInWorldSpace = DirectX::XMVector3Transform(mousePosition, invProjectionView); + return PxVec3(DirectX::XMVectorGetX(mouseInWorldSpace), DirectX::XMVectorGetY(mouseInWorldSpace), DirectX::XMVectorGetZ(mouseInWorldSpace)); +} + +// work right +PxVec3 unprojectLH(DirectX::XMMATRIX& proj, DirectX::XMMATRIX& view, float x, float y) +{ + //DirectX::XMMATRIX invProjectionView = DirectX::XMMatrixInverse(&DirectX::XMMatrixDeterminant(view * proj), (view * proj)); + + //DirectX::XMVECTOR mousePosition = DirectX::XMVectorSet(x, y, 0.0f, 0.0f); + //DirectX::XMVECTOR mouseInWorldSpace = DirectX::XMVector3Transform(mousePosition, invProjectionView); + //return PxVec3(DirectX::XMVectorGetX(mouseInWorldSpace), DirectX::XMVectorGetY(mouseInWorldSpace), DirectX::XMVectorGetZ(mouseInWorldSpace)); + + + DirectX::XMMATRIX inView = DirectX::XMMatrixInverse(&DirectX::XMMatrixDeterminant(view), view); + + DirectX::XMVECTOR screenPoint = DirectX::XMVectorSet(x, y, 0, 1); + DirectX::XMVECTOR viewPoint = DirectX::XMVectorSet(x / DirectX::XMVectorGetX(proj.r[0]), y / DirectX::XMVectorGetY(proj.r[1]), 1, 1); + DirectX::XMVECTOR nearPoint = DirectX::XMVector3Transform(viewPoint, inView); + PxVec3 nearPnt = PxVec3(DirectX::XMVectorGetX(nearPoint), DirectX::XMVectorGetY(nearPoint), DirectX::XMVectorGetZ(nearPoint)); + if (DirectX::XMVectorGetW(nearPoint)) + nearPnt *= 1.0f / DirectX::XMVectorGetW(nearPoint); + return nearPnt; +} + +#include "SimpleScene.h" void PhysXController::getEyePoseAndPickDir(float mouseX, float mouseY, PxVec3& eyePos, PxVec3& pickDir) { +#if(0) // Add By Lixu Begin PxMat44 view, proj; SimpleScene* simpleScene = SimpleScene::Inst(); @@ -886,10 +938,46 @@ void PhysXController::getEyePoseAndPickDir(float mouseX, float mouseY, PxVec3& e PxMat44 eyeTransform = view.inverseRT(); eyePos = eyeTransform.getPosition(); - PxVec3 nearPos = unproject(proj, view, mouseX * 2 - 1, 1 - mouseY * 2); + PxVec3 nearPos = unprojectRH(proj, view, mouseX * 2 - 1, 1 - mouseY * 2); pickDir = nearPos - eyePos; -} +#endif + +#if(0) + if (SimpleScene::Inst()->m_pCamera->UseLHS()) + { + DirectX::XMMATRIX view = SimpleScene::Inst()->GetViewMatrix(); + DirectX::XMMATRIX proj = SimpleScene::Inst()->GetProjMatrix(); + + DirectX::XMMATRIX eyeTransform = DirectX::XMMatrixInverse(&DirectX::XMMatrixDeterminant(view), view); + eyePos = PxVec3(DirectX::XMVectorGetX(eyeTransform.r[3]), DirectX::XMVectorGetY(eyeTransform.r[3]), DirectX::XMVectorGetZ(eyeTransform.r[3])); + + PxVec3 nearPos = unprojectLH(proj, view, mouseX * 2 - 1, 1 - mouseY * 2); + + pickDir = nearPos - eyePos; + } + else + { + PxMat44 view = XMMATRIXToPxMat44(getRenderer().getCamera().GetViewMatrix()); + PxMat44 proj = XMMATRIXToPxMat44(getRenderer().getCamera().GetProjMatrix()); + + PxMat44 eyeTransform = view.inverseRT(); + eyePos = eyeTransform.getPosition(); + + PxVec3 nearPos = unprojectRH(proj, view, mouseX * 2 - 1, 1 - mouseY * 2); + + pickDir = nearPos - eyePos; + } +#endif + atcore_float3 eye = SimpleScene::Inst()->m_pCamera->GetEye(); + eyePos = PxVec3(eye.x, eye.y, eye.z); + + float x = 0, y = 0, z = 0; + SimpleScene::Inst()->m_pCamera->getWorldCoord(mouseX, mouseY, x, y, z); + + PxVec3 nearPos(x, y, z); + pickDir = nearPos - eyePos; +} /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// @@ -981,12 +1069,28 @@ void PhysXController::ClearOldCOllisions() bool PhysXController::isPlaneVisible() { - return !planeActor_Pri->isHidden(); + if (GlobalSettings::Inst().m_zup) + { + return !planeActor_Pri[1]->isHidden(); + } + else + { + return !planeActor_Pri[0]->isHidden(); + } } void PhysXController::setPlaneVisible(bool bVisible) { - planeActor_Pri->setHidden(!bVisible); + if (GlobalSettings::Inst().m_zup) + { + planeActor_Pri[0]->setHidden(true); + planeActor_Pri[1]->setHidden(!bVisible); + } + else + { + planeActor_Pri[0]->setHidden(!bVisible); + planeActor_Pri[1]->setHidden(true); + } } PxRigidDynamic* PhysXController::createEditPhysXActor(const std::vector<BlastModel::Chunk::Mesh>& meshes, const PxTransform& pos) @@ -1051,4 +1155,38 @@ PxRigidDynamic* PhysXController::createEditPhysXActor(const std::vector<BlastMod m_editPhysicsScene->addActor(*actor); return actor; } + +void PhysXController::setPaused(bool paused) +{ + m_paused = paused; + if (m_paused) + { + return; + } + + if (GlobalSettings::Inst().m_zup) + { + m_physicsScene->removeActor(*planeActor_Pri[0]->getActor()); + m_physicsScene->addActor(*planeActor_Pri[1]->getActor()); + } + else + { + m_physicsScene->removeActor(*planeActor_Pri[1]->getActor()); + m_physicsScene->addActor(*planeActor_Pri[0]->getActor()); + } +} + +void PhysXController::ResetUpDir(bool zup) +{ + setPaused(m_paused); + setPlaneVisible(isPlaneVisible()); + if (zup) + { + m_physicsScene->setGravity(PxVec3(0.0f, 0.0f, -9.81f)); + } + else + { + m_physicsScene->setGravity(PxVec3(0.0f, -9.81f, 0.0f)); + } +} // Add By Lixu End diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/physx/PhysXController.h b/tools/ArtistTools/source/BlastPlugin/SampleBase/physx/PhysXController.h index fc59203..9394adb 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/physx/PhysXController.h +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/physx/PhysXController.h @@ -148,10 +148,8 @@ class PhysXController : public ISampleController return m_paused; } - void setPaused(bool paused) - { - m_paused = paused; - } + void setPaused(bool paused); + void ResetUpDir(bool zup); void setDraggingEnabled(bool enabled); bool getDraggingEnabled() const { return m_draggingEnabled; } diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderable.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderable.cpp index d51101f..b72c3b0 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderable.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderable.cpp @@ -50,6 +50,33 @@ void Renderable::setMaterial(RenderMaterial& material) void Renderable::render(Renderer& renderer, bool depthStencilOnly) const { + if (renderer.bFetchSelection) + { + RenderMaterial::InstancePtr materialInstance = renderer.getSelectionRenderMaterialInstance(); + if (!materialInstance->isValid()) + { + PX_ALWAYS_ASSERT(); + return; + } + + materialInstance->bind(*renderer.m_context, 0); + + // setup object CB + { + D3D11_MAPPED_SUBRESOURCE mappedResource; + renderer.m_context->Map(renderer.m_objectCB, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource); + Renderer::CBObject* objectBuffer = (Renderer::CBObject*)mappedResource.pData; + objectBuffer->worldMatrix = PxMat44ToXMMATRIX(getModelMatrix()); + // use selected to store mUniqueId + objectBuffer->selected = m_mesh.mUniqueId; + renderer.m_context->Unmap(renderer.m_objectCB, 0); + } + + m_mesh.render(*renderer.m_context); + + return; + } + if (!m_materialInstance->isValid()) { PX_ALWAYS_ASSERT(); diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderable.h b/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderable.h index 2d2e37b..129b8f2 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderable.h +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderable.h @@ -50,6 +50,7 @@ public: virtual void render(ID3D11DeviceContext& context) const = 0; // Add By Lixu Begin virtual void setScale(PxMat44 scale, bool replace) {}; + int mUniqueId; // Add By Lixu End }; @@ -62,6 +63,18 @@ class Renderable public: //////// public API //////// + // suppose chunk count is less than 10000 + static int getRenderableId(int familyId, int chunkId) + { + int renderableId = familyId * 10000 + chunkId; + return renderableId; + } + static void getFamilyChunkId(int renderableId, int& familyId, int& chunkId) + { + familyId = renderableId / 10000; + chunkId = renderableId % 10000; + } + void setMaterial(RenderMaterial& material); PxMat44 getModelMatrix() const diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderer.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderer.cpp index 00b3256..05941df 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderer.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderer.cpp @@ -38,6 +38,7 @@ #include "GlobalSettings.h" #include "Light.h" #include "AppMainWindow.h" +#include "PxVec2.h" const float CAMERA_CLIP_NEAR = 1.0f; @@ -45,10 +46,17 @@ const float CAMERA_CLIP_FAR = 1000.00f; const float CLEAR_SCENE_COLOR[4] = { 0.0f, 0.0f, 0.0f, 0.0f }; +const int RenderTarget_Size = 512; +const float SelectionTexture_InitData = -1; /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // Renderer /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +Renderer* g_Renderer = nullptr; +Renderer* Renderer::Inst() +{ + return g_Renderer; +} Renderer::Renderer() @@ -61,11 +69,20 @@ Renderer::Renderer() , m_DSTexture(nullptr) , m_DSView(nullptr) , m_DSTextureSRV(nullptr) +, m_selectionRenderTargetTexture(nullptr) +, m_selectionRenderTargetView(nullptr) +, m_selectionRenderTargetSRV(nullptr) +, m_selectionDepthStencilTexture(nullptr) +, m_selectionDepthStencilView(nullptr) +, m_selectionDepthStencilSRV(nullptr) +, m_selectionTextureForCPU(nullptr) , m_pointSampler(nullptr) , m_linearSampler(nullptr) , m_wireframeMode(false) , m_debugPrimitiveVB(nullptr) , m_debugPrimitiveVBVerticesCount(0) +, m_screenPrimitiveVB(nullptr) +, m_screenPrimitiveVBVerticesCount(0) , m_shadowEnabled(true) , m_HBAOEnabled(true) , m_visibleOpaqueRenderablesCount(0) @@ -83,6 +100,9 @@ Renderer::Renderer() m_RSState[1] = nullptr; toggleCameraSpeed(false); + + g_Renderer = this; + bFetchSelection = false; } Renderer::~Renderer() @@ -252,9 +272,17 @@ void Renderer::DeviceDestroyed() SAFE_RELEASE(m_pointSampler); SAFE_RELEASE(m_linearSampler); SAFE_RELEASE(m_debugPrimitiveVB); + SAFE_RELEASE(m_screenPrimitiveVB); SAFE_RELEASE(m_DSTexture); SAFE_RELEASE(m_DSView); SAFE_RELEASE(m_DSTextureSRV); + SAFE_RELEASE(m_selectionRenderTargetTexture); + SAFE_RELEASE(m_selectionRenderTargetView); + SAFE_RELEASE(m_selectionRenderTargetSRV); + SAFE_RELEASE(m_selectionDepthStencilTexture); + SAFE_RELEASE(m_selectionDepthStencilView); + SAFE_RELEASE(m_selectionDepthStencilSRV); + SAFE_RELEASE(m_selectionTextureForCPU); for (uint32_t i = 0; i < PrimitiveRenderMeshType::Count; i++) { @@ -281,11 +309,40 @@ void Renderer::onInitialize() m_debugPrimitiveRenderMaterialInstance = m_debugPrimitiveRenderMaterial->getMaterialInstance(layout, ARRAYSIZE(layout)); } + + // screen primitive render material and input layout + { + m_screenPrimitiveRenderMaterial = new RenderMaterial("", m_resourceManager, "screen_primitive_ex", ""); + + D3D11_INPUT_ELEMENT_DESC layout[] = { + { "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "COLOR", 0, DXGI_FORMAT_R8G8B8A8_UNORM, 0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0 } + }; + + m_screenPrimitiveRenderMaterialInstance = m_screenPrimitiveRenderMaterial->getMaterialInstance(layout, ARRAYSIZE(layout)); + } + + // selection render material and input layout + { + m_selectionRenderMaterial = new RenderMaterial("idm", m_resourceManager, "model_simple_id_ex", ""); + + D3D11_INPUT_ELEMENT_DESC layout[] = { + { "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "VERTEX_NORMAL", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "FACE_NORMAL", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 24, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "TANGENT", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 36, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT, 0, 48, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "TEXCOORD", 1, DXGI_FORMAT_R32_FLOAT, 1, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 } + }; + + m_selectionRenderMaterialInstance = m_selectionRenderMaterial->getMaterialInstance(layout, ARRAYSIZE(layout)); + } } void Renderer::onTerminate() { SAFE_DELETE(m_debugPrimitiveRenderMaterial); + SAFE_DELETE(m_screenPrimitiveRenderMaterial); } void Renderer::BackBufferResized(ID3D11Device* /*device*/, const DXGI_SURFACE_DESC* sd) @@ -300,6 +357,109 @@ void Renderer::BackBufferResized(ID3D11Device* /*device*/, const DXGI_SURFACE_DE SAFE_RELEASE(m_DSTexture); SAFE_RELEASE(m_DSView); SAFE_RELEASE(m_DSTextureSRV); + SAFE_RELEASE(m_selectionRenderTargetTexture); + SAFE_RELEASE(m_selectionRenderTargetView); + SAFE_RELEASE(m_selectionRenderTargetSRV); + SAFE_RELEASE(m_selectionDepthStencilTexture); + SAFE_RELEASE(m_selectionDepthStencilView); + SAFE_RELEASE(m_selectionDepthStencilSRV); + SAFE_RELEASE(m_selectionTextureForCPU); + + // create m_selectionRenderTargetTexture + { + D3D11_TEXTURE2D_DESC desc; + ZeroMemory(&desc, sizeof(desc)); + desc.Width = RenderTarget_Size; + desc.Height = RenderTarget_Size; + desc.MipLevels = 1; + desc.ArraySize = 1; + desc.Format = DXGI_FORMAT_R32_FLOAT; // Use a typeless type here so that it can be both depth-stencil and shader resource. + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Usage = D3D11_USAGE_DEFAULT; + desc.BindFlags = D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE; + desc.CPUAccessFlags = 0; + desc.MiscFlags = 0; + V(m_device->CreateTexture2D(&desc, NULL, &m_selectionRenderTargetTexture)); + } + + // create m_selectionRenderTargetView + { + D3D11_RENDER_TARGET_VIEW_DESC desc; + ZeroMemory(&desc, sizeof(desc)); + desc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D; + desc.Format = DXGI_FORMAT_R32_FLOAT; // Make the view see this as D32_FLOAT instead of typeless + desc.Texture2D.MipSlice = 0; + V(m_device->CreateRenderTargetView(m_selectionRenderTargetTexture, &desc, &m_selectionRenderTargetView)); + } + + // create m_selectionRenderTargetSRV + { + D3D11_SHADER_RESOURCE_VIEW_DESC desc; + ZeroMemory(&desc, sizeof(desc)); + desc.Format = DXGI_FORMAT_R32_FLOAT; // Make the shaders see this as R32_FLOAT instead of typeless + desc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + desc.Texture2D.MipLevels = 1; + desc.Texture2D.MostDetailedMip = 0; + V(m_device->CreateShaderResourceView(m_selectionRenderTargetTexture, &desc, &m_selectionRenderTargetSRV)); + } + + // create m_selectionDepthStencilTexture + { + D3D11_TEXTURE2D_DESC desc; + ZeroMemory(&desc, sizeof(desc)); + desc.Width = RenderTarget_Size; + desc.Height = RenderTarget_Size; + desc.MipLevels = 1; + desc.ArraySize = 1; + desc.Format = DXGI_FORMAT_R32_TYPELESS; // Use a typeless type here so that it can be both depth-stencil and shader resource. + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Usage = D3D11_USAGE_DEFAULT; + desc.BindFlags = D3D11_BIND_DEPTH_STENCIL | D3D11_BIND_SHADER_RESOURCE; + desc.CPUAccessFlags = 0; + desc.MiscFlags = 0; + V(m_device->CreateTexture2D(&desc, NULL, &m_selectionDepthStencilTexture)); + } + + // create m_selectionDepthStencilView + { + D3D11_DEPTH_STENCIL_VIEW_DESC desc; + ZeroMemory(&desc, sizeof(desc)); + desc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D; + desc.Format = DXGI_FORMAT_D32_FLOAT; // Make the view see this as D32_FLOAT instead of typeless + desc.Texture2D.MipSlice = 0; + V(m_device->CreateDepthStencilView(m_selectionDepthStencilTexture, &desc, &m_selectionDepthStencilView)); + } + + // create m_selectionDepthStencilSRV + { + D3D11_SHADER_RESOURCE_VIEW_DESC desc; + ZeroMemory(&desc, sizeof(desc)); + desc.Format = DXGI_FORMAT_R32_FLOAT; // Make the shaders see this as R32_FLOAT instead of typeless + desc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + desc.Texture2D.MipLevels = 1; + desc.Texture2D.MostDetailedMip = 0; + V(m_device->CreateShaderResourceView(m_selectionDepthStencilTexture, &desc, &m_selectionDepthStencilSRV)); + } + + // create m_selectionTextureForCPU + { + D3D11_TEXTURE2D_DESC desc; + ZeroMemory(&desc, sizeof(desc)); + desc.Width = RenderTarget_Size; + desc.Height = RenderTarget_Size; + desc.MipLevels = 1; + desc.ArraySize = 1; + desc.Format = DXGI_FORMAT_R32_FLOAT; // Use a typeless type here so that it can be both depth-stencil and shader resource. + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Usage = D3D11_USAGE_STAGING; + desc.BindFlags = 0; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.MiscFlags = 0; + V(m_device->CreateTexture2D(&desc, NULL, &m_selectionTextureForCPU)); + } // create a new Depth-Stencil texture { @@ -528,7 +688,10 @@ void Renderer::Render(ID3D11Device* /*device*/, ID3D11DeviceContext* ctx, ID3D11 // draw overline if (globalSettings.m_showWireframe) { - ctx->RSSetState(m_RSState[1]); + if (globalSettings.m_renderStyle != MESH_RENDER_WIREFRAME) + { + ctx->RSSetState(m_RSState[1]); + } // update wireFrameOver { @@ -585,6 +748,11 @@ void Renderer::Render(ID3D11Device* /*device*/, ID3D11DeviceContext* ctx, ID3D11 render(m_queuedRenderBuffers.back()); m_queuedRenderBuffers.pop_back(); } + while (m_screenRenderBuffers.size() > 0) + { + render(m_screenRenderBuffers.back(), true); + m_screenRenderBuffers.pop_back(); + } // Transparency render ctx->OMSetRenderTargets(1, &pRTV, m_DSView); @@ -670,7 +838,7 @@ void Renderer::renderDepthOnly(DirectX::XMMATRIX* viewProjectionSubstitute) } } -void Renderer::render(const PxRenderBuffer* renderBuffer) +void Renderer::render(const PxRenderBuffer* renderBuffer, bool bScreen) { // points uint32_t pointsCount = renderBuffer->getNbPoints(); @@ -702,7 +870,7 @@ void Renderer::render(const PxRenderBuffer* renderBuffer) verts[i * 2 + 1].mColor = lines[i].color1; } - renderDebugPrimitive(verts, linesCount * 2, D3D11_PRIMITIVE_TOPOLOGY_LINELIST); + renderDebugPrimitive(verts, linesCount * 2, D3D11_PRIMITIVE_TOPOLOGY_LINELIST, bScreen); delete[] verts; } @@ -730,11 +898,18 @@ void Renderer::render(const PxRenderBuffer* renderBuffer) // .... } -void Renderer::renderDebugPrimitive(const Renderer::RenderDebugVertex *vertices, uint32_t verticesCount, D3D11_PRIMITIVE_TOPOLOGY topology) +void Renderer::renderDebugPrimitive(const Renderer::RenderDebugVertex *vertices, uint32_t verticesCount, D3D11_PRIMITIVE_TOPOLOGY topology, bool bScreen) { m_context->IASetPrimitiveTopology(topology); - m_debugPrimitiveRenderMaterialInstance->bind(*m_context, 0); + if (bScreen) + { + m_screenPrimitiveRenderMaterialInstance->bind(*m_context, 0); + } + else + { + m_debugPrimitiveRenderMaterialInstance->bind(*m_context, 0); + } D3D11_MAPPED_SUBRESOURCE mappedResource; m_context->Map(m_objectCB, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource); @@ -882,4 +1057,189 @@ void Renderer::UpdateCamera() DirectX::XMVECTORF32 lookAtPt = { pCamera->_at.x, pCamera->_at.y, pCamera->_at.z, 0 }; m_camera.SetViewParams(eyePt, lookAtPt); m_camera.SetProjParams(pCamera->_fov, pCamera->_aspectRatio, pCamera->_znear, pCamera->_zfar); +} + +bool _pointInPolygon(std::vector<PxVec2>& screenPoints, PxVec2& test) +{ + int polySides = screenPoints.size(); + int i, j = polySides - 1; + bool oddNodes = false; + for (i = 0; i < polySides; i++) + { + if ((screenPoints[i].y < test.y && screenPoints[j].y >= test.y + || screenPoints[j].y <test.y && screenPoints[i].y >= test.y) + && (screenPoints[i].x <= test.x || screenPoints[j].x <= test.x)) + { + float temp = (test.y - screenPoints[i].y) / + (screenPoints[j].y - screenPoints[i].y) * + (screenPoints[j].x - screenPoints[i].x); + oddNodes ^= (screenPoints[i].x + temp < test.x); + } + j = i; + } + return oddNodes; +} + +void Renderer::fetchSelection(std::vector<PxVec2>& screenPoints, std::map<int, std::set<int>>& selection) +{ + PROFILER_SCOPED_FUNCTION(); + + selection.clear(); + + int pointSize = screenPoints.size(); + if (pointSize == 0) + { + return; + } + + GlobalSettings& globalSettings = GlobalSettings::Inst(); + if (!globalSettings.m_showGraphicsMesh) + return; + + ID3D11DeviceContext* ctx = m_context; + + // needed matrices + DirectX::XMMATRIX viewMatrix = SimpleScene::Inst()->GetViewMatrix(); + DirectX::XMMATRIX projMatrix = SimpleScene::Inst()->GetProjMatrix(); + DirectX::XMMATRIX projMatrixInv = DirectX::XMMatrixInverse(NULL, projMatrix); + DirectX::XMMATRIX viewProjMatrix = viewMatrix * projMatrix; + + // Fill Camera constant buffer + { + D3D11_MAPPED_SUBRESOURCE mappedResource; + ctx->Map(m_cameraCB, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource); + CBCamera* cameraBuffer = (CBCamera*)mappedResource.pData; + cameraBuffer->viewProjection = viewProjMatrix; + ctx->Unmap(m_cameraCB, 0); + } + + int width = RenderTarget_Size; + int height = RenderTarget_Size; + float init_data = SelectionTexture_InitData; + int dataSize = width * height; + if (m_selectionTextureData.size() != dataSize) + { + m_selectionTextureData.resize(dataSize); + } + std::fill(m_selectionTextureData.begin(), m_selectionTextureData.end(), init_data); + + ctx->OMSetRenderTargets(1, &m_selectionRenderTargetView, m_selectionDepthStencilView); + float ClearColor[4] = { init_data, init_data, init_data, init_data }; + ctx->ClearRenderTargetView(m_selectionRenderTargetView, ClearColor); + ctx->ClearDepthStencilView(m_selectionDepthStencilView, D3D11_CLEAR_DEPTH, 1.0, 0); + D3D11_VIEWPORT vp = { 0.0f, 0.0f, (float)width, (float)height, 0.0f, 1.0f }; + ctx->RSSetViewports(1, &vp); + ctx->RSSetState(m_RSState[0]); + ctx->OMSetDepthStencilState(m_opaqueRenderDSState, 0xFF); + + // set constants buffers + setAllConstantBuffers(ctx); + + bFetchSelection = true; + + // Render renderables + for (auto it = m_renderables.begin(); it != m_renderables.end(); it++) + { + if (!(*it)->isHidden()) + { + (*it)->render(*this); + } + } + + bFetchSelection = false; + + { + ctx->CopyResource(m_selectionTextureForCPU, m_selectionRenderTargetTexture); + D3D11_MAPPED_SUBRESOURCE mapResource; + HRESULT hr = ctx->Map(m_selectionTextureForCPU, 0, D3D11_MAP_READ, NULL, &mapResource); + memcpy(m_selectionTextureData.data(), mapResource.pData, dataSize * sizeof(float)); + ctx->Unmap(m_selectionTextureForCPU, 0); + } + + std::set<int> vids; + if (pointSize == 1) + { + // point selection + int centerX = screenPoints[0].x * width; + int centerY = screenPoints[0].y * height; + + int ds = centerY * width + centerX; + int vid = m_selectionTextureData[ds]; + vids.emplace(vid); + } + else if (pointSize == 2) + { + // rect selection + PxVec2 lefttop = screenPoints[0]; + PxVec2 rightbottom = screenPoints[1]; + int startX = lefttop.x * width; + int startY = lefttop.y * height; + int endX = rightbottom.x * width; + int endY = rightbottom.y * height; + for (int h = startY; h <= endY; h++) + { + for (int w = startX; w <= endX; w++) + { + int ds = h * width + w; + int vid = m_selectionTextureData[ds]; + vids.emplace(vid); + } + } + } + else + { + // draw selection + PxVec2 pMin, pMax; + pMin = pMax = screenPoints[0]; + for (int ps = 1; ps < pointSize; ps++) + { + PxVec2& p = screenPoints[ps]; + if (p.x < pMin.x) + { + pMin.x = p.x; + } + if (p.y < pMin.y) + { + pMin.y = p.y; + } + if (p.x > pMax.x) + { + pMax.x = p.x; + } + if (p.y > pMax.y) + { + pMax.y = p.y; + } + } + int startX = pMin.x * width; + int startY = pMin.y * height; + int endX = pMax.x * width; + int endY = pMax.y * height; + for (int h = startY; h <= endY; h++) + { + for (int w = startX; w <= endX; w++) + { + PxVec2 test(1.0 * w / width, 1.0 * h / height); + bool valid = _pointInPolygon(screenPoints, test); + if (valid) + { + int ds = h * width + w; + int vid = m_selectionTextureData[ds]; + vids.emplace(vid); + } + } + } + } + + int familyId, chunkId; + for (int vid : vids) + { + if (vid < 0) + { + continue; + } + + Renderable::getFamilyChunkId(vid, familyId, chunkId); + selection[familyId].emplace(chunkId); + } }
\ No newline at end of file diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderer.h b/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderer.h index 2142921..eeaf98c 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderer.h +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/renderer/Renderer.h @@ -70,7 +70,9 @@ class Renderer : public ISampleController Renderer(); ~Renderer(); - + static Renderer* Inst(); + bool bFetchSelection; + void fetchSelection(std::vector<PxVec2>& screenPoints, std::map<int, std::set<int>>& selection); //////// public API //////// void reloadShaders(); @@ -109,13 +111,21 @@ class Renderer : public ISampleController return m_screenHeight; } - void queueRenderBuffer(const PxRenderBuffer* buffer) + void queueRenderBuffer(const PxRenderBuffer* buffer, bool bScreen = false) { - m_queuedRenderBuffers.push_back(buffer); + if (bScreen) + { + m_screenRenderBuffers.push_back(buffer); + } + else + { + m_queuedRenderBuffers.push_back(buffer); + } } void clearQueue() { + m_screenRenderBuffers.clear(); m_queuedRenderBuffers.clear(); } @@ -139,6 +149,10 @@ class Renderer : public ISampleController return m_camera; } + RenderMaterial::InstancePtr getSelectionRenderMaterialInstance() + { + return m_selectionRenderMaterialInstance; + } //////// public 'internal' methods //////// @@ -169,9 +183,9 @@ class Renderer : public ISampleController uint32_t mColor; }; - void render(const PxRenderBuffer* renderBuffer); + void render(const PxRenderBuffer* renderBuffer, bool bScreen = false); void render(Renderable* renderable); - void renderDebugPrimitive(const RenderDebugVertex *vertices, uint32_t verticesCount, D3D11_PRIMITIVE_TOPOLOGY topology); + void renderDebugPrimitive(const RenderDebugVertex *vertices, uint32_t verticesCount, D3D11_PRIMITIVE_TOPOLOGY topology, bool bScreen = false); void initializeDefaultRSState(); void setAllConstantBuffers(ID3D11DeviceContext* ctx); void toggleCameraSpeed(bool overspeed); @@ -278,6 +292,25 @@ class Renderer : public ISampleController ID3D11Buffer* m_debugPrimitiveVB; uint32_t m_debugPrimitiveVBVerticesCount; std::vector<const PxRenderBuffer*> m_queuedRenderBuffers; + + // Screen Render + RenderMaterial* m_screenPrimitiveRenderMaterial; + RenderMaterial::InstancePtr m_screenPrimitiveRenderMaterialInstance; + ID3D11Buffer* m_screenPrimitiveVB; + uint32_t m_screenPrimitiveVBVerticesCount; + std::vector<const PxRenderBuffer*> m_screenRenderBuffers; + + // Selection Render Resource + RenderMaterial* m_selectionRenderMaterial; + RenderMaterial::InstancePtr m_selectionRenderMaterialInstance; + ID3D11Texture2D* m_selectionRenderTargetTexture; + ID3D11RenderTargetView* m_selectionRenderTargetView; + ID3D11ShaderResourceView* m_selectionRenderTargetSRV; + ID3D11Texture2D* m_selectionDepthStencilTexture; + ID3D11DepthStencilView* m_selectionDepthStencilView; + ID3D11ShaderResourceView* m_selectionDepthStencilSRV; + ID3D11Texture2D* m_selectionTextureForCPU; + std::vector<float> m_selectionTextureData; }; diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/DamageToolController.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/DamageToolController.cpp index 7f426bd..ecc3cb9 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/DamageToolController.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/DamageToolController.cpp @@ -406,12 +406,8 @@ LRESULT DamageToolController::MsgProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARA if (uMsg == WM_LBUTTONDOWN || uMsg == WM_MOUSEMOVE || uMsg == WM_LBUTTONUP) { - m_lastMousePos.x = (short)LOWORD(lParam) / getRenderer().getScreenWidth(); - if (!SimpleScene::Inst()->m_pCamera->_lhs) - { - m_lastMousePos.x = 1 - m_lastMousePos.x; - } - m_lastMousePos.y = (short)HIWORD(lParam) / getRenderer().getScreenHeight(); + m_lastMousePos.x = (float)LOWORD(lParam); + m_lastMousePos.y = (float)HIWORD(lParam); } if (uMsg == WM_LBUTTONDOWN || uMsg == WM_LBUTTONUP) diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/EditionToolController.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/EditionToolController.cpp index b2533a6..a3a6dd1 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/EditionToolController.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/EditionToolController.cpp @@ -82,8 +82,8 @@ LRESULT EditionToolController::MsgProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPAR if (uMsg == WM_LBUTTONDOWN || uMsg == WM_MOUSEMOVE || uMsg == WM_LBUTTONUP) { - float mouseX = (short)LOWORD(lParam) / getRenderer().getScreenWidth(); - float mouseY = (short)HIWORD(lParam) / getRenderer().getScreenHeight(); + float mouseX = (float)LOWORD(lParam); + float mouseY = (float)HIWORD(lParam); bool press = uMsg == WM_LBUTTONDOWN; if (uMsg == WM_LBUTTONUP) diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/GizmoToolController.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/GizmoToolController.cpp index ea91766..5942b45 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/GizmoToolController.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/GizmoToolController.cpp @@ -552,12 +552,8 @@ LRESULT GizmoToolController::MsgProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM if (uMsg == WM_LBUTTONDOWN || uMsg == WM_MOUSEMOVE || uMsg == WM_LBUTTONUP) { - float mouseX = (short)LOWORD(lParam) / getRenderer().getScreenWidth(); - if (!SimpleScene::Inst()->m_pCamera->_lhs) - { - mouseX = 1 - mouseX; - } - float mouseY = (short)HIWORD(lParam) / getRenderer().getScreenHeight(); + float mouseX = (float)LOWORD(lParam); + float mouseY = (float)HIWORD(lParam); PxVec3 eyePos, pickDir; getPhysXController().getEyePoseAndPickDir(mouseX, mouseY, eyePos, pickDir); diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/SelectionToolController.cpp b/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/SelectionToolController.cpp index 458aec3..4232fe4 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/SelectionToolController.cpp +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/SelectionToolController.cpp @@ -58,7 +58,10 @@ using namespace physx; SelectionToolController::SelectionToolController() { m_bRectSelecting = false; + m_bDrawSelecting = false; m_bSelecting = false; + m_ScreenRenderBuffer.clear(); + m_DrawSelectScreenPos.clear(); BlastSceneTree::ins()->addObserver(this); } @@ -107,9 +110,9 @@ void SelectionToolController::Animate(double dt) { PROFILER_SCOPED_FUNCTION(); - if (m_bRectSelecting) - { - getRenderer().queueRenderBuffer(&m_RectRenderBuffer); + if (m_ScreenRenderBuffer.getNbLines() > 0) + { + getRenderer().queueRenderBuffer(&m_ScreenRenderBuffer, true); } } @@ -121,106 +124,75 @@ LRESULT SelectionToolController::MsgProc(HWND hWnd, UINT uMsg, WPARAM wParam, LP if (uMsg == WM_LBUTTONDOWN || uMsg == WM_RBUTTONDOWN || uMsg == WM_MOUSEMOVE || uMsg == WM_LBUTTONUP || uMsg == WM_RBUTTONUP) { float mouseX = (short)LOWORD(lParam) / getRenderer().getScreenWidth(); - if (!SimpleScene::Inst()->m_pCamera->_lhs) - { - mouseX = 1 - mouseX; - } float mouseY = (short)HIWORD(lParam) / getRenderer().getScreenHeight(); - bool press = uMsg == WM_LBUTTONDOWN; if (uMsg == WM_LBUTTONDOWN || uMsg == WM_RBUTTONDOWN) { - PxVec3 eyePos, pickDir; - getPhysXController().getEyePoseAndPickDir(mouseX, mouseY, eyePos, pickDir); - - m_RectSelectScreenPos.x = mouseX; - m_RectSelectScreenPos.y = mouseY; - m_RectSelectSpaceDir = pickDir.getNormalized(); + m_ScreenRenderBuffer.clear(); - m_RectRenderBuffer.clear(); bool isCtrl = (GetAsyncKeyState(VK_CONTROL) && 0x8000); bool isAlt = (GetAsyncKeyState(VK_MENU) && 0x8000); bool isLight = (GetAsyncKeyState('L') && 0x8000); // ctrl+leftbutton is used for light changing // alt+leftbutton is used for camera rotate movement in AppMainWindow.cpp // so, we use rect select when ctrl and alt off - m_bRectSelecting = !(isAlt || isLight);// !(isCtrl || isAlt); - if (isAlt || isLight) + bool Selecting = !(isAlt || isLight);// !(isCtrl || isAlt); + + if (uMsg == WM_LBUTTONDOWN && !m_bDrawSelecting) { - m_RectRenderBuffer.clear(); + m_RectSelectScreenPos.x = mouseX; + m_RectSelectScreenPos.y = mouseY; + + m_bRectSelecting = Selecting; } - m_bSelecting = true; + else // uMsg == WM_RBUTTONDOWN + { + m_DrawSelectScreenPos.push_back(PxVec2(mouseX, mouseY)); + + m_bDrawSelecting = Selecting; + } + + m_bSelecting = m_bRectSelecting || m_bDrawSelecting; } else if (uMsg == WM_MOUSEMOVE) { if (m_bRectSelecting) { - PxVec3 eyePos, pickDir[3]; - getPhysXController().getEyePoseAndPickDir(mouseX, mouseY, eyePos, pickDir[0]); - getPhysXController().getEyePoseAndPickDir(m_RectSelectScreenPos.x, mouseY, eyePos, pickDir[1]); - getPhysXController().getEyePoseAndPickDir(mouseX, m_RectSelectScreenPos.y, eyePos, pickDir[2]); - pickDir[0] = pickDir[0].getNormalized(); - pickDir[1] = pickDir[1].getNormalized(); - pickDir[2] = pickDir[2].getNormalized(); - - PxVec3 lefttop, leftbottom, righttop, rightbottom; - - if (mouseX > m_RectSelectScreenPos.x) // right + float left, right, top, bottom; + left = right = mouseX; + top = bottom = mouseY; + if (mouseX > m_RectSelectScreenPos.x) { - if (mouseY > m_RectSelectScreenPos.y) // top - { - leftbottom = m_RectSelectSpaceDir; - righttop = pickDir[0]; - lefttop = pickDir[2]; - rightbottom = pickDir[1]; - } - else // bottom - { - leftbottom = pickDir[1]; - righttop = pickDir[2]; - lefttop = m_RectSelectSpaceDir; - rightbottom = pickDir[0]; - } + left = m_RectSelectScreenPos.x; } - else // left + else { - if (mouseY > m_RectSelectScreenPos.y) // top - { - leftbottom = pickDir[2]; - righttop = pickDir[1]; - lefttop = pickDir[0]; - rightbottom = m_RectSelectSpaceDir; - } - else // bottom - { - leftbottom = pickDir[0]; - righttop = m_RectSelectSpaceDir; - lefttop = pickDir[2]; - rightbottom = pickDir[1]; - } + right = m_RectSelectScreenPos.x; + } + if (mouseY > m_RectSelectScreenPos.y) + { + top = m_RectSelectScreenPos.y; + } + else + { + bottom = m_RectSelectScreenPos.y; } - float multiply = 10; // in order to draw line - lefttop = eyePos + lefttop * multiply; - righttop = eyePos + righttop * multiply; - leftbottom = eyePos + leftbottom * multiply; - rightbottom = eyePos + rightbottom * multiply; - - m_RectRenderBuffer.clear(); + m_ScreenRenderBuffer.clear(); + PxVec3 left_top(left, top, 0); + PxVec3 left_bottom(left, bottom, 0); + PxVec3 right_bottom(right, bottom, 0); + PxVec3 right_top(right, top, 0); DirectX::XMFLOAT4 LINE_COLOR(1.0f, 0.0f, 0.0f, 1.0f); - m_RectRenderBuffer.m_lines.push_back(PxDebugLine(lefttop, leftbottom, XMFLOAT4ToU32Color(LINE_COLOR))); - m_RectRenderBuffer.m_lines.push_back(PxDebugLine(lefttop, righttop, XMFLOAT4ToU32Color(LINE_COLOR))); - m_RectRenderBuffer.m_lines.push_back(PxDebugLine(righttop, rightbottom, XMFLOAT4ToU32Color(LINE_COLOR))); - m_RectRenderBuffer.m_lines.push_back(PxDebugLine(leftbottom, rightbottom, XMFLOAT4ToU32Color(LINE_COLOR))); + m_ScreenRenderBuffer.m_lines.push_back(PxDebugLine(left_top, left_bottom, XMFLOAT4ToU32Color(LINE_COLOR))); + m_ScreenRenderBuffer.m_lines.push_back(PxDebugLine(left_bottom, right_bottom, XMFLOAT4ToU32Color(LINE_COLOR))); + m_ScreenRenderBuffer.m_lines.push_back(PxDebugLine(right_bottom, right_top, XMFLOAT4ToU32Color(LINE_COLOR))); + m_ScreenRenderBuffer.m_lines.push_back(PxDebugLine(right_top, left_top, XMFLOAT4ToU32Color(LINE_COLOR))); } } - else if (uMsg == WM_LBUTTONUP || uMsg == WM_RBUTTONUP) + else if (uMsg == WM_LBUTTONUP) { - if (uMsg == WM_RBUTTONUP && m_actorsSelected.size() > 1) - { - return 1; - } bool isAlt = (GetAsyncKeyState(VK_MENU) && 0x8000); bool isLight = (GetAsyncKeyState('L') && 0x8000); if (m_bSelecting && !(isAlt || isLight)) @@ -241,102 +213,124 @@ LRESULT SelectionToolController::MsgProc(HWND hWnd, UINT uMsg, WPARAM wParam, LP { selectMode = SM_SUB; } - int width = getRenderer().getScreenWidth(); - int height = getRenderer().getScreenHeight(); - int deltaX = (mouseX - m_RectSelectScreenPos.x) * width; - int deltaY = (mouseY - m_RectSelectScreenPos.y) * height; - float distance = deltaX * deltaX + deltaY * deltaY; - if (distance < 1) - { - m_bRectSelecting = false; - } + + Renderer* pRenderer = Renderer::Inst(); + std::vector<PxVec2> screenPoints; + std::map<int, std::set<int>> selection; + if (m_bRectSelecting) { - // rect select mode - PxVec3 eyePos, pickDir[3]; - getPhysXController().getEyePoseAndPickDir(mouseX, mouseY, eyePos, pickDir[0]); - getPhysXController().getEyePoseAndPickDir(m_RectSelectScreenPos.x, mouseY, eyePos, pickDir[1]); - getPhysXController().getEyePoseAndPickDir(mouseX, m_RectSelectScreenPos.y, eyePos, pickDir[2]); - pickDir[0] = pickDir[0].getNormalized(); - pickDir[1] = pickDir[1].getNormalized(); - pickDir[2] = pickDir[2].getNormalized(); - - PxVec3 lefttop, leftbottom, righttop, rightbottom; - - if (mouseX > m_RectSelectScreenPos.x) // right + int width = getRenderer().getScreenWidth(); + int height = getRenderer().getScreenHeight(); + int deltaX = (mouseX - m_RectSelectScreenPos.x) * width; + int deltaY = (mouseY - m_RectSelectScreenPos.y) * height; + float distance = deltaX * deltaX + deltaY * deltaY; + if (distance < 1) { - if (mouseY > m_RectSelectScreenPos.y) // top + // point select + screenPoints.push_back(m_RectSelectScreenPos); + } + else + { + // rect select + float left, right, top, bottom; + left = right = mouseX; + top = bottom = mouseY; + if (mouseX > m_RectSelectScreenPos.x) { - leftbottom = m_RectSelectSpaceDir; - righttop = pickDir[0]; - lefttop = pickDir[2]; - rightbottom = pickDir[1]; + left = m_RectSelectScreenPos.x; } - else // bottom + else { - leftbottom = pickDir[1]; - righttop = pickDir[2]; - lefttop = m_RectSelectSpaceDir; - rightbottom = pickDir[0]; + right = m_RectSelectScreenPos.x; } - } - else // left - { - if (mouseY > m_RectSelectScreenPos.y) // top + if (mouseY > m_RectSelectScreenPos.y) { - leftbottom = pickDir[2]; - righttop = pickDir[1]; - lefttop = pickDir[0]; - rightbottom = m_RectSelectSpaceDir; + top = m_RectSelectScreenPos.y; } - else // bottom + else { - leftbottom = pickDir[0]; - righttop = m_RectSelectSpaceDir; - lefttop = pickDir[2]; - rightbottom = pickDir[1]; + bottom = m_RectSelectScreenPos.y; } - } - rectSelect(eyePos, lefttop, leftbottom, righttop, rightbottom, selectMode); + screenPoints.push_back(PxVec2(left, top)); + screenPoints.push_back(PxVec2(right, bottom)); + } } - // point select mode - else + else if(m_bDrawSelecting) { - PxVec3 eyePos, pickDir; - getPhysXController().getEyePoseAndPickDir(mouseX, mouseY, eyePos, pickDir); - pickDir = pickDir.getNormalized(); - - PxRaycastBufferN<32> hits; - - GetPhysXScene().raycast(eyePos, pickDir, PX_MAX_F32, hits, PxHitFlag::eDEFAULT | PxHitFlag::eMESH_MULTIPLE); + // draw select + if (m_DrawSelectScreenPos.size() > 2) + { + screenPoints.swap(m_DrawSelectScreenPos); + } + } - PxU32 nbThouches = hits.getNbTouches(); - const PxRaycastHit* touches = hits.getTouches(); + pRenderer->fetchSelection(screenPoints, selection); - PxRigidActor* actor = NULL; - float fDistance = PX_MAX_F32; - for (PxU32 u = 0; u < nbThouches; ++u) - { - const PxRaycastHit& t = touches[u]; - if (t.shape && getBlastController().isActorVisible(*(t.actor))) + std::set<PxActor*> actors; + PxActor* pActor; + BlastController& blastController = getBlastController(); + for (std::pair<int, std::set<int>> familychunksId : selection) + { + BlastFamily* pBlastFamily = blastController.getFamilyById(familychunksId.first); + std::set<int>& chunkIds = familychunksId.second; + for (int chunkId : chunkIds) + { + pBlastFamily->getPxActorByChunkIndex(chunkId, &pActor); + if (pActor != nullptr) { - if (fDistance > t.distance) - { - fDistance = t.distance; - actor = t.actor; - } + actors.emplace(pActor); } } - - pointSelect(actor, selectMode); } + rangeSelect(actors, selectMode); } - m_RectRenderBuffer.clear(); + m_DrawSelectScreenPos.clear(); + m_ScreenRenderBuffer.clear(); m_bRectSelecting = false; + m_bDrawSelecting = false; m_bSelecting = false; } + else if (uMsg == WM_RBUTTONUP) + { + /* + if (m_actorsSelected.size() > 1) + { + return 1; + } + */ + if (m_bDrawSelecting) + { + m_ScreenRenderBuffer.clear(); + + DirectX::XMFLOAT4 LINE_COLOR(1.0f, 0.0f, 0.0f, 1.0f); + + int size = m_DrawSelectScreenPos.size() - 1; + if (size == 0) + { + return 1; + } + + PxVec3 from(0, 0, 0); + PxVec3 to(0, 0, 0); + for (int i = 0; i < size; i++) + { + from.x = m_DrawSelectScreenPos[i].x; + from.y = m_DrawSelectScreenPos[i].y; + to.x = m_DrawSelectScreenPos[i + 1].x; + to.y = m_DrawSelectScreenPos[i + 1].y; + m_ScreenRenderBuffer.m_lines.push_back( + PxDebugLine(from, to, XMFLOAT4ToU32Color(LINE_COLOR))); + } + // connect tail and head to close + from.x = m_DrawSelectScreenPos[0].x; + from.y = m_DrawSelectScreenPos[0].y; + m_ScreenRenderBuffer.m_lines.push_back( + PxDebugLine(to, from, XMFLOAT4ToU32Color(LINE_COLOR))); + } + } } return 1; @@ -348,100 +342,13 @@ void SelectionToolController::drawUI() void SelectionToolController::pointSelect(PxActor* actor, SelectMode selectMode) { - if (selectMode == SM_RESET) - { - clearSelect(); - - if (NULL != actor) - { - setActorSelected(*actor, true); - m_actorsSelected.emplace(actor); - } - } - else if (selectMode == SM_ADD) - { - if (NULL != actor) - { - setActorSelected(*actor, true); - m_actorsSelected.emplace(actor); - } - } - else if (selectMode == SM_SUB) - { - if (NULL != actor) - { - setActorSelected(*actor, false); - m_actorsSelected.erase(actor); - } - } - - BlastSceneTree::ins()->updateChunkItemSelection(); - trySelectAssetInstanceNode(m_actorsSelected); + std::set<PxActor*> actors; + actors.emplace(actor); + rangeSelect(actors, selectMode); } -#include "PxPhysics.h" -#include "cooking/PxCooking.h" - -class RectSelectionCallback : public PxOverlapCallback +void SelectionToolController::rangeSelect(std::set<PxActor*>& actorsToSelect, SelectMode selectMode) { -public: - RectSelectionCallback(std::set<PxActor*>& actorBuffer) - :m_actorBuffer(actorBuffer), PxOverlapCallback(m_hitBuffer, sizeof(m_hitBuffer) / sizeof(m_hitBuffer[0])) {} - - PxAgain processTouches(const PxOverlapHit* buffer, PxU32 nbHits) - { - for (PxU32 i = 0; i < nbHits; ++i) - { - PxRigidDynamic* rigidDynamic = buffer[i].actor->is<PxRigidDynamic>(); - if (rigidDynamic) - { - m_actorBuffer.insert(rigidDynamic); - } - } - return true; - } - -private: - std::set<PxActor*>& m_actorBuffer; - PxOverlapHit m_hitBuffer[1000]; -}; - -void SelectionToolController::rectSelect(PxVec3 eyePos, PxVec3 lefttop, PxVec3 leftbottom, PxVec3 righttop, PxVec3 rightbottom, SelectMode selectMode) -{ - std::set<PxActor*> actorsToSelect; - - float nearClip = 1; - PxVec3 nearlefttop = lefttop * nearClip; - PxVec3 nearrighttop = righttop * nearClip; - PxVec3 nearleftbottom = leftbottom * nearClip; - PxVec3 nearrightbottom = rightbottom * nearClip; - - float farClip = 1000; - PxVec3 farlefttop = lefttop * farClip; - PxVec3 farrighttop = righttop * farClip; - PxVec3 farleftbottom = leftbottom * farClip; - PxVec3 farrightbottom = rightbottom * farClip; - - PxVec3 vertices[8] = - { - nearlefttop, nearrighttop, nearleftbottom, nearrightbottom, - farlefttop, farrighttop, farleftbottom, farrightbottom - }; - PxConvexMeshDesc convexMeshDesc; - convexMeshDesc.points.count = 8; - convexMeshDesc.points.data = vertices; - convexMeshDesc.points.stride = sizeof(PxVec3); - convexMeshDesc.flags = PxConvexFlag::eCOMPUTE_CONVEX; - PxPhysics& physics = getManager()->getPhysXController().getPhysics(); - PxCooking& cooking = getManager()->getPhysXController().getCooking(); - PxConvexMesh* convexMesh = cooking.createConvexMesh(convexMeshDesc, physics.getPhysicsInsertionCallback()); - if (NULL != convexMesh) - { - RectSelectionCallback overlapCallback(actorsToSelect); - GetPhysXScene().overlap(PxConvexMeshGeometry(convexMesh), PxTransform(eyePos), overlapCallback); - convexMesh->release(); - } - if (selectMode == SM_RESET) { clearSelect(); diff --git a/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/SelectionToolController.h b/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/SelectionToolController.h index 74220e7..d90ae36 100644 --- a/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/SelectionToolController.h +++ b/tools/ArtistTools/source/BlastPlugin/SampleBase/ui/SelectionToolController.h @@ -70,7 +70,7 @@ public: virtual void dataSelected(std::vector<BlastNode*> selections); void pointSelect(PxActor* actor, SelectMode selectMode = SM_RESET); - void rectSelect(PxVec3 eyePos, PxVec3 lefttop, PxVec3 leftbottom, PxVec3 righttop, PxVec3 rightbottom, SelectMode selectMode = SM_RESET); + void rangeSelect(std::set<PxActor*>& actors, SelectMode selectMode = SM_RESET); void clearSelect(); void setTargetActor(PxActor* actor); @@ -108,10 +108,11 @@ private: //////// internal data //////// PxVec2 m_RectSelectScreenPos; - PxVec3 m_RectSelectSpaceDir; bool m_bRectSelecting; + std::vector<PxVec2> m_DrawSelectScreenPos; + bool m_bDrawSelecting; + DebugRenderBuffer m_ScreenRenderBuffer; bool m_bSelecting; - DebugRenderBuffer m_RectRenderBuffer; void setActorSelected(const PxActor& actor, bool selected); std::set<PxActor*> m_actorsSelected; |