aboutsummaryrefslogtreecommitdiff
path: root/KaplaDemo/samples/sampleViewer3/Fracture/SimScene.cpp
diff options
context:
space:
mode:
authorgit perforce import user <a@b>2016-10-25 12:29:14 -0600
committerSheikh Dawood Abdul Ajees <Sheikh Dawood Abdul Ajees>2016-10-25 18:56:37 -0500
commit3dfe2108cfab31ba3ee5527e217d0d8e99a51162 (patch)
treefa6485c169e50d7415a651bf838f5bcd0fd3bfbd /KaplaDemo/samples/sampleViewer3/Fracture/SimScene.cpp
downloadphysx-3.4-3dfe2108cfab31ba3ee5527e217d0d8e99a51162.tar.xz
physx-3.4-3dfe2108cfab31ba3ee5527e217d0d8e99a51162.zip
Initial commit:
PhysX 3.4.0 Update @ 21294896 APEX 1.4.0 Update @ 21275617 [CL 21300167]
Diffstat (limited to 'KaplaDemo/samples/sampleViewer3/Fracture/SimScene.cpp')
-rw-r--r--KaplaDemo/samples/sampleViewer3/Fracture/SimScene.cpp778
1 files changed, 778 insertions, 0 deletions
diff --git a/KaplaDemo/samples/sampleViewer3/Fracture/SimScene.cpp b/KaplaDemo/samples/sampleViewer3/Fracture/SimScene.cpp
new file mode 100644
index 00000000..a94e02e1
--- /dev/null
+++ b/KaplaDemo/samples/sampleViewer3/Fracture/SimScene.cpp
@@ -0,0 +1,778 @@
+#include "SimScene.h"
+#include <foundation/PxMat44.h>
+#include "PxRigidBodyExt.h"
+
+#include "Actor.h"
+#include "Compound.h"
+#include "Convex.h"
+#include "CompoundCreator.h"
+#include "PolygonTriangulator.h"
+
+#include "SampleViewerScene.h"
+#include "XMLParser.h"
+
+#include <windows.h>
+
+#include <iostream>
+
+using namespace std;
+
+#include <vector>
+#include "TerrainMesh.h"
+#include "IJGWin32/CPPJPEGWrapper.h"
+
+#define USE_CONVEX_RENDERER 1
+#define NUM_NO_SOUND_FRAMES 1
+
+//#define REL_VEL_FRACTURE_THRESHOLD 5.0f
+#define REL_VEL_FRACTURE_THRESHOLD 0.1f
+
+//extern std::vector<Compound*> delCompoundList;
+
+SimScene* SimScene::createSimScene(PxPhysics *pxPhysics, PxCooking *pxCooking, bool isGrbScene, float minConvexSize, PxMaterial* defaultMat, const char *resourcePath)
+{
+ SimScene* s = PX_NEW(SimScene)(pxPhysics,pxCooking,isGrbScene,minConvexSize,defaultMat,resourcePath);
+ s->createSingletons();
+ return s;
+}
+
+void SimScene::createSingletons()
+{
+ mCompoundCreator = PX_NEW(CompoundCreator)(this);
+ mPolygonTriangulator = PX_NEW(PolygonTriangulator)(this);
+ addActor(createActor());
+}
+
+base::Actor* SimScene::createActor()
+{
+ return (base::Actor*)PX_NEW(Actor)(this);
+}
+
+base::Convex* SimScene::createConvex()
+{
+ return (base::Convex*)PX_NEW(Convex)(this);
+}
+
+base::Compound* SimScene::createCompound(PxReal contactOffset, PxReal restOffset)
+{
+ return (base::Compound*)PX_NEW(Compound)(this, contactOffset, restOffset);
+}
+
+SimScene::SimScene(PxPhysics *pxPhysics, PxCooking *pxCooking, bool isGrbScene, float minConvexSize, PxMaterial* defaultMat, const char *resourcePath):
+ base::SimScene(pxPhysics,pxCooking,isGrbScene,minConvexSize,defaultMat,resourcePath)
+{
+ //mParticles = NULL;
+
+ diffuseTexArray = 0;
+ bumpTexArray = 0;
+ specularTexArray = 0;
+ emissiveReflectSpecPowerTexArray = 0;
+
+ create3dTexture();
+}
+
+// --------------------------------------------------------------------------------------------
+SimScene::~SimScene()
+{
+ mShader = NULL;
+ mShaderMat.init();
+
+ if (mRenderBuffers.volTex) glDeleteTextures(1, &mRenderBuffers.volTex);
+ if (mRenderBuffers.VBO) glDeleteBuffersARB(1, &mRenderBuffers.VBO);
+ if (mRenderBuffers.IBO) glDeleteBuffersARB(1, &mRenderBuffers.IBO);
+ if (mRenderBuffers.matTex) glDeleteTextures(1, &mRenderBuffers.matTex);
+}
+
+// --------------------------------------------------------------------------------------------
+void SimScene::clear()
+{
+ base::SimScene::clear();
+}
+
+// --------------------------------------------------------------------------------------------
+void SimScene::postSim(float dt, RegularCell3D* fluidSim)
+{
+ for (int i = 0; i < mActors.size(); i++)
+ {
+ mActors[i]->postSim(dt);
+ }
+
+ mFrameNr++;
+ mNoFractureFrames--;
+ mNoSoundFrames--;
+}
+
+void SimScene::profileBegin(const char* name)
+{
+}
+
+void SimScene::profileEnd(const char* name)
+{
+}
+
+// --------------------------------------------------------------------------------------------
+bool SimScene::addXml(const std::string &path, const std::string &filename, bool ignoreVisualMesh,
+ float scale, const PxTransform &trans,
+ Shader* defaultShader, const ShaderMaterial &defaultMat)
+{
+ XMLParser *p = XMLParser::getInstance();
+ if (!p->open(path + "\\" + filename))
+ return false;
+
+ diffuseTexNames.clear();
+
+ bumpTexNames.clear();
+ specularTexNames.clear();
+ emissiveReflectSpecPowerTexNames.clear();
+
+
+ while (!p->endOfFile()) {
+ if (!p->endOfFile() && p->tagName == "SurfaceMaterials") {
+ p->readNextTag();
+ while (!p->endOfFile() && p->tagName != "SurfaceMaterials") {
+ if (p->tagName == "SurfaceMaterial") {
+ for (int i = 0; i < (int)p->vars.size(); i++) {
+ if (p->vars[i].name == "name") {
+ }
+ else if (p->vars[i].name == "map_Kd") {
+ diffuseTexNames.push_back(path + "\\" + p->vars[i].value);
+
+ string suffix = p->vars[i].value.substr(p->vars[i].value.size()-4);
+ string prefix = p->vars[i].value.substr(0, p->vars[i].value.size()-5);
+
+ bumpTexNames.push_back(path + "\\" + prefix + "n" + suffix);
+ specularTexNames.push_back(path + "\\" + prefix + "s" + suffix);
+ emissiveReflectSpecPowerTexNames.push_back(path + "\\" + prefix + "e" + suffix);
+ }
+ }
+ }
+ p->readNextTag();
+ }
+ p->readNextTag();
+ }
+ else if (!p->endOfFile() && p->tagName == "Compound") {
+ Compound *c = (Compound*)createCompound();
+ if (!c->createFromXml(p, scale, trans, ignoreVisualMesh)) {
+ delete c;
+ return false;
+ }
+
+ addCompound(c);
+ c->setShader(defaultShader, defaultMat);
+ }
+ else
+ p->readNextTag();
+ }
+
+ p->close();
+ loadAndCreateTextureArrays();
+ return true;
+}
+
+// ------------------------- Renderering --------------------------------
+
+GLuint SimScene::loadTextureArray(std::vector<std::string>& names) {
+
+ GLuint texid;
+ glGenTextures(1, &texid);
+ glBindTexture( GL_TEXTURE_2D_ARRAY_EXT, texid);
+
+ glTexParameteri( GL_TEXTURE_2D_ARRAY_EXT, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
+ glTexParameteri( GL_TEXTURE_2D_ARRAY_EXT, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
+ glTexParameteri( GL_TEXTURE_2D_ARRAY_EXT, GL_TEXTURE_WRAP_S, GL_REPEAT);
+ glTexParameteri( GL_TEXTURE_2D_ARRAY_EXT, GL_TEXTURE_WRAP_T, GL_REPEAT);
+ glTexParameteri( GL_TEXTURE_2D_ARRAY_EXT, GL_GENERATE_MIPMAP_SGIS, GL_TRUE);
+
+ class BmpLoaderBuffer : public ::BmpLoaderBuffer, public ::physx::shdfnd::UserAllocated {};
+ class CPPJPEGWrapper : public ::CPPJPEGWrapper, public ::physx::shdfnd::UserAllocated {};
+ BmpLoaderBuffer *bmps;
+ CPPJPEGWrapper *jpgs;
+ bmps = PX_NEW(BmpLoaderBuffer)[names.size()];
+ jpgs = PX_NEW(CPPJPEGWrapper)[names.size()];
+
+ char path[512];
+
+ int w = 0, h = 0, d = 0;
+ for (int i = 0; i < (int)names.size(); i++) {
+
+ if (names[i].size() > 0) {
+ sprintf_s(path, 512, "%s", names[i].c_str());
+ int len = strlen(path);
+
+ int mw = 0, mh = 0;
+ if (strcmp(&path[len-4], ".jpg") == 0) {
+ jpgs[i].LoadJPEG(path, "false");
+
+ mw = jpgs[i].GetWidth();
+ mh = jpgs[i].GetHeight();
+ } else {
+ bmps[i].loadFile(path);
+ mw = bmps[i].mWidth;
+ mh = bmps[i].mHeight;
+ }
+
+ if ((mw != 0) && (mh != 0)) {
+ if ( ((w != 0) && (w != mw)) ||
+ ((h != 0) && (h != mh)) ) {
+ printf("Textures in array need to be same size!\n");
+ }
+ w = mw;
+ h = mh;
+ }
+ }
+ }
+ d = names.size();
+ if (w == 0) {
+ w=h=128;
+
+ }
+ unsigned char* tmpBlack = (unsigned char*)PX_ALLOC(sizeof(unsigned char)*w*h*3,PX_DEBUG_EXP("RT_FRACTURE"));
+ memset(tmpBlack, 0, w*h*3);
+
+ glTexImage3D(GL_TEXTURE_2D_ARRAY_EXT, 0, GL_RGB8, w, h, d, 0, GL_RGB, GL_UNSIGNED_BYTE, NULL);
+ for (int i = 0; i < (int)names.size(); i++) {
+ glTexSubImage3D( GL_TEXTURE_2D_ARRAY_EXT, 0, 0, 0, i, w, h, 1, GL_RGB, GL_UNSIGNED_BYTE, (bmps[i].mRGB) ? bmps[i].mRGB : (
+ jpgs[i].GetData() ? jpgs[i].GetData() : tmpBlack)
+ );
+
+ }
+
+
+ glGenerateMipmapEXT(GL_TEXTURE_2D_ARRAY_EXT);
+
+ PX_FREE(tmpBlack);
+ PX_DELETE_ARRAY(bmps);
+ PX_DELETE_ARRAY(jpgs);
+
+/* names
+ // 2D Texture arrays a loaded just like 3D textures
+ glTexImage3D(GL_TEXTURE_2D_ARRAY_EXT, 0, GL_RGBA8, images[0].getWidth(), images[0].getHeight(), NIMAGES, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
+ for (int i = 0; i < NIMAGES; i++) {
+ glTexSubImage3D( GL_TEXTURE_2D_ARRAY_EXT, 0, 0, 0, i, images[i].getWidth(), images[i].getHeight(), 1, images[i].getFormat(), images[i].getType(), images[i].getLevel(0));
+ }
+*/
+ return texid;
+
+}
+
+void SimScene::loadAndCreateTextureArrays() {
+ diffuseTexArray = loadTextureArray(diffuseTexNames);
+ bumpTexArray = loadTextureArray(bumpTexNames);
+ specularTexArray = loadTextureArray(specularTexNames);
+ emissiveReflectSpecPowerTexArray = loadTextureArray(emissiveReflectSpecPowerTexNames);
+
+}
+
+// --------------------------------------------------------------------------------------------
+#define WIDTH 128
+#define HEIGHT 128
+#define DEPTH 128
+#define BYTES_PER_TEXEL 3
+#define LAYER(r) (WIDTH * HEIGHT * r * BYTES_PER_TEXEL)
+// 2->1 dimension mapping function
+#define TEXEL2(s, t) (BYTES_PER_TEXEL * (s * WIDTH + t))
+// 3->1 dimension mapping function
+#define TEXEL3(s, t, r) (TEXEL2(s, t) + LAYER(r))
+
+// --------------------------------------------------------------------------------------------
+void SimScene::create3dTexture()
+{
+ unsigned char *texels = (unsigned char *)malloc(WIDTH * HEIGHT * DEPTH * BYTES_PER_TEXEL);
+ memset(texels, 0, WIDTH*HEIGHT*DEPTH);
+
+ // each of the following loops defines one layer of our 3d texture, there are 3 unsigned bytes (red, green, blue) for each texel so each iteration sets 3 bytes
+ // the memory pointed to by texels is technically a single dimension (C++ won't allow more than one dimension to be of variable length), the
+ // work around is to use a mapping function like the one above that maps the 3 coordinates onto one dimension
+ // layer 0 occupies the first (width * height * bytes per texel) bytes, followed by layer 1, etc...
+ // define layer 0 as red
+
+// Perlin perlin(8,4,1,91114);
+ unsigned char* tt = texels;
+ float idx = 1.0f / DEPTH;
+ for (int i = 0; i < DEPTH; i++) {
+ for (int j = 0; j < HEIGHT; j++) {
+ for (int k = 0; k < WIDTH; k++) {
+ //float v[3] = {i*idx, j*idx, k*idx};
+ //float val = (perlin.noise3(v)*0.5f + 0.5f)*255.0f;//cos( (perlin.Noise3(i*0.01f,j*0.01f,k*0.01f)*255000 + i*0.)*5.0f)*0.5f+0.5f;//perlin.Noise3(k,j,i)*255.0f;
+ //(cos(perlin.Noise3(k,j,i) + j*0.01f) + 1.0f)*0.5f*255;
+ unsigned char val = rand() % 255;
+ tt[0] = val;
+ tt[1] = val;
+ tt[2] = val;
+ tt+=3;
+ }
+ }
+ }
+
+ // request 1 texture name from OpenGL
+ glGenTextures(1, &mRenderBuffers.volTex);
+ // tell OpenGL we're going to be setting up the texture name it gave us
+ glBindTexture(GL_TEXTURE_3D, mRenderBuffers.volTex);
+ // when this texture needs to be shrunk to fit on small polygons, use linear interpolation of the texels to determine the color
+ glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
+ // when this texture needs to be magnified to fit on a big polygon, use linear interpolation of the texels to determine the color
+ glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
+ // we want the texture to repeat over the S axis, so if we specify coordinates out of range we still get textured.
+ glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_S, GL_REPEAT);
+ // same as above for T axis
+ glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_T, GL_REPEAT);
+ // same as above for R axis
+ glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_R, GL_REPEAT);
+ // this is a 3d texture, level 0 (max detail), GL should store it in RGB8 format, its WIDTHxHEIGHTxDEPTH in size,
+ // it doesnt have a border, we're giving it to GL in RGB format as a series of unsigned bytes, and texels is where the texel data is.
+ glTexImage3D(GL_TEXTURE_3D, 0, GL_RGB8, WIDTH, HEIGHT, DEPTH, 0, GL_RGB, GL_UNSIGNED_BYTE, texels);
+
+ glBindTexture(GL_TEXTURE_3D, 0);
+}
+
+// --------------------------------------------------------------------------------------------
+void SimScene::createRenderBuffers()
+{
+ if (!mRenderBuffers.VBO) {
+ glGenBuffersARB(1, &mRenderBuffers.VBO);
+ }
+ if (!mRenderBuffers.IBO) {
+ glGenBuffersARB(1, &mRenderBuffers.IBO);
+ }
+ if (!mRenderBuffers.matTex) {
+ glGenTextures(1, &mRenderBuffers.matTex);
+ glBindTexture(GL_TEXTURE_2D, mRenderBuffers.matTex);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
+ glBindTexture(GL_TEXTURE_2D, 0);
+
+ }
+
+ // Count number of vertices and indices in convexes
+ // Count number of indices in convexes
+ mRenderBuffers.numConvexes = 0;
+ mRenderBuffers.numVertices = 0;
+ mRenderBuffers.numIndices = 0;
+
+ for (int k = 0; k < (int)mActors.size(); k++)
+ {
+ const shdfnd::Array<base::Compound*>& mCompounds = mActors[k]->getCompounds();
+ for (int i = 0; i < (int)mCompounds.size(); i++) {
+ if (((Compound*)mCompounds[i])->getShader() != mShader)
+ continue;
+ const shdfnd::Array<base::Convex*> &convexes = mCompounds[i]->getConvexes();
+ mRenderBuffers.numConvexes += convexes.size();
+ for (int j = 0; j < (int)convexes.size(); j++) {
+ mRenderBuffers.numVertices += convexes[j]->getVisVertices().size();
+ mRenderBuffers.numIndices += convexes[j]->getVisTriIndices().size();
+ }
+ }
+ }
+
+ if (mRenderBuffers.numVertices == 0 || mRenderBuffers.numIndices == 0)
+ return;
+
+ mRenderBuffers.tmpVertices.resize(mRenderBuffers.numVertices*12);
+ mRenderBuffers.tmpIndices.resize(mRenderBuffers.numIndices);
+ float* vp = &mRenderBuffers.tmpVertices[0];
+ unsigned int* ip = &mRenderBuffers.tmpIndices[0];
+
+ int sumV = 0;
+ // Make cpu copy of VBO and IBO
+
+ int convexNr = 0;
+
+ for (int k = 0; k < (int)mActors.size(); k++)
+ {
+ const shdfnd::Array<base::Compound*>& mCompounds = mActors[k]->getCompounds();
+ for (int i = 0; i < (int)mCompounds.size(); i++) {
+ if (((Compound*)mCompounds[i])->getShader() != mShader)
+ continue;
+
+ const shdfnd::Array<base::Convex*> &convexes = mCompounds[i]->getConvexes();
+ for (int j = 0; j < (int)convexes.size(); j++, convexNr++) {
+ Convex* c = (Convex*)convexes[j];
+ // PxVec3 matOff = c->getMaterialOffset();
+
+ int nv = c->getVisVertices().size();
+ int ni = c->getVisTriIndices().size();
+
+ if (nv > 0) {
+ float* cvp = (float*)&c->getVisVertices()[0]; // float3
+ float* cnp = (float*)&c->getVisNormals()[0]; // float3
+ // float* c3dtp = (float*)&c->getVisVertices()[0]; // float3
+ float* c2dtp = (float*)&c->getVisTexCoords()[0]; // float2
+ float* ctanp = (float*)&c->getVisTangents()[0]; // float3
+
+ int* cip = (int*)&c->getVisTriIndices()[0];
+ for (int k = 0; k < nv; k++) {
+ *(vp++) = *(cvp++);
+ *(vp++) = *(cvp++);
+ *(vp++) = *(cvp++);
+
+ *(vp++) = *(cnp++);
+ *(vp++) = *(cnp++);
+ *(vp++) = *(cnp++);
+
+ *(vp++) = *(ctanp++);
+ *(vp++) = *(ctanp++);
+ *(vp++) = *(ctanp++);
+ *(vp++) = (float)convexNr;
+
+ *(vp++) = *(c2dtp++);
+ *(vp++) = *(c2dtp++);
+
+ }
+ for (int k = 0; k < ni; k++) {
+ *(ip++) = *(cip++) + sumV;
+ }
+ }
+ //memcpy(ip, cip, sizeof(int)*ni);
+ //ip += 3*ni;
+
+ //std::vector<PxVec3> mTriVertices;
+ //std::vector<PxVec3> mTriNormals;
+ //std::vector<int> mTriIndices;
+ //std::vector<float> mTriTexCoords; // 3d + obj nr
+ sumV += nv;
+ }
+ }
+ }
+
+ glBindBufferARB(GL_ARRAY_BUFFER_ARB, mRenderBuffers.VBO);
+ glBufferDataARB(GL_ARRAY_BUFFER_ARB, mRenderBuffers.tmpVertices.size()*sizeof(float), &mRenderBuffers.tmpVertices[0], GL_STATIC_DRAW);
+
+ glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, mRenderBuffers.IBO);
+ glBufferDataARB(GL_ELEMENT_ARRAY_BUFFER_ARB, mRenderBuffers.tmpIndices.size()*sizeof(unsigned int), &mRenderBuffers.tmpIndices[0], GL_STATIC_DRAW);
+
+ glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, 0);
+ glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
+
+ int oldTexSize = mRenderBuffers.texSize;
+ if (mRenderBuffers.texSize == 0) {
+ // First time
+ oldTexSize = 1;
+ mRenderBuffers.texSize = 32;
+ }
+
+ while (1) {
+ int convexesPerRow = mRenderBuffers.texSize / 4;
+ if (convexesPerRow * mRenderBuffers.texSize >= mRenderBuffers.numConvexes) {
+ break;
+ } else {
+ mRenderBuffers.texSize *= 2;
+ }
+ }
+ if (mRenderBuffers.texSize != oldTexSize) {
+ mRenderBuffers.tmpTexCoords.resize(mRenderBuffers.texSize*mRenderBuffers.texSize*4);
+ // Let's allocate texture
+ glBindTexture(GL_TEXTURE_2D, mRenderBuffers.matTex);
+ glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA32F_ARB, mRenderBuffers.texSize, mRenderBuffers.texSize, 0, GL_RGBA, GL_FLOAT, 0);
+ glBindTexture(GL_TEXTURE_2D, 0);
+ }
+
+ mRenderBufferVersion = mSceneVersion;
+
+ //instanceVBOCPU.resize( newSize * 16);
+}
+
+// --------------------------------------------------------------------------------------------
+void SimScene::updateConvexesTex()
+{
+ float* tt = &mRenderBuffers.tmpTexCoords[0];
+
+ for (int k = 0; k < (int)mActors.size(); k++)
+ {
+ const shdfnd::Array<base::Compound*>& mCompounds = mActors[k]->getCompounds();
+ for (int i = 0; i < (int)mCompounds.size(); i++) {
+ if ( ((Compound*)mCompounds[i])->getShader() != mShader)
+ continue;
+
+ const shdfnd::Array<base::Convex*> &convexes = mCompounds[i]->getConvexes();
+ for (int j = 0; j < (int)convexes.size(); j++) {
+ Convex* c = (Convex*)convexes[j];
+
+ PxMat44 pose(convexes[j]->getGlobalPose());
+ float* mp = (float*)pose.front();
+
+ float* ta = tt;
+ for (int k = 0; k < 16; k++) {
+ *(tt++) = *(mp++);
+ }
+ PxVec3 matOff = c->getMaterialOffset();
+ ta[3] = matOff.x;
+ ta[7] = matOff.y;
+ ta[11] = matOff.z;
+ int idFor2DTex = c->getSurfaceMaterialId();
+ int idFor3DTex = 0;
+ const int MAX_3D_TEX = 8;
+ ta[15] = (float)(idFor2DTex*MAX_3D_TEX + idFor3DTex);
+ }
+ }
+ }
+ glBindTexture(GL_TEXTURE_2D, mRenderBuffers.matTex);
+ glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, mRenderBuffers.texSize, mRenderBuffers.texSize,
+ GL_RGBA, GL_FLOAT, &mRenderBuffers.tmpTexCoords[0]);
+ glBindTexture(GL_TEXTURE_2D, 0);
+}
+
+// --------------------------------------------------------------------------------------------
+#ifdef USE_OPTIX
+
+// Updater class for Optix renderer.
+class FractureModelUpdate : public optix_demo::IModelUpdate
+{
+public:
+
+ FractureModelUpdate( shdfnd::Array< Compound* > const& compounds, bool complete_update )
+ : m_compounds(compounds), m_is_complete_update( complete_update )
+ {}
+
+ bool isCompleteUpdate() const {return m_is_complete_update;}
+ void to_first();
+ void to_next();
+ bool at_end() const;
+
+ size_t num_vertices() const {return (*m_iconvex)->getVisVertices().size();}
+ size_t num_indices() const {return (*m_iconvex)->getVisTriIndices().size();}
+ float const* vertices() const {return &(*m_iconvex)->getVisVertices()[0].x;}
+ float const* normals() const {return &(*m_iconvex)->getVisNormals()[0].x;}
+ int const* indices() const {return &(*m_iconvex)->getVisTriIndices()[0];}
+
+ void global_transform( float* rmat3x3, float* translation );
+
+private:
+ void advance();
+ bool is_valid_convex( Convex const* c ) const
+ {
+ return !c->getVisVertices().empty();
+ }
+
+ shdfnd::Array< Compound* > const& m_compounds;
+ bool m_is_complete_update;
+ shdfnd::Array< Compound* >::ConstIterator m_icompound;
+ shdfnd::Array< Convex* >::ConstIterator m_iconvex;
+};
+
+void FractureModelUpdate::to_first()
+{
+ m_icompound = m_compounds.begin();
+ if (m_icompound == m_compounds.end()) return;
+
+ while ((*m_icompound)->getConvexes().empty()) {
+ ++m_icompound;
+ if (m_icompound == m_compounds.end()) return;
+ }
+ m_iconvex = (*m_icompound)->getConvexes().begin();
+ while (!is_valid_convex(*m_iconvex)) {
+ advance();
+ if (m_icompound == m_compounds.end()) return;
+ }
+}
+
+void FractureModelUpdate::to_next()
+{
+ if (m_icompound != m_compounds.end()) {
+ do {
+ advance();
+ } while (m_icompound != m_compounds.end() && !is_valid_convex(*m_iconvex));
+ }
+}
+
+void FractureModelUpdate::advance()
+{
+ if (m_iconvex != (*m_icompound)->getConvexes().end()) {
+ ++m_iconvex;
+ }
+ if (m_iconvex == (*m_icompound)->getConvexes().end()) {
+ // End of convexes of this compound.
+ do {
+ ++m_icompound;
+ if (m_icompound == m_compounds.end()) return;
+ } while ((*m_icompound)->getConvexes().empty());
+ m_iconvex = (*m_icompound)->getConvexes().begin();
+ }
+}
+
+bool FractureModelUpdate::at_end() const
+{
+ return m_icompound == m_compounds.end();
+}
+
+void FractureModelUpdate::global_transform( float* rmat3x3, float* translation )
+{
+ PxTransform pose = (*m_iconvex)->getGlobalPose();
+ PxMat33 rot(pose.q);
+ rmat3x3[0] = rot.column0.x; rmat3x3[1] = rot.column1.x; rmat3x3[2] = rot.column2.x;
+ rmat3x3[3] = rot.column0.y; rmat3x3[4] = rot.column1.y; rmat3x3[5] = rot.column2.y;
+ rmat3x3[6] = rot.column0.z; rmat3x3[7] = rot.column1.z; rmat3x3[8] = rot.column2.z;
+ translation[0] = pose.p.x;
+ translation[1] = pose.p.y;
+ translation[2] = pose.p.z;
+}
+
+#endif //USE_OPTIX
+
+extern bool gConvexTexOutdate;
+
+// --------------------------------------------------------------------------------------------
+void SimScene::draw(bool useShader)
+{
+ if (mDebugDraw) {
+ for (int k = 0; k < (int)mActors.size(); k++)
+ {
+ const shdfnd::Array<base::Compound*>& mCompounds = mActors[k]->getCompounds();
+ for (int i = 0; i < (int)mCompounds.size(); i++)
+ mCompounds[i]->draw(false, true);
+ }
+ return;
+ }
+
+ int numCompounds = 0;
+ for (int k = 0; k < (int)mActors.size(); k++)
+ {
+ const shdfnd::Array<base::Compound*>& mCompounds = mActors[k]->getCompounds();
+ numCompounds += mCompounds.size();
+ }
+ if (numCompounds == 0) return;
+
+
+ if (SampleViewerScene::getRenderType() == SampleViewerScene::rtOPENGL) {
+#if USE_CONVEX_RENDERER
+ mConvexRenderer.setShaderMaterial(mShader, mShaderMat);
+ mConvexRenderer.setTexArrays(diffuseTexArray, bumpTexArray,
+ specularTexArray, emissiveReflectSpecPowerTexArray);
+ mConvexRenderer.setVolTex(mRenderBuffers.volTex);
+ mConvexRenderer.render();
+#else
+ mConvexRenderer.setActive(false);
+
+ if (mRenderBufferVersion != mSceneVersion)
+ createRenderBuffers();
+
+ if (mRenderBuffers.numIndices > 0) {
+
+ if (gConvexTexOutdate) {
+ updateConvexesTex();
+ gConvexTexOutdate = false;
+ }
+
+ mShader->activate(mShaderMat);
+ // Assume convex all use the same shader
+
+ glActiveTexture(GL_TEXTURE7);
+ glBindTexture(GL_TEXTURE_3D, mRenderBuffers.volTex);
+
+ glActiveTexture(GL_TEXTURE8);
+ glBindTexture(GL_TEXTURE_2D, mRenderBuffers.matTex);
+
+
+
+ glActiveTexture(GL_TEXTURE10);
+ glBindTexture(GL_TEXTURE_2D_ARRAY_EXT, diffuseTexArray);
+ glActiveTexture(GL_TEXTURE11);
+ glBindTexture(GL_TEXTURE_2D_ARRAY_EXT, bumpTexArray);
+ glActiveTexture(GL_TEXTURE12);
+ glBindTexture(GL_TEXTURE_2D_ARRAY_EXT, specularTexArray);
+ glActiveTexture(GL_TEXTURE13);
+ glBindTexture(GL_TEXTURE_2D_ARRAY_EXT, emissiveReflectSpecPowerTexArray);
+
+ glActiveTexture(GL_TEXTURE0);
+
+ float itt = 1.0f/mRenderBuffers.texSize;
+
+ mShader->setUniform("diffuseTexArray", 10);
+ mShader->setUniform("bumpTexArray", 11);
+ mShader->setUniform("specularTexArray", 12);
+ mShader->setUniform("emissiveReflectSpecPowerTexArray", 13);
+
+ mShader->setUniform("ttt3D", 7);
+ mShader->setUniform("transTex", 8);
+ mShader->setUniform("transTexSize", mRenderBuffers.texSize);
+ mShader->setUniform("iTransTexSize", itt);
+ mShader->setUniform("bumpTextureUVScale", bumpTextureUVScale);
+ mShader->setUniform("extraNoiseScale",extraNoiseScale);
+ mShader->setUniform("roughnessScale", roughnessScale);
+ if (mShaderMat.color[3] < 1.0f) {
+ glEnable(GL_BLEND);
+ glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+ glDisable(GL_DEPTH_TEST);
+ glColor4f(mShaderMat.color[0], mShaderMat.color[1], mShaderMat.color[2], mShaderMat.color[3]);
+ }
+
+ glEnableClientState(GL_VERTEX_ARRAY);
+ glEnableClientState(GL_NORMAL_ARRAY);
+ glClientActiveTexture(GL_TEXTURE0);
+ glEnableClientState(GL_TEXTURE_COORD_ARRAY);
+
+ glBindBufferARB(GL_ARRAY_BUFFER_ARB, mRenderBuffers.VBO);
+ glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, mRenderBuffers.IBO);
+
+ int stride = 12*sizeof(float);
+ glVertexPointer(3, GL_FLOAT, stride, 0);
+
+ glNormalPointer(GL_FLOAT, stride, (void*)(3*sizeof(float)));
+
+ glTexCoordPointer(4, GL_FLOAT, stride, (void*)(6*sizeof(float)));
+
+ glClientActiveTexture(GL_TEXTURE1);
+ glTexCoordPointer(2, GL_FLOAT, stride, (void*)(10*sizeof(float)));
+ glEnableClientState(GL_TEXTURE_COORD_ARRAY);
+
+ glDrawElements(GL_TRIANGLES, mRenderBuffers.numIndices, GL_UNSIGNED_INT, 0);
+
+ glDisableClientState(GL_TEXTURE_COORD_ARRAY);
+ glClientActiveTexture(GL_TEXTURE0);
+ glDisableClientState(GL_TEXTURE_COORD_ARRAY);
+ glDisableClientState(GL_VERTEX_ARRAY);
+ glDisableClientState(GL_NORMAL_ARRAY);
+ glBindBufferARB(GL_ARRAY_BUFFER_ARB, 0);
+ glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, 0);
+
+ if (mShaderMat.color[3] < 1.0f) {
+ glDisable(GL_BLEND);
+ glEnable(GL_DEPTH_TEST);
+ }
+
+ mShader->deactivate();
+ }
+#endif
+ }
+#ifdef USE_OPTIX
+ else if (SampleViewerScene::getRenderType() == SampleViewerScene::rtOPTIX) {
+
+ FractureModelUpdate update( mCompounds, mOptixBufferVersion != mSceneVersion );
+
+ if (mOptixBufferVersion != mSceneVersion) {
+ // Complete buffer update.
+ mOptixBufferVersion = mSceneVersion;
+ }
+
+ Profiler::getInstance()->begin("Optix data update");
+
+ SampleViewerScene::getOptixRenderer()->update( update );
+
+ OptixRenderer::Camera cam;
+ const size_t size_of_float3 = sizeof(float) * 3;
+ PxVec3 lookat = mCameraPos + mCameraDir;
+ memcpy( cam.eye, &mCameraPos.x, size_of_float3);
+ memcpy( cam.lookat, &lookat.x, size_of_float3);
+ memcpy( cam.up, &mCameraUp.x, size_of_float3);
+ cam.fov = mCameraFov;
+ Profiler::getInstance()->end("Optix data update");
+
+ Profiler::getInstance()->begin("Optix render");
+ SampleViewerScene::getOptixRenderer()->render( cam );
+ Profiler::getInstance()->end("Optix render");
+ }
+#endif // USE_OPTIX
+
+}
+
+
+// --------------------------------------------------------------------------------------------
+void SimScene::dumpSceneGeometry()
+{
+#ifdef USE_OPTIX
+ if( SampleViewerScene::getRenderType() == SampleViewerScene::rtOPTIX && SampleViewerScene::getOptixRenderer()) {
+ SampleViewerScene::getOptixRenderer()->dump_geometry();
+ }
+#endif
+}