实现推送接收并在指定页面中处理(涉及推送、service)

来源:互联网 发布:stm32 socket编程 编辑:程序博客网 时间:2024/06/05 15:35

需求来源:

在观察QQ以及其他APP在一些场景的处理: APP 在运行期间,不定时的一条推送,然APP 会相应的在当前页面弹出当前信息。

逻辑难点:
app 哪个页面在栈的最顶部不可控。 从开一个栈并不能达到这种需求。

实现过程: 我曾经用过这种方法,在广播接受着中使用:


此方法还需在配置文件中 添加 :uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />

-- 弹出系统对话框的权限是有问题的,比如小米就禁用。 并且这个权限也是无法正常签名打包的,为何在此不做深究。


这种 方式 可以实现一些简单的需求。但问题又来了:

比如: APP 重新打开先过广告页,在广告页 dialog 就已经提示出来了,并且因为它是系统级别的,在dialog 显示的时候 你的App 已然执行着此操作: 广告页跳转主界面。

这样 这个对话框的显示流程 和触发时机 就已经错误了。


----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

                                                                                  Service Or Receiver


在整理思路之后 换一种思路: 在接收推送之后,是否可开启一个本地服务, 这个本地服务 过一秒发一次广播, 而在我需要场景弹框的页面 注册这个广播,这样可实现需求,并且在不同页面 接收,也可以做不同的操作,比如:跳转、刷新、关闭。

好了 啰嗦这么多:


首先 自定义广播接收者:       在次代码  以 Jpush通知 为例 。没实现推送的小伙伴先去Jpush官网看下   地址 :https://www.jiguang.cn/push


