基于后端云的吉他谱小程序开发
人的一生90%的时间都在做着无聊的事情,社会的发展使得我们的闲暇时间越来越多,我们把除了工作的其他时间放在各种娱乐活动上。
程序员有点特殊,他们把敲代码看成娱乐活动的一部分,以此打发时间的不占少数。这不最近无聊搞了一个口袋吉他小程序,使用bmob后端云提供数据存储服务,除吉他谱图片,其他图片存储在七牛。
关于bmob小程序开发文档请戳这里,文档详细简练,主要是缩短了开发周期,不过对于复杂的项目,还是推荐使用自己服务器提供数据服务。
使用微信扫描二维码预览
源码地址:https://github.com/alex1504/wx-guita_tab
下面分点分享下小程序的开发过程中的关键点及感受,说明:
- 小程序标签统称组件,Html标签统称元素。
- 部分内容会与vuejs及jQuery作对比
使用iconfont字体图标
新建项目并添加图标
在app.wxss中以unicode方式引入
@font-face {
font-family: 'iconfont'; /* project id 431644 */
src: url('//at.alicdn.com/t/font_431644_aahynh26y6lp7gb9.eot');
src: url('//at.alicdn.com/t/font_431644_aahynh26y6lp7gb9.eot?#iefix') format('embedded-opentype'),
url('//at.alicdn.com/t/font_431644_aahynh26y6lp7gb9.woff') format('woff'),
url('//at.alicdn.com/t/font_431644_aahynh26y6lp7gb9.ttf') format('truetype'),
url('//at.alicdn.com/t/font_431644_aahynh26y6lp7gb9.svg#iconfont') format('svg');
}
定义通用icon样式,定义伪元素
.icon{
display: inline-block;
font-family: 'iconfont';
}
.icon-home::before{
content: "e600";
}
使用
<view class="icon icon-home"</view>
小程序事件绑定及处理器
小程序并没有类似vuejs的v-model进行双向绑定,使用bindinput类似jQuery监听input事件在事件处理器中更新数据,通过event对象e.data.value即可获得input的值。
// bindconfirm监听键盘回车事件,focus属性聚焦渲染组件时会自动弹出手机软键盘
<input type='text' placeholder='歌曲名 / 歌手' bindinput='bindSearchInput' bindconfirm='onSearch' focus></input>
bindSearchInput(e) {
this.setData({
searchTxt: e.detail.value
})
}
小程序中的事件处理器并不能像vue一样传入参数,因为事件处理器只有一个默认的参数event对象,在for循环的组件中如果要想获取元素绑定的id,可以通过和jQuery相同的方式绑定data属性。
<!-- 轮播图 -->
<swiper indicator-dots="{{indicatorDots}}" autoplay="{{autoplay}}" interval="{{interval}}" duration="{{duration}}">
<block wx:for="{{banner_list}}" wx:key="{{index}}">
<swiper-item bindtap="navigateToDetail" data-id="{{item.href}}">
<image src="{{item.image}}" class="slide-image" mode="widthFix"></image>
</swiper-item>
</block>
</swiper>
获取id:
//事件处理函数
navigateToDetail: function (e) {
const id = e.currentTarget.dataset.id;
}
阻止事件冒泡
bindtap、bindlongtap、bindtouchstart、bindtouchmove、bindtouchend、bindtouchcancle
对应阻止冒泡事件将bind用catch替代
setData
小程序的视图更新需要调用setData修改绑定数据,直接对数据进行修改是不会触发视图层更新的。setData接受一个对象,为需要添加或修改的属性。属性名有点特殊,[]中的值会被识别为变量,因此如果要对对象数组中的某个属性进行修改,只能预先拼接好属性名。
错误做法:
// 视图不更新
this.data.searchSongs[index].love_flag': 2
// SyntaxError: unknown: Unexpected token
this.setData({
'searchSongs[' + index + '].love_flag': 2
})
正确做法:
setSongFlag(e) {
// 注意setData属性名[]中的非整数值会被识别为变量
let key = 'searchSongs[' + index + '].love_flag'
this.setData({
[key]: 2
})
关于image组件
小程序wxss的background-image及image组件都不支持本地url
在H5的开发中,通常我们会将页面一些不需要根据容器大小来选择显示方式的图片使用img标签,需要一些特殊显示方式的使用background。但小程序只需要image组件便可。它提供的mode属性和背景定义图片及img元素控制图片显示方式对比
mode属性 |
background-size |
html img元素 |
---|---|---|
scaleToFill |
100%,100%(默认) |
width:100%;height:100% |
aspectFit |
contain |
js实现 |
aspectFill |
cover |
js实现 |
widthFix |
100%, auto |
width: 100%; |
其他的top、bottom、right、left等不缩放图片调整位置的属性与background-position作用相同,img元素则只能通过定位控制。
小程序API异步方案
如果没有强迫症,小程序API使用默认回调的方式即可;另外由于小程序只支持es6,不支持async及await,也可以将API封装成promise的方式。
function promisify(fn) {
return function (obj = {}) {
return new Promise((resolve, reject) => {
obj.success = function (res) {
resolve(res)
}
obj.fail = function (res) {
reject(res)
}
fn(obj)//执行函数,obj为传入函数的参数
})
}
}
module.exports = {
promisify: promisify
}
使用:
const promisify = require('./promisify.js')
const request = promisify(wx.request);
request({
url: 'some URL'
method: 'GET',
}).then(res => {
console.log(res)
}
小程序问题
- 调试器没有css快捷提示功能和颜色面板,影响布局及颜色调整效率(随性派)
- 无法引入第三方js库
- 内置组件单调,没有考虑字体数量比较多时的自适应情况
- 不支持跳转外部链接
- 背景图片或者image组件不能用本地图片
关于小程序审发布或更新
小程序上线需要经过审核、发布两个过程。
审核通过后有全量更新、或者分阶段发布,小程序才会更新,首次发布没有选项。
全量发布:即时向全量微信用户发布新版小程序。
分阶段发布:新版小程序将在15天内以开发者自定义比例,向微信用户发布更新
详情见知乎:发布小程序时选择全量发布和分阶段发布是什么意思?
不得不说小程序审核速度是非常快的,即便是个人申请(相比以企业账号申请会有应用服务类型限制),通常小程序没有涉及政策不允许的内容或者超过小程序允许的应用服务类型,都是可以顺利通过,初次体验,即便在国庆期间,也是有工作团队进行审核,审核时间通常在几小时内。
总结
在开发这个小程序时,微信小程序只支持页面级开发,如今小程序已支持组件开发和插件开发。组件的结构和页面并无区别,自定义组件可以引入其他的组件,具体的开发步骤可以参考这边文章【微信小程序】自定义组件
小程序的兴起使得前端开发又多了一个工作任务,但这也使得前端程序员的成就感越来越强,当然没有经历过浏览器刀耕火种年代的工程师难以体会这种辛酸,但也没必要,只要跟上时代的潮流和注重自身的基础建设便已足够了,前端路途艰辛,我在路上与你共勉。
- 给出一组非负整数,重新排序组成最大的数
- [机智的机器在学习] TensorFlow实现Kmeans聚类
- [机智的机器在学习] 利用TensorFlow实现多元线性回归分类器
- [数据结构和算法]《算法导论》动态规划笔记(1)
- [数据结构和算法]《算法导论》动态规划笔记(2)
- [算法与数据结构] 《算法导论》堆排序笔记
- [数据结构与算法] 链表的其他类型
- [数据结构与算法] 链接表总结
- [数据结构与算法] 线性表总结
- [数据结构与算法] Python实现二分查找
- [机智的机器在学习] 机器学习中的归一化和正则化问题
- [情人节] jieba分词介绍
- 左手用R右手Python系列——异常捕获与容错处理
- 【观点】漫谈推荐系统及数据库技术(二)——分布式数据库技术
- JavaScript 教程
- JavaScript 编辑工具
- JavaScript 与HTML
- JavaScript 与Java
- JavaScript 数据结构
- JavaScript 基本数据类型
- JavaScript 特殊数据类型
- JavaScript 运算符
- JavaScript typeof 运算符
- JavaScript 表达式
- JavaScript 类型转换
- JavaScript 基本语法
- JavaScript 注释
- Javascript 基本处理流程
- Javascript 选择结构
- Javascript if 语句
- Javascript if 语句的嵌套
- Javascript switch 语句
- Javascript 循环结构
- Javascript 循环结构实例
- Javascript 跳转语句
- Javascript 控制语句总结
- Javascript 函数介绍
- Javascript 函数的定义
- Javascript 函数调用
- Javascript 几种特殊的函数
- JavaScript 内置函数简介
- Javascript eval() 函数
- Javascript isFinite() 函数
- Javascript isNaN() 函数
- parseInt() 与 parseFloat()
- escape() 与 unescape()
- Javascript 字符串介绍
- Javascript length属性
- javascript 字符串函数
- Javascript 日期对象简介
- Javascript 日期对象用途
- Date 对象属性和方法
- Javascript 数组是什么
- Javascript 创建数组
- Javascript 数组赋值与取值
- Javascript 数组属性和方法
- 提升低端设备的 Web 性能
- TypeScript 4.0 RC发布,带来诸多更新
- istio mcp实现探究
- K8S 生态周报| Helm v2 进入维护期倒计时
- Halcon实例转OpenCV:计算回形针方向
- OpenCV检测轮廓极点(Python C++)
- 「Python 正则」使用专题总结
- 如何真正理解好一个「设计模式」?
- 10 行实现最短路算法
- 深度学习Pytorch检测实战 - Notes - 第6章 单阶经典检测器:YOLO
- 从图片裁剪来聊聊前端二进制
- 【投稿】刀哥:Rust学习笔记 2
- 【每周一库】- JWT的Rust实现
- 【Rust日报】2020-08-15 Rust Nightly 标准库文档已涵盖了每个关键字
- 【Rust日报】2020-08-16 Cranelift现在可以编译rustc,比LLVM的编译速度快7倍!