mirror of
https://github.com/TombEngine/TombEngine.git
synced 2025-04-28 07:47:57 +03:00
Implement flyby spline looping in lua API
This commit is contained in:
parent
7ba9370281
commit
9fc370833b
5 changed files with 58 additions and 17 deletions
|
@ -20,6 +20,7 @@ TombEngine releases are located in this repository (alongside with Tomb Editor):
|
|||
|
||||
### Lua API changes
|
||||
* Added missing constructor for `Collision.Probe` without room number.
|
||||
* Added optional looping argument for `View.GetFlybyPosition` and `View.GetFlybyRotation` functions.
|
||||
|
||||
## [Version 1.8](https://github.com/TombEngine/TombEditorReleases/releases/tag/v1.8) - 2025-03-16
|
||||
|
||||
|
|
|
@ -176,11 +176,11 @@
|
|||
<td class="summary">Play a flyby sequence.</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="name" ><a href="#GetFlybyPosition">GetFlybyPosition(seqID, progress)</a></td>
|
||||
<td class="name" ><a href="#GetFlybyPosition">GetFlybyPosition(seqID, progress[, loop])</a></td>
|
||||
<td class="summary">Get a flyby sequence's position at a specified progress point in percent.</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="name" ><a href="#GetFlybyRotation">GetFlybyRotation(seqID, progress)</a></td>
|
||||
<td class="name" ><a href="#GetFlybyRotation">GetFlybyRotation(seqID, progress[, loop])</a></td>
|
||||
<td class="summary">Get a flyby sequence's rotation at a specified progress point in percent.</td>
|
||||
</tr>
|
||||
<tr>
|
||||
|
@ -499,7 +499,7 @@
|
|||
</dd>
|
||||
<dt>
|
||||
<a name = "GetFlybyPosition"></a>
|
||||
<strong>GetFlybyPosition(seqID, progress)</strong>
|
||||
<strong>GetFlybyPosition(seqID, progress[, loop])</strong>
|
||||
</dt>
|
||||
<dd>
|
||||
Get a flyby sequence's position at a specified progress point in percent.
|
||||
|
@ -516,6 +516,11 @@
|
|||
<span class="types"><span class="type">float</span></span>
|
||||
Progress point in percent. Clamped to [0, 100].
|
||||
</li>
|
||||
<li><span class="parameter">loop</span>
|
||||
<span class="types"><span class="type">bool</span></span>
|
||||
Smooth the position near start and end points, as if the sequence is looped.
|
||||
(<em>optional</em>)
|
||||
</li>
|
||||
</ul>
|
||||
|
||||
<h3>Returns:</h3>
|
||||
|
@ -531,7 +536,7 @@
|
|||
</dd>
|
||||
<dt>
|
||||
<a name = "GetFlybyRotation"></a>
|
||||
<strong>GetFlybyRotation(seqID, progress)</strong>
|
||||
<strong>GetFlybyRotation(seqID, progress[, loop])</strong>
|
||||
</dt>
|
||||
<dd>
|
||||
Get a flyby sequence's rotation at a specified progress point in percent.
|
||||
|
@ -548,6 +553,11 @@
|
|||
<span class="types"><span class="type">float</span></span>
|
||||
Progress point in percent. Clamped to [0, 100].
|
||||
</li>
|
||||
<li><span class="parameter">loop</span>
|
||||
<span class="types"><span class="type">bool</span></span>
|
||||
Smooth the position near start and end points, as if the sequence is looped.
|
||||
(<em>optional</em>)
|
||||
</li>
|
||||
</ul>
|
||||
|
||||
<h3>Returns:</h3>
|
||||
|
|
|
@ -839,7 +839,7 @@ int Spline(int x, int* knots, int nk)
|
|||
return ((__int64)x * (((__int64)x * (((__int64)x * c1 >> 16) + c2) >> 16) + (k[2] >> 1) + ((-k[0] - 1) >> 1)) >> 16) + k[1];
|
||||
}
|
||||
|
||||
Pose GetCameraTransform(int sequence, float alpha)
|
||||
Pose GetCameraTransform(int sequence, float alpha, bool loop)
|
||||
{
|
||||
alpha = std::clamp(alpha, 0.0f, 1.0f);
|
||||
|
||||
|
@ -873,15 +873,43 @@ Pose GetCameraTransform(int sequence, float alpha)
|
|||
}
|
||||
|
||||
// Compute spline interpolation of main flyby camera parameters.
|
||||
auto origin = Vector3(Spline(splineAlpha, xOrigins.data(), splinePoints),
|
||||
Spline(splineAlpha, yOrigins.data(), splinePoints),
|
||||
Spline(splineAlpha, zOrigins.data(), splinePoints));
|
||||
auto getInterpolatedPoint = [&](float t, std::vector<int>& x, std::vector<int>& y, std::vector<int>& z)
|
||||
{
|
||||
int tAlpha = int(t * (float)USHRT_MAX);
|
||||
return Vector3(Spline(tAlpha, x.data(), splinePoints),
|
||||
Spline(tAlpha, y.data(), splinePoints),
|
||||
Spline(tAlpha, z.data(), splinePoints));
|
||||
};
|
||||
|
||||
auto target = Vector3(Spline(splineAlpha, xTargets.data(), splinePoints),
|
||||
Spline(splineAlpha, yTargets.data(), splinePoints),
|
||||
Spline(splineAlpha, zTargets.data(), splinePoints));
|
||||
auto getInterpolatedRoll = [&](float t)
|
||||
{
|
||||
int tAlpha = int(t * (float)USHRT_MAX);
|
||||
return Spline(tAlpha, rolls.data(), splinePoints);
|
||||
};
|
||||
|
||||
short orientZ = Spline(splineAlpha, rolls.data(), splinePoints);
|
||||
Vector3 origin = {};
|
||||
Vector3 target = {};
|
||||
short orientZ = 0;
|
||||
|
||||
constexpr float BLEND_RANGE = 0.1f;
|
||||
constexpr float BLEND_START = BLEND_RANGE;
|
||||
constexpr float BLEND_END = 1.0f - BLEND_RANGE;
|
||||
|
||||
// If loop is enabled and we are at the start or end of the sequence, blend between the last and first cameras.
|
||||
if (loop && (alpha < BLEND_START || alpha >= BLEND_END))
|
||||
{
|
||||
float blendFactor = (alpha < BLEND_START) ? 0.5f + (alpha / BLEND_RANGE) * 0.5f : (alpha - BLEND_END) / BLEND_START * 0.5f;
|
||||
|
||||
origin = Vector3::Lerp(getInterpolatedPoint(BLEND_END, xOrigins, yOrigins, zOrigins), getInterpolatedPoint(BLEND_START, xOrigins, yOrigins, zOrigins), blendFactor);
|
||||
target = Vector3::Lerp(getInterpolatedPoint(BLEND_END, xTargets, yTargets, zTargets), getInterpolatedPoint(BLEND_START, xTargets, yTargets, zTargets), blendFactor);
|
||||
orientZ = Lerp(getInterpolatedRoll(BLEND_END), getInterpolatedRoll(BLEND_START), blendFactor);
|
||||
}
|
||||
else
|
||||
{
|
||||
origin = getInterpolatedPoint(alpha, xOrigins, yOrigins, zOrigins);
|
||||
target = getInterpolatedPoint(alpha, xTargets, yTargets, zTargets);
|
||||
orientZ = getInterpolatedRoll(alpha);
|
||||
}
|
||||
|
||||
auto pose = Pose(origin, EulerAngles(target - origin));
|
||||
pose.Orientation.z = orientZ;
|
||||
|
|
|
@ -64,4 +64,4 @@ void InitializeSpotCam(short sequence);
|
|||
void CalculateSpotCameras();
|
||||
int Spline(int x, int* knots, int nk);
|
||||
|
||||
Pose GetCameraTransform(int sequence, float alpha);
|
||||
Pose GetCameraTransform(int sequence, float alpha, bool loop);
|
||||
|
|
|
@ -111,18 +111,18 @@ namespace TEN::Scripting::View
|
|||
InitializeSpotCam(seqID);
|
||||
}
|
||||
|
||||
static Vec3 GetFlybyPosition(int seqID, float progress)
|
||||
static Vec3 GetFlybyPosition(int seqID, float progress, TypeOrNil<bool> loop)
|
||||
{
|
||||
constexpr auto PROGRESS_MAX = 100.0f;
|
||||
|
||||
return Vec3(GetCameraTransform(seqID, progress / PROGRESS_MAX).Position);
|
||||
return Vec3(GetCameraTransform(seqID, progress / PROGRESS_MAX, ValueOr<bool>(loop, false)).Position);
|
||||
}
|
||||
|
||||
static Rotation GetFlybyRotation(int seqID, float progress)
|
||||
static Rotation GetFlybyRotation(int seqID, float progress, TypeOrNil<bool> loop)
|
||||
{
|
||||
constexpr auto PROGRESS_MAX = 100.0f;
|
||||
|
||||
return Rotation(GetCameraTransform(seqID, progress / PROGRESS_MAX).Orientation);
|
||||
return Rotation(GetCameraTransform(seqID, progress / PROGRESS_MAX, ValueOr<bool>(loop, false)).Orientation);
|
||||
}
|
||||
|
||||
static void FlashScreen(TypeOrNil<ScriptColor> col, TypeOrNil<float> speed)
|
||||
|
@ -244,6 +244,7 @@ namespace TEN::Scripting::View
|
|||
// @function GetFlybyPosition
|
||||
// @tparam int seqID Flyby sequence ID.
|
||||
// @tparam float progress Progress point in percent. Clamped to [0, 100].
|
||||
// @tparam[opt] bool loop Smooth the position near start and end points, as if the sequence is looped.
|
||||
// @treturn Vec3 Position at the given progress point.
|
||||
tableView.set_function(ScriptReserved_GetFlybyPosition, &GetFlybyPosition);
|
||||
|
||||
|
@ -251,6 +252,7 @@ namespace TEN::Scripting::View
|
|||
// @function GetFlybyRotation
|
||||
// @tparam int seqID Flyby sequence ID.
|
||||
// @tparam float progress Progress point in percent. Clamped to [0, 100].
|
||||
// @tparam[opt] bool loop Smooth the position near start and end points, as if the sequence is looped.
|
||||
// @treturn Rotation Rotation at the given progress point.
|
||||
tableView.set_function(ScriptReserved_GetFlybyRotation, &GetFlybyRotation);
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue