From d6480189c1f888055cfec0c3f11a20d829835b62 Mon Sep 17 00:00:00 2001 From: Peter Schaefer Date: Sat, 2 May 2015 10:06:13 +0200 Subject: [PATCH] moved Scale to Model rewrite BBox Kollide --- Weave/Game.cpp | 4 +- Weave/Graphix/GLM.cpp | 8 ++- Weave/Graphix/GLM.h | 5 +- Weave/Graphix/Model/BBox.cpp | 4 +- Weave/Graphix/Model/IMesh.cpp | 29 ++++++--- Weave/Graphix/Model/IMesh.h | 6 +- Weave/Graphix/Model/IMetaMesh.cpp | 39 ++++++++++-- Weave/Graphix/Model/IMetaMesh.h | 7 ++- Weave/Graphix/Model/Model.cpp | 98 +++++++++++++++++++++---------- Weave/Graphix/Model/Model.h | 15 +++-- Weave/Scene/SceneObject.cpp | 7 ++- Weave/Scene/SceneObject.h | 2 +- 12 files changed, 162 insertions(+), 62 deletions(-) diff --git a/Weave/Game.cpp b/Weave/Game.cpp index 912f028..7cc1437 100644 --- a/Weave/Game.cpp +++ b/Weave/Game.cpp @@ -51,7 +51,7 @@ Game::Game() : playing(true) Shader* shader1 = new Shader("basicTexture_VS.hlsl", "lightingTexture_FS.hlsl"); // load LVL - SceneObject* tmp_world = new SceneObject(shader1, scale(3.f * vec3(1.f, .3f, 1.f)), vec4(4.0f, 1.0f, 1.0f, 2.0f), "level_test.dae", "model_levelTest_2D.png"); + SceneObject* tmp_world = new SceneObject(shader1, mat4(1.f), vec4(4.0f, 1.0f, 1.0f, 2.0f), "level_test.dae", "model_levelTest_2D.png", 3.f * vec3(1.f, .3f, 1.f)); tmp_world->ignore = true; current_world->addObject(tmp_world); @@ -67,7 +67,7 @@ Game::Game() : playing(true) //current_world->addObject(new SceneObject(shader1, glm::mat4(1.0f), "Player.dae", "model_player.png")); //current_world->addObject(new SceneObject(shader1, translate(vec3(-3.f, .4f, 0.f))*scale(vec3(3.f)), "cow/cow.dae", "model_cow_2D.jpg")); - current_world->addObject(new SceneObject(shader1, translate(vec3(-3.f, .4f, 0.f))*scale(vec3(.4f)), vec4(3.0f, 0.5f, 0.4f, 1.5f), "duck.dae", "model_duck_2D.png")); + current_world->addObject(new SceneObject(shader1, translate(vec3(-3.f, .4f, 0.f)), vec4(3.0f, 0.5f, 0.4f, 1.5f), "duck.dae", "model_duck_2D.png", vec3(.3f))); } diff --git a/Weave/Graphix/GLM.cpp b/Weave/Graphix/GLM.cpp index 8ee8974..801f0aa 100644 --- a/Weave/Graphix/GLM.cpp +++ b/Weave/Graphix/GLM.cpp @@ -3,4 +3,10 @@ float VektorAbs(const vec3& vek) { return sqrt(vek.x*vek.x + vek.y*vek.y + vek.z*vek.z); -} \ No newline at end of file +} + +mat4 removeScale(const mat4& _mat) +{ + return _mat*(mat4)inverse(transpose((mat3)_mat)*(mat3)_mat); +} + diff --git a/Weave/Graphix/GLM.h b/Weave/Graphix/GLM.h index 46799a9..2f3e470 100644 --- a/Weave/Graphix/GLM.h +++ b/Weave/Graphix/GLM.h @@ -13,10 +13,11 @@ using glm::vec4; using glm::translate; using glm::rotate; -using glm::scale; +//using glm::scale; using glm::perspective; using glm::normalize; using glm::inverse; +using glm::transpose; using glm::dot; using glm::angle; @@ -38,4 +39,6 @@ using glm::max; __declspec(deprecated) float VektorAbs(const vec3& vek); +mat4 removeScale(const mat4& mat); + //#include "matM.h" diff --git a/Weave/Graphix/Model/BBox.cpp b/Weave/Graphix/Model/BBox.cpp index a959685..99dba6d 100644 --- a/Weave/Graphix/Model/BBox.cpp +++ b/Weave/Graphix/Model/BBox.cpp @@ -8,9 +8,7 @@ BBox::BBox() float vertex[] { -.5f, -.5f, -.5f, .5f, -.5f, -.5f, .5f, .5f, -.5f, -.5f, .5f, -.5f, -.5f, -.5f, .5f, .5f, -.5f, .5f, .5f, .5f, .5f, -.5f, .5f, .5f }; - BBmin = vec3(-.5f); - BBmax = vec3(.5f); - updateBB(BBmin, BBmax); + updateBB(vec3(-.5f), vec3(.5f)); //import("skybox.dae", numvertices, numfaces, vertex, uvs, normals, index, 0); diff --git a/Weave/Graphix/Model/IMesh.cpp b/Weave/Graphix/Model/IMesh.cpp index 19edef9..d06493d 100644 --- a/Weave/Graphix/Model/IMesh.cpp +++ b/Weave/Graphix/Model/IMesh.cpp @@ -64,14 +64,17 @@ IMesh::~IMesh() void IMesh::useModelMat(const mat4& _model, Shader* _shader) const { // Model::useModelMat(_model, _shader); - Model::useModelMat(_model * modelMat, _shader); +// Model::useModelMat(_model * modelMat, _shader); + int tmp = _shader->getUniformLocation("uModel"); + if (tmp >= 0) + glUniformMatrix4fv(tmp, 1, GL_FALSE, value_ptr(_model*glm::scale(modelScale)* modelMat)); } -void IMesh::useMaterial(const vec4& _material, Shader* _shader) const -{ - // Model::useMaterial(_material, _shader); - Model::useMaterial(_material, _shader); -} +//void IMesh::useMaterial(const vec4& _material, Shader* _shader) const +//{ +// // Model::useMaterial(_material, _shader); +// Model::useMaterial(_material, _shader); +//} //void IMesh::drawModel(Shader* _shader, Texture* _texture, const mat4& _modelMat) const //{ @@ -150,7 +153,19 @@ bool IMesh::import(const aiMesh* mesh, uint& numvertices, uint& numfaces, float* return true; } -void IMesh::isColliding(int& _overlap, int& _inside, const Model* _model, const mat4& _modelMatThis, const mat4& _modelMatOther) const +void IMesh::isColliding(float& _overlap, float& _inside, const Model* _model, const mat4& _modelMatThis, const mat4& _modelMatOther) const { Model::isColliding(_overlap, _inside, _model, _modelMatThis*modelMat, _modelMatOther); + /* nicht überschneidend also keine weiteren Tests nötig */ + if (_overlap < 0) + return; + + +} + +void IMesh::getBBsp(vec3& _size, vec3& _position) const +{ + Model::getBBsp(_size, _position); + + scaleVec3(_position, modelScale); } \ No newline at end of file diff --git a/Weave/Graphix/Model/IMesh.h b/Weave/Graphix/Model/IMesh.h index 164bc6a..43ee0ac 100644 --- a/Weave/Graphix/Model/IMesh.h +++ b/Weave/Graphix/Model/IMesh.h @@ -20,14 +20,16 @@ public: virtual ~IMesh(); void useModelMat(const mat4& model, Shader* shader) const; - void useMaterial(const vec4& material, Shader* shader) const; +// void useMaterial(const vec4& material, Shader* shader) const; //void drawModel(Shader* shader, Texture* texture, const mat4& modelMat) const; //void bindShader(Shader* shader); /* calls Colliding to check if self collides with model*/ - virtual void isColliding(int& overlap, int& inside, const Model* model, const mat4& modelMatThis, const mat4& modelMatOther) const; + virtual void isColliding(float& overlap, float& inside, const Model* model, const mat4& modelMatThis, const mat4& modelMatOther) const; + + void getBBsp(vec3& size, vec3& pos) const; protected: diff --git a/Weave/Graphix/Model/IMetaMesh.cpp b/Weave/Graphix/Model/IMetaMesh.cpp index 552cc76..8515171 100644 --- a/Weave/Graphix/Model/IMetaMesh.cpp +++ b/Weave/Graphix/Model/IMetaMesh.cpp @@ -24,7 +24,7 @@ IMetaMesh::IMetaMesh(const string& _modelpath) aiMatrix4x4* aimat; mat4 tmpModelMat; - vec3 tmpMin, tmpMax; + vec3 BBmin, BBmax, tmpMin, tmpMax; if (scene->HasMeshes())// && scene->mNumMeshes > mindex) { aimat = &(root->mChildren[0]->mTransformation); @@ -34,7 +34,7 @@ IMetaMesh::IMetaMesh(const string& _modelpath) IMesh* tmpIMesh = new IMesh(scene->mMeshes[0], tmpModelMat); models.push_back(tmpIMesh); tmpIMesh->getBBmm(BBmin, BBmax); - + for (uint i = 1; i < scene->mNumMeshes; i++) { aimat = &(root->mChildren[i]->mTransformation); @@ -99,14 +99,14 @@ void IMetaMesh::drawBBox(Shader* _shader, const mat4& _modelMat) const } -void IMetaMesh::isColliding(int& _overlap, int& _inside, const Model* _model, const mat4& _modelMatThis, const mat4& _modelMatOther) const +void IMetaMesh::isColliding(float& _overlap, float& _inside, const Model* _model, const mat4& _modelMatThis, const mat4& _modelMatOther) const { Model::isColliding(_overlap, _inside, _model, _modelMatThis, _modelMatOther); - if (min(_overlap, _inside)>=0) + if (min(_overlap, _inside) >= 0) { _overlap = -1; _inside = -1; - int subOverlap=-1, subInside=-1; + float subOverlap = -1, subInside = -1; for (auto i = models.begin(); i != models.end(); ++i) { _model->isColliding(subOverlap, subInside, *i, _modelMatThis, _modelMatOther); @@ -116,4 +116,33 @@ void IMetaMesh::isColliding(int& _overlap, int& _inside, const Model* _model, co _inside = subInside; } } +} + +void IMetaMesh::scale(const vec3& _scale) +{ + Model::scale(_scale); + for (auto i = models.begin(); i != models.end(); ++i) + { + + (*i)->scale(_scale); + } + +} + +void IMetaMesh::unScale() +{ + Model::unScale(); + for (auto i = models.begin(); i != models.end(); ++i) + { + + (*i)->unScale(); + } + +} + +void IMetaMesh::getBBsp(vec3& _size, vec3& _position) const +{ + Model::getBBsp(_size, _position); + + scaleVec3(_position, modelScale); } \ No newline at end of file diff --git a/Weave/Graphix/Model/IMetaMesh.h b/Weave/Graphix/Model/IMetaMesh.h index cdfa182..0632152 100644 --- a/Weave/Graphix/Model/IMetaMesh.h +++ b/Weave/Graphix/Model/IMetaMesh.h @@ -24,8 +24,13 @@ public: void drawBBox(Shader* shader, const mat4& modelMat) const; + void getBBsp(vec3& size, vec3& pos) const; + /* calls Colliding to check if self collides with model*/ - void isColliding(int& overlap, int& inside, const Model* model, const mat4& modelMatThis, const mat4& modelMatOther) const; + void isColliding(float& overlap, float& inside, const Model* model, const mat4& modelMatThis, const mat4& modelMatOther) const; + + void scale(const vec3& scale); + void unScale(); protected: std::list models; diff --git a/Weave/Graphix/Model/Model.cpp b/Weave/Graphix/Model/Model.cpp index c79aa39..7faa651 100644 --- a/Weave/Graphix/Model/Model.cpp +++ b/Weave/Graphix/Model/Model.cpp @@ -13,12 +13,13 @@ #include "../../Events.h" Model::Model() : - numfaces(0), - numvertices(0), - vertexBuffer(-1), - normalBuffer(-1), - uvBuffer(-1), - indexBuffer(-1) +numfaces(0), +numvertices(0), +vertexBuffer(-1), +normalBuffer(-1), +uvBuffer(-1), +indexBuffer(-1), +modelScale(1.f) { } @@ -74,7 +75,7 @@ void Model::bindShader(Shader* _shader) void Model::drawModel() const { - if(Events::isKToggleActive(SDLK_F3)) + if (Events::isKToggleActive(SDLK_F3)) glDrawElements(GL_LINE_LOOP, numfaces * 3, GL_UNSIGNED_INT, 0); else glDrawElements(GL_TRIANGLES, numfaces * 3, GL_UNSIGNED_INT, 0); @@ -103,9 +104,9 @@ void Model::drawModel(Shader* _shader, Texture* _texture, const mat4& _modelMat, //system("pause"); } -void Model::drawBBox(Shader* _shader,const mat4& _modelMat) const +void Model::drawBBox(Shader* _shader, const mat4& _modelMat) const { - if (BoundingBox==nullptr) + if (BoundingBox == nullptr) { BoundingBox = new BBox(); //BBoxShader = new Shader("basic_FS.hlsl", "basic_VS.hlsl"); @@ -115,12 +116,16 @@ void Model::drawBBox(Shader* _shader,const mat4& _modelMat) const //if (tmp >= 0) // glUniform4fv(Graphix::shader_BBox->getHandle(), 1, value_ptr(vec4(.3f, .9f, .9f, 1.f))); } -// BoundingBox->bindShader(_shader); - BoundingBox->drawModel(Graphix::shader_BBox, (Texture*)nullptr, _modelMat*translate(BBposition)*scale(BBsize), vec4(1.0f, 1.0f, 1.0f, 3.0f)); + // BoundingBox->bindShader(_shader); + vec3 BBsiz, BBpos; + getBBsp(BBsiz, BBpos); + BoundingBox->drawModel(Graphix::shader_BBox, (Texture*)nullptr, _modelMat*translate(BBpos)*glm::scale(BBsiz), vec4(1.0f, 1.0f, 1.0f, 3.0f)); } void Model::updateBB(const vec3& _min, const vec3& _max) { + BBmin = _min; + BBmax = _max; BBsize = _max - _min; BBposition = (_min + _max) / 2.f; } @@ -143,7 +148,7 @@ void Model::updateBB(const uint _numvertices, const float* _vertices) void Model::updateBB(const uint _numvertices, const float* _vertices, const mat4& _modelMat) { - BBmin = (vec3)(_modelMat * vec4(_vertices[0], _vertices[1], _vertices[2],1.f)); + BBmin = (vec3)(_modelMat * vec4(_vertices[0], _vertices[1], _vertices[2], 1.f)); BBmax = BBmin; vec3 tmpVert; for (uint j = 3; j < _numvertices * 3; j += 3) @@ -167,12 +172,17 @@ void Model::getBBmm(vec3& _min, vec3& _max) const { _min = BBmin; _max = BBmax; + + scaleVec3(_min, modelScale); + scaleVec3(_max, modelScale); } void Model::getBBsp(vec3& _size, vec3& _position) const { _size = BBsize; _position = BBposition; + + scaleVec3(_size, modelScale); } @@ -232,7 +242,7 @@ void Model::useModelMat(const mat4& _model, Shader* _shader) const { int tmp = _shader->getUniformLocation("uModel"); if (tmp >= 0) - glUniformMatrix4fv(tmp, 1, GL_FALSE, value_ptr(_model)); + glUniformMatrix4fv(tmp, 1, GL_FALSE, value_ptr(_model*glm::scale(modelScale))); } void Model::useMaterial(const vec4& _material, Shader* _shader) const @@ -243,39 +253,48 @@ void Model::useMaterial(const vec4& _material, Shader* _shader) const } -void Model::isColliding(int& _overlap, int& _inside, const Model* _model,const mat4& _modelMatThis, const mat4& _modelMatOther) const +void Model::isColliding(float& _overlap, float& _inside, const Model* _model, const mat4& _modelMatThis, const mat4& _modelMatOther) const { vec3 posA, sizeA, posB, sizeB; getBBsp(sizeA, posA); _model->getBBsp(sizeB, posB); - posA = posA+(vec3)(_modelMatThis[3]); //transpose sollte eigentlich reichen - posB = posB+(vec3)(_modelMatOther[3]); - - sizeA = rotateSize(sizeA, _modelMatThis); - sizeB = rotateSize(sizeB, _modelMatOther); - - vec3 pDist, sDist; - vec3 overlap, inside; + posA = posA + (vec3)(_modelMatThis[3]); //transpose sollte eigentlich reichen + posB = posB + (vec3)(_modelMatOther[3]); sizeA /= 2; sizeB /= 2; - pDist = posB - posA; - pDist *= sign(pDist); + vec3 sizeAR = rotateSize(sizeA, glm::inverse(_modelMatOther)*_modelMatThis); + vec3 sizeBR = rotateSize(sizeB, glm::inverse(_modelMatThis)*_modelMatOther); + + sizeA = rotateSize(sizeA,_modelMatThis); + sizeB = rotateSize(sizeB,_modelMatOther); - sDist = sizeB - sizeA; - sDist *= sign(sDist); - overlap = (sizeA + sizeB) - pDist; - inside = sDist - pDist; + checkCollideByAxis(_overlap, _inside, 3, value_ptr(posA), value_ptr(posB), value_ptr(sizeA), value_ptr(sizeB)); +} - /* overlapping 1 yes, 0 touch, -1 no*/ - _overlap = (int)sign(glm::min(glm::min(overlap.x, overlap.y), overlap.z)); - /* inside 1 yes, 0 touch, -1 no*/ - _inside = (int)sign(glm::min(glm::min(inside.x, inside.y), inside.z)); +void Model::checkCollideByAxis(float& _overlap, float& _inside, uint dim, const float* posA, const float* posB, const float* sizeA,const float* sizeB) +{ + _overlap = sizeA[0] + sizeB[0] - abs(posA[0] - posB[0]); + _inside = abs(sizeA[0] - sizeB[0]) - abs(posA[0] - posB[0]); + for (uint i = 0; i < dim; ++i) + { + _overlap = min(sizeA[i] + sizeB[i] - abs(posA[i] - posB[i]), _overlap); + if (_inside >= 0) + _inside = min(abs(sizeA[i] - sizeB[i]) - abs(posA[i] - posB[i]), _inside); + if (_overlap < 0) + { + _overlap = -1; + _inside = -1; + return; + } + } + if (_inside < 0) + _inside = -1; } vec3 Model::rotateSize(const vec3& _size, const mat4& _modelMat) @@ -291,6 +310,21 @@ vec3 Model::rotateSize(const vec3& _size, const mat4& _modelMat) return Size; } +void Model::scale(const vec3& _scale) +{ + scaleVec3(modelScale, _scale); +} + +void Model::unScale() +{ + modelScale = vec3(1.f); +} + +void Model::scaleVec3(vec3& _vec, const vec3& _scale) +{ + for (uint i = 0; i < 3; ++i) + _vec[i] *= _scale[i]; +} Model* Model::BoundingBox = nullptr; Shader* Model::BBoxShader = nullptr; diff --git a/Weave/Graphix/Model/Model.h b/Weave/Graphix/Model/Model.h index d5f2df3..034d22c 100644 --- a/Weave/Graphix/Model/Model.h +++ b/Weave/Graphix/Model/Model.h @@ -24,12 +24,15 @@ public: virtual void drawBBox(Shader* shader, const mat4& modelMat) const; /* Get min&max from BBox */ - void getBBmm(vec3& min, vec3& max) const; + virtual void getBBmm(vec3& min, vec3& max) const; /* Get size&position from BBox */ - void getBBsp(vec3& size, vec3& pos) const; + virtual void getBBsp(vec3& size, vec3& pos) const; /* calls Colliding to check if self collides with model*/ - virtual void isColliding(int& overlap, int& inside, const Model* model, const mat4& modelMatThis, const mat4& modelMatOther) const; + virtual void isColliding(float& overlap, float& inside, const Model* model, const mat4& modelMatThis, const mat4& modelMatOther) const; + + virtual void scale(const vec3& scale); + virtual void unScale(); protected: uint numvertices, numfaces; @@ -55,12 +58,14 @@ protected: static bool exBBox; static vec3 rotateSize(const vec3& size, const mat4& modelMat); + static void checkCollideByAxis(float& overlap, float& inside, uint dim, const float* posA, const float* posB, const float* sizeA, const float* sizeB); + static void scaleVec3(vec3& vec, const vec3& scale); - vec3 BBmin, BBmax; + vec3 modelScale; private: + vec3 BBmin, BBmax; vec3 BBsize, BBposition; - }; diff --git a/Weave/Scene/SceneObject.cpp b/Weave/Scene/SceneObject.cpp index 5d11b0e..81cebec 100644 --- a/Weave/Scene/SceneObject.cpp +++ b/Weave/Scene/SceneObject.cpp @@ -20,7 +20,7 @@ using std::string; #define YFALL_SPEED 9.8f -SceneObject::SceneObject(Shader* _shader, const mat4& _modelMat, const vec4& _material, string _modelpath, string texturepath, unsigned int _model_index) : +SceneObject::SceneObject(Shader* _shader, const mat4& _modelMat, const vec4& _material, string _modelpath, string texturepath, const vec3& _scale) : model(nullptr), modelMat(_modelMat), material(_material), @@ -39,7 +39,10 @@ ignore(false) //Graphix::getGlError(); //modelID = _shader->getUniformLocation("modelMat"); if (_modelpath != "") + { model = new IMetaMesh(_modelpath); + model->scale(_scale); + } if (texturepath != "") texture = new Texture(texturepath); @@ -157,7 +160,7 @@ void SceneObject::collisions(SceneObject* _other) if (collision_ignore || _other->collision_ignore) return; - int isOverlaping, isInside; + float isOverlaping, isInside; model->isColliding(isOverlaping,isInside,_other->model,modelMat,_other->modelMat); /* overlapping 1 yes, 0 touch, -1 no*/ /* inside 1 yes, 0 touch, -1 no*/ diff --git a/Weave/Scene/SceneObject.h b/Weave/Scene/SceneObject.h index 80a2309..7ad1338 100644 --- a/Weave/Scene/SceneObject.h +++ b/Weave/Scene/SceneObject.h @@ -18,7 +18,7 @@ class SceneObject public: //SceneObject(Shader* _shader, mat4& model); - SceneObject(Shader* _shader, const mat4& model, const vec4& material, string modelpath, string texturepath, unsigned int model_index=0); + SceneObject(Shader* _shader, const mat4& model, const vec4& material, string modelpath, string texturepath, const vec3& scale=vec3(1.f)); SceneObject(Shader* _shader, const mat4& modelMat, const vec4& material, Model* model, string texturepath); virtual ~SceneObject(); -- 2.47.3