Android 在 bindService 方法之后从未调用过 onServiceConnected

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/2486692/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-20 06:02:42  来源:igfitidea点击:

onServiceConnected never called after bindService method

androidbindingservicespeech-recognition

提问by Matroska

I have a particular situation: a service started by a broadcast receiver starts an activity. I want to make it possible for this activity to communicate back to the service. I have chosen to use AIDL to make it possible. Everything seems works good except for bindService()method called in onCreate()of the activity. bindService(), in fact, throws a null pointer exception because onServiceConnected()is never called while onBind()method of the service is. Anyway bindService()returns true. The service is obviously active because it starts the activity. I know that calling an activity from a service could sound strange, but unfortunately this is the only way to have speech recognition in a service.

我有一个特殊情况:由广播接收器启动的服务启动一个活动。我想让此活动能够与服务进行通信。我选择使用 AIDL 使其成为可能。除了活动中bindService()调用的方法外,一切似乎都很好onCreate()。实际上,bindService() 会抛出空指针异常,因为服务的onServiceConnected()whileonBind()方法从未被调用。无论如何bindService()返回true。该服务显然处于活动状态,因为它启动了活动。我知道从服务调用活动听起来很奇怪,但不幸的是,这是在服务中进行语音识别的唯一方法。

Thanks in advance

提前致谢

采纳答案by MrSnowflake

I can't make up the exact problem out of your description, so I'm going to guess here!

我无法从你的描述中弥补确切的问题,所以我要在这里猜测!

How can bindService()throw a NullPointerException? The only way this could (/should) happen is when you don't supply a Serviceor a ServiceConnectionlistener.

怎么能bindService()扔一个NullPointerException?这可能(/应该)发生的唯一方法是当您不提供 aServiceServiceConnection侦听器时。

bindService()can't throw a NullPointerExceptionbecauseonServiceConnected()isn't called. The call to onServiceConnected()is a product of bindService().

bindService()不能抛出 aNullPointerException因为onServiceConnected()没有被调用。对 的调用onServiceConnected()是 的产物bindService()

So I guess you are calling a AIDLmethod, before the Servicehas actually bonded?

所以我猜你是在调用一个AIDL方法,在Service它实际绑定之前?

回答by KomodoDave

I've just experienced another version of this problem, with the same symptom of onServiceConnected(...)not being called. The cause was different in my case.

我刚刚遇到了这个问题的另一个版本,onServiceConnected(...)没有被调用的相同症状。在我的情况下,原因是不同的。

You must make sure to have a service declaration in your AndroidManifest.xml within the application tag - this was the root of the problem for me.

您必须确保在应用程序标记内的 AndroidManifest.xml 中有一个服务声明 - 这对我来说是问题的根源。

<application android:name=".YourAppTitle" android:icon="@drawable/icon" android:label="@string/app_name">
    <activity android:name=".Main" android:label="@string/app_name">
    </activity>
    <service android:name="YourService" />
</application>

There's an extra complication if you're using a separate Android library within Eclipse - adding this Service tag only seems to fix the issue if the referenced service is in the same package as the manifest; i.e. if your app is in package a.b.c and this is where AndroidManifest.xml resides, then 'YourService' must also be in package a.b.c. (manually copied from another library, if necessary) or else the <service..>tag may/will be ignored and onServiceConnected(...)still won't be called.

如果您在 Eclipse 中使用单独的 Android 库,则会有额外的复杂性 - 如果引用的服务与清单位于同一包中,添加此服务标签似乎只能解决问题;即,如果您的应用程序位于 abc 包中并且这是 AndroidManifest.xml 所在的位置,则“YourService”也必须位于 abc 包中(如有必要,从另一个库手动复制),否则该<service..>标签可能/将被忽略并且onServiceConnected(...)仍然会成功”不叫。

This was the case for my project even though I used a suitable import statement for the Service in my code. Eclipse showed no error, so the import was correctly identifying the class from another library in the Eclipse workspace.

即使我在代码中为 Service 使用了合适的 import 语句,我的项目也是如此。Eclipse 没有显示错误,因此导入正确地识别了来自 Eclipse 工作区中另一个库的类。

HTH

HTH

回答by Brad Brown

After hours and hours of trying to figure this out, the issue is that the examples that show the creation of the service, don't include the onBind method or they have the following sample code or it generates this for you:

经过数小时和数小时的尝试,问题是显示服务创建的示例不包含 onBind 方法,或者它们具有以下示例代码,或者它会为您生成此代码:

public IBinder onBind(Intent intent) {
    // TODO Auto-generated method stub
    return null;
}

This causes the onServiceConnected method to fail or never actually get executed. The fix is VERY simple, which is the following:

这会导致 onServiceConnected 方法失​​败或从未真正执行。修复非常简单,如下所示:

public IBinder onBind(Intent intent) {
    return mBinder;
}

Where you could create a simple binder such as the following to return:

您可以在哪里创建一个简单的活页夹,如下所示:

