How to use MatPaginatorIntl?

前端 未结 9 1118
盖世英雄少女心
盖世英雄少女心 2020-12-02 17:59

I\'m using MatPaginator component and I\'m trying to figure out how to translate those labels (documentation isn\'t clear enough about this).

I\'ve found this articl

相关标签:
9条回答
  • 2020-12-02 18:38

    If you want a dynamic language switch with ngx-translate to work for you, here’s the solution, it works for me.

    mat-paginator-i18n.service.ts

    import { MatPaginatorIntl } from '@angular/material';
    import { TranslateService } from '@ngx-translate/core';
    import { Injectable } from '@angular/core';
    
    const ITEMS_PER_PAGE = 'Items per page:';
    const NEXT_PAGE = 'Next page';
    const PREV_PAGE = 'Previous page';
    const FIRST_PAGE = 'First page';
    const LAST_PAGE = 'Last page';
    
    @Injectable()
    export class MatPaginatorI18nService extends MatPaginatorIntl {
    public constructor(private translate: TranslateService) {
      super();
    
      this.translate.onLangChange.subscribe((e: Event) => {
        this.getAndInitTranslations();
      });
    
      this.getAndInitTranslations();
    }
    
    public getRangeLabel = (page: number, pageSize: number, length: number): string => {
      if (length === 0 || pageSize === 0) {
        return `0 / ${length}`;
      }
    
      length = Math.max(length, 0);
    
      const startIndex: number = page * pageSize;
      const endIndex: number = startIndex < length
        ? Math.min(startIndex + pageSize, length)
        : startIndex + pageSize;
    
      return `${startIndex + 1} - ${endIndex} / ${length}`;
    };
    
    public getAndInitTranslations(): void {
      this.translate.get([
        ITEMS_PER_PAGE,
        NEXT_PAGE,
        PREV_PAGE,
        FIRST_PAGE,
        LAST_PAGE,
      ])
        .subscribe((translation: any) => {
          this.itemsPerPageLabel = translation[ITEMS_PER_PAGE];
          this.nextPageLabel = translation[NEXT_PAGE];
          this.previousPageLabel = translation[PREV_PAGE];
          this.firstPageLabel = translation[FIRST_PAGE];
          this.lastPageLabel = translation[LAST_PAGE];
    
          this.changes.next();
        });
    }
    }
    

    In your module AppModule

    @NgModule({
      // ...
      providers: [
        {
          provide: MatPaginatorIntl,
          useClass: MatPaginatorI18nService,
        },
      ],
    })
    export class AppModule {
    // ...
    

    en.json, etc.

    {
      "Items per page:": "Items per page:",
      "Next page": "Next page",
      "Previous page": "Previous page",
      "First page": "First page",
      "Last page": "Last page",
    }
    
    0 讨论(0)
  • 2020-12-02 18:38

    Additionally you can use injected services by marking the Intl to be an injectable itself. See example (ignore specifics of DoneSubject and LocalizeService as those are custom implementations):

        import { Injectable, OnDestroy } from '@angular/core';
        import { MatPaginatorIntl } from '@angular/material';
        import { LocalizeService } from 'app/general';
        import { DoneSubject } from 'app/rx';
        import { takeUntil } from 'rxjs/operators';
    
        @Injectable()
        export class MatPaginatorIntlLoc extends MatPaginatorIntl implements OnDestroy {
          constructor(private readonly localizer: LocalizeService) {
            super();
    
            localizer.locale$.pipe(takeUntil(this.done$)).subscribe(() => {
              this.itemsPerPageLabel = localizer.translate('mat paginator label: items per page');
              this.nextPageLabel = localizer.translate('mat paginator label: next page');
              this.previousPageLabel = localizer.translate('mat paginator label: previous page');
              this.firstPageLabel = localizer.translate('mat paginator label: first page');
              this.lastPageLabel = localizer.translate('mat paginator label: last page');
            });
          }
    
          private readonly done$ = new DoneSubject();
    
          ngOnDestroy() { this.done$.done(); }
    
          getRangeLabel = (page: number, pageSize: number, length: number) => this.localizer
            .translate('mat paginator label: x of y', [
              length > 0 && pageSize > 0 ? (page * pageSize + 1) + ' - ' + Math.min((page + 1) * pageSize, Math.max(length, 0)) : 0,
              Math.max(length, 0),
            ]);
        }
    

    And don't forget to provide it in your module:

        providers: [
            ...
            { provide: MatPaginatorIntl, useClass: MatPaginatorIntlLoc },
            ...
          ]
    
    0 讨论(0)
  • 2020-12-02 18:38

    Inject MatPaginatorIntl anywhere in your application, set desired translations and call changes.next(). Repeat on every language change (e.g. by subscribing to onLangChange when using ngx-translate).

    0 讨论(0)
  • 2020-12-02 18:39

    You can do it like this: I'm providing you with croatian labels:

    customClass.ts

    import { Injectable } from '@angular/core';
    import { MatPaginatorIntl } from '@angular/material/paginator';
    
    @Injectable()
    export class MatPaginatorIntlCro extends MatPaginatorIntl {
      itemsPerPageLabel = 'Stavki po stranici';
      nextPageLabel     = 'Slijedeća stranica';
      previousPageLabel = 'Prethodna stranica';
    
      getRangeLabel = function (page, pageSize, length) {
        if (length === 0 || pageSize === 0) {
          return '0 od ' + length;
        }
        length = Math.max(length, 0);
        const startIndex = page * pageSize;
        // If the start index exceeds the list length, do not try and fix the end index to the end.
        const endIndex = startIndex < length ?
          Math.min(startIndex + pageSize, length) :
          startIndex + pageSize;
        return startIndex + 1 + ' - ' + endIndex + ' od ' + length;
      };
    
    }
    

    and AppModule.ts:

    providers: [{ provide: MatPaginatorIntl, useClass: MatPaginatorIntlCro}],
    
    0 讨论(0)
  • 2020-12-02 18:43

    in file: matPaginatorIntlCroClass.ts

    import {MatPaginatorIntl} from '@angular/material';
    export class MatPaginatorIntlCro extends MatPaginatorIntl {
      itemsPerPageLabel = 'Items par page';
      nextPageLabel     = 'Page Prochaine';
      previousPageLabel = 'Page Précedente';
    }
    

    in File: AppModule.ts:

    import { MatPaginatorModule, MatPaginatorIntl} from '@angular/material';
    import { MatPaginatorIntlCro } from './matPaginatorIntlCroClass'
    
    @NgModule({
      imports: [],
      providers: [{ provide: MatPaginatorIntl, useClass: MatPaginatorIntlCro}],
      ..
    })
    

    Source: https://material.angular.io/components/paginator/api

    0 讨论(0)
  • 2020-12-02 18:45

    Based on Vinko Vorih code, I made a paginator working with ngx-translate, here is the code :

    import { Injectable } from '@angular/core';
    import { MatPaginatorIntl } from '@angular/material';
    import { TranslateService } from "@ngx-translate/core";
    
    export class PaginatorIntlService extends MatPaginatorIntl {
      translate: TranslateService;
      itemsPerPageLabel = 'Items per page';
      nextPageLabel     = 'Next page';
      previousPageLabel = 'Previous page';
      getRangeLabel = function (page, pageSize, length) {
        const of = this.translate ? this.translate.instant('paginator.of') : 'of';
        if (length === 0 || pageSize === 0) {
          return '0 ' + of + ' ' + length;
        }
        length = Math.max(length, 0);
        const startIndex = page * pageSize;
        // If the start index exceeds the list length, do not try and fix the end index to the end.
        const endIndex = startIndex < length ?
          Math.min(startIndex + pageSize, length) :
          startIndex + pageSize;
        return startIndex + 1 + ' - ' + endIndex + ' ' + of + ' ' + length;
      };
    
      injectTranslateService(translate: TranslateService) {
        this.translate = translate;
    
        this.translate.onLangChange.subscribe(() => {
          this.translateLabels();
        });
    
        this.translateLabels();
      }
    
      translateLabels() {
        this.itemsPerPageLabel = this.translate.instant('paginator.items_per_page');
        this.nextPageLabel = this.translate.instant('paginator.next_page');
        this.previousPageLabel = this.translate.instant('paginator.previous_page');
      }
    
    }
    

    And then in your module providers entry :

    {
      provide: MatPaginatorIntl,
      useFactory: (translate) => {
        const service = new PaginatorIntlService();
        service.injectTranslateService(translate);
        return service;
      },
      deps: [TranslateService]
    }
    

    This way, you can store translations in your usual i18n file and if your web app is able to dynamically change locale, paginator will be translated on demand.

    0 讨论(0)
提交回复
热议问题