Javascript Angular 2 Material 2 datepicker 日期格式

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/44452966/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-23 02:32:42  来源:igfitidea点击:

Angular 2 Material 2 datepicker date format

javascriptangularangular-material2

提问by Igor Jankovi?

I need help. I don't know how to change the date format of the material 2 datepicker. I've read documentation but I don't understand what I actually need to do. Output date format which datepicker provides by default is f.e.: 6/9/2017

我需要帮助。我不知道如何更改材料2日期选择器的日期格式。我已经阅读了文档,但我不明白我真正需要做什么。datepicker 默认提供的输出日期格式为 fe: 6/9/2017

What I'm trying to achieve is to change format to the 9-Jun-2017 or any other.

我想要实现的是将格式更改为 9-Jun-2017 或任何其他格式。

Documentation https://material.angular.io/components/component/datepickerdoesn't help me at all. Thanks in advance

文档https://material.angular.io/components/component/datepicker根本没有帮助我。提前致谢

采纳答案by Igor Jankovi?

Here is the only solution I found for this one:

这是我为此找到的唯一解决方案:

First, create const:

首先,创建常量:

const MY_DATE_FORMATS = {
   parse: {
       dateInput: {month: 'short', year: 'numeric', day: 'numeric'}
   },
   display: {
       // dateInput: { month: 'short', year: 'numeric', day: 'numeric' },
       dateInput: 'input',
       monthYearLabel: {year: 'numeric', month: 'short'},
       dateA11yLabel: {year: 'numeric', month: 'long', day: 'numeric'},
       monthYearA11yLabel: {year: 'numeric', month: 'long'},
   }
};

Then you have to extend NativeDateADapter:

然后你必须扩展 NativeDateADapter:

export class MyDateAdapter extends NativeDateAdapter {
   format(date: Date, displayFormat: Object): string {
       if (displayFormat == "input") {
           let day = date.getDate();
           let month = date.getMonth() + 1;
           let year = date.getFullYear();
           return this._to2digit(day) + '/' + this._to2digit(month) + '/' + year;
       } else {
           return date.toDateString();
       }
   }

   private _to2digit(n: number) {
       return ('00' + n).slice(-2);
   } 
}

In format function, you can choose whatever format you want

在格式功能中,您可以选择您想要的任何格式

And the last step, you have to add it into module providers:

最后一步,您必须将其添加到模块提供程序中:

providers: [
    {provide: DateAdapter, useClass: MyDateAdapter},
    {provide: MD_DATE_FORMATS, useValue: MY_DATE_FORMATS},
],

And that's it. I can not believe that there is no some easy way to change date format through the @Input but let's hope it will be implemented in some future version of material 2 (currently beta 6).

就是这样。我不敢相信没有一些简单的方法可以通过 @Input 更改日期格式,但我们希望它会在未来的材料 2 版本(目前是beta 6)中实现。

回答by Robouste

Igor's answer didn't work for me so I asked directly on Angular 2 Material's githuband someone gave me that answer which worked for me :

Igor 的回答对我不起作用,所以我直接在Angular 2 Material 的 github上提问,有人给了我这个对我有用的答案:

  1. First write your own adapter :

    import { NativeDateAdapter } from "@angular/material";
    
    
    export class AppDateAdapter extends NativeDateAdapter {
    
        format(date: Date, displayFormat: Object): string {
    
            if (displayFormat === 'input') {
    
                const day = date.getDate();
                const month = date.getMonth() + 1;
                const year = date.getFullYear();
    
                return `${day}-${month}-${year}`;
            }
    
            return date.toDateString();
        }
    }
    
  2. Create your date format :

    export const APP_DATE_FORMATS =
    {
        parse: {
            dateInput: { month: 'short', year: 'numeric', day: 'numeric' },
        },
        display: {
            dateInput: 'input',
            monthYearLabel: { year: 'numeric', month: 'numeric' },
            dateA11yLabel: { year: 'numeric', month: 'long', day: 'numeric' },
            monthYearA11yLabel: { year: 'numeric', month: 'long' },
        }
    };
    
  3. Provide those two to your module

    providers: [
            {
                provide: DateAdapter, useClass: AppDateAdapter
            },
            {
                provide: MAT_DATE_FORMATS, useValue: APP_DATE_FORMATS
            }
        ]
    
  1. 首先编写自己的适配器:

    import { NativeDateAdapter } from "@angular/material";
    
    
    export class AppDateAdapter extends NativeDateAdapter {
    
        format(date: Date, displayFormat: Object): string {
    
            if (displayFormat === 'input') {
    
                const day = date.getDate();
                const month = date.getMonth() + 1;
                const year = date.getFullYear();
    
                return `${day}-${month}-${year}`;
            }
    
            return date.toDateString();
        }
    }
    
  2. 创建您的日期格式:

    export const APP_DATE_FORMATS =
    {
        parse: {
            dateInput: { month: 'short', year: 'numeric', day: 'numeric' },
        },
        display: {
            dateInput: 'input',
            monthYearLabel: { year: 'numeric', month: 'numeric' },
            dateA11yLabel: { year: 'numeric', month: 'long', day: 'numeric' },
            monthYearA11yLabel: { year: 'numeric', month: 'long' },
        }
    };
    
  3. 将这两个提供给您的模块

    providers: [
            {
                provide: DateAdapter, useClass: AppDateAdapter
            },
            {
                provide: MAT_DATE_FORMATS, useValue: APP_DATE_FORMATS
            }
        ]
    

