当前标签 / Android / 总共65篇

Android入门到进阶视频教程(17~20)

Android 视频教程连载中...

从今天开始我们来研究一下 Android 中的本地持久化数据,在 Android 中本地持久化的主要方式有如下三种:

  • SharePreference : key-value 形式,主用于数据较少的配置信息的存储。
  • SQLite :一些比较复杂的数据结构,特别适合对象存储。
  • File Save : 比较大的文件(例如日志,图片缓存,apk包等)或者某些特殊的配置文件。

本次视频的所有主题都有对应的示例代码,可以在这里下载: https://github.com/lxqxsyu/InnerShareCode2

第十七讲:SharePreference【上】

SharePreference 是我们平时开发过程中最常用的一种持久化存储方式,它是一种键值对的存储方式(key-value),可以存储基本数据类型。支持的数据类型有:String, boolean, float, int, long, Set<String>.

阅读更多

Android入门到进阶视频教程(13~16)

Android 视频教程连载中...

在前面的视频中我们对 Android 的项目界面部分有了一个基础认识并且可以实现一些相对简单的界面了,接下来我们先来看看 Gradle 项目构建过程,随后我特意准备了两节关于 Java 扫盲的课程,如果你对 Java 基础不是很熟悉或者有些生疏可以观看此视频,帮助你对后面课程的理解。

第十三讲:项目构建过程概述

我们前面编写的 Android 源码要执行打包并安装到手机(或模拟器)上到底经历了怎样的一个过程,看完这个视频你就会明白。

阅读更多

Android入门到进阶视频教程(9~12)

Android 视频教程连载中...

今天开放的四节 Android 视频教程都是关于界面布局相关的,基于这些基础布局知识你可以完成很多甚至是复杂的界面样式。

第九讲:线性布局和相对布局

还是那个大家常说的 2,8 定律,线性布局和相对布局可能是你以后开发中使用率最高的布局(暂且不说约束布局),所以说不要看它们两个简单,它们是开启布局大门的重要环节,掌握它并熟练应用它。

阅读更多

Android入门到进阶视频教程(5~8)

Android 视频教程连载中...

今天开放了四节免费课程,关注此博客,后续会不定期开放新的免费课程,有任何疑问和问题可以在此留言。

第五讲:编辑界面样式和Android尺寸单位

Android 中的单位尺寸是一个比较重要的知识点,理解屏幕分辨率、屏幕密度 以及 和尺寸之间的换算关系很重要。

阅读更多

Android 音频播放器应用开发

前言

音频播放和视频播放还是有很多本质的区别的,例如视频播放需要和对应的界面(Activity 或者 Fragment)绑定,因为它需要显示内容,而音频播放不需要显示内容,所以通常和对应的 Service 绑定。但是它们也有一些共同的行为抽象和播放过程抽象,也就是说有共同的控制逻辑。

音视频控制逻辑

MediaController(媒体控制器)负责隔离界面和媒体播放器,来实现控制隔离。它只会对 UI 暴露部分的控制接口 API 例如播放、暂停等。当 Media Session(媒体会话)的状态发送变化的时候也会通过回调的方式传递到媒体控制器。而媒体会话则负责维护具体的播放逻辑,例如播放,暂停等,它负责和具体的 Player(播放器)之间进行通信。

阅读更多

Android入门到进阶视频教程(1~4)

Android 视频教程连载中...

第一讲:自我介绍和如何学习 Android

如何开始并学好一个技术栈是一个比较普遍的问题,对所有技术栈都适用,我的观点是从宏观到微观,先要从整体上对这个技术栈的方向、特点、用途等有一个总体认识,然后再进入到技术细节,这样才不至于盲人摸象。

阅读更多

Android内部分享[7]——系统广播和服务

什么是 Service

Service 是 Android 中一个可以长时间在后台运行的组件,Service 可由其他组件启动,而且就算用户切换到其它应用,服务仍然可以在后台继续运行。此外,组件可以绑定到服务,以与之进行交互,甚至是执行进程间通信 (IPC)。 例如,服务可以处理网络事务、播放音乐,执行文件 I/O 或与内容提供程序交互,而所有这一切均可在后台进行。

Service 基本上分为两种形式:

  1. startService

当应用组件(如 Activity)通过调用 startService() 启动服务时,服务即处于“启动”状态。一旦启动,服务即可在后台无限期运行,即使启动服务的组件已被销毁也不受影响。 已启动的服务通常是执行单一操作,而且不会将结果返回给调用方。例如,它可能通过网络下载或上传文件。 操作完成后,服务会自行停止运行。

  1. bindService

当应用组件通过调用 bindService() 绑定到服务时,服务即处于“绑定”状态。绑定服务提供了一个客户端-服务器接口,允许组件与服务进行交互、发送请求、获取结果,甚至是利用进程间通信 (IPC) 跨进程执行这些操作。 仅当与另一个应用组件绑定时,绑定服务才会运行。 多个组件可以同时绑定到该服务,但全部取消绑定后,该服务即会被销毁。

