载入中...
搜索中...
未找到
VoxelRectDecode.h
浏览该文件的文档.
1#pragma once
2
3#include "voxel/FaceDir.h"
4#include "voxel/VoxelPack.h"
5
6namespace eve::voxel {
7
9struct DecodedRect {
10 float corners[4][3]{}; // (0,0), (1,0), (1,1), (0,1)
11 float normal[3]{};
12 float uv[4][2]{};
13 int tex = 0;
14 float width = 1.f;
15 float height = 1.f;
16 uint8_t ao[4] = {3, 3, 3, 3}; // per-corner 0..3, shader corner order
17};
18
23inline DecodedRect decodePackedRect(PackedRect rect, FaceDir dir, float originX, float originY,
24 float originZ, int tilesPerRow = 16,
25 uint32_t aoWord = 0xFFu) {
26 DecodedRect out;
27 const float ix = float(rect.x());
28 const float iy = float(rect.y());
29 const float iz = float(rect.z());
30 const float w = float(rect.width());
31 const float h = float(rect.height());
32 out.width = w;
33 out.height = h;
34 out.tex = rect.tex();
35
36 for (int i = 0; i < 4; ++i) out.ao[i] = uint8_t((aoWord >> (2 * i)) & 3u);
37
38 const float corners2[4][2] = {{0.f, 0.f}, {1.f, 0.f}, {1.f, 1.f}, {0.f, 1.f}};
39 for (int i = 0; i < 4; ++i) {
40 const float cu = corners2[i][0];
41 const float cv = corners2[i][1];
42 float x = ix, y = iy, z = iz;
43 float nx = 0.f, ny = 0.f, nz = 0.f;
44 switch (dir) {
45 case FaceDir::PosX:
46 x = ix + 1.f;
47 y = iy + cv * h;
48 z = iz + cu * w;
49 nx = 1.f;
50 break;
51 case FaceDir::NegX:
52 x = ix;
53 y = iy + cv * h;
54 z = iz + (1.f - cu) * w;
55 nx = -1.f;
56 break;
57 case FaceDir::PosY:
58 x = ix + cu * w;
59 y = iy + 1.f;
60 z = iz + cv * h;
61 ny = 1.f;
62 break;
63 case FaceDir::NegY:
64 x = ix + cu * w;
65 y = iy;
66 z = iz + (1.f - cv) * h;
67 ny = -1.f;
68 break;
69 case FaceDir::PosZ:
70 x = ix + (1.f - cu) * w;
71 y = iy + cv * h;
72 z = iz + 1.f;
73 nz = 1.f;
74 break;
75 case FaceDir::NegZ:
76 default:
77 x = ix + cu * w;
78 y = iy + cv * h;
79 z = iz;
80 nz = -1.f;
81 break;
82 }
83 out.corners[i][0] = x + originX;
84 out.corners[i][1] = y + originY;
85 out.corners[i][2] = z + originZ;
86 out.normal[0] = nx;
87 out.normal[1] = ny;
88 out.normal[2] = nz;
89
90 const float tiles = float(tilesPerRow < 1 ? 1 : tilesPerRow);
91 const float tileU = 1.f / tiles;
92 const float col = float(out.tex % (tilesPerRow < 1 ? 1 : tilesPerRow));
93 const float row = float(out.tex / (tilesPerRow < 1 ? 1 : tilesPerRow));
94 out.uv[i][0] = (col + cu) * tileU;
95 out.uv[i][1] = (row + cv) * tileU;
96 }
97 return out;
98}
99
102 // GPU draws 0-2-1 and 0-3-2 (see ensureVoxelUnitQuad).
103 const float e1x = q.corners[2][0] - q.corners[0][0];
104 const float e1y = q.corners[2][1] - q.corners[0][1];
105 const float e1z = q.corners[2][2] - q.corners[0][2];
106 const float e2x = q.corners[1][0] - q.corners[0][0];
107 const float e2y = q.corners[1][1] - q.corners[0][1];
108 const float e2z = q.corners[1][2] - q.corners[0][2];
109 const float cx = e1y * e2z - e1z * e2y;
110 const float cy = e1z * e2x - e1x * e2z;
111 const float cz = e1x * e2y - e1y * e2x;
112 return cx * q.normal[0] + cy * q.normal[1] + cz * q.normal[2] > 0.f;
113}
114
117 const float e1x = q.corners[3][0] - q.corners[0][0];
118 const float e1y = q.corners[3][1] - q.corners[0][1];
119 const float e1z = q.corners[3][2] - q.corners[0][2];
120 const float e2x = q.corners[2][0] - q.corners[0][0];
121 const float e2y = q.corners[2][1] - q.corners[0][1];
122 const float e2z = q.corners[2][2] - q.corners[0][2];
123 const float cx = e1y * e2z - e1z * e2y;
124 const float cy = e1z * e2x - e1x * e2z;
125 const float cz = e1x * e2y - e1y * e2x;
126 return cx * q.normal[0] + cy * q.normal[1] + cz * q.normal[2] > 0.f;
127}
128
129} // namespace eve::voxel
float cx
Definition CardTypes.cpp:31
float cy
Definition CardTypes.cpp:32
int y
Definition Grass.cpp:135
int z
Definition Grass.cpp:135
int x
Definition Grass.cpp:135
int h
int w
V3 dir
Definition TreeMesh.cpp:121
std::vector< WfcTile > tiles
Definition WfcSimple.cpp:22
方块类型定义:名字、各面图集纹理、方向性、组合声明。 方向性方块在注册时按 orientation 绕 Y 轴展开成多个"具体类型"变体, 每个变体持有旋转后的各面纹理;渲染端只消费纹理 id,不接触 ...
Definition Chunk.h:12
bool decodedWindingMatchesNormal(const DecodedRect &q)
True when triangle (0,2,1) winding matches outward normal (matches GPU index order).
DecodedRect decodePackedRect(PackedRect rect, FaceDir dir, float originX, float originY, float originZ, int tilesPerRow=16, uint32_t aoWord=0xFFu)
CPU mirror of the instanced voxel vertex shader placement / UV logic. Used by unit tests to validate ...
bool decodedSecondTriangleMatchesNormal(const DecodedRect &q)
True when the second GPU triangle (0,3,2) also matches the outward normal.
FaceDir
Six axis-aligned face directions. Each chunk keeps a separate instance buffer per direction so camera...
Definition FaceDir.h:17
One decoded face rectangle in world space (mirrors voxel_rect.vert).
Packed face-rectangle instance (exactly 32 bits): bits 0..4 : x (0..31) bits 5..9 : y (0....
Definition VoxelPack.h:22