harmony:基本使用

简介: HarmonyOS提供了一套强大的UI开发框架——方舟开发框架(ArkUI),支持ArkTS声明式开发范式和类Web开发范式。ArkUI框架不仅提供了丰富的组件、布局计算、动画能力和UI交互等功能,还针对不同开发者需求提供了灵活的开发方式。项目结构清晰,包括entry模块、ArkTS源码目录、页面定义、资源文件管理等。此外,还支持自定义组件、装饰器、生命周期管理、路由跳转等高级特性,极大提升了开发效率和应用性能。

简介

官方的解释

UI框架

HarmonyOS提供了一套UI开发框架,即方舟开发框架(ArkUI框架)。方舟开发框架可为开发者提供应用UI开发所必需的能力,比如多种组件、布局计算、动画能力、UI交互、绘制等。

方舟开发框架针对不同目的和技术背景的开发者提供了两种开发范式,分别是基于ArkTS的声明式开发范式(简称“声明式开发范式”)和兼容JS的类Web开发范式(简称“类Web开发范式”)。以下是两种开发范式的简单对比。

ArkTS是一种为构建高性能应用而设计的编程语言。ArkTS在继承TypeScript语法的基础上进行了优化,以提供更高的性能和开发效率。

项目结构

entry:HarmonyOS工程模块,编译构建生成一个HAP包。

src > main > ets:用于存放ArkTS源码。

src > main > ets > entryability:应用/服务的入口。

src > main > ets > entrybackupability:应用提供扩展的备份恢复能力。

src > main > ets > pages:应用/服务包含的页面。

src > main > resources:用于存放应用/服务所用到的资源文件,如图形、多媒体、字符串、布局文件等。关于资源文件,详见资源分类与访问。

src > main > module.json5:模块配置文件。主要包含HAP包的配置信息、应用/服务在具体设备上的配置信息以及应用/服务的全局配置信息。具体的配置文件说明,详见module.json5配置文件。

build-profile.json5:当前的模块信息 、编译信息配置项,包括buildOption、targets配置等。

hvigorfile.ts:模块级编译构建任务脚本。

obfuscation-rules.txt:混淆规则文件。混淆开启后,在使用Release模式进行编译时,会对代码进行编译、混淆及压缩处理,保护代码资产。详见开启代码混淆。

oh-package.json5:用来描述包名、版本、入口文件(类型声明文件)和依赖项等信息。

oh_modules:用于存放三方库依赖信息。

build-profile.json5:工程级配置信息,包括签名signingConfigs、产品配置products等。其中products中可配置当前运行环境,默认为HarmonyOS。

hvigorfile.ts:工程级编译构建任务脚本。

oh-package.json5:主要用来描述全局配置,如:依赖覆盖(overrides)、依赖关系重写(overrideDependencyMap)和参数化配置(parameterFile)等。


基本组件

按钮

  Button() {

         Text('Next')

           .fontSize(30)

           .fontWeight(FontWeight.Bold)

       }

       .type(ButtonType.Capsule)

       .margin({

         top: 20

       })

       .backgroundColor('#0D9FFB')

       .width('40%')

       .height('5%')

       // 跳转按钮绑定onClick事件,点击时跳转到第二页

       .onClick(() => {

         console.info(`Succeeded in clicking the 'Next' button.`)

         // 跳转到第二页

         router.pushUrl({ url: 'pages/Second' }).then(() => {

           console.info('Succeeded in jumping to the second page.')

         }).catch((err: BusinessError) => {

           console.error(`Failed to jump to the second page. Code is ${err.code}, message is ${err.message}`)

         })

       })

arkts

装饰器

@Component
struct ParentComponent {
  doSomeCalculations() {
  }

  calcTextValue(): string {
    return 'Hello World';
  }

  @Builder doSomeRender() {
    Text(`Hello World`)
  }

  build() {
    Column() {
      // 反例:不能调用没有用@Builder装饰的方法
      this.doSomeCalculations();
      // 正例:可以调用
      this.doSomeRender();
      // 正例:参数可以为调用TS方法的返回值
      Text(this.calcTextValue())
    }
  }
}

@Builder装饰器:自定义构建函数

装饰器:用于装饰类、结构、方法以及变量,并赋予特殊含义。如上述的代码片段中@Entry/@Component/@State都属于装饰器,@表示自定义组件,@Entry表示该自定义组件为入口组件,@State表示组件中的状态变量,类似于赋予变量响应式,状态变量值发生变化会触发组件更新。


