android回弹效果
㈠ 关于刚刚发布的 Android10,需要知道这 6 大改进
9月4日,Google 终于发布了Android 10的正式版本。此前的内测阶段它一直以 Android Q 的名字示人,无论是交互、使用体验的优化,还是技术上的升级,正式的 Android 10 在诸多方面都进行了更为人性化的改变。
虽然每一次 Android 更新都有一个长长的新特性列表,但是每次最值得关注的核心功能,始终只有那么几个。关于 Andorid 10,最值得你关心的,就是下面的 6 大改变。
1. 优雅的深色暗黑模式上线
“深色模式”是今年产品设计的流行趋势,深色模式的设计不仅是出于对用户视力保护与减少视觉疲劳的考量,也利于营造更沉浸式的体验。而Google将“深色模式”称为“暗黑主题”。
从视觉的角度上来说,Android 10深色模式下的界面并非是简单地在色彩上做反相处理,而是有更加细致更多元素与细节上的差异化处理。无论是抽屉菜单、设置还是应用的界面按钮,都会由“白底黑字”变成“黑底白字”。
Google 官方的 Material Design设计规范中,在 Color 部分也新增了关于Dark Mod即深色主题界面的设计规则详细阐述。并且深色模式会比全白背景的普通模式更省电,当然这与大多数中高端智能机常使用OLED屏幕有关。但目前 Android 10的“暗黑主题”适用范围仅限于系统界面与 Google 自家的部分应用,很多第三方应用如我们常用的“微信”“微博”等都尚未支持新的深色模式。
2. 开启全局手势操作
引入全局手势操作,是Android 10最值得被关注的直观改变。虽然部分手势操作与先前发布的内测版本Android Q Beta有所改变,但核心导航功能与设计逻辑并无较大调整。启用新系统后,屏幕底部的虚拟按键与导航栏将不会再出现,取而代之的是一个指示条。在市场培育下,iOS的去按键化全屏手势交互已让许多用户逐渐养成使用习惯,这里的手势操作逻辑与iOS基本保持一致对于用户而言学习成本已降低很多。
▲ 图片来自:Android Central
上滑返回主屏,侧滑返回上一层,左右滑动导航条能快速切换多任务。比较特别的是区别于iOS与前内测版本,当执行上滑返回主屏的操作时,会看到图标有个小回弹的效果能更加直观的反馈交互的变化。
整体而言经过多个版本的微调,Android 10 的这套手势设计已基本能取代以前的虚拟键操作了,且操作流畅度和使用手感已接近iOS的效果。
▲ 图片来自:The Verge
但如果一时间依旧无法适应取消虚拟按键的操作,Android 10还贴心的为我们保留了传统的三按键模式与Android P时代的二键模式,供用户随时在设置中切换使用。
▲ 图片来自:Arstechnica
3. 新增“专注模式”,专治注意力分散症
在早前的内测版Android Q, Google已将“专注模式”(Focus Mode) 直接集成到系统顶部的快捷菜单当中了。注意力管理近几年已逐渐成为系统平台、厂商与用户本身都高度关注的一件事情。
“专注模式”是一个结合“数字 健康 管理”(Digital Wellbeing) 与“勿扰模式”(Do Not Disturb)的功能。用户可以自己选择想要屏蔽的应用,在每次开启“专注模式”后将这些让人分心的应用免打扰处理。被屏蔽的应用图标会呈不可点击的置灰状态无法被打开,可有效减少工作时注意力被分散。
4. 关注用户隐私与个人数据保护,加强权限调用限制
于Android 10而言,最重要的改变就是对隐私保护与权限控制的限制更新。 Google官方在更新指南里花费了很大的篇幅来说明Android 10对于App获取与使用用户数据的权限限制与说明。Android 10 系统整体而言对于用户安全和隐私保护方面进行了加强管理。
对于第三方应用获取如用户手机摄像头、相机或麦克风等传感器的调用权限,使用用户GPS 定位等与个人隐私相关甚密的数据,都有了更为细化的权限管理。当某些App正在调用非必须的权限时,系统还会发出通知提醒用户,以确认信息授权的意愿。
此外, Google 还推出了“Project Mainline”项目,将Android 系统涉及的隐私管理,以及通用接口(比如 OpenGL)模块单独划分出来进行管理,进一步加强安全保护和方便后期的漏洞修复。
5. 人工智能技术的更广泛使用
Google在本次的Android 10 系统中,进行了更多对近几年来机器学习技术与成果的运用尝试。比如下拉通知栏里增加了“智能回复”功能。可根据接受的信息或邮件内容,自动为用户提供一些回复语或Emoji表情的回复参考。还有特别实用的“Live Caption”实时字幕功能。像YouTube 中的实时字幕功能一样,Android 10能够自动为手机中正在播放的影片和音频配上字幕。对于听觉障碍人士而言,这个功能的增加让理解有声视频不再困难重重。但该功能暂时还未正式上线,将在今年秋季推送到Android 10系统中。
6. 取消系统甜品名后缀,迎接更广泛的受众
曾今, Android 系统有将甜品名作为系统命名后缀的传统。如上一代的“Android P”,也被称作“Android Pie”,但一些用户和媒体依旧倾向用“Android 9”来称呼它。对于不熟悉Android系统和其甜品命名规则的用户而言,称呼难记易混淆。
从这一代 Android 10起,Android系统开始回归以全球更为通用的数字后缀来进行系统命名。Google希望借此次系统命名规则的改变,降低大家对Android系统的认知门槛,去迎接更为广泛的用户群体。
㈡ 如何优雅地在Android上实现iOS的图片预览
原文博客链接
用过 iOS 的都知道,拟物理的回弹效果在上面非常普遍,因为这是 iOS 系统支持的一套 UI 框架,但是 Android 就没有了,就拿图片查看器来讲,iOS 的效果就是感觉一张图片被绑定在了弹簧装置上,滑动很自然,Android 没有自带的图片查看器,需要自己实现
市面上主流的图片查看器都没有回弹的效果,一部分原因是没有这个需求,还有一部分是实现麻烦,这里讲述一个个人认为最好的方案
一个图片查看器,要求可以滑动 Fling,触碰到边界的时候回弹,有越界孝唤回弹的效果,支持双指缩放,双击缩放
咋一看需求,应该好写,滚动的时候用 Scroller 来解巧态凯决,回弹效果直接用 ValueAnimator ,设置插值器为减速插值器来解决。看似简单,但是因为是仿物理效果,中间牵扯到从滚动到回弹的时候( Scroller 动画切换到 ValueAnimator 动画)的闭老速度衔接问题,要看上去从滚动到开始回弹至结束没有突兀,中间的特判边界处理是很麻烦的,还要牵扯到缩放,所以不考虑这种方案
既然是要模拟现实中的物理效果,为何不在每一帧根据当前的状态得到对用的加速度,然后去计算下一帧的状态位置,这样只要模拟现实中的物理加速度不就可以实现了吗,那些边界特判之类的就可以去见阎王了
方案确定完毕,接下来就是选定加速度的方程,要模拟弹簧的效果,拉力很简单,用胡克定律嘛! F = k * dx ,摩擦力呢? Ff = μ*FN ? 这里推荐一个更加好的方案,借鉴自 Rebound 库,这是 Facebook 的一个弹簧动画库,设定一个目的数值,它会根据当前的拉力,摩擦力,速度然后变化到目标值,加速度方程为
其中 tension 为弹性系数, friction 为摩擦力系数,为什么让摩擦力和速度成正比呢?如果摩擦力和速度成正比,那么就不存在静摩擦力,也就是不存在物体静止情况下拉力小于摩擦力的情况(因为速度为0的时候,阻力为0,除非拉力为0),物体肯定会向目标地点靠近,遏制了物体摩擦力过大而无法达到目的地情况
为了方便接入各种 View ,设计一个 ZoomableGestureHelper 类
设计目的,我只需要知道视图的大小边界 (bounds) 和内部可滚动回弹的边界 (innerBounds),就可以通过计算得到一个新的转换矩阵
对于物理状态,需要一个类 SpringPhysicsState 来做存储,里面包含了速度、拉力系数、摩擦力系数,不保存位置,因为位置是通过 getBounds 动态计算得到的
速度分解成水平方向和垂直方向,因为处理方法一样,下面只讲述垂直方向的计算
状态1 :其中一边有越界
分析一下上图中的位置,蓝色部分为内部图片,它被拖动越界了,此时的合力应该为 tension * dx - friction * v , v 为图片在 y 轴方向上的速度,( dx 和 v 都是矢量,我暂且设置向右和向下为正),之后就直接调用 invalidate(); ,就可以播放动画了。
状态2:两边都没越界
此时因为两边都没有越界,所以应该不存在拉力,可以认为此时 dx 为0,摩擦力需要注意下,因为可以支持滑动( Fling ),所以此时的摩擦力要比之前越界回弹时候的摩擦力小,至于具体数值,文末会给出
状态3:两边都超出
此时两边都超出边界,蓝色区域应该和红色区域中心绑定,所以此时的 dx 为 dxBottom - dxTop (注意符号,因为 dx 为矢量,所以不能是 dxTop - dxBottom )
缩放的方法和移动一致,设定 tension 和 friction ,边界设定为外面红色的框框,蓝色区域无法某一边充满红色区域的时候,有拉力,否则没拉力,摩擦力一直存在,至于双击放大和放小,只需要在双击的时候给缩放状态设置一个初速度,然后 invalidate(); ,搞定!是不是很简单啊
时间这一个参数在计算中是非常重要的,这关系到当前微分状态的数值变化,假如用欧拉方法模拟速度和位置的变化, x' = x + v * dt , v' = v + a * dt ,公式可以看出时间决定了动画的快慢,为了接近现实物理时间,这里采用的时间单位为秒(计算机中常用的是毫秒)
确定了单位,还需要控制一下时间间隔的数值范围,我们不能让两次 computeScroll 的时间间隔过于短或者过于长,这里采用的策略为固定每次计算时候的时间间隔,如果两次 computeScroll 的时间间隔小于此时间间隔,那么保存累计时间间隔,等待下一次 computeScroll ,直到大于等于固定的时间间隔,再用 while 循环一步一步的计算
结束判定是唯一的一个坑,因为计算机只是在 dt 时间内模拟速度和位移的变化,不是通过微积分计算的,存在误差,比如欧拉方法 x' = x + v * dt 和 v' = v + a * dt 计算得到的 x' 和 v' 都是近似数值,把 dt 这段时间内的变化看成了匀变速运动
所以结束判定还需要设置一个阈值,当速度和偏移量小于此数值的时候,可以认定为达到了目的地
对于 ViewPager 的适配有些问题,如果在 Down 的时候 requestDisallow true 移动过程中到了左右边界又 requestDisallow false ,此时 ViewPager 会有一个突变( 突变可耻但有用 ),而且多指头的时候可能会崩溃,这是 ViewPager 的 Bug,具体细节请看源码
㈢ 自定义scrollview怎么实现回弹
先我们先建一个类:UserDefineScrollView.Java 代码如下
package com.ysbl.myview;
import android.content.Context;
import android.graphics.Rect;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.View;
import android.view.animation.TranslateAnimation;
import android.widget.ScrollView;
/**
* 有弹性的ScrollView
* 实现下拉弹回和上拉弹回
* @author zhangjg
* @date Feb 13, 2014 6:11:33 PM
*/
public class UserDefineScrollView extends ScrollView {
private static final String TAG = "ElasticScrollView";
//移动因子, 是一个百分比, 比如手指移动了100px, 那么View就只移动50px
//目的是达到一个延迟的效果
㈣ android上怎样加快过场动画的速度
android:interpolator="@android:anim/accelerate_interpolator" 设置动画为加速动画(动画播放中越来越快)
android:interpolator="@android:anim/decelerate_interpolator" 设置动画为减速动画(动画播放中越来越慢)
android:interpolator="@android:anim/accelerate_decelerate_interpolator" 设置动画为先加速在减速(开始速度最快 逐渐减慢)
android:interpolator="@android:anim/anticipate_interpolator" 先反向执行一段,然后再加速反向回来(相当于我们弹簧,先反向压缩一小段,然后在加速弹出)
android:interpolator="@android:anim/anticipate_overshoot_interpolator" 同上先反向一段,然后加速反向回来,执行完毕自带回弹效果(更形象的弹簧效果)
android:interpolator="@android:anim/bounce_interpolator" 执行完毕之后会回弹跳跃几段(相当于我们高空掉下一颗皮球,到地面是会跳动几下)
android:interpolator="@android:anim/cycle_interpolator" 循环,动画循环一定次数,值的改变为一正弦函数:Math.sin(2* mCycles* Math.PI* input)
android:interpolator="@android:anim/linear_interpolator" 线性均匀改变
㈤ android 中如何去掉listView自带的回弹效果
在xml中,listView的一个属性
android:overScrollMode="never"
在代码中
mListView.setOverScrollMode(View.OVER_SCROLL_NEVER);
设置后,魅族等手机下拉时就不会显示HOLD了
㈥ Android自定义控件之可平移、缩放、旋转图片控件
先上效果图
源码
单点拖动图片对图片进行平移操作。双手缩放图片大小和旋转图片到一定的角度。图片缩放的时候 不能大于最大的缩放因子和小于最小的缩放因子。大于最大缩放因子或者小于最小缩放因子需要对图像进行回弹。图片旋转的角度只能为90度的倍数,不满足90度要进行回弹。图片回弹要一个渐变的效果。
大体思路: 首先,Android中提供了Matrix类可以对图像进行处理。其次,要显示一张图片最容易想到的就是ImageView。回弹要求渐变的过程,可以通过属性动画进行设置。所以大体的思路是:继承ImageView,重写onTouchEvent()方法,判断事件类型,在对应的事件使用Matrix对图像进行变换。
Matrix是一个已经封装好的矩阵,最重要的作用就是对坐标点进行变换。
举个栗子:
1.某个点(x0,y0,1)通过单位矩阵E映射得到的点还是(x0,y0,1)。
3.点(x0,y0,1)通过矩阵T映射得到的点就会做如下的变换
可以看到点(x0,y0,1)经过T矩阵在x轴方向上平移了dx,在y轴方向上平移了dy。
通过以上的变换可以得到具体的思路: 我们维护一个图像对应的矩阵mCurrentMatrix,该矩阵主要是对ImageView中的图像的各个点进行映射。ImageView在容器位置摆放完成之后,置mCurrentMatrix矩阵为单位矩阵。当onTouchEvent()方法中触发单点触控并且手指进行平移的时候,调用矩阵mCurrentMatrix的postTranslate(dx,dy),对mCurrentMatrix进行变换。当手指抬起,利用变换结束后的矩阵对图像的各个点进行映射,从而得到平移变换后的图像。同理可得,在两只手指进行缩放旋转的时候,我们对矩阵mCurrentMatrix进行各种变换,当缩放旋转的事件结束再利用变换完的矩阵去映射图像的各个点,从而得到缩放、旋转后的图像。
安卓自定义View进阶 - Matrix原理
安卓自定义View进阶 - Matrix详解
首先理清事件的逻辑:
初始化图像大小和位置
缩放图像大小和控件大小自适应,平移图像中心和控件中心重合
onTouchEvent()函数
平移操作
将图像对应的矩阵进行变换。
缩放操作
mBoundRectF为记录图像边界的矩形。缩放的时候选取图像的中心进行缩放。
旋转操作
旋转的时候旋转的旋转中心也是图像的中心
图像中各个点的映射
调用ImageView的setImageMatrix(Matrix matrix)会让ImageView根据设置的matrix去重新绘制图像。
更新图像的矩形边界
获得图像的矩形,并根据矩阵映射矩形各个点的坐标。
缩放回弹
旋转回弹
一些计算方法
要求图像的变换是一个渐变的过程,很容易想到的就是属性动画。因为属性动画本身就是对值进行不断set的过程。而我们维护的矩阵也是一个值,所以很自然可以想到,如果得到回弹之前的矩阵的值以及回弹之后矩阵的值,就可以根据动画监听器中动画当前的系数值去改变矩阵的值。
对animator对象设置完监听器之后,就可以在手指抬起的时候调用属性动画的start()方法开启动画。
自定义可平移、缩放、旋转的控件主要点有两个方面:一是onTouchEvent()中判断平移、旋转、缩放的触发条件,平移位移量、缩放比例因子、旋转角度的计算。二是Matrix矩阵的应用。
㈦ 【Android】打造下拉放大效果
在其他App上看到了这样的一个效果,感觉有点意思,于是决定实现一个类似的效果。
( 其实是iOS的同学在实现功能的时候随意发挥了一下 )
效果大概值这样子的:
UI看完后
“这个效果不错啊”
“要不你们Android也么做?” 于是~~
作为一个有追求的程序员,决定也要实现一个这样的效果 (满脑子都是草泥马在奔腾)
这样的效果嘛~~
利用自定义的 ViewGroup ,通过对手势的处理,应该就能实现了吧?
主要应该分两部分:
比较麻烦的应该是在第一部分,需要对事件的分发有一些理解。
说到手势的判断,难免需要对事件分发进行处理。
下拉部分
1、在 onInterceptTouchEvent 中对事件进行处理,如果为下拉事件,则将该事件拦截,交给 onTouchEvent 处理;
2、在 onTouchEvent 中通过计算得到下拉的距离,然后动态改变 Header 的配置,实现放大的效果。
重置部分
在 onTouchEvent 的 ACTION_UP 中重置 Header ,实现回弹
知道思路以后,实现起来就比较简单了
创建一个 ViewGroup (这么命名为 FlexibleLayout )继承 LinearLayout 。
onInterceptTouchEvent的处理
先通过两个条件判断是否为下拉事件:
然后通过 mIsBeingDragged 来标记开始拖拽
onTouchEvent的处理
修改头部大小
得到下拉的距离后,就可以来改变 Header 的大小,实现放大效果了。
放大、重置的部分大家可以自由发挥
这里利用 Math.pow(offsetY, 0.8) 得到实际需要增加的高度,通过计算得到对应的宽度以及偏移(类似阻尼效果)。
重置头部
直接将宽高以及偏移设置成原来的参数即可。
(如果觉得这样重置过程不够丝滑,可以通过动画来完成一个流畅的重置效果,这里就不演示了)
到这里,一个简易拉下放大的效果就做完了。试试效果
使用
直接在需要下拉放大的布局外面套上 FlexibleLayout 即可,例如 ScrollView
效果
ScrollVIew:
RecyclerView:
CoordinatorLayout:
大功告成!!!
当然里面还有一些细节的处理,比如下拉的条件、回弹的动画、最大高度等,具体内容的可以在 源码 中看到。
完成下拉放大后,貌似把一个很重要的功能遗忘了下拉刷新 ??
光顾这下拉放大,刷新怎么办?【黑人问号】
这个功能留着下周实现吧,我的7小时睡眠已遥遥无期~~
虽然没有直接实现下拉刷新的功能,不过源码中已经暴露了一个下拉的监听,你也可以通过这个监听实现下拉刷新的操作
到这里就结束了
(来还上周欠下的债~~)
和下拉放大类似,通过希手指下滑的监听,利用 View 的 translationY 和 rotation 实现移动和旋转。
具体的实现过程这里就不贴出来了,直接看效果吧
有兴趣的可以直接去 Github 上看源码以及用法。
Github
PullZoomView
Android事件分发机制 详解攻略,您值得拥有
㈧ android中scrollview怎么实现阻尼回弹
1。你可以用ViewFlipper 来实现效果,每一张图片为一页,加上滑屏动画效果,这个网上资料很全。2。你可以使用gallery来显示图片,这个跟ListView的使用方法是一样的,网上资料和SDK文档里面都介绍很详细。3。用手势监听需要给View上面实现OntouchListener,具体方法跟ViewFlipper的翻页效果是一样的