Reworks the common xls files and attempt to fix bug 18886 excel5 files are truncated when imported

git-svn-id: https://svn.code.sf.net/p/lazarus-ccr/svn@1654 8e941d3f-bd1b-0410-a28a-d453659cc2b4
This commit is contained in:
sekelsenmat
2011-05-29 17:21:51 +00:00
parent fdc4538c45
commit 948839a79a
6 changed files with 119 additions and 99 deletions

View File

@ -18,7 +18,7 @@
<CompilerPath Value="$(CompPath)"/> <CompilerPath Value="$(CompPath)"/>
</Other> </Other>
</CompilerOptions> </CompilerOptions>
<Files Count="20"> <Files Count="19">
<Item1> <Item1>
<Filename Value="fpolestorage.pas"/> <Filename Value="fpolestorage.pas"/>
<UnitName Value="fpolestorage"/> <UnitName Value="fpolestorage"/>
@ -95,10 +95,6 @@
<Filename Value="fpsconvencoding.pas"/> <Filename Value="fpsconvencoding.pas"/>
<UnitName Value="fpsconvencoding"/> <UnitName Value="fpsconvencoding"/>
</Item19> </Item19>
<Item20>
<Filename Value="xlsbiffcommon.pas"/>
<UnitName Value="xlsbiffcommon"/>
</Item20>
</Files> </Files>
<Type Value="RunAndDesignTime"/> <Type Value="RunAndDesignTime"/>
<RequiredPkgs Count="1"> <RequiredPkgs Count="1">

View File

@ -11,7 +11,7 @@ uses
xlsbiff5, xlsbiff8, xlsxooxml, fpsutils, fpszipper, uvirtuallayer_types, xlsbiff5, xlsbiff8, xlsxooxml, fpsutils, fpszipper, uvirtuallayer_types,
uvirtuallayer, uvirtuallayer_ole, uvirtuallayer_ole_helpers, uvirtuallayer, uvirtuallayer_ole, uvirtuallayer_ole_helpers,
uvirtuallayer_ole_types, uvirtuallayer_stream, fpolebasic, xlscommon, uvirtuallayer_ole_types, uvirtuallayer_stream, fpolebasic, xlscommon,
fpsconvencoding, xlsbiffcommon, LazarusPackageIntf; fpsconvencoding, LazarusPackageIntf;
implementation implementation

View File

@ -101,7 +101,7 @@ type
{ TsSpreadBIFF5Writer } { TsSpreadBIFF5Writer }
TsSpreadBIFF5Writer = class(TsCustomSpreadWriter) TsSpreadBIFF5Writer = class(TsSpreadBIFFWriter)
private private
WorkBookEncoding: TsEncoding; WorkBookEncoding: TsEncoding;
function FEKindToExcelID(AElement: TFEKind; var AParamsNum: Byte; var AExtra: Word): Byte; function FEKindToExcelID(AElement: TFEKind; var AParamsNum: Byte; var AExtra: Word): Byte;
@ -116,7 +116,7 @@ type
procedure WriteBOF(AStream: TStream; ADataType: Word); procedure WriteBOF(AStream: TStream; ADataType: Word);
function WriteBoundsheet(AStream: TStream; ASheetName: string): Int64; function WriteBoundsheet(AStream: TStream; ASheetName: string): Int64;
procedure WriteCodepage(AStream: TStream; AEncoding: TsEncoding); procedure WriteCodepage(AStream: TStream; AEncoding: TsEncoding);
procedure WriteDimensions(AStream: TStream); procedure WriteDimensions(AStream: TStream; AWorksheet: TsWorksheet);
procedure WriteEOF(AStream: TStream); procedure WriteEOF(AStream: TStream);
procedure WriteFont(AStream: TStream; AFont: TFPCustomFont); procedure WriteFont(AStream: TStream; AFont: TFPCustomFont);
procedure WriteRPNFormula(AStream: TStream; const ARow, ACol: Word; const AFormula: TsRPNFormula); override; procedure WriteRPNFormula(AStream: TStream; const ARow, ACol: Word; const AFormula: TsRPNFormula); override;
@ -445,7 +445,7 @@ begin
WriteIndex(AStream); WriteIndex(AStream);
WriteDimensions(AStream); WriteDimensions(AStream, AData.GetWorksheetByIndex(i));
WriteWindow2(AStream, True); WriteWindow2(AStream, True);
@ -560,7 +560,9 @@ end;
* nm = (rl - rf - 1) / 32 + 1 (using integer division) * nm = (rl - rf - 1) / 32 + 1 (using integer division)
* *
*******************************************************************} *******************************************************************}
procedure TsSpreadBIFF5Writer.WriteDimensions(AStream: TStream); procedure TsSpreadBIFF5Writer.WriteDimensions(AStream: TStream; AWorksheet: TsWorksheet);
var
lLastCol, lLastRow: Word;
begin begin
{ BIFF Record header } { BIFF Record header }
AStream.WriteWord(WordToLE(INT_EXCEL_ID_DIMENSIONS)); AStream.WriteWord(WordToLE(INT_EXCEL_ID_DIMENSIONS));
@ -570,13 +572,15 @@ begin
AStream.WriteWord(0); AStream.WriteWord(0);
{ Index to last used row, increased by 1 } { Index to last used row, increased by 1 }
AStream.WriteWord(33); lLastRow := Word(GetLastRowIndex(AWorksheet)+1);
AStream.WriteWord(WordToLE(lLastRow)); // Old dummy value: 33
{ Index to first used column } { Index to first used column }
AStream.WriteWord(0); AStream.WriteWord(0);
{ Index to last used column, increased by 1 } { Index to last used column, increased by 1 }
AStream.WriteWord(10); lLastCol := Word(GetLastColIndex(AWorksheet)+1);
AStream.WriteWord(WordToLE(lLastCol)); // Old dummy value: 10
{ Not used } { Not used }
AStream.WriteWord(0); AStream.WriteWord(0);

