commit 0f0a6aa6c02c42898dc193083c1555b455ac1eda
parent 973cf6cb773411eafd74c7f7eecf8bb34103ea68
Author: Georges Dupéron <jahvascriptmaniac+github@free.fr>
Date: Sun, 6 Nov 2011 00:28:58 +0100
Une première règle presque finie (pour la géométrie).
Diffstat:
| M | hash.cpp | | | 7 | ++++++- |
| M | hash.h | | | 3 | ++- |
| M | rules.cpp | | | 111 | +++++++++++++++++++++++++++++++++++++++++++++++++++++++------------------------ |
| M | rules.h | | | 12 | +++++++++--- |
4 files changed, 95 insertions(+), 38 deletions(-)
diff --git a/hash.cpp b/hash.cpp
@@ -1,3 +1,8 @@
+#include <time.h>
+unsigned int random() {
+ return (unsigned int)time((time_t*)0);
+}
+
// Ce hash donne des bons résultats sur tous les bits de l'entier
// généré (pas d'artefacts, répartition homogène des 0 et des 1).
unsigned int hash2(unsigned int a, unsigned int b) {
@@ -17,7 +22,7 @@ unsigned int hash3(unsigned int seed, int x, int y) {
return hash2(seed,hash2(x, y));
}
-int randomInRange(int seed, int n, int a, int b) {
+int hashInRange(int seed, int n, int a, int b) {
return (hash2(seed, n) % (b - a)) + a;
}
diff --git a/hash.h b/hash.h
@@ -1,4 +1,5 @@
+unsigned int random();
unsigned int hash2(unsigned int a, unsigned int b);
unsigned int hash3(unsigned int seed, int x, int y);
-int randomInRange(int seed, int n, int a, int b);
+int hashInRange(int seed, int n, int a, int b);
int newSeed(int seed, int n);
diff --git a/rules.cpp b/rules.cpp
@@ -2,27 +2,87 @@
#include "rules.h"
#include "hash.h"
+class Carrefour;
+std::ostream& operator<<(std::ostream& os, const Carrefour& c);
+std::ostream& operator<<(std::ostream& os, const Carrefour* c);
+
+class Carrefour {
+public:
+ Vertex corners[4];
+public:
+ Carrefour(Vertex ne, Vertex se, Vertex sw, Vertex nw) {
+ corners[NE]=ne;
+ corners[SE]=se;
+ corners[SW]=sw;
+ corners[NW]=nw;
+ std::cout << this << std::endl;
+ }
+};
+
+std::ostream& operator<<(std::ostream& os, const Carrefour* c) { return os << *c; }
+std::ostream& operator<<(std::ostream& os, const Carrefour& c) {
+ return os << "Carrefour " << c.corners[NE] << "-" << c.corners[SE] << "-" << c.corners[NW] << "-" << c.corners[SW];
+}
+
+class Route;
+std::ostream& operator<<(std::ostream& os, const Route& r);
+std::ostream& operator<<(std::ostream& os, const Route* r);
+
+class Route {
+public:
+ Vertex corners[4];
+public:
+ Route(Vertex ne, Vertex se, Vertex sw, Vertex nw) {
+ corners[NE]=ne;
+ corners[SE]=se;
+ corners[SW]=sw;
+ corners[NW]=nw;
+ std::cout << this << std::endl;
+ }
+};
+
+std::ostream& operator<<(std::ostream& os, const Route* r) { return os << *r; }
+std::ostream& operator<<(std::ostream& os, const Route& r) {
+ return os << "Route " << r.corners[NE] << "-" << r.corners[SE] << "-" << r.corners[NW] << "-" << r.corners[SW];
+}
+
+class RectangleRoutes;
+std::ostream& operator<<(std::ostream& os, const RectangleRoutes& r);
+std::ostream& operator<<(std::ostream& os, const RectangleRoutes* r);
+
// RectangleRoutes est un quadrilatère de routes avec des angles aux coins égaux à 90°.
class RectangleRoutes {
public:
Vertex ne;
- Vertex so;
+ Vertex sw;
IO io [4];
int seed;
public:
- RectangleRoutes(Vertex ne, Vertex so, int seed) : ne(ne), so(so), seed(seed) {}
- void display() { };
- int width() { return this->ne.x - this->so.x; }
- int height() { return this->ne.y - this->so.y; }
- void subdivide() {
- Vertex split = {
- randomInRange(this->seed, 0, this->so.x + this->width()*1/4, this->so.x + this->width()*3/4),
- randomInRange(this->seed, 1, this->so.y + this->height()*1/4, this->so.y + this->height()*3/4)
- };
- split = split;
+ RectangleRoutes(Vertex ne, Vertex sw, int seed) : ne(ne), sw(sw), seed(seed) {
std::cout << this << std::endl;
- RectangleRoutes rr(ne, so, 42);
- // std::cout << rr << std::endl;
+ }
+ int width() { return this->ne.x - this->sw.x; }
+ int height() { return this->ne.y - this->sw.y; }
+ void subdivide() {
+ Vertex split(
+ hashInRange(this->seed, 0, this->sw.x + this->width()*1/4, this->sw.x + this->width()*3/4),
+ hashInRange(this->seed, 1, this->sw.y + this->height()*1/4, this->sw.y + this->height()*3/4)
+ );
+ Carrefour c(split.add(1,1), split.add(1,-1), split.add(-1,-1), split.add(-1,1));
+ // routes au NESW du carrefour
+ Vertex roadEndN(this->ne.y, split.x);
+ Vertex roadEndE(this->ne.x, split.y);
+ Vertex roadEndS(this->sw.y, split.x);
+ Vertex roadEndW(this->sw.x, split.y);
+ Route rn(roadEndN.add(-1,0), roadEndN.add(+1,0), split.add(+1,+1), split.add(-1,+1));
+ Route re(roadEndE.add(0,+1), roadEndE.add(0,-1), split.add(+1,-1), split.add(+1,+1));
+ Route rs(roadEndS.add(+1,0), roadEndS.add(-1,0), split.add(-1,-1), split.add(+1,-1));
+ Route rw(roadEndW.add(0,-1), roadEndW.add(0,+1), split.add(-1,+1), split.add(-1,-1));
+ // Sous-quartiers
+ RectangleRoutes(this->ne, re.corners[NW], newSeed(this->seed, 2));
+ RectangleRoutes(re.corners[SE], rs.corners[SE], newSeed(this->seed, 3));
+ RectangleRoutes(rs.corners[NW], this->sw, newSeed(this->seed, 4));
+ RectangleRoutes(Vertex(this->sw.x, this->ne.y), rn.corners[SW], newSeed(this->seed, 5));
}
};
@@ -30,32 +90,17 @@ std::ostream& operator<<(std::ostream& os, const Vertex& v) {
return os << "(" << v.x << "," << v.y << ")";
}
+std::ostream& operator<<(std::ostream& os, const RectangleRoutes* r) { return os << *r; }
std::ostream& operator<<(std::ostream& os, const RectangleRoutes& r) {
- int a = r.ne.x;
- a = a;
- return os << "42!";//<< r.ne << "-" << r.so;
+ return os << "RectangleRoutes " << r.ne << "-" << r.sw;
}
-
- /* Carrefour(split + (1,1), split - (1,1)) */
- /* // routes au NESW du carrefour */
- /* Route((r.ne.x, split.y) + (0,1)), split + (1,1)) */
- /* Route((split.x, r.se.y) + (1,0)), split + (-1,1)) */
- /* Route((r.so.x, split.y) + (0,-1)), split + (-1,-1)) */
- /* Route((split.x, r.no.y) + (-1,0)), split + (1,-1)) */
- /* // subrectangles */
- /* RectangleRoutes(split + (1,1), r.ne, newSeed(r.seed, 2)); */
- /* RectangleRoutes(split + (1,-1), r.se, newSeed(r.seed, 3)); */
- /* RectangleRoutes(split + (-1,-1), r.so, newSeed(r.seed, 4)); */
- /* RectangleRoutes(split + (-1,1), r.no, newSeed(r.seed, 5)); */
-
int main() {
// Générer une tile de base
- Vertex ne = {100,0};
- Vertex so = {0,100};
- RectangleRoutes r(ne, so, 42);
+ Vertex ne(100, 100);
+ Vertex sw(0, 0);
+ RectangleRoutes r(ne, sw, random());
r.subdivide();
- std::cout << r << std::endl;
// tile.subdivide tant qu'on n'a pas le niveau de détail désiré.
return 0;
}
diff --git a/rules.h b/rules.h
@@ -1,21 +1,27 @@
+#include <iostream>
+
typedef struct Vertex {
int x;
int y;
//int z;
+ Vertex() {}
+ Vertex(int x, int y): x(x), y(y) {}
+ Vertex add(int dx, int dy) { Vertex v = *this; v.x += dx; v.y += dy; return v; }
} Vertex;
+std::ostream& operator<<(std::ostream& os, const Vertex& v);
typedef enum Cardinaux {
N = 0,
E = 1,
S = 2,
- O = 3
+ W = 3
} Cardinaux;
typedef enum Diagonales {
NE = 0,
SE = 1,
- SO = 2,
- NO = 3
+ SW = 2,
+ NW = 3
} Diagonales;
typedef struct IO {