如何开发一款以太坊安卓钱包系列3 - 资产信息展现

本文首发于深刻浅出区块链社区
原文连接:开发以太坊安卓钱包系列第3篇,原文已更新,请读者前往原文阅读html

这是如何开发以太坊(安卓)钱包系列第3篇, 钱包帐号资产信息展现,展现信息主要包括帐号地址、eth余额及该帐号所拥有的Token及余额。java

预备知识 MVVM

本文会涉及和UI界面的交互,提早理解下界面和数据如何交互是很是有必要的,若是你已经很熟悉MVVM,可跳过这一小节。android

最先写Android的时候,数据和界面常常耦合在一块儿,一个Activity文件老是特别大,每当产品界面改版就很是痛苦,吐槽下,不少产品经理都喜欢对界面改来改去。git

后来Google 推荐多个架构模式: MPV、 MVVM模式来解决数据和UI耦合的问题,登链钱包代码,使用的就是MVVM模式,因此对它作一个简单介绍,下面是MVVM的视图和数据的交互图:github

View 一般对应于Activity/Fragment/自定义View
Model:则是和数据相关的模块。数据库

View 与 Model 不直接发生联系, 而是经过ViewModel负责接收View层的事件以及获取并处理数据,ViewModel层的数据变化也会通知给View层进行相应的UI的更新,从而实现业务逻辑和Ui的隔离。编程

使用MVVM模式最大的优势就是解耦, 由于数据处理逻辑是独立于View, 在UI更改时,ViewModel 不用作太多改动。微信

咱们使用了Google在I/O大会推出的一套遵循MVVM开发模式的LiveData和ViewModel组件架构。架构

ViewModel 和 LiveData

ViewModel 会关注UI生命周期来存储和管理数据,在Activity发生变化(锁屏开屏、旋转)时,ViewModel 会自动保留以前的数据并给新的Activity或Fragment使用,当界面被系统销毁时,ViewModel也会进行资源清理,避免内存泄漏。异步

ViewModel 还能够用于不一样界面间数据共享。

LiveData是一个可观察的数据持有者类。观察者能够方便咱们以异步的方式获取数据,同时LiveData也是有生命周期感知的。若是其生命周期处于STARTED或RESUMED状态。LiveData会将观察者视为活动状态,并通知其数据的变化。LiveData未注册的观察对象以及非活动观察者是不会收到有关更新的通知。

了解更多,可自行以关键字: Lifecycle、ViewModel、LiveData 进行搜索。

帐号信息展现

展现信息主要包括帐号地址、eth余额及该帐号所拥有的Token及余额, 其界面效果以下:

上图

这个界面应的是登链钱包PropertyFragment,上图的UPT 是我本身发行的Token,因此没有显示价格

如今咱们来思考一下, 怎么来展示上面的数据, 别着急往下看, 能够先想一想。

先对问题作一个拆分,把数据拆分为4个部分:

  1. 显示当前选中的帐号
  2. 显示当前帐号 ETH 余额
  3. 显示当前帐号下 Token 数量
  4. 显示对应的法币金额。

为了不 UI 与上面4个数据的耦合,代码使用了一个TokensViewModel, 获取到的数据用 LiveData作了一个Wrap,以便UI能够订阅数据,TokensViewModel类像下面,代码有删减:

public class TokensViewModel extends ViewModel {
    private final MutableLiveData<ETHWallet> defaultWallet;
    private final MutableLiveData<NetworkInfo> defaultNetwork;

    private final MutableLiveData<Token[]> tokens;
    private final MutableLiveData<Ticker> prices;
}

MutableLiveData 是前面提到的 LiveData的子类,在UI界面中就能够对数据进行订阅,下面咱们逐一拆解下每一个数据。

显示当前帐号

能够分为两个步骤:

  1. 从数据库中读取帐号;
  2. 界面显示帐号

TokensViewModel中定义了一个MutableLiveData<ETHWallet> defaultWallet ,从数据库中读取帐号会保存在defaultWallet中,而后UI对 defaultWallet 进行观察显示。

注解: 登链钱包 里大量使用的这个方式,经过一个LiveData 作数据桥接。

在上一篇导入帐号及帐号管理,全部的帐号使用greenDao 存储起来, 所以咱们只须要把全部帐号从加载出来,挑选出当前选中的那一个。 结合代码看一看:

// WalletDaoUtils.java
    public static ETHWallet getCurrent() {
        List<ETHWallet> ethWallets = ethWalletDao.loadAll();
        for (ETHWallet ethwallet : ethWallets) {
            if (ethwallet.isCurrent()) {
                ethwallet.setCurrent(true);
                return ethwallet;
            }
        }
        return null;
    }

上面代码先用 ETHWalletDao.loadAll 加载出全部的帐号,返回当前选中的,上面的代码会被FetchWalletInteract 类的 findDefault方法调用,在ViewModle里,不少时候以数据进行交互的类,咱们会命名为 xxxInteract,这也是一个习惯用法。

其代码以下:

// FetchWalletInteract.java
   // 返回一个可订阅的Single<ETHWallet> 对象
   public Single<ETHWallet> findDefault() {
        return Single.fromCallable(() -> {
            return WalletDaoUtils.getCurrent();
        }).subscribe(this::onDefaultWallet);
    } 

    // 获取到默认钱包帐号 设置到 defaultWallet 这个LiveData
    private void onDefaultWallet(ETHWallet wallet) {
        defaultWallet.setValue(wallet);
    }

findDefault()返回一个可订阅的Single 对象,若是不熟悉可参考后面的文档。

以后,在UI界面PropertyFragment.java 中, 就能够对 defaultWallet 进行订阅:

tokensViewModel.defaultWallet().observe(this,  this::showWallet);

当获取到默认帐号时,就会回调showWallet:

// UI 显示
    public void showWallet(ETHWallet wallet) {
        tvWalletName.setText(wallet.getName());
        tvWalletAddress.setText(wallet.getAddress());

    }

这样, 界面的显示就完成了,下一篇继续介绍获取余额。

参考文档

  1. lifecycle官方文档地址
  2. RxAndroid 了解更多响应式编程

我建立了一个专门讨论钱包开发的微信群,加微信:xlbxiong 备注:钱包。

加入知识星球,和一群优秀的区块链从业者一块儿学习。
深刻浅出区块链 - 系统学习区块链,学区块链的都在这里,打造最好的区块链技术博客。

本文原文连接

相关文章
相关标签/搜索