Sort by Sibling Index

I need to sort a list of arbitrary transforms by their sibling index. But it has to be global.
Essentially I want them in the order they appear in the hierarchy and are rendered under the new UI system. But the transforms themselves can be from anywhere in the hierarchy.

For example, I might have references to the highlighted children and I need to sort them by the order they will be rendered by the new UI system.

34709-capture2.png

EDIT: clarified question

I think the following piece of code does what you want it to do (I didn’t fully test it yet, but I believe this should always work).

Note, this solution might be slow if you do it often, especially if your list is very long.

The code of the comparer:

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


public class Example : IComparer<Transform>
{
    public int Compare(Transform x, Transform y)
    {
        if (x == y)
            return 0;
        if (y.IsChildOf(x))
        {
            return -1;
        }
        if (x.IsChildOf(y))
        {
            return 1;
        }

        List<Transform> xparentList = GetParents(x);
        List<Transform> yparentList = GetParents(y);

        for (int xIndex = 0; xIndex < xparentList.Count; xIndex++)
        {
            if (y.IsChildOf(xparentList[xIndex]))
            {
                int yIndex = yparentList.IndexOf(xparentList[xIndex]) - 1;
                xIndex -= 1;
                return xparentList[xIndex].GetSiblingIndex() - yparentList[yIndex].GetSiblingIndex();
            }
        }

        return xparentList[xparentList.Count - 1].GetSiblingIndex() - yparentList[yparentList.Count - 1].GetSiblingIndex();
    }


    private List<Transform> GetParents(Transform t)
    {
        List<Transform> parents = new List<Transform>();
        parents.Add(t);

        while (t.parent != null)
        {
            parents.Add(t.parent);
            t = t.parent;
        }
        return parents;
    }
}

How you can use it:

public class Example2 : MonoBehaviour
{
    public Transform[] list;

    public void Start()
    {
        List<Transform> newList = new List<Transform>(list);

        newList.Sort(new Example());
        for (int i = 0; i < newList.Count; i++)
        {
            Debug.Log(newList*.name);*

}
}
}
Obviously you should rename the Example class if you use this :wink:

This function returns a list of all the children of the transform provided, in the order they would appear in the Hierarchy panel :

List<Transform> ChildTransformsSorted(Transform t) {

	List<Transform> sorted = new List<Transform>();

	for (int i = 0; i < t.childCount; i++) {

		Transform child = t.GetChild(i);

		sorted.Add( child );
		sorted.AddRange( ChildTransformsSorted(child) );
	}

	return sorted;
}

A few highlights :

  • The function works in a recursive way
  • The list does not include the transform passed as a parameter