『HarmonyOS』Page与AbilitySlice的生命周期

2年前 (2023) 程序员胖胖胖虎阿
268 0 0

👨‍🎓作者简介:一位喜欢写作,计科专业大二菜鸟

🏡个人主页:starry陆离

🕒首发日期:2022年8月8日星期一
📚订阅专栏:『HarmonyOS』

🍁每日推荐:牛客网-面试神器
『HarmonyOS』Page与AbilitySlice的生命周期
如果文章有帮到你的话记得点赞👍+收藏💗支持一下哦

『HarmonyOS』Page与AbilitySlice的生命周期

『HarmonyOS』Page与AbilitySlice的生命周期

  • 1.Page的生命周期
  • 2.AbilitySlice生命周期
  • 3.Page与AbilitySlice生命周期关联
  • 4.Page与AbilitySlice生命周期的例子
  • 5.MainAbilitySlice
  • 6.PayAbilitySlice

系统管理或用户操作等行为均会引起Page实例在其生命周期的不同状态之间进行转换。Ability类提供的回调机制能够让Page及时感知外界变化,从而正确地应对状态变化(比如释放资源),这有助于提升应用的性能和稳健性。

生命周期(百度百科)

生命周期就是指一个对象的生老病死。

​ 生命周期(Life Cycle)的概念应用很广泛,特别是在政治、经济、环境、技术、社会等诸多领域经常出现,其基本涵义可以通俗地理解为 “从摇篮到坟墓”(Cradle-to-Grave的整个过程。对于某个产品而言,就是从自然中来回到自然中去的全过程,也就是既包括制造产品所需要的原材料的采集、加工等生产过程,也包括产品贮存、运输等流通过程,还包括产品的使用过程以及产品报废或处置等废弃回到自然过程,这个过程构成了一个完整的产品的生命周期。

1.Page的生命周期

Page Ability是主要负责页面交互的,所以Page有几个状态:可见,可交互,不可见,销毁等等。每一个状态,都有一个生命周期函数和它对应。Page生命周期的不同状态转换及其对应的回调如下图所示:

『HarmonyOS』Page与AbilitySlice的生命周期

1.onStart()

当系统首次创建Page实例时,触发该回调。对于一个Page实例,该回调在其生命周期过程中仅触发一次,Page在该逻辑后将进入INACTIVE状态。开发者必须重写该方法,并在此配置默认展示的AbilitySlice。

@Override
public void onStart(Intent intent) {
    super.onStart(intent);
    super.setMainRoute(MainAbilitySlice.class.getName());
}

2.onActive()

Page会在进入INACTIVE状态后来到前台,然后系统调用此回调。Page在此之后进入ACTIVE状态,该状态是应用与用户交互的状态Page将保持在此状态,除非某类事件发生导致Page失去焦点,比如用户点击返回键或导航到其他Page。当此类事件发生时,会触发Page回到INACTIVE状态,系统将调用onInactive()回调。此后,Page可能重新回到ACTIVE状态,系统将再次调用onActive()回调。因此,开发者通常需要成对实现onActive()和onInactive(),并在onActive()中获取在onInactive()中被释放的资源。

3.onInactive()
**当Page失去焦点时,系统将调用此回调,**此后Page进入INACTIVE状态。开发者可以在此回调中实现Page失去焦点时应表现的恰当行为。

4.onBackground()
如果Page不再对用户可见,系统将调用此回调通知开发者用户进行相应的资源释放,此后Page进入BACKGROUND状态。开发者应该在此回调中释放Page不可见时无用的资源,或在此回调中执行较为耗时的状态保存操作。

5.onForeground()
处于BACKGROUND状态的Page仍然驻留在内存中,当重新回到前台时(重新导航到此Page),系统将先调用onForeground()回调通知开发者,而后Page的生命周期状态回到INACTIVE状态。开发者应当在此回调中重新申请在onBackground()中释放的资源,最后Page的生命周期状态进一步回到ACTIVE状态,系统将通过onActive()回调通知开发者用户。

6.onStop()

系统将要销毁Page时,将会触发此回调函数,通知用户进行系统资源的释放。销毁Page的可能原因包括以下几个方面:

  • 用户通过系统管理能力关闭指定Page,例如使用任务管理器关闭Page。
  • 用户行为触发Page的terminateAbility()方法调用,例如使用应用的退出功能。
  • 配置变更导致系统暂时销毁Page并重建。
  • 系统出于资源管理目的,自动触发对处于BACKGROUND状态Page的销毁。

2.AbilitySlice生命周期

AbilitySlice作为Page的组成单元,其生命周期是依托于其所属Page生命周期的AbilitySlice和Page具有相同的生命周期状态和同名的回调,当Page生命周期发生变化时,它的AbilitySlice也会发生相同的生命周期变化。此外,AbilitySlice还具有独立于Page的生命周期变化,这发生在同一Page中的AbilitySlice之间导航时,此时Page的生命周期状态不会改变。

AbilitySlice生命周期回调与Page的相应回调类似,因此不再赘述。由于AbilitySlice承载具体的页面,开发者必须重写AbilitySlice的onStart()回调,并在此方法中通过setUIContent()方法设置页面,如下所示:

    @Override
    protected void onStart(Intent intent) {
        super.onStart(intent);

        setUIContent(ResourceTable.Layout_main_layout);
    }

AbilitySlice实例创建和管理通常由应用负责,系统仅在特定情况下会创建AbilitySlice实例。例如,通过导航启动某个AbilitySlice时,是由系统负责实例化;但是在同一个Page中不同的AbilitySlice间导航时则由应用负责实例化。

3.Page与AbilitySlice生命周期关联

当AbilitySlice处于前台且具有焦点时,其生命周期状态随着所属Page的生命周期状态的变化而变化。

当一个Page拥有多个AbilitySlice时,例如:MyAbility下有FooAbilitySlice和BarAbilitySlice,当前FooAbilitySlice处于前台并获得焦点,并即将导航到BarAbilitySlice,在此期间的生命周期状态变化顺序为:

  1. FooAbilitySlice从ACTIVE状态变为INACTIVE状态
  2. BarAbilitySlice则从INITIAL状态首先变为INACTIVE状态,然后变为ACTIVE状态(假定此前BarAbilitySlice未曾启动)。
  3. FooAbilitySlice从INACTIVE状态变为BACKGROUND状态

对应两个slice的生命周期方法回调顺序为:

FooAbilitySlice.onInactive() --> BarAbilitySlice.onStart() --> BarAbilitySlice.onActive() --> FooAbilitySlice.onBackground()

在整个流程中,MyAbility始终处于ACTIVE状态。但是,当Page被系统销毁时,其所有已实例化的AbilitySlice将联动销毁,而不仅是处于前台的AbilitySlice。

4.Page与AbilitySlice生命周期的例子

​ 为了更好地理解Page与AbilitySlice的生命周期,我们将创建一个PageAndAbilitySliceLifeCycle的应用作为演示。

此应用中包含两个Slice,MainAbilitySlicePayAbilitySlice分别代表主页界面和支付界面

我们运行项目首先创建主页界面,主页界面的onStart()onActive()方法分别调用,MainAbilitySlice处于与用户交互的状态

『HarmonyOS』Page与AbilitySlice的生命周期

用户点击跳转到支付界面,首先MainAbilitySlice界面失去焦点,进入onInactive()状态;马上创建了一个PayAbilitySlice界面,onStart()方法被调用,紧接着PayAbilitySlice进入onActive()状态,此时用户可见的是支付界面,而MainAbilitySlice调用onBackground()方法,此Slice不再对用户可见,通知开发者释放资源

『HarmonyOS』Page与AbilitySlice的生命周期

在这个demo中,系统没有销毁MainAbilitySlice,而是将其存入幕后不再让用户可见,因为我们可以看到日志台并没有打印onStop()方法;也就是说我们每点击一次跳转,就创建一个新的Slice(调用onStart()方法)。

『HarmonyOS』Page与AbilitySlice的生命周期

这一次我们不点击跳转了,而是点击虚拟机上的返回按键,可以看到这一次打印了五条日志。首先PayAbilitySlice失去焦点,进入onInactive状态,而MainAbilitySlice从后台资源中重新回到前台,(这里也再次证明了我们的MainAbilitySlice是没有被销毁的)然后就如用户可见的onActive状态;而用户不可见的PayAbilitySlice调用onBackground方法进入后台资源中,最终被onStop()方法销毁,至此PayAbilitySlice度过了它的一个生命周期

5.MainAbilitySlice

package com.hnucm.hmos0501_pageandabilityslicelifecycle.slice;

import com.hnucm.hmos0501_pageandabilityslicelifecycle.ResourceTable;
import ohos.aafwk.ability.AbilitySlice;
import ohos.aafwk.content.Intent;
import ohos.agp.components.Button;
import ohos.hiviewdfx.HiLog;
import ohos.hiviewdfx.HiLogLabel;

public class MainAbilitySlice extends AbilitySlice {

    static final HiLogLabel label = new HiLogLabel(HiLog.LOG_APP, 0x00201, "MainAbilitySlice"); //MY_MODULE=0x00201
    @Override
    public void onStart(Intent intent) {

        HiLog.info(label, "MainAbilitySlice---->onStart");
        super.onStart(intent);
        super.setUIContent(ResourceTable.Layout_ability_main);
        Button toPayBtn=findComponentById(ResourceTable.Id_toPayBtn);
        toPayBtn.setClickedListener(listener-> present(new PayAbilitySlice(),new Intent()));
    }

    @Override
    protected void onInactive() {
        super.onInactive();
        HiLog.info(label, "MainAbilitySlice---->onInactive");
    }

    @Override
    protected void onBackground() {
        super.onBackground();

        HiLog.info(label, "MainAbilitySlice---->onBackground");

    }

    @Override
    protected void onStop() {
        super.onStop();
        HiLog.info(label, "MainAbilitySlice---->onStop");

    }

    @Override
    public void onActive() {
        super.onActive();
        HiLog.info(label,  "MainAbilitySlice---->onActive");
    }
    @Override
    public void onForeground(Intent intent) {
        super.onForeground(intent);
        HiLog.info(label, "MainAbilitySlice---->onForeground");
    }
}

6.PayAbilitySlice

package com.hnucm.hmos0501_pageandabilityslicelifecycle.slice;

import com.hnucm.hmos0501_pageandabilityslicelifecycle.ResourceTable;
import ohos.aafwk.ability.AbilitySlice;
import ohos.aafwk.content.Intent;
import ohos.agp.components.Button;
import ohos.hiviewdfx.HiLog;
import ohos.hiviewdfx.HiLogLabel;

public class PayAbilitySlice extends AbilitySlice {

    static final HiLogLabel label = new HiLogLabel(HiLog.LOG_APP, 0x00201, "PayAbilitySlice"); //MY_MODULE=0x00201

    @Override
    public void onStart(Intent intent) {

        super.onStart(intent);
        super.setUIContent(ResourceTable.Layout_ability_pay);

        HiLog.info(label, "PayAbilitySlice---->onStart");


        Button backMainBtn=findComponentById(ResourceTable.Id_backMainBtn);
        backMainBtn.setClickedListener(listener-> present(new MainAbilitySlice(),new Intent()));
    }

    @Override
    public void onActive() {
        super.onActive();
        HiLog.info(label, "PayAbilitySlice---->onActive");

    }

    @Override
    protected void onInactive() {
        super.onInactive();
        HiLog.info(label, "PayAbilitySlice---->onInactive");

    }

    @Override
    protected void onBackground() {
        super.onBackground();
        HiLog.info(label, "PayAbilitySlice---->onBackground");


    }

    @Override
    protected void onStop() {
        super.onStop();
        HiLog.info(label, "PayAbilitySlice---->onStop");

    }

    @Override
    public void onForeground(Intent intent) {
        super.onForeground(intent);
        HiLog.info(label, "PayAbilitySlice---->onForeground");

    }
}

🍁每日推荐:牛客网-面试神器
『HarmonyOS』Page与AbilitySlice的生命周期

版权声明:程序员胖胖胖虎阿 发表于 2023年3月20日 下午11:00。
转载请注明:『HarmonyOS』Page与AbilitySlice的生命周期 | 胖虎的工具箱-编程导航

相关文章

暂无评论

暂无评论...