Bladeren bron

Merge remote-tracking branch 'origin/sheep2.0' into sheep2.0

liujiangyao 8 jaren geleden
bovenliggende
commit
820d57f445

+ 19 - 0
app/src/main/AndroidManifest.xml

@@ -67,6 +67,7 @@
         android:name=".SheepApp"
         android:allowBackup="true"
         android:icon="@mipmap/icon"
+        android:persistent="true"
         android:label="@string/app_name"
         android:supportsRtl="true"
         android:theme="@style/AppTheme">
@@ -80,7 +81,25 @@
             android:screenOrientation="portrait"/>
 
         <service android:name=".service.DownloadService"/>
+        <service
+            android:name=".service.FloatService"
+            android:enabled="true"
+            android:exported="true">
+        </service>
+        <service
+            android:name=".service.MonitorAppService"
+            android:enabled="true"
+            android:exported="true"
+            android:label="@string/app_name"
+            android:permission="android.permission.BIND_ACCESSIBILITY_SERVICE" >
+            <intent-filter>
+                <action android:name="android.accessibilityservice.AccessibilityService" />
+            </intent-filter>
 
+            <meta-data
+                android:name="android.accessibilityservice"
+                android:resource="@xml/accessibility" />
+        </service>
         <provider
             android:name=".provider.SheepFileProvider"
             android:authorities="${applicationId}.fileprovider"

+ 0 - 1
app/src/main/java/com/kfzs/duanduan/BaseCompatActivity.java

@@ -74,7 +74,6 @@ public abstract class BaseCompatActivity extends CompatActivity {
         return (T) super.findViewById(id);
     }
 
