当前位置: 首页 > news >正文

深入分析 Android Activity (三)

深入分析 Android Activity (三)

1. Activity 的配置变化处理

当设备配置(如屏幕方向、语言、屏幕大小等)发生变化时,默认情况下,Android 会销毁并重新创建当前的 Activity。这种行为确保了新配置能够正确应用,但在某些情况下,重新创建 Activity 会带来性能问题或不必要的复杂性。

可以通过 android:configChanges 属性来指定当特定配置变化发生时,不销毁 Activity,而是调用 onConfigurationChanged 方法。

1.1 处理配置变化

AndroidManifest.xml 文件中声明需要处理的配置变化:

<activity android:name=".MyActivity"android:configChanges="orientation|screenSize|keyboardHidden">
</activity>

Activity 中覆盖 onConfigurationChanged 方法以处理配置变化:

@Override
public void onConfigurationChanged(Configuration newConfig) {super.onConfigurationChanged(newConfig);// Handle configuration changesif (newConfig.orientation == Configuration.ORIENTATION_LANDSCAPE) {// Handle landscape orientation} else if (newConfig.orientation == Configuration.ORIENTATION_PORTRAIT) {// Handle portrait orientation}
}

2. Activity 的存储和恢复状态

为了在配置变化、进程被终止或其他情况发生时保存和恢复 Activity 的状态,可以使用 onSaveInstanceStateonRestoreInstanceState 方法。

2.1 保存状态

onSaveInstanceState 方法在 Activity 即将被销毁时调用,用于保存临时状态信息:

@Override
protected void onSaveInstanceState(Bundle outState) {super.onSaveInstanceState(outState);outState.putString("key", "value");
}
2.2 恢复状态

onRestoreInstanceState 方法在 Activity 被重新创建后调用,用于恢复之前保存的状态信息:

@Override
protected void onRestoreInstanceState(Bundle savedInstanceState) {super.onRestoreInstanceState(savedInstanceState);String value = savedInstanceState.getString("key");
}

也可以在 onCreate 方法中恢复状态:

@Override
protected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);if (savedInstanceState != null) {String value = savedInstanceState.getString("key");}
}

3. Activity 与 Fragment 的通信

Fragment 是一个可重用的 UI 组件,能够在 Activity 中管理部分 UI 和逻辑。Fragment 可以独立于 Activity 管理自己的生命周期和状态。

3.1 通过接口进行通信

ActivityFragment 之间可以通过接口进行通信。在 Fragment 中定义一个接口,并在 Activity 中实现它:

public class MyFragment extends Fragment {private OnFragmentInteractionListener mListener;public interface OnFragmentInteractionListener {void onFragmentInteraction(String data);}@Overridepublic void onAttach(Context context) {super.onAttach(context);if (context instanceof OnFragmentInteractionListener) {mListener = (OnFragmentInteractionListener) context;} else {throw new RuntimeException(context.toString() + " must implement OnFragmentInteractionListener");}}// Call this method to send data to the activitypublic void sendDataToActivity(String data) {if (mListener != null) {mListener.onFragmentInteraction(data);}}
}

Activity 中实现接口方法:

public class MyActivity extends AppCompatActivity implements MyFragment.OnFragmentInteractionListener {@Overridepublic void onFragmentInteraction(String data) {// Handle interaction with the fragment}
}
3.2 通过 ViewModel 进行通信

使用 ViewModelLiveData 可以在 ActivityFragment 之间进行数据共享和通信,尤其是在 MVVM 架构中:

public class SharedViewModel extends ViewModel {private final MutableLiveData<String> selected = new MutableLiveData<String>();public void select(String item) {selected.setValue(item);}public LiveData<String> getSelected() {return selected;}
}

Activity 中:

public class MyActivity extends AppCompatActivity {private SharedViewModel viewModel;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);viewModel = new ViewModelProvider(this).get(SharedViewModel.class);viewModel.getSelected().observe(this, new Observer<String>() {@Overridepublic void onChanged(@Nullable String item) {// Update the UI}});}
}

Fragment 中:

public class MyFragment extends Fragment {private SharedViewModel viewModel;@Overridepublic View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {View view = inflater.inflate(R.layout.fragment_my, container, false);viewModel = new ViewModelProvider(requireActivity()).get(SharedViewModel.class);viewModel.getSelected().observe(getViewLifecycleOwner(), new Observer<String>() {@Overridepublic void onChanged(@Nullable String item) {// Update the UI}});return view;}
}

4. Activity 的窗口管理和视图层次结构

4.1 DecorView

DecorViewActivity 窗口中的最顶层视图容器,包含了状态栏、标题栏和内容区域。Window 类通过 setContentView 将视图层次结构添加到 DecorView 中。

@Override
protected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);
}
4.2 Window 和 WindowManager

Window 是一个抽象类,表示一个顶级窗口。在大多数情况下,Activity 使用 PhoneWindow 类,它是 Window 的具体实现。WindowManager 是一个系统服务,负责管理窗口。

通过 WindowWindowManager 可以控制窗口的布局参数:

Window window = getWindow();
WindowManager.LayoutParams params = window.getAttributes();
params.height = WindowManager.LayoutParams.MATCH_PARENT;
params.width = WindowManager.LayoutParams.MATCH_PARENT;
window.setAttributes(params);

5. Activity 的任务和返回栈(Back Stack)

Android 使用任务和返回栈来管理 Activity 的导航。每个任务由一个栈(返回栈)来管理 Activity

5.1 启动 Activity 的 Intent 标志

可以使用 Intent 标志来控制 Activity 的启动行为和返回栈。例如:

  • FLAG_ACTIVITY_NEW_TASK:在新的任务中启动 Activity
  • FLAG_ACTIVITY_CLEAR_TOP:如果目标 Activity 已经在栈中存在,则将其上面的所有 Activity 清除。
Intent intent = new Intent(this, MyActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(intent);
5.2 处理返回栈中的数据

可以使用 onActivityResult 方法处理从另一个 Activity 返回的数据:

@Override
protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {super.onActivityResult(requestCode, resultCode, data);if (requestCode == REQUEST_CODE && resultCode == RESULT_OK) {String result = data.getStringExtra("key");// Handle the result}
}

在启动 Activity 时可以传递请求代码:

Intent intent = new Intent(this, AnotherActivity.class);
startActivityForResult(intent, REQUEST_CODE);

总结

Android 的 Activity 设计涉及生命周期管理、启动模式、视图层次结构、与 Fragment 的交互、进程和线程模型、任务和返回栈管理、以及配置变化处理。理解这些关键概念和内部实现,有助于开发者创建高效、稳定和响应迅速的应用程序。通过灵活应用这些知识,可以提升应用程序的用户体验和性能。

相关文章:

深入分析 Android Activity (三)

深入分析 Android Activity (三) 1. Activity 的配置变化处理 当设备配置&#xff08;如屏幕方向、语言、屏幕大小等&#xff09;发生变化时&#xff0c;默认情况下&#xff0c;Android 会销毁并重新创建当前的 Activity。这种行为确保了新配置能够正确应用&#xff0c;但在某…...

电影《朝云暮雨》观后感

上周看了电影《朝云暮雨》&#xff0c;看完之后&#xff0c;感觉自己整个人都不太好了&#xff0c;也不是说电影太差&#xff0c;只是觉得电影没有传达正能量&#xff0c;让人很不舒服。 &#xff08;1&#xff09;演技在线 对于著名的演员“范伟”&#xff0c;或者说&#x…...

Isaac Sim仿真平台学习(1)认识Isaac Sim

0.前言 上一个教程中我们下载好了Isaac Sim&#xff0c;这一章我们将来简单了解一下Isaac Sim平台。 isaac Sim仿真平台安装-CSDN博客 1.Isaac Sim是啥&#xff1f; What Is Isaac Sim? — Omniverse IsaacSim latest documentation Isaac Sim是NVDIA Omniverse平台的机器…...

C++:vector基础讲解

hello&#xff0c;各位小伙伴&#xff0c;本篇文章跟大家一起学习《C&#xff1a;vector基础讲解》&#xff0c;感谢大家对我上一篇的支持&#xff0c;如有什么问题&#xff0c;还请多多指教 &#xff01; 如果本篇文章对你有帮助&#xff0c;还请各位点点赞&#xff01;&#…...

Grafana 路径遍历所有路径 CVE-2021-43798漏洞预警

简介​ ​Grafana是一个跨平台、开源的数据可视化网络应用程序平台。用户配置连接的数据源之后&#xff0c;Grafana可以在网络浏览器里显示数据图表和警告。 漏洞危害等级 高危 CVE 编号​ CVE-2021-43798 FOFA查询 ​app"Grafana" ​zoomeyes查询 ​app:"gr…...

基于Docker部署GitLab环境搭建

文件在D:\E\学习文档子目录压缩\专项进阶&#xff0c;如ngnix,webservice,linux,redis等\docker 建议虚拟机内存2G以上 1.下载镜像文件 docker pull beginor/gitlab-ce:11.0.1-ce.0 注意&#xff1a;一定要配置阿里云的加速镜像 创建GitLab 的配置 (etc) 、 日志 (log) 、数…...

初始化是什么

定义 初始化&#xff08;Initialization&#xff09;是指在计算机科学和软件开发中&#xff0c;将系统、变量、对象或其他可用组件设置为其初始状态或初始值的过程。这通常是在程序开始执行或组件第一次使用之前进行的&#xff0c;以确保其处于可预测和稳定的状态。 初始化的…...

Python图形界面(GUI)Tkinter笔记(九):用【Button()】功能按钮实现人机交互

在Tkinter库中,功能按钮(Button)是实现人机交互的一个非常重要的组件: 【一】主要可实现功能及意义: (1)响应用户交互: Button组件允许用户通过点击来触发某个事件或动作。当用户点击按钮时,可以执行一个指定的函数或方法。 (2)提供用户输入: Button组件是图形用户界面(G…...

linux 内核安装、切换版本,禁用内核更新

安装内核 版本5.15.0-105 sudo apt-get install linux-image-5.15.0-105-generic sudo apt-get install linux-headers-5.15.0-105-generic切换内核版本 #查看已安装内核版本 grep menuentry /boot/grub/grub.cfg sudo dpkg --get-selections |grep linux-image#修改文件/etc…...

充电桩中PE接地实时监测的一种电路.pdf

pdf下载链接&#xff1a;https://pan.baidu.com/s/18k8tEwa6h3WAOGJs3lAsTQ 提取码&#xff1a;Ronv...

鲲泰新闻丨第七届数字中国建设峰会正式启幕,神州鲲泰携手天翼云共筑智算云生态

2024年5月23日&#xff0c;由国家发展改革委、国家数据局、国家网信办、科技部、国务院国资委、福建省人民政府共同主办的“第七届数字中国建设峰会”在福建省福州市海峡国际会展中心盛大开幕。 数字中国建设峰会是展示数字中国建设成就的盛会&#xff0c;本次峰会以“释放数据…...

零基础学Java第二十二天之IO流之内存流,打印流,随机流

IO流之内存流&#xff0c;打印流&#xff0c;随机流 1、内存流 1、理解 内存流"&#xff08;Memory Stream&#xff09;在计算机编程中通常指的是一种特殊的数据流&#xff0c;它在内存中存储和操作数据&#xff0c;而不是在外部存储&#xff08;如硬盘、网络等&#xf…...

vue-router路由懒加载以及三种实现方式

什么是路由懒加载&#xff1f; 延迟加载或按需加载路由所对应的组件&#xff0c;而不是在应用初始化时就一次性加载所有组件。 路由懒加载做了什么事情&#xff1f; 主要作用是将路由对应的组件打包成一个个的js代码块 只有在这个路由被访问到的时候&#xff0c;才加载对应…...

Java轻松转换Markdown文件到Word和PDF文档

Markdown 凭借其简洁易用的特性&#xff0c;成为创建和编辑纯文本文档的常用选择。但某些时候我们需要更加精致的展示效果&#xff0c;例如在专业分享文档或打印成离线使用的纸质版时&#xff0c;就需要将Markdown文件以其他固定的文档格式呈现。通过将 Markdown 转换为 Word 和…...

【JAVA基础之内部类】匿名内部类

&#x1f525;作者主页&#xff1a;小林同学的学习笔录 &#x1f525;小林同学的专栏&#xff1a;JAVA之基础专栏 目录 1.内部类 1.1 概述 1.1.1 什么是内部类 1.1.2 什么时候使用内部类 1.2 内部类的分类 1.3 成员内部类 1.3.1 获取成员内部类对象的两种方式 1.3.2 经典面试…...

远动通讯屏的原理和应用

远动通讯屏的原理和应用 远动通讯屏&#xff0c;是一种集显示和远程控制于一体的智能化控制设备。它可以通过网络、通信线路等方式实现与远程设备的通讯和交互&#xff0c;从而实现远程监控和控制。 远动通讯屏实现远程控制的核心原理是基于PLC&#xff08;Programmable Logic …...

C++ (week4):Linux基础

文章目录 零、Linux简介1.配置环境2.Linux历史3.Linux模型 一、vim二、Linux命令行 (shell命令)1.常用命令与快捷键(1)常用命令①man命令&#xff1a;查看帮助手册 (2)快捷键 2.用户子系统(1)Linux用户(2)用户命令 3.文件子系统命令(1)目录命令1.创建文件&#xff1a;mkdir2.删…...

如何将手机中的音乐转移到 SD 卡上?轻松传输音乐

概括 如何将音乐从手机转移到 SD 卡&#xff1f;我们的智能手机可以充当个人点唱机&#xff0c;因此有效管理我们的音乐库变得至关重要。无论您是存储空间不足还是只是想整理您的音乐收藏&#xff0c;将音乐从手机传输到 SD 卡都是一个实用的解决方案。 在本指南中&#xff0…...

JKTECH柔性振动盘用途

柔性振动盘的作用与用途 在现代工业自动化领域&#xff0c;柔性振动盘凭借其独特的功能和广泛的应用场景&#xff0c;正逐渐成为生产线上的重要工具。柔性振动盘&#xff0c;又称柔性供料器&#xff0c;它结合了传统振动盘的高效性和现代自动化技术的灵活性&#xff0c;为各种…...

【职场心灵伴侣】文心一言智能体

【文心一言】智能体 写在最前面名称和简介&#xff1a;职场心灵伴侣AI生成头像添加工具智能体调优 &#x1f308;你好呀&#xff01;我是 是Yu欸 &#x1f30c; 2024每日百字篆刻时光&#xff0c;感谢你的陪伴与支持 ~ &#x1f680; 欢迎一起踏上探险之旅&#xff0c;挖掘无限…...

【运维】笔记本电脑风扇清洁

笔记本电脑是我们不可或缺的工具&#xff0c;无论是工作、学习还是娱乐。然而&#xff0c;随着时间的推移&#xff0c;笔记本电脑的性能可能会因为各种原因受到影响&#xff0c;尤其是散热问题。过热不仅会降低性能&#xff0c;还可能缩短硬件的寿命。最近&#xff0c;在使用我…...

3.1 掌握RDD的创建

在Apache Spark中&#xff0c;RDD&#xff08;Resilient Distributed Dataset&#xff09;是一个基本的、不可变的、分布式的和可分区的数据集。它能够自动进行容错处理&#xff0c;并支持在大规模集群上的并行操作。RDD之间存在依赖关系&#xff0c;可以实现管道化&#xff0c…...

深入理解 Java 中的 `volatile` 关键字:可见性与有序性的保障

深入理解 Java 中的 volatile 关键字&#xff1a;可见性与有序性的保障 volatile主要做了两个事情可见性保证 和 有序性 可见性保证就是&#xff1a; 对volatile的写操作会对其他线程可见。 简单来说我们A线程的修改了volatile的值&#xff0c;那么我B线程也可以看见。 有序…...

1077: 平衡二叉树的判定

解法&#xff1a; 平衡二叉树是一种特殊的二叉树&#xff0c;它满足以下两个条件&#xff1a; 左子树和右子树的高度差不超过1&#xff08;即&#xff0c;左右子树高度差的绝对值不超过1&#xff09;。左子树和右子树都是平衡二叉树。 后序遍历过程中每次判断左右子树高度差…...

深度学习-Softmax回归+损失函数+图像分类数据集

目录 Softmax回归回归 VS 分类Kaggle上的分类问题 从回归到多类分类回归分类从回归到多类分类-均方损失从回归到多类分类-无校验比例从回归到多类分类-校验比例 Softmax和交叉熵损失总结损失函数均方损失绝对值损失函数鲁棒损失 图像分类数据集通过框架中内置函数将FashionMNIS…...

【论文解读】Overview of the Scalable Video Coding Extension of the H.264/AVC Standard

介绍 该篇论文是一篇关于H.264/AVC标准可扩展视频编码(SVC)扩展的综述论文,由Heiko Schwarz、Detlev Marpe和Thomas Wiegand撰写,发表在《IEEE Transactions on Circuits and Systems for Video Technology》2007年9月第17卷第9期上。 论文解读 摘要: H.264/AVC视频编…...

【C语言】程序员自我修养之文件操作

【C语言】程序员自我修养之文件操作 &#x1f525;个人主页&#xff1a;大白的编程日记 &#x1f525;专栏&#xff1a;C语言学习之路 文章目录 【C语言】程序员自我修养之文件操作前言一.文件介绍1.1为什么使用文件1.2文件分类1.3二进制文件和文本文件 二.文件的打开和关闭2.…...

一种获取java代码结构的实现思路

一种获取java代码结构的实现思路 有时,我们需要获取java文件里的代码结构,即,只需要里面的class定义、方法声明、属性定义。不需要额外的方法实现 这里提供一下实现思路: 采用语法解析器Tree-sitter对java代码进行解析,获取里面的方法实现遍历第一步获取到的方法列表,在源…...

MySQL---增删改查

MySQL是一个流行的关系型数据库管理系统,它使用结构化查询语言(SQL)来管理数据库中的数据。以下是MySQL中增删改查(CRUD)操作的基本命令: 创建(Create): 创建新表:CREATE TABLE table_name (column1 datatype,column2 datatype,...PRIMARY KEY (column) );插入数据:…...

C#编程-.NET Framework使用工具类简化对象之间的属性复制和操作

在C#编程中&#xff0c;对象之间的属性复制和操作是一个常见的需求。为此&#xff0c;.NET Framework提供了多种实用工具库&#xff0c;如AutoMapper、ValueInjecter和ExpressMapper。这些库通过简化代码&#xff0c;提高了开发效率。本文将介绍这些工具库&#xff0c;比较它们…...