xlsx 0.1

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.
data/LICENSE ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (C) 2009 Brian Buchanan. All rights reserved.
2
+
3
+ Redistribution and use in source and binary forms, with or without
4
+ modification, are permitted provided that the following conditions
5
+ are met:
6
+ 1. Redistributions of source code must retain the above copyright
7
+ notice, this list of conditions and the following disclaimer.
8
+ 2. Redistributions in binary form must reproduce the above copyright
9
+ notice, this list of conditions and the following disclaimer in the
10
+ documentation and/or other materials provided with the distribution.
11
+
12
+ THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND
13
+ ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
14
+ IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
15
+ ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE
16
+ FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
17
+ DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
18
+ OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
19
+ HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
20
+ LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
21
+ OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
22
+ SUCH DAMAGE.
data/README ADDED
@@ -0,0 +1,12 @@
1
+ This is a work-in-progress.
2
+
3
+ Right now, just a small subset of the Spreadsheet gem's API is implemented:
4
+
5
+ require 'xlsx'
6
+
7
+ workbook = XLSX::Workbook.new
8
+ worksheet = workbook.create_worksheet :name => 'My Sheet'
9
+ worksheet.update_row(0, 'A1', 'A2', 'A3')
10
+ worksheet.update_row(1, 'B1', 'B2', 'B3')
11
+ worksheet.update_row(2, 5, 6, 7)
12
+ worksheet.write('my_spreadsheet.xlsx')
@@ -0,0 +1,27 @@
1
+ # Copyright (C) 2009 Brian Buchanan. All rights reserved.
2
+ #
3
+ # Redistribution and use in source and binary forms, with or without
4
+ # modification, are permitted provided that the following conditions
5
+ # are met:
6
+ # 1. Redistributions of source code must retain the above copyright
7
+ # notice, this list of conditions and the following disclaimer.
8
+ # 2. Redistributions in binary form must reproduce the above copyright
9
+ # notice, this list of conditions and the following disclaimer in the
10
+ # documentation and/or other materials provided with the distribution.
11
+ #
12
+ # THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND
13
+ # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
14
+ # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
15
+ # ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE
16
+ # FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
17
+ # DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
18
+ # OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
19
+ # HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
20
+ # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
21
+ # OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
22
+ # SUCH DAMAGE.
23
+
24
+ require 'xlsx/workbook'
25
+ require 'xlsx/worksheet'
26
+ require 'xlsx/row'
27
+ require 'xlsx/cell'
@@ -0,0 +1,54 @@
1
+ # Copyright (C) 2009 Brian Buchanan. All rights reserved.
2
+ #
3
+ # Redistribution and use in source and binary forms, with or without
4
+ # modification, are permitted provided that the following conditions
5
+ # are met:
6
+ # 1. Redistributions of source code must retain the above copyright
7
+ # notice, this list of conditions and the following disclaimer.
8
+ # 2. Redistributions in binary form must reproduce the above copyright
9
+ # notice, this list of conditions and the following disclaimer in the
10
+ # documentation and/or other materials provided with the distribution.
11
+ #
12
+ # THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND
13
+ # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
14
+ # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
15
+ # ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE
16
+ # FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
17
+ # DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
18
+ # OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
19
+ # HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
20
+ # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
21
+ # OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
22
+ # SUCH DAMAGE.
23
+
24
+ module XLSX
25
+ class Cell
26
+ attr_reader :row_number
27
+ attr_reader :col_number
28
+ attr_accessor :value
29
+
30
+ def initialize(row_number, col_number, value)
31
+ @row_number = row_number
32
+ @col_number = col_number
33
+ @value = value
34
+ end
35
+
36
+ def name
37
+ XLSX::Cell.cell_name(@row_number, @col_number)
38
+ end
39
+
40
+ def self.cell_name(row_number, col_number)
41
+ raise "Column #{col_number} out of range" if col_number > 701
42
+
43
+ if col_number <= 25
44
+ col_name = ''
45
+ else
46
+ c = col_number / 26
47
+ col_name = (?A + c - 1).chr
48
+ col_number = col_number % 26
49
+ end
50
+ col_name += (?A + col_number).chr
51
+ "#{col_name}#{row_number + 1}"
52
+ end
53
+ end
54
+ end
@@ -0,0 +1,55 @@
1
+ # Copyright (C) 2009 Brian Buchanan. All rights reserved.
2
+ #
3
+ # Redistribution and use in source and binary forms, with or without
4
+ # modification, are permitted provided that the following conditions
5
+ # are met:
6
+ # 1. Redistributions of source code must retain the above copyright
7
+ # notice, this list of conditions and the following disclaimer.
8
+ # 2. Redistributions in binary form must reproduce the above copyright
9
+ # notice, this list of conditions and the following disclaimer in the
10
+ # documentation and/or other materials provided with the distribution.
11
+ #
12
+ # THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND
13
+ # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
14
+ # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
15
+ # ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE
16
+ # FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
17
+ # DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
18
+ # OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
19
+ # HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
20
+ # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
21
+ # OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
22
+ # SUCH DAMAGE.
23
+
24
+ module XLSX
25
+ class Row
26
+ include Enumerable
27
+
28
+ attr_reader :row_number, :min_col, :max_col
29
+
30
+ def initialize(worksheet, row_number)
31
+ @worksheet = worksheet
32
+ @row_number = row_number
33
+ @cells = {}
34
+ @min_col = 0
35
+ @max_col = 0
36
+ end
37
+
38
+ def []=(col_number, value)
39
+ raise "Column number must be a non-negative integer." unless col_number.is_a?(Integer) && col_number >= 0
40
+ @cells[col_number] = XLSX::Cell.new(@row_number, col_number, value)
41
+ @min_col = col_number if col_number < @min_col
42
+ @max_col = col_number if col_number > @max_col
43
+ end
44
+
45
+ def each
46
+ @cells.keys.sort.each do |col_no|
47
+ yield @cells[col_no]
48
+ end
49
+ end
50
+
51
+ def last
52
+ @cells[@cells.keys.sort.last]
53
+ end
54
+ end
55
+ end
@@ -0,0 +1,328 @@
1
+ # Copyright (C) 2009 Brian Buchanan. All rights reserved.
2
+ #
3
+ # Redistribution and use in source and binary forms, with or without
4
+ # modification, are permitted provided that the following conditions
5
+ # are met:
6
+ # 1. Redistributions of source code must retain the above copyright
7
+ # notice, this list of conditions and the following disclaimer.
8
+ # 2. Redistributions in binary form must reproduce the above copyright
9
+ # notice, this list of conditions and the following disclaimer in the
10
+ # documentation and/or other materials provided with the distribution.
11
+ #
12
+ # THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND
13
+ # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
14
+ # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
15
+ # ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE
16
+ # FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
17
+ # DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
18
+ # OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
19
+ # HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
20
+ # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
21
+ # OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
22
+ # SUCH DAMAGE.
23
+
24
+ require 'builder'
25
+ require 'zip/zip'
26
+
27
+ module XLSX
28
+ class Workbook
29
+ def initialize(filename=nil)
30
+ @filename = filename
31
+ @sheets = []
32
+ end
33
+
34
+ def worksheet(sheet_no)
35
+ @sheets[sheet_no]
36
+ end
37
+
38
+ def create_worksheet(params)
39
+ params[:name] ||= "Sheet #{@sheets.size + 1}"
40
+ ws = XLSX::Worksheet.new(self, params)
41
+ @sheets << ws
42
+ ws
43
+ end
44
+
45
+ def write(filename=nil)
46
+ @strings_count = 0
47
+ @strings = []
48
+
49
+ filename ||= @filename
50
+ File.unlink(filename) if File.exists?(filename)
51
+ Zip::ZipFile.open(filename, Zip::ZipFile::CREATE) do |zipfile|
52
+ zipfile.get_output_stream("[Content_Types].xml") { |f| write_content_types(f) }
53
+ zipfile.get_output_stream("_rels/.rels") { |f| write_root_rels(f) }
54
+ zipfile.get_output_stream("docProps/app.xml") { |f| write_app_properties(f) }
55
+ zipfile.get_output_stream("docProps/core.xml") { |f| write_core_properties(f) }
56
+ zipfile.get_output_stream("xl/_rels/workbook.xml.rels") { |f| write_workbook_rels(f) }
57
+ zipfile.get_output_stream("xl/workbook.xml") { |f| write_workbook(f) }
58
+ zipfile.get_output_stream("xl/styles.xml") { |f| write_styles(f) }
59
+
60
+ 0.upto(@sheets.size - 1) do |sheet_no|
61
+ zipfile.get_output_stream("xl/worksheets/sheet#{sheet_no + 1}.xml") { |f| write_worksheet(@sheets[sheet_no], f) }
62
+ end
63
+
64
+ zipfile.get_output_stream("xl/sharedStrings.xml") { |f| write_shared_strings(f) }
65
+ end
66
+ end
67
+
68
+ private
69
+ def write_content_types(f)
70
+ x = Builder::XmlMarkup.new(:target => f, :indent => 0)
71
+ x.instruct! 'xml', :version => '1.0', :encoding => 'UTF-8'
72
+ x.Types :xmlns => XMLNS_CONTENT_TYPES do |types|
73
+ types.Override :PartName => '/docProps/app.xml', :ContentType => CT_EXTPROP
74
+ 1.upto(@sheets.size) do |sheet_no|
75
+ types.Override :PartName => "/xl/worksheets/sheet#{sheet_no}.xml", :ContentType => CT_SS_WORKSHEET
76
+ end
77
+ types.Override :PartName => '/xl/workbook.xml', :ContentType => CT_SS_MAIN
78
+ types.Override :PartName => '/docProps/core.xml', :ContentType => CT_COREPROP
79
+ types.Default :Extension => 'xml', :ContentType => 'application/xml'
80
+ types.Override :PartName => '/xl/styles.xml', :ContentType => CT_SS_STYLES
81
+ types.Override :PartName => '/xl/sharedStrings.xml', :ContentType => CT_SS_SHAREDSTRINGS
82
+ types.Default :Extension => 'rels', :ContentType => CT_RELATIONSHIPS
83
+ end
84
+ end
85
+
86
+ def write_root_rels(f)
87
+ x = Builder::XmlMarkup.new(:target => f, :indent => 0)
88
+ x.instruct! 'xml', :version => '1.0', :encoding => 'UTF-8', :standalone => 'yes'
89
+ x.Relationships :xmlns => XMLNS_RELATIONSHIPS do |rels|
90
+ rels.Relationship :Id => 'rId3', :Type => REL_TYPE_EXTPROP, :Target => 'docProps/app.xml'
91
+ rels.Relationship :Id => 'rId1', :Type => REL_TYPE_OFFICEDOC, :Target => 'xl/workbook.xml'
92
+ rels.Relationship :Id => 'rId2', :Type => REL_TYPE_COREPROP, :Target => 'docProps/core.xml'
93
+ end
94
+ end
95
+
96
+ def write_core_properties(f)
97
+ modified_at = Time.now.utc
98
+
99
+ x = Builder::XmlMarkup.new(:target => f, :indent => 0)
100
+ x.instruct! 'xml', :version => '1.0', :encoding => 'UTF-8', :standalone => 'yes'
101
+ x.cp :coreProperties, 'xmlns:cp' => XMLNS_COREPROP, 'xmlns:dc' => XMLNS_DC,
102
+ 'xmlns:dcterms' => XMLNS_DCTERMS, 'xmlns:dcmitype' => XMLNS_DCMITYPE,
103
+ 'xmlns:xsi' => XMLNS_XSI do |cp|
104
+ cp.dc :creator, 'ruby-xlsx'
105
+ cp.cp :lastModifiedBy, 'ruby-xlsx'
106
+ cp.dcterms(:created, { 'xsi:type' => 'dcterms:W3CDTF' },
107
+ modified_at.strftime('%Y-%m-%dT%H:%M:%SZ'))
108
+ cp.dcterms(:modified, { 'xsi:type' => 'dcterms:W3CDTF' },
109
+ modified_at.strftime('%Y-%m-%dT%H:%M:%SZ'))
110
+ end
111
+ end
112
+
113
+ def write_app_properties(f)
114
+ x = Builder::XmlMarkup.new(:target => f, :indent => 0)
115
+ x.instruct! 'xml', :version => '1.0', :encoding => 'UTF-8', :standalone => 'yes'
116
+ x.Properties 'xmlns' => XMLNS_EXTPROP, 'xmlns:vt' => XMLNS_VT do |prop|
117
+ prop.Application 'Microsoft Macintosh Excel'
118
+ prop.DocSecurity '0'
119
+ prop.ScaleCrop 'false'
120
+ prop.HeadingPairs do |hp|
121
+ hp.vt :vector, :size => '2', :baseType => 'variant' do |v|
122
+ v.vt :variant do |var|
123
+ var.vt :lpstr, 'Worksheets'
124
+ end
125
+ v.vt :variant do |var|
126
+ var.vt :i4, @sheets.size.to_s
127
+ end
128
+ end
129
+ end
130
+ prop.TitlesOfParts do |t|
131
+ t.vt :vector, :size => @sheets.size.to_s, :baseType => 'lpstr' do |v|
132
+ @sheets.each do |sheet|
133
+ v.vt :lpstr, sheet.title
134
+ end
135
+ end
136
+ end
137
+ prop.Company ''
138
+ prop.LinksUpToDate 'false'
139
+ prop.SharedDoc 'false'
140
+ prop.HyperlinksChanged 'false'
141
+ prop.AppVersion '12.0000'
142
+ end
143
+ end
144
+
145
+ def write_workbook_rels(f)
146
+ x = Builder::XmlMarkup.new(:target => f, :indent => 0)
147
+ x.instruct! 'xml', :version => '1.0', :encoding => 'UTF-8', :standalone => 'yes'
148
+ x.Relationships :xmlns => XMLNS_RELATIONSHIPS do |rels|
149
+ id = 1
150
+ 1.upto(@sheets.size) do |sheet_no|
151
+ rels.Relationship :Id => "rId#{id}", :Type => REL_TYPE_WORKSHEET, :Target => "worksheets/sheet#{sheet_no}.xml"
152
+ id += 1
153
+ end
154
+ rels.Relationship :Id => "rId#{id}", :Type => REL_TYPE_STYLES, :Target => 'styles.xml'
155
+ id += 1
156
+ rels.Relationship :Id => "rId#{id}", :Type => REL_TYPE_CONNECTIONS, :Target => 'connections.xml'
157
+ id += 1
158
+ rels.Relationship :Id => "rId#{id}", :Type => REL_TYPE_SHAREDSTRINGS, :Target => 'sharedStrings.xml'
159
+ end
160
+ end
161
+
162
+ def write_workbook(f)
163
+ x = Builder::XmlMarkup.new(:target => f, :indent => 0)
164
+ x.instruct! 'xml', :version => '1.0', :encoding => 'UTF-8', :standalone => 'yes'
165
+ x.workbook :xmlns => XMLNS_SSXML_MAIN, 'xmlns:r' => XMLNS_OD_RELATIONSHIPS do |wb|
166
+ wb.fileVersion :appName => 'xl', :lastEdited => '4', :lowestEdited => '4', :rupBuild => '4505'
167
+ wb.workbookPr :date1904 => '1', :showInkAnnotation => '0', :autoCompressPictures => '0'
168
+ wb.bookViews do |bv|
169
+ bv.workbookView :tabRatio => '500', :xWindow => '-20', :yWindow => '-20', :windowWidth => '47120', :windowHeight => '30680', :activeTab => '1'
170
+ end
171
+ x.sheets do |sheets|
172
+ 1.upto(@sheets.count) do |sheet_no|
173
+ sheet = @sheets[sheet_no - 1]
174
+ sheets.sheet :name => sheet.title, :sheetId => sheet_no.to_s,
175
+ 'r:id' => "rId#{sheet_no}"
176
+ end
177
+ end
178
+ x.calcPr :calcId => '130407', :concurrentCalc => '0'
179
+ x.extLst do |exts|
180
+ exts.ext 'xmlns:mx' => XMLNS_MAC_EXCEL, :uri => XMLNS_MAC_EXCEL do |mx|
181
+ mx.mx :ArchID, :Flags => '2'
182
+ end
183
+ end
184
+ end
185
+ end
186
+
187
+ def write_worksheet(sheet, f)
188
+ min_col = sheet.rows.map { |r| r.min_col }.min + 1
189
+ max_col = sheet.rows.map { |r| r.max_col }.max + 1
190
+ spans = "#{min_col}:#{max_col}"
191
+ dimension = "#{XLSX::Cell.cell_name(sheet.min_row + 1, min_col)}:#{XLSX::Cell.cell_name(sheet.max_row + 1, max_col)}"
192
+
193
+ x = Builder::XmlMarkup.new(:target => f, :indent => 0)
194
+ x.instruct! 'xml', :version => '1.0', :encoding => 'UTF-8', :standalone => 'yes'
195
+ f.write("\n")
196
+ x.worksheet 'xmlns:mc' => XMLNS_MARKUP_COMPATIBILITY,
197
+ 'mc:PreserveAttributes' => 'mv:*',
198
+ 'mc:Ignorable' => 'mv',
199
+ 'xmlns:r' => XMLNS_OD_RELATIONSHIPS,
200
+ 'xmlns:mv' => XMLNS_MAC_VML,
201
+ 'xmlns' => XMLNS_SSXML_MAIN do |ws|
202
+ ws.dimension :ref => dimension
203
+ ws.sheetViews do |sviews|
204
+ sviews.sheetView :workbookViewId => '0' do |sv|
205
+ sv.selection :activeCell => 'A1', :sqref => 'A1'
206
+ end
207
+ end
208
+ ws.sheetFormatPr :defaultRowHeight => '13', :baseColWidth => '10'
209
+ ws.sheetData do |sd|
210
+ sheet.rows.each do |row|
211
+ cells = row.to_a
212
+ sd.row :r => (row.row_number + 1).to_s, :spans => spans do |r|
213
+ row.each do |cell|
214
+ value = cell.value
215
+ c_params = { :r => cell.name }
216
+ c_params[:t] = 's' unless value.is_a?(Numeric)
217
+ r.c c_params do |c|
218
+ case value
219
+ when Numeric
220
+ c.v(value.to_s)
221
+ else
222
+ @strings << value.to_s
223
+ @strings_count += 1
224
+ c.v((@strings.size - 1).to_s)
225
+ end
226
+ end
227
+ end
228
+ end
229
+ end
230
+ end
231
+ ws.sheetCalcPr :fullCalcOnLoad => '1'
232
+ ws.phoneticPr :fontId => '1', :type => 'noConversion'
233
+ ws.pageMargins :left => '0.75', :bottom => '1', :header => '0.5', :footer => '0.5', :right => '0.75', :top => '1'
234
+ ws.pageSetup :horizontalDpi => '4294967292', :orientation => 'portrait', :verticalDpi => '4294967292'
235
+ end
236
+ end
237
+
238
+ def write_shared_strings(f)
239
+ x = Builder::XmlMarkup.new(:target => f, :indent => 0)
240
+ x.instruct! 'xml', :version => '1.0', :encoding => 'UTF-8'
241
+ x.sst :count => @strings_count, :uniqueCount => @strings.size, :xmlns => XMLNS_SSXML_MAIN do |sst|
242
+ @strings.each do |string|
243
+ sst.si do |si|
244
+ si.t string
245
+ # Unnecessary?
246
+ # si.phoneticPr :fontId => '1', :type => 'noConversion'
247
+ end
248
+ end
249
+ end
250
+ end
251
+
252
+ def write_styles(f)
253
+ x = Builder::XmlMarkup.new(:target => f, :indent => 0)
254
+ x.instruct! 'xml', :version => '1.0', :encoding => 'UTF-8'
255
+ x.styleSheet :xmlns => XMLNS_SSXML_MAIN do |ss|
256
+ ss.fonts :count => '2' do |fonts|
257
+ fonts.font do |font|
258
+ font.sz :val => '10'
259
+ font.name :val => 'Verdana'
260
+ end
261
+ fonts.font do |font|
262
+ font.sz :val => '8'
263
+ font.name :val => 'Verdana'
264
+ end
265
+ end
266
+ ss.fills :count => '2' do |fills|
267
+ fills.fill { |fill| fill.patternFill :patternType => 'none' }
268
+ fills.fill { |fill| fill.patternFill :patternType => 'gray125' }
269
+ end
270
+ ss.borders :count => '1' do |borders|
271
+ borders.border do |b|
272
+ b.left
273
+ b.right
274
+ b.top
275
+ b.bottom
276
+ b.diagonal
277
+ end
278
+ end
279
+ ss.cellStyleXfs :count => 1 do |cs|
280
+ cs.xf :fontId => '0', :numFmtId => '0', :borderId => '0', :fillId => '0'
281
+ end
282
+ ss.cellXfs :count => 1 do |cs|
283
+ cs.xf :fontId => '0', :numFmtId => '0', :borderId => '0', :xfId => '0', :fillId => '0'
284
+ end
285
+ ss.cellStyles :count => 1 do |cs|
286
+ cs.cellStyle :name => 'Normal', :xfId => '0', :builtinId => '0'
287
+ end
288
+ ss.dxfs :count => '0'
289
+ ss.tableStyles :count => '0', :defaultTableStyle => 'TableStyleMedium9'
290
+ end
291
+ end
292
+
293
+ XMLNS_RELATIONSHIPS = 'http://schemas.openxmlformats.org/package/2006/relationships'
294
+ XMLNS_COREPROP = 'http://schemas.openxmlformats.org/package/2006/metadata/core-properties'
295
+ XMLNS_EXTPROP = 'http://schemas.openxmlformats.org/officeDocument/2006/extended-properties'
296
+ XMLNS_VT = 'http://schemas.openxmlformats.org/officeDocument/2006/docPropsVTypes'
297
+ XMLNS_DC = 'http://purl.org/dc/elements/1.1/'
298
+ XMLNS_DCTERMS = 'http://purl.org/dc/terms/'
299
+ XMLNS_DCMITYPE = 'http://purl.org/dc/dcmitype/'
300
+ XMLNS_XSI = 'http://www.w3.org/2001/XMLSchema-instance'
301
+ XMLNS_SSXML_MAIN = 'http://schemas.openxmlformats.org/spreadsheetml/2006/main'
302
+ XMLNS_OD_RELATIONSHIPS = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships'
303
+ XMLNS_MAC_EXCEL = 'http://schemas.microsoft.com/office/mac/excel/2008/main'
304
+ XMLNS_CONTENT_TYPES = 'http://schemas.openxmlformats.org/package/2006/content-types'
305
+ XMLNS_MARKUP_COMPATIBILITY = 'http://schemas.openxmlformats.org/markup-compatibility/2006'
306
+ XMLNS_MAC_VML = 'urn:schemas-microsoft-com:mac:vml'
307
+
308
+ CT_EXTPROP = 'application/vnd.openxmlformats-officedocument.extended-properties+xml'
309
+ CT_SS_WORKSHEET = 'application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml'
310
+ CT_SS_MAIN = 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml'
311
+ CT_COREPROP = 'application/vnd.openxmlformats-package.core-properties+xml'
312
+ CT_THEME = 'application/vnd.openxmlformats-officedocument.theme+xml'
313
+ CT_SS_STYLES = 'application/vnd.openxmlformats-officedocument.spreadsheetml.styles+xml'
314
+ CT_SS_SHAREDSTRINGS = 'application/vnd.openxmlformats-officedocument.spreadsheetml.sharedStrings+xml'
315
+ CT_RELATIONSHIPS = 'application/vnd.openxmlformats-package.relationships+xml'
316
+
317
+ REL_TYPE_EXTPROP = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/extended-properties'
318
+ REL_TYPE_OFFICEDOC = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/officeDocument'
319
+ REL_TYPE_THUMBNAIL = 'http://schemas.openxmlformats.org/package/2006/relationships/metadata/thumbnail'
320
+ REL_TYPE_COREPROP = 'http://schemas.openxmlformats.org/package/2006/relationships/metadata/core-properties'
321
+ REL_TYPE_STYLES = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/styles'
322
+ REL_TYPE_WORKSHEET = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/worksheet'
323
+ REL_TYPE_THEME = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/theme'
324
+ REL_TYPE_CONNECTIONS = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/connections'
325
+ REL_TYPE_SHAREDSTRINGS = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/sharedStrings'
326
+
327
+ end
328
+ end
@@ -0,0 +1,63 @@
1
+ # Copyright (C) 2009 Brian Buchanan. All rights reserved.
2
+ #
3
+ # Redistribution and use in source and binary forms, with or without
4
+ # modification, are permitted provided that the following conditions
5
+ # are met:
6
+ # 1. Redistributions of source code must retain the above copyright
7
+ # notice, this list of conditions and the following disclaimer.
8
+ # 2. Redistributions in binary form must reproduce the above copyright
9
+ # notice, this list of conditions and the following disclaimer in the
10
+ # documentation and/or other materials provided with the distribution.
11
+ #
12
+ # THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND
13
+ # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
14
+ # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
15
+ # ARE DISCLAIMED. IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE
16
+ # FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
17
+ # DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
18
+ # OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
19
+ # HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
20
+ # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
21
+ # OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
22
+ # SUCH DAMAGE.
23
+
24
+ module XLSX
25
+ class Worksheet
26
+ attr_accessor :title
27
+ attr_reader :min_row, :max_row
28
+
29
+ def initialize(workbook, params={})
30
+ @workbook = workbook
31
+ @title = params[:name] || ''
32
+ @rows = {}
33
+ @min_row = 0
34
+ @max_row = 0
35
+ end
36
+
37
+ def row(row_number)
38
+ @rows[row_number]
39
+ end
40
+
41
+ def rows
42
+ @rows.keys.sort.map { |n| @rows[n] }
43
+ end
44
+
45
+ def update_row(row_number, *values)
46
+ row = get_row(row_number)
47
+ 0.upto(values.length - 1) do |col|
48
+ row[col] = values[col]
49
+ end
50
+ row
51
+ end
52
+
53
+ def get_row(row_number)
54
+ raise "Row number must be a non-negative integer" unless row_number.is_a?(Integer) && row_number >= 0
55
+ r = row(row_number)
56
+ return r unless r.nil?
57
+
58
+ @min_row = row_number if row_number < @min_row
59
+ @max_row = row_number if row_number > @max_row
60
+ @rows[row_number] = Row.new(self, row_number)
61
+ end
62
+ end
63
+ end
metadata ADDED
@@ -0,0 +1,82 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: xlsx
3
+ version: !ruby/object:Gem::Version
4
+ version: "0.1"
5
+ platform: ruby
6
+ authors:
7
+ - Brian Buchanan
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2010-10-21 00:00:00 -07:00
13
+ default_executable:
14
+ dependencies:
15
+ - !ruby/object:Gem::Dependency
16
+ name: builder
17
+ type: :runtime
18
+ version_requirement:
19
+ version_requirements: !ruby/object:Gem::Requirement
20
+ requirements:
21
+ - - ">="
22
+ - !ruby/object:Gem::Version
23
+ version: 2.1.2
24
+ version:
25
+ - !ruby/object:Gem::Dependency
26
+ name: rubyzip
27
+ type: :runtime
28
+ version_requirement:
29
+ version_requirements: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: 0.9.1
34
+ version:
35
+ description: XLSX is a Ruby library for writing simple XLSX-format Excel documents.
36
+ email: bwb@holo.org
37
+ executables: []
38
+
39
+ extensions: []
40
+
41
+ extra_rdoc_files:
42
+ - README
43
+ - LICENSE
44
+ files:
45
+ - README
46
+ - LICENSE
47
+ - lib/xlsx.rb
48
+ - lib/xlsx/workbook.rb
49
+ - lib/xlsx/worksheet.rb
50
+ - lib/xlsx/row.rb
51
+ - lib/xlsx/cell.rb
52
+ has_rdoc: true
53
+ homepage: http://github.com/bwbuchanan/xlsx
54
+ licenses: []
55
+
56
+ post_install_message:
57
+ rdoc_options:
58
+ - --inline-source
59
+ - --charset=UTF-8
60
+ require_paths:
61
+ - lib
62
+ required_ruby_version: !ruby/object:Gem::Requirement
63
+ requirements:
64
+ - - ">="
65
+ - !ruby/object:Gem::Version
66
+ version: "0"
67
+ version:
68
+ required_rubygems_version: !ruby/object:Gem::Requirement
69
+ requirements:
70
+ - - ">="
71
+ - !ruby/object:Gem::Version
72
+ version: "0"
73
+ version:
74
+ requirements: []
75
+
76
+ rubyforge_project:
77
+ rubygems_version: 1.3.5
78
+ signing_key:
79
+ specification_version: 2
80
+ summary: XLSX is a Ruby library for writing simple XLSX-format Excel documents.
81
+ test_files: []
82
+