0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

VATからSkinMatrixを復元する関数の実装メモ

Last updated at Posted at 2025-02-09

実装

vec4 fetchElement(float JointIndex, int Offset, float v)
{
    float texelSizeX = 1.0 / vat_ubo.texW;

    vec2 st = vec2(float(JointIndex * 4 + Offset + 0.5) * texelSizeX, v);

    #ifdef USE_OPENGL
    vec4 val = texture(vertexAnimationTexture, st);
    #else
    vec4 val = texture(sampler2D(vertexAnimationTexture, vertexAnimationTextureSampler), st);
    #endif

    return val;
}

mat4 GetSkinMatFromVAT(uint JointIndex, int FrameIndex)
{
    float f_JointIndex = float(JointIndex);
    float texelSizeY = 1.0 / vat_ubo.texH;

    float v = (float(FrameIndex) + 0.5) * texelSizeY;

    mat4 SkinMatrix = mat4(
        fetchElement(f_JointIndex, 0, v),
        fetchElement(f_JointIndex, 1, v),
        fetchElement(f_JointIndex, 2, v),
        fetchElement(f_JointIndex, 3, v)
    );
    
    return SkinMatrix;
}

void main()
{
    mat4 SkinMat =
        inWeights0.x * GetSkinMatFromVAT(inJoint0.x, CurrentFrame) +
        inWeights0.y * GetSkinMatFromVAT(inJoint0.y, CurrentFrame) +
        inWeights0.z * GetSkinMatFromVAT(inJoint0.z, CurrentFrame) +
        inWeights0.w * GetSkinMatFromVAT(inJoint0.w, CurrentFrame);
}

ポイント

// テクスチャに焼いたデータを使う時はテクセルの中心からサンプリングすることを心がける(texelSizeX * 0.5 を足す)
// これを足さない時の値はテクセルの左下、つまりテクセルとテクセルの境界線を差している
// もしこのままだと補完時にとなりのテクセルの影響を受けて、意図しない値が返ってくることがある
// この結果、ボーンの動きがブレたり、不安定になるといったことが起こる。
// VATにはGL_RGBA32F, GL_FLOATのテクスチャに対して、GL_NEAREST・CLAMP_TO_EDGEのサンプラーを適応している
// GL_NEARESTはサンプリングに最も近い値に補完して返す機能だが、テクセル境界のままだとこれで混ざってしまう
// 用語整理 /////
// - ピクセル: 画面上の最小単位(ディスプレイのドット)
// - テクセル: テクスチャ画像内の最小単位(テクスチャのピクセル)
////////////////

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?