improved 3d rendering, minor changes

added support for thick 3d walls
This commit is contained in:
2017-08-02 14:30:01 +02:00
parent 6f06984c4e
commit 29d5ce19ff
10 changed files with 234 additions and 18 deletions

View File

@@ -19,6 +19,9 @@ public:
/** repaint me */
virtual void paintGL() = 0;
/** is this a transparent element? */
virtual bool isTransparent() const = 0;
};

View File

@@ -30,6 +30,10 @@ protected:
}
bool isTransparent() const override {
return false;
}
};
#endif // MV3DELEMENTACCESSPOINT_H

View File

@@ -31,6 +31,11 @@ protected:
}
bool isTransparent() const override {
return false;
}
};
#endif // MV3DELEMENTFINGERPRINTLOCATION_H

View File

@@ -4,8 +4,9 @@
#include <Indoor/floorplan/v2/Floorplan.h>
#include <Indoor/math/Math.h>
#include "misc/Cube.h"
#include "MV3DElement.h"
#include "misc/Plane.h"
//#include "misc/Plane.h"
@@ -24,12 +25,43 @@ public:
/** repaint me */
void paintGL() override {
glColor3f(0.4, 0.4, 0.4);
Plane p(fo->from, fo->to, f->atHeight, fo->height);
p.paintGL();
const Point2 from = fo->from;
const Point2 to = fo->to;
const float atHeight = f->atHeight;
const float height = fo->height;
const float thickness_m = 0.05; // 5cm door
const float rad = std::atan2(to.y - from.y, to.x - from.x);
const float deg = rad * 180 / M_PI;
const Point2 cen2 = (from+to)/2;
const Point3 pos(cen2.x, cen2.y, atHeight + height/2);
// div by 2.01 to prevent overlapps and z-fi
const float sx = from.getDistance(to) / 2.01f;
const float sy = thickness_m / 2.01f;
const float sz = height / 2.01f; // prevent overlaps
const Point3 size(sx, sy, sz);
const Point3 rot(0,0,deg);
// fill color
glColor3f(0.395, 0.263, 0.129);
// build
Cube cube(pos, size, rot);
cube.paintGL();
//glColor3f(0.4, 0.4, 0.4);
//Plane p(fo->from, fo->to, f->atHeight, fo->height);
//p.paintGL();
}
bool isTransparent() const override {
return false;
}
};
#endif // MV3DELEMENTFLOOROBSTACLEDOOR_H

View File

