aspose-cells-foss 25.12.1__py3-none-any.whl → 26.2.2__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (93) hide show
  1. aspose_cells/__init__.py +88 -0
  2. aspose_cells/auto_filter.py +527 -0
  3. aspose_cells/cell.py +483 -0
  4. aspose_cells/cell_value_handler.py +319 -0
  5. aspose_cells/cells.py +779 -0
  6. aspose_cells/cfb_handler.py +445 -0
  7. aspose_cells/cfb_writer.py +659 -0
  8. aspose_cells/cfb_writer_minimal.py +337 -0
  9. aspose_cells/comment_xml.py +475 -0
  10. aspose_cells/conditional_format.py +1185 -0
  11. aspose_cells/csv_handler.py +690 -0
  12. aspose_cells/data_validation.py +911 -0
  13. aspose_cells/document_properties.py +356 -0
  14. aspose_cells/encryption_crypto.py +247 -0
  15. aspose_cells/encryption_params.py +138 -0
  16. aspose_cells/hyperlink.py +372 -0
  17. aspose_cells/json_handler.py +185 -0
  18. aspose_cells/markdown_handler.py +583 -0
  19. aspose_cells/shared_strings.py +101 -0
  20. aspose_cells/style.py +841 -0
  21. aspose_cells/workbook.py +499 -0
  22. aspose_cells/workbook_hash_password.py +68 -0
  23. aspose_cells/workbook_properties.py +712 -0
  24. aspose_cells/worksheet.py +570 -0
  25. aspose_cells/worksheet_properties.py +1239 -0
  26. aspose_cells/xlsx_encryptor.py +403 -0
  27. aspose_cells/xml_autofilter_loader.py +195 -0
  28. aspose_cells/xml_autofilter_saver.py +173 -0
  29. aspose_cells/xml_conditional_format_loader.py +215 -0
  30. aspose_cells/xml_conditional_format_saver.py +351 -0
  31. aspose_cells/xml_datavalidation_loader.py +239 -0
  32. aspose_cells/xml_datavalidation_saver.py +245 -0
  33. aspose_cells/xml_hyperlink_handler.py +323 -0
  34. aspose_cells/xml_loader.py +986 -0
  35. aspose_cells/xml_properties_loader.py +512 -0
  36. aspose_cells/xml_properties_saver.py +607 -0
  37. aspose_cells/xml_saver.py +1306 -0
  38. aspose_cells_foss-26.2.2.dist-info/METADATA +190 -0
  39. aspose_cells_foss-26.2.2.dist-info/RECORD +41 -0
  40. {aspose_cells_foss-25.12.1.dist-info → aspose_cells_foss-26.2.2.dist-info}/WHEEL +1 -1
  41. aspose_cells_foss-26.2.2.dist-info/top_level.txt +1 -0
  42. aspose/__init__.py +0 -14
  43. aspose/cells/__init__.py +0 -31
  44. aspose/cells/cell.py +0 -350
  45. aspose/cells/constants.py +0 -44
  46. aspose/cells/converters/__init__.py +0 -13
  47. aspose/cells/converters/csv_converter.py +0 -55
  48. aspose/cells/converters/json_converter.py +0 -46
  49. aspose/cells/converters/markdown_converter.py +0 -453
  50. aspose/cells/drawing/__init__.py +0 -17
  51. aspose/cells/drawing/anchor.py +0 -172
  52. aspose/cells/drawing/collection.py +0 -233
  53. aspose/cells/drawing/image.py +0 -338
  54. aspose/cells/formats.py +0 -80
  55. aspose/cells/formula/__init__.py +0 -10
  56. aspose/cells/formula/evaluator.py +0 -360
  57. aspose/cells/formula/functions.py +0 -433
  58. aspose/cells/formula/tokenizer.py +0 -340
  59. aspose/cells/io/__init__.py +0 -27
  60. aspose/cells/io/csv/__init__.py +0 -8
  61. aspose/cells/io/csv/reader.py +0 -88
  62. aspose/cells/io/csv/writer.py +0 -98
  63. aspose/cells/io/factory.py +0 -138
  64. aspose/cells/io/interfaces.py +0 -48
  65. aspose/cells/io/json/__init__.py +0 -8
  66. aspose/cells/io/json/reader.py +0 -126
  67. aspose/cells/io/json/writer.py +0 -119
  68. aspose/cells/io/md/__init__.py +0 -8
  69. aspose/cells/io/md/reader.py +0 -161
  70. aspose/cells/io/md/writer.py +0 -334
  71. aspose/cells/io/models.py +0 -64
  72. aspose/cells/io/xlsx/__init__.py +0 -9
  73. aspose/cells/io/xlsx/constants.py +0 -312
  74. aspose/cells/io/xlsx/image_writer.py +0 -311
  75. aspose/cells/io/xlsx/reader.py +0 -284
  76. aspose/cells/io/xlsx/writer.py +0 -931
  77. aspose/cells/plugins/__init__.py +0 -6
  78. aspose/cells/plugins/docling_backend/__init__.py +0 -7
  79. aspose/cells/plugins/docling_backend/backend.py +0 -535
  80. aspose/cells/plugins/markitdown_plugin/__init__.py +0 -15
  81. aspose/cells/plugins/markitdown_plugin/plugin.py +0 -128
  82. aspose/cells/range.py +0 -210
  83. aspose/cells/style.py +0 -287
  84. aspose/cells/utils/__init__.py +0 -54
  85. aspose/cells/utils/coordinates.py +0 -68
  86. aspose/cells/utils/exceptions.py +0 -43
  87. aspose/cells/utils/validation.py +0 -102
  88. aspose/cells/workbook.py +0 -352
  89. aspose/cells/worksheet.py +0 -670
  90. aspose_cells_foss-25.12.1.dist-info/METADATA +0 -189
  91. aspose_cells_foss-25.12.1.dist-info/RECORD +0 -53
  92. aspose_cells_foss-25.12.1.dist-info/entry_points.txt +0 -2
  93. aspose_cells_foss-25.12.1.dist-info/top_level.txt +0 -1
