android - 如何在 Android Studio 的后台服务中检测屏幕是否被触摸?

标签 android service touch screen detect

我正在 android studio 上做一个项目。 我需要在后台服务中检测屏幕是否被触摸(并为此弹出一条消息)。 但是,在不影响用户使用智能手机的情况下,我无法在后台服务中检测屏幕是否被触摸

当我说“在后台检测”时,我的意思是应用程序的效果不会干扰用户在屏幕上的操作。我下面的进度应该可以解释我在这里的意思:

我制作了一个应用程序,它通过在 android 中实现 onTouchListener 并为该 onTouchListener 使用布局来检测用户是否在后台触摸屏幕。我按照网站上的说明做到了这一点 “http://kpbird.blogspot.com.au/2013/03/android-detect-global-touch-event.html” 我对布局进行了一些更改以覆盖整个屏幕,以便它可以检测到整个屏幕。

但是,在我运行创建了不断检测屏幕触摸的服务的应用程序之后,每次当用户触摸屏幕时,该触摸都会被我的服务(布局)吸收,因此用户无法正确使用他们的电话(如按图标启动其他应用程序)。这是因为布局覆盖了整个屏幕并阻止了其下方图标的任何触摸信息(布局检测屏幕触摸),因此图标不知道有触摸,因此不会对用户使用react。但我希望我的应用和服务允许用户正常使用他们的手机。

我听说 android 中的服务设计为不与用户交互(即屏幕触摸)并在后台工作,但我想知道是否有解决此问题的方法。

下面是我的服务代码:

public class GlobalTouchService extends Service implements OnTouchListener{

    private String TAG = this.getClass().getSimpleName();
    // window manager
    private WindowManager mWindowManager;
    // linear layout will use to detect touch event
    private LinearLayout touchLayout;
    @Override
    public IBinder onBind(Intent arg0) {
        return null;
    }
    @Override
    public void onCreate() {
        super.onCreate();
        // create linear layout
        touchLayout = new LinearLayout(this);
        // set layout width 30 px and height is equal to full screen
        LayoutParams lp = new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
        touchLayout.setLayoutParams(lp);
        // set color if you want layout visible on screen
        //touchLayout.setBackgroundColor(Color.CYAN);
        // set on touch listener
        touchLayout.setOnTouchListener(this);

        // fetch window manager object
        mWindowManager = (WindowManager) getSystemService(WINDOW_SERVICE);
        // set layout parameter of window manager
        WindowManager.LayoutParams mParams = new WindowManager.LayoutParams(
                WindowManager.LayoutParams.MATCH_PARENT, // width is equal to full screen
                WindowManager.LayoutParams.MATCH_PARENT, // height is equal to full screen
                WindowManager.LayoutParams.TYPE_PHONE, // Type Phone, These are non-application windows providing user interaction with the phone (in particular incoming calls).
                WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE, // this window won't ever get key input focus
                PixelFormat.TRANSLUCENT);
        mParams.gravity = Gravity.LEFT | Gravity.TOP;
        Log.i(TAG, "add View");

        mWindowManager.addView(touchLayout, mParams);

    }


    @Override
    public void onDestroy() {
        if(mWindowManager != null) {
            if(touchLayout != null) mWindowManager.removeView(touchLayout);
        }
        super.onDestroy();
    }

    public void showAlert(View view) {
        AlertDialog.Builder myAlertBuilder = new AlertDialog.Builder(this);
        myAlertBuilder.setMessage(getString(R.string.alertMessage))
                .setTitle(getString(R.string.alertTitle))
                .setPositiveButton(getString(R.string.alertPositiveChoice), new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialog, int which) {
                        dialog.dismiss();
                    }
                })
                .setNegativeButton(getString(R.string.alertNegativeChoice), new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialog, int which) {
                        dialog.dismiss();
                        onDestroy();
                    }
                });
        AlertDialog myAlert = myAlertBuilder.create();
        myAlert.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ALERT);
        myAlert.show();
    }


    @Override
    public boolean onTouch(View v, MotionEvent event) {
        //if (event.getAction() == MotionEvent.ACTION_DOWN || event.getAction() == MotionEvent.ACTION_UP)
        //    Log.i(TAG, "Action :" + event.getAction() + "\t X :" + event.getRawX() + "\t Y :" + event.getRawY());
        ////////////////////
        View myView = null;
        //showAlert(myView);
        ///////////////////////
        return false;
    }
}

最佳答案

那里有 onTouch 方法。只需返回 false,触摸就不会被您的应用吸收。

请同时检查: https://stackoverflow.com/a/6384443/1723095

编辑: 这可能不是你想要的,但如果你 Root设备,你可以做这样的事情:

adb shell getevent dev/input/event1

在我的例子中,event1 负责触摸事件,但它可能有所不同。

关于android - 如何在 Android Studio 的后台服务中检测屏幕是否被触摸?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30074771/

相关文章:

linux - Kaltura 缺少 Sphinx 服务?

jquery - 悬停菜单在触摸设备上不起作用,因为链接被触发

android - Apksigner 不验证签名

Android GridLayout 和 Space 向后移植

android - Facebook SDK导致 'appDebug'错误

javascript - 获取触摸事件路径中的元素

ios - 如何添加计时器?

Android 用户界面 ListView

javascript - 通过链式服务传递 header

node.js - 当服务器作为 Linux 服务启动时,readFileSync 抛出错误