-
     @Override
     protected void onDestroy() {
         super.onDestroy();

+ 10 - 2
app/src/main/java/com/kfzs/duanduan/fragment/FgtSmallSheep.java

@@ -42,6 +42,7 @@ import com.sheep.gamegroup.di.modules.TryMakeMoneyModule;
 import com.sheep.gamegroup.event.ImageHeadChange;
 import com.sheep.gamegroup.event.MoneyChange;
 import com.sheep.gamegroup.event.UserNameChange;
+import com.sheep.gamegroup.model.entity.AppRecord;
 import com.sheep.gamegroup.model.entity.BaseMessage;
 import com.sheep.gamegroup.model.entity.BulletinEnty;
 import com.sheep.gamegroup.model.entity.HomeListEntity;
@@ -436,9 +437,16 @@ public class FgtSmallSheep extends BaseCompatFragment implements SmallSheepContr
                 Jump2View.getInstance().tryGoWxfz(activity,null);
                 break;
             case R.id.icon_layout://
-                if(BuildConfig.DEBUG)
+                if(BuildConfig.DEBUG) {
+                    System.out.println(String.format(Locale.CHINA, "MonitorAppService %s %s", activity.getPackageName(), MyDbManager.getInstance().getAppRunTime(activity.getPackageName())));
+                    MyDbManager.getInstance().removeAppRecord();
+                    List<AppRecord> list = MyDbManager.getInstance().getAppRecordList(activity.getPackageName());
+                    if(list != null)
+                        for (AppRecord appRecord : list) {
+                            System.out.println(String.format(Locale.CHINA, "MonitorAppService %s %s %s %d %d", appRecord.getPackageName(), appRecord.getClassName(), appRecord.getTag(), appRecord.getType_id(), appRecord.getTime()));
+                        }
                     Jump2View.getInstance().goUnderstandSheep(activity, null);
-                else
+                }else
                     Jump2View.getInstance().goPersonnalCenterView(activity, null);
                 break;
             case R.id.info_layout://其它信息

+ 1 - 1
app/src/main/java/com/sheep/gamegroup/model/api/ApiService.java

@@ -282,7 +282,7 @@ public interface ApiService {
     @GET("app/bulletin")
     Observable<BaseMessage> bulletin(@Query("page") int page, @Query("per_page") int per_page);
     /**
-     *
+     * 获取微信辅助h5链接
      */
     @GET("qr/task/get_url")
     Observable<BaseMessage> wxfzGetUrl();

+ 74 - 0
app/src/main/java/com/sheep/gamegroup/model/entity/AppRecord.java

@@ -0,0 +1,74 @@
+package com.sheep.gamegroup.model.entity;
+
+import org.xutils.db.annotation.Column;
+import org.xutils.db.annotation.Table;
+
+import java.io.Serializable;
+
+/**
+ * Created by realicing on 2018/5/11.
+ */
+@Table(name = "app_record")
+public class AppRecord implements Serializable {
+
+    @Column(name = "id", isId = true, autoGen = true)
+    private String id;
+    @Column(name = "package_name")
+    private String packageName;
+    @Column(name = "class_name")
+    private String className;
+    @Column(name = "tag")
+    private String tag;
+    @Column(name = "type_id")
+    private int type_id;
+    @Column(name = "time")
+    private long time;
+
+    public String getId() {
+        return id;
+    }
+
+    public void setId(String id) {
+        this.id = id;
+    }
+
+    public String getPackageName() {
+        return packageName;
+    }
+
+    public void setPackageName(String packageName) {
+        this.packageName = packageName;
+    }
+
+    public String getClassName() {
+        return className;
+    }
+
+    public void setClassName(String className) {
+        this.className = className;
+    }
+
+    public String getTag() {
+        return tag;
+    }
+
+    public void setTag(String tag) {
+        this.tag = tag;
+    }
+
+    public int getType_id() {
+        return type_id;
+    }
+
+    public void setType_id(int type_id) {
+        this.type_id = type_id;
+    }
+
+    public long getTime() {
+        return time;
+    }
+
+    public void setTime(long time) {
+        this.time = time;
+    }
+}

+ 52 - 0
app/src/main/java/com/sheep/gamegroup/util/Jump2View.java

@@ -1,11 +1,16 @@
 package com.sheep.gamegroup.util;
 
 import android.app.Activity;
+import android.app.AlertDialog;
 import android.content.Context;
+import android.content.DialogInterface;
 import android.content.Intent;
 import android.net.Uri;
+import android.os.Build;
 import android.os.Bundle;
+import android.provider.Settings;
 import android.text.TextUtils;
+import android.view.WindowManager;
 
 import com.alibaba.fastjson.JSON;
 import com.kfzs.duanduan.ActMain;
@@ -63,7 +68,10 @@ import com.sheep.gamegroup.view.activity.WithdrawalResultAct;
 import com.sheep.jiuyan.samllsheep.BuildConfig;
 import com.sheep.jiuyan.samllsheep.R;
 import com.sheep.jiuyan.samllsheep.SheepApp;
+import com.sheep.jiuyan.samllsheep.service.FloatService;
+import com.sheep.jiuyan.samllsheep.service.MonitorAppService;
 import com.sheep.jiuyan.samllsheep.utils.G;
+import com.sheep.jiuyan.samllsheep.utils.OpenService;
 import com.sheep.jiuyan.samllsheep.utils.SpUtils;
 
 import org.xutils.ex.DbException;
@@ -723,4 +731,48 @@ public class Jump2View {
         Intent intent = new Intent(context, ActMainGame.class);
         context.startActivity(intent);
     }
+
+
+    /**
+     * 启动小绵羊悬浮窗
+     * @param context
+     */
+    public void startFloat(Context context, boolean isShow) {
+        Intent intent = new Intent(context, FloatService.class);
+        intent.putExtra("isShow", isShow);
+        context.startService(intent);
+    }
+    private AlertDialog tipToOpernAccessibilityDialog;
+    public void clearAlertDialog(){
+        tipToOpernAccessibilityDialog = null;
+    }
+    /**
+     * 启动小绵羊辅助
+     * @param context
+     */
+    public boolean startAccessibility(final Context context) {
+        if(MonitorAppService.isAccessibilitySettingsOn(SheepApp.getInstance()) && new OpenService().isAccessibilitySettingsOn(context))
+            return true;
+        if(tipToOpernAccessibilityDialog != null){
+            return false;
+        }
+        AlertDialog.Builder  builder = new AlertDialog.Builder(context)
+                .setTitle("温馨提示!")
+                .setMessage("亲!要赚钱需要手动开启小绵羊辅助功能哟!")
+                .setPositiveButton("去开启", new DialogInterface.OnClickListener() {
+                    @Override
+                    public void onClick(DialogInterface dialog, int which) {
+                        Intent intent = new Intent(Settings.ACTION_ACCESSIBILITY_SETTINGS);
+                        intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+                        context.startActivity(intent);
+                    }
+                });
+        builder.setCancelable(false);
+        tipToOpernAccessibilityDialog = builder.create();
+        if(tipToOpernAccessibilityDialog.getWindow() != null) {
+            tipToOpernAccessibilityDialog.getWindow().setType(Build.VERSION.SDK_INT >= Build.VERSION_CODES.N ? WindowManager.LayoutParams.TYPE_PHONE : WindowManager.LayoutParams.TYPE_TOAST);
+            tipToOpernAccessibilityDialog.show();
+        }
+        return false;
+    }
 }

+ 7 - 2
app/src/main/java/com/sheep/gamegroup/util/ListUtil.java

@@ -9,14 +9,19 @@ import java.util.List;
  * realicing@sina.com
  */
 public class ListUtil {
-    public static <T> boolean hasIndex(List<T> list, int i) {
-        return !ListUtil.isEmpty(list) && list.size() > i;
+    public static <T> boolean hasIndex(List<T> list, int index) {
+        return !ListUtil.isEmpty(list) && list.size() > index;
     }
 
     private static <T> boolean isEmpty(List<T> list) {
         return list == null || list.isEmpty();
     }
 
+    public static <T> T getIndex(List<T> list, int index) {
+        return hasIndex(list, index) ? list.get(index) : null;
+    }
+
+
     public static int getTotalPage(int count, int per_page) {
         return (count - 1) / per_page + 1;
     }

+ 45 - 0
app/src/main/java/com/sheep/gamegroup/util/MyDbManager.java

@@ -1,7 +1,9 @@
 package com.sheep.gamegroup.util;
 
+import android.database.Cursor;
 import android.os.Handler;
 
+import com.sheep.gamegroup.model.entity.AppRecord;
 import com.sheep.gamegroup.model.entity.NewbieTaskRecord;
 import com.sheep.gamegroup.model.entity.UserEntity;
 import com.sheep.jiuyan.samllsheep.SheepApp;
@@ -12,6 +14,7 @@ import org.xutils.ex.DbException;
 import org.xutils.x;
 
 import java.util.List;
+import java.util.Locale;
 
 /**
  * Created by ljy on 2018/3/17.
@@ -116,4 +119,46 @@ public class MyDbManager {
             e.printStackTrace();
         }
     }
+    public List<AppRecord> getAppRecordList(String packageName){
+        try{
+            return db.selector(AppRecord.class)
+                    .where("package_name", "=", packageName)
+                    .findAll();
+        }catch (Exception e){
+            e.printStackTrace();
+        }
+        return ListUtil.emptyList();
+    }
+    public void removeAppRecord(){
+        try{
+            db.dropTable(AppRecord.class);
+//            String sql = String.format(Locale.CHINA,"delete from app_record where package_name in('%s')" , packageName);
+//            Cursor cursor = db.execQuery(sql);
+//            cursor.close();
+        }catch (Exception e){
+            e.printStackTrace();
+        }
+    }
+    public long getAppRunTime(String packageName){
+        try{
+    //type_id 为32时对应 AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED
+//            Cursor cursor = db.execQuery(String.format(Locale.CHINA,"select sum(time) as all_time from app_record where package_name = '%s' and type_id = 32" , packageName));
+            Cursor cursor = db.execQuery(String.format(Locale.CHINA,"select sum(time) from app_record where package_name = '%s'" , packageName));
+            cursor.moveToFirst();
+            long time = cursor.getLong(0);
+            cursor.close();
+            return time;
+        }catch (Exception e){
+            e.printStackTrace();
+        }
+        return 0;
+    }
+//    public long getAppRunTime(String packageName){
+//        long time = 0;
+//        List<AppRecord> list = getAppRecordList(packageName);
+//        for (AppRecord appRecord : list) {
+//            time += appRecord.getTime();
+//        }
+//        return time;
+//    }
 }

+ 7 - 1
app/src/main/java/com/sheep/jiuyan/samllsheep/SheepApp.java

@@ -12,10 +12,10 @@ import com.sheep.gamegroup.di.components.NetComponent;
 import com.sheep.gamegroup.di.modules.NetModule;
 import com.sheep.gamegroup.model.entity.TaskEty;
 import com.sheep.gamegroup.util.ConnectAddress;
+import com.sheep.gamegroup.util.Jump2View;
 import com.sheep.gamegroup.util.UMConfigUtils;
 import com.sheep.jiuyan.samllsheep.utils.G;
 import com.tencent.bugly.Bugly;
-import com.tencent.mm.opensdk.openapi.IWXAPI;
 
 /**
  * Created by kemllor on 2017/12/21.
@@ -108,6 +108,9 @@ public class SheepApp extends BaseApplication {
         @Override
         public void onActivityResumed(Activity activity) {
             UMConfigUtils.onPageStart(activity);
+            if (mActivityAount > 0) {
+                Jump2View.getInstance().startFloat(activity, false);
+            }
         }
 
         @Override
@@ -118,6 +121,9 @@ public class SheepApp extends BaseApplication {
         @Override
         public void onActivityStopped(Activity activity) {
             mActivityAount--;
+            if (mActivityAount <= 0) {
+                Jump2View.getInstance().startFloat(activity, true);
+            }
         }
 
         @Override

+ 1 - 0
app/src/main/java/com/sheep/jiuyan/samllsheep/base/BaseFragment.java

@@ -113,6 +113,7 @@ public abstract class BaseFragment extends Fragment {
         onViewCreated();
     }
 
+
     /**
      * 万能的找View类
      *

+ 213 - 0
app/src/main/java/com/sheep/jiuyan/samllsheep/service/FloatService.java

@@ -0,0 +1,213 @@
+package com.sheep.jiuyan.samllsheep.service;
+
+import android.app.AlertDialog;
+import android.app.Service;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.content.Intent;
+import android.graphics.PixelFormat;
+import android.graphics.Point;
+import android.os.Build;
+import android.os.IBinder;
+import android.provider.Settings;
+import android.util.Log;
+import android.view.Gravity;
+import android.view.LayoutInflater;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.WindowManager;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+
+import com.sheep.gamegroup.util.Jump2View;
+import com.sheep.jiuyan.samllsheep.R;
+import com.sheep.jiuyan.samllsheep.utils.DeviceInfo;
+import com.sheep.jiuyan.samllsheep.utils.OpenService;
+
+
+import java.util.concurrent.TimeUnit;
+
+import rx.Observable;
+import rx.Subscription;
+import rx.android.schedulers.AndroidSchedulers;
+import rx.functions.Action1;
+import rx.schedulers.Schedulers;
+
+/**
+ * Created by realicing on 2018/5/8.
+ * realicing@sina.com
+ */
+public class FloatService extends Service implements View.OnClickListener {
+
+    private static final String TAG = "MainService";
+
+    LinearLayout mFloatwindow;
+    WindowManager.LayoutParams params;
+    WindowManager mWm;
+
+    ImageView floaticon;
+
+    //状态栏高度.
+    int statusBarHeight = -1;
+
+    //不与Activity进行绑定.
+    @Override
+    public IBinder onBind(Intent intent) {
+        return null;
+    }
+
+    @Override
+    public void onCreate() {
+        super.onCreate();
+        Log.i(TAG, "MainService Created");
+        createToucher();
+        startTimer();
+    }
+
+    private void stopTimer() {
+        if(subscription != null){
+            subscription.unsubscribe();
+        }
+        subscription = null;
+    }
+
+    private Subscription subscription;
+    private void startTimer() {
+        if(subscription == null)
+            subscription = Observable.interval(1000, TimeUnit.MILLISECONDS)
+                    .subscribeOn(Schedulers.io())
+                    .observeOn(AndroidSchedulers.mainThread())
+                    .subscribe(new Action1<Long>() {
+                        @Override
+                        public void call(Long aLong) {
+
+                            Jump2View.getInstance().startAccessibility(getApplication());
+
+                        }
+                    }, new Action1<Throwable>() {
+                        @Override
+                        public void call(Throwable throwable) {
+                            throwable.printStackTrace();
+                        }
+                    });
+    }
+
+
+    private void createToucher() {
+        //赋值WindowManager&LayoutParam.
+        params = new WindowManager.LayoutParams();
+        if(mWm==null) {
+            mWm = (WindowManager) getApplicationContext().getSystemService(Context.WINDOW_SERVICE);
+        }
+        //设置type.系统提示型窗口,一般都在应用程序窗口之上.
+        //设置效果为背景透明.
+        params.format = PixelFormat.RGBA_8888;
+        //设置flags.不可聚焦及不可使用按钮对悬浮窗进行操控.
+        params.flags = WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL
+                | WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE;
+//
+//        //设置窗口初始停靠位置.
+        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
+            //  大于等于 24 即为 7.0 及以上执行内容
+            Log.e("qx", "7.0");
+            params.type = WindowManager.LayoutParams.TYPE_PHONE; // 7.1
+        } else {
+            //  低于 24 即为 7.0 以下执行内容
+            params.type = WindowManager.LayoutParams.TYPE_TOAST;   // 4.4
+            Log.e("qx", "4.4");
+
+        }
+
+        params.gravity = Gravity.LEFT | Gravity.TOP;
+        params.x = 0;
+        params.y = DeviceInfo.dip2px(getApplicationContext(), 25);
+
+        //设置悬浮窗口长宽数据.
+        params.width = -2;
+        params.height = DeviceInfo.dip2px(getApplicationContext(), 40f);
+
+        LayoutInflater inflater = LayoutInflater.from(getApplication());
+        //获取浮动窗口视图所在布局.
+        mFloatwindow = (LinearLayout) inflater.inflate(R.layout.float_window, null);
+        //添加toucherlayout
+        Log.i(TAG, "toucherlayout-->left:" + mFloatwindow.getLeft());
+        Log.i(TAG, "toucherlayout-->right:" + mFloatwindow.getRight());
+        Log.i(TAG, "toucherlayout-->top:" + mFloatwindow.getTop());
+        Log.i(TAG, "toucherlayout-->bottom:" + mFloatwindow.getBottom());
+
+        //主动计算出当前View的宽高信息.
+        mFloatwindow.measure(View.MeasureSpec.UNSPECIFIED, View.MeasureSpec.UNSPECIFIED);
+
+        //用于检测状态栏高度.
+        int resourceId = getResources().getIdentifier("status_bar_height", "dimen", "android");
+        if (resourceId > 0) {
+            statusBarHeight = getResources().getDimensionPixelSize(resourceId);
+        }
+        Log.i(TAG, "状态栏高度为:" + statusBarHeight);
+
+        //浮动窗口按钮.
+        floaticon = mFloatwindow.findViewById(R.id.floate_icon);
+        floaticon.setAlpha(0.0f);
+
+
+    }
+
+    @Override
+    public int onStartCommand(Intent intent, int flags, int startId) {
+        try {
+            if (intent != null && intent.getBooleanExtra("isShow", true)) {
+                if (mFloatwindow != null) {
+                    mWm.addView(mFloatwindow, params);
+                }
+            } else {
+                if (mFloatwindow != null)
+                    mWm.removeViewImmediate(mFloatwindow);
+
+            }
+        } catch (Exception ignore) {
+        }
+        return super.onStartCommand(intent, flags, START_STICKY);
+    }
+    @Override
+    public void onDestroy() {
+        if (floaticon != null) {
+            mWm.removeView(mFloatwindow);
+        }
+        stopTimer();
+        super.onDestroy();
+    }
+
+
+
+    /**
+     * 前往开启辅助服务界面
+     */
+    private void goAccess() {
+        Intent intent = new Intent(Settings.ACTION_ACCESSIBILITY_SETTINGS);
+        intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+        startActivity(intent);
+
+        Intent intent2 = new Intent(this, MonitorAppService.class);
+        startService(intent2);
+
+    }
+
+    @Override
+    public void onClick(View v) {
+        if (!new OpenService().isAccessibilitySettingsOn(this)) {
+            AlertDialog.Builder  builder=    new AlertDialog.Builder(this)
+                    .setTitle("温馨提示!")
+                    .setMessage("亲!要赚钱需要手动开启小绵羊辅助功能哟!")
+                    .setPositiveButton("去开启", new DialogInterface.OnClickListener() {
+                        @Override
+                        public void onClick(DialogInterface dialog, int which) {
+                            goAccess();
+                        }
+                    });
+            builder.setCancelable(false);
+            builder.show();
+            return ;
+        }
+    }
+
+}

+ 107 - 0
app/src/main/java/com/sheep/jiuyan/samllsheep/service/MonitorAppService.java

@@ -0,0 +1,107 @@
+package com.sheep.jiuyan.samllsheep.service;
+
+import android.accessibilityservice.AccessibilityService;
+import android.content.Context;
+import android.content.Intent;
+import android.provider.Settings;
+import android.text.TextUtils;
+import android.view.accessibility.AccessibilityEvent;
+
+import com.sheep.gamegroup.model.entity.AppRecord;
+import com.sheep.gamegroup.util.Jump2View;
+import com.sheep.gamegroup.util.ListUtil;
+import com.sheep.gamegroup.util.MyDbManager;
+
+import java.util.List;
+
+/**
+ * Created by realicing on 2018/5/4.
+ * realicing@sina.com
+ */
+public class MonitorAppService extends AccessibilityService {
+    private AppRecord lastAppRecord;
+    private long lastTime;
+    @Override
+    public void onAccessibilityEvent(AccessibilityEvent accessibilityEvent) {
+        // 此方法是在主线程中回调过来的,所以消息是阻塞执行的
+        // 获取包名
+        CharSequence packageName = accessibilityEvent.getPackageName();
+        CharSequence className = accessibilityEvent.getClassName();
+        int eventType = accessibilityEvent.getEventType();
+        List<CharSequence> textList = accessibilityEvent.getText();
+        switch (eventType) {
+            case AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED:
+                System.out.println("MonitorAppService TYPE_WINDOW_STATE_CHANGED: " + " pkgName: " + packageName + " className: " + className + " source: " + ListUtil.getIndex(textList, 0));
+
+                long curTime = System.currentTimeMillis();
+                AppRecord appRecord = new AppRecord();
+                appRecord.setType_id(eventType);
+                appRecord.setClassName(className.toString());
+                appRecord.setPackageName(packageName.toString());
+                if(!textList.isEmpty())
+                    appRecord.setTag(textList.get(0).toString());
+                if(lastAppRecord != null && lastTime != 0)
+                    lastAppRecord.setTime(lastAppRecord.getTime() + curTime - lastTime);
+                if(lastAppRecord != null)
+                    MyDbManager.getInstance().saveOrUpdate(lastAppRecord);
+
+                lastTime = curTime;
+                lastAppRecord = appRecord;
+                break;
+//            case AccessibilityEvent.TYPE_WINDOW_CONTENT_CHANGED:
+//                System.out.println("MonitorAppService TYPE_WINDOW_CONTENT_CHANGED: " + " packageName: " + packageName + " source: " + ListUtil.getIndex(textList, 0));
+//                break;
+//            case AccessibilityEvent.TYPE_VIEW_CLICKED:
+//                System.out.println("MonitorAppService TYPE_VIEW_CLICKED: " + " pkgName: " + packageName + " className: " + className  + " source: " + ListUtil.getIndex(textList, 0));
+//                break;
+        }
+    }
+
+    @Override
+    public int onStartCommand(Intent intent, int flags, int startId) {
+        Jump2View.getInstance().clearAlertDialog();
+        return super.onStartCommand(intent, flags, START_STICKY);
+    }
+
+    @Override
+    public void onInterrupt() {
+        Jump2View.getInstance().startAccessibility(getApplicationContext());
+        System.out.println("MonitorAppService onInterrupt");
+    }
+
+    @Override
+    public boolean onUnbind(Intent intent) {
+        Jump2View.getInstance().startAccessibility(getApplicationContext());
+        System.out.println("MonitorAppService onUnbind");
+        return super.onUnbind(intent);
+    }
+
+    public static boolean isAccessibilitySettingsOn(Context mContext) {
+        int accessibilityEnabled = 0;
+        final String service = mContext.getPackageName() + "/" + MonitorAppService.class.getCanonicalName();
+        // com.z.buildingaccessibilityservices/android.accessibilityservice.AccessibilityService
+        try {
+            accessibilityEnabled = Settings.Secure.getInt(mContext.getApplicationContext().getContentResolver(),
+                    android.provider.Settings.Secure.ACCESSIBILITY_ENABLED);
+        } catch (Settings.SettingNotFoundException e) {
+        }
+        TextUtils.SimpleStringSplitter mStringColonSplitter = new TextUtils.SimpleStringSplitter(':');
+
+        if (accessibilityEnabled == 1) {
+            String settingValue = Settings.Secure.getString(mContext.getApplicationContext().getContentResolver(),
+                    Settings.Secure.ENABLED_ACCESSIBILITY_SERVICES);
+            // com.z.buildingaccessibilityservices/com.z.buildingaccessibilityservices.TestService
+            if (settingValue != null) {
+                mStringColonSplitter.setString(settingValue);
+                while (mStringColonSplitter.hasNext()) {
+                    String accessibilityService = mStringColonSplitter.next();
+
+                    if (accessibilityService.equalsIgnoreCase(service)) {
+                        return true;
+                    }
+                }
+            }
+        }
+        return false;
+    }
+}

+ 14 - 0
app/src/main/res/layout/float_window.xml

@@ -0,0 +1,14 @@
+<?xml version="1.0" encoding="utf-8"?>
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="wrap_content"
+    android:layout_height="wrap_content"
+    android:orientation="horizontal">
+
+    <ImageView
+        android:id="@+id/floate_icon"
+        android:layout_width="40dp"
+        android:layout_height="40dp"
+        android:scaleType="fitCenter"
+        android:src="@drawable/icon"/>
+
+</LinearLayout>

+ 2 - 0
app/src/main/res/values/strings.xml

@@ -14,6 +14,7 @@
     <string name="coming_soon">敬请期待</string>
     <string name="last_page">&#060;</string>
     <string name="next_page">&#062;</string>
+
     <string name="total_money">绵羊币总资产:%s元</string>
     <string name="task_reward">任务奖励:%s元</string>
     <string name="agent_extract">代理提成:%s元</string>
@@ -27,4 +28,5 @@
     <string name="feedback_notice_input_email_address">请输入您的邮箱地址</string>
     <string name="contact_qq_email">联系QQ/邮箱</string>
     <string name="input_notice_feedback">请留下您的联系方式,我们会不定期地给予优质建议提供丰厚奖励哦!</string>
+    <string name="accessibility_desc">小绵羊任务</string>
 </resources>

+ 8 - 0
app/src/main/res/xml/accessibility.xml

@@ -0,0 +1,8 @@
+<?xml version="1.0" encoding="utf-8"?>
+<accessibility-service xmlns:android="http://schemas.android.com/apk/res/android"
+    android:accessibilityEventTypes="typeWindowStateChanged"
+    android:accessibilityFeedbackType="feedbackAllMask"
+    android:accessibilityFlags="flagDefault"
+    android:canRetrieveWindowContent="true"
+    android:description="@string/accessibility_desc"
+    android:notificationTimeout="100" />