我是Android新手.我想知道Looper课程的作用以及如何使用它.我已阅读Android Looper类文档,但我无法完全理解它.我在很多地方都看过它但却无法理解它的目的.任何人都可以通过定义目的来帮助我,Looper并且如果可能的话也给出一个简单的例子吗?
我们在应用程序的不同部分看到了此 ANR。想了解导致此 ANR 的原因吗?
main (native): tid=1 systid=31940
#00 pc 0x5431c libc.so
#01 pc 0x1313a5 libart.so
#02 pc 0x2ab05b libart.so
#03 pc 0x3659 libnativehelper.so
#04 pc 0x9dee9 libandroid_runtime.so
#05 pc 0x65c45 libgui.so
#06 pc 0x11dcd libutils.so
#07 pc 0x11abf libutils.so
#08 pc 0xbcc7d libandroid_runtime.so
at android.os.MessageQueue.nativePollOnce(MessageQueue.java)
at android.os.MessageQueue.next(MessageQueue.java:339)
at android.os.Looper.loop(Looper.java:199)
at android.app.ActivityThread.main(ActivityThread.java:8276)
at java.lang.reflect.Method.invoke(Method.java)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:612)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1006)
Run Code Online (Sandbox Code Playgroud)
这是 firebase 对于此 ANR 的说法 -
ANR 发生时该线程处于空闲状态。我们没有足够的信息来确定根本原因。
performance android android-anr-dialog firebase android-looper
我试图绕过线程,我知道我可以使用a Handler来发送消息/ runnables MessageQueue,然后由它接收Looper并发送回处理程序进行处理.
如果我发布到一个处理器在我的活动,是Activity,Handler,MessageQueue并且Looper在UI线程上所有正在运行的?如果没有,有人可以解释这一切是如何结合在一起的吗?:)
我已经基于一个函数创建了一个图像上传asynctask.上传后,我在onPostExecute上收到此错误.我在Runnable上读了一些Stackoverflow的答案,但我不断反复地得到错误,尽管实现了不同的解决方案.
我的代码:
class uploadFile extends AsyncTask<String, String, String> {
private ProgressDialog pDialog;
/**
* --------------------------------------------------------------------
* --------------------------------- Before starting background thread
* Show Progress Dialog
*/
@Override
protected void onPreExecute() {
super.onPreExecute();
pDialog = new ProgressDialog(MainActivity.this);
pDialog.setMessage("Uploading file");
pDialog.setIndeterminate(false);
pDialog.setCancelable(false);
pDialog.show();
}
/**
* --------------------------------------------------------------------
* --------------------------------- getting all recent articles and
* showing them in listview
*/
@Override
protected String doInBackground(String... args) {
HttpURLConnection conn = null;
DataOutputStream dos = null;
DataInputStream inStream = null;
String existingFileName = Environment.getExternalStorageDirectory() …Run Code Online (Sandbox Code Playgroud) 我想知道我们是否有可能postDelayed在android上处理/检测带有延迟(方法)的可运行回调?
例如,handler.postDelayed(new Runnable()...我的应用程序(用于测试目的的应用程序)有一个或几个splashscreen(运行).在这个应用程序中,我还有一个库(我正在应用程序中创建和使用它)以及一些在类上运行的IntentService类.
有时,当应用程序运行那些splashscreenActivities(for Testing purpose)时,我正在创建的库可能会在UI中自动弹出一些活动.但似乎如果这些活动出现在splashscreen活动上并且splashscreen正在被销毁,那些活动(自动弹出)也将被销毁并在logcat中记录"泄露的窗口"消息.
问题是:
所以我的问题是(相对于我正在创建的库方面而没有UI应用程序流的信息):
PS:请注意,通常情况下,我正在使用自动出现的假设活动的对话框.
UPDATE
图解说明:
现在我有一个正在执行Splashscreen的案例.
扩展IntentService类的类已收到来自Internet的请求,该请求将启动一个Activity.
同时启动了启动画面postdelayed,其他活动已创建并在UI中显示.当X秒已经过去且另一个Activity未被销毁时,将创建Next Activity并自动销毁另一个Activity.在这样做时,Android会相对于Activity抛出"泄露的窗口"消息.
java android android-activity android-handler android-looper
只是澄清但是在MAIN Thread上的Android活动中,如果我调用Looper.myLooper()vs Looper.getMainLooper()返回相同的引用,对吧?他们是一样的东西 ?我知道我永远不必调用这些通常因为android负责这个,但我想知道它们从主线程调用时有何不同?
如果从主线程我打电话
Looper.myLooper().quit();
// or
Looper.getMainLooper().quit();
Run Code Online (Sandbox Code Playgroud)
它们都提供相同的运行时异常,所以我假设它们是相同的引用:
Looper.myLooper().quit();
// or
Looper.getMainLooper().quit();
Run Code Online (Sandbox Code Playgroud)
谁能确认一下?
我曾经使用过FusedLocationApi,直到我得知它已被弃用(参见下面的参考资料).实施起来很简单.正如文档所说,您需要将其与GoogleApiClient结合使用
LocationServices.FusedLocationApi.requestLocationUpdates(googleApiClient,
locationRequest, this);
Run Code Online (Sandbox Code Playgroud)
我最近更改为FusedLocationProviderClient(参见下面的参考资料)根据教程,我能够成功地使FusedLocationProviderClient工作
教程:https://github.com/codepath/android_guides/wiki/Retrieving-Location-with-LocationServices-API
// new Google API SDK v11 uses getFusedLocationProviderClient(this)
getFusedLocationProviderClient(this).requestLocationUpdates(mLocationRequest, new LocationCallback() {
@Override
public void onLocationResult(LocationResult locationResult) {
// do work here
onLocationChanged(locationResult.getLastLocation();
}
},
Looper.myLooper());
Run Code Online (Sandbox Code Playgroud)
我遇到的问题是Looper线程.即使应用程序在后台运行,Looper线程也会继续运行.我想在应用程序在后台时暂停位置更新,然后在应用程序位于前台时恢复位置更新.我怎样才能做到这一点?
参考文献:
我使用了一些处理程序
new Handler(Looper.getMainLooper()).post(new Runnable() {
@Override
public void run() {
try{
Messages.onAcknowledgeReceived();
}catch(Exception e){
e.printStackTrace();
}
}
});
Run Code Online (Sandbox Code Playgroud)
它每15秒执行一次,有时它开始抛出一些警告
The Looper class instance count has over a limit(100). There should be some leakage of Looper or HandlerThread.
12-16 12:16:11.357: E/Looper(4647): Looper class instance count = 221
12-16 12:16:11.357: E/Looper(4647): Current Thread Name: IntentService[AppService]
12-16 12:16:12.316: E/Looper(4647): WARNING: The Looper class instance count has over a limit(100). There should be some leakage of Looper or HandlerThread.
12-16 12:16:12.318: E/Looper(4647): Looper class …Run Code Online (Sandbox Code Playgroud) 我知道在Android中执行类似背景的任务的推荐方法是启动某种类型的工作线程,但我想知道当后台任务很小且很多时,是否有更简单的替代方案可用.所以这是我的问题:
为UI线程Looper创建一个新的Handler时,它能以某种方式被赋予比运行UI的默认Handler更低的优先级吗?或者,当排队消息由Handler/Looper处理时,单个消息的优先级是否低于默认消息,因此它们排在UI消息后面,新的UI消息将排在它们前面?
我只是想,如果这是可能的,它对我的应用程序来说已经足够了,我可以避免使用工作线程以及界面UI和工作线程所需的额外编码.
我一直想知道使用Handler( Looper.getMainLooper()) 或启动新的协程作业在主线程上执行小操作(例如更新视图)是否是更好的方法。
处理程序:
val uiHandler = Handler(Looper.getMainLooper())
fun foo() {
uiHandler.post {
someView.update()
}
}
Run Code Online (Sandbox Code Playgroud)
协程
fun foo() {
lifecycleScope.launch {
someView.update()
}
}
Run Code Online (Sandbox Code Playgroud)
我真的不知道,也无法在互联网上找到任何相关内容,但我很想获得这些知识。
android android-handler android-handlerthread android-looper kotlin-coroutines