lib/rspreadsheet/cell.rb in rspreadsheet-0.2.7 vs lib/rspreadsheet/cell.rb in rspreadsheet-0.2.9

- old
+ new

@@ -1,11 +1,12 @@ # @markup markdown # @author Jakub Tesinsky -# @titel rspreadsheet Cell +# @title rspreadsheet Cell require 'andand' require 'rspreadsheet/xml_tied' +require 'date' module Rspreadsheet @@ -70,42 +71,47 @@ detach_if_needed if self.mode == :regular gt = guess_cell_type(avalue) case when gt == nil then raise 'This value type is not storable to cell' - when gt == Float - set_type_attribute('float') + when gt == Float then remove_all_value_attributes_and_content(xmlnode) + set_type_attribute('float') Tools.set_ns_attribute(xmlnode,'office','value', avalue.to_s) xmlnode << Tools.prepare_ns_node('text','p', avalue.to_f.to_s) when gt == String then - set_type_attribute('string') remove_all_value_attributes_and_content(xmlnode) + set_type_attribute('string') xmlnode << Tools.prepare_ns_node('text','p', avalue.to_s) when gt == Date then - set_type_attribute('date') remove_all_value_attributes_and_content(xmlnode) + set_type_attribute('date') Tools.set_ns_attribute(xmlnode,'office','date-value', avalue.strftime('%Y-%m-%d')) xmlnode << Tools.prepare_ns_node('text','p', avalue.strftime('%Y-%m-%d')) - when gt == :percentage - set_type_attribute('percentage') + when gt == :percentage then remove_all_value_attributes_and_content(xmlnode) + set_type_attribute('percentage') Tools.set_ns_attribute(xmlnode,'office','value', '%0.2d%' % avalue.to_f) xmlnode << Tools.prepare_ns_node('text','p', (avalue.to_f*100).round.to_s+'%') end else raise "Unknown cell mode #{self.mode}" end end def set_type_attribute(typestring) Tools.set_ns_attribute(xmlnode,'office','value-type',typestring) + Tools.set_ns_attribute(xmlnode,'calcext','value-type',typestring) end - def remove_all_value_attributes_and_content(node) + def remove_all_value_attributes_and_content(node=xmlnode) if att = Tools.get_ns_attribute(node, 'office','value') then att.remove! end if att = Tools.get_ns_attribute(node, 'office','date-value') then att.remove! end + if att = Tools.get_ns_attribute(node, 'table','formula') then att.remove! end node.content='' end + def remove_all_type_attributes + set_type_attribute(nil) + end def relative(rowdiff,coldiff) @worksheet.cells(self.rowi+rowdiff, self.coli+coldiff) end def type gct = guess_cell_type @@ -113,10 +119,11 @@ when gct == Float then :float when gct == String then :string when gct == Date then :date when gct == :percentage then :percentage when gct == :unassigned then :unassigned + when gct == NilClass then :empty when gct == nil then :unknown else :unknown end end def guess_cell_type(avalue=nil) @@ -159,13 +166,15 @@ end else # without value we just beleive typeguess typeguess end else # it not have a typeguess - if (String(avalue) rescue false) # convertible to String + if (avalue.nil?) # if nil then nil + NilClass + elsif (String(avalue) rescue false) # convertible to String String - else + else # giving up nil end end elsif valueguess == Float and xmlnode.andand.attributes['value-type'] == 'percentage' result = :percentage @@ -176,10 +185,28 @@ @format ||= CellFormat.new(self) end def address Tools.convert_cell_coordinates_to_address(coordinates) end + + def formula + rawformula = Tools.get_ns_attribute(xmlnode,'table','formula',nil).andand.value + if rawformula.nil? + nil + elsif rawformula.match(/^of:(.*)$/) + $1 + else + raise "Mischmatched value in table:formula attribute - does not start with of: (#{rawformula.to_s})" + end + end + def formula=(formulastring) + detach_if_needed + raise 'Formula string must begin with "=" character' unless formulastring[0,1] == '=' + remove_all_value_attributes_and_content(xmlnode) + remove_all_type_attributes + Tools.set_ns_attribute(xmlnode,'table','formula','of:'+formulastring.to_s) + end end # proxy object to allow cell.format syntax. Also handles all logic for formats. # @private @@ -207,10 +234,11 @@ def bold=(value); set_text_style_node_attribute('font-weight', value ? 'bold' : 'normal') end def italic=(value); set_text_style_node_attribute('font-style', value ? 'italic' : 'normal') end def color=(value); set_text_style_node_attribute('color', value) end def font_size=(value);set_text_style_node_attribute('font-size', value) end def set_text_style_node_attribute(attribute_name,value) + @cell.detach if @cell.mode != :regular if text_style_node.nil? self.create_text_style_node raise 'Style node was not correctly initialized' if text_style_node.nil? end Tools.set_ns_attribute(text_style_node,'fo',attribute_name,value) @@ -248,20 +276,25 @@ automatic_styles_node << anode raise 'Style node was not correctly initialized' if style_node.nil? end def unused_cell_style_name - last = cellnode.doc.root.find('./office:automatic-styles/style:style'). + last = (cellnode.nil? ? [] : cellnode.doc.root.find('./office:automatic-styles/style:style')). collect {|node| node['name']}. collect{ |name| /^ce(\d*)$/.match(name); $1.andand.to_i}. compact.max || 0 "ce#{last+1}" end - def automatic_styles_node; cellnode.doc.root.find("./office:automatic-styles").first end - def style_name; Tools.get_ns_attribute_value(cellnode,'table','style-name') end - def style_node; cellnode.doc.root.find("./office:automatic-styles/style:style[@style:name=\"#{style_name}\"]").first end - def text_style_node; cellnode.doc.root.find("./office:automatic-styles/style:style[@style:name=\"#{style_name}\"]/style:text-properties").first end - def cell_style_node; cellnode.doc.root.find("./office:automatic-styles/style:style[@style:name=\"#{style_name}\"]/style:table-cell-properties").first end + def automatic_styles_node; style_node_with_partial_xpath('') end + def style_name; Tools.get_ns_attribute_value(cellnode,'table','style-name',nil) end + def style_node; style_node_with_partial_xpath("/style:style[@style:name=\"#{style_name}\"]") end + def text_style_node; style_node_with_partial_xpath("/style:style[@style:name=\"#{style_name}\"]/style:text-properties") end + def cell_style_node; style_node_with_partial_xpath("/style:style[@style:name=\"#{style_name}\"]/style:table-cell-properties") end + def style_node_with_partial_xpath(xpath) + return nil if cellnode.nil? + cellnode.doc.root.find("./office:automatic-styles#{xpath}").first + end + end end