1fb726d48Sopenharmony_ci/*
2fb726d48Sopenharmony_ci * Copyright (C) 2022 Huawei Device Co., Ltd.
3fb726d48Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
4fb726d48Sopenharmony_ci * you may not use this file except in compliance with the License.
5fb726d48Sopenharmony_ci * You may obtain a copy of the License at
6fb726d48Sopenharmony_ci *
7fb726d48Sopenharmony_ci *     http://www.apache.org/licenses/LICENSE-2.0
8fb726d48Sopenharmony_ci *
9fb726d48Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software
10fb726d48Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
11fb726d48Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12fb726d48Sopenharmony_ci * See the License for the specific language governing permissions and
13fb726d48Sopenharmony_ci * limitations under the License.
14fb726d48Sopenharmony_ci */
15fb726d48Sopenharmony_ci
16fb726d48Sopenharmony_ciconst htmlStr = (): unknown => {
17fb726d48Sopenharmony_ci  const html_start =
18fb726d48Sopenharmony_ci    '<html xmlns:v="urn:schemas-microsoft-com:vml" xmlns:o="urn:schemas-microsoft-com:office:office" xmlns:x="urn:schemas-microsoft-com:office:excel" xmlns="http://www.w3.org/TR/REC-html40">';
19fb726d48Sopenharmony_ci  return {
20fb726d48Sopenharmony_ci    uri: 'data:application/vnd.ms-excel;base64,',
21fb726d48Sopenharmony_ci    template_ExcelWorksheet:
22fb726d48Sopenharmony_ci      '<x:ExcelWorksheet><x:Name>{SheetName}</x:Name><x:WorksheetSource HRef="sheet{SheetIndex}.htm"/><x:WorksheetOptions><x:DisplayGridlines/></x:WorksheetOptions></x:ExcelWorksheet>',
23fb726d48Sopenharmony_ci    template_ListWorksheet: '<o:File HRef="sheet{SheetIndex}.htm"/>',
24fb726d48Sopenharmony_ci    template_WorkBook:
25fb726d48Sopenharmony_ci      `MIME-Version: 1.0
26fb726d48Sopenharmony_ciX-Document-Type: Workbook
27fb726d48Sopenharmony_ciContent-Type: multipart/related; boundary="----=_NextPart_dummy"
28fb726d48Sopenharmony_ci
29fb726d48Sopenharmony_ci------=_NextPart_dummy
30fb726d48Sopenharmony_ciContent-Location: WorkBook.htm
31fb726d48Sopenharmony_ciContent-Type: text/html; charset=windows-1252
32fb726d48Sopenharmony_ci
33fb726d48Sopenharmony_ci` +
34fb726d48Sopenharmony_ci      html_start +
35fb726d48Sopenharmony_ci      `
36fb726d48Sopenharmony_ci<head>
37fb726d48Sopenharmony_ci<meta name="Excel Workbook Frameset">
38fb726d48Sopenharmony_ci<meta http-equiv="Content-Type" charset="UTF-8" content="text/html; charset=windows-1252">
39fb726d48Sopenharmony_ci<link rel="File-List" href="filelist.xml">
40fb726d48Sopenharmony_ci<!--[if gte mso 9]><xml>
41fb726d48Sopenharmony_ci <x:ExcelWorkbook>
42fb726d48Sopenharmony_ci    <x:ExcelWorksheets>{ExcelWorksheets}</x:ExcelWorksheets>
43fb726d48Sopenharmony_ci    <x:ActiveSheet>0</x:ActiveSheet>
44fb726d48Sopenharmony_ci </x:ExcelWorkbook>
45fb726d48Sopenharmony_ci</xml><![endif]-->
46fb726d48Sopenharmony_ci</head>
47fb726d48Sopenharmony_ci<frameset>
48fb726d48Sopenharmony_ci    <frame src="sheet0.htm" name="frSheet">
49fb726d48Sopenharmony_ci    <noframes><body><p>This page uses frames, but your browser does not support them.</p></body></noframes>
50fb726d48Sopenharmony_ci</frameset>
51fb726d48Sopenharmony_ci</html>
52fb726d48Sopenharmony_ci{HTMLWorksheets}
53fb726d48Sopenharmony_ciContent-Location: filelist.xml
54fb726d48Sopenharmony_ciContent-Type: text/xml; charset="utf-8"
55fb726d48Sopenharmony_ci
56fb726d48Sopenharmony_ci<xml xmlns:o="urn:schemas-microsoft-com:office:office">
57fb726d48Sopenharmony_ci    <o:MainFile HRef="../WorkBook.htm"/>
58fb726d48Sopenharmony_ci    {ListWorksheets}
59fb726d48Sopenharmony_ci    <o:File HRef="filelist.xml"/>
60fb726d48Sopenharmony_ci</xml>
61fb726d48Sopenharmony_ci------=_NextPart_dummy--
62fb726d48Sopenharmony_ci`,
63fb726d48Sopenharmony_ci  };
64fb726d48Sopenharmony_ci};
65fb726d48Sopenharmony_ci
66fb726d48Sopenharmony_ciexport class ExcelFormater {
67fb726d48Sopenharmony_ci  static tmplCellXML = '<Cell{attributeStyleID}{attributeFormula}><Data ss:Type="{nameType}">{data}</Data></Cell>';
68fb726d48Sopenharmony_ci  static base64 = function (s: unknown): string {
69fb726d48Sopenharmony_ci    //@ts-ignore
70fb726d48Sopenharmony_ci    return window.btoa(unescape(encodeURIComponent(s)));
71fb726d48Sopenharmony_ci  };
72fb726d48Sopenharmony_ci
73fb726d48Sopenharmony_ci  static format(s: unknown, c: unknown): string {
74fb726d48Sopenharmony_ci    //@ts-ignore
75fb726d48Sopenharmony_ci    return s.replace(/{(\w+)}/g, function (m: unknown, p: unknown) {
76fb726d48Sopenharmony_ci      //@ts-ignore
77fb726d48Sopenharmony_ci      return c[p];
78fb726d48Sopenharmony_ci    });
79fb726d48Sopenharmony_ci  }
80fb726d48Sopenharmony_ci
81fb726d48Sopenharmony_ci  static createExcelRow(columns: unknown[], data: unknown): string {
82fb726d48Sopenharmony_ci    let rowsXML = '';
83fb726d48Sopenharmony_ci    rowsXML += '<Row>';
84fb726d48Sopenharmony_ci    for (let k = 0; k < columns.length; k++) {
85fb726d48Sopenharmony_ci      //@ts-ignore
86fb726d48Sopenharmony_ci      let dataIndex = columns[k].getAttribute('data-index'); //@ts-ignore
87fb726d48Sopenharmony_ci      let columnName = columns[k].getAttribute('title');
88fb726d48Sopenharmony_ci      if (columnName === '') {
89fb726d48Sopenharmony_ci        columnName = dataIndex;
90fb726d48Sopenharmony_ci      }
91fb726d48Sopenharmony_ci      let ctx = {
92fb726d48Sopenharmony_ci        attributeStyleID: '',
93fb726d48Sopenharmony_ci        nameType: 'String', //@ts-ignore
94fb726d48Sopenharmony_ci        data: data ? data[dataIndex] || '' : columnName,
95fb726d48Sopenharmony_ci        attributeFormula: '',
96fb726d48Sopenharmony_ci      };
97fb726d48Sopenharmony_ci      rowsXML += this.format(this.tmplCellXML, ctx);
98fb726d48Sopenharmony_ci    }
99fb726d48Sopenharmony_ci    rowsXML += '</Row>'; //@ts-ignore
100fb726d48Sopenharmony_ci    if (data && data.children !== undefined && data.children.length > 0) {
101fb726d48Sopenharmony_ci      //@ts-ignore
102fb726d48Sopenharmony_ci      data.children.forEach((child: unknown) => {
103fb726d48Sopenharmony_ci        rowsXML += this.createExcelRow(columns, child);
104fb726d48Sopenharmony_ci      });
105fb726d48Sopenharmony_ci    }
106fb726d48Sopenharmony_ci    return rowsXML;
107fb726d48Sopenharmony_ci  }
108fb726d48Sopenharmony_ci
109fb726d48Sopenharmony_ci  static addImage(baseStr: string): string {
110fb726d48Sopenharmony_ci    return `<Row>${this.format(this.tmplCellXML, {
111fb726d48Sopenharmony_ci      attributeStyleID: '',
112fb726d48Sopenharmony_ci      nameType: 'String',
113fb726d48Sopenharmony_ci      data: `<div><img src="${baseStr}"></img></div>`,
114fb726d48Sopenharmony_ci      attributeFormula: '',
115fb726d48Sopenharmony_ci    })}</Row>`;
116fb726d48Sopenharmony_ci  }
117fb726d48Sopenharmony_ci
118fb726d48Sopenharmony_ci  static testExport(
119fb726d48Sopenharmony_ci    dataSource: { columns: unknown[]; tables: unknown[]; sheetName: string }[],
120fb726d48Sopenharmony_ci    fileName: string
121fb726d48Sopenharmony_ci  ): void {
122fb726d48Sopenharmony_ci    this.tablesToHtmlExcelMultipleSheet(dataSource, fileName);
123fb726d48Sopenharmony_ci  }
124fb726d48Sopenharmony_ci
125fb726d48Sopenharmony_ci  static tablesToHtmlExcelMultipleSheet(
126fb726d48Sopenharmony_ci    dataSource: { columns: unknown[]; tables: unknown[]; sheetName: string }[],
127fb726d48Sopenharmony_ci    fileName: string,
128fb726d48Sopenharmony_ci    image?: string
129fb726d48Sopenharmony_ci  ): void {
130fb726d48Sopenharmony_ci    let sheets: unknown[] = [];
131fb726d48Sopenharmony_ci    dataSource.forEach((data): void => {
132fb726d48Sopenharmony_ci      sheets.push(this.createTableData(data.columns, data.tables, image));
133fb726d48Sopenharmony_ci    });
134fb726d48Sopenharmony_ci    this.tablesToExcelTestSheet(sheets, fileName, dataSource);
135fb726d48Sopenharmony_ci  }
136fb726d48Sopenharmony_ci
137fb726d48Sopenharmony_ci  static createTableData(columns: unknown[], dataSource: unknown[], image?: string): string {
138fb726d48Sopenharmony_ci    let tableData = '';
139fb726d48Sopenharmony_ci    let columnDatas = columns.map((column) => {
140fb726d48Sopenharmony_ci      //@ts-ignore
141fb726d48Sopenharmony_ci      let dataIndex = column.getAttribute('data-index'); //@ts-ignore
142fb726d48Sopenharmony_ci      let columnName = column.getAttribute('title');
143fb726d48Sopenharmony_ci      if (columnName === '') {
144fb726d48Sopenharmony_ci        columnName = dataIndex;
145fb726d48Sopenharmony_ci      }
146fb726d48Sopenharmony_ci      return {
147fb726d48Sopenharmony_ci        columnName: columnName,
148fb726d48Sopenharmony_ci        dataIndex: dataIndex,
149fb726d48Sopenharmony_ci      };
150fb726d48Sopenharmony_ci    });
151fb726d48Sopenharmony_ci    tableData += this.createTHead(
152fb726d48Sopenharmony_ci      columnDatas.map((item) => {
153fb726d48Sopenharmony_ci        return item.columnName;
154fb726d48Sopenharmony_ci      })
155fb726d48Sopenharmony_ci    );
156fb726d48Sopenharmony_ci    let columnDataIndexes = columnDatas.map((item) => item.dataIndex);
157fb726d48Sopenharmony_ci    dataSource.forEach((data, index) => {
158fb726d48Sopenharmony_ci      if (index === 0 && image) {
159fb726d48Sopenharmony_ci        tableData += this.createTableRow(columnDataIndexes, data, image);
160fb726d48Sopenharmony_ci      } else {
161fb726d48Sopenharmony_ci        tableData += this.createTableRow(columnDataIndexes, data);
162fb726d48Sopenharmony_ci      }
163fb726d48Sopenharmony_ci    });
164fb726d48Sopenharmony_ci    return tableData;
165fb726d48Sopenharmony_ci  }
166fb726d48Sopenharmony_ci
167fb726d48Sopenharmony_ci  static createTHead(columns: unknown[]): string {
168fb726d48Sopenharmony_ci    let header = '<thead>';
169fb726d48Sopenharmony_ci    columns.forEach((column) => {
170fb726d48Sopenharmony_ci      header += `<td>${column}</td>`;
171fb726d48Sopenharmony_ci    });
172fb726d48Sopenharmony_ci    header += '</thrad>';
173fb726d48Sopenharmony_ci    return header;
174fb726d48Sopenharmony_ci  }
175fb726d48Sopenharmony_ci
176fb726d48Sopenharmony_ci  static createTableRow(columns: unknown[], data: unknown, image?: unknown): string {
177fb726d48Sopenharmony_ci    let childrenData = ''; //@ts-ignore
178fb726d48Sopenharmony_ci    if (data.children !== undefined) {
179fb726d48Sopenharmony_ci      //@ts-ignore
180fb726d48Sopenharmony_ci      data.children.forEach((child: unknown) => {
181fb726d48Sopenharmony_ci        if (child) {
182fb726d48Sopenharmony_ci          childrenData += this.createTableRow(columns, child);
183fb726d48Sopenharmony_ci        }
184fb726d48Sopenharmony_ci      });
185fb726d48Sopenharmony_ci    }
186fb726d48Sopenharmony_ci    return `<tr>${columns
187fb726d48Sopenharmony_ci      .map((column) => {
188fb726d48Sopenharmony_ci        //@ts-ignore
189fb726d48Sopenharmony_ci        return `<td>${(data[column] + '').replace('μ', 'u')}</td>` || '';
190fb726d48Sopenharmony_ci      })
191fb726d48Sopenharmony_ci      .join('')}${image ? `<td><div><img src="${image}"></img></div></td>` : ''}</tr>${childrenData}`;
192fb726d48Sopenharmony_ci  }
193fb726d48Sopenharmony_ci
194fb726d48Sopenharmony_ci  static tablesToExcelTestSheet(
195fb726d48Sopenharmony_ci    tables: unknown[],
196fb726d48Sopenharmony_ci    filename: string,
197fb726d48Sopenharmony_ci    dataSource: { columns: unknown[]; tables: unknown[]; sheetName: string }[]
198fb726d48Sopenharmony_ci  ): void {
199fb726d48Sopenharmony_ci    const html_start =
200fb726d48Sopenharmony_ci      '<html xmlns:v="urn:schemas-microsoft-com:vml" xmlns:o="urn:schemas-microsoft-com:office:office" xmlns:x="urn:schemas-microsoft-com:office:excel" xmlns="http://www.w3.org/TR/REC-html40">'; //@ts-ignore
201fb726d48Sopenharmony_ci    let { uri, template_ExcelWorksheet, template_ListWorksheet, template_WorkBook } = htmlStr();
202fb726d48Sopenharmony_ci    let template_HTMLWorksheet =
203fb726d48Sopenharmony_ci      `
204fb726d48Sopenharmony_ci------=_NextPart_dummy
205fb726d48Sopenharmony_ciContent-Location: sheet{SheetIndex}.htm
206fb726d48Sopenharmony_ciContent-Type: text/html; charset=windows-1252
207fb726d48Sopenharmony_ci
208fb726d48Sopenharmony_ci` +
209fb726d48Sopenharmony_ci      html_start +
210fb726d48Sopenharmony_ci      `
211fb726d48Sopenharmony_ci<head>
212fb726d48Sopenharmony_ci    <meta http-equiv="Content-Type" charset="UTF-8" content="text/html; charset=windows-1252">
213fb726d48Sopenharmony_ci    <link id="Main-File" rel="Main-File" href="../WorkBook.htm">
214fb726d48Sopenharmony_ci    <link rel="File-List" href="filelist.xml">
215fb726d48Sopenharmony_ci</head>
216fb726d48Sopenharmony_ci<body><table>{SheetContent}</table></body>
217fb726d48Sopenharmony_ci</html>`;
218fb726d48Sopenharmony_ci    let context_WorkBook = {
219fb726d48Sopenharmony_ci      ExcelWorksheets: '',
220fb726d48Sopenharmony_ci      HTMLWorksheets: '',
221fb726d48Sopenharmony_ci      ListWorksheets: '',
222fb726d48Sopenharmony_ci    };
223fb726d48Sopenharmony_ci    tables.forEach((item, sheetIndex) => {
224fb726d48Sopenharmony_ci      context_WorkBook.ExcelWorksheets += this.format(template_ExcelWorksheet, {
225fb726d48Sopenharmony_ci        SheetIndex: sheetIndex,
226fb726d48Sopenharmony_ci        SheetName: dataSource[sheetIndex].sheetName,
227fb726d48Sopenharmony_ci      });
228fb726d48Sopenharmony_ci      context_WorkBook.HTMLWorksheets += this.format(template_HTMLWorksheet, {
229fb726d48Sopenharmony_ci        SheetIndex: sheetIndex,
230fb726d48Sopenharmony_ci        SheetContent: item,
231fb726d48Sopenharmony_ci      });
232fb726d48Sopenharmony_ci      context_WorkBook.ListWorksheets += this.format(template_ListWorksheet, {
233fb726d48Sopenharmony_ci        SheetIndex: sheetIndex,
234fb726d48Sopenharmony_ci      });
235fb726d48Sopenharmony_ci    });
236fb726d48Sopenharmony_ci    let link = document.createElement('a');
237fb726d48Sopenharmony_ci    link.href = uri + this.base64(this.format(template_WorkBook, context_WorkBook));
238fb726d48Sopenharmony_ci    link.download = filename + '.xls';
239fb726d48Sopenharmony_ci    link.target = '_blank';
240fb726d48Sopenharmony_ci    link.click();
241fb726d48Sopenharmony_ci  }
242fb726d48Sopenharmony_ci}
243