2
0

shaderMethods.h 4.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  1. // zlib open source license
  2. //
  3. // Copyright (c) 2017 to 2023 David Forsgren Piuva
  4. //
  5. // This software is provided 'as-is', without any express or implied
  6. // warranty. In no event will the authors be held liable for any damages
  7. // arising from the use of this software.
  8. //
  9. // Permission is granted to anyone to use this software for any purpose,
  10. // including commercial applications, and to alter it and redistribute it
  11. // freely, subject to the following restrictions:
  12. //
  13. // 1. The origin of this software must not be misrepresented; you must not
  14. // claim that you wrote the original software. If you use this software
  15. // in a product, an acknowledgment in the product documentation would be
  16. // appreciated but is not required.
  17. //
  18. // 2. Altered source versions must be plainly marked as such, and must not be
  19. // misrepresented as being the original software.
  20. //
  21. // 3. This notice may not be removed or altered from any source
  22. // distribution.
  23. #ifndef DFPSR_RENDER_SHADER_METHODS
  24. #define DFPSR_RENDER_SHADER_METHODS
  25. #include <cstdint>
  26. #include "../../math/FVector.h"
  27. #include "../../math/scalar.h"
  28. #include "../../base/simd3D.h"
  29. #include "../../api/textureAPI.h"
  30. #include "shaderTypes.h"
  31. #include "../constants.h"
  32. namespace dsr {
  33. namespace shaderMethods {
  34. // Returns the linear interpolation of the values using corresponding weight ratios for A, B and C in 4 pixels at the same time.
  35. inline F32x4 interpolate(const FVector3D &vertexData, const F32x4x3 &vertexWeights) {
  36. F32x4 vMA = vertexData.x * vertexWeights.v1;
  37. F32x4 vMB = vertexData.y * vertexWeights.v2;
  38. F32x4 vMC = vertexData.z * vertexWeights.v3;
  39. return vMA + vMB + vMC;
  40. }
  41. inline Rgba_F32x4 interpolateVertexColor(const FVector3D &red, const FVector3D &green, const FVector3D &blue, const FVector3D &alpha, const F32x4x3 &vertexWeights) {
  42. return Rgba_F32x4(
  43. interpolate(red, vertexWeights),
  44. interpolate(green, vertexWeights),
  45. interpolate(blue, vertexWeights),
  46. interpolate(alpha, vertexWeights)
  47. );
  48. }
  49. // TODO: Implement sparse computation of floating-point mip levels in a grid, which can increase the density when getting closer to a horizon.
  50. // TODO: Let RgbaMultipy generate additional template instances, especially for SQUARE and MIP_INSIDE which are common.
  51. // If the texture has at least 5 mip levels, MIP_INSIDE can be true.
  52. // For the majority of textures that are square, SQUARE can be true.
  53. template<
  54. Interpolation INTERPOLATION,
  55. bool SQUARE = false,
  56. bool SINGLE_LAYER = false,
  57. bool XY_INSIDE = false,
  58. bool MIP_INSIDE = false,
  59. bool HIGHEST_RESOLUTION = false
  60. >
  61. inline U32x4 sample_U32(const TextureRgbaU8 *source, const F32x4 &u, const F32x4 &v) {
  62. if (INTERPOLATION == Interpolation::NN) {
  63. if (HIGHEST_RESOLUTION) {
  64. return texture_sample_nearest<SQUARE, SINGLE_LAYER, MIP_INSIDE, HIGHEST_RESOLUTION, U32x4, F32x4>(*source, u, v, U32x4(0u));
  65. } else {
  66. // TODO: Calculate MIP levels using a separate rendering stage with sparse resolution writing results into thread-local memory.
  67. uint32_t mipLevel = texture_getMipLevelIndex<F32x4>(*source, u, v);
  68. return texture_sample_nearest<SQUARE, SINGLE_LAYER, MIP_INSIDE, HIGHEST_RESOLUTION, U32x4, F32x4>(*source, u, v, U32x4(mipLevel));
  69. }
  70. } else {
  71. if (HIGHEST_RESOLUTION) {
  72. return texture_sample_bilinear<SQUARE, SINGLE_LAYER, MIP_INSIDE, HIGHEST_RESOLUTION, U32x4, U16x8, F32x4>(*source, u, v, U32x4(0u));
  73. } else {
  74. uint32_t mipLevel = texture_getMipLevelIndex<F32x4>(*source, u, v);
  75. return texture_sample_bilinear<SQUARE, SINGLE_LAYER, MIP_INSIDE, HIGHEST_RESOLUTION, U32x4, U16x8, F32x4>(*source, u, v, U32x4(mipLevel));
  76. }
  77. }
  78. }
  79. template<Interpolation INTERPOLATION,
  80. bool SQUARE = false,
  81. bool SINGLE_LAYER = false,
  82. bool XY_INSIDE = false,
  83. bool MIP_INSIDE = false,
  84. bool HIGHEST_RESOLUTION = false
  85. >
  86. inline Rgba_F32<U32x4, F32x4> sample_F32(const TextureRgbaU8 *source, const F32x4 &u, const F32x4 &v) {
  87. return Rgba_F32<U32x4, F32x4>(sample_U32<INTERPOLATION, SQUARE, SINGLE_LAYER, XY_INSIDE, MIP_INSIDE, HIGHEST_RESOLUTION>(source, u, v));
  88. }
  89. }
  90. }
  91. #endif