@@ -4,6 +4,7 @@
#include <Indoor/floorplan/v2/Floorplan.h>
#include <Indoor/math/Math.h>
#include "misc/Cube.h"
#include "MV3DElement.h"
@@ -28,17 +29,93 @@ protected:
Point2 from;
Point2 to;
float thickness_m;
Floorplan::Material mat;
float atHeight;
float height;
Wall(const Point2 from, const Point2 to, float atHeight, float height) :
from(from), to(to), atHeight(atHeight), height(height) {;}
Wall(const Point2 from, const Point2 to, const float thickness_m, const Floorplan::Material mat, float atHeight, float height) :
from(from), to(to), thickness_m(thickness_m), mat(mat), atHeight(atHeight), height(height) {;}
void paintGL() {
const float rad = std::atan2(to.y - from.y, to.x - from.x);
const float deg = rad * 180 / M_PI;
//const Point2 dir = (to - from).normalized();
//const Point2 dirPerp = dir.perpendicular();
//const float w = 0.1;
const Point2 cen2 = (from+to)/2;
const Point3 pos(cen2.x, cen2.y, atHeight + height/2);
// div by 2.01 to prevent overlapps and z-fi
const float sx = from.getDistance(to) / 2.01f;
const float sy = thickness_m / 2.01f;
const float sz = height / 2.01f; // prevent overlaps
const Point3 size(sx, sy, sz);
const Point3 rot(0,0,deg);
// fill color
if (mat == Floorplan::Material::CONCRETE) {
glColor3f(0.5, 0.5, 0.5);
} else {
glColor3f(0.75, 0.75, 0.75);
}
// build
Cube cube(pos, size, rot);
cube.paintGL();
/*
float y1 = atHeight;
float y2 = atHeight + height;
const Point2 p01 = from + dirPerp * w;
const Point2 p02 = from - dirPerp * w;
const Point2 p03 = to - dirPerp * w;
const Point2 p04 = to + dirPerp * w;
// fill the wall
if (mat == Floorplan::Material::CONCRETE) {
glColor3f(0.5, 0.5, 0.5);
} else {
glColor3f(0.75, 0.75, 0.75);
}
auto renderQuad = [&] (const Point2 p1, const Point2 p2) {
glVertex3f(p1.x, y1, p1.y);
glVertex3f(p2.x, y1, p2.y);
glVertex3f(p2.x, y2, p2.y);
glVertex3f(p1.x, y2, p1.y);
};
glDisable(GL_CULL_FACE);
glBegin(GL_QUADS);
//glNormal3f(n.x, n.y, n.z);
// short
renderQuad(p01, p02);
renderQuad(p03, p04);
// long
renderQuad(p02, p03);
renderQuad(p04, p01);
//glVertex3f(p1.x, p1.y, p1.z);
//glVertex3f(p2.x, p2.y, p2.z);
//glVertex3f(p3.x, p3.y, p3.z);
//glVertex3f(p4.x, p4.y, p4.z);
glEnd();
glBegin(GL_CULL_FACE);
*/
/*
// polygon edges
Point3 p1 = Point3(from.x, y1, from.y);
Point3 p2 = Point3(to.x, y1, to.y);
@@ -56,8 +133,8 @@ protected:
Point3 view(99,99,99);
if ((view-n).length() > (view+n).length()) {n = -n;}
// fill the wall
glColor3f(0.75, 0.75, 0.75);
glDisable(GL_CULL_FACE);
glBegin(GL_QUADS);
glNormal3f(n.x, n.y, n.z);
@@ -68,6 +145,54 @@ protected:
glEnd();
glEnable(GL_CULL_FACE);
*/
}
};
struct Window {
Point2 from;
Point2 to;
float atHeight;
float height;
Window(const Point2 from, const Point2 to, float atHeight, float height) :
from(from), to(to), atHeight(atHeight), height(height) {;}
void paintGL() {
float y1 = atHeight;
float y2 = atHeight + height;
// polygon edges
Point3 p1 = Point3(from.x, y1, from.y);
Point3 p2 = Point3(to.x, y1, to.y);
Point3 p3 = Point3(to.x, y2, to.y);
Point3 p4 = Point3(from.x, y2, from.y);
// calculate normal
Point3 n = Math::normal(p2-p1, p3-p1);
// align normals to virtual viewport
Point3 view(99,99,99);
if ((view-n).length() > (view+n).length()) {n = -n;}
glColor4f(0.75, 0.85, 1.0, 0.35);
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glDisable(GL_CULL_FACE);
glBegin(GL_QUADS);
glNormal3f(n.x, n.y, n.z);
glVertex3f(p1.x, p1.y, p1.z);
glVertex3f(p2.x, p2.y, p2.z);
glVertex3f(p3.x, p3.y, p3.z);
glVertex3f(p4.x, p4.y, p4.z);
glEnd();
glEnable(GL_CULL_FACE);
glDisable(GL_BLEND);
}
};
@@ -97,7 +222,7 @@ protected:
glDisable(GL_LIGHTING);
glBegin(GL_LINES);
glColor3f(1,1,1);
glColor3f(0.9, 0.9, 0.9);
// top
glVertex3f(p3.x, p3.y, p3.z);
@@ -134,13 +259,14 @@ protected:
/** repaint me */
void paintGL() override {
if (fo->material == Floorplan::Material::GLASS) {
Window win(fo->from, fo->to, f->atHeight, f->height);
win.paintGL();
} else if (fo->type == Floorplan::ObstacleType::WALL) {
if (fo->type == Floorplan::ObstacleType::WALL) {
Wall wall(fo->from, fo->to, f->atHeight, f->height);
Wall wall(fo->from, fo->to, fo->thickness_m, fo->material, f->atHeight, f->height);
wall.paintGL();
} else if (fo->type == Floorplan::ObstacleType::HANDRAIL) {
@@ -152,6 +278,11 @@ protected:
}
bool isTransparent() const override {
return fo->material == Floorplan::Material::GLASS;
}
};
#endif // MV3DELEMENTFLOOROBSTACLEWALL_H

View File

@@ -118,6 +118,9 @@ protected:
}
bool isTransparent() const override {
return false;
}
};

View File

@@ -29,6 +29,10 @@ protected:
}
bool isTransparent() const override {
return false;
}
};
#endif // MV3DELEMENTREGISTRATIONPOINT_H

View File

@@ -57,6 +57,10 @@ protected:
}
bool isTransparent() const override {
return false;
}
};
#endif // MV3DELEMENTSTAIR_H

View File

@@ -212,8 +212,21 @@ void MapView3D::draw() {
} else {
std::vector<MapModelElement*> elements = getModel()->getVisibleElements();
// order: transparent last
auto func = [] (const MapModelElement* e1, const MapModelElement* e2) {
if (e1->getMV3D() == nullptr) {return false;}
if (e2->getMV3D() == nullptr) {return true;}
const bool e1t = e1->getMV3D()->isTransparent();
const bool e2t = e2->getMV3D()->isTransparent();
return e1t < e2t;
};
std::sort(elements.begin(), elements.end(), func);
// show floorplan
for (MapModelElement* el : getModel()->getVisibleElements()) {
for (MapModelElement* el : elements) {
if (el->getMV3D()) {el->getMV3D()->paintGL();}
}

View File

@@ -9,21 +9,38 @@ class Cube {
private:
Point3 pos;
float size;
Point3 size;
Point3 rot;
public:
Cube(Point3 pos, float size) : pos(pos), size(size) {
Cube(Point3 pos, float size) : pos(pos), size(size,size,size), rot(0,0,0) {
}
Cube(Point3 pos, Point3 size, Point3 rot) : pos(pos), size(size), rot(rot) {
}
void paintGL() {
float s = size;
float s = 1;
glPushMatrix();
glTranslatef(pos.x, pos.z, pos.y);
// 3) move to destination
glTranslatef(pos.x, pos.z, pos.y); // swap yz
// 2) rotate
glRotatef(rot.x, 1, 0, 0);
glRotatef(rot.y, 0, 0, 1); // swap yz
glRotatef(rot.z, 0, 1, 0);
// 1) scale
glScalef(size.x, size.z, size.y); // swap yz
glBegin(GL_QUADS);