ngx-print hide mat-paginator and print all records

问题描述 投票:0回答:1

我正在使用ngx-print在Angular 9应用程序中将HTML内容打印为PDF文档。我使用Angular Components和Bootstrap进行样式设置。我将mat-table与排序,过滤和分页选项一起使用,以将数据呈现给用户。默认情况下,mat-table每页分10条记录,可以根据需要进行更改。

  1. 因此,每当用户单击链接到mat-table打印(ngx-print)按钮时,分页应消失,并且将打印数据源中的所有记录。
  2. 打印后,分页应该与最后使用的选项一起出现
angular angular-material angular-components
1个回答
0
投票

ngx-print插件没有任何选项可以拦截打印点击或提供自定义选项。为了实现这一点,我必须创建新的ngx-print指令(从库回购中复制源代码)并添加自定义属性和方法。

添加的属性:

  @Input() printSectionId: string;

  @Input() matTableDataSource: MatTableDataSource<any>;

  @Input() paginator: MatPaginator;

  @Input() paginatorId: string;

  @Input() hidePaginator: boolean;

修改后的打印方法和2种新方法

  @HostListener('click')
  public print(): void
  {
    if(this.matTableDataSource.paginator!==undefined && this.matTableDataSource.paginator!==null && this.hidePaginator)
    {
      this.matTableDataSource.paginator=null;
    }

    setTimeout(() =>
    {
      this.hideMatPaginatorBeforePrinting();

      // Do something after
      let printContents, popupWin, styles = '', links = '';

      if (this.useExistingCss)
      {
        styles = this.getElementTag('style');
        links = this.getElementTag('link');
      }

      printContents = document.getElementById(this.printSectionId).innerHTML;
      popupWin = window.open('', '_blank', 'top=0,left=0,height=auto,width=auto');
      popupWin.document.open();
      popupWin.document.write(`
      <html>
        <head>
          <title>${this.printTitle ? this.printTitle : ''}</title>
          ${this.returnStyleValues()}
          ${this.returnStyleSheetLinkTags()}
          ${styles}
          ${links}
        </head>
        <body>
          ${printContents}
          <script defer>
            function triggerPrint(event) {
              window.removeEventListener('load', triggerPrint, false);
              setTimeout(() => {
                window.print();
                setTimeout(function() { window.close(); }, 0);
              }, ${this.printDelay});
            }
            window.addEventListener('load', triggerPrint, false);
          </script>
        </body>
      </html>`);

      popupWin.document.close();

      //Revert back the paginator after printing
      this.showMatPaginatorAfterPrinting();

    }, 1000); //1 second timeout to hide paginator

  }

  //hide Mat Paginator before Printing
  private hideMatPaginatorBeforePrinting()
  {
    document.getElementById(this.paginatorId).style.display='none';
  }

  //Show Mat Paginator after Printing
  private showMatPaginatorAfterPrinting()
  {
    this.matTableDataSource.paginator=this.paginator;
    document.getElementById(this.paginatorId).style.display='block';
  }

并通过ngxPrint按钮提供必要的输入

<button *ngIf="records!==undefined" id="ngxPrintControl"  [matTableDataSource]="reportDataSource" [paginator]="paginator" paginatorId="mat-paginator" [hidePaginator]="true" mat-raised-button useExistingCss="true"    type="button"   printSectionId="report_id"      ngxPrint> Print</button>

这里是新的ngx-print.directive.ts指令代码。只需将指令代码复制到项目中,然后使用它代替ngx-print插件

ngx-print.directive.ts

import {Directive, HostListener, Input} from '@angular/core';
import {MatPaginator} from '@angular/material/paginator';
import {MatTableDataSource} from '@angular/material/table';

@Directive({
  selector: 'button[ngxPrint]'
})
export class NgxPrintDirective
{

  /**
   *
   *
   * @memberof NgxPrintDirective
   */
  @Input() printSectionId: string;

  @Input() matTableDataSource: MatTableDataSource<any>;

  @Input() paginator: MatPaginator;

  @Input() paginatorId: string;

  @Input() hidePaginator: boolean;

