lib/roo/excel.rb in roo-1.3.11 vs lib/roo/excel.rb in roo-1.9.0

- old
+ new

@@ -1,6 +1,9 @@ +require 'rubygems' require 'spreadsheet' +#require 'lib/roo/generic_spreadsheet' +#require 'parseexcel' CHARGUESS = begin require 'charguess' true rescue LoadError => e false @@ -10,10 +13,30 @@ # base dates so if the file is a 1904 base date then # dates are off by a day. 1900 base dates work fine module Spreadsheet module Excel class Row < Spreadsheet::Row + def _date data # :nodoc: + return data if data.is_a?(Date) + date = @worksheet.date_base + data.to_i + if LEAP_ERROR > @worksheet.date_base + date -= 1 + end + date + end + public :_datetime + end + end +end + +#===================================================================== +# TODO: +# redefinition of this method, the method in the spreadsheet gem has a bug +# redefinition can be removed, if spreadsheet does it in the correct way +module Spreadsheet + module Excel + class Row < Spreadsheet::Row def _datetime data # :nodoc: return data if data.is_a?(DateTime) base = @worksheet.date_base date = base + data.to_f hour = (data % 1) * 24 @@ -36,61 +59,26 @@ if LEAP_ERROR > base date -= 1 end DateTime.new(date.year, date.month, date.day, hour, min, sec) end - public :_date - public :_datetime end - # patch for ruby-spreadsheet parsing formulas - class Reader - def read_formula worksheet, addr, work - row, column, xf, rtype, rval, rcheck, opts = work.unpack 'v3CxCx3v2' - formula = Formula.new - formula.shared = (opts & 0x08) > 0 - formula.data = work[20..-1] - if rcheck != 0xffff || rtype > 3 - value, = work.unpack 'x6E' - unless value - # on architectures where sizeof(double) > 8 - value, = work.unpack 'x6e' - end - formula.value = value - elsif rtype == 0 - pos, op, len, work = get_next_chunk - if op == :string - formula.value = client read_string(work, 2), @workbook.encoding - else - # This seems to work but I don't know why :). It at least - # seems to correct the case we saw but doubtful it's the right fix - formula.value = client read_string(work[10..-1], 2), @workbook.encoding - end - elsif rtype == 1 - formula.value = rval > 0 - elsif rtype == 2 - formula.value = Error.new rval - else - # leave the Formula value blank - end - set_cell worksheet, row, column, xf, formula - end - end end end +#===================================================================== - # ruby-spreadsheet has a font object so we're extending it # with our own functionality but still providing full access # to the user for other font information module ExcelFontExtensions def bold?(*args) #From ruby-spreadsheet doc: 100 <= weight <= 1000, bold => 700, normal => 400 case weight when 700 - true + true else - false + false end end def italic? italic @@ -225,10 +213,26 @@ sheet = @default_sheet unless sheet read_cells(sheet) unless @cells_read[sheet] @cell[sheet].inspect end + # returns the row,col values of the labelled cell + # (nil,nil) if label is not defined + # sheet parameter is not really needed because label names are global + # to the whole spreadsheet + def label(labelname,sheet=nil) + sheet = @default_sheet unless sheet + read_cells(sheet) unless @cells_read[sheet] + if @labels.has_key? labelname + return @labels[labelname][1].to_i, + GenericSpreadsheet.letter_to_number(@labels[labelname][2]), + @labels[labelname][0] + else + return nil,nil,nil + end + end + private # converts name of a sheet to index (0,1,2,..) def sheet_no(name) return name-1 if name.kind_of?(Fixnum) @@ -412,11 +416,11 @@ datetime = row._datetime(cell) else datetime = row.datetime(idx) end if datetime.hour != 0 or - datetime.min != 0 or - datetime.sec != 0 + datetime.min != 0 or + datetime.sec != 0 value_type = :datetime value = datetime else value_type = :date if row.at(idx).class == Spreadsheet::Formula