【Android】ViewModel+LiveData:更加直接地控制视图的方式
LiveData
前言
ViewModel通过将UI data保存在ViewModel类实例的内部,从而大大地将MVC中的 Controller 与 View 分割开,并且通过ViewModel,我们可以较为方便地解决Activity生命周期发生改变(比如由屏幕旋转引起的生命周期重建)时,UI data的保存以及重现问题。
下图展示了MVC中Controller与View的关系。简而言之就是,Controller负责处理UI data,通过reference传递给ViewGroup。

在使用了ViewModel后,Controller与View的关系大致可以用下图中的左半部分表示:

虽然将UI data交给ViewModel保存处理的方式解决了生命周期变化的问题,但我们仍需要通过Controller传递UI data给View。LiveData的出现,进一步地降低了Controller与View之间地耦合。通过LiveData我们可以不使用Controller,直接将LiveData数据传递给View。如上图右半部分所示。
使用ViewModel+LiveData
在本例中,我们通过ViewModel+LiveData控制视图中的一个点赞图形,点击点赞图形,视图中的TextView的值便会加一。
Step 1:创建继承自ViewModel类的子类。
package com.hello.livedatatest;
import androidx.lifecycle.MutableLiveData;
import androidx.lifecycle.ViewModel;
public class MyViewModel extends ViewModel {
/* MutableLiveData为一种容器,需要按照以下方法创建 */
private MutableLiveData<Integer> thumbup;
/* MutableLiveData中地数据无法直接赋值,需通过setValue或getaValue赋值或取值 */
/* 获取thumbup的值 */
public MutableLiveData<Integer> getThumbup() {
if (thumbup==null){
thumbup = new MutableLiveData<>();
thumbup.setValue(0);
}
return thumbup;
}
/* thumbup值加一 */
public MutableLiveData<Integer> setThumbup(){
thumbup .setValue(thumbup.getValue()+1);
return thumbup;
}
}
Step 2:创建实例并绑定,为LiveData创建Ovserve方法
package com.hello.livedatatest;
import androidx.appcompat.app.AppCompatActivity;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProvider;
import android.os.Bundle;
import android.view.View;
import android.widget.ImageView;
import android.widget.TextView;
/* 引入ViewModelProviders类,注意同时引入该类所需依赖 */
import androidx.lifecycle.ViewModelProviders;
public class MainActivity extends AppCompatActivity {
/* 创建实例 */
MyViewModel myViewModel;
ImageView imageView;
TextView textView;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
imageView = findViewById(R.id.imageView);
textView = findViewById(R.id.textView);
myViewModel = ViewModelProviders.of(this).get(MyViewModel.class);
/* 为ViewModel中的thumbup数据设置observe,observe的功能为:
检测数值变化,在底层数据库更改时通知视图 */
myViewModel.getThumbup().observe(this, new Observer<Integer>() {
@Override
public void onChanged(Integer integer) {
textView.setText(String.valueOf(integer));
}
});
/* 为imageView设置onClick功能,每次点击,使TextView数值加一 */
imageView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
myViewModel.setThumbup();
}
});
}
}
Step 3:运行结果
如下图所示,可正常运行。