** * Jpush 自定义广播接收 */public class MyJpushReceiver extends BroadcastReceiver {    @Override    public void onReceive(Context context, Intent intent) {        Bundle bundle = intent.getExtras();        if (JPushInterface.ACTION_REGISTRATION_ID.equals(intent.getAction())) {            //    "JPush用户注册成功"        } else if (JPushInterface.ACTION_MESSAGE_RECEIVED.equals(intent.getAction())) {            //"接受到推送下来的自定义消息"        } else if (JPushInterface.ACTION_NOTIFICATION_RECEIVED.equals(intent.getAction())) {            //"接受到推送下来的通知"            receivingNotification(context, bundle);        } else if (JPushInterface.ACTION_NOTIFICATION_OPENED.equals(intent.getAction())) {            //"用户点击打开了通知"        } else {            //"Unhandled intent - "        }    }    private void receivingNotification(final Context context, Bundle bundle) {        String title = bundle.getString(JPushInterface.EXTRA_NOTIFICATION_TITLE);        Log.d("Bruce", " title : " + title);        String message = bundle.getString(JPushInterface.EXTRA_ALERT);        Log.d("Bruce", "message : " + message);        final String extras = bundle.getString(JPushInterface.EXTRA_EXTRA);        Log.d("Bruce", "extras : " + extras);        try {            JSONObject jsonObject =new JSONObject(extras);            String orderNo = jsonObject.getString("orderNo");            MyJpushOrderBean orderBean = new MyJpushOrderBean(title,message,orderNo);            Intent intent = new Intent(context,MyBroatService.class);            intent.putExtra("JpushMsg",orderBean);            context.startService(intent);        } catch (JSONException e) {            e.printStackTrace();        }    }}

接收推送通知信息之后开启服务:

** * 接收jpush 信息 开启服务 发送本地广播 */public class MyBroatService extends IntentService {    private MyJpushOrderBean jpushMsg;    private Intent it;    public String RECEIVER_ACTION = "JpushMsg_hint";    private boolean isSend = true;    public MyBroatService() {        super("MyBroatService");    }    private void StartBroatReceiver() {        try {            while (isSend) {                Log.d("service", "----------------一次次----------------");                sendBroadcast(it);                Thread.sleep(1000);            }        } catch (InterruptedException e) {        }    }    @Override    protected void onHandleIntent(Intent intent) {        if (intent != null) {            jpushMsg = ((MyJpushOrderBean) intent.getSerializableExtra("JpushMsg"));            Log.d("Bruce", "----------service- 开启-------------" + jpushMsg.toString());            it = new Intent(RECEIVER_ACTION);            it.putExtra("JpushInfo", jpushMsg);            StartBroatReceiver();        }    }    @Override    public void onDestroy() {        isSend = false;        super.onDestroy();    }}

然后在 BaseActivity 中 注册广播接收者:

/** * 父类 广播接收 * 接收提示 操作 * 管理类 */public class BaseActivity extends Activity {    private String RECEIVER_ACTION = "JpushMsg_hint";    private AlertDialog.Builder builder = null;    private AlertDialog dialog = null;    private MyHttpUtils httpUtils;    private boolean isReceive = true;    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        RegiListener();    }    private void RegiListener() {        IntentFilter intentFilter = new IntentFilter();        intentFilter.addAction(RECEIVER_ACTION);        registerReceiver(broadcastReceiver, intentFilter);    }    private BroadcastReceiver broadcastReceiver = new BroadcastReceiver() {        @Override        public void onReceive(Context context, Intent intent) {            if (intent.getAction().equals(RECEIVER_ACTION)) {                if (isReceive) {                    isReceive = false;                    MyJpushOrderBean orderBean = (MyJpushOrderBean) intent.getSerializableExtra("JpushInfo");                    Log.d("Bruce", "-----------------我是广播收到的 信息------------" + orderBean.toString());                    ShowHintDialog(orderBean);                    StopIntentService();                }            }        }    };    private void StopIntentService() {        Intent intent = new Intent(this, MyBroatService.class);        stopService(intent);        Log.d("Bruce", "--------服务停止了------------");    }    private void ShowHintDialog(final MyJpushOrderBean orderBean) {        builder = new AlertDialog.Builder(this);        builder.setTitle(orderBean.getTitle());        builder.setMessage(orderBean.getMessage());        builder.setCancelable(false);        builder.setNegativeButton("不要了", new DialogInterface.OnClickListener() {            @Override            public void onClick(DialogInterface dialogInterface, int i) {                recycleDialog();            }        });        builder.setPositiveButton("立即前往", new DialogInterface.OnClickListener() {            @Override            public void onClick(DialogInterface dialogInterface, int i) {                StartOrder(orderBean.getExtras());            }        });        dialog = builder.show();    }    private void StartOrder(final String extras) {        recycleDialog();        httpUtils = MyHttpUtils.getInstance();        Map<String, String> map = new HashMap<>();        map.put("orderNo", extras);        httpUtils.asyncGetOrInfo(UrlUtils.GETCARIMGINFO, this, false, null, map, new MyInterFaceUtils.HttpCallBack() {            @Override            public void onError(Request request, IOException e) {            }            @Override            public void onSuccess(Request request, String result) {                Log.d("Bruce", "------------推送 拿数据-------------" + result + "--订单号----" + extras);                Gson gson = new Gson();                GetCarReviewInfoBean getCarReviewInfoBean = gson.fromJson(result, GetCarReviewInfoBean.class);                OrderInfo data = getCarReviewInfoBean.data;                ChangeInfoOfStart(data);            }        });    }    /***     * 子类页面重写此方法     * 不同页面可实现不同操作     * @param data     */    public void ChangeInfoOfStart(OrderInfo data) {    }    public void recycleDialog() {        if (dialog != null) {            if (dialog.isShowing()) {                dialog.dismiss();            }            dialog = null;        }        builder = null;    }    @Override    protected void onDestroy() {        recycleDialog();        httpUtils = null;        unregisterReceiver(broadcastReceiver);        super.onDestroy();    }}

以上为主要逻辑代码。还有 对IntentService 不太熟悉的 小伙伴可以去谷歌一下。

IntentService是继承于Service并处理异步请求的一个类。具体有很多博客写得很透彻,在此就不班门弄斧了。


下章会发项目实战中 Recyclerview  根据type 加载复杂布局的简单示例。

转载请注明原创: http://blog.csdn.net/qq_34062297/article/details/77772442