设为首页收藏本站

LUPA开源社区

 找回密码
 注册
文章 帖子 博客
LUPA开源社区 首页 业界资讯 技术文摘 查看内容

Android中提取表单模型

2014-7-10 11:35| 发布者: joejoe0332| 查看: 4453| 评论: 0|原作者: lum|来自: 伯乐在线

摘要:   我一直追求从Android活动中分离代码。在最近的一个项目中,我成功的实现了传统的”Form Model”模式,想在此分享我的感想。  “Form Model”的基本思想是,把处理UI交互以及数据绑定和状态保持的代码提取到单 ...

  我一直追求从Android活动中分离代码。在最近的一个项目中,我成功的实现了传统的”Form Model”模式,想在此分享我的感想。


  “Form Model”的基本思想是,把处理UI交互以及数据绑定和状态保持的代码提取到单独的类中。这种分离非常自然,并且让我们的Activity变得简单。


  我认为Android中这个领域不太被关注——在大多数的开发文档中数据录入和表单不是重点。在很多流行的社交应用程序中,大多数的画面只是显示信息;可能也有几个画面用于发微博或者消息,但不是应用的痛点。


  对我来说,上两个Android应用有特别多的数据录入工作。部分原因是因为所处的领域(医疗、金融)和客户(更贴近于企业应用而不是创业)。但我们经常把“表单输入”界面搞得一片混乱——特别是当开始添加东西的时候,比如编辑现有的条目,提示丢弃未保存的更改,以及处理旋转而不会清除所有字段值。


  使用这种表单模型方案会减少bug,让代码更容易理解,开发者也会变得更快乐。


搜索表单示例


  我们有一个银行应用程序,希望有一个画面来搜索交易数据。有多个过滤条件:开始是一个金额下拉列表,一个关键字字段和一个金额范围。(希望你可以想象在未来将会增加更多的这类过滤器,复杂性会激增)。


  我们没有把所有的视图、单击处理程序,验证逻辑和数据绑定的代码堆到一个Activity中,而是要创建一个 SearchForm类来处理这一切。


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
public class SearchForm extends LinearLayout {
 
  @InjectView(R.id.account)
  private Spinner mAccountSpinner;
  private AccountAdapter mAccountAdapter;
 
  @InjectView(R.id.keyword)
  private EditText mKeywordField;
 
  @InjectView(R.id.min_amount)
  private CurrencyEditText mMinAmountField;
 
  @InjectView(R.id.max_amount)
  private CurrencyEditText mMaxAmountField;
 
  public SearchFormModel(Context context, AttributeSet attrs) {
    super(context, attrs);
    setup(context);
  }
 
  private void setup(Context context) {
    LayoutInflater.from(context).inflate(R.layout.search_form, this, true);
 
    ButterKnife.inject(this); // <3 @JakeWharton
 
    mAccountAdapter = new AccountAdapter(context);
    mAccountSpinner.setAdapter(mAccountAdapter);
  }
 
  public initialize(List<Account> accounts) {
    mAccountAdapter.setItems(accounts);
  }
 
  public String getKeywords() {
    return mKeywordField.getText().toString();
  }
 
  public void setKeywords(String keywords) {
    mKeywordField.setText(keywords);
  }
 
  public MoneyAmount getMinimumAmount() {
    return mMinAmountField.getAmount();
  }
 
  public void setMinimumAmount(double amount) {
    mMinmountField.setAmountFromDouble(amount);
  }
 
  public MoneyAmount getMaximumAmount() {
    return mMaxAmountField.getAmount();
  }
 
  public void setMaximumAmount(double amount) {
    mMaxAmountField.setAmountFromDouble(amount);
  }
 
  public Account getSelectedAccount() {
    return mAccountSpinner.getSelectedItem();
  
 
  public boolean validate() {
    clearErrors();
    boolean isValid = true;
 
    if (!isValidAmountRange()) {
      isValid = false;
      mMinAmountField.setError("Invalid range");
      mMaxAmountField.setError("Invalid range");
    }
 
    return isValid;
  }
 
  private boolean isValidAmountRange() {
    return getMinimumAmount() <= getMaximumAmount();
  }
 
  private void clearErrors() {
    mMinAmountField.setError(null);
    mMaxAmountField.setError(null);
  }
 
  public SearchParameters buildParameters() {
    return new SearchParameters(getSelectedAccount(),
                                getKeywords(),
                                getMinimumAmount(),
                                getMaximumAmount());
  }
 
  public void persist(Bundle outState) {
    outState.putInt("SELECTED_ACCT_INDEX", mAccountSpinner.getSelectedItemPosition());
  }
 
  public void restore(Bundle bundle) {
    int accountPosition = bundle.getInt("SELECTED_ACCT_INDEX");
    mAccountSpinner.setSelection(accountPosition, false);
  }
}


  我们创建了一个类,继承自LinearLayout(或者FrameLayout,由你的喜好决定)。它允许把相关的控件组织到一个布局中,我们将填充布局,设置列表视图并为金额列表创建一个适配器。



酷毙

雷人

鲜花

鸡蛋

漂亮
  • 快毕业了,没工作经验,
    找份工作好难啊?
    赶紧去人才芯片公司磨练吧!!

最新评论

关于LUPA|人才芯片工程|人才招聘|LUPA认证|LUPA教育|LUPA开源社区 ( 浙B2-20090187 浙公网安备 33010602006705号   

返回顶部