鸿蒙待办事项应用【鸿蒙专题14】
作者:坚果
公众号:""
华为云享专家,InfoQ签约作者,阿里云专家博主,51CTO博客首席体验官,,专注于大前端技术的分享,包括Flutter,小程序,安卓,VUE,JavaScript。
在前几篇文章里也介绍了许多关于鸿蒙开发的技巧,今天我们就来做自己的第一个代办事项应用。鸿蒙开发和Flutter一样,都具有跨平台的特性,Flutter一套代码可以在Android,ios,web。linux,desk等部署,鸿蒙也有这样的特性,可同时在手机、大屏、手表生效,体验“一次开发、多设备部署”特性。
接下来我们开始正文
第一步必然是安装 。推荐安装3.0beta版,学习的话,用3.0还是蛮不错的。
第二部新建工程
自从微信小程序出现以来,各种“小程序”如雨后春笋一般出现。事实证明小程序这种开发方式非常好,鸿蒙 JS UI 框架采用类似的方式也是在意料之中的。
一个小程序(在鸿蒙 OS 中,也就是 Ability)由多个页面组成,每个页面由三部分组成:
-
.hml 用来描述界面的元素
-
.css 用来描述界面的风格
-
.js 用来编写处理事件逻辑
我们来看个例子:
js文件
const BUTTON_STATE_IMAGE = ["/common/checkbutton.png", "/common/done.png"];
const TAG_STATE = ["show", "hide"];
const TEXT_COLOR = ["text-default", "text-gray"];
const EVENT_LEVEL = ["urgent", "senior", "middle", "low"];
export default {
title: "任务列表",
taskList: [
{
id: "id-1",
event: "购买礼物",
time: "10:30",
checkBtn: BUTTON_STATE_IMAGE[1],
color: TEXT_COLOR[1],
showTag: TAG_STATE[1],
tag: EVENT_LEVEL[1],
},
{
id: "id-2",
event: "健身锻炼",
time: "15:30",
checkBtn: BUTTON_STATE_IMAGE[0],
color: TEXT_COLOR[0],
showTag: TAG_STATE[0],
tag: EVENT_LEVEL[0],
},
{
id: "id-3",
event: "生日约会",
time: "19:30",
checkBtn: BUTTON_STATE_IMAGE[0],
color: TEXT_COLOR[0],
showTag: TAG_STATE[0],
tag: EVENT_LEVEL[2],
},
]
};
css文件
.container {
flex-direction: column;
background-color: black;
}
.title {
font-weight: 600;
color: #ccc;
background-color: black;
opacity: 1;
}
.tag-list {
width: 100%;
}
.todo-list-item {
width: 100%;
}
.todo-item {
width: 100%;
border-radius: 2px;
align-items: center;
}
.flex-row {
display: flex;
flex-direction: row;
align-items: center;
}
.todo-name-mark {
width: 100%;
height: 100%;
align-items: center;
}
.todo-name {
font-size: 16px;
color: white;
margin-right: 2px;
max-lines: 1;
text-overflow: ellipsis;
overflow: hidden;
white-space: nowrap;
display: inline-block;
vertical-align: middle;
}
.text-default {
color: white;
}
.text-gray {
color: gray;
}
.todo-mark {
width: 9px;
height: 9px;
margin-left: 8px;
border-radius: 25px;
background-color: lightslategrey;
}
.todo-time {
font-size: 14px;
width: 100%;
height: 100%;
text-align: left;
color: gray;
margin-top:1px;
}
.urgent {
background-color: firebrick;
}
.senior {
background-color: gold;
}
.middle {
background-color: mediumaquamarine;
}
.low {
background-color: #0D9FFB;
}
.hide {
display: none;
}
.show {
display: inline-block;
}
.todo-image {
width: 20px;
height: 20px;
object-fit: contain;
margin-top: 1px;
}
.todo-text-wrapper {
height: 100%;
flex-grow: 1;
margin: 0px 16px;
flex-direction: column;
}
@media (device-type: tv) {
.title {
font-size: 22px;
padding: 10px;
}
.tag-list {
padding-top:30px;
padding-left:12px;
}
.todo-list-item {
margin-top: 20px;
}
.todo-image {
width: 20px;
height: 20px;
}
.todo-name {
font-size: 18px;
max-width: 460px
}
}
@media (device-type: phone) {
.title {
font-size: 21px;
padding-top: 10px;
padding-bottom: 10px;
padding-left: 10px;
}
.tag-list {
padding-top:48px;
}
.todo-list-item {
margin: 2px 8px;
}
.todo-name-mark {
margin: 5px 0px;
}
.todo-name {
max-width: 180px;
}
}
@media (device-type: wearable) {
.title {
font-size: 26px;
width: 100%;
height: 54px;
text-align: center;
}
.tag-list {
padding-top:54px;
}
.todo-list-item {
padding-left: 50px;
padding-right: 25px;
}
.todo-name-mark {
margin: 3px 0px;
}
.todo-name {
max-width: 106px
}
}
htm文件
<div class="container">
<text class="title">
{{title}}
</text>
<list class="tag-list">
<list-item for="{{taskList}}" class="todo-list-item" focusable="false">
<div class="todo-item flex-row">
<image class="todo-image" src="{{$item.checkBtn}}" onclick="completeEvent({{$item.id}})"></image>
<div class="todo-text-wrapper">
<div class="todo-name-mark">
<text class="todo-name {{$item.color}}" focusable="false">{{$item.event}}</text>
<text class="todo-mark {{$item.tag}} {{$item.showTag}}"></text>
</div>
<text class="todo-time">{{$item.time}}</text>
</div>
</div>
</list-item>
</list>
</div>
2. 工作原理
要理解它的工作原理,先研究一下编译之后的代码是非常重要的。上面的三个文件,编译之后会生成一个文件,其位置在:./entry/build/intermediates/res/debug/lite/assets/js/default/pages/index/index.js
index.hml 变成了创建函数:
index.css 变成了 JSON 文件。
这种处理方式很妙,把 JS 不擅长处理的 XML/CSS 转换成了 JS 代码和 JSON 对象,这个转换由工具完成,避免了运行时的开销。
在没有研究编译之后的代码时,我尝试在 ace/graphic 两个包中寻找解析 HML 的代码,让我惊讶的是没有找到相关代码。看了这些生成的代码之后才恍然大悟。
计数器应用:
index.hml
<div class="container">
<text>{{count}}</text>
<input if="{{count < 10}}"type="button" value="Inc" onclick="inc"/>
<input if="{{count > 0}}" type="button" value="Dec" onclick="dec"/>
</div>
index.css
.container {
flex-direction: column;
justify-content: center;
align-items: center;
left: 0px;
top: 0px;
width: 454px;
height: 454px;
}
index.js
export default {
data: {
count: 5
},
inc() {
this.count++;
},
dec() {
this.count--;
}
}
参考文档
- 点赞
- 收藏
- 关注作者
评论(0)