struct:自定义组件基于struct实现,struct + 自定义组件名 + {...}的组合构成自定义组件,不能有继承关系。对于struct的实例化,可以省略new。

                                         、

                                       

                                         @Component:@Component装饰器仅能装饰struct关键字声明的数据结构。struct被@Component装饰后具备组件化的能力,需要实现build方法描述UI,一个struct只能被一个@Component装饰。

                                       

                                         build()函数:build()函数用于定义自定义组件的声明式UI描述,自定义组件必须定义build()函数。

                                       

 

                                           @Entry:@Entry装饰的自定义组件将作为UI页面的入口。在单个UI页面中,最多可以使用@Entry装饰一个自定义组件。@Entry可以接受一个可选的LocalStorage的参数。


所有声明在build()函数的语句,我们统称为UI描述,UI描述需要遵循以下规则:


@builder

//在组件外定义words构建函数
@Entry
@Component
struct Index {
  @State message: string = '@Builder \n 组件内构建函数'
  //设置状态变量,方便在选中诗词时能够作为标志位,默认未选中
  @State isChoose: boolean = false
  //  这个是用来创建一个容器的 用来创建组件更好
  @Builder words(content:string){
    Row(){
      Image(this.isChoose ? $r('app.media.foreground') : $r('app.media.startIcon'))
        .width(35)
        .margin(15)
      //构建函数调用自己的形式参数时不需要使用this引用
      Text(content)
        .fontSize(25)
        .decoration({type:this.isChoose ? TextDecorationType.LineThrough : TextDecorationType.None})
    }
    .backgroundColor(Color.Orange)
    .padding(5)
    .borderRadius(25)
    .width('85%')
    .height(70)
    .margin({
      top:10
    })
    //给row组件加上点击事件
    .onClick(()=>{
      this.isChoose = !this.isChoose
    })
  }
  build() {
    Row() {
      Column({space:20}) {
        Text(this.message)
          .fontSize(50)
          .fontWeight(FontWeight.Bold)
          .textAlign(TextAlign.Center)  //设置文本居中显示
        //在组件内调用组件内定义的构建函数:由于该构建函数属于组件内的一部分,因此需要使用this进行调用
        this.words('是造物者之无尽藏也,')
        this.words('而吾与子之所共适!')
        //调用组件外构建函数
        // words2('是造物者之无尽藏也,')
        // words2('而吾与子之所共适!')
      }
      .width('100%')
    }
    .height('100%')
  }
}
 let isChoose = false
//创建组件外构建函数:必须加上关键字function
@Builder function words2(content:string){
  Row(){
    Image(isChoose ? $r('app.media.layered_image') : $r('app.media.background'))
      .width(35)
      .margin(15)
    //构建函数调用自己的形式参数时不需要使用this引用
    Text(content)
      .fontSize(25)
      .decoration({type:isChoose ? TextDecorationType.LineThrough : TextDecorationType.None})
  }
  .backgroundColor(Color.Pink)
  .padding(5)
  .borderRadius(25)
  .width('85%')
  .height(70)
  .margin({
    top:10
  })
  //给row组件加上点击事件
  .onClick(()=>{
    isChoose = !isChoose
  })
}

自定义组件


创建一个 component 文件 下面 放组件

@Component
export struct MyButton {
  @State count: number = 0;
  @State btnName: string = 'click me'
  build() {
    Column() {
      // text 只能 放 string 类型
      Text(''+this.count)
      Divider()
      // 直接使用便可以了
      Button(this.btnName)
        .onClick(() => {
          this.count += 1;
        })
    }
    .width("100%")
    .height("100%")
  }
}

引用和 使用 像vue 一样

//  可以直接使用名字,会自动引用
import { MyButton } from '../Component/MyButton';
@Entry
@Component
struct Index {
  @State message: string = 'Hello World'
  build() {
      Column(){
        Text("this is father")
        MyButton({
          //里面 定义的变量名 加上 就可以了
          btnName:'father button'
        })
    }.height('100%')
    .width('100%')
  }
}


生命周期

onCreate

如用户打开电池管理应用,在应用加载的过程中,在UI界面出现之前,可以在onCreate回调中读取;
在Create状态,在UIAbility实例创建时触发,系统会调用onCreate回调。

