某相册类小程序项目总结
1.项目简介
一款为家庭设计的亲密社交产品,分为云端存储、智能电视、小程序三个平台,小程序端主要功能包括:
- 建立相册,上传图片、视频,
- 单张图片(视频)的预览、分享、下载、评论
- 相册集预览、分享、下载、评论
- 相册内容管理,删除、下载、设置封面、重命名、设置成开机视屏及屏保图片等
- 照片共享,手机、电视多端家庭内容同步和管理
- 邀请、删除家庭成员,添加、删除绑定设备
- 个性化设置家庭昵称、自己昵称、相册名称
2. 主要工作和疑难点汇总
2.1 主要工作
- 封装api请求,改造wx.requeset方法,封装http请求
- 抽取公共样式文件,在每个page文件夹的.wxss文件中,通过import 引入,
如:@import "../../lib/base.wxss"; - 抽取公共组件,如单个相册组件、弹出卡片组件、个人头像组件、照片卡片组件,通过在各个页面配置usingComponents参数使用。
- 封装全局公共函数
- 业务逻辑
-
接入百度统计,统计实时数据
在我的应用中添加小程序appkey,下载解压后的js文件到utils文件夹中去,同时将百度添加到request合法域名中去。
2.2 业务亮点
2.3 疑难点汇总
- 如何在小程序中使用less,可以实时转化为 .wxss文件?
- 小程序Page里的函数比app.js先执行的解决办法
- fixed 元素 auto 不生效原因
- 封装一个有输入框的modal层组件
- 微信小程序去除button默认边框样式
- 小程序如何获取点击元素信息
- 小程序如何在页面间传递数组对象?
-
小程序如何批量上传图片
chooseImage、chooseVideo的回调函数中,wx.uploadFile 上传,更新进度 this.data.updated_length + 1 当所有照片都上传成功,updated_length == total_length时, 显示完全上传完毕 视频的进度显示和图片的不一样 图片是每次上传成功一张,updated_length + 1 视频是调用 wx.uploadFile 对象的 onProgressUpdate 函数,看到视频上传进度,每500毫秒更新一次
- 小程序几个组件
-
如何让swiper 跳转到点击的index ?
current 参数 preview了,还能点击图片么,失败,不使用 https://www.cnblogs.com/BlueCc/p/10172742.html
- 动态设置小程序背景图片
-
如何实现分享、点赞功能
分享: onShareAppMessage,点赞:根据本人是否点赞过,是否有点赞权限 onShareAppMessage: function(res) { var obj = { from: 'sharephoto',mac: app.globalData.mac,open_id: app.globalData.open_id,member_id: app.globalData.current_member.member_id,family_id: app.globalData.family_id,album_id: this.data.album_id } obj = JSON.stringify(obj); var name = app.globalData.current_member.nick_name; var shareObj = { title: `${name}跟你分享了一本有趣的相册集‘${this.data.album_title}’`,// 默认是小程序的名称(可以写slogan等) path:`pages/login/login?message=${obj}`, imageUrl: this.data.album_cover,136);">//自定义图片路径,可以是本地文件路径、代码包文件路径或者网络图片路径,支持PNG及JPG,不传入 imageUrl 则使用默认截图。显示图片长宽比是 5:4 success: function(res){ }, fail: function(){ } }; return shareObj; },136);">//节流,300ms才能点一次 if (this.timer) { clearTimeout(this.timer) } this.timer = setTimeout(() => { console.log('点击点赞',this.data.like_id); server.like(family_id,51); font-weight: 700;">this.data.album_id,mac,member_id,open_id,app.globalData.open_id,form_id,51); font-weight: 700;">this.data.like_id).then((res)=>{ this.getPhotoBlock(); }) },300)
-
如何实现全选、单选功能
对某一天日期的照片,如果没张都选了,传递今天整个相册 每次单选照片都会重新判断是否全选
-
小程序时间过滤器 formatTime util的使用
wxs中new Date()等js方法不可用,所以不能用过滤器,还是用方法
-
为什么多个 formId 会重复,
因为不支持同时获取多个 formId,每次只能获取一个
-
如何实现预览照片,点击后跳转到单张照片?
wx.previewImage,这里注意 swiper中,currentIndex 左右滑动是否一致,change函数的处理。
-
如何支持同时预览图片和视频?
直接使用 wx.previewImage缺点:不能支持视频,不支持对单张照片做其他操作,智能预览,所以先跳转到 swiper页面 点击照片,预览单张照片。点击视频,跳转到vediofull页面。
-
视频播放是否全屏
videofullchange,监听全屏事件,小程序视频根据尺寸判断全屏 在 chooseVideo 的时候, 获取视频的高宽
-
解决,如果有其他照片上传失败怎么办?
每次调用 showProgress
-
如何判断小程序来源?分享?邀请?
data.message.from几个值判断,一共有9种情况 邀请、分享、在家庭中,不在家庭中,是不是管理员,是否来源扫一扫 单张相片 相册 受到邀请,不在家庭 受到邀请,在家庭中 扫一扫,不在家庭中 扫一扫,在家庭中,是管理员 扫一扫,在家庭中,不是管理员 不是成员,不是扫一扫 已经在家庭中 其他
-
showActionSheet 有长度限制吗?
有6个,超过怎么办?二层底部弹卡
- 如何见人照片与视频
- 内容过滤
- 接入百度移动统计
-
授权问题
问题出现在,分享给第三人单张照片的时候,未先授权小程序前,不能查看照片,改变login页面逻辑,去掉入门授权,在点击分享、下载时候再询问授权 首页、家庭页,操作后才授权,点击前会有蒙层
-
安全问题
需要操作的页面,onLoad都会 checkInFamily,如果不在任何家庭中,跳转到scan页面
-
哪些情况下展示红包?
创建相册、邀请成功成员
-
如何通过扫描二维码获得数据
.scanCode,获取返回参数
-
如何判断自己有没有全选评论、点赞、编辑?
如果照片、视频来源于分享者,且分享人的id=评论id,用分享人的信息给后端传递参数。无论是获取评论、删除评论、发送评论,被分享人都是使用的分享者信息。
-
一级tab页面需要哪些验证?
1,首先检查有没有授权,.getUserInfo,授权后下一步操作 2,检查checkIn,在不在家庭中,有没有操作权限,没有退出 3,获取成员信息,检查有没有红包,有,领取后下一步操作
-
如何拿到信息扫描?
wx.scanCode({ success: (res)... 通过res值获取
-
获取验证码逻辑
clearInterval(me.data.timerFun); } },0);">1000);
4. 业务逻辑梳理
4.1 项目哪几个page组成?有几个组件?
| 16个page | 5个组件 |
| ---- | ---- |
| login | 获取token、管理跳转 |
| le_login | 同步账号 |
| about | 账号绑定、消息、关于、意见反馈 |
| photo-edit | 照片编辑页 |
| select-device | 选择屏保页面 |
| h5 | 红包页面 |
| comment | 评论列表页面 |
| swiperphotos | 视频、照片滑动页面 |
| vediofull | 全屏播放视频页面 |
| photomanage | 照片管理页面,全选、反选、下载 |
| photos | 相册所有照片页面 |
| one-photo | 单张照片分享页面 |
| homepage | 首页,我的相册页面 |
| familypage | 家庭首页 |
| del-member | 删除成员、设备页面 |
| my-modal | 弹卡组件|
| member-icon | 头像组件|
| photo-album | 相册组件|
| photo-detail | 相册详情组件|
| red-packet | 红包组件|
4.2 挑几个页面看看
-
family 页面?
1.1 邀请成员
主要通过 onShareAppMessage 函数,将邀请人的信息添加在 path的参数中,在login页面中获得
1.2 添加设备
调整到 homescan页面
1.3 退出家庭
//如果只剩本人自己,解散家庭,否则按照退出家庭算
-
photomanage 页面?(点击,下载、设置壁纸,设置屏保后跳转的页面)
全选,反选逻辑 设置封面逻辑,如何做到 所有天,只有一个封面?每一天的照片、视频,是一个组件 select_photos 所有选中的照片 选照片、下载、删除逻辑: 传值过来的是 按日期分布的数组,按照日期对应,修改当天的照片数组。 遍历所有天的照片,计算选中张数,编号。 设置封面逻辑: 所有天照片,只有有一天选中了,其他所有置灰。
-
photos 页面? 点击相册进入的页面
功能:上传照片、视频,点赞、评论
-
vediofull 页面
首先需要创建视频播放上下文对象 .createVideoContext('myVideo'); 退出: 视频对象 pause,退出全屏, 对象置为null 监听是否需要横屏: 如果视频宽度大于高度,横屏
-
swiperphotos 页面
如何支持,同时预览照片和视频? 不使用原生自带的 wx.previewImage 视频,跳转到 vediofull 页面 定位到当前照片是,所有 swiper数组的第几章照片 初始状态,当前滑动照片数,预览照片上面的显示数字,current_index,和 swiper组件绑定的,current值差1,change函数滑动照片,改变current_index值
5. 几个组件简介
-
member-icon:
支持头像组件两种形态:文字在头像下方、文字在头像右方
-
my-modal:
支持弹出会话层有input文本框,支持编辑和新建功能 新建相册名称为空,编辑相册名称为相册名称,怎么做到的? 新建,文本框内容为update_value,编辑为从父类传过来的数据,textvalue 如何在操作完编辑后,新建,相册名称为空? 每次确认后,input框内容置空 实时计算文本框字数? bindinput函数
-
photo-album: 相册组件
每个相册组件,点击跳转到该相册详情页面
-
red-packet: 红包组件
//将红包信息参数发送给后端,传递给前端一个web-view 地址链接 //webview src指向网页的链接。(承载网页的容器,会自动铺满整个小程序页面) <web-view src="{{link}}"></web-view>
-
photo-detail: 相册详情组件,支持同一天照片全选、反选,设置屏保、删除、下载等功能
如何区分对照片的操作类型?设置封面?下载?删除?根据前一个页面传过来的操作类型判断 photo-detail只是一天的照片、视频操作,如何将所有日期选中照片传递给后端? 每次触发某一天的照片,是一个数组,向父元素触发事件, data.photo_block.forEach((item,index)=> { if(item.days == photo.days) { data.photo_block[index] = photo; } }) 如何统计总数? 每次重新计算选中照片。遍历。
6. 问题汇总解答
1. 如何在小程序中使用less,可以实时转化为 .wxss文件?
微信小程序只支持原生css写法,但是很浪费时间,使用 wxss-cli 可以实时将编写的 .less 文件自动编译为 .wxss 文件
1、npm或者yarn全局安装wxss-cli
npm install -g wxss-cli
2、运行wxss-cli命令(miniProject为小程序目录),less文件保存时自动编译
参考资料
2. 小程序Page里的函数比app.js先执行的解决办法
问题描述:
当我们初始化一个小程序时,默认文件 app.js 中有onLaunch函数,
onLaunch: function () {
"onLaunch");
wx.login({
success: res => {
"login");
// 发送 res.code 到后台换取 openId,sessionKey,unionId
}
})
}
默认目录,"pages/index/index",中index.js 有 onLoad函数
onLoad: "index onLoad");
}
小程序网络请求默认为异步请求,在app.js的onLaunch运行后进行异步请求时,程序不会停止,index.js页已执行onload,onload里面的数据会因为没有获取到app.js里的东西而报错,我们希望onLaunch执行完后再执行onLoad。
他们的执行顺序是,onLaunch > index onLoad > login
我们希望的执行顺序是:
onLaunch > login > index onLoad
解决办法
- 定义回调函数,onload里获取不到东西就一直获取,不执行下一步操作,直到获取到app.js的数据才继续执行。若login返回为空,则给app.js注册一个loginSuccessCallback回调,这个回调方法的执行时机,就是app.js中的异步请求完毕
- 把 app.js 中的 onLaunch 中方法拿到 index.js 文件中,按照自己的逻辑写
- 使用promise
方法1:
App({
onLaunch: function () {
wx.login({
success: res => {
this.globalData.checkLogin = true;
//由于这里是网络请求,可能会在 Page.onLoad 之后才返回
// 所以此处加入 callback 以防止这种情况
this.checkLoginReadyCallback){
this.checkLoginReadyCallback(res);
}
}
})
},globalData: {
checkLogin: false
}
...
})
//index.js
//获取应用实例
const app = getApp()
Page({
data: {
test: false
},onLoad: function () {
let that = this;
//判断onLaunch是否执行完毕
if (app.globalData.checkLogin){
that.setData({
test:true
})
}else{
app.checkLoginReadyCallback = res => {
//登陆成功后自己希望执行的,和上面一样
that.setData({
test:true
})
};
}
}
})
方法2:
把 app.js 中的 onLaunch 中登陆后才执行的方法拿到 index.js 文件中,这是最简单的方法
方法3:
)
})
}
3. fixed 元素 auto 必须要同时设置 top、left
4.封装一个有输入框的modal层组件
其实很简单,就是在modal中添加新的 input,
<view>
<modal class="modal" wx:if={{!hiddenModal}}"
title={{title}}" confirm-text="确定" cancel-text="取消" bindconfirm="modalconfirm" bindcancel="modalcancel">
<view class="input-line">
<input placeholder='请输入内容' maxlength={{ maxlength }}" bindinput='input' type="text" type="text" value={{ textvalue }}" />
<text>{{ currentlength}}/{{ maxlength }}</text>
</view>
</modal>
</view>
.modal{
width: 540rpx;
max-width: 540rpx;
border-radius: 28rpx;
.input-line {
display: flex;
border: 2rpx solid rgba(0,0.05);
font-size: 28rpx;
padding: 16rpx;
height: 40rpx;
line-height: 40rpx;
}
input,text{
display: inline-block;
vertical-align: top;
}
input {
flex: 1;
}
text {
width: 90rpx;
color: #FFA004 ;
}
}
5.微信小程序去除button默认边框样式
6.小程序如何获取点击元素信息
使用驼峰模式,给点击元素绑定 data- * ,通过 event.currentTarget.dataset 获取
<image src="{{ item.mini_pic }}" class="{{ item.show_opacity ? 'show_opacity' : ''}}" bindtap="tap" data-message="{{ item }}">
</image>
// 获取的点击节点元素是一个对象
tap: function(event) {
var message = event.currentTarget.dataset.message;
}
7. 小程序如何在页面间传递数组对象?
方法1:A页面跳转链接添加参数,B页面onLoad 接受
方法2:设置全局变量 globalData,用的少,一般适用于全局共享的一份信息,如用户open_id等
+ listData + '&taskArray=' + taskArray
})
//B页面
onLoad: function (options) {
this
JSON.parse(options.listData)
JSON.parse(options.taskArray)
}
//A页面:
app.globalData.open_id = 3;
//B页面:
var lala = app.globalData.open_id;
8. 小程序如何批量上传图片
6. 其他
-
封装http请求
class HTTP{
request({url,data={},method='POST',header={'content-type':'application/json'} }){
new Promise((resolve,reject)=>{
this._request(url,l:url,method:method,data:data,header: header,success:(res)=>{
const code = res.statusCode.toString()
if (code.startsWith('2') && res.data.errno == 10000){
resolve(res.data)
}
else{
if(res && res.data && res.data.errmsg) {
this._show_error(res.data.errmsg)
}
else {
this._show_error(tips[1])
}
console.log('错111111111')
reject(res)
}
},fail:(err)=>{
reject(err)
console.'错22222222')
this._show_error(tips[1])
}
})
}
_show_error(tip){
if(!tip){
tip = tips[1]
}
wx.showToast({
title: tip,icon:'none',duration:2000
})
}
}
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。