axlsx 2.0.1 → 2.1.0.pre
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.
- checksums.yaml +4 -4
- data/README.md +6 -3
- data/Rakefile +9 -10
- data/examples/IMAGE1UP.JPEG +0 -0
- data/examples/auto_filter.rb +10 -1
- data/examples/conditional_formatting/example_conditional_formatting.rb +3 -3
- data/examples/example.rb +72 -4
- data/examples/merge_cells.rb +17 -0
- data/examples/no_grid_with_borders.rb +18 -0
- data/examples/pivot_test.rb +63 -0
- data/examples/split.rb +16 -0
- data/lib/axlsx.rb +30 -16
- data/lib/axlsx/content_type/abstract_content_type.rb +1 -1
- data/lib/axlsx/content_type/content_type.rb +1 -1
- data/lib/axlsx/doc_props/app.rb +1 -1
- data/lib/axlsx/doc_props/core.rb +5 -5
- data/lib/axlsx/drawing/axes.rb +1 -1
- data/lib/axlsx/drawing/axis.rb +12 -9
- data/lib/axlsx/drawing/bar_3D_chart.rb +13 -13
- data/lib/axlsx/drawing/bar_series.rb +9 -9
- data/lib/axlsx/drawing/bubble_chart.rb +59 -0
- data/lib/axlsx/drawing/bubble_series.rb +63 -0
- data/lib/axlsx/drawing/cat_axis.rb +5 -5
- data/lib/axlsx/drawing/chart.rb +44 -7
- data/lib/axlsx/drawing/drawing.rb +3 -1
- data/lib/axlsx/drawing/graphic_frame.rb +3 -3
- data/lib/axlsx/drawing/hyperlink.rb +1 -3
- data/lib/axlsx/drawing/line_3D_chart.rb +2 -2
- data/lib/axlsx/drawing/line_chart.rb +10 -10
- data/lib/axlsx/drawing/line_series.rb +14 -2
- data/lib/axlsx/drawing/marker.rb +1 -1
- data/lib/axlsx/drawing/num_data.rb +4 -4
- data/lib/axlsx/drawing/num_data_source.rb +6 -6
- data/lib/axlsx/drawing/num_val.rb +1 -1
- data/lib/axlsx/drawing/one_cell_anchor.rb +1 -1
- data/lib/axlsx/drawing/pic.rb +2 -3
- data/lib/axlsx/drawing/picture_locking.rb +1 -3
- data/lib/axlsx/drawing/pie_3D_chart.rb +5 -6
- data/lib/axlsx/drawing/pie_series.rb +6 -6
- data/lib/axlsx/drawing/scaling.rb +4 -4
- data/lib/axlsx/drawing/scatter_chart.rb +10 -10
- data/lib/axlsx/drawing/scatter_series.rb +26 -7
- data/lib/axlsx/drawing/ser_axis.rb +2 -2
- data/lib/axlsx/drawing/series.rb +3 -3
- data/lib/axlsx/drawing/series_title.rb +2 -2
- data/lib/axlsx/drawing/str_data.rb +3 -3
- data/lib/axlsx/drawing/str_val.rb +1 -1
- data/lib/axlsx/drawing/title.rb +3 -3
- data/lib/axlsx/drawing/val_axis.rb +1 -1
- data/lib/axlsx/drawing/vml_drawing.rb +1 -1
- data/lib/axlsx/package.rb +39 -28
- data/lib/axlsx/rels/relationship.rb +1 -1
- data/lib/axlsx/rels/relationships.rb +2 -2
- data/lib/axlsx/stylesheet/border_pr.rb +2 -2
- data/lib/axlsx/stylesheet/cell_alignment.rb +1 -3
- data/lib/axlsx/stylesheet/cell_protection.rb +1 -3
- data/lib/axlsx/stylesheet/cell_style.rb +1 -3
- data/lib/axlsx/stylesheet/color.rb +1 -3
- data/lib/axlsx/stylesheet/font.rb +1 -1
- data/lib/axlsx/stylesheet/gradient_stop.rb +1 -1
- data/lib/axlsx/stylesheet/num_fmt.rb +1 -3
- data/lib/axlsx/stylesheet/pattern_fill.rb +1 -1
- data/lib/axlsx/stylesheet/styles.rb +6 -6
- data/lib/axlsx/stylesheet/table_style_element.rb +1 -3
- data/lib/axlsx/util/accessors.rb +6 -6
- data/lib/axlsx/util/constants.rb +106 -101
- data/lib/axlsx/util/options_parser.rb +2 -1
- data/lib/axlsx/util/parser.rb +4 -4
- data/lib/axlsx/util/serialized_attributes.rb +16 -6
- data/lib/axlsx/util/simple_typed_list.rb +28 -52
- data/lib/axlsx/util/storage.rb +4 -4
- data/lib/axlsx/util/string.rb +7 -0
- data/lib/axlsx/util/validators.rb +20 -13
- data/lib/axlsx/version.rb +1 -1
- data/lib/axlsx/workbook/defined_name.rb +11 -12
- data/lib/axlsx/workbook/defined_names.rb +2 -2
- data/lib/axlsx/workbook/shared_strings_table.rb +5 -5
- data/lib/axlsx/workbook/workbook.rb +19 -12
- data/lib/axlsx/workbook/workbook_view.rb +78 -0
- data/lib/axlsx/workbook/workbook_views.rb +22 -0
- data/lib/axlsx/workbook/worksheet/auto_filter/auto_filter.rb +2 -2
- data/lib/axlsx/workbook/worksheet/auto_filter/filters.rb +1 -3
- data/lib/axlsx/workbook/worksheet/break.rb +1 -3
- data/lib/axlsx/workbook/worksheet/cell.rb +128 -73
- data/lib/axlsx/workbook/worksheet/cell_serializer.rb +50 -40
- data/lib/axlsx/workbook/worksheet/cfvo.rb +1 -3
- data/lib/axlsx/workbook/worksheet/cfvos.rb +1 -1
- data/lib/axlsx/workbook/worksheet/col.rb +7 -10
- data/lib/axlsx/workbook/worksheet/col_breaks.rb +2 -2
- data/lib/axlsx/workbook/worksheet/comment.rb +5 -6
- data/lib/axlsx/workbook/worksheet/comments.rb +9 -12
- data/lib/axlsx/workbook/worksheet/conditional_formatting.rb +1 -1
- data/lib/axlsx/workbook/worksheet/conditional_formatting_rule.rb +1 -1
- data/lib/axlsx/workbook/worksheet/data_bar.rb +4 -6
- data/lib/axlsx/workbook/worksheet/data_validation.rb +6 -4
- data/lib/axlsx/workbook/worksheet/dimension.rb +2 -2
- data/lib/axlsx/workbook/worksheet/header_footer.rb +6 -8
- data/lib/axlsx/workbook/worksheet/icon_set.rb +3 -5
- data/lib/axlsx/workbook/worksheet/merged_cells.rb +2 -2
- data/lib/axlsx/workbook/worksheet/page_margins.rb +1 -3
- data/lib/axlsx/workbook/worksheet/page_set_up_pr.rb +1 -1
- data/lib/axlsx/workbook/worksheet/page_setup.rb +21 -23
- data/lib/axlsx/workbook/worksheet/pane.rb +1 -3
- data/lib/axlsx/workbook/worksheet/pivot_table.rb +17 -24
- data/lib/axlsx/workbook/worksheet/pivot_table_cache_definition.rb +4 -4
- data/lib/axlsx/workbook/worksheet/print_options.rb +1 -3
- data/lib/axlsx/workbook/worksheet/protected_range.rb +1 -3
- data/lib/axlsx/workbook/worksheet/protected_ranges.rb +1 -1
- data/lib/axlsx/workbook/worksheet/rich_text.rb +35 -0
- data/lib/axlsx/workbook/worksheet/rich_text_run.rb +254 -0
- data/lib/axlsx/workbook/worksheet/row.rb +33 -51
- data/lib/axlsx/workbook/worksheet/row_breaks.rb +2 -2
- data/lib/axlsx/workbook/worksheet/selection.rb +1 -3
- data/lib/axlsx/workbook/worksheet/sheet_data.rb +3 -1
- data/lib/axlsx/workbook/worksheet/sheet_protection.rb +1 -3
- data/lib/axlsx/workbook/worksheet/table.rb +6 -6
- data/lib/axlsx/workbook/worksheet/table_style_info.rb +1 -3
- data/lib/axlsx/workbook/worksheet/tables.rb +1 -1
- data/lib/axlsx/workbook/worksheet/worksheet.rb +59 -30
- data/lib/axlsx/workbook/worksheet/worksheet_hyperlinks.rb +3 -3
- data/test/drawing/tc_axis.rb +27 -0
- data/test/drawing/tc_bubble_chart.rb +44 -0
- data/test/drawing/tc_bubble_series.rb +21 -0
- data/test/drawing/tc_data_source.rb +6 -0
- data/test/drawing/tc_line_chart.rb +5 -5
- data/test/drawing/tc_line_series.rb +10 -2
- data/test/drawing/tc_pic.rb +4 -0
- data/test/drawing/tc_scatter_series.rb +25 -1
- data/test/tc_helper.rb +1 -1
- data/test/tc_package.rb +7 -1
- data/test/util/tc_simple_typed_list.rb +1 -2
- data/test/workbook/tc_defined_name.rb +12 -4
- data/test/workbook/tc_workbook.rb +16 -2
- data/test/workbook/tc_workbook_view.rb +50 -0
- data/test/workbook/worksheet/auto_filter/tc_filters.rb +1 -1
- data/test/workbook/worksheet/tc_break.rb +1 -1
- data/test/workbook/worksheet/tc_cell.rb +30 -4
- data/test/workbook/worksheet/tc_col.rb +2 -2
- data/test/workbook/worksheet/tc_conditional_formatting.rb +2 -2
- data/test/workbook/worksheet/tc_data_bar.rb +1 -1
- data/test/workbook/worksheet/tc_data_validation.rb +11 -11
- data/test/workbook/worksheet/tc_header_footer.rb +2 -2
- data/test/workbook/worksheet/tc_icon_set.rb +1 -1
- data/test/workbook/worksheet/tc_page_setup.rb +3 -3
- data/test/workbook/worksheet/tc_print_options.rb +1 -1
- data/test/workbook/worksheet/tc_rich_text.rb +44 -0
- data/test/workbook/worksheet/tc_rich_text_run.rb +172 -0
- data/test/workbook/worksheet/tc_row.rb +2 -2
- data/test/workbook/worksheet/tc_sheet_calc_pr.rb +1 -1
- data/test/workbook/worksheet/tc_sheet_format_pr.rb +4 -4
- data/test/workbook/worksheet/tc_sheet_protection.rb +5 -5
- data/test/workbook/worksheet/tc_sheet_view.rb +4 -4
- data/test/workbook/worksheet/tc_worksheet.rb +49 -10
- metadata +81 -55
- data/test/axlsx.qcachegrind +0 -2226
|
@@ -63,11 +63,9 @@ module Axlsx
|
|
|
63
63
|
# @param [String] str
|
|
64
64
|
# @return [String]
|
|
65
65
|
def to_xml_string(str="")
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
@value_objects.each { |cfvo| cfvo.to_xml_string(str) }
|
|
70
|
-
str << '</iconSet>'
|
|
66
|
+
serialized_tag('iconSet', str) do
|
|
67
|
+
@value_objects.each { |cfvo| cfvo.to_xml_string(str) }
|
|
68
|
+
end
|
|
71
69
|
end
|
|
72
70
|
|
|
73
71
|
private
|
|
@@ -15,7 +15,7 @@ module Axlsx
|
|
|
15
15
|
# collection. This can be an array of actual cells or a string style
|
|
16
16
|
# range like 'A1:C1'
|
|
17
17
|
def add(cells)
|
|
18
|
-
|
|
18
|
+
self << if cells.is_a?(String)
|
|
19
19
|
cells
|
|
20
20
|
elsif cells.is_a?(Array)
|
|
21
21
|
Axlsx::cell_range(cells, false)
|
|
@@ -26,7 +26,7 @@ module Axlsx
|
|
|
26
26
|
# @param [String] str
|
|
27
27
|
# @return [String]
|
|
28
28
|
def to_xml_string(str = '')
|
|
29
|
-
return if
|
|
29
|
+
return if empty?
|
|
30
30
|
str << "<mergeCells count='#{size}'>"
|
|
31
31
|
each { |merged_cell| str << "<mergeCell ref='#{merged_cell}'></mergeCell>" }
|
|
32
32
|
str << '</mergeCells>'
|
|
@@ -91,9 +91,7 @@ module Axlsx
|
|
|
91
91
|
# @note For compatibility, this is a noop unless custom margins have been specified.
|
|
92
92
|
# @see #custom_margins_specified?
|
|
93
93
|
def to_xml_string(str = '')
|
|
94
|
-
|
|
95
|
-
serialized_attributes str
|
|
96
|
-
str << '/>'
|
|
94
|
+
serialized_tag('pageMargins', str)
|
|
97
95
|
end
|
|
98
96
|
end
|
|
99
97
|
end
|
|
@@ -44,13 +44,13 @@ module Axlsx
|
|
|
44
44
|
|
|
45
45
|
# Number of horizontal pages to fit on.
|
|
46
46
|
# @note PageSetup#fit_to is the recomended way to manage page fitting as only specifying one of width/height will result in the counterpart
|
|
47
|
-
# being set to 1.
|
|
47
|
+
# being set to 1.
|
|
48
48
|
# @return [Integer]
|
|
49
49
|
attr_reader :fit_to_width
|
|
50
50
|
|
|
51
51
|
# Orientation of the page (:default, :landscape, :portrait)
|
|
52
52
|
# @return [Symbol]
|
|
53
|
-
attr_reader :orientation
|
|
53
|
+
attr_reader :orientation
|
|
54
54
|
|
|
55
55
|
# Height of paper (string containing a number followed by a unit identifier: "297mm", "11in")
|
|
56
56
|
# @return [String]
|
|
@@ -74,18 +74,18 @@ module Axlsx
|
|
|
74
74
|
#7 = Executive paper (7.25 in. by 10.5 in.)
|
|
75
75
|
#8 = A3 paper (297 mm by 420 mm)
|
|
76
76
|
#9 = A4 paper (210 mm by 297 mm)
|
|
77
|
-
#10 = A4 small paper (210 mm by 297 mm)
|
|
77
|
+
#10 = A4 small paper (210 mm by 297 mm)
|
|
78
78
|
#11 = A5 paper (148 mm by 210 mm)
|
|
79
79
|
#12 = B4 paper (250 mm by 353 mm)
|
|
80
80
|
#13 = B5 paper (176 mm by 250 mm)
|
|
81
81
|
#14 = Folio paper (8.5 in. by 13 in.)
|
|
82
|
-
#15 = Quarto paper (215 mm by 275 mm)
|
|
82
|
+
#15 = Quarto paper (215 mm by 275 mm)
|
|
83
83
|
#16 = Standard paper (10 in. by 14 in.)
|
|
84
84
|
#17 = Standard paper (11 in. by 17 in.)
|
|
85
85
|
#18 = Note paper (8.5 in. by 11 in.)
|
|
86
|
-
#19 = #9 envelope (3.875 in. by 8.875 in.)
|
|
87
|
-
#20 = #10 envelope (4.125 in. by 9.5 in.)
|
|
88
|
-
#21 = #11 envelope (4.5 in. by 10.375 in.)
|
|
86
|
+
#19 = #9 envelope (3.875 in. by 8.875 in.)
|
|
87
|
+
#20 = #10 envelope (4.125 in. by 9.5 in.)
|
|
88
|
+
#21 = #11 envelope (4.5 in. by 10.375 in.)
|
|
89
89
|
#22 = #12 envelope (4.75 in. by 11 in.)
|
|
90
90
|
#23 = #14 envelope (5 in. by 11.5 in.) 24 = C paper (17 in. by 22 in.)
|
|
91
91
|
#25 = D paper (22 in. by 34 in.)
|
|
@@ -105,7 +105,7 @@ module Axlsx
|
|
|
105
105
|
#40 = German standard fanfold (8.5 in. by 12 in.)
|
|
106
106
|
#41 = German legal fanfold (8.5 in. by 13 in.)
|
|
107
107
|
#42 = ISO B4 (250 mm by 353 mm)
|
|
108
|
-
#43 = Japanese double postcard (200 mm by 148 mm)
|
|
108
|
+
#43 = Japanese double postcard (200 mm by 148 mm)
|
|
109
109
|
#44 = Standard paper (9 in. by 11 in.)
|
|
110
110
|
#45 = Standard paper (10 in. by 11 in.)
|
|
111
111
|
#46 = Standard paper (15 in. by 11 in.)
|
|
@@ -116,9 +116,9 @@ module Axlsx
|
|
|
116
116
|
#53 = A4 extra paper (236 mm by 322 mm)
|
|
117
117
|
#54 = Letter transverse paper (8.275 in. by 11 in.)
|
|
118
118
|
#55 = A4 transverse paper (210 mm by 297 mm)
|
|
119
|
-
#56 = Letter extra transverse paper (9.275 in. by 12 in.)
|
|
120
|
-
#57 = SuperA/SuperA/A4 paper (227 mm by 356 mm)
|
|
121
|
-
#58 = SuperB/SuperB/A3 paper (305 mm by 487 mm)
|
|
119
|
+
#56 = Letter extra transverse paper (9.275 in. by 12 in.)
|
|
120
|
+
#57 = SuperA/SuperA/A4 paper (227 mm by 356 mm)
|
|
121
|
+
#58 = SuperB/SuperB/A3 paper (305 mm by 487 mm)
|
|
122
122
|
#59 = Letter plus paper (8.5 in. by 12.69 in.)
|
|
123
123
|
#60 = A4 plus paper (210 mm by 330 mm)
|
|
124
124
|
#61 = A5 transverse paper (148 mm by 210 mm)
|
|
@@ -128,8 +128,8 @@ module Axlsx
|
|
|
128
128
|
#65 = ISO B5 extra paper (201 mm by 276 mm)
|
|
129
129
|
#66 = A2 paper (420 mm by 594 mm)
|
|
130
130
|
#67 = A3 transverse paper (297 mm by 420 mm)
|
|
131
|
-
#68 = A3 extra transverse paper (322 mm by 445 mm)
|
|
132
|
-
#69 = Japanese Double Postcard (200 mm x 148 mm)
|
|
131
|
+
#68 = A3 extra transverse paper (322 mm by 445 mm)
|
|
132
|
+
#69 = Japanese Double Postcard (200 mm x 148 mm)
|
|
133
133
|
#70 = A6 (105 mm x 148 mm
|
|
134
134
|
#71 = Japanese Envelope Kaku #2
|
|
135
135
|
#72 = Japanese Envelope Kaku #3
|
|
@@ -142,7 +142,7 @@ module Axlsx
|
|
|
142
142
|
#79 = B4 (JIS) Rotated (364 mm x 257 mm)
|
|
143
143
|
#80 = B5 (JIS) Rotated (257 mm x 182 mm)
|
|
144
144
|
#81 = Japanese Postcard Rotated (148 mm x 100 mm)
|
|
145
|
-
#82 = Double Japanese Postcard Rotated (148 mm x 200 mm)
|
|
145
|
+
#82 = Double Japanese Postcard Rotated (148 mm x 200 mm)
|
|
146
146
|
#83 = A6 Rotated (148 mm x 105 mm)
|
|
147
147
|
#84 = Japanese Envelope Kaku #2 Rotated
|
|
148
148
|
#85 = Japanese Envelope Kaku #3 Rotated
|
|
@@ -210,20 +210,20 @@ module Axlsx
|
|
|
210
210
|
# @see scale
|
|
211
211
|
def scale=(v); Axlsx::validate_scale_10_400(v); @scale = v; end
|
|
212
212
|
|
|
213
|
-
# convenience method to achieve sanity when setting fit_to_width and fit_to_height
|
|
213
|
+
# convenience method to achieve sanity when setting fit_to_width and fit_to_height
|
|
214
214
|
# as they both default to 1 if only their counterpart is specified.
|
|
215
215
|
# @note This method will overwrite any value you explicitly set via the fit_to_height or fit_to_width methods.
|
|
216
|
-
# @option options [Integer] width The number of pages to fit this worksheet on horizontally. Default
|
|
217
|
-
# @option options [Integer] height The number of pages to fit this worksheet on vertically. Default
|
|
216
|
+
# @option options [Integer] width The number of pages to fit this worksheet on horizontally. Default 999
|
|
217
|
+
# @option options [Integer] height The number of pages to fit this worksheet on vertically. Default 999
|
|
218
218
|
def fit_to(options={})
|
|
219
|
-
self.fit_to_width = options[:width] ||
|
|
220
|
-
self.fit_to_height = options[:height] ||
|
|
219
|
+
self.fit_to_width = options[:width] || 999
|
|
220
|
+
self.fit_to_height = options[:height] || 999
|
|
221
221
|
[@fit_to_width, @fit_to_height]
|
|
222
222
|
end
|
|
223
223
|
|
|
224
224
|
|
|
225
225
|
# helper method for worksheet to determine if the page setup is configured for fit to page printing
|
|
226
|
-
# We treat any page set up that has a value set for fit_to_width or fit_to_height value as fit_to_page.
|
|
226
|
+
# We treat any page set up that has a value set for fit_to_width or fit_to_height value as fit_to_page.
|
|
227
227
|
# @return [Boolean]
|
|
228
228
|
def fit_to_page?
|
|
229
229
|
# is there some better what to express this?
|
|
@@ -234,9 +234,7 @@ module Axlsx
|
|
|
234
234
|
# @param [String] str
|
|
235
235
|
# @return [String]
|
|
236
236
|
def to_xml_string(str = '')
|
|
237
|
-
|
|
238
|
-
serialized_attributes str
|
|
239
|
-
str << '/>'
|
|
237
|
+
serialized_tag('pageSetup', str)
|
|
240
238
|
end
|
|
241
239
|
end
|
|
242
240
|
end
|
|
@@ -159,9 +159,9 @@ module Axlsx
|
|
|
159
159
|
# @return [String]
|
|
160
160
|
def to_xml_string(str = '')
|
|
161
161
|
str << '<?xml version="1.0" encoding="UTF-8"?>'
|
|
162
|
-
str << '<pivotTableDefinition xmlns="' << XML_NS << '" name="' << name << '" cacheId="' << cache_definition.cache_id.to_s << '" dataOnRows="1" applyNumberFormats="0" applyBorderFormats="0" applyFontFormats="0" applyPatternFormats="0" applyAlignmentFormats="0" applyWidthHeightFormats="1" dataCaption="Data" showMultipleLabel="0" showMemberPropertyTips="0" useAutoFormatting="1" indent="0" compact="0" compactData="0" gridDropZones="1" multipleFieldFilters="0">'
|
|
163
|
-
str <<
|
|
164
|
-
str <<
|
|
162
|
+
str << ('<pivotTableDefinition xmlns="' << XML_NS << '" name="' << name << '" cacheId="' << cache_definition.cache_id.to_s << '" dataOnRows="1" applyNumberFormats="0" applyBorderFormats="0" applyFontFormats="0" applyPatternFormats="0" applyAlignmentFormats="0" applyWidthHeightFormats="1" dataCaption="Data" showMultipleLabel="0" showMemberPropertyTips="0" useAutoFormatting="1" indent="0" compact="0" compactData="0" gridDropZones="1" multipleFieldFilters="0">')
|
|
163
|
+
str << ( '<location firstDataCol="1" firstDataRow="1" firstHeaderRow="1" ref="' << ref << '"/>')
|
|
164
|
+
str << ( '<pivotFields count="' << header_cells_count.to_s << '">')
|
|
165
165
|
header_cell_values.each do |cell_value|
|
|
166
166
|
str << pivot_field_for(cell_value)
|
|
167
167
|
end
|
|
@@ -170,12 +170,12 @@ module Axlsx
|
|
|
170
170
|
str << '<rowFields count="1"><field x="-2"/></rowFields>'
|
|
171
171
|
str << '<rowItems count="2"><i><x/></i> <i i="1"><x v="1"/></i></rowItems>'
|
|
172
172
|
else
|
|
173
|
-
str << '<rowFields count="' << rows.size.to_s << '">'
|
|
173
|
+
str << ('<rowFields count="' << rows.size.to_s << '">')
|
|
174
174
|
rows.each do |row_value|
|
|
175
|
-
str << '<field x="' << header_index_of(row_value).to_s << '"/>'
|
|
175
|
+
str << ('<field x="' << header_index_of(row_value).to_s << '"/>')
|
|
176
176
|
end
|
|
177
177
|
str << '</rowFields>'
|
|
178
|
-
str << '<rowItems count="' << rows.size.to_s << '">'
|
|
178
|
+
str << ('<rowItems count="' << rows.size.to_s << '">')
|
|
179
179
|
rows.size.times do |i|
|
|
180
180
|
str << '<i/>'
|
|
181
181
|
end
|
|
@@ -184,16 +184,16 @@ module Axlsx
|
|
|
184
184
|
if columns.empty?
|
|
185
185
|
str << '<colItems count="1"><i/></colItems>'
|
|
186
186
|
else
|
|
187
|
-
str << '<colFields count="' << columns.size.to_s << '">'
|
|
187
|
+
str << ('<colFields count="' << columns.size.to_s << '">')
|
|
188
188
|
columns.each do |column_value|
|
|
189
|
-
str << '<field x="' << header_index_of(column_value).to_s << '"/>'
|
|
189
|
+
str << ('<field x="' << header_index_of(column_value).to_s << '"/>')
|
|
190
190
|
end
|
|
191
191
|
str << '</colFields>'
|
|
192
192
|
end
|
|
193
193
|
unless pages.empty?
|
|
194
|
-
str << '<pageFields count="' << pages.size.to_s << '">'
|
|
194
|
+
str << ('<pageFields count="' << pages.size.to_s << '">')
|
|
195
195
|
pages.each do |page_value|
|
|
196
|
-
str << '<pageField fld="' << header_index_of(page_value).to_s << '"/>'
|
|
196
|
+
str << ('<pageField fld="' << header_index_of(page_value).to_s << '"/>')
|
|
197
197
|
end
|
|
198
198
|
str << '</pageFields>'
|
|
199
199
|
end
|
|
@@ -243,31 +243,24 @@ module Axlsx
|
|
|
243
243
|
|
|
244
244
|
def pivot_field_for(cell_ref)
|
|
245
245
|
if rows.include? cell_ref
|
|
246
|
-
'<pivotField axis="axisRow" compact="0" outline="0" subtotalTop="0" showAll="0" includeNewItemsInFilter="1">'
|
|
247
|
-
'<items count="1"><item t="default"/></items>' <<
|
|
248
|
-
'</pivotField>'
|
|
246
|
+
'<pivotField axis="axisRow" compact="0" outline="0" subtotalTop="0" showAll="0" includeNewItemsInFilter="1">' + '<items count="1"><item t="default"/></items>' + '</pivotField>'
|
|
249
247
|
elsif columns.include? cell_ref
|
|
250
|
-
'<pivotField axis="axisCol" compact="0" outline="0" subtotalTop="0" showAll="0" includeNewItemsInFilter="1">'
|
|
251
|
-
'<items count="1"><item t="default"/></items>' <<
|
|
252
|
-
'</pivotField>'
|
|
248
|
+
'<pivotField axis="axisCol" compact="0" outline="0" subtotalTop="0" showAll="0" includeNewItemsInFilter="1">' + '<items count="1"><item t="default"/></items>' + '</pivotField>'
|
|
253
249
|
elsif pages.include? cell_ref
|
|
254
|
-
'<pivotField axis="axisCol" compact="0" outline="0" subtotalTop="0" showAll="0" includeNewItemsInFilter="1">'
|
|
255
|
-
'<items count="1"><item t="default"/></items>' <<
|
|
256
|
-
'</pivotField>'
|
|
250
|
+
'<pivotField axis="axisCol" compact="0" outline="0" subtotalTop="0" showAll="0" includeNewItemsInFilter="1">' + '<items count="1"><item t="default"/></items>' + '</pivotField>'
|
|
257
251
|
elsif data_refs.include? cell_ref
|
|
258
|
-
'<pivotField dataField="1" compact="0" outline="0" subtotalTop="0" showAll="0" includeNewItemsInFilter="1">'
|
|
259
|
-
'</pivotField>'
|
|
252
|
+
'<pivotField dataField="1" compact="0" outline="0" subtotalTop="0" showAll="0" includeNewItemsInFilter="1">' + '</pivotField>'
|
|
260
253
|
else
|
|
261
|
-
'<pivotField compact="0" outline="0" subtotalTop="0" showAll="0" includeNewItemsInFilter="1">'
|
|
262
|
-
'</pivotField>'
|
|
254
|
+
'<pivotField compact="0" outline="0" subtotalTop="0" showAll="0" includeNewItemsInFilter="1">' + '</pivotField>'
|
|
263
255
|
end
|
|
264
256
|
end
|
|
257
|
+
|
|
265
258
|
def data_refs
|
|
266
259
|
data.map { |hash| hash[:ref] }
|
|
267
260
|
end
|
|
261
|
+
|
|
268
262
|
def header_range
|
|
269
263
|
range.gsub(/^(\w+?)(\d+)\:(\w+?)\d+$/, '\1\2:\3\2')
|
|
270
264
|
end
|
|
271
|
-
|
|
272
265
|
end
|
|
273
266
|
end
|
|
@@ -47,13 +47,13 @@ module Axlsx
|
|
|
47
47
|
# @return [String]
|
|
48
48
|
def to_xml_string(str = '')
|
|
49
49
|
str << '<?xml version="1.0" encoding="UTF-8"?>'
|
|
50
|
-
str << '<pivotCacheDefinition xmlns="' << XML_NS << '" xmlns:r="' << XML_NS_R << '" invalid="1" refreshOnLoad="1" recordCount="0">'
|
|
50
|
+
str << ('<pivotCacheDefinition xmlns="' << XML_NS << '" xmlns:r="' << XML_NS_R << '" invalid="1" refreshOnLoad="1" recordCount="0">')
|
|
51
51
|
str << '<cacheSource type="worksheet">'
|
|
52
|
-
str <<
|
|
52
|
+
str << ( '<worksheetSource ref="' << pivot_table.range << '" sheet="' << pivot_table.data_sheet.name << '"/>')
|
|
53
53
|
str << '</cacheSource>'
|
|
54
|
-
str <<
|
|
54
|
+
str << ( '<cacheFields count="' << pivot_table.header_cells_count.to_s << '">')
|
|
55
55
|
pivot_table.header_cells.each do |cell|
|
|
56
|
-
str <<
|
|
56
|
+
str << ( '<cacheField name="' << cell.value << '" numFmtId="0">')
|
|
57
57
|
str << '<sharedItems count="0">'
|
|
58
58
|
str << '</sharedItems>'
|
|
59
59
|
str << '</cacheField>'
|
|
@@ -41,9 +41,7 @@ module Axlsx
|
|
|
41
41
|
# our output to that object. Use this - it helps limit the number of
|
|
42
42
|
# objects created during serialization
|
|
43
43
|
def to_xml_string(str="")
|
|
44
|
-
|
|
45
|
-
serialized_attributes str
|
|
46
|
-
str << '/>'
|
|
44
|
+
serialized_tag 'protectedRange', str
|
|
47
45
|
end
|
|
48
46
|
end
|
|
49
47
|
end
|
|
@@ -20,7 +20,7 @@ module Axlsx
|
|
|
20
20
|
elsif cells.is_a?(SimpleTypedList) || cells.is_a?(Array)
|
|
21
21
|
Axlsx::cell_range(cells, false)
|
|
22
22
|
end
|
|
23
|
-
|
|
23
|
+
self << ProtectedRange.new(:sqref => sqref, :name => "Range#{size}")
|
|
24
24
|
last
|
|
25
25
|
end
|
|
26
26
|
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
module Axlsx
|
|
2
|
+
class RichText < SimpleTypedList
|
|
3
|
+
def initialize(text = nil, options={})
|
|
4
|
+
super(RichTextRun)
|
|
5
|
+
add_run(text, options) unless text.nil?
|
|
6
|
+
yield self if block_given?
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
attr_reader :cell
|
|
10
|
+
|
|
11
|
+
def cell=(cell)
|
|
12
|
+
@cell = cell
|
|
13
|
+
each { |run| run.cell = cell }
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def autowidth
|
|
17
|
+
widtharray = [0] # Are arrays the best way of solving this problem?
|
|
18
|
+
each { |run| run.autowidth(widtharray) }
|
|
19
|
+
widtharray.max
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
def add_run(text, options={})
|
|
23
|
+
self << RichTextRun.new(text, options)
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
def runs
|
|
27
|
+
self
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
def to_xml_string(str='')
|
|
31
|
+
each{ |run| run.to_xml_string(str) }
|
|
32
|
+
str
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
end
|
|
@@ -0,0 +1,254 @@
|
|
|
1
|
+
module Axlsx
|
|
2
|
+
class RichTextRun
|
|
3
|
+
|
|
4
|
+
include Axlsx::OptionsParser
|
|
5
|
+
|
|
6
|
+
attr_reader :value
|
|
7
|
+
|
|
8
|
+
INLINE_STYLES = [:font_name, :charset,
|
|
9
|
+
:family, :b, :i, :strike, :outline,
|
|
10
|
+
:shadow, :condense, :extend, :u,
|
|
11
|
+
:vertAlign, :sz, :color, :scheme].freeze
|
|
12
|
+
|
|
13
|
+
def initialize(value, options={})
|
|
14
|
+
self.value = value
|
|
15
|
+
parse_options(options)
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
def value=(value)
|
|
19
|
+
@value = value
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
attr_accessor :cell
|
|
23
|
+
|
|
24
|
+
# The inline font_name property for the cell
|
|
25
|
+
# @return [String]
|
|
26
|
+
attr_reader :font_name
|
|
27
|
+
# @see font_name
|
|
28
|
+
def font_name=(v) set_run_style :validate_string, :font_name, v; end
|
|
29
|
+
|
|
30
|
+
# The inline charset property for the cell
|
|
31
|
+
# As far as I can tell, this is pretty much ignored. However, based on the spec it should be one of the following:
|
|
32
|
+
# 0  ANSI_CHARSET
|
|
33
|
+
# 1 DEFAULT_CHARSET
|
|
34
|
+
# 2 SYMBOL_CHARSET
|
|
35
|
+
# 77 MAC_CHARSET
|
|
36
|
+
# 128 SHIFTJIS_CHARSET
|
|
37
|
+
# 129  HANGUL_CHARSET
|
|
38
|
+
# 130  JOHAB_CHARSET
|
|
39
|
+
# 134  GB2312_CHARSET
|
|
40
|
+
# 136  CHINESEBIG5_CHARSET
|
|
41
|
+
# 161  GREEK_CHARSET
|
|
42
|
+
# 162  TURKISH_CHARSET
|
|
43
|
+
# 163  VIETNAMESE_CHARSET
|
|
44
|
+
# 177  HEBREW_CHARSET
|
|
45
|
+
# 178  ARABIC_CHARSET
|
|
46
|
+
# 186  BALTIC_CHARSET
|
|
47
|
+
# 204  RUSSIAN_CHARSET
|
|
48
|
+
# 222  THAI_CHARSET
|
|
49
|
+
# 238  EASTEUROPE_CHARSET
|
|
50
|
+
# 255  OEM_CHARSET
|
|
51
|
+
# @return [String]
|
|
52
|
+
attr_reader :charset
|
|
53
|
+
# @see charset
|
|
54
|
+
def charset=(v) set_run_style :validate_unsigned_int, :charset, v; end
|
|
55
|
+
|
|
56
|
+
# The inline family property for the cell
|
|
57
|
+
# @return [Integer]
|
|
58
|
+
# 1 Roman
|
|
59
|
+
# 2 Swiss
|
|
60
|
+
# 3 Modern
|
|
61
|
+
# 4 Script
|
|
62
|
+
# 5 Decorative
|
|
63
|
+
attr_reader :family
|
|
64
|
+
# @see family
|
|
65
|
+
def family=(v)
|
|
66
|
+
set_run_style :validate_family, :family, v.to_i
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
# The inline bold property for the cell
|
|
70
|
+
# @return [Boolean]
|
|
71
|
+
attr_reader :b
|
|
72
|
+
# @see b
|
|
73
|
+
def b=(v) set_run_style :validate_boolean, :b, v; end
|
|
74
|
+
|
|
75
|
+
# The inline italic property for the cell
|
|
76
|
+
# @return [Boolean]
|
|
77
|
+
attr_reader :i
|
|
78
|
+
# @see i
|
|
79
|
+
def i=(v) set_run_style :validate_boolean, :i, v; end
|
|
80
|
+
|
|
81
|
+
# The inline strike property for the cell
|
|
82
|
+
# @return [Boolean]
|
|
83
|
+
attr_reader :strike
|
|
84
|
+
# @see strike
|
|
85
|
+
def strike=(v) set_run_style :validate_boolean, :strike, v; end
|
|
86
|
+
|
|
87
|
+
# The inline outline property for the cell
|
|
88
|
+
# @return [Boolean]
|
|
89
|
+
attr_reader :outline
|
|
90
|
+
# @see outline
|
|
91
|
+
def outline=(v) set_run_style :validate_boolean, :outline, v; end
|
|
92
|
+
|
|
93
|
+
# The inline shadow property for the cell
|
|
94
|
+
# @return [Boolean]
|
|
95
|
+
attr_reader :shadow
|
|
96
|
+
# @see shadow
|
|
97
|
+
def shadow=(v) set_run_style :validate_boolean, :shadow, v; end
|
|
98
|
+
|
|
99
|
+
# The inline condense property for the cell
|
|
100
|
+
# @return [Boolean]
|
|
101
|
+
attr_reader :condense
|
|
102
|
+
# @see condense
|
|
103
|
+
def condense=(v) set_run_style :validate_boolean, :condense, v; end
|
|
104
|
+
|
|
105
|
+
# The inline extend property for the cell
|
|
106
|
+
# @return [Boolean]
|
|
107
|
+
attr_reader :extend
|
|
108
|
+
# @see extend
|
|
109
|
+
def extend=(v) set_run_style :validate_boolean, :extend, v; end
|
|
110
|
+
|
|
111
|
+
# The inline underline property for the cell.
|
|
112
|
+
# It must be one of :none, :single, :double, :singleAccounting, :doubleAccounting, true
|
|
113
|
+
# @return [Boolean]
|
|
114
|
+
# @return [String]
|
|
115
|
+
# @note true is for backwards compatability and is reassigned to :single
|
|
116
|
+
attr_reader :u
|
|
117
|
+
# @see u
|
|
118
|
+
def u=(v)
|
|
119
|
+
v = :single if (v == true || v == 1 || v == :true || v == 'true')
|
|
120
|
+
set_run_style :validate_cell_u, :u, v
|
|
121
|
+
end
|
|
122
|
+
|
|
123
|
+
# The inline color property for the cell
|
|
124
|
+
# @return [Color]
|
|
125
|
+
attr_reader :color
|
|
126
|
+
# @param [String] v The 8 character representation for an rgb color #FFFFFFFF"
|
|
127
|
+
def color=(v)
|
|
128
|
+
@color = v.is_a?(Color) ? v : Color.new(:rgb=>v)
|
|
129
|
+
end
|
|
130
|
+
|
|
131
|
+
# The inline sz property for the cell
|
|
132
|
+
# @return [Inteter]
|
|
133
|
+
attr_reader :sz
|
|
134
|
+
# @see sz
|
|
135
|
+
def sz=(v) set_run_style :validate_unsigned_int, :sz, v; end
|
|
136
|
+
|
|
137
|
+
# The inline vertical alignment property for the cell
|
|
138
|
+
# this must be one of [:baseline, :subscript, :superscript]
|
|
139
|
+
# @return [Symbol]
|
|
140
|
+
attr_reader :vertAlign
|
|
141
|
+
# @see vertAlign
|
|
142
|
+
def vertAlign=(v)
|
|
143
|
+
RestrictionValidator.validate :cell_vertAlign, [:baseline, :subscript, :superscript], v
|
|
144
|
+
set_run_style nil, :vertAlign, v
|
|
145
|
+
end
|
|
146
|
+
|
|
147
|
+
# The inline scheme property for the cell
|
|
148
|
+
# this must be one of [:none, major, minor]
|
|
149
|
+
# @return [Symbol]
|
|
150
|
+
attr_reader :scheme
|
|
151
|
+
# @see scheme
|
|
152
|
+
def scheme=(v)
|
|
153
|
+
RestrictionValidator.validate :cell_scheme, [:none, :major, :minor], v
|
|
154
|
+
set_run_style nil, :scheme, v
|
|
155
|
+
end
|
|
156
|
+
|
|
157
|
+
# The Shared Strings Table index for this cell
|
|
158
|
+
# @return [Integer]
|
|
159
|
+
attr_reader :ssti
|
|
160
|
+
|
|
161
|
+
# @return [Integer] The cellXfs item index applied to this cell.
|
|
162
|
+
# @raise [ArgumentError] Invalid cellXfs id if the value provided is not within cellXfs items range.
|
|
163
|
+
def style=(v)
|
|
164
|
+
Axlsx::validate_unsigned_int(v)
|
|
165
|
+
count = styles.cellXfs.size
|
|
166
|
+
raise ArgumentError, "Invalid cellXfs id" unless v < count
|
|
167
|
+
@style = v
|
|
168
|
+
end
|
|
169
|
+
|
|
170
|
+
def autowidth(widtharray)
|
|
171
|
+
return if value.nil?
|
|
172
|
+
if styles.cellXfs[style].alignment && styles.cellXfs[style].alignment.wrap_text
|
|
173
|
+
first = true
|
|
174
|
+
value.to_s.split(/\r?\n/, -1).each do |line|
|
|
175
|
+
if first
|
|
176
|
+
first = false
|
|
177
|
+
else
|
|
178
|
+
widtharray << 0
|
|
179
|
+
end
|
|
180
|
+
widtharray[-1] += string_width(line, font_size)
|
|
181
|
+
end
|
|
182
|
+
else
|
|
183
|
+
widtharray[-1] += string_width(value.to_s, font_size)
|
|
184
|
+
end
|
|
185
|
+
widtharray
|
|
186
|
+
end
|
|
187
|
+
|
|
188
|
+
# Utility method for setting inline style attributes
|
|
189
|
+
def set_run_style(validator, attr, value)
|
|
190
|
+
return unless INLINE_STYLES.include?(attr.to_sym)
|
|
191
|
+
Axlsx.send(validator, value) unless validator.nil?
|
|
192
|
+
self.instance_variable_set :"@#{attr.to_s}", value
|
|
193
|
+
end
|
|
194
|
+
|
|
195
|
+
def to_xml_string(str = '')
|
|
196
|
+
valid = RichTextRun::INLINE_STYLES
|
|
197
|
+
data = Hash[self.instance_values.map{ |k, v| [k.to_sym, v] }]
|
|
198
|
+
data = data.select { |key, value| valid.include?(key) && !value.nil? }
|
|
199
|
+
|
|
200
|
+
str << '<r><rPr>'
|
|
201
|
+
data.keys.each do |key|
|
|
202
|
+
case key
|
|
203
|
+
when :font_name
|
|
204
|
+
str << ('<rFont val="' << font_name << '"/>')
|
|
205
|
+
when :color
|
|
206
|
+
str << data[key].to_xml_string
|
|
207
|
+
else
|
|
208
|
+
str << ('<' << key.to_s << ' val="' << xml_value(data[key]) << '"/>')
|
|
209
|
+
end
|
|
210
|
+
end
|
|
211
|
+
clean_value = Axlsx::trust_input ? @value.to_s : ::CGI.escapeHTML(Axlsx::sanitize(@value.to_s))
|
|
212
|
+
str << ('</rPr><t>' << clean_value << '</t></r>')
|
|
213
|
+
end
|
|
214
|
+
|
|
215
|
+
private
|
|
216
|
+
|
|
217
|
+
# Returns the width of a string according to the current style
|
|
218
|
+
# This is still not perfect...
|
|
219
|
+
# - scaling is not linear as font sizes increase
|
|
220
|
+
def string_width(string, font_size)
|
|
221
|
+
font_scale = font_size / 10.0
|
|
222
|
+
string.count(Worksheet::THIN_CHARS) * font_scale
|
|
223
|
+
end
|
|
224
|
+
|
|
225
|
+
# we scale the font size if bold style is applied to either the style font or
|
|
226
|
+
# the cell itself. Yes, it is a bit of a hack, but it is much better than using
|
|
227
|
+
# imagemagick and loading metrics for every character.
|
|
228
|
+
def font_size
|
|
229
|
+
return sz if sz
|
|
230
|
+
font = styles.fonts[styles.cellXfs[style].fontId] || styles.fonts[0]
|
|
231
|
+
(font.b || (defined?(@b) && @b)) ? (font.sz * 1.5) : font.sz
|
|
232
|
+
end
|
|
233
|
+
|
|
234
|
+
def style
|
|
235
|
+
cell.style
|
|
236
|
+
end
|
|
237
|
+
|
|
238
|
+
def styles
|
|
239
|
+
cell.row.worksheet.styles
|
|
240
|
+
end
|
|
241
|
+
|
|
242
|
+
# Converts the value to the correct XML representation (fixes issues with
|
|
243
|
+
# Numbers)
|
|
244
|
+
def xml_value value
|
|
245
|
+
if value == true
|
|
246
|
+
1
|
|
247
|
+
elsif value == false
|
|
248
|
+
0
|
|
249
|
+
else
|
|
250
|
+
value
|
|
251
|
+
end.to_s
|
|
252
|
+
end
|
|
253
|
+
end
|
|
254
|
+
end
|