View File

@ -53,7 +53,7 @@ interface
uses uses
Classes, SysUtils, fpcanvas, Classes, SysUtils, fpcanvas,
fpspreadsheet, xlsbiffcommon, fpspreadsheet, xlscommon,
{$ifdef USE_NEW_OLE} {$ifdef USE_NEW_OLE}
fpolebasic, fpolebasic,
{$else} {$else}
@ -117,7 +117,7 @@ type
{ Record writing methods } { Record writing methods }
procedure WriteBOF(AStream: TStream; ADataType: Word); procedure WriteBOF(AStream: TStream; ADataType: Word);
function WriteBoundsheet(AStream: TStream; ASheetName: string): Int64; function WriteBoundsheet(AStream: TStream; ASheetName: string): Int64;
procedure WriteDimensions(AStream: TStream); procedure WriteDimensions(AStream: TStream; AWorksheet: TsWorksheet);
procedure WriteEOF(AStream: TStream); procedure WriteEOF(AStream: TStream);
procedure WriteFont(AStream: TStream; AFont: TFPCustomFont); procedure WriteFont(AStream: TStream; AFont: TFPCustomFont);
procedure WriteFormula(AStream: TStream; const ARow, ACol: Word; const AFormula: TsFormula); override; procedure WriteFormula(AStream: TStream; const ARow, ACol: Word; const AFormula: TsFormula); override;
@ -517,7 +517,7 @@ begin
WriteIndex(AStream); WriteIndex(AStream);
WriteDimensions(AStream); WriteDimensions(AStream, AData.GetWorksheetByIndex(i));
WriteWindow2(AStream, True); WriteWindow2(AStream, True);
@ -618,7 +618,10 @@ end;
* nm = (rl - rf - 1) / 32 + 1 (using integer division) * nm = (rl - rf - 1) / 32 + 1 (using integer division)
* *
*******************************************************************} *******************************************************************}
procedure TsSpreadBIFF8Writer.WriteDimensions(AStream: TStream); procedure TsSpreadBIFF8Writer.WriteDimensions(AStream: TStream; AWorksheet: TsWorksheet);
var
lLastCol: Word;
lLastRow: Integer;
begin begin
{ BIFF Record header } { BIFF Record header }
AStream.WriteWord(WordToLE(INT_EXCEL_ID_DIMENSIONS)); AStream.WriteWord(WordToLE(INT_EXCEL_ID_DIMENSIONS));
@ -628,13 +631,15 @@ begin
AStream.WriteDWord(DWordToLE(0)); AStream.WriteDWord(DWordToLE(0));
{ Index to last used row, increased by 1 } { Index to last used row, increased by 1 }
AStream.WriteDWord(DWordToLE(33)); lLastRow := GetLastRowIndex(AWorksheet)+1;
AStream.WriteDWord(DWordToLE(lLastRow)); // Old dummy value: 33
{ Index to first used column } { Index to first used column }
AStream.WriteWord(WordToLE(0)); AStream.WriteWord(WordToLE(0));
{ Index to last used column, increased by 1 } { Index to last used column, increased by 1 }
AStream.WriteWord(WordToLE(10)); lLastCol := GetLastColIndex(AWorksheet)+1;
AStream.WriteWord(WordToLE(lLastCol)); // Old dummy value: 10
{ Not used } { Not used }
AStream.WriteWord(WordToLE(0)); AStream.WriteWord(WordToLE(0));

View File

