Android app添加后台拉起机制

本demo源码下载地址 App拉起机制源码下载

简介:

做智能售卖设备需要app一直在前台显示,但是有时由于一些不当操作或者系统原因会使app退出,导致设备不能使用。这时就需要拉起机制了。

拉起机制目前实现方式主要有2种。

1、利用Activity生命周期

创建一个类MyApp继承自Application类,在该类通过监听所有activity生命周期来判断activity是否全部销毁,以此来判断app是否退出。
代码如下:

/**
*  监听各个Activity生命周期情况
*/
private void startActivityLifeListener(){
    registerActivityLifecycleCallbacks(new ActivityLifecycleCallbacks() {
        @Override
        public void onActivityCreated(Activity activity, Bundle savedInstanceState) {
            showLog("add activity "+activity.toString());
        }

        @Override
        public void onActivityStarted(Activity activity) {
            mActivityCount++;
            showLog(activity.getComponentName()+" onActivityStarted activityCounts= "+mActivityCount);
        }

        @Override
        public void onActivityResumed(Activity activity) {

        }

        @Override
        public void onActivityPaused(Activity activity) {
            showLog(activity.getComponentName().toString()+" onActivityPaused");
        }

        @Override
        public void onActivityStopped(Activity activity) {
            mActivityCount--;
            showLog(activity.getComponentName()+" onActivityStopped activityCounts= "+mActivityCount);
            if (mActivityCount <= 0){
                // 5秒后拉起
                new Handler().postDelayed(new Runnable() {
                    @Override
                    public void run() {
                        showLog("try to restart");
                        Intent intent = new Intent(getApplicationContext(), MainActivity.class);
                        intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
                        startActivity(intent);
                    }
                }, 5000);
            }
        }

        @Override
        public void onActivitySaveInstanceState(Activity activity, Bundle outState) {

        }

        @Override
        public void onActivityDestroyed(Activity activity) {
            showLog("remove activity "+activity.toString());
        }
    });
}

然后在onCreate方法里面调用startActivityLifeListener()方法。
在这里插入图片描述

2、利用RunningAppProcessInfo类判断

通过ActivityManager类获取所有正在运行的进程,然后利用app包名找到应用的运行进程,再判断是否处于后台,不过该方法在有些系统版本可能不能用。
创建一个远程服务类PullUpService在后台一直运行轮询检查app是否后台运行。代码如下:

package com.mhwang.apppullup;

import android.app.ActivityManager;
import android.app.Service;
import android.content.Context;
import android.content.Intent;
import android.os.IBinder;
import android.os.SystemClock;
import android.util.Log;

import java.util.List;

/** 后台拉起服务
* Author : mhwang
* Date : 2018/11/6
* Version : V1.0
*/
public class PullUpService extends Service implements Runnable{
    private boolean running = false;
    private Intent intent;
    private Thread thread;

    private static void showLog(String s){
        Log.d("PullUpService=>", s);
    }

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

