欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

Android中activity从创建到显示的基本介绍

程序员文章站 2022-04-11 18:38:32
前言 说道android中的activity,如果你做过ios开发的话,activity类似于ios中的viewcontroller(视图控制器)。在应用中能看到的东西都...

前言

说道android中的activity,如果你做过ios开发的话,activity类似于ios中的viewcontroller(视图控制器)。在应用中能看到的东西都是放在活动中的。活动是安卓开发比较重要的东西,是用户交互和数据的入口。本篇博客要介绍的内容是活动的创建,活动的跳转与值的透传。

ios中的viewcontroller也是有自己的生命周期的,了解activity或者viewcontroller的生命周期是很有必要的,本文将详细的给大家介绍关于android中activity从创建到显示的相关内容,分享出来供大家参考学习,下面话不多说了,来一起看看详细的介绍吧。

activity是我们平常开发最常用的一个组件,我们有必要了解activity的创建以及显示的过程,这些应该作为我们的储备知识。

activity的创建

activity的创建以及初始化的过程是在activitythread#performlaunchactivity方法中,在这个方法中,有以下几个关键点,

  • 创建activity
  • activity#attach
  • instrumentation#callactivityoncreate
  • activity#performstart
  • instrumentation#callactivityonpostcreate

这个地方能看到activity生命周期的一小部分。我们需要对其中一些点进行学习,在这些点里面都有一些非常重要的操作。

创建activity的过程就不说了,直接反射。我们重点说下attach方法,

activity#attach

attach部分代码如下

mwindow = new phonewindow(this, window);
mwindow.setwindowcontrollercallback(this);
mwindow.setcallback(this);
mwindow.setonwindowdismissedcallback(this);
mwindow.getlayoutinflater().setprivatefactory(this);

在activity的attach方法中,很关键的一点就是初始化window,从这里就能看到,window的实现类,是phonewindow。phonewindow的创建对于我们后面的操作很重要。

activity#oncreate

public void callactivityoncreate(activity activity, bundle icicle,
  persistablebundle persistentstate) {
 preperformcreate(activity);
 activity.performcreate(icicle, persistentstate);
 postperformcreate(activity);
}

在activity.performcreate中,会调用activity的oncreate方法,这个是我们平常开发中非常熟悉的,在oncreate中,我们调用setcontentview去填充布局,并进行一些初始化操作

setcontentview

到了我们相当熟悉的setcontentview,在setcontentview中,会调用phonewindow的setcontentview方法。我们简单看下phonewindow的setcontentview

public void setcontentview(int layoutresid) {
 // note: feature_content_transitions may be set in the process of installing the window
 // decor, when theme attributes and the like are crystalized. do not check the feature
 // before this happens.
 if (mcontentparent == null) {
  installdecor();
 } else if (!hasfeature(feature_content_transitions)) {
  mcontentparent.removeallviews();
 }
 if (hasfeature(feature_content_transitions)) {
  final scene newscene = scene.getsceneforlayout(mcontentparent, layoutresid,
    getcontext());
  transitionto(newscene);
 } else {
  mlayoutinflater.inflate(layoutresid, mcontentparent);
 }
 mcontentparent.requestapplyinsets();
 final callback cb = getcallback();
 if (cb != null && !isdestroyed()) {
  cb.oncontentchanged();
 }
 mcontentparentexplicitlyset = true;
}

在phonewindoe的setcontentview方法中,会进行初始化decorview,并将我们设置的布局加载到contentparent中。installdecor的具体逻辑我们这里就不多说了。

resume过程

在activitythread#handleresumeactivity方法中,有两个关键点。

  • performresumeactivity
  • window#addview

performresumeactivity中会调用activity的performresume,performresume中会调用onresume,然后进入onresume声明周期中

我们重点说下addview以及后续的处理。

addview

wm.addview(decor, l);

这里的wm是windowmanager,是在attach法法中,通过setwindowmanager来实现初始化的,对应的实例为windowmanagerimpl的一个实例。那么,我们去看下windoemanageimpl的addview方法,在这个方法中,直接调用windowmanagerglobal的addview方法,我们关心的中点转移了。其中最关键的diam是如下几行。

root = new viewrootimpl(view.getcontext(), display);
view.setlayoutparams(wparams);
mviews.add(view);
mroots.add(root);
mparams.add(wparams);
root.setview(view, wparams, panelparentview);

首先创建一个viewrootimpl,然后setview。viewrootimpl#setview方法代码较长,我们能发现requestlayout这个方法,进去看下。

@override
public void requestlayout() {
 if (!mhandlinglayoutinlayoutrequest) {
  checkthread();
  mlayoutrequested = true;
  scheduletraversals();
 }
}

在这里,进行了首次线程检查。

void scheduletraversals() {
 if (!mtraversalscheduled) {
  mtraversalscheduled = true;
  mtraversalbarrier = mhandler.getlooper().getqueue().postsyncbarrier();
  mchoreographer.postcallback(
    choreographer.callback_traversal, mtraversalrunnable, null);
  if (!munbufferedinputdispatch) {
   scheduleconsumebatchedinput();
  }
  notifyrendererofframepending();
  pokedrawlockifneeded();
 }
}

choreographer,post了一个callback,这个callback是view刷新的核心所在。我们看下traversalrunnable的run方法,

final class traversalrunnable implements runnable {
 @override
 public void run() {
  dotraversal();
 }
}
void dotraversal() {
 if (mtraversalscheduled) {
  mtraversalscheduled = false;
  mhandler.getlooper().getqueue().removesyncbarrier(mtraversalbarrier);
  if (mprofile) {
   debug.startmethodtracing("viewancestor");
  }
  performtraversals();
  if (mprofile) {
   debug.stopmethodtracing();
   mprofile = false;
  }
 }
}

在dotraversal中,又会调用performtraversals方法,我们看下performtraversals方法是干啥的。这个方法非常非常的长,但是在这个方法中,有非常关键的performmeasure,performlayout,performdraw等方法,至此,进入的view的的三大过程,,三大过程之后,就显示在我们面前了。

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作具有一定的参考学习价值,如果有疑问大家可以留言交流,谢谢大家对的支持。