private final IBinder mBinder = new LocalBinder();
public class LocalBinder extends Binder {
    public ConferenceService getService() {
    return ConferenceService.this;
  }
}

回答by IanGSY

The onServiceConnectedevent was never being called in my application.

onServiceConnected事件从未被称为在我的应用程序。

The problem was that I had the service name defined in my Application Manifest as:

问题是我在应用程序清单中定义了服务名称:

<service android:name="MyService" android:enabled="true"></service>

Once I changed it to the full class name it worked:

一旦我将其更改为完整的类名,它就起作用了:

<service android:name="com.example.MyService" android:enabled="true"></service>

Update:You can also have use a relative class name:

更新:您还可以使用相对类名:

<service android:name=".MyService" android:enabled="true"></service>

Specify the class name using its full com.example.MyServiceClassinstead of just MyServiceClass.

使用完整的com.example.MyServiceClass而不是MyServiceClass来指定类名。

回答by Abhijeet

One more thing is that if you are calling bindservicemethod inside the oncreatemethod then the onserviceconnectedis called after the oncreatemethod is finished.

另一件事是,如果您在bindservice方法内部调用方法,oncreateonserviceconnectedoncreate方法完成后调用。

So any references to the interface functions before the oncreateends (or before onserviceconnectedis called) shows null pointer exception.

因此,在oncreate结束之前(或在onserviceconnected调用之前)对接口函数的任何引用都会显示空指针异常。

回答by pakerfeldt

Yet another cause to the original question might be that the service isn't already running and you are passing 0 as flag to bindService. Like so:

原始问题的另一个原因可能是该服务尚未运行,并且您将 0 作为标志传递给 bindService。像这样:

bindService(intent, serviceConnection, 0);

When what you are looking for would be:

当您要寻找的是:

bindService(intent, serviceConnection, Context.BIND_AUTO_CREATE);

回答by Stefan Alexandru

There can be another explanation, not a very frequent situation, but I managed to get into it and lose 2 hours to solve it.

可以有另一种解释,不是很常见的情况,但我设法进入它并浪费了 2 个小时来解决它。

So what I did was that I wanted to reuse the bundle from the intent received by the onBind method. But I went for the lazy version and changed the class of the intent. Apparently this causes the onServiceConnected not to get called. Probably because the system keeps a reference to the intent and uses it when calling onServiceConnected.

所以我所做的是我想重用来自 onBind 方法接收到的意图的包。但是我选择了懒惰的版本并更改了意图的类。显然这会导致 onServiceConnected 不被调用。可能是因为系统保留了对意图的引用并在调用 onServiceConnected 时使用它。

In conclusion don't change the intent you receive in onBind.

总之,不要更改您在 onBind 中收到的意图。

回答by Rohan buddy

If someone's still looking for the answer after trying all others then this might help.. onServiceConnected()is not called immediatelyafter bindService(...). it takes few seconds. So if you are receiving some value from the onServiceConnected()and you have to use it somewhere else in onCreateor onStartit will throw a NullPointerException because of the delay. So if you can shift that line of code which needs the value from onCreateor onStart, inside onServiceConnected(){......}, below the line of declaration of the value that you need then it might work.

如果有人在尝试了所有其他人后仍在寻找答案,那么这可能会有所帮助.. 之后onServiceConnected()不会立即调用bindService(...)。这需要几秒钟。所以,如果你收到来自一些值onServiceConnected(),你必须在其他地方使用它onCreateonStart它会抛出,因为一个NullPointerException异常延迟。因此,如果您可以将需要值的那行代码从onCreateonStart, inside 移动onServiceConnected(){......}到您需要的值的声明行下方,那么它可能会起作用。

回答by yonix

I just spent a lot of time on this one, and since in my case it was neither of the above answers I'll just lay out another possible scenario:

我只是在这个问题上花了很多时间,因为就我而言,以上答案都不是,我将列出另一种可能的情况:

This happened to me when I was using a kotlin.coroutines.Deferredobject to represent my bound service, and I blocked the thread that onServiceConnectedshould be called on when I called await()on this object.

当我使用一个kotlin.coroutines.Deferred对象来表示我的绑定服务时,这发生在我身上onServiceConnected,当我调用await()这个对象时,我阻塞了应该调用的线程。

So basically - don't block the main thread waiting for onServiceConnectedto be called, or it won't be able to be called...

所以基本上 - 不要阻塞等待onServiceConnected被调用的主线程,否则它将无法被调用......

回答by Gallal

I was calling bind with an empty Intent - getContext().bindService(new Intent(), mConnection, Context.BIND_AUTO_CREATE). I have to make the intent more specific to indicate which service I want to bind to. This is obviously a code error, but the Logcat output was unfortunately not clear enough.

我正在用一个空的 Intent - 调用 bind getContext().bindService(new Intent(), mConnection, Context.BIND_AUTO_CREATE)。我必须使意图更具体,以指示我要绑定到哪个服务。这显然是代码错误,但遗憾的是 Logcat 输出不够清晰。