6
6
7
7
chunk * create_chunk (GLfloat x , GLfloat z ) {
8
8
chunk * new_chunk = malloc (sizeof (chunk ));
9
- new_chunk -> blocks = (uint8_t * ) calloc (1 , sizeof (CHUNK_SIZE ));
9
+ new_chunk -> blocks = (uint8_t * ) calloc (1 , sizeof (uint8_t ) * CHUNK_SIZE );
10
+
11
+ // Sets all blocks to a non-air type. (1)
12
+ for (int i = 0 ; i < CHUNK_SIZE ; i ++ ) {
13
+ new_chunk -> blocks [i ] = 1 ;
14
+ }
15
+
10
16
new_chunk -> x = x ;
11
17
new_chunk -> z = z ;
12
18
13
19
return new_chunk ;
14
20
}
15
21
16
22
void generate_chunk_mesh (chunk * render_chunk ) {
17
- GLfloat * buffer = malloc (sizeof (GLfloat ) * (6 * 5 * 5 ) * CHUNK_SIZE );
23
+ GLfloat * buffer = malloc (sizeof (GLfloat ) * (6 * 6 * 5 ) * CHUNK_SIZE );
18
24
GLfloat * buffer_pointer = buffer ;
19
-
20
- for (int x = 0 ; x < CHUNK_WIDTH ; x ++ ) {
21
- for (int z = 0 ; z < CHUNK_HEIGHT ; z ++ ) {
22
- for (int y = 0 ; y < CHUNK_DEPTH ; y ++ ) {
23
- uint32_t index = x + z + y ;
24
- uint8_t block = render_chunk -> blocks [index ];
25
-
26
- create_cube_mesh (& buffer_pointer ,
27
- 1 , 1 , 1 , 0 , 1 , 1 ,
28
- 1 , 1 , 1 , 1 , 1 , 1 ,
29
- x , y , z , 0.5
30
- );
31
- }
32
- }
25
+ int vertices_count = 0 ;
26
+
27
+ for (int i = 0 ; i < CHUNK_SIZE ; i ++ ) {
28
+ int x = i % CHUNK_X ;
29
+ int z = (i / CHUNK_X ) % CHUNK_Z ;
30
+ int y = i / (CHUNK_X * CHUNK_Z );
31
+
32
+ uint8_t block = render_chunk -> blocks [i ];
33
+
34
+ // left(-x), right(+x), top(+y), bottom(-y), front(-z), back(+z)
35
+ uint8_t neighbors [6 ] = {1 , 1 , 1 , 1 , 1 , 1 };
36
+
37
+ // Calculate neighboring voxels and check if they are solid or not.
38
+ // If they are not solid, we should render a face. Otherwise, it is
39
+ // unnecessary to include the face. This resulting mesh will be
40
+ // contain only the exposed faces. Perf++.
41
+ //
42
+ // TODO(vy): Need to check between chunk boundaries for checking
43
+ // face exposure.
44
+ neighbors [0 ] = (x - 1 < 0 ) ? 1 : render_chunk -> blocks [i - 1 ] == 0 ;
45
+ neighbors [1 ] = (x + 1 >= CHUNK_X ) ? 1 : render_chunk -> blocks [i + 1 ] == 0 ;
46
+ neighbors [2 ] = (y + 1 >= CHUNK_Y ) ? 1 : render_chunk -> blocks [i + (CHUNK_X * CHUNK_Z )] == 0 ;
47
+ neighbors [3 ] = (y - 1 < 0 ) ? 1 : render_chunk -> blocks [i - (CHUNK_X * CHUNK_Z )] == 0 ;
48
+ neighbors [4 ] = (z - 1 < 0 ) ? 1 : render_chunk -> blocks [i - CHUNK_X ] == 0 ;
49
+ neighbors [5 ] = (z + 1 >= CHUNK_Z ) ? 1 : render_chunk -> blocks [i + CHUNK_X ] == 0 ;
50
+
51
+ vertices_count += create_cube_mesh (& buffer_pointer ,
52
+ neighbors [0 ], neighbors [1 ], neighbors [2 ], neighbors [3 ], neighbors [4 ], neighbors [5 ],
53
+ 1 , 1 , 1 , 1 , 1 , 1 ,
54
+ x , y , z , 0.5
55
+ );
33
56
}
34
57
58
+
59
+ // Resize the mesh buffer to the actual size, since we allocated
60
+ // the largest size, but during mesh creation, we could have
61
+ // omitted faces, causing the buffer to be smaller than the
62
+ // maximum size.
63
+ buffer = realloc (buffer , (sizeof (GLfloat ) * vertices_count * 5 ));
64
+
35
65
// TODO(vy): Figure out how to calculate vertices of exposed faces:
36
66
// 6 vertices per face * NUMBER OF FACES
37
67
render_chunk -> render_object = create_render_obj (
38
68
GL_TRIANGLES ,
39
69
buffer ,
40
- (6 * 5 * 5 ) * CHUNK_SIZE ,
41
- ( 6 * 5 ) * CHUNK_SIZE
70
+ (6 * 6 * 5 ) * CHUNK_SIZE ,
71
+ vertices_count
42
72
);
43
73
44
74
// Bind Vertices
@@ -69,9 +99,9 @@ void generate_chunk_mesh(chunk *render_chunk) {
69
99
render_chunk -> render_object -> transform = m4_transpose (
70
100
m4_translation (
71
101
vec3 (
72
- render_chunk -> x * CHUNK_WIDTH ,
102
+ render_chunk -> x * CHUNK_X ,
73
103
0 ,
74
- render_chunk -> z * CHUNK_HEIGHT
104
+ render_chunk -> z * CHUNK_Z
75
105
)
76
106
)
77
107
);
@@ -91,13 +121,15 @@ void generate_chunk_mesh(chunk *render_chunk) {
91
121
// vertices, normals, uvs of ONLY the exposed faces. This impacts
92
122
// mem space on the overall mesh significantly.
93
123
94
- void create_cube_mesh (
124
+ int create_cube_mesh (
95
125
GLfloat * * data_pointer ,
96
126
int left , int right , int top , int bottom , int front , int back ,
97
127
int wleft , int wright , int wtop , int wbottom , int wfront , int wback ,
98
128
GLfloat x , GLfloat y , GLfloat z , GLfloat cube_size
99
129
) {
100
130
131
+ int vertices_count = 0 ;
132
+
101
133
static const GLfloat vertices [6 ][4 ][3 ] = {
102
134
{{-1 , -1 , -1 }, {-1 , -1 , +1 }, {-1 , +1 , -1 }, {-1 , +1 , +1 }},
103
135
{{+1 , -1 , -1 }, {+1 , -1 , +1 }, {+1 , +1 , -1 }, {+1 , +1 , +1 }},
@@ -163,8 +195,11 @@ void create_cube_mesh(
163
195
* ((* data_pointer )++ ) = z + cube_size * vertices [i ][j ][2 ];
164
196
* ((* data_pointer )++ ) = (uvs [i ][j ][0 ] ? b : a );
165
197
* ((* data_pointer )++ ) = (uvs [i ][j ][1 ] ? b : a );
198
+ vertices_count ++ ;
166
199
}
167
200
}
201
+
202
+ return vertices_count ;
168
203
}
169
204
170
205
uint8_t block_from_index (chunk * render_chunk , uint32_t index ) {
@@ -178,9 +213,9 @@ uint32_t index_from_block(uint16_t x, uint16_t y, uint16_t z) {
178
213
179
214
// return (modz * SIZEXY) + (modx * SIZEY) + mody;
180
215
181
- uint32_t x_length = CHUNK_WIDTH ;
182
- uint32_t z_length = CHUNK_HEIGHT ;
183
- uint32_t y_length = CHUNK_DEPTH ;
216
+ uint32_t x_length = CHUNK_X ;
217
+ uint32_t z_length = CHUNK_Z ;
218
+ uint32_t y_length = CHUNK_Y ;
184
219
if (x > x_length ) x = x_length ;
185
220
if (y > y_length ) y = y_length ;
186
221
if (z > z_length ) z = z_length ;
0 commit comments