简体   繁体   中英

How can you access elements from a fixed buffer in a struct?

I am trying to do this, however it seems that nothing ever gets assigned to BoneIDs or BoneWeights , what is the proper way of doing this in C#?

public unsafe struct VertexBoneData
{
    public Vector3 Position;
    public Vector3 Normal;
    public Vector2 TexCoord;
    public fixed float BoneIDs[Bone.MaxBoneCount];
    public fixed float BoneWeights[Bone.MaxBoneCount];

    public float GetBoneID(int i)
    {
        return BoneIDs[i];
    }

    public void SetBoneID(int i, float value)
    {
        BoneIDs[i] = value;
    }

    public float GetBoneWeight(int i)
    {
        return BoneWeights[i];
    }

    public void SetBoneWeight(int i, float value)
    {
         BoneWeights[i] = value;
    }
}

What you have is fine, broadly speaking (personally I'd make the fixed buffer fields private , and add some range checks on i ). I strongly suspect that what you're actually fighting with here is pass-by-value semantics, in which you're operating on an isolated copy of the value. Here's a fully runnable demo with your type "as is" (no changes) that shows everything working fine:


using System;

static class Program
{
    static void Main()
    {
        VertexBoneData data = new VertexBoneData();
        data.SetBoneID(3, 42F);
        Console.WriteLine(data.GetBoneID(3)); // writes 42

        // here's what I *suspect* you're doing
        SomePassByValueMethod(data);
        Console.WriteLine(data.GetBoneID(3)); // still writes 42, not 16

        // here's one way to fix that
        SomePassByReferenceMethod(ref data);
        Console.WriteLine(data.GetBoneID(3)); // writes 122
    }
    static void SomePassByValueMethod(VertexBoneData data)
    {
        data.SetBoneID(3, 16F);
    }
    static void SomePassByReferenceMethod(ref VertexBoneData data)
    {
        data.SetBoneID(3, 122F);
    }
}
public unsafe struct VertexBoneData
{
    public Vector3 Position;
    public Vector3 Normal;
    public Vector2 TexCoord;
    public fixed float BoneIDs[Bone.MaxBoneCount];
    public fixed float BoneWeights[Bone.MaxBoneCount];

    public float GetBoneID(int i)
    {
        return BoneIDs[i];
    }

    public void SetBoneID(int i, float value)
    {
        BoneIDs[i] = value;
    }

    public float GetBoneWeight(int i)
    {
        return BoneWeights[i];
    }

    public void SetBoneWeight(int i, float value)
    {
        BoneWeights[i] = value;
    }
}
static class Bone
{
    public const int MaxBoneCount = 4; // whatever
}

// just avoiding a dependency here, since I'm in a console exe
public readonly struct Vector3 { }
public readonly struct Vector2 { }

Use Marshal Technique

        const int MaxBoneCount = 10;
        public struct VertexBoneData
        {
            public Vector3 Position;
            public Vector3 Normal;
            public Vector2 TexCoord;
            [MarshalAs(UnmanagedType.I4, SizeConst = MaxBoneCount)]
            public float BoneIDs[];
            [MarshalAs(UnmanagedType.I4, SizeConst = MaxBoneCount)]
            public float BoneWeights[];
        }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM