Android 4.0 ICS SystemUI浅析——StatusBar加载流程之Notification

        前面三篇文章《Android 4.0 ICS SystemUI浅析——SystemUI启动流程》、《Android 4.0 ICS SystemUI浅析——StatusBar结构分析》、《Android 4.0 ICS SystemUI浅析——StatusBar加载流程分析》逐步分析了SystemUI中StatusBar的启动以及加载流程,本文主要分析StatusBar上的Notification的加载,如有不正之处还恳请各位帮忙指正。

        本文来自:http://blog.csdn.net/yihongyuelan 欢迎转载 请务必注明出处!

        在上一篇文章《Android 4.0 ICS SystemUI浅析——StatusBar加载流程分析》中,我们主要分析了StatusBar上的系统Icons加载的过程,包括了耳机图标、蓝牙图标、禁音图标等等,此文是紧接着上文分析的,因此我们首先看到/SourceCode/frameworks/base/packages/SystemUI/src/com/android/systemui/statusbar/StatusBar.java的start():

    
         public void start() {
        // First set up our views and stuff.首先准备我们需要显示的view以及原材料
        //我们先跟踪这里的makeStatusBarView
        View sb = makeStatusBarView();

        // Connect in to the status bar manager service
        //初始化各个存储器,用于存储各类信息,这些信息通过StatusBarManagerService获取
        //iconsList用于存放icons
        StatusBarIconList iconList = new StatusBarIconList();
        //nodificationKeys保存以Binder为Key的notification
        ArrayList<IBinder> notificationKeys = new ArrayList<IBinder>();
        //保存StatusBarNotification类型的notifications
        ArrayList<StatusBarNotification> notifications = new ArrayList<StatusBarNotification>();
        //mCommandQueue是和IStatusBarService进行交互的IBinder
        mCommandQueue = new CommandQueue(this, iconList);
        //这里实际上获取的是StatusBarManagerService
        mBarService = IStatusBarService.Stub.asInterface(
                ServiceManager.getService(Context.STATUS_BAR_SERVICE));
        int[] switches = new int[7];
        ArrayList<IBinder> binders = new ArrayList<IBinder>();
        try {
            //通过StatusBarManagerService中的registerStatusBar来获取初始设置
            mBarService.registerStatusBar(mCommandQueue, iconList, notificationKeys, notifications,
                    switches, binders);
        } catch (RemoteException ex) {
            // If the system process isn't there we're doomed anyway.
        }
        ... ...

        // Set up the initial notification state
        //加载notifications,本文的分析主要从这里开始!
        N = notificationKeys.size();
        if (N == notifications.size()) {
            for (int i=0; i<N; i++) {
                addNotification(notificationKeys.get(i), notifications.get(i));
            }
        } else {
            Log.wtf(TAG, "Notification list length mismatch: keys=" + N
                    + " notifications=" + notifications.size());
        }

        ... ...
        lp.gravity = getStatusBarGravity();
        lp.setTitle("StatusBar");
        lp.packageName = mContext.getPackageName();
        lp.windowAnimations = R.style.Animation_StatusBar;
        //在Window上显示StatusBar界面
        WindowManagerImpl.getDefault().addView(sb, lp);
        mDoNotDisturb = new DoNotDisturb(mContext);
    }

    我们可以看到addNotification()方法主要完成Notification图标的加载。跟进去看看(因为我们分析的是Phone因此选择PhoneStatusBar),代码如下:

    
   public void addNotification(IBinder key, StatusBarNotification notification) {
        //该方法主要构造Notification Icons以及Expaned View
        StatusBarIconView iconView = addNotificationViews(key, notification);
        if (iconView == null) return;

        boolean immersive = false;
        try {
            //判断当前栈顶Activity是否具有android:immersive属性。该属性在Android 4.0中新加入的属性,如果该属性为true则该Activity不能被其他Activity或者Notification所打断。
            immersive = ActivityManagerNative.getDefault().isTopActivityImmersive();
            if (DEBUG) {
                Slog.d(TAG, "Top activity is " + (immersive?"immersive":"not immersive"));
            }
        } catch (RemoteException ex) {
        }
        //因为这里我们返回的是false,所以不会执行
        if (immersive) {
            if ((notification.notification.flags & Notification.FLAG_HIGH_PRIORITY) != 0) {
                Slog.d(TAG, "Presenting high-priority notification in immersive activity");
                // special new transient ticker mode
                // 1. Populate mIntruderAlertView

                ImageView alertIcon = (ImageView) mIntruderAlertView.findViewById(R.id.alertIcon);
                TextView alertText = (TextView) mIntruderAlertView.findViewById(R.id.alertText);
                alertIcon.setImageDrawable(StatusBarIconView.getIcon(
                    alertIcon.getContext(),
                    iconView.getStatusBarIcon()));
                alertText.setText(notification.notification.tickerText);

                View button = mIntruderAlertView.findViewById(R.id.intruder_alert_content);
                button.setOnClickListener(
                    new NotificationClicker(notification.notification.contentIntent,
                        notification.pkg, notification.tag, notification.id));

                // 2. Animate mIntruderAlertView in
                mHandler.sendEmptyMessage(MSG_SHOW_INTRUDER);

                // 3. Set alarm to age the notification off (TODO
  • 10
    点赞
  • 23
    收藏
    觉得还不错? 一键收藏
  • 5
    评论
Android 12的SystemUI下拉框中的亮度条的显示隐藏流程如下: 1. 下拉通知栏时,SystemUI会发送一个通知栏展开的广播,应用可以通过监听该广播来响应下拉通知栏的事件。 2. 在通知栏展开的回调方法中,应用可以根据当前的亮度调节状态来判断是否需要显示亮度条。 3. 如果需要显示亮度条,则可以获取亮度条的控件引用,并设置其可见性为可见。如果不需要显示亮度条,则将其可见性设置为不可见。 4. 当通知栏被收起时,SystemUI会发送一个通知栏收起的广播,应用可以通过监听该广播来响应通知栏收起的事件。 5. 在通知栏收起的回调方法中,应用可以将亮度条的可见性设置为不可见。 具体实现步骤可以参考以下代码示例: ``` public class MyNotificationListener extends NotificationListenerService { private SeekBar mBrightnessSeekBar; @Override public void onNotificationPosted(StatusBarNotification sbn) { // 检测到通知栏展开事件 if (sbn.getNotification().fullScreenIntent != null) { // 获取亮度调节状态 boolean isAdjustBrightness = isAdjustBrightness(sbn); // 如果需要显示亮度条 if (isAdjustBrightness) { // 获取亮度条控件的引用 mBrightnessSeekBar = findViewById(R.id.brightness_seekbar); // 设置亮度条的可见性为可见 mBrightnessSeekBar.setVisibility(View.VISIBLE); } } } @Override public void onNotificationRemoved(StatusBarNotification sbn) { // 检测到通知栏收起事件 if (sbn.getNotification().fullScreenIntent != null) { // 如果亮度条控件存在,将其可见性设置为不可见 if (mBrightnessSeekBar != null) { mBrightnessSeekBar.setVisibility(View.GONE); } } } // 判断是否需要显示亮度条 private boolean isAdjustBrightness(StatusBarNotification sbn) { Bundle extras = sbn.getNotification().extras; int flags = extras.getInt(Notification.EXTRA_FLAGS); return (flags & Notification.FLAG_AUTO_BRIGHTNESS) == 0 && (flags & Notification.FLAG_HIGH_PRIORITY) != 0; } } ``` 需要注意的是,具体实现可能会根据不同的设备厂商或Android版本而有所不同,需要根据具体情况进行调整。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值