您的位置:首页 > 移动开发 > Android开发

Android 超级萌的猫头鹰登录界面

2017-07-05 16:48 155 查看
  最近在网上看到了一个比较不错的登录界面,效果如下图:



  是不是很好玩;后来研究了一下,主要是通过自定义的View加上动画实现的,先看代码:

  首先是自定义View:

 public class OwlView extends View {

    private Context mContext;

    private Bitmap bm_owl;

    private Bitmap bm_owl_arm_left;

    private Bitmap bm_owl_arm_right;

    private int bm_height;

    private int moveHeight;

    private int alpha = 255;

    private int move_length = 0;

    private Paint handPaintBefore;

    private Paint handPaintAfter;

    public OwlView(Context context) {

        this(context, null);

    }

    public OwlView(Context context, AttributeSet attrs) {

        this(context, attrs, 0);

    }

    public OwlView(Context context, AttributeSet attrs, int defStyleAttr) {

        super(context, attrs, defStyleAttr);

        this.mContext = context;

        init();

    }

    private void init() {

        setBackgroundColor(Color.TRANSPARENT);

        getViewTreeObserver().addOnGlobalLayoutListener(

                new ViewTreeObserver.OnGlobalLayoutListener() {

                    @Override

                    public void onGlobalLayout() {

                        getViewTreeObserver()

                                .removeGlobalOnLayoutListener(this);

                        ViewGroup.LayoutParams lp = getLayoutParams();

                        if (lp == null)

                            return;

                        lp.width = dip2px(175);

                        lp.height = dip2px(107);

                        setLayoutParams(lp);

                        setTranslationY(dip2px(9));

                    }

                });

        bm_owl = BitmapFactory.decodeResource(getResources(),

                R.drawable.owl_login);

        bm_owl_arm_left = BitmapFactory.decodeResource(getResources(),

                R.drawable.owl_login_arm_left);

        bm_owl_arm_right = BitmapFactory.decodeResource(getResources(),

                R.drawable.owl_login_arm_right);

        bm_owl = compressBitmap(bm_owl, dip2px(115), dip2px(107), false);

        bm_owl_arm_left = compressBitmap(bm_owl_arm_left, dip2px(40),

                dip2px(65), true);

        bm_owl_arm_right = compressBitmap(bm_owl_arm_right, dip2px(40),

                dip2px(65), true);

        bm_height = bm_owl_arm_left.getHeight() / 3 * 2 - dip2px(10);

        handPaintBefore = new Paint();

        handPaintBefore.setColor(Color.parseColor("#472d20"));

        handPaintBefore.setAntiAlias(true);

        handPaintAfter = new Paint();

        handPaintAfter.setAntiAlias(true);

    }

    public void close() {

        ValueAnimator alphaVa = ValueAnimator.ofInt(0, 255).setDuration(300);

        alphaVa.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {

            @Override

            public void onAnimationUpdate(ValueAnimator animation) {

                alpha = (Integer) animation.getAnimatedValue();

                invalidate();

            }

        });

        alphaVa.start();

        ValueAnimator moveVa = ValueAnimator.ofInt(dip2px(45), 0).setDuration(

                200);

        moveVa.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {

            @Override

            public void onAnimationUpdate(ValueAnimator animation) {

                move_length = (Integer) animation.getAnimatedValue();

                invalidate();

            }

        });

        moveVa.setStartDelay(200);

        moveVa.start();

        ValueAnimator va = ValueAnimator.ofInt(bm_height, 0).setDuration(300);

        va.setInterpolator(new LinearInterpolator());

        va.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {

            @Override

            public void onAnimationUpdate(ValueAnimator animation) {

                moveHeight = (Integer) animation.getAnimatedValue();

                invalidate();

            }

        });

        va.start();

    }

    public void open() {

        final ValueAnimator alphaVa = ValueAnimator.ofInt(255, 0).setDuration(

                300);

        alphaVa.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {

            @Override

            public void onAnimationUpdate(ValueAnimator animation) {

                alpha = (Integer) animation.getAnimatedValue();

                invalidate();

            }

        });

        alphaVa.start();

        ValueAnimator moveVa = ValueAnimator.ofInt(0, dip2px(45)).setDuration(

                200);

        moveVa.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {

            @Override

            public void onAnimationUpdate(ValueAnimator animation) {

                move_length = (Integer) animation.getAnimatedValue();

                invalidate();

            }

        });

        moveVa.start();

        ValueAnimator va = ValueAnimator.ofInt(0, bm_height).setDuration(300);

        va.setInterpolator(new LinearInterpolator());

        va.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {

            @Override

            public void onAnimationUpdate(ValueAnimator animation) {

                moveHeight = (Integer) animation.getAnimatedValue();

                invalidate();

            }

        });

        va.setStartDelay(100);

        va.start();

    }

    @Override

    protected void onDraw(Canvas canvas) {

        super.onDraw(canvas);

        canvas.drawBitmap(

                bm_owl,

                new Rect(0, 0, bm_owl.getWidth(), bm_owl.getHeight()),

                new Rect(dip2px(30), 0, dip2px(30) + bm_owl.getWidth(), bm_owl

                        .getHeight()), handPaintAfter);

        handPaintBefore.setAlpha(alpha);

        canvas.drawOval(new RectF(moveHeight, getHeight() - dip2px(20),

                move_length + dip2px(30), getHeight()), handPaintBefore);

        canvas.drawOval(

                new RectF(getWidth() - dip2px(30) - move_length, getHeight()

                        - dip2px(20), getWidth() - move_length, getHeight()),

                handPaintBefore);

        canvas.drawBitmap(bm_owl_arm_left,// Bitmap

                new Rect(0,// left

                        0,// top

                        bm_owl_arm_left.getWidth(),// right

                        moveHeight),// bottom

                new Rect(dip2px(43), getHeight() - moveHeight - dip2px(10),

                        dip2px(43) + bm_owl_arm_left.getWidth(), getHeight()

                                - dip2px(9)), handPaintAfter);// Paint

        // canvas.drawBitmap(Bitmap,Rect,Rect,Paint)

        canvas.drawBitmap(bm_owl_arm_right,// Bitmap

                new Rect(0,// left

                        0,// top

                        bm_owl_arm_right.getWidth(),// right

                        moveHeight),// bottom

                new Rect(getWidth() - dip2px(40) - bm_owl_arm_right.getWidth(),// left

                        getHeight() - moveHeight - dip2px(10),// top

                        getWidth() - dip2px(40),// right

                        getHeight() - dip2px(9)),// bottom

                handPaintAfter);// Paint

    }

    /**

     * 压缩图片

     *

     * @param bitmap

     * @param reqsW

     * @param reqsH

     * @param isAdjust

     * @return

     */

    private Bitmap compressBitmap(Bitmap bitmap, int reqsW, int reqsH,

            boolean isAdjust) {

        if (bitmap == null || reqsW == 0 || reqsH == 0)

            return bitmap;

        if (bitmap.getWidth() > reqsW || bitmap.getHeight() > reqsH) {

            /**

             * BigDecimal用法详解

             *

             * 由于NumberFormat类的format()方法可以使用BigDecimal对象作为其参数,

             * 可以利用BigDecimal对超出16位有效数字的货币值,百分值,以及一般数值进行格式化控制。

             * 以利用BigDecimal对
977e
货币和百分比格式化为例

             * 。首先,创建BigDecimal对象,进行BigDecimal的算术运算后,分别建立对货币和百分比格式化的引用

             * ,最后利用BigDecimal对象作为format()方法的参数,输出其格式化的货币值和百分比。

             */

            float scaleX = new BigDecimal(reqsW).divide(

                    new BigDecimal(bitmap.getWidth()), 4, RoundingMode.DOWN)

                    .floatValue();

            float scaleY = new BigDecimal(reqsH).divide(

                    new BigDecimal(bitmap.getHeight()), 4, RoundingMode.DOWN)

                    .floatValue();

            if (isAdjust) {

                scaleX = scaleX < scaleY ? scaleX : scaleY;

                scaleY = scaleX;

            }

            Matrix matrix = new Matrix();

            matrix.postScale(scaleX, scaleY);

            bitmap = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(),

                    bitmap.getHeight(), matrix, true);

        }

        return bitmap;

    }

    private int dip2px(int dpValue) {

        float scale = mContext.getResources().getDisplayMetrics().density;

        return (int) (dpValue * scale + 0.5f);

    }

}

