2024年HarmonyOS鸿蒙最新OpenHarmony开发实战:List组件的使用之商品列表(ArkTS)(2),2024年最新字节跳动算法工程师面试题

img
img

网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。

需要这份系统化的资料的朋友,可以戳这里获取

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

相关概念
  • Scroll:可滚动的容器组件,当子组件的布局尺寸超过父组件的视口时,内容可以滚动。
  • List:列表包含一系列相同宽度的列表项。适合连续、多行呈现同类数据,例如图片和文本。
  • Tabs:一种可以通过页签进行内容视图切换的容器组件,每个页签对应一个内容视图。
  • LazyForEach :开发框架提供数据懒加载(LazyForEach组件)从提供的数据源中按需迭代数据,并在每次迭代过程中创建相应的组件。
环境搭建
软件要求
  • DevEco Studio版本:DevEco Studio 3.1 Release。
  • OpenHarmony SDK版本:API version 9。
硬件要求
环境搭建

完成本篇Codelab我们首先要完成开发环境的搭建,本示例以RK3568开发板为例,参照以下步骤进行:

  1. 获取OpenHarmony系统版本:标准系统解决方案(二进制)。以3.2 Release版本为例:


2. 搭建烧录环境。

1. [完成DevEco Device Tool的安装]( )
2. [完成RK3568开发板的烧录]( )
  1. 搭建开发环境。

    1. 开始前请参考工具准备,完成DevEco Studio的安装和开发环境配置。
    2. 开发环境配置完成后,请参考使用工程向导创建工程(模板选择“Empty Ability”),选择JS或者eTS语言开发。
    3. 工程创建完成后,选择使用真机进行调测

代码结构解读

本篇Codelab只对核心代码进行讲解,完整代码可以直接从gitee获取。

├──entry/src/main/ets                      // 代码区
│  ├──common
│  │  └──CommonConstants.ets               // 常量集合文件
│  ├──entryability
│  │  └──EntryAbility.ts                   // 应用入口,承载应用的生命周期
│  ├──pages
│  │  └──ListIndex.ets                     // 页面入口
│  ├──view
│  │  ├──GoodsListComponent.ets            // 商品列表组件
│  │  ├──PutDownRefreshLayout.ets          // 下拉刷新组件
│  │  └──TabBarsComponent.ets              // Tabs组件
│  └──viewmodel
│     ├──InitialData.ets                   // 初始化数据
│     └──ListDataSource.ets                // List使用的相关数据加载
└──entry/src/main/resources
    ├──base
    │  ├──element                          // 字符串以及颜色的资源文件
    │  ├──media                            // 图片等资源文件
    │  └──profile                          // 页面配置文件存放位置
    ├──en_US
    │  └──element
    │     └──string.json                   // 英文字符存放位置
    └──zh_CN
        └──element
           └──string.json                  // 中文字符存放位置

页面布局

页面使用Navigation与Tabs做页面布局,使用Navigation的title属性实现页面的标题,Tabs做商品内容的分类。示例代码如下:

// ListIndex.ets
Row() {
  Navigation() {
    Column() {
      TabBars()
    }
    .width(LAYOUT_WIDTH_OR_HEIGHT)
    .justifyContent(FlexAlign.Center)
  }
  .size({ width: LAYOUT_WIDTH_OR_HEIGHT, height: LAYOUT_WIDTH_OR_HEIGHT })
  .title(STORE)
  .titleMode(NavigationTitleMode.Mini)
}
.height(LAYOUT_WIDTH_OR_HEIGHT)
.backgroundColor($r('app.color.primaryBgColor'))

页面分为“精选”、“手机”、“服饰”、“穿搭”、“家居”五个模块,由于本篇CodeLab的主要内容在“精选”部分,故将“精选”部分单独编写代码,其余模块使用ForEach遍历生成。示例代码如下:

// TabBarsComponent.ets
Tabs() {
  // 精选模块
  TabContent() {
    Scroll() {
      Column() {
        if (this.refreshStatus) {
          PutDownRefresh({ refreshText: $refreshText })
        }
        GoodsList()
        Text($r('app.string.to_bottom'))
          .fontSize(NORMAL_FONT_SIZE)
          .fontColor($r('app.color.gray'))
      }
      .width(LAYOUT_WIDTH_OR_HEIGHT)
    }
    ...
  }
  .tabBar(this.firstTabBar)

  // 其他模块
  ForEach(initTabBarData, (item: Resource, index?: number) => {
    TabContent() {
      Column() {
        Text(item).fontSize(MAX_FONT_SIZE)
      }
      .justifyContent(FlexAlign.Center)
      .width(LAYOUT_WIDTH_OR_HEIGHT)
      .height(LAYOUT_WIDTH_OR_HEIGHT)
    }
    .tabBar(this.otherTabBar(item, index !== undefined ? index : 0))
  })
}
...

