我是靠谱客的博主 热心海燕,最近开发中收集的这篇文章主要介绍SystemUI之状态栏StatusBar的加载,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

一:

在Android 9.0 SystemUI的启动这篇文章中介绍到,我们要启动的服务都是在config_systemUIServiceComponents中配置的。并通过java反射机制调用

 

我们的状态栏同样配置在内 

<item>com.android.systemui.SystemBars</item>

startServicesIfNeeded中关键代码块:


private void startServicesIfNeeded(String[] services) {

    for (int i = 0; i < N; i++) {
        String clsName = services[i];
        if (DEBUG) Log.d(TAG, "loading: " + clsName);
        log.traceBegin("StartServices" + clsName);
        long ti = System.currentTimeMillis();
        Class cls;
        try {
            cls = Class.forName(clsName);
            Object o = cls.newInstance();
            if (o instanceof SystemUI.Injector) {
                o = ((SystemUI.Injector) o).apply(this);
            }
            mServices[i] = (SystemUI) o;
        } catch(ClassNotFoundException ex){
            throw new RuntimeException(ex);
        } catch (IllegalAccessException ex) {
            throw new RuntimeException(ex);
        } catch (InstantiationException ex) {
            throw new RuntimeException(ex);
        }
 
        mServices[i].mContext = this;
        mServices[i].mComponents = mComponents;
        if (DEBUG) Log.d(TAG, "running: " + mServices[i]);
        mServices[i].start();

        if (mBootCompleted) {
            mServices[i].onBootCompleted();
        }
    }
}

当在for循环中遍历到com.android.systemui.SystemBars的时候,通过java反射找到SystemBars 然后先后调用其start()和onBootCompleted()方法,

来看看SystemBars的start方法

public class SystemBars extends SystemUI {
    private static final String TAG = "SystemBars";
    private static final boolean DEBUG = false;
    private static final int WAIT_FOR_BARS_TO_DIE = 500;

    // in-process fallback implementation, per the product config
    private SystemUI mStatusBar;

    @Override
    public void start() {
        if (DEBUG) Log.d(TAG, "start");
        createStatusBarFromConfig();//从配置文件中创建状态栏
    }

    @Override
    public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
        if (mStatusBar != null) {
            mStatusBar.dump(fd, pw, args);
        }
    }

    private void createStatusBarFromConfig() {
        if (DEBUG) Log.d(TAG, "createStatusBarFromConfig");
        //config_statusBarComponent定义在config.xml中其值为com.android.systemui.statusbar.phone.StatusBar
        final String clsName = mContext.getString(R.string.config_statusBarComponent);
        if (clsName == null || clsName.length() == 0) {
            throw andLog("No status bar component configured", null);
        }
        Class<?> cls = null;
        try {
            cls = mContext.getClassLoader().loadClass(clsName);
        } catch (Throwable t) {
            throw andLog("Error loading status bar component: " + clsName, t);
        }
        try {
            mStatusBar = (SystemUI) cls.newInstance();//这里的mStatusBar即为通过java反射获取的StatusBar
        } catch (Throwable t) {
            throw andLog("Error creating status bar component: " + clsName, t);
        }
        mStatusBar.mContext = mContext;
        mStatusBar.mComponents = mComponents;
        mStatusBar.start();//调用StatusBar.start()
        if (DEBUG) Log.d(TAG, "started " + mStatusBar.getClass().getSimpleName());
    }

    private RuntimeException andLog(String msg, Throwable t) {
        Log.w(TAG, msg, t);
        throw new RuntimeException(msg, t);
    }
}

start()方法调用createStatusBarFromConfig ,createStatusBarFromConfig的逻辑也比较简单,也是从config.xml中读取config_statusBarComponent的值,然后也是通过java反射获取得到StatusBar对象然后调用其start()方法;

 

那么继续看StatusBar具体是个啥?

StatusBar.start()-->createAndAddWindows()-->addStatusBarWindow()-->makeStatusBarView()-->inflateStatusBarWindow()

