神交互!饿了么 imageView 放大变为详情页
来源:互联网 发布:软件外包公司培训 编辑:程序博客网 时间:2024/05/22 03:32
ZoomHeader
下载体验
不是共享元素!不是共享元素!不是共享元素!重要的话说三遍。共享元素不可以随手指移动的。
先吐槽下饿了么。不提示左右可以滑动。我还是无意中发现的。不提示我怎么知道可以滑动??
这是一个模仿饿了么详情页的例子。并非一个库,并非拿来就可以用,主要讲解思路以及如何实现,可能有一些细节没有处理。 讲述了如何实现。具体祥见源码。
他是一个 Activity 还是两个?
相信你肯定有这样的疑问,答案是一个。所以这不是用共享元素实现的,使用共享元素会导致图片无法跟随手指移动。
你看到的中间 imageview 是 viewpager。在 Viewpager 上面是一个透明的 View。当然,这个 Activity 的背景也是透明的。
实现思路
我使用 CoordinatorLayout+Behavior 实现的。说实话,Behavior 真心强大。。
viewpager+头部
整个实现的思路是这样的。整体布局从上到下依次是:
- 透明 View
- viewpager
- RecyclerView
其中透明 View 和 Viewpager 合并成一个自定义的 Header。当这个 Header 上移的时候,图片放大,并且 RecyclerView 联动上衣,从透明转向并且不透明。
所以首先要定制一个透明的可移动的 HeaderView。
在 onTouchEvent 处理一下手势。。
@Override public boolean onTouchEvent(MotionEvent ev) { switch (ev.getAction()) { case MotionEvent.ACTION_DOWN: return true; case MotionEvent.ACTION_MOVE: if(上下移动到阀值){ 展开为详情() }else if(上下滑动到阀值,恢复 viewpager){ }else if(下滑,则关闭 Activity)
将 header 分为三种状态:
- 上移。则展开为详情页。
- 下移,则恢复为 viewpager。
- 再下移,则 finish Activity。
在上移的过程中,遇到了一点小挑战,这里分享下:
上移的过程中,图片需要放大。但是在做的过程中,不能使用 LayoutParams 实现。这里就关系到一些动画的小细节。
动画使用 LayoutParams 实现是一个禁忌。他会导致不停 requestLayout,从而影响 UI 性能。
所以这里我的一个解法就是,我放大图片,不是真正的改变 ImageView 大小,而是去 Scale 图片。即使看起来变大了,他的 View 真正大小也不会变。
所以,有一句话叫做真亦是假、假亦是真 真真假假,你又何必当真呢?动画效果只要遵循这句话,基本上都是可以实现的。你所看到的效果都是假的。都是障眼法。View 变大不是真正的变大。View 悬浮不是真正的悬浮(有可能是显隐)。就像变魔术一样。。其实很简单。
接下来又遇到问题了。图片放大了,文字如何对齐? 文字的位置当然也不能真正改变。所以这里使用 TranslationX 实现。在图片放大的过程中,使用 scale 的系数,与两个端点值进行一个线性变化计算。主要文字对齐代码如下:
bottom.offsetLeftAndRight( (int) (target.getWidth() / 2 - target.getWidth() * (1 + progress) / 2 + MarginConfig.MARGIN_LEFT_RIGHT - bottom.getX()));
第二个点。就是在图片放大过程中,底部文字和按钮左右 padding 不能变。这也是我没有封装成一个拿来就用的 View 的原因(其实还是水平不够)。因为这些空间需要全部按照上方的方法进行动态计算。。所以也是比较坑爹的。。
ViewPager
拿了网上一个画廊的效果。直接
setPageTransformer(true, new ZoomOutPageTransformer());
这里注意,需要改变一下 view 的绘制顺序,保证当前 view 是最后绘制处于最上层
/改变系统绘制顺序 @Override protected int getChildDrawingOrder(int childCount, int i) { int position = getCurrentItem(); if(position<0){ return i; }else{ if(i == childCount - 1){//这是最后一个需要刷新的 item if(position>i){ position=i; } return position; } if(i == position){//这是原本要在最后一个刷新的 item return childCount - 1; } } return i; }}
RecyclerView
RecyclerView 最开始是完全透明的。并且跟随 HeaderView 上移而上移,在上移的过程中渐渐显示出来。 需要监听 RecyclerView 滚动,当 RecyclerView 滚动到顶部的时候。告知 Header,该恢复最初原样了。
@Override public boolean onNestedFling(CoordinatorLayout coordinatorLayout, View child, View target, float velocityX, float velocityY, boolean consumed) { //向下 Fling 并且到顶部 if (velocityY < 0 && ((RecyclerView) target).getChildAt(0).getY() == 0) { mDependency.restore(mDependency.getY()); } return super.onNestedFling(coordinatorLayout, child, target, velocityX, velocityY, consumed); } @Override public void onNestedPreScroll(CoordinatorLayout coordinatorLayout, View child, View target, int dx, int dy, int[] consumed) { //如果在顶部 if (((RecyclerView) target).getChildAt(0).getY() == 0) { //向下滑动 if (dy < 0) { mDependency.setY(mDependency.getY() - dy); //小于阀值 if (mDependency.getY() < 500) { mDependency.restore(mDependency.getY()); } } } super.onNestedPreScroll(coordinatorLayout, child, target, dx, dy, consumed); }}
Behavior
让 header 和 RecyclerView 关联起来的就是 Behavior 了。Behavior 之前写过几篇介绍过了,这里就不再啰嗦。
denpendcy 为 HeaderView。并且监听 RecyclerView 的滑动。
具体的细节还是看源码吧~
如果你觉得还不错,欢迎 Star
欢迎加入我的 qq 群: 425983695
- 神交互!饿了么 imageView 放大变为详情页
- 这交互炸了:饿了么是怎么让Image变成详情页的
- Android这交互炸了:饿了么是怎么让Image变成详情页的
- 这交互炸了:饿了么是怎么让Image变成详情页的
- 这交互炸了:饿了么是怎么让Image变成详情页的
- 商品详情放大效果
- 暗恋的男神交了女朋友,那女人尖嘴猴腮
- ReclyerView双联动,仿饿了吗店铺详情页
- ImageView 等比例放大
- ImageView 放大缩小
- ImageView逐渐放大动画
- 放大可以移动的ImageView
- 用Martix 放大缩小ImageView
- 点击ImageView放大到全屏
- 可放大缩小的ImageView
- 使用ColorMatrix将imageview变为灰色
- 【Android】商品详情页下拉放大动画工具类,一行代码集成使用
- Ecshop模板开发(五):商品详情页图片相册jqzoom放大
- 先验概率与后验概率、贝叶斯区别与联系
- 排序算法(1)----选择排序算法
- HDU 6121 K叉树的异或值和
- 第一次使用Android Studio时你应该知道的一切配置
- Php学习之两个特性导致waf绕过注入详解
- 神交互!饿了么 imageView 放大变为详情页
- QWizard
- AI芯片怎么降功耗?从ISSCC2017说起
- PLSQL 11 注册码
- hdu6040 Hints of sd0061【nth_element使用】
- 自定义 SeekBar,进度变化由可视化气泡样式呈现
- C语言之指针学习笔记
- 时间片轮询
- C++学习之内存重叠