角UI日期选择器限制每月的天 [英] Angular UI Datepicker Limiting Days per month

查看:97
本文介绍了角UI日期选择器限制每月的天的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我使用的使用角度日期选择器:

http://angular-ui.github.io/bootstrap/#/datepicker

目前很难coded到显示设备42天或6个星期。

我想知道如何覆盖(即角装饰)在UI的引导,0.13.1.js该功能显示4周。

下面是函数:

\r
\r

ctrl._refreshView =功能(){\r
  VAR年= ctrl.activeDate.getFullYear()\r
    一个月= ctrl.activeDate.getMonth(),\r
    firstDayOfMonth =新的日期(年,月,1)\r
    差值= ctrl.startingDay - firstDayOfMonth.getDay()\r
    numDisplayedFrom previousMonth =(差大于0)? 7 - 区别:-difference,\r
    firstDate =新的日期(firstDayOfMonth);\r
\r
  如果(numDisplayedFrom previousMonth大于0){\r
    firstDate.setDate(-numDisplayedFrom previousMonth + 1);\r
  }\r
\r
  // 42日在为期六个月的日历数\r
  VAR天= getDates(firstDate,42);\r
  对于(VAR I = 0; I< 42;我++){\r
    天[I] = angular.extend(ctrl.createDateObject(天[I],ctrl.formatDay),{\r
      二级:天[I] .getMonth()==月!\r
      UID:scope.uniqueId +' - '+ I\r
    });\r
  }\r
\r
  scope.labels =新阵列(7);\r
  为(VAR J = 0; J&下; 7; J ++){\r
    scope.labels [J] = {\r
      简称:dateFilter(天[J] .date,ctrl.formatDayHeader)\r
      全:dateFilter(天[J] .date,EEEE)\r
    };\r
  }\r
\r
  scope.title = dateFilter(ctrl.activeDate,ctrl.formatDayTitle);\r
  scope.rows = ctrl.split(天,7);\r
\r
  如果(scope.showWeeks){\r
    scope.weekNumbers = [];\r
    VAR thursdayIndex =(4 + 7 - ctrl.startingDay)%7,\r
      numWeeks = scope.rows.length;\r
    为(VAR curWeek = 0; curWeek&下; numWeeks; curWeek ++){\r
      scope.weekNumbers.push(\r
        getISO8601WeekNumber(scope.rows [curWeek] [thursdayIndex] .date));\r
    }\r
  }\r
};

\r

\r
\r

我试着硬编码的42天缩短为更小的东西,但它打破了日历计算。只是看看是否有人在此之前延长?

干杯


解决方案

您应该能包住 _refreshView 新的编译功能,包装旧的链接功能中,如果你使用装饰。在你的 ctrl._refreshView 包装,你可以这样做:

  directive.compile =功能(){
  返回功能(范围,元素,ATTRS,CTRL){
    link.apply(这一点,参数);    VAR _refreshView = ctrl._refreshView;
    ctrl._refreshView =功能(){
      _refreshView.apply(这一点,参数);
      removeAnySecondaryOnlyRows(scope.rows);
    };    removeAnySecondaryOnlyRows(scope.rows);
  };
};

  //删除只包含次要时间(从其他个月)的行
功能removeAnySecondaryOnlyRows(行){
  对于(VAR I = 0; I< rows.length;我++){
    VAR行=行[I]
      areAllSecondary = FALSE;    //检查第一和最后一个单元格的.secondary财产
    areAllSecondary =行[0] .secondary&放大器;&安培;行[(row.length - 1)]二次。    如果(areAllSecondary){
      rows.splice(I,1);
      一世 - ;
    }
  }
}

和所有一起作为一个正常运作的片段,包括自定义模板和一些CSS隐藏次要天(那些来自不同的月份):

\r
\r

