文档章节

利用ngrepeat实现的日历加上ion-slide-box效果

邪气小生
 邪气小生
发布于 2015/12/15 20:27
字数 1575
阅读 121
收藏 2

开发招聘助手的有个页面需要画日历,因为开发比较急,想换个方式去实现功能的,但是想想自己本来就打算写个日历,这次未必不是个很好的机会啊~所以也就花了一天整了个日历
先看效果:

默认打开是定位到当月当天,本日之前的天数灰色字体标识

点击按钮切换月份

左右滑动切换当月的周

说一下主要的实现原理吧:
在做之前参考了很多的代码,但是不知道为什么,心里面总觉得这样去实现太麻烦了,而且可能由于资历不够,看别人的代码也比较难懂。。。
所以就自己想了下:
这里主要是通过二维数组ng-repeat实现的,给出

$scope.days = [
  [
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}
  ],
  [
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}
  ],
  [
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}
  ],
  [
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}
  ],
  [
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}
  ],
  [
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}, {"date": "", "check": false, "year": "", "month": ""},
    {"date": "", "check": false, "year": "", "month": ""}
  ]
];

前端代码:

<ion-slide>
  <table>
    <tbody>
    <tr>
      <th>日</th>
      <th>一</th>
      <th>二</th>
      <th>三</th>
      <th>四</th>
      <th>五</th>
      <th>六</th>
    </tr>
    <tr ng-repeat="weeek in [4,5]" ng-init="index = $index+4">
      <td ng-repeat="day in days[index] track by $index" ng-click="choiceToday(day)">
        <div ng-class="{true:'yimianshi'}[day.date == currentDate]"></div>
        <div ng-class="{true:'checked'}[day.check]">
          <span ng-class="{true:'spanColor'}[day.smallToday]">{{day.date}}</span>
        </div>
      </td>
    </tr>
    </tbody>
  </table>
</ion-slide>

本想用三维数组,以为这个ion-slide是顾哥的建议,之前都已完成60%,所以就没有做太多的修改
还有给$scope.days赋值的的一个对象数组:

var valueArr = new Array();//用于给$scope.days赋值的数组

下面将以功能化去展现代码:
首先日历的初始化:

//初始化日期操作
    function initDate() {
      myDate = new Date();
      $scope.year = myDate.getFullYear();
      $scope.month = myDate.getMonth() + 1;      $scope.date = myDate.getDate();
      $scope.currentDate = $scope.date;
      $scope.currentMonth = $scope.month;
      $scope.headerMonth = $scope.month;
      $scope.currentEnMonth = monthShort($scope.month);
      $scope.currentYear = $scope.year;
      day = myDate.getDay();
      num = day - ($scope.date % 7 - 1); 
      if (ROOTCONFIG) {
        console.log("myDate = " + myDate);
        console.log($scope.year + "年" + $scope.month + "月" + $scope.date + "日 星期" + day);
        console.log("本月第一天星期" + num);
      }
    }

判断每一个月多少天:
这个比较简单

function thisMonthDays(month, year) {
  var end = 0;
  switch (month) {
    case 1:
      end = 31;
      break;
    case 2:
      if ((year % 4 == 0 && year % 100 != 0) || (year % 400 == 0))end = 29; else end = 28;
      break;
    case 3:
      end = 31;
      break;
    case 4:
      end = 30;
      break;
    case 5:
      end = 31;
      break;
    case 6:
      end = 30;
      break;
    case 7:
      end = 31;
      break;
    case 8:
      end = 31;
      break;
    case 9:
      end = 30;
      break;
    case 10:
      end = 31;
      break;
    case 11:
      end = 30;
      break;
    case 12:
      end = 31;
      break;
  }
  return end;
}

为数组赋值:

function initValueArr(year, month, num, valueArr) {
  $scope.enMonth = monthShort(month);
  var newDay = 1;//每月第一天
  //var newMonthDay = 1;
  var templateMonth = $scope.month - 1;
  var templateYear = $scope.year;
  if (templateMonth == 0) {
    templateMonth = 12;
    templateYear = $scope.year - 1;
  }
  var preMon = thisMonthDays(templateMonth, year);//上一个月天数
  var currentMon = thisMonthDays(month, year);//本月天数
  //num之前的赋值
  for (var i = num - 1; i >= 0; i--) {
    var obj = {};
    //obj.date = preMon-i;
    //console.log(obj.date);
    //obj.month = templateMonth;
    //obj.year = templateYear;
    obj.data = "";
    obj.month = "";
    obj.year = "";
    valueArr.push(obj);
  }
  //num以后的赋值操作
  for (var i = num; i < 42; i++) {
    var obj = {};
    obj.date = newDay++;
    obj.month = $scope.month;
    obj.year = $scope.year;

    //如果大于半月的天数以后将从1开始算起
    if (obj.date > currentMon) {
      //newDay = 1;
      //obj.date = newDay++;
      //$scope.month += 1;
      //if ($scope.month > 12) {
      //  $scope.month = 1;
      //  obj.month = $scope.month;
      //  $scope.year += 1;
      //  obj.year = $scope.year;
      //}
      obj.date = "";
      obj.month = "";
      obj.year = "";
    }
    valueArr.push(obj);
  }
  console.log(angular.toJson(valueArr));
}