而且我们的服务可以同时以上面的两种方式运行,也就是说,它既可以是启动服务(以无限期运行),也允许绑定。问题只是在于您是否实现了一组回调方法:onStartCommand()(允许组件启动服务)和 onBind()(允许绑定服务)。

阅读更多

Android内部分享[6]——列表和适配器详解

列表复用

列表的一个重大职责是复用 View, 因为我们的可见区域是有限的,要不断的回收再利用。我画了一张列表在手机上展示的关系示意图:

列表展示重用示意图

如上图,手机屏幕是呈现给用户的窗口,这个窗口是一个固定宽高的区域(上图绿色区域),而一个列表是可以无限长度的(分页加载),我们不需要创建这么多的子 View ,这样极大的浪费内存。所以这里我们可以利用适配器来完成列表(ListView)的列表项(item)的复用。在屏幕滚动的同时,如上面箭头所示意那样我们可以将看过的 View 拿来继续复用,这样可以保证列表项是无限的,而我们创建的 View 是有限的几个即可。

阅读更多

Android内部分享[5]——后台线程和多线程的使用

概述

我们前面提到过,在 Android 中有一个核心线程 UI 线程(或者叫主线程),负责处理 UI 渲染(包括去测量和绘制图形),协调用户交互和生命周期事件等。如果这个主线程中发送了太多的耗时操作和工作就会影响用户体验,我们的应用就会变得缓慢或者无响应,甚至出现 ANR(Application Not Responding),所以对我们开发者而言应该将那些比较耗时或者大段很多的操作委托给其他线程来处理,这些线程(非 UI 线程)在后台帮我们处理完成后再交给我们主线程来重新渲染界面。或者有时候我们需要做一些非用户交互的任务,比如定时去和服务器同步一些数据,像这种后台任务也应该直接交给非主线程,让它们在后台帮我们完成。

需要我们特别注意的是,我们在使用多线程来处理任务的时候要考虑到后台任务可能会消耗过多的资源,例如RAM 和电量,在 Android 系统中为了最大的优化系统性能和电池电量,当用户看不到应用在前台的时候会限制后台线程的工作,有可能会杀死这些线程。

Android 6.0 (API 23) 中引入了一个叫 Doze 的模式和应用程序待机处理, 当我们的屏幕关闭(也就是我们通常说的锁屏)且设备静止的时候, Doze 模式会限制应用程序的一些行为,例如网络不可访问, 线程执行的任务停止等。在 Android 7.0 和 8.0 之后更是进一步限制了后台行为,例如在后台获取位置将被禁止,通过 wakelocks 唤醒应用也被禁止。在 Android 9.0 之后引入了 App Standby Buckets, 应用程序对资源的请求根据应用程序使用模式进行动态优先级排序

阅读更多

Android内部分享[4]——Intent 和 Intent 过滤器

概述

前面我们已经对 Android 中的界面跳转和本地存储有了一定的认识,接下来我们来详细研究一下 Android 中的意图(Intent),理解它有助于我们后续理解系统广播和服务。

我们先来回顾一下前面的界面跳转代码:

Intent intent = new Intent(MainActivity.this, SecondActivity.class);
startActivity(intent);

可以看到 Intent 就像一座桥梁,来实现从一个界面到另一个界面的切换,事实上上面的是显式的 Intent,我们很明确我们即将要跳转到的页面,还有一种意图是不可知不确定的,或者说在绑定意图的时候不是固定的某个具体的 Activity, 例如:

Intent intent = new Intent();
sendIntent.setAction(Intent.ACTION_SEND);
sendIntent.putExtra(Intent.EXTRA_TEXT, textMessage);
sendIntent.setType("text/plain");
startActivity(intent);

这个时候我们的 Intent (意图)可能指定的不是一个界面了,有可能是多个界面,只要我们的 Activity 含 ACTION_SEND 操作并携带 text/plain 数据就会被调起。如果只有一个应用能够处理,则该应用将立即打开并为其提供 Intent。 如果多个 Activity 接受 Intent,则系统将显示一个对话框,使用户能够选取要使用的应用。

多个意图响应

阅读更多

Android内部分享

本书籍是公司内部Android技术分享培训的整理内容,部分章节有对应的示例代码,均可下载。另外我正在更新本系列对应的视频教程:

Android从入门到进阶全套视频教程--点击跳转

水寒(作者)在写作和整理过程中花费了大量时间和精力,另外服务器费用也是一笔不小的开支,如果你觉得我的文章和书籍对你有所帮助,可以请我喝杯咖啡或者农夫山泉:

如果在阅读过程中有任何疑问,可以去作者博客对应页面留言, 你也可以从我的体系树中找到对应文章。

阅读更多

Android内部分享[3]——网络请求和图片加载

概述

