我目前正在将一个大型应用程序移植到一个基于 HTML5 的 Web 应用程序 - 我已经开始在 AngularJS 中构建应用程序并享受 AngularJS 框架的强大功能 - 我目前遇到一个问题:
我有一个指令,它给了我一个 jQuery Datepicker,但是与模型的绑定似乎不起作用。
我可能误解了指令的工作方式,并想看看我是否可以修补这部分我对框架的理解。我已经浏览了大量示例(包括 github 上的 angularui 项目,但仍然不明白为什么绑定没有发生)
任何帮助将不胜感激。
我目前正在将一个大型应用程序移植到一个基于 HTML5 的 Web 应用程序 - 我已经开始在 AngularJS 中构建应用程序并享受 AngularJS 框架的强大功能 - 我目前遇到一个问题:
我有一个指令,它给了我一个 jQuery Datepicker,但是与模型的绑定似乎不起作用。
我可能误解了指令的工作方式,并想看看我是否可以修补这部分我对框架的理解。我已经浏览了大量示例(包括 github 上的 angularui 项目,但仍然不明白为什么绑定没有发生)
任何帮助将不胜感激。
对于那些在谷歌上搜索这个问题的人(就像我一样),将 jQuery UI 日期选择器与 Angular 绑定的更简单方法是这样做......
$.datepicker.setDefaults({
// When a date is selected from the picker
onSelect: function(newValue) {
if (window.angular && angular.element)
// Update the angular model
angular.element(this).controller("ngModel").$setViewValue(newValue);
}
});
只需将它放在您的初始化代码之前。.datepicker()
(取自我在这里发布的另一个答案:https ://stackoverflow.com/a/17206242/195835 )
首先,您使用 angularjs 真是太好了,它是一个很好的框架。不久前开始了一个分支项目,以处理诸如包装 jquery-ui 和创建 ui 模块之类的事情。
下面是 Peter Bacon Darwin 实现的链接。
https://github.com/angular-ui/angular-ui/tree/master/modules/directives/date
- 担
angular-ui datepicker 不适用于 Angular 1.0.0,所以我重写了它。我的 fork 使您能够设置日期在输入中的格式以及如何将其保存回模型。
代码: https: //gist.github.com/2967979 jsFiddle:http: //jsfiddle.net/m8L8Y/8/(它缺少 jquery-ui 样式但工作方式相同)
// Code inspired by angular-ui https://github.com/angular-ui/angular-ui/blob/master/modules/directives/date/src/date.js
/*
Features:
* via the ui-date attribute:
* Ability to say how model is parsed into a date object
* Ability to say how input's value is parsed into a date object
* Ability to say how a date object is saved to the model
* Ability to say how a date object is displayed in the input
* via the ui-date-picker attribute
* Ability to directly configure the jQuery-ui datepicker
*/
angular.module('ui.directives', [])
.directive('uiDate', function () {
return {
require: '?ngModel',
//scope: {},
link: function ($scope, element, attrs, ngModel) {
// Date Handling Functions
var dateHandler = $.extend({ model: {}, view: {} }, $scope.$eval(attrs.uiDate));
// This will attempt to use preferredParser to parse a date.
function defaultDateParse(date, preferredParser) {
if (!preferredParser)
return new Date(date);
return preferredParser(date);
}
// This will attempt to use preferredFormatter to format a date, otherwise use 'mm/dd/yy'.
function defaultDateFormatter(date, preferredFormatter) {
if (!preferredFormatter)
preferredFormatter = "mm/dd/yy";
if (typeof preferredFormatter == 'string')
return $.datepicker.formatDate(preferredFormatter, date);
else
return preferredFormatter(date);
}
// Functions for Parsing & Formatting on the Model & View
function parseDateFromModel(date) {
return defaultDateParse(date, dateHandler.model.parse)
}
function parseDateFromView(date) {
return defaultDateParse(date, dateHandler.view.parse)
}
function formatDateForModel(date) {
return defaultDateFormatter(date, dateHandler.model.format)
}
function formatDateForView(date) {
return defaultDateFormatter(date, dateHandler.view.format)
}
var defaultDateViewFormat = (
typeof dateHandler.view.format == 'string'
? dateHandler.view.format
: 'mm/dd/yy'
)
// Initialize the jQuery-ui datePicker
var datePickerSettings = $.extend({ dateFormat: defaultDateViewFormat }, $scope.$eval(attrs.uiDatePicker))
var oldOnSelect = datePickerSettings.onSelect;
datePickerSettings.onSelect = function (dateVal) {
$scope.$apply(function () {
element.focus().val(dateVal);
updateModel();
})
if (oldOnSelect)
oldOnSelect.apply(this, arguments)
}
element.datepicker(datePickerSettings);
if (ngModel) {
// Specify how UI should be updated
ngModel.$render = function () {
element.val(ngModel.$viewValue || '');
};
// Listen for change events to enable binding
element.bind('blur keyup change', function () {
$scope.$apply(updateModel);
});
// Write data to the model
function updateModel() {
ngModel.$setViewValue(element.val());
}
// Convert the model into a string value
ngModel.$formatters.push(function (v) {
if (v != "" && v != null)
return formatDateForView(parseDateFromModel(v));
return null;
});
// Convert the string value into the model
ngModel.$parsers.push(function (v) {
if (v != "" && v != null)
return formatDateForModel(parseDateFromView(v))
return null;
});
}
}
};
})
类似于 praveepd(使用他们的作为基础),但这将包括深度模型选择。
var myApp = angular.module('myApp', ['myApp.directives']);
function MainCtrl($scope) {
$scope.deepValue = {
fromDate: null,
toDate: null
}
}
angular.module('myApp.directives', [])
.directive('myDatepicker', function() {
return function(scope, element, attrs) {
element.datepicker({
changeYear : true,
changeMonth : true,
appendText : '(yyyy-mm-dd)',
dateFormat : 'yy-mm-dd',
onSelect: function(dateText) {
var mdlAttr = $(this).attr('ng-model').split(".");
if (mdlAttr.length > 1) {
var objAttr = mdlAttr[mdlAttr.length-1];
var s = scope[mdlAttr[0]];
for (var i=0; i < mdlAttr.length-2; i++) {
s = s[mdlAttr[i]];
}
s[objAttr] = dateText;
} else {
scope[mdlAttr[0]] = dateText;
}
scope.$apply();
}
});
}
});
http://jsfiddle.net/9BRNf/74/这里是解决方案:)
代码:
var myApp = angular.module('myApp', ['myApp.directives']);
function MainCtrl() {
}
angular.module('myApp.directives', [])
.directive('myDatepicker', function() {
return {
require: '?ngModel',
link: function (scope, element, attrs, ngModelCtrl) {
element.datepicker({
changeYear : true,
changeMonth : true,
appendText : '(yyyy-mm-dd)',
dateFormat : 'yy-mm-dd',
onSelect: function(date) {
ngModelCtrl.$setViewValue(date);
scope.$apply();
}
});
}
}
});
我刚刚修剪了代码,看看这个:http: //jsfiddle.net/YU5mV/
HTML
<input id="date1" value="1/1/1980" ng-model="fromDate" my-datepicker />
<input id="date2" value="1/1/1980" ng-model="toDate" my-datepicker />
JavaScript
angular.module('myApp.directives', [])
.directive('myDatepicker', function() {
return function(scope, element, attrs) {
element.datepicker({
changeYear : true,
changeMonth : true,
appendText : '(yyyy-mm-dd)',
dateFormat : 'yy-mm-dd',
onSelect: function(dateText) {
var mdlAttr = $(this).attr('ng-model');
scope[mdlAttr] = dateText;
scope.$apply();
}
});
}
});
老问题,但这是我在谷歌搜索中的第一个命中。无论如何,我使用了使用 jquery 和 angular 指令一起工作的双日期选择器,所以我想我会分享以帮助其他尝试这样做的人。
这是它的笨拙:
http://plnkr.co/edit/veEmtCM3ZnQAhGTn5EGy?p=preview
基本上它使用 json 初始化表单。datepickers 有他们自己的条件,如 mindate 等。如果 true = 禁用日历上的星期日,则第一个选择框会启用它们。
单击“完成”时,视图模型会更新。这是其中一个日期选择器的一些代码:
html:
<input id="StartDate" data-ng-model="viewModel.startdate" date-from />
指令:
app.directive('dateFrom', function() {
return function (scope, element, attrs) {
var doDate = $('#EndDate');
element.datepicker({
dateFormat: 'dd-M-yy', showOtherMonths: true,
selectOtherMonths: true, minDate: '0',
beforeShowDay: function (date) {
var day = date.getDay();
console.log(scope.nosunday);
if (scope.nosunday === 'true') return [(day !== 0), '']; // disable sundays
else return [true, ''];
},
onSelect: function (selectedDate) {
var toDate = new Date(element.datepicker("getDate"));
toDate.setDate(toDate.getDate() + 1);
doDate.datepicker('option', 'minDate', toDate);
scope.viewModel.startdate = selectedDate;
scope.viewModel.enddate = doDate.val();
}
});
}
})
随意进一步优化它。如果您这样做,请发表带有分叉的评论:)