嘗試用 ArkUI 做一個(gè)相冊(cè)應(yīng)用
想了解更多內(nèi)容,請(qǐng)?jiān)L問(wèn):
51CTO和華為官方合作共建的鴻蒙技術(shù)社區(qū)
前言
今年的HDC華為開(kāi)發(fā)者大會(huì)2021,華為又雙叒推出新的聲明式UI開(kāi)發(fā)框架(ArkUI),咋說(shuō)呢,學(xué)無(wú)止境啊,更新速度堪比坐火箭。雖然沒(méi)能到發(fā)布的現(xiàn)場(chǎng)比較遺憾,但是這并不妨礙我們擼代碼的熱情。我也是第一時(shí)間更新IDE,使用新的開(kāi)發(fā)框架嘗試開(kāi)發(fā)一款圖庫(kù)應(yīng)用。先看效果:

一、基本語(yǔ)法
新的編譯框架基于TS,相比于之前的JS代碼更簡(jiǎn)潔,將原來(lái)的js、hml、css合并為了*.ets一個(gè)文件,而且更接近自然語(yǔ)義,學(xué)習(xí)成本很低。基本是下面的寫法:
- @裝飾器
- struct 組件名 {
- build(){
- //一個(gè)根容器組件,比如:
- Flex (接口){
- //內(nèi)容
- }.屬性
- Tabs (接口){
- TabContent(接口) {
- //內(nèi)容
- }
- }.屬性
- List (接口){
- ListItem(接口) {
- //內(nèi)容
- }
- }.屬性
- }
- }
詳細(xì)的內(nèi)容可以參考官方文檔:https://developer.harmonyos.com/cn/docs/documentation/doc-references/ts-general-ui-concepts-0000001215268053
目前支持的裝飾器:
二、實(shí)現(xiàn)一個(gè)菜單欄


上面2個(gè)圖片使用了兩種不同的實(shí)現(xiàn)方式,第一種使用的是Tabs + TabContent,現(xiàn)成的組件實(shí)現(xiàn)也比較簡(jiǎn)單,代碼如下:
- Tabs(
- { barPosition: BarPosition.End } //指定頁(yè)簽位置
- ) {
- TabContent() {
- Photo() //要實(shí)現(xiàn)的內(nèi)容
- }.tabBar({
- icon: this.menuData[0].url,
- text: this.menuData[0].text
- })
- ... ...
- }
不過(guò)也有點(diǎn)問(wèn)題。第一個(gè)就是圖一中的icon和text有點(diǎn)小,想把尺寸調(diào)大卻發(fā)現(xiàn)各種不支持,只能是這樣默認(rèn)大小,不知道是不是我設(shè)置有問(wèn)題,有知道怎么操作的大佬歡迎留言指點(diǎn)迷津。第二個(gè)問(wèn)題,按理說(shuō)TabContent內(nèi)容是一樣的,可以使用ForEach+數(shù)組,但是也沒(méi)有成功。最終Tabs實(shí)現(xiàn)的效果著實(shí)讓人不太滿意,所以我使用了Flex基本布局 + ForEach 重新實(shí)現(xiàn)了圖二中的效果,代碼如下:
- Flex({
- direction: FlexDirection.Row, // 主軸:橫向布局
- alignItems: ItemAlign.Center, // 主軸:
- justifyContent: FlexAlign.SpaceEvenly
- }) {
- ForEach(this.menuData, (item) => {
- Column() { //列方向布局容器
- this.MenuItem(item.url, item.text)
- }
- .onClick(() => {
- console.info("memememe")
- })
- })
- }
源數(shù)據(jù):
- //State:數(shù)據(jù)變化觸發(fā)build(),實(shí)現(xiàn)UI更新
- @State menuData: Array<any> = [
- { url: $r("app.media.0"), text: "照片" },
- { url: $r("app.media.1blue"), text: "相冊(cè)" },
- { url: $r("app.media.2"), text: "時(shí)刻" },
- { url: $r("app.media.3"), text: "發(fā)現(xiàn)" }
菜單項(xiàng):
- @Builder MenuItem(url, text) {
- Column() {
- Image(url)
- .objectFit(ImageFit.Contain) // 保持長(zhǎng)寬比縮小或放大,以便圖像完全顯示在顯示邊界內(nèi)。
- .width('60%').height('60%')
- Text(text)
- .fontSize(14)
- }
- }
總體來(lái)看Flex + ForEach效果的實(shí)現(xiàn)更自由一些,但是點(diǎn)擊交互切換標(biāo)簽等操作都需要手動(dòng)實(shí)現(xiàn),不如組件化的Tabs方便,或許以后會(huì)支持把。
三、實(shí)現(xiàn)照片區(qū)域
首先照片區(qū)域使用了下面的數(shù)據(jù)格式:
- @State photoData: Array<any> = [
- {
- date: "昨天",
- photos: [{ src: $r("app.media.today1") }, { src: $r("app.media.today2") }, { src: $r("app.media.today3") }]
- },
- {
- date: "2021年10月27日",
- photos: [{ src: $r("app.media.today4") }, { src: $r("app.media.today5") }, { src: $r("app.media.today6") }, {
- src: $r("app.media.today7")
- }]
- },
- {
- date: "2021年10月26日",
- photos: [{ src: $r("app.media.today8") }]
- },
- {
- date: "2021年10月25日",
- photos: [{ src: $r("app.media.today9") },{ src: $r("app.media.today11") }]
- },
- {
- date: "2021年10月24日",
- photos: [{ src: $r("app.media.today10") }]
- }
- ,
- {
- date: "2021年10月23日",
- photos: [{ src: $r("app.media.today1") }]
- }
- ]
所以可以使用ForEach循環(huán)嵌套的方式,只需要簡(jiǎn)單的代碼,就可以實(shí)現(xiàn)照片列表的效果。
- // 照片區(qū)
- List() {
- ForEach(this.photoData, (item) => {
- ListItem() {
- Flex({ direction: FlexDirection.Column }) {
- Text(item.date).fontSize(18).margin({ top: 20,left:15,bottom:5 })
- Flex({ direction: FlexDirection.Row }) {
- ForEach(item.photos, (item) => {
- Image(item.src).objectFit(ImageFit.Cover).width(80).height(80).margin({right:2})
- })
- }
- }
- }
- })
代碼打包上傳了,感興趣的小伙伴,可以下載源碼查看。時(shí)間有限,先體驗(yàn)這么多,有新的心得再來(lái)發(fā)帖和大家交流。
https://harmonyos.51cto.com/resource/1585
想了解更多內(nèi)容,請(qǐng)?jiān)L問(wèn):
51CTO和華為官方合作共建的鴻蒙技術(shù)社區(qū)