最近在弄腾讯的开源矿建shadow,估计是时间和精力有限,其对service插件支持不是很友好,导致踩了各种坑。上面这个报错是在service插件中调用资源文件导致的问题。
代码:
mContext 是application 的context;
private static Context mContext = getApplicationContext();
initReceiver(mContext);
private void initReceiver(Context context) {
Logger.i(TAG, "initReceiver");
IntentFilter timeFilter = new IntentFilter();
timeFilter.addAction("android.net.ethernet.ETHERNET_STATE_CHANGED");
timeFilter.addAction("android.net.ethernet.STATE_CHANGE");
timeFilter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);
timeFilter.addAction("android.net.wifi.WIFI_STATE_CHANGED");
timeFilter.addAction("android.net.wifi.STATE_CHANGE");
timeFilter.addAction(WifiManager.NETWORK_STATE_CHANGED_ACTION);
context.registerReceiver(netReceiver, timeFilter);
}
BroadcastReceiver netReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
String action = intent.getAction();
Logger.i(TAG, "onReceive:" + action);
if (action.equals(ConnectivityManager.CONNECTIVITY_ACTION)) {
ConnectivityManager connectivityManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo networkInfo = connectivityManager.getActiveNetworkInfo();
if (networkInfo != null && networkInfo.isAvailable()) {
int type2 = networkInfo.getType();
isAlerted = false;
String typeName = networkInfo.getTypeName();
switch (type2) {
case 0:
case 1:
case 9:
if (type2 == 0) {
Logger.i(TAG, "MOBILE");
} else if (type2 == 1) {
Logger.i(TAG, "WIFI");
} else {
Logger.i(TAG, "ETHERNET");
}
doDismissNetworkAlert();
SystemManager.getInstance().onNetWorkOK();
break;
}
} else {
SystemManager.getInstance().onNetWorkFail();
if (!isAlerted) {
if ("com.android.settings".equals(SystemManager.getInstance().getTopApp())) {
return;
}
doNetworkAlert(context);
Logger.i(TAG, "NO NETWORK CONNECT");
}
}
}
}
};
private void doNetworkAlert(final Context context) {
mHandler.postDelayed(new Runnable() {
@Override
public void run() {
CustomDialog dialog = new CustomDialog(context);
dialog.setContentView(R.layout.custom_dialog);
Log.d("tangtang", "run: -=======================================================");
dialog.show();
}
}, 5000);
}
废话不多说直接看报错信息:
04-03 10:02:47.024 19036 19036 D AndroidRuntime: Shutting down VM
--------- beginning of crash
04-03 10:02:47.049 19036 19036 E AndroidRuntime: FATAL EXCEPTION: main
04-03 10:02:47.049 19036 19036 E AndroidRuntime: Process: com.android.vpsclient:plugin, PID: 19036
04-03 10:02:47.049 19036 19036 E AndroidRuntime: android.content.res.Resources$NotFoundException: Resource ID #0x7f09001d
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at android.content.res.ResourcesImpl.getValue(ResourcesImpl.java:190)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at android.content.res.Resources.loadXmlResourceParser(Resources.java:2094)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at android.content.res.Resources.getLayout(Resources.java:1111)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at android.view.LayoutInflater.inflate(LayoutInflater.java:424)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at com.android.vps.basic.manager.CustomDialog$Builder.<init>(CustomDialog.java:40)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at com.android.vps.basic.Receiver.NetWorkMonitorReceiver$2.run(NetWorkMonitorReceiver.java:119)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at android.os.Handler.handleCallback(Handler.java:751)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at android.os.Handler.dispatchMessage(Handler.java:95)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at android.os.Looper.loop(Looper.java:154)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at android.app.ActivityThread.main(ActivityThread.java:6077)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at java.lang.reflect.Method.invoke(Native Method)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:915)
04-03 10:02:47.049 19036 19036 E AndroidRuntime: at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:805)
实验:
排除:弹窗资源文件问题
- 尝试1:在失败的地方加载service中现有的activity中加载成功的弹窗资源文件(activity_main)---调用测试,失败
- 尝试2:在service插件中将弹窗xml文件修改成sample中的弹窗资源文件---调用测试,失败
- 尝试3:在service的MainActivity.class中调用现有service调用失败的资源文件(custom_dialog)---调用测试,成功
排除:received本身的问题
- 尝试1:在sample中的MyReceived.class文件中调用资源文件---调用测试,成功
猜测,service的类型没有去加载资源文件。
验证:activity和service中初始化received导致的区别
- 测试1:在service中启动的activity去初始化received,并点击发送广播。-----调用测试,成功
- 测试2:在测试1其他不变的情况下,将received初始化放到service中去。-----调用测试,失败
- 测试3:在测试1其他不变的情况下,将received初始化的上下文修改成application的上下文。-----调用测试,失败
结论:application上下文,获取不到资源文件。
解决方案:
将application上下文修改成activity的资源文件。