/// <summary>
/// fly 在xy轴平面内,按bezier曲线移动
/// </summary>
private IEnumerator EnergyFly(GameObject fly, GObject target)
{
Vector3 start = fly.transform.position;//起始位置
Vector3 end = UIToWorldPos(target);//取fairGUI界面上的点作为目标位置
Vector3 between = BezierBetweenPos(start, end);
float fTime = 0f;
float tTime = Vector3.Distance(start, end) / 10;
while (fTime <= tTime)
{
fTime += Time.deltaTime;
Vector3 temp = Bezier3(start, between, end, fTime / tTime);
fly.transform.position = temp;
yield return new WaitForSeconds(0.01f);
}
}
/// <summary>
/// 将FairGUI界面上的点转到unity世界坐标
/// </summary>
private Vector3 UIToWorldPos(GObject obj)
{
Vector2 uiPos = GRoot.inst.LocalToGlobal(obj.LocalToRoot(Vector2.zero, GRoot.inst));
uiPos.y = Screen.height - uiPos.y;
Vector3 pos = Camera.main.ScreenToWorldPoint(uiPos);
pos.z = 0;
return pos;
}
/// <summary>
/// 取z轴为0
/// 将起始位置到终点位置线段的中垂线上的一个点,作为bezier曲线上的中间点
/// </summary>
private Vector3 BezierBetweenPos(Vector3 start, Vector3 end)
{
Vector3 move = end - start;
Vector3 between = start + new Vector3(move.x /= 2f, move.y /= 2f, move.z /= 2f);
if (move.y == 0) return between;
Vector2 vNormalize = new Vector2(1, -move.x / move.y);//将z轴设为0
vNormalize.Normalize();//向量标准化
between.x += vNormalize.x * Vector3.Distance(start, end);//将两点距离加在,中垂线交点上
between.y += vNormalize.y * Vector3.Distance(start, end);//将两点距离加在,中垂线交点上
between.z = 0;
return between;
}
Vector3 Bezier3(Vector3 p0, Vector3 p1, Vector3 p2, float t)
{
Vector3 p0p1 = (1 - t) * p0 + t * p1;
Vector3 p1p2 = (1 - t) * p1 + t * p2;
Vector3 result = (1 - t) * p0p1 + t * p1p2;
return result;
}