重生之我在大学自学鸿蒙开发第五天-《实战篇》

目录

一、前言

二、实践

2.1、Banner区域

2.2、List区域

​编辑

2.3、详情页界面设计

2.4、定义数据结构

2.5、实现区域4

2.6、实现区域三

2.7、改变数据获取方式

三、测试

四、总结


一、前言

经过前四篇文章的学习相信大家已经具备一定的开发能力的,现在来参考官方文档完成一个简易页面的创建,这是官方文档给出的示意图,简单分析下可以看出也就三部分组成,相信对于大家来说问题不大,我这里还是以文档为主进行学习。

废话不多说开始实践。

二、实践

本章节内容参考官方链接

通过结构化数据构建页面-HarmonyOS应用开发快速入门-Codelabs-华为开发者联盟

我这里不知道为啥直接使用preview会这样,所以还是在default中观看吧

我这里将KnowledgeMap组件导出了直接在default中进行展示的

导出这部分就不过多介绍了,就是在map模块中的index文件直接导出即可

复制代码
export { KnowledgeMap } from './src/main/ets/pages/KnowledgeMap';

2.1、Banner区域

文字区域就不多说了,直接从Banner区域进行讲解,不知道为什么这里目录不完整,目录结构和我的统一下,放一张图片用于展示Banner区域,当然也可以和之前一样弄轮播图进行展示

整体的实现效果如下:

这里主要是Banner和简介区域,这段感觉完全可以提取出来

复制代码
@Component
export struct KnowledgeMap{
  build() {
    Column(){
      Text('知识地图')
        .fontFamily('HarmonyHeiTi-Bold')
        .fontSize(24)
        .fontColor(Color.Black)
        .textAlign(TextAlign.Start)
        .lineHeight(33)
        .fontWeight(700)
        .width('100%')
      Image($r('app.media.img'))
        .width('100%')
        .height('30%')
        .borderRadius(16)
        .margin({ top: 19, bottom: 8 })
      Text('她扎着低马尾,碎发贴在耳侧,白衬衫领口别着小珍珠别针。笑时会抿下嘴角,说起花艺眼睛亮,像盛着春日花园。')
        .fontFamily('HarmonyHeiTi')
        .fontSize(14)
        .fontColor('rgba(0,0,0,0.60)')
        .fontWeight(400)
        .textAlign(TextAlign.Start)
    }
    .padding({ top: 12, right: 16, bottom: 12, left: 16})
    .backgroundColor('#F1F3F5')
  }
}

2.2、List区域

这里的List区域又两种方法来实现

**官方解释:**一种是使用@Component来自定义组件,另外一种是使用@Builder自定义构建函数,两者各自特点如下:

  • @Component功能更加多样,有自己的生命周期,还能支持预览效果。
  • 而@Builder更加轻量,能满足基础的组件封装,性能更好,但是不支持预览。

此处为了呈现预览效果,采用了@Component进行定义。如果需要更好的性能的建议采用@Builder的方式进行组件定义封装。

这里直接添加List组件即可,这段代码主要就是要明白数据获取的逻辑

复制代码
    List({ space: 12 }) {
          ForEach(this.navBarList, (item: NavBarItemType, index: number) => {
            ListItem() {
              NavBarItem({ navBarItem: item })
            }
            .width('100%')
          }, (item: NavBarItemType): string => item.title)
        }

这里的父组件定义好数据NavBarItemType类型的数据,用数组来接受数据,ForEach遍历数据,将数据传入NavBarItem组件来进行渲染操作。

这里的NavBarItem组件逻辑如下👇:

应该可以理解吧,这里的逻辑并不是很复杂

复制代码
export interface NavBarItemType {
  order: string,
  title: string
}

@Component
export struct NavBarItem{
  @Prop navBarItem: NavBarItemType;
  build() {
    Row(){
      Text(this.navBarItem.order)
        .margin({ right: 6 })
        .fontFamily('HarmonyHeiTi-Bold')
        .fontSize(21)
        .fontColor('#182431')
        .textAlign(TextAlign.Start)
        .lineHeight(22)
        .fontWeight(700)
      Text(this.navBarItem.title)
        .fontFamily('HarmonyHeiTi-Medium')
        .fontSize(16)
        .fontColor('#182431')
        .textAlign(TextAlign.Start)
        .lineHeight(22)
        .fontWeight(500)
      Blank()//此处采用Blank组件,该组件可以自动填充主轴方向的空余空间
      Image($r('app.media.right'))
        .width(12)
        .height(24)
    }
    .width('100%')
    .height(48)
    .borderRadius(16)
    .alignItems(VerticalAlign.Center)
    .padding({ left: 12, right: 12 })
    .backgroundColor('#F1F3F5')
  }
}

