How to change sprite mesh using ISpriteMeshDataProvider?

I can’t seem to figure out how to change a sprite mesh using ISpriteMeshDataProvider
It seems to do nothing?

I have a custom scriptable object that references a texture. Here is a simple content menu method that updates the sprite meshes on the texture:

[ContextMenu("Update Meshes")]
private void UpdateMeshes() {

    Texture2D tex = AssetDatabase.LoadAssetAtPath<Texture2D>(texturePath);

    var factory = new SpriteDataProviderFactories();
    factory.Init();

    var dataProvider = factory.GetSpriteEditorDataProviderFromObject(tex);
    dataProvider.InitSpriteEditorDataProvider();

    var meshProvider = dataProvider.GetDataProvider<ISpriteMeshDataProvider>();
    var spriteRects = dataProvider.GetSpriteRects();

    foreach (SpriteRect sr in spriteRects) {

        if (TryGetGeometry(sr.name, out SpriteGeometry geometry)) {

            geometry.Apply(sr, meshProvider);
        }
    }

    dataProvider.Apply();

    AssetDatabase.ImportAsset(texturePath);
}

The scriptable object contains an array of SpriteGeometry objects that define the mesh data for each sprite.
The Apply function looks like this:

class SpriteGeometry {

    public void Apply(SpriteRect rect, ISpriteMeshDataProvider dataProvider) {

        GUID guid = rect.spriteID;

        Vertex2DMetaData[] verts = new Vertex2DMetaData[vertices.Length];           

        for (int i = 0; i < vertices.Length; i++) {

            Vector2 position = vertices[i];

            verts[i] = new Vertex2DMetaData() {
                position = position
            };
        }
       
        Vector2Int[] edges = new Vector2Int[vertices.Length / 2];

        for (int i = 0; i < edges.Length; i++) {

            int edge = i * 2;

            edges[i] = new Vector2Int(edge, edge + 1);
        }

        int[] indices = new int[triangles.Length];

        for (int i = 0; i < triangles.Length; i++) {

            indices[i] = triangles[i];
        }

        dataProvider.SetVertices(guid, verts);
        dataProvider.SetIndices(guid, indices);
        dataProvider.SetEdges(guid, edges);
    }
}

But nothing happens after re-importing the texture?

How should I be using ISpriteMeshDataProvider to change sprite meshes?

You have several steps between the texture asset on disk and those other factories and providers.

Whatever object you are sticking in to SO that is showing up null actually MUST be written to disk before you reference it in the ScriptableObject, and order actually matters.

This will fail 100%:

  • create an X asset
  • assign a reference to that asset in a scriptable object
  • write X asset to disk (eg, add to asset database)

This will succeed 100%:

  • create an X asset
  • write X asset to disk (eg, add to asset database)
  • assign a reference to that asset in a scriptable object

Essentially as it serializes the fields in the SO, anything not already on disk fails to stick.

Is that perhaps what is going on? I don’t know those intermediate objects well enough but they have to exist on disk to refer to them in the SO.

Not sure I follow. The texture and geometry SO are already imported on disk.
This is a context menu function to update sprite meshes.

What’s interesting, is that I can use ISpriteOutlineDataProvider and change outlines just fine. But the ISpriteMeshDataProvider doesn’t seem to make any changes.

Maybe I’m misunderstanding what ISpriteMeshDataProvider is used for?

I want to change the sprites mesh used for rendering. I know you can use Sprite.OverrideGeometry, but that can only be called from AssetPostprocessor.OnPostProcessSprites, which I don’t want.

Essentially, I want to do what Sprite.OverrideGeometry does, but using a ISpriteMeshDataProvider.
Am I misunderstanding the usage here?