Unity3D技术之绘制曲线详解

本文介绍如何在Unity中不依赖ITweenPath插件实现游戏对象平滑路径移动。通过自定义PointPath类和PointController类,可以获取并绘制平滑路径上的点。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

为了平滑游戏对象在 Unity 中的行进路线,我们经常会在 Unity 中使用 ITweenPath 插件,但有时候我们或许只会使用到通过 ITweenPath 绘制出来的点(比如把这些点放到配置文件中),并不希望加载 ITweenPath 插件或者通过自己的函数去实现游戏对象的移动,通过查看 ITweenPath 的代码,很容易就把 ITweenPath 绘制曲线点的方法给提取出来了,主函数并不多,只有三个方法,希望能给你带来帮助! 

先来看看最终的 Demo 实现方式: 

 

 

Demo 代码: 

1. </blockquote></div>

2. <div class="blockcode"><blockquote>using UnityEngine;using System.Collections.Generic;

3. public class PointPath : MonoBehaviour {

4. private Vector3[] pathList;

5. public GameObject sphere;

6. public GameObject path;

7. void Awake()

8. {

9. Transform[] transformList = path.GetComponentsInChildren<Transform> ();

10. int length = transformList.Length;

11. pathList = new Vector3[length];

12. 

13. for (int index = 0; index < length; index ++)

14. {

15. pathList[index] = transformList[index].transform.position;

16. } 

17. 

18. Vector3[] resultList = PointController.PointList (this.pathList, 20);

19. 

20. foreach (Vector3 point in resultList)

21. { 

22. 

23. GameObject gameObject = (GameObject)Instantiate(sphere); 

24. gameObject.transform.localPosition = point; 

25. gameObject.transform.localScale = new Vector3(0.5f, 0.5f, 0.5f);

26. }

27. }

28. PointController.cs 

29. 

30. using UnityEngine;

31. using System;

32. using System.Collections;

33. public class PointController{

34. 

35. /// <summary> 

36. /// 获取曲线上面的所有点

37. 

38. /// </summary>

39. 

40. /// <returns>The list.</returns>

41. /// <param name="path">需要穿过的点列表</param>

42. 

43. /// <param name="pointSize">两个点之间的节点数量</param>

44. public static Vector3[] PointList(Vector3[] path, int pointSize)

45. {

46. 

47. Vector3[] controlPointList = PathControlPointGenerator(path); 

48. int smoothAmount = path.Length * pointSize;

49. 

50. Vector3[] pointList = new Vector3[smoothAmount]; 

51. for (int index = 1; index <= smoothAmount; index++)

52. {

53. 

54. Vector3 currPt = Interp(controlPointList, (float) index / smoothAmount); 

55. pointList[index - 1] = currPt;

56. 

57. 

58. }

59. return pointList;

60. 

61. 

62. }

63. /// <summary>

64. 

65. 

66. /// 获取控制点

67. /// </summary>

68. /// <returns>The control point generator.</returns>

69. /// <param name="path">Path.</param>

70. 

71. 

72. private static Vector3[] PathControlPointGenerator(Vector3[] path)

73. {

74. int offset = 2;

75. 

76. 

77. Vector3[] suppliedPath = path;

78. 

79. 

80. Vector3[] controlPoint = new Vector3[suppliedPath.Length + offset];

81. 

82. 

83. Array.Copy(suppliedPath, 0, controlPoint, 1, suppliedPath.Length);

84. 

85. 

86. controlPoint[0] = controlPoint[1] + (controlPoint[1] - controlPoint[2]);

87. 

88. 

89. controlPoint[controlPoint.Length - 1] = controlPoint[controlPoint.Length - 2] + (controlPoint[controlPoint.Length - 2] - controlPoint[controlPoint.Length - 3]); 

90. 

91. 

92. if(controlPoint[1] == controlPoint[controlPoint.Length - 2])

93. {

94. Vector3[] tmpLoopSpline = new Vector3[controlPoint.Length];

95. 

96. 

97. Array.Copy(controlPoint, tmpLoopSpline, controlPoint.Length);

98. 

99. 

100. tmpLoopSpline[0] = tmpLoopSpline[tmpLoopSpline.Length - 3];

101. 

102. 

103. tmpLoopSpline[tmpLoopSpline.Length - 1] = tmpLoopSpline[2];

104. 

105. 

106. controlPoint = new Vector3[tmpLoopSpline.Length]; 

107. 

108. 

109. Array.Copy(tmpLoopSpline, controlPoint, tmpLoopSpline.Length);

110. }

111. return(controlPoint);

112. }

113. /// <summary>

114. /// 根据 获取曲线上面的点位置

115. /// </summary>

116. 

117. 

118. /// <param name="pts">Pts.</param>

119. /// <param name="t">T.</param>

120. 

121. 

122. private static Vector3 Interp(Vector3[] pts, float t)

123. {

124. int numSections = pts.Length - 3;

125. int currPt = Mathf.Min(Mathf.FloorToInt(t * (float) numSections), numSections - 1);

126. 

127. 

128. float u = t * (float) numSections - (float) currPt;

129. 

130. 

131. Vector3 a = pts[currPt];

132. 

133. 

134. Vector3 b = pts[currPt + 1];

135. Vector3 c = pts[currPt + 2];

136. Vector3 d = pts[currPt + 3];

137. 

138. 

139. return .5f * (                        (-a + 3f * b - 3f * c + d) * (u * u * u)                        + (2f * a - 5f * b + 4f * c - d) * (u * u)                        + (-a + c) * u                        + 2f * b                        );

140. } 

141. } 

希望本文章对大家有所帮助...

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值