SafetyAreaEightNeighbourHelper.cs 3.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106
  1. using System;
  2. using System.Collections;
  3. using System.Collections.Generic;
  4. using UnityEngine;
  5. public class SafetyAreaEightNeighbourHelper
  6. {
  7. private static List<int> edgeVertexIndexList = new List<int>();
  8. private static Dictionary<int, int> eightNeighboursDic = new Dictionary<int, int>()
  9. {
  10. { 0, 6},
  11. { 1, 6},
  12. { 2, 0},
  13. { 3, 0},
  14. { 4, 2},
  15. { 5, 2},
  16. { 6, 4},
  17. { 7, 4}
  18. };
  19. /// <summary>
  20. /// 1 2 3
  21. /// 0 x 4
  22. /// 7 6 5
  23. /// </summary>
  24. private static Dictionary<int, Func<int, int>> eightNeighboursIndexCaculatorDic = new Dictionary<int, Func<int, int>>()
  25. {
  26. { 0, (index) => { return index - 1; } },
  27. { 1, (index) => { return index - 1 + PlayAreaConstant.GRID_SIZE + 1 ; } },
  28. { 2, (index) => { return index + PlayAreaConstant.GRID_SIZE + 1; } },
  29. { 3, (index) => { return index + 1 + PlayAreaConstant.GRID_SIZE + 1; } },
  30. { 4, (index) => { return index + 1; } },
  31. { 5, (index) => { return index + 1 - (PlayAreaConstant.GRID_SIZE + 1); } },
  32. { 6, (index) => { return index - (PlayAreaConstant.GRID_SIZE + 1); } },
  33. { 7, (index) => { return index - 1 - (PlayAreaConstant.GRID_SIZE + 1); } }
  34. };
  35. public static void EightNeighbours(int startCaculateIndex, Func<int, bool> conditionFunc, Action<List<int>> onGetEdgeCallback)
  36. {
  37. int firstRedColorIndex = FindFirstConditionIndex(startCaculateIndex, conditionFunc);
  38. edgeVertexIndexList.Clear();
  39. EightNeighboursRecursion(0, firstRedColorIndex, conditionFunc, onGetEdgeCallback);
  40. }
  41. private static int loopCount = 0;
  42. private static void EightNeighboursRecursion(int neighbourIndex, int vertexIndex, Func<int, bool> condition, Action<List<int>> onGetEdgeCallback)
  43. {
  44. loopCount++;
  45. if (loopCount > 5000)
  46. {
  47. Debug.LogError("Too much loop");
  48. onGetEdgeCallback?.Invoke(edgeVertexIndexList);
  49. return;
  50. }
  51. Func<int, int> checkIndexFunc = eightNeighboursIndexCaculatorDic[neighbourIndex];
  52. int checkIndex = checkIndexFunc(vertexIndex);
  53. if (checkIndex >= 0 && checkIndex <= ((PlayAreaConstant.GRID_SIZE + 1) * (PlayAreaConstant.GRID_SIZE + 1) - 1) && condition(checkIndex))
  54. {
  55. if (edgeVertexIndexList.Contains(checkIndex))
  56. {
  57. //for (int i = 0; i < edgeVertexIndexList.Count; i++)
  58. //{
  59. // colors[edgeVertexIndexList[i]] = Color.yellow;
  60. //}
  61. //mesh.colors = colors;
  62. edgeVertexIndexList.Add(checkIndex);
  63. onGetEdgeCallback?.Invoke(edgeVertexIndexList);
  64. Debug.Log("LoopCount:" + loopCount);
  65. return;
  66. }
  67. else
  68. {
  69. edgeVertexIndexList.Add(checkIndex);
  70. int nextNeighbourIndex = eightNeighboursDic[neighbourIndex];
  71. EightNeighboursRecursion(nextNeighbourIndex, checkIndex, condition, onGetEdgeCallback);
  72. }
  73. }
  74. else
  75. {
  76. EightNeighboursRecursion((neighbourIndex + 1) % 8, vertexIndex, condition, onGetEdgeCallback);
  77. }
  78. }
  79. private static int FindFirstConditionIndex(int index, Func<int, bool> conditionFunc)
  80. {
  81. int rowIndex = index / (PlayAreaConstant.GRID_SIZE + 1);
  82. int startIndex = rowIndex * (PlayAreaConstant.GRID_SIZE + 1);
  83. if (index == startIndex)
  84. {
  85. return startIndex;
  86. }
  87. int currentIndex = 0;
  88. for (int i = 0; i < (PlayAreaConstant.GRID_SIZE + 1); i++)
  89. {
  90. currentIndex = startIndex + i;
  91. if (conditionFunc(currentIndex))
  92. {
  93. break;
  94. }
  95. }
  96. return currentIndex;
  97. }
  98. }