Arches : 100% .

This commit is contained in:
Georges Dupéron 2012-01-20 01:48:21 +01:00
parent b8cc7bd90e
commit 8be65b8703
18 changed files with 128 additions and 74 deletions

View File

@ -103,7 +103,7 @@ Triangle Triangle::offsetNormal(float offset) const {
Triangle Triangle::insetProportionnal(float prop) {
Triangle rTriangle = *this;
//ibc : isobarycentre.
Vertex ibc = Segment(c[TOP],Segment(c[LEFT],c[RIGHT]).center()).at(2./3.);
Vertex ibc = Segment(c[TOP],Segment(c[LEFT],c[RIGHT]).center()).at(2.f/3.f);
prop = prop;
rTriangle[TOP] = Segment(ibc,c[TOP]).at(prop);

View File

@ -9,7 +9,7 @@ public:
float key;
Chose* value;
friend bool operator< (const HeapNode &a, const HeapNode &b) {
return (a.key < b.key || (a.key == b.key && a.value < b.value));
return (a.key < b.key || (a.key >= b.key && a.key <= b.key && a.value < b.value));
}
};

View File

@ -7,10 +7,10 @@ int main(int argc, char* argv[]) {
std::cout << "Initial seed = " << Chose::initialSeed << std::endl;
float size = 200 * 100;
Vertex ne(size, size, 0);
Vertex se(size, 0, 0);
Vertex sw(0, 0, 0);
Vertex nw(0, size, 0);
Vertex ne(+size/2.f, +size/2.f, 0);
Vertex se(+size/2.f, -size/2.f, 0);
Vertex sw(-size/2.f, -size/2.f, 0);
Vertex nw(-size/2.f, +size/2.f, 0);
Chose* c = new QuartierQuad(Quad(ne, se, sw, nw));
c->triangulation();

View File

@ -26,7 +26,7 @@ Arbre::Arbre(Vertex _start, Quad plane) {
Arbre::Arbre(Vertex _start, Angle3D _rotation, float _length, Type _type) : start(_start), rotation(_rotation), length(_length), type(_type) {
addEntropy(start, rotation.h, rotation.l, rotation.u);
addEntropy(length);
addEntropyf(length);
addEntropy((int)(type));
}
@ -36,7 +36,7 @@ bool Arbre::split() {
for (int i = 0; i < nbBranches; i++) {
Vertex bStart = end(floatInRange(seed, 4*i, 0.7f, 0.9f));
Angle3D rot = rotation;
rot = rot.rotateH(Angle::d2r(floatInRange(seed, 4*i+1, 25.f, 37.f) + i*(360.f / (float)nbBranches)));
rot = rot.rotateH(Angle::d2r(floatInRange(seed, 4*i+1, 25.f, 37.f) + (float)i*(360.f / (float)nbBranches)));
rot = rot.rotateU(Angle::d2r(floatInRange(seed, 4*i+2, 35.f, 55.f)));
float len = length * floatInRange(seed, 4*i+3, tauxMax()*2.f/3.f, tauxMax());
addChild(new Arbre(bStart, rot, len, ARBRE));
@ -103,7 +103,7 @@ void Arbre::feuille() {
Vertex startFeuillage = end(1.f);
unsigned int c = Couleurs::feuillage;
if (length < 20 && proba(seed, 12345, 0.04))
if (length < 20 && proba(seed, 12345, 0.04f))
c = Couleurs::pomme;
Quad cFeuillage(startFeuillage +uFeuillage +lFeuillage, startFeuillage -uFeuillage +lFeuillage, startFeuillage -uFeuillage -lFeuillage, startFeuillage +uFeuillage -lFeuillage);

View File

@ -3,7 +3,7 @@
ArcheQuad::ArcheQuad(Quad _c, float _height, float _start, float _end, Type _type) : Chose(), c(_c), height(_height), start(_start), end(_end), type(_type) {
if (type == RANDOM) {
addEntropy(c);
addEntropy(height);
addEntropyf(height);
switch (hash2(seed, 0) % 3) {
case 0: type = OGIVE; break;
case 1: type = BERCEAU; break;
@ -28,8 +28,8 @@ bool ArcheQuad::split() {
void ArcheQuad::triangulation() {
Quad ch = c.offsetNormal(height);
Quad che = c.offsetNormal(f(end) * height * 0.9);
Quad chw = c.offsetNormal(f(start) * height * 0.9);
Quad che = c.offsetNormal(f(end) * height * 0.9f);
Quad chw = c.offsetNormal(f(start) * height * 0.9f);
addGPUQuad(Quad(ch[NW], chw[NW], che[NE], ch[NE]), Couleurs::mur);
addGPUQuad(Quad(ch[SE], che[SE], chw[SW], ch[SW]), Couleurs::mur);
addGPUQuad(Quad(che[SE], che[NE], chw[NW], chw[SW]), Couleurs::mur);

View File

@ -1,13 +1,13 @@
#include "all_includes.hh"
BatimentQuad_::BatimentQuad_(Quad _c, bool _isSub, QuadBool _w)
BatimentQuad::BatimentQuad(Quad _c, bool _isSub, QuadBool _w)
: Chose(), c(_c), isSub(_isSub), w(_w) {
addEntropy(c);
for (int i = 0; i < 4; i++)
addEntropy(w[N+i] ? 0 : 1);
}
bool BatimentQuad_::split() {
bool BatimentQuad::split() {
if (!isSub) {
bordureRouteTrottoir();
} else {
@ -25,7 +25,7 @@ bool BatimentQuad_::split() {
return true;
}
void BatimentQuad_::bordureRouteTrottoir() {
void BatimentQuad::bordureRouteTrottoir() {
Quad qtrottoir = c.insetNESW(Dimensions::largeurRoute);
Quad qinterieur = qtrottoir.insetNESW(Dimensions::largeurTrottoir);
Quad qbatiments = qinterieur.offsetNormal(Dimensions::hauteurTrottoir);
@ -38,13 +38,13 @@ void BatimentQuad_::bordureRouteTrottoir() {
bool anglesAcceptable = c.minAngle() > Angle::d2r(90-60) && c.maxAngle() < Angle::d2r(90+60);
if (anglesAcceptable && proba(seed, 0, 0.95f)) {
addChild(new BatimentQuad_(qbatiments, true));
addChild(new BatimentQuad(qbatiments, true));
} else {
addChild(new TerrainQuad(qbatiments));
}
}
void BatimentQuad_::sousBatiments() {
void BatimentQuad::sousBatiments() {
Quad q = c << c.maxLengthSide();
QuadBool qb = w << c.maxLengthSide();
@ -56,37 +56,31 @@ void BatimentQuad_::sousBatiments() {
if (small && qb[E] && proba(seed, 2, 0.3f)) {
addChild(new TerrainQuad(Quad(q[SE], s, n, q[NE])));
addChild(new BatimentQuad_(Quad(q[NW], n, s, q[SW]), true, QuadBool(qb[W],qb[N],true,qb[S])));
addChild(new BatimentQuad(Quad(q[NW], n, s, q[SW]), true, QuadBool(qb[W],qb[N],true,qb[S])));
} else if (small && qb[W] && proba(seed, 2, 0.5f)) {
addChild(new BatimentQuad_(Quad(q[SE], s, n, q[NE]), true, QuadBool(qb[E],qb[S],true,qb[N])));
addChild(new BatimentQuad(Quad(q[SE], s, n, q[NE]), true, QuadBool(qb[E],qb[S],true,qb[N])));
addChild(new TerrainQuad(Quad(q[NW], n, s, q[SW])));
} else {
addChild(new BatimentQuad_(Quad(q[SE], s, n, q[NE]), true, QuadBool(qb[E],qb[S],false,qb[N])));
addChild(new BatimentQuad_(Quad(q[NW], n, s, q[SW]), true, QuadBool(qb[W],qb[N],false,qb[S])));
addChild(new BatimentQuad(Quad(q[SE], s, n, q[NE]), true, QuadBool(qb[E],qb[S],false,qb[N])));
addChild(new BatimentQuad(Quad(q[NW], n, s, q[SW]), true, QuadBool(qb[W],qb[N],false,qb[S])));
}
}
void BatimentQuad_::etages() {
void BatimentQuad::etages() {
// TODO : indiquer aux bâtiments où est-ce qu'ils peuvent faire des fenêtres.
float randEtages = floatInRange(seed, 0, 0.f, 1.f);
int nbEtages = 1 + (int)(randEtages * randEtages * (Dimensions::maxEtages - 1));
Quad q = c; // c.insetNESW(30)
Quad qh;
for (int i = 0; i < nbEtages; i++) {
if (nbEtages > 1 && i == 0 && w[N] && w[S]) {
float h = floatInRange(seed, 1+i, Dimensions::hauteurEtage*1.4f, Dimensions::hauteurEtage*1.6f);
qh = q.offsetNormal(h);
addChild(new ArcheQuad(q, h));
} else {
qh = q.offsetNormal(floatInRange(seed, 1+i, Dimensions::hauteurEtage*0.9f, Dimensions::hauteurEtage*1.1f));
addChild(new EtageQuad(q, qh, w));
}
qh = q.offsetNormal(floatInRange(seed, 1+i, Dimensions::hauteurEtage*0.9f, Dimensions::hauteurEtage*1.1f));
addChild(new EtageQuad(q, qh, w, i, nbEtages));
q = qh;
}
addChild(new ToitQuad(qh, Dimensions::hauteurToit));
}
void BatimentQuad_::triangulation() {
void BatimentQuad::triangulation() {
if (w[N] || w[E] || w[S] || w[W]) {
Quad ch = c.offsetNormal(Dimensions::hauteurEtage * 2 + Dimensions::hauteurToit);
addGPUQuad(ch, Couleurs::toit);
@ -97,7 +91,7 @@ void BatimentQuad_::triangulation() {
}
}
void BatimentQuad_::getBoundingBoxPoints() {
void BatimentQuad::getBoundingBoxPoints() {
addBBPoints(c, Dimensions::hauteurEtage * 2 + Dimensions::hauteurToit);
}

View File

@ -3,7 +3,7 @@
#include "all_includes.hh"
class BatimentQuad_ : public Chose {
class BatimentQuad : public Chose {
private:
Quad c;
bool isSub;
@ -13,11 +13,11 @@ private:
void etages();
public:
BatimentQuad_(Quad _c, bool _isSub = false, QuadBool _w = QuadBool(true, true, true, true));
BatimentQuad(Quad _c, bool _isSub = false, QuadBool _w = QuadBool(true, true, true, true));
virtual bool split();
virtual void triangulation();
virtual void getBoundingBoxPoints();
BatimentQuad_* isSubdivision(bool val);
BatimentQuad* isSubdivision(bool val);
};
class BatimentTri_ : public Chose {

View File

@ -34,6 +34,9 @@ protected :
inline void addEntropy(unsigned int x1) {
seed = hash2(seed, x1);
}
inline void addEntropyf(float f) {
addEntropy(float2uint(f));
}
inline void addEntropy(unsigned int x1, unsigned int x2) {
addEntropy(x1); addEntropy(x2);
}

View File

@ -2,5 +2,7 @@
const unsigned int Couleurs::fog = mix(cielHaut, cielBas, 0.5);
const float Dimensions::frontFrustum = 1;
const float Dimensions::splitFactor = 5.f;
const float Dimensions::mergeFactor = 6.f;
const float Dimensions::frontFrustum = 1.f;
const float Dimensions::backFrustum = 4000 * 100; // 4km

View File

@ -14,14 +14,14 @@ public:
static unsigned int mix(unsigned int colorA, unsigned int colorB, float mixA) {
float mixB = 1 - mixA;
return rgb(
r(colorA) * mixA + r(colorB) * mixB,
g(colorA) * mixA + g(colorB) * mixB,
b(colorA) * mixA + b(colorB) * mixB
(unsigned char)(r(colorA) * mixA + r(colorB) * mixB),
(unsigned char)(g(colorA) * mixA + g(colorB) * mixB),
(unsigned char)(b(colorA) * mixA + b(colorB) * mixB)
);
};
static const unsigned int mur = 0xF1E3AD;
static const unsigned int plafond = mur;
static const unsigned int plancher = mur;
static const unsigned int plafond = 0xA39E8B;
static const unsigned int plancher = 0xA5A079;
static const unsigned int toit = 0x961618;
static const unsigned int route = 0x363636;
static const unsigned int trottoir = 0x666666;
@ -47,9 +47,8 @@ public:
static const unsigned int minSurfaceSousBatiment = 100 * 100*100; // 100 m²
// Qualité
// TODO : devrait être 5.f et 6.f
static const unsigned int splitFactor = 2.f;
static const unsigned int mergeFactor = 3.f;
static const float splitFactor;
static const float mergeFactor;
static const unsigned int windowWidth = 1024;
static const unsigned int windowHeight = 768;
static const float frontFrustum;

View File

@ -1,6 +1,6 @@
#include "all_includes.hh"
EtageQuad::EtageQuad(Quad _c, Quad _ch, QuadBool _w) : Chose(), c(_c), ch(_ch), w(_w) {
EtageQuad::EtageQuad(Quad _c, Quad _ch, QuadBool _w, int _etage, int _nbEtages) : Chose(), c(_c), ch(_ch), w(_w), etage(_etage), nbEtages(_nbEtages) {
addEntropy(c);
addEntropy(ch);
for (int i = 0; i < 4; i++)
@ -13,20 +13,45 @@ void EtageQuad::getBoundingBoxPoints() {
}
bool EtageQuad::split() {
Quad me = c.insetOpp(E,28);
Quad ms = c.inset(E,28).inset(W,28).insetOpp(S,28);
Quad mw = c.insetOpp(W,28);
Quad mn = c.inset(E,28).inset(W,28).insetOpp(N,28);
Quad meh = ch.insetOpp(E,28);
Quad msh = ch.inset(E,28).inset(W,28).insetOpp(S,28);
Quad mwh = ch.insetOpp(W,28);
Quad mnh = ch.inset(E,28).inset(W,28).insetOpp(N,28);
addChild(new MurQuad(me << 1,meh << 1,w[E]));
addChild(new MurQuad(mw >> 1,mwh >> 1,w[W]));
addChild(new MurQuad(mn,mnh,w[N]));
addChild(new MurQuad(ms >> 2,msh >> 2,w[S]));
if (nbEtages > 1 && etage == 0 && ((w[N] && w[S]) || (w[E] && w[W])) && c.minLengthEW() > 800 && proba(seed, 0, 0.4)) {
Quad q = c << ((w[N] && w[S]) ? 0 : 1);
Quad qh = ch << ((w[N] && w[S]) ? 0 : 1);
Vertex n = (q[NW] + q[NE]) / 2.f;
Vertex s = (q[SE] + q[SW]) / 2.f;
Vertex nh = (qh[NW] + qh[NE]) / 2.f;
Vertex sh = (qh[SE] + qh[SW]) / 2.f;
Quad e = Quad(q[NE], q[SE], s, n).inset(W, 200);
Quad w = Quad(n, s, q[SW], q[NW]).inset(E, 200);
Quad eh = Quad(qh[NE], qh[SE], sh, nh).inset(W, 200);
Quad wh = Quad(nh, sh, qh[SW], qh[NW]).inset(E, 200);
Quad ei = e.insetNESW(28, 28, 28, 0);
Quad wi = w.insetNESW(28, 0, 28, 28);
Quad eih = eh.insetNESW(28, 28, 28, 0);
Quad wih = wh.insetNESW(28, 0, 28, 28);
// TODO : ArcheQuad(q, q);
addChild(new ArcheQuad(Quad(e[NW], e[SW], w[SE], w[NE]), Segment(qh[NE], q[NE]).length()));
// Mur sur e[N], e[E], e[S], w[S], w[W], w[N];
for (int i = 0; i < 3; i++) {
addChild(new MurQuad(Quad(e[NE+i], ei[NE+i], ei[NW+i], e[NW+i]), Quad(eh[NE+i], eih[NE+i], eih[NW+i], eh[NW+i])));
addChild(new MurQuad(Quad(w[SE+i], w[SW+i], wi[SW+i], wi[SE+i]), Quad(wh[SE+i], wh[SW+i], wih[SW+i], wih[SE+i])));
}
} else {
Quad me = c.insetOpp(E,28);
Quad ms = c.inset(E,28).inset(W,28).insetOpp(S,28);
Quad mw = c.insetOpp(W,28);
Quad mn = c.inset(E,28).inset(W,28).insetOpp(N,28);
Quad meh = ch.insetOpp(E,28);
Quad msh = ch.inset(E,28).inset(W,28).insetOpp(S,28);
Quad mwh = ch.insetOpp(W,28);
Quad mnh = ch.inset(E,28).inset(W,28).insetOpp(N,28);
addChild(new MurQuad(me << 1,meh << 1,w[E]));
addChild(new MurQuad(mw >> 1,mwh >> 1,w[W]));
addChild(new MurQuad(mn,mnh,w[N]));
addChild(new MurQuad(ms >> 2,msh >> 2,w[S]));
}
addChild(new PlancherPlafond(c, PlancherPlafond::PLANCHER));
addChild(new PlancherPlafond(ch.offsetNormal(-10), PlancherPlafond::PLAFOND));
return true;
}

View File

@ -9,9 +9,11 @@ class EtageQuad : public Chose {
Quad c;
Quad ch;
QuadBool w;
int etage;
int nbEtages;
public :
EtageQuad(Quad c, Quad ch, QuadBool _w);
EtageQuad(Quad c, Quad ch, QuadBool _w, int _etage, int _nbEtages);
virtual bool split();
virtual void triangulation();
virtual void getBoundingBoxPoints();

View File

@ -14,7 +14,7 @@ void MurQuad::getBoundingBoxPoints() {
void MurQuad::setWindow() {
Quad q = Quad(ch[NE],c[NE],c[NW],ch[NW]);
int lr = (q.length(S) - 120)/2;
float lr = (q.length(S) - 120)/2.f;
Quad wFront = q.insetNESW(40,lr,120,lr);
Quad wBack = wFront.offsetNormal(28);
@ -54,5 +54,21 @@ bool MurQuad::split() {
}
void MurQuad::triangulation() {
addGPUOcto(c, ch, Couleurs::mur);
addGPUFourQuads(c, ch, Couleurs::mur);
}
PlancherPlafond::PlancherPlafond(Quad _c, Type _type) : Chose(), c(_c), type(_type) {
addEntropy(c);
addEntropy((int)type);
}
void PlancherPlafond::triangulation() {
unsigned int clr = Couleurs::plancher;
if (type == PLAFOND)
clr = Couleurs::plafond;
addGPUQuad(c, clr);
}
void PlancherPlafond::getBoundingBoxPoints() {
addBBPoints(c);
}

View File

@ -4,14 +4,14 @@
#include "all_includes.hh"
class MurQuad: public Chose {
private :
private :
Quad c;
Quad ch;
bool window; // Contient une fenêtre ou non.
Quad windowPos;
Quad windowPosh;
public :
public :
MurQuad(Quad c, Quad ch, bool _window=false);
virtual void triangulation();
@ -20,5 +20,21 @@ class MurQuad: public Chose {
void setWindow();
};
class PlancherPlafond: public Chose {
public:
enum Type {
PLANCHER,
PLAFOND
};
private:
Quad c;
Type type;
public:
PlancherPlafond(Quad _c, Type _type);
virtual void triangulation();
virtual void getBoundingBoxPoints();
};
#endif

View File

@ -31,7 +31,7 @@ bool QuartierQuad::split() {
else if (!small)
carre();
else
addChild(new BatimentQuad_(c));
addChild(new BatimentQuad(c));
return true;
}
@ -116,7 +116,7 @@ void QuartierQuad::longueRue() {
addChild(new QuartierQuad(qn));
addChild(new QuartierQuad(qs));
addChild(new BatimentQuad_(Quad(qn[SE], qs[SW], qs[SE], qn[SW]))); // TODO
addChild(new BatimentQuad(Quad(qn[SE], qs[SW], qs[SE], qn[SW]))); // TODO
}
QuartierTri::QuartierTri(Triangle _c) : Chose(), c(_c) {

View File

@ -9,12 +9,12 @@ bool TerrainQuad::split() {
addChild(new TerrainQuad(c, false));
Vertex p[10];
int maxNArbres = std::min(10, (int)(c.surface() / (7.f*7.f*100.f*100.f)));
Vertex p[maxNArbres];
int pi = 0;
int nArbres = hash2(seed, -1) % (maxNArbres + 1);
for (int essai = 0; essai < nArbres * 2 && pi < nArbres; essai++) {
p[pi] = c.insetProportionnal(0.7).randomPoint(seed, essai);
p[pi] = c.insetProportionnal(0.7f).randomPoint(seed, essai);
bool success = true;
for (int j = 0; j < pi; j++) {
if (Segment(p[j], p[pi]).length() < 3 * 100) {

View File

@ -17,9 +17,6 @@ private:
void deuxPoints();
void deuxPointsVerticaux();
void plat();
static const char r = 0xF1;
static const char g = 0xE0;
static const char b = 0xE0;
};
class ToitTri : public Chose {

View File

@ -2,7 +2,7 @@
View::View(Chose* _root)
: root(_root),
camera(Camera(Vertex(2980,1567,16012), 45, 150, 10000, 0.6f)),
camera(Camera(Vertex(0,0,5000), 45, 100, 10000, 0.6f)),
lod(camera.cameraCenter, _root) {
fogColor[0] = Couleurs::r(Couleurs::fog) / 255.f;
@ -49,8 +49,8 @@ void View::initWindow() {
glEnable (GL_FOG);
glFogi (GL_FOG_MODE, GL_LINEAR);
glFogfv (GL_FOG_COLOR, fogColor);
glFogf (GL_FOG_START, Dimensions::backFrustum / sqrt(3) / 2.f);
glFogf (GL_FOG_END, Dimensions::backFrustum / sqrt(3) * 0.9);
glFogf (GL_FOG_START, Dimensions::backFrustum / std::sqrt(3.f) / 2.f);
glFogf (GL_FOG_END, Dimensions::backFrustum / std::sqrt(3.f) * 0.9f);
//glHint (GL_FOG_HINT, GL_NICEST);
}
@ -94,7 +94,7 @@ void View::displayAxes() {
void View::setSkybox() {
//int z = 40000;
float d = Dimensions::backFrustum / std::sqrt(3) * 0.9;
float d = Dimensions::backFrustum / std::sqrt(3.f) * 0.9f;
glDisable(GL_FOG);
glDisable(GL_LIGHTING);
glPushMatrix();