IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 移动开发 -> Android过渡动画,发现掘金小秘密,太爽了 -> 正文阅读

[移动开发]Android过渡动画,发现掘金小秘密,太爽了

android:id="@+id/tvText"
android:layout_width=“match_parent”
android:layout_height=“wrap_content”
android:layout_above="@id/ivImage"
android:layout_marginBottom=“10dp”
android:gravity=“center”
android:text=“我是第2个Activity”
android:textColor="@color/c_333"
android:textSize=“18sp” />
`


**「预览图」** ![](https://user-gold-cdn.xitu.io/2020/7/11/173398cdb47bb032?imageView2/0/w/1280/h/960/ignore-error/1) `activityTransform`属性也可以通过代码设置。

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { ivImage.transitionName="activityTransform" }


2.  在`FirstActivity`中给`ImageView`设置点击事件,跳转到第二个Activity。

ivImage.setOnClickListener { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {//判断Android版本 val bundle = ActivityOptions.makeSceneTransitionAnimation(this, ivImage, "activityTransform") .toBundle() startActivity(Intent(this, SecondActivity::class.java), bundle) } else { startActivity(Intent(this, SecondActivity::class.java)) } }


代码中,先判断当前`Android`版本是否大于等于5.0,大于或等于`Android 5.0`的话就设置共享元素动画,小于5.0 就正常启动第二个`Activity`。

通过`ActivityOptions.makeSceneTransitionAnimation()`创建启动`Activity`过渡的一些参数,`makeSceneTransitionAnimation()`函数第一个参数为`Activity`对象;第二个参数为共享元素组件,这里设置为`id`是`ivImage`的`ImageView`视图;第三个参数为`transitionName`属性的值,这里是`activityTransform`。在调用`AcivityOptions`对象`toBundle`函数,包装成`Bundle`对象。

**「效果图:」**

![](https://user-gold-cdn.xitu.io/2020/7/11/173399a99a8948a3?imageslim) **「多个共享元素过渡」**

多个共享元素过渡也很简单,只需要调用`makeSceneTransitionAnimation()`函数的另外一个重载函数即可。

1.  在前面XML布局的基础上,给`TextView`增加`transitionName`属性:`textTransform`。

`

<?xml version="1.0" encoding="utf-8"?>




<?xml version="1.0" encoding="utf-8"?>




