【笔记】快应用QuickApp(hap) -- 构建一个微博应用

一、背景

  在上次和小伙伴分享了快应用(后面简称hap)后,有很多待定的思路没有去尝试。这周有时间简单开发了一个热门微博的应用,主要涉及到的难点:富文本、长列表、画廊。这里将整个开发过程中遇到的问题以及解决思路和方法分享给大家,希望对想踩坑的各位有所帮助。

  代码:https://github.com/SmileSmith/quickapp-weibo

  PS:快应用目前好像还没有发布正式版,中间会包含一些吐槽(红字),欢迎指导和拍砖~

二、开发问题和难点记录

1、前期准备

  注意package.json中的toolkit和packager的版本号,表明hap工程toolkit的版本,建议执行 hap update --force更新到最新版本,支持更多特性。

"toolkit": "0.0.30",
"packager": "0.0.5"

  例如在写【原创】快应用QuickApp--HelloWorld体验中,这个版本还是0.0.26,babel还不支持stage2。目前0.0.30版本已经默认支持。

执行 hap update --force会导致.babelrc和.eslintrc.json被刷新,请注意。

2、目录结构

  因之前项目的习惯,不喜欢直接将页面的文件夹放在src下面,改为统一放在src/pages下,在mainfest.json修改如下

  "router": {
    "entry": "pages/Home",
    "pages": {
      "pages/Home": { // 加上pages/
        "component": "index"
      },
      ...  
  },
  "display": {
    "titleBarBackgroundColor": "#e6162d",
    "titleBarTextColor": "#eeeeee",
    "menu": true,
    "pages": {
      "pages/Home": { // 加上pages/
        "titleBarText": "主页",
        "menu": false
      },
      ...

3、内部接口封装

  内部接口中涉及异步操作的,大部分和微信小程序一样使用 success、fail 的回调实现。为方便后续开发,用Promise简单封装了内部接口,并保持接口名称与微信小程序一致。然后在app.ux中全局导入$app中。

  这样,在各个页面中就不需要反复写  import router from '@system.router';  或 var router = require(''@system.router''),直接使用this.$app.api()即可。

详情见src/utils/mv.js、src/utils/app.ux

4、长列表使用内部组件List

  请先参考官方List教程说明,注意下面的性能优化建议,这里着重说明几点:

  1、List通过,对不同结构的列表元素设置不同type,对列表的元素设置唯一的tid,以实现DOM结构复用,提升滑动和渲染的性能表现

  2、官方说明中使用对象池概念的memList,在数据量大的情况下会导致渲染对象List丢失,这点和小程序很像。所以本项目没有使用memList的做法

  3、目前遇到两个问题

    (a) List中的子组件使用if和for进行判断渲染时,会刷新不及时。即修改了if中的条件,但是界面没有刷新

(b)在List中嵌套for循环,for循环的子组件如果是可复用的DOM标签,会导致DOM节点被错误复用。表现为,下图中a微博的图片出现在b微博中。

    <block for="(picIndex, pic) in backPics"> // image标签会因为复用,混乱地出现在不同的子元素中
      <image if="{{showIndex === picIndex}}" class="picture {{enterClass}}" src="{{pic}}" @swipe="changePic()"></image>
    </block>
  <text class="gallery"> // text中的span是行元素,不会复用,在List中嵌套这样的组件没问题。这里代码只做说明,格式有问题
    <block for="(picIndex, pic) in backPics">
      <span if="{{showIndex === picIndex}}" class="picture {{enterClass}}" src="{{pic}}" @swipe="changePic()"></span>
    </block>
  </text>>

4、富文本

  官方的rich-text支持吃快应用格式的html字符串,所以微博接口返回的原生html字符串中含有icon等表情,不能使用。

  项目参考在小程序中的做法,先用正则过滤,并遍历形成内容数组,然后在template中for循环出来。详情见 src/components/richContent.ux

  目前有个问题:

  用text嵌入span和a,text中不支持image或其它形式的图片,无法展示表情icon。

  如果采用div嵌入text、a和image,又会遇到List中元素错乱问题。

5、画廊展示大图

  开始的做法,开发一个gallery组件,放在全局,然后通过消息控制,然而还是遇到List渲染问题。

  目前采用页面的做法,通过路由传参数。一是可以做到全屏,二是避开List优化的问题。详情见 src/pages/Gallery/index.ux

  利用stack覆盖的特性,将小图和加载动画放在下面,然后等待大图加载,大图加载完毕后会覆盖小图和加载动画。

  <stack class="gallery">
    <block for="(picIndex, pic) in backPics"> // 在列表中已经加载好的小图,保证用户能第一时间看到内容,虽然是模糊的
      <image if="{{showIndex === picIndex}}" class="picture {{enterClass}}" src="{{pic}}" @swipe="changePic()"></image>
    </block>
    <progress class="load-progress" type="circular"></progress> // 加载动画
    <block for="(picIndex, pic) in showPics"> // 大图,等待加载完毕后覆盖小图和动画
      <image if="{{showIndex === picIndex}}" class="picture {{enterClass}}" src="{{pic}}" @longpress="longpress" @swipe="changePic()"></image>
    </block>
    <div show="{{showIndex > 0}}" class="button left-button" @click="changePic({direction: 'right'})"><text>«</text></div>
    <div show="{{showIndex < showPics.length - 1}}"  class="button right-button" @click="changePic({direction: 'left'})"><text>»</text></div>
    <div class="button back-button" @click="closeGallery"><text>︽</text></div>
  </stack>

  目前有个问题:

  统一元素不支持同时监听click和swiper事件,所以无法实现点击返回列表

  大图渲染问题,实测大图在高宽比不超过屏幕时,显示正常;超过时(如长图片)会导致渲染模糊,越长越模糊:

5、样式类问题

  • 没有样式继承,div中写的font-size只无效的,必须写在对应的text或span中
  • justify-content 不支持 space-around,可以用容器包裹,容器padding实现。
  • position只有fixed,要实现relative用padding调整位置
  • border不支持border-left写法,需要border: 0px solid #eeeeee; border-left: 1px;

5、Debugger

  在调试器中点击开始调试,在代码中打上debugger,就能调试了。

三、总结

快应用整体还处于beat阶段,许多特性还有问题,希望官方尽快解决吧。整体写法偏向小程序,以后类似mpvue的东西应该也会出现;性能优于小程序,目前生态小,最大的问题还是推广。。。

之前想到的几个方向,目前还有两个在探索中,有结果再写吧。

1)组件 √

2)路由 √

3)原生接口 √