@ -1,80 +0,0 @@
unit xlsbiffcommon;
{$ifdef fpc}
{$mode delphi}
{$endif}
interface
uses
Classes, SysUtils,
fpspreadsheet,
fpsutils;
{ Excel Constants which don't change across versions }
const
{ Built In Color Pallete Indexes }
BUILT_IN_COLOR_PALLETE_BLACK = $08; // 000000H
BUILT_IN_COLOR_PALLETE_WHITE = $09; // FFFFFFH
BUILT_IN_COLOR_PALLETE_RED = $0A; // FF0000H
BUILT_IN_COLOR_PALLETE_GREEN = $0B; // 00FF00H
BUILT_IN_COLOR_PALLETE_BLUE = $0C; // 0000FFH
BUILT_IN_COLOR_PALLETE_YELLOW = $0D; // FFFF00H
BUILT_IN_COLOR_PALLETE_MAGENTA = $0E; // FF00FFH
BUILT_IN_COLOR_PALLETE_CYAN = $0F; // 00FFFFH
BUILT_IN_COLOR_PALLETE_DARK_RED = $10; // 800000H
BUILT_IN_COLOR_PALLETE_DARK_GREEN= $11; // 008000H
BUILT_IN_COLOR_PALLETE_DARK_BLUE = $12; // 000080H
BUILT_IN_COLOR_PALLETE_OLIVE = $13; // 808000H
BUILT_IN_COLOR_PALLETE_PURPLE = $14; // 800080H
BUILT_IN_COLOR_PALLETE_TEAL = $15; // 008080H
BUILT_IN_COLOR_PALLETE_SILVER = $16; // C0C0C0H
BUILT_IN_COLOR_PALLETE_GREY = $17; // 808080H
EXTRA_COLOR_PALETTE_GREY10PCT = $18; // E6E6E6H
EXTRA_COLOR_PALETTE_GREY20PCT = $19; // E6E6E6H
type
{ TsSpreadBIFFReader }
TsSpreadBIFFReader = class(TsCustomSpreadReader)
protected
end;
{ TsSpreadBIFFWriter }
TsSpreadBIFFWriter = class(TsCustomSpreadWriter)
protected
function FPSColorToEXCELPallete(AColor: TsColor): Word;
end;
implementation
function TsSpreadBIFFWriter.FPSColorToEXCELPallete(AColor: TsColor): Word;
begin
case AColor of
scBlack: Result := BUILT_IN_COLOR_PALLETE_BLACK;
scWhite: Result := BUILT_IN_COLOR_PALLETE_WHITE;
scRed: Result := BUILT_IN_COLOR_PALLETE_RED;
scGREEN: Result := BUILT_IN_COLOR_PALLETE_GREEN;
scBLUE: Result := BUILT_IN_COLOR_PALLETE_BLUE;
scYELLOW: Result := BUILT_IN_COLOR_PALLETE_YELLOW;
scMAGENTA: Result := BUILT_IN_COLOR_PALLETE_MAGENTA;
scCYAN: Result := BUILT_IN_COLOR_PALLETE_CYAN;
scDarkRed: Result := BUILT_IN_COLOR_PALLETE_DARK_RED;
scDarkGreen: Result := BUILT_IN_COLOR_PALLETE_DARK_GREEN;
scDarkBlue: Result := BUILT_IN_COLOR_PALLETE_DARK_BLUE;
scOLIVE: Result := BUILT_IN_COLOR_PALLETE_OLIVE;
scPURPLE: Result := BUILT_IN_COLOR_PALLETE_PURPLE;
scTEAL: Result := BUILT_IN_COLOR_PALLETE_TEAL;
scSilver: Result := BUILT_IN_COLOR_PALLETE_SILVER;
scGrey: Result := BUILT_IN_COLOR_PALLETE_GREY;
//
scGrey10pct: Result := EXTRA_COLOR_PALETTE_GREY10PCT;
scGrey20pct: Result := EXTRA_COLOR_PALETTE_GREY20PCT;
end;
end;
end.

View File

@ -1,9 +1,16 @@
unit xlscommon; unit xlscommon;
{$mode objfpc}{$H+} {$ifdef fpc}
{$mode delphi}
{$endif}
interface interface
uses
Classes, SysUtils,
fpspreadsheet,
fpsutils;
const const
{ Formula constants TokenID values } { Formula constants TokenID values }
@ -31,7 +38,95 @@ const
INT_EXCEL_SHEET_FUNC_ABS = 24; INT_EXCEL_SHEET_FUNC_ABS = 24;
INT_EXCEL_SHEET_FUNC_ROUND = 27; INT_EXCEL_SHEET_FUNC_ROUND = 27;
{ Built In Color Pallete Indexes }
BUILT_IN_COLOR_PALLETE_BLACK = $08; // 000000H
BUILT_IN_COLOR_PALLETE_WHITE = $09; // FFFFFFH
BUILT_IN_COLOR_PALLETE_RED = $0A; // FF0000H
BUILT_IN_COLOR_PALLETE_GREEN = $0B; // 00FF00H
BUILT_IN_COLOR_PALLETE_BLUE = $0C; // 0000FFH
BUILT_IN_COLOR_PALLETE_YELLOW = $0D; // FFFF00H
BUILT_IN_COLOR_PALLETE_MAGENTA = $0E; // FF00FFH
BUILT_IN_COLOR_PALLETE_CYAN = $0F; // 00FFFFH
BUILT_IN_COLOR_PALLETE_DARK_RED = $10; // 800000H
BUILT_IN_COLOR_PALLETE_DARK_GREEN= $11; // 008000H
BUILT_IN_COLOR_PALLETE_DARK_BLUE = $12; // 000080H
BUILT_IN_COLOR_PALLETE_OLIVE = $13; // 808000H
BUILT_IN_COLOR_PALLETE_PURPLE = $14; // 800080H
BUILT_IN_COLOR_PALLETE_TEAL = $15; // 008080H
BUILT_IN_COLOR_PALLETE_SILVER = $16; // C0C0C0H
BUILT_IN_COLOR_PALLETE_GREY = $17; // 808080H
EXTRA_COLOR_PALETTE_GREY10PCT = $18; // E6E6E6H
EXTRA_COLOR_PALETTE_GREY20PCT = $19; // E6E6E6H
type
{ TsSpreadBIFFReader }
TsSpreadBIFFReader = class(TsCustomSpreadReader)
protected
end;
{ TsSpreadBIFFWriter }
TsSpreadBIFFWriter = class(TsCustomSpreadWriter)
protected
FLastRow, FLastCol: Integer;
function FPSColorToEXCELPallete(AColor: TsColor): Word;
procedure GetLastRowCallback(ACell: PCell; AStream: TStream);
function GetLastRowIndex(AWorksheet: TsWorksheet): Integer;
procedure GetLastColCallback(ACell: PCell; AStream: TStream);
function GetLastColIndex(AWorksheet: TsWorksheet): Word;
end;
implementation implementation
function TsSpreadBIFFWriter.FPSColorToEXCELPallete(AColor: TsColor): Word;
begin
case AColor of
scBlack: Result := BUILT_IN_COLOR_PALLETE_BLACK;
scWhite: Result := BUILT_IN_COLOR_PALLETE_WHITE;
scRed: Result := BUILT_IN_COLOR_PALLETE_RED;
scGREEN: Result := BUILT_IN_COLOR_PALLETE_GREEN;
scBLUE: Result := BUILT_IN_COLOR_PALLETE_BLUE;
scYELLOW: Result := BUILT_IN_COLOR_PALLETE_YELLOW;
scMAGENTA: Result := BUILT_IN_COLOR_PALLETE_MAGENTA;
scCYAN: Result := BUILT_IN_COLOR_PALLETE_CYAN;
scDarkRed: Result := BUILT_IN_COLOR_PALLETE_DARK_RED;
scDarkGreen: Result := BUILT_IN_COLOR_PALLETE_DARK_GREEN;
scDarkBlue: Result := BUILT_IN_COLOR_PALLETE_DARK_BLUE;
scOLIVE: Result := BUILT_IN_COLOR_PALLETE_OLIVE;
scPURPLE: Result := BUILT_IN_COLOR_PALLETE_PURPLE;
scTEAL: Result := BUILT_IN_COLOR_PALLETE_TEAL;
scSilver: Result := BUILT_IN_COLOR_PALLETE_SILVER;
scGrey: Result := BUILT_IN_COLOR_PALLETE_GREY;
//
scGrey10pct: Result := EXTRA_COLOR_PALETTE_GREY10PCT;
scGrey20pct: Result := EXTRA_COLOR_PALETTE_GREY20PCT;
end;
end;
procedure TsSpreadBIFFWriter.GetLastRowCallback(ACell: PCell; AStream: TStream);
begin
if ACell^.Row > FLastRow then FLastRow := ACell^.Row;
end;
function TsSpreadBIFFWriter.GetLastRowIndex(AWorksheet: TsWorksheet): Integer;
begin
FLastRow := 0;
IterateThroughCells(nil, AWorksheet.Cells, GetLastRowCallback);
end;
procedure TsSpreadBIFFWriter.GetLastColCallback(ACell: PCell; AStream: TStream);
begin
if ACell^.Col > FLastCol then FLastCol := ACell^.Col;
end;
function TsSpreadBIFFWriter.GetLastColIndex(AWorksheet: TsWorksheet): Word;
begin
FLastCol := 0;
IterateThroughCells(nil, AWorksheet.Cells, GetLastColCallback);
end;
end. end.