From d9b05e54cc79e172c4d73d76ef8e7f62196cb95d Mon Sep 17 00:00:00 2001 From: Godfather <981964879@qq.com> Date: Tue, 4 Jan 2022 15:02:18 +0800 Subject: [PATCH] version:1.2 fix: add: --- app/build.gradle | 4 +- .../uiui/sn/activity/main/MainActivity.java | 4 +- .../uiui/sn/activity/main/MainContact.java | 1 + .../uiui/sn/activity/main/MainPresenter.java | 8 +- .../com/uiui/sn/base/BaseApplication.java | 6 +- .../uiui/sn/bean/zuoye/SystemSettings.java | 87 ++++--- .../com/uiui/sn/manager/ControlManager.java | 186 ++++++++------ .../com/uiui/sn/network/HTTPInterface.java | 163 +++--------- .../java/com/uiui/sn/network/UrlAddress.java | 43 ++-- .../com/uiui/sn/receiver/MyJPushReceiver.java | 233 ++++++++++-------- .../java/com/uiui/sn/service/MainService.java | 2 +- .../com/uiui/sn/service/ManagerService.java | 8 +- .../main/java/com/uiui/sn/utils/ApkUtils.java | 24 +- .../com/uiui/sn/utils/AppUsedTimeUtils.java | 120 +++++++++ .../com/uiui/sn/utils/AudioMngHelper.java | 168 +++++++++++++ .../main/java/com/uiui/sn/utils/JGYUtils.java | 187 ++++++++++---- .../main/java/com/uiui/sn/utils/Utils.java | 7 +- app/src/main/res/mipmap-hdpi/ic_launcher.png | Bin 4464 -> 4576 bytes app/src/main/res/mipmap-mdpi/ic_launcher.png | Bin 4464 -> 4576 bytes app/src/main/res/mipmap-xhdpi/ic_launcher.png | Bin 4464 -> 4576 bytes .../main/res/mipmap-xxhdpi/ic_launcher.png | Bin 4464 -> 4576 bytes .../main/res/mipmap-xxxhdpi/ic_launcher.png | Bin 4464 -> 4576 bytes app/src/main/res/values/arrays.xml | 16 ++ 23 files changed, 800 insertions(+), 467 deletions(-) create mode 100644 app/src/main/java/com/uiui/sn/utils/AppUsedTimeUtils.java create mode 100644 app/src/main/java/com/uiui/sn/utils/AudioMngHelper.java create mode 100644 app/src/main/res/values/arrays.xml diff --git a/app/build.gradle b/app/build.gradle index 65abcfb..3f63e63 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -60,8 +60,8 @@ android { productFlavors { beta { flavorDimensions "default" - versionCode 2 - versionName "1.1" + versionCode 3 + versionName "1.2" manifestPlaceholders = [ JPUSH_PKGNAME: "com.uiui.sn", JPUSH_APPKEY : "1a1e405ca5a1a5cd50e9f734", //JPush 上注册的包名对应的 Appkey. diff --git a/app/src/main/java/com/uiui/sn/activity/main/MainActivity.java b/app/src/main/java/com/uiui/sn/activity/main/MainActivity.java index a4257d9..1c98526 100644 --- a/app/src/main/java/com/uiui/sn/activity/main/MainActivity.java +++ b/app/src/main/java/com/uiui/sn/activity/main/MainActivity.java @@ -85,7 +85,6 @@ import static com.uiui.sn.jpush.TagAliasOperatorHelper.ACTION_SET; public class MainActivity extends BaseActivity implements MainContact.MainView, NetworkUtils.OnNetworkStatusChangedListener { private final String TAG = MainActivity.class.getSimpleName(); - private final String defaultText = "未绑定"; private MainPresenter mPresenter = new MainPresenter(this); @@ -193,7 +192,7 @@ public class MainActivity extends BaseActivity implements MainContact.MainView, registerReceiver(); setJpush(); HTTPInterface.sendAppUsed(this); -// HTTPInterface.sendRunningApp(this); + HTTPInterface.sendRunningApp(this); HTTPInterface.getAPPinfo(this); time0 = System.currentTimeMillis(); timeMillis = System.currentTimeMillis(); @@ -853,4 +852,5 @@ public class MainActivity extends BaseActivity implements MainContact.MainView, public void setScreenLock() { Log.e(TAG, "SettingFinished: " + (System.currentTimeMillis() - timeMillis) + " ms"); } + } diff --git a/app/src/main/java/com/uiui/sn/activity/main/MainContact.java b/app/src/main/java/com/uiui/sn/activity/main/MainContact.java index 2172c46..72a358e 100644 --- a/app/src/main/java/com/uiui/sn/activity/main/MainContact.java +++ b/app/src/main/java/com/uiui/sn/activity/main/MainContact.java @@ -85,5 +85,6 @@ public class MainContact { void getTimeControl(); //获取锁屏管控 void getScreenLock(); + } } diff --git a/app/src/main/java/com/uiui/sn/activity/main/MainPresenter.java b/app/src/main/java/com/uiui/sn/activity/main/MainPresenter.java index 90b69de..a64304d 100644 --- a/app/src/main/java/com/uiui/sn/activity/main/MainPresenter.java +++ b/app/src/main/java/com/uiui/sn/activity/main/MainPresenter.java @@ -168,6 +168,7 @@ public class MainPresenter implements MainContact.Presenter { public void getBatch() { NetInterfaceManager.getInstance() .getBatchApiControl() + .compose(getProvider().bindUntilEvent(ActivityEvent.DESTROY)) .subscribe(new Observer() { @Override public void onSubscribe(Disposable d) { @@ -535,9 +536,9 @@ public class MainPresenter implements MainContact.Presenter { SPUtils.put(mContext, "is_first_connection", 0); int code = systemSettingsBaseResponse.code; if (code == 200) { - JSONObject jsonObject = (JSONObject) JSON.toJSON(systemSettingsBaseResponse.data); - Log.e(TAG + "getSystemSettings", "onNext: settings: " + jsonObject.toString()); - ControlManager.getInstance().setSystemSetting(mContext, jsonObject.toJSONString()); + String data = new Gson().toJson(systemSettingsBaseResponse.data); + Log.e("getSystemSettings", "onNext: " + data); + ControlManager.getInstance().setSystemSetting(data); } else { ControlManager.getInstance().setDisableSetting(); } @@ -794,6 +795,7 @@ public class MainPresenter implements MainContact.Presenter { .getScreenshot(Utils.getSerial()) .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) + .compose(getProvider().bindUntilEvent(ActivityEvent.DESTROY)) .subscribe(new Observer() { @Override diff --git a/app/src/main/java/com/uiui/sn/base/BaseApplication.java b/app/src/main/java/com/uiui/sn/base/BaseApplication.java index c646efa..e0144c4 100644 --- a/app/src/main/java/com/uiui/sn/base/BaseApplication.java +++ b/app/src/main/java/com/uiui/sn/base/BaseApplication.java @@ -16,6 +16,7 @@ import com.uiui.sn.manager.ControlManager; import com.uiui.sn.manager.DeviceManager; import com.uiui.sn.network.HTTPInterface; import com.uiui.sn.network.UrlAddress; +import com.uiui.sn.utils.AppUsedTimeUtils; import com.uiui.sn.utils.JGYUtils; import com.uiui.sn.utils.ToastUtil; import com.uiui.sn.utils.Utils; @@ -66,8 +67,8 @@ public class BaseApplication extends Application { context = this; instance = this; // if (SystemUtils.isMainProcessName(this, Process.myPid())) { - //非主进程不初始化 - utilsInint(); + //非主进程不初始化 + utilsInint(); // } } @@ -87,6 +88,7 @@ public class BaseApplication extends Application { AmapManager.init(this); AmapManager.getInstance().initAmap(); NetInterfaceManager.init(this); + AppUsedTimeUtils.init(this); JGYUtils.hookWebView(); initAliasObservable(); initTagObservable(); diff --git a/app/src/main/java/com/uiui/sn/bean/zuoye/SystemSettings.java b/app/src/main/java/com/uiui/sn/bean/zuoye/SystemSettings.java index 017649a..5f7d942 100644 --- a/app/src/main/java/com/uiui/sn/bean/zuoye/SystemSettings.java +++ b/app/src/main/java/com/uiui/sn/bean/zuoye/SystemSettings.java @@ -1,6 +1,9 @@ package com.uiui.sn.bean.zuoye; +import com.google.gson.Gson; +import com.google.gson.JsonParser; + import java.io.Serializable; public class SystemSettings implements Serializable { @@ -32,6 +35,11 @@ public class SystemSettings implements Serializable { int qch_restore; int setting_browserInput; int dev_mode; + String setting_sos; + int setting_volume; + int setting_luminance; + String setting_typeface; + public int getQch_restore() { return qch_restore; @@ -234,52 +242,41 @@ public class SystemSettings implements Serializable { this.setting_hotspot = setting_hotspot; } + public String getSetting_sos() { + return setting_sos; + } + + public void setSetting_sos(String setting_sos) { + this.setting_sos = setting_sos; + } + + public int getSetting_volume() { + return setting_volume; + } + + public void setSetting_volume(int setting_volume) { + this.setting_volume = setting_volume; + } + + public int getSetting_luminance() { + return setting_luminance; + } + + public void setSetting_luminance(int setting_luminance) { + this.setting_luminance = setting_luminance; + } + + public String getSetting_typeface() { + return setting_typeface; + } + + public void setSetting_typeface(String setting_typeface) { + this.setting_typeface = setting_typeface; + } + + @Override public String toString() { - final StringBuilder sb = new StringBuilder("{"); - sb.append("\"setting_call\":") - .append(setting_call); - sb.append(",\"setting_memory\":") - .append(setting_memory); - sb.append(",\"setting_usb\":\"") - .append(setting_usb).append('\"'); - sb.append(",\"setting_bluetooth\":") - .append(setting_bluetooth); - sb.append(",\"setting_navigation\":") - .append(setting_navigation); - sb.append(",\"setting_statusbar\":") - .append(setting_statusbar); - sb.append(",\"setting_tfmedia\":") - .append(setting_tfmedia); - sb.append(",\"setting_phones\":\"") - .append(setting_phones).append('\"'); - sb.append(",\"setting_phone\":") - .append(setting_phone); - sb.append(",\"setting_camera\":") - .append(setting_camera); - sb.append(",\"setting_tfmedia_format\":\"") - .append(setting_tfmedia_format).append('\"'); - sb.append(",\"setting_clock\":") - .append(setting_clock); - sb.append(",\"setting_recording\":") - .append(setting_recording); - sb.append(",\"setting_music\":") - .append(setting_music); - sb.append(",\"setting_picture\":") - .append(setting_picture); - sb.append(",\"setting_wallpaper\":") - .append(setting_wallpaper); - sb.append(",\"setting_file\":") - .append(setting_file); - sb.append(",\"setting_bhtvideo\":") - .append(setting_bhtvideo); - sb.append(",\"setting_context\":\"") - .append(setting_context).append('\"'); - sb.append(",\"setting_bht\":") - .append(setting_bht); - sb.append(",\"setting_hotspot\":") - .append(setting_hotspot); - sb.append('}'); - return sb.toString(); + return JsonParser.parseString(new Gson().toJson(this)).getAsJsonObject().toString(); } } diff --git a/app/src/main/java/com/uiui/sn/manager/ControlManager.java b/app/src/main/java/com/uiui/sn/manager/ControlManager.java index 9bc2771..53d490c 100644 --- a/app/src/main/java/com/uiui/sn/manager/ControlManager.java +++ b/app/src/main/java/com/uiui/sn/manager/ControlManager.java @@ -2,6 +2,7 @@ package com.uiui.sn.manager; import android.annotation.SuppressLint; import android.bluetooth.BluetoothAdapter; +import android.content.ContentResolver; import android.content.Context; import android.content.Intent; import android.os.Build; @@ -34,9 +35,14 @@ public class ControlManager { @SuppressLint("StaticFieldLeak") private static ControlManager sInstance; private Context mContext; + private ContentResolver resolver; private ControlManager(Context mContext) { + if (mContext == null) { + throw new RuntimeException("Context is NULL"); + } this.mContext = mContext; + this.resolver = mContext.getContentResolver(); } public static void init(Context mContext) { @@ -52,27 +58,29 @@ public class ControlManager { return sInstance; } - private static int changeNum(int status) { + private int changeNum(int status) { return status == 0 ? 1 : 0; } - public void setSystemSetting(Context context, String jsonString) { + public void setSystemSetting(String jsonString) { if (TextUtils.isEmpty(jsonString)) { return; } SystemSettings settings = JSON.parseObject(jsonString, SystemSettings.class); if (null != settings) { - setUSBstate(context, settings); - setPhoneList(context, settings); - setBluetooth(context, settings); - setHotspot(context, settings); - setBar(context, settings); - setCamera(context, settings); - setTF(context, settings); - setIcon(context, settings); - setCanReset(context, jsonString); - setDeveloperOptions(context, jsonString); - setSearchTopic(context, jsonString); + setUSBstate(settings); + setPhoneList(settings); + setBluetooth(settings); + setHotspot(settings); + setBar(settings); + setCamera(settings); + setTF(settings); + setIcon(settings); + setCanReset(settings); + setDeveloperOptions(jsonString); + setSearchTopic(jsonString); + setSOSNumber(settings); + JGYUtils.getInstance().updateForbidList(); } } @@ -101,10 +109,9 @@ public class ControlManager { /** * usb连接模式管控 * - * @param mContext * @param settings */ - private static void setUSBstate(Context mContext, SystemSettings settings) { + private void setUSBstate(SystemSettings settings) { //USB数据功能管控 //仅充电:usb_charge //MTP模式:usb_mtp @@ -113,7 +120,7 @@ public class ControlManager { Log.e("SystemSetting", "setting_usb:" + setting_usb); if (!DeviceManager.isDebugMode()) { try { - boolean qch_usb_choose = JGYUtils.putString(mContext.getContentResolver(), "qch_usb_choose", setting_usb); + boolean qch_usb_choose = JGYUtils.putString(resolver, "qch_usb_choose", setting_usb); Log.e("SystemSetting", "qch_usb_choose:" + qch_usb_choose); String usbStatus = ""; switch (setting_usb) { @@ -150,7 +157,7 @@ public class ControlManager { //Midi模式:usb_midi if (!DeviceManager.isDebugMode()) { try { - boolean qch_usb_choose = Settings.System.putString(mContext.getContentResolver(), "qch_usb_choose", "usb_charge"); + boolean qch_usb_choose = Settings.System.putString(resolver, "qch_usb_choose", "usb_charge"); Log.e(TAG, "qch_usb_choose:" + qch_usb_choose); String usbStatus = "qch_action_usb_usb_charge"; Intent usbIntent = new Intent(usbStatus).setPackage("com.android.settings"); @@ -161,46 +168,46 @@ public class ControlManager { } } - private static void setPhoneList(Context mContext, SystemSettings settings) { + private void setPhoneList(SystemSettings settings) { //设置电话功能,电话白名单 int setting_call = changeNum(settings.getSetting_call()); - boolean qch_call_forbid = JGYUtils.putInt(mContext.getContentResolver(), "qch_call_forbid", setting_call); + boolean qch_call_forbid = JGYUtils.putInt(resolver, "qch_call_forbid", setting_call); Log.e("SystemSetting", "qch_call_forbid: " + setting_call); int setting_phone = changeNum(settings.getSetting_phone()); - boolean qch_white_list_on = JGYUtils.putInt(mContext.getContentResolver(), "qch_white_list_on", setting_phone); + boolean qch_white_list_on = JGYUtils.putInt(resolver, "qch_white_list_on", setting_phone); Log.e("SystemSetting", "qch_white_list_on: " + setting_phone); String setting_phones = settings.getSetting_phones(); - boolean qch_white_list_Array = JGYUtils.putString(mContext.getContentResolver(), "qch_white_list_Array", setting_phones); + boolean qch_white_list_Array = JGYUtils.putString(resolver, "qch_white_list_Array", setting_phones); Log.e("SystemSetting", "qch_white_list_Array: " + qch_white_list_Array + "=" + setting_phones); int setting_memory = changeNum(settings.getSetting_memory()); - boolean qch_sdcard_forbid_on = JGYUtils.putInt(mContext.getContentResolver(), "qch_sdcard_forbid_on", setting_memory); + boolean qch_sdcard_forbid_on = JGYUtils.putInt(resolver, "qch_sdcard_forbid_on", setting_memory); Log.e("SystemSetting", "qch_sdcard_forbid_on: " + setting_memory); } private void setPhoneList(int state) { try { //设置电话功能,电话白名单 - boolean qch_call_forbid = Settings.System.putInt(mContext.getContentResolver(), "qch_call_forbid", state); + boolean qch_call_forbid = Settings.System.putInt(resolver, "qch_call_forbid", state); Log.e(TAG, "qch_call_forbid:" + qch_call_forbid); - boolean qch_white_list_on = Settings.System.putInt(mContext.getContentResolver(), "qch_white_list_on", state); + boolean qch_white_list_on = Settings.System.putInt(resolver, "qch_white_list_on", state); Log.e(TAG, "qch_white_list_on:" + qch_white_list_on); - boolean qch_white_list_Array = Settings.System.putString(mContext.getContentResolver(), "qch_white_list_Array", ""); + boolean qch_white_list_Array = Settings.System.putString(resolver, "qch_white_list_Array", ""); // ToastTool.show("qch_call_forbid::"+setting_call+"----setting_phones::"+setting_phones+"----"+qch_white_list_Array+"---"+qch_call_forbid); Log.e(TAG, "qch_white_list_Array:" + qch_white_list_Array + "---" + qch_white_list_Array); - boolean qch_sdcard_forbid_on = Settings.System.putInt(mContext.getContentResolver(), "qch_sdcard_forbid_on", state); + boolean qch_sdcard_forbid_on = Settings.System.putInt(resolver, "qch_sdcard_forbid_on", state); Log.e(TAG, "qch_sdcard_forbid_on:" + qch_sdcard_forbid_on); } catch (Exception e) { Log.e(TAG, "setPhoneList: " + e.getMessage()); } } - private static void setBluetooth(Context mContext, SystemSettings settings) { + private void setBluetooth(SystemSettings settings) { try { //蓝牙开关 int setting_bht = changeNum(settings.getSetting_bht()); @@ -209,7 +216,7 @@ public class ControlManager { //蓝牙音频开关 int setting_bluetooth = changeNum(settings.getSetting_bluetooth()); //蓝牙传输开关 - boolean qch_bht_forbid_on = JGYUtils.putInt(mContext.getContentResolver(), "qch_bht_forbid_on", setting_bht); + boolean qch_bht_forbid_on = JGYUtils.putInt(resolver, "qch_bht_forbid_on", setting_bht); //写入系统数据库 Log.e("SystemSetting", "qch_bht_forbid_on:" + qch_bht_forbid_on); BluetoothAdapter mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter(); @@ -225,14 +232,14 @@ public class ControlManager { if (setting_bhtvideo == 0) { if (null != setting_context && !"".equals(setting_context) && !" ".equals(setting_context) && !"null".equals(setting_context)) { Log.e("SystemSetting", "setting_context:" + setting_context); - JGYUtils.putString(mContext.getContentResolver(), "qch_bhtvideo_forbid_on", setting_context); + JGYUtils.putString(resolver, "qch_bhtvideo_forbid_on", setting_context); } else { - JGYUtils.putString(mContext.getContentResolver(), "qch_bhtvideo_forbid_on", "Empty"); + JGYUtils.putString(resolver, "qch_bhtvideo_forbid_on", "Empty"); } } else if (setting_bhtvideo == 1) { - JGYUtils.putString(mContext.getContentResolver(), "qch_bhtvideo_forbid_on", "Empty"); + JGYUtils.putString(resolver, "qch_bhtvideo_forbid_on", "Empty"); } - JGYUtils.putInt(mContext.getContentResolver(), "qch_bt_forbid_on", setting_bluetooth); + JGYUtils.putInt(resolver, "qch_bt_forbid_on", setting_bluetooth); } else { mBluetoothAdapter.disable(); //设置关闭时关闭蓝牙 @@ -245,7 +252,7 @@ public class ControlManager { private void setBluetooth(int state) { try { - boolean qch_bht_forbid_on = Settings.System.putInt(mContext.getContentResolver(), "qch_bht_forbid_on", state); + boolean qch_bht_forbid_on = Settings.System.putInt(resolver, "qch_bht_forbid_on", state); //写入系统数据库 Log.e(TAG, "qch_bht_forbid_on:" + qch_bht_forbid_on); BluetoothAdapter mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter(); @@ -256,8 +263,8 @@ public class ControlManager { //获取默认蓝牙适配器 } //蓝牙总开关开启 - Settings.System.putString(mContext.getContentResolver(), "qch_bhtvideo_forbid_on", "Empty"); - Settings.System.putInt(mContext.getContentResolver(), "qch_bt_forbid_on", state); + Settings.System.putString(resolver, "qch_bhtvideo_forbid_on", "Empty"); + Settings.System.putInt(resolver, "qch_bt_forbid_on", state); mBluetoothAdapter.disable(); //设置关闭时关闭蓝牙 } @@ -266,7 +273,7 @@ public class ControlManager { } } - private static void setHotspot(Context mContext, SystemSettings settings) { + private void setHotspot(SystemSettings settings) { try { int setting_hotspot = changeNum(settings.getSetting_hotspot());//热点 if (setting_hotspot == 1) { @@ -275,7 +282,7 @@ public class ControlManager { intent.setPackage("com.android.settings"); mContext.sendStickyBroadcast(intent); } - boolean qch_hotspot_forbid_on = JGYUtils.putInt(mContext.getContentResolver(), "qch_hotspot_forbid_on", setting_hotspot);//写入系统数据库 + boolean qch_hotspot_forbid_on = JGYUtils.putInt(resolver, "qch_hotspot_forbid_on", setting_hotspot);//写入系统数据库 Log.e("SystemSetting", "qch_hotspot_forbid_on:" + setting_hotspot); Log.e("SystemSetting", "qch_hotspot_forbid_on:" + qch_hotspot_forbid_on); } catch (Exception e) { @@ -289,17 +296,17 @@ public class ControlManager { intent.setAction("qch_hotspot_close"); intent.setPackage("com.android.settings"); mContext.sendStickyBroadcast(intent); - boolean qch_hotspot_forbid_on = Settings.System.putInt(mContext.getContentResolver(), "qch_hotspot_forbid_on", state); + boolean qch_hotspot_forbid_on = Settings.System.putInt(resolver, "qch_hotspot_forbid_on", state); Log.e(TAG, "qch_hotspot_forbid_on:" + qch_hotspot_forbid_on); } catch (Exception e) { Log.e(TAG, "setHotspot: " + e.getMessage()); } } - private static void setBar(Context mContext, SystemSettings settings) { + private void setBar(SystemSettings settings) { //系统导航条显示开关 int setting_navigation = changeNum(settings.getSetting_navigation()); - boolean qch_hide_navigationBar = JGYUtils.putInt(mContext.getContentResolver(), "qch_hide_NavigationBar", setting_navigation); + boolean qch_hide_navigationBar = JGYUtils.putInt(resolver, "qch_hide_NavigationBar", setting_navigation); Log.e("SystemSetting", "qch_hide_navigationBar:" + qch_hide_navigationBar); String navigationStatus = ""; @@ -317,9 +324,9 @@ public class ControlManager { //状态栏显示开关 int setting_statusbar = changeNum(settings.getSetting_statusbar()); - int oldNum = JGYUtils.getInt(mContext.getContentResolver(), "qch_hide_statusBar", 0); + int oldNum = JGYUtils.getInt(resolver, "qch_hide_statusBar", 0); if (oldNum != setting_statusbar) { - boolean qch_hide_statusBar = JGYUtils.putInt(mContext.getContentResolver(), "qch_hide_statusBar", setting_statusbar); + boolean qch_hide_statusBar = JGYUtils.putInt(resolver, "qch_hide_statusBar", setting_statusbar); Log.e("SystemSetting", "qch_hide_statusBar:" + qch_hide_statusBar); String statusbarStatus = ""; switch (setting_statusbar) { @@ -335,11 +342,11 @@ public class ControlManager { } } - private static void setCamera(Context mContext, SystemSettings settings) { + private void setCamera(SystemSettings settings) { try { //摄像头开关 int setting_camera = changeNum(settings.getSetting_camera()); - JGYUtils.putInt(mContext.getContentResolver(), "qch_app_camera", setting_camera); + JGYUtils.putInt(resolver, "qch_app_camera", setting_camera); // ApkUtils.hideSystemSettingAPP(mContext, "com.mediatek.camera"); Log.e("SystemSetting", "setting_camera:" + setting_camera); String cameraStatus = ""; @@ -361,7 +368,7 @@ public class ControlManager { private void setCamera(int state) { try { //摄像头开关 - boolean qch_app_camera = Settings.System.putInt(mContext.getContentResolver(), "qch_app_camera", state); + boolean qch_app_camera = Settings.System.putInt(resolver, "qch_app_camera", state); Log.e(TAG, "qch_app_camera1:" + state); // ApkUtils.hideSystemSettingAPP(mContext, "com.mediatek.camera"); Log.e(TAG, "setting_camera---------" + qch_app_camera); @@ -382,10 +389,10 @@ public class ControlManager { } @SuppressLint("NewApi") - private static void setTF(Context mContext, SystemSettings settings) { + private void setTF(SystemSettings settings) { //tfmedia开关 int setting_tfmedia = changeNum(settings.getSetting_tfmedia()); - boolean qch_tfmedia_forbid = JGYUtils.putInt(mContext.getContentResolver(), "qch_tfmedia_forbid", setting_tfmedia); + boolean qch_tfmedia_forbid = JGYUtils.putInt(resolver, "qch_tfmedia_forbid", setting_tfmedia); Log.e("SystemSetting", "setting_tfmedia:" + qch_tfmedia_forbid); String tfmediaStatus = ""; switch (setting_tfmedia) { @@ -403,7 +410,7 @@ public class ControlManager { if (setting_tfmedia == 1) { String qch_tfmedia_filetypes = settings.getSetting_tfmedia_format(); if (TextUtils.isEmpty(qch_tfmedia_filetypes)) { - JGYUtils.putString(mContext.getContentResolver(), "qch_tfmedia_filetypes", "");//影音管控 + JGYUtils.putString(resolver, "qch_tfmedia_filetypes", "");//影音管控 } else { HashSet types = new HashSet<>(Arrays.asList(qch_tfmedia_filetypes.split(","))); types.removeIf(new Predicate() { @@ -413,11 +420,11 @@ public class ControlManager { } }); String typesString = String.join(",", types); - JGYUtils.putString(mContext.getContentResolver(), "qch_tfmedia_filetypes", typesString);//影音管控 + JGYUtils.putString(resolver, "qch_tfmedia_filetypes", typesString);//影音管控 Log.e("SystemSetting", "qch_tfmedia_filetypes :" + typesString); } } else { - JGYUtils.putInt(mContext.getContentResolver(), "qch_tfmedia_forbid", 0); + JGYUtils.putInt(resolver, "qch_tfmedia_forbid", 0); } } @@ -425,7 +432,7 @@ public class ControlManager { try { //tfmedia开关 // int setting_tfmedia = 1; - boolean qch_tfmedia_forbid = Settings.System.putInt(mContext.getContentResolver(), "qch_tfmedia_forbid", state); + boolean qch_tfmedia_forbid = Settings.System.putInt(resolver, "qch_tfmedia_forbid", state); Log.e(TAG, "setting_tfmedia---------" + qch_tfmedia_forbid); String tfmediaStatus = ""; switch (state) { @@ -439,47 +446,47 @@ public class ControlManager { Intent tfmediaIntent = new Intent(tfmediaStatus).setPackage("com.android.settings"); mContext.sendBroadcast(tfmediaIntent); if (state == 1) { - boolean qch_tfmedia_filetypes = Settings.System.putString(mContext.getContentResolver(), "qch_tfmedia_filetypes", "Empty");//影音管控 + boolean qch_tfmedia_filetypes = Settings.System.putString(resolver, "qch_tfmedia_filetypes", "Empty");//影音管控 Log.e(TAG, "qch_tfmedia_filetypes:" + qch_tfmedia_filetypes); } else { - Settings.System.putInt(mContext.getContentResolver(), "qch_tfmedia_forbid", 0); + Settings.System.putInt(resolver, "qch_tfmedia_forbid", 0); } } catch (Exception e) { Log.e(TAG, "setTF: " + e.getMessage()); } } - private static void setIcon(Context mContext, SystemSettings settings) { + private void setIcon(SystemSettings settings) { try { //added:2019.12.6 //设置5个app的开关 //时钟 int deskclock = changeNum(settings.getSetting_clock()); - JGYUtils.putInt(mContext.getContentResolver(), "qch_app_deskclock", deskclock); + JGYUtils.putInt(resolver, "qch_app_deskclock", deskclock); ApkUtils.hideSystemSettingAPP(mContext, "com.android.deskclock"); Log.e("SystemSetting", "qch_app_deskclock:" + deskclock); //录音机 int soundrecorder = changeNum(settings.getSetting_recording()); - JGYUtils.putInt(mContext.getContentResolver(), "qch_app_soundrecorder", soundrecorder); + JGYUtils.putInt(resolver, "qch_app_soundrecorder", soundrecorder); ApkUtils.hideSystemSettingAPP(mContext, "com.android.soundrecorder"); Log.e("SystemSetting", "qch_app_soundrecorder:" + soundrecorder); //音乐 int music = changeNum(settings.getSetting_music()); - JGYUtils.putInt(mContext.getContentResolver(), "qch_app_music", music); + JGYUtils.putInt(resolver, "qch_app_music", music); ApkUtils.hideSystemSettingAPP(mContext, "com.android.music"); Log.e("SystemSetting", "qch_app_music:" + music); //图库 int gallery = changeNum(settings.getSetting_picture()); - JGYUtils.putInt(mContext.getContentResolver(), "qch_app_gallery", gallery); + JGYUtils.putInt(resolver, "qch_app_gallery", gallery); ApkUtils.hideSystemSettingAPP(mContext, "com.android.gallery3d"); Log.e("SystemSetting", "qch_app_gallery:" + gallery); //壁纸 int wallpaper = changeNum(settings.getSetting_wallpaper()); - JGYUtils.putInt(mContext.getContentResolver(), "qch_app_wallpaper", wallpaper); + JGYUtils.putInt(resolver, "qch_app_wallpaper", wallpaper); Log.e("SystemSetting", "qch_app_wallpaper:" + wallpaper); //文件管理器 int filemanager = changeNum(settings.getSetting_file()); - JGYUtils.putInt(mContext.getContentResolver(), "qch_app_filemanager", filemanager); + JGYUtils.putInt(resolver, "qch_app_filemanager", filemanager); if (Build.VERSION.SDK_INT < Build.VERSION_CODES.O) { ApkUtils.hideSystemSettingAPP(mContext, "com.mediatek.filemanager"); } else { @@ -488,7 +495,7 @@ public class ControlManager { Log.e("SystemSetting", "qch_app_filemanager:" + filemanager); //浏览器 int browser = changeNum(settings.getSetting_browser()); - JGYUtils.putInt(mContext.getContentResolver(), "qch_app_browser", browser); + JGYUtils.putInt(resolver, "qch_app_browser", browser); Log.e(TAG, "qch_app_browser" + browser); } catch (Exception e) { Log.e(TAG, "setIcon: " + e.getMessage()); @@ -501,27 +508,27 @@ public class ControlManager { //设置5个app的开关 //时钟 // int deskclock = 1; - Settings.System.putInt(mContext.getContentResolver(), "qch_app_deskclock", state); + Settings.System.putInt(resolver, "qch_app_deskclock", state); ApkUtils.hideSystemSettingAPP(mContext, "com.android.deskclock"); Log.e(TAG, "qch_app_deskclock" + state); //录音机 // int soundrecorder = 1; - Settings.System.putInt(mContext.getContentResolver(), "qch_app_soundrecorder", state); + Settings.System.putInt(resolver, "qch_app_soundrecorder", state); ApkUtils.hideSystemSettingAPP(mContext, "com.android.soundrecorder"); Log.e(TAG, "qch_app_soundrecorder" + state); //音乐 // int music = 1; - Settings.System.putInt(mContext.getContentResolver(), "qch_app_music", state); + Settings.System.putInt(resolver, "qch_app_music", state); ApkUtils.hideSystemSettingAPP(mContext, "com.android.music"); Log.e(TAG, "qch_app_music" + state); //图库 // int gallery = 1; - Settings.System.putInt(mContext.getContentResolver(), "qch_app_gallery", state); + Settings.System.putInt(resolver, "qch_app_gallery", state); ApkUtils.hideSystemSettingAPP(mContext, "com.android.gallery3d"); Log.e(TAG, "qch_app_gallery" + state); //文件管理器 // int filemanager = 1; - Settings.System.putInt(mContext.getContentResolver(), "qch_app_filemanager", state); + Settings.System.putInt(resolver, "qch_app_filemanager", state); if (Build.VERSION.SDK_INT < Build.VERSION_CODES.O) { ApkUtils.hideSystemSettingAPP(mContext, "com.mediatek.filemanager"); } else { @@ -529,7 +536,7 @@ public class ControlManager { } Log.e(TAG, "qch_app_filemanager" + state); //浏览器 - Settings.System.putInt(mContext.getContentResolver(), "qch_app_browser", state); + Settings.System.putInt(resolver, "qch_app_browser", state); Log.e(TAG, "qch_app_browser" + state); } catch (Exception e) { Log.e(TAG, "setIcon: " + e.getMessage()); @@ -539,23 +546,22 @@ public class ControlManager { private void setWallpaper(int state) { //壁纸 // int wallpaper = 1; - Settings.System.putInt(mContext.getContentResolver(), "qch_app_wallpaper", state); + Settings.System.putInt(resolver, "qch_app_wallpaper", state); Log.e(TAG, "qch_app_wallpaper" + state); } - private static void setCanReset(Context context, String jsonString) { - JSONObject jsonObject = JSON.parseObject(jsonString); - int mode = jsonObject.getIntValue("qch_restore"); + private void setCanReset(SystemSettings settings) { + int mode = settings.getQch_restore(); if (mode == 1) { - Settings.System.putInt(context.getContentResolver(), "qch_restore_forbid_on", 0); + Settings.System.putInt(resolver, "qch_restore_forbid_on", 0); } else { - Settings.System.putInt(context.getContentResolver(), "qch_restore_forbid_on", 1); + Settings.System.putInt(resolver, "qch_restore_forbid_on", 1); } Log.e(TAG, "qch_restore_forbid_on:" + mode); } private void setCanReset(int state) { - boolean qch_restore_forbid_on = Settings.System.putInt(mContext.getContentResolver(), "qch_restore_forbid_on", 0); + boolean qch_restore_forbid_on = Settings.System.putInt(resolver, "qch_restore_forbid_on", 0); Log.e(TAG, "qch_restore_forbid_on:" + qch_restore_forbid_on); //默认打开 } @@ -566,20 +572,20 @@ public class ControlManager { * @param state */ private void setBrowserInput(int state) { - Settings.System.putInt(mContext.getContentResolver(), "qch_Browser_input", 0); + Settings.System.putInt(resolver, "qch_Browser_input", 0); } - public void setDeveloperOptions(Context context, String jsonString) { + public void setDeveloperOptions(String jsonString) { JSONObject jsonObject = JSON.parseObject(jsonString); int dev_mode = changeNum(jsonObject.getIntValue("dev_mode")); Log.e(TAG, "getDeveloper: " + dev_mode); if (!DeviceManager.isDebugMode()) { - JGYUtils.putInt(context.getContentResolver(), "qch_Developeroptions", dev_mode); + JGYUtils.putInt(resolver, "qch_Developeroptions", dev_mode); if (dev_mode == 1) { Intent intent = new Intent(); intent.setAction("qch_developeroptions_close"); intent.setPackage("com.android.settings"); - context.sendBroadcast(intent); + mContext.sendBroadcast(intent); Log.e(TAG, "getDeveloper: " + "关闭开发者模式"); ToastUtil.debugShow("关闭开发者模式"); } else { @@ -592,7 +598,7 @@ public class ControlManager { public void setDeveloperOptions(int state) { Log.e(TAG, "getDeveloper: " + state); if (!DeviceManager.isDebugMode()) { - Settings.System.putInt(mContext.getContentResolver(), "qch_Developeroptions", state); + Settings.System.putInt(resolver, "qch_Developeroptions", state); if (state == 1) { Intent intent = new Intent(); intent.setAction("qch_developeroptions_close"); @@ -606,10 +612,10 @@ public class ControlManager { } } - public void setSearchTopic(Context context, String jsonString) { + public void setSearchTopic(String jsonString) { JSONObject jsonObject = JSON.parseObject(jsonString); int mode = jsonObject.getIntValue("search_topic"); - SPUtils.put(context, "search_topic", mode); + SPUtils.put(mContext, "search_topic", mode); Log.e(TAG, "search_topic:" + mode); } @@ -626,7 +632,7 @@ public class ControlManager { //仅充电:usb_charge //MTP模式:usb_mtp //Midi模式:usb_midi - String setting_usb = JGYUtils.getString(mContext.getContentResolver(), "qch_usb_choose"); + String setting_usb = JGYUtils.getString(resolver, "qch_usb_choose"); Log.e("SystemSetting", "setting_usb:" + setting_usb); String usbStatus = ""; if (TextUtils.isEmpty(setting_usb)) { @@ -653,4 +659,20 @@ public class ControlManager { mContext.sendBroadcast(usbIntent); } + private void setSOSNumber(SystemSettings settings) { + String setting_sos = settings.getSetting_sos(); + Settings.System.putString(resolver, "setting_sos", setting_sos); + Intent intent = new Intent("setting_sos"); + intent.putExtra("setting_sos", setting_sos); + intent.setPackage("com.uiui.os"); + mContext.sendBroadcast(intent); + } + + private void setSetting(SystemSettings settings) { + int setting_volume = settings.getSetting_volume(); + int setting_luminance = settings.getSetting_luminance(); + String setting_typeface = settings.getSetting_typeface(); + + } + } diff --git a/app/src/main/java/com/uiui/sn/network/HTTPInterface.java b/app/src/main/java/com/uiui/sn/network/HTTPInterface.java index 10c9c15..bf26950 100644 --- a/app/src/main/java/com/uiui/sn/network/HTTPInterface.java +++ b/app/src/main/java/com/uiui/sn/network/HTTPInterface.java @@ -9,10 +9,13 @@ import android.content.pm.ResolveInfo; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.os.Build; +import android.os.Environment; import android.provider.Settings; import android.text.TextUtils; import android.util.Log; +import androidx.core.content.ContextCompat; + import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSONArray; import com.alibaba.fastjson.JSONObject; @@ -39,6 +42,7 @@ import com.uiui.sn.network.api.UpdateAdminSn; import com.uiui.sn.network.api.UploadScreenshot; import com.uiui.sn.service.ManagerService; import com.uiui.sn.utils.ApkUtils; +import com.uiui.sn.utils.AppUsedTimeUtils; import com.uiui.sn.utils.CmdUtil; import com.uiui.sn.utils.FileUtils; import com.uiui.sn.utils.JGYUtils; @@ -915,9 +919,9 @@ public class HTTPInterface { public void onNext(@NonNull BaseResponse BaseResponse) { int code = BaseResponse.code; if (code == 200) { - JSONObject jsonObject = (JSONObject) JSON.toJSON(BaseResponse.data); - Log.e("getSystemSettings", "onNext: " + jsonObject); - ControlManager.getInstance().setSystemSetting(context, jsonObject.toJSONString()); + String data = new Gson().toJson(BaseResponse.data); + Log.e("getSystemSettings", "onNext: " + data); + ControlManager.getInstance().setSystemSetting(data); } } @@ -1022,15 +1026,8 @@ public class HTTPInterface { } public static void sendRunningApp(Context context) { - String packageName = ApkUtils.getTaskPackname(context); - long time = 0; - StatisticsInfo statisticsInfo = new StatisticsInfo(context, 1); - List datalist = statisticsInfo.getShowList(); - for (AppInformation information : datalist) { - if (packageName.equals(information.getPackageName())) { - time = information.getUsedTimebyDay(); - } - } + String packageName = AppUsedTimeUtils.getInstance().getAppPackageName(); + long time = AppUsedTimeUtils.getInstance().getStartTime(); JsonObject jsonObject = new JsonObject(); jsonObject.addProperty("app_package", packageName); jsonObject.addProperty("version_name", ApkUtils.getAPPVersionName(context, packageName)); @@ -1119,7 +1116,8 @@ public class HTTPInterface { } public static void screenshot(Context context) { - String path = context.getExternalFilesDir("db").getAbsolutePath(); +// String path = context.getExternalFilesDir("db").getAbsolutePath(); + String path = ContextCompat.getExternalFilesDirs(context, Environment.DIRECTORY_DOWNLOADS)[0].getAbsolutePath(); String filePath = path + File.separator + Utils.getSerial() + ".png"; getScreenshot(context, filePath).concatMap(new Function>() { @Override @@ -1131,23 +1129,24 @@ public class HTTPInterface { if (!file.exists()) { throw new FileNotFoundException(filePath); } - Bitmap bitmap = BitmapFactory.decodeFile(filePath); - if (bitmap.getWidth() < bitmap.getHeight()) { - bitmap = ImageUtils.rotate(bitmap, -90, bitmap.getWidth(), bitmap.getHeight()); - } - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - bitmap.compress(Bitmap.CompressFormat.JPEG, 100, baos); - file.createNewFile(); - FileOutputStream fos = new FileOutputStream(file); - InputStream is = new ByteArrayInputStream(baos.toByteArray()); - int x; - byte[] b = new byte[1024 * 100]; - while ((x = is.read(b)) != -1) { - fos.write(b, 0, x); - } - fos.close(); - RequestBody requestFile = RequestBody.create(MediaType.parse("multipart/form-data"), file); - MultipartBody.Part body = MultipartBody.Part.createFormData("file", file.getName(), requestFile); +// Bitmap bitmap = BitmapFactory.decodeFile(filePath); +// if (bitmap.getWidth() < bitmap.getHeight()) { +// bitmap = ImageUtils.rotate(bitmap, -90, bitmap.getWidth(), bitmap.getHeight()); +// } +// ByteArrayOutputStream baos = new ByteArrayOutputStream(); +// bitmap.compress(Bitmap.CompressFormat.JPEG, 100, baos); +// file.createNewFile(); +// FileOutputStream fos = new FileOutputStream(file); +// InputStream is = new ByteArrayInputStream(baos.toByteArray()); +// int x; +// byte[] b = new byte[1024 * 100]; +// while ((x = is.read(b)) != -1) { +// fos.write(b, 0, x); +// } +// fos.close(); + MediaType mediaType = MediaType.Companion.parse("image/png"); + RequestBody requestBody = RequestBody.Companion.create(file, mediaType); + MultipartBody.Part body = MultipartBody.Part.createFormData("file", file.getName(), requestBody); return getSendFile(filePath, body); } }).subscribeOn(Schedulers.io()) @@ -1176,110 +1175,6 @@ public class HTTPInterface { }); } - - public static void doscreenshot(final Context context) { - String path = context.getExternalFilesDir("db").getAbsolutePath(); - String filePath = path + File.separator + Utils.getSerial() + ".png"; - Observable.create(new ObservableOnSubscribe() { - @Override - public void subscribe(ObservableEmitter e) throws Exception { - int n = CmdUtil.execute("screencap -p " + filePath).code; - e.onNext(n); - } - }).subscribeOn(Schedulers.io()) - .observeOn(AndroidSchedulers.mainThread()) - .subscribe(new Observer() { - @Override - public void onSubscribe(Disposable d) { - - } - - @Override - public void onNext(Integer integer) { - if (integer == 0) { - uplaodImage(context, filePath); - } else { - Log.e("doss", "失败"); - } - } - - @Override - public void onError(Throwable e) { - Log.e("doss", "Throwable=" + e.getMessage()); - } - - @Override - public void onComplete() { - - } - }); - } - - private static void uplaodImage(final Context context, String filePath) { - File file = new File(filePath); - if (!file.exists()) { - Log.e("uplaodImage", "File does not exists"); - return; - } - - Bitmap bitmap = BitmapFactory.decodeFile(filePath); - if (bitmap.getWidth() < bitmap.getHeight()) { - bitmap = ImageUtils.rotate(bitmap, -90, bitmap.getWidth(), bitmap.getHeight()); - } - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - bitmap.compress(Bitmap.CompressFormat.JPEG, 100, baos); - - try { - file.createNewFile(); - FileOutputStream fos = new FileOutputStream(file); - InputStream is = new ByteArrayInputStream(baos.toByteArray()); - int x = 0; - byte[] b = new byte[1024 * 100]; - while ((x = is.read(b)) != -1) { - fos.write(b, 0, x); - } - fos.close(); - } catch (Exception e) { - e.printStackTrace(); - } - - - RequestBody requestFile = RequestBody.create(MediaType.parse("multipart/form-data"), file); - MultipartBody.Part body = MultipartBody.Part.createFormData("file", file.getName(), requestFile); - NetInterfaceManager.getInstance() - .getControlScreenshotApi() - .getControlScreenshot(Utils.getSerial(), body) - .subscribeOn(Schedulers.io()) - .observeOn(AndroidSchedulers.mainThread()) - .subscribe(new Observer() { - @Override - public void onSubscribe(Disposable d) { - Log.e("uplaod", "onSubscribe: "); - } - - @Override - public void onNext(BaseResponse baseResponse) { - int code = baseResponse.code; - if (code == 200) { - Log.e("uplaod", "onNext: " + baseResponse.msg); - } else { - Log.e("uplaod", code + ": " + baseResponse.msg); - } - } - - @Override - public void onError(Throwable e) { - Log.e("uplaod", "onError: " + e.getMessage()); - onComplete(); - } - - @Override - public void onComplete() { - Log.e("uplaod", "onComplete: "); - } - }); - } - private static List factoryApp = new ArrayList() {{ this.add("com.gankao.gkwxhd"); this.add("com.jiaoguanyi.os"); diff --git a/app/src/main/java/com/uiui/sn/network/UrlAddress.java b/app/src/main/java/com/uiui/sn/network/UrlAddress.java index e956bbd..df651f1 100644 --- a/app/src/main/java/com/uiui/sn/network/UrlAddress.java +++ b/app/src/main/java/com/uiui/sn/network/UrlAddress.java @@ -4,49 +4,49 @@ public class UrlAddress { //主页接口 public static final String ROOT_URL = "https://led.aolelearn.cn/android/"; //获取班级ID - public static final String GET_BATCH = "sn/getBatch"; + public static final String GET_BATCH = "sn/getBatch"; //设备信息接口 - public static final String SNINFO = "sn/getSnInfo"; + public static final String SNINFO = "sn/getSnInfo"; //发送app信息 - public static final String APPLOG = "App/getApplog"; + public static final String APPLOG = "App/getApplog"; //获取正在运行的app public static final String RUN_NEW_APP = "app/runNewApp"; //根据包名获取更新 - public final static String GET_APP_UPDATE = "Update/update"; + public final static String GET_APP_UPDATE = "Update/update"; //获取当前最顶层应用和电量 - public final static String SEND_RUNINGAPPINFO = "Monitoring/getAppNow"; + public final static String SEND_RUNINGAPPINFO = "Monitoring/getAppNow"; //在线状态 - public final static String SEND_DRIVE_STATE = "Online/online"; + public final static String SEND_DRIVE_STATE = "Online/online"; //获取所有应用 - public final static String GET_ALL_PACKAGE = "app/queryAllApp"; + public final static String GET_ALL_PACKAGE = "app/queryAllApp"; //绑定设备消息 - public final static String BIND_DEVICES = "sn/bindSn"; + public final static String BIND_DEVICES = "sn/bindSn"; //获取系统设置 - public final static String GET_SETTINGS = "control/getSetting"; + public final static String GET_SETTINGS = "control/getSetting"; //浏览器网址管控 - public final static String SET_BROWSER_URL = "control/getBrowser"; + public final static String SET_BROWSER_URL = "control/getBrowser"; //浏览器书签管控 - public final static String SET_BROWSER_LABEL = "control/getLabel"; + public final static String SET_BROWSER_LABEL = "control/getLabel"; //获取强制下载 - public final static String GET_FORCE_INSTALL = "app/getForceDownload"; + public final static String GET_FORCE_INSTALL = "app/getForceDownload"; //获取app管控 - public final static String GET_APP_START = "sn/querySnAppStart"; + public final static String GET_APP_START = "sn/querySnAppStart"; //发app跳转管控 - public final static String GET_APP_JUMP = "sn/querySnJump"; + public final static String GET_APP_JUMP = "sn/querySnJump"; //发app跳转管控 - public final static String QUERY_APP_INSIDE = "control/queryAppInside"; + public final static String QUERY_APP_INSIDE = "control/queryAppInside"; //发送卸载或者安装信息 - public final static String SEND_INSTALLEDORREMOVED = "app/addAppInstall"; + public final static String SEND_INSTALLEDORREMOVED = "app/addAppInstall"; //发送卸载或者安装信息 - public final static String UPDATE_SNINFO = "sn/updateAdminSn"; + public final static String UPDATE_SNINFO = "sn/updateAdminSn"; //根据包名获取更新 - public final static String GET_NEWESTAPPUPDATE = "app/newestAppUpdate"; + public final static String GET_NEWESTAPPUPDATE = "app/newestAppUpdate"; //上传屏幕截图 - public final static String UPLOAD_SCREEN_SNAPSHOT = "sn/uploadScreenshot"; + public final static String UPLOAD_SCREEN_SNAPSHOT = "sn/uploadScreenshot"; //获取屏幕管控 - public final static String GET_SCREEN_LOCK = "sn/getScreenshot"; + public final static String GET_SCREEN_LOCK = "sn/getScreenshot"; //获取时间管控 - public final static String GET_TIME_CONTROL = "sn/getTimeControl"; + public final static String GET_TIME_CONTROL = "sn/getTimeControl"; //获取用户头像和信息 public static final String GET_USER_AVATAR_INFO = "sn/getUserAvatarInfo"; //上传设备赶考的UID @@ -65,6 +65,7 @@ public class UrlAddress { public static final String GET_APP_AND_WHITE = "getAppAndWhite"; + // //赶考 // public static final String GANKAN_ROOT_URL = "https://www.gankao.com/api/service/"; // //创建/查询用户 diff --git a/app/src/main/java/com/uiui/sn/receiver/MyJPushReceiver.java b/app/src/main/java/com/uiui/sn/receiver/MyJPushReceiver.java index 8d13b98..3a5179d 100644 --- a/app/src/main/java/com/uiui/sn/receiver/MyJPushReceiver.java +++ b/app/src/main/java/com/uiui/sn/receiver/MyJPushReceiver.java @@ -1,6 +1,7 @@ package com.uiui.sn.receiver; import android.annotation.SuppressLint; +import android.app.NotificationManager; import android.bluetooth.BluetoothAdapter; import android.content.BroadcastReceiver; import android.content.ComponentName; @@ -8,12 +9,15 @@ import android.content.Context; import android.content.Intent; import android.content.IntentFilter; import android.content.pm.PackageManager; +import android.content.res.Resources; import android.graphics.Bitmap; import android.graphics.BitmapFactory; +import android.media.AudioManager; import android.os.Bundle; import android.os.CountDownTimer; import android.os.Environment; import android.os.Handler; +import android.provider.Settings; import android.text.TextUtils; import android.util.Log; import android.view.Gravity; @@ -21,9 +25,14 @@ import android.view.WindowManager; import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSONObject; +import com.android.internal.view.RotationPolicy; import com.arialyy.aria.core.Aria; import com.arialyy.aria.core.download.DownloadEntity; import com.blankj.utilcode.util.ImageUtils; +import com.google.gson.Gson; +import com.google.gson.JsonObject; +import com.google.gson.JsonParser; +import com.uiui.sn.R; import com.uiui.sn.bean.zuoye.BaseResponse; import com.uiui.sn.dialog.CustomDialog; import com.uiui.sn.jpush.Logger; @@ -188,6 +197,10 @@ public class MyJPushReceiver extends BroadcastReceiver { private static final String JIGUANG_HIDE_APPICON = "59"; //优化内存 private static final String JIGUANG_KILL_APP = "60"; + //SOS联系人 + private static final String JIGUANG_SOS_PHONENUM = "61"; + //重新安装应用 + private static final String JIGUANG_REINSTALL_APP = "62"; @Override @@ -344,7 +357,7 @@ public class MyJPushReceiver extends BroadcastReceiver { break; case JIGUANG_SYSTEM_SETTING: ToastUtil.debugShow("收到推送消息: 系统管控"); - ControlManager.getInstance().setSystemSetting(context, extras); + ControlManager.getInstance().setSystemSetting(extras); // if ("com.jiaoguanyi.os".equals(ForegroundAppUtil.getForegroundPackageName(context))) { // JGYUtils.getInstance().killBackgroundProcesses(context, "com.jiaoguanyi.os"); // Intent intent = context.getPackageManager().getLaunchIntentForPackage("com.jiaoguanyi.os"); @@ -366,7 +379,7 @@ public class MyJPushReceiver extends BroadcastReceiver { ToastUtil.debugShow("收到推送消息: 强制停止应用"); JSONObject killJSONObject = JSON.parseObject(extras); String packages = killJSONObject.getString("app_package"); - JGYUtils.getInstance().killBackgroundProcesses(context, packages); + JGYUtils.getInstance().killBackgroundProcesses(packages); Log.e(TAG, extras); break; case JIGUANG_LOCK_SCREEN: @@ -397,7 +410,7 @@ public class MyJPushReceiver extends BroadcastReceiver { break; case JIGUANG_DEVELOPER_CONTROL: ToastUtil.debugShow("收到推送消息: 开发人员选项"); - ControlManager.getInstance().setDeveloperOptions(context, extras); + ControlManager.getInstance().setDeveloperOptions(extras); break; case JIGUANG_CLEAN_APP_CACHE: ToastUtil.debugShow("收到推送消息: 清除应用缓存"); @@ -440,16 +453,28 @@ public class MyJPushReceiver extends BroadcastReceiver { case JIGUANG_FLIGHT_MODE: break; case JIGUANG_NOTDISTURB_MODE: + ToastUtil.debugShow("收到推送消息: 设置勿扰模式"); + setZenMode(context, extras); break; case JIGUANG_LOCATION: break; case JIGUANG_CHARGING_REMINDER: break; case JIGUANG_VOLUME: + ToastUtil.debugShow("收到推送消息: 设置音量"); + setVolume(context, extras); break; case JIGUANG_LUMINANCE: + ToastUtil.debugShow("收到推送消息: 设置屏幕亮度"); + setScreenBrightness(context, extras); + break; + case JIGUANG_TYPEFACE: + ToastUtil.debugShow("收到推送消息: 设置字体大小"); + setFontSize(context, extras); break; case JIGUANG_SCREEN_ROTATION: + ToastUtil.debugShow("收到推送消息: 设置自动旋转"); + setRotationLock(context, extras); break; case JIGUANG_WIFI_SET: break; @@ -463,17 +488,83 @@ public class MyJPushReceiver extends BroadcastReceiver { case JIGUANG_KILL_APP: Utils.killBackgroundApp(context); break; + case JIGUANG_SOS_PHONENUM: + setSOSPhoneNumber(context, extras); + break; + case JIGUANG_REINSTALL_APP: + reinstallApp(context, extras); + break; } } + private void setZenMode(Context context, String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + int setting_disturbance = jsonObject.getInteger("setting_disturbance"); + + } + + private void setRotationLock(Context context, String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + int setting_rotation = jsonObject.getInteger("setting_rotation"); + RotationPolicy.setRotationLock(context, setting_rotation == 0); + } + + private void setScreenBrightness(Context context, String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + int setting_luminance = jsonObject.getInteger("setting_luminance"); + Settings.System.putInt(context.getContentResolver(), Settings.System.SCREEN_BRIGHTNESS_MODE, Settings.System.SCREEN_BRIGHTNESS_MODE_MANUAL); + int Scrern_brightness = (int) ((1.0 * 255 / 100) * setting_luminance); + Settings.System.putInt(context.getContentResolver(), Settings.System.SCREEN_BRIGHTNESS, Scrern_brightness); + } + + private float[] mValues; + /** + * Index of the entry corresponding to current value of the settings. + */ + protected int mCurrentIndex; + /** + * List of entries corresponding the settings being set. + */ + protected List mEntries; + + private void setFontSize(Context context, String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + String setting_typeface = jsonObject.getString("setting_typeface"); + final Resources res = context.getResources(); + mEntries = Arrays.asList(res.getStringArray(R.array.entries_font_size)); + final String[] strEntryValues = res.getStringArray(R.array.entryvalues_font_size); + mValues = new float[strEntryValues.length]; + for (int i = 0; i < strEntryValues.length; ++i) { + mValues[i] = Float.parseFloat(strEntryValues[i]); + } + mCurrentIndex = mEntries.indexOf(setting_typeface); + if (mCurrentIndex == -1) { + return; + } + Settings.System.putFloat(context.getContentResolver(), Settings.System.FONT_SCALE, mValues[mCurrentIndex]); + } + + private void setVolume(Context context, String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + int setting_volume = jsonObject.getInteger("setting_volume"); + //获取系统的Audio管理者 + AudioManager mAudioManager = (AudioManager) context.getSystemService(Context.AUDIO_SERVICE); + //最大音量 + int maxVolume = mAudioManager.getStreamMaxVolume(AudioManager.STREAM_MUSIC); + //当前音量 +// int currentVolume = mAudioManager.getStreamVolume(AudioManager.STREAM_MUSIC); + int currentVolume = (int) ((1.0f * maxVolume / 100) * setting_volume); + mAudioManager.setStreamVolume(AudioManager.STREAM_MUSIC, currentVolume, 0); + } + private int changeNum(int paramInt) { return paramInt == 1 ? 0 : 1; } synchronized private void sendStartTime(Context context, String jsonString) { HTTPInterface.updateAdminInfo(context); -// HTTPInterface.sendRunningApp(context); + HTTPInterface.sendRunningApp(context); HTTPInterface.sendAppUsed(context); if (JGYUtils.getInstance().isScreenOn()) { HTTPInterface.screenshot(context); @@ -855,23 +946,24 @@ public class MyJPushReceiver extends BroadcastReceiver { if (!file.exists()) { throw new FileNotFoundException(filePath); } - Bitmap bitmap = BitmapFactory.decodeFile(filePath); - if (bitmap.getWidth() < bitmap.getHeight()) { - bitmap = ImageUtils.rotate(bitmap, -90, bitmap.getWidth(), bitmap.getHeight()); - } - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - bitmap.compress(Bitmap.CompressFormat.JPEG, 100, baos); - file.createNewFile(); - FileOutputStream fos = new FileOutputStream(file); - InputStream is = new ByteArrayInputStream(baos.toByteArray()); - int x; - byte[] b = new byte[1024 * 100]; - while ((x = is.read(b)) != -1) { - fos.write(b, 0, x); - } - fos.close(); - RequestBody requestFile = RequestBody.create(MediaType.parse("multipart/form-data"), file); - MultipartBody.Part body = MultipartBody.Part.createFormData("file", file.getName(), requestFile); +// Bitmap bitmap = BitmapFactory.decodeFile(filePath); +// if (bitmap.getWidth() < bitmap.getHeight()) { +// bitmap = ImageUtils.rotate(bitmap, -90, bitmap.getWidth(), bitmap.getHeight()); +// } +// ByteArrayOutputStream baos = new ByteArrayOutputStream(); +// bitmap.compress(Bitmap.CompressFormat.JPEG, 100, baos); +// file.createNewFile(); +// FileOutputStream fos = new FileOutputStream(file); +// InputStream is = new ByteArrayInputStream(baos.toByteArray()); +// int x; +// byte[] b = new byte[1024 * 100]; +// while ((x = is.read(b)) != -1) { +// fos.write(b, 0, x); +// } +// fos.close(); + MediaType mediaType = MediaType.Companion.parse("image/png"); + RequestBody requestBody = RequestBody.Companion.create(file, mediaType); + MultipartBody.Part body = MultipartBody.Part.createFormData("file", file.getName(), requestBody); return getSendFile(filePath, body); } }).subscribeOn(Schedulers.io()) @@ -900,90 +992,6 @@ public class MyJPushReceiver extends BroadcastReceiver { }); } -// public void doscreenshot(final Context context) { -// final long time = System.currentTimeMillis(); -// Observable.create(new ObservableOnSubscribe() { -// @Override -// public void subscribe(ObservableEmitter e) throws Exception { -// String filepath = context.getExternalFilesDir("db").getAbsolutePath(); -// int n = CmdUtil.execute("screencap -p " + filepath + File.separator + time + ".png").code; -// e.onNext(n); -// } -// }).subscribeOn(Schedulers.io()) -// .observeOn(AndroidSchedulers.mainThread()) -// .subscribe(new Observer() { -// @Override -// public void onSubscribe(Disposable d) { -// -// } -// -// @Override -// public void onNext(Integer integer) { -// if (integer == 0) { -// uplaodImage(context, time); -// } else { -// Log.e("doss", "失败"); -// } -// } -// -// @Override -// public void onError(Throwable e) { -// Log.e("doss", "Throwable=" + e.getMessage()); -// } -// -// @Override -// public void onComplete() { -// -// } -// }); -// } - - private void uplaodImage(final Context context, long time) { - String filepath = context.getExternalFilesDir("db").getAbsolutePath(); -// String filepath = mContext.getFileStreamPath("screenshot").getAbsolutePath(); - //放在app内部data下面 - File file = new File(filepath + File.separator + time + ".png"); - //不要直接使用常用图片格式 - if (!file.exists()) { - Log.e("uplaodImage", "File does not exists"); - return; - } - RequestBody requestFile = RequestBody.create(MediaType.parse("multipart/form-data"), file); - MultipartBody.Part body = MultipartBody.Part.createFormData("file", file.getName(), requestFile); - NetInterfaceManager.getInstance() - .getUploadScreenshotControl() - .uploadScreenshot(Utils.getSerial(), body) - .subscribeOn(Schedulers.io()) - .observeOn(AndroidSchedulers.mainThread()) - .subscribe(new Observer() { - @Override - public void onSubscribe(Disposable d) { - - } - - @Override - public void onNext(BaseResponse baseResponse) { - int code = baseResponse.code; - if (code == 200) { - Log.e(TAG, "onNext: " + baseResponse.msg); - } else { - Log.e(TAG, code + ": " + baseResponse.msg); - } - } - - @Override - public void onError(Throwable e) { - Log.e("uplaod", "onError: " + e.getMessage()); - } - - @Override - public void onComplete() { - - } - }); - - } - /** * 实时获取电量 */ @@ -1117,4 +1125,19 @@ public class MyJPushReceiver extends BroadcastReceiver { context.sendBroadcast(bootIntent); } + private void setSOSPhoneNumber(Context context, String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + String setting_sos = jsonObject.getString("setting_sos"); + Settings.System.putString(context.getContentResolver(), "setting_sos", setting_sos); + Intent intent = new Intent("setting_sos"); + intent.putExtra("setting_sos", setting_sos); + intent.setPackage("com.uiui.os"); + context.sendBroadcast(intent); + } + + private void reinstallApp(Context context, String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + String packages = jsonObject.getString("package"); + String app_url = jsonObject.getString("app_url"); + } } diff --git a/app/src/main/java/com/uiui/sn/service/MainService.java b/app/src/main/java/com/uiui/sn/service/MainService.java index 7c7d4a3..695f86e 100644 --- a/app/src/main/java/com/uiui/sn/service/MainService.java +++ b/app/src/main/java/com/uiui/sn/service/MainService.java @@ -130,7 +130,7 @@ public class MainService extends Service implements MainContact.MainView, Networ mPresenter.initAmap(); mPresenter.getUserInfo(); HTTPInterface.sendAppUsed(MainService.this); -// HTTPInterface.sendRunningApp(MainService.this); + HTTPInterface.sendRunningApp(MainService.this); HTTPInterface.getAPPinfo(MainService.this); startService(); mPresenter.setAlias(); diff --git a/app/src/main/java/com/uiui/sn/service/ManagerService.java b/app/src/main/java/com/uiui/sn/service/ManagerService.java index f3915f3..cf3b8b2 100644 --- a/app/src/main/java/com/uiui/sn/service/ManagerService.java +++ b/app/src/main/java/com/uiui/sn/service/ManagerService.java @@ -98,9 +98,11 @@ public class ManagerService extends Service implements NetworkUtils.OnNetworkSta public void onNext(Long aLong) { Log.e("TimeObserver", "onNext: " + aLong); Handler.getMain().postDelayed(() -> HTTPInterface.checkUpdate(ManagerService.this), 1234); - Handler.getMain().postDelayed(() -> HTTPInterface.checkUpdate(ManagerService.this, "com.uiui.appstore"), 3456); - Handler.getMain().postDelayed(() -> HTTPInterface.checkUpdate(ManagerService.this, "com.uiui.browser"), 5678); - Handler.getMain().postDelayed(() -> HTTPInterface.checkUpdate(ManagerService.this, "com.uiui.os"), 6789); + Handler.getMain().postDelayed(() -> HTTPInterface.checkUpdate(ManagerService.this, "com.uiui.appstore"), 2345); + Handler.getMain().postDelayed(() -> HTTPInterface.checkUpdate(ManagerService.this, "com.uiui.browser"), 3456); + Handler.getMain().postDelayed(() -> HTTPInterface.checkUpdate(ManagerService.this, "com.uiui.os"), 5678); + Handler.getMain().postDelayed(() -> HTTPInterface.checkUpdate(ManagerService.this, "com.uiui.videoplayer"), 6789); + } @Override diff --git a/app/src/main/java/com/uiui/sn/utils/ApkUtils.java b/app/src/main/java/com/uiui/sn/utils/ApkUtils.java index 8320eab..b732fa4 100644 --- a/app/src/main/java/com/uiui/sn/utils/ApkUtils.java +++ b/app/src/main/java/com/uiui/sn/utils/ApkUtils.java @@ -56,6 +56,7 @@ public class ApkUtils { /** * 获取第三方应用 + * * @param context * @return */ @@ -749,32 +750,15 @@ public class ApkUtils { @SuppressLint("NewApi") public static void writeAppPackageList(Context context, String result) { addShortcut(context);//开机之后添加图标到桌面 - - HashSet factoryAppList = new HashSet() {{ - this.add("com.jiaoguanyi.appstore"); - this.add("com.jiaoguanyi.store"); - this.add("com.uiui.sn"); - this.add("com.appstore.uiui"); - this.add("com.uiui.appstore"); - this.add("com.android.uiuios"); - this.add("com.uiuios.jgy1"); - this.add("com.uiuios.jgy2"); - this.add("com.tt.ttutils"); - this.add("com.info.chat"); - this.add("com.info.learning"); - this.add("com.uiui.browser"); - this.add("com.uiui.os"); - this.add("com.alarmclock.uiui"); - }}; - HashSet factoryAppSet = new HashSet<>(factoryAppList); + HashSet factoryAppList = JGYUtils.getInstance().getOwnApp(); if (!TextUtils.isEmpty(result)) { HashSet writeAppSet = new HashSet<>(Arrays.asList(result.split(","))); - writeAppSet.addAll(factoryAppSet); + writeAppSet.addAll(factoryAppList); String pkgString = String.join(",", writeAppSet); Log.e("fht", "qch_app_forbid :" + pkgString); boolean qch_app_forbid = JGYUtils.putString(context.getContentResolver(), "qch_app_forbid", pkgString); } else { - JGYUtils.putString(context.getContentResolver(), "qch_app_forbid", String.join(",", factoryAppSet)); + JGYUtils.putString(context.getContentResolver(), "qch_app_forbid", String.join(",", factoryAppList)); Log.e("fht", "writeAppPackageList is null:"); } Utils.writeDisableUpdateList(context); diff --git a/app/src/main/java/com/uiui/sn/utils/AppUsedTimeUtils.java b/app/src/main/java/com/uiui/sn/utils/AppUsedTimeUtils.java new file mode 100644 index 0000000..2d57c44 --- /dev/null +++ b/app/src/main/java/com/uiui/sn/utils/AppUsedTimeUtils.java @@ -0,0 +1,120 @@ +package com.uiui.sn.utils; + +import android.annotation.SuppressLint; +import android.content.Context; +import android.provider.Settings; +import android.text.TextUtils; +import android.util.Log; + +import androidx.annotation.NonNull; + +import com.google.gson.Gson; +import com.google.gson.JsonParser; +import com.google.gson.reflect.TypeToken; + +import java.io.Serializable; +import java.lang.reflect.Type; +import java.text.ParseException; +import java.text.SimpleDateFormat; +import java.util.Date; +import java.util.List; + +public class AppUsedTimeUtils { + private static final String TAG = AppUsedTimeUtils.class.getSimpleName(); + + @SuppressLint("StaticFieldLeak") + private static AppUsedTimeUtils sInstance; + private Context mContext; + + private AppTimeinfo appTimeinfo; + + private AppUsedTimeUtils(Context context) { + this.mContext = context; + appTimeinfo = getAppTimeinfo(); + } + + public static void init(Context context) { + if (sInstance == null) { + sInstance = new AppUsedTimeUtils(context); + } + } + + public static AppUsedTimeUtils getInstance() { + if (sInstance == null) { + throw new IllegalStateException("You must be init TimeUtils first"); + } + return sInstance; + } + + static class AppTimeinfo implements Serializable { + private static final long serialVersionUID = 5373751133823666192L; + + AppTimeinfo() { + this.appPackageName = ""; + this.endTime = 0; + this.startTime = 0; + } + + private String appPackageName; + private long endTime; + private long startTime; + + public String getAppPackageName() { + return appPackageName; + } + + public void setAppPackageName(String appPackageName) { + this.appPackageName = appPackageName; + } + + public long getEndTime() { + return endTime; + } + + public void setEndTime(long endTime) { + this.endTime = endTime; + } + + public long getStartTime() { + return startTime; + } + + public void setStartTime(long startTime) { + this.startTime = startTime; + } + + @NonNull + @Override + public String toString() { + return JsonParser.parseString(new Gson().toJson(this)).getAsJsonObject().toString(); + } + } + + synchronized public String getAppPackageName() { + appTimeinfo = getAppTimeinfo(); + return appTimeinfo.getAppPackageName(); + } + + synchronized public long getStartTime() { + appTimeinfo = getAppTimeinfo(); + return appTimeinfo.getStartTime(); + } + + synchronized public long getEndTime() { + appTimeinfo = getAppTimeinfo(); + return appTimeinfo.getEndTime(); + } + + synchronized private AppTimeinfo getAppTimeinfo() { + String jsonString = Settings.System.getString(mContext.getContentResolver(), "runningAppInfo"); + if (TextUtils.isEmpty(jsonString)) { + return new AppTimeinfo(); + } + Log.e(TAG, "getAppTimeinfo: " + jsonString); + Type type = new TypeToken() { + }.getType(); + Gson gson = new Gson(); + AppTimeinfo appTimeinfo = gson.fromJson(jsonString, type); + return appTimeinfo; + } +} diff --git a/app/src/main/java/com/uiui/sn/utils/AudioMngHelper.java b/app/src/main/java/com/uiui/sn/utils/AudioMngHelper.java new file mode 100644 index 0000000..4c8b85a --- /dev/null +++ b/app/src/main/java/com/uiui/sn/utils/AudioMngHelper.java @@ -0,0 +1,168 @@ +package com.uiui.sn.utils; + + +import android.content.Context; +import android.media.AudioManager; + +import androidx.annotation.IntDef; + +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; + +/** + *
+ *     author: Chestnut
+ *     blog  : http://www.jianshu.com/u/a0206b5f4526
+ *     time  : 2017/6/17 16:11
+ *     desc  :  集成音量控制
+ *     thanks To:   http://blog.csdn.net/hufeng882412/article/details/7310131
+ *     dependent on:
+ *     update log:
+ * 
+ */ + +public class AudioMngHelper { + + private final String TAG = "AudioMngHelper"; + private final boolean OpenLog = true; + + private AudioManager audioManager; + private int NOW_AUDIO_TYPE = TYPE_MUSIC; + private int NOW_FLAG = FLAG_NOTHING; + private int VOICE_STEP_100 = 2; //0-100的步进。 + + /** + * 封装:STREAM_类型 + */ + public final static int TYPE_MUSIC = AudioManager.STREAM_MUSIC; + public final static int TYPE_ALARM = AudioManager.STREAM_ALARM; + public final static int TYPE_RING = AudioManager.STREAM_RING; + + @IntDef({TYPE_MUSIC, TYPE_ALARM, TYPE_RING}) + @Retention(RetentionPolicy.SOURCE) + public @interface TYPE { + } + + /** + * 封装:FLAG + */ + public final static int FLAG_SHOW_UI = AudioManager.FLAG_SHOW_UI; + public final static int FLAG_PLAY_SOUND = AudioManager.FLAG_PLAY_SOUND; + public final static int FLAG_NOTHING = 0; + + @IntDef({FLAG_SHOW_UI, FLAG_PLAY_SOUND, FLAG_NOTHING}) + @Retention(RetentionPolicy.SOURCE) + public @interface FLAG { + } + + /** + * 初始化,获取音量管理者 + * + * @param context 上下文 + */ + public AudioMngHelper(Context context) { + audioManager = (AudioManager) context.getSystemService(Context.AUDIO_SERVICE); + } + + public int getSystemMaxVolume() { + return audioManager.getStreamMaxVolume(NOW_AUDIO_TYPE); + } + + public int getSystemCurrentVolume() { + return audioManager.getStreamVolume(NOW_AUDIO_TYPE); + } + + /** + * 以0-100为范围,获取当前的音量值 + * + * @return 获取当前的音量值 + */ + public int get100CurrentVolume() { + return 100 * getSystemCurrentVolume() / getSystemMaxVolume(); + } + + /** + * 修改步进值 + * + * @param step step + * @return this + */ + public AudioMngHelper setVoiceStep100(int step) { + VOICE_STEP_100 = step; + return this; + } + + /** + * 改变当前的模式,对全局API生效 + * + * @param type + * @return + */ + public AudioMngHelper setAudioType(@TYPE int type) { + NOW_AUDIO_TYPE = type; + return this; + } + + /** + * 改变当前FLAG,对全局API生效 + * + * @param flag + * @return + */ + public AudioMngHelper setFlag(@FLAG int flag) { + NOW_FLAG = flag; + return this; + } + + public AudioMngHelper addVoiceSystem() { + audioManager.adjustStreamVolume(NOW_AUDIO_TYPE, AudioManager.ADJUST_RAISE, NOW_FLAG); + return this; + } + + public AudioMngHelper subVoiceSystem() { + audioManager.adjustStreamVolume(NOW_AUDIO_TYPE, AudioManager.ADJUST_LOWER, NOW_FLAG); + return this; + } + + /** + * 调整音量,自定义 + * + * @param num 0-100 + * @return 改完后的音量值 + */ + public int setVoice100(int num) { + int a = (int) Math.ceil((num) * getSystemMaxVolume() * 0.01); + a = a <= 0 ? 0 : a; + a = a >= 100 ? 100 : a; + audioManager.setStreamVolume(NOW_AUDIO_TYPE, a, 0); + return get100CurrentVolume(); + } + + /** + * 步进加,步进值可修改 + * 0——100 + * + * @return 改完后的音量值 + */ + public int addVoice100() { + int a = (int) Math.ceil((VOICE_STEP_100 + get100CurrentVolume()) * getSystemMaxVolume() * 0.01); + a = a <= 0 ? 0 : a; + a = a >= 100 ? 100 : a; + audioManager.setStreamVolume(NOW_AUDIO_TYPE, a, NOW_FLAG); + return get100CurrentVolume(); + } + + /** + * 步进减,步进值可修改 + * 0——100 + * + * @return 改完后的音量值 + */ + public int subVoice100() { + int a = (int) Math.floor((get100CurrentVolume() - VOICE_STEP_100) * getSystemMaxVolume() * 0.01); + a = a <= 0 ? 0 : a; + a = a >= 100 ? 100 : a; + audioManager.setStreamVolume(NOW_AUDIO_TYPE, a, NOW_FLAG); + return get100CurrentVolume(); + } +} diff --git a/app/src/main/java/com/uiui/sn/utils/JGYUtils.java b/app/src/main/java/com/uiui/sn/utils/JGYUtils.java index 08ba586..949d11f 100644 --- a/app/src/main/java/com/uiui/sn/utils/JGYUtils.java +++ b/app/src/main/java/com/uiui/sn/utils/JGYUtils.java @@ -4,6 +4,7 @@ import android.annotation.SuppressLint; import android.app.ActivityManager; import android.app.ActivityManagerNative; import android.app.ActivityTaskManager; +import android.app.NotificationManager; import android.content.ComponentName; import android.content.ContentResolver; import android.content.Context; @@ -13,6 +14,8 @@ import android.content.IntentFilter; import android.content.pm.ApplicationInfo; import android.content.pm.PackageManager; import android.content.pm.UserInfo; +import android.content.res.Resources; +import android.media.AudioManager; import android.net.ConnectivityManager; import android.net.NetworkInfo; import android.net.Uri; @@ -27,8 +30,11 @@ import android.util.Log; import androidx.core.content.ContextCompat; +import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSONObject; +import com.android.internal.view.RotationPolicy; import com.uiui.sn.BuildConfig; +import com.uiui.sn.R; import java.io.File; import java.lang.reflect.Constructor; @@ -51,15 +57,43 @@ public class JGYUtils { @SuppressLint("StaticFieldLeak") private static JGYUtils sInstance; private Context mContext; + private ContentResolver resolver; public static int MTKPlatform = 1; public static int ZhanruiPlatform = 2; public static int UnknowPlatform = 0; public static String MTKTag = "MTK"; public static String ZhanruiTag = "展锐"; + HashSet ownApp = new HashSet() {{ + this.add("com.tt.ttutils"); + this.add(BuildConfig.APPLICATION_ID); + this.add("com.appstore.uiui"); + this.add("com.alarmclock.uiui"); + this.add("com.android.uiuios"); + this.add("com.aoleyun.os"); + this.add("com.jiaoguanyi.appstore"); + this.add("com.jiaoguanyi.store"); + this.add("com.uiui.appstore"); + this.add("com.uiui.browser"); + this.add("com.uiui.os"); + this.add("com.uiui.sn"); + this.add("com.uiui.videoplayer"); + this.add("com.uiuios.jgy1"); + this.add("com.uiuios.jgy2"); + this.add("com.info.chat"); + this.add("com.info.learning"); + }}; + + public HashSet getOwnApp() { + return ownApp; + } private JGYUtils(Context context) { + if (context == null) { + throw new RuntimeException("Context is NULL"); + } this.mContext = context; + this.resolver = mContext.getContentResolver(); } public static void init(Context context) { @@ -187,33 +221,33 @@ public class JGYUtils { } - String olddeselectViewArray = JGYUtils.getString(mContext.getContentResolver(), "qch_app_forbid_id"); + String olddeselectViewArray = JGYUtils.getString(resolver, "qch_app_forbid_id"); Log.e("writeDeselectIDtoSystem", "olddeselectViewArray: " + olddeselectViewArray); - JGYUtils.putString(mContext.getContentResolver(), "qch_app_forbid_id", packageStringBuilder.toString()); - JGYUtils.putString(mContext.getContentResolver(), "DeselectViewArray", idStringBuilder.toString()); + JGYUtils.putString(resolver, "qch_app_forbid_id", packageStringBuilder.toString()); + JGYUtils.putString(resolver, "DeselectViewArray", idStringBuilder.toString()); Log.e("writeDeselectIDtoSystem", "qch_app_forbid_id: " + packageStringBuilder.toString()); Log.e("writeDeselectIDtoSystem", "deselectViewArray: " + idStringBuilder.toString()); } else { Log.e("writeDeselectIDtoSystem", "writeDeselectIDtoSystem is null:"); - JGYUtils.putString(mContext.getContentResolver(), "qch_app_forbid_id", " "); - JGYUtils.putString(mContext.getContentResolver(), "DeselectViewArray", " "); + JGYUtils.putString(resolver, "qch_app_forbid_id", " "); + JGYUtils.putString(resolver, "DeselectViewArray", " "); } } - private static void sendAllweb(Context context) { + private void sendAllweb() { Intent intent = new Intent("qch_app_website") .setPackage("com.android.settings"); intent.putExtra("package_name", "Invalid"); - context.sendBroadcast(intent); + mContext.sendBroadcast(intent); } - private static void sendwebUrl(Context context) { + private void sendwebUrl() { Intent intent = new Intent("qch_app_inside_website") .setPackage("com.android.settings"); intent.putExtra("websitelist", "Invalid"); - context.sendBroadcast(intent); + mContext.sendBroadcast(intent); } /** @@ -279,16 +313,16 @@ public class JGYUtils { /** * 忽略电池优化 */ - private void ignoreBatteryOptimization(Context context) { + private void ignoreBatteryOptimization() { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { PowerManager powerManager = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE); - boolean hasIgnored = powerManager.isIgnoringBatteryOptimizations(context.getPackageName()); + boolean hasIgnored = powerManager.isIgnoringBatteryOptimizations(mContext.getPackageName()); // 判断当前APP是否有加入电池优化的白名单,如果没有,弹出加入电池优化的白名单的设置对话框。 if (!hasIgnored) { Intent intent = new Intent(Settings.ACTION_REQUEST_IGNORE_BATTERY_OPTIMIZATIONS); - intent.setData(Uri.parse("package:" + context.getPackageName())); + intent.setData(Uri.parse("package:" + mContext.getPackageName())); intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); mContext.startActivity(intent); } @@ -428,11 +462,11 @@ public class JGYUtils { } } - public void killBackgroundProcesses(Context context, String processName) { + public void killBackgroundProcesses(String processName) { gotoLauncher(); // mIsScanning = true; removeTask(processName); - ActivityManager activityManager = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE); + ActivityManager activityManager = (ActivityManager) mContext.getSystemService(Context.ACTIVITY_SERVICE); String packageName = null; try { if (processName.indexOf(":") == -1) { @@ -454,7 +488,7 @@ public class JGYUtils { /** * 清除所有最近记录 */ - public void removeAllTask(Context context) { + public void removeAllTask() { List list = getRecentTasks(ActivityManager.getMaxRecentTasksStatic(), getCurrentUserId()); for (ActivityManager.RecentTaskInfo info : list) { @@ -529,9 +563,9 @@ public class JGYUtils { } } - public static int isWifiConnect(Context context) { + public int isWifiConnect() { // 网络管理对象 - ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE); + ConnectivityManager cm = (ConnectivityManager) mContext.getSystemService(Context.CONNECTIVITY_SERVICE); // 获取所有类型的链接管理对象 NetworkInfo info = cm.getNetworkInfo(ConnectivityManager.TYPE_WIFI); NetworkInfo.State state = info.getState(); @@ -569,10 +603,10 @@ public class JGYUtils { /** * 获取当前进程名 */ - public static String getCurrentProcessName(Context context) { + public String getCurrentProcessName() { int pid = android.os.Process.myPid(); String processName = ""; - ActivityManager manager = (ActivityManager) context.getSystemService + ActivityManager manager = (ActivityManager) mContext.getSystemService (Context.ACTIVITY_SERVICE); for (ActivityManager.RunningAppProcessInfo process : manager.getRunningAppProcesses()) { if (process.pid == pid) { @@ -599,26 +633,26 @@ public class JGYUtils { if (search_topic == 0) { disableApp.add("拍照搜题"); } - if (JGYUtils.getInt(mContext.getContentResolver(), "qch_app_camera", 0) == 1) { + if (JGYUtils.getInt(resolver, "qch_app_camera", 0) == 1) { disableApp.add("com.mediatek.camera"); } - if (JGYUtils.getInt(mContext.getContentResolver(), "qch_app_filemanager", 0) == 1) { + if (JGYUtils.getInt(resolver, "qch_app_filemanager", 0) == 1) { disableApp.add("com.android.documentsui"); disableApp.add("com.mediatek.filemanager"); } - if (JGYUtils.getInt(mContext.getContentResolver(), "qch_app_deskclock", 0) == 1) { + if (JGYUtils.getInt(resolver, "qch_app_deskclock", 0) == 1) { disableApp.add("com.android.deskclock"); } - if (JGYUtils.getInt(mContext.getContentResolver(), "qch_app_soundrecorder", 0) == 1) { + if (JGYUtils.getInt(resolver, "qch_app_soundrecorder", 0) == 1) { disableApp.add("com.android.soundrecorder"); } - if (JGYUtils.getInt(mContext.getContentResolver(), "qch_app_gallery", 0) == 1) { + if (JGYUtils.getInt(resolver, "qch_app_gallery", 0) == 1) { disableApp.add("com.android.gallery3d"); } - if (JGYUtils.getInt(mContext.getContentResolver(), "qch_app_music", 0) == 1) { + if (JGYUtils.getInt(resolver, "qch_app_music", 0) == 1) { disableApp.add("com.android.music"); } - if (JGYUtils.getInt(mContext.getContentResolver(), "qch_app_browser", 0) == 1) { + if (JGYUtils.getInt(resolver, "qch_app_browser", 0) == 1) { disableApp.add("com.android.browser"); } Log.e(TAG, "getForbidAPP: " + disableApp); @@ -664,21 +698,21 @@ public class JGYUtils { public final static String ACTION_HrReceiver_JGY_DIS = "qch_jgy_network_disallow"; @SuppressLint("NewApi") - synchronized public static void setAppNetwork(Context context, HashSet blackList) { + synchronized public void setAppNetwork(HashSet blackList) { Log.e(TAG, "setAppNetwork: " + "设置应用联网管控" + blackList); - String dis = Settings.System.getString(context.getContentResolver(), ACTION_HrReceiver_JGY_DIS); - String not = Settings.System.getString(context.getContentResolver(), ACTION_HrReceiver_JGY); + String dis = Settings.System.getString(resolver, ACTION_HrReceiver_JGY_DIS); + String not = Settings.System.getString(resolver, ACTION_HrReceiver_JGY); //清除旧数据 if (!TextUtils.isEmpty(dis)) { Log.e(TAG, "setAppNetwork: dis = " + dis); - Settings.System.putString(context.getContentResolver(), ACTION_HrReceiver_JGY_DIS, "Invalid"); + Settings.System.putString(resolver, ACTION_HrReceiver_JGY_DIS, "Invalid"); } if (!TextUtils.isEmpty(not)) { Log.e(TAG, "setAppNetwork: not = " + not); - Settings.System.putString(context.getContentResolver(), ACTION_HrReceiver_JGY, "Invalid"); + Settings.System.putString(resolver, ACTION_HrReceiver_JGY, "Invalid"); } - String oldBlackList = (String) SPUtils.get(context, ACTION_HrReceiver_JGY_DIS, ""); + String oldBlackList = (String) SPUtils.get(mContext, ACTION_HrReceiver_JGY_DIS, ""); HashSet oldBlackListSet = new HashSet<>(Arrays.asList(oldBlackList.split(","))); //去空 oldBlackListSet.removeIf(s -> TextUtils.isEmpty(s.trim())); @@ -689,7 +723,7 @@ public class JGYUtils { for (String pkg : blackList) { if (TextUtils.isEmpty(pkg)) continue; //发送没有安装的 - if (!ApkUtils.isAvailable(context, pkg)) { + if (!ApkUtils.isAvailable(mContext, pkg)) { Log.e(TAG, "setAppNetwork: skip: " + pkg); continue; } else { @@ -698,7 +732,7 @@ public class JGYUtils { Intent netControlNotIntent = new Intent(ACTION_HrReceiver_JGY_DIS); netControlNotIntent.putExtra("package_name", pkg); netControlNotIntent.setPackage("com.android.settings"); - context.sendBroadcast(netControlNotIntent); + mContext.sendBroadcast(netControlNotIntent); } } else { //减少的 @@ -721,11 +755,11 @@ public class JGYUtils { Intent netControlNotIntent = new Intent(ACTION_HrReceiver_JGY); netControlNotIntent.putExtra("package_name", pkg); netControlNotIntent.setPackage("com.android.settings"); - context.sendBroadcast(netControlNotIntent); + mContext.sendBroadcast(netControlNotIntent); } for (String pkg : addedNet) { if (TextUtils.isEmpty(pkg)) continue; - if (!ApkUtils.isAvailable(context, pkg)) { + if (!ApkUtils.isAvailable(mContext, pkg)) { Log.e(TAG, "setAppNetwork: skip: " + pkg); continue; } else { @@ -734,13 +768,13 @@ public class JGYUtils { Intent netControlNotIntent = new Intent(ACTION_HrReceiver_JGY_DIS); netControlNotIntent.putExtra("package_name", pkg); netControlNotIntent.setPackage("com.android.settings"); - context.sendBroadcast(netControlNotIntent); + mContext.sendBroadcast(netControlNotIntent); } } String net_not = String.join(",", blackList); - SPUtils.put(context, ACTION_HrReceiver_JGY_DIS, net_not); - //Settings.System.putString(mContext.getContentResolver(), JGYActions.ACTION_HrReceiver_JGY_DIS, net_not); + SPUtils.put(mContext, ACTION_HrReceiver_JGY_DIS, net_not); + //Settings.System.putString(resolver, JGYActions.ACTION_HrReceiver_JGY_DIS, net_not); Log.e("fht", "not::" + net_not); //Intent netControlIntent = new Intent(CommonDatas.ACTION_HrReceiver_JGY_DIS); @@ -773,15 +807,15 @@ public class JGYUtils { //删除用户除了在应用市场的其他应用 public void deleteOtherApp() { - int locked = Settings.System.getInt(mContext.getContentResolver(), "qch_unlock_ipad", 0); + int locked = Settings.System.getInt(resolver, "qch_unlock_ipad", 0); if (locked == 1) { return; } Log.e(TAG, "deleteOtherApp: " + "start"); //获取后台应用白名单 - String only_jgy_shortcut_list = Settings.System.getString(mContext.getContentResolver(), "only_jgy_shortcut_list"); + String only_jgy_shortcut_list = Settings.System.getString(resolver, "only_jgy_shortcut_list"); //获取可以被安装的包名 - String qch_app_forbid = Settings.System.getString(mContext.getContentResolver(), "qch_app_forbid"); + String qch_app_forbid = Settings.System.getString(resolver, "qch_app_forbid"); Log.e("deleteOtherApp", "only_jgy_shortcut_list:" + only_jgy_shortcut_list); Log.e("deleteOtherApp", "qch_app_forbid:" + qch_app_forbid); String[] result_white = only_jgy_shortcut_list.split(","); @@ -805,8 +839,7 @@ public class JGYUtils { // if (ApkUtils.canremove_systemapp.contains(packageName)) { // continue; // } - if ("com.jiaoguanyi.appstore".equals(packageName) || "com.jiaoguanyi.store".equals(packageName) - ) { + if (ownApp.contains(packageName)) { continue; } if (!allWhitePkg.contains(packageName)) { @@ -823,4 +856,70 @@ public class JGYUtils { //true为打开,false为关闭 return powerManager.isInteractive(); } + + private int zenModOn = Settings.Global.ZEN_MODE_IMPORTANT_INTERRUPTIONS; + private int zenModOff = Settings.Global.ZEN_MODE_OFF; + private String ZENNODETAG = "ZenModeSettingsBackend"; + + public void setZenMode(String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + int setting_disturbance = jsonObject.getInteger("setting_disturbance"); + NotificationManager.from(mContext).setZenMode(setting_disturbance, null, ZENNODETAG); + } + + public void setRotationLock(String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + int setting_rotation = jsonObject.getInteger("setting_rotation"); + RotationPolicy.setRotationLock(mContext, setting_rotation == 0); + } + + public void setScreenBrightness(String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + int setting_luminance = jsonObject.getInteger("setting_luminance"); + Settings.System.putInt(resolver, Settings.System.SCREEN_BRIGHTNESS_MODE, Settings.System.SCREEN_BRIGHTNESS_MODE_MANUAL); + int Scrern_brightness = (int) ((1.0 * 255 / 100) * setting_luminance); + Settings.System.putInt(resolver, Settings.System.SCREEN_BRIGHTNESS, Scrern_brightness); + } + + private float[] mValues; + /** + * Index of the entry corresponding to current value of the settings. + */ + protected int mCurrentIndex; + /** + * List of entries corresponding the settings being set. + */ + protected List mEntries; + + public void setFontSize(String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + String setting_typeface = jsonObject.getString("setting_typeface"); + final Resources res = mContext.getResources(); + mEntries = Arrays.asList(res.getStringArray(R.array.entries_font_size)); + final String[] strEntryValues = res.getStringArray(R.array.entryvalues_font_size); + mValues = new float[strEntryValues.length]; + for (int i = 0; i < strEntryValues.length; ++i) { + mValues[i] = Float.parseFloat(strEntryValues[i]); + } + mCurrentIndex = mEntries.indexOf(setting_typeface); + if (mCurrentIndex == -1) { + return; + } + Settings.System.putFloat(resolver, Settings.System.FONT_SCALE, mValues[mCurrentIndex]); + } + + public void setVolume(String extras) { + JSONObject jsonObject = JSON.parseObject(extras); + int setting_volume = jsonObject.getInteger("setting_volume"); + //获取系统的Audio管理者 + AudioManager mAudioManager = (AudioManager) mContext.getSystemService(Context.AUDIO_SERVICE); + //最大音量 + int maxVolume = mAudioManager.getStreamMaxVolume(AudioManager.STREAM_MUSIC); + //当前音量 +// int currentVolume = mAudioManager.getStreamVolume(AudioManager.STREAM_MUSIC); + int currentVolume = (int) ((1.0f * maxVolume / 100) * setting_volume); + mAudioManager.setStreamVolume(AudioManager.STREAM_MUSIC, currentVolume, 0); + } + + } diff --git a/app/src/main/java/com/uiui/sn/utils/Utils.java b/app/src/main/java/com/uiui/sn/utils/Utils.java index b425fe3..eb0ccbd 100644 --- a/app/src/main/java/com/uiui/sn/utils/Utils.java +++ b/app/src/main/java/com/uiui/sn/utils/Utils.java @@ -1101,7 +1101,8 @@ public class Utils { Log.e(TAG, "getUse_space: blockSize = " + blockSize); long totalBlocks = sf.getBlockCount(); Log.e(TAG, "getUse_space: totalBlocks = " + totalBlocks); - return (float) 1.0 * availableSize / (blockSize * totalBlocks); + + return (float) 100.0 * ((blockSize * totalBlocks) - availableSize) / (blockSize * totalBlocks); } public static String getRemnantSize(Context context) { @@ -1189,7 +1190,7 @@ public class Utils { jsonObject.put("charging", charging); jsonObject.put("memory", memory); jsonObject.put("storage", storage); - jsonObject.put("is_wifi", JGYUtils.isWifiConnect(context)); + jsonObject.put("is_wifi", JGYUtils.getInstance().isWifiConnect()); jsonObject.put("CPU", CPU + "核"); jsonObject.put("use_space", use_space); jsonObject.put("use_ram", use_ram); @@ -1237,7 +1238,7 @@ public class Utils { } } - public static List runningAppWhitelist = new ArrayList() {{ + public static List runningAppWhitelist = new ArrayList() {{ this.add("com.android.launcher3"); this.add(BuildConfig.APPLICATION_ID); this.add("com.uiui.appstore"); diff --git a/app/src/main/res/mipmap-hdpi/ic_launcher.png b/app/src/main/res/mipmap-hdpi/ic_launcher.png index dbf6ba0e3d36e894b343d59ea16ee104255da1e8..9e3dd80a7cff956f4961c239218b2c6413eadd02 100644 GIT binary patch delta 3927 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 delta 3814 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 Z*R?BGjB9H1hoozNM_a=HU8`;z`F|q-9;g5S diff --git a/app/src/main/res/mipmap-mdpi/ic_launcher.png b/app/src/main/res/mipmap-mdpi/ic_launcher.png index dbf6ba0e3d36e894b343d59ea16ee104255da1e8..9e3dd80a7cff956f4961c239218b2c6413eadd02 100644 GIT binary patch delta 3927 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 delta 3814 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 Z*R?BGjB9H1hoozNM_a=HU8`;z`F|q-9;g5S diff --git a/app/src/main/res/mipmap-xhdpi/ic_launcher.png b/app/src/main/res/mipmap-xhdpi/ic_launcher.png index dbf6ba0e3d36e894b343d59ea16ee104255da1e8..9e3dd80a7cff956f4961c239218b2c6413eadd02 100644 GIT binary patch delta 3927 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 delta 3814 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 Z*R?BGjB9H1hoozNM_a=HU8`;z`F|q-9;g5S diff --git a/app/src/main/res/mipmap-xxhdpi/ic_launcher.png b/app/src/main/res/mipmap-xxhdpi/ic_launcher.png index dbf6ba0e3d36e894b343d59ea16ee104255da1e8..9e3dd80a7cff956f4961c239218b2c6413eadd02 100644 GIT binary patch delta 3927 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 delta 3814 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 Z*R?BGjB9H1hoozNM_a=HU8`;z`F|q-9;g5S diff --git a/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png b/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png index dbf6ba0e3d36e894b343d59ea16ee104255da1e8..9e3dd80a7cff956f4961c239218b2c6413eadd02 100644 GIT binary patch delta 3927 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 delta 3814 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 Z*R?BGjB9H1hoozNM_a=HU8`;z`F|q-9;g5S diff --git a/app/src/main/res/values/arrays.xml b/app/src/main/res/values/arrays.xml new file mode 100644 index 0000000..5bb210e --- /dev/null +++ b/app/src/main/res/values/arrays.xml @@ -0,0 +1,16 @@ + + + + 0.85 + 1.0 + 1.15 + 1.30 + + + "小" + "默认" + "大" + "最大" + + + \ No newline at end of file