auf-libreoffice-extension 1204.5
[macros-openoffice.git] / auf-libreoffice-extension / extension / calc2moin.py
1 #!
2 # -*- coding: utf-8 -*-
3 """
4 Macro pour faciliter l'intégration des données d'une feuille de calcul
5 vers un wiki MoinMoin.
6
7 Copyright : Agence universitaire de la Francophonie
8 Licence : GNU General Public Licence, version 2
9 Auteur : Jean Christophe André
10 Date de création : septembre 2009
11 """
12 import uno
13 import unohelper
14 from com.sun.star.task import XJobExecutor
15 from com.sun.star.beans import PropertyValue
16 from com.sun.star.table.CellContentType import EMPTY, VALUE, TEXT, FORMULA
17 from com.sun.star.table.CellHoriJustify import STANDARD, LEFT, CENTER, RIGHT
18 from com.sun.star.table.CellVertJustify import STANDARD, TOP, CENTER as MIDDLE, BOTTOM
19 from com.sun.star.awt.FontWeight import DONTKNOW, NORMAL, BOLD
20
21 _settings = {
22 'MoinMoinOldStyle': True,
23 'MoinMoinVertOnMulti': True,
24 }
25
26 def getRangeSize(sheet, cursor):
27 r = cursor.getRangeAddress()
28 realRange = sheet.getCellRangeByPosition(r.StartColumn, r.StartRow,
29 r.EndColumn, r.EndRow)
30 return (realRange.Columns.Count, realRange.Rows.Count)
31
32 def getCellRealPosition(cursor, column, row):
33 r = cursor.getRangeAddress()
34 return (r.StartColumn + column, r.StartRow + row)
35
36 def cell2moin(cell):
37 global _settings
38 cell_string = cell.getString()
39 if not cell_string: return ''
40 cell_string = cell_string.replace('\n','<<BR>>')
41 if _settings['MoinMoinOldStyle']:
42 if hasattr(cell, 'CharWeight') and cell.CharWeight == BOLD:
43 cell_string = "'''%s'''" % cell_string
44 return cell_string
45
46 def calc2moin(ctx):
47 global _settings
48 data = list()
49
50 # récupération du document en cours, vérification du type Spreadsheet
51 smgr = ctx.ServiceManager
52 desktop = smgr.createInstanceWithContext(
53 "com.sun.star.frame.Desktop", ctx)
54 curdoc = desktop.getCurrentComponent()
55 if not curdoc.supportsService("com.sun.star.sheet.SpreadsheetDocument"):
56 raise RuntimeError, u"Ce n'est pas un document de type Spreadsheet (Calc)."
57 controller = curdoc.getCurrentController()
58 sheet = controller.getActiveSheet()
59 #open('/tmp/calc2moin.log','a').write('sheet=[%s]\n' % ', '.join(dir(sheet)))
60
61 # localisation de la la zone déjà utilisée
62 cursor = sheet.createCursor()
63 cursor.gotoEndOfUsedArea(False)
64 cursor.gotoStartOfUsedArea(True)
65 columns, rows = getRangeSize(sheet, cursor)
66 for row in range(rows):
67 row_data = list()
68 row_has_multiline_cell = False
69 column = 0
70 while column < columns:
71 cell = cursor.getCellByPosition(column, row)
72 cell_type = cell.getType()
73 cell_string = cell.getString()
74 if not row_has_multiline_cell:
75 row_has_multiline_cell = '\n' in cell_string
76 # calcul de l'étendue de la cellule courante
77 if cell.getIsMerged():
78 c, r = getCellRealPosition(cursor, column, row)
79 cellRange = sheet.getCellRangeByPosition(c, r, c, r)
80 cursor2 = sheet.createCursorByRange(cellRange)
81 cursor2.collapseToMergedArea()
82 cell_colspan, cell_rowspan = getRangeSize(sheet, cursor2)
83 #open('/tmp/calc2moin.log','a').write('Merged(%d,%d)=[%d,%d]\n' % (column,row,cell_colspan,cell_rowspan))
84 else:
85 cell_colspan, cell_rowspan = 1, 1
86 # traitement des attributs et styles de la cellule
87 cell_attributes = list()
88 cell_styles = list()
89 if cell_string and hasattr(cell, 'HoriJustify'):
90 horiJustify = cell.getPropertyValue('HoriJustify')
91 if horiJustify == LEFT:
92 if cell_colspan > 1 or cell_rowspan > 1:
93 text_align = 'left'
94 text_align_old = '('
95 else:
96 text_align = '' # left par défaut si span == 1
97 text_align_old = ''
98 elif horiJustify == CENTER:
99 if cell_colspan == 1 and cell_rowspan == 1:
100 text_align = 'center'
101 text_align_old = ':'
102 else:
103 text_align = '' # center par défaut si span > 1
104 text_align_old = ''
105 elif horiJustify == RIGHT:
106 text_align = 'right'
107 text_align_old = ')'
108 else:
109 if cell_type == TEXT:
110 if cell_colspan > 1 or cell_rowspan > 1:
111 text_align = 'left'
112 text_align_old = '('
113 else:
114 text_align = '' # left par défaut si span == 1
115 text_align_old = ''
116 elif cell_type != EMPTY:
117 text_align = 'right'
118 text_align_old = ')'
119 if text_align:
120 if _settings['MoinMoinOldStyle']:
121 cell_attributes.append(text_align_old)
122 else:
123 cell_styles.append('text-align: ' + text_align)
124 if cell_string and hasattr(cell, 'VertJustify') and \
125 (row_has_multiline_cell or not _settings['MoinMoinVertOnMulti']):
126 vertJustify = cell.getPropertyValue('VertJustify')
127 if vertJustify == 1: #TOP(1)
128 vertical_align = 'top'
129 vertical_align_old = '^'
130 elif vertJustify == 2: #MIDDLE(2)
131 vertical_align = '' # middle par défaut
132 vertical_align_old = ''
133 else: #STANDARD(0), BOTTOM(3)
134 vertical_align = 'bottom'
135 vertical_align_old = 'v'
136 if vertical_align:
137 if _settings['MoinMoinOldStyle']:
138 cell_attributes.append(vertical_align_old)
139 else:
140 cell_styles.append('vertical-align: ' + vertical_align)
141 if cell_string and hasattr(cell, 'CharWeight'):
142 charWeight = cell.getPropertyValue('CharWeight')
143 if charWeight == BOLD and not _settings['MoinMoinOldStyle']:
144 cell_styles.append('font-weight: bold')
145 if cell_rowspan > 1:
146 cell_attributes.append('|%d' % cell_rowspan)
147 if cell_colspan > 1:
148 cell_attributes.append('-%d' % cell_colspan)
149 if hasattr(cell, 'CellBackColor'):
150 color = cell.getPropertyValue('CellBackColor')
151 if color >= 0:
152 if _settings['MoinMoinOldStyle']:
153 cell_attributes.append('#%06x' % color)
154 else:
155 cell_styles.append('background: #%06x' % color)
156 if hasattr(cell, 'CharColor'):
157 color = cell.getPropertyValue('CharColor')
158 if color >= 0:
159 cell_styles.append('color: #%06x' % color)
160 # compilation des styles de la cellule
161 if cell_styles:
162 cell_attributes.insert(0, 'style="%s;"' % '; '.join(cell_styles))
163 # ajout de la définition de la cellule à la ligne courante
164 cell_data = list()
165 if cell_attributes:
166 cell_data.append('<' + ''.join(cell_attributes) + '>')
167 if cell_string:
168 cell_data.append(cell2moin(cell))
169 else:
170 cell_data.append(' ')
171 row_data.append(''.join(cell_data))
172 column += cell_colspan
173 # display row's code
174 data.append('||' + '||'.join(row_data) + '||')
175
176 #
177 # création d'un document Writer pour écrire le code MoinMoin
178 #
179 # ouverture d'un document Writer caché
180 hidden = PropertyValue()
181 hidden.Name = "Hidden"
182 hidden.Value = True
183 doc = desktop.loadComponentFromURL(
184 "private:factory/swriter", "_blank", 0, (hidden, ) )
185 text = doc.Text
186 textcursor = text.createTextCursor()
187 text.insertString(textcursor, '\n'.join(data) + '\n', 0)
188 # on copie ça dans le presse papier
189 dispatcher = smgr.createInstanceWithContext(
190 "com.sun.star.frame.DispatchHelper", ctx)
191 frame = doc.getCurrentController().getFrame()
192 dispatcher.executeDispatch(frame, ".uno:SelectAll", "", 0, ())
193 dispatcher.executeDispatch(frame, ".uno:Copy", "", 0, ())
194 doc.close(True)
195
196 ##############################################################################
197
198 def copier(event=False):
199 u"""Copier une feuille de calcul vers un wiki MoinMoin."""
200 ctx = uno.getComponentContext()
201 calc2moin(ctx)
202 return None
203
204 # lists the scripts, that shall be visible inside OOo. Can be omited, if
205 # all functions shall be visible, however here getNewString shall be surpressed
206 g_exportedScripts = (copier, )
207
208 ##############################################################################
209
210 class CopierJob(unohelper.Base, XJobExecutor):
211 def __init__(self, context):
212 self._context = context
213 self._readConfig()
214
215 def _readConfig(self):
216 cfgprov = self._context.ServiceManager.createInstanceWithContext(
217 "com.sun.star.configuration.ConfigurationProvider", self._context)
218 node = PropertyValue()
219 node.Name = "nodepath"
220 node.Value = "/org.auf.openoffice.macros/General"
221 ConfigReader = cfgprov.createInstanceWithArguments(
222 "com.sun.star.configuration.ConfigurationAccess", (node,))
223 cfgnames = ("MoinMoinOldStyle", "MoinMoinVertOnMulti", )
224 cfgvalues = ConfigReader.getPropertyValues(cfgnames)
225 if not cfgvalues:
226 raise RuntimeError("Unable to read the configuration.")
227 global _settings
228 _settings = dict(zip(cfgnames, cfgvalues))
229
230 def trigger(self, args):
231 calc2moin(self._context)
232
233 g_ImplementationHelper = unohelper.ImplementationHelper()
234 g_ImplementationHelper.addImplementation( \
235 CopierJob, "org.auf.openoffice.calc2moin.Copier", \
236 ("com.sun.star.task.Job",),)