`


2.  构建多个`Pair`对象,并传递给`makeSceneTransitionAnimation()`函数,启动`Activity`。

ivImage.setOnClickListener { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { val imagePair=Pair<View,String>(ivImage,"activityTransform") val textPair=Pair<View,String>(ivImage,"textTransform") val bundle = ActivityOptions.makeSceneTransitionAnimation(this, imagePair,textPair).toBundle() startActivity(Intent(this, SecondActivity::class.java), bundle) } else { startActivity(Intent(this, SecondActivity::class.java)) } }


这里主要是通过将共享视图和`transitionName`属性的值包装到`Pair`对象,其他操作和一个共享元素的操作步骤并无区别。

**「效果图:」**

![](https://user-gold-cdn.xitu.io/2020/7/11/1733cfa764aa491f?imageslim)

**「深坑提醒」**

有时从`RecyclerView`界面进入到详情页,由于详情页加载延迟,可能出现没有效果。例如`ImageView`从网络加载图片,可能A界面到B界面没效果,B回到A界面有效果。

![](https://user-gold-cdn.xitu.io/2020/7/13/173473efe2c8292e?imageslim) 解决步骤:

1.  在`setContentView`后添加下面代码,延迟加载过渡动画。

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { postponeEnterTransition() }


2.  在共享元素视图加载完毕,或者图片加载完毕后调用下面代码,开始加载过渡动画。

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { startPostponedEnterTransition() }


![](https://user-gold-cdn.xitu.io/2020/7/13/173473cc8f694a47?imageslim) 例如我是在Glide加载完再调用:

Glide.with(mContext) .asBitmap() .load(value?.avatar ?: "") .listener(object : RequestListener<Bitmap> { override fun onResourceReady(resource: Bitmap?, model: Any?, target: Target<Bitmap>?, dataSource: DataSource?, isFirstResource: Boolean): Boolean { animatorCallback?.invoke()//回调开始加载过渡动画 return false } override fun onLoadFailed(e: GlideException?, model: Any?, target: Target<Bitmap>?, isFirstResource: Boolean): Boolean { animatorCallback?.invoke()//回调开始加载过渡动画 return false } }) .apply(RequestOptions.circleCropTransform()) .placeholder(R.mipmap.ic_default) .error(R.mipmap.ic_default) .into(authorBinding!!.ivAvatar)


大家也可以考虑下面代码:

shareElement.viewTreeObserver.addOnPreDrawListener(object : ViewTreeObserver.OnPreDrawListener { override fun onPreDraw(): Boolean { shareElement!!.viewTreeObserver.removeOnPreDrawListener(this) if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { animatorCallback?.invoke() } return true } })


#### 二)、进入过渡与退出过渡动画

与共享元素相反的,就是Activity进入与退出过渡动画,两个Activity之间在没有共享的视图情况下进行动画切换。下面先看三种动画效果图:**「爆炸式效果」**和**「淡入淡出式效果」**、**「滑动式效果」**。

*   **「爆炸式」**:将视图移入场景中心或从中移出;
*   **「滑动式」**:将视图从场景的其中一个边缘移入或移出;
*   **「爆炸式」**:通过更改视图的不透明度,在场景中添加视图或从中移除视图;

第一个界面采用`Fade`淡入淡出效果,第二个界面采用了`Explode`爆炸效果。

![](https://user-gold-cdn.xitu.io/2020/7/12/17340f22a8a3dea0?imageslim) 前后两个界面都采用了`Slide`滑入滑出效果。

![](https://user-gold-cdn.xitu.io/2020/7/12/17340fc926f651e5?imageslim) 利用Android现有的过渡框架,实现起来是很简单的,步骤如下:

1.  在`Activity`的`onCreate()`方法中调用 `setContentView()`前设置启用窗口过渡属性;

window.requestFeature(Window.FEATURE_CONTENT_TRANSITIONS)


2.  创建过渡效果对象`Slide`、`Explode`、`Fade`;

val slide=Slide() slide.slideEdge=Gravity.START slide.duration=300//效果时长,一般Activity切换时间很短,不建议设置过长


如果是`Slide`效果,可以设置`slideEdge`属性来指定滑动方向,默认是`Gravity.BOTTOM`。

3.  将过渡效果设置给window相关属性,设置;

//退出当前界面的过渡动画 window.exitTransition = slide //进入当前界面的过渡动画 window.enterTransition = slide //重新进入界面的过渡动画 window.reenterTransition = slide


4.  调用第二个`Activity`界面,使用过渡效果。

startActivity( Intent(this, SecondActivity::class.java), ActivityOptions.makeSceneTransitionAnimation(this).toBundle())


那么`Activity`的`OnCreate()`方法看起来是这样子的。

override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { window.requestFeature(Window.FEATURE_CONTENT_TRANSITIONS) window.allowEnterTransitionOverlap=false Slide().apply { duration = 300 excludeTarget(android.R.id.statusBarBackground, true) excludeTarget(android.R.id.navigationBarBackground, true) }.also { window.exitTransition = it window.enterTransition = it window.reenterTransition = it } } setContentView(R.layout.activity_first) ivContent.setOnClickListener { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { startActivity( Intent(this, SecondActivity::class.java), ActivityOptions.makeSceneTransitionAnimation(this).toBundle() ) } } }


上面代码中调用 了`excludeTarget()`方法将状态栏和导航栏排除在过渡动画效果之外。否则会跟着一起起动画效果,不是很美观。

正常情况,退出与进入过渡动画会有一小段交叉的过程,而`window.allowEnterTransitionOverlap=false`就是禁止交叉,只有退出过渡动画结束后才会再显示进入过渡动画。

如果第二个`Activity`在`finish`掉后,回到第一个`Activity`界面也想有过渡效果,就不要手动调用`finish()`,可以调用`finishAfterTransition ()`方法。

#### 三)、兼容Android 5.0前

如果Android 5.0前也想要有切换动画怎么办?

1.  在`res/anim`文件夹下创建想要的效果:

<alpha xmlns:android="http://schemas.android.com/apk/res/android" android:interpolator="@interpolator/decelerate_quad" android:fromAlpha="0.0" android:toAlpha="1.0" android:duration="@android:integer/config_longAnimTime" />


2.  在启动`Activity`后调用`overridePendingTransition()`方法。

val intent = Intent(this, TestActivity2::class.java) startActivity(intent) overridePendingTransition(R.anim.fade_in, R.anim.fade_out)


`overridePendingTransition()`方法第一个参数为下一个界面进入动画,第二个参数为当前界面退出动画。

到这里,`Activity`的切换使用过渡动画基本就结束了。有朋友可能会问,只有Activity切换才能应用过渡效果么?

### 二、布局变化过渡动画

在上一节要理解一个概念:场景。布局的显示与隐藏可以理解分别为一个场景,过渡动画就是解决场景切换带来的生硬视觉感受。Activity切换过渡动画指在两个Activity之间,而布局变化过渡动画,是指同个Activity之间View的变化过渡动画。

#### 一)、手动创建Scene

手动创建场景的话,需要我们自己创建起始和结束场景,利用现有的过渡效果来达到两个场景的切换。默认情况下,当前界面就是起始场景。

1.  创建起始场景和结束场景的`xml`布局。起始场景和结束场景需要有相同根元素,例如下面代码`id`为`flConatent`的`FrameLayout`布局。

<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical"> <TextView android:id="@+id/tvText" android:text="内容过渡动画" android:gravity="center" android:textSize="18sp" android:layout_width="match_parent" android:layout_height="50dp"/> <FrameLayout android:id="@+id/flContent" android:layout_weight="1" android:layout_width="match_parent" android:layout_height="0dp"> <include layout="@layout/layout_first_scene"/> </FrameLayout> </LinearLayout>


初始视图,第一个场景,布局`layout_first_scene.xml`:

<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical"> <TextView android:id="@+id/tvFirst" android:textSize="18sp" android:layout_marginTop="100dp" android:layout_width="match_parent" android:layout_height="match_parent" android:gravity="center_horizontal|top" android:text="感谢大家阅读文章" /> </LinearLayout>


第二个场景,布局`layout_second_scene.xml`:

<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical"> <TextView android:textSize="18sp" android:layout_marginTop="100dp" android:layout_width="match_parent" android:layout_height="match_parent" android:gravity="center_horizontal|top" android:text="我是新小梦\n欢迎大家点赞支持一下" /> </LinearLayout>


2.  创建起始场景和结束场景。

val firstScene = Scene.getSceneForLayout(flContent, R.layout.layout_first_scene, this) val secondScene = Scene.getSceneForLayout(flContent, R.layout.layout_sencod_scene, this)


默认情况下,过渡动画应用整个场景,如果场景某个`View`不参加,可以通过`过渡效果对象`的`removeTarget()`方法进行移除。

Slide(Gravity.TOP).removeTarget(tvNoJoin)

学习分享

在当下这个信息共享的时代,很多资源都可以在网络上找到,只取决于你愿不愿意找或是找的方法对不对了

很多朋友不是没有资料,大多都是有几十上百个G,但是杂乱无章,不知道怎么看从哪看起,甚至是看后就忘

如果大家觉得自己在网上找的资料非常杂乱、不成体系的话,我也分享一套给大家,比较系统,我平常自己也会经常研读。

2021最新上万页的大厂面试真题

CodeChina开源项目地址:https://codechina.csdn.net/m0_60958482/android_p7

七大模块学习资料:如NDK模块开发、Android框架体系架构…

只有系统,有方向的学习,才能在段时间内迅速提高自己的技术。

这份体系学习笔记,适应人群:
第一,学习知识比较碎片化,没有合理的学习路线与进阶方向。
第二,开发几年,不知道如何进阶更进一步,比较迷茫。
第三,到了合适的年纪,后续不知道该如何发展,转型管理,还是加强技术研究。如果你有需要,我这里恰好有为什么,不来领取!说不定能改变你现在的状态呢!
m0_60958482/android_p7](https://codechina.csdn.net/m0_60958482/android_p7)**

[外链图片转存中…(img-T4rGLly0-1630921143941)]

七大模块学习资料:如NDK模块开发、Android框架体系架构…

[外链图片转存中…(img-gvPi6Dy9-1630921143943)]

只有系统,有方向的学习,才能在段时间内迅速提高自己的技术。

这份体系学习笔记,适应人群:
第一,学习知识比较碎片化,没有合理的学习路线与进阶方向。
第二,开发几年,不知道如何进阶更进一步,比较迷茫。
第三,到了合适的年纪,后续不知道该如何发展,转型管理,还是加强技术研究。如果你有需要,我这里恰好有为什么,不来领取!说不定能改变你现在的状态呢!
由于文章内容比较多,篇幅不允许,部分未展示内容以截图方式展示 。

  移动开发 最新文章
Vue3装载axios和element-ui
android adb cmd
【xcode】Xcode常用快捷键与技巧
Android开发中的线程池使用
Java 和 Android 的 Base64
Android 测试文字编码格式
微信小程序支付
安卓权限记录
知乎之自动养号
【Android Jetpack】DataStore
上一篇文章      下一篇文章      查看所有文章
加:2021-09-07 10:56:29  更:2021-09-07 10:57:31 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/23 16:54:56-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码