在onWindowStageCreate(windowStage)中通过loadContent接口设置应用要加载的页面。

在UIAbility的UI页面完全不可见之后,即UIAbility切换⾄后台时候触发;

当地图应用切换到后台状态,可以在onBackground回调中停止定位功能,以节省系统的资源消耗;

可以在onBackground回调中释放UI页面不可见时无用的资源,或者在此回调中执行较为耗时的操作。

路由

简单的跳转

// Index.ets
// 导入页面路由模块
import { router } from '@kit.ArkUI';
@Entry
@Component
struct Index {
  @State message: string = 'Hello World'
  build() {
      Column(){
        Text("this is father")
        Button('跳转').onClick(()=>{
          router.pushUrl({
            url:'pages/Demo'
            // params:{
            //   id:'index',
            //   data:10
            // }
          }).then(()=>{
            console.log(
              "成功");
          })
        })
    }.height('100%')
    .width('100%')
  }
}
@Entry
@Component
struct Demo {
  build() {
    Column(){
      Text("this is child")
    }.height('100%')
    .width('100%')
  }
}

管理路由的页面


跳转加参数

// Index.ets
// 导入页面路由模块
import { router } from '@kit.ArkUI';
@Entry
@Component
struct Index {
  @State message: string = 'Hello World'
  build() {
      Column(){
        Text("this is father")
        Button('跳转').onClick(()=>{
          router.pushUrl({
            url:'pages/Demo',
            params:{
              id:'index',
              data:10
            }
          }).then(()=>{
            console.log(
              "成功");
          })
        })
    }.height('100%')
    .width('100%')
  }
}
import { router } from '@kit.ArkUI';
// 定义参数的结构
interface ParamsFromIndex {
  index?: string; // 假设 index 是一个可选的字符串
  id?: string;
  // 其他参数可以在这里添加
}
@Entry
@Component
struct Demo {
  @State message: string = "second page";
  @State paramsFromIndex: ParamsFromIndex = router.getParams() as ParamsFromIndex; // 明确类型
  build() {
    Column() {
      Button('click me').onClick(() => {
        console.log(this.paramsFromIndex.id); // 访问 index
      });
    }.height('100%')
    .width('100%');
  }
}

函数

基本使用通过


function print(name?: string) {
  if (name == undefined) {
    console.log('Hello!');
  } else {
    console.log(`Hello, ${name}!`);
  }
}
      Button("click me").onClick(()=>{
        print("youren")
      })
function sum(...numbers: number[]): number {
  let res = 0;
  for (let n of numbers)
    res += n;
  return res;
}
      Button("click me").onClick(()=>{
       let a = sum(1, 2, 3) // 返回6
        console.log(''+a)
      })
function foo(x: number): void;            /* 第一个函数定义 */
function foo(x: string): void;            /* 第二个函数定义 */
function foo(x: number | string): void {  /* 函数实现 */
}
foo(123);     //  OK,使用第一个定义
foo('aa'); // OK,使用第二个定义


class Person {
  name: string = ''
  surname: string = ''
  constructor (n: string, sn: string) {
    this.name = n;
    this.surname = sn;
  }
  fullName(): string {
    return this.name + ' ' + this.surname;
  }
}
let p = new Person('John', 'Smith');
console.log(p.fullName());