More infos here

更多信息在这里

EDIT:For those who are having the trouble of the manual input is being not respected with the format, you may override the parse(value: any)function from the NativeDateAdapteras follows.

编辑:对于那些因手动输入格式不遵守而遇到麻烦的人,您可以按如下方式覆盖该parse(value: any)功能NativeDateAdapter

parse(value: any): Date | null {
    const date = moment(value, 'DD/MM/YYYY');
    return date.isValid() ? date.toDate() : null;
}

So, the custom adapter will take the final shape as follows.

因此,自定义适配器将采用如下最终形状。

import { NativeDateAdapter } from "@angular/material";
import * as moment from 'moment';

export class AppDateAdapter extends NativeDateAdapter {

    format(date: Date, displayFormat: Object): string {
        if (displayFormat === 'input') {

            const day = date.getDate();
            const month = date.getMonth() + 1;
            const year = date.getFullYear();

            return `${day}/${month}/${year}`;
        }

        return date.toDateString();
    }

    parse(value: any): Date | null {
        const date = moment(value, environment.APP_DATE_FORMAT);
        return date.isValid() ? date.toDate() : null;
    }
}

回答by Abhishek Jha

You just need to provide a custom MAT_DATE_FORMATS

您只需要提供自定义 MAT_DATE_FORMATS

export const APP_DATE_FORMATS = {
    parse: {dateInput: {month: 'short', year: 'numeric', day: 'numeric'}},
    display: {
        dateInput: {month: 'short', year: 'numeric', day: 'numeric'},
        monthYearLabel: {year: 'numeric'}
    }
};

and add it to providers.

并将其添加到提供者。

providers: [{
   provide: MAT_DATE_FORMATS, useValue: APP_DATE_FORMATS
}]

Working code

工作代码

回答by luka martinovic

The work around that works for me is:

对我有用的解决方法是:

my.component.html:

<md-input-container>
  <input mdInput disabled [ngModel]="someDate | date:'d-MMM-y'" >
  <input mdInput [hidden]='true' [(ngModel)]="someDate"  
[mdDatepicker]="picker">
  <button mdSuffix [mdDatepickerToggle]="picker"></button>
</md-input-container>
<md-datepicker #picker></md-datepicker> 

my.component.ts :


@Component({...
})
export class MyComponent implements OnInit {
  ....
  public someDate: Date;
  ...

So now you can have the format (Ex. 'd-MMM-y') that works best for you.

所以现在您可以拥有最适合您的格式(例如“d-MMM-y”)。

回答by Arthur Z.

There's a high chance that you already use a library that provides you with an convinient way of manipulating (parsing, validating, displaying, etc.) dates and times in JavaScript. If you dont, take a look at one of them, for example moment.js.

您很有可能已经使用了一个库,该库为您提供了一种在 JavaScript 中操作(解析、验证、显示等)日期和时间的便捷方式。如果没有,请查看其中一个,例如moment.js

Implementing your custom adapter using moment.js would look like this.

使用 moment.js 实现您的自定义适配器看起来像这样。

Create CustomDateAdapter.tsand implement it like this:

创建CustomDateAdapter.ts并像这样实现它:

import { NativeDateAdapter } from "@angular/material";
import * as moment from 'moment';

export class CustomDateAdapter extends NativeDateAdapter {
    format(date: Date, displayFormat: Object): string {
        moment.locale('ru-RU'); // Choose the locale
        var formatString = (displayFormat === 'input')? 'DD.MM.YYYY' : 'LLL';
        return moment(date).format(formatString);
    }
}

In your app.module.ts:

在您的app.module.ts 中

import { DateAdapter } from '@angular/material';

providers: [
    ...
    {
        provide: DateAdapter, useClass: CustomDateAdapter
    },
    ...
]

That's it. Simple, easy and no need of reinventing bicycles.

就是这样。简单、容易,无需重新发明自行车。

回答by YoungHyeong Ryu

Robouste worked perfect!!

Robouste 工作完美!!

I made easy one (Angular 4 "@angular/material": "^2.0.0-beta.10") first made datepicker.module.ts

我做了一个简单的(Angular 4 "@angular/material": "^2.0.0-beta.10")首先做了 datepicker.module.ts



