文章目录
场景-需求
实际应用场景太多了,举个例子Framework层释放动态控制底部导航栏显示和隐藏,如果客户端app设置了打开或者关闭,就需要保存一个状态。重启机器后根据保存的状态值去控制当前导航栏显示还是隐藏。
即:重启后保持关机前的状态。
分析
既然是状态的保存和获取、动态控制等方式。那么这个动作 保存和获取状态值,动态控制等操作实现需求的解决方案,可以放到Framework层去处理,也可以客户端应用App 自己去处理。
实际问题:
-
如上分析,要么Framework层处理,要么应用端处理。实际开发过程中,特别客户对接过程中,app 端开发并不擅长也不愿意做这个工作、Framework层也不愿意做这个工作。
-
其实存储相关,无论App应用层还是framework层,因为是基于Linux系统开发的,存在进程、用户空间访问的读写权限、安全隔离等。所以存储方式不同,都是基于不同方式和为了解决某些问题而存在的。
下面仅从需求的角度集合Framework层,来介绍存储和读取的相关知识。
参考资料
先通过部分资料,了解下 Settings.System, Settings.Secure和Settings.Global存储 的应用环境
Android系统APP之SettingsProvider数据库的使用介绍
Android Settings中System/Global/Secure
Android中的Settings.System, Settings.Secure和Settings.Global:区别与用途
Settings属性读写:
Android 官网 Settings.Global:
Android 官网 Settings.Secure
Android 官网 Settings.System
理解-使用 Global-Secure-System
先从概念上来理解这方面内容,
Settings.Global
Global system settings, containing preferences that always apply identically to all defined users. Applications can read these but are not allowed to write; like the "Secure" settings, these are for preferences that the user must explicitly modify through the system UI or specialized APIs for those values.
意思是对所有用户都是公开的,第三方应用没有写入权限,那么系统用它存储那些内容呢? 我们可以看官网链接、也可以看源码
再次贴一下官网位置 Settings.Global: https://developer.android.com/reference/android/provider/Settings.Global
同时也可以从源码中查看,Global 到底能存储哪些内容, 源码位置 :
看看相关存储的内容:
static {
MOVED_TO_GLOBAL = new HashSet<>();
MOVED_TO_SECURE_THEN_GLOBAL = new HashSet<>();
// these were originally in system but migrated to secure in the past,
// so are duplicated in the Secure.* namespace
MOVED_TO_SECURE_THEN_GLOBAL.add(Global.ADB_ENABLED);
MOVED_TO_SECURE_THEN_GLOBAL.add(Global.BLUETOOTH_ON);
MOVED_TO_SECURE_THEN_GLOBAL.add(Global.DATA_ROAMING);
MOVED_TO_SECURE_THEN_GLOBAL.add(Global.DEVICE_PROVISIONED);
MOVED_TO_SECURE_THEN_GLOBAL.add(Global.HTTP_PROXY);
MOVED_TO_SECURE_THEN_GLOBAL.add(Global.NETWORK_PREFERENCE);
MOVED_TO_SECURE_THEN_GLOBAL.add(Global.USB_MASS_STORAGE_ENABLED);
MOVED_TO_SECURE_THEN_GLOBAL.add(Global.WIFI_MOBILE_DATA_TRANSITION_WAKELOCK_TIMEOUT_MS);
MOVED_TO_SECURE_THEN_GLOBAL.add(Global.WIFI_MAX_DHCP_RETRY_COUNT);
// these are moving directly from system to global
MOVED_TO_GLOBAL.add(Settings.Global.AIRPLANE_MODE_ON);
MOVED_TO_GLOBAL.add(Settings.Global.AIRPLANE_MODE_RADIOS);
MOVED_TO_GLOBAL.add(Settings.Global.AIRPLANE_MODE_TOGGLEABLE_RADIOS);
MOVED_TO_GLOBAL.add(Settings.Global.AUTO_TIME);
MOVED_TO_GLOBAL.add(Settings.Global.AUTO_TIME_ZONE);
MOVED_TO_GLOBAL.add(Settings.Global.CAR_DOCK_SOUND);
MOVED_TO_GLOBAL.add(Settings.Global.CAR_UNDOCK_SOUND);
MOVED_TO_GLOBAL.add(Settings.Global.DESK_DOCK_SOUND);
MOVED_TO_GLOBAL.add(Settings.Global.DESK_UNDOCK_SOUND);
MOVED_TO_GLOBAL.add(Settings.Global.DOCK_SOUNDS_ENABLED);
MOVED_TO_GLOBAL.add(Settings.Global.LOCK_SOUND);
MOVED_TO_GLOBAL.add(Settings.Global.UNLOCK_SOUND);
MOVED_TO_GLOBAL.add(Settings.Global.LOW_BATTERY_SOUND);
MOVED_TO_GLOBAL.add(Settings.Global.POWER_SOUNDS_ENABLED);
MOVED_TO_GLOBAL.add(Settings.Global.STAY_ON_WHILE_PLUGGED_IN);
MOVED_TO_GLOBAL.add(Settings.Global.WIFI_SLEEP_POLICY);
MOVED_TO_GLOBAL.add(Settings.Global.MODE_RINGER);
MOVED_TO_GLOBAL.add(Settings.Global.WINDOW_ANIMATION_SCALE);
MOVED_TO_GLOBAL.add(Settings.Global.TRANSITION_ANIMATION_SCALE);
MOVED_TO_GLOBAL.add(Settings.Global.ANIMATOR_DURATION_SCALE);
MOVED_TO_GLOBAL.add(Settings.Global.FANCY_IME_ANIMATIONS);
MOVED_TO_GLOBAL.add(Settings.Global.COMPATIBILITY_MODE);
MOVED_TO_GLOBAL.add(Settings.Global.EMERGENCY_TONE);
MOVED_TO_GLOBAL.add(Settings.Global.CALL_AUTO_RETRY);
MOVED_TO_GLOBAL.add(Settings.Global.DEBUG_APP);
MOVED_TO_GLOBAL.add(Settings.Global.WAIT_FOR_DEBUGGER);
MOVED_TO_GLOBAL.add(Settings.Global.ALWAYS_FINISH_ACTIVITIES);
MOVED_TO_GLOBAL.add(Settings.Global.TZINFO_UPDATE_CONTENT_URL);
MOVED_TO_GLOBAL.add(Settings.Global.TZINFO_UPDATE_METADATA_URL);
MOVED_TO_GLOBAL.add(Settings.Global.SELINUX_UPDATE_CONTENT_URL);
MOVED_TO_GLOBAL.add(Settings.Global.SELINUX_UPDATE_METADATA_URL);
MOVED_TO_GLOBAL.add(Settings.Global.SMS_SHORT_CODES_UPDATE_CONTENT_URL);
MOVED_TO_GLOBAL.add(Settings.Global.SMS_SHORT_CODES_UPDATE_METADATA_URL);
MOVED_TO_GLOBAL.add(Settings.Global.CERT_PIN_UPDATE_CONTENT_URL);
MOVED_TO_GLOBAL.add(Settings.Global.CERT_PIN_UPDATE_METADATA_URL);
MOVED_TO_GLOBAL.add(Settings.Global.RADIO_NFC);
MOVED_TO_GLOBAL.add(Settings.Global.RADIO_CELL);
MOVED_TO_GLOBAL.add(Settings.Global.RADIO_WIFI);
MOVED_TO_GLOBAL.add(Settings.Global.RADIO_BLUETOOTH);
MOVED_TO_GLOBAL.add(Settings.Global.RADIO_WIMAX);
MOVED_TO_GLOBAL.add(Settings.Global.SHOW_PROCESSES);
}
代码层面读写:
//读Global 根据类型来, getLong getString
Settings.Global.getLong(context.getContentResolver(), key, defaltValue);
//写Global 根据类型来, putLong putString等
Settings.Global.putLong(mContext.getContentResolver(), key, value);
很多时候,我们为了更好的调试程序,直接通过adb 来看数据的状态
adb 对应操作
// adb读
adb shell settings get global key
// adb写
adb shell settings put global key value
// 列出所有属性值
adb shell settings list global
// 如果需要过滤,那么就过滤获取下
settings list global | grep adb_enabled
实际代码使用
上面概念上面已经介绍了如何读取及有哪些相关的属性值,我们看看实际中的使用。
设置飞行模式:
fun setAirplaneMode(context: Context, isEnabled: Boolean) {
Settings.Global.putInt(
context.contentResolver,
Settings.Global.AIRPLANE_MODE_ON,
if (isEnabled) 1 else 0
)
}
获取当前飞行模式状态
@SuppressLint("NewApi")
private fun checkAirPlan() {
val data = DeviceStateLiveData.value!!
// //飞行模式判断 0:非 飞行模式 1:飞行模式
val isAirplaneMode= Settings.Global.getInt(ContextProvider.get().context.contentResolver, Settings.Global.AIRPLANE_MODE_ON, 0) != 0
Log.d(TAG," checkAirPlan isAirplaneMode:${isAirplaneMode}")
data.isAirPlan=isAirplaneMode
}
关闭蓝牙服务:
fun disableA2dpSource() {
val contentResolver = ContextProvider.get().applicationContext.contentResolver;
val value = (1 shl 2).toLong()//1<<BluetoothProfile.A2DP
Log.i(TAG

最低0.47元/天 解锁文章
287

被折叠的 条评论
为什么被折叠?