2.3、详情页界面设计

设计页面如下:

这里主要注意下3、4,因为很多组件都十分相似,我们可以进行复用从而降低代码量

官方解释:

  • 区域3,知识地图详情页知识块:从设计图中可以观察到,这样的知识块可以不止一个,组件构造也都是一致,包含一个副标题和多行的知识点。因此可以将其封装成一个组件。

  • 区域4,知识块内的每个知识点:左侧图标与右侧的右箭头图标可以采用Image组件实现,类型、标题可以用Text组件实现。

2.4、定义数据结构

这里不知道大家能否理解,其实第一次看见我真的一脸懵逼,仔细看了下发现并不难,我这里用简单的形式来讲解下数据是如何进行定义的。

复制代码
interface KnowledgeBaseItem {
  type: string,
  title: string
}

interface Material {
  subtitle: string,
  knowledgeBase: KnowledgeBaseItem[]
}

export interface Section {
  title: string,
  brief: string,
  materials: Material[]
}

大致就是这样子分类的,这里可以好好去理解下,我这里因为空间有限没有全部进行表明

开始准备本地的静态数据

复制代码
  @State  section: Section = {
    "title": "准备与学习",
    "brief": "加入HarmonyOS生态,注册成为开发者,通过HarmonyOS课程了解基本概念和基础知识,轻松开启HarmonyOS的开发旅程。",
    "materials": [
      {
        "subtitle": "HarmonyOS简介",
        "knowledgeBase": [
          { "type": "准备", "title": "注册账号" },
          { "type": "准备", "title": "实名认证" },
          { "type": "学习与获取证书", "title": "HarmonyOS第一课" },
          { "type": "学习与获取证书", "title": "HarmonyOS应用开发者基础认证" }
        ]
      },
      {
        "subtitle": "赋能套件介绍",
        "knowledgeBase": [
          { "type": "指南", "title": "开发" },
          { "type": "指南", "title": "最佳实践" },
          { "type": "指南", "title": "API参考" },
          { "type": "指南", "title": "视频课程" },
          { "type": "指南", "title": "Codelabs" },
          { "type": "指南", "title": "FAQ" }
        ]
      }
    ]
  };

2.5、实现区域4

build内容如下,因为数据需要在父组件中获取,所以需要先进行引入