    import { NgModule }  from '@angular/core';
    import { MdDatepickerModule, MdNativeDateModule, NativeDateAdapter, DateAdapter, MD_DATE_FORMATS  }  from '@angular/material';

    class AppDateAdapter extends NativeDateAdapter {
        format(date: Date, displayFormat: Object): string {
            if (displayFormat === 'input') {
                const day = date.getDate();
                const month = date.getMonth() + 1;
                const year = date.getFullYear();
                return `${year}-${month}-${day}`;
            } else {
                return date.toDateString();
            }
        }
    }

    const APP_DATE_FORMATS = {
    parse: {
    dateInput: {month: 'short', year: 'numeric', day: 'numeric'}
    },
    display: {
    // dateInput: { month: 'short', year: 'numeric', day: 'numeric' },
    dateInput: 'input',
    monthYearLabel: {year: 'numeric', month: 'short'},
    dateA11yLabel: {year: 'numeric', month: 'long', day: 'numeric'},
    monthYearA11yLabel: {year: 'numeric', month: 'long'},
    }
    };

    @NgModule({
    declarations:  [ ],
    imports:  [ ],
        exports:  [ MdDatepickerModule, MdNativeDateModule ],
    providers: [
    {
        provide: DateAdapter, useClass: AppDateAdapter
    },
    {
        provide: MD_DATE_FORMATS, useValue: APP_DATE_FORMATS
    }
    ]
    })

    export class DatePickerModule {

    }

just import it (app.module.ts)

只需导入它(app.module.ts)


    import {Component, NgModule, VERSION,  ReflectiveInjector}   from '@angular/core'//NgZone,
    import { CommonModule }              from '@angular/common';
    import {BrowserModule}               from '@angular/platform-browser'
    import { BrowserAnimationsModule }        from '@angular/platform-browser/animations';
    import { FormsModule }              from '@angular/forms';
    import { DatePickerModule }            from './modules/date.picker/datepicker.module';

    @Component({
    selector: 'app-root',
    template: `
    <input (click)="picker.open()" [mdDatepicker]="picker" placeholder="Choose a date" [(ngModel)]="datepicker.SearchDate"  >
    <md-datepicker-toggle mdSuffix [for]="picker"></md-datepicker-toggle>
    <md-datepicker #picker touchUi="true"  ></md-datepicker>
    `,
    })


    export class App{
        datepicker = {SearchDate:new Date()}
        constructor( ) {}

        }

    @NgModule({
    declarations: [ App ],
    imports: [ CommonModule, BrowserModule, BrowserAnimationsModule, FormsModule, DatePickerModule],
    bootstrap: [ App ],
    providers: [   ]//NgZone
    })
    export class AppModule {}

回答by Mohan Singh

Create a constant for date format.

为日期格式创建一个常量。

export const DateFormat = {
parse: {
  dateInput: 'input',
  },
  display: {
  dateInput: 'DD-MMM-YYYY',
  monthYearLabel: 'MMMM YYYY',
  dateA11yLabel: 'MM/DD/YYYY',
  monthYearA11yLabel: 'MMMM YYYY',
  }
};

And Use the below code inside app module

并在 app 模块中使用以下代码

 providers: [
  { provide: DateAdapter, useClass: MomentDateAdapter, deps: [MAT_DATE_LOCALE] },
  { provide: MAT_DATE_FORMATS, useValue: DateFormat }
]

回答by onalbi

Why to not use Angular DatePipe?

为什么不使用 Angular DatePipe?

import {Component} from '@angular/core';
import {DateAdapter, MAT_DATE_FORMATS, NativeDateAdapter} from '@angular/material';
import {FormControl} from '@angular/forms';
import {DatePipe} from '@angular/common';

export const PICK_FORMATS = {
    parse: {dateInput: {month: 'short', year: 'numeric', day: 'numeric'}},
    display: {
        dateInput: 'input',
        monthYearLabel: {year: 'numeric', month: 'short'},
        dateA11yLabel: {year: 'numeric', month: 'long', day: 'numeric'},
        monthYearA11yLabel: {year: 'numeric', month: 'long'}
    }
};
class PickDateAdapter extends NativeDateAdapter {
    format(date: Date, displayFormat: Object): string {
        if (displayFormat === 'input') {
            return new DatePipe('en-US').transform(date, 'EEE, MMM dd, yyyy');
        } else {
            return date.toDateString();
        }
    }
}
@Component({
    selector: 'custom-date',
    template: `<mat-form-field>
                   <input matInput [formControl]="date" />
                   <mat-datepicker-toggle matSuffix [for]="picker"></mat-datepicker-toggle>
                   <mat-datepicker #picker></mat-datepicker>
               </mat-form-field>`,
    providers: [
        {provide: DateAdapter, useClass: PickDateAdapter},
        {provide: MAT_DATE_FORMATS, useValue: PICK_FORMATS}
    ]
})
export class DateComponent {
    date = new FormControl(new Date());
    constructor() {}
}

回答by ffcc

I used the solution propose by @igor-jankovi? and had the problem of "Error: Uncaught (in promise): TypeError: Cannot read property 'dateInput' of undefined". I realized that this problem was because MY_DATE_FORMATSneed to be declare like type MdDateFormats:

我使用了@igor-jankovi 提出的解决方案?并遇到了“错误:未捕获(承诺):类型错误:无法读取未定义的属性‘dateInput’”的问题。我意识到这个问题是因为MY_DATE_FORMATS需要声明如下type MdDateFormats

export declare type MdDateFormats = {
    parse: {
        dateInput: any;
    };
    display: {
        dateInput: any;
        monthYearLabel: any;
        dateA11yLabel: any;
        monthYearA11yLabel: any;
    };
};

So, the correct way of declare MY_DATE_FORMATSis:

所以,正确的声明方式MY_DATE_FORMATS是:

const MY_DATE_FORMATS:MdDateFormats = {
   parse: {
       dateInput: {month: 'short', year: 'numeric', day: 'numeric'}
   },
   display: {
       dateInput: 'input',
       monthYearLabel: {year: 'numeric', month: 'short'},
       dateA11yLabel: {year: 'numeric', month: 'long', day: 'numeric'},
       monthYearA11yLabel: {year: 'numeric', month: 'long'},
   }
};

With the above modification the solution work for me.

通过上述修改,解决方案对我有用。

Regards

问候

回答by Tienanhvn

create a file date.adapter.ts

创建文件 date.adapter.ts

import { NativeDateAdapter, DateAdapter, MAT_DATE_FORMATS, MatDateFormats } from "@angular/material";

export class AppDateAdapter extends NativeDateAdapter {
    parse(value: any): Date | null {
        if ((typeof value === 'string') && (value.indexOf('/') > -1)) {
          const str = value.split('/');
          const year = Number(str[2]);
          const month = Number(str[1]) - 1;
          const date = Number(str[0]);
          return new Date(year, month, date);
        }
        const timestamp = typeof value === 'number' ? value : Date.parse(value);
        return isNaN(timestamp) ? null : new Date(timestamp);
      }
   format(date: Date, displayFormat: string): string {
       if (displayFormat == "input") {
          let day = date.getDate();
          let month = date.getMonth() + 1;
          let year = date.getFullYear();
          return   year + '-' + this._to2digit(month) + '-' + this._to2digit(day)   ;
       } else if (displayFormat == "inputMonth") {
          let month = date.getMonth() + 1;
          let year = date.getFullYear();
          return  year + '-' + this._to2digit(month);
       } else {
           return date.toDateString();
       }
   }
   private _to2digit(n: number) {
       return ('00' + n).slice(-2);
   }
}
export const APP_DATE_FORMATS =
{
   parse: {
       dateInput: {month: 'short', year: 'numeric', day: 'numeric'}
   },
   display: {
       dateInput: 'input',
       monthYearLabel: 'inputMonth',
       dateA11yLabel: {year: 'numeric', month: 'long', day: 'numeric'},
       monthYearA11yLabel: {year: 'numeric', month: 'long'},
   }
}

app.module.ts

app.module.ts

  providers: [
    DatePipe,
    {
        provide: DateAdapter, useClass: AppDateAdapter
    },
    {
        provide: MAT_DATE_FORMATS, useValue: APP_DATE_FORMATS
    }
    ]

app.component.ts

app.component.ts

import { FormControl } from '@angular/forms';
import { DatePipe } from '@angular/common';
@Component({
  selector: 'datepicker-overview-example',
  templateUrl: 'datepicker-overview-example.html',
  styleUrls: ['datepicker-overview-example.css'],
  providers: [
    DatePipe,
    {
        provide: DateAdapter, useClass: AppDateAdapter
    },
    {
        provide: MAT_DATE_FORMATS, useValue: APP_DATE_FORMATS
    }
    ]
})
export class DatepickerOverviewExample {
  day = new Date();
  public date;
 constructor(private datePipe: DatePipe){
    console.log("anh "," " +datePipe.transform(this.day.setDate(this.day.getDate()+7)));
    this.date = new FormControl(this.datePipe.transform(this.day.setDate(this.day.getDate()+7)));
    console.log("anht",' ' +new Date());
 }
}

app.component.html

应用程序组件.html

<mat-form-field>
  <input matInput [matDatepicker]="picker" placeholder="Choose a date" [formControl]="date">
  <mat-datepicker-toggle matSuffix [for]="picker"></mat-datepicker-toggle>
  <mat-datepicker #picker></mat-datepicker>
</mat-form-field>