Реализация 32-битного вершинного шейдера карты высот в ThreeJS
Я пытаюсь переназначить найденный пример карты высотВот в тот, который будет работать с 32-битной точностью вместо 8. Код незавершенного производства находится на github:https://github.com/bgourlie/three_heightmap
Карта высот создается в .NET. Высоты находятся в пределах 0f ... 200f и преобразуются в 32-битное значение цвета (Unity'sЦветовая структура) используя следующий метод:
private static Color DepthToColor(float height)
{
var depthBytes = BitConverter.GetBytes(height);
int enc = BitConverter.ToInt32(depthBytes, 0);
return new Color((enc >> 24 & 255)/255f, (enc >> 16 & 255)/255f, (enc >> 8 & 255)/255f,
(enc & 255)/255f);
}
Данные о цвете кодируются как png, а результат выглядит следующим образом:
Вершинный шейдер берет эти данные изображения и покрывает значения RBGA обратно к исходному значению высоты (используя технику, ответ на мой вопросВот):
uniform sampler2D bumpTexture; // defined in heightmap.js
varying float vAmount;
varying vec2 vUV;
void main()
{
vUV = uv;
vec4 bumpData = texture2D( bumpTexture, uv );
vAmount = dot(bumpData, vec4(1.0, 255.0, 65025.0, 16581375.0));
// Uncomment to see a "flatter" version
//vAmount = dot(bumpData, vec4(1.0, 1.0/255.0, 1.0/65025.0, 1.0/160581375.0));
// move the position along the normal
vec3 newPosition = position + normal * vAmount;
gl_Position = projectionMatrix * modelViewMatrix * vec4( newPosition, 1.0 );
}
Результат определенно испорчен:
Я могу сделать это лучше, изменив эту строку:
vAmount = dot(bumpData, vec4(1.0, 1.0/255.0, 1.0/65025.0, 1.0/16581375.0));
Это даст мне намного более плоское изображение, которое по крайней мере показывает хороший контур сгенерированного ландшафта, но с почти полностью плоской плоскостью (есть небольшое, хотя и незаметное изменение):
Я предполагаю, что делаю несколько вещей неправильно, я просто не знаю что. Я не уверен, правильно ли я кодирую оригинальный float. Я не уверен, правильно ли я декодирую его в вершинном шейдере (полученное значение находится вне диапазона 0 ... 200). Я также не очень опытный в 3D-графике в целом. Так что любые указания относительно того, что я делаю неправильно, или вообще, как этого добиться, будут с благодарностью.
Опять же, самодостаточный код незавершенного производства можно найти здесь:https://github.com/bgourlie/three_heightmap