(函数(){\r
  使用严格的;\r
\r
  angular.module('对myApp',['ui.bootstrap'])\r
    的.config(['$提供,装饰])\r
    .controller(MainController,['$范围,MainController]);\r
\r
  函数装饰($提供){\r
\r
    //修复程序日期选择器白天模式,从当月仅显示与天行\r
    $ provide.decorator('daypickerDirective',['$委托,daypickerDirectiveDecorator]);\r
\r
    功能daypickerDirectiveDecorator($代表){\r
      变种指令= $代表[0],\r
        链接= directive.link;\r
\r
      //自定义HTML模板:\r
      directive.templateUrl =普通/指令/ uiBootstrapDatepickerDay.tpl.html\r
\r
      directive.compile =功能(){\r
        返回功能(范围,元素,ATTRS,CTRL){\r
          link.apply(这一点,参数);\r
\r
          VAR _refreshView = ctrl._refreshView;\r
          ctrl._refreshView =功能(){\r
            _refreshView.apply(这一点,参数);\r
            removeAnySecondaryOnlyRows(scope.rows);\r
          };\r
\r
          removeAnySecondaryOnlyRows(scope.rows);\r
        };\r
      };\r
\r
      返回$代表;\r
    }\r
\r
    //删除只包含次要时间(从其他个月)的行\r
    功能removeAnySecondaryOnlyRows(行){\r
      对于(VAR I = 0; I< rows.length;我++){\r
        VAR行=行[I]\r
          areAllSecondary = FALSE;\r
\r
        //检查第一和最后一个单元格的.secondary财产\r
        areAllSecondary =行[0] .secondary&放大器;&安培;行[(row.length - 1)]二次。\r
\r
        如果(areAllSecondary){\r
          rows.splice(I,1);\r
          一世 - ;\r
        }\r
      }\r
    }\r
  }\r
\r
  功能MainController($范围){\r
    $ scope.dt =新的日期();\r
  }\r
})();

\r

/ *\r
从其他月份藏匿的天数例:\r
我们已经把一个类的日期选择器的元素加载日期选择器指令上,\r
我们已经定制了一天模板,如果一个invis类添加到当天的按钮\r
这是一个次要的一天(从另一个一个月日)。\r
* /\r
\r
.datepicker .invis {\r
  visibility:hidden的;\r
}

\r

<链接HREF =// netdna.bootstrapcdn.com/bootstrap/3.1 .1 / CSS / bootstrap.min.css的rel =stylesheet属性>\r
&LT;脚本的src =// ajax.googleapis.com/ajax/libs/angularjs/1.2.28/angular.min.js\"></script>\r
&LT;脚本src=\"//cdnjs.cloudflare.com/ajax/libs/angular-ui-bootstrap/0.13.0/ui-bootstrap-tpls.min.js\"></script>\r
\r
&LT; D​​IV NG-应用=对myAppNG控制器=MainController&GT;\r
\r
  &LT;! - \r
   修改一天模板的invis类添加到二级天按钮。\r
   这可以/应当保持在单独的文件(http://stackoverflow.com/a/26339919/446030)\r
    - &GT;\r
  &LT;脚本ID =普通/指令/ uiBootstrapDatepickerDay.tpl.html类型=文/ NG-模板&GT;\r
    &LT;表的作用=网格的唱段,labelledby ={{UNIQUEID}} - 标题咏叹调-activedescendant ={{activeDateId}}&GT;\r
      &LT;&THEAD GT;\r
        &所述; TR&GT;\r
          &LT;第i个\r
            &LT;按钮式=按钮级=BTN BTN-默认BTN-SM拉左NG点击=移动(-1)的tabindex = - 1&GT;&LT; I类=glyphicon glyphicon-雪佛龙左&GT;&LT; I&GT /;\r
            &LT; /按钮&GT;\r
          &LT; /第i\r
          百分位列跨度={{5 + showWeeks}}&GT;\r
            &LT;按钮的ID ={{UNIQUEID}} - 标题为角色=标题ARIA生存=自信的咏叹调原子=真类型=按钮级=BTN BTN-默认BTN-SMNG - 点击=toggleMode()NG-禁用=datepickerMode === maxMode的tabindex = - 1的风格=宽度:100%;&GT;&LT;强&GT;的{{title}}&LT; / STRONG&GT;\r
            &LT; /按钮&GT;\r
          &LT; /第i\r
          &LT;第i个\r
            &LT;按钮式=按钮级=BTN BTN-默认BTN-SM右拉式NG点击=招(1)的tabindex = - 1&GT;&LT; I类=glyphicon glyphicon雪佛龙右汉字&GT;&LT; / I&GT;\r
            &LT; /按钮&GT;\r
          &LT; /第i\r
        &LT; / TR&GT;\r
        &所述; TR&GT;\r
          百分位NG-IF =showWeeks级=TEXT-中心&GT;&LT; /第i\r
          百分位NG重复=,在标签标签跟踪由$指数级=TEXT-中心&GT;&LT;小咏叹调标签={{label.full}}&GT; {{label.abbr}} &LT; /小&GT;\r
          &LT; /第i\r
        &LT; / TR&GT;\r
      &LT; / THEAD&GT;\r
      &LT;&TBODY GT;\r
        &LT; TR NG重复=行中的行跟踪由$指数&GT;\r
          &LT; TD NG-IF =showWeeks级=TEXT-中心H6&GT;&LT;环境监察及GT; {{weekNumbers [$指数]}}&LT; / EM&GT;\r
          &LT; / TD&GT;\r
          &LT; TD NG重复=dt的行迹被dt.date级=TEXT-中心的角色=栅格单元ID ={{dt.uid}}NG-CLASS =dt.customClass&GT ;\r
            &LT; - ########加入invis类纳克级上的按钮:####### - &GT;\r
            &LT;按钮式=button风格=最小宽度:100%;类=BTN BTN-默认BTN-SMNG-CLASS ={'BTN-信息:dt.selected,活跃:isActive(DT),invis':dt.secondary}NG点击=SELECT( dt.date)NG残疾=dt.disabled的tabindex = - 1&GT;&LT;跨度纳克级={'文本静音:dt.secondary,文本信息:dt.current }&GT; {{dt.label}}&LT; / SPAN&GT;\r
            &LT; /按钮&GT;\r
          &LT; / TD&GT;\r
        &LT; / TR&GT;\r
      &LT; / TBODY&GT;\r
    &LT; /表&gt;\r
  &LT; / SCRIPT&GT;\r
\r
  &LT; D​​IV&GT;\r
    &LT;强&GT;选定的日期:LT; / STRONG&GT; {{dt.toDateString()}}\r
  &LT; / DIV&GT;\r
  &LT; D​​IV的风格=显示:inline-block的;最小高度:290px;&GT;\r
    &LT; D​​IV日期选择器NG模型=DT级=喏喏平方米的日期选择器&GT;&LT; / DIV&GT;\r
  &LT; / DIV&GT;\r
\r
&LT; / DIV&GT;

\r

\r
\r

I am using using the angular datepicker:

http://angular-ui.github.io/bootstrap/#/datepicker

Currently it is hardcoded to display 42 days or 6 weeks.

I would like to know how to overwrite (ie. angular decorator) this function in ui-bootstrap-0.13.1.js to display 4 weeks.

Here is the function:

ctrl._refreshView = function() {
  var year = ctrl.activeDate.getFullYear(),
    month = ctrl.activeDate.getMonth(),
    firstDayOfMonth = new Date(year, month, 1),
    difference = ctrl.startingDay - firstDayOfMonth.getDay(),
    numDisplayedFromPreviousMonth = (difference > 0) ? 7 - difference : -difference,
    firstDate = new Date(firstDayOfMonth);

  if (numDisplayedFromPreviousMonth > 0) {
    firstDate.setDate(-numDisplayedFromPreviousMonth + 1);
  }

  // 42 is the number of days on a six-month calendar
  var days = getDates(firstDate, 42);
  for (var i = 0; i < 42; i++) {
    days[i] = angular.extend(ctrl.createDateObject(days[i], ctrl.formatDay), {
      secondary: days[i].getMonth() !== month,
      uid: scope.uniqueId + '-' + i
    });
  }

  scope.labels = new Array(7);
  for (var j = 0; j < 7; j++) {
    scope.labels[j] = {
      abbr: dateFilter(days[j].date, ctrl.formatDayHeader),
      full: dateFilter(days[j].date, 'EEEE')
    };
  }

  scope.title = dateFilter(ctrl.activeDate, ctrl.formatDayTitle);
  scope.rows = ctrl.split(days, 7);

  if (scope.showWeeks) {
    scope.weekNumbers = [];
    var thursdayIndex = (4 + 7 - ctrl.startingDay) % 7,
      numWeeks = scope.rows.length;
    for (var curWeek = 0; curWeek < numWeeks; curWeek++) {
      scope.weekNumbers.push(
        getISO8601WeekNumber(scope.rows[curWeek][thursdayIndex].date));
    }
  }
};

I've tried hard coding the 42 days to something smaller but it breaks the calender calculation. Just looking if anyone has extended this before?

Cheers

解决方案

You should be able to wrap _refreshView within a new compile function wrapping the old link function, if you use decorator. Within your ctrl._refreshView wrapper, you can do something like:

directive.compile = function() {
  return function(scope, element, attrs, ctrl) {
    link.apply(this, arguments);

    var _refreshView = ctrl._refreshView;
    ctrl._refreshView = function() {
      _refreshView.apply(this, arguments);
      removeAnySecondaryOnlyRows(scope.rows);
    };

    removeAnySecondaryOnlyRows(scope.rows);
  };
};

And:

//Remove any rows that contain only 'secondary' dates (those from other months)
function removeAnySecondaryOnlyRows(rows) {
  for (var i = 0; i < rows.length; i++) {
    var row = rows[i],
      areAllSecondary = false;

    //check the first and the last cell's .secondary property
    areAllSecondary = row[0].secondary && row[(row.length - 1)].secondary;

    if (areAllSecondary) {
      rows.splice(i, 1);
      i--;
    }
  }
}

And all together as a functioning snippet, including a custom template and some css to hide the 'secondary' days (those from a different month):

(function() {
  "use strict";

  angular.module('myApp', ['ui.bootstrap'])
    .config(['$provide', Decorate])
    .controller("MainController", ['$scope', MainController]);

  function Decorate($provide) {

    //fix for Datepicker 'day mode' to show only rows with days from the current month
    $provide.decorator('daypickerDirective', ['$delegate', daypickerDirectiveDecorator]);

    function daypickerDirectiveDecorator($delegate) {
      var directive = $delegate[0],
        link = directive.link;

      // custom html template:
      directive.templateUrl = "common/directives/uiBootstrapDatepickerDay.tpl.html";

      directive.compile = function() {
        return function(scope, element, attrs, ctrl) {
          link.apply(this, arguments);

          var _refreshView = ctrl._refreshView;
          ctrl._refreshView = function() {
            _refreshView.apply(this, arguments);
            removeAnySecondaryOnlyRows(scope.rows);
          };

          removeAnySecondaryOnlyRows(scope.rows);
        };
      };

      return $delegate;
    }

    //Remove any rows that contain only 'secondary' dates (those from other months)
    function removeAnySecondaryOnlyRows(rows) {
      for (var i = 0; i < rows.length; i++) {
        var row = rows[i],
          areAllSecondary = false;

        //check the first and the last cell's .secondary property
        areAllSecondary = row[0].secondary && row[(row.length - 1)].secondary;

        if (areAllSecondary) {
          rows.splice(i, 1);
          i--;
        }
      }
    }
  }

  function MainController($scope) {
    $scope.dt = new Date();
  }
})();

/*
Example of hiding days from other months:
We've put a class of 'datepicker' on the element loading the datepicker directive,
and we've customised the day template to add an 'invis' class to the day's button if
it's a 'secondary' day (a day from another month).
*/

.datepicker .invis {
  visibility: hidden;
}

<link href="//netdna.bootstrapcdn.com/bootstrap/3.1.1/css/bootstrap.min.css" rel="stylesheet">
<script src="//ajax.googleapis.com/ajax/libs/angularjs/1.2.28/angular.min.js"></script>
<script src="//cdnjs.cloudflare.com/ajax/libs/angular-ui-bootstrap/0.13.0/ui-bootstrap-tpls.min.js"></script>

<div ng-app="myApp" ng-controller="MainController">

  <!--
   Modified day template to add an 'invis' class to secondary day buttons.
   This could/should be kept in a separate file (http://stackoverflow.com/a/26339919/446030)
   -->
  <script id="common/directives/uiBootstrapDatepickerDay.tpl.html" type="text/ng-template">
    <table role="grid" aria-labelledby="{{uniqueId}}-title" aria-activedescendant="{{activeDateId}}">
      <thead>
        <tr>
          <th>
            <button type="button" class="btn btn-default btn-sm pull-left" ng-click="move(-1)" tabindex="-1"><i class="glyphicon glyphicon-chevron-left"></i>
            </button>
          </th>
          <th colspan="{{5 + showWeeks}}">
            <button id="{{uniqueId}}-title" role="heading" aria-live="assertive" aria-atomic="true" type="button" class="btn btn-default btn-sm" ng-click="toggleMode()" ng-disabled="datepickerMode === maxMode" tabindex="-1" style="width:100%;"><strong>{{title}}</strong>
            </button>
          </th>
          <th>
            <button type="button" class="btn btn-default btn-sm pull-right" ng-click="move(1)" tabindex="-1"><i class="glyphicon glyphicon-chevron-right"></i>
            </button>
          </th>
        </tr>
        <tr>
          <th ng-if="showWeeks" class="text-center"></th>
          <th ng-repeat="label in labels track by $index" class="text-center"><small aria-label="{{label.full}}">{{label.abbr}}</small>
          </th>
        </tr>
      </thead>
      <tbody>
        <tr ng-repeat="row in rows track by $index">
          <td ng-if="showWeeks" class="text-center h6"><em>{{ weekNumbers[$index] }}</em>
          </td>
          <td ng-repeat="dt in row track by dt.date" class="text-center" role="gridcell" id="{{dt.uid}}" ng-class="dt.customClass">
            <!--######## 'invis' class added in ng-class on the button: #######-->
            <button type="button" style="min-width:100%;" class="btn btn-default btn-sm" ng-class="{'btn-info': dt.selected, active: isActive(dt), 'invis': dt.secondary}" ng-click="select(dt.date)" ng-disabled="dt.disabled" tabindex="-1"><span ng-class="{'text-muted': dt.secondary, 'text-info': dt.current}">{{dt.label}}</span>
            </button>
          </td>
        </tr>
      </tbody>
    </table>
  </script>

  <div>
    <strong>Selected date:</strong> {{dt.toDateString()}}
  </div>
  <div style="display:inline-block; min-height:290px;">
    <div datepicker ng-model="dt" class="well well-sm datepicker"></div>
  </div>

</div>

这篇关于角UI日期选择器限制每月的天的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