отсортировать масиив по глубине ветвей (все дочерние элементы следуют за родителем)

Есть массив данных, который необходимо отсортировать:

    const array = [{
      _id: 5,
      title: 'vueJS',
      parent: {_id: 3}
    }, {
      _id: 6,
      title: 'reactJS',
      parent: {_id: 3}
    }, {
      _id: 3,
      title: 'js',
      parent: {_id: 1}
    }, {
      _id: 1,
      title: 'dev',
      parent: null
    }, {
      _id: 4,
      title: 'photoshop',
      parent: {_id: 2}
    }, {
      _id: 2,
      title: 'UX',
      parent: null
    }];
    ```
Вернуть так же плоский массив но уже с другим порядком (дочерние элементы после родительских): 

    ```
    array = [{
        _id: 1,
          title: 'dev',
          parent: null
        }, {
        _id: 3,
          title: 'js',
          parent: {_id: 1}
        }, {
        _id: 5,
          title: 'vueJS',
          parent: {_id: 3}
        }, {
        _id: 6,
          title: 'reactJS',
          parent: {_id: 3}
        }, {
        _id: 2,
          title: 'UX',
          parent: null
        }, {
          _id: 4,
          title: 'photoshop',
          parent: {_id: 2}
        }];
    ```
Дополнительно.
Глубину можно показать добавив символ в начало title: 
    ```
    array = [{
        _id: 1,
          title: 'dev',
          parent: null
        }, {
        _id: 3,
          title: '-js',
          parent: {_id: 1}
        }, {
        _id: 5,
          title: '--vueJS',
          parent: {_id: 3}
        }, {
        _id: 6,
          title: '--reactJS',
          parent: {_id: 3}
        }, {
        _id: 2,
          title: 'UX',
          parent: null
        }, {
          _id: 4,
          title: '-photoshop',
          parent: {_id: 2}
        }];
    ```

Ответы (3 шт):

Автор решения: rureeru
    const array = [{
        _id: 5,
        title: 'vueJS',
        parent: {_id: 3}
      }, {
        _id: 6,
        title: 'reactJS',
        parent: {_id: 3}
      }, {
        _id: 3,
        title: 'js',
        parent: {_id: 1}
      }, {
        _id: 1,
        title: 'dev',
        parent: null
      }, {
        _id: 4,
        title: 'photoshop',
        parent: {_id: 2}
      }, {
        _id: 2,
        title: 'UX',
        parent: null
      }];
    
    const convert = (data) => {
        // создаем ассоциативный массив с ключами айдишниками и добавляем к элементу поле children
        let mapList = {}
        data.forEach(item => mapList[item._id] = { ...item, children: [] })
        // console.log(mapList)
    
        // собираем дерево
        let tree = []
        Object.values(mapList).forEach(item => {
            if (!item.parent) {
                tree.push(item)
            } else {
                console.log(mapList[item.parent._id])
                mapList[item.parent._id].children.push(item)
            }
        })
        // console.log(tree)
    
        // обходим дерево рекурсивно и отбираем данные с форматированным title
        const treeToFlatList = (tree, level = 0) => {
            let result = []
            tree.forEach(treeItem => {
                let { children, ...item } = treeItem
                item.title = '-'.repeat(level) + item.title
                result.push(item)
                result = result.concat(treeToFlatList(children, level + 1))
            })
            return result
        }
    
        return treeToFlatList(tree)
    }
    
    console.log(convert(array))

→ Ссылка
Автор решения: rureeru

    const array = [{
          _id: 5,
          title: 'vueJS',
          parent: {_id: 3}
        }, {
          _id: 6,
          title: 'reactJS',
          parent: {_id: 3}
        }, {
          _id: 3,
          title: 'js',
          parent: {_id: 1}
        }, {
          _id: 1,
          title: 'dev',
          parent: null
        }, {
          _id: 4,
          title: 'photoshop',
          parent: {_id: 2}
        }, {
          _id: 2,
          title: 'UX',
          parent: null
        }
    ];
        
    const getFullTree = (arr, parent = null, inner = 0) => {
      return arr.reduce((arr, elem) => {
        if (elem.parent && elem.parent._id !== parent) {
          return arr;
        }
        const title = inner 
          ? `${'-'.repeat(inner)}${elem.title}`
          : elem.title;
    
        arr.push({
          ...elem,
          title,
        });
    
        const children = array.filter((item) => item.parent && item.parent._id === elem._id);
        if(!children) {
          return arr;
        }
        const childArr = getFullTree(children, elem._id, inner + 1);
        return arr.concat(childArr);
      }, []);
    }
    
    const result = getFullTree(array);
    
    console.log('\n\nresult: ', result);
    
    // result = [
    // {_id: 1, title: 'dev',parent: null}, 
    // { _id: 3, title: '-js',  parent: {_id: 1}},
    // {_id: 5, title: '--vueJS', parent: {_id: 3} }, 
    // {_id: 6, title: '--reactJS', parent: {_id: 3} }, 
    // { _id: 2, title: 'UX', parent: null }, 
    // { _id: 4, title: '-photoshop', parent: {_id: 2} }
    // ];

→ Ссылка
Автор решения: rureeru

    const array = [{
          _id: 5,
          title: 'vueJS',
          parent: {_id: 3}
        }, {
          _id: 6,
          title: 'reactJS',
          parent: {_id: 3}
        }, {
          _id: 3,
          title: 'js',
          parent: {_id: 1}
        }, {
          _id: 1,
          title: 'dev',
          parent: null
        }, {
          _id: 4,
          title: 'photoshop',
          parent: {_id: 2}
        }, {
          _id: 2,
          title: 'UX',
          parent: null
        }
    ];
        
    const getFullTree = (rootArray) => {
  const getTree = (array, parent = null, inner = 0) => {
    return array.reduce((arr, elem) => {
      if (elem.parent && elem.parent._id !== parent) {
        return arr;
      }

      arr.push({
        ...elem,
        title: `${'-'.repeat(inner)}${elem.title}`,
      });

      const children = rootArray.filter((item) => item.parent && item.parent._id === elem._id);
      if(!children) {
        return arr;
      }
      const childArr = getTree(children, elem._id, inner + 1);
      return arr.concat(childArr);
    }, []);
  }
  return getTree(rootArray);
}
    
    // const result = getFullTree(array);
    
    console.log('result: ', getFullTree(array));
    
    // array = [
    // {_id: 1, title: 'dev',parent: null}, 
    // { _id: 3, title: '-js',  parent: {_id: 1}},
    // {_id: 5, title: '--vueJS', parent: {_id: 3} }, 
    // {_id: 6, title: '--reactJS', parent: {_id: 3} }, 
    // { _id: 2, title: 'UX', parent: null }, 
    // { _id: 4, title: '-photoshop', parent: {_id: 2} }
    // ];

→ Ссылка