Repository: godotengine/godot
File: scene/resources/animation.cpp (C++)

Code before:
	while (i < vt->values.size() - 2) {
		bool erase = false;
		if (track_get_interpolation_type(i) == Animation::INTERPOLATION_NEAREST) {
			p_is_nearest = true;
		}
		switch (type) {
			case Variant::FLOAT: {
				TKey<float> t0;
				TKey<float> t1;
				TKey<float> t2;
				t0.time = vt->values[i].time;
				t1.time = vt->values[i + 1].time;
				t2.time = vt->values[i + 2].time;
				t0.value = vt->values[i].value;
				t1.value = vt->values[i + 1].value;
				t2.value = vt->values[i + 2].value;
				if (is_using_angle) {
					float diff1 = fmod(t1.value - t0.value, Math::TAU);
					t1.value = t0.value + fmod(2.0 * diff1, Math::TAU) - diff1;
					float diff2 = fmod(t2.value - t1.value, Math::TAU);
					t2.value = t1.value + fmod(2.0 * diff2, Math::TAU) - diff2;
					if (abs(abs(diff1) + abs(diff2)) >= Math::PI) {
						break; // Rotation is more than 180 deg, keep key.
					}
				}
				erase = _float_track_optimize_key(t0, t1, t2, p_allowed_velocity_err, p_allowed_precision_error, p_is_nearest);
			} break;
			case Variant::VECTOR2: {
				TKey<Vector2> t0;
				TKey<Vector2> t1;
				TKey<Vector2> t2;
				t0.time = vt->values[i].time;
				t1.time = vt->values[i + 1].time;
				t2.time = vt->values[i + 2].time;
				t0.value = vt->values[i].value;
				t1.value = vt->values[i + 1].value;
				t2.value = vt->values[i + 2].value;
				erase = _vector2_track_optimize_key(t0, t1, t2, p_allowed_velocity_err, p_allowed_angular_err, p_allowed_precision_error, p_is_nearest);
			} break;
			case Variant::VECTOR3: {
				TKey<Vector3> t0;
				TKey<Vector3> t1;
				TKey<Vector3> t2;
				t0.time = vt->values[i].time;
				t1.time = vt->values[i + 1].time;
				t2.time = vt->values[i + 2].time;
				t0.value = vt->values[i].value;
				t1.value = vt->values[i + 1].value;
				t2.value = vt->values[i + 2].value;
				erase = _vector3_track_optimize_key(t0, t1, t2, p_allowed_velocity_err, p_allowed_angular_err, p_allowed_precision_error, p_is_nearest);
			} break;

Review comment (performance):
```suggestion
				erase = _float_track_optimize_key(t0, t1, t2, p_allowed_velocity_err, p_allowed_precision_error, track_get_interpolation_type(i) == Animation::INTERPOLATION_NEAREST);
```

Code after:
		is_nearest = true;
	} else if (tracks[p_idx]->interpolation != INTERPOLATION_LINEAR && tracks[p_idx]->interpolation != INTERPOLATION_LINEAR_ANGLE) {
		return;
	}
	ValueTrack *vt = static_cast<ValueTrack *>(tracks[p_idx]);
	if (vt->values.is_empty()) {
		return;
	}
	Variant::Type type = vt->values[0].value.get_type();

	// Special case for angle interpolation.
	bool is_using_angle = vt->interpolation == Animation::INTERPOLATION_LINEAR_ANGLE || vt->interpolation == Animation::INTERPOLATION_CUBIC_ANGLE;
	int i = 0;
	while (i < vt->values.size() - 2) {
		bool erase = false;
		switch (type) {
			case Variant::FLOAT: {
				TKey<float> t0;
				TKey<float> t1;
				TKey<float> t2;
				t0.time = vt->values[i].time;
				t1.time = vt->values[i + 1].time;
				t2.time = vt->values[i + 2].time;
				t0.value = vt->values[i].value;
				t1.value = vt->values[i + 1].value;
				t2.value = vt->values[i + 2].value;
				if (is_using_angle) {
					float diff1 = fmod(t1.value - t0.value, Math::TAU);
					t1.value = t0.value + fmod(2.0 * diff1, Math::TAU) - diff1;
					float diff2 = fmod(t2.value - t1.value, Math::TAU);
					t2.value = t1.value + fmod(2.0 * diff2, Math::TAU) - diff2;
					if (abs(abs(diff1) + abs(diff2)) >= Math::PI) {
						break; // Rotation is more than 180 deg, keep key.
					}
				}
				erase = _float_track_optimize_key(t0, t1, t2, p_allowed_velocity_err, p_allowed_precision_error, is_nearest);
			} break;
			case Variant::VECTOR2: {
				TKey<Vector2> t0;
				TKey<Vector2> t1;
				TKey<Vector2> t2;
				t0.time = vt->values[i].time;
				t1.time = vt->values[i + 1].time;
				t2.time = vt->values[i + 2].time;
				t0.value = vt->values[i].value;
				t1.value = vt->values[i + 1].value;
				t2.value = vt->values[i + 2].value;
				erase = _vector2_track_optimize_key(t0, t1, t2, p_allowed_velocity_err, p_allowed_angular_err, p_allowed_precision_error, is_nearest);
			} break;
			case Variant::VECTOR3: {
				TKey<Vector3> t0;