mirror of
https://bitbucket.org/TheBosZ/cordova-plugin-run-in-background
synced 2024-12-23 13:57:35 +00:00
Initial Android support
This commit is contained in:
parent
a782f8ffe9
commit
e4f6d7cd0b
32
plugin.xml
32
plugin.xml
@ -14,10 +14,12 @@
|
||||
|
||||
<author>Sebastián Katzer</author>
|
||||
|
||||
<!-- cordova -->
|
||||
<engines>
|
||||
<engine name="cordova" version=">=3.0.0" />
|
||||
</engines>
|
||||
|
||||
<!-- js -->
|
||||
<js-module src="www/background-mode.js" name="BackgroundMode">
|
||||
<clobbers target="plugin.backgroundMode" />
|
||||
</js-module>
|
||||
@ -49,9 +51,37 @@
|
||||
|
||||
<!-- android -->
|
||||
<platform name="android">
|
||||
<config-file target="config.xml" parent="/*">
|
||||
<config-file target="res/xml/config.xml" parent="/*">
|
||||
<feature name="BackgroundMode" >
|
||||
<param name="android-package"
|
||||
value="de.appplant.cordova.plugin.background.BackgroundMode"/>
|
||||
</feature>
|
||||
</config-file>
|
||||
|
||||
<config-file target="res/xml/config.xml" parent="/*">
|
||||
<preference name="KeepRunning" value="true" />
|
||||
</config-file>
|
||||
|
||||
<config-file target="AndroidManifest.xml" parent="/manifest/application">
|
||||
<!--
|
||||
* Puts the service in a foreground state, where the system considers
|
||||
* it to be something the user is actively aware of and thus not a
|
||||
* candidate for killing when low on memory.
|
||||
-->
|
||||
<service
|
||||
android:name="de.appplant.cordova.plugin.background.ForegroundService"
|
||||
android:enabled="true" />
|
||||
|
||||
</config-file>
|
||||
|
||||
<source-file
|
||||
src="src/android/BackgroundMode.java"
|
||||
target-dir="src/de/appplant/cordova/plugin/background" />
|
||||
|
||||
<source-file
|
||||
src="src/android/ForegroundService.java"
|
||||
target-dir="src/de/appplant/cordova/plugin/background" />
|
||||
|
||||
</platform>
|
||||
|
||||
<!-- wp8 -->
|
||||
|
180
src/android/BackgroundMode.java
Normal file
180
src/android/BackgroundMode.java
Normal file
@ -0,0 +1,180 @@
|
||||
/*
|
||||
Copyright 2013-2014 appPlant UG
|
||||
|
||||
Licensed to the Apache Software Foundation (ASF) under one
|
||||
or more contributor license agreements. See the NOTICE file
|
||||
distributed with this work for additional information
|
||||
regarding copyright ownership. The ASF licenses this file
|
||||
to you under the Apache License, Version 2.0 (the
|
||||
"License"); you may not use this file except in compliance
|
||||
with the License. You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing,
|
||||
software distributed under the License is distributed on an
|
||||
"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
KIND, either express or implied. See the License for the
|
||||
specific language governing permissions and limitations
|
||||
under the License.
|
||||
*/
|
||||
|
||||
package de.appplant.cordova.plugin.background;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.content.ComponentName;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.ServiceConnection;
|
||||
import android.os.IBinder;
|
||||
import android.util.Log;
|
||||
|
||||
import org.apache.cordova.CallbackContext;
|
||||
import org.apache.cordova.CordovaPlugin;
|
||||
import org.json.JSONArray;
|
||||
import org.json.JSONException;
|
||||
|
||||
public class BackgroundMode extends CordovaPlugin {
|
||||
|
||||
// Flag indicates if the app is in background or foreground
|
||||
private boolean inBackground = false;
|
||||
|
||||
// Flag indicates if the plugin is enabled or disabled
|
||||
private boolean isDisabled = false;
|
||||
|
||||
// Used to (un)bind the service to with the activity
|
||||
private ServiceConnection connection = new ServiceConnection() {
|
||||
|
||||
@Override
|
||||
public void onServiceConnected(ComponentName name, IBinder binder) {
|
||||
// Nothing to do here
|
||||
Log.d("BackgroundMode", "Service connected");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onServiceDisconnected(ComponentName name) {
|
||||
Log.w("BackgroundMode", "Service disrupted");
|
||||
//stopService();
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Executes the request.
|
||||
*
|
||||
* @param action The action to execute.
|
||||
* @param args The exec() arguments.
|
||||
* @param callback The callback context used when
|
||||
* calling back into JavaScript.
|
||||
*
|
||||
* @return
|
||||
* Returning false results in a "MethodNotFound" error.
|
||||
*
|
||||
* @throws JSONException
|
||||
*/
|
||||
@Override
|
||||
public boolean execute (String action, JSONArray args,
|
||||
CallbackContext callback) throws JSONException {
|
||||
|
||||
if (action.equalsIgnoreCase("observeLifeCycle")) {
|
||||
// Nothing to do here
|
||||
return true;
|
||||
}
|
||||
|
||||
if (action.equalsIgnoreCase("enable")) {
|
||||
enableMode();
|
||||
return true;
|
||||
}
|
||||
|
||||
if (action.equalsIgnoreCase("disable")) {
|
||||
disableMode();
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the system is about to start resuming a previous activity.
|
||||
*
|
||||
* @param multitasking
|
||||
* Flag indicating if multitasking is turned on for app
|
||||
*/
|
||||
@Override
|
||||
public void onPause(boolean multitasking) {
|
||||
super.onPause(multitasking);
|
||||
inBackground = true;
|
||||
startService();
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Called when the activity will start interacting with the user.
|
||||
*
|
||||
* @param multitasking
|
||||
* Flag indicating if multitasking is turned on for app
|
||||
*/
|
||||
@Override
|
||||
public void onResume(boolean multitasking) {
|
||||
super.onResume(multitasking);
|
||||
inBackground = false;
|
||||
stopService();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
super.onDestroy();
|
||||
stopService();
|
||||
}
|
||||
|
||||
/**
|
||||
* Enable the background mode.
|
||||
*/
|
||||
private void enableMode() {
|
||||
isDisabled = false;
|
||||
|
||||
if (inBackground) {
|
||||
startService();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Disable the background mode.
|
||||
*/
|
||||
private void disableMode() {
|
||||
stopService();
|
||||
isDisabled = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Bind the activity to a background service and put them into foreground
|
||||
* state.
|
||||
*/
|
||||
private void startService() {
|
||||
Activity context = cordova.getActivity();
|
||||
|
||||
Intent intent = new Intent(
|
||||
context, ForegroundService.class);
|
||||
|
||||
if (isDisabled)
|
||||
return;
|
||||
|
||||
context.bindService(
|
||||
intent, connection, Context.BIND_AUTO_CREATE);
|
||||
|
||||
context.startService(intent);
|
||||
}
|
||||
|
||||
/**
|
||||
* Bind the activity to a background service and put them into foreground
|
||||
* state.
|
||||
*/
|
||||
private void stopService() {
|
||||
Activity context = cordova.getActivity();
|
||||
|
||||
Intent intent = new Intent(
|
||||
context, ForegroundService.class);
|
||||
|
||||
context.unbindService(connection);
|
||||
context.stopService(intent);
|
||||
}
|
||||
}
|
164
src/android/ForegroundService.java
Normal file
164
src/android/ForegroundService.java
Normal file
@ -0,0 +1,164 @@
|
||||
/*
|
||||
Copyright 2013-2014 appPlant UG
|
||||
|
||||
Licensed to the Apache Software Foundation (ASF) under one
|
||||
or more contributor license agreements. See the NOTICE file
|
||||
distributed with this work for additional information
|
||||
regarding copyright ownership. The ASF licenses this file
|
||||
to you under the Apache License, Version 2.0 (the
|
||||
"License"); you may not use this file except in compliance
|
||||
with the License. You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing,
|
||||
software distributed under the License is distributed on an
|
||||
"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
KIND, either express or implied. See the License for the
|
||||
specific language governing permissions and limitations
|
||||
under the License.
|
||||
*/
|
||||
|
||||
package de.appplant.cordova.plugin.background;
|
||||
|
||||
import android.app.Notification;
|
||||
import android.app.PendingIntent;
|
||||
import android.app.Service;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.res.Resources;
|
||||
import android.os.Build;
|
||||
import android.os.Handler;
|
||||
import android.os.IBinder;
|
||||
import android.util.Log;
|
||||
|
||||
import java.util.Date;
|
||||
import java.util.Timer;
|
||||
import java.util.TimerTask;
|
||||
|
||||
/**
|
||||
* Puts the service in a foreground state, where the system considers it to be
|
||||
* something the user is actively aware of and thus not a candidate for killing
|
||||
* when low on memory.
|
||||
*/
|
||||
public class ForegroundService extends Service {
|
||||
|
||||
// Fixed ID for the 'foreground' notification
|
||||
private static final int NOTIFICATION_ID = -574543954;
|
||||
|
||||
// Scheduler to exec periodic tasks
|
||||
final Timer scheduler = new Timer();
|
||||
|
||||
// Used to keep the app alive
|
||||
TimerTask keepAliveTask;
|
||||
|
||||
/**
|
||||
* Allow clients to call on to the service.
|
||||
*/
|
||||
@Override
|
||||
public IBinder onBind (Intent intent) {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Put the service in a foreground state to prevent app from being killed
|
||||
* by the OS.
|
||||
*/
|
||||
@Override
|
||||
public void onCreate () {
|
||||
super.onCreate();
|
||||
keepAwake();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
super.onDestroy();
|
||||
sleepWell();
|
||||
}
|
||||
|
||||
/**
|
||||
* Put the service in a foreground state to prevent app from being killed
|
||||
* by the OS.
|
||||
*/
|
||||
public void keepAwake() {
|
||||
final Handler handler = new Handler();
|
||||
|
||||
startForeground(NOTIFICATION_ID, makeNotification());
|
||||
|
||||
keepAliveTask = new TimerTask() {
|
||||
@Override
|
||||
public void run() {
|
||||
handler.post(new Runnable() {
|
||||
public void run() {
|
||||
// Nothing to do here
|
||||
// Log.d("BackgroundMode", "" + new Date().getTime());
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
scheduler.schedule(keepAliveTask, 0, 1000);
|
||||
}
|
||||
|
||||
/**
|
||||
* Stop background mode.
|
||||
*/
|
||||
private void sleepWell() {
|
||||
stopForeground(true);
|
||||
keepAliveTask.cancel();
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a notification as the visible part to be able to put the service
|
||||
* in a foreground state.
|
||||
*
|
||||
* @return
|
||||
* A local ongoing notification which pending intent is bound to the
|
||||
* main activity.
|
||||
*/
|
||||
@SuppressWarnings("deprecation")
|
||||
private Notification makeNotification() {
|
||||
Context context = getApplicationContext();
|
||||
String pkgName = context.getPackageName();
|
||||
Intent intent = context.getPackageManager()
|
||||
.getLaunchIntentForPackage(pkgName);
|
||||
|
||||
PendingIntent contentIntent = PendingIntent.getActivity(
|
||||
context, NOTIFICATION_ID, intent, PendingIntent.FLAG_CANCEL_CURRENT);
|
||||
|
||||
String title = "App is running in background";
|
||||
|
||||
Notification.Builder notification = new Notification.Builder(context)
|
||||
.setContentTitle(title)
|
||||
.setContentText(title)
|
||||
.setTicker(title)
|
||||
.setOngoing(true)
|
||||
.setSmallIcon(getIconResId())
|
||||
.setContentIntent(contentIntent);
|
||||
|
||||
if (Build.VERSION.SDK_INT < 16) {
|
||||
// Build notification for HoneyComb to ICS
|
||||
return notification.getNotification();
|
||||
} else {
|
||||
// Notification for Jellybean and above
|
||||
return notification.build();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves the resource ID of the app icon.
|
||||
*
|
||||
* @return
|
||||
* The resource ID of the app icon
|
||||
*/
|
||||
private int getIconResId () {
|
||||
Context context = getApplicationContext();
|
||||
Resources res = context.getResources();
|
||||
String pkgName = context.getPackageName();
|
||||
|
||||
int resId;
|
||||
resId = res.getIdentifier("icon", "drawable", pkgName);
|
||||
|
||||
return resId;
|
||||
}
|
||||
}
|
@ -46,4 +46,6 @@ BackgroundMode.prototype = {
|
||||
|
||||
var plugin = new BackgroundMode();
|
||||
|
||||
document.addEventListener("backbutton", function () {}, false);
|
||||
|
||||
module.exports = plugin;
|
Loading…
Reference in New Issue
Block a user