Bugfix in printscreen encoding
[odoo/odoo.git] / bin / report / printscreen / ps_list.py
1 ##############################################################################
2 #
3 # Copyright (c) 2004 TINY SPRL. (http://tiny.be) All Rights Reserved.
4 #                    Fabien Pinckaers <fp@tiny.Be>
5 #
6 # WARNING: This program as such is intended to be used by professional
7 # programmers who take the whole responsability of assessing all potential
8 # consequences resulting from its eventual inadequacies and bugs
9 # End users who are looking for a ready-to-use solution with commercial
10 # garantees and support are strongly adviced to contract a Free Software
11 # Service Company
12 #
13 # This program is Free Software; you can redistribute it and/or
14 # modify it under the terms of the GNU General Public License
15 # as published by the Free Software Foundation; either version 2
16 # of the License, or (at your option) any later version.
17 #
18 # This program is distributed in the hope that it will be useful,
19 # but WITHOUT ANY WARRANTY; without even the implied warranty of
20 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
21 # GNU General Public License for more details.
22 #
23 # You should have received a copy of the GNU General Public License
24 # along with this program; if not, write to the Free Software
25 # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
26 #
27 ##############################################################################
28
29 from report.interface import report_int
30 import pooler
31 import tools
32
33 from report import render
34
35 from xml.dom import minidom
36 import libxml2
37 import libxslt
38
39 import time, os
40
41 class report_printscreen_list(report_int):
42         def __init__(self, name):
43                 report_int.__init__(self, name)
44
45         def _parse_node(self, root_node):
46                 result = []
47                 for node in root_node.childNodes:
48                         if node.localName == 'field':
49                                 attrsa = node.attributes
50                                 attrs = {}
51                                 if not attrsa is None:
52                                         for i in range(attrsa.length):
53                                                 attrs[attrsa.item(i).localName] = attrsa.item(i).nodeValue
54                                 result.append(attrs['name'])
55                         else:
56                                 result.extend(self._parse_node(node))
57                 return result
58
59         def _parse_string(self, view):
60                 dom = minidom.parseString(view.encode('utf-8'))
61                 return self._parse_node(dom)
62
63         def create(self, cr, uid, ids, datas, context={}):
64                 datas['ids'] = ids
65                 model = pooler.get_pool(cr.dbname).get(datas['model'])
66                 result = model.fields_view_get(cr, uid, view_type='tree', context=context)
67
68                 fields_order = self._parse_string(result['arch'])
69                 rows = model.read(cr, uid, datas['ids'], result['fields'].keys() )
70                 res = self._create_table(uid, datas['ids'], result['fields'], fields_order, rows, context, model._description)
71                 return (self.obj.get(), 'pdf')
72
73
74         def _create_table(self, uid, ids, fields, fields_order, results, context, title=''):
75
76
77                 pageSize=[297.0,210.0]
78
79                 impl = minidom.getDOMImplementation()
80                 new_doc = impl.createDocument(None, "report", None)
81
82                 # build header
83                 config = new_doc.createElement("config")
84
85                 def _append_node(name, text):
86                         n = new_doc.createElement(name)
87                         t = new_doc.createTextNode(text)
88                         n.appendChild(t)
89                         config.appendChild(n)
90
91                 _append_node('date', time.strftime('%d/%m/%Y'))
92                 _append_node('PageSize', '%.2fmm,%.2fmm' % tuple(pageSize))
93                 _append_node('PageWidth', '%.2f' % (pageSize[0] * 2.8346,))
94                 _append_node('PageHeight', '%.2f' %(pageSize[1] * 2.8346,))
95
96                 _append_node('report-header', title)
97                 l = []
98                 t = 0
99                 rowcount=0;
100                 strmax = (pageSize[0]-40) * 2.8346
101                 temp = []
102                 count = len(fields_order)
103                 for i in range(0,count):
104                         temp.append(0)
105
106                 ince = -1;
107                 for f in fields_order:
108                         s = 0
109                         ince += 1
110                         if fields[f]['type'] in ('date','time','float','integer'):
111                                 s = 60
112                                 strmax -= s
113                                 if fields[f]['type'] in ('float','integer'):
114                                         temp[ince]=1;
115                         else:
116                                 t += fields[f].get('size', 80) / 28 + 1
117
118                         l.append(s)
119
120                 for pos in range(len(l)):
121                         if not l[pos]:
122                                 s = fields[fields_order[pos]].get('size', 80) / 28 + 1
123                                 l[pos] = strmax * s / t
124
125                 _append_node('tableSize', ','.join(map(str,l)) )
126                 new_doc.childNodes[0].appendChild(config)
127                 header = new_doc.createElement("header")
128
129                 for f in fields_order:
130                         field = new_doc.createElement("field")
131                         field_txt = new_doc.createTextNode('%s' % (fields[f]['string'],))
132                         field.appendChild(field_txt)
133                         header.appendChild(field)
134
135                 new_doc.childNodes[0].appendChild(header)
136
137                 lines = new_doc.createElement("lines")
138
139                 tsum = []
140                 count = len(fields_order)
141                 for i in range(0,count):
142                         tsum.append(0)
143
144                 for line in results:
145                         node_line = new_doc.createElement("row")
146
147                         count = -1
148                         for f in fields_order:
149                                 count += 1
150                                 if fields[f]['type']=='many2one' and line[f]:
151                                         line[f] = line[f][1]
152                                 if fields[f]['type'] in ('one2many','many2many') and line[f]:
153                                         line[f] = '( '+str(len(line[f])) + ' )'
154                                 col = new_doc.createElement("col")
155                                 col.setAttribute('para','yes')
156                                 col.setAttribute('tree','no')
157                                 if line[f] != None:
158                                         txt = new_doc.createTextNode(str(line[f] or ''))
159                                         if temp[count] == 1:
160                                                 tsum[count] = tsum[count] + line[f];
161
162                                 else:
163                                         txt = new_doc.createTextNode('/')
164                                 col.appendChild(txt)
165                                 node_line.appendChild(col)
166                         lines.appendChild(node_line)
167                 node_line = new_doc.createElement("row")
168                 lines.appendChild(node_line)
169                 node_line = new_doc.createElement("row")
170                 for f in range(0,count):
171                         col = new_doc.createElement("col")
172                         col.setAttribute('para','yes')
173                         col.setAttribute('tree','no')
174                         if tsum[f] != None:
175                                 txt = new_doc.createTextNode(str(tsum[f] or ''))
176                         else:
177                                 txt = new_doc.createTextNode('/')
178                         if f == 0:
179                                 txt = new_doc.createTextNode('Total')
180
181                         col.appendChild(txt)
182                         node_line.appendChild(col)
183                 lines.appendChild(node_line)
184
185                 new_doc.childNodes[0].appendChild(lines)
186
187                 styledoc = libxml2.parseFile(os.path.join(tools.config['root_path'],'addons/base/report/custom_new.xsl'))
188                 style = libxslt.parseStylesheetDoc(styledoc)
189                 doc = libxml2.parseDoc(new_doc.toxml())
190                 rml_obj = style.applyStylesheet(doc, None)
191                 rml = style.saveResultToString(rml_obj)
192                 self.obj = render.rml(rml)
193                 self.obj.render()
194                 return True
195 report_printscreen_list('report.printscreen.list')
196