在我的任务中,我使用http://mdbootstrap.com/javascript/date-picker
我如何在angular 2组件中使用日期选择器,我必须在jquery中将此代码添加到组件中的typescript组件$('.datepicker').pickadate();
。
my_component.ts
import { Component, OnInit, ElementRef } from '@angular/core';
declare var $: any;
@Component({
// selector: 'clients',
templateUrl: './src/client/app/views/clients.html',
})
export class ClientsModel implements OnInit {
constructor(private _elmRef: ElementRef) {}
/* this code not work*/
ngOnInit() {
$(this._elmRef.nativeElement)
.find('#date-picker-example')
.on('click', function(){
$('#date-picker-example').pickadate();
});
}
}
my_component.html
<div class="md-form col-xl-2 col-lg-3 col-md-4 col-sm-6 col-xs-12" style="margin-top: 1%;">
<input type="text" id="date-picker-example" class="form-control datepicker">
<label for="date-picker-example">Date begin</label>
</div>
答案 0 :(得分:0)
如果您想使用MDB日期选择器,我不认为您可以使用jQuery。我为自己的项目编写了一个包装器,希望它对你也有帮助。我将其基于this article,它向您展示如何制作适用于[(ngModel)]
的自定义组件。我还要求以与显示日期不同的格式保存日期,这增加了一些您可能不需要处理的复杂性。
值得注意的是,MDB日期选择器在内部使用pickadate.js,因此您也可以使用整个API。
import { Component, forwardRef, ViewChild, ElementRef, Input, OnChanges, SimpleChanges } from '@angular/core';
import { NG_VALUE_ACCESSOR, ControlValueAccessor } from '@angular/forms';
const noop = () => {
};
export const CUSTOM_INPUT_CONTROL_VALUE_ACCESSOR: any = {
provide: NG_VALUE_ACCESSOR,
useExisting: forwardRef(() => DatePickerComponent),
multi: true
};
// Wrapper component for MDB's date picker, which is in turn a wrapper for pickadate.js.
// Uses the approach outlined here: http://almerosteyn.com/2016/04/linkup-custom-control-to-ngcontrol-ngmodel
@Component({
selector: 'date-picker',
template: `<input #element class="form-control" [attr.data-value]="value">`,
providers: [CUSTOM_INPUT_CONTROL_VALUE_ACCESSOR]
})
export class DatePickerComponent implements ControlValueAccessor, OnChanges {
// we need the native element here because we have to call the .pickadate() function on our element.
@ViewChild('element') element: ElementRef;
//The string representation of the currently selected date in the yyyy-mm-dd format.
private innerValue: any = '';
// A js date object representing the currently selected date.
private innerValueDate: Date = null;
// The format that actually gets displayed to the user, but not bound to anything directly.
private dateFormat: string = 'd mmm yyyy';
// The jquery object that is our api to pickadate.js.
private pickerObject: any;
//Placeholders for the callbacks which are later provided by the Control Value Accessor
private onTouchedCallback: () => void = noop;
private onChangeCallback: (_: any) => void = noop;
// Minimum date the user can select
@Input() minDate: Date;
// If true and date is null, valid will return false, invalid will return true.
@Input() required: boolean;
// True after the user has opened and closed the date picker. No way to reset it currently.
public touched: boolean;
//get accessor used in the template.
get value(): string {
return this.innerValue;
};
ngOnInit() {
// Wire up the pickadate plugin to our native element.
let element: any = $(this.element.nativeElement);
let $pickerInput = element.pickadate({
format: this.dateFormat,
// If you are using non-standard formats when setting the value, pickadate requires that you pass in
// formatSubmit tells the plugin how to parse them.
formatSubmit: 'yyyy-MM-dd',
onSet: context => {
// For ngModel to work we need to let angular know this control has been touched.
this.touched = true;
this.onTouchedCallback();
// Parse the date and set our internal tracking values.
this.setValue(context.select);
// Let angular know our value has changed.
this.onChangeCallback(this.innerValue);
},
onClose: () => {
this.touched = true;
this.onTouchedCallback();
// hack to get around this MDB date picker bug: https://github.com/amsul/pickadate.js/issues/160
$(document.activeElement).blur();
}
});
// Keep track of the picker object we just created so we can call its apis later.
this.pickerObject = $pickerInput.pickadate('picker');
this.pickerObject.set('min', this.minDate);
}
// Properties to give this some of the same behavior/interface as a native control.
get valid(): boolean {
return this.required ? !!this.value : true;
}
get invalid(): boolean {
return !this.valid;
}
get errors(): any {
return this.valid ? null : { required: true };
}
// Used if you want to show the date picker programatically.
public showDatePicker($event) {
this.pickerObject.open();
// If you don't stopPropagation() on this event, the picker doesn't open.
// https://github.com/amsul/pickadate.js/issues/481
if ($event) {
$event.stopPropagation();
}
}
// writeValue, registerOnChange, and registerOnTouched are from ControlValueAccessor interface
writeValue(value: any) {
this.setValue(value);
this.pickerObject.set('select', this.innerValueDate);
}
registerOnChange(fn: any) {
this.onChangeCallback = fn;
}
registerOnTouched(fn: any) {
this.onTouchedCallback = fn;
}
// Get notified when minDate changes so we can tell the pickadate plugin to respond accordingly.
ngOnChanges(changes: SimpleChanges): void {
// this actually gets called before ngOnInit, so the pickerObject may not be there yet.
if (this.pickerObject && changes['minDate']) {
this.pickerObject.set('min', this.minDate);
}
}
// ***** Helper functions ******//
// Parse and test the new value, but don't notify angular or anything in here.
private setValue(value) {
if (!value) {
this.innerValue = '';
this.innerValueDate = null;
} else {
let newValueDate: Date = new Date(Date.parse(value));
if (!this.datesAreEqual(this.innerValueDate, newValueDate)) {
this.innerValue = this.formatDate(newValueDate);
this.innerValueDate = newValueDate;
}
}
}
// Compare two dates' values to see if they are equal.
datesAreEqual(v1: Date, v2: Date) {
if (v1 === null && v2 === null) {
return true;
} else if (!v1 || !v2) {
return false;
}
return v1.getTime() === v2.getTime();
}
// There are lots more robust ways of formatting dates but since this is just an internal representation,
// we can just do something simple and convert the date to yyyy-mm-dd.
formatDate(d: Date) {
if (d === null) {
return null;
}
return d.getFullYear() + '-' + ('0'+(d.getMonth()+1)).slice(-2) + '-' + ('0' + d.getDate()).slice(-2);
}
}
&#13;