【Android】ViewModel+LiveData:更加直接地控制视图的方式的更多相关文章
- android自己定义控件系列教程----视图
理解android视图 对于android设备我们所示区域事实上和它在底层的绘制有着非常大的关系,非常多时候我们都仅仅关心我们所示,那么在底层一点它究竟是怎么样的一个东西呢?让我们先来看看这个图. w ...
- Android okHttp网络请求之缓存控制Cache-Control
前言: 前面的学习基本上已经可以完成开发需求了,但是在项目中有时会遇到对请求做个缓存,当没网络的时候优先加载本地缓存,基于这个需求我们来学习一直okHttp的Cache-Control. okHttp ...
- 用Kotlin开发Android应用(IV):定制视图和Android扩展
原文标题:Kotlin for Android (IV): Custom Views and Android Extensions 原文链接:http://antonioleiva.com/kotli ...
- laravel4通过控制视图模板路劲来动态切换主题
通过控制视图模板路劲来动态切换主题 App::before(function($request) { $paths = Terminal::isMobile() ? array(__dir__.'/v ...
- 【Android Developers Training】 72. 缩放一个视图
注:本文翻译自Google官方的Android Developers Training文档,译者技术一般,由于喜爱安卓而产生了翻译的念头,纯属个人兴趣爱好. 原文链接:http://developer ...
- 【Android】9.2 内置行视图的分类和呈现效果
分类:C#.Android.VS2015: 创建日期:2016-02-18 一.简介 Android内置了很多行视图模板,在应用程序中可直接使用这些内置的视图来呈现列表项. 要在ListView中使用 ...
- angular学习笔记(八)-控制视图显示隐藏
本篇介绍angular控制视图的显示和隐藏: 通过给元素添加ng-show属性或者ng-hide属性来控制视图的显示或隐藏: ng-show: 绑定的数据值为true时,显示元素,值为false时,隐 ...
- 理解Android绘制视图的方式
在创建自定义ViewGroup前,读者首先需要理解Android绘制视图的方式.我不会涉及过多细节,但是需要读者理解Android开发文档(见3.5节)中的一段话,这段话解释如何绘制一个布局.内容如下 ...
- Android开发 LiveData与MutableLiveData详解
前言 LiveData与ViewMode是经常搭配在一起使用的,但是为了不太混乱,我还是拆分开来说明,此篇博客只讲解 LiveData 与 MutableLiveData的概念与使用方式(但是会涉及到 ...
随机推荐
- Scala 学习之路(八)—— 类和对象
一.初识类和对象 Scala的类与Java的类具有非常多的相似性,示例如下: // 1. 在scala中,类不需要用public声明,所有的类都具有公共的可见性 class Person { // 2 ...
- 数据库root密码删除
1 打开mysql.exe和mysqld.exe所在的文件夹,复制路径地址 2 打开cmd命令提示符,进入上一步mysql.exe所在的文件夹. 3 输入命令 mysqld --skip-g ...
- kubernetes实战之consul简单测试环境搭建及填坑
这一节内容有点长,我们将介绍如何基于docker搭建一client一server的consul测试环境,以及如何搭建多server consul测试集群.在基于docker搭建多server的cons ...
- 常用的方法论-5why
- UVALive 7037:The Problem Needs 3D Arrays(最大密度子图)
题目链接 题意 给出n个点,每个点有一个值,现在要选择一些点的集合,使得(选择的点生成的逆序对数目)/(选择的点的数量)的比率最大. 思路 点与点之间生成一个逆序对可以看做是得到一个边,那么就是分数规 ...
- kuangbin专题 专题一 简单搜索 Fliptile POJ - 3279
题目链接:https://vjudge.net/problem/POJ-3279 题意:格子有两面,1表示黑色格子,0表示白色格子,奶牛每次可以踩一个格子,踩到的格子和它周围的上下左右格子都会翻面,也 ...
- .Net Core Api 授权认证
一.所使用到的NuGet: 1. System.IdentityModel.Tokens.Jwt 2. Microsoft.AspNetCore.Authentication.JwtBearer 二. ...
- 记一次linux服务器入侵应急响应
近日接到客户求助,他们收到托管电信机房的信息,通知检测到他们的一台服务器有对外发送攻击流量的行为.希望我们能协助排查问题. 一.确认安全事件 情况紧急,首先要确认安全事件的真实性.经过和服务器运维人员 ...
- Mybatis__模糊查询
在一个Web工程中,查询功能几乎都要用到姓名模糊查询,,虽然学号,工号等可以最准确最快的定位,但如果清楚信息到连学号,工号都一个数不差,应该也没必要去查询了. 故需要用到一下语句实现模糊查询: sel ...
- Java编程思想:为什么要使用内部类
public class Test { public static void main(String[] args) { Callbacks.test(); } } /* 为什么需要内部类: 1.可以 ...