    public void onCreate(){
        super.onCreate();
        intent = getPackageManager().getLaunchIntentForPackage(getPackageName());
        if (intent != null) {
            intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
        }
        showLog("onCreate");
    }

    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        showLog("onStartCommand");
        if(thread == null){
            thread = new Thread(this);
            thread.start();
        }
        return START_STICKY;
    }

    @Override
    public void onDestroy() {
        showLog("onDestroy");
        running = false;
        if(thread != null && !thread.isInterrupted()){
            try {
                thread.interrupt();
                thread.join(100);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
        thread = null;
        super.onDestroy();
    }

    @Override
    public void run() {
        running = true;
        showLog("background service start");
        while(running){
            showLog("check background");
            if(isBackground(PullUpService.this)){
                showLog("restart activity");
                startActivity(intent);
            }
            SystemClock.sleep(10 * 1000);         // 由于模拟器较卡,这里提高10秒检查一次
        }
    }

    /** 判断是否处于后台
     * @param context
     * @return true:处于后台, false:不处于后台
     */
    public static boolean isBackground(Context context) {
        ActivityManager activityManager = (ActivityManager) context
                .getSystemService(Context.ACTIVITY_SERVICE);
        List<ActivityManager.RunningAppProcessInfo> appProcesses = activityManager
                .getRunningAppProcesses();
        if(appProcesses == null){
            return false;
        }
        for (ActivityManager.RunningAppProcessInfo appProcess : appProcesses) {
            if (appProcess.processName.equals(context.getPackageName())) {
                if (appProcess.importance != ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND) {
                    return true;
                } else {
                    return false;
                }
            }
        }
        return false;
    }

}

记得在AndroidMainifest.xml注册该服务。

<service android:name=".PullUpService" android:process=":remote"/>

然后在MyApp类开启服务:
在这里插入图片描述

如下图所示,使用back键和home键退出app,每隔5秒后都能有效拉起(图示效果运行在模拟器系统版本4.4.2)。但是有个缺点就是使用多任务键杀死时,由于此时整个app都被干掉了,因此MyApp里面的拉起机制不能生效。
在这里插入图片描述

<think>好的,我现在需要帮助用户了解如何从小程序跳转并拉起APP的方法。首先,我应该回顾用户提供的引用内容,看看有没有相关的实现方案。 用户提到了引用[1],里面提到APP可以拉起小程序,但用户的问题是小程序跳转回APP,所以需要反过来。引用[2]和[4]提到了APP如何拉起小程序,尤其是引用[4]提到使用明文scheme,比如`weixin://dl/business/...`。这可能是一个线索,因为通常跳转APP需要配置URL Scheme。 接下来,我需要确认小程序是否支持直接跳转APP。微信小程序的文档中应该有相关的API,比如使用`wx.navigateToMiniProgram`或者开放标签等。不过根据引用[3],短信跳转小程序需要配置拉起网页,可能类似的流程需要网页作为中间步骤。 可能的步骤是:小程序内通过开放标签`<wx-open-launch-app>`来拉起APP。这需要小程序的开发者在页面上配置这个标签,并且APP需要注册相应的URL Scheme。同时,用户提到的引用[4]中的URL Scheme格式可能适用于APP拉起的情况。 需要注意的是,微信小程序对于跳转外部APP可能有安全限制,通常只能在特定的场景下使用,比如用户主动触发,或者通过客服消息等。另外,iOS和Android的处理方式可能不同,比如Android需要配置intent。 还需要考虑用户是否已经正确配置了APP的Scheme,以及在小程序后台是否添加了合法的业务域名。此外,携带参数时需要进行编码处理,避免特殊字符导致的问题,如引用[4]中提到的encode编码。 总结可能的实现方案:在小程序中使用开放标签或API,结合APP注册的URL Scheme,用户点击后触发跳转。同时,可能需要服务端生成签名等安全措施,确保跳转的合法性。此外,还需要处理不同平台的兼容性问题,以及用户未安装APP时的降级处理,比如跳转到下载页面。</think>### 小程序跳转并拉起APP的实现方案 #### 1. **基本原理** 通过微信小程序的开放能力(如开放标签或API)触发URL Scheme跳转,结合APP预先注册的Scheme协议实现拉起。具体流程如下: - **APP注册URL Scheme**:在APPAndroidManifest.xml(Android)或Info.plist(iOS)中声明自定义Scheme(例如`myapp://`)[^4]。 - **小程序调用开放标签**:在小程序页面嵌入`<wx-open-launch-app>`组件,配置APP的Scheme及参数,用户点击后触发跳转[^3]。 #### 2. **具体实现步骤 ** **(1)APP端配置** - **Android**:在`AndroidManifest.xml`中定义Intent Filter: ```xml <intent-filter> <action android:name="android.intent.action.VIEW"/> <category android:name="android.intent.category.DEFAULT"/> <category android:name="android.intent.category.BROWSABLE"/> <data android:scheme="myapp" android:host="path"/> </intent-filter> ``` - **iOS**:在`Info.plist`中添加URL Types: ```xml <key>CFBundleURLTypes</key> <array> <dict> <key>CFBundleURLSchemes</key> <array> <string>myapp</string> </array> </dict> </array> ``` **(2)小程序端调用** - **使用开放标签**(需通过微信认证且非个人主体小程序): ```html <wx-open-launch-app appid="APP注册的Scheme,如myapp" extinfo="自定义参数(需encode)" > <template>点击跳转APP</template> </wx-open-launch-app> ``` 需在服务端生成签名,并在小程序页面引入`jweixin-1.6.0.js`。 - **通过API动态跳转**(需用户主动触发): ```javascript wx.navigateTo({ url: 'myapp://path?param=value' // 需encode特殊字符 }) ``` #### 3. **注意事项** - **安全限制**:iOS要求Scheme跳转必须由用户主动触发(如点击事件),否则会被系统拦截。 - **未安装APP的降级处理**:通过`wx.getLaunchOptionsSync`检测跳转是否成功,若失败则跳转下载页。 - **参数编码**:携带参数时需用`encodeURIComponent`处理,避免`&`或`=`导致解析错误[^4]。 #### 4. **示例代码(携带参数)** ```javascript // 小程序端 const path = encodeURIComponent('pages/index?query=123'); window.open('myapp://launch?path=' + path, '_blank'); ``` ---
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值