注释的部分是因为最终决定在当前月份中不显示前一个月和后一个月的日期,由于日期的颜色只区分今天的之前和以后,所以这里显示出之前的会比较乱。
对象数组给二维对象数组赋值的函数

function setDaysValue(arr) {
  for (var i = 0; i < 6; i++) {
    for (var j = 0; j < 7; j++) {
      $scope.days[i][j].date = arr[0].date;
      $scope.days[i][j].year = arr[0].year;
      $scope.days[i][j].month = arr[0].month;
      if ($scope.days[i][j].date == $scope.currentDate) {
        if ($scope.days[i][j].month == $scope.currentMonth) {
          if ($scope.days[i][j].year == $scope.currentYear) {
            console.log($scope.currentYear);
            console.log($scope.currentMonth);
            console.log($scope.currentDate);
            console.log("yanglei" + angular.toJson($scope.days[i][j]));
            $scope.days[i][j].check = true;
            if (i > 1 && i < 4) {
              $scope.myIndex = 1;
            } else {
              $scope.myIndex = 2;
            }
          }
        }
      }
      if ($scope.days[i][j].year > $scope.currentYear) {
        $scope.days[i][j].smallToday = false;
      } else {
        if ($scope.days[i][j].month > $scope.currentMonth) {
          $scope.days[i][j].smallToday = false;
        } else if ($scope.days[i][j].month < $scope.currentMonth) {
          $scope.days[i][j].smallToday = true;
        } else {
          if ($scope.days[i][j].date >= $scope.currentDate) {
            $scope.days[i][j].smallToday = false;
          } else {
            $scope.days[i][j].smallToday = true;
          }
        }
      }
      arr.shift();
    }
  }
}

点击跳转下一个月和上一个月的操作
其实我觉得这里是可以抽离封装出来的,不至于代码的这么大重复性
后续再做优化

$scope.nextMon = function () {
      //var myDate = new Date();
      var nian = myDate.getFullYear();
      var yue = myDate.getMonth();
      yue += 2;
      if (yue == 13) {
        nian++;
        yue = 1;
      }
      var ri = "1";
      var str = nian + " " + yue + " " + ri;
      myDate = new Date(str);
      $scope.year = myDate.getFullYear();
      $scope.month = myDate.getMonth() + 1;
      $scope.date = myDate.getDate();
      $scope.headerMonth = $scope.month;
      day = myDate.getDay();
      num = day - ($scope.date % 7 - 1);
      initValueArr($scope.year, $scope.month, num, valueArr);
      for (var i = 0; i < 6; i++) {
        for (var j = 0; j < 7; j++) {
          $scope.days[i][j].check = false;
        }
      }
      setDaysValue(valueArr);
      //if($scope.month != $scope.currentMonth){
      //  $scope.myIndex = 0;
      //}
      $ionicSlideBoxDelegate.slide(0);
      if (ROOTCONFIG) {
        console.log("myDate = " + myDate);
        console.log($scope.year + "年" + $scope.month + "月" + $scope.date + "日 星期" + day);
        console.log("本月第一天星期" + num);
      }
    };
//上一个月
    $scope.preMon = function () {
      var nian = myDate.getFullYear();
      var yue = myDate.getMonth();
      if (yue == 0) {
        nian--;
        yue = 12;
      }
      var ri = "01";
      var str = nian + " " + yue + " " + ri;
      myDate = new Date(str);
      $scope.year = myDate.getFullYear();
      $scope.month = myDate.getMonth() + 1;
      $scope.date = myDate.getDate();//获取日期
      $scope.headerMonth = $scope.month;
      day = myDate.getDay();
      num = day - ($scope.date % 7 - 1);
      initValueArr($scope.year, $scope.month, num, valueArr);
      for (var i = 0; i < 6; i++) {
        for (var j = 0; j < 7; j++) {
          $scope.days[i][j].check = false;
        }
      }
      setDaysValue(valueArr);
      //if($scope.month != $scope.currentMonth){
      //  $scope.myIndex = 0;
      //}
      $ionicSlideBoxDelegate.slide(0);
      if (ROOTCONFIG) {
        console.log("myDate = " + myDate);
        console.log($scope.year + "年" + $scope.month + "月" + $scope.date + "日 星期" + day);
        console.log("本月第一天星期" + num);
      }
    };

