I would like to do bounce animation of layer.
I have done that layer comes from right to center, now I would like to move it a little back and then back to center. That would create bounce effect.
I was thinking that I can do it with a translate like this:
<translate
android:duration="900"
android:fromXDelta="100%p"
android:toXDelta="0%p" />
<translate
android:duration="900"
android:fromXDelta="0%p"
android:toXDelta="100%p" />
<translate
android:duration="900"
android:fromXDelta="70%p"
android:toXDelta="0%p" />
Well this code does not working, only thing I can achieve is that Layer comes from left to center, and then animation stops.
I cannot use this code: because it does not achieve what I want
setInterpolator(AnimationUtils.loadInterpolator(this,
android.R.anim.bounce_interpolator));
Any help would be appreciated.
You can use the BounceInterpolator to have this effect. The docs contain a very good description how to use it in XML. Just have a animation xml like this:
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="#android:anim/bounce_interpolator">
<!-- Use your working translate animation here-->
<translate
android:duration="900"
android:fromXDelta="100%p"
android:toXDelta="0%p" />
</set>
use this xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:fillAfter="true"
android:interpolator="#android:anim/bounce_interpolator">
<scale
android:duration="600"
android:fromXScale="1.0"
android:fromYScale="0.0"
android:toXScale="1.0"
android:toYScale="1.0" />
</set>
This will show bounce effect with scale ,different from translate,(fits better in some situations),for more check THIS out..
Add code on button or image click
final Animation myAnim = AnimationUtils.loadAnimation(getActivity(), R.anim.bounce);
// Use bounce interpolator with amplitude 0.1 and frequency 15
MyBounceInterpolator interpolator = new MyBounceInterpolator(0.1, 15);
myAnim.setInterpolator(interpolator);
imgVoiceSearch.startAnimation(myAnim);
Add this class
public class MyBounceInterpolator implements android.view.animation.Interpolator {
private double mAmplitude = 1;
private double mFrequency = 10;
public MyBounceInterpolator(double amplitude, double frequency) {
mAmplitude = amplitude;
mFrequency = frequency;
}
public float getInterpolation(float time) {
return (float) (-1 * Math.pow(Math.E, -time / mAmplitude) *
Math.cos(mFrequency * time) + 1);
}
}
Related
I need to have an animation that scales a view to the screen width over 1500 seconds.
I haven't got a clue how to achieve this. I searched for an hour now on the internet...
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:fillEnabled="true"
android:fillAfter="true">
<scale
android:interpolator="#android:anim/accelerate_decelerate_interpolator"
android:fromXScale="0"
android:toXScale="?"
android:fromYScale="1.0"
android:toYScale="1.0"
android:fillAfter="false"
/>
</set>
The method where the animation gets called:
tab1.Click += delegate
{
ResetMenuItem();
animation = AnimationUtils.LoadAnimation(ApplicationContext, Resource.Animation.grow_anim1);
animation.Duration = duration;
// int width = Resources.DisplayMetrics.WidthPixels;
RelativeLayout.LayoutParams p = new RelativeLayout.LayoutParams((int)ConvertDpToPix(3f),RelativeLayout.LayoutParams.MatchParent);
selector1.LayoutParameters = p;
selector1.StartAnimation(animation);
animation.AnimationEnd+=delegate
{
drawer.CloseDrawers();
};
tabIndex=1;
};
I ended up solving this by using a thread to edit the width of the view.
I'm trying to do a splashscreen where a logo appears from the top of the screen, and stop at the center of the screen.
I am using XML in my anim file:
<?xml version="1.0" encoding="utf-8"?>
<set
xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="#android:anim/linear_interpolator"
android:fillAfter="true">
<translate
android:fromYDelta="0%p"
android:toYDelta="75%p"
android:duration="3000" />
</set>
And this method to load the movement:
Animation fadein = AnimationUtils.loadAnimation(getActivity(), R.anim.fadein);
background.startAnimation(fadein);
background.setVisibility(ImageView.VISIBLE);
// load the animation
Animation animMoveDown = AnimationUtils.loadAnimation(getActivity(), R.anim.movedown);
// set animation listener
animMoveDown.setAnimationListener(this);
overlay.startAnimation(animMoveDown);
How I can put the logo above the screen and have it slide down to the center? Is it possible?
Thank you all, in my case the XML is:
<?xml version="1.0" encoding="utf-8"?>
<set
xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="#android:anim/linear_interpolator"
android:fillAfter="true">
<translate
**android:fromYDelta="-50%p"**
android:toYDelta="75%p"
android:duration="3000" />
</set>
It is absolutely possible! You'll have to play around with this a bit, but you'll basically just want to start at a negative YDelta
Here's what I used in my app, where I needed the very bottom of the image to start on the screen.
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate
android:fromYDelta="-84%"
android:toYDelta="0%"
android:duration="500" />
</set>
You're going to want to start at -100% and end at 50%, I think, so try this:
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate
android:fromYDelta="-100%"
android:toYDelta="50%"
android:duration="3000" />
</set>
Just as simple define android:fromYDelta with negative value.
private fun buildSlideDownAndScaleAnimation(view: View): AnimationSet {
val animSet = AnimationSet(true)
animSet.fillAfter = false
val duration: Long = 1000
animSet.duration = duration
animSet.interpolator = AccelerateDecelerateInterpolator()
val translate = TranslateAnimation(0f, 0f, -1000f, 0f)
animSet.addAnimation(translate)
val scale = ScaleAnimation(0f,
1f,
0f,
1f,
ScaleAnimation.RELATIVE_TO_SELF,
.5f,
ScaleAnimation.RELATIVE_TO_SELF,
.5f)
animSet.addAnimation(scale)
val alphaAnimation = AlphaAnimation(0f, 1f)
alphaAnimation.startOffset = duration / 3
animSet.addAnimation(alphaAnimation)
return animSet
}
I am trying to animate an ImageView when the said image view is clicked.
Specifically I want the size of the ImageView gets bigger (say .20 bigger) and the immediately shrink back to its original size).
So far I have been experimenting with this code with no luck.
// thumbLike is the imageView I would like to animate.
button.setOnClickListener(new OnClickListener(){
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
ScaleAnimation scaleAnim = new ScaleAnimation(1.0f, 2.5f, 1.0f, 2.5f,
Animation.RELATIVE_TO_SELF, 0.5f,
Animation.RELATIVE_TO_SELF, 0.5f);
scaleAnim.setInterpolator(new LinearInterpolator());
scaleAnim.setDuration(1500);
thumbLike.startAnimation(scaleAnim);
thumbLike.setAnimation(null);
}
});
Can anyone suggest me with a possible solution?
Edit #1
It is working through XML as answered by Hardik4560:
// finally i use this code to execute the animation
Animation animationScaleUp = AnimationUtils.loadAnimation(this, R.anim.scale_up);
Animation animationScaleDown = AnimationUtils.loadAnimation(this, R.anim.scale_down);
AnimationSet growShrink = new AnimationSet(true);
growShrink.addAnimation(animationScaleUp);
growShrink.addAnimation(animationScaleDown);
thumbLike.startAnimation(growShrink);
and the XML
SCALE_UP
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="#android:anim/linear_interpolator">
<scale
android:fromXScale="1.0"
android:toXScale="1.5"
android:fromYScale="1.0"
android:toYScale="1.5"
android:pivotX="50%"
android:pivotY="50%"
android:duration="1000" />
</set>
SCALE_DOWN
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="#android:anim/linear_interpolator">
<scale
android:fromXScale="1.5"
android:toXScale="1.0"
android:fromYScale="1.5"
android:toYScale="1.0"
android:pivotX="50%"
android:pivotY="50%"
android:duration="1000" />
</set>
ps: this is awkward, since I already accepted an answer. I am trying to combine between #tharkbad and #Hardik4560 's answers yet now the way it animates does not look smooth.
during the scale_up animation, it kinda look like being "skip" to the end of animation and then immediately starting scale_down animation. I guess I have to play around with it a bit.
If you want to implement this without XML you could do so as follows
final float growTo = 1.2f;
final long duration = 1200;
ScaleAnimation grow = new ScaleAnimation(1, growTo, 1, growTo,
Animation.RELATIVE_TO_SELF, 0.5f,
Animation.RELATIVE_TO_SELF, 0.5f);
grow.setDuration(duration / 2);
ScaleAnimation shrink = new ScaleAnimation(growTo, 1, growTo, 1,
Animation.RELATIVE_TO_SELF, 0.5f,
Animation.RELATIVE_TO_SELF, 0.5f);
shrink.setDuration(duration / 2);
shrink.setStartOffset(duration / 2);
AnimationSet growAndShrink = new AnimationSet(true);
growAndShrink.setInterpolator(new LinearInterpolator());
growAndShrink.addAnimation(grow);
growAndShrink.addAnimation(shrink);
thumbLike.startAnimation(growAndShrink);
Of course, you could also use NineOldAndroids and use the new animation methods.
I think your original error is this line, it removes the animation you just started from the view again.
thumbLike.setAnimation(null);
I use this to achieve popin popout effect,
See if its of any use to you
Pop Out.
<?xml version="1.0" encoding="utf-8"?>
<set
xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="#android:anim/bounce_interpolator" >
<scale
android:pivotX="50%"
android:pivotY="50%"
android:fromXScale="0.5"
android:fromYScale="0.5"
android:toXScale="1.0"
android:toYScale="1.0"
android:duration="500" />
</set>
Pop In
<?xml version="1.0" encoding="utf-8"?>
<set
xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="#android:anim/bounce_interpolator" >
<scale
android:pivotX="50%"
android:pivotY="50%"
android:fromXScale="1.0"
android:fromYScale="1.0"
android:toXScale="0.0"
android:toYScale="0.0"
android:duration="500" />
</set>
I created the same animation using kotlin:
Repo: https://github.com/David-Hackro/Bounce-Animation
You need create your element and extend of anything (ImageView,Button etc)
in my case y created a class named BounceWidget
Add element in xml
<hackro.tutorials.com.bounceWidget.widget.BounceWidget
android:layout_width="match_parent"
android:layout_height="match_parent" />
Add element programmatically
val xpp = resources.getXml(R.xml.bouncewidget)
val attr = Xml.asAttributeSet(xpp)
val layout : LinearLayout = findViewById(R.id.layout)
val octocat1 : BounceWidget = BounceWidget(this,attr)
//you can change this values and have default values
//octocat1.id_resource(R.mipmap.bounceimage) // change image --> default : R.mipmap.ic_launcher
//octocat1.positionX = 1 //position X starting --> default : 0
//octocat1.positionY = 1 //position Y starting--> default : 0
//octocat1.velocityX = 1 //Velocity X --> default : 20
//octocat1.velocityY = 1 //Velocity Y --> default : 15
octocat1.layoutParams = LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT)
layout.addView(octocat1)
I created the following animation:
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="#android:anim/anticipate_overshoot_interpolator"
>
<translate
android:fromXDelta="0"
android:toXDelta="100%p"
android:duration="500"
/>
<translate
android:fromXDelta="-100%p"
android:toXDelta="0"
android:startOffset="500"
android:duration="500"/>
</set>
I test it on an Android 2.3.6 phone and the animation goes sequentially but REVERSED.
First it goes from left to the middle then from the middle to the right. How can I play it in the correct order?
final ImageView iv = new ImageView(this);
iv.setScaleType(ScaleType.CENTER);
final Bitmap b = BitmapFactory.decodeResource(getResources(), R.drawable.layer0);
iv.setImageBitmap(b);
OnClickListener l = new OnClickListener() {
#Override
public void onClick(View v) {
float x = (iv.getWidth() + b.getWidth()) / 2;
AnimationSet set = new AnimationSet(true);
set.setFillBefore(false);
Animation a;
a = new TranslateAnimation(0, x, 0, 0);
a.setDuration(500);
a.setFillAfter(false);
a.setFillBefore(false);
a.setFillEnabled(true);
set.addAnimation(a);
a = new TranslateAnimation(-x, 0, 0, 0);
a.setStartOffset(500);
a.setDuration(500);
a.setFillAfter(false);
a.setFillBefore(false);
a.setFillEnabled(true);
set.addAnimation(a);
iv.startAnimation(set);
}
};
iv.setOnClickListener(l);
setContentView(iv);
As I couldn't modify their orders, I eventually created two separate animations and used an AnimationListener to start the second one.
you can do it simply adding a set attribute element android:repeatMode="reverse". Thus your code should be..
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="#android:anim/anticipate_overshoot_interpolator"
android:repeatMode="reverse"
>
<translate
android:repeatCount="infinite"
android:fromXDelta="0"
android:toXDelta="100%p"
android:duration="2500"
/>
<!-- <translate
android:fromXDelta="-100%p"
android:toXDelta="0"
android:startOffset="500"
android:duration="500"/> -->
</set>
I created an anim.xml file such as below to shake imageview like IOS icon shaking in android.
However it does not provide me same result.
Is there any better idea?
<?xml version="1.0" encoding="utf-8"?>
<rotate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="300"
android:fromDegrees="-2"
android:pivotX="50%"
android:pivotY="50%"
android:repeatCount="infinite"
android:toDegrees="2" />
Try setting android:repeatMode="reverse". Below animation gives a very reasonable immitation on my Galaxy Nexus. Obviously you can fine tune the parameters to your own liking.
<?xml version="1.0" encoding="utf-8"?>
<rotate xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="100"
android:fromDegrees="-5"
android:pivotX="50%"
android:pivotY="50%"
android:repeatCount="infinite"
android:repeatMode="reverse"
android:toDegrees="5" />
Nice shake animation;
res/anim/shake.xml
<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate android:duration="150"
android:fromXDelta="-10%"
android:repeatCount="5"
android:repeatMode="reverse"
android:toXDelta="10%"/>
</set>
How to use it
final Animation animShake = AnimationUtils.loadAnimation(this, R.anim.shake);
btn_done = (Button) findViewById(R.id.btn_act_confirm_done);
btn_done.startAnimation(animShake);
How to use it (Simpler version):
btn_done.startAnimation(AnimationUtils.loadAnimation(this,R.anim.shake));
You could try this:
shake.xml
<translate xmlns:android="http://schemas.android.com/apk/res/android"
android:fromXDelta="0"
android:toXDelta="10"
android:duration="1000"
android:interpolator="#anim/cycle_7" />
cycle_7.xml
<cycleInterpolator xmlns:android="http://schemas.android.com/apk/res/android"
android:cycles="7" />
try to use this one:
<set xmlns:android="http://schemas.android.com/apk/res/android">
<rotate
android:duration="70"
android:fromDegrees="-5"
android:pivotX="50%"
android:pivotY="50%"
android:repeatCount="5"
android:repeatMode="reverse"
android:interpolator="#android:anim/linear_interpolator"
android:toDegrees="5" />
<translate
android:fromXDelta="-10"
android:toXDelta="10"
android:repeatCount="5"
android:repeatMode="reverse"
android:interpolator="#android:anim/linear_interpolator"
android:duration="70" />
</set>
To make shake effect like this
First define shake animation inside anim folder as shake.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<rotate
android:duration="70"
android:fromDegrees="-5"
android:interpolator="#android:anim/linear_interpolator"
android:pivotX="50%"
android:pivotY="50%"
android:repeatCount="5"
android:repeatMode="reverse"
android:toDegrees="5" />
<translate
android:duration="70"
android:fromXDelta="-10"
android:interpolator="#android:anim/linear_interpolator"
android:repeatCount="5"
android:repeatMode="reverse"
android:toXDelta="10" />
</set>
Then in code
if (TextUtils.isEmpty(phone.getText())
|| phone.getText().length() < 10)
{
//shake animation
phone.startAnimation(AnimationUtils.loadAnimation(getActivity(), R.anim.shake));
}
I created a shake effect on Android and posted in GitHub. See if it works better.
https://github.com/teoinke/ShakeAnimation
Relevant code:
<?xml version="1.0" encoding="utf-8"?>
<set
xmlns:android="http://schemas.android.com/apk/res/android"
android:interpolator="#android:anim/overshoot_interpolator"
android:fillAfter="true">
<translate
android:startOffset="100"
android:fromXDelta="0%p"
android:toXDelta="10%p"
android:duration="50" />
<translate
android:startOffset="150"
android:fromXDelta="0%p"
android:toXDelta="-25%p"
android:duration="110" />
<translate
android:startOffset="260"
android:fromXDelta="0%p"
android:toXDelta="25%p"
android:duration="120" />
<translate
android:startOffset="380"
android:fromXDelta="0%p"
android:toXDelta="-20%p"
android:duration="130" />
<translate
android:startOffset="510"
android:fromXDelta="0%p"
android:toXDelta="10%p"
android:duration="140" />
</set>
This one works pretty well (though not perfectly) as an iOS "incorrect PIN" shaking clone:
final float FREQ = 3f;
final float DECAY = 2f;
// interpolator that goes 1 -> -1 -> 1 -> -1 in a sine wave pattern.
TimeInterpolator decayingSineWave = new TimeInterpolator() {
#Override
public float getInterpolation(float input) {
double raw = Math.sin(FREQ * input * 2 * Math.PI);
return (float)(raw * Math.exp(-input * DECAY));
}
};
shakeField.animate()
.xBy(-100)
.setInterpolator(decayingSineWave)
.setDuration(500)
.start();
/**
*
* #param view view that will be animated
* #param duration for how long in ms will it shake
* #param offset start offset of the animation
* #return returns the same view with animation properties
*/
public static View makeMeShake(View view, int duration, int offset) {
Animation anim = new TranslateAnimation(-offset,offset,0,0);
anim.setDuration(duration);
anim.setRepeatMode(Animation.REVERSE);
anim.setRepeatCount(5);
view.startAnimation(anim);
return view;
}
use:
TextView tv;
makeMeShake(tv,20,5); // it will shake quite fast
For Kotlin users:
First create an Animation resource file called shake.xml. Right click on the res folder in Android Studio, then click New > Android Resource File > enter shake for the file name and select Animation for Resource type dropdown. Click OK.
Inside shake.xml paste the following:
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate android:duration="200"
android:fromXDelta="-5%"
android:repeatCount="3"
android:repeatMode="reverse"
android:toXDelta="5%"/>
</set>
Now just call it on a view!
From within a fragment:
myView.startAnimation(AnimationUtils.loadAnimation(requireContext(), R.anim.shake))
From within an activity:
myView.startAnimation(AnimationUtils.loadAnimation(this, R.anim.shake))
(note - myView is the ID given to the view that you want to animate)
If you would like to fine-tune the animation, simply modify the values in shake.xml.
I created a very good approximation of iOS shaking (when you long press a icon to remove app from homescreen). You have to apply inside your code, programmatically, as it requires random number generation:
int dur1 = 70 + (int)(Math.random() * 30);
int dur2 = 70 + (int)(Math.random() * 30);
// Create an animation instance
Animation an = new RotateAnimation(-3, 3, Animation.RELATIVE_TO_SELF, 0.5f, Animation.RELATIVE_TO_SELF, 0.5f);
// Set the animation's parameters
an.setDuration(dur1); // duration in ms
an.setRepeatCount(-1); // -1 = infinite repeated
an.setRepeatMode(Animation.REVERSE);
an.setFillAfter(true); // keep rotation after animation
// Create an animation instance
Animation an2 = new TranslateAnimation(-TranslateAnimation.RELATIVE_TO_SELF,0.02f,
TranslateAnimation.RELATIVE_TO_SELF,0.02f,
-TranslateAnimation.RELATIVE_TO_SELF,0.02f,
TranslateAnimation.RELATIVE_TO_SELF,0.02f);
// Set the animation's parameters
an2.setDuration(dur2); // duration in ms
an2.setRepeatCount(-1); // -1 = infinite repeated
an2.setRepeatMode(Animation.REVERSE);
an2.setFillAfter(true); // keep rotation after animation
AnimationSet s = new AnimationSet(false);//false means don't share interpolators
s.addAnimation(an);
s.addAnimation(an2);
// Apply animation to image view
itemView.setAnimation(s);
This code was design to be applied inside an adapter's gridview (getView), but you can apply to any view by changing the last line to:
yourViewName.setAnimations(s);
Kotlin version of lincolnq's answer
val FREQ = 3f
val DECAY = 2f
val decayingSineWave = TimeInterpolator { input ->
val raw = sin(FREQ * input * 2 * Math.PI)
(raw * exp((-input * DECAY).toDouble())).toFloat()
}
// where binding.loginFrame is the view you wanna shake
binding.loguinFrame.animate()
.withEndAction{
// here you can clear the fields after the shake
}
.xBy(-100f)
.setInterpolator(decayingSineWave)
.setDuration(500)
.start()
IOS wobble animation is not that simple try to change pivot x and y randomly when rotate. You should change the value programatically though. May be you also can use translate animation simultaneously
Banging my head for more than two hours, I knew how to shake and wobble an view.
Unfortunately the accepted answer won't work apart from onCreateView of fragment.
Example if you have onClick method and inside in it. You have animation like below it won't work.
Please go through the code.
DoneStart.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View view) {
register(view);
}
});
The register method has some checks like below code
private void register(View view) {
String type = typedThings.getText.toString();
String km = Km_Now.getText().toString();
if (serviceType == null) {
animationServiceList = AnimationUtils.loadAnimation(getActivity(), R.anim.shake_wobble);
silverServiceButton.setAnimation(animationServiceList);
generalServiceButton.setAnimation(animationServiceList);
platinumServiceButton.setAnimation(animationServiceList);
animationServiceList.start();
} else if (km == null) {
animationEditText = AnimationUtils.loadAnimation(getActivity(), R.anim.shake_wobble);
Km_Now.setAnimation(animationEditText);
animationEditText.start();
}
The Call animationServiceList.start(); will never be called,
SOLUTION: Use PropertyAnimator like ObjectAnimator.
Other answers are correct as well but this is a bit smoother than them since it uses an interpolator produces smooth numbers for back an forth movement
public class WobblyView extends ImageView implements ValueAnimator.AnimatorUpdateListener {
private final ValueAnimator va = ValueAnimator.ofInt(-10, 10);
public WobblyView(Context context) {
this(context, null);
}
public WobblyView(Context context, #Nullable AttributeSet attrs) {
this(context, attrs, 0);
}
public WobblyView(Context context, #Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
setAdjustViewBounds(true);
setImageResource(R.drawable.ic_logo);
va.setInterpolator(new AccelerateDecelerateInterpolator());
va.setRepeatMode(ValueAnimator.REVERSE);
va.setRepeatCount(ValueAnimator.INFINITE);
va.setDuration(1000);
}
#Override
protected void onAttachedToWindow() {
super.onAttachedToWindow();
va.addUpdateListener(this);
va.start();
}
#Override
protected void onDetachedFromWindow() {
super.onDetachedFromWindow();
va.removeUpdateListener(this);
}
#Override
public void onAnimationUpdate(ValueAnimator animation) {
int heading = (int) animation.getAnimatedValue();
setRotation(heading);
}
}