MaidPlacementUtility.cs 5.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148
  1. using System.Collections.Generic;
  2. using UnityEngine;
  3. namespace COM3D2.MeidoPhotoStudio.Plugin
  4. {
  5. internal static class MaidPlacementUtility
  6. {
  7. private static readonly float pi = Mathf.PI;
  8. private static readonly float tau = Mathf.PI * 2f;
  9. public static readonly string[] placementTypes = {
  10. "horizontalRow", "verticalRow", "diagonalRow", "diagonalRowInverse", "wave", "waveInverse",
  11. "v", "vInverse", "circleInner", "circleOuter", "fanInner", "fanOuter"
  12. };
  13. public static int AlternatingSequence(int x)
  14. {
  15. return (int)((x % 2 == 0 ? 1 : -1) * Mathf.Ceil(x / 2f));
  16. }
  17. public static void ApplyPlacement(string placementType, IList<Meido> list)
  18. {
  19. switch (placementType)
  20. {
  21. case "horizontalRow": PlacementRow(list, false); break;
  22. case "verticalRow": PlacementRow(list, true); break;
  23. case "diagonalRow": PlacementDiagonal(list, false); break;
  24. case "diagonalRowInverse": PlacementDiagonal(list, true); break;
  25. case "wave": PlacementWave(list, false); break;
  26. case "waveInverse": PlacementWave(list, true); break;
  27. case "v": PlacementV(list, false); break;
  28. case "vInverse": PlacementV(list, true); break;
  29. case "circleOuter": PlacementCircle(list, false); break;
  30. case "circleInner": PlacementCircle(list, true); break;
  31. case "fanInner": PlacementFan(list, false); break;
  32. case "fanOuter": PlacementFan(list, true); break;
  33. default: return;
  34. }
  35. }
  36. public static void PlacementRow(IList<Meido> list, bool vertical = false)
  37. {
  38. for (int i = 0; i < list.Count; i++)
  39. {
  40. Vector3 position = Vector3.zero;
  41. Maid maid = list[i].Maid;
  42. float a = AlternatingSequence(i) * 0.6f;
  43. if (vertical) position.z = a;
  44. else position.x = a;
  45. maid.SetPos(position);
  46. maid.SetRot(Vector3.zero);
  47. }
  48. }
  49. public static void PlacementDiagonal(IList<Meido> list, bool inverse = false)
  50. {
  51. for (int i = 0; i < list.Count; i++)
  52. {
  53. Maid maid = list[i].Maid;
  54. float z = AlternatingSequence(i) * 0.5f;
  55. maid.SetPos(inverse ? new Vector3(z, 0, -z) : new Vector3(z, 0, z));
  56. maid.SetRot(Vector3.zero);
  57. }
  58. }
  59. public static void PlacementWave(IList<Meido> list, bool inverse = false)
  60. {
  61. for (int i = 0; i < list.Count; i++)
  62. {
  63. Maid maid = list[i].Maid;
  64. float x = AlternatingSequence(i) * 0.4f;
  65. float z = (inverse ? -1 : 1) * Mathf.Cos(AlternatingSequence(i) * pi) * 0.35f;
  66. maid.SetPos(new Vector3(x, 0, z));
  67. maid.SetRot(Vector3.zero);
  68. }
  69. }
  70. public static void PlacementV(IList<Meido> list, bool inverse = false)
  71. {
  72. for (int i = 0; i < list.Count; i++)
  73. {
  74. Maid maid = list[i].Maid;
  75. float x = AlternatingSequence(i) * 0.4f;
  76. float z = (inverse ? 1 : -1) * Mathf.Abs(AlternatingSequence(i)) * 0.4f;
  77. maid.SetPos(new Vector3(x, 0, z));
  78. maid.SetRot(Vector3.zero);
  79. }
  80. }
  81. public static void PlacementCircle(IList<Meido> list, bool inner = false)
  82. {
  83. int maidCount = list.Count;
  84. float radius = (0.3f + 0.1f * maidCount);
  85. for (int i = 0; i < maidCount; i++)
  86. {
  87. Maid maid = list[i].Maid;
  88. float angle = (pi / 2f) + tau * AlternatingSequence(i) / maidCount;
  89. float x = Mathf.Cos(angle) * radius;
  90. float z = Mathf.Sin(angle) * radius;
  91. float rotation = Mathf.Atan2(x, z);
  92. if (inner) rotation += pi;
  93. maid.SetPos(new Vector3(x, 0, z));
  94. maid.SetRot(new Vector3(0, rotation * Mathf.Rad2Deg, 0));
  95. }
  96. }
  97. public static void PlacementFan(IList<Meido> list, bool outer = false)
  98. {
  99. int maidCount = list.Count;
  100. float radius = (0.2f + 0.2f * maidCount);
  101. list[0].Maid.SetPos(Vector3.zero);
  102. list[0].Maid.SetRot(Vector3.zero);
  103. for (int i = 1; i < maidCount; i++)
  104. {
  105. Maid maid = list[i].Maid;
  106. float angle = pi * AlternatingSequence(i - 1) / maidCount;
  107. float x = Mathf.Sin(angle) * radius;
  108. float z = Mathf.Cos(angle) * radius;
  109. float rotation = Mathf.Atan2(x, z);
  110. if (outer) rotation += pi;
  111. maid.SetPos(new Vector3(-x, 0, -z));
  112. maid.SetRot(new Vector3(0, rotation * Mathf.Rad2Deg, 0));
  113. }
  114. }
  115. }
  116. }