复制代码
 build() {
    Scroll(this.scroller) {
      Column() {
        Text("准备与学习")
          .fontFamily('HarmonyHeiTi-Bold')
          .fontSize(20)
          .fontWeight(700)
          .fontColor(Color.Black)
        Text(this.section?.brief)
          .fontFamily('HarmonyHeiTi')
          .fontSize(12)
          .fontColor('rgba(0,0,0,0.60)')
          .textAlign(TextAlign.JUSTIFY)
          .fontWeight(400)
          .margin({ top: 12 })
        ForEach(this.section?.materials, (material: Material) => {
          this.KnowledgeBlock(material)
        }, (material: Material, index: number) => material.subtitle + index)
      }
      .alignItems(HorizontalAlign.Start)
      .padding({top: 12, left: 16, bottom: 12, right: 16})
      .backgroundColor('#F1F3F5')
      .width('100%')
    }
    .align(Alignment.TopStart)
    .constraintSize({ minHeight: '100%' })
    .edgeEffect(EdgeEffect.Spring)
    .scrollable(ScrollDirection.Vertical)
    .scrollBar(BarState.Auto)
    .backgroundColor('green')

不难看出这里很多组件都重复了,我们可以将它抽取出来,这里为了和官网保持一致,也选用@Builder来进行统一定义函数来完成

复制代码
  @Builder
  KnowledgeBlockLine(knowledgeBaseItem: KnowledgeBaseItem) {
    Row() {
      Image($r(TypeMapIcon[knowledgeBaseItem.type]))
        .width(20)
        .height(20)
      Column() {
        Text(knowledgeBaseItem.title)
          .fontFamily('HarmonyHeiTi-Medium')
          .fontSize(16)
          .fontWeight(500)
        Text(knowledgeBaseItem.type)
          .fontFamily('HarmonyHeiTi')
          .fontSize(14)
          .fontWeight(400)
      }
      .alignItems(HorizontalAlign.Start)
      .margin({ left: 18 })
      Blank()
      Image($r('app.media.right'))
        .width(12)
        .height(24)
    }
    .width('100%')
    .height(64)
    .alignItems(VerticalAlign.Center)
  }

这里的类型我们都提前定义好了,前面的图标是通过传入的string来对应的

这里大家可以进行自定义

复制代码
const TypeMapIcon: Record<string, string> = {
  '指南': 'app.media.logo',
  '准备': 'app.media.logo2',
  '学习与获取证书': 'app.media.logo',
  '视频教程': 'app.media.logo2',
}

2.6、实现区域三

注意看这里也有重复的部分,所以我们也要将其抽象出来,这里还是用的@Builder

复制代码
  @Builder
  KnowledgeBlock(material: Material) {
    Column() {
      Text(material.subtitle)
        .fontFamily('HarmonyHeiTi-Medium')
        .fontSize(14)
        .fontWeight(500)
        .margin({ bottom: 8 })
      List({ space: 12 }) {
        ForEach(material.knowledgeBase, (item: KnowledgeBaseItem, index: number) => {
          ListItem(){
            this.KnowledgeBlockLine(item)
          }
        }, (item: KnowledgeBaseItem, index: number) => item.title)
      }
      .backgroundColor(Color.White)
      .borderRadius(16)
      .padding({ left: 12, right: 12 })
      .divider({
        strokeWidth: 0.5,
        startMargin: 38,
        endMargin: 0,
        color: '#F2F2F2'
      })
    }
    .width('100%')
    .margin({ top: 28 })
    .alignItems(HorizontalAlign.Start)
  }

这里为了方便大家观看我将这两个函数进行平行解释,就是通过函数调用的方式来进行循环渲染使得代码量大大减少

最后通过在build中调用KnowledgeBlock,注意下这里的Scroll,这里传入的参数应该是为了继承父组件的样式吧,这里我也不是很清楚,不传入参数应该也不会应影响正常运行

官方解释:

添加Scroll。Scroll内容可能会超过应用界面的长度,和之前在知识地图页的方案一样,采用Scroll组件包裹住外层,使得界面内容部分可以滑动展示。同时可以将之前加到外层Column容器上的背景色属性移动到Scroll上。

其中scrollable属性表示设置滚动方向,此处设置为ScrollDirection.Vertical表示允许纵向滚动。scrollBar属性表示以何种方式显示滚动条,支持一直显示、不显示以及滑动时显示,此处设为BarState.Auto表示滑动时显示。


2.7、改变数据获取方式

之前我们的数据是从json文件中进行获取的,现在我们需要改造一下,同样从接送文件中获取

这里不知道为什么和上次处理的模式不同了,可能是又多种方式吧

三、测试

全部完成后开始测试,这里的详情页不知道为什么无法展示,就是因为这里昨天硬控我一个小时也是没有解决,今天下午用官方给的文件也是这样,我一直以为是我的问题

知识地图页面测试成功,我这里的数据是自定义的

四、总结

相当于对单页面的能力进行了加强又熟悉了下整体的架构模式,下一节就要开启导航功能了,也就相当于路由功能,通过点击不同图标进行跳转页面。

相关推荐
QiZhang | UESTC3 小时前
学习日记day
学习
饮马长城窟3 小时前
华为Asend NPU 大模型W8A8量化调优
华为
文火冰糖的硅基工坊5 小时前
[嵌入式系统-114]:华为的操作系统:鸿蒙操作系统(HarmonyOS)和欧拉操作系统(openEuler)
科技·华为·架构·harmonyos
2025年一定要上岸5 小时前
【日常学习】10-15 学习re
学习·算法·正则表达式
千码君20165 小时前
Go语言:记录一下Go语言系统学习的第一天
java·开发语言·学习·golang·gin·并发编程·编译语言
学工科的皮皮志^_^5 小时前
电压源和电流源学习理解
单片机·嵌入式硬件·学习
岸芷漫步5 小时前
鸿蒙应用中的页面跳转分析
harmonyos
骁的小小站6 小时前
Learn C the Hardway学习笔记和拓展知识(一)
c语言·开发语言·c++·经验分享·笔记·学习·bash
大雷神6 小时前
windows开发中使用flutter开发鸿蒙
华为·harmonyos