前两次分享已经对 Android 内部的组件和存储有了认识,接下来研究一下 Android 内从服务器如何请求数据,如何加载网络图片,对图片如何裁切和缓冲,以及近几年来比较流行的图片加载框架。

这次分享我们通过一个简单的案例贯穿始终来探究实现过程比较偏向实践,所以下面代码比较多。

接口文档:

请求方式:POST 请求地址:https://api.apiopen.top/getImages

Body参数名类型必需描述
pagestring页码(传0或者不传会随机推荐)
countstring返回总数

返回示例:

{
    "code": 200,
    "message": "成功!",
    "result": [
        {
            "id": 666,
            "time": "2018-12-14 04:00:01",
            "img": "https://ws1.sinaimg.cn/large/0065oQSqgy1fy58bi1wlgj30sg10hguu.jpg"
        },
        {
            "id": 665,
            "time": "2018-11-29 04:00:00",
            "img": "https://ws1.sinaimg.cn/large/0065oQSqgy1fxno2dvxusj30sf10nqcm.jpg"
        },
        {
            "id": 664,
            "time": "2018-11-20 04:00:01",
            "img": "https://ws1.sinaimg.cn/large/0065oQSqgy1fxd7vcz86nj30qo0ybqc1.jpg"
        },
        {
            "id": 663,
            "time": "2018-11-07 04:00:01",
            "img": "https://ws1.sinaimg.cn/large/0065oQSqgy1fwyf0wr8hhj30ie0nhq6p.jpg"
        },
        {
            "id": 662,
            "time": "2018-10-23 04:00:00",
            "img": "https://ws1.sinaimg.cn/large/0065oQSqgy1fwgzx8n1syj30sg15h7ew.jpg"
        }
    ]
}

阅读更多

Android内部分享[2]——数据存储和绑定

概述

回顾上一次分享,我们已经对 Android 的整体发展,体系结构,工程搭建,界面布局,组件注册,生命周期有了一定认识,接下来研究一下在 Android 中数据如何存储,如何将数据和界面控件绑定。

Android 中的本地存储主要有三种方式:

  • SharePreference : key-value 形式,主用于数据较少的配置信息的存储。
  • SQLite :一些比较复杂的数据结构,特别适合对象存储。
  • File Save : 比较大的文件(例如日志,图片缓存,apk包等)或者某些特殊的配置文件。

另外还有 ContentProvider 用于进程间数据共享,不是很常用,下面会简要叙述其原理和 FileProvider 的使用。

上面描述的都是数据持久化的方式,在某些特殊情况下我们可能需要用到内存缓存,使用一些弱(WeakReference)软(SoftReference)引用技术和 LruCache 内存缓存类来实现,这里不做讨论。

阅读更多

Android内部分享[1]——概述和起步

概述

如何开始并学好一个技术栈是一个比较普遍的问题,对所有技术栈都适用,我的观点是从宏观到微观,先要从整体上对这个技术栈的方向、特点、用途等有一个总体认识,然后再进入到技术细节,这样才不至于盲人摸象。

从整体上我们先来认识一下我们要学习的Android技术是要学习哪些方面:

  1. 平台环境(Android系统、Linux系统、浏览器、数据库)。
  2. 平台所支持的计算机语言(Java、C/C++、Kotlin)和基于平台的操作API(JDK、SDK、JNI)。
  3. 通信协议(TCP/IP [Socket], HTTP, MQTT, Modbus, 串口)。
  4. 软件工程的设计和重构思维(整体结构 [MVP, MVVP, MVC]、组件化、模块化、解耦性、健壮性、可迭代性),学习使用一些优秀框架(RxJava, Retrofit, Okttp, Fresco, Glide, … 很多)。

阅读更多

Android项目优化检测工具Lint

前言

我们在实现Android界面功能之外还需要考虑结构对性能、维护成本的影响。例如,如果 XML 资源文件包含未使用的命名空间,则不仅占用空间,还会导致不必要的额外处理。其他结构问题,例如使用目标 API 版本不支持的已弃用的元素或 API 调用等,可能导致代码无法正常运行。Android Studio 提供一个名为 Lint 的代码扫描工具,可帮助您发现并纠正代码结构质量的问题,而无需实际执行该应用,也不必编写测试用例。

Lint工作流程

该工具会报告其检测到的每个问题并提供该问题的描述消息和严重级别,以便您可以快速确定需要优先进行哪些关键改进。此外,您可以调低问题的严重级别,忽略与项目无关的问题,也可以调高严重级别,以突出特定问题。

Lint 工具可检查您的 Android 项目源文件是否包含潜在错误,以及在正确性、安全性、性能、易用性、便利性和国际化方面是否需要优化改进。

Lint 工具的代码扫描工作流

可以看到源文件(包括Java和XML)、图标、配置文件等,通过 lint.xml 中的问题严重级别配置,然后执行 Lint 命令工具对代码静态扫码。

阅读更多