]> git.localhorst.tv Git - blank.git/blob - src/block.cpp
update light levels from border on neighbor change
[blank.git] / src / block.cpp
1 #include "block.hpp"
2
3 #include "geometry.hpp"
4
5 #include <glm/gtx/euler_angles.hpp>
6 #include <glm/gtx/transform.hpp>
7
8
9 namespace blank {
10
11 namespace {
12
13 const glm::mat4 block_transforms[Block::FACE_COUNT * Block::TURN_COUNT] = {
14         {  1,  0,  0,  0,  0,  1,  0,  0,  0,  0,  1,  0,  0,  0,  0,  1, }, // face: up,    turn: none
15         {  0,  0, -1,  0,  0,  1,  0,  0,  1,  0,  0,  0,  0,  0,  0,  1, }, // face: up,    turn: left
16         { -1,  0,  0,  0,  0,  1,  0,  0,  0,  0, -1,  0,  0,  0,  0,  1, }, // face: up,    turn: around
17         {  0,  0,  1,  0,  0,  1,  0,  0, -1,  0,  0,  0,  0,  0,  0,  1, }, // face: up,    turn: right
18         {  1,  0,  0,  0,  0, -1,  0,  0,  0,  0, -1,  0,  0,  0,  0,  1, }, // face: down,  turn: none
19         {  0,  0, -1,  0,  0, -1,  0,  0, -1,  0,  0,  0,  0,  0,  0,  1, }, // face: down,  turn: left
20         { -1,  0,  0,  0,  0, -1,  0,  0,  0,  0,  1,  0,  0,  0,  0,  1, }, // face: down,  turn: around
21         {  0,  0,  1,  0,  0, -1,  0,  0,  1,  0,  0,  0,  0,  0,  0,  1, }, // face: down,  turn: right
22         {  0, -1,  0,  0,  1,  0,  0,  0,  0,  0,  1,  0,  0,  0,  0,  1, }, // face: right, turn: none
23         {  0, -1,  0,  0,  0,  0, -1,  0,  1,  0,  0,  0,  0,  0,  0,  1, }, // face: right, turn: left
24         {  0, -1,  0,  0, -1,  0,  0,  0,  0,  0, -1,  0,  0,  0,  0,  1, }, // face: right, turn: around
25         {  0, -1,  0,  0,  0,  0,  1,  0, -1,  0,  0,  0,  0,  0,  0,  1, }, // face: right, turn: right
26         {  0,  1,  0,  0, -1,  0,  0,  0,  0,  0,  1,  0,  0,  0,  0,  1, }, // face: left,  turn: none
27         {  0,  1,  0,  0,  0,  0,  1,  0,  1,  0,  0,  0,  0,  0,  0,  1, }, // face: left,  turn: left
28         {  0,  1,  0,  0,  1,  0,  0,  0,  0,  0, -1,  0,  0,  0,  0,  1, }, // face: left,  turn: around
29         {  0,  1,  0,  0,  0,  0, -1,  0, -1,  0,  0,  0,  0,  0,  0,  1, }, // face: left,  turn: right
30         {  1,  0,  0,  0,  0,  0,  1,  0,  0, -1,  0,  0,  0,  0,  0,  1, }, // face: front, turn: none
31         {  0,  0, -1,  0,  1,  0,  0,  0,  0, -1,  0,  0,  0,  0,  0,  1, }, // face: front, turn: left
32         { -1,  0,  0,  0,  0,  0, -1,  0,  0, -1,  0,  0,  0,  0,  0,  1, }, // face: front, turn: around
33         {  0,  0,  1,  0, -1,  0,  0,  0,  0, -1,  0,  0,  0,  0,  0,  1, }, // face: front, turn: right
34         {  1,  0,  0,  0,  0,  0, -1,  0,  0,  1,  0,  0,  0,  0,  0,  1, }, // face: back,  turn: none
35         {  0,  0, -1,  0, -1,  0,  0,  0,  0,  1,  0,  0,  0,  0,  0,  1, }, // face: back,  turn: left
36         { -1,  0,  0,  0,  0,  0,  1,  0,  0,  1,  0,  0,  0,  0,  0,  1, }, // face: back,  turn: around
37         {  0,  0,  1,  0,  1,  0,  0,  0,  0,  1,  0,  0,  0,  0,  0,  1, }, // face: back,  turn: right
38 };
39
40 }
41
42 const glm::mat4 &Block::Transform() const {
43         return block_transforms[orient];
44 }
45
46
47 const NullShape BlockType::DEFAULT_SHAPE;
48
49 BlockType::BlockType(bool v, const glm::vec3 &col, const Shape *s)
50 : shape(s)
51 , color(col)
52 , outline_color(-1, -1, -1)
53 , id(0)
54 , luminosity(0)
55 , visible(v)
56 , block_light(false)
57 , fill({ false, false, false, false, false, false }) {
58
59 }
60
61 namespace {
62
63 const Block::Face face_map[Block::FACE_COUNT * Block::TURN_COUNT][Block::FACE_COUNT] = {
64         { Block::FACE_UP,    Block::FACE_DOWN,  Block::FACE_RIGHT, Block::FACE_LEFT,  Block::FACE_FRONT, Block::FACE_BACK,  }, // face: up,    turn: none x
65         { Block::FACE_UP,    Block::FACE_DOWN,  Block::FACE_FRONT, Block::FACE_BACK,  Block::FACE_LEFT,  Block::FACE_RIGHT, }, // face: up,    turn: left
66         { Block::FACE_UP,    Block::FACE_DOWN,  Block::FACE_LEFT,  Block::FACE_RIGHT, Block::FACE_BACK,  Block::FACE_FRONT, }, // face: up,    turn: around
67         { Block::FACE_UP,    Block::FACE_DOWN,  Block::FACE_BACK,  Block::FACE_FRONT, Block::FACE_RIGHT, Block::FACE_LEFT,  }, // face: up,    turn: right
68         { Block::FACE_DOWN,  Block::FACE_UP,    Block::FACE_RIGHT, Block::FACE_LEFT,  Block::FACE_BACK,  Block::FACE_FRONT, }, // face: down,  turn: none
69         { Block::FACE_DOWN,  Block::FACE_UP,    Block::FACE_BACK,  Block::FACE_FRONT, Block::FACE_LEFT,  Block::FACE_RIGHT, }, // face: down,  turn: left
70         { Block::FACE_DOWN,  Block::FACE_UP,    Block::FACE_LEFT,  Block::FACE_RIGHT, Block::FACE_FRONT, Block::FACE_BACK,  }, // face: down,  turn: around
71         { Block::FACE_DOWN,  Block::FACE_UP,    Block::FACE_FRONT, Block::FACE_BACK,  Block::FACE_RIGHT, Block::FACE_LEFT,  }, // face: down,  turn: right
72         { Block::FACE_LEFT,  Block::FACE_RIGHT, Block::FACE_UP,    Block::FACE_DOWN,  Block::FACE_FRONT, Block::FACE_BACK,  }, // face: right, turn: none
73         { Block::FACE_LEFT,  Block::FACE_RIGHT, Block::FACE_FRONT, Block::FACE_BACK,  Block::FACE_DOWN,  Block::FACE_UP,    }, // face: right, turn: left
74         { Block::FACE_LEFT,  Block::FACE_RIGHT, Block::FACE_DOWN,  Block::FACE_UP,    Block::FACE_BACK,  Block::FACE_FRONT, }, // face: right, turn: around
75         { Block::FACE_LEFT,  Block::FACE_RIGHT, Block::FACE_BACK,  Block::FACE_FRONT, Block::FACE_UP,    Block::FACE_DOWN,  }, // face: right, turn: right
76         { Block::FACE_RIGHT, Block::FACE_LEFT,  Block::FACE_DOWN,  Block::FACE_UP,    Block::FACE_FRONT, Block::FACE_BACK,  }, // face: left,  turn: none
77         { Block::FACE_RIGHT, Block::FACE_LEFT,  Block::FACE_FRONT, Block::FACE_BACK,  Block::FACE_UP,    Block::FACE_DOWN,  }, // face: left,  turn: left
78         { Block::FACE_RIGHT, Block::FACE_LEFT,  Block::FACE_UP,    Block::FACE_DOWN,  Block::FACE_BACK,  Block::FACE_FRONT, }, // face: left,  turn: around
79         { Block::FACE_RIGHT, Block::FACE_LEFT,  Block::FACE_BACK,  Block::FACE_FRONT, Block::FACE_DOWN,  Block::FACE_UP,    }, // face: left,  turn: right
80         { Block::FACE_BACK,  Block::FACE_FRONT, Block::FACE_RIGHT, Block::FACE_LEFT,  Block::FACE_UP,    Block::FACE_DOWN,  }, // face: front, turn: none
81         { Block::FACE_BACK,  Block::FACE_FRONT, Block::FACE_UP,    Block::FACE_DOWN,  Block::FACE_LEFT,  Block::FACE_RIGHT, }, // face: front, turn: left
82         { Block::FACE_BACK,  Block::FACE_FRONT, Block::FACE_LEFT,  Block::FACE_RIGHT, Block::FACE_DOWN,  Block::FACE_UP,    }, // face: front, turn: around
83         { Block::FACE_BACK,  Block::FACE_FRONT, Block::FACE_DOWN,  Block::FACE_UP,    Block::FACE_RIGHT, Block::FACE_LEFT,  }, // face: front, turn: right
84         { Block::FACE_FRONT, Block::FACE_BACK,  Block::FACE_RIGHT, Block::FACE_LEFT,  Block::FACE_DOWN,  Block::FACE_UP,    }, // face: back,  turn: none
85         { Block::FACE_FRONT, Block::FACE_BACK,  Block::FACE_DOWN,  Block::FACE_UP,    Block::FACE_LEFT,  Block::FACE_RIGHT, }, // face: back,  turn: left
86         { Block::FACE_FRONT, Block::FACE_BACK,  Block::FACE_LEFT,  Block::FACE_RIGHT, Block::FACE_UP,    Block::FACE_DOWN,  }, // face: back,  turn: around
87         { Block::FACE_FRONT, Block::FACE_BACK,  Block::FACE_UP,    Block::FACE_DOWN,  Block::FACE_RIGHT, Block::FACE_LEFT,  }, // face: back,  turn: right
88 };
89
90 }
91
92 bool BlockType::FaceFilled(const Block &block, Block::Face face) const {
93         return fill[face_map[block.orient][face]];
94 }
95
96 void BlockType::FillModel(
97         Model::Buffer &buf,
98         const glm::mat4 &transform,
99         Model::Index idx_offset
100 ) const {
101         shape->Vertices(buf.vertices, buf.normals, buf.indices, transform, idx_offset);
102         buf.colors.insert(buf.colors.end(), shape->VertexCount(), color);
103 }
104
105 void BlockType::FillBlockModel(
106         BlockModel::Buffer &buf,
107         const glm::mat4 &transform,
108         BlockModel::Index idx_offset
109 ) const {
110         shape->Vertices(buf.vertices, buf.normals, buf.indices, transform, idx_offset);
111         buf.colors.insert(buf.colors.end(), shape->VertexCount(), color);
112 }
113
114 void BlockType::FillOutlineModel(
115         OutlineModel &model,
116         const glm::vec3 &pos_offset,
117         OutlineModel::Index idx_offset
118 ) const {
119         shape->Outline(model.vertices, model.indices, pos_offset, idx_offset);
120         model.colors.insert(model.colors.end(), shape->OutlineCount(), outline_color);
121 }
122
123
124 BlockTypeRegistry::BlockTypeRegistry() {
125         Add(BlockType());
126 }
127
128 Block::Type BlockTypeRegistry::Add(const BlockType &t) {
129         int id = types.size();
130         types.push_back(t);
131         types.back().id = id;
132         return id;
133 }
134
135 }