【Android M】平台方实现三指左右滑动任何应用界面截屏

来源:互联网 发布:化工制图软件 编辑:程序博客网 时间:2024/06/08 02:18


frameworks/base/core/java/com/android/internal/policy/MultiGestureSupport/MultiGestureMonitor.java //新增的类

frameworks/base/core/java/com/android/internal/policy/PhoneWindow.java


原文地址:http://blog.csdn.net/yelangjueqi/article/details/56275913

源码

1 MultiGestureMonitor.java //多指检测类

package com.example.android;import android.content.Context;import android.content.Intent;import android.provider.Settings;import android.util.Log;import android.view.MotionEvent;import android.view.VelocityTracker;/** * Multi Finger Screenshot Gesture Monitor * * @hide */public class MultiGestureMonitor {    private static final String TAG = "FingerScreenShotGesture/" + MultiGestureMonitor.class.getSimpleName();    private final String TAG_EVENT = TAG + "/EventPoint";    private boolean DBG = false;    private boolean isSupportHorizontalSlide = true;    public static final String ACTION_MULTI_FINGER_SCREEN_SHOT = "android.intent.action.MULTI_FINGER_SCREEN_SHOT";    public static final String MULTI_FINGER_SCREEN_SHOT_ENABLED = "multi_finger_screen_shot_enabled";    private final int SUPPORT_FINGER_COUNTS = 3;    private final int HORIZONTAL_SLIDE_OFFSET_DISTANCEY = 300;    private final int HORIZONTAL_SLIDE_OFFSET_DISTANCEX = 160;    private final int VERTICAL_SLIDE_OFFSET_DISTANCEY = 160;    private final int VERTICAL_SLIDE_OFFSET_DISTANCEX = 80;    private final float BASEVELOCOTY = 45;    private int mode;    private float mOldx0;    private float mOldy0;    private float mOldx1;    private float mOldy1;    private float mOldx2;    private float mOldy2;    private float mVelocityX0;    private float mVelocityY0;    private Context mContext;    private VelocityTracker mVelocityTracker;    private boolean mFingerScreenShotEnabled = false;    private boolean getFingerEnable() {        int mFingerMode = Settings.System.getInt(mContext.getContentResolver(), MULTI_FINGER_SCREEN_SHOT_ENABLED, 0);        if (mFingerMode == 1) {            return true;        } else {            return false;        }    }    // private static MultiGestureMonitor sInstance;    //    // public static MultiGestureMonitor getInstance(Context context) {    // if (sInstance == null) {    // sInstance = new MultiGestureMonitor(context);    // }    // return sInstance;    // }    public MultiGestureMonitor(Context context) {        mContext = context;    }    public boolean onTouchEvent(MotionEvent event) {        boolean handled = false;        int action = event.getAction();        switch (action & MotionEvent.ACTION_MASK) {        case MotionEvent.ACTION_DOWN:            if (mVelocityTracker == null) {                mVelocityTracker = VelocityTracker.obtain();            } else {                mVelocityTracker.clear();            }            mVelocityTracker.addMovement(event);            mode = 1;            break;        case MotionEvent.ACTION_MOVE:            if (mVelocityTracker != null) {                mVelocityTracker.addMovement(event);                mVelocityTracker.computeCurrentVelocity(1000);                mVelocityX0 = mVelocityTracker.getXVelocity();                mVelocityY0 = mVelocityTracker.getYVelocity();            }            break;        case MotionEvent.ACTION_POINTER_DOWN:            mode += 1;            if (mode == SUPPORT_FINGER_COUNTS) {                mFingerScreenShotEnabled = getFingerEnable();                try {                    mOldx0 = event.getX(event.getPointerId(0));                    mOldy0 = event.getY(event.getPointerId(0));                    mOldx1 = event.getX(event.getPointerId(1));                    mOldy1 = event.getY(event.getPointerId(1));                    mOldx2 = event.getX(event.getPointerId(2));                    mOldy2 = event.getY(event.getPointerId(2));                    if (DBG) {                        Log.v(TAG_EVENT, "oldx0:" + mOldx0 + ",oldy0:" + mOldy0 + ",oldx1:" + mOldx1 + ",oldy1:"                                + mOldy1 + ",mOldx2=" + mOldx2 + ",mOldy2=" + mOldy2);                    }                } catch (IllegalArgumentException e) {                    e.printStackTrace();                }            }            break;        case MotionEvent.ACTION_POINTER_UP:            if (mode == SUPPORT_FINGER_COUNTS) {                if (!mFingerScreenShotEnabled) {                    return false;                }                try {                    float newx0 = event.getX(event.getPointerId(0));                    float newy0 = event.getY(event.getPointerId(0));                    float newx1 = event.getX(event.getPointerId(1));                    float newy1 = event.getY(event.getPointerId(1));                    float newx2 = event.getX(event.getPointerId(2));                    float newy2 = event.getY(event.getPointerId(2));                    if (DBG) {                        Log.d(TAG_EVENT,                                "newx0:" + (Math.abs(newx0 - mOldx0) > HORIZONTAL_SLIDE_OFFSET_DISTANCEX) + ",newy0:"                                        + (Math.abs(newy0 - mOldy0) < HORIZONTAL_SLIDE_OFFSET_DISTANCEY) + ",newx1:"                                        + (Math.abs(mVelocityX0) > BASEVELOCOTY) + ",newy1:"                                        + (Math.abs(newy0 - mOldy0) > VERTICAL_SLIDE_OFFSET_DISTANCEY) + ",newx2="                                        + (Math.abs(newx0 - mOldx0) < VERTICAL_SLIDE_OFFSET_DISTANCEX) + ",newy2="                                        + (Math.abs(mVelocityY0) > BASEVELOCOTY));                        Log.d(TAG_EVENT, "mVelocityX0=" + mVelocityX0 + ",mVelocityY0=" + mVelocityY0);                    }                    if (isSupportHorizontalSlide) {                        if (Math.abs(newx0 - mOldx0) > HORIZONTAL_SLIDE_OFFSET_DISTANCEX                                && Math.abs(newy0 - mOldy0) < HORIZONTAL_SLIDE_OFFSET_DISTANCEY                                && Math.abs(mVelocityX0) > BASEVELOCOTY) {                            notifyScreenshotGestureCompleted();                        }                    } else {                        if (Math.abs(newy0 - mOldy0) > VERTICAL_SLIDE_OFFSET_DISTANCEY                                && Math.abs(newx0 - mOldx0) < VERTICAL_SLIDE_OFFSET_DISTANCEX                                && Math.abs(mVelocityY0) > BASEVELOCOTY) {                            notifyScreenshotGestureCompleted();                        }                    }                } catch (IllegalArgumentException e) {                    e.printStackTrace();                }            }            mode -= 1;            break;        case MotionEvent.ACTION_UP:        case MotionEvent.ACTION_CANCEL:            Log.v(TAG, "ACTION_UP or ACTION_CANCEL");            mode = 0;            if (mVelocityTracker != null) {                mVelocityTracker.recycle();                mVelocityTracker = null;            }            resetToInitValue();            break;        }        Log.v(TAG, TAG + String.valueOf(handled));        return handled;    }    private void notifyScreenshotGestureCompleted() {        if (mContext != null) {            Intent intent = new Intent();            intent.setAction(ACTION_MULTI_FINGER_SCREEN_SHOT);            mContext.sendBroadcast(intent);            Log.d(TAG, "sendBroadcast:" + ACTION_MULTI_FINGER_SCREEN_SHOT);        }    }    private void resetToInitValue() {        mOldx0 = 0;        mOldy0 = 0;        mOldx1 = 0;        mOldy1 = 0;        mOldx2 = 0;        mOldy2 = 0;    }}

说明:

该类为多指手势检测的关键类,具体支持几个手指截屏,由常亮"SUPPORT_FINGER_COUNTS"控制,此处为3,即三指截屏

A,MULTI_FINGER_SCREEN_SHOT_ENABLED = "multi_finger_screen_shot_enabled" 为三指截屏的控制开关

B,满足三指滑动手势后调用notifyScreenshotGestureCompleted()方法发送Action到PhoneWindowManager类,调用takeScreenshot()进行截屏


2 PhoneWindow.java

PhoneWindow类修改如下,见高亮部分代码:


    public PhoneWindow(Context context) {
        super(context);
        mLayoutInflater = LayoutInflater.from(context);

        initFingerScreenshot();
    }

    ......

    private final String TAG_FINGER = "/FingerScreenShotGesture";
    private boolean DBG = true;
    private MultiGestureMonitor mMultiGestureMonitor;
    private int mFingerScreenShotEnabled = 0;
    private final String MULTI_FINGER_SCREEN_SHOT_ENABLED = MultiGestureMonitor.MULTI_FINGER_SCREEN_SHOT_ENABLED;

    private void initFingerScreenshot() {
        mMultiGestureMonitor = new MultiGestureMonitor(getContext());
    }

    private boolean isSupportFingerScreenshot() {
        return Settings.System.getInt(getContext().getContentResolver(),
                MULTI_FINGER_SCREEN_SHOT_ENABLED, 0) == 1;
    }

    ......

    @Override
    public boolean dispatchTouchEvent(MotionEvent ev) {
            if (mMultiGestureMonitor != null) {
                boolean ishanded = mMultiGestureMonitor.onTouchEvent(ev);
                if (DBG) Log.v(TAG, "dispatchTouchEvent:" + String.valueOf(ishanded));
                if (ishanded) {
                    return true;
                }
            }


            final Callback cb = getCallback();
            return cb != null && !isDestroyed() && mFeatureId < 0 ? cb.dispatchTouchEvent(ev)
                    : super.dispatchTouchEvent(ev);
     }

0 0
原创粉丝点击