知乎等应用的开场动画是:全屏显示一副图像,并以图像的中间为原点,实现放大(也就是zoomin)的动画,让等待的过程不再单调乏味。
最近不是很忙,因此想了下如何实现这种效果,方案是:采用调整imageview的matrix的方式来实现此效果。
这个例子中我只是简单的将原理实现,没有对效果进行任何的优化。如果想达到比较完美的效果,需要添加动画,如使用valueAnimator,在updatelistener中不断的更新matrix或者float[]即可。
为了演示方便,我将其实现过程拆分为两部:
1.调整图片,使图片位于屏幕的正中间。由于android手机屏幕尺寸多种多样,而图片的大小也不甚相同,为了灵活的使用此效果,需要将任意尺寸比例的图片显示在任意尺寸比例的手机屏幕的正中间,同时不使图片扭曲变形
2.采用点击button模拟zoomin的效果,当然可以优化成使用valueanimator的方式,由于这不是本篇文章的重点,因此不进行优化了
 
 实现的效果:[屏幕截图有点问题,所以显得有点卡]
原理在代码中进行说明:
主界面:
package com.carbs.testandroidimage;

import android.app.Activity;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Matrix;
import android.graphics.PixelFormat;
import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.ImageView; public class MainActivity extends Activity implements View.OnClickListener { private ImageView iv;
private Button bt1_refine;
private Button bt2_zoomin; private int iv_height = 0;
private int iv_width = 0;
private int dr_height = 0;
private int dr_width = 0; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout. activity_main); iv = (ImageView) this.findViewById(R.id.iv);
bt1_refine = (Button) this.findViewById(R.id.bt1);
bt2_zoomin = (Button) this.findViewById(R.id.bt2); bt1_refine.setOnClickListener(this);
bt2_zoomin.setOnClickListener(this); iv.post( new Runnable() { @Override
public void run() {
//获取imageview的宽和高、获取drawable的宽和高
Drawable d = iv.getDrawable();
//drawable的宽高,存储到全局变量中
dr_width = d.getIntrinsicWidth();
dr_height = d.getIntrinsicHeight();
//imageview的宽高,存储到全局变量中
iv_height = iv .getMeasuredHeight();
iv_width = iv.getMeasuredWidth();
Log. d("a", "onClick() --> dr_width is " + dr_width + " | dr_height is " + dr_height + " | iv_height is " + iv_height + " | iv_width is " + iv_width);
}
});
} @Override
public void onClick(View v) { switch (v.getId()) { case R.id.bt1 : if((iv_height * dr_width > dr_height * iv_width)){
//如果iv更细高,也就是我们需要调整其中图片的高度,使其高度和imageview的高度一致,这样算出scale后,使drawable的宽高同时放大scale倍。由于matrix模式下,调整scale后imageview显示图片依然是从左上角开始显示的,因此需要调整imageview的左右平移,使显示的drawable正好位于正中间。另一种情况(如果iv更宽扁)同理
//计算出高度需要放大多少倍
float scale1 = ((float)iv_height )/((float)dr_height);
//计算出左右平移多少
float offset1 = (dr_width *scale1 - (float)iv_width )/2;
Log. d("1223", "offset1 is " + offset1); Matrix matrix1 = new Matrix();
matrix1.postScale(scale1, scale1);
matrix1.postTranslate(-offset1, 0);
iv.setImageMatrix(matrix1); } else{
//如果iv更宽扁,同理
float scale2 = ((float)iv_width )/((float)dr_width); float offset2 = (dr_height *scale2 - (float)iv_height )/2;
Log. d("1223", "offset2 is " + offset2);
//产生新的大小但Bitmap对象
Matrix matrix2 = new Matrix();
matrix2.postScale(scale2, scale2);
matrix2.postTranslate(0, -offset2);
iv.setImageMatrix(matrix2);
} break; case R.id.bt2 : Matrix ma = iv.getImageMatrix(); float[] dValues = new float[9]; ma.getValues(dValues); dValues[0] = dValues[0] + 0.1f;
dValues[4] = dValues[4] + 0.1f; float offsetheight = (dr_height *dValues[0] - (float)iv_height )/2;
dValues[5] = - offsetheight;
float offsetwidth = (dr_width *dValues[0] - (float)iv_width )/2;
dValues[2] = - offsetwidth; Matrix m = new Matrix();
m.setValues(dValues); iv.setImageMatrix(m);
break;
}
} public String printMyMatrix(Matrix m){
String s = "";
float[] valueFloat = new float[9];
m.getValues(valueFloat); for(int i = 0; i < 9; i++){
s = s + " [ " + valueFloat[i] + " ] " ;
} return s;
} }
Matrix的使用说明:
android.graphics.Matrix;包下的Matrix类主要用于imageview的图形变换,主要包括平移、缩放、旋转等,具体的使用方法可以参考如下这片博客:http://blog.csdn.net/hahajluzxb/article/details/8165258
Matrix可以由一个包含9个float类型的float数组构成,下标为[0]和[4]控制x轴和y轴的伸缩,大于1为放大,小于1为缩小。下标为[2]和[5]分别控制宽和高的平移,正数为图片向左平移,负数为图片向右平移。
点击button进行zoomin效果的原理就是不断的设置imageview的matrix,使其按照float[]数组的值进行变换,在放大的情况下同时进行平移,从而达到了zoomin的效果
布局文件:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width= "match_parent"
android:layout_height= "match_parent"
android:gravity= "center_horizontal"
android:orientation= "vertical"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop= "@dimen/activity_vertical_margin" > <ImageView
android:id="@+id/iv"
android:layout_width="1200px"
android:layout_height="700px"
android:background="@drawable/background_stroke"
android:scaleType="matrix"
android:src="@drawable/dog" /> <LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content" > <Button
android:id="@+id/bt1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="button 1" /> <Button
android:id="@+id/bt2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="button 2" /> </LinearLayout > </LinearLayout>
 

实现仿知乎的开场动画,图片zoomin的效果,实现原理,没加动效的更多相关文章

  1. [原创]实现android知乎、一览等的开场动画图片放大效果

    代码下载地址: https://github.com/Carbs0126/AutoZoomInImageView 知乎等app的开场动画为:一张图片被显示到屏幕的正中央,并充满整个屏幕,过一小段时间后 ...

  2. iOS动画进阶 - 实现炫酷的上拉刷新动效

    移动端訪问不佳,请訪问我的个人博客 近期撸了一个上拉刷新的小轮子.仅仅要遵循一个协议就能自己定义自己动效的上拉刷新和载入,我自己也写了几个动效进去,以下是一个比較好的动效的实现过程 先上效果图和git ...

  3. 微信小程序开发日记——高仿知乎日报(上)

    本人对知乎日报是情有独钟,看我的博客和github就知道了,写了几个不同技术类型的知乎日报APP 要做微信小程序首先要对html,css,js有一定的基础,还有对微信小程序的API也要非常熟悉 我将该 ...

  4. 微信小程序开发日记——高仿知乎日报(下)

    本人对知乎日报是情有独钟,看我的博客和github就知道了,写了几个不同技术类型的知乎日报APP 要做微信小程序首先要对html,css,js有一定的基础,还有对微信小程序的API也要非常熟悉 我将该 ...

  5. 微信小程序开发日记——高仿知乎日报(中)

    本人对知乎日报是情有独钟,看我的博客和github就知道了,写了几个不同技术类型的知乎日报APP要做微信小程序首先要对html,css,js有一定的基础,还有对微信小程序的API也要非常熟悉 我将该教 ...

  6. 仿知乎app登录界面(Material Design设计框架拿来就用的TexnInputLayout)

    在我脑子里还没有Material Design这种概念,就我个人而言,PC端应用扁平化设计必须成为首选,手当其冲的两款即时通讯旺旺和QQ早就完成UI扁平化的更新,然而客户端扁平化的设计本身就存在天生的 ...

  7. Android 仿知乎创意广告

    代码地址如下:http://www.demodashi.com/demo/14904.html 一.概述 貌似前段时间刷知乎看到的一种非常有特色的广告展现方式,即在列表页,某一个Item显示背后部分广 ...

  8. 用仿ActionScript的语法来编写html5——第八篇,图片处理+粒子效果

    用仿ActionScript的语法来编写html5系列开发到现在,应该可以做出一些东西了,下面先来研究下图片的各种效果预览各种效果看下图效果和代码看这里,看不到效果的请下载支持html5的浏览器 ht ...

  9. HTML5动画图片播放器 高端大气

    我们见过很多图片播放插件(焦点图),很多都基于jQuery.今天介绍的HTML5图片播放器很特别,它不仅在图片间切换有过渡动画效果,而且在切换时图片中的元素也将出现动画效果,比如图中的文字移动.打散. ...

随机推荐

  1. PHP header函数使用教程

    在php语言中,header()这个函数很有用的,尤其在用到ajax时候,他会帮你解决一些意想不到的问题.下面是header的一些详细讲解.希望对phper有帮助 代码如下: <?php// f ...

  2. Oracle EBS的BIP报表中显示特殊字体

    http://oracleseeker.com/2009/08/25/font_mapping_setup_for_special_character_print_in_oracle_ebs_bip/ ...

  3. C++类库介绍

    如果你有一定的C基础可能学起来比较容易些,但是学习C++的过程中又要尽量避免去使用一些C中的思想:平时还要多看一些高手写的代码,遇到问题多多思考,怎样才能把问题抽象化,以使自己头脑中有类的概念:最后别 ...

  4. php redis 代码实例

    <?phpheader("Content-type:text/html;charset=utf8");$redis = new redis();$redis ->con ...

  5. Orchard Express Oracle v1.7.2 发布

    发布说明: 1. 添加Oracle支持,在AppData目录下提供Oracle及Sql Server数据库创建脚本. 2. 修正上一版本(精简版 v1.7.2)中,Dashboard无需登录问题. O ...

  6. 用c#开发微信(3)基于Senparc.Weixin框架的接收普通消息处理 (源码下载)

    本文讲述使用Senparc.Weixin框架来快速处理各种接收的普通消息.这里的消息指的是传统的微信公众平台消息交互,微信用户向公众号发送消息后,公众号回复消息给微信用户.包括以下7种类型: 1 文本 ...

  7. Windows7上搭建Cocos2d-x 3.1.1开发环境

    前言 现在,越来越多的公司采用Cocos2d-x 3.0来开发游戏了,但是现在这样的文章并不多,所以打算写一系列来帮助初学者快速掌握Cocos2d-x 3.0.首先就从开发环境的大家说起吧. 开发工具 ...

  8. PHP合成图片、生成文字、居中对齐、画线、矩形、三角形、多边形、图片抗锯齿、不失真 高性能源码示例

    function generateImg($source, $text1, $text2, $text3, $font = './msyhbd.ttf') { $date = '' . date ( ...

  9. thinkphp支持大小写url地址访问,不产生下划线

    from:http://www.111cn.net/phper/thinkPhp/57748.htm 一.在配置文件中开启了thinkphp的大小写识别功能,使链接大小写都可以正常访问: ‘URL_C ...

  10. RabbitMQ(三) -- Publish/Subscribe

    RabbitMQ(三) -- Publish/Subscribe `rabbitmq`支持一对多的模式,一般称为发布/订阅.也就是说,生产者产生一条消息后,`rabbitmq`会把该消息分发给所有的消 ...