4)全局状态管理:考虑继承mobx或类似的flux组件

5)类型检测: 考虑用ts

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏葡萄城控件技术团队

免费资源 | ActiveReports 报表控件发布多平台 Demo 代码集合

近期,ActiveReports 产品开发组的小伙伴针对大家比较关注的报表功能、常见问题、经典实现,特意准备了一个Demo代码集合,涉及WinFormss \ ...

23340
来自专栏Java成神之路

js_调试_01_14 个你可能不知道的 JavaScript 调试技巧

了解你的工具在完成任务时有很重要的意义。 尽管 JavaScript 是出了名的难以调试,但是如果你掌握了一些小技巧,错误和 bug 解决起来就会快多了。

12730
来自专栏开源优测

Robot Framework | 02 从抛弃RIDE开始创建你的RFS测试

概述 大多数情况下,我们用RobotFramework时,一般基于其图形界面的RIDE来编辑、管理、执行用例。 今天我们分享下基于非编辑器模式的RobotFra...

61740
来自专栏非著名程序员

倍数提高工作效率的 Android Studio 奇技

这是从Philippe Breault的系列文章《Android Studio Tips Of the Day》中提取出来的自认为精华的部分。这些技巧在实际应用...

24790
来自专栏听雨堂

ASP.Net Web Page深入探讨

这篇文章经典,看过之后大受启发。值得一看!看来ASP.NET跟JSP其实是一样的,本质上没区别,ASP.NET能做到的JSP一样可以做到,反之亦然。只不过ASP...

28870
来自专栏开源优测

Robot Framework | 02 从抛弃RIDE开始创建你的RFS测试

概述 大多数情况下,我们用RobotFramework时,一般基于其图形界面的RIDE来编辑、管理、执行用例。 今天我们分享下基于非编辑器模式的RobotFra...

35590
来自专栏云飞学编程

Python爬虫基础学习,从一个小案例来学习xpath匹配方法

学习目的是为了实践,而实践又可以加深我们的学习效率,今天给大家带来了lxml库的xpath匹配方法的实例!教程大家网上搜索有很多,我们只看实用功能,当然,如果您...

8730
来自专栏xiaoxi666的专栏

【开源项目】将图片转换为字符画

请移步Github仓库:https://github.com/xiaoxi666/Img2AsciiVision

15610
来自专栏搞前端的李蚊子

ReactJs移动端兼容问题汇总

A:初步怀疑是css属性没有加前缀引发的兼容问题,但添加后发现也不行,通过webview调试后控制台输出Set is undefined,搜索后发现React依...

26450
来自专栏Google Dart

开始使用-编写你的第一个Flutter应用程序 顶

这是创建您的第一个Flutter应用程序的指南。 如果您熟悉面向对象的代码和基本编程概念(如变量,循环和条件),则可以完成本教程。 您不需要以前使用Dart或移...

10620

扫码关注云+社区

领取腾讯云代金券