Skip to content

Commit 4a48745

Browse files
Calinoudacrystal
andcommitted
Add Tween.interpolate() as a low-level tweening option
This can be used as an alternative to `Tween.interpolate_property()` when additional control is needed. This closes godotengine/godot-proposals#36. Co-authored-by: Nasser Alansari <alansari.n@gmail.com>
1 parent aeff25f commit 4a48745

File tree

3 files changed

+63
-0
lines changed

3 files changed

+63
-0
lines changed

doc/classes/Tween.xml

+30
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,36 @@
7979
Returns the total time needed for all tweens to end. If you have two tweens, one lasting 10 seconds and the other 20 seconds, it would return 20 seconds, as by that time all tweens would have finished.
8080
</description>
8181
</method>
82+
<method name="interpolate">
83+
<return type="Variant">
84+
</return>
85+
<argument index="0" name="initial_val" type="Variant">
86+
</argument>
87+
<argument index="1" name="final_val" type="Variant">
88+
</argument>
89+
<argument index="2" name="weight" type="float">
90+
</argument>
91+
<argument index="3" name="trans_type" type="int" enum="Tween.TransitionType" default="0">
92+
</argument>
93+
<argument index="4" name="ease_type" type="int" enum="Tween.EaseType" default="2">
94+
</argument>
95+
<description>
96+
Returns an interpolated value between [code]initial_val[/code] and [code]final_val[/code], following the transition and easing curves defined in [code]trans_type[/code] and [code]ease_type[/code]. [code]weight[/code] must be between 0 and 1 (inclusive). This can be used as a lower-level alternative to [method interpolate_property].
97+
[code]initial_val[/code] and [code]final_val[/code] must be of the same type. If interpolation fails, this method will return [code]false[/code].
98+
[b]Note:[/b] If you only need linear interpolation, [method @GDScript.lerp], [method Vector2.linear_interpolate] or [method Vector3.linear_interpolate] may be easier to set up.
99+
[codeblock]
100+
var tween = Tween.new()
101+
# Prints 0.5
102+
print(tween.interpolate(0, 1, 0.5, Tween.TRANS_LINEAR, Tween.EASE_IN))
103+
# Prints 0.25
104+
print(tween.interpolate(0, 1, 0.5, Tween.TRANS_QUAD, Tween.EASE_IN))
105+
# Prints 12.5
106+
print(tween.interpolate(5, 20, 0.5, Tween.TRANS_LINEAR, Tween.EASE_IN))
107+
# Prints 8.75
108+
print(tween.interpolate(5, 20, 0.5, Tween.TRANS_QUAD, Tween.EASE_IN))
109+
[/codeblock]
110+
</description>
111+
</method>
82112
<method name="interpolate_callback">
83113
<return type="void">
84114
</return>

scene/animation/tween.cpp

+32
Original file line numberDiff line numberDiff line change
@@ -238,6 +238,7 @@ void Tween::_bind_methods() {
238238
ClassDB::bind_method(D_METHOD("get_runtime"), &Tween::get_runtime);
239239

240240
// Bind interpolation and follow methods
241+
ClassDB::bind_method(D_METHOD("interpolate", "initial_val", "final_val", "weight", "trans_type", "ease_type"), &Tween::interpolate, DEFVAL(TRANS_LINEAR), DEFVAL(EASE_IN_OUT));
241242
ClassDB::bind_method(D_METHOD("interpolate_property", "object", "property", "initial_val", "final_val", "duration", "trans_type", "ease_type", "delay"), &Tween::interpolate_property, DEFVAL(TRANS_LINEAR), DEFVAL(EASE_IN_OUT), DEFVAL(0));
242243
ClassDB::bind_method(D_METHOD("interpolate_method", "object", "method", "initial_val", "final_val", "duration", "trans_type", "ease_type", "delay"), &Tween::interpolate_method, DEFVAL(TRANS_LINEAR), DEFVAL(EASE_IN_OUT), DEFVAL(0));
243244
ClassDB::bind_method(D_METHOD("interpolate_callback", "object", "duration", "callback", "arg1", "arg2", "arg3", "arg4", "arg5"), &Tween::interpolate_callback, DEFVAL(Variant()), DEFVAL(Variant()), DEFVAL(Variant()), DEFVAL(Variant()), DEFVAL(Variant()));
@@ -1316,6 +1317,37 @@ void Tween::_build_interpolation(InterpolateType p_interpolation_type, Object *p
13161317
_push_interpolate_data(data);
13171318
}
13181319

1320+
Variant Tween::interpolate(Variant p_initial_val, Variant p_final_val, real_t p_weight, TransitionType p_trans_type, EaseType p_ease_type) {
1321+
1322+
// Convert any integers into REALs as they are better for interpolation.
1323+
if (p_initial_val.get_type() == Variant::INT) {
1324+
p_initial_val = p_initial_val.operator real_t();
1325+
}
1326+
if (p_final_val.get_type() == Variant::INT) {
1327+
p_final_val = p_final_val.operator real_t();
1328+
}
1329+
1330+
ERR_FAIL_COND_V(p_initial_val.get_type() == Variant::NIL, false);
1331+
ERR_FAIL_COND_V(p_initial_val.get_type() != p_final_val.get_type(), false);
1332+
ERR_FAIL_COND_V(p_weight < 0 || p_weight > 1, false);
1333+
ERR_FAIL_COND_V(p_trans_type < 0 || p_trans_type >= TRANS_COUNT, false);
1334+
ERR_FAIL_COND_V(p_ease_type < 0 || p_ease_type >= EASE_COUNT, false);
1335+
1336+
InterpolateData data;
1337+
data.type = INTER_PROPERTY;
1338+
data.elapsed = p_weight;
1339+
data.initial_val = p_initial_val;
1340+
data.final_val = p_final_val;
1341+
data.duration = 1.0;
1342+
data.trans_type = p_trans_type;
1343+
data.ease_type = p_ease_type;
1344+
data.delay = 0;
1345+
1346+
ERR_FAIL_COND_V(!_calc_delta_val(data.initial_val, data.final_val, data.delta_val), false);
1347+
1348+
return _run_equation(data);
1349+
}
1350+
13191351
void Tween::interpolate_property(Object *p_object, NodePath p_property, Variant p_initial_val, Variant p_final_val, real_t p_duration, TransitionType p_trans_type, EaseType p_ease_type, real_t p_delay) {
13201352
// If we are busy updating, call this function again later
13211353
if (pending_update != 0) {

scene/animation/tween.h

+1
Original file line numberDiff line numberDiff line change
@@ -179,6 +179,7 @@ class Tween : public Node {
179179
real_t tell() const;
180180
real_t get_runtime() const;
181181

182+
Variant interpolate(Variant p_initial_val, Variant p_final_val, real_t p_weight, TransitionType p_trans_type = TRANS_LINEAR, EaseType p_ease_type = EASE_IN_OUT);
182183
void interpolate_property(Object *p_object, NodePath p_property, Variant p_initial_val, Variant p_final_val, real_t p_duration, TransitionType p_trans_type = TRANS_LINEAR, EaseType p_ease_type = EASE_IN_OUT, real_t p_delay = 0);
183184
void interpolate_method(Object *p_object, StringName p_method, Variant p_initial_val, Variant p_final_val, real_t p_duration, TransitionType p_trans_type = TRANS_LINEAR, EaseType p_ease_type = EASE_IN_OUT, real_t p_delay = 0);
184185
void interpolate_callback(Object *p_object, real_t p_duration, String p_callback, VARIANT_ARG_DECLARE);

0 commit comments

Comments
 (0)