In android, we have overshoot interpolator for animation using Object animator which overshoots the end value of animation and then comes back to end value. Is there any alternative for flutter like in gif below.
According to #pskink help, Similar behaviour of overshoot interpolator is Curves.elasticOut. As I wanted to control oscillation too I used ElasticOutCurve() curve. below code solved the problem.
_clockWiseRotationAnimation =
Tween<double>(begin: 0.0, end: 2 * pi).animate(CurvedAnimation(parent: _controller, curve: ElasticOutCurve(1.0)));
Related
I have a Flutter app that is showing some Lottie animations. I sometimes need to flip the animation by 180 degrees on Y axis so that it it is a mirror image of itself.
In C# this is easily achievable by setting animated visual player's plane projection rotationY property to 180 (see below).
<muxc:AnimatedVisualPlayer x:Name="LottiePlayer">
<muxc:AnimatedVisualPlayer.Projection>
<PlaneProjection RotationY="180" x:Name="LottiePayerRotation"/>
</muxc:AnimatedVisualPlayer.Projection>
In flutter I tried using RotationBox, but that only rotates around X axis. I need to rotate around Y axis (see image below).
I also tried wrapping Lottie animation inside Transform widget (see below), but that doesn't work. After I added that, the Lottie animation completely disappears. I don't quite understand how Matrix4 works, there is very little documentation on it. I found this Matrix4 explanation but I still don't understand it. :-(
Transform(
transform: Matrix4(
1,0,0,0,
0,1,0,0,
0,0,1,0,
0,0,0,1,
)..rotateX(0)..rotateY(180)..rotateZ(0),
child: Lottie(
frameRate: FrameRate.max,
composition: _composition,
controller: _controller,
),
),
Note that I do not need the flip to be animated, I just want to flip the Lottie animation instantly so that it looks like a mirror image of itself. So an instant change, not a transition animated.
Any help appreciated.
I have used something like this before to rotate items... not sure if its what you are after
child: Transform.rotate(
angle: 180 / Math.pi, // Rotations are supplied in radians
child: Container())
Turns out I almost had it! What was missing was the alignment. The default value was causing the rotation to get outside the visible area. Changing alignment to "center" fixed that:
child: Transform(
alignment: FractionalOffset.center,
transform: Matrix4(
1,0,0,0,
0,1,0,0,
0,0,1,0,
0,0,0,1,
)..rotateY(180),
child: Lottie(
frameRate: FrameRate.max,
composition: _composition,
controller: _controller,
),
Simply wrap your widget with RotatedBox & give quarterTurns value(0, 1, 2, 3)
Assuming my widget is image of right arrow : →
0 no rotation - →
1 90 rotation - ↓
2 180 rotation - ←
3 270 rotation - ↑
So if I want my image to face left side ←:
RotatedBox(
quarterTurns: 2,
child: Image.asset('assets/right_arrow.png'),
),
EDIT
To rotate on axis, you need to use Transform widget.
Give the transform property as Matrix4
NOTE: You have to give rotation in radians.
import 'dart:math' as math;
Transform(
// to mirror, rotate Y axis
// math.pi is 180 degree in radian
transform: Matrix4.rotationY(math.pi),
child: Text('Hello world!'),
),
What is the animation layer weight in the animation controller in Unity?
What does SetLayerWeight do in the animation state controller?
Layer weight defines how much (normalized) animation from the layer will evaluate in the final output.
For example:
If you have have 2 layers "layer_1" with weight=0.25 and "layer_2" with weight=0.75. The final frame animation evaluation, will take 0.25 effect from "layer_1" and 0.75 effect from "layer_2".
For more info: https://docs.unity3d.com/Manual/AnimationLayers.html
I would like a RectTransform (panel) in Unity 4.6 to follow a worldObject. I got this working, but the movement is not as smooth as I'd like. It seems a bit jagged and it lags behind when I start moving the camera.
Vector2 followObjectScreenPos = Camera.main.WorldToScreenPoint (planet.transform.position);
rectTransform.anchoredPosition = new Vector2 (followObjectScreenPos.x - Screen.width / 2, followObjectScreenPos.y - Screen.height / 2);
Tips and tricks are greatly appreciated. :-)
There is a bunch of options:
1) You can add a gui canvas to the worldObject and render your panel with this canvas (just add it as a child), but that may not be exactly what you need.
2) To eliminate jagged movement you should tween in one way or another. DOTween is my personal preference, where something along the following lines would give you the required result:
Tweener tweener = transfrom.DOMove (Target.position, 1).SetSpeedBased();
tweener.OnUpdate (() => tweener.ChangeEndValue (Target.position, true));
3) if you don't want to include dependencies in your code, you can perform linear interpolation between current and desired position (or in your case - anchoredPosition) in Update function.
I'd suggest using a tweener so as not to clutter your update function and generally tweeners have loads of potential uses in all kinds of games.
Below is code sample for linear interpolation in case you don't want to use tweener library:
float smoothFactor = 1.0f; //used to sharpen or dull the effect of lerp
var newPosition = new Vector3(x,y,z);
var t = gameObject.transform;
t.position = Vector3.Lerp (t.position,
newPosition,
Time.deltaTime * smoothFactor);
Place it in Update function and it will make the gameObject follow specific newPosition.
I have a cube. A script is attached to it. I want, that the cube gets an impulse at the start in a random direction. My problem is the addForce. I don't know what to add there.
public Transform myObject;
void Start () {
Vector3 randomDirection = new Vector3(0f,0f,Random.Range(-359, 359));
myObject.Rotate (randomDirection);
myObject.rigidbody.AddForce(transform.?????? * speed, ForceMode.Impulse);
}
For random you want
myObject.rigid body.AddForce(Random.Range(0, 10), Random.Range(0, 10), Random.Range(0, 10), ForceMode.Impulse);
The code is saying, give me a random force value for the x, y, z.
Rotation has nothing to do with it. If you push a cat from a random Angle, you add force to the cat. You don't need to rotate the cat to push it. Although you shouldn't go around pushing cats.
If you insist on random rotation then make your object fire off forwards:
myObject.rigid body.AddForce(myObject.transform.forward * speed, ForceMode.Impulse);
transform.forward is a property on Transform that represents the direction the object is facing. In the Editor, it is represented by the blue axis on the object's transform handle.
If you use it in your script, the object will have a force applied to it in the random direction determined by the myObject.Rotate(...) line.
This is basically a simple issue, which I can't get around ...
So, I have an object of UIImageView of a certain frame over which, I implement CAAnimation with rotation and translation, and it is at new coordinates (x,y), and has been rotated by some degrees.
This animation works beautifully. But if I again do a rotation and movement from THAT state, I want the object to use the new frame and new properties from STEP 1 after its rotation and again rotate by the new angle.
As of now, when I try rotation again, it uses its standard state & frame size(during initialization) and performs rotation on it...
And by this I mean... If I have a square of frame (100, 200, 10, 10), and I rotate it by 45 degrees, the shape is now a different square, with different frame size and end points compared to the original square, and I implement a new rotation by (say) 152 degrees on it and it needs to perform a rotation on the newer square... But it turns out that it uses the same frame size as the previous one (x,y, 10, 10).
How can I continue rotating / moving the object with its updated position and state ??
Note: (if you need to see the code for animation)
This is the code for my animation, which involves simple rotation and movement ! http://pastebin.com/cR8zrKRq
You need to save the rotation step and update object rotation in animationDidStop: method. So, in your cas, you should apply:
-(void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag
{
//angle is global
CATransform3D rotationTransform = CATransform3DMakeRotation((angle%4)*M_PI_4, 0, 0, 1);
[object.layer setTransform:rotationTransform];
object.center = tempFrame; //already there
}
where angle is an integer counter of animations(steps) with values 0,1,2,3. My step is M_PI_4. There is probably a better solution to the problem, but this should do the trick