Android 如何正确设置路径值来描述圆弧动画
How to properly set path values to describe an arc animation in Android
我在一个按钮内有一个视图 "whiteCircle",我想从它的初始位置移动到描述弧线的白框 "imageSquared",然后返回到它的初始位置。
我试过的是:
private fun startArcAnimation() {
val path = Path()
val location = IntArray(2)
imageSquared.getLocationOnScreen(location)
path.arcTo(
0f,
0f,
location[0].toFloat() + imageSquared.width,
location[0].toFloat() + imageSquared.height,
180f,
180f,
true
)
val animator = ObjectAnimator.ofFloat(whiteCircle, View.X, View.Y, path)
animator.duration = 1000
animator.start()
}
这是结果:
你能帮我正确设置路径值吗?
我一直在努力使用 arcTo 属性,但没有成功。
提前致谢。
这是我的实现:
arcTo
方法创建放置在矩形中的椭圆。所以首先你需要创建正确的矩形。你的路径应该从椭圆形的 180 度开始,顺时针移动 180 度(椭圆形的零角在右侧)。
我建议为视图的 translationX
和 translationY
属性设置动画。
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
greenButton.setOnClickListener {
startArcAnimation()
}
}
private fun startArcAnimation() {
if (red.translationX != 0f) {
//return to start position animation
red.animate().translationX(0f).translationY(0f).start()
return
}
val rectHeight = 600
val left = 0f
val top = -rectHeight / 2
val right = white.x - red.x
val bottom = white.y + rectHeight / 2 - red.y
val path = Path()
path.arcTo(left, top.toFloat(), right, bottom, 180f, 180f, true)
val animator = ObjectAnimator.ofFloat(red, View.TRANSLATION_X, View.TRANSLATION_Y, path)
animator.duration = 1000
animator.start()
}
}
这里是activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#000"
android:padding="16dp">
<Button
android:id="@+id/greenButton"
android:layout_width="100dp"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:background="#0a0"
android:stateListAnimator="@null" />
<ImageView
android:id="@+id/white"
android:layout_width="50dp"
android:layout_height="50dp"
android:layout_gravity="center_vertical|right"
android:background="#fff" />
<ImageView
android:id="@+id/red"
android:layout_width="20dp"
android:layout_height="20dp"
android:layout_gravity="center_vertical"
android:layout_marginLeft="70dp"
android:layout_marginBottom="10dp"
android:background="#f00" />
</FrameLayout>
我在一个按钮内有一个视图 "whiteCircle",我想从它的初始位置移动到描述弧线的白框 "imageSquared",然后返回到它的初始位置。
我试过的是:
private fun startArcAnimation() {
val path = Path()
val location = IntArray(2)
imageSquared.getLocationOnScreen(location)
path.arcTo(
0f,
0f,
location[0].toFloat() + imageSquared.width,
location[0].toFloat() + imageSquared.height,
180f,
180f,
true
)
val animator = ObjectAnimator.ofFloat(whiteCircle, View.X, View.Y, path)
animator.duration = 1000
animator.start()
}
这是结果:
你能帮我正确设置路径值吗? 我一直在努力使用 arcTo 属性,但没有成功。
提前致谢。
这是我的实现:
arcTo
方法创建放置在矩形中的椭圆。所以首先你需要创建正确的矩形。你的路径应该从椭圆形的 180 度开始,顺时针移动 180 度(椭圆形的零角在右侧)。
我建议为视图的 translationX
和 translationY
属性设置动画。
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
greenButton.setOnClickListener {
startArcAnimation()
}
}
private fun startArcAnimation() {
if (red.translationX != 0f) {
//return to start position animation
red.animate().translationX(0f).translationY(0f).start()
return
}
val rectHeight = 600
val left = 0f
val top = -rectHeight / 2
val right = white.x - red.x
val bottom = white.y + rectHeight / 2 - red.y
val path = Path()
path.arcTo(left, top.toFloat(), right, bottom, 180f, 180f, true)
val animator = ObjectAnimator.ofFloat(red, View.TRANSLATION_X, View.TRANSLATION_Y, path)
animator.duration = 1000
animator.start()
}
}
这里是activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#000"
android:padding="16dp">
<Button
android:id="@+id/greenButton"
android:layout_width="100dp"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:background="#0a0"
android:stateListAnimator="@null" />
<ImageView
android:id="@+id/white"
android:layout_width="50dp"
android:layout_height="50dp"
android:layout_gravity="center_vertical|right"
android:background="#fff" />
<ImageView
android:id="@+id/red"
android:layout_width="20dp"
android:layout_height="20dp"
android:layout_gravity="center_vertical"
android:layout_marginLeft="70dp"
android:layout_marginBottom="10dp"
android:background="#f00" />
</FrameLayout>