angular-ui-grid
Version:
A data grid for Angular
1,097 lines (1,029 loc) • 75.2 kB
JavaScript
/*!
* ui-grid - v4.9.1 - 2020-10-26
* Copyright (c) 2020 ; License: MIT
*/
/* global ExcelBuilder */
/* global console */
(function () {
'use strict';
/**
* @ngdoc overview
* @name ui.grid.exporter
* @description
*
* # ui.grid.exporter
*
* <div class="alert alert-success" role="alert"><strong>Stable</strong> This feature is stable. There should no longer be breaking api changes without a deprecation warning.</div>
*
* This module provides the ability to export data from the grid.
*
* Data can be exported in a range of formats, and all data, visible
* data, or selected rows can be exported, with all columns or visible
* columns.
*
* No UI is provided, the caller should provide their own UI/buttons
* as appropriate, or enable the gridMenu
*
* <br/>
* <br/>
*
* <div doc-module-components="ui.grid.exporter"></div>
*/
var module = angular.module('ui.grid.exporter', ['ui.grid']);
/**
* @ngdoc object
* @name ui.grid.exporter.constant:uiGridExporterConstants
*
* @description constants available in exporter module
*/
/**
* @ngdoc property
* @propertyOf ui.grid.exporter.constant:uiGridExporterConstants
* @name ALL
* @description export all data, including data not visible. Can
* be set for either rowTypes or colTypes
*/
/**
* @ngdoc property
* @propertyOf ui.grid.exporter.constant:uiGridExporterConstants
* @name VISIBLE
* @description export only visible data, including data not visible. Can
* be set for either rowTypes or colTypes
*/
/**
* @ngdoc property
* @propertyOf ui.grid.exporter.constant:uiGridExporterConstants
* @name SELECTED
* @description export all data, including data not visible. Can
* be set only for rowTypes, selection of only some columns is
* not supported
*/
module.constant('uiGridExporterConstants', {
featureName: 'exporter',
rowHeaderColName: 'treeBaseRowHeaderCol',
selectionRowHeaderColName: 'selectionRowHeaderCol',
ALL: 'all',
VISIBLE: 'visible',
SELECTED: 'selected',
CSV_CONTENT: 'CSV_CONTENT',
BUTTON_LABEL: 'BUTTON_LABEL',
FILE_NAME: 'FILE_NAME'
});
/**
* @ngdoc service
* @name ui.grid.exporter.service:uiGridExporterService
*
* @description Services for exporter feature
*/
module.service('uiGridExporterService', ['$filter', '$q', 'uiGridExporterConstants', 'gridUtil', '$compile', '$interval', 'i18nService',
function ($filter, $q, uiGridExporterConstants, gridUtil, $compile, $interval, i18nService) {
var service = {
delay: 100,
initializeGrid: function (grid) {
// add feature namespace and any properties to grid for needed state
grid.exporter = {};
this.defaultGridOptions(grid.options);
/**
* @ngdoc object
* @name ui.grid.exporter.api:PublicApi
*
* @description Public Api for exporter feature
*/
var publicApi = {
events: {
exporter: {
}
},
methods: {
exporter: {
/**
* @ngdoc function
* @name csvExport
* @methodOf ui.grid.exporter.api:PublicApi
* @description Exports rows from the grid in csv format,
* the data exported is selected based on the provided options
* @param {string} rowTypes which rows to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE,
* uiGridExporterConstants.SELECTED
* @param {string} colTypes which columns to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE
*/
csvExport: function (rowTypes, colTypes) {
service.csvExport(grid, rowTypes, colTypes);
},
/**
* @ngdoc function
* @name pdfExport
* @methodOf ui.grid.exporter.api:PublicApi
* @description Exports rows from the grid in pdf format,
* the data exported is selected based on the provided options
* Note that this function has a dependency on pdfMake, all
* going well this has been installed for you.
* The resulting pdf opens in a new browser window.
* @param {string} rowTypes which rows to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE,
* uiGridExporterConstants.SELECTED
* @param {string} colTypes which columns to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE
*/
pdfExport: function (rowTypes, colTypes) {
service.pdfExport(grid, rowTypes, colTypes);
},
/**
* @ngdoc function
* @name excelExport
* @methodOf ui.grid.exporter.api:PublicApi
* @description Exports rows from the grid in excel format,
* the data exported is selected based on the provided options
* @param {string} rowTypes which rows to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE,
* uiGridExporterConstants.SELECTED
* @param {string} colTypes which columns to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE
*/
excelExport: function (rowTypes, colTypes) {
service.excelExport(grid, rowTypes, colTypes);
}
}
}
};
grid.api.registerEventsFromObject(publicApi.events);
grid.api.registerMethodsFromObject(publicApi.methods);
if (grid.api.core.addToGridMenu) {
service.addToMenu( grid );
} else {
// order of registration is not guaranteed, register in a little while
$interval( function() {
if (grid.api.core.addToGridMenu) {
service.addToMenu( grid );
}
}, this.delay, 1);
}
},
defaultGridOptions: function (gridOptions) {
// default option to true unless it was explicitly set to false
/**
* @ngdoc object
* @name ui.grid.exporter.api:GridOptions
*
* @description GridOptions for exporter feature, these are available to be
* set using the ui-grid {@link ui.grid.class:GridOptions gridOptions}
*/
/**
* @ngdoc object
* @name ui.grid.exporter.api:ColumnDef
* @description ColumnDef settings for exporter
*/
/**
* @ngdoc object
* @name exporterSuppressMenu
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Don't show the export menu button, implying the user
* will roll their own UI for calling the exporter
* <br/>Defaults to false
*/
gridOptions.exporterSuppressMenu = gridOptions.exporterSuppressMenu === true;
/**
* @ngdoc object
* @name exporterMenuLabel
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The text to show on the exporter menu button
* link
* <br/>Defaults to 'Export'
*/
gridOptions.exporterMenuLabel = gridOptions.exporterMenuLabel ? gridOptions.exporterMenuLabel : 'Export';
/**
* @ngdoc object
* @name exporterSuppressColumns
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Columns that should not be exported. The selectionRowHeader is already automatically
* suppressed, but if you had a button column or some other "system" column that shouldn't be shown in the
* output then add it in this list. You should provide an array of column names.
* <br/>Defaults to: []
* <pre>
* gridOptions.exporterSuppressColumns = [ 'buttons' ];
* </pre>
*/
gridOptions.exporterSuppressColumns = gridOptions.exporterSuppressColumns ? gridOptions.exporterSuppressColumns : [];
/**
* @ngdoc object
* @name exporterCsvColumnSeparator
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The character to use as column separator
* link
* <br/>Defaults to ','
*/
gridOptions.exporterCsvColumnSeparator = gridOptions.exporterCsvColumnSeparator ? gridOptions.exporterCsvColumnSeparator : ',';
/**
* @ngdoc object
* @name exporterCsvFilename
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The default filename to use when saving the downloaded csv.
* This will only work in some browsers.
* <br/>Defaults to 'download.csv'
*/
gridOptions.exporterCsvFilename = gridOptions.exporterCsvFilename ? gridOptions.exporterCsvFilename : 'download.csv';
/**
* @ngdoc object
* @name exporterPdfFilename
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The default filename to use when saving the downloaded pdf, only used in IE (other browsers open pdfs in a new window)
* <br/>Defaults to 'download.pdf'
*/
gridOptions.exporterPdfFilename = gridOptions.exporterPdfFilename ? gridOptions.exporterPdfFilename : 'download.pdf';
/**
* @ngdoc object
* @name exporterExcelFilename
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The default filename to use when saving the downloaded excel, only used in IE (other browsers open excels in a new window)
* <br/>Defaults to 'download.xlsx'
*/
gridOptions.exporterExcelFilename = gridOptions.exporterExcelFilename ? gridOptions.exporterExcelFilename : 'download.xlsx';
/**
* @ngdoc object
* @name exporterExcelSheetName
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The default sheetname to use when saving the downloaded to excel
* <br/>Defaults to 'Sheet1'
*/
gridOptions.exporterExcelSheetName = gridOptions.exporterExcelSheetName ? gridOptions.exporterExcelSheetName : 'Sheet1';
/**
* @ngdoc object
* @name exporterOlderExcelCompatibility
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Some versions of excel don't like the utf-16 BOM on the front, and it comes
* through as  in the first column header. Setting this option to false will suppress this, at the
* expense of proper utf-16 handling in applications that do recognise the BOM
* <br/>Defaults to false
*/
gridOptions.exporterOlderExcelCompatibility = gridOptions.exporterOlderExcelCompatibility === true;
/**
* @ngdoc object
* @name exporterIsExcelCompatible
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Separator header, used to set a custom column separator in a csv file, only works on MS Excel.
* Used it on other programs will make csv content display unproperly. Setting this option to false won't add this header.
* <br/>Defaults to false
*/
gridOptions.exporterIsExcelCompatible = gridOptions.exporterIsExcelCompatible === true;
/**
* @ngdoc object
* @name exporterMenuItemOrder
* @propertyOf ui.grid.exporter.api:GridOptions
* @description An option to determine the starting point for the menu items created by the exporter
* <br/>Defaults to 200
*/
gridOptions.exporterMenuItemOrder = gridOptions.exporterMenuItemOrder ? gridOptions.exporterMenuItemOrder : 200;
/**
* @ngdoc object
* @name exporterPdfDefaultStyle
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The default style in pdfMake format
* <br/>Defaults to:
* <pre>
* {
* fontSize: 11
* }
* </pre>
*/
gridOptions.exporterPdfDefaultStyle = gridOptions.exporterPdfDefaultStyle ? gridOptions.exporterPdfDefaultStyle : { fontSize: 11 };
/**
* @ngdoc object
* @name exporterPdfTableStyle
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The table style in pdfMake format
* <br/>Defaults to:
* <pre>
* {
* margin: [0, 5, 0, 15]
* }
* </pre>
*/
gridOptions.exporterPdfTableStyle = gridOptions.exporterPdfTableStyle ? gridOptions.exporterPdfTableStyle : { margin: [0, 5, 0, 15] };
/**
* @ngdoc object
* @name exporterPdfTableHeaderStyle
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The tableHeader style in pdfMake format
* <br/>Defaults to:
* <pre>
* {
* bold: true,
* fontSize: 12,
* color: 'black'
* }
* </pre>
*/
gridOptions.exporterPdfTableHeaderStyle = gridOptions.exporterPdfTableHeaderStyle ? gridOptions.exporterPdfTableHeaderStyle : { bold: true, fontSize: 12, color: 'black' };
/**
* @ngdoc object
* @name exporterPdfHeader
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The header section for pdf exports. Can be
* simple text:
* <pre>
* gridOptions.exporterPdfHeader = 'My Header';
* </pre>
* Can be a more complex object in pdfMake format:
* <pre>
* gridOptions.exporterPdfHeader = {
* columns: [
* 'Left part',
* { text: 'Right part', alignment: 'right' }
* ]
* };
* </pre>
* Or can be a function, allowing page numbers and the like
* <pre>
* gridOptions.exporterPdfHeader: function(currentPage, pageCount) { return currentPage.toString() + ' of ' + pageCount; };
* </pre>
*/
gridOptions.exporterPdfHeader = gridOptions.exporterPdfHeader ? gridOptions.exporterPdfHeader : null;
/**
* @ngdoc object
* @name exporterPdfFooter
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The header section for pdf exports. Can be
* simple text:
* <pre>
* gridOptions.exporterPdfFooter = 'My Footer';
* </pre>
* Can be a more complex object in pdfMake format:
* <pre>
* gridOptions.exporterPdfFooter = {
* columns: [
* 'Left part',
* { text: 'Right part', alignment: 'right' }
* ]
* };
* </pre>
* Or can be a function, allowing page numbers and the like
* <pre>
* gridOptions.exporterPdfFooter: function(currentPage, pageCount) { return currentPage.toString() + ' of ' + pageCount; };
* </pre>
*/
gridOptions.exporterPdfFooter = gridOptions.exporterPdfFooter ? gridOptions.exporterPdfFooter : null;
/**
* @ngdoc object
* @name exporterPdfOrientation
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The orientation, should be a valid pdfMake value,
* 'landscape' or 'portrait'
* <br/>Defaults to landscape
*/
gridOptions.exporterPdfOrientation = gridOptions.exporterPdfOrientation ? gridOptions.exporterPdfOrientation : 'landscape';
/**
* @ngdoc object
* @name exporterPdfPageSize
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The orientation, should be a valid pdfMake
* paper size, usually 'A4' or 'LETTER'
* {@link https://github.com/bpampuch/pdfmake/blob/master/src/standardPageSizes.js pdfMake page sizes}
* <br/>Defaults to A4
*/
gridOptions.exporterPdfPageSize = gridOptions.exporterPdfPageSize ? gridOptions.exporterPdfPageSize : 'A4';
/**
* @ngdoc object
* @name exporterPdfMaxGridWidth
* @propertyOf ui.grid.exporter.api:GridOptions
* @description The maxium grid width - the current grid width
* will be scaled to match this, with any fixed width columns
* being adjusted accordingly.
* <br/>Defaults to 720 (for A4 landscape), use 670 for LETTER
*/
gridOptions.exporterPdfMaxGridWidth = gridOptions.exporterPdfMaxGridWidth ? gridOptions.exporterPdfMaxGridWidth : 720;
/**
* @ngdoc object
* @name exporterPdfTableLayout
* @propertyOf ui.grid.exporter.api:GridOptions
* @description A tableLayout in pdfMake format,
* controls gridlines and the like. We use the default
* layout usually.
* <br/>Defaults to null, which means no layout
*/
/**
* @ngdoc object
* @name exporterMenuAllData
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Add export all data as cvs/pdf menu items to the ui-grid grid menu, if it's present. Defaults to true.
*/
gridOptions.exporterMenuAllData = gridOptions.exporterMenuAllData !== undefined ? gridOptions.exporterMenuAllData : true;
/**
* @ngdoc object
* @name exporterMenuVisibleData
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Add export visible data as cvs/pdf menu items to the ui-grid grid menu, if it's present. Defaults to true.
*/
gridOptions.exporterMenuVisibleData = gridOptions.exporterMenuVisibleData !== undefined ? gridOptions.exporterMenuVisibleData : true;
/**
* @ngdoc object
* @name exporterMenuSelectedData
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Add export selected data as cvs/pdf menu items to the ui-grid grid menu, if it's present. Defaults to true.
*/
gridOptions.exporterMenuSelectedData = gridOptions.exporterMenuSelectedData !== undefined ? gridOptions.exporterMenuSelectedData : true;
/**
* @ngdoc object
* @name exporterMenuCsv
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Add csv export menu items to the ui-grid grid menu, if it's present. Defaults to true.
*/
gridOptions.exporterMenuCsv = gridOptions.exporterMenuCsv !== undefined ? gridOptions.exporterMenuCsv : true;
/**
* @ngdoc object
* @name exporterMenuPdf
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Add pdf export menu items to the ui-grid grid menu, if it's present. Defaults to true.
*/
gridOptions.exporterMenuPdf = gridOptions.exporterMenuPdf !== undefined ? gridOptions.exporterMenuPdf : true;
/**
* @ngdoc object
* @name exporterMenuExcel
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Add excel export menu items to the ui-grid grid menu, if it's present. Defaults to true.
*/
gridOptions.exporterMenuExcel = gridOptions.exporterMenuExcel !== undefined ? gridOptions.exporterMenuExcel : true;
/**
* @ngdoc object
* @name exporterPdfCustomFormatter
* @propertyOf ui.grid.exporter.api:GridOptions
* @description A custom callback routine that changes the pdf document, adding any
* custom styling or content that is supported by pdfMake. Takes in the complete docDefinition, and
* must return an updated docDefinition ready for pdfMake.
* @example
* In this example we add a style to the style array, so that we can use it in our
* footer definition.
* <pre>
* gridOptions.exporterPdfCustomFormatter = function ( docDefinition ) {
* docDefinition.styles.footerStyle = { bold: true, fontSize: 10 };
* return docDefinition;
* }
*
* gridOptions.exporterPdfFooter = { text: 'My footer', style: 'footerStyle' }
* </pre>
*/
gridOptions.exporterPdfCustomFormatter = ( gridOptions.exporterPdfCustomFormatter && typeof( gridOptions.exporterPdfCustomFormatter ) === 'function' ) ? gridOptions.exporterPdfCustomFormatter : function ( docDef ) { return docDef; };
/**
* @ngdoc object
* @name exporterHeaderFilterUseName
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Defaults to false, which leads to `displayName` being passed into the headerFilter.
* If set to true, then will pass `name` instead.
*
*
* @example
* <pre>
* gridOptions.exporterHeaderFilterUseName = true;
* </pre>
*/
gridOptions.exporterHeaderFilterUseName = gridOptions.exporterHeaderFilterUseName === true;
/**
* @ngdoc object
* @name exporterHeaderFilter
* @propertyOf ui.grid.exporter.api:GridOptions
* @description A function to apply to the header displayNames before exporting. Useful for internationalisation,
* for example if you were using angular-translate you'd set this to `$translate.instant`. Note that this
* call must be synchronous, it cannot be a call that returns a promise.
*
* Behaviour can be changed to pass in `name` instead of `displayName` through use of `exporterHeaderFilterUseName: true`.
*
* @example
* <pre>
* gridOptions.exporterHeaderFilter = function( displayName ) { return 'col: ' + name; };
* </pre>
* OR
* <pre>
* gridOptions.exporterHeaderFilter = $translate.instant;
* </pre>
*/
/**
* @ngdoc function
* @name exporterFieldCallback
* @propertyOf ui.grid.exporter.api:GridOptions
* @description A function to call for each field before exporting it. Allows
* massaging of raw data into a display format, for example if you have applied
* filters to convert codes into decodes, or you require
* a specific date format in the exported content.
*
* The method is called once for each field exported, and provides the grid, the
* gridCol and the GridRow for you to use as context in massaging the data.
*
* @param {Grid} grid provides the grid in case you have need of it
* @param {GridRow} row the row from which the data comes
* @param {GridColumn} col the column from which the data comes
* @param {object} value the value for your massaging
* @returns {object} you must return the massaged value ready for exporting
*
* @example
* <pre>
* gridOptions.exporterFieldCallback = function ( grid, row, col, value ) {
* if ( col.name === 'status' ) {
* value = decodeStatus( value );
* }
* return value;
* }
* </pre>
*/
gridOptions.exporterFieldCallback = gridOptions.exporterFieldCallback ? gridOptions.exporterFieldCallback : defaultExporterFieldCallback;
/**
* @ngdoc function
* @name exporterFieldFormatCallback
* @propertyOf ui.grid.exporter.api:GridOptions
* @description A function to call for each field before exporting it. Allows
* general object to be return to modify the format of a cell in the case of
* excel exports
*
* The method is called once for each field exported, and provides the grid, the
* gridCol and the GridRow for you to use as context in massaging the data.
*
* @param {Grid} grid provides the grid in case you have need of it
* @param {GridRow} row the row from which the data comes
* @param {GridColumn} col the column from which the data comes
* @param {object} value the value for your massaging
* @returns {object} you must return the massaged value ready for exporting
*
* @example
* <pre>
* gridOptions.exporterFieldCallback = function ( grid, row, col, value ) {
* if ( col.name === 'status' ) {
* value = decodeStatus( value );
* }
* return value;
* }
* </pre>
*/
gridOptions.exporterFieldFormatCallback = gridOptions.exporterFieldFormatCallback ? gridOptions.exporterFieldFormatCallback : function( grid, row, col, value ) { return null; };
/**
* @ngdoc function
* @name exporterExcelCustomFormatters
* @propertyOf ui.grid.exporter.api:GridOptions
* @description A function to call to setup formatters and store on docDefinition.
*
* The method is called at the start and can setup all the formatters to export to excel
*
* @param {Grid} grid provides the grid in case you have need of it
* @param {Workbook} row the row from which the data comes
* @param {docDefinition} The docDefinition that will have styles as a object to store formatters
* @returns {docDefinition} Updated docDefinition with formatter styles
*
* @example
* <pre>
* gridOptions.exporterExcelCustomFormatters = function(grid, workbook, docDefinition) {
* const formatters = {};
* const stylesheet = workbook.getStyleSheet();
* const headerFormatDefn = {
* 'font': { 'size': 11, 'fontName': 'Calibri', 'bold': true },
* 'alignment': { 'wrapText': false }
* };
*
* formatters['header'] = headerFormatter;
* Object.assign(docDefinition.styles , formatters);
* grid.docDefinition = docDefinition;
* return docDefinition;
* }
* </pre>
*/
gridOptions.exporterExcelCustomFormatters = gridOptions.exporterExcelCustomFormatters ? gridOptions.exporterExcelCustomFormatters : function( grid, workbook, docDefinition ) { return docDefinition; };
/**
* @ngdoc function
* @name exporterExcelHeader
* @propertyOf ui.grid.exporter.api:GridOptions
* @description A function to write formatted header data to sheet.
*
* The method is called to provide custom header building for Excel. This data comes before the grid header
*
* @param {grid} grid provides the grid in case you have need of it
* @param {Workbook} row the row from which the data comes
* @param {Sheet} the sheet to insert data
* @param {docDefinition} The docDefinition that will have styles as a object to store formatters
* @returns {docDefinition} Updated docDefinition with formatter styles
*
* @example
* <pre>
* gridOptions.exporterExcelCustomFormatters = function (grid, workbook, sheet, docDefinition) {
* const headerFormatter = docDefinition.styles['header'];
* let cols = [];
* // push data in A1 cell with metadata formatter
* cols.push({ value: 'Summary Report', metadata: {style: headerFormatter.id} });
* sheet.data.push(cols);
* }
* </pre>
*/
gridOptions.exporterExcelHeader = gridOptions.exporterExcelHeader ? gridOptions.exporterExcelHeader : function( grid, workbook, sheet, docDefinition ) { return null; };
/**
* @ngdoc object
* @name exporterColumnScaleFactor
* @propertyOf ui.grid.exporter.api:GridOptions
* @description A scaling factor to divide the drawnwidth of a column to convert to target excel column
* format size
* @example
* In this example we add a number to divide the drawnwidth of a column to get the excel width.
* <br/>Defaults to 3.5
*/
gridOptions.exporterColumnScaleFactor = gridOptions.exporterColumnScaleFactor ? gridOptions.exporterColumnScaleFactor : 3.5;
/**
* @ngdoc object
* @name exporterFieldApplyFilters
* @propertyOf ui.grid.exporter.api:GridOptions
* @description Defaults to false, which leads to filters being evaluated on export *
*
* @example
* <pre>
* gridOptions.exporterFieldApplyFilters = true;
* </pre>
*/
gridOptions.exporterFieldApplyFilters = gridOptions.exporterFieldApplyFilters === true;
/**
* @ngdoc function
* @name exporterAllDataFn
* @propertyOf ui.grid.exporter.api:GridOptions
* @description This promise is needed when exporting all rows,
* and the data need to be provided by server side. Default is null.
* @returns {Promise} a promise to load all data from server
*
* @example
* <pre>
* gridOptions.exporterAllDataFn = function () {
* return $http.get('/data/100.json')
* }
* </pre>
*/
gridOptions.exporterAllDataFn = gridOptions.exporterAllDataFn ? gridOptions.exporterAllDataFn : null;
/**
* @ngdoc function
* @name exporterAllDataPromise
* @propertyOf ui.grid.exporter.api:GridOptions
* @description DEPRECATED - exporterAllDataFn used to be
* called this, but it wasn't a promise, it was a function that returned
* a promise. Deprecated, but supported for backward compatibility, use
* exporterAllDataFn instead.
* @returns {Promise} a promise to load all data from server
*
* @example
* <pre>
* gridOptions.exporterAllDataFn = function () {
* return $http.get('/data/100.json')
* }
* </pre>
*/
if ( gridOptions.exporterAllDataFn === null && gridOptions.exporterAllDataPromise ) {
gridOptions.exporterAllDataFn = gridOptions.exporterAllDataPromise;
}
},
/**
* @ngdoc function
* @name addToMenu
* @methodOf ui.grid.exporter.service:uiGridExporterService
* @description Adds export items to the grid menu,
* allowing the user to select export options
* @param {Grid} grid the grid from which data should be exported
*/
addToMenu: function ( grid ) {
grid.api.core.addToGridMenu( grid, [
{
title: i18nService.getSafeText('gridMenu.exporterAllAsCsv'),
action: function () {
grid.api.exporter.csvExport( uiGridExporterConstants.ALL, uiGridExporterConstants.ALL );
},
shown: function() {
return grid.options.exporterMenuCsv && grid.options.exporterMenuAllData;
},
order: grid.options.exporterMenuItemOrder
},
{
title: i18nService.getSafeText('gridMenu.exporterVisibleAsCsv'),
action: function () {
grid.api.exporter.csvExport( uiGridExporterConstants.VISIBLE, uiGridExporterConstants.VISIBLE );
},
shown: function() {
return grid.options.exporterMenuCsv && grid.options.exporterMenuVisibleData;
},
order: grid.options.exporterMenuItemOrder + 1
},
{
title: i18nService.getSafeText('gridMenu.exporterSelectedAsCsv'),
action: function () {
grid.api.exporter.csvExport( uiGridExporterConstants.SELECTED, uiGridExporterConstants.VISIBLE );
},
shown: function() {
return grid.options.exporterMenuCsv && grid.options.exporterMenuSelectedData &&
( grid.api.selection && grid.api.selection.getSelectedRows().length > 0 );
},
order: grid.options.exporterMenuItemOrder + 2
},
{
title: i18nService.getSafeText('gridMenu.exporterAllAsPdf'),
action: function () {
grid.api.exporter.pdfExport( uiGridExporterConstants.ALL, uiGridExporterConstants.ALL );
},
shown: function() {
return grid.options.exporterMenuPdf && grid.options.exporterMenuAllData;
},
order: grid.options.exporterMenuItemOrder + 3
},
{
title: i18nService.getSafeText('gridMenu.exporterVisibleAsPdf'),
action: function () {
grid.api.exporter.pdfExport( uiGridExporterConstants.VISIBLE, uiGridExporterConstants.VISIBLE );
},
shown: function() {
return grid.options.exporterMenuPdf && grid.options.exporterMenuVisibleData;
},
order: grid.options.exporterMenuItemOrder + 4
},
{
title: i18nService.getSafeText('gridMenu.exporterSelectedAsPdf'),
action: function () {
grid.api.exporter.pdfExport( uiGridExporterConstants.SELECTED, uiGridExporterConstants.VISIBLE );
},
shown: function() {
return grid.options.exporterMenuPdf && grid.options.exporterMenuSelectedData &&
( grid.api.selection && grid.api.selection.getSelectedRows().length > 0 );
},
order: grid.options.exporterMenuItemOrder + 5
},
{
title: i18nService.getSafeText('gridMenu.exporterAllAsExcel'),
action: function () {
grid.api.exporter.excelExport( uiGridExporterConstants.ALL, uiGridExporterConstants.ALL );
},
shown: function() {
return grid.options.exporterMenuExcel && grid.options.exporterMenuAllData;
},
order: grid.options.exporterMenuItemOrder + 6
},
{
title: i18nService.getSafeText('gridMenu.exporterVisibleAsExcel'),
action: function () {
grid.api.exporter.excelExport( uiGridExporterConstants.VISIBLE, uiGridExporterConstants.VISIBLE );
},
shown: function() {
return grid.options.exporterMenuExcel && grid.options.exporterMenuVisibleData;
},
order: grid.options.exporterMenuItemOrder + 7
},
{
title: i18nService.getSafeText('gridMenu.exporterSelectedAsExcel'),
action: function () {
grid.api.exporter.excelExport( uiGridExporterConstants.SELECTED, uiGridExporterConstants.VISIBLE );
},
shown: function() {
return grid.options.exporterMenuExcel && grid.options.exporterMenuSelectedData &&
( grid.api.selection && grid.api.selection.getSelectedRows().length > 0 );
},
order: grid.options.exporterMenuItemOrder + 8
}
]);
},
/**
* @ngdoc function
* @name csvExport
* @methodOf ui.grid.exporter.service:uiGridExporterService
* @description Exports rows from the grid in csv format,
* the data exported is selected based on the provided options
* @param {Grid} grid the grid from which data should be exported
* @param {string} rowTypes which rows to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE,
* uiGridExporterConstants.SELECTED
* @param {string} colTypes which columns to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE,
* uiGridExporterConstants.SELECTED
*/
csvExport: function (grid, rowTypes, colTypes) {
var self = this;
this.loadAllDataIfNeeded(grid, rowTypes, colTypes).then(function() {
var exportColumnHeaders = grid.options.showHeader ? self.getColumnHeaders(grid, colTypes) : [];
var exportData = self.getData(grid, rowTypes, colTypes);
var csvContent = self.formatAsCsv(exportColumnHeaders, exportData, grid.options.exporterCsvColumnSeparator);
self.downloadFile (grid.options.exporterCsvFilename, csvContent, grid.options.exporterCsvColumnSeparator, grid.options.exporterOlderExcelCompatibility, grid.options.exporterIsExcelCompatible);
});
},
/**
* @ngdoc function
* @name loadAllDataIfNeeded
* @methodOf ui.grid.exporter.service:uiGridExporterService
* @description When using server side pagination, use exporterAllDataFn to
* load all data before continuing processing.
* When using client side pagination, return a resolved promise so processing
* continues immediately
* @param {Grid} grid the grid from which data should be exported
* @param {string} rowTypes which rows to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE,
* uiGridExporterConstants.SELECTED
* @param {string} colTypes which columns to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE,
* uiGridExporterConstants.SELECTED
*/
loadAllDataIfNeeded: function (grid, rowTypes, colTypes) {
if ( rowTypes === uiGridExporterConstants.ALL && grid.rows.length !== grid.options.totalItems && grid.options.exporterAllDataFn) {
return grid.options.exporterAllDataFn()
.then(function(allData) {
grid.modifyRows(allData);
});
} else {
var deferred = $q.defer();
deferred.resolve();
return deferred.promise;
}
},
/**
* @ngdoc property
* @propertyOf ui.grid.exporter.api:ColumnDef
* @name exporterSuppressExport
* @description Suppresses export for this column. Used by selection and expandable.
*/
/**
* @ngdoc function
* @name getColumnHeaders
* @methodOf ui.grid.exporter.service:uiGridExporterService
* @description Gets the column headers from the grid to use
* as a title row for the exported file, all headers have
* headerCellFilters applied as appropriate.
*
* Column headers are an array of objects, each object has
* name, displayName, width and align attributes. Only name is
* used for csv, all attributes are used for pdf.
*
* @param {Grid} grid the grid from which data should be exported
* @param {string} colTypes which columns to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE,
* uiGridExporterConstants.SELECTED
*/
getColumnHeaders: function (grid, colTypes) {
var headers = [],
columns;
if ( colTypes === uiGridExporterConstants.ALL ) {
columns = grid.columns;
} else {
var leftColumns = grid.renderContainers.left ? grid.renderContainers.left.visibleColumnCache.filter( function( column ) { return column.visible; } ) : [],
bodyColumns = grid.renderContainers.body ? grid.renderContainers.body.visibleColumnCache.filter( function( column ) { return column.visible; } ) : [],
rightColumns = grid.renderContainers.right ? grid.renderContainers.right.visibleColumnCache.filter( function( column ) { return column.visible; } ) : [];
columns = leftColumns.concat(bodyColumns, rightColumns);
}
columns.forEach( function( gridCol ) {
// $$hashKey check since when grouping and sorting pragmatically this ends up in export. Filtering it out
if ( gridCol.colDef.exporterSuppressExport !== true && gridCol.field !== '$$hashKey' &&
grid.options.exporterSuppressColumns.indexOf( gridCol.name ) === -1 ) {
var headerEntry = {
name: gridCol.field,
displayName: getDisplayName(grid, gridCol),
width: gridCol.drawnWidth ? gridCol.drawnWidth : gridCol.width,
align: gridCol.colDef.align ? gridCol.colDef.align : (gridCol.colDef.type === 'number' ? 'right' : 'left')
};
headers.push(headerEntry);
}
});
return headers;
},
/**
* @ngdoc property
* @propertyOf ui.grid.exporter.api:ColumnDef
* @name exporterPdfAlign
* @description the alignment you'd like for this specific column when
* exported into a pdf. Can be 'left', 'right', 'center' or any other
* valid pdfMake alignment option.
*/
/**
* @ngdoc object
* @name ui.grid.exporter.api:GridRow
* @description GridRow settings for exporter
*/
/**
* @ngdoc object
* @name exporterEnableExporting
* @propertyOf ui.grid.exporter.api:GridRow
* @description If set to false, then don't export this row, notwithstanding visible or
* other settings
* <br/>Defaults to true
*/
/**
* @ngdoc function
* @name getRowsFromNode
* @methodOf ui.grid.exporter.service:uiGridExporterService
* @description Gets rows from a node. If the node is grouped it will
* recurse down into the children to get to the raw data element
* which is a row without children (a leaf).
* @param {Node} aNode the tree node on the grid
* @returns {Array} an array with all child nodes from aNode
*/
getRowsFromNode: function(aNode) {
var rows = [];
// Push parent node if it is not undefined and has values other than 'children'
var nodeKeys = aNode ? Object.keys(aNode) : ['children'];
if (nodeKeys.length > 1 || nodeKeys[0] != 'children') {
rows.push(aNode);
}
if (aNode && aNode.children && aNode.children.length > 0) {
for (var i = 0; i < aNode.children.length; i++) {
rows = rows.concat(this.getRowsFromNode(aNode.children[i]));
}
}
return rows;
},
/**
* @ngdoc function
* @name getDataSorted
* @methodOf ui.grid.exporter.service:uiGridExporterService
* @description Gets rows from a node. If the node is grouped it will
* recurse down into the children to get to the raw data element
* which is a row without children (a leaf). If the grid is not
* grouped this will return just the raw rows
* @param {Grid} grid the grid from which data should be exported
* @returns {Array} an array of leaf nodes
*/
getDataSorted: function (grid) {
if (!grid.treeBase || grid.treeBase.numberLevels === 0) {
return grid.rows;
}
var rows = [];
for (var i = 0; i< grid.treeBase.tree.length; i++) {
var nodeRows = this.getRowsFromNode(grid.treeBase.tree[i]);
for (var j = 0; j<nodeRows.length; j++) {
rows.push(nodeRows[j].row);
}
}
return rows;
},
/**
* @ngdoc function
* @name getData
* @methodOf ui.grid.exporter.service:uiGridExporterService
* @description Gets data from the grid based on the provided options,
* all cells have cellFilters applied as appropriate. Any rows marked
* `exporterEnableExporting: false` will not be exported
* @param {Grid} grid the grid from which data should be exported
* @param {string} rowTypes which rows to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE,
* uiGridExporterConstants.SELECTED
* @param {string} colTypes which columns to export, valid values are
* uiGridExporterConstants.ALL, uiGridExporterConstants.VISIBLE,
* uiGridExporterConstants.SELECTED
* @param {boolean} applyCellFilters whether or not to get the display value or the raw value of the data
*/
getData: function (grid, rowTypes, colTypes, applyCellFilters) {
var data = [],
rows,
columns;
switch ( rowTypes ) {
case uiGridExporterConstants.ALL:
rows = this.getDataSorted(grid, rowTypes, colTypes, applyCellFilters);
break;
case uiGridExporterConstants.VISIBLE:
rows = grid.getVisibleRows();
break;
case uiGridExporterConstants.SELECTED:
if ( grid.api.selection ) {
rows = grid.api.selection.getSelectedGridRows();
} else {
gridUtil.logError('selection feature must be enabled to allow selected rows to be exported');
}
break;
}
if ( colTypes === uiGridExporterConstants.ALL ) {
columns = grid.columns;
} else {
var leftColumns = grid.renderContainers.left ? grid.renderContainers.left.visibleColumnCache.filter( function( column ) { return column.visible; } ) : [];
var bodyColumns = grid.renderContainers.body ? grid.renderContainers.body.visibleColumnCache.filter( function( column ) { return column.visible; } ) : [];
var rightColumns = grid.renderContainers.right ? grid.renderContainers.right.visibleColumnCache.filter( function( column ) { return column.visible; } ) : [];
columns = leftColumns.concat(bodyColumns, rightColumns);
}
rows.forEach(function( row ) {
if (row.exporterEnableExporting !== false) {
var extractedRow = [];
columns.forEach( function( gridCol ) {
// $$hashKey check since when grouping and sorting programmatically this ends up in export. Filtering it out
if ( (gridCol.visible || colTypes === uiGridExporterConstants.ALL ) &&
gridCol.colDef.exporterSuppressExport !== true && gridCol.field !== '$$hashKey' &&
grid.options.exporterSuppressColumns.indexOf( gridCol.name ) === -1 ) {
var cellValue = applyCellFilters ? grid.getCellDisplayValue( row, gridCol ) : grid.getCellValue( row, gridCol ),
extractedField = { value: grid.options.exporterFieldCallback( grid, row, gridCol, cellValue ) },
extension = grid.options.exporterFieldFormatCallback( grid, row, gridCol, cellValue );
if (extension) {
Object.assign(extractedField, extension);
}
if ( gridCol.colDef.exporterPdfAlign ) {
extractedField.alignment = gridCol.colDef.exporterPdfAlign;
}
extractedRow.push(extractedField);
}
});
data.push(extractedRow);
}
});
return data;
},
/**
* @ngdoc function
* @name formatAsCsv
* @methodOf ui.grid.exporter.service:uiGridExporterService
* @description Formats the column headers and data as a CSV,
* and sends that data to the user
* @param {array} exportColumnHeaders an array of column headers,
* where each header is an object with name, width and maybe alignment
* @param {array} exportData an array of rows, where each row is
* an array of column data
* @param {string} separator a string that represents the separator to be used in the csv file
* @returns {string} csv the formatted csv as a string
*/
formatAsCsv: function (exportColumnHeaders, exportData, separator) {
var self = this,