demos: Introduce a helper function to create a projection matrix.

This commit is contained in:
Henri Verbeet
2025-06-10 18:31:36 +02:00
parent eb988e95e1
commit c3c36d8517
Notes: Henri Verbeet 2025-06-16 17:48:41 +02:00
Approved-by: Henri Verbeet (@hverbeet)
Merge-Request: https://gitlab.winehq.org/wine/vkd3d/-/merge_requests/1567
2 changed files with 51 additions and 33 deletions

View File

@@ -98,6 +98,11 @@ struct demo_vec4
float x, y, z, w;
};
struct demo_matrix
{
float m[4][4];
};
struct demo_swapchain_desc
{
unsigned int width;
@@ -123,6 +128,39 @@ static inline void demo_vec4_set(struct demo_vec4 *v, float x, float y, float z,
v->w = w;
}
static inline void demo_matrix_multiply(struct demo_matrix *out,
const struct demo_matrix *a, const struct demo_matrix *b)
{
unsigned int i, j;
for (i = 0; i < 4; ++i)
{
for (j = 0; j < 4; ++j)
{
out->m[i][j] = a->m[i][0] * b->m[0][j]
+ a->m[i][1] * b->m[1][j]
+ a->m[i][2] * b->m[2][j]
+ a->m[i][3] * b->m[3][j];
}
}
}
static inline void demo_matrix_perspective_rh(struct demo_matrix *m, float w, float h, float z_near, float z_far)
{
float sx = 2.0 * z_near / w;
float sy = 2.0 * z_near / h;
float sz = z_far / (z_near - z_far);
float d = z_near * sz;
*m = (struct demo_matrix)
{{
{ sx, 0.0f, 0.0f, 0.0f},
{0.0f, sy, 0.0f, 0.0f},
{0.0f, 0.0f, sz, -1.0f},
{0.0f, 0.0f, d, 0.0f},
}};
}
static inline void demo_rasterizer_desc_init_default(D3D12_RASTERIZER_DESC *desc)
{
desc->FillMode = D3D12_FILL_MODE_SOLID;

View File

@@ -59,7 +59,7 @@ struct cxg_fence
struct cxg_cb_data
{
float mvp_matrix[16];
struct demo_matrix mvp_matrix;
float normal_matrix[12];
};
@@ -230,44 +230,24 @@ static void cxg_wait_for_previous_frame(struct cx_gears *cxg)
static void cxg_update_mvp(struct cx_gears *cxg)
{
struct demo_matrix projection, world;
float s1 = sinf(cxg->theta);
float c1 = cosf(cxg->theta);
float s2 = sinf(cxg->phi);
float c2 = cosf(cxg->phi);
float z_offset = -40.0f;
float z_max = 60.0f;
float z_min = 5.0f;
float sx = z_min;
float sy = z_min * cxg->aspect_ratio;
float sz = -((z_max + z_min) / (z_max - z_min));
float d = (-2.0f * z_max * z_min) / (z_max - z_min);
unsigned int i, j;
float world[] =
{
c1, s2 * s1, c2 * -s1, 0.0f,
0.0f, c2, s2, 0.0f,
s1, -s2 * c1, c2 * c1, 0.0f,
0.0f, 0.0f, z_offset, 1.0f,
};
float projection[] =
{
sx, 0.0f, 0.0f, 0.0f,
0.0f, sy, 0.0f, 0.0f,
0.0f, 0.0f, sz, -1.0f,
0.0f, 0.0f, d, 0.0f,
};
for (i = 0; i < 4; ++i)
{
for (j = 0; j < 4; ++j)
{
cxg->cb_data->mvp_matrix[i * 4 + j] = projection[j] * world[i * 4]
+ projection[j + 4] * world[i * 4 + 1]
+ projection[j + 8] * world[i * 4 + 2]
+ projection[j + 12] * world[i * 4 + 3];
}
}
memcpy(cxg->cb_data->normal_matrix, world, sizeof(cxg->cb_data->normal_matrix));
world = (struct demo_matrix)
{{
{ c1, s2 * s1, c2 * -s1, 0.0f},
{0.0f, c2, s2, 0.0f},
{ s1, -s2 * c1, c2 * c1, 0.0f},
{0.0f, 0.0f, z_offset, 1.0f},
}};
demo_matrix_perspective_rh(&projection, 2.0f, 2.0f / cxg->aspect_ratio, 5.0f, 60.0f);
demo_matrix_multiply(&cxg->cb_data->mvp_matrix, &world, &projection);
memcpy(cxg->cb_data->normal_matrix, &world, sizeof(cxg->cb_data->normal_matrix));
}
static void cxg_render_frame(struct cx_gears *cxg)