123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110 |
- # -*- coding: utf-8 -*-
- import datetime
- import io
- from odoo.tools import pycompat
- from odoo.tools.translate import _
- from odoo.tools.misc import xlsxwriter
- from odoo.exceptions import UserError
- # 根据addons/web/controllers/main.py中的ExportXlsxWriter改编而来
- class ExportXlsxWriter:
- def __init__(self, headers, row_count=0):
- self.headers = headers
- self.output = io.BytesIO()
- self.workbook = xlsxwriter.Workbook(self.output, {'in_memory': True})
- self.base_style = self.workbook.add_format({'text_wrap': True})
- self.header_style = self.workbook.add_format(
- {'bold': True, 'align': 'center', 'valign': 'vcenter', 'bg_color': '#ADD8E6'})
- self.sum_style = self.workbook.add_format({'bold': True, 'align': 'center', 'valign': 'vcenter'})
- self.header_bold_style = self.workbook.add_format({'text_wrap': True, 'bold': True, 'bg_color': '#e9ecef'})
- # self.date_style = self.workbook.add_format({'text_wrap': True, 'num_format': 'yyyy-mm-dd'})
- # self.datetime_style = self.workbook.add_format({'text_wrap': True, 'num_format': 'yyyy-mm-dd hh:mm:ss'})
- self.worksheet = self.workbook.add_worksheet()
- self.value = False
- self._font_color_dic = {}
- self._background_color_dic = {}
- self._font_and_background_color_dic = {}
- if row_count > self.worksheet.xls_rowmax:
- raise UserError('行数%s,超过Excel允许的最大行数%s' % (row_count, self.worksheet.xls_rowmax))
- return
- def __enter__(self):
- self.write_header()
- return self
- def __exit__(self, exc_type, exc_value, exc_traceback):
- self.close()
- return
- def get_font_color(self, color):
- if not color:
- return None
- if color not in self._font_color_dic:
- style = self.workbook.add_format({'font_color': color}) # font_color: also can use color
- self._font_color_dic[color] = style
- return style
- return self._font_color_dic[color]
- def get_background_color(self, color):
- if not color:
- return None
- if color not in self._background_color_dic:
- style = self.workbook.add_format({'fg_color': color})
- self._background_color_dic[color] = style
- return style
- return self._background_color_dic[color]
- def get_font_and_background_color(self, font_color, background_color):
- if not font_color and not background_color:
- return None
- if not font_color:
- return self.get_background_color(background_color)
- if not background_color:
- return self.get_font_color(font_color)
- key = font_color + background_color
- if key not in self._font_and_background_color_dic:
- style = self.workbook.add_format({'font_color': font_color, 'fg_color': background_color})
- self._font_and_background_color_dic[key] = style
- return style
- return self._font_and_background_color_dic[key]
- def write_header(self):
- # Write main header
- for i, head_data in enumerate(self.headers):
- name = head_data[0]
- width = ExportXlsxWriter._get_width(head_data[1])
- self.write(0, i, name, self.header_style)
- self.worksheet.set_column(i, i, width)
- return
- @staticmethod
- def _get_width(width):
- return width * 30 / 220 # 30:around 220 pixels
- def close(self):
- self.workbook.close()
- with self.output:
- self.value = self.output.getvalue()
- return
- def write(self, row, column, cell_value, style=None):
- self.worksheet.write(row, column, cell_value, style)
- return
- def write_cell(self, row, column, cell_value, cell_style=None):
- cell_style = cell_style if cell_style else self.base_style
- if isinstance(cell_value, str):
- if len(cell_value) > self.worksheet.xls_strmax:
- cell_value = _(
- "The content of this cell is too long for an XLSX file (more than %s characters). Please use the CSV format for this export.",
- self.worksheet.xls_strmax)
- else:
- cell_value = cell_value.replace("\r", " ")
- self.write(row, column, cell_value, cell_style)
- return
|