相关文章
|
17天前
|
存储 弹性计算 人工智能
阿里云Alex Chen:普惠计算服务,助力企业创新
本文整理自阿里云弹性计算产品线、存储产品线产品负责人陈起鲲(Alex Chen)在2024云栖大会「弹性计算专场-普惠计算服务,助力企业创新」中的分享。在演讲中,他分享了阿里云弹性计算,如何帮助千行百业的客户在多样化的业务环境和不同的计算能力需求下,实现了成本降低和效率提升的实际案例。同时,基于全面升级的CIPU2.0技术,弹性计算全线产品的性能、稳定性等关键指标得到了全面升级。此外,他还宣布了弹性计算包括:通用计算、加速计算和容器计算的全新产品家族,旨在加速AI与云计算的融合,推动客户的业务创新。
|
7天前
|
SQL 人工智能 安全
【灵码助力安全1】——利用通义灵码辅助快速代码审计的最佳实践
本文介绍了作者在数据安全比赛中遇到的一个开源框架的代码审计过程。作者使用了多种工具,特别是“通义灵码”,帮助发现了多个高危漏洞,包括路径遍历、文件上传、目录删除、SQL注入和XSS漏洞。文章详细描述了如何利用这些工具进行漏洞定位和验证,并分享了使用“通义灵码”的心得和体验。最后,作者总结了AI在代码审计中的优势和不足,并展望了未来的发展方向。
|
3天前
|
负载均衡 算法 网络安全
阿里云WoSign SSL证书申请指南_沃通SSL技术文档
阿里云平台WoSign品牌SSL证书是由阿里云合作伙伴沃通CA提供,上线阿里云平台以来,成为阿里云平台热销的国产品牌证书产品,用户在阿里云平台https://www.aliyun.com/product/cas 可直接下单购买WoSign SSL证书,快捷部署到阿里云产品中。
1843 6
阿里云WoSign SSL证书申请指南_沃通SSL技术文档
|
1天前
|
存储 安全 Oracle
【灵码助力安全3】——利用通义灵码辅助智能合约漏洞检测的尝试
本文探讨了智能合约的安全性问题,特别是重入攻击、预言机操纵、整数溢出和时间戳依赖性等常见漏洞。文章通过实例详细分析了重入攻击的原理和防范措施,展示了如何利用通义灵码辅助检测和修复这些漏洞。此外,文章还介绍了最新的研究成果,如GPTScan工具,该工具通过结合大模型和静态分析技术,提高了智能合约漏洞检测的准确性和效率。最后,文章总结了灵码在智能合约安全领域的应用前景,指出尽管存在一些局限性,但其在检测和预防逻辑漏洞方面仍展现出巨大潜力。
|
24天前
|
存储 人工智能 弹性计算
产品技术能力飞跃,阿里云E-HPC荣获“CCF 产品创新奖”!
9月24日,在中国计算机学会举办的“2024 CCF 全国高性能计算学术年会”中,阿里云弹性高性能计算(E-HPC)荣获「 CCF HPC China 2024 产品创新奖」。这也是继 2022 年之后,阿里云E-HPC 再次荣获此奖项,代表着阿里云在云超算领域的持续创新结果,其产品能力和技术成果得到了业界的一致认可。
|
6天前
|
Web App开发 算法 安全
什么是阿里云WoSign SSL证书?_沃通SSL技术文档
WoSign品牌SSL证书由阿里云平台SSL证书合作伙伴沃通CA提供,上线阿里云平台以来,成为阿里云平台热销的国产品牌证书产品。
1777 2
|
15天前
|
编解码 Java 程序员
写代码还有专业的编程显示器?
写代码已经十个年头了, 一直都是习惯直接用一台Mac电脑写代码 偶尔接一个显示器, 但是可能因为公司配的显示器不怎么样, 还要接转接头 搞得桌面杂乱无章,分辨率也低,感觉屏幕还是Mac自带的看着舒服
|
22天前
|
存储 人工智能 缓存
AI助理直击要害,从繁复中提炼精华——使用CDN加速访问OSS存储的图片
本案例介绍如何利用AI助理快速实现OSS存储的图片接入CDN,以加速图片访问。通过AI助理提炼关键操作步骤,避免在复杂文档中寻找解决方案。主要步骤包括开通CDN、添加加速域名、配置CNAME等。实测显示,接入CDN后图片加载时间显著缩短,验证了加速效果。此方法大幅提高了操作效率,降低了学习成本。
5028 15
|
9天前
|
人工智能 关系型数据库 Serverless
1024,致开发者们——希望和你一起用技术人独有的方式,庆祝你的主场
阿里云开发者社区推出“1024·云上见”程序员节专题活动,包括云上实操、开发者测评和征文三个分会场,提供14个实操活动、3个解决方案、3 个产品方案的测评及征文比赛,旨在帮助开发者提升技能、分享经验,共筑技术梦想。
1018 147
|
17天前
|
存储 缓存 关系型数据库
MySQL事务日志-Redo Log工作原理分析
事务的隔离性和原子性分别通过锁和事务日志实现,而持久性则依赖于事务日志中的`Redo Log`。在MySQL中,`Redo Log`确保已提交事务的数据能持久保存,即使系统崩溃也能通过重做日志恢复数据。其工作原理是记录数据在内存中的更改,待事务提交时写入磁盘。此外,`Redo Log`采用简单的物理日志格式和高效的顺序IO,确保快速提交。通过不同的落盘策略,可在性能和安全性之间做出权衡。
1582 12