@@ -0,0 +1,512 @@
1
+ """
2
+ Aspose.Cells for Python - XML Properties Loader Module
3
+
4
+ This module provides classes for loading workbook and worksheet properties
5
+ from XML format according to ECMA-376 specification.
6
+
7
+ ECMA-376 Sections: 18.2 (Workbook), 18.3.1 (Worksheet)
8
+ """
9
+
10
+
11
+ class WorkbookPropertiesXMLLoader:
12
+ """
13
+ Handles loading workbook properties from XML format for .xlsx files.
14
+
15
+ Examples:
16
+ >>> loader = WorkbookPropertiesXMLLoader(namespaces)
17
+ >>> loader.load_file_version(workbook.properties.file_version, root)
18
+ """
19
+
20
+ def __init__(self, namespaces):
21
+ """
22
+ Initializes a new instance of the WorkbookPropertiesXMLLoader class.
23
+
24
+ Args:
25
+ namespaces: XML namespaces dictionary for parsing.
26
+ """
27
+ self.ns = namespaces
28
+
29
+ def load_file_version(self, file_version, root):
30
+ """
31
+ Loads file version from XML.
32
+
33
+ ECMA-376 Section: 18.2.10
34
+
35
+ Args:
36
+ file_version: FileVersion object to load into.
37
+ root: XML root element.
38
+ """
39
+ elem = root.find('main:fileVersion', namespaces=self.ns)
40
+ if elem is None:
41
+ return
42
+
43
+ if elem.get('appName'):
44
+ file_version._app_name = elem.get('appName')
45
+ if elem.get('lastEdited'):
46
+ file_version._last_edited = int(elem.get('lastEdited'))
47
+ if elem.get('lowestEdited'):
48
+ file_version._lowest_edited = int(elem.get('lowestEdited'))
49
+ if elem.get('rupBuild'):
50
+ file_version._rup_build = int(elem.get('rupBuild'))
51
+
52
+ def load_workbook_protection(self, protection, root):
53
+ """
54
+ Loads workbook protection from XML.
55
+
56
+ ECMA-376 Section: 18.2.29
57
+
58
+ Args:
59
+ protection: WorkbookProtection object to load into.
60
+ root: XML root element.
61
+ """
62
+ elem = root.find('main:workbookProtection', namespaces=self.ns)
63
+ if elem is None:
64
+ return
65
+
66
+ protection._lock_structure = elem.get('lockStructure') == '1'
67
+ protection._lock_windows = elem.get('lockWindows') == '1'
68
+ protection._lock_revision = elem.get('lockRevision') == '1'
69
+ if elem.get('workbookPassword'):
70
+ protection._workbook_password = elem.get('workbookPassword')
71
+ if elem.get('revisionsPassword'):
72
+ protection._revisions_password = elem.get('revisionsPassword')
73
+
74
+ def load_workbook_pr(self, workbook_pr, root):
75
+ """
76
+ Loads workbook properties (workbookPr) from XML.
77
+
78
+ ECMA-376 Section: 18.2.13
79
+
80
+ Args:
81
+ workbook_pr: WorkbookPr object to load into.
82
+ root: XML root element.
83
+ """
84
+ elem = root.find('main:workbookPr', namespaces=self.ns)
85
+ if elem is None:
86
+ return
87
+
88
+ workbook_pr._date1904 = elem.get('date1904') == '1'
89
+ if elem.get('codeName'):
90
+ workbook_pr._code_name = elem.get('codeName')
91
+ if elem.get('showObjects'):
92
+ workbook_pr._show_objects = elem.get('showObjects')
93
+ workbook_pr._filter_privacy = elem.get('filterPrivacy') == '1'
94
+ if elem.get('showBorderUnselectedTables') is not None:
95
+ workbook_pr._show_border_unselected_tables = elem.get('showBorderUnselectedTables') != '0'
96
+ if elem.get('showInkAnnotation') is not None:
97
+ workbook_pr._show_ink_annotation = elem.get('showInkAnnotation') != '0'
98
+ workbook_pr._backup_file = elem.get('backupFile') == '1'
99
+ if elem.get('saveExternalLinkValues') is not None:
100
+ workbook_pr._save_external_link_values = elem.get('saveExternalLinkValues') != '0'
101
+ if elem.get('updateLinks'):
102
+ workbook_pr._update_links = elem.get('updateLinks')
103
+ workbook_pr._hide_pivot_field_list = elem.get('hidePivotFieldList') == '1'
104
+ if elem.get('defaultThemeVersion'):
105
+ workbook_pr._default_theme_version = int(elem.get('defaultThemeVersion'))
106
+
107
+ def load_book_views(self, view, root):
108
+ """
109
+ Loads book views from XML.
110
+
111
+ ECMA-376 Section: 18.2.1, 18.2.30
112
+
113
+ Args:
114
+ view: WorkbookView object to load into.
115
+ root: XML root element.
116
+ """
117
+ book_views = root.find('main:bookViews', namespaces=self.ns)
118
+ if book_views is None:
119
+ return
120
+
121
+ wb_view = book_views.find('main:workbookView', namespaces=self.ns)
122
+ if wb_view is None:
123
+ return
124
+
125
+ if wb_view.get('xWindow'):
126
+ view._x_window = int(wb_view.get('xWindow'))
127
+ if wb_view.get('yWindow'):
128
+ view._y_window = int(wb_view.get('yWindow'))
129
+ if wb_view.get('windowWidth'):
130
+ view._window_width = int(wb_view.get('windowWidth'))
131
+ if wb_view.get('windowHeight'):
132
+ view._window_height = int(wb_view.get('windowHeight'))
133
+ if wb_view.get('activeTab'):
134
+ view._active_tab = int(wb_view.get('activeTab'))
135
+ if wb_view.get('firstSheet'):
136
+ view._first_sheet = int(wb_view.get('firstSheet'))
137
+
138
+ view._show_horizontal_scroll = wb_view.get('showHorizontalScroll', '1') != '0'
139
+ view._show_vertical_scroll = wb_view.get('showVerticalScroll', '1') != '0'
140
+ view._show_sheet_tabs = wb_view.get('showSheetTabs', '1') != '0'
141
+
142
+ if wb_view.get('tabRatio'):
143
+ view._tab_ratio = int(wb_view.get('tabRatio'))
144
+ view._minimized = wb_view.get('minimized') == '1'
145
+ if wb_view.get('visibility'):
146
+ view._visibility = wb_view.get('visibility')
147
+
148
+ def load_calc_pr(self, calculation, root):
149
+ """
150
+ Loads calculation properties from XML.
151
+
152
+ ECMA-376 Section: 18.2.2
153
+
154
+ Args:
155
+ calculation: CalculationProperties object to load into.
156
+ root: XML root element.
157
+ """
158
+ elem = root.find('main:calcPr', namespaces=self.ns)
159
+ if elem is None:
160
+ return
161
+
162
+ if elem.get('calcId'):
163
+ calculation._calc_id = int(elem.get('calcId'))
164
+ if elem.get('calcMode'):
165
+ calculation._calc_mode = elem.get('calcMode')
166
+ calculation._full_calc_on_load = elem.get('fullCalcOnLoad') == '1'
167
+ if elem.get('refMode'):
168
+ calculation._ref_mode = elem.get('refMode')
169
+ calculation._iterate = elem.get('iterate') == '1'
170
+ if elem.get('iterateCount'):
171
+ calculation._iterate_count = int(elem.get('iterateCount'))
172
+ if elem.get('iterateDelta'):
173
+ calculation._iterate_delta = float(elem.get('iterateDelta'))
174
+ calculation._full_precision = elem.get('fullPrecision', '1') != '0'
175
+ calculation._calc_on_save = elem.get('calcOnSave', '1') != '0'
176
+ calculation._concurrent_calc = elem.get('concurrentCalc', '1') != '0'
177
+ calculation._calc_completed = elem.get('calcCompleted', '1') != '0'
178
+ calculation._force_full_calc = elem.get('forceFullCalc') == '1'
179
+
180
+ def load_defined_names(self, defined_names, root):
181
+ """
182
+ Loads defined names from XML.
183
+
184
+ ECMA-376 Section: 18.2.6
185
+
186
+ Args:
187
+ defined_names: DefinedNameCollection object to load into.
188
+ root: XML root element.
189
+ """
190
+ from .workbook_properties import DefinedName
191
+
192
+ dn_container = root.find('main:definedNames', namespaces=self.ns)
193
+ if dn_container is None:
194
+ return
195
+
196
+ for dn_elem in dn_container.findall('main:definedName', namespaces=self.ns):
197
+ name = dn_elem.get('name')
198
+ refers_to = dn_elem.text or ''
199
+
200
+ local_sheet_id = None
201
+ if dn_elem.get('localSheetId'):
202
+ local_sheet_id = int(dn_elem.get('localSheetId'))
203
+
204
+ dn = DefinedName(name, refers_to, local_sheet_id)
205
+ dn._hidden = dn_elem.get('hidden') == '1'
206
+ dn._comment = dn_elem.get('comment')
207
+
208
+ defined_names._names.append(dn)
209
+
210
+
211
+ class WorksheetPropertiesXMLLoader:
212
+ """
213
+ Handles loading worksheet properties from XML format for .xlsx files.
214
+
215
+ Examples:
216
+ >>> loader = WorksheetPropertiesXMLLoader(namespaces)
217
+ >>> loader.load_sheet_views(worksheet.properties, root)
218
+ """
219
+
220
+ def __init__(self, namespaces):
221
+ """
222
+ Initializes a new instance of the WorksheetPropertiesXMLLoader class.
223
+
224
+ Args:
225
+ namespaces: XML namespaces dictionary for parsing.
226
+ """
227
+ self.ns = namespaces
228
+
229
+ def load_sheet_views(self, properties, root):
230
+ """
231
+ Loads sheet views from XML.
232
+
233
+ ECMA-376 Section: 18.3.1.88, 18.3.1.87
234
+
235
+ Args:
236
+ properties: WorksheetProperties object to load into.
237
+ root: XML root element.
238
+ """
239
+ sheet_views = root.find('main:sheetViews', namespaces=self.ns)
240
+ if sheet_views is None:
241
+ return
242
+
243
+ sheet_view = sheet_views.find('main:sheetView', namespaces=self.ns)
244
+ if sheet_view is None:
245
+ return
246
+
247
+ view = properties.view
248
+ view._show_formulas = sheet_view.get('showFormulas') == '1'
249
+ view._show_grid_lines = sheet_view.get('showGridLines', '1') != '0'
250
+ view._show_row_col_headers = sheet_view.get('showRowColHeaders', '1') != '0'
251
+ view._show_zeros = sheet_view.get('showZeros', '1') != '0'
252
+ view._right_to_left = sheet_view.get('rightToLeft') == '1'
253
+ view._tab_selected = sheet_view.get('tabSelected') == '1'
254
+ view._show_ruler = sheet_view.get('showRuler', '1') != '0'
255
+ view._show_outline_symbols = sheet_view.get('showOutlineSymbols', '1') != '0'
256
+ view._default_grid_color = sheet_view.get('defaultGridColor', '1') != '0'
257
+ view._show_white_space = sheet_view.get('showWhiteSpace', '1') != '0'
258
+ view._window_protection = sheet_view.get('windowProtection') == '1'
259
+
260
+ if sheet_view.get('view'):
261
+ view._view = sheet_view.get('view')
262
+ if sheet_view.get('topLeftCell'):
263
+ view._top_left_cell = sheet_view.get('topLeftCell')
264
+ if sheet_view.get('colorId'):
265
+ view._color_id = int(sheet_view.get('colorId'))
266
+ if sheet_view.get('zoomScale'):
267
+ view._zoom_scale = int(sheet_view.get('zoomScale'))
268
+ if sheet_view.get('zoomScaleNormal'):
269
+ view._zoom_scale_normal = int(sheet_view.get('zoomScaleNormal'))
270
+ if sheet_view.get('zoomScaleSheetLayoutView'):
271
+ view._zoom_scale_sheet_layout_view = int(sheet_view.get('zoomScaleSheetLayoutView'))
272
+ if sheet_view.get('zoomScalePageLayoutView'):
273
+ view._zoom_scale_page_layout_view = int(sheet_view.get('zoomScalePageLayoutView'))
274
+ if sheet_view.get('workbookViewId'):
275
+ view._workbook_view_id = int(sheet_view.get('workbookViewId'))
276
+
277
+ # Load pane
278
+ pane_elem = sheet_view.find('main:pane', namespaces=self.ns)
279
+ if pane_elem is not None:
280
+ pane = properties.pane
281
+ if pane_elem.get('xSplit'):
282
+ pane._x_split = float(pane_elem.get('xSplit'))
283
+ if pane_elem.get('ySplit'):
284
+ pane._y_split = float(pane_elem.get('ySplit'))
285
+ if pane_elem.get('topLeftCell'):
286
+ pane._top_left_cell = pane_elem.get('topLeftCell')
287
+ if pane_elem.get('activePane'):
288
+ pane._active_pane = pane_elem.get('activePane')
289
+ if pane_elem.get('state'):
290
+ pane._state = pane_elem.get('state')
291
+
292
+ # Load selection
293
+ selection_elem = sheet_view.find('main:selection', namespaces=self.ns)
294
+ if selection_elem is not None:
295
+ selection = properties.selection
296
+ if selection_elem.get('pane'):
297
+ selection._pane = selection_elem.get('pane')
298
+ if selection_elem.get('activeCell'):
299
+ selection._active_cell = selection_elem.get('activeCell')
300
+ if selection_elem.get('sqref'):
301
+ selection._sqref = selection_elem.get('sqref')
302
+
303
+ def load_sheet_format_pr(self, properties, root):
304
+ """
305
+ Loads sheet format properties from XML.
306
+
307
+ ECMA-376 Section: 18.3.1.82
308
+
309
+ Args:
310
+ properties: WorksheetProperties object to load into.
311
+ root: XML root element.
312
+ """
313
+ elem = root.find('main:sheetFormatPr', namespaces=self.ns)
314
+ if elem is None:
315
+ return
316
+
317
+ format_props = properties.format
318
+ if elem.get('baseColWidth'):
319
+ format_props._base_col_width = int(elem.get('baseColWidth'))
320
+ if elem.get('defaultColWidth'):
321
+ format_props._default_col_width = float(elem.get('defaultColWidth'))
322
+ if elem.get('defaultRowHeight'):
323
+ format_props._default_row_height = float(elem.get('defaultRowHeight'))
324
+ format_props._custom_height = elem.get('customHeight') == '1'
325
+ format_props._zero_height = elem.get('zeroHeight') == '1'
326
+ format_props._thick_top = elem.get('thickTop') == '1'
327
+ format_props._thick_bottom = elem.get('thickBottom') == '1'
328
+ if elem.get('outlineLevelRow'):
329
+ format_props._outline_level_row = int(elem.get('outlineLevelRow'))
330
+ if elem.get('outlineLevelCol'):
331
+ format_props._outline_level_col = int(elem.get('outlineLevelCol'))
332
+
333
+ def load_sheet_protection(self, properties, root):
334
+ """
335
+ Loads sheet protection from XML.
336
+
337
+ ECMA-376 Section: 18.3.1.85
338
+
339
+ Args:
340
+ properties: WorksheetProperties object to load into.
341
+ root: XML root element.
342
+ """
343
+ elem = root.find('main:sheetProtection', namespaces=self.ns)
344
+ if elem is None:
345
+ return
346
+
347
+ prot = properties.protection
348
+ prot._sheet = elem.get('sheet') == '1'
349
+ prot._objects = elem.get('objects') == '1'
350
+ prot._scenarios = elem.get('scenarios') == '1'
351
+ prot._format_cells = elem.get('formatCells', '1') != '0'
352
+ prot._format_columns = elem.get('formatColumns', '1') != '0'
353
+ prot._format_rows = elem.get('formatRows', '1') != '0'
354
+ prot._insert_columns = elem.get('insertColumns', '1') != '0'
355
+ prot._insert_rows = elem.get('insertRows', '1') != '0'
356
+ prot._insert_hyperlinks = elem.get('insertHyperlinks', '1') != '0'
357
+ prot._delete_columns = elem.get('deleteColumns', '1') != '0'
358
+ prot._delete_rows = elem.get('deleteRows', '1') != '0'
359
+ prot._select_locked_cells = elem.get('selectLockedCells') == '1'
360
+ prot._sort = elem.get('sort', '1') != '0'
361
+ prot._auto_filter = elem.get('autoFilter', '1') != '0'
362
+ prot._pivot_tables = elem.get('pivotTables', '1') != '0'
363
+ prot._select_unlocked_cells = elem.get('selectUnlockedCells') == '1'
364
+ if elem.get('password'):
365
+ prot._password = elem.get('password')
366
+ if elem.get('algorithmName'):
367
+ prot._algorithm_name = elem.get('algorithmName')
368
+ if elem.get('hashValue'):
369
+ prot._hash_value = elem.get('hashValue')
370
+ if elem.get('saltValue'):
371
+ prot._salt_value = elem.get('saltValue')
372
+ if elem.get('spinCount'):
373
+ prot._spin_count = int(elem.get('spinCount'))
374
+
375
+ def load_print_options(self, properties, root):
376
+ """
377
+ Loads print options from XML.
378
+
379
+ ECMA-376 Section: 18.3.1.70
380
+
381
+ Args:
382
+ properties: WorksheetProperties object to load into.
383
+ root: XML root element.
384
+ """
385
+ elem = root.find('main:printOptions', namespaces=self.ns)
386
+ if elem is None:
387
+ return
388
+
389
+ print_opts = properties.print_options
390
+ print_opts._print_headings = elem.get('headings') == '1'
391
+ print_opts._print_grid_lines = elem.get('gridLines') == '1'
392
+ print_opts._horizontal_centered = elem.get('horizontalCentered') == '1'
393
+ print_opts._vertical_centered = elem.get('verticalCentered') == '1'
394
+ print_opts._black_and_white = elem.get('blackAndWhite') == '1'
395
+ print_opts._draft_quality = elem.get('draft') == '1'
396
+ if elem.get('comments'):
397
+ print_opts._cell_comments = elem.get('comments')
398
+ if elem.get('errors'):
399
+ print_opts._print_errors = elem.get('errors')
400
+
401
+ def load_page_margins(self, properties, root):
402
+ """
403
+ Loads page margins from XML.
404
+
405
+ ECMA-376 Section: 18.3.1.62
406
+
407
+ Args:
408
+ properties: WorksheetProperties object to load into.
409
+ root: XML root element.
410
+ """
411
+ elem = root.find('main:pageMargins', namespaces=self.ns)
412
+ if elem is None:
413
+ return
414
+
415
+ margins = properties.page_margins
416
+ if elem.get('left'):
417
+ margins._left = float(elem.get('left'))
418
+ if elem.get('right'):
419
+ margins._right = float(elem.get('right'))
420
+ if elem.get('top'):
421
+ margins._top = float(elem.get('top'))
422
+ if elem.get('bottom'):
423
+ margins._bottom = float(elem.get('bottom'))
424
+ if elem.get('header'):
425
+ margins._header = float(elem.get('header'))
426
+ if elem.get('footer'):
427
+ margins._footer = float(elem.get('footer'))
428
+
429
+ def load_page_setup(self, properties, root):
430
+ """
431
+ Loads page setup from XML.
432
+
433
+ ECMA-376 Section: 18.3.1.63
434
+
435
+ Args:
436
+ properties: WorksheetProperties object to load into.
437
+ root: XML root element.
438
+ """
439
+ elem = root.find('main:pageSetup', namespaces=self.ns)
440
+ if elem is None:
441
+ return
442
+
443
+ page_setup = properties.page_setup
444
+ if elem.get('paperSize'):
445
+ page_setup._paper_size = int(elem.get('paperSize'))
446
+ if elem.get('scale'):
447
+ page_setup._scale = int(elem.get('scale'))
448
+ if elem.get('firstPageNumber'):
449
+ page_setup._first_page_number = int(elem.get('firstPageNumber'))
450
+ if elem.get('fitToWidth'):
451
+ page_setup._fit_to_width = int(elem.get('fitToWidth'))
452
+ if elem.get('fitToHeight'):
453
+ page_setup._fit_to_height = int(elem.get('fitToHeight'))
454
+ if elem.get('pageOrder'):
455
+ page_setup._page_order = elem.get('pageOrder')
456
+ if elem.get('orientation'):
457
+ page_setup._orientation = elem.get('orientation')
458
+ if elem.get('usePrinterDefaults') is not None:
459
+ page_setup._use_printer_defaults = elem.get('usePrinterDefaults') != '0'
460
+ page_setup._black_and_white = elem.get('blackAndWhite') == '1'
461
+ page_setup._draft = elem.get('draft') == '1'
462
+ if elem.get('comments'):
463
+ page_setup._cell_comments = elem.get('comments')
464
+ if elem.get('useFirstPageNumber') == '1' and page_setup._first_page_number is None:
465
+ page_setup._first_page_number = 1
466
+ if elem.get('errors'):
467
+ page_setup._errors = elem.get('errors')
468
+ if elem.get('horizontalDpi'):
469
+ page_setup._horizontal_dpi = int(elem.get('horizontalDpi'))
470
+ if elem.get('verticalDpi'):
471
+ page_setup._vertical_dpi = int(elem.get('verticalDpi'))
472
+ if elem.get('copies'):
473
+ page_setup._copies = int(elem.get('copies'))
474
+
475
+ def load_header_footer(self, properties, root):
476
+ """
477
+ Loads header/footer from XML.
478
+
479
+ ECMA-376 Section: 18.3.1.46
480
+
481
+ Args:
482
+ properties: WorksheetProperties object to load into.
483
+ root: XML root element.
484
+ """
485
+ elem = root.find('main:headerFooter', namespaces=self.ns)
486
+ if elem is None:
487
+ return
488
+
489
+ hf = properties.header_footer
490
+ hf._different_first = elem.get('differentFirst') == '1'
491
+ hf._different_odd_even = elem.get('differentOddEven') == '1'
492
+ hf._scale_with_doc = elem.get('scaleWithDoc', '1') != '0'
493
+ hf._align_with_margins = elem.get('alignWithMargins', '1') != '0'
494
+
495
+ odd_header = elem.find('main:oddHeader', namespaces=self.ns)
496
+ if odd_header is not None and odd_header.text:
497
+ hf._odd_header = odd_header.text
498
+ odd_footer = elem.find('main:oddFooter', namespaces=self.ns)
499
+ if odd_footer is not None and odd_footer.text:
500
+ hf._odd_footer = odd_footer.text
501
+ even_header = elem.find('main:evenHeader', namespaces=self.ns)
502
+ if even_header is not None and even_header.text:
503
+ hf._even_header = even_header.text
504
+ even_footer = elem.find('main:evenFooter', namespaces=self.ns)
505
+ if even_footer is not None and even_footer.text:
506
+ hf._even_footer = even_footer.text
507
+ first_header = elem.find('main:firstHeader', namespaces=self.ns)
508
+ if first_header is not None and first_header.text:
509
+ hf._first_header = first_header.text
510
+ first_footer = elem.find('main:firstFooter', namespaces=self.ns)
511
+ if first_footer is not None and first_footer.text:
512
+ hf._first_footer = first_footer.text