2017-03-01 78 views
0

首先,我创建的应用程序必须在后台工作(即使用户杀死了应用程序)。我有蓝牙服务器(树莓派),我的应用应该像服务器的客户端。当连接建立时,我需要保持活动状态,并且只在用户太远的时候断开prom服务器或服务器发送特定的断开连接命令。所以我简单地找到了BluetoothChatExample并将活动中的所有代码都放到了服务中(因为即使用户杀死了应用程序,我的服务也应该独立于我的主要活动,因此我需要进行通信)。Android服务被破坏活动后重新创建

下面是从我的服务

public class BluetoothCommunicationService extends Service { 
    public BluetoothCommunicationService() { 

    } 

    @Override 
    public void onCreate() { 
     super.onCreate(); 

    //.... 
    //.... 
    //.... 
    } 

    @Override 
    public int onStartCommand(Intent intent, int flags, int startId) { 
     if(intent.getAction.equals("stop") { 
      stopSelf(); 
     } 
     return START_STICKY; 
    } 

private class AcceptThread extends Thread { 
      //.... 
} 

private class ConnectThread extends Thread { 
    //.... 
} 

private class ConnectedThread extends Thread { 
    //.... 
} 

@Override 
    public void onDestroy() { 
     super.onDestroy(); 

} 

} 因此,大家可以看到,我开始我的服务为START_STICKY一些代码片段,但这里的时候,我杀从“最近使用的应用程序”应用程序的问题列表我也杀了我的服务(即使onDestroy()未被调用!!!),然后再调用onCreate,服务从头开始。但蓝牙通信基于套接字,因此它们也被重新创建,并且我的连接丢失。我也尝试过START_NOT_STICKY然而,当我关闭我的应用程序并且它从不重新创建时,我的服务就被销毁了。在用户关闭我的应用程序之后,是否有可能保持服务活着(甚至不重新创建)?

回答

1

所有我创建的应用程序,必须在后台 (即使用户杀死的应用)来工作的第一位。

不除非你是一个系统应用程序,你不是。 Android的应用程序模型非常清楚,应用程序无法强制自己持续运行,理由很充分。如果手机上的大量应用程序决定这么做,会怎么样?移动设备不是台式计算机。他们拥有电池,并且无法实现合理的电池续航时间,并且工艺在后台持续旋转。为了获得合理的电池续航时间,Android依赖于能够在没有任何事情发生时让CPU进入睡眠状态。

此外,如果用户划掉您的活动,应用程序将处于非活动状态。这意味着它无法接收广播(包括警报管理器唤醒),只能由用户从启动器启动您的活动,启动其中一项活动的另一个应用或在应用内启动服务的其他应用重新启动。对于新安装的应用程序也是如此:在明确使用它们之前,它们无法运行。

对于非系统应用程序,最好的办法是使用startForeground() + START_STICKY。这是Android最强的指标,您的服务很重要,不应该被杀死。

系统应用程序可以声明自己持久性在他们的清单,他们的过程永远不会被杀死。除非您正在构建Android Dist并自行闪烁,但这不是一种选择。

1

您不能保证该服务不会被杀死。它可以并将在某个时候终止,关闭所有应用程序将会破坏您的服务。您从START_STICKY获得的唯一好处是它将在稍后尝试重新启动服务。

1

这是按设计。当你在最近的应用程序中刷一个应用程序时,它会杀死整个应用程序。这包括任何后台服务。

0

是的,可以让您的服务保持活力。您应该添加到您的清单:

<service android:name=".BluetoothCommunicationService" 
      android:process=":nameNewProcessThatYourServiceWillUseHere"/> 

现在,您的服务将在比您最初的应用程序独立进程运行。

+0

在另一个进程中运行服务对Android决定是关闭服务还是终止进程没有影响。 –

+0

是的,但是如果你杀了你的应用程序的进程,并且你想让你的服务继续运行,你必须为它做一个单独的过程。据我了解,它的应用程序和唯一的应用程序的杀死过程不会影响服务的过程,它们独立工作,这就是大卫所问的。 –

+0

如果他只是在谈论用户手动终止进程,答案将是“不这样做”。 –

0

如果之前已启动,您的服务应在一段时间后重新启动,并返回START_STICKY或START_REDELIVER_INTENT并在清单中声明。 Android会决定这个时间,并将它记录到监视器控制台中。它说是这样的:

Scheduling restart of crashed service com.company.app/MyService in 1000ms 

哦,如果你想看到Android Studio中这条消息,请确保您设置了Android监视器logcat的以放牧和无过滤。筛选由您的服务的类名也将有所帮助,就像这样:

Android Studio logcat

再次,首先要确保您的服务正在运行。如果您没有在清单中声明它,它将不会启动。

+0

“您的服务应该重新启动” - 确切地说,它应该,通常会,但Android不能保证它,并且这不会保持它持续运行。 –

+0

是啊,你没有任何其他的机会,所以这是最好的,你可以做些什么来保持你的应用程序关闭时运行的东西。 –

+0

这实际上不是你能做的最好的事情。查看我的帖子,并参考Android文档。 –