2
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

インスペクタでListを編集した際に、条件で要素を取り除く

Last updated at Posted at 2024-04-18

目的

SerializeField属性でインスペクタにListを表示している場合、編集時に条件で要素をフィルターしたい。

結論

ISerializationCallbackReceiverを実装し、OnBeforeSerialize()内でListを編集する。
ScriptableObjectをインスペクタで表示した場合を想定したコードを下記に示す。

using System;
using System.Collections.Generic;
using System.Linq;
using UnityEngine;

public enum SomeEnum
{
    None, 
    A, 
    B, 
    C
}

[Serializable]
public class SomeSerializableClass
{
    [SerializeField]
    SomeEnum type;
    public SomeEnum Type => type;
}

public class SomeScriptableObject : ScriptableObject, ISerializationCallbackReceiver
{
    [SerializeField]
    List<SomeSerializableClass> list;

    int prevCount;

    void Awake()
    {
        prevCount = list.Count;
    }

    public void OnAfterDeserialize() { }
    public void OnBeforeSerialize()
    {
        if (list is null)
        {
            return;
        }
        
        if (prevCount < list.Count)
        {
            list[^1] = new();
        }

        list = list
            .GroupBy(x => x.Type)
            .Select(x => x.First())
            .ToList();

        prevCount = list.Count;
    }
}

失敗例

下記コードは、インスペクタ上で要素の追加ができなくなる。
インスペクタで要素を追加した時、最後の要素が複製されて追加されるが、それが重複とみなされ排除されてしまうためである。

public class SomeBehaviour : MonoBehaviour, ISerializationCallbackReceiver
{
    [SerializeField]
    List<SomeSerializableClass> list;

    public void OnAfterDeserialize() { }
    public void OnBeforeSerialize()
    {
        if (list is null)
        {
            return;
        }

        list = list
            .GroupBy(x => x.Type)
            .Select(x => x.First())
            .ToList();
}

参考

2
3
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
2
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?