ベクトルの線形補間について
全然わからないので、まずは言葉の意味から
補間とは
内挿(ないそう、英: interpolation、補間とも言う)とは、ある既知の数値データ列を基にして、そのデータ列の各区間の範囲内を埋める数値を求めること、またはそのような関数を与えること。またその手法を内挿法(補間法)という。内挿するためには、各区間の範囲内で成り立つと期待される関数と境界での振舞い(境界条件)を決めることが必要である。
分かるようなわからないような。
内挿やinterpolationの方が意味が分かるきもします。
Unityでは(以下引用)
まずは二次元から 2D
Vector2.Lerp
説明
a と b by t ベクトルの間で線形補間します。
t は [0...1] の間で制限されます。
When t = 0 returns a. When t = 1 return b. t = 0.5 のときは a と b の平均(ちょうど真ん中)を返します。
使い方
C Sharp
public static Vector2 Lerp(Vector2 a, Vector2 b, float t);
JavaScript
public static function Lerp(a: Vector2, b: Vector2, t: float): Vector2;
3Dでは
Vector3.Lerp
説明
直線上にある 2 つのベクトル間を補間します
t で a と b の間を補間します。t は、0-1 の範囲に固定されています。これは、直線状にあるポイント間(両端)で割合に対しての位置を取得するのに使用します(例えば徐々に目的地へ移動していくときに使用します)。
t = 0 のときは a を返します。 t = 1 のときは b を返します。 t = 0.5 のときは a と b の平均(ちょうど真ん中)を返します。
使い方
C Sharp
public static Vector3 Lerp(Vector3 a, Vector3 b, float t);
using UnityEngine; using System.Collections; public class ExampleClass : MonoBehaviour { public Transform startMarker; public Transform endMarker; public float speed = 1.0F; private float startTime; private float journeyLength; void Start() { startTime = Time.time; journeyLength = Vector3.Distance(startMarker.position, endMarker.position); } void Update() { float distCovered = (Time.time - startTime) * speed; float fracJourney = distCovered / journeyLength; transform.position = Vector3.Lerp(startMarker.position, endMarker.position, fracJourney); } }
JavaScript
public static function Lerp(a: Vector3, b: Vector3, t: float): Vector3;
// Transforms to act as start and end markers for the journey. var startMarker: Transform; var endMarker: Transform; // Movement speed in units/sec. var speed = 1.0; // Time when the movement started. private var startTime: float; // Total distance between the markers. private var journeyLength: float; function Start() { // Keep a note of the time the movement started. startTime = Time.time; // Calculate the journey length. journeyLength = Vector3.Distance(startMarker.position, endMarker.position); } // Follows the target position like with a spring function Update () { // Distance moved = time * speed. var distCovered = (Time.time - startTime) * speed; // Fraction of journey completed = current distance divided by total distance. var fracJourney = distCovered / journeyLength; // Set our position as a fraction of the distance between the markers. transform.position = Vector3.Lerp(startMarker.position, endMarker.position, fracJourney); }
lerp
Three.jsを思いっきり参考にしました。
基本的に(二点間)
- 書き方1
function lerp (start, end, alpha){ return (1 - alpha) * start + alpha * end }
2Dの場合
- 書き方1
function lerp ( v, alpha ) { this.x += ( v.x - this.x ) * alpha; this.y += ( v.y - this.y ) * alpha; return this; }
- 書き方2
function lerpVectors( v1, v2, alpha ) { return this.subVectors( v2, v1 ).multiplyScalar( alpha ).add( v1 ); } function add( v ) { this.x += v.x; this.y += v.y; return this; } function subVectors( a, b ) { this.x = a.x - b.x; this.y = a.y - b.y; return this; } function multiplyScalar( scalar ) { if ( isFinite( scalar ) ) { this.x *= scalar; this.y *= scalar; } else { this.x = 0; this.y = 0; } return this; }
3Dの場合
- 書き方1
function lerp( v, alpha ) { this.x += ( v.x - this.x ) * alpha; this.y += ( v.y - this.y ) * alpha; this.z += ( v.z - this.z ) * alpha; return this; }
- 書き方2
function lerpVectors( v1, v2, alpha ) { return this.subVectors( v2, v1 ).multiplyScalar( alpha ).add( v1 ); } function add( v ) { this.x += v.x; this.y += v.y; this.z += v.z; return this; } function subVectors( a, b ) { this.x = a.x - b.x; this.y = a.y - b.y; this.z = a.z - b.z; return this; } function multiplyScalar( scalar ) { if ( isFinite( scalar ) ) { this.x *= scalar; this.y *= scalar; this.z *= scalar; } else { this.x = 0; this.y = 0; this.z = 0; } return this; }
こんな感じなのだろうか?