然后界面:

<FrameLayout 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:background="#008ECB" >

    <FrameLayout

        android:layout_width="match_parent"

        android:layout_height="140dp"

        android:layout_marginTop="107dp"

        android:background="@drawable/bg_layout">"

        <LinearLayout

            android:layout_width="match_parent"

            android:layout_height="140dp"

            android:orientation="vertical" >

            <EditText

                android:id="@+id/uname"

                android:layout_width="match_parent"

                android:layout_height="50dp"

                android:layout_marginTop="10dp"

                android:layout_marginLeft="5dp"

                android:layout_marginRight="5dp"

                android:layout_marginBottom="5dp"

                android:background="@drawable/bg_edittext"

                android:hint="请输入账号"

                android:paddingLeft="10dp" />

            <EditText

                android:id="@+id/upwd"

                android:layout_width="match_parent"

                android:layout_height="50dp"

                android:layout_marginTop="10dp"

                android:layout_marginLeft="5dp"

                android:layout_marginRight="5dp"

                android:layout_marginBottom="5dp"

                android:password="true"

                android:background="@drawable/bg_edittext"

                android:hint="请输入密码"

                android:paddingLeft="10dp" />

        </LinearLayout>

    </FrameLayout>

    <com.example.logindemo.OwlView

        android:id="@+id/owl"

        android:layout_width="match_parent"

        android:layout_height="match_parent"

        android:layout_gravity="center_horizontal" >

    </com.example.logindemo.OwlView>

</FrameLayout>

最后就是在activity里给两个Editext加监听了:

public class MainActivity extends Activity {

    private EditText uname, upwd;

    private OwlView owl;

    @Override

    protected void onCreate(Bundle savedInstanceState) {

        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);

        uname = (EditText) findViewById(R.id.uname);

        upwd = (EditText) findViewById(R.id.upwd);

        owl = (OwlView) findViewById(R.id.owl);

        uname.setOnFocusChangeListener(new OnFocusChangeListener() {

            @Override

            public void onFocusChange(View v, boolean hasFocus) {

                // TODO Auto-generated method stub

                if (hasFocus) {

                    owl.close();

                }

            }

        });

        upwd.setOnFocusChangeListener(new OnFocusChangeListener() {

            @Override

            public void onFocusChange(View v, boolean hasFocus) {

                // TODO Auto-generated method stub

                if (hasFocus) {

                    owl.open();

                }

            }

        });

    }

}

 附上项目下载地址:http://download.csdn.net/detail/stephenzml/9889642
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: