zoukankan      html  css  js  c++  java
  • 仿Twitter登陆移动背景效果

    有使用Twitter客户端的朋友应该有发现在登录的时候,屏幕上方和下方的云朵图片是不断移动着的,再加上Twitter那支可爱的小鸟在不停的动着,给人的感觉就好像是小鸟在飞翔一样,感觉效果很不错。

    我也试着实现了一下,发现使用自定义的Drawable加上线程,还是比较容易实现的。下面是自定义Drawable的代码,注释已经写的很详细了。这里是使用了三张图片,使用一张图就更简单了,大家完全可以举一反三,实现自己的动画图片效果。

    package com.liuzhichao.dynamicdrawable;
    
    import android.app.Activity;
    import android.graphics.Bitmap;
    import android.graphics.BitmapFactory;
    import android.graphics.Canvas;
    import android.graphics.ColorFilter;
    import android.graphics.drawable.Drawable;
    import android.util.DisplayMetrics;
    import android.view.View;
    
    public class DynamicDrawable extends Drawable implements Runnable {
    
        private static Bitmap mBottomBgBitmap;   //底部大图  
        private static Bitmap mBottomFgBitmap;   // 底部小图 
        private static Bitmap mTopBitmap;      //顶部云图片
    
        private final int dispalyWidth;       //手机屏幕宽度
        private final int dispalyHeight;     //手机屏幕高度
        private float mBottomBgTop;             //顶部大图显示的位置
        private float mBottomFgTop;            //顶部小图显示的位置    
    
        private int startX;                //顶部云图片和底部大图移动偏移变量
        private int mBottomFgStartX;       //底部小图移动偏移变量
        private View mView;
    
        public DynamicDrawable(Activity activity, View mView) {
            this.mView = mView;
    
            if (mTopBitmap == null) {
                mTopBitmap = BitmapFactory.decodeResource(activity.getResources(),
                        R.drawable.cloud_top_bg);
            }
            if (mBottomBgBitmap == null) {
                mBottomBgBitmap = BitmapFactory.decodeResource(
                        activity.getResources(), R.drawable.cloud_bottom_bg);
            }
            if (mBottomFgBitmap == null) {
                mBottomFgBitmap = BitmapFactory.decodeResource(
                        activity.getResources(), R.drawable.cloud_bottom_fg);
            }
    
            //获取屏幕高度和宽度
            DisplayMetrics dm = new DisplayMetrics();
            dm = activity.getResources().getDisplayMetrics();
            this.dispalyHeight = dm.heightPixels;
            this.dispalyWidth = dm.widthPixels;
    
            //顶部图片显示的位置  = 屏幕高度 - 图片自身高 - 标题高度
            this.mBottomBgTop = dispalyHeight - mBottomBgBitmap.getHeight() - 100;
            this.mBottomFgTop = dispalyHeight - mBottomFgBitmap.getHeight() - 100;
    
            //开始移动图片线程
            new Thread(this).start();
        }
    
        @Override
        public void draw(Canvas canvas) {
            // drawBitmap (Bitmap bitmap, float left, float top, Paint paint)
            canvas.drawBitmap(mTopBitmap, startX, 0, null);
            canvas.drawBitmap(mBottomBgBitmap, startX, mBottomBgTop, null);
            canvas.drawBitmap(mBottomFgBitmap, mBottomFgStartX, mBottomFgTop, null);
        }
    
        @Override
        public int getOpacity() {
            // TODO Auto-generated method stub
            return 0;
        }
    
        @Override
        public void setAlpha(int arg0) {
            // TODO Auto-generated method stub
    
        }
    
        @Override
        public void setColorFilter(ColorFilter arg0) {
            // TODO Auto-generated method stub
    
        }
    
        @Override
        public void run() {
            while (!Thread.currentThread().isInterrupted()) {
                //900 是图片的长度
                //如果移动偏量已经大于图片的长度 - 屏幕宽度,则说明已经移动到了图片的末端,如果继续移动,则会显示空白
                //所以将startX重新赋予0,让图片重新开始移动
                //但是这样过渡效果会比较明显,再切换的那一刹那,会明显感觉图片变化较大
                if (startX + (900 - dispalyWidth) == 0) {
                    startX = 0;
                } else {
                    startX -= 1;
                }
    
                //底部小图的移动,
                // -=2 是让小图移动的比大图快,造成不同的视觉效果
                if (mBottomFgStartX + (900 - dispalyWidth) == 0) {
                    mBottomFgStartX = 0;
                } else {
                    mBottomFgStartX -= 2;
                }
                try {
                    //每 1/10秒移动一次
                    Thread.sleep(100L);
                } catch (InterruptedException e) {
                    Thread.currentThread().interrupt();
                }
                //刷新界面
                mView.postInvalidate();
            }
    
        }
    
    }

    然后在需要背景图的地方,直接setBackgroundDrawable就可以了,下面的background是整个布局文件的id。

    private View background;
        @Override
        public void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            background = findViewById(android.R.id.background);
            background.setBackgroundDrawable(new DynamicDrawable(this, background));
        }

    布局文件也还是贴出来吧:

    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:id="@android:id/background" >
    
        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_centerHorizontal="true"
            android:layout_centerVertical="true"
            android:padding="@dimen/padding_medium"
            android:text="@string/hello_world"
            tools:context=".MainActivity" />
    
    </RelativeLayout>

    还是截张图吧,虽然看不到动画效果。

    本文转自:http://liuzhichao.com/p/659.html

  • 相关阅读:
    使用docker搭建gitlab版本控制系统
    Spring Boot与Docker部署
    CentOS7 使用yum命令安装Java SDK(openjdk)
    配置带用户权限的docker registry v2
    Docker搭建带有访问认证的私有仓库
    CentOS7 关闭防火墙
    CentOS7.2网络配置
    Docker Machine 简介
    docker的常用命令汇总
    实时查看docker容器日志
  • 原文地址:https://www.cnblogs.com/sishuiliuyun/p/4450537.html
Copyright © 2011-2022 走看看