商品列表的懒加载

使用Scroll嵌套List做长列表,实现Scroll与List的联动。具体实现代码如下:

// TabBarsComponent.ets
Scroll() {
  Column() {
    // 下拉刷新的组件
    if (this.refreshStatus) {
      PutDownRefresh({ refreshText:$refreshText })
    }

    // List的自定义组件
    GoodsList()
    Text($r('app.string.to_bottom')).fontSize(NORMAL_FONT_SIZE).fontColor($r('app.color.gray'))
  }
  .width(LAYOUT_WIDTH_OR_HEIGHT)
}
...

商品列表往往数据量很多,如果使用ForEach一次性遍历生成的话,性能不好,所以这里使用LazyForEach进行数据的懒加载。当向下滑动时,需要加载新的数据的时候,再将新的数据加载出来,生成新的列表。

通过onTouch事件来触发懒加载行为,当商品列表向下滑动,加载新的数据。示例代码如下:

// GoodsListComponent.ets
List({ space:commonConst.LIST_ITEM_SPACE }) {
  LazyForEach(this.goodsListData, (item: GoodsListItemType) => {
    ListItem() {
      Row() {
        Column() {
          Image(item?.goodsImg)
            ...
        }
        ... // 布局样式

        Column() {
          ... // 布局代码
        }
        ... // 布局样式
      }
    }

    // 通过Touch事件来触发懒加载
    .onTouch((event?:TouchEvent) => {
      if (event === undefined) {
        return;
      }
      switch (event.type) {
        case TouchType.Down:
          this.startTouchOffsetY = event.touches[0].y;
          break;
        case TouchType.Up:
          this.startTouchOffsetY = event.touches[0].y;
          break;
        case TouchType.Move:
          if (this.startTouchOffsetY - this.endTouchOffsetY > 0) {
            this.goodsListData.pushData();
          }
          break;
      }
    })
  })
}
...

下拉刷新与到底提示

下拉刷新同样使用TouchEvent做下拉的判断,当下拉的偏移量超出将要刷新的偏移量时,就展示下拉刷新的布局,同时使用条件渲染判断是否显示下拉刷新布局,实现效果如下图:

具体代码如下:

// TabBarsComponent.ets
putDownRefresh(event?:TouchEvent): void {
  if (event === undefined) {
    return;
  }
  switch (event.type) {
    case TouchType.Down:
      // 记录手指按下的y坐标
      this.currentOffsetY = event.touches[0].y;
      break;
    case TouchType.Move:
      // 根据下拉的偏移量来判断是否刷新
      this.refreshStatus = event.touches[0].y - this.currentOffsetY > MAX_OFFSET_Y;
      break;
    case TouchType.Cancel:
      break;
    case TouchType.Up:
      // 模拟刷新效果,并未真实请求数据
      this.timer = setTimeout(() => {
        this.refreshStatus = false;
        }, REFRESH_TIME)
      break;
  }
}
...
// 下拉刷新的组件根据条件决定是否显示
if (this.refreshStatus) {
  PutDownRefresh({ refreshText:$refreshText })
}

列表到底提示“已经到底了”并回弹的效果使用了Scroll的edgeEffect来控制回弹,实现效果如下图:

深知大多数程序员,想要提升技能,往往是自己摸索成长,但自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!


img
img

既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,涵盖了95%以上鸿蒙开发知识点,真正体系化!

由于文件比较多,这里只是将部分目录截图出来,全套包含大厂面经、学习笔记、源码讲义、实战项目、大纲路线、讲解视频,并且后续会持续更新

需要这份系统化的资料的朋友,可以戳这里获取

[外链图片转存中…(img-2loUfXy1-1715631727547)]
[外链图片转存中…(img-yHpsLgzo-1715631727547)]

既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,涵盖了95%以上鸿蒙开发知识点,真正体系化!

由于文件比较多,这里只是将部分目录截图出来,全套包含大厂面经、学习笔记、源码讲义、实战项目、大纲路线、讲解视频,并且后续会持续更新

需要这份系统化的资料的朋友,可以戳这里获取

  • 29
    点赞
  • 25
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值