C# 统一体中动态变化的对象速度
我需要一个对象根据动态计时上下移动。确切位置存储在名为Timings的列表()中。这将包含排序的条目,如0.90 1.895 2.64 3.98。。。这些计时与音乐的播放有关,因此可以与音乐时间进行比较。(音乐是我的音源) 现在(参见下面的代码),它使用moveSpeed静态地上下移动。我如何使其在预定义的时间达到顶部和底部?当到达计时列表的末尾时,移动应停止C# 统一体中动态变化的对象速度,c#,unity3d,C#,Unity3d,我需要一个对象根据动态计时上下移动。确切位置存储在名为Timings的列表()中。这将包含排序的条目,如0.90 1.895 2.64 3.98。。。这些计时与音乐的播放有关,因此可以与音乐时间进行比较。(音乐是我的音源) 现在(参见下面的代码),它使用moveSpeed静态地上下移动。我如何使其在预定义的时间达到顶部和底部?当到达计时列表的末尾时,移动应停止 public class Patrol : MonoBehaviour { public Transform[] patrol
public class Patrol : MonoBehaviour {
public Transform[] patrolPoints; //contains top and bottom position
public float moveSpeed; //needs to be changed dynamically
private int currentPoint;
// Initialization
void Start () {
transform.position = patrolPoints [0].position;
currentPoint = 0;
}
// Update is called once per frame
void Update () {
print (currentPoint);
if (currentPoint >= patrolPoints.Length) {
currentPoint = 0;
}
if (transform.position == patrolPoints [currentPoint].position) {
currentPoint++;
}
transform.position = Vector3.MoveTowards (transform.position, patrolPoints[currentPoint].position, moveSpeed * Time.deltaTime);
}
}
重要的是,不能偏离绝对时间点。例如,当计时达到1009这样的高时间时,应该不会有太大的漂移
还要注意,其他事情(如更改颜色和检查用户行为)需要同时进行,请参见我的 添加一个浮点数组,比如说
public float[]moveSpeedArray代码>
您可以在Start()
或编辑器中随意填充此数组
您已经在获取并更新您的currentPoint
将该currentPoint
作为moveSpeedArray
的索引
喜欢
这样,您就可以在不同的预定义时间将对象移动到不同的位置
希望这有帮助!干杯 不要重新发明轮子。使用两个库,例如。为您定义了20多种缓解类型:
示例代码:
iTween.MoveBy(gameObject,iTween.Hash(
"x" , 2,
"time", 0.2f
));
解决方案的路径是answer,它显示了随时间移动游戏对象的功能
有了这个函数,您可以启动一个协同程序,在包含beatsTimer
的列表上循环。在每个循环中,您应该有一个变量,用于确定在每个循环之后是向上还是向下。在我的示例中,我将该变量命名为upDownMoveDecider
。这个变量将决定使用patrolPoints
数组的哪个索引(我假设只有两个索引为0和1的点)
此外,每次都可以在for
循环中调用moveToX
函数。确保yield
it,以便在转到下一个函数之前,它将等待moveToX
函数完成或返回
下面是它应该是什么样子:
public Transform[] patrolPoints; //contains top and bottom position
List<float> beatsTimer = new List<float>();
public Transform objectToMove;
void Start()
{
//For testing purposes
beatsTimer.Add(0.90f);
beatsTimer.Add(1.895f);
beatsTimer.Add(2.64f);
beatsTimer.Add(3.98f);
//Start the moveobject
StartCoroutine(beginToMove());
}
IEnumerator beginToMove()
{
// 0 = move up, 1 = move down
int upDownMoveDecider = 0;
//Loop through the timers
for (int i = 0; i < beatsTimer.Count; i++)
{
if (upDownMoveDecider == 0)
{
//Move up
Debug.Log("Moving Up with time: " + beatsTimer[i] + " in index: " + i);
//Start Moving and wait here until move is complete(moveToX returns)
yield return StartCoroutine(moveToX(objectToMove, patrolPoints[upDownMoveDecider].position, beatsTimer[i]));
//Change direction to 1 for next move
upDownMoveDecider = 1;
}
else
{
//Move down
Debug.Log("Moving Down with time: " + beatsTimer[i] + " in index: " + i);
//Start Moving and wait here until move is complete(moveToX returns)
yield return StartCoroutine(moveToX(objectToMove, patrolPoints[upDownMoveDecider].position, beatsTimer[i]));
//Change direction to 0 for next move
upDownMoveDecider = 0;
}
}
}
IEnumerator moveToX(Transform fromPosition, Vector3 toPosition, float duration)
{
float counter = 0;
//Get the current position of the object to be moved
Vector3 startPos = fromPosition.position;
while (counter < duration)
{
counter += Time.deltaTime;
fromPosition.position = Vector3.Lerp(startPos, toPosition, counter / duration);
yield return null;
}
}
你的意思是像Senoid一样周期性地上下移动?它是一个随着音乐节拍(由时间列表定义)反弹的球,上下位置存储在哪里?巡逻点包含上下位置。嗨,出于某些原因,你发表评论时我没有得到通知。您可以使用@Programmer通知我。让我明确你的编辑…它在0.90秒内从上到下,然后在1.895秒内从下到上,然后在2.64秒内从上到下,最后在3.98秒内从下到上?如果是这样,当它到达列表末尾时会发生什么?停止清除名单?谢谢。我试过这个。但是,如果我在数组中放入[0.5 3]。移动速度要慢得多。5秒和3秒。时间单位可能是关闭的?可能是0.5*时间。deltaTime不等于0.5秒或3*时间。deltaTime不等于3秒?我现在不能证实这一点。如果没有,尝试使用不同的值,这些值将对应于秒,并得出一个公式@多里尼不得不改变你的一些建议。moveSpeedArray的索引不应是currentPoint,而应是另一个不断上升的计数器(不像currentPoint那样上下)。然后数组需要格式化为时间差,而不是绝对时间。然后它似乎起作用了。谢谢事实上,我还没有完全掌握,我认为,我应该考虑两个物体之间的距离,以便能够以规定的速度通过,从而使物体到达所需的计时窗口。这将如何帮助我使顶部/底部之间的时间精确到我在列表中确定的秒数?我是否正确理解iTween.MoveBy需要在每个“回合”执行一次,默认情况下它将线性移动?在您的示例中,x是它需要移动的x坐标?我想有人已经将另一个答复标记为答案,您最好使用该解决方案?谢谢,但这些时间加起来并不正确,很高兴我能够提供帮助。快乐编码!
public Transform[] patrolPoints; //contains top and bottom position
List<float> beatsTimer = new List<float>();
public Transform objectToMove;
void Start()
{
//For testing purposes
beatsTimer.Add(0.90f);
beatsTimer.Add(1.895f);
beatsTimer.Add(2.64f);
beatsTimer.Add(3.98f);
//Start the moveobject
StartCoroutine(beginToMove());
}
IEnumerator beginToMove()
{
// 0 = move up, 1 = move down
int upDownMoveDecider = 0;
//Loop through the timers
for (int i = 0; i < beatsTimer.Count; i++)
{
if (upDownMoveDecider == 0)
{
//Move up
Debug.Log("Moving Up with time: " + beatsTimer[i] + " in index: " + i);
//Start Moving and wait here until move is complete(moveToX returns)
yield return StartCoroutine(moveToX(objectToMove, patrolPoints[upDownMoveDecider].position, beatsTimer[i]));
//Change direction to 1 for next move
upDownMoveDecider = 1;
}
else
{
//Move down
Debug.Log("Moving Down with time: " + beatsTimer[i] + " in index: " + i);
//Start Moving and wait here until move is complete(moveToX returns)
yield return StartCoroutine(moveToX(objectToMove, patrolPoints[upDownMoveDecider].position, beatsTimer[i]));
//Change direction to 0 for next move
upDownMoveDecider = 0;
}
}
}
IEnumerator moveToX(Transform fromPosition, Vector3 toPosition, float duration)
{
float counter = 0;
//Get the current position of the object to be moved
Vector3 startPos = fromPosition.position;
while (counter < duration)
{
counter += Time.deltaTime;
fromPosition.position = Vector3.Lerp(startPos, toPosition, counter / duration);
yield return null;
}
}
//Loop through the timers
for (int i = 0; i < beatsTimer.Count; i++)
{
//Move up/Down depening on the upDownMoveDecider variable
string upDown = (upDownMoveDecider == 0) ? "Up" : "Down";
Debug.Log("Moving " + upDown + " with time: " + beatsTimer[i] + " in index: " + i);
//Start Moving and wait here until move is complete(moveToX returns)
yield return StartCoroutine(moveToX(objectToMove, patrolPoints[upDownMoveDecider].position, beatsTimer[i]));
//Change direction
upDownMoveDecider = (upDownMoveDecider == 1) ? 0 : 1;
}