]> git.lizzy.rs Git - dragonblocks_alpha.git/blob - src/client/client_node.c
18283ebbdc69495cdd9696622741904efd1edd65
[dragonblocks_alpha.git] / src / client / client_node.c
1 #include "client/client.h"
2 #include "client/client_node.h"
3 #include "environment.h"
4 #include "node.h"
5 #include "perlin.h"
6 #include "util.h"
7 #define TILES_SIMPLE(path) {.paths = {path, NULL, NULL, NULL, NULL, NULL}, .indices = {0, 0, 0, 0, 0, 0}, .textures = {NULL}}
8 #define TILES_NONE {.paths = {NULL}, .indices = {0}, .textures = {NULL}}
9
10 static f32 hue_to_rgb(f32 p, f32 q, f32 t)
11 {
12     if (t < 0.0f)
13         t += 1.0f;
14
15     if (t > 1.0f)
16         t -= 1.0f;
17
18     if (t < 1.0f / 6.0f)
19         return p + (q - p) * 6.0f * t;
20
21     if (t < 1.0f / 2.0f)
22         return q;
23
24     if (t < 2.0f / 3.0f)
25         return p + (q - p) * (2.0f / 3.0f - t) * 6.0f;
26
27     return p;
28 }
29
30 static Vertex3DColor hsl_to_rgb(v3f32 hsl)
31 {
32         Vertex3DColor rgb;
33
34     if (hsl.y == 0.0f) {
35                 rgb = (Vertex3DColor) {hsl.z, hsl.z, hsl.z};
36     } else {
37         f32 q = hsl.z < 0.5f ? hsl.z * (1.0f + hsl.y) : hsl.z + hsl.y - hsl.z * hsl.y;
38         f32 p = 2.0f * hsl.z - q;
39
40         rgb.r = hue_to_rgb(p, q, hsl.x + 1.0f / 3.0f);
41         rgb.g = hue_to_rgb(p, q, hsl.x);
42         rgb.b = hue_to_rgb(p, q, hsl.x - 1.0f / 3.0f);
43     }
44
45     return rgb;
46 }
47
48 static void render_grass(v3s32 pos, unused MapNode *node, Vertex3D *vertex, unused int f, unused int v)
49 {
50         f32 hum_min, hum_max, temp_max;
51         hum_min = 0.13f;
52         hum_max = 0.33f;
53         temp_max = 0.45f;
54
55         f32 temp_f = f64_clamp(0.3f - get_temperature(pos), 0.0f, 0.3f) / 0.3f;
56
57         vertex->color = hsl_to_rgb((v3f32) {(get_humidity(pos) * (hum_max - hum_min) + hum_min) * (1.0f - temp_f) + temp_max * temp_f, 1.0f, 0.5f});
58 }
59
60 static void render_stone(v3s32 pos, unused MapNode *node, Vertex3D *vertex, unused int f, unused int v)
61 {
62         vertex->textureCoordinates.s += noise2d(pos.x, pos.z, 0, seed + SO_TEXTURE_OFFSET_S);
63         vertex->textureCoordinates.t += noise2d(pos.x, pos.z, 0, seed + SO_TEXTURE_OFFSET_T);
64 }
65
66 static void render_hsl(unused v3s32 pos, MapNode *node, Vertex3D *vertex, unused int f, unused int v)
67 {
68         vertex->color = hsl_to_rgb(((HSLData *) node->data)->color);
69 }
70
71 ClientNodeDefinition client_node_definitions[NODE_UNLOADED] = {
72         // unknown
73         {
74                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/unknown.png"),
75                 .visibility = NV_SOLID,
76                 .mipmap = true,
77                 .render = NULL,
78         },
79         // air
80         {
81                 .tiles = TILES_NONE,
82                 .visibility = NV_NONE,
83                 .mipmap = true,
84                 .render = NULL,
85         },
86         // grass
87         {
88                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/grass.png"),
89                 .visibility = NV_SOLID,
90                 .mipmap = true,
91                 .render = &render_grass,
92         },
93         // dirt
94         {
95                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/dirt.png"),
96                 .visibility = NV_SOLID,
97                 .mipmap = true,
98                 .render = NULL,
99         },
100         // stone
101         {
102                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/stone.png"),
103                 .visibility = NV_SOLID,
104                 .mipmap = true,
105                 .render = &render_stone,
106         },
107         // snow
108         {
109                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/snow.png"),
110                 .visibility = NV_SOLID,
111                 .mipmap = true,
112                 .render = NULL,
113         },
114         // oak wood
115         {
116                 .tiles = {
117                         .paths = {RESSOURCE_PATH "textures/oak_wood.png", RESSOURCE_PATH "textures/oak_wood_top.png", NULL, NULL, NULL, NULL},
118                         .indices = {0, 0, 0, 0, 1, 1},
119                         .textures = {NULL},
120                 },
121                 .visibility = NV_SOLID,
122                 .mipmap = true,
123                 .render = &render_hsl,
124         },
125         // oak leaves
126         {
127                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/oak_leaves.png"),
128                 .visibility = NV_SOLID,
129                 .mipmap = true,
130                 .render = &render_hsl,
131         },
132         // pine wood
133         {
134                 .tiles = {
135                         .paths = {RESSOURCE_PATH "textures/pine_wood.png", RESSOURCE_PATH "textures/pine_wood_top.png", NULL, NULL, NULL, NULL},
136                         .indices = {0, 0, 0, 0, 1, 1},
137                         .textures = {NULL},
138                 },
139                 .visibility = NV_SOLID,
140                 .mipmap = true,
141                 .render = &render_hsl,
142         },
143         // pine leaves
144         {
145                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/pine_leaves.png"),
146                 .visibility = NV_CLIP,
147                 .mipmap = true,
148                 .render = &render_hsl,
149         },
150         // palm wood
151         {
152                 .tiles = {
153                         .paths = {RESSOURCE_PATH "textures/palm_wood.png", RESSOURCE_PATH "textures/palm_wood_top.png", NULL, NULL, NULL, NULL},
154                         .indices = {0, 0, 0, 0, 1, 1},
155                         .textures = {NULL},
156                 },
157                 .visibility = NV_SOLID,
158                 .mipmap = true,
159                 .render = &render_hsl,
160         },
161         // palm leaves
162         {
163                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/palm_leaves.png"),
164                 .visibility = NV_SOLID,
165                 .mipmap = true,
166                 .render = &render_hsl,
167         },
168         // sand
169         {
170                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/sand.png"),
171                 .visibility = NV_SOLID,
172                 .mipmap = true,
173                 .render = NULL,
174         },
175         // water
176         {
177                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/water.png"),
178                 .visibility = NV_BLEND,
179                 .mipmap = true,
180                 .render = NULL,
181         },
182         // lava
183         {
184                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/lava.png"),
185                 .visibility = NV_BLEND,
186                 .mipmap = true,
187                 .render = NULL,
188         },
189         // vulcano_stone
190         {
191                 .tiles = TILES_SIMPLE(RESSOURCE_PATH "textures/vulcano_stone.png"),
192                 .visibility = NV_SOLID,
193                 .mipmap = true,
194                 .render = NULL,
195         },
196 };
197
198 void client_node_init()
199 {
200         for (Node node = NODE_UNKNOWN; node < NODE_UNLOADED; node++) {
201                 ClientNodeDefinition *def = &client_node_definitions[node];
202
203                 if (def->visibility != NV_NONE) {
204                         Texture *textures[6];
205
206                         for (int i = 0; i < 6; i++) {
207                                 char *path = def->tiles.paths[i];
208
209                                 if (path)
210                                         textures[i] = texture_load(path, def->mipmap);
211                                 else
212                                         break;
213                         }
214
215                         for (int i = 0; i < 6; i++)
216                                 def->tiles.textures[i] = textures[def->tiles.indices[i]];
217                 }
218         }
219 }