protected void makeStatusBarView() {
          final Context context = mContext;
          updateDisplaySize(); // populates mDisplayMetrics
          updateResources();
          updateTheme();
  
          inflateStatusBarWindow(context);
          mStatusBarWindow.setService(this);
          mStatusBarWindow.setOnTouchListener(getStatusBarWindowTouchListener());
          //..........
          //省略部分代码
          FragmentHostManager.get(mStatusBarWindow)
                  .addTagListener(CollapsedStatusBarFragment.TAG, (tag, fragment) -> {
                      CollapsedStatusBarFragment statusBarFragment =
                              (CollapsedStatusBarFragment) fragment;
                      statusBarFragment.initNotificationIconArea(mNotificationIconAreaController);
                      mStatusBarView = (PhoneStatusBarView) fragment.getView();
                      mStatusBarView.setBar(this);
                      mStatusBarView.setPanel(mNotificationPanel);
                      mStatusBarView.setScrimController(mScrimController);
                      mStatusBarView.setBouncerShowing(mBouncerShowing);
                      if (mHeadsUpAppearanceController != null) {
                          // This view is being recreated, let's destroy the old one
                          mHeadsUpAppearanceController.destroy();
                      }
                      mHeadsUpAppearanceController = new HeadsUpAppearanceController(
                              mNotificationIconAreaController, mHeadsUpManager, mStatusBarWindow);
                      setAreThereNotifications();
                      checkBarModes();
                      /// M: add for plmn display feature @{
                      attachPlmnPlugin();
                      ///@}
                  }).getFragmentManager()
                  .beginTransaction()
                  .replace(R.id.status_bar_container, new CollapsedStatusBarFragment(),
                          CollapsedStatusBarFragment.TAG)
                   .commit(); 
}
protected void inflateStatusBarWindow(Context context) {
         mStatusBarWindow = (StatusBarWindowView) View.inflate(context,
                  R.layout.super_status_bar, null);
}

super_status_bar.xml--->FrameLayout(@+id/status_bar_container)// 这个就是我们状态栏的容器,它是由CollapsedStatusBarFragment来填充的。

replace(R.id.status_bar_container, new CollapsedStatusBarFragment(),
                          CollapsedStatusBarFragment.TAG)

来看下CollapsedStatusBarFragment是如何填充status_bar_container

      @Override
      public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container,
              Bundle savedInstanceState) {
          return inflater.inflate(R.layout.status_bar, container, false);
      }

CollapsedStatusBarFragment 加载的布局是status_bar.xml

ImageView    android:id="@+id/notification_lights_out"     未知

LinearLayout android:id="@+id/status_bar_contents"

       ViewStub      android:id="@+id/operator_name"     运营商名称

       <include layout="@layout/heads_up_status_bar_layout" />   未知

       com.android.systemui.statusbar.policy.Clock      android:id="@+id/clock"      //时间

       com.android.systemui.statusbar.AlphaOptimizedFrameLayout  android:id="@+id/notification_icon_area"   通知图标区域

        android.widget.Space    android:id="@+id/cutout_space_view"   未知

        com.android.keyguard.AlphaOptimizedLinearLayout    android:id="@+id/system_icon_area"    系统图标

    ViewStub  android:id="@+id/emergency_cryptkeeper_text"   未知

 

图标的初始化:

 

public class StatusBarManagerService extends IStatusBarService.Stub {

StatusBar.start()-->

741          // Set up the initial icon state
742          int N = iconSlots.size();
743          for (int i=0; i < N; i++) {
744              mCommandQueue.setIcon(iconSlots.get(i), icons.get(i));
745          }

 

 

最后

以上就是热心海燕为你收集整理的SystemUI之状态栏StatusBar的加载的全部内容,希望文章能够帮你解决SystemUI之状态栏StatusBar的加载所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(40)

评论列表共有 0 条评论

立即
投稿
返回
顶部