欢迎光临,了解微信小程序开发,就上易用通!

小程序踩坑记《二》页面关闭数据传递,picker的日期bug

发布:2017-11-29 18:06浏览: 来源:网络 作者:tianshu

一:页面关闭数据传递在页面关闭的时候,将数据传递到上一个界面,这是一个很常用的功能,一般用于数据选择,比如淘宝的收货人选择,需要在收货人管理界面将选择的收货人信息传递到订单 ...

 
 

一:页面关闭数据传递

在页面关闭的时候,将数据传递到上一个界面,这是一个很常用的功能,一般用于数据选择,比如淘宝的收货人选择,需要在收货人管理界面将选择的收货人信息传递到订单界面。

在Android中,activity自带有activityForResult,进行传递

在IOS中,一般通过Delegate/Block来处理

在React-Native中,则是通过navigator 在push的时候,传递一个callback,子页面关闭之前,回调该callback进行值传递,然后进行处理

那么在小程序中怎么做呢?

通过文档,我们可以看到小程序没有像Android 和 IOS 那样,有系统提供的api进行操作,而页面跳转是通过

 


			
  1. wx.navigateTo(OBJECT)
  2.  
  3. //url String 是 需要跳转的应用内非 tabBar 的页面的路径 , 路径后可以带参数。参数与路径之间使用?分隔,参数键与参数值用=相连,不同参数用&分隔;如 'path?key=value&key2=value2'
  4. //success Function 否 接口调用成功的回调函数
  5. //fail Function 否 接口调用失败的回调函数
  6. //complete Function 否 接口调用结束的回调函数(调用成功、失败都会执行)

跳转传递的参数和web的连接一样,也不能像React-Native 那样,传递callback。

这tm就尴尬了,大写的懵逼!!!!

看来,不能通过跳转的时候做处理,换个思路,看看是否能在返回的时候做文章,我们看文档,小程序的返回是通过

 


			
  1. wx.navigateBack(OBJECT)
  2. // 关闭当前页面,返回上一页面或多级页面。可通过 getCurrentPages()) 获取当前的页面栈,决定需要返回几层。
  3.  
  4. //OBJECT 参数说明:
  5.  
  6. //参数 类型 默认值 说明
  7. //delta Number 1 返回的页面数,如果 delta 大于现有页面数,则返回到首页。

看上去,这个好像并不能做什么文章,只是一个返回操作,参数只能传递返回的页面数,并没有说可以回传数据过去

难道真的没有解决办法了吗?

当然不是!

文档中有句非常重要的提示

可通过 getCurrentPages()) 获取当前的页面栈,决定需要返回几层。

我们先看一下getCurrentPages()返回的数据是什么

小程序踩坑记《二》页面关闭数据传递,picker的日期bug(图1)

我们可以看到,返回的是通过 wx.navigateTo方法到当前页面的路径的所有页面,好像有点眉目了,我们是否可以找到上级页面然后去修改他的data属性呢?

 


			
  1. Page({
  2. ...
  3.  
  4. submit: function(e) {
  5.  
  6. let pages = getCurrentPages()
  7. let curPage = pages[pages.length - (delta + 1)];
  8. let data = curPage.data;
  9. curPage.seo?tData({'data.invoice': {key1: "111", "key2": "222"}});
  10. }
  11. })

运行之后,喜极而泣,果然能修改上个页面data属性,从而更新UI

封装自己的pageForResult

这个方法很有可能用的地方比较多,而且可能返回的不是上级页面,我们可以做下简单的封装

 


			
  1. class Router {
  2.  
  3. /**
  4. * 返回并回传值
  5. *
  6. */
  7. navigateBack(obj) {
  8.  
  9. let delta = obj.delta ? obj.delta : 1;
  10.  
  11. if (obj.data) {
  12. let pages = getCurrentPages()
  13. let curPage = pages[pages.length - (delta + 1)];
  14. if(curPage.pageForResult) {
  15. curPage.pageForResult(obj.data);
  16. } elseo? {
  17. curPage.setData(obj.data);
  18. }
  19. }
  20. wx.navigateBack({
  21. delta: delta, // 回退前 delta(默认为1) 页面
  22. success: function (res) {
  23. // success
  24. obj.success && obj.success(res);
  25. },
  26. fail: function (err) {
  27. // fail
  28. obj.function && obj.function(err);
  29. },
  30. complete: function () {
  31. // complete
  32. obj.complete && obj.complete();
  33. }
  34. })
  35. }
  36. }
  37.  
  38. Router = new Router();
  39. module.exports = Router;

使用起来很简单

 


			
  1. // 修改上个界面的invoice
  2. let invoice = {
  3. type: type,
  4. header: header,
  5. content: content,
  6. header_content: this.data.headerContent
  7. }
  8.  
  9. Router.navigateBack({data: {invoice: invoice}});
  10. // 或是在上级页面增加一个 pageForResualt方法

上面的封装,我们可以通过两种方式进行数据传递

如果你有更高的方法,请告诉我

 

    通过在父级界面定义pageFroResult来接受数据通过在子页面调用setData({}) 指定父级的相关data字段进行页面刷新

二:picker的日期bug

对于一个app来说,日期选择是一个非常常用的功能,无论是在IOS 、Android 还是 React-Native中都有系统空间或是比较成熟的解决方案,同样,在小程序中,微信也给我提供了一个比较强大的日期组件——picker。

从底部弹起的滚动选择器,现支持三种选择器,通过mode来区分,分别是普通选择器,时间选择器,日期选择器,默认是普通选择器。

通过查看小程序文档

可以看到,通过mode属性,分别可以支持普通选择器、时间选择器和日期选择器。

使用方法比较简单,可以直接在wxml 文件中进行使用

 


			
  1. // wxml
  2. <picker mode="selector" >
  3. <picker mode="time" >
  4. <picker mode="date" >

重点来了

我在开发过程中有个需求是按月份进行订单的筛选,所以需要用日期选择器,先看一下日期控件的使用方法

小程序踩坑记《二》页面关闭数据传递,picker的日期bug(图2)

 


			
  1. // page/test/index.js
  2. Page({
  3. data: {
  4. year: 2017,
  5. month: 1,
  6.  
  7. },
  8.  
  9. bindDateChange: function (e) {
  10.  
  11. let [year, month] = e.detail.value.split("-");
  12. this.setData({
  13. year: year,
  14. month: month
  15. })
  16. },
  17. })

 


			
  1. // wxml
  2.  
  3. <picker mode="date" fields="month" value="2017-01" start="2016-05" end="2017-01" bindchange="bindDateChange">
  4. <text class="t-title">{{year}}年</text>
  5. <text class="t-value">{{month}}月</text>
  6. </picker>

以上是测试代码,代码比较简单,就是在页面有个picker控件,默认显示日期是2017-01,开始日期和结束日期分别是:2016-05 和 2017-01,粒度为月份(month,这个很重要,只有粒度为month的时候才会出现这个bug)当选择新的日期后,在页面上更新对应的年和月。

运行一下代码

 

没有任何毛病啊,显示完全正常。别急,上面的视频我们是在devTools 上面运行的,我们试试在真机上运行

 

我们可以看到,切换到2016年其他月份后,在切回2017年1月,会显示2017年5月,目测问题是月份没有更新到,而是显示了2016年开始的月份。






免责声明:本站所有文章和图片均来自用户分享和网络收集,文章和图片版权归原作者及原出处所有,仅供学习与参考,请勿用于商业用途,如果损害了您的权利,请联系网站客服处理。