ArkTS List刷新行的方式二

List 是通过 LazyForEach 来实现的;通过改变 keyGenertator(LazyForEach中的参数)的返回值,来实现刷新行的效果。代码如下:

@Entry
@Component
struct ListAct {
  @State baseAdapter: MyAdapter = null;
  private scroller: Scroller = new Scroller();

  aboutToAppear() {
    this.initDatas();
  }

  initDatas() {
    let list: ListDataItem[] = new Array<ListDataItem>(100);
    for (let i = 0, end = list.length; i < end; i++) {
      list[i] = new ListDataItem("条目:" + (i + 1));
    }
    this.baseAdapter = new MyAdapter(list);
  }

  addDatas(index: number, count: number) {
    let list: ListDataItem[] = new Array<ListDataItem>(count);
    for (let i = 0, end = count; i < end; i++) {
      list[i] = new ListDataItem("新增条目:" + (i + 1));
    }
    this.baseAdapter.addDatas(list, index);
  }

  refreshAllDatas() {
    let list: ListDataItem[] = new Array<ListDataItem>(20);
    for (let i = 0, end = list.length; i < end; i++) {
      list[i] = new ListDataItem("刷新条目:" + (i + 1));
    }
    this.baseAdapter.refreshDatas(list);
  }

  @Builder itemEnd(item: ListDataItem, index: number) {
    // 侧滑后尾端出现的组件
    Button({ type: ButtonType.Normal }) {
      Row() {
        Row() {
          Image($r('app.media.app_icon'))
            .width(20)
            .height(20)
            .objectFit(ImageFit.Contain)
            .margin({ left: 16, right: 16 })
          Text("修改")
        }.onClick(() => {
          item.name = "修改" + item.name;
          // this.baseAdapter.refreshDataByIndex(index);
          this.baseAdapter.refreshData(item);
        })

        Row() {
          Image($r('app.media.app_icon'))
            .width(20)
            .height(20)
            .objectFit(ImageFit.Contain)
            .margin({ left: 16, right: 16 })
          Text("删除")
        }.onClick(() => {
          // this.baseAdapter.removeDataByIndex(index);
          this.baseAdapter.removeData(item);
        })
      }
    }.height(40)

  }

  build() {
    Column() {
      Row() {
        Button("添加数据").onClick(() => {
          this.addDatas(0, 2);
        })
        Button("刷新数据").onClick(() => {
          this.refreshAllDatas();
        })
      }

      List({ space: 8, scroller: this.scroller }) {
        LazyForEach(this.baseAdapter, (item: ListDataItem, index) => {
          ListItem() {
            if (item) {
              Row() {
                Text(item.name).margin(24)
              }.width("100%").align(Alignment.Start)
            }
          }
          .swipeAction({ end: this.itemEnd.bind(this, item, index) }) // 设置侧滑属性
        }, (item: ListDataItem, index) => item.getKey())
      }
      .backgroundColor('#eeeeee')
      .divider({ strokeWidth: 1, color: 0x222222 })
      .layoutWeight(1)
    }
  }
}

class ListDataItem {
  name: string;
  private key: string = null;

  constructor(name: string) {
    this.name = name;
  }

  public clearKey() {
    this.key = null;
  }

  public getKey() {
    if (this.key == null) {
      this.key = uuid();
    }
    return this.key;
  }
}


class BaseAdapter <T> implements IDataSource {
  private listeners: DataChangeListener[] = new Array<DataChangeListener>();
  protected dataArray: T[];

  constructor(dataArray: T[]) {
    this.dataArray = dataArray ? dataArray : [];
  }

  public refreshDatas(dataArray: T[]) {
    this.dataArray = dataArray;
    this.notifyDataReload();
  }

  notifyDataReload(): void {
    this.listeners.forEach(listener => {
      listener.onDataReloaded();
    })
  }

  registerDataChangeListener(listener: DataChangeListener): void {
    if (this.listeners.indexOf(listener) < 0) {
      this.listeners.push(listener);
    }
  }

  unregisterDataChangeListener(listener: DataChangeListener): void {
    const pos = this.listeners.indexOf(listener);
    if (pos >= 0) {
      this.listeners.splice(pos, 1);
    }
  }

  public totalCount(): number {
    return this.dataArray.length;
  }

  public getData(index: number): T {
    return this.dataArray[index];
  }

  public getCount(): number {
    return this.dataArray.length;
  }
}

class MyAdapter extends BaseAdapter<ListDataItem> {
  constructor(dataArray: ListDataItem[]) {
    super(dataArray);
  }

  public refreshData(t: ListDataItem) {
    this.refreshDataByIndex(this.dataArray.indexOf(t));
  }

  public refreshDataByIndex(index: number) {
    if (index >= 0 && index < this.dataArray.length) {
      this.dataArray[index].clearKey();
      this.notifyDataReload();
    }
  }

  public addData(t: ListDataItem, index: number = -1): void {
    for (let item of this.dataArray) item.clearKey();
    if (index < 0 && index >= this.dataArray.length) {
      this.dataArray.push(t);
    } else {
      this.dataArray.splice(index, 0, t);
    }
    this.notifyDataReload();
  }

  public addDatas(ts: ListDataItem[], index: number = -1): void {
    if (ts && ts.length > 0) {
      for (let item of this.dataArray) item.clearKey();
      if (index >= 0 && index < this.dataArray.length) {
        this.dataArray.splice(index, 0, ...ts);
      } else {
        index = this.dataArray.length;
        this.dataArray.splice(index, 0, ...ts);
      }
      this.notifyDataReload();
    }
  }

  public removeData(t: ListDataItem) {
    this.removeDataByIndex(this.dataArray.indexOf(t));
  }

  public removeDataByIndex(index: number) {
    if (index >= 0 && index < this.dataArray.length) {
      this.dataArray.splice(index, 1)
      for (let item of this.dataArray) item.clearKey();
      this.notifyDataReload();
    }
  }
}

function uuid(): string {
  var uuidValue = "", k, randomValue;
  for (k = 0; k < 32; k++) {
    randomValue = Math.random() * 16 | 0;

    if (k == 8 || k == 12 || k == 16 || k == 20) {
      uuidValue += "-"
    }
    uuidValue += (k == 12 ? 4 : (k == 16 ? (randomValue & 3 | 8) : randomValue)).toString(16);
  }
  return uuidValue;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值