对了,这其中还有个月份的转化下(貌似并没有什么好说的哦):

//月份的英语缩写
    function monthShort(month) {
      var enMonth = "";
      switch (month) {
        case 1:
          enMonth = "Jan";
          break;
        case 2:
          enMonth = "Feb";
          break;
        case 3:
          enMonth = "Mar";
          break;
        case 4:
          enMonth = "Apr";
          break;
        case 5:
          enMonth = "May";
          break;
        case 6:
          enMonth = "Jun";
          break;
        case 7:
          enMonth = "Jul";
          break;
        case 8:
          enMonth = "Aug";
          break;
        case 9:
          enMonth = "Sep";
          break;
        case 10:
          enMonth = "Oct";
          break;
        case 11:
          enMonth = "Nov";
          break;
        case 12:
          enMonth = "Dec";
          break;
      }
      return enMonth;
    }

其中还有各种函数的调用

initDate();
initValueArr($scope.year, $scope.month, num, valueArr);
setDaysValue(valueArr);

就这样,一个简单的日历就出来了
感觉很多东西还是要自己去尝试,看别人的代码怎么怎么的,其实也不是一气呵成的。
慢慢来~

© 著作权归作者所有

邪气小生
粉丝 23
博文 52
码字总数 67752
作品 0
朝阳
程序员
私信 提问
ionic 中轮播的问题和解决方案

##ionic轮播的问题解决方案 #### 首先说明了我的问题 先上 html 代码 这段代码显示效果是没有问题的,但是我遇到的问题是:<br > 1. 加载页面后轮播显示的是最后的一张图片,而不是默认的第一...

anziguoer
2016/04/27
3K
0
ion-slide-box 两项数据时BUG

代码如下 当banner数组长度等于2时,由于设置了does-continue="true",因此实际上会有4个,但是后面两个banner的click事件无效。

小虎Oni
2015/12/28
3K
5
IONIC+AngularJS 动态插入幻灯片图片

请教一个关于动态插入幻灯片图片的问题 目前在使用ionic+angular做开发,页面中使用了做幻灯片,然后ajax获得图片链接异步插入到中,但是插入的图片不能组成幻灯片,而是全部显示在页面上了,...

hosealee
2014/08/24
9.2K
3
angularjs array改变,但ng-repeat没有刷新

angular菜鸟,在网上下载了一个自定义指令,实现ionic 的slide tab scroll结合,在ion-slide使用ng-repeat指令,在controller实现对数组的操作,但是数组发生改变,ng-repeat却没有更新。对m...

elysium09
2017/03/31
813
0
ionic框架中一个页面中用了两个ion-slide-box

ionic框架中一个页面中用了两个ion-slide-box,会相互影响,大家有遇到过这种情况吗?

qs754947618
2016/04/27
1K
0

没有更多内容

加载失败,请刷新页面

加载更多

最简单的获取相机拍照的图片

  import android.content.Intent;import android.graphics.Bitmap;import android.os.Bundle;import android.os.Environment;import android.provider.MediaStore;import andr......

MrLins
23分钟前
2
0
说好不哭!数据可视化深度干货,前端开发下一个涨薪点在这里~

随着互联网在各行各业的影响不断深入,数据规模越来越大,各企业也越来越重视数据的价值。作为一家专业的数据智能公司,个推从消息推送服务起家,经过多年的持续耕耘,积累沉淀了海量数据,在...

个推
24分钟前
5
0
第三方支付-返回与回调注意事项

不管是支付宝,微信,还是其它第三方支付,第四方支付,支付机构服务商只要涉及到钱的交易都要进行如下校验,全部成功了才视为成功订单 1.http请求是否成功 2.校验商户号 3.校验订单号及状态...

Shingfi
27分钟前
3
0
简述Java内存分配和回收策略以及Minor GC 和 Major GC(Full GC)

内存分配: 1. 栈区:栈可分为Java虚拟机和本地方法栈 2. 堆区:堆被所有线程共享,在虚拟机启动时创建,是唯一的目的是存放对象实例,是gc的主要区域。通常可分为两个区块年轻代和年老代。更...

DustinChan
33分钟前
4
0
Excel插入批注:可在批注插入文字、形状、图片

1.批注一直显示:审阅选项卡-------->勾选显示批注选项: 2.插入批注快捷键:Shift+F2 组合键 3.在批注中插入图片:鼠标右键点击批注框的小圆点【重点不可以在批注文本框内点击】----->调出批...

东方墨天
57分钟前
6
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部