Litho學習之--列表的實現(xiàn)-1

這篇文章主要講解一個簡單列表的實現(xiàn),包括如何自定義列表中的每個條目, 利用 RecyclerCollectionComponent 組件以及 Sections 庫來創(chuàng)建列表,如何自定義每個組件的屬性。

第一個自定義組件

首先我們先來定義列表中的條目,每個條目包含一個主標題和副標題,Litho 的預定義組件中并沒有這樣的組件,事實上也不應該有這樣的組件,需要我們自定義組件,相當于在 Android 系統(tǒng)中 LinearLayout 中的垂直方向擺放兩個 TextView 。 Litho 中,編寫 Spec 類來聲明組件的布局,也就是編寫各種不同組件的組合,在 Spec 類上添加 @LayoutSpec 注解,編寫一個用 @OnCreateLayout 注解的方法返回需要顯示的組件,實際上用到的類是去掉 Spec 后綴的 Component 類,框架會生成代碼中真正用到的 Component 類,這里我們的自定義組件叫做 ListItem ,相應地,我們要編寫 ListItemSpec 類:

@LayoutSpec
public class ListItemSpec {

  @OnCreateLayout
  static Component onCreateLayout(ComponentContext c) {

    return Column.create(c)
        .paddingDip(ALL, 16)
        .backgroundColor(Color.WHITE)
        .child(
            Text.create(c)
                .text("Hello world")
                .textSizeSp(40))
        .child(
            Text.create(c)
                .text("Litho tutorial")
                .textSizeSp(20))
        .build();
  }

}

解釋:

這里的 Text 就是 Hello World 里面見到的 Litho 中的核心組件,這個例子中,我們把 Text 組件作為 Column 的子組件傳入,這里的 Column 相當于 Android 中垂直方向的 LinearLayout ,里面設置了 padding 和 backbroundColor 兩個屬性。

那么如何使用我們剛剛編寫的這個組件?

final Component component = ListItem.create(context).build();

注意:這里我們用的是 ListItem,而不是 ListItemSpec。

那么 ListItem 是怎么來的? create() 和 build() 方法在哪里定義的?
在 Hello World 中我們在 gradle 文件中添加入了有關注解處理器的依賴, Litho 的注解處理器會掃描代碼,查找 Spec 類,并生成去掉后綴 Spec 的組件類,同時自動填充一些必要的方法。

Litho 還可以實現(xiàn)類似于 LinearLayout 中的 weight 和 FrameLayout 的效果,請參考 Layout 。

運行APP,效果如下:

First Custom Component

創(chuàng)建列表

這一節(jié)我們要使用到 Litho 中的 RecyclerCollectionComponent 組件以及 Sections 庫來創(chuàng)建列表。
RecyclerCollectionComponent 用于創(chuàng)建 Litho 滾動的單元,隱藏了直接使用 Android 中 RecyclerView 和 Adapter 交互的復雜性。
Sections API 可以把列表中的條目放到 Section 中,寫 GroupSectionSpec 類來聲明每個 Section 要渲染的內(nèi)容和使用的數(shù)據(jù)。
這里我們要自定義的 Section 叫做 ListSection, 因此需要聲明 ListSectionSpec 類,在類上添加 @GroupSectionSpec 注解,定義 onCreateChildren 方法,返回需要渲染的子 Section 們,這里每個子 Section 顯示一個 ListItem 組件。

@GroupSectionSpec
public class ListSectionSpec {

  @OnCreateChildren
  static Children onCreateChildren(final SectionContext c) {
    Children.Builder builder = Children.create();

    for (int i = 0; i < 32; i++) {
      builder.child(
          SingleComponentSection.create(c)
              .key(String.valueOf(i))
              .component(ListItem.create(c).build()));
    }
    return builder.build();
  }
}

解釋:
SingleComponentSection 是 Litho Section API 提供中的一個核心 Section,定義在 com.facebook.litho.sections.widget 這個包中,只不過這個 Section 負責渲染一個單一的 Component 。ListSectionSpec 描述了一個包含有 32 個子 Section 的 Section ,這 32 個子 Section 中,每個 Section 負責渲染一個 ListItem 組件。
這里定義的是 Section ,并沒有定義 Component,那么如何把 Section 顯示在屏幕上?
把 Activity 中組件的定義改成下面的代碼:

final Component component =
    RecyclerCollectionComponent.create(context)
        .disablePTR(true)
        .section(ListSection.create(new SectionContext(context)).build())
        .build();

注意:這里使用的是 ListSection ,而不是 ListSectionSpec 。

解釋:

這里我們用 RecyclerCollectionComponent 這個組件,把剛剛定義的Section 顯示在屏幕上。 RecyclerCollectionComponent 接收一個 Section 作為屬性,會渲染一個 RecyclerView 顯示 Section中的內(nèi)容。它來管理數(shù)據(jù)刷新的操作,這里不使用下拉刷新功能,所以 通過設置 .disablePTR(true) 把這個功能關掉。

運行代碼,效果如下:

列表實現(xiàn)1

定義組件的屬性

上面的列表中,我們所有的列表項都顯示重復的內(nèi)容,現(xiàn)在我們想要列表中的內(nèi)容是變化的。
這里引入 Litho 中屬性的概念,也就是 Prop 。Component 的屬性就是 Component Spec 類(這個類是我們編寫用于生成對應的 Component 類的)中方法的參數(shù),這些參數(shù)上帶有 @Prop 注解。

把 ListItemSpec 進行如下修改:

@OnCreateLayout
static Component onCreateLayout(
    ComponentContext c,
    @Prop int color,
    @Prop String title,
    @Prop String subtitle) {

  return Column.create(c)
        .paddingDip(ALL, 16)
        .backgroundColor(color)
        .child(
            Text.create(c)
                .text(title)
                .textSizeSp(40))
        .child(
            Text.create(c)
                .text(subtitle)
                .textSizeSp(20))
        .build();
}

解釋:
這里我們添加了三個屬性,color,title,subtitle 。這里的 backgroundColor 以及 Text 組件的 文本內(nèi)容不再是硬編碼的形式,而是根據(jù) onCreateLayout 方法中的參數(shù)給出。

Litho 的注解處理器會根據(jù) @Prop 注解,為注解的參數(shù)生成相應的構(gòu)造器方法,例如這里參數(shù)名稱是 color,就會為 ListItem 生成 color(int) 方法,相應地,這里還會生成另外兩個構(gòu)造器方法,title(String) ,subtitle(String) 。在創(chuàng)建 ListItem 組件的時候,就需要在構(gòu)造器方法中,對屬性進行賦值。

修改 ListSection 中的方法:

@OnCreateChildren
static Children onCreateChildren(final SectionContext c) {
  Children.Builder builder = Children.create();

  for (int i = 0; i < 32; i++) {
    builder.child(
        SingleComponentSection.create(c)
            .key(String.valueOf(i))
            .component(ListItem.create(c)
               .color(i % 2 == 0 ? Color.WHITE : Color.LTGRAY)
               .title(i + ". Hello, world!")
               .subtitle("Litho tutorial")
               .build()));
  }
  return builder.build();
}

另外,屬性上還可以有其他選項,例如:
@Prop(optional = true, resType = ResType.DIMEN_OFFSET) int shadowRadius,

注解處理器還會生成一些對應的方法 :shadowRadiusPx, shadowRadiusDip, shadowRadiusSp 以及 shadowRadiusRes。

注意:

  1. Prop 可以被 Spec 中不同的生命周期方法訪問,只需要在相應的方法參數(shù)上添加這個 Prop ,Litho 保證每個方法訪問到的屬性值是一致的,但是要保證同一個Prop 在不同方法中的聲明完全一致,比如 方法1 中 使用 @Prop(optional = true) String prop1,那么 方法2 中也要采用 @Prop(optional = true) String prop1, 否則注解處理器會報錯。
  2. 另外對于 optional = true 的屬性,在組件創(chuàng)建時可不傳入該屬性的值,如果未添加此項設置,則會在運行時報如下錯誤:下面是我把上面代碼中的 subtitle一樣注釋掉報的錯:
    java.lang.IllegalStateException: The following props are not marked as optional and were not supplied: [subtitle]
    有關屬性的問題,請參考 Props

運行APP,會看到如下效果:


列表實現(xiàn)-帶屬性
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內(nèi)容

  • Spring Cloud為開發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見模式的工具(例如配置管理,服務發(fā)現(xiàn),斷路器,智...
    卡卡羅2017閱讀 136,593評論 19 139
  • Spring Boot 參考指南 介紹 轉(zhuǎn)載自:https://www.gitbook.com/book/qbgb...
    毛宇鵬閱讀 47,275評論 6 342
  • Spring Web MVC Spring Web MVC 是包含在 Spring 框架中的 Web 框架,建立于...
    Hsinwong閱讀 22,943評論 1 92
  • 凌寒夜冷風, 蹣跚雨中行, 繁逝悲由空寂寥。 唯犬吠知更獨行! 徒步到?jīng)龀浚?荒雞難鳴。 應化流風水斷冰, 世道怎...
    夏墨凌語閱讀 205評論 0 5
  • 1、15年底以前,我抵抗低落情緒的時候使用最多的方法之一就是跑步。 2、不幸的是,左膝關節(jié)外側(cè)長年積累發(fā)生疼痛,5...
    五彩冰峰閱讀 236評論 0 0

友情鏈接更多精彩內(nèi)容