  /**
   *
   *
   * @memberof NgxPrintDirective
   */
  @Input() printTitle: string;
  /**
   *
   *
   * @memberof NgxPrintDirective
   */
  @Input() useExistingCss = false;
  /**
   * A delay in milliseconds to force the print dialog to wait before opened. Default: 0
   *
   * @memberof NgxPrintDirective
   */
  @Input() printDelay = 0;

  public _printStyle = [];

  /**
   *
   *
   * @memberof NgxPrintDirective
   */
  @Input()
  set printStyle(values: { [key: string]: { [key: string]: string } })
  {
    for (let key in values)
    {
      if (values.hasOwnProperty(key))
      {
        this._printStyle.push((key + JSON.stringify(values[key])).replace(/['"]+/g, ''));
      }
    }
    this.returnStyleValues();
  }

  /**
   *
   *
   * @returns html for the given tag
   *
   * @memberof NgxPrintDirective
   */
  private _styleSheetFile = '';

  /**
   * @memberof NgxPrintDirective
   * @param cssList
   */
  @Input()
  set styleSheetFile(cssList: string)
  {
    let linkTagFn = cssFileName =>
        `<link rel="stylesheet" type="text/css" href="${cssFileName}">`;
    if (cssList.indexOf(',') !== -1)
    {
      const valueArr = cssList.split(',');
      for (let val of valueArr)
      {
        this._styleSheetFile = this._styleSheetFile + linkTagFn(val);
      }
    }
    else
    {
      this._styleSheetFile = linkTagFn(cssList);
    }
  }

  /**
   *
   *
   * @returns the string that create the stylesheet which will be injected
   * later within <style></style> tag.
   *
   * -join/replace to transform an array objects to css-styled string
   *
   * @memberof NgxPrintDirective
   */
  public returnStyleValues()
  {
    return `<style> ${this._printStyle.join(' ').replace(/,/g, ';')} </style>`;
  }

  /**
   *
   *
   * @memberof NgxPrintDirective
   */
  @HostListener('click')
  public print(): void
  {
    if(this.matTableDataSource.paginator!==undefined && this.matTableDataSource.paginator!==null && this.hidePaginator)
    {
      this.matTableDataSource.paginator=null;
    }

    setTimeout(() =>
    {
      this.hideMatPaginatorBeforePrinting();

      // Do something after
      let printContents, popupWin, styles = '', links = '';

      if (this.useExistingCss)
      {
        styles = this.getElementTag('style');
        links = this.getElementTag('link');
      }

      printContents = document.getElementById(this.printSectionId).innerHTML;
      popupWin = window.open('', '_blank', 'top=0,left=0,height=auto,width=auto');
      popupWin.document.open();
      popupWin.document.write(`
      <html>
        <head>
          <title>${this.printTitle ? this.printTitle : ''}</title>
          ${this.returnStyleValues()}
          ${this.returnStyleSheetLinkTags()}
          ${styles}
          ${links}
        </head>
        <body>
          ${printContents}
          <script defer>
            function triggerPrint(event) {
              window.removeEventListener('load', triggerPrint, false);
              setTimeout(() => {
                window.print();
                setTimeout(function() { window.close(); }, 0);
              }, ${this.printDelay});
            }
            window.addEventListener('load', triggerPrint, false);
          </script>
        </body>
      </html>`);

      popupWin.document.close();

      //Revert back the paginator after printing
      this.showMatPaginatorAfterPrinting();

    }, 1000); //1 second timeout to hide paginator

  }

  //hide Mat Paginator before Printing
  private hideMatPaginatorBeforePrinting()
  {
    document.getElementById(this.paginatorId).style.display='none';
  }

  //Show Mat Paginator after Printing
  private showMatPaginatorAfterPrinting()
  {
    this.matTableDataSource.paginator=this.paginator;
    document.getElementById(this.paginatorId).style.display='block';
  }

  /**
   * @returns string which contains the link tags containing the css which will
   * be injected later within <head></head> tag.
   *
   */
  private returnStyleSheetLinkTags()
  {
    return this._styleSheetFile;
  }

  private getElementTag(tag: keyof HTMLElementTagNameMap): string
  {
    const html: string[] = [];
    const elements = document.getElementsByTagName(tag);
    for (let index = 0; index < elements.length; index++)
    {
      html.push(elements[index].outerHTML);
    }
    return html.join('\r\n');
  }
}

© www.soinside.com 2019 - 2024. All rights reserved.