diff options
author | clayjohn <claynjohn@gmail.com> | 2022-09-20 14:21:31 -0700 |
---|---|---|
committer | clayjohn <claynjohn@gmail.com> | 2022-09-20 23:40:01 -0700 |
commit | 27a3014f5052ae40f89684a5559c17fbebe7aa8d (patch) | |
tree | 7bf20c7a8150f15e1732c020d05ba0654d3402fd /servers/rendering/renderer_rd/storage_rd | |
parent | 6f5704d86f95171ba8b6b2ac9f56e284c4d35d7a (diff) |
Emulate double precision for regular rendering operation.
We calculate the lost precision on the CPU and pass it into the GPU
so that it can calculate an error-corrected version of the vertex position
Diffstat (limited to 'servers/rendering/renderer_rd/storage_rd')
-rw-r--r-- | servers/rendering/renderer_rd/storage_rd/material_storage.h | 12 | ||||
-rw-r--r-- | servers/rendering/renderer_rd/storage_rd/render_scene_data_rd.cpp | 6 |
2 files changed, 18 insertions, 0 deletions
diff --git a/servers/rendering/renderer_rd/storage_rd/material_storage.h b/servers/rendering/renderer_rd/storage_rd/material_storage.h index db2e4cfa2a..2ce6550cc1 100644 --- a/servers/rendering/renderer_rd/storage_rd/material_storage.h +++ b/servers/rendering/renderer_rd/storage_rd/material_storage.h @@ -311,6 +311,18 @@ public: } } + // http://andrewthall.org/papers/df64_qf128.pdf +#ifdef REAL_T_IS_DOUBLE + static _FORCE_INLINE_ void split_double(double a, float *ahi, float *alo) { + const double SPLITTER = (1 << 29) + 1; + double t = a * SPLITTER; + double thi = t - (t - a); + double tlo = a - thi; + *ahi = (float)thi; + *alo = (float)tlo; + } +#endif + /* Samplers */ _FORCE_INLINE_ RID sampler_rd_get_default(RS::CanvasItemTextureFilter p_filter, RS::CanvasItemTextureRepeat p_repeat) { diff --git a/servers/rendering/renderer_rd/storage_rd/render_scene_data_rd.cpp b/servers/rendering/renderer_rd/storage_rd/render_scene_data_rd.cpp index f925f87cbe..7dd790d1da 100644 --- a/servers/rendering/renderer_rd/storage_rd/render_scene_data_rd.cpp +++ b/servers/rendering/renderer_rd/storage_rd/render_scene_data_rd.cpp @@ -59,6 +59,12 @@ void RenderSceneDataRD::update_ubo(RID p_uniform_buffer, RS::ViewportDebugDraw p RendererRD::MaterialStorage::store_transform(cam_transform, ubo.inv_view_matrix); RendererRD::MaterialStorage::store_transform(cam_transform.affine_inverse(), ubo.view_matrix); +#ifdef REAL_T_IS_DOUBLE + RendererRD::MaterialStorage::split_double(-cam_transform.origin.x, &ubo.inv_view_matrix[12], &ubo.inv_view_matrix[3]); + RendererRD::MaterialStorage::split_double(-cam_transform.origin.y, &ubo.inv_view_matrix[13], &ubo.inv_view_matrix[7]); + RendererRD::MaterialStorage::split_double(-cam_transform.origin.z, &ubo.inv_view_matrix[14], &ubo.inv_view_matrix[11]); +#endif + for (uint32_t v = 0; v < view_count; v++) { projection = correction * view_projection[v]; RendererRD::MaterialStorage::store_camera(projection, ubo.projection_matrix_view[v]); |