You've already forked lazarus-ccr
fpspreadsheet: Major reconstructor of color management: no more palettes now, use direct rgb colors instead. May break existing code - sorry! Update all demos and unit tests (passed).
git-svn-id: https://svn.code.sf.net/p/lazarus-ccr/svn@4156 8e941d3f-bd1b-0410-a28a-d453659cc2b4
This commit is contained in:
@ -49,7 +49,7 @@ begin
|
|||||||
writeln('Finished.');
|
writeln('Finished.');
|
||||||
writeln;
|
writeln;
|
||||||
writeln('Please open "'+OutputFile+'" in "fpsgrid".');
|
writeln('Please open "'+OutputFile+'" in "fpsgrid".');
|
||||||
writeLn('It should show calculation results in cells B1 and B2.');
|
writeLn('It must show correct calculation results in cells B1 and B2.');
|
||||||
finally
|
finally
|
||||||
workbook.Free;
|
workbook.Free;
|
||||||
end;
|
end;
|
||||||
|
@ -10,7 +10,7 @@ program excel5write;
|
|||||||
{$mode delphi}{$H+}
|
{$mode delphi}{$H+}
|
||||||
|
|
||||||
uses
|
uses
|
||||||
Classes, SysUtils, fpsTypes, fpspreadsheet, xlsbiff5;
|
Classes, SysUtils, fpsTypes, fpSpreadsheet, fpsPalette, fpsUtils, xlsbiff5;
|
||||||
|
|
||||||
const
|
const
|
||||||
Str_First = 'First';
|
Str_First = 'First';
|
||||||
@ -28,6 +28,7 @@ var
|
|||||||
i, r: Integer;
|
i, r: Integer;
|
||||||
number: Double;
|
number: Double;
|
||||||
fmt: string;
|
fmt: string;
|
||||||
|
palette: TsPalette;
|
||||||
begin
|
begin
|
||||||
MyDir := ExtractFilePath(ParamStr(0));
|
MyDir := ExtractFilePath(ParamStr(0));
|
||||||
|
|
||||||
@ -359,10 +360,16 @@ begin
|
|||||||
|
|
||||||
// Creates a new worksheet
|
// Creates a new worksheet
|
||||||
MyWorksheet := MyWorkbook.AddWorksheet('Colors');
|
MyWorksheet := MyWorkbook.AddWorksheet('Colors');
|
||||||
for i:=0 to MyWorkbook.GetPaletteSize-1 do begin
|
palette := TsPalette.Create;
|
||||||
|
try
|
||||||
|
palette.UseColors(PALETTE_BIFF5); // This stores the colors of BIFF5 files in the local palette
|
||||||
|
for i:=0 to palette.Count-1 do begin
|
||||||
MyWorksheet.WriteBlank(i, 0);
|
MyWorksheet.WriteBlank(i, 0);
|
||||||
Myworksheet.WriteBackgroundColor(i, 0, TsColor(i));
|
Myworksheet.WriteBackgroundColor(i, 0, palette[i]);
|
||||||
MyWorksheet.WriteUTF8Text(i, 1, MyWorkbook.GetColorName(i));
|
MyWorksheet.WriteUTF8Text(i, 1, GetColorName(palette[i]));
|
||||||
|
end;
|
||||||
|
finally
|
||||||
|
palette.Free;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
// Save the spreadsheet to a file
|
// Save the spreadsheet to a file
|
||||||
|
@ -36,7 +36,6 @@ begin
|
|||||||
// Create the spreadsheet
|
// Create the spreadsheet
|
||||||
MyWorkbook := TsWorkbook.Create;
|
MyWorkbook := TsWorkbook.Create;
|
||||||
MyWorkbook.SetDefaultFont('Calibri', 9);
|
MyWorkbook.SetDefaultFont('Calibri', 9);
|
||||||
MyWorkbook.UsePalette(@PALETTE_BIFF8, Length(PALETTE_BIFF8));
|
|
||||||
MyWorkbook.FormatSettings.CurrencyFormat := 2;
|
MyWorkbook.FormatSettings.CurrencyFormat := 2;
|
||||||
MyWorkbook.FormatSettings.NegCurrFormat := 14;
|
MyWorkbook.FormatSettings.NegCurrFormat := 14;
|
||||||
MyWorkbook.Options := MyWorkbook.Options + [boCalcBeforeSaving];
|
MyWorkbook.Options := MyWorkbook.Options + [boCalcBeforeSaving];
|
||||||
|
@ -135,8 +135,8 @@ begin
|
|||||||
|
|
||||||
MyWorksheet.WriteNumber(row, 0, row);
|
MyWorksheet.WriteNumber(row, 0, row);
|
||||||
MyWorksheet.WriteUTF8Text(row, 1, 'RGB background color:');
|
MyWorksheet.WriteUTF8Text(row, 1, 'RGB background color:');
|
||||||
MyWorksheet.WriteUTF8Text(row, 2, 'color #FF77C3');
|
MyWorksheet.WriteUTF8Text(row, 2, 'color #FF77C3'); // HTML colors are big-endian
|
||||||
MyWorksheet.WriteBackgroundColor(row, 2, MyWorkbook.AddColorToPalette($C377FF));
|
MyWorksheet.WriteBackgroundColor(row, 2, $C377FF); // fps colors are little-endian
|
||||||
inc(row);
|
inc(row);
|
||||||
|
|
||||||
MyWorksheet.WriteNumber(row, 0, row);
|
MyWorksheet.WriteNumber(row, 0, row);
|
||||||
|
@ -9,6 +9,7 @@ object MainFrm: TMainFrm
|
|||||||
Menu = MainMenu
|
Menu = MainMenu
|
||||||
OnActivate = FormActivate
|
OnActivate = FormActivate
|
||||||
OnCreate = FormCreate
|
OnCreate = FormCreate
|
||||||
|
OnDestroy = FormDestroy
|
||||||
ShowHint = True
|
ShowHint = True
|
||||||
LCLVersion = '1.5'
|
LCLVersion = '1.5'
|
||||||
object Panel1: TPanel
|
object Panel1: TPanel
|
||||||
@ -425,7 +426,7 @@ object MainFrm: TMainFrm
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
object InspectorSplitter: TSplitter
|
object InspectorSplitter: TSplitter
|
||||||
Left = 639
|
Left = 591
|
||||||
Height = 453
|
Height = 453
|
||||||
Top = 84
|
Top = 84
|
||||||
Width = 5
|
Width = 5
|
||||||
@ -433,10 +434,10 @@ object MainFrm: TMainFrm
|
|||||||
ResizeAnchor = akRight
|
ResizeAnchor = akRight
|
||||||
end
|
end
|
||||||
object InspectorPageControl: TPageControl
|
object InspectorPageControl: TPageControl
|
||||||
Left = 644
|
Left = 596
|
||||||
Height = 453
|
Height = 453
|
||||||
Top = 84
|
Top = 84
|
||||||
Width = 241
|
Width = 289
|
||||||
ActivePage = PgCellValue
|
ActivePage = PgCellValue
|
||||||
Align = alRight
|
Align = alRight
|
||||||
TabIndex = 0
|
TabIndex = 0
|
||||||
@ -445,18 +446,20 @@ object MainFrm: TMainFrm
|
|||||||
object PgCellValue: TTabSheet
|
object PgCellValue: TTabSheet
|
||||||
Caption = 'Cell value'
|
Caption = 'Cell value'
|
||||||
ClientHeight = 425
|
ClientHeight = 425
|
||||||
ClientWidth = 233
|
ClientWidth = 281
|
||||||
object CellInspector: TValueListEditor
|
object CellInspector: TValueListEditor
|
||||||
Left = 0
|
Left = 0
|
||||||
Height = 425
|
Height = 425
|
||||||
Top = 0
|
Top = 0
|
||||||
Width = 233
|
Width = 281
|
||||||
Align = alClient
|
Align = alClient
|
||||||
FixedCols = 0
|
FixedCols = 0
|
||||||
|
MouseWheelOption = mwGrid
|
||||||
RowCount = 15
|
RowCount = 15
|
||||||
TabOrder = 0
|
TabOrder = 0
|
||||||
TitleStyle = tsNative
|
TitleStyle = tsNative
|
||||||
DisplayOptions = [doColumnTitles, doAutoColResize]
|
DisplayOptions = [doColumnTitles]
|
||||||
|
Options = [goFixedVertLine, goFixedHorzLine, goVertLine, goHorzLine, goColSizing, goAlwaysShowEditor, goThumbTracking]
|
||||||
Strings.Strings = (
|
Strings.Strings = (
|
||||||
'Row='
|
'Row='
|
||||||
'Column='
|
'Column='
|
||||||
@ -478,8 +481,8 @@ object MainFrm: TMainFrm
|
|||||||
''
|
''
|
||||||
)
|
)
|
||||||
ColWidths = (
|
ColWidths = (
|
||||||
114
|
138
|
||||||
115
|
139
|
||||||
)
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@ -494,7 +497,7 @@ object MainFrm: TMainFrm
|
|||||||
Left = 0
|
Left = 0
|
||||||
Height = 453
|
Height = 453
|
||||||
Top = 84
|
Top = 84
|
||||||
Width = 639
|
Width = 591
|
||||||
OnChange = TabControlChange
|
OnChange = TabControlChange
|
||||||
Align = alClient
|
Align = alClient
|
||||||
TabOrder = 3
|
TabOrder = 3
|
||||||
@ -502,7 +505,7 @@ object MainFrm: TMainFrm
|
|||||||
Left = 2
|
Left = 2
|
||||||
Height = 448
|
Height = 448
|
||||||
Top = 3
|
Top = 3
|
||||||
Width = 635
|
Width = 587
|
||||||
FrozenCols = 0
|
FrozenCols = 0
|
||||||
FrozenRows = 0
|
FrozenRows = 0
|
||||||
ReadFormulas = False
|
ReadFormulas = False
|
||||||
|
@ -8,7 +8,7 @@ uses
|
|||||||
Classes, SysUtils, FileUtil, LResources, Forms, Controls, Graphics, Dialogs,
|
Classes, SysUtils, FileUtil, LResources, Forms, Controls, Graphics, Dialogs,
|
||||||
StdCtrls, Menus, ExtCtrls, ComCtrls, ActnList, Spin, Grids,
|
StdCtrls, Menus, ExtCtrls, ComCtrls, ActnList, Spin, Grids,
|
||||||
ColorBox, ValEdit,
|
ColorBox, ValEdit,
|
||||||
fpstypes, fpspreadsheetgrid, fpspreadsheet,
|
fpstypes, fpspalette, fpspreadsheetgrid, fpspreadsheet,
|
||||||
{%H-}fpsallformats;
|
{%H-}fpsallformats;
|
||||||
|
|
||||||
type
|
type
|
||||||
@ -325,6 +325,7 @@ type
|
|||||||
procedure FontSizeComboBoxSelect(Sender: TObject);
|
procedure FontSizeComboBoxSelect(Sender: TObject);
|
||||||
procedure FormActivate(Sender: TObject);
|
procedure FormActivate(Sender: TObject);
|
||||||
procedure FormCreate(Sender: TObject);
|
procedure FormCreate(Sender: TObject);
|
||||||
|
procedure FormDestroy(Sender: TObject);
|
||||||
procedure InspectorPageControlChange(Sender: TObject);
|
procedure InspectorPageControlChange(Sender: TObject);
|
||||||
procedure MemoFormulaEditingDone(Sender: TObject);
|
procedure MemoFormulaEditingDone(Sender: TObject);
|
||||||
procedure TabControlChange(Sender: TObject);
|
procedure TabControlChange(Sender: TObject);
|
||||||
@ -334,6 +335,7 @@ type
|
|||||||
|
|
||||||
private
|
private
|
||||||
FCopiedFormat: TCell;
|
FCopiedFormat: TCell;
|
||||||
|
FPalette: TsPalette;
|
||||||
|
|
||||||
function EditComment(ACaption: String; var AText: String): Boolean;
|
function EditComment(ACaption: String; var AText: String): Boolean;
|
||||||
procedure LoadFile(const AFileName: String);
|
procedure LoadFile(const AFileName: String);
|
||||||
@ -928,9 +930,9 @@ begin
|
|||||||
if WorksheetGrid.Workbook <> nil then begin
|
if WorksheetGrid.Workbook <> nil then begin
|
||||||
Items.Clear;
|
Items.Clear;
|
||||||
Items.AddObject('no fill', TObject(PtrInt(clNone)));
|
Items.AddObject('no fill', TObject(PtrInt(clNone)));
|
||||||
for i:=0 to WorksheetGrid.Workbook.GetPaletteSize-1 do begin
|
for i:=0 to FPalette.Count-1 do begin
|
||||||
clr := WorksheetGrid.Workbook.GetPaletteColor(i);
|
clr := FPalette[i];
|
||||||
clrName := WorksheetGrid.Workbook.GetColorName(i);
|
clrName := GetColorName(clr);
|
||||||
Items.AddObject(Format('%d: %s', [i, clrName]), TObject(PtrInt(clr)));
|
Items.AddObject(Format('%d: %s', [i, clrName]), TObject(PtrInt(clr)));
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
@ -947,7 +949,7 @@ begin
|
|||||||
if CbBackgroundColor.ItemIndex <= 0 then
|
if CbBackgroundColor.ItemIndex <= 0 then
|
||||||
with WorksheetGrid do BackgroundColors[Selection] := scNotDefined
|
with WorksheetGrid do BackgroundColors[Selection] := scNotDefined
|
||||||
else
|
else
|
||||||
with WorksheetGrid do BackgroundColors[Selection] := CbBackgroundColor.ItemIndex - 1;
|
with WorksheetGrid do BackgroundColors[Selection] := PtrInt(CbBackgroundColor.Items.Objects[CbBackgroundColor.ItemIndex]);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TMainFrm.CbHeaderStyleChange(Sender: TObject);
|
procedure TMainFrm.CbHeaderStyleChange(Sender: TObject);
|
||||||
@ -1087,12 +1089,20 @@ begin
|
|||||||
FontSizeCombobox.DropDownCount := DROPDOWN_COUNT;
|
FontSizeCombobox.DropDownCount := DROPDOWN_COUNT;
|
||||||
CbBackgroundColor.DropDownCount := DROPDOWN_COUNT;
|
CbBackgroundColor.DropDownCount := DROPDOWN_COUNT;
|
||||||
|
|
||||||
|
FPalette := TsPalette.Create;
|
||||||
|
FPalette.AddExcelColors;
|
||||||
|
|
||||||
// Initialize a new empty workbook
|
// Initialize a new empty workbook
|
||||||
AcNewExecute(nil);
|
AcNewExecute(nil);
|
||||||
|
|
||||||
ActiveControl := WorksheetGrid;
|
ActiveControl := WorksheetGrid;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
procedure TMainFrm.FormDestroy(Sender: TObject);
|
||||||
|
begin
|
||||||
|
FPalette.Free;
|
||||||
|
end;
|
||||||
|
|
||||||
procedure TMainFrm.InspectorPageControlChange(Sender: TObject);
|
procedure TMainFrm.InspectorPageControlChange(Sender: TObject);
|
||||||
begin
|
begin
|
||||||
CellInspector.Parent := InspectorPageControl.ActivePage;
|
CellInspector.Parent := InspectorPageControl.ActivePage;
|
||||||
@ -1184,13 +1194,14 @@ end;
|
|||||||
|
|
||||||
procedure TMainFrm.UpdateBackgroundColorIndex;
|
procedure TMainFrm.UpdateBackgroundColorIndex;
|
||||||
var
|
var
|
||||||
sClr: TsColor;
|
clr: TsColor;
|
||||||
begin
|
begin
|
||||||
with WorksheetGrid do sClr := BackgroundColors[Selection];
|
with WorksheetGrid do
|
||||||
if sClr = scNotDefined then
|
clr := BackgroundColors[Selection];
|
||||||
|
if (clr = scNotDefined) or (clr = scTransparent) then
|
||||||
CbBackgroundColor.ItemIndex := 0 // no fill
|
CbBackgroundColor.ItemIndex := 0 // no fill
|
||||||
else
|
else
|
||||||
CbBackgroundColor.ItemIndex := sClr + 1;
|
CbBackgroundColor.ItemIndex := CbBackgroundColor.Items.IndexOfObject(TObject(PtrInt(clr)));
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TMainFrm.UpdateHorAlignmentActions;
|
procedure TMainFrm.UpdateHorAlignmentActions;
|
||||||
@ -1214,6 +1225,7 @@ var
|
|||||||
cb: TsCellBorder;
|
cb: TsCellBorder;
|
||||||
r1,r2,c1,c2: Cardinal;
|
r1,r2,c1,c2: Cardinal;
|
||||||
fmt: TsCellFormat;
|
fmt: TsCellFormat;
|
||||||
|
nfparams: TsNumFormatParams;
|
||||||
begin
|
begin
|
||||||
with CellInspector do
|
with CellInspector do
|
||||||
begin
|
begin
|
||||||
@ -1223,10 +1235,10 @@ begin
|
|||||||
if InspectorPageControl.ActivePage = PgCellValue then
|
if InspectorPageControl.ActivePage = PgCellValue then
|
||||||
begin
|
begin
|
||||||
if ACell=nil
|
if ACell=nil
|
||||||
then Strings.Add('Row=')
|
then Strings.Add(Format('Row=%d', [WorksheetGrid.GetWorksheetRow(WorksheetGrid.Row)]))
|
||||||
else Strings.Add(Format('Row=%d', [ACell^.Row]));
|
else Strings.Add(Format('Row=%d', [ACell^.Row]));
|
||||||
if ACell=nil
|
if ACell=nil
|
||||||
then Strings.Add('Column=')
|
then Strings.Add(Format('Column=%d', [WorksheetGrid.GetWorksheetCol(WorksheetGrid.Col)]))
|
||||||
else Strings.Add(Format('Column=%d', [ACell^.Col]));
|
else Strings.Add(Format('Column=%d', [ACell^.Col]));
|
||||||
if ACell=nil
|
if ACell=nil
|
||||||
then Strings.Add('ContentType=')
|
then Strings.Add('ContentType=')
|
||||||
@ -1308,29 +1320,40 @@ begin
|
|||||||
else
|
else
|
||||||
Strings.Add(Format('BorderStyles[%s]=%s, %s', [
|
Strings.Add(Format('BorderStyles[%s]=%s, %s', [
|
||||||
GetEnumName(TypeInfo(TsCellBorder), ord(cb)),
|
GetEnumName(TypeInfo(TsCellBorder), ord(cb)),
|
||||||
GetEnumName(TypeInfo(TsLineStyle), ord(fmt.BorderStyles[cbEast].LineStyle)),
|
GetEnumName(TypeInfo(TsLineStyle), ord(fmt.BorderStyles[cb].LineStyle)),
|
||||||
WorksheetGrid.Workbook.GetColorName(fmt.BorderStyles[cbEast].Color)
|
GetColorName(fmt.BorderStyles[cb].Color)
|
||||||
]));
|
]));
|
||||||
if (ACell=nil) or not (uffBackground in fmt.UsedformattingFields)
|
if (ACell=nil) or not (uffBackground in fmt.UsedformattingFields)
|
||||||
then Strings.Add('BackgroundColor=')
|
then Strings.Add('BackgroundColor=')
|
||||||
else Strings.Add(Format('BackgroundColor=%d (%s)', [
|
else Strings.Add(Format('BackgroundColor=$%8x (%s)', [
|
||||||
fmt.Background.BgColor,
|
fmt.Background.BgColor,
|
||||||
WorksheetGrid.Workbook.GetColorName(fmt.Background.BgColor)
|
GetColorName(fmt.Background.BgColor)
|
||||||
]));
|
]));
|
||||||
if (ACell=nil) or not (uffNumberFormat in fmt.UsedFormattingFields)
|
if (ACell=nil) or not (uffNumberFormat in fmt.UsedFormattingFields)
|
||||||
then Strings.Add('NumberFormat=')
|
then Strings.Add('NumberFormat=')
|
||||||
else Strings.Add(Format('NumberFormat=%s', [GetEnumName(TypeInfo(TsNumberFormat), ord(fmt.NumberFormat))]));
|
else begin
|
||||||
|
nfparams := WorksheetGrid.Workbook.GetNumberFormat(fmt.NumberFormatIndex);
|
||||||
|
if nfparams = nil then
|
||||||
|
begin
|
||||||
|
Strings.Add('NumberFormat=General');
|
||||||
|
Strings.Add('NumberFormatStr=');
|
||||||
|
end else
|
||||||
|
begin
|
||||||
|
Strings.Add(Format('NumberFormat=%s', [GetEnumName(TypeInfo(TsNumberFormat), ord(nfparams.NumFormat))]));
|
||||||
|
Strings.Add(Format('NumberFormatStr=%s', [nfparams.NumFormatStr]));
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
{
|
||||||
if (ACell=nil) or not (uffNumberFormat in fmt.UsedFormattingFields)
|
if (ACell=nil) or not (uffNumberFormat in fmt.UsedFormattingFields)
|
||||||
then Strings.Add('NumberFormatStr=')
|
then Strings.Add('NumberFormatStr=')
|
||||||
else Strings.Add('NumberFormatStr=' + fmt.NumberFormatStr);
|
else Strings.Add('NumberFormatStr=' + fmt.NumberFormatStr);
|
||||||
if not WorksheetGrid.Worksheet.IsMerged(ACell) then
|
}
|
||||||
Strings.Add('Merged range=')
|
if not WorksheetGrid.Worksheet.IsMerged(ACell)
|
||||||
else
|
then Strings.Add('Merged range=')
|
||||||
begin
|
else begin
|
||||||
WorksheetGrid.Worksheet.FindMergedRange(ACell, r1, c1, r2, c2);
|
WorksheetGrid.Worksheet.FindMergedRange(ACell, r1, c1, r2, c2);
|
||||||
Strings.Add('Merged range=' + GetCellRangeString(r1, c1, r2, c2));
|
Strings.Add('Merged range=' + GetCellRangeString(r1, c1, r2, c2));
|
||||||
end;
|
end;
|
||||||
|
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
@ -103,7 +103,6 @@
|
|||||||
<ComponentName Value="MainFrm"/>
|
<ComponentName Value="MainFrm"/>
|
||||||
<HasResources Value="True"/>
|
<HasResources Value="True"/>
|
||||||
<ResourceBaseClass Value="Form"/>
|
<ResourceBaseClass Value="Form"/>
|
||||||
<UnitName Value="mainform"/>
|
|
||||||
</Unit1>
|
</Unit1>
|
||||||
<Unit2>
|
<Unit2>
|
||||||
<Filename Value="..\shared\scsvparamsform.pas"/>
|
<Filename Value="..\shared\scsvparamsform.pas"/>
|
||||||
@ -128,6 +127,7 @@
|
|||||||
<Unit5>
|
<Unit5>
|
||||||
<Filename Value="..\shared\sctrls.pas"/>
|
<Filename Value="..\shared\sctrls.pas"/>
|
||||||
<IsPartOfProject Value="True"/>
|
<IsPartOfProject Value="True"/>
|
||||||
|
<UnitName Value="sCtrls"/>
|
||||||
</Unit5>
|
</Unit5>
|
||||||
<Unit6>
|
<Unit6>
|
||||||
<Filename Value="..\shared\scurrencyform.pas"/>
|
<Filename Value="..\shared\scurrencyform.pas"/>
|
||||||
|
@ -9,6 +9,7 @@ object MainFrm: TMainFrm
|
|||||||
Menu = MainMenu
|
Menu = MainMenu
|
||||||
OnActivate = FormActivate
|
OnActivate = FormActivate
|
||||||
OnCreate = FormCreate
|
OnCreate = FormCreate
|
||||||
|
OnDestroy = FormDestroy
|
||||||
ShowHint = True
|
ShowHint = True
|
||||||
LCLVersion = '1.5'
|
LCLVersion = '1.5'
|
||||||
object MainToolBar: TToolBar
|
object MainToolBar: TToolBar
|
||||||
|
@ -9,7 +9,7 @@ uses
|
|||||||
StdCtrls, Menus, ExtCtrls, ComCtrls, ActnList, Grids, ColorBox, SynEdit,
|
StdCtrls, Menus, ExtCtrls, ComCtrls, ActnList, Grids, ColorBox, SynEdit,
|
||||||
SynEditHighlighter, SynHighlighterHTML, SynHighlighterMulti,
|
SynEditHighlighter, SynHighlighterHTML, SynHighlighterMulti,
|
||||||
SynHighlighterCss, SynGutterCodeFolding, fpspreadsheetgrid,
|
SynHighlighterCss, SynGutterCodeFolding, fpspreadsheetgrid,
|
||||||
fpstypes, fpspreadsheet, fpsallformats;
|
fpstypes, fpspalette, fpspreadsheet, fpsallformats;
|
||||||
|
|
||||||
type
|
type
|
||||||
|
|
||||||
@ -187,6 +187,7 @@ type
|
|||||||
procedure FontSizeComboBoxSelect(Sender: TObject);
|
procedure FontSizeComboBoxSelect(Sender: TObject);
|
||||||
procedure FormActivate(Sender: TObject);
|
procedure FormActivate(Sender: TObject);
|
||||||
procedure FormCreate(Sender: TObject);
|
procedure FormCreate(Sender: TObject);
|
||||||
|
procedure FormDestroy(Sender: TObject);
|
||||||
procedure PageControlChange(Sender: TObject);
|
procedure PageControlChange(Sender: TObject);
|
||||||
procedure TabControlChange(Sender: TObject);
|
procedure TabControlChange(Sender: TObject);
|
||||||
procedure WorksheetGridSelection(Sender: TObject; aCol, aRow: Integer);
|
procedure WorksheetGridSelection(Sender: TObject; aCol, aRow: Integer);
|
||||||
@ -194,6 +195,7 @@ type
|
|||||||
WorksheetGrid: TsWorksheetGrid;
|
WorksheetGrid: TsWorksheetGrid;
|
||||||
FCopiedFormat: TCell;
|
FCopiedFormat: TCell;
|
||||||
FHighlighter: TSynCustomHighlighter;
|
FHighlighter: TSynCustomHighlighter;
|
||||||
|
FPalette: TsPalette;
|
||||||
procedure LoadFile(const AFileName: String);
|
procedure LoadFile(const AFileName: String);
|
||||||
procedure SetupBackgroundColorBox;
|
procedure SetupBackgroundColorBox;
|
||||||
procedure UpdateBackgroundColorIndex;
|
procedure UpdateBackgroundColorIndex;
|
||||||
@ -543,20 +545,22 @@ begin
|
|||||||
if (WorksheetGrid <> nil) and (WorksheetGrid.Workbook <> nil) then begin
|
if (WorksheetGrid <> nil) and (WorksheetGrid.Workbook <> nil) then begin
|
||||||
Items.Clear;
|
Items.Clear;
|
||||||
Items.AddObject('no fill', TObject(PtrInt(clNone)));
|
Items.AddObject('no fill', TObject(PtrInt(clNone)));
|
||||||
for i:=0 to WorksheetGrid.Workbook.GetPaletteSize-1 do begin
|
for i:=0 to FPalette.Count-1 do begin
|
||||||
clr := WorksheetGrid.Workbook.GetPaletteColor(i);
|
clr := FPalette[i];
|
||||||
clrName := WorksheetGrid.Workbook.GetColorName(i);
|
clrName := GetColorName(clr);
|
||||||
Items.AddObject(Format('%d: %s', [i, clrName]), TObject(PtrInt(clr)));
|
Items.AddObject(Format('%d: %s', [i, clrName]), TObject(PtrInt(clr)));
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TMainFrm.CbBackgroundColorSelect(Sender: TObject);
|
procedure TMainFrm.CbBackgroundColorSelect(Sender: TObject);
|
||||||
|
var
|
||||||
|
clr: TsColor;
|
||||||
begin
|
begin
|
||||||
if CbBackgroundColor.ItemIndex <= 0 then
|
if CbBackgroundColor.ItemIndex <= 0 then
|
||||||
with WorksheetGrid do BackgroundColors[Selection] := scNotDefined
|
with WorksheetGrid do BackgroundColors[Selection] := scNotDefined
|
||||||
else
|
else
|
||||||
with WorksheetGrid do BackgroundColors[Selection] := CbBackgroundColor.ItemIndex - 1;
|
with WorksheetGrid do BackgroundColors[Selection] := PtrInt(CbBackgroundColor.Items.Objects[CbBackgroundColor.ItemIndex]);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TMainFrm.FontComboBoxSelect(Sender: TObject);
|
procedure TMainFrm.FontComboBoxSelect(Sender: TObject);
|
||||||
@ -637,6 +641,9 @@ begin
|
|||||||
CbBackgroundColor.ColorRectWidth := CbBackgroundColor.ItemHeight - 6; // to get a square box...
|
CbBackgroundColor.ColorRectWidth := CbBackgroundColor.ItemHeight - 6; // to get a square box...
|
||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
|
|
||||||
|
FPalette := TsPalette.Create;
|
||||||
|
FPalette.AddExcelColors;
|
||||||
|
|
||||||
// Initialize a new empty workbook
|
// Initialize a new empty workbook
|
||||||
AcNewExecute(nil);
|
AcNewExecute(nil);
|
||||||
|
|
||||||
@ -645,6 +652,11 @@ begin
|
|||||||
ActiveControl := WorksheetGrid;
|
ActiveControl := WorksheetGrid;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
procedure TMainFrm.FormDestroy(Sender: TObject);
|
||||||
|
begin
|
||||||
|
FPalette.Free;
|
||||||
|
end;
|
||||||
|
|
||||||
procedure TMainFrm.PageControlChange(Sender: TObject);
|
procedure TMainFrm.PageControlChange(Sender: TObject);
|
||||||
var
|
var
|
||||||
stream: TMemoryStream;
|
stream: TMemoryStream;
|
||||||
@ -726,13 +738,13 @@ end;
|
|||||||
|
|
||||||
procedure TMainFrm.UpdateBackgroundColorIndex;
|
procedure TMainFrm.UpdateBackgroundColorIndex;
|
||||||
var
|
var
|
||||||
sClr: TsColor;
|
clr: TsColor;
|
||||||
begin
|
begin
|
||||||
with WorksheetGrid do sClr := BackgroundColors[Selection];
|
with WorksheetGrid do clr := BackgroundColors[Selection];
|
||||||
if sClr = scNotDefined then
|
if (clr = scNotDefined) or (clr = scTransparent) then
|
||||||
CbBackgroundColor.ItemIndex := 0 // no fill
|
CbBackgroundColor.ItemIndex := 0 // no fill
|
||||||
else
|
else
|
||||||
CbBackgroundColor.ItemIndex := sClr + 1;
|
CbBackgroundColor.ItemIndex := CbBackgroundColor.Items.IndexOfObject(TObject(PtrInt(clr)));
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TMainFrm.UpdateHorAlignmentActions;
|
procedure TMainFrm.UpdateHorAlignmentActions;
|
||||||
|
@ -1078,14 +1078,14 @@ procedure TsActionBorder.ApplyStyle(AWorkbook: TsWorkbook;
|
|||||||
out ABorderStyle: TsCellBorderStyle);
|
out ABorderStyle: TsCellBorderStyle);
|
||||||
begin
|
begin
|
||||||
ABorderStyle.LineStyle := FLineStyle;
|
ABorderStyle.LineStyle := FLineStyle;
|
||||||
ABorderStyle.Color := AWorkbook.GetPaletteColor(ABorderStyle.Color);
|
ABorderStyle.Color := ABorderStyle.Color and $00FFFFFF;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TsActionBorder.ExtractStyle(AWorkbook: TsWorkbook;
|
procedure TsActionBorder.ExtractStyle(AWorkbook: TsWorkbook;
|
||||||
ABorderStyle: TsCellBorderStyle);
|
ABorderStyle: TsCellBorderStyle);
|
||||||
begin
|
begin
|
||||||
FLineStyle := ABorderStyle.LineStyle;
|
FLineStyle := ABorderStyle.LineStyle;
|
||||||
Color := AWorkbook.AddColorToPalette(ABorderStyle.Color);
|
Color := ColorToRGB(ABorderStyle.Color);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
constructor TsActionBorders.Create;
|
constructor TsActionBorders.Create;
|
||||||
@ -1575,14 +1575,14 @@ end;
|
|||||||
|
|
||||||
procedure TsBackgroundColorDialogAction.DoAccept;
|
procedure TsBackgroundColorDialogAction.DoAccept;
|
||||||
begin
|
begin
|
||||||
FBackgroundColor := Workbook.AddColorToPalette(TsColorValue(Dialog.Color));
|
FBackgroundColor := ColorToRgb(Dialog.Color);
|
||||||
inherited;
|
inherited;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TsBackgroundColorDialogAction.DoBeforeExecute;
|
procedure TsBackgroundColorDialogAction.DoBeforeExecute;
|
||||||
begin
|
begin
|
||||||
inherited;
|
inherited;
|
||||||
Dialog.Color := Workbook.GetPaletteColor(FBackgroundColor);
|
Dialog.Color := FBackgroundColor and $00FFFFFF;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TsBackgroundColorDialogAction.ExtractFromCell(ACell: PCell);
|
procedure TsBackgroundColorDialogAction.ExtractFromCell(ACell: PCell);
|
||||||
|
@ -20,11 +20,11 @@ type
|
|||||||
FontName: String;
|
FontName: String;
|
||||||
Size: Double;
|
Size: Double;
|
||||||
Style: TsHeaderFooterFontStyles;
|
Style: TsHeaderFooterFontStyles;
|
||||||
Color: TsColorValue;
|
Color: TsColor;
|
||||||
constructor Create; overload;
|
constructor Create; overload;
|
||||||
constructor Create(AFont: TsFont); overload;
|
constructor Create(AFont: TsFont); overload;
|
||||||
constructor Create(AFontName: String; ASize: Double;
|
constructor Create(AFontName: String; ASize: Double;
|
||||||
AStyle: TsHeaderFooterFontStyles; AColor: TsColorValue); overload;
|
AStyle: TsHeaderFooterFontStyles; AColor: TsColor); overload;
|
||||||
procedure Assign(AFont: TObject);
|
procedure Assign(AFont: TObject);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -99,7 +99,7 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
constructor TsHeaderFooterFont.Create(AFontName: String; ASize: Double;
|
constructor TsHeaderFooterFont.Create(AFontName: String; ASize: Double;
|
||||||
AStyle: TsHeaderFooterFontStyles; AColor: TsColorValue);
|
AStyle: TsHeaderFooterFontStyles; AColor: TsColor);
|
||||||
begin
|
begin
|
||||||
FontName := AFontName;
|
FontName := AFontName;
|
||||||
Size := ASize;
|
Size := ASize;
|
||||||
|
@ -108,7 +108,7 @@ type
|
|||||||
function ReadFont(ANode: TDOMnode; APreferredIndex: Integer = -1): Integer;
|
function ReadFont(ANode: TDOMnode; APreferredIndex: Integer = -1): Integer;
|
||||||
procedure ReadHeaderFooterFont(ANode: TDOMNode; var AFontName: String;
|
procedure ReadHeaderFooterFont(ANode: TDOMNode; var AFontName: String;
|
||||||
var AFontSize: Double; var AFontStyle: TsHeaderFooterFontStyles;
|
var AFontSize: Double; var AFontStyle: TsHeaderFooterFontStyles;
|
||||||
var AFontColor: TsColorValue);
|
var AFontColor: TsColor);
|
||||||
function ReadHeaderFooterText(ANode: TDOMNode): String;
|
function ReadHeaderFooterText(ANode: TDOMNode): String;
|
||||||
procedure ReadRowsAndCells(ATableNode: TDOMNode);
|
procedure ReadRowsAndCells(ATableNode: TDOMNode);
|
||||||
procedure ReadRowStyle(AStyleNode: TDOMNode);
|
procedure ReadRowStyle(AStyleNode: TDOMNode);
|
||||||
@ -561,7 +561,7 @@ var
|
|||||||
n: Integer;
|
n: Integer;
|
||||||
el, nEl: Integer;
|
el, nEl: Integer;
|
||||||
ns: Integer;
|
ns: Integer;
|
||||||
clr: TsColorvalue;
|
clr: TsColor;
|
||||||
mask: String;
|
mask: String;
|
||||||
timeIntervalStr: String;
|
timeIntervalStr: String;
|
||||||
styleMapStr: String;
|
styleMapStr: String;
|
||||||
@ -607,7 +607,7 @@ begin
|
|||||||
case Elements[el].Token of
|
case Elements[el].Token of
|
||||||
nftColor:
|
nftColor:
|
||||||
begin
|
begin
|
||||||
clr := FWorkbook.GetPaletteColor(Elements[el].IntValue);
|
clr := TsColor(Elements[el].IntValue);
|
||||||
Result := Result + '<style:text-properties fo:color="' + ColorToHTMLColorStr(clr) + '" />';
|
Result := Result + '<style:text-properties fo:color="' + ColorToHTMLColorStr(clr) + '" />';
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -679,7 +679,9 @@ begin
|
|||||||
// Mixed fraction
|
// Mixed fraction
|
||||||
if nfkFraction in Kind then
|
if nfkFraction in Kind then
|
||||||
begin
|
begin
|
||||||
int := Elements[el].IntValue;
|
if Elements[el].Token = nftIntOptDigit
|
||||||
|
then int := 0
|
||||||
|
else int := Elements[el].IntValue;
|
||||||
inc(el);
|
inc(el);
|
||||||
while (el < nel) and not
|
while (el < nel) and not
|
||||||
(Elements[el].Token in [nftFracNumZeroDigit, nftFracNumOptDigit, nftFracNumSpaceDigit])
|
(Elements[el].Token in [nftFracNumZeroDigit, nftFracNumOptDigit, nftFracNumSpaceDigit])
|
||||||
@ -874,8 +876,6 @@ begin
|
|||||||
FMasterPageList := TFPList.Create;
|
FMasterPageList := TFPList.Create;
|
||||||
FHeaderFooterFontList := TObjectList.Create; // frees objects
|
FHeaderFooterFontList := TObjectList.Create; // frees objects
|
||||||
|
|
||||||
// Set up the default palette in order to have the default color names correct.
|
|
||||||
Workbook.UseDefaultPalette;
|
|
||||||
// Initial base date in case it won't be read from file
|
// Initial base date in case it won't be read from file
|
||||||
FDateMode := dm1899;
|
FDateMode := dm1899;
|
||||||
end;
|
end;
|
||||||
@ -1129,7 +1129,7 @@ var
|
|||||||
fntName: String;
|
fntName: String;
|
||||||
fntSize: Double;
|
fntSize: Double;
|
||||||
fntStyle: TsHeaderFooterFontStyles;
|
fntStyle: TsHeaderFooterFontStyles;
|
||||||
fntColor: TsColorValue;
|
fntColor: TsColor;
|
||||||
begin
|
begin
|
||||||
if not Assigned(AStylesNode) then
|
if not Assigned(AStylesNode) then
|
||||||
exit;
|
exit;
|
||||||
@ -1683,7 +1683,7 @@ begin
|
|||||||
|
|
||||||
s := GetAttrValue(ANode, 'fo:color');
|
s := GetAttrValue(ANode, 'fo:color');
|
||||||
if s <> '' then
|
if s <> '' then
|
||||||
fntColor := FWorkbook.AddColorToPalette(HTMLColorStrToColor(s))
|
fntColor := HTMLColorStrToColor(s)
|
||||||
else
|
else
|
||||||
fntColor := FWorkbook.GetDefaultFont.Color;
|
fntColor := FWorkbook.GetDefaultFont.Color;
|
||||||
|
|
||||||
@ -1694,10 +1694,6 @@ begin
|
|||||||
end else
|
end else
|
||||||
if (APreferredIndex > -1) then
|
if (APreferredIndex > -1) then
|
||||||
begin
|
begin
|
||||||
{ --- wp: No more missing font #4 now !!!
|
|
||||||
if (APreferredIndex = 4) then
|
|
||||||
raise Exception.Create('Cannot replace font #4');
|
|
||||||
}
|
|
||||||
FWorkbook.ReplaceFont(APreferredIndex, fntName, fntSize, fntStyles, fntColor);
|
FWorkbook.ReplaceFont(APreferredIndex, fntName, fntSize, fntStyles, fntColor);
|
||||||
Result := APreferredIndex;
|
Result := APreferredIndex;
|
||||||
end else
|
end else
|
||||||
@ -1938,7 +1934,7 @@ end;
|
|||||||
|
|
||||||
procedure TsSpreadOpenDocReader.ReadHeaderFooterFont(ANode: TDOMNode;
|
procedure TsSpreadOpenDocReader.ReadHeaderFooterFont(ANode: TDOMNode;
|
||||||
var AFontName: String; var AFontSize: Double;
|
var AFontName: String; var AFontSize: Double;
|
||||||
var AFontStyle: TsHeaderFooterFontStyles; var AFontColor: TsColorValue);
|
var AFontStyle: TsHeaderFooterFontStyles; var AFontColor: TsColor);
|
||||||
var
|
var
|
||||||
s: String;
|
s: String;
|
||||||
begin
|
begin
|
||||||
@ -2241,7 +2237,7 @@ procedure TsSpreadOpenDocReader.ReadNumFormats(AStylesNode: TDOMNode);
|
|||||||
grouping: Boolean;
|
grouping: Boolean;
|
||||||
nex: Integer;
|
nex: Integer;
|
||||||
cs: String;
|
cs: String;
|
||||||
color: TsColorValue;
|
color: TsColor;
|
||||||
hasColor: Boolean;
|
hasColor: Boolean;
|
||||||
idx: Integer;
|
idx: Integer;
|
||||||
begin
|
begin
|
||||||
@ -2280,14 +2276,14 @@ procedure TsSpreadOpenDocReader.ReadNumFormats(AStylesNode: TDOMNode);
|
|||||||
begin
|
begin
|
||||||
nf := nfFraction;
|
nf := nfFraction;
|
||||||
s := GetAttrValue(node, 'number:min-integer-digits');
|
s := GetAttrValue(node, 'number:min-integer-digits');
|
||||||
if s <> '' then fracInt := StrToInt(s) else fracInt := 0;
|
if s <> '' then fracInt := StrToInt(s) else fracInt := -1;
|
||||||
s := GetAttrValue(node, 'number:min-numerator-digits');
|
s := GetAttrValue(node, 'number:min-numerator-digits');
|
||||||
if s <> '' then fracNum := StrToInt(s) else fracNum := 0;
|
if s <> '' then fracNum := StrToInt(s) else fracNum := 0;
|
||||||
s := GetAttrValue(node, 'number:min-denominator-digits');
|
s := GetAttrValue(node, 'number:min-denominator-digits');
|
||||||
if s <> '' then fracDenom := StrToInt(s) else fracDenom := 0;
|
if s <> '' then fracDenom := StrToInt(s) else fracDenom := 0;
|
||||||
s := GetAttrValue(node, 'number:denominator-value');
|
s := GetAttrValue(node, 'number:denominator-value');
|
||||||
if s <> '' then fracDenom := -StrToInt(s);
|
if s <> '' then fracDenom := -StrToInt(s);
|
||||||
nfs := nfs + BuildFractionFormatString(fracInt > 0, fracNum, fracDenom);
|
nfs := nfs + BuildFractionFormatString(fracInt > -1, fracNum, fracDenom);
|
||||||
end else
|
end else
|
||||||
if nodeName = 'number:scientific-number' then
|
if nodeName = 'number:scientific-number' then
|
||||||
begin
|
begin
|
||||||
@ -2324,14 +2320,12 @@ procedure TsSpreadOpenDocReader.ReadNumFormats(AStylesNode: TDOMNode);
|
|||||||
if s <> '' then
|
if s <> '' then
|
||||||
begin
|
begin
|
||||||
hasColor := true;
|
hasColor := true;
|
||||||
// { // currently not needed
|
|
||||||
color := HTMLColorStrToColor(s);
|
color := HTMLColorStrToColor(s);
|
||||||
idx := FWorkbook.AddColorToPalette(color);
|
case color of
|
||||||
if idx < 8 then
|
scBlack, scWhite, scRed, scGreen,
|
||||||
nfs := Format('[%s]%s', [FWorkbook.GetColorName(idx), nfs])
|
scBlue, scYellow, scMagenta, scCyan:
|
||||||
else
|
nfs := Format('[%s]%s', [GetColorName(color), nfs]);
|
||||||
nfs := Format('[Color%d]%s', [idx, nfs]);
|
end;
|
||||||
// }
|
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
node := node.NextSibling;
|
node := node.NextSibling;
|
||||||
@ -2913,7 +2907,7 @@ var
|
|||||||
numFmtStr: String;
|
numFmtStr: String;
|
||||||
numFmtIndex: Integer;
|
numFmtIndex: Integer;
|
||||||
numFmtParams: TsNumFormatParams;
|
numFmtParams: TsNumFormatParams;
|
||||||
clr: TsColorValue;
|
clr: TsColor;
|
||||||
s: String;
|
s: String;
|
||||||
|
|
||||||
procedure SetBorderStyle(ABorder: TsCellBorder; AStyleValue: String);
|
procedure SetBorderStyle(ABorder: TsCellBorder; AStyleValue: String);
|
||||||
@ -2925,7 +2919,7 @@ var
|
|||||||
s: String;
|
s: String;
|
||||||
wid: Double;
|
wid: Double;
|
||||||
linestyle: String;
|
linestyle: String;
|
||||||
rgb: TsColorValue;
|
rgb: TsColor;
|
||||||
p: Integer;
|
p: Integer;
|
||||||
begin
|
begin
|
||||||
L := TStringList.Create;
|
L := TStringList.Create;
|
||||||
@ -2934,7 +2928,7 @@ var
|
|||||||
L.StrictDelimiter := true;
|
L.StrictDelimiter := true;
|
||||||
L.DelimitedText := AStyleValue;
|
L.DelimitedText := AStyleValue;
|
||||||
wid := 0;
|
wid := 0;
|
||||||
rgb := TsColorValue(-1);
|
rgb := scNotDefined;
|
||||||
linestyle := '';
|
linestyle := '';
|
||||||
for i:=0 to L.Count-1 do
|
for i:=0 to L.Count-1 do
|
||||||
begin
|
begin
|
||||||
@ -2981,8 +2975,7 @@ var
|
|||||||
else
|
else
|
||||||
if (linestyle = 'double') then
|
if (linestyle = 'double') then
|
||||||
fmt.BorderStyles[ABorder].LineStyle := lsDouble;
|
fmt.BorderStyles[ABorder].LineStyle := lsDouble;
|
||||||
fmt.BorderStyles[ABorder].Color := IfThen(rgb = TsColorValue(-1),
|
fmt.BorderStyles[ABorder].Color := IfThen(rgb = scNotDefined, scBlack, rgb);
|
||||||
scBlack, Workbook.AddColorToPalette(rgb));
|
|
||||||
finally
|
finally
|
||||||
L.Free;
|
L.Free;
|
||||||
end;
|
end;
|
||||||
@ -3048,10 +3041,6 @@ begin
|
|||||||
fmt.FontIndex := ReadFont(styleChildNode, HYPERLINK_FONTINDEX)
|
fmt.FontIndex := ReadFont(styleChildNode, HYPERLINK_FONTINDEX)
|
||||||
else
|
else
|
||||||
fmt.FontIndex := ReadFont(styleChildNode);
|
fmt.FontIndex := ReadFont(styleChildNode);
|
||||||
{
|
|
||||||
if fmt.FontIndex = BOLD_FONTINDEX then
|
|
||||||
Include(fmt.UsedFormattingFields, uffBold)
|
|
||||||
else }
|
|
||||||
if fmt.FontIndex > 0 then
|
if fmt.FontIndex > 0 then
|
||||||
Include(fmt.UsedFormattingFields, uffFont);
|
Include(fmt.UsedFormattingFields, uffFont);
|
||||||
end else
|
end else
|
||||||
@ -3062,8 +3051,7 @@ begin
|
|||||||
if (s <> '') and (s <> 'transparent') then begin
|
if (s <> '') and (s <> 'transparent') then begin
|
||||||
clr := HTMLColorStrToColor(s);
|
clr := HTMLColorStrToColor(s);
|
||||||
// ODS does not support background fill patterns!
|
// ODS does not support background fill patterns!
|
||||||
fmt.Background.FgColor := IfThen(clr = TsColorValue(-1),
|
fmt.Background.FgColor := IfThen(clr = scNotDefined, scTransparent, clr);
|
||||||
scTransparent, Workbook.AddColorToPalette(clr));
|
|
||||||
fmt.Background.BgColor := fmt.Background.FgColor;
|
fmt.Background.BgColor := fmt.Background.FgColor;
|
||||||
if (fmt.Background.BgColor <> scTransparent) then
|
if (fmt.Background.BgColor <> scTransparent) then
|
||||||
begin
|
begin
|
||||||
@ -4444,8 +4432,6 @@ end;
|
|||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function TsSpreadOpenDocWriter.WriteBackgroundColorStyleXMLAsString(
|
function TsSpreadOpenDocWriter.WriteBackgroundColorStyleXMLAsString(
|
||||||
const AFormat: TsCellFormat): String;
|
const AFormat: TsCellFormat): String;
|
||||||
type
|
|
||||||
TRgb = record r,g,b,a: byte; end;
|
|
||||||
const // fraction of pattern color in fill pattern
|
const // fraction of pattern color in fill pattern
|
||||||
FRACTION: array[TsFillStyle] of Double = (
|
FRACTION: array[TsFillStyle] of Double = (
|
||||||
0.0, 1.0, 0.75, 0.50, 0.25, 0.125, 0.0625, // fsNoFill..fsGray6
|
0.0, 1.0, 0.75, 0.50, 0.25, 0.125, 0.0625, // fsNoFill..fsGray6
|
||||||
@ -4453,8 +4439,8 @@ const // fraction of pattern color in fill pattern
|
|||||||
0.25, 0.25, 0.25, 0.25, // fsThinStripeHor..fsThinStripeDiagDown
|
0.25, 0.25, 0.25, 0.25, // fsThinStripeHor..fsThinStripeDiagDown
|
||||||
0.5, 6.0/16, 0.75, 7.0/16); // fsHatchDiag..fsThinHatchHor
|
0.5, 6.0/16, 0.75, 7.0/16); // fsHatchDiag..fsThinHatchHor
|
||||||
var
|
var
|
||||||
fc,bc: TsColorValue;
|
fc,bc: TsColor;
|
||||||
mix: TRgb;
|
mix: TRgba;
|
||||||
fraction_fc, fraction_bc: Double;
|
fraction_fc, fraction_bc: Double;
|
||||||
begin
|
begin
|
||||||
Result := '';
|
Result := '';
|
||||||
@ -4463,22 +4449,22 @@ begin
|
|||||||
exit;
|
exit;
|
||||||
|
|
||||||
// Foreground and background colors
|
// Foreground and background colors
|
||||||
fc := Workbook.GetPaletteColor(AFormat.Background.FgColor);
|
fc := AFormat.Background.FgColor;
|
||||||
if Aformat.Background.BgColor = scTransparent then
|
if Aformat.Background.BgColor = scTransparent then
|
||||||
bc := Workbook.GetPaletteColor(scWhite)
|
bc := scWhite
|
||||||
else
|
else
|
||||||
bc := Workbook.GetPaletteColor(AFormat.Background.BgColor);
|
bc := AFormat.Background.BgColor;
|
||||||
|
|
||||||
// Mixing fraction
|
// Mixing fraction
|
||||||
fraction_fc := FRACTION[AFormat.Background.Style];
|
fraction_fc := FRACTION[AFormat.Background.Style];
|
||||||
fraction_bc := 1.0 - fraction_fc;
|
fraction_bc := 1.0 - fraction_fc;
|
||||||
// Mixed color
|
|
||||||
mix.r := Min(round(fraction_fc*TRgb(fc).r + fraction_bc*TRgb(bc).r), 255);
|
|
||||||
mix.g := Min(round(fraction_fc*TRgb(fc).g + fraction_bc*TRgb(bc).g), 255);
|
|
||||||
mix.b := Min(round(fraction_fc*TRgb(fc).b + fraction_bc*TRgb(bc).b), 255);
|
|
||||||
|
|
||||||
Result := Format('fo:background-color="%s" ', [
|
// Mixed color
|
||||||
ColorToHTMLColorStr(TsColorValue(mix))
|
mix.r := Min(round(fraction_fc*TRgba(fc).r + fraction_bc*TRgba(bc).r), 255);
|
||||||
]);
|
mix.g := Min(round(fraction_fc*TRgba(fc).g + fraction_bc*TRgba(bc).g), 255);
|
||||||
|
mix.b := Min(round(fraction_fc*TRgba(fc).b + fraction_bc*TRgba(bc).b), 255);
|
||||||
|
|
||||||
|
Result := Format('fo:background-color="%s" ', [ColorToHTMLColorStr(TsColor(mix))]);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
@ -4499,7 +4485,7 @@ begin
|
|||||||
Result := Result + Format('fo:border-bottom="%s %s %s" ', [
|
Result := Result + Format('fo:border-bottom="%s %s %s" ', [
|
||||||
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbSouth].LineStyle],
|
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbSouth].LineStyle],
|
||||||
BORDER_LINESTYLES[AFormat.BorderStyles[cbSouth].LineStyle],
|
BORDER_LINESTYLES[AFormat.BorderStyles[cbSouth].LineStyle],
|
||||||
Workbook.GetPaletteColorAsHTMLStr(AFormat.BorderStyles[cbSouth].Color)
|
ColorToHTMLColorStr(AFormat.BorderStyles[cbSouth].Color)
|
||||||
]);
|
]);
|
||||||
if AFormat.BorderStyles[cbSouth].LineStyle = lsDouble then
|
if AFormat.BorderStyles[cbSouth].LineStyle = lsDouble then
|
||||||
Result := Result + 'style:border-linewidth-bottom="0.002cm 0.035cm 0.002cm" ';
|
Result := Result + 'style:border-linewidth-bottom="0.002cm 0.035cm 0.002cm" ';
|
||||||
@ -4512,7 +4498,7 @@ begin
|
|||||||
Result := Result + Format('fo:border-left="%s %s %s" ', [
|
Result := Result + Format('fo:border-left="%s %s %s" ', [
|
||||||
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbWest].LineStyle],
|
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbWest].LineStyle],
|
||||||
BORDER_LINESTYLES[AFormat.BorderStyles[cbWest].LineStyle],
|
BORDER_LINESTYLES[AFormat.BorderStyles[cbWest].LineStyle],
|
||||||
Workbook.GetPaletteColorAsHTMLStr(AFormat.BorderStyles[cbWest].Color)
|
ColorToHTMLColorStr(AFormat.BorderStyles[cbWest].Color)
|
||||||
]);
|
]);
|
||||||
if AFormat.BorderStyles[cbWest].LineStyle = lsDouble then
|
if AFormat.BorderStyles[cbWest].LineStyle = lsDouble then
|
||||||
Result := Result + 'style:border-linewidth-left="0.002cm 0.035cm 0.002cm" ';
|
Result := Result + 'style:border-linewidth-left="0.002cm 0.035cm 0.002cm" ';
|
||||||
@ -4525,7 +4511,7 @@ begin
|
|||||||
Result := Result + Format('fo:border-right="%s %s %s" ', [
|
Result := Result + Format('fo:border-right="%s %s %s" ', [
|
||||||
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbEast].LineStyle],
|
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbEast].LineStyle],
|
||||||
BORDER_LINESTYLES[AFormat.BorderStyles[cbEast].LineStyle],
|
BORDER_LINESTYLES[AFormat.BorderStyles[cbEast].LineStyle],
|
||||||
Workbook.GetPaletteColorAsHTMLStr(AFormat.BorderStyles[cbEast].Color)
|
ColorToHTMLColorStr(AFormat.BorderStyles[cbEast].Color)
|
||||||
]);
|
]);
|
||||||
if AFormat.BorderStyles[cbSouth].LineStyle = lsDouble then
|
if AFormat.BorderStyles[cbSouth].LineStyle = lsDouble then
|
||||||
Result := Result + 'style:border-linewidth-right="0.002cm 0.035cm 0.002cm" ';
|
Result := Result + 'style:border-linewidth-right="0.002cm 0.035cm 0.002cm" ';
|
||||||
@ -4538,7 +4524,7 @@ begin
|
|||||||
Result := Result + Format('fo:border-top="%s %s %s" ', [
|
Result := Result + Format('fo:border-top="%s %s %s" ', [
|
||||||
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbNorth].LineStyle],
|
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbNorth].LineStyle],
|
||||||
BORDER_LINESTYLES[AFormat.BorderStyles[cbNorth].LineStyle],
|
BORDER_LINESTYLES[AFormat.BorderStyles[cbNorth].LineStyle],
|
||||||
Workbook.GetPaletteColorAsHTMLStr(AFormat.BorderStyles[cbNorth].Color)
|
ColorToHTMLColorStr(AFormat.BorderStyles[cbNorth].Color)
|
||||||
]);
|
]);
|
||||||
if AFormat.BorderStyles[cbSouth].LineStyle = lsDouble then
|
if AFormat.BorderStyles[cbSouth].LineStyle = lsDouble then
|
||||||
Result := Result + 'style:border-linewidth-top="0.002cm 0.035cm 0.002cm" ';
|
Result := Result + 'style:border-linewidth-top="0.002cm 0.035cm 0.002cm" ';
|
||||||
@ -4550,7 +4536,7 @@ begin
|
|||||||
Result := Result + Format('style:diagonal-bl-tr="%s %s %s" ', [
|
Result := Result + Format('style:diagonal-bl-tr="%s %s %s" ', [
|
||||||
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbDiagUp].LineStyle],
|
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbDiagUp].LineStyle],
|
||||||
BORDER_LINESTYLES[AFormat.BorderStyles[cbDiagUp].LineStyle],
|
BORDER_LINESTYLES[AFormat.BorderStyles[cbDiagUp].LineStyle],
|
||||||
Workbook.GetPaletteColorAsHTMLStr(AFormat.BorderStyles[cbDiagUp].Color)
|
ColorToHTMLColorStr(AFormat.BorderStyles[cbDiagUp].Color)
|
||||||
]);
|
]);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -4559,7 +4545,7 @@ begin
|
|||||||
Result := Result + Format('style:diagonal-tl-br="%s %s %s" ', [
|
Result := Result + Format('style:diagonal-tl-br="%s %s %s" ', [
|
||||||
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbDiagDown].LineStyle],
|
BORDER_LINEWIDTHS[AFormat.BorderStyles[cbDiagDown].LineStyle],
|
||||||
BORDER_LINESTYLES[AFormat.BorderStyles[cbDiagDown].LineStyle],
|
BORDER_LINESTYLES[AFormat.BorderStyles[cbDiagDown].LineStyle],
|
||||||
Workbook.GetPaletteColorAsHTMLStr(AFormat.BorderStyles[cbDiagDown].Color)
|
ColorToHTMLColorStr(AFormat.BorderStyles[cbDiagDown].Color)
|
||||||
]);
|
]);
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
@ -4613,7 +4599,7 @@ begin
|
|||||||
Result := Result + 'style:text-line-through-style="solid" ';
|
Result := Result + 'style:text-line-through-style="solid" ';
|
||||||
|
|
||||||
if AFont.Color <> defFnt.Color then
|
if AFont.Color <> defFnt.Color then
|
||||||
Result := Result + Format('fo:color="%s" ', [Workbook.GetPaletteColorAsHTMLStr(AFont.Color)]);
|
Result := Result + Format('fo:color="%s" ', [ColorToHTMLColorStr(AFont.Color)]);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TsSpreadOpenDocWriter.WriteFontStyleXMLAsString(
|
function TsSpreadOpenDocWriter.WriteFontStyleXMLAsString(
|
||||||
|
414
components/fpspreadsheet/fpspalette.pas
Normal file
414
components/fpspreadsheet/fpspalette.pas
Normal file
@ -0,0 +1,414 @@
|
|||||||
|
{ fpsPalette }
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Palette support for fpspreadsheet file formats
|
||||||
|
|
||||||
|
AUTHORS: Werner Pamler, Felipe Monteiro de Carvalho, Reinier Olislagers
|
||||||
|
|
||||||
|
LICENSE: See the file COPYING.modifiedLGPL.txt, included in the Lazarus
|
||||||
|
distribution, for details about the license.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
|
||||||
|
unit fpsPalette;
|
||||||
|
|
||||||
|
{$mode objfpc}{$H+}
|
||||||
|
|
||||||
|
interface
|
||||||
|
|
||||||
|
uses
|
||||||
|
Classes, SysUtils, fpstypes, fpspreadsheet;
|
||||||
|
|
||||||
|
type
|
||||||
|
|
||||||
|
{ TsPalette }
|
||||||
|
TsPalette = class
|
||||||
|
private
|
||||||
|
FColors: array of TsColor;
|
||||||
|
function GetColor(AIndex: Integer): TsColor;
|
||||||
|
procedure SetColor(AIndex: Integer; AColor: TsColor);
|
||||||
|
public
|
||||||
|
constructor Create;
|
||||||
|
procedure AddBuiltinColors; virtual;
|
||||||
|
function AddColor(AColor: TsColor; ABigEndian: Boolean = false): Integer;
|
||||||
|
procedure AddExcelColors;
|
||||||
|
function AddUniqueColor(AColor: TsColor; ABigEndian: Boolean = false): Integer;
|
||||||
|
procedure Clear;
|
||||||
|
procedure CollectFromWorkbook(AWorkbook: TsWorkbook);
|
||||||
|
function ColorUsedInWorkbook(APaletteIndex: Integer; AWorkbook: TsWorkbook): Boolean;
|
||||||
|
function FindClosestColorIndex(AColor: TsColor; AMaxPaletteCount: Integer = -1): Integer;
|
||||||
|
function FindColor(AColor: TsColor; AMaxPaletteCount: Integer = -1): Integer;
|
||||||
|
function Count: Integer;
|
||||||
|
procedure Trim(AMaxSize: Integer);
|
||||||
|
procedure UseColors(const AColors: array of TsColor; ABigEndian: Boolean = false);
|
||||||
|
property Colors[AIndex: Integer]: TsColor read GetColor write SetColor; default;
|
||||||
|
end;
|
||||||
|
|
||||||
|
procedure MakeLEPalette(var AColors: array of TsColor);
|
||||||
|
|
||||||
|
|
||||||
|
implementation
|
||||||
|
|
||||||
|
uses
|
||||||
|
fpsutils;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
If a palette is coded as big-endian (e.g. by copying the rgb values from
|
||||||
|
the OpenOffice documentation) the palette values can be converted by means
|
||||||
|
of this procedure to little-endian which is required by fpspreadsheet.
|
||||||
|
|
||||||
|
@param AColors Color array to be converted.
|
||||||
|
After conversion, its color values are replaced.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure MakeLEPalette(var AColors: array of TsColor);
|
||||||
|
var
|
||||||
|
i: Integer;
|
||||||
|
begin
|
||||||
|
for i := 0 to High(AColors) do
|
||||||
|
AColors[i] := LongRGBToExcelPhysical(AColors[i])
|
||||||
|
end;
|
||||||
|
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Constructor of the palette: initializes the color array
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
constructor TsPalette.Create;
|
||||||
|
begin
|
||||||
|
inherited;
|
||||||
|
SetLength(FColors, 0);
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Adds an rgb color value to the palette and returns the palette index
|
||||||
|
of the new color.
|
||||||
|
|
||||||
|
Existing colors are not checked.
|
||||||
|
|
||||||
|
If ABigEndian is TRUE then the rgb values are assumed to be in big endian
|
||||||
|
order (r = high byte).
|
||||||
|
By default, rgb is in little-endian order (r = low byte)
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function TsPalette.AddColor(AColor: TsColor; ABigEndian: Boolean = false): Integer;
|
||||||
|
begin
|
||||||
|
if ABigEndian then
|
||||||
|
AColor := LongRGBToExcelPhysical(AColor);
|
||||||
|
|
||||||
|
SetLength(FColors, Length(FColors) + 1);
|
||||||
|
FColors[High(FColors)] := AColor;
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Adds the built-in colors
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsPalette.AddBuiltinColors;
|
||||||
|
begin
|
||||||
|
AddColor(scBlack); // 0
|
||||||
|
AddColor(scWhite); // 1
|
||||||
|
AddColor(scRed); // 2
|
||||||
|
AddColor(scGreen); // 3
|
||||||
|
AddColor(scBlue); // 4
|
||||||
|
AddColor(scYellow); // 5
|
||||||
|
AddColor(scMagenta); // 6
|
||||||
|
AddColor(scCyan); // 7
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Adds the standard palette of Excel 8
|
||||||
|
|
||||||
|
NOTE: To get the full Excel8 palette call this after AddBuiltinColors
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsPalette.AddExcelColors;
|
||||||
|
begin
|
||||||
|
AddColor($000000, true); // $08: EGA black
|
||||||
|
AddColor($FFFFFF, true); // $09: EGA white
|
||||||
|
AddColor($FF0000, true); // $0A: EGA red
|
||||||
|
AddColor($00FF00, true); // $0B: EGA green
|
||||||
|
AddColor($0000FF, true); // $0C: EGA blue
|
||||||
|
AddColor($FFFF00, true); // $0D: EGA yellow
|
||||||
|
AddColor($FF00FF, true); // $0E: EGA magenta
|
||||||
|
AddColor($00FFFF, true); // $0F: EGA cyan
|
||||||
|
|
||||||
|
AddColor($800000, true); // $10: EGA dark red
|
||||||
|
AddColor($008000, true); // $11: EGA dark green
|
||||||
|
AddColor($000080, true); // $12: EGA dark blue
|
||||||
|
AddColor($808000, true); // $13: EGA olive
|
||||||
|
AddColor($800080, true); // $14: EGA purple
|
||||||
|
AddColor($008080, true); // $15: EGA teal
|
||||||
|
AddColor($C0C0C0, true); // $16: EGA silver
|
||||||
|
AddColor($808080, true); // $17: EGA gray
|
||||||
|
|
||||||
|
AddColor($9999FF, true); // $18:
|
||||||
|
AddColor($993366, true); // $19:
|
||||||
|
AddColor($FFFFCC, true); // $1A:
|
||||||
|
AddColor($CCFFFF, true); // $1B:
|
||||||
|
AddColor($660066, true); // $1C:
|
||||||
|
AddColor($FF8080, true); // $1D:
|
||||||
|
AddColor($0066CC, true); // $1E:
|
||||||
|
AddColor($CCCCFF, true); // $1F:
|
||||||
|
|
||||||
|
AddColor($000080, true); // $20:
|
||||||
|
AddColor($FF00FF, true); // $21:
|
||||||
|
AddColor($FFFF00, true); // $22:
|
||||||
|
AddColor($00FFFF, true); // $23:
|
||||||
|
AddColor($800080, true); // $24:
|
||||||
|
AddColor($800000, true); // $25:
|
||||||
|
AddColor($008080, true); // $26:
|
||||||
|
AddColor($0000FF, true); // $27:
|
||||||
|
AddColor($00CCFF, true); // $28:
|
||||||
|
AddColor($CCFFFF, true); // $29:
|
||||||
|
AddColor($CCFFCC, true); // $2A:
|
||||||
|
AddColor($FFFF99, true); // $2B:
|
||||||
|
AddColor($99CCFF, true); // $2C:
|
||||||
|
AddColor($FF99CC, true); // $2D:
|
||||||
|
AddColor($CC99FF, true); // $2E:
|
||||||
|
AddColor($FFCC99, true); // $2F:
|
||||||
|
|
||||||
|
AddColor($3366FF, true); // $30:
|
||||||
|
AddColor($33CCCC, true); // $31:
|
||||||
|
AddColor($99CC00, true); // $32:
|
||||||
|
AddColor($FFCC00, true); // $33:
|
||||||
|
AddColor($FF9900, true); // $34:
|
||||||
|
AddColor($FF6600, true); // $35:
|
||||||
|
AddColor($666699, true); // $36:
|
||||||
|
AddColor($969696, true); // $37:
|
||||||
|
AddColor($003366, true); // $38:
|
||||||
|
AddColor($339966, true); // $39:
|
||||||
|
AddColor($003300, true); // $3A:
|
||||||
|
AddColor($333300, true); // $3B:
|
||||||
|
AddColor($993300, true); // $3C:
|
||||||
|
AddColor($993366, true); // $3D:
|
||||||
|
AddColor($333399, true); // $3E:
|
||||||
|
AddColor($333333, true); // $3F:
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Adds the specified color to the palette if it does not yet exist.
|
||||||
|
|
||||||
|
Returns the palette index of the new or existing color
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function TsPalette.AddUniqueColor(AColor: TsColor;
|
||||||
|
ABigEndian: Boolean = false): Integer;
|
||||||
|
begin
|
||||||
|
if ABigEndian then
|
||||||
|
AColor := LongRGBToExcelPhysical(AColor);
|
||||||
|
|
||||||
|
Result := FindColor(AColor);
|
||||||
|
if Result = -1 then result := AddColor(AColor);
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Clears the palette
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsPalette.Clear;
|
||||||
|
begin
|
||||||
|
SetLength(FColors, 0);
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Collects the colors used in the specified workbook
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsPalette.CollectFromWorkbook(AWorkbook: TsWorkbook);
|
||||||
|
var
|
||||||
|
i: Integer;
|
||||||
|
sheet: TsWorksheet;
|
||||||
|
cell: PCell;
|
||||||
|
fmt: TsCellFormat;
|
||||||
|
fnt: TsFont;
|
||||||
|
cb: TsCellBorder;
|
||||||
|
begin
|
||||||
|
for i:=0 to AWorkbook.GetWorksheetCount-1 do
|
||||||
|
begin
|
||||||
|
sheet := AWorkbook.GetWorksheetByIndex(i);
|
||||||
|
for cell in sheet.Cells do begin
|
||||||
|
fmt := sheet.ReadCellFormat(cell);
|
||||||
|
if (uffBackground in fmt.UsedFormattingFields) then
|
||||||
|
begin
|
||||||
|
AddUniqueColor(fmt.Background.BgColor);
|
||||||
|
AddUniqueColor(fmt.Background.FgColor);
|
||||||
|
end;
|
||||||
|
if (uffFont in fmt.UsedFormattingFields) then
|
||||||
|
begin
|
||||||
|
fnt := AWorkbook.GetFont(fmt.FontIndex);
|
||||||
|
AddUniqueColor(fnt.Color);
|
||||||
|
end;
|
||||||
|
if (uffBorder in fmt.UsedFormattingFields) then
|
||||||
|
begin
|
||||||
|
for cb in TsCellBorder do
|
||||||
|
if (cb in fmt.Border) then
|
||||||
|
AddUniqueColor(fmt.BorderStyles[cb].Color);
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Checks whether a given color is used somewhere within the entire workbook
|
||||||
|
|
||||||
|
@param APaletteIndex Palette index of the color
|
||||||
|
@result True if the color is used by at least one cell, false if not.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function TsPalette.ColorUsedInWorkbook(APaletteIndex: Integer;
|
||||||
|
AWorkbook: TsWorkbook): Boolean;
|
||||||
|
var
|
||||||
|
sheet: TsWorksheet;
|
||||||
|
cell: PCell;
|
||||||
|
i: Integer;
|
||||||
|
fnt: TsFont;
|
||||||
|
b: TsCellBorder;
|
||||||
|
fmt: PsCellFormat;
|
||||||
|
color: TsColor;
|
||||||
|
begin
|
||||||
|
color := GetColor(APaletteIndex);
|
||||||
|
if (color = scNotDefined) or (AWorkbook = nil) then
|
||||||
|
exit(false);
|
||||||
|
|
||||||
|
Result := true;
|
||||||
|
for i:=0 to AWorkbook.GetWorksheetCount-1 do
|
||||||
|
begin
|
||||||
|
sheet := AWorkbook.GetWorksheetByIndex(i);
|
||||||
|
for cell in sheet.Cells do
|
||||||
|
begin
|
||||||
|
fmt := AWorkbook.GetPointerToCellFormat(cell^.FormatIndex);
|
||||||
|
if (uffBackground in fmt^.UsedFormattingFields) then
|
||||||
|
begin
|
||||||
|
if fmt^.Background.BgColor = color then exit;
|
||||||
|
if fmt^.Background.FgColor = color then exit;
|
||||||
|
end;
|
||||||
|
if (uffBorder in fmt^.UsedFormattingFields) then
|
||||||
|
for b in TsCellBorders do
|
||||||
|
if (b in fmt^.Border) and (fmt^.BorderStyles[b].Color = color) then
|
||||||
|
exit;
|
||||||
|
if (uffFont in fmt^.UsedFormattingFields) then
|
||||||
|
begin
|
||||||
|
fnt := AWorkbook.GetFont(fmt^.FontIndex);
|
||||||
|
if fnt.Color = color then
|
||||||
|
exit;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
Result := false;
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Finds the palette color index which points to a color that is "closest" to a
|
||||||
|
given color. "Close" means here smallest length of the rgb-difference vector.
|
||||||
|
|
||||||
|
@param AColor Rgb color value to be considered
|
||||||
|
@param AMaxPaletteCount Number of palette entries considered. Example:
|
||||||
|
BIFF5/BIFF8 can write only 64 colors, i.e
|
||||||
|
AMaxPaletteCount = 64
|
||||||
|
@return Palette index of the color closest to AColor
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function TsPalette.FindClosestColorIndex(AColor: TsColor;
|
||||||
|
AMaxPaletteCount: Integer = -1): Integer;
|
||||||
|
type
|
||||||
|
TRGBA = record r,g,b,a: Byte end;
|
||||||
|
var
|
||||||
|
rgb: TRGBA;
|
||||||
|
rgb0: TRGBA absolute AColor;
|
||||||
|
dist: Double;
|
||||||
|
minDist: Double;
|
||||||
|
i: Integer;
|
||||||
|
n: Integer;
|
||||||
|
begin
|
||||||
|
Result := -1;
|
||||||
|
minDist := 1E108;
|
||||||
|
n := Length(FColors);
|
||||||
|
if AMaxPaletteCount > n then n := AMaxPaletteCount;
|
||||||
|
for i := 0 to n - 1 do
|
||||||
|
begin
|
||||||
|
rgb := TRGBA(GetColor(i));
|
||||||
|
dist := sqr(rgb.r - rgb0.r) + sqr(rgb.g - rgb0.g) + sqr(rgb.b - rgb0.b);
|
||||||
|
if dist < minDist then
|
||||||
|
begin
|
||||||
|
Result := i;
|
||||||
|
minDist := dist;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Finds the palette color index which belongs to the specified color.
|
||||||
|
Returns -1 if the color is not contained in the palette.
|
||||||
|
|
||||||
|
@param AColor Rgb color value to be considered
|
||||||
|
@param AMaxPaletteCount Number of palette entries considered. Example:
|
||||||
|
BIFF5/BIFF8 can write only 64 colors, i.e
|
||||||
|
AMaxPaletteCount = 64
|
||||||
|
@return Palette index of AColor
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function TsPalette.FindColor(AColor: TsColor;
|
||||||
|
AMaxPaletteCount: Integer = -1): Integer;
|
||||||
|
var
|
||||||
|
n: Integer;
|
||||||
|
begin
|
||||||
|
n := Length(FColors);
|
||||||
|
if AMaxPaletteCount > n then n := AMaxPaletteCount;
|
||||||
|
for Result := 0 to n - 1 do
|
||||||
|
if GetColor(Result) = AColor then
|
||||||
|
exit;
|
||||||
|
Result := -1;
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Reads the rgb color for the given index from the palette.
|
||||||
|
Can be type-cast to TColor for usage in GUI applications.
|
||||||
|
|
||||||
|
@param AIndex Index of the color considered
|
||||||
|
@return A number containing the rgb components in little-endian notation.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function TsPalette.GetColor(AIndex: Integer): TsColor;
|
||||||
|
begin
|
||||||
|
if (AIndex >= 0) and (AIndex < Length(FColors)) then
|
||||||
|
Result := FColors[AIndex]
|
||||||
|
else
|
||||||
|
Result := scNotDefined;
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Returns the number of palette colors
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function TsPalette.Count: Integer;
|
||||||
|
begin
|
||||||
|
Result := Length(FColors);
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Replaces a color value of the palette by a new value.
|
||||||
|
The color must be given in little-endian notation (ABGR, with A=0).
|
||||||
|
|
||||||
|
@param AIndex Palette index of the color to be replaced
|
||||||
|
@param AColor Number containing the rgb components of the new color
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsPalette.SetColor(AIndex: Integer; AColor: TsColor);
|
||||||
|
begin
|
||||||
|
if (AIndex >= 0) and (AIndex < Length(FColors)) then
|
||||||
|
FColors[AIndex] := AColor;
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Trims the size of the palette
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsPalette.Trim(AMaxSize: Integer);
|
||||||
|
begin
|
||||||
|
if Length(FColors) > AMaxSize then
|
||||||
|
SetLength(FColors, AMaxSize);
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Uses the color array to with "APalette" points in the palette.
|
||||||
|
If ABigEndian is true it is assumed that the input colors are specified in
|
||||||
|
big-endian notation, i.e. "blue" in the low-value byte.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsPalette.UseColors(const AColors: array of TsColor; ABigEndian: Boolean = false);
|
||||||
|
var
|
||||||
|
i: Integer;
|
||||||
|
begin
|
||||||
|
SetLength(FColors, High(AColors)+1);
|
||||||
|
if ABigEndian then
|
||||||
|
for i:=0 to High(AColors) do FColors[i] := LongRGBToExcelPhysical(AColors[i])
|
||||||
|
else
|
||||||
|
for i:=0 to High(AColors) do FColors[i] := AColors[i];
|
||||||
|
end;
|
||||||
|
|
||||||
|
|
||||||
|
end.
|
@ -549,7 +549,7 @@ type
|
|||||||
FWorksheets: TFPList;
|
FWorksheets: TFPList;
|
||||||
FFormat: TsSpreadsheetFormat;
|
FFormat: TsSpreadsheetFormat;
|
||||||
FBuiltinFontCount: Integer;
|
FBuiltinFontCount: Integer;
|
||||||
FPalette: array of TsColorValue;
|
//FPalette: array of TsColorValue;
|
||||||
FVirtualColCount: Cardinal;
|
FVirtualColCount: Cardinal;
|
||||||
FVirtualRowCount: Cardinal;
|
FVirtualRowCount: Cardinal;
|
||||||
FReadWriteFlag: TsReadWriteFlag;
|
FReadWriteFlag: TsReadWriteFlag;
|
||||||
@ -565,7 +565,7 @@ type
|
|||||||
FOnRemoveWorksheet: TsRemoveWorksheetEvent;
|
FOnRemoveWorksheet: TsRemoveWorksheetEvent;
|
||||||
FOnRemovingWorksheet: TsWorksheetEvent;
|
FOnRemovingWorksheet: TsWorksheetEvent;
|
||||||
FOnSelectWorksheet: TsWorksheetEvent;
|
FOnSelectWorksheet: TsWorksheetEvent;
|
||||||
FOnChangePalette: TNotifyEvent;
|
// FOnChangePalette: TNotifyEvent;
|
||||||
FFileName: String;
|
FFileName: String;
|
||||||
FLockCount: Integer;
|
FLockCount: Integer;
|
||||||
FLog: TStringList;
|
FLog: TStringList;
|
||||||
@ -668,11 +668,8 @@ type
|
|||||||
function AddNumberFormat(AFormatStr: String): Integer;
|
function AddNumberFormat(AFormatStr: String): Integer;
|
||||||
function GetNumberFormat(AIndex: Integer): TsNumFormatParams;
|
function GetNumberFormat(AIndex: Integer): TsNumFormatParams;
|
||||||
function GetNumberFormatCount: Integer;
|
function GetNumberFormatCount: Integer;
|
||||||
|
(*
|
||||||
{ Color handling }
|
{ Color handling }
|
||||||
function AddColorToPalette(AColorValue: TsColorValue): TsColor;
|
|
||||||
function FindClosestColor(AColorValue: TsColorValue;
|
|
||||||
AMaxPaletteCount: Integer = -1): TsColor;
|
|
||||||
function FPSColorToHexString(AColor: TsColor; ARGBColor: TFPColor): String;
|
function FPSColorToHexString(AColor: TsColor; ARGBColor: TFPColor): String;
|
||||||
function GetColorName(AColorIndex: TsColor): string; overload;
|
function GetColorName(AColorIndex: TsColor): string; overload;
|
||||||
procedure GetColorName(AColorValue: TsColorValue; out AName: String); overload;
|
procedure GetColorName(AColorValue: TsColorValue; out AName: String); overload;
|
||||||
@ -684,6 +681,7 @@ type
|
|||||||
procedure UsePalette(APalette: PsPalette; APaletteCount: Word;
|
procedure UsePalette(APalette: PsPalette; APaletteCount: Word;
|
||||||
ABigEndian: Boolean = false);
|
ABigEndian: Boolean = false);
|
||||||
function UsesColor(AColorIndex: TsColor): Boolean;
|
function UsesColor(AColorIndex: TsColor): Boolean;
|
||||||
|
*)
|
||||||
|
|
||||||
{ Utilities }
|
{ Utilities }
|
||||||
procedure UpdateCaches;
|
procedure UpdateCaches;
|
||||||
@ -708,7 +706,7 @@ type
|
|||||||
{@@ This event fires whenever a new worksheet is added }
|
{@@ This event fires whenever a new worksheet is added }
|
||||||
property OnAddWorksheet: TsWorksheetEvent read FOnAddWorksheet write FOnAddWorksheet;
|
property OnAddWorksheet: TsWorksheetEvent read FOnAddWorksheet write FOnAddWorksheet;
|
||||||
{@@ This event fires whenever the workbook palette changes. }
|
{@@ This event fires whenever the workbook palette changes. }
|
||||||
property OnChangePalette: TNotifyEvent read FOnChangePalette write FOnChangePalette;
|
// property OnChangePalette: TNotifyEvent read FOnChangePalette write FOnChangePalette;
|
||||||
{@@ This event fires whenever a worksheet is changed }
|
{@@ This event fires whenever a worksheet is changed }
|
||||||
property OnChangeWorksheet: TsWorksheetEvent read FOnChangeWorksheet write FOnChangeWorksheet;
|
property OnChangeWorksheet: TsWorksheetEvent read FOnChangeWorksheet write FOnChangeWorksheet;
|
||||||
{@@ This event fires whenever a workbook is loaded }
|
{@@ This event fires whenever a workbook is loaded }
|
||||||
@ -778,7 +776,6 @@ type
|
|||||||
procedure CopyCellFormat(AFromCell, AToCell: PCell);
|
procedure CopyCellFormat(AFromCell, AToCell: PCell);
|
||||||
procedure CopyCellValue(AFromCell, AToCell: PCell);
|
procedure CopyCellValue(AFromCell, AToCell: PCell);
|
||||||
|
|
||||||
procedure MakeLEPalette(APalette: PsPalette; APaletteSize: Integer);
|
|
||||||
//function SameCellBorders(ACell1, ACell2: PCell): Boolean; overload;
|
//function SameCellBorders(ACell1, ACell2: PCell): Boolean; overload;
|
||||||
function SameCellBorders(AFormat1, AFormat2: PsCellFormat): Boolean; //overload;
|
function SameCellBorders(AFormat1, AFormat2: PsCellFormat): Boolean; //overload;
|
||||||
|
|
||||||
@ -826,7 +823,7 @@ const
|
|||||||
DEF_CHART_NEUTRAL_COLORVALUE = $FFFFFF;
|
DEF_CHART_NEUTRAL_COLORVALUE = $FFFFFF;
|
||||||
DEF_TOOLTIP_TEXT_COLORVALUE = $000000;
|
DEF_TOOLTIP_TEXT_COLORVALUE = $000000;
|
||||||
DEF_FONT_AUTOMATIC_COLORVALUE = $000000;
|
DEF_FONT_AUTOMATIC_COLORVALUE = $000000;
|
||||||
|
(*
|
||||||
var
|
var
|
||||||
{@@ RGB colors RGB in "big-endian" notation (red at left). The values are inverted
|
{@@ RGB colors RGB in "big-endian" notation (red at left). The values are inverted
|
||||||
at initialization to be little-endian at run-time!
|
at initialization to be little-endian at run-time!
|
||||||
@ -883,26 +880,7 @@ var
|
|||||||
'beige', // $15
|
'beige', // $15
|
||||||
'wheat' // $16
|
'wheat' // $16
|
||||||
);
|
);
|
||||||
|
*)
|
||||||
{@@ ----------------------------------------------------------------------------
|
|
||||||
If a palette is coded as big-endian (e.g. by copying the rgb values from
|
|
||||||
the OpenOffice documentation) the palette values can be converted by means
|
|
||||||
of this procedure to little-endian which is required internally by TsWorkbook.
|
|
||||||
|
|
||||||
@param APalette Pointer to the palette to be converted. After conversion,
|
|
||||||
its color values are replaced.
|
|
||||||
@param APaletteSize Number of colors contained in the palette
|
|
||||||
-------------------------------------------------------------------------------}
|
|
||||||
procedure MakeLEPalette(APalette: PsPalette; APaletteSize: Integer);
|
|
||||||
var
|
|
||||||
i: Integer;
|
|
||||||
begin
|
|
||||||
{$PUSH}{$R-}
|
|
||||||
for i := 0 to APaletteSize-1 do
|
|
||||||
APalette^[i] := LongRGBToExcelPhysical(APalette^[i])
|
|
||||||
{$POP}
|
|
||||||
end;
|
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Copies the format of a cell to another one.
|
Copies the format of a cell to another one.
|
||||||
|
|
||||||
@ -916,7 +894,6 @@ var
|
|||||||
numFmtParams: TsNumFormatParams;
|
numFmtParams: TsNumFormatParams;
|
||||||
nfs: String;
|
nfs: String;
|
||||||
font: TsFont;
|
font: TsFont;
|
||||||
clr: TsColorvalue;
|
|
||||||
cb: TsCellBorder;
|
cb: TsCellBorder;
|
||||||
begin
|
begin
|
||||||
Assert(AFromCell <> nil);
|
Assert(AFromCell <> nil);
|
||||||
@ -929,6 +906,7 @@ begin
|
|||||||
begin
|
begin
|
||||||
fmt := sourceSheet.ReadCellFormat(AFromCell);
|
fmt := sourceSheet.ReadCellFormat(AFromCell);
|
||||||
//destSheet.WriteCellFormat(AToCell, fmt);
|
//destSheet.WriteCellFormat(AToCell, fmt);
|
||||||
|
{
|
||||||
if (uffBackground in fmt.UsedFormattingFields) then
|
if (uffBackground in fmt.UsedFormattingFields) then
|
||||||
begin
|
begin
|
||||||
clr := sourceSheet.Workbook.GetPaletteColor(fmt.Background.BgColor);
|
clr := sourceSheet.Workbook.GetPaletteColor(fmt.Background.BgColor);
|
||||||
@ -936,21 +914,26 @@ begin
|
|||||||
clr := sourceSheet.Workbook.GetPaletteColor(fmt.Background.FgColor);
|
clr := sourceSheet.Workbook.GetPaletteColor(fmt.Background.FgColor);
|
||||||
fmt.Background.FgColor := destSheet.Workbook.AddColorToPalette(clr);
|
fmt.Background.FgColor := destSheet.Workbook.AddColorToPalette(clr);
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
if (uffFont in fmt.UsedFormattingFields) then
|
if (uffFont in fmt.UsedFormattingFields) then
|
||||||
begin
|
begin
|
||||||
font := sourceSheet.ReadCellFont(AFromCell);
|
font := sourceSheet.ReadCellFont(AFromCell);
|
||||||
|
{
|
||||||
clr := sourceSheet.Workbook.GetPaletteColor(font.Color);
|
clr := sourceSheet.Workbook.GetPaletteColor(font.Color);
|
||||||
font.Color := destSheet.Workbook.AddColorToPalette(clr);
|
font.Color := destSheet.Workbook.AddColorToPalette(clr);
|
||||||
|
}
|
||||||
fmt.FontIndex := destSheet.Workbook.FindFont(font.FontName, font.Size, font.Style, font.Color);
|
fmt.FontIndex := destSheet.Workbook.FindFont(font.FontName, font.Size, font.Style, font.Color);
|
||||||
if fmt.FontIndex = -1 then
|
if fmt.FontIndex = -1 then
|
||||||
fmt.FontIndex := destSheet.Workbook.AddFont(font.FontName, font.Size, font.Style, font.Color);
|
fmt.FontIndex := destSheet.Workbook.AddFont(font.FontName, font.Size, font.Style, font.Color);
|
||||||
end;
|
end;
|
||||||
|
{
|
||||||
if (uffBorder in fmt.UsedFormattingFields) then
|
if (uffBorder in fmt.UsedFormattingFields) then
|
||||||
for cb in fmt.Border do
|
for cb in fmt.Border do
|
||||||
begin
|
begin
|
||||||
clr := sourceSheet.Workbook.GetPaletteColor(fmt.BorderStyles[cb].Color);
|
clr := sourceSheet.Workbook.GetPaletteColor(fmt.BorderStyles[cb].Color);
|
||||||
fmt.BorderStyles[cb].Color := destSheet.Workbook.AddColorToPalette(clr);
|
fmt.BorderStyles[cb].Color := destSheet.Workbook.AddColorToPalette(clr);
|
||||||
end;
|
end;
|
||||||
|
}
|
||||||
if (uffNumberformat in fmt.UsedFormattingFields) then
|
if (uffNumberformat in fmt.UsedFormattingFields) then
|
||||||
begin
|
begin
|
||||||
numFmtParams := sourceSheet.Workbook.GetNumberFormat(fmt.NumberFormatIndex);
|
numFmtParams := sourceSheet.Workbook.GetNumberFormat(fmt.NumberFormatIndex);
|
||||||
@ -1086,7 +1069,8 @@ begin
|
|||||||
IfThen(fssItalic in fnt.Style, 'i', '.'),
|
IfThen(fssItalic in fnt.Style, 'i', '.'),
|
||||||
IfThen(fssUnderline in fnt.Style, 'u', '.'),
|
IfThen(fssUnderline in fnt.Style, 'u', '.'),
|
||||||
IfThen(fssStrikeOut in fnt.Style, 's', '.'),
|
IfThen(fssStrikeOut in fnt.Style, 's', '.'),
|
||||||
AWorkbook.GetPaletteColorAsHTMLStr(fnt.Color)
|
ColorToHTMLColorStr(fnt.Color)
|
||||||
|
//AWorkbook.GetPaletteColorAsHTMLStr(fnt.Color)
|
||||||
]));
|
]));
|
||||||
end;
|
end;
|
||||||
L.SaveToFile(AFileName);
|
L.SaveToFile(AFileName);
|
||||||
@ -2847,10 +2831,10 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Returns the background color of a cell as index into the workbook's color palette.
|
Returns the background color of a cell as rbg value
|
||||||
|
|
||||||
@param ACell Pointer to the cell
|
@param ACell Pointer to the cell
|
||||||
@return Index of the cell background color into the workbook's color palette
|
@return Value containing the rgb bytes in little-endian order
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function TsWorksheet.ReadBackgroundColor(ACell: PCell): TsColor;
|
function TsWorksheet.ReadBackgroundColor(ACell: PCell): TsColor;
|
||||||
var
|
var
|
||||||
@ -4857,8 +4841,7 @@ end;
|
|||||||
|
|
||||||
@param ARow The row of the cell
|
@param ARow The row of the cell
|
||||||
@param ACol The column of the cell
|
@param ACol The column of the cell
|
||||||
@param AFontColor Index into the workbook's color palette identifying the
|
@param AFontColor RGB value of the new text color
|
||||||
new text color.
|
|
||||||
@return Index of the font in the workbook's font list.
|
@return Index of the font in the workbook's font list.
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function TsWorksheet.WriteFontColor(ARow, ACol: Cardinal; AFontColor: TsColor): Integer;
|
function TsWorksheet.WriteFontColor(ARow, ACol: Cardinal; AFontColor: TsColor): Integer;
|
||||||
@ -4872,8 +4855,7 @@ end;
|
|||||||
is created. Returns the index of this font in the font list.
|
is created. Returns the index of this font in the font list.
|
||||||
|
|
||||||
@param ACell Pointer to the cell
|
@param ACell Pointer to the cell
|
||||||
@param AFontColor Index into the workbook's color palette identifying the
|
@param AFontColor RGB value of the new text color
|
||||||
new text color.
|
|
||||||
@return Index of the font in the workbook's font list.
|
@return Index of the font in the workbook's font list.
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function TsWorksheet.WriteFontColor(ACell: PCell; AFontColor: TsColor): Integer;
|
function TsWorksheet.WriteFontColor(ACell: PCell; AFontColor: TsColor): Integer;
|
||||||
@ -5093,8 +5075,8 @@ end;
|
|||||||
@param ARow Row index of the cell
|
@param ARow Row index of the cell
|
||||||
@param ACol Column index of the cell
|
@param ACol Column index of the cell
|
||||||
@param AFillStyle Fill style to be used - see TsFillStyle
|
@param AFillStyle Fill style to be used - see TsFillStyle
|
||||||
@param APatternColor Palette index of the pattern color
|
@param APatternColor RGB value of the pattern color
|
||||||
@param ABackgroundColor Palette index of the background color
|
@param ABackgroundColor RGB value of the background color
|
||||||
@return Pointer to cell
|
@return Pointer to cell
|
||||||
|
|
||||||
@NOTE Is replaced by uniform fill if WriteBackgroundColor is called later.
|
@NOTE Is replaced by uniform fill if WriteBackgroundColor is called later.
|
||||||
@ -5111,8 +5093,8 @@ end;
|
|||||||
|
|
||||||
@param ACell Pointer to the cell
|
@param ACell Pointer to the cell
|
||||||
@param AStyle Fill style ("pattern") to be used - see TsFillStyle
|
@param AStyle Fill style ("pattern") to be used - see TsFillStyle
|
||||||
@param APatternColor Palette index of the pattern color
|
@param APatternColor RGB value of the pattern color
|
||||||
@param ABackgroundColor Palette index of the background color
|
@param ABackgroundColor RGB value of the background color
|
||||||
|
|
||||||
@NOTE Is replaced by uniform fill if WriteBackgroundColor is called later.
|
@NOTE Is replaced by uniform fill if WriteBackgroundColor is called later.
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
@ -5147,9 +5129,9 @@ end;
|
|||||||
|
|
||||||
@param ARow Row index of the cell
|
@param ARow Row index of the cell
|
||||||
@param ACol Column index of the cell
|
@param ACol Column index of the cell
|
||||||
@param AColor Index of the new background color into the workbook's
|
@param AColor RGB value of the new background color.
|
||||||
color palette. Use the color index scTransparent to
|
Use the value "scTransparent" to clear an existing
|
||||||
erase an existing background color.
|
background color.
|
||||||
@return Pointer to cell
|
@return Pointer to cell
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function TsWorksheet.WriteBackgroundColor(ARow, ACol: Cardinal;
|
function TsWorksheet.WriteBackgroundColor(ARow, ACol: Cardinal;
|
||||||
@ -5163,9 +5145,9 @@ end;
|
|||||||
Sets a uniform background color of a cell.
|
Sets a uniform background color of a cell.
|
||||||
|
|
||||||
@param ACell Pointer to cell
|
@param ACell Pointer to cell
|
||||||
@param AColor Index of the new background color into the workbook's
|
@param AColor RGB value of the new background color.
|
||||||
color palette. Use the color index scTransparent to
|
Use the value "scTransparent" to clear an existing
|
||||||
erase an existing background color.
|
background color.
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
procedure TsWorksheet.WriteBackgroundColor(ACell: PCell; AColor: TsColor);
|
procedure TsWorksheet.WriteBackgroundColor(ACell: PCell; AColor: TsColor);
|
||||||
begin
|
begin
|
||||||
@ -5185,8 +5167,7 @@ end;
|
|||||||
@param ACol Column index of the cell
|
@param ACol Column index of the cell
|
||||||
@param ABorder Indicates to which border (left/top etc) this color is
|
@param ABorder Indicates to which border (left/top etc) this color is
|
||||||
to be applied
|
to be applied
|
||||||
@param AColor Index of the new border color into the workbook's
|
@param AColor RGB value of the new border color
|
||||||
color palette.
|
|
||||||
@return Pointer to cell
|
@return Pointer to cell
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function TsWorksheet.WriteBorderColor(ARow, ACol: Cardinal;
|
function TsWorksheet.WriteBorderColor(ARow, ACol: Cardinal;
|
||||||
@ -5203,8 +5184,7 @@ end;
|
|||||||
@param ACell Pointer to cell
|
@param ACell Pointer to cell
|
||||||
@param ABorder Indicates to which border (left/top etc) this color is
|
@param ABorder Indicates to which border (left/top etc) this color is
|
||||||
to be applied
|
to be applied
|
||||||
@param AColor Index of the new border color into the workbook's
|
@param AColor RGB value of the new border color
|
||||||
color palette.
|
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
procedure TsWorksheet.WriteBorderColor(ACell: PCell; ABorder: TsCellBorder;
|
procedure TsWorksheet.WriteBorderColor(ACell: PCell; ABorder: TsCellBorder;
|
||||||
AColor: TsColor);
|
AColor: TsColor);
|
||||||
@ -5355,7 +5335,7 @@ end;
|
|||||||
@param ACol Column index of the considered cell
|
@param ACol Column index of the considered cell
|
||||||
@param ABorder Identifier of the border to be modified
|
@param ABorder Identifier of the border to be modified
|
||||||
@param ALineStyle Identifier for the new line style of the border
|
@param ALineStyle Identifier for the new line style of the border
|
||||||
@param AColor Palette index for the color of the border line
|
@param AColor RGB value of the border line color
|
||||||
@return Pointer to cell
|
@return Pointer to cell
|
||||||
|
|
||||||
@see WriteBorderStyles
|
@see WriteBorderStyles
|
||||||
@ -5374,7 +5354,7 @@ end;
|
|||||||
@param ACell Pointer to cell
|
@param ACell Pointer to cell
|
||||||
@param ABorder Identifier of the border to be modified
|
@param ABorder Identifier of the border to be modified
|
||||||
@param ALineStyle Identifier for the new line style of the border
|
@param ALineStyle Identifier for the new line style of the border
|
||||||
@param AColor Palette index for the color of the border line
|
@param AColor RGB value of the color of the border line
|
||||||
|
|
||||||
@see WriteBorderStyles
|
@see WriteBorderStyles
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
@ -6302,8 +6282,6 @@ begin
|
|||||||
FormatSettings.ShortDateFormat := MakeShortDateFormat(FormatSettings.ShortDateFormat);
|
FormatSettings.ShortDateFormat := MakeShortDateFormat(FormatSettings.ShortDateFormat);
|
||||||
FormatSettings.LongDateFormat := MakeLongDateFormat(FormatSettings.ShortDateFormat);
|
FormatSettings.LongDateFormat := MakeLongDateFormat(FormatSettings.ShortDateFormat);
|
||||||
|
|
||||||
UseDefaultPalette;
|
|
||||||
|
|
||||||
FFontList := TFPList.Create;
|
FFontList := TFPList.Create;
|
||||||
SetDefaultFont(DEFAULT_FONTNAME, DEFAULT_FONTSIZE);
|
SetDefaultFont(DEFAULT_FONTNAME, DEFAULT_FONTSIZE);
|
||||||
InitFonts;
|
InitFonts;
|
||||||
@ -7249,7 +7227,7 @@ end;
|
|||||||
@param AFontName Name of the font (like 'Arial')
|
@param AFontName Name of the font (like 'Arial')
|
||||||
@param ASize Size of the font in points
|
@param ASize Size of the font in points
|
||||||
@param AStyle Style of the font, a combination of TsFontStyle elements
|
@param AStyle Style of the font, a combination of TsFontStyle elements
|
||||||
@param AColor Color of the font, given by its index into the workbook's palette.
|
@param AColor RGB valoe of the font color
|
||||||
@return Index of the font in the workbook's font list
|
@return Index of the font in the workbook's font list
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function TsWorkbook.AddFont(const AFontName: String; ASize: Single;
|
function TsWorkbook.AddFont(const AFontName: String; ASize: Single;
|
||||||
@ -7301,11 +7279,13 @@ end;
|
|||||||
@param AFontName Name of the font (like 'Arial')
|
@param AFontName Name of the font (like 'Arial')
|
||||||
@param ASize Size of the font in points
|
@param ASize Size of the font in points
|
||||||
@param AStyle Style of the font, a combination of TsFontStyle elements
|
@param AStyle Style of the font, a combination of TsFontStyle elements
|
||||||
@param AColor Color of the font, given by its index into the workbook's palette.
|
@param AColor RGB value of the font color
|
||||||
@return Index of the font in the font list, or -1 if not found.
|
@return Index of the font in the font list, or -1 if not found.
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function TsWorkbook.FindFont(const AFontName: String; ASize: Single;
|
function TsWorkbook.FindFont(const AFontName: String; ASize: Single;
|
||||||
AStyle: TsFontStyles; AColor: TsColor): Integer;
|
AStyle: TsFontStyles; AColor: TsColor): Integer;
|
||||||
|
const
|
||||||
|
EPS = 1e-3;
|
||||||
var
|
var
|
||||||
fnt: TsFont;
|
fnt: TsFont;
|
||||||
begin
|
begin
|
||||||
@ -7314,9 +7294,9 @@ begin
|
|||||||
fnt := TsFont(FFontList.Items[Result]);
|
fnt := TsFont(FFontList.Items[Result]);
|
||||||
if (fnt <> nil) and
|
if (fnt <> nil) and
|
||||||
SameText(AFontName, fnt.FontName) and
|
SameText(AFontName, fnt.FontName) and
|
||||||
(abs(ASize - fnt.Size) < 0.001) and // careful when comparing floating point numbers
|
SameValue(ASize, fnt.Size, EPS) and // careful when comparing floating point numbers
|
||||||
(AStyle = fnt.Style) and
|
(AStyle = fnt.Style) and
|
||||||
(AColor = fnt.Color) // Take care of limited palette size!
|
(AColor = fnt.Color)
|
||||||
then
|
then
|
||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
@ -7520,7 +7500,7 @@ function TsWorkbook.GetNumberFormatCount: Integer;
|
|||||||
begin
|
begin
|
||||||
Result := FNumFormatList.Count;
|
Result := FNumFormatList.Count;
|
||||||
end;
|
end;
|
||||||
|
(*
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Adds a color to the palette and returns its palette index, but only if the
|
Adds a color to the palette and returns its palette index, but only if the
|
||||||
color does not already exist - in this case, it returns the index of the
|
color does not already exist - in this case, it returns the index of the
|
||||||
@ -7602,7 +7582,7 @@ begin
|
|||||||
|
|
||||||
if Assigned(FOnChangePalette) then FOnChangePalette(self);
|
if Assigned(FOnChangePalette) then FOnChangePalette(self);
|
||||||
end;
|
end;
|
||||||
|
*)
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Adds a (simple) error message to an internal list
|
Adds a (simple) error message to an internal list
|
||||||
|
|
||||||
@ -7639,47 +7619,7 @@ function TsWorkbook.GetErrorMsg: String;
|
|||||||
begin
|
begin
|
||||||
Result := FLog.Text;
|
Result := FLog.Text;
|
||||||
end;
|
end;
|
||||||
|
(*
|
||||||
{@@ ----------------------------------------------------------------------------
|
|
||||||
Finds the palette color index which points to a color that is closest to a
|
|
||||||
given color. "Close" means here smallest length of the rgb-difference vector.
|
|
||||||
|
|
||||||
@param AColorValue Rgb color value to be considered
|
|
||||||
@param AMaxPaletteCount Number of palette entries considered. Example:
|
|
||||||
BIFF5/BIFF8 can write only 64 colors, i.e
|
|
||||||
AMaxPaletteCount = 64
|
|
||||||
@return Palette index of the color closest to AColorValue
|
|
||||||
-------------------------------------------------------------------------------}
|
|
||||||
function TsWorkbook.FindClosestColor(AColorValue: TsColorValue;
|
|
||||||
AMaxPaletteCount: Integer = -1): TsColor;
|
|
||||||
type
|
|
||||||
TRGBA = record r,g,b, a: Byte end;
|
|
||||||
var
|
|
||||||
rgb: TRGBA;
|
|
||||||
rgb0: TRGBA absolute AColorValue;
|
|
||||||
dist: Double;
|
|
||||||
minDist: Double;
|
|
||||||
i: Integer;
|
|
||||||
n: Integer;
|
|
||||||
begin
|
|
||||||
Result := scNotDefined;
|
|
||||||
minDist := 1E108;
|
|
||||||
if AMaxPaletteCount = -1 then
|
|
||||||
n := Length(FPalette)
|
|
||||||
else
|
|
||||||
n := Min(Length(FPalette), AMaxPaletteCount);
|
|
||||||
for i:=0 to n-1 do
|
|
||||||
begin
|
|
||||||
rgb := TRGBA(GetPaletteColor(i));
|
|
||||||
dist := sqr(rgb.r - rgb0.r) + sqr(rgb.g - rgb0.g) + sqr(rgb.b - rgb0.b);
|
|
||||||
if dist < minDist then
|
|
||||||
begin
|
|
||||||
Result := i;
|
|
||||||
minDist := dist;
|
|
||||||
end;
|
|
||||||
end;
|
|
||||||
end;
|
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Converts a fpspreadsheet color into into a string RRGGBB.
|
Converts a fpspreadsheet color into into a string RRGGBB.
|
||||||
Note that colors are written to xls files as ABGR (where A is 0).
|
Note that colors are written to xls files as ABGR (where A is 0).
|
||||||
@ -7757,26 +7697,6 @@ begin
|
|||||||
AName := Format('%.2x%.2x%.2x', [R, G, B]);
|
AName := Format('%.2x%.2x%.2x', [R, G, B]);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
|
||||||
Reads the rgb color for the given index from the current palette. Can be
|
|
||||||
type-cast to TColor for usage in GUI applications.
|
|
||||||
|
|
||||||
@param AColorIndex Index of the color considered
|
|
||||||
@return A number containing the rgb components in little-endian notation.
|
|
||||||
-------------------------------------------------------------------------------}
|
|
||||||
function TsWorkbook.GetPaletteColor(AColorIndex: TsColor): TsColorValue;
|
|
||||||
begin
|
|
||||||
if (AColorIndex >= 0) and (AColorIndex < GetPaletteSize) then
|
|
||||||
begin
|
|
||||||
if ((FPalette = nil) or (Length(FPalette) = 0)) then
|
|
||||||
Result := DEFAULT_PALETTE[AColorIndex]
|
|
||||||
else
|
|
||||||
Result := FPalette[AColorIndex];
|
|
||||||
end
|
|
||||||
else
|
|
||||||
Result := $000000; // "black" as default
|
|
||||||
end;
|
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Converts the palette color of the given index to a string that can be used
|
Converts the palette color of the given index to a string that can be used
|
||||||
in HTML code. For ODS.
|
in HTML code. For ODS.
|
||||||
@ -7790,36 +7710,6 @@ begin
|
|||||||
Result := ColorToHTMLColorStr(GetPaletteColor(AColorIndex));
|
Result := ColorToHTMLColorStr(GetPaletteColor(AColorIndex));
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
|
||||||
Replaces a color value of the current palette by a new value. The color must
|
|
||||||
be given as ABGR (little-endian), with A=0).
|
|
||||||
|
|
||||||
@param AColorIndex Palette index of the color to be replaced
|
|
||||||
@param AColorValue Number containing the rgb components of the new color
|
|
||||||
-------------------------------------------------------------------------------}
|
|
||||||
procedure TsWorkbook.SetPaletteColor(AColorIndex: TsColor;
|
|
||||||
AColorValue: TsColorValue);
|
|
||||||
begin
|
|
||||||
if (AColorIndex >= 0) and (AColorIndex < GetPaletteSize) then
|
|
||||||
begin
|
|
||||||
if ((FPalette = nil) or (Length(FPalette) = 0)) then
|
|
||||||
DEFAULT_PALETTE[AColorIndex] := AColorValue
|
|
||||||
else
|
|
||||||
FPalette[AColorIndex] := AColorValue;
|
|
||||||
end;
|
|
||||||
end;
|
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
|
||||||
Returns the count of palette colors
|
|
||||||
-------------------------------------------------------------------------------}
|
|
||||||
function TsWorkbook.GetPaletteSize: Integer;
|
|
||||||
begin
|
|
||||||
if (FPalette = nil) or (Length(FPalette) = 0) then
|
|
||||||
Result := High(DEFAULT_PALETTE) + 1
|
|
||||||
else
|
|
||||||
Result := Length(FPalette);
|
|
||||||
end;
|
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Instructs the workbook to take colors from the default palette. Is called
|
Instructs the workbook to take colors from the default palette. Is called
|
||||||
from ODS reader because ODS does not have a palette. Without a palette the
|
from ODS reader because ODS does not have a palette. Without a palette the
|
||||||
@ -7919,7 +7809,7 @@ begin
|
|||||||
end;
|
end;
|
||||||
Result := false;
|
Result := false;
|
||||||
end;
|
end;
|
||||||
|
*)
|
||||||
|
|
||||||
{*******************************************************************************
|
{*******************************************************************************
|
||||||
* TsBasicSpreadReaderWriter *
|
* TsBasicSpreadReaderWriter *
|
||||||
@ -7963,7 +7853,6 @@ end;
|
|||||||
procedure TsBasicSpreadWriter.CheckLimitations;
|
procedure TsBasicSpreadWriter.CheckLimitations;
|
||||||
var
|
var
|
||||||
lastCol, lastRow: Cardinal;
|
lastCol, lastRow: Cardinal;
|
||||||
i, n: Integer;
|
|
||||||
begin
|
begin
|
||||||
Workbook.GetLastRowColIndex(lastRow, lastCol);
|
Workbook.GetLastRowColIndex(lastRow, lastCol);
|
||||||
|
|
||||||
@ -7974,22 +7863,10 @@ begin
|
|||||||
// Check column count
|
// Check column count
|
||||||
if lastCol >= FLimitations.MaxColCount then
|
if lastCol >= FLimitations.MaxColCount then
|
||||||
Workbook.AddErrorMsg(rsMaxColsExceeded, [lastCol+1, FLimitations.MaxColCount]);
|
Workbook.AddErrorMsg(rsMaxColsExceeded, [lastCol+1, FLimitations.MaxColCount]);
|
||||||
|
|
||||||
// Check color count.
|
|
||||||
n := Workbook.GetPaletteSize;
|
|
||||||
if n > FLimitations.MaxPaletteSize then
|
|
||||||
for i:= FLimitations.MaxPaletteSize to n-1 do
|
|
||||||
if Workbook.UsesColor(i) then
|
|
||||||
begin
|
|
||||||
Workbook.AddErrorMsg(rsTooManyPaletteColors, [n, FLimitations.MaxPaletteSize]);
|
|
||||||
break;
|
|
||||||
end;
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
|
||||||
initialization
|
initialization
|
||||||
// Default palette
|
|
||||||
MakeLEPalette(@DEFAULT_PALETTE, Length(DEFAULT_PALETTE));
|
|
||||||
|
|
||||||
finalization
|
finalization
|
||||||
SetLength(GsSpreadFormats, 0);
|
SetLength(GsSpreadFormats, 0);
|
||||||
|
@ -28,7 +28,7 @@ interface
|
|||||||
uses
|
uses
|
||||||
Classes, Graphics, SysUtils, Controls, StdCtrls, ComCtrls, ValEdit, ActnList,
|
Classes, Graphics, SysUtils, Controls, StdCtrls, ComCtrls, ValEdit, ActnList,
|
||||||
LResources,
|
LResources,
|
||||||
fpstypes, fpspreadsheet, {%H-}fpsAllFormats;
|
fpstypes, fpspalette, fpspreadsheet, {%H-}fpsAllFormats;
|
||||||
|
|
||||||
type
|
type
|
||||||
{@@ Event handler procedure for displaying a message if an error or
|
{@@ Event handler procedure for displaying a message if an error or
|
||||||
@ -42,7 +42,7 @@ type
|
|||||||
TsNotificationItem = (lniWorkbook,
|
TsNotificationItem = (lniWorkbook,
|
||||||
lniWorksheet, lniWorksheetAdd, lniWorksheetRemoving, lniWorksheetRemove,
|
lniWorksheet, lniWorksheetAdd, lniWorksheetRemoving, lniWorksheetRemove,
|
||||||
lniWorksheetRename,
|
lniWorksheetRename,
|
||||||
lniCell, lniSelection, lniAbortSelection, lniRow, lniPalette);
|
lniCell, lniSelection, lniAbortSelection, lniRow); //, lniPalette);
|
||||||
{@@ This set accompanies the notification between WorkbookSource and visual
|
{@@ This set accompanies the notification between WorkbookSource and visual
|
||||||
controls and describes which items have changed in the spreadsheet. }
|
controls and describes which items have changed in the spreadsheet. }
|
||||||
TsNotificationItems = set of TsNotificationItem;
|
TsNotificationItems = set of TsNotificationItem;
|
||||||
@ -78,7 +78,7 @@ type
|
|||||||
AFormat: TsSpreadsheetFormat; AWorksheetIndex: Integer = 0);
|
AFormat: TsSpreadsheetFormat; AWorksheetIndex: Integer = 0);
|
||||||
procedure SetFileName(const AFileName: TFileName);
|
procedure SetFileName(const AFileName: TFileName);
|
||||||
procedure SetOptions(AValue: TsWorkbookOptions);
|
procedure SetOptions(AValue: TsWorkbookOptions);
|
||||||
procedure WorkbookChangedPaletteHandler(Sender: TObject);
|
// procedure WorkbookChangedPaletteHandler(Sender: TObject);
|
||||||
procedure WorkbookOpenedHandler(Sender: TObject);
|
procedure WorkbookOpenedHandler(Sender: TObject);
|
||||||
procedure WorksheetAddedHandler(Sender: TObject; ASheet: TsWorksheet);
|
procedure WorksheetAddedHandler(Sender: TObject; ASheet: TsWorksheet);
|
||||||
procedure WorksheetChangedHandler(Sender: TObject; ASheet: TsWorksheet);
|
procedure WorksheetChangedHandler(Sender: TObject; ASheet: TsWorksheet);
|
||||||
@ -436,6 +436,9 @@ type
|
|||||||
property FixedCols default 0;
|
property FixedCols default 0;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
var
|
||||||
|
ComboColors: TsPalette = nil;
|
||||||
|
|
||||||
procedure Register;
|
procedure Register;
|
||||||
|
|
||||||
|
|
||||||
@ -445,7 +448,6 @@ uses
|
|||||||
Types, Math, TypInfo, LCLType, LCLProc, Dialogs, Forms,
|
Types, Math, TypInfo, LCLType, LCLProc, Dialogs, Forms,
|
||||||
fpsStrings, fpsUtils;
|
fpsStrings, fpsUtils;
|
||||||
|
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Registers the spreadsheet components in the Lazarus component palette,
|
Registers the spreadsheet components in the Lazarus component palette,
|
||||||
page "FPSpreadsheet".
|
page "FPSpreadsheet".
|
||||||
@ -797,7 +799,7 @@ begin
|
|||||||
FWorkbook.OnRemovingWorksheet := @WorksheetRemovingHandler;
|
FWorkbook.OnRemovingWorksheet := @WorksheetRemovingHandler;
|
||||||
FWorkbook.OnRenameWorksheet := @WorksheetRenamedHandler;
|
FWorkbook.OnRenameWorksheet := @WorksheetRenamedHandler;
|
||||||
FWorkbook.OnSelectWorksheet := @WorksheetSelectedHandler;
|
FWorkbook.OnSelectWorksheet := @WorksheetSelectedHandler;
|
||||||
FWorkbook.OnChangePalette := @WorkbookChangedPaletteHandler;
|
// FWorkbook.OnChangePalette := @WorkbookChangedPaletteHandler;
|
||||||
// Pass options to workbook
|
// Pass options to workbook
|
||||||
SetOptions(FOptions);
|
SetOptions(FOptions);
|
||||||
end;
|
end;
|
||||||
@ -1240,7 +1242,7 @@ begin
|
|||||||
EnableControls;
|
EnableControls;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
(*
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Event handler called whenever the palette of the workbook is changed.
|
Event handler called whenever the palette of the workbook is changed.
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
@ -1248,7 +1250,7 @@ procedure TsWorkbookSource.WorkbookChangedPaletteHandler(Sender: TObject);
|
|||||||
begin
|
begin
|
||||||
Unused(Sender);
|
Unused(Sender);
|
||||||
NotifyListeners([lniPalette]);
|
NotifyListeners([lniPalette]);
|
||||||
end;
|
end; *)
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Event handler called whenever a new workbook is opened.
|
Event handler called whenever a new workbook is opened.
|
||||||
@ -1970,7 +1972,7 @@ begin
|
|||||||
Brush.Style := bsClear;
|
Brush.Style := bsClear;
|
||||||
end else
|
end else
|
||||||
begin
|
begin
|
||||||
Brush.Color := Workbook.GetPaletteColor(clr);
|
Brush.Color := clr and $00FFFFFF;
|
||||||
Brush.Style := bsSolid;
|
Brush.Style := bsSolid;
|
||||||
end;
|
end;
|
||||||
Pen.Color := clBlack;
|
Pen.Color := clBlack;
|
||||||
@ -2010,6 +2012,7 @@ procedure TsCellCombobox.ExtractFromCell(ACell: PCell);
|
|||||||
var
|
var
|
||||||
fnt: TsFont;
|
fnt: TsFont;
|
||||||
clr: TsColor;
|
clr: TsColor;
|
||||||
|
idx: Integer;
|
||||||
begin
|
begin
|
||||||
case FFormatItem of
|
case FFormatItem of
|
||||||
cfiFontName:
|
cfiFontName:
|
||||||
@ -2091,7 +2094,7 @@ var
|
|||||||
begin
|
begin
|
||||||
Unused(AData);
|
Unused(AData);
|
||||||
if (Worksheet = nil) or
|
if (Worksheet = nil) or
|
||||||
([lniCell, lniSelection, lniPalette]*AChangedItems = [])
|
([lniCell, lniSelection]*AChangedItems = [])
|
||||||
then
|
then
|
||||||
exit;
|
exit;
|
||||||
|
|
||||||
@ -2100,11 +2103,9 @@ begin
|
|||||||
(lniSelection in AChangedItems)
|
(lniSelection in AChangedItems)
|
||||||
then
|
then
|
||||||
ExtractFromCell(activeCell);
|
ExtractFromCell(activeCell);
|
||||||
|
{
|
||||||
if (FFormatItem in [cfiFontColor, cfiBorderColor, cfiBackgroundColor]) and
|
if (FFormatItem in [cfiFontColor, cfiBorderColor, cfiBackgroundColor]) then
|
||||||
(lniPalette in AChangedItems)
|
Populate; }
|
||||||
then
|
|
||||||
Populate;
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
@ -2136,6 +2137,7 @@ end;
|
|||||||
procedure TsCellCombobox.Populate;
|
procedure TsCellCombobox.Populate;
|
||||||
var
|
var
|
||||||
i: Integer;
|
i: Integer;
|
||||||
|
clr: TsColor;
|
||||||
begin
|
begin
|
||||||
if Workbook = nil then
|
if Workbook = nil then
|
||||||
exit;
|
exit;
|
||||||
@ -2145,18 +2147,19 @@ begin
|
|||||||
Items.Assign(Screen.Fonts);
|
Items.Assign(Screen.Fonts);
|
||||||
cfiFontSize:
|
cfiFontSize:
|
||||||
Items.CommaText := '8,9,10,11,12,13,14,16,18,20,22,24,26,28,32,36,48,72';
|
Items.CommaText := '8,9,10,11,12,13,14,16,18,20,22,24,26,28,32,36,48,72';
|
||||||
cfiFontColor:
|
cfiBackgroundColor,
|
||||||
for i:=0 to Workbook.GetPaletteSize-1 do
|
cfiFontColor,
|
||||||
Items.AddObject(Workbook.GetColorName(i), TObject(PtrInt(i)));
|
|
||||||
cfiBackgroundColor:
|
|
||||||
begin
|
|
||||||
Items.AddObject('(none)', TObject(scTransparent));
|
|
||||||
for i:=0 to Workbook.GetPaletteSize-1 do
|
|
||||||
Items.AddObject(Workbook.GetColorName(i), TObject(PtrInt(i)));
|
|
||||||
end;
|
|
||||||
cfiBorderColor:
|
cfiBorderColor:
|
||||||
for i:=0 to Workbook.GetPaletteSize-1 do
|
begin
|
||||||
Items.AddObject(Workbook.GetColorName(i), TObject(PtrInt(i)));
|
Items.Clear;
|
||||||
|
if FFormatItem = cfiBackgroundColor then
|
||||||
|
Items.AddObject('(none)', TObject(scTransparent));
|
||||||
|
for i:=0 to ComboColors.Count-1 do
|
||||||
|
begin
|
||||||
|
clr := ComboColors[i];
|
||||||
|
Items.AddObject(GetColorName(clr), TObject(PtrInt(clr)));
|
||||||
|
end;
|
||||||
|
end;
|
||||||
else
|
else
|
||||||
raise Exception.Create('[TsCellCombobox.Populate] Unknown cell format item.');
|
raise Exception.Create('[TsCellCombobox.Populate] Unknown cell format item.');
|
||||||
end;
|
end;
|
||||||
@ -2673,8 +2676,8 @@ begin
|
|||||||
else
|
else
|
||||||
AStrings.Add(Format('BorderStyles[%s]=%s, %s', [
|
AStrings.Add(Format('BorderStyles[%s]=%s, %s', [
|
||||||
GetEnumName(TypeInfo(TsCellBorder), ord(cb)),
|
GetEnumName(TypeInfo(TsCellBorder), ord(cb)),
|
||||||
GetEnumName(TypeInfo(TsLineStyle), ord(fmt.BorderStyles[cbEast].LineStyle)),
|
GetEnumName(TypeInfo(TsLineStyle), ord(fmt.BorderStyles[cb].LineStyle)),
|
||||||
Workbook.GetColorName(fmt.BorderStyles[cbEast].Color)]));
|
GetColorName(fmt.BorderStyles[cb].Color)]));
|
||||||
|
|
||||||
if (ACell = nil) or not (uffBackground in fmt.UsedformattingFields) then
|
if (ACell = nil) or not (uffBackground in fmt.UsedformattingFields) then
|
||||||
begin
|
begin
|
||||||
@ -2685,10 +2688,10 @@ begin
|
|||||||
begin
|
begin
|
||||||
AStrings.Add(Format('Style=%s', [
|
AStrings.Add(Format('Style=%s', [
|
||||||
GetEnumName(TypeInfo(TsFillStyle), ord(fmt.Background.Style))]));
|
GetEnumName(TypeInfo(TsFillStyle), ord(fmt.Background.Style))]));
|
||||||
AStrings.Add(Format('PatternColor=%d (%s)', [
|
AStrings.Add(Format('PatternColor=$%.8x (%s)', [
|
||||||
fmt.Background.FgColor, Workbook.GetColorName(fmt.Background.FgColor)]));
|
fmt.Background.FgColor, GetColorName(fmt.Background.FgColor)]));
|
||||||
AStrings.Add(Format('BackgroundColor=%d (%s)', [
|
AStrings.Add(Format('BackgroundColor=$%.8x (%s)', [
|
||||||
fmt.Background.BgColor, Workbook.GetColorName(fmt.Background.BgColor)]));
|
fmt.Background.BgColor, GetColorName(fmt.Background.BgColor)]));
|
||||||
end;
|
end;
|
||||||
|
|
||||||
if (ACell = nil) or not (uffNumberFormat in fmt.UsedFormattingFields) then
|
if (ACell = nil) or not (uffNumberFormat in fmt.UsedFormattingFields) then
|
||||||
@ -2949,12 +2952,16 @@ initialization
|
|||||||
|
|
||||||
CellClipboard := TsCellList.Create;
|
CellClipboard := TsCellList.Create;
|
||||||
|
|
||||||
|
ComboColors := TsPalette.Create;
|
||||||
|
ComboColors.AddExcelColors;
|
||||||
|
|
||||||
RegisterPropertyToSkip(TsSpreadsheetInspector, 'RowHeights', 'For compatibility with older Laz versions.', '');
|
RegisterPropertyToSkip(TsSpreadsheetInspector, 'RowHeights', 'For compatibility with older Laz versions.', '');
|
||||||
RegisterPropertyToSkip(TsSpreadsheetInspector, 'ColWidths', 'For compatibility with older Laz versions.', '');
|
RegisterPropertyToSkip(TsSpreadsheetInspector, 'ColWidths', 'For compatibility with older Laz versions.', '');
|
||||||
|
|
||||||
|
|
||||||
finalization
|
finalization
|
||||||
CellClipboard.Free;
|
CellClipboard.Free;
|
||||||
|
if ComboColors <> nil then ComboColors.Free;
|
||||||
|
|
||||||
|
|
||||||
end.
|
end.
|
||||||
|
@ -247,7 +247,6 @@ type
|
|||||||
{ Utilities related to Workbooks }
|
{ Utilities related to Workbooks }
|
||||||
procedure Convert_sFont_to_Font(sFont: TsFont; AFont: TFont);
|
procedure Convert_sFont_to_Font(sFont: TsFont; AFont: TFont);
|
||||||
procedure Convert_Font_to_sFont(AFont: TFont; sFont: TsFont);
|
procedure Convert_Font_to_sFont(AFont: TFont; sFont: TsFont);
|
||||||
function FindNearestPaletteIndex(AColor: TColor): TsColor;
|
|
||||||
|
|
||||||
{ Interfacing with WorkbookSource}
|
{ Interfacing with WorkbookSource}
|
||||||
procedure ListenerNotification(AChangedItems: TsNotificationItems;
|
procedure ListenerNotification(AChangedItems: TsNotificationItems;
|
||||||
@ -1392,15 +1391,15 @@ begin
|
|||||||
fsSolidFill:
|
fsSolidFill:
|
||||||
begin
|
begin
|
||||||
Canvas.Brush.Style := bsSolid;
|
Canvas.Brush.Style := bsSolid;
|
||||||
Canvas.Brush.Color := Workbook.GetPaletteColor(fmt^.Background.FgColor);
|
Canvas.Brush.Color := fmt^.Background.FgColor and $00FFFFFF;
|
||||||
end;
|
end;
|
||||||
else
|
else
|
||||||
if fmt^.Background.BgColor = scTransparent
|
if fmt^.Background.BgColor = scTransparent
|
||||||
then bgcolor := Color
|
then bgcolor := Color
|
||||||
else bgcolor := Workbook.GetPaletteColor(fmt^.Background.BgColor);
|
else bgcolor := fmt^.Background.BgColor and $00FFFFFF;
|
||||||
if fmt^.Background.FgColor = scTransparent
|
if fmt^.Background.FgColor = scTransparent
|
||||||
then fgcolor := Color
|
then fgcolor := Color
|
||||||
else fgcolor := Workbook.GetPaletteColor(fmt^.Background.FgColor);
|
else fgcolor := fmt^.Background.FgColor and $00FFFFFF;
|
||||||
CreateFillPattern(FillPatternBitmap, fmt^.Background.Style, fgColor, bgColor);
|
CreateFillPattern(FillPatternBitmap, fmt^.Background.Style, fgColor, bgColor);
|
||||||
Canvas.Brush.Style := bsImage;
|
Canvas.Brush.Style := bsImage;
|
||||||
Canvas.Brush.Bitmap := FillPatternBitmap;
|
Canvas.Brush.Bitmap := FillPatternBitmap;
|
||||||
@ -1424,7 +1423,7 @@ begin
|
|||||||
begin
|
begin
|
||||||
Canvas.Font.Name := fnt.FontName;
|
Canvas.Font.Name := fnt.FontName;
|
||||||
Canvas.Font.Size := round(fnt.Size);
|
Canvas.Font.Size := round(fnt.Size);
|
||||||
Canvas.Font.Color := Workbook.GetPaletteColor(fnt.Color);
|
Canvas.Font.Color := fnt.Color and $00FFFFFF;
|
||||||
style := [];
|
style := [];
|
||||||
if fssBold in fnt.Style then Include(style, fsBold);
|
if fssBold in fnt.Style then Include(style, fsBold);
|
||||||
if fssItalic in fnt.Style then Include(style, fsItalic);
|
if fssItalic in fnt.Style then Include(style, fsItalic);
|
||||||
@ -1444,7 +1443,7 @@ begin
|
|||||||
if (nfkHasColor in numFmt.Sections[sidx].Kind) then
|
if (nfkHasColor in numFmt.Sections[sidx].Kind) then
|
||||||
begin
|
begin
|
||||||
clr := numFmt.Sections[sidx].Color;
|
clr := numFmt.Sections[sidx].Color;
|
||||||
Canvas.Font.Color := Workbook.GetPaletteColor(clr);
|
Canvas.Font.Color := clr and $00FFFFFF;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
// Wordwrap, text alignment and text rotation are handled by "DrawTextInCell".
|
// Wordwrap, text alignment and text rotation are handled by "DrawTextInCell".
|
||||||
@ -1569,7 +1568,7 @@ const
|
|||||||
begin
|
begin
|
||||||
Canvas.Pen.Style := PEN_STYLES[ABorderStyle.LineStyle];
|
Canvas.Pen.Style := PEN_STYLES[ABorderStyle.LineStyle];
|
||||||
Canvas.Pen.Width := PEN_WIDTHS[ABorderStyle.LineStyle];
|
Canvas.Pen.Width := PEN_WIDTHS[ABorderStyle.LineStyle];
|
||||||
Canvas.Pen.Color := Workbook.GetPaletteColor(ABorderStyle.Color);
|
Canvas.Pen.Color := ABorderStyle.Color and $00FFFFFF;
|
||||||
Canvas.Pen.EndCap := pecSquare;
|
Canvas.Pen.EndCap := pecSquare;
|
||||||
width3 := (ABorderStyle.LineStyle in [lsThick, lsDouble]);
|
width3 := (ABorderStyle.LineStyle in [lsThick, lsDouble]);
|
||||||
|
|
||||||
@ -2282,6 +2281,7 @@ begin
|
|||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
(*
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
The "colors" used by the spreadsheet are indexes into the workbook's color
|
The "colors" used by the spreadsheet are indexes into the workbook's color
|
||||||
palette. If the user wants to set a color to a particular RGB value this is
|
palette. If the user wants to set a color to a particular RGB value this is
|
||||||
@ -2294,7 +2294,7 @@ function TsCustomWorksheetGrid.FindNearestPaletteIndex(AColor: TColor): TsColor;
|
|||||||
begin
|
begin
|
||||||
Result := fpsVisualUtils.FindNearestPaletteIndex(Workbook, AColor);
|
Result := fpsVisualUtils.FindNearestPaletteIndex(Workbook, AColor);
|
||||||
end;
|
end;
|
||||||
|
*)
|
||||||
(*
|
(*
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Notification by the workbook link that a cell has been modified. --> Repaint.
|
Notification by the workbook link that a cell has been modified. --> Repaint.
|
||||||
|
@ -95,7 +95,7 @@ type
|
|||||||
|
|
||||||
procedure AddBuiltinNumFormats; virtual;
|
procedure AddBuiltinNumFormats; virtual;
|
||||||
function FindNumFormatInList(ANumFormatStr: String): Integer;
|
function FindNumFormatInList(ANumFormatStr: String): Integer;
|
||||||
function FixColor(AColor: TsColor): TsColor; virtual;
|
// function FixColor(AColor: TsColor): TsColor; virtual;
|
||||||
procedure FixFormat(ACell: PCell); virtual;
|
procedure FixFormat(ACell: PCell); virtual;
|
||||||
procedure GetSheetDimensions(AWorksheet: TsWorksheet;
|
procedure GetSheetDimensions(AWorksheet: TsWorksheet;
|
||||||
out AFirstRow, ALastRow, AFirstCol, ALastCol: Cardinal); virtual;
|
out AFirstRow, ALastRow, AFirstCol, ALastCol: Cardinal); virtual;
|
||||||
@ -404,7 +404,7 @@ begin
|
|||||||
exit;
|
exit;
|
||||||
Result := -1;
|
Result := -1;
|
||||||
end;
|
end;
|
||||||
|
(*
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
If a color index is greater then the maximum palette color count this
|
If a color index is greater then the maximum palette color count this
|
||||||
color is replaced by the closest palette color.
|
color is replaced by the closest palette color.
|
||||||
@ -420,7 +420,7 @@ function TsCustomSpreadWriter.FixColor(AColor: TsColor): TsColor;
|
|||||||
begin
|
begin
|
||||||
Result := AColor;
|
Result := AColor;
|
||||||
end;
|
end;
|
||||||
|
*)
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
If formatting features of a cell are not supported by the destination file
|
If formatting features of a cell are not supported by the destination file
|
||||||
format of the writer, here is the place to apply replacements.
|
format of the writer, here is the place to apply replacements.
|
||||||
|
@ -67,6 +67,66 @@ resourcestring
|
|||||||
|
|
||||||
rsCannotSortMerged = 'The cell range cannot be sorted because it contains merged cells.';
|
rsCannotSortMerged = 'The cell range cannot be sorted because it contains merged cells.';
|
||||||
|
|
||||||
|
// Colors
|
||||||
|
rsAqua = 'aqua';
|
||||||
|
rsBeige = 'beige';
|
||||||
|
rsBlack = 'black';
|
||||||
|
rsBlue = 'blue';
|
||||||
|
rsBlueGray = 'blue gray';
|
||||||
|
rsBrown = 'brown';
|
||||||
|
rsCoral = 'coral';
|
||||||
|
rsCyan = 'cyan';
|
||||||
|
rsDarkBlue = 'dark blue';
|
||||||
|
rsDarkGreen = 'dark green';
|
||||||
|
rsDarkPurple = 'dark purple';
|
||||||
|
rsDarkRed = 'dark red';
|
||||||
|
rsDarkTeal = 'dark teal';
|
||||||
|
rsGold = 'gold';
|
||||||
|
rsGray = 'gray';
|
||||||
|
rsGray10pct = '10% gray';
|
||||||
|
rsGray20pct = '20% gray';
|
||||||
|
rsGray25pct = '25% gray';
|
||||||
|
rsGray40pct = '40% gray';
|
||||||
|
rsGray50pct = '50% gray';
|
||||||
|
rsGray80pct = '80% gray';
|
||||||
|
rsGreen = 'green';
|
||||||
|
rsIceBlue = 'ice blue';
|
||||||
|
rsIndigo = 'indigo';
|
||||||
|
rsIvory = 'ivory';
|
||||||
|
rsLavander = 'lavander';
|
||||||
|
rsLightBlue = 'light blue';
|
||||||
|
rsLightGreen = 'light green';
|
||||||
|
rsLightOrange = 'light orange';
|
||||||
|
rsLightTurquoise = 'light turquoise';
|
||||||
|
rsLightYellow = 'light yellow';
|
||||||
|
rsLime = 'lime';
|
||||||
|
rsMagenta = 'magenta';
|
||||||
|
rsNavy = 'navy';
|
||||||
|
rsOceanBlue = 'ocean blue';
|
||||||
|
rsOlive = 'olive';
|
||||||
|
rsOliveGreen = 'olive green';
|
||||||
|
rsOrange = 'orange';
|
||||||
|
rsPaleBlue = 'pale blue';
|
||||||
|
rsPeriwinkle = 'periwinkle';
|
||||||
|
rsPink = 'pink';
|
||||||
|
rsPlum = 'plum';
|
||||||
|
rsPurple = 'purple';
|
||||||
|
rsRed = 'red';
|
||||||
|
rsRose = 'rose';
|
||||||
|
rsSeaGreen = 'sea green';
|
||||||
|
rsSilver = 'silver';
|
||||||
|
rsSkyBlue = 'sky blue';
|
||||||
|
rsTan = 'tan';
|
||||||
|
rsTeal = 'teal';
|
||||||
|
rsVeryDarkGreen = 'very dark green';
|
||||||
|
rsViolet = 'violet';
|
||||||
|
rsWheat = 'wheat';
|
||||||
|
rsWhite = 'white';
|
||||||
|
rsYellow = 'yellow';
|
||||||
|
|
||||||
|
rsNotDefined = 'not defined';
|
||||||
|
rsTransparent = 'transparent';
|
||||||
|
|
||||||
rsTRUE = 'TRUE'; // wp: Do we really want to translate these strings?
|
rsTRUE = 'TRUE'; // wp: Do we really want to translate these strings?
|
||||||
rsFALSE = 'FALSE';
|
rsFALSE = 'FALSE';
|
||||||
rsErrEmptyIntersection = '#NULL!';
|
rsErrEmptyIntersection = '#NULL!';
|
||||||
|
@ -264,92 +264,147 @@ type
|
|||||||
{@@ Indicates vertical text alignment in cells }
|
{@@ Indicates vertical text alignment in cells }
|
||||||
TsVertAlignment = (vaDefault, vaTop, vaCenter, vaBottom);
|
TsVertAlignment = (vaDefault, vaTop, vaCenter, vaBottom);
|
||||||
|
|
||||||
{@@
|
{@@ Colors in fpspreadsheet are given as rgb values in little-endian notation
|
||||||
Colors in fpspreadsheet are given as indices into a palette.
|
(i.e. "r" is the low-value byte). The highest-value byte, if not zero,
|
||||||
Use the workbook's GetPaletteColor to determine the color rgb value as
|
indicates special colors. }
|
||||||
little-endian (with "r" being the low-value byte, in agreement with TColor).
|
TsColor = DWord;
|
||||||
The data type for rgb values is TsColorValue. }
|
|
||||||
TsColor = Word;
|
|
||||||
|
|
||||||
{@@
|
|
||||||
These are some constants for color indices into the default palette.
|
|
||||||
Note, however, that if a different palette is used there may be more colors,
|
|
||||||
and the names of the color constants may no longer be correct.
|
|
||||||
}
|
|
||||||
const
|
const
|
||||||
{@@ Index of <b>black</b> color in the standard color palettes }
|
{@@ These are some important rgb color volues.
|
||||||
scBlack = $00;
|
}
|
||||||
{@@ Index of <b>white</b> color in the standard color palettes }
|
{@@ rgb value of <b>black</b> color, BIFF2 palette index 0, BIFF8 index 8}
|
||||||
scWhite = $01;
|
scBlack = $00000000;
|
||||||
{@@ Index of <b>red</b> color in the standard color palettes }
|
{@@ rgb value of <b>white</b> color, BIFF2 palette index 1, BIFF8 index 9 }
|
||||||
scRed = $02;
|
scWhite = $00FFFFFF;
|
||||||
{@@ Index of <b>green</b> color in the standard color palettes }
|
{@@ rgb value of <b>red</b> color, BIFF2 palette index 2, BIFF8 index 10 }
|
||||||
scGreen = $03;
|
scRed = $000000FF;
|
||||||
{@@ Index of <b>blue</b> color in the standard color palettes }
|
{@@ rgb value of <b>green</b> color, BIFF2 palette index 3, BIFF8 index 11 }
|
||||||
scBlue = $04;
|
scGreen = $0000FF00;
|
||||||
{@@ Index of <b>yellow</b> color in the standard color palettes }
|
{@@ rgb value of <b>blue</b> color, BIFF2 palette index 4, BIFF8 indexes 12 and 39}
|
||||||
scYellow = $05;
|
scBlue = $00FF0000;
|
||||||
{@@ Index of <b>magenta</b> color in the standard color palettes }
|
{@@ rgb value of <b>yellow</b> color, BIFF2 palette index 5, BIFF8 indexes 13 and 34}
|
||||||
scMagenta = $06;
|
scYellow = $0000FFFF;
|
||||||
{@@ Index of <b>cyan</b> color in the standard color palettes }
|
{@@ rgb value of <b>magenta</b> color, BIFF2 palette index 6, BIFF8 index 14 and 33}
|
||||||
scCyan = $07;
|
scMagenta = $00FF00FF;
|
||||||
{@@ Index of <b>dark red</b> color in the standard color palettes }
|
scPink = $00FE00FE;
|
||||||
scDarkRed = $08;
|
{@@ rgb value of <b>cyan</b> color, BIFF2 palette index 7, BIFF8 indexes 15}
|
||||||
{@@ Index of <b>dark green</b> color in the standard color palettes }
|
scCyan = $00FFFF00;
|
||||||
scDarkGreen = $09;
|
scTurquoise = scCyan;
|
||||||
{@@ Index of <b>dark blue</b> color in the standard color palettes }
|
{@@ rgb value of <b>dark red</b> color, BIFF8 indexes 16 and 35}
|
||||||
scDarkBlue = $0A;
|
scDarkRed = $00000080;
|
||||||
{@@ Index of <b>"navy"</b> color (dark blue) in the standard color palettes }
|
{@@ rgb value of <b>dark green</b> color, BIFF8 index 17 }
|
||||||
scNavy = $0A;
|
scDarkGreen = $00008000;
|
||||||
{@@ Index of <b>olive</b> color in the standard color palettes }
|
{@@ rgb value of <b>dark blue</b> color }
|
||||||
scOlive = $0B;
|
scDarkBlue = $008B0000;
|
||||||
{@@ Index of <b>purple</b> color in the standard color palettes }
|
{@@ rgb value of <b>"navy"</b> color, BIFF8 palette indexes 18 and 32 }
|
||||||
scPurple = $0C;
|
scNavy = $00800000;
|
||||||
{@@ Index of <b>teal</b> color in the standard color palettes }
|
{@@ rgb value of <b>olive</b> color }
|
||||||
scTeal = $0D;
|
scOlive = $00008080;
|
||||||
{@@ Index of <b>silver</b> color in the standard color palettes }
|
{@@ rgb value of <b>purple</b> color, BIFF8 palette indexes 20 and 36 }
|
||||||
scSilver = $0E;
|
scPurple = $00800080;
|
||||||
{@@ Index of <b>grey</b> color in the standard color palettes }
|
{@@ rgb value of <b>teal</b> color, BIFF8 palette index 21 and 38 }
|
||||||
scGrey = $0F;
|
scTeal = $00808000;
|
||||||
{@@ Index of <b>gray</b> color in the standard color palettes }
|
{@@ rgb value of <b>silver</b> color }
|
||||||
scGray = $0F; // redefine to allow different spelling
|
scSilver = $00C0C0C0;
|
||||||
{@@ Index of a <b>10% grey</b> color in the standard color palettes }
|
scGray25pct = scSilver;
|
||||||
scGrey10pct = $10;
|
{@@ rgb value of <b>grey</b> color }
|
||||||
{@@ Index of a <b>10% gray</b> color in the standard color palettes }
|
scGray = $00808080;
|
||||||
scGray10pct = $10;
|
{@@ rgb value of <b>gray</b> color }
|
||||||
{@@ Index of a <b>20% grey</b> color in the standard color palettes }
|
scGrey = scGray; // redefine to allow different spelling
|
||||||
scGrey20pct = $11;
|
scGray50pct = scGray;
|
||||||
{@@ Index of a <b>20% gray</b> color in the standard color palettes }
|
{@@ rgb value of a <b>10% grey</b> color }
|
||||||
scGray20pct = $11;
|
scGray10pct = $00E6E6E6;
|
||||||
{@@ Index of <b>orange</b> color in the standard color palettes }
|
{@@ rgb value of a <b>10% gray</b> color }
|
||||||
scOrange = $12;
|
scGrey10pct = scGray10pct;
|
||||||
{@@ Index of <b>dark brown</b> color in the standard color palettes }
|
{@@ rgb value of a <b>20% grey</b> color }
|
||||||
scDarkbrown = $13;
|
scGray20pct = $00CCCCCC;
|
||||||
{@@ Index of <b>brown</b> color in the standard color palettes }
|
{@@ rgb value of a <b>20% gray</b> color }
|
||||||
scBrown = $14;
|
scGrey20pct = scGray20pct;
|
||||||
{@@ Index of <b>beige</b> color in the standard color palettes }
|
{@@ rgb value of <b>periwinkle</b> color, BIFF8 palette index 24 }
|
||||||
scBeige = $15;
|
scPeriwinkle = $00FF9999;
|
||||||
{@@ Index of <b>"wheat"</b> color (yellow-orange) in the standard color palettes }
|
{@@ rgb value of <b>plum</b> color, BIFF8 palette indexes 25 and 61 }
|
||||||
scWheat = $16;
|
scPlum = $00663399;
|
||||||
|
{@@ rgb value of <b>ivory</b> color, BIFF8 palette index 26 }
|
||||||
|
scIvory = $00CCFFFF;
|
||||||
|
{@@ rgb value of <b>light turquoise</b> color, BIFF8 palette indexes 27 and 41 }
|
||||||
|
scLightTurquoise = $00FFFFCC;
|
||||||
|
{@@ rgb value of <b>dark purple</b> color, BIFF8 palette index 28 }
|
||||||
|
scDarkPurple = $00660066;
|
||||||
|
{@@ rgb value of <b>coral</b> color, BIFF8 palette index 29 }
|
||||||
|
scCoral = $008080FF;
|
||||||
|
{@@ rgb value of <b>ocean blue</b> color, BIFF8 palette index 30 }
|
||||||
|
scOceanBlue = $00CC6600;
|
||||||
|
{@@ rgb value of <b>ice blue</b> color, BIFF8 palette index 31 }
|
||||||
|
scIceBlue = $00FFCCCC;
|
||||||
|
{@@ rgb value of <b>sky blue </b>color, BIFF8 palette index 40 }
|
||||||
|
scSkyBlue = $00FFCC00;
|
||||||
|
{@@ rgb value of <b>light green</b> color, BIFF8 palette index 42 }
|
||||||
|
scLightGreen = $00CCFFCC;
|
||||||
|
{@@ rgb value of <b>light yellow</b> color, BIFF8 palette index 43 }
|
||||||
|
scLightYellow = $0099FFFF;
|
||||||
|
{@@ rgb value of <b>pale blue</b> color, BIFF8 palette index 44 }
|
||||||
|
scPaleBlue = $00FFCC99;
|
||||||
|
{@@ rgb value of <b>rose</b> color, BIFF8 palette index 45 }
|
||||||
|
scRose = $00CC99FF;
|
||||||
|
{@@ rgb value of <b>lavander</b> color, BIFF8 palette index 46 }
|
||||||
|
scLavander = $00FF99CC;
|
||||||
|
{@@ rgb value of <b>tan</b> color, BIFF8 palette index 47 }
|
||||||
|
scTan = $0099CCFF;
|
||||||
|
{@@ rgb value of <b>light blue</b> color, BIFF8 palette index 48 }
|
||||||
|
scLightBlue = $00FF6633;
|
||||||
|
{@@ rgb value of <b>aqua</b> color, BIFF8 palette index 49 }
|
||||||
|
scAqua = $00CCCC33;
|
||||||
|
{@@ rgb value of <b>lime</b> color, BIFF8 palette index 50 }
|
||||||
|
scLime = $0000CC99;
|
||||||
|
{@@ rgb value of <b>golden</b> color, BIFF8 palette index 51 }
|
||||||
|
scGold = $0000CCFF;
|
||||||
|
{@@ rgb value of <b>light orange</b> color, BIFF8 palette index 52 }
|
||||||
|
scLightOrange = $000099FF;
|
||||||
|
{@@ rgb value of <b>orange</b> color, BIFF8 palette index 53 }
|
||||||
|
scOrange = $000066FF;
|
||||||
|
{@@ rgb value of <b>blue gray</b>, BIFF8 palette index 54 }
|
||||||
|
scBlueGray = $00996666;
|
||||||
|
scBlueGrey = scBlueGray;
|
||||||
|
{@@ rgb value of <b>gray 40%</b>, BIFF8 palette index 55 }
|
||||||
|
scGray40pct = $00969696;
|
||||||
|
{@@ rgb value of <b>dark teal</b>, BIFF8 palette index 56 }
|
||||||
|
scDarkTeal = $00663300;
|
||||||
|
{@@ rgb value of <b>sea green</b>, BIFF8 palette index 57 }
|
||||||
|
scSeaGreen = $00669933;
|
||||||
|
{@@ rgb value of <b>very dark green</b>, BIFF8 palette index 58 }
|
||||||
|
scVeryDarkGreen = $00003300;
|
||||||
|
{@@ rgb value of <b>olive green</b> color, BIFF8 palette index 59 }
|
||||||
|
scOliveGreen = $00003333;
|
||||||
|
{@@ rgb value of <b>brown</b> color, BIFF8 palette index 60 }
|
||||||
|
scBrown = $00003399;
|
||||||
|
{@@ rgb value of <b>indigo</b> color, BIFF8 palette index 62 }
|
||||||
|
scIndigo = $00993333;
|
||||||
|
{@@ rgb value of <b>80% gray</b>, BIFF8 palette index 63 }
|
||||||
|
scGray80pct = $00333333;
|
||||||
|
scGrey80pct = scGray80pct;
|
||||||
|
|
||||||
// not sure - but I think the mechanism with scRGBColor is not working...
|
// {@@ rgb value of <b>orange</b> color }
|
||||||
// Will be removed sooner or later...
|
// scOrange = $0000A5FF;
|
||||||
scRGBColor = $FFFD;
|
{@@ rgb value of <b>dark brown</b> color }
|
||||||
|
scDarkBrown = $002D52A0;
|
||||||
|
|
||||||
|
// {@@ rgb value of <b>brown</b> color }
|
||||||
|
// scBrown = $003F85CD;
|
||||||
|
{@@ rgb value of <b>beige</b> color }
|
||||||
|
scBeige = $00DCF5F5;
|
||||||
|
{@@ rgb value of <b>"wheat"</b> color (yellow-orange) }
|
||||||
|
scWheat = $00B3DEF5;
|
||||||
|
|
||||||
{@@ Identifier for transparent color }
|
|
||||||
scTransparent = $FFFE;
|
|
||||||
{@@ Identifier for not-defined color }
|
{@@ Identifier for not-defined color }
|
||||||
scNotDefined = $FFFF;
|
scNotDefined = $40000000;
|
||||||
|
{@@ Identifier for transparent color }
|
||||||
|
scTransparent = $20000000;
|
||||||
|
{@@ Identifier for palette index encoded into the TsColor }
|
||||||
|
scPaletteIndexMask = $80000000;
|
||||||
|
{@@ Mask for the rgb components contained in the TsColor }
|
||||||
|
scRGBMask = $00FFFFFF;
|
||||||
|
|
||||||
type
|
type
|
||||||
{@@ Data type for rgb color values }
|
|
||||||
TsColorValue = DWord;
|
|
||||||
|
|
||||||
{@@ Palette of color values. A "color value" is a DWord value containing
|
|
||||||
rgb colors. }
|
|
||||||
TsPalette = array[0..0] of TsColorValue;
|
|
||||||
PsPalette = ^TsPalette;
|
|
||||||
|
|
||||||
{@@ Font style (redefined to avoid usage of "Graphics" }
|
{@@ Font style (redefined to avoid usage of "Graphics" }
|
||||||
TsFontStyle = (fssBold, fssItalic, fssStrikeOut, fssUnderline);
|
TsFontStyle = (fssBold, fssItalic, fssStrikeOut, fssUnderline);
|
||||||
|
|
||||||
@ -365,7 +420,7 @@ type
|
|||||||
Size: Single; // in "points"
|
Size: Single; // in "points"
|
||||||
{@@ Font style, such as bold, italics etc. - see TsFontStyle}
|
{@@ Font style, such as bold, italics etc. - see TsFontStyle}
|
||||||
Style: TsFontStyles;
|
Style: TsFontStyles;
|
||||||
{@@ Text color given by the index into the workbook's color palette }
|
{@@ Text color given as rgb value }
|
||||||
Color: TsColor;
|
Color: TsColor;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
@ -28,6 +28,9 @@ type
|
|||||||
{@@ Set of characters }
|
{@@ Set of characters }
|
||||||
TsDecsChars = set of char;
|
TsDecsChars = set of char;
|
||||||
|
|
||||||
|
{@@ Color value, composed of r(ed), g(reen) and b(lue) components }
|
||||||
|
TRGBA = record r, g, b, a: byte end;
|
||||||
|
|
||||||
const
|
const
|
||||||
{@@ Date formatting string for unambiguous date/time display as strings
|
{@@ Date formatting string for unambiguous date/time display as strings
|
||||||
Can be used for text output when date/time cell support is not available }
|
Can be used for text output when date/time cell support is not available }
|
||||||
@ -51,8 +54,6 @@ function WordLEtoN(AValue: Word): Word;
|
|||||||
function DWordLEtoN(AValue: Cardinal): Cardinal;
|
function DWordLEtoN(AValue: Cardinal): Cardinal;
|
||||||
function WideStringLEToN(const AValue: WideString): WideString;
|
function WideStringLEToN(const AValue: WideString): WideString;
|
||||||
|
|
||||||
function LongRGBToExcelPhysical(const RGB: DWord): DWord;
|
|
||||||
|
|
||||||
// Other routines
|
// Other routines
|
||||||
function ParseIntervalString(const AStr: string;
|
function ParseIntervalString(const AStr: string;
|
||||||
out AFirstCellRow, AFirstCellCol, ACount: Cardinal;
|
out AFirstCellRow, AFirstCellCol, ACount: Cardinal;
|
||||||
@ -140,13 +141,18 @@ function pxToPts(AValue, AScreenPixelsPerInch: Integer): Double; inline;
|
|||||||
function PtsToPx(AValue: Double; AScreenPixelsPerInch: Integer): Integer; inline;
|
function PtsToPx(AValue: Double; AScreenPixelsPerInch: Integer): Integer; inline;
|
||||||
function HTMLLengthStrToPts(AValue: String; DefaultUnits: String = 'pt'): Double;
|
function HTMLLengthStrToPts(AValue: String; DefaultUnits: String = 'pt'): Double;
|
||||||
|
|
||||||
function HTMLColorStrToColor(AValue: String): TsColorValue;
|
|
||||||
function ColorToHTMLColorStr(AValue: TsColorValue; AExcelDialect: Boolean = false): String;
|
|
||||||
function UTF8TextToXMLText(AText: ansistring): ansistring;
|
function UTF8TextToXMLText(AText: ansistring): ansistring;
|
||||||
function ValidXMLText(var AText: ansistring; ReplaceSpecialChars: Boolean = true): Boolean;
|
function ValidXMLText(var AText: ansistring; ReplaceSpecialChars: Boolean = true): Boolean;
|
||||||
|
|
||||||
function TintedColor(AColor: TsColorValue; tint: Double): TsColorValue;
|
function ColorToHTMLColorStr(AValue: TsColor; AExcelDialect: Boolean = false): String;
|
||||||
function HighContrastColor(AColorValue: TsColorValue): TsColor;
|
function HTMLColorStrToColor(AValue: String): TsColor;
|
||||||
|
|
||||||
|
function GetColorName(AColor: TsColor): String;
|
||||||
|
function HighContrastColor(AColor: TsColor): TsColor;
|
||||||
|
function IsPaletteIndex(AColor: TsColor): Boolean;
|
||||||
|
function LongRGBToExcelPhysical(const RGB: DWord): DWord;
|
||||||
|
function SetAsPaletteIndex(AIndex: Integer): TsColor;
|
||||||
|
function TintedColor(AColor: TsColor; tint: Double): TsColor;
|
||||||
|
|
||||||
function AnalyzeCompareStr(AString: String; out ACompareOp: TsCompareOperation): String;
|
function AnalyzeCompareStr(AString: String; out ACompareOp: TsCompareOperation): String;
|
||||||
|
|
||||||
@ -183,9 +189,6 @@ implementation
|
|||||||
uses
|
uses
|
||||||
Math, lazutf8, fpsStrings;
|
Math, lazutf8, fpsStrings;
|
||||||
|
|
||||||
type
|
|
||||||
TRGBA = record r, g, b, a: byte end;
|
|
||||||
|
|
||||||
const
|
const
|
||||||
POS_CURR_FMT: array[0..3] of string = (
|
POS_CURR_FMT: array[0..3] of string = (
|
||||||
// Format parameter 0 is "value", parameter 1 is "currency symbol"
|
// Format parameter 0 is "value", parameter 1 is "currency symbol"
|
||||||
@ -356,29 +359,6 @@ begin
|
|||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
|
||||||
Converts the RGB part of a LongRGB logical structure to its physical representation.
|
|
||||||
In other words: RGBA (where A is 0 and omitted in the function call) => ABGR
|
|
||||||
Needed for conversion of palette colors.
|
|
||||||
|
|
||||||
@param RGB DWord value containing RGBA bytes in big endian byte-order
|
|
||||||
@return DWord containing RGB bytes in little-endian byte-order (A = 0)
|
|
||||||
-------------------------------------------------------------------------------}
|
|
||||||
function LongRGBToExcelPhysical(const RGB: DWord): DWord;
|
|
||||||
begin
|
|
||||||
{$IFDEF FPC}
|
|
||||||
{$IFDEF ENDIAN_LITTLE}
|
|
||||||
result := RGB shl 8; //tags $00 at end for the A byte
|
|
||||||
result := SwapEndian(result); //flip byte order
|
|
||||||
{$ELSE}
|
|
||||||
//Big endian
|
|
||||||
result := RGB; //leave value as is //todo: verify if this turns out ok
|
|
||||||
{$ENDIF}
|
|
||||||
{$ELSE}
|
|
||||||
// messed up result
|
|
||||||
{$ENDIF}
|
|
||||||
end;
|
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Parses strings like A5:A10 into an selection interval information
|
Parses strings like A5:A10 into an selection interval information
|
||||||
|
|
||||||
@ -1968,13 +1948,83 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Converts a HTML color string to a TsColorValue. Need for the ODS file format.
|
Determines the name of a color from its rgb value
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function GetColorName(AColor: TsColor): string;
|
||||||
|
var
|
||||||
|
rgba: TRGBA absolute AColor;
|
||||||
|
begin
|
||||||
|
case AColor of
|
||||||
|
scAqua : Result := rsAqua;
|
||||||
|
scBeige : Result := rsBeige;
|
||||||
|
scBlack : Result := rsBlack;
|
||||||
|
scBlue : Result := rsBlue;
|
||||||
|
scBlueGray : Result := rsBlueGray;
|
||||||
|
scBrown : Result := rsBrown;
|
||||||
|
scCoral : Result := rsCoral;
|
||||||
|
scCyan : Result := rsCyan;
|
||||||
|
scDarkBlue : Result := rsDarkBlue;
|
||||||
|
scDarkGreen : Result := rsDarkGreen;
|
||||||
|
scDarkPurple : Result := rsDarkPurple;
|
||||||
|
scDarkRed : Result := rsDarkRed;
|
||||||
|
scDarkTeal : Result := rsDarkTeal;
|
||||||
|
scGold : Result := rsGold;
|
||||||
|
scGray : Result := rsGray;
|
||||||
|
scGray10pct : Result := rsGray10pct;
|
||||||
|
scGray20pct : Result := rsGray20pct;
|
||||||
|
scGray40pct : Result := rsGray40pct;
|
||||||
|
scGray80pct : Result := rsGray80pct;
|
||||||
|
scGreen : Result := rsGreen;
|
||||||
|
scIceBlue : Result := rsIceBlue;
|
||||||
|
scIndigo : Result := rsIndigo;
|
||||||
|
scIvory : Result := rsIvory;
|
||||||
|
scLavander : Result := rsLavander;
|
||||||
|
scLightBlue : Result := rsLightBlue;
|
||||||
|
scLightGreen : Result := rsLightGreen;
|
||||||
|
scLightOrange: Result := rsLightOrange;
|
||||||
|
scLightTurquoise: Result := rsLightTurquoise;
|
||||||
|
scLightYellow: Result := rsLightYellow;
|
||||||
|
scLime : Result := rsLime;
|
||||||
|
scMagenta : Result := rsMagenta;
|
||||||
|
scNavy : Result := rsNavy;
|
||||||
|
scOceanBlue : Result := rsOceanBlue;
|
||||||
|
scOlive : Result := rsOlive;
|
||||||
|
scOliveGreen : Result := rsOliveGreen;
|
||||||
|
scOrange : Result := rsOrange;
|
||||||
|
scPaleBlue : Result := rsPaleBlue;
|
||||||
|
scPeriwinkle : Result := rsPeriwinkle;
|
||||||
|
scPink : Result := rsPink;
|
||||||
|
scPlum : Result := rsPlum;
|
||||||
|
scPurple : Result := rsPurple;
|
||||||
|
scRed : Result := rsRed;
|
||||||
|
scRose : Result := rsRose;
|
||||||
|
scSeaGreen : Result := rsSeaGreen;
|
||||||
|
scSilver : Result := rsSilver;
|
||||||
|
scSkyBlue : Result := rsSkyBlue;
|
||||||
|
scTan : Result := rsTan;
|
||||||
|
scTeal : Result := rsTeal;
|
||||||
|
scVeryDarkGreen: Result := rsVeryDarkGreen;
|
||||||
|
// scViolet : Result := rsViolet;
|
||||||
|
scWheat : Result := rsWheat;
|
||||||
|
scWhite : Result := rsWhite;
|
||||||
|
scYellow : Result := rsYellow;
|
||||||
|
scTransparent: Result := rsTransparent;
|
||||||
|
scNotDefined : Result := rsNotDefined;
|
||||||
|
else if rgba.a = 0 then
|
||||||
|
Result := Format('r%d g%d b%d', [rgba.r, rgba.g, rgba.b])
|
||||||
|
else
|
||||||
|
Result := '';
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Converts a HTML color string to a TsColor alue. Needed for the ODS file format.
|
||||||
|
|
||||||
@param AValue HTML color string, such as '#FF0000'
|
@param AValue HTML color string, such as '#FF0000'
|
||||||
@return rgb color value in little endian byte-sequence. This value is
|
@return rgb color value in little endian byte-sequence. This value is
|
||||||
compatible with the TColor data type of the graphics unit.
|
compatible with the TColor data type of the graphics unit.
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function HTMLColorStrToColor(AValue: String): TsColorValue;
|
function HTMLColorStrToColor(AValue: String): TsColor;
|
||||||
begin
|
begin
|
||||||
if AValue = '' then
|
if AValue = '' then
|
||||||
Result := scNotDefined
|
Result := scNotDefined
|
||||||
@ -2022,13 +2072,11 @@ end;
|
|||||||
i.e. in AARRGGBB notation, like '00FF0000' for "red"
|
i.e. in AARRGGBB notation, like '00FF0000' for "red"
|
||||||
@return HTML-compatible string, like '#FF0000' (AExcelDialect = false)
|
@return HTML-compatible string, like '#FF0000' (AExcelDialect = false)
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function ColorToHTMLColorStr(AValue: TsColorValue; AExcelDialect: Boolean = false): String;
|
function ColorToHTMLColorStr(AValue: TsColor;
|
||||||
type
|
AExcelDialect: Boolean = false): String;
|
||||||
TRGB = record r,g,b,a: Byte end;
|
|
||||||
var
|
var
|
||||||
rgb: TRGB;
|
rgb: TRGBA absolute AValue;
|
||||||
begin
|
begin
|
||||||
rgb := TRGB(AValue);
|
|
||||||
if AExcelDialect then
|
if AExcelDialect then
|
||||||
Result := Format('00%.2x%.2x%.2x', [rgb.r, rgb.g, rgb.b])
|
Result := Format('00%.2x%.2x%.2x', [rgb.r, rgb.g, rgb.b])
|
||||||
else
|
else
|
||||||
@ -3069,6 +3117,23 @@ begin
|
|||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Constructs a TsColor from a palette index. It has bit 15 in the high-order
|
||||||
|
byte set.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function SetAsPaletteIndex(AIndex: Integer): TsColor;
|
||||||
|
begin
|
||||||
|
Result := (DWord(AIndex) and scRGBMask) or scPaletteIndexMask;
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Checks whether the specified TsColor represents a palette index
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function IsPaletteIndex(AColor: TsColor): Boolean;
|
||||||
|
begin
|
||||||
|
Result := AColor and scPaletteIndexMask = scPaletteIndexMask;
|
||||||
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Excel defines theme colors and applies a "tint" factor (-1...+1) to darken
|
Excel defines theme colors and applies a "tint" factor (-1...+1) to darken
|
||||||
or brighten them.
|
or brighten them.
|
||||||
@ -3082,7 +3147,7 @@ end;
|
|||||||
@param tint Factor (-1...+1) to be used for the operation
|
@param tint Factor (-1...+1) to be used for the operation
|
||||||
@return Modified color
|
@return Modified color
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function TintedColor(AColor: TsColorValue; tint: Double): TsColorValue;
|
function TintedColor(AColor: TsColor; tint: Double): TsColor;
|
||||||
const
|
const
|
||||||
HLSMAX = 255;
|
HLSMAX = 255;
|
||||||
var
|
var
|
||||||
@ -3090,7 +3155,7 @@ var
|
|||||||
h, l, s: Byte;
|
h, l, s: Byte;
|
||||||
lum: Double;
|
lum: Double;
|
||||||
begin
|
begin
|
||||||
if tint = 0 then begin
|
if (tint = 0) or (TRGBA(AColor).a <> 0) then begin
|
||||||
Result := AColor;
|
Result := AColor;
|
||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
@ -3119,18 +3184,42 @@ end;
|
|||||||
Returns the color index for black or white depending on a color being "bright"
|
Returns the color index for black or white depending on a color being "bright"
|
||||||
or "dark".
|
or "dark".
|
||||||
|
|
||||||
@param AColorValue rgb color to be analyzed
|
@param AColor rgb color to be analyzed
|
||||||
@return The color index for black (scBlack) if AColorValue is a "bright" color,
|
@return The color index for black (scBlack) if AColorValue is a "bright" color,
|
||||||
or white (scWhite) if AColorValue is a "dark" color.
|
or white (scWhite) if AColorValue is a "dark" color.
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
function HighContrastColor(AColorValue: TsColorvalue): TsColor;
|
function HighContrastColor(AColor: TsColor): TsColor;
|
||||||
begin
|
begin
|
||||||
if TRGBA(AColorValue).r + TRGBA(AColorValue).g + TRGBA(AColorValue).b < 3*128 then
|
if TRGBA(AColor).r + TRGBA(AColor).g + TRGBA(AColor).b < 3*128 then
|
||||||
Result := scWhite
|
Result := scWhite
|
||||||
else
|
else
|
||||||
Result := scBlack;
|
Result := scBlack;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Converts the RGB part of a LongRGB logical structure to its physical representation.
|
||||||
|
In other words: RGBA (where A is 0 and omitted in the function call) => ABGR
|
||||||
|
Needed for conversion of palette colors.
|
||||||
|
|
||||||
|
@param RGB DWord value containing RGBA bytes in big endian byte-order
|
||||||
|
@return DWord containing RGB bytes in little-endian byte-order (A = 0)
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function LongRGBToExcelPhysical(const RGB: DWord): DWord;
|
||||||
|
begin
|
||||||
|
{$IFDEF FPC}
|
||||||
|
{$IFDEF ENDIAN_LITTLE}
|
||||||
|
result := RGB shl 8; //tags $00 at end for the A byte
|
||||||
|
result := SwapEndian(result); //flip byte order
|
||||||
|
{$ELSE}
|
||||||
|
//Big endian
|
||||||
|
result := RGB; //leave value as is //todo: verify if this turns out ok
|
||||||
|
{$ENDIF}
|
||||||
|
{$ELSE}
|
||||||
|
// messed up result
|
||||||
|
{$ENDIF}
|
||||||
|
end;
|
||||||
|
|
||||||
|
|
||||||
{$PUSH}{$HINTS OFF}
|
{$PUSH}{$HINTS OFF}
|
||||||
{@@ Silence warnings due to an unused parameter }
|
{@@ Silence warnings due to an unused parameter }
|
||||||
procedure Unused(const A1);
|
procedure Unused(const A1);
|
||||||
|
@ -10,7 +10,7 @@ uses
|
|||||||
|
|
||||||
procedure Convert_sFont_to_Font(AWorkbook: TsWorkbook; sFont: TsFont; AFont: TFont);
|
procedure Convert_sFont_to_Font(AWorkbook: TsWorkbook; sFont: TsFont; AFont: TFont);
|
||||||
procedure Convert_Font_to_sFont(AWorkbook: TsWorkbook; AFont: TFont; sFont: TsFont);
|
procedure Convert_Font_to_sFont(AWorkbook: TsWorkbook; AFont: TFont; sFont: TsFont);
|
||||||
function FindNearestPaletteIndex(AWorkbook: TsWorkbook; AColor: TColor): TsColor;
|
//function FindNearestPaletteIndex(AWorkbook: TsWorkbook; AColor: TColor): TsColor;
|
||||||
function WrapText(ACanvas: TCanvas; const AText: string; AMaxWidth: integer): string;
|
function WrapText(ACanvas: TCanvas; const AText: string; AMaxWidth: integer): string;
|
||||||
|
|
||||||
|
|
||||||
@ -36,7 +36,7 @@ begin
|
|||||||
if fssItalic in sFont.Style then AFont.Style := AFont.Style + [fsItalic];
|
if fssItalic in sFont.Style then AFont.Style := AFont.Style + [fsItalic];
|
||||||
if fssUnderline in sFont.Style then AFont.Style := AFont.Style + [fsUnderline];
|
if fssUnderline in sFont.Style then AFont.Style := AFont.Style + [fsUnderline];
|
||||||
if fssStrikeout in sFont.Style then AFont.Style := AFont.Style + [fsStrikeout];
|
if fssStrikeout in sFont.Style then AFont.Style := AFont.Style + [fsStrikeout];
|
||||||
AFont.Color := AWorkbook.GetPaletteColor(sFont.Color);
|
AFont.Color := TColor(sFont.Color and $00FFFFFF);
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -56,10 +56,10 @@ begin
|
|||||||
if fsItalic in AFont.Style then Include(sFont.Style, fssItalic);
|
if fsItalic in AFont.Style then Include(sFont.Style, fssItalic);
|
||||||
if fsUnderline in AFont.Style then Include(sFont.Style, fssUnderline);
|
if fsUnderline in AFont.Style then Include(sFont.Style, fssUnderline);
|
||||||
if fsStrikeout in AFont.Style then Include(sFont.Style, fssStrikeout);
|
if fsStrikeout in AFont.Style then Include(sFont.Style, fssStrikeout);
|
||||||
sFont.Color := FindNearestPaletteIndex(AWorkbook, AFont.Color);
|
sFont.Color := ColorToRGB(AFont.Color);
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
(*
|
||||||
function FindNearestPaletteIndex(AWorkbook: TsWorkbook; AColor: TColor): TsColor;
|
function FindNearestPaletteIndex(AWorkbook: TsWorkbook; AColor: TColor): TsColor;
|
||||||
|
|
||||||
procedure ColorToHSL(RGB: TColor; out H, S, L : double);
|
procedure ColorToHSL(RGB: TColor; out H, S, L : double);
|
||||||
@ -148,7 +148,7 @@ begin
|
|||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
*)
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Wraps text by inserting line ending characters so that the lines are not
|
Wraps text by inserting line ending characters so that the lines are not
|
||||||
longer than AMaxWidth.
|
longer than AMaxWidth.
|
||||||
|
@ -28,7 +28,7 @@
|
|||||||
This package is all you need if you don't want graphical components (like grids and charts)."/>
|
This package is all you need if you don't want graphical components (like grids and charts)."/>
|
||||||
<License Value="LGPL with static linking exception. This is the same license as is used in the LCL (Lazarus Component Library)."/>
|
<License Value="LGPL with static linking exception. This is the same license as is used in the LCL (Lazarus Component Library)."/>
|
||||||
<Version Major="1" Minor="5"/>
|
<Version Major="1" Minor="5"/>
|
||||||
<Files Count="34">
|
<Files Count="35">
|
||||||
<Item1>
|
<Item1>
|
||||||
<Filename Value="fpolestorage.pas"/>
|
<Filename Value="fpolestorage.pas"/>
|
||||||
<UnitName Value="fpolestorage"/>
|
<UnitName Value="fpolestorage"/>
|
||||||
@ -165,6 +165,10 @@ This package is all you need if you don't want graphical components (like grids
|
|||||||
<Filename Value="fpsheaderfooterparser.pas"/>
|
<Filename Value="fpsheaderfooterparser.pas"/>
|
||||||
<UnitName Value="fpsHeaderFooterParser"/>
|
<UnitName Value="fpsHeaderFooterParser"/>
|
||||||
</Item34>
|
</Item34>
|
||||||
|
<Item35>
|
||||||
|
<Filename Value="fpspalette.pas"/>
|
||||||
|
<UnitName Value="fpsPalette"/>
|
||||||
|
</Item35>
|
||||||
</Files>
|
</Files>
|
||||||
<RequiredPkgs Count="2">
|
<RequiredPkgs Count="2">
|
||||||
<Item1>
|
<Item1>
|
||||||
|
@ -13,7 +13,7 @@ uses
|
|||||||
uvirtuallayer_ole_helpers, uvirtuallayer_ole_types, uvirtuallayer_stream,
|
uvirtuallayer_ole_helpers, uvirtuallayer_ole_types, uvirtuallayer_stream,
|
||||||
fpolebasic, wikitable, fpsNumFormatParser, fpsfunc, fpsRPN, fpsStrings,
|
fpolebasic, wikitable, fpsNumFormatParser, fpsfunc, fpsRPN, fpsStrings,
|
||||||
fpscsv, fpsCsvDocument, fpspatches, fpsTypes, xlsEscher, fpsReaderWriter,
|
fpscsv, fpsCsvDocument, fpspatches, fpsTypes, xlsEscher, fpsReaderWriter,
|
||||||
fpsNumFormat, fpsclasses, fpsHeaderFooterParser;
|
fpsNumFormat, fpsclasses, fpsHeaderFooterParser, fpsPalette;
|
||||||
|
|
||||||
implementation
|
implementation
|
||||||
|
|
||||||
|
@ -80,8 +80,12 @@ type
|
|||||||
procedure TestWriteRead_OOXML_Font_RandomPal; // palette 64, top 56 entries random
|
procedure TestWriteRead_OOXML_Font_RandomPal; // palette 64, top 56 entries random
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
|
||||||
implementation
|
implementation
|
||||||
|
|
||||||
|
uses
|
||||||
|
fpsPalette;
|
||||||
|
|
||||||
const
|
const
|
||||||
ColorsSheet = 'Colors';
|
ColorsSheet = 'Colors';
|
||||||
|
|
||||||
@ -111,47 +115,41 @@ var
|
|||||||
row, col: Integer;
|
row, col: Integer;
|
||||||
MyCell: PCell;
|
MyCell: PCell;
|
||||||
TempFile: string; //write xls/xml to this file and read back from it
|
TempFile: string; //write xls/xml to this file and read back from it
|
||||||
color: TsColor;
|
|
||||||
expectedRGB: DWord;
|
expectedRGB: DWord;
|
||||||
currentRGB: DWord;
|
currentRGB: DWord;
|
||||||
pal: Array of TsColorValue;
|
palette: TsPalette;
|
||||||
i: Integer;
|
i: Integer;
|
||||||
begin
|
begin
|
||||||
TempFile:=GetTempFileName;
|
TempFile:=GetTempFileName;
|
||||||
|
|
||||||
|
// Define palette
|
||||||
|
palette := TsPalette.Create;
|
||||||
|
try
|
||||||
|
case whichPalette of
|
||||||
|
5: palette.UseColors(PALETTE_BIFF5);
|
||||||
|
8: palette.UseColors(PALETTE_BIFF8);
|
||||||
|
999: begin // random palette: testing of color replacement
|
||||||
|
palette.UseColors(PALETTE_BIFF8);
|
||||||
|
for i:=8 to 63 do // first 8 colors must not be changed in Excel
|
||||||
|
palette[i] := random(256) + random(256) shr 8 + random(256) shr 16;
|
||||||
|
end;
|
||||||
|
else palette.AddBuiltinColors;
|
||||||
|
end;
|
||||||
|
|
||||||
MyWorkbook := TsWorkbook.Create;
|
MyWorkbook := TsWorkbook.Create;
|
||||||
try
|
try
|
||||||
MyWorkSheet:= MyWorkBook.AddWorksheet(ColorsSheet);
|
MyWorkSheet:= MyWorkBook.AddWorksheet(ColorsSheet);
|
||||||
|
|
||||||
// Define palette
|
|
||||||
case whichPalette of
|
|
||||||
5: MyWorkbook.UsePalette(@PALETTE_BIFF5, Length(PALETTE_BIFF5));
|
|
||||||
8: MyWorkbook.UsePalette(@PALETTE_BIFF8, Length(PALETTE_BIFF8));
|
|
||||||
999: begin // Random palette: testing of color replacement
|
|
||||||
MyWorkbook.UsePalette(@PALETTE_BIFF8, Length(PALETTE_BIFF8));
|
|
||||||
for i:=8 to 63 do // first 8 colors cannot be changed
|
|
||||||
MyWorkbook.SetPaletteColor(i, random(256) + random(256) shr 8 + random(256) shr 16);
|
|
||||||
end;
|
|
||||||
// else use default palette
|
|
||||||
end;
|
|
||||||
|
|
||||||
// Remember all colors because ODS does not have a palette in the file; therefore
|
|
||||||
// we do not know which colors to expect.
|
|
||||||
SetLength(pal, MyWorkbook.GetPaletteSize);
|
|
||||||
for i:=0 to High(pal) do
|
|
||||||
pal[i] := MyWorkbook.GetPaletteColor(i);
|
|
||||||
|
|
||||||
// Write out all colors
|
// Write out all colors
|
||||||
row := 0;
|
row := 0;
|
||||||
col := 0;
|
col := 0;
|
||||||
for color := 0 to MyWorkbook.GetPaletteSize-1 do begin
|
for i := 0 to palette.Count-1 do begin
|
||||||
MyWorksheet.WriteUTF8Text(row, col, CELLTEXT);
|
MyWorksheet.WriteUTF8Text(row, col, CELLTEXT);
|
||||||
MyWorksheet.WriteBackgroundColor(row, col, color);
|
MyCell := MyWorksheet.WriteBackgroundColor(row, col, palette[i]);
|
||||||
MyCell := MyWorksheet.FindCell(row, col);
|
|
||||||
if MyCell = nil then
|
if MyCell = nil then
|
||||||
fail('Error in test code. Failed to get cell.');
|
fail('Error in test code. Failed to get cell.');
|
||||||
currentRGB := MyWorkbook.GetPaletteColor(MyWorksheet.ReadBackgroundColor(MyCell));
|
currentRGB := MyWorksheet.ReadBackgroundColor(MyCell);
|
||||||
expectedRGB := MyWorkbook.GetPaletteColor(color);
|
expectedRGB := palette[i];
|
||||||
CheckEquals(expectedRGB, currentRGB,
|
CheckEquals(expectedRGB, currentRGB,
|
||||||
'Test unsaved background color, cell ' + CellNotation(MyWorksheet,0,0));
|
'Test unsaved background color, cell ' + CellNotation(MyWorksheet,0,0));
|
||||||
inc(row);
|
inc(row);
|
||||||
@ -175,9 +173,8 @@ begin
|
|||||||
MyCell := MyWorksheet.FindCell(row, col);
|
MyCell := MyWorksheet.FindCell(row, col);
|
||||||
if MyCell = nil then
|
if MyCell = nil then
|
||||||
fail('Error in test code. Failed to get cell.');
|
fail('Error in test code. Failed to get cell.');
|
||||||
color := TsColor(row);
|
currentRGB := MyWorksheet.ReadBackgroundColor(MyCell);
|
||||||
currentRGB := MyWorkbook.GetPaletteColor(MyWorksheet.ReadBackgroundColor(MyCell));
|
expectedRGB := palette[row];
|
||||||
expectedRGB := pal[color];
|
|
||||||
CheckEquals(expectedRGB, currentRGB,
|
CheckEquals(expectedRGB, currentRGB,
|
||||||
'Test saved background color, cell '+CellNotation(MyWorksheet,Row,Col));
|
'Test saved background color, cell '+CellNotation(MyWorksheet,Row,Col));
|
||||||
end;
|
end;
|
||||||
@ -185,6 +182,10 @@ begin
|
|||||||
MyWorkbook.Free;
|
MyWorkbook.Free;
|
||||||
DeleteFile(TempFile);
|
DeleteFile(TempFile);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
finally
|
||||||
|
palette.Free
|
||||||
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TSpreadWriteReadColorTests.TestWriteReadFontColors(AFormat: TsSpreadsheetFormat;
|
procedure TSpreadWriteReadColorTests.TestWriteReadFontColors(AFormat: TsSpreadsheetFormat;
|
||||||
@ -201,47 +202,41 @@ var
|
|||||||
row, col: Integer;
|
row, col: Integer;
|
||||||
MyCell: PCell;
|
MyCell: PCell;
|
||||||
TempFile: string; //write xls/xml to this file and read back from it
|
TempFile: string; //write xls/xml to this file and read back from it
|
||||||
color, colorInFile: TsColor;
|
|
||||||
expectedRGB, currentRGB: DWord;
|
expectedRGB, currentRGB: DWord;
|
||||||
pal: Array of TsColorValue;
|
palette: TsPalette;
|
||||||
i: Integer;
|
i: Integer;
|
||||||
begin
|
begin
|
||||||
TempFile:=GetTempFileName;
|
TempFile:=GetTempFileName;
|
||||||
|
|
||||||
|
// Define palette
|
||||||
|
palette := TsPalette.Create;
|
||||||
|
try
|
||||||
|
case whichPalette of
|
||||||
|
5: palette.UseColors(PALETTE_BIFF5);
|
||||||
|
8: palette.UseColors(PALETTE_BIFF8);
|
||||||
|
999: begin // random palette: testing of color replacement
|
||||||
|
palette.UseColors(PALETTE_BIFF8);
|
||||||
|
for i:=8 to 63 do // first 8 colors must not be changed in Excel
|
||||||
|
palette[i] := random(256) + random(256) shr 8 + random(256) shr 16;
|
||||||
|
end;
|
||||||
|
else palette.AddBuiltinColors;
|
||||||
|
end;
|
||||||
|
|
||||||
MyWorkbook := TsWorkbook.Create;
|
MyWorkbook := TsWorkbook.Create;
|
||||||
try
|
try
|
||||||
MyWorkSheet:= MyWorkBook.AddWorksheet(ColorsSheet);
|
MyWorkSheet:= MyWorkBook.AddWorksheet(ColorsSheet);
|
||||||
|
|
||||||
// Define palette
|
|
||||||
case whichPalette of
|
|
||||||
5: MyWorkbook.UsePalette(@PALETTE_BIFF5, High(PALETTE_BIFF5)+1);
|
|
||||||
8: MyWorkbook.UsePalette(@PALETTE_BIFF8, High(PALETTE_BIFF8)+1);
|
|
||||||
999: begin // Random palette: testing of color replacement
|
|
||||||
MyWorkbook.UsePalette(@PALETTE_BIFF8, Length(PALETTE_BIFF8));
|
|
||||||
for i:=8 to 63 do // first 8 colors cannot be changed
|
|
||||||
MyWorkbook.SetPaletteColor(i, random(256) + random(256) shr 8 + random(256) shr 16);
|
|
||||||
end;
|
|
||||||
// else use default palette
|
|
||||||
end;
|
|
||||||
|
|
||||||
// Remember all colors because ODS does not have a palette in the file;
|
|
||||||
// therefore we do not know which colors to expect.
|
|
||||||
SetLength(pal, MyWorkbook.GetPaletteSize);
|
|
||||||
for color:=0 to High(pal) do
|
|
||||||
pal[color] := MyWorkbook.GetPaletteColor(color);
|
|
||||||
|
|
||||||
// Write out all colors
|
// Write out all colors
|
||||||
row := 0;
|
row := 0;
|
||||||
col := 0;
|
col := 0;
|
||||||
for color := 0 to MyWorkbook.GetPaletteSize-1 do begin
|
for i := 0 to palette.Count-1 do begin
|
||||||
MyWorksheet.WriteUTF8Text(row, col, CELLTEXT);
|
MyWorksheet.WriteUTF8Text(row, col, CELLTEXT);
|
||||||
MyWorksheet.WriteFontColor(row, col, color);
|
MyWorksheet.WriteFontColor(row, col, palette[i]);
|
||||||
MyCell := MyWorksheet.FindCell(row, col);
|
MyCell := MyWorksheet.FindCell(row, col);
|
||||||
if MyCell = nil then
|
if MyCell = nil then
|
||||||
fail('Error in test code. Failed to get cell.');
|
fail('Error in test code. Failed to get cell.');
|
||||||
colorInFile := MyWorksheet.ReadCellFont(MyCell).Color;
|
currentRGB := MyWorksheet.ReadCellFont(MyCell).Color;
|
||||||
currentRGB := MyWorkbook.GetPaletteColor(colorInFile);
|
expectedRGB := palette[i];
|
||||||
expectedRGB := MyWorkbook.GetPaletteColor(color);
|
|
||||||
CheckEquals(expectedRGB, currentRGB,
|
CheckEquals(expectedRGB, currentRGB,
|
||||||
'Test unsaved font color, cell ' + CellNotation(MyWorksheet,row, col));
|
'Test unsaved font color, cell ' + CellNotation(MyWorksheet,row, col));
|
||||||
inc(row);
|
inc(row);
|
||||||
@ -261,21 +256,18 @@ begin
|
|||||||
MyWorksheet := GetWorksheetByName(MyWorkBook, ColorsSheet);
|
MyWorksheet := GetWorksheetByName(MyWorkBook, ColorsSheet);
|
||||||
if MyWorksheet=nil then
|
if MyWorksheet=nil then
|
||||||
fail('Error in test code. Failed to get named worksheet');
|
fail('Error in test code. Failed to get named worksheet');
|
||||||
|
col := 0;
|
||||||
for row := 0 to MyWorksheet.GetLastRowIndex do begin
|
for row := 0 to MyWorksheet.GetLastRowIndex do begin
|
||||||
MyCell := MyWorksheet.FindCell(row, col);
|
MyCell := MyWorksheet.FindCell(row, col);
|
||||||
if MyCell = nil then
|
if MyCell = nil then
|
||||||
fail('Error in test code. Failed to get cell.');
|
fail('Error in test code. Failed to get cell.');
|
||||||
color := TsColor(row);
|
expectedRGB := palette[row];
|
||||||
expectedRGB := pal[color];
|
currentRGB := MyWorksheet.ReadCellFont(MyCell).Color;
|
||||||
colorInFile := MyWorksheet.ReadCellFont(MyCell).Color;
|
|
||||||
currentRGB := MyWorkbook.GetPaletteColor(colorInFile);
|
|
||||||
|
|
||||||
// Excel2 cannot write the entire palette. The writer had called "FixColor".
|
// Excel2 cannot write the entire palette. We have to look for the
|
||||||
// We simulate that here to get the color correct.
|
// closest color.
|
||||||
if (AFormat = sfExcel2) and (color >= BIFF2_MAX_PALETTE_SIZE) then begin
|
if (AFormat = sfExcel2) then
|
||||||
color := MyWorkbook.FindClosestColor(expectedRGB, BIFF2_MAX_PALETTE_SIZE);
|
expectedRGB := palette[palette.FindClosestColorIndex(expectedRGB, BIFF2_MAX_PALETTE_SIZE)];
|
||||||
expectedRGB := MyWorkbook.GetPaletteColor(color);
|
|
||||||
end;
|
|
||||||
CheckEquals(expectedRGB, currentRGB,
|
CheckEquals(expectedRGB, currentRGB,
|
||||||
'Test saved font color, cell '+CellNotation(MyWorksheet,Row,Col));
|
'Test saved font color, cell '+CellNotation(MyWorksheet,Row,Col));
|
||||||
end;
|
end;
|
||||||
@ -283,6 +275,10 @@ begin
|
|||||||
MyWorkbook.Free;
|
MyWorkbook.Free;
|
||||||
DeleteFile(TempFile);
|
DeleteFile(TempFile);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
finally
|
||||||
|
palette.Free;
|
||||||
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ Tests for BIFF2 file format }
|
{ Tests for BIFF2 file format }
|
||||||
|
@ -35,7 +35,7 @@ type
|
|||||||
implementation
|
implementation
|
||||||
|
|
||||||
uses
|
uses
|
||||||
StrUtils, fpsRPN, xlsbiff5;
|
StrUtils, fpsPalette, fpsRPN, xlsbiff5;
|
||||||
|
|
||||||
const
|
const
|
||||||
ERROR_SHEET = 'ErrorTest'; //worksheet name
|
ERROR_SHEET = 'ErrorTest'; //worksheet name
|
||||||
@ -67,6 +67,8 @@ var
|
|||||||
ErrList: TStringList;
|
ErrList: TStringList;
|
||||||
newColor: TsColor;
|
newColor: TsColor;
|
||||||
expected: integer;
|
expected: integer;
|
||||||
|
palette: TsPalette;
|
||||||
|
i: Integer;
|
||||||
begin
|
begin
|
||||||
formula := '=A1';
|
formula := '=A1';
|
||||||
|
|
||||||
@ -122,14 +124,28 @@ begin
|
|||||||
MyWorkbook := TsWorkbook.Create;
|
MyWorkbook := TsWorkbook.Create;
|
||||||
try
|
try
|
||||||
// Prepare a full palette
|
// Prepare a full palette
|
||||||
MyWorkbook.UsePalette(@PALETTE_BIFF5[0], Length(PALETTE_BIFF5));
|
palette := TsPalette.Create;
|
||||||
// Add 1 more color - this is one too many for BIFF5 and 8, and a lot
|
try
|
||||||
// too many for BIFF2 !
|
// Create random palette of 65 unique entries - 1 too many for Excel5/8
|
||||||
newColor := MyWorkbook.AddColorToPalette($FF7878);
|
// and a lot too many for BIFF2
|
||||||
|
palette.AddBuiltinColors;
|
||||||
|
for i:=8 to 65 do
|
||||||
|
begin
|
||||||
|
repeat
|
||||||
|
newColor := random(256) + random(256) shl 8 + random(256) shl 16;
|
||||||
|
until palette.FindColor(newColor) = -1;
|
||||||
|
palette.AddColor(newColor);
|
||||||
|
end;
|
||||||
|
|
||||||
MyWorkSheet:= MyWorkBook.AddWorksheet(ERROR_SHEET);
|
MyWorkSheet:= MyWorkBook.AddWorksheet(ERROR_SHEET);
|
||||||
MyWorksheet.WriteUTF8Text(0, 0, s);
|
|
||||||
MyWorksheet.WriteFontColor(0, 0, newColor);
|
// Use all colors in order to have them in the palette to be written
|
||||||
|
// to file.
|
||||||
|
for row := 0 to palette.Count-1 do
|
||||||
|
begin
|
||||||
|
MyWorksheet.WriteUTF8Text(row, 0, s);
|
||||||
|
MyWorksheet.WriteFontColor(row, 0, palette[row]);
|
||||||
|
end;
|
||||||
|
|
||||||
TempFile:=NewTempFile;
|
TempFile:=NewTempFile;
|
||||||
MyWorkBook.WriteToFile(TempFile, AFormat, true);
|
MyWorkBook.WriteToFile(TempFile, AFormat, true);
|
||||||
@ -141,6 +157,11 @@ begin
|
|||||||
// no palette in xml --> no error expected
|
// no palette in xml --> no error expected
|
||||||
expected := 0;
|
expected := 0;
|
||||||
CheckEquals(expected, ErrList.Count, 'Error count mismatch in test 3');
|
CheckEquals(expected, ErrList.Count, 'Error count mismatch in test 3');
|
||||||
|
|
||||||
|
finally
|
||||||
|
palette.Free;
|
||||||
|
end;
|
||||||
|
|
||||||
finally
|
finally
|
||||||
MyWorkbook.Free;
|
MyWorkbook.Free;
|
||||||
DeleteFile(TempFile);
|
DeleteFile(TempFile);
|
||||||
|
@ -156,7 +156,7 @@ type
|
|||||||
implementation
|
implementation
|
||||||
|
|
||||||
uses
|
uses
|
||||||
TypInfo, fpsPatches, fpsutils, fpsnumformat, fpscsv;
|
TypInfo, fpsPatches, fpsutils, fpsnumformat, fpspalette, fpscsv;
|
||||||
|
|
||||||
const
|
const
|
||||||
FmtNumbersSheet = 'NumbersFormat'; //let's distinguish it from the regular numbers sheet
|
FmtNumbersSheet = 'NumbersFormat'; //let's distinguish it from the regular numbers sheet
|
||||||
@ -311,7 +311,7 @@ begin
|
|||||||
SollBorderLineStyles[5] := lsDouble;
|
SollBorderLineStyles[5] := lsDouble;
|
||||||
SollBorderLineStyles[6] := lsHair;
|
SollBorderLineStyles[6] := lsHair;
|
||||||
|
|
||||||
SollBorderColors[0] := scBlue;
|
SollBorderColors[0] := scBlack;
|
||||||
SollBorderColors[1] := scRed;
|
SollBorderColors[1] := scRed;
|
||||||
SollBorderColors[2] := scBlue;
|
SollBorderColors[2] := scBlue;
|
||||||
SollBorderColors[3] := scGray;
|
SollBorderColors[3] := scGray;
|
||||||
@ -728,7 +728,6 @@ begin
|
|||||||
// Write out all test values
|
// Write out all test values
|
||||||
MyWorkbook := TsWorkbook.Create;
|
MyWorkbook := TsWorkbook.Create;
|
||||||
try
|
try
|
||||||
MyWorkbook.UsePalette(@PALETTE_BIFF8, Length(PALETTE_BIFF8));
|
|
||||||
MyWorkSheet:= MyWorkBook.AddWorksheet(BackgroundSheet);
|
MyWorkSheet:= MyWorkBook.AddWorksheet(BackgroundSheet);
|
||||||
for style in TsFillStyle do begin
|
for style in TsFillStyle do begin
|
||||||
row := ord(style);
|
row := ord(style);
|
||||||
@ -752,7 +751,6 @@ begin
|
|||||||
MyWorksheet := GetWorksheetByName(MyWorkBook, BackgroundSheet);
|
MyWorksheet := GetWorksheetByName(MyWorkBook, BackgroundSheet);
|
||||||
if MyWorksheet=nil then
|
if MyWorksheet=nil then
|
||||||
fail('Error in test code. Failed to get named worksheet');
|
fail('Error in test code. Failed to get named worksheet');
|
||||||
|
|
||||||
for style in TsFillStyle do begin
|
for style in TsFillStyle do begin
|
||||||
row := ord(style);
|
row := ord(style);
|
||||||
|
|
||||||
@ -770,13 +768,13 @@ begin
|
|||||||
begin
|
begin
|
||||||
if PATTERN_COLOR <> patt.FgColor then
|
if PATTERN_COLOR <> patt.FgColor then
|
||||||
CheckEquals(
|
CheckEquals(
|
||||||
MyWorkbook.GetColorName(PATTERN_COLOR),
|
GetColorName(PATTERN_COLOR),
|
||||||
MyWorkbook.GetColorName(patt.FgColor),
|
GetColorName(patt.FgColor),
|
||||||
'Test saved fill pattern color mismatch, cell ' + CellNotation(MyWorksheet, row, col));
|
'Test saved fill pattern color mismatch, cell ' + CellNotation(MyWorksheet, row, col));
|
||||||
if BK_COLOR <> patt.BgColor then
|
if BK_COLOR <> patt.BgColor then
|
||||||
CheckEquals(
|
CheckEquals(
|
||||||
MyWorkbook.GetColorName(BK_COLOR),
|
GetColorName(BK_COLOR),
|
||||||
MyWorkbook.GetColorName(patt.BgColor),
|
GetColorName(patt.BgColor),
|
||||||
'Test saved fill background color mismatch, cell ' + CellNotation(MyWorksheet, row, col));
|
'Test saved fill background color mismatch, cell ' + CellNotation(MyWorksheet, row, col));
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -794,20 +792,20 @@ begin
|
|||||||
begin
|
begin
|
||||||
if PATTERN_COLOR <> patt.FgColor then
|
if PATTERN_COLOR <> patt.FgColor then
|
||||||
CheckEquals(
|
CheckEquals(
|
||||||
MyWorkbook.GetColorName(PATTERN_COLOR),
|
GetColorName(PATTERN_COLOR),
|
||||||
MyWorkbook.GetColorName(patt.FgColor),
|
GetColorName(patt.FgColor),
|
||||||
'Test saved fill pattern color mismatch, cell ' + CellNotation(MyWorksheet, row, col));
|
'Test saved fill pattern color mismatch, cell ' + CellNotation(MyWorksheet, row, col));
|
||||||
// SolidFill is a special case: here the background color is always equal
|
// SolidFill is a special case: here the background color is always equal
|
||||||
// to the pattern color - the cell layout does not know this...
|
// to the pattern color - the cell layout does not know this...
|
||||||
if style = fsSolidFill then
|
if style = fsSolidFill then
|
||||||
CheckEquals(
|
CheckEquals(
|
||||||
MyWorkbook.GetColorName(PATTERN_COLOR),
|
GetColorName(PATTERN_COLOR),
|
||||||
MyWorkbook.GetColorName(patt.BgColor),
|
GetColorName(patt.BgColor),
|
||||||
'Test saved fill pattern color mismatch, cell ' + CellNotation(MyWorksheet, row, col))
|
'Test saved fill pattern color mismatch, cell ' + CellNotation(MyWorksheet, row, col))
|
||||||
else
|
else
|
||||||
CheckEquals(
|
CheckEquals(
|
||||||
MyWorkbook.GetColorName(scTransparent),
|
GetColorName(scTransparent),
|
||||||
MyWorkbook.GetColorName(patt.BgColor),
|
GetColorName(patt.BgColor),
|
||||||
'Test saved fill background color mismatch, cell ' + CellNotation(MyWorksheet, row, col));
|
'Test saved fill background color mismatch, cell ' + CellNotation(MyWorksheet, row, col));
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
@ -983,11 +981,11 @@ begin
|
|||||||
begin
|
begin
|
||||||
for col := 1 to 10 do
|
for col := 1 to 10 do
|
||||||
begin
|
begin
|
||||||
MyWorksheet.WriteBorders(row*2, col*2, borders);
|
MyWorksheet.WriteBorders(row*2-1, col*2-1, borders);
|
||||||
for b in borders do
|
for b in borders do
|
||||||
begin
|
begin
|
||||||
MyWorksheet.WriteBorderLineStyle(row*2, col*2, b, SollBorderLineStyles[ls]);
|
MyWorksheet.WriteBorderLineStyle(row*2-1, col*2-1, b, SollBorderLineStyles[ls]);
|
||||||
MyWorksheet.WriteBorderColor(row*2, col*2, b, SollBorderColors[c]);
|
MyWorksheet.WriteBorderColor(row*2-1, col*2-1, b, SollBorderColors[c]);
|
||||||
inc(ls);
|
inc(ls);
|
||||||
if ls > High(SollBorderLineStyles) then
|
if ls > High(SollBorderLineStyles) then
|
||||||
begin
|
begin
|
||||||
@ -1021,7 +1019,7 @@ begin
|
|||||||
begin
|
begin
|
||||||
for col := 1 to 10 do
|
for col := 1 to 10 do
|
||||||
begin
|
begin
|
||||||
MyCell := MyWorksheet.FindCell(row*2, col*2);
|
MyCell := MyWorksheet.FindCell(row*2-1, col*2-1);
|
||||||
if myCell = nil then
|
if myCell = nil then
|
||||||
fail('Error in test code. Failed to get cell.');
|
fail('Error in test code. Failed to get cell.');
|
||||||
for b in borders do
|
for b in borders do
|
||||||
@ -1035,7 +1033,7 @@ begin
|
|||||||
if AFormat in [sfExcel8, sfOOXML] then
|
if AFormat in [sfExcel8, sfOOXML] then
|
||||||
case b of
|
case b of
|
||||||
cbDiagUp : diagUp_ls := expected;
|
cbDiagUp : diagUp_ls := expected;
|
||||||
cbDiagDown: expected := diagUp_ls;
|
cbDiagDown : expected := diagUp_ls;
|
||||||
end;
|
end;
|
||||||
CheckEquals(expected, current,
|
CheckEquals(expected, current,
|
||||||
'Test saved border line style mismatch, cell ' + CellNotation(MyWorksheet, row*2, col*2));
|
'Test saved border line style mismatch, cell ' + CellNotation(MyWorksheet, row*2, col*2));
|
||||||
@ -1047,7 +1045,7 @@ begin
|
|||||||
if AFormat in [sfExcel8, sfOOXML] then
|
if AFormat in [sfExcel8, sfOOXML] then
|
||||||
case b of
|
case b of
|
||||||
cbDiagUp : diagUp_clr := expected;
|
cbDiagUp : diagUp_clr := expected;
|
||||||
cbDiagDown: expected := diagUp_clr;
|
cbDiagDown : expected := diagUp_clr;
|
||||||
end;
|
end;
|
||||||
CheckEquals(expected, current,
|
CheckEquals(expected, current,
|
||||||
'Test saved border color mismatch, cell ' + CellNotation(MyWorksheet, row*2, col*2));
|
'Test saved border color mismatch, cell ' + CellNotation(MyWorksheet, row*2, col*2));
|
||||||
@ -1591,7 +1589,12 @@ var
|
|||||||
fnt: TsFont;
|
fnt: TsFont;
|
||||||
actual, expected: String;
|
actual, expected: String;
|
||||||
i: Integer;
|
i: Integer;
|
||||||
|
palette: TsPalette;
|
||||||
begin
|
begin
|
||||||
|
palette := TsPalette.Create;
|
||||||
|
try
|
||||||
|
palette.AddBuiltinColors;
|
||||||
|
|
||||||
MyWorkbook := TsWorkbook.Create;
|
MyWorkbook := TsWorkbook.Create;
|
||||||
try
|
try
|
||||||
MyWorksheet:= MyWorkBook.AddWorksheet(SHEETNAME);
|
MyWorksheet:= MyWorkBook.AddWorksheet(SHEETNAME);
|
||||||
@ -1600,7 +1603,7 @@ begin
|
|||||||
begin
|
begin
|
||||||
MyWorksheet.WriteNumber(r, c, 123);
|
MyWorksheet.WriteNumber(r, c, 123);
|
||||||
MyWorksheet.WriteBackgroundColor(r, c, 0);
|
MyWorksheet.WriteBackgroundColor(r, c, 0);
|
||||||
MyWorksheet.WriteFont(r, c, 'Times New Roman', FontSizes[r], [], c); // Biff2 has only 8 colors --> re-use the black!
|
MyWorksheet.WriteFont(r, c, 'Times New Roman', FontSizes[r], [], palette[c]); // Biff2 has only 8 colors --> re-use the black!
|
||||||
// --> in total 64 combinations
|
// --> in total 64 combinations
|
||||||
end;
|
end;
|
||||||
TempFile:=NewTempFile;
|
TempFile:=NewTempFile;
|
||||||
@ -1631,7 +1634,7 @@ begin
|
|||||||
actual := FloatToStr(fnt.Size);
|
actual := FloatToStr(fnt.Size);
|
||||||
CheckEquals(expected, actual,
|
CheckEquals(expected, actual,
|
||||||
'Font size mismatch, cell '+ CellNotation(MyWorksheet, r, c));
|
'Font size mismatch, cell '+ CellNotation(MyWorksheet, r, c));
|
||||||
expected := IntToStr(c);
|
expected := IntToStr(palette[c]);
|
||||||
actual := IntToStr(fnt.Color);
|
actual := IntToStr(fnt.Color);
|
||||||
CheckEquals(expected, actual,
|
CheckEquals(expected, actual,
|
||||||
'Font color mismatch, cell '+ CellNotation(MyWorksheet, r, c));
|
'Font color mismatch, cell '+ CellNotation(MyWorksheet, r, c));
|
||||||
@ -1641,6 +1644,10 @@ begin
|
|||||||
MyWorkbook.Free;
|
MyWorkbook.Free;
|
||||||
DeleteFile(TempFile);
|
DeleteFile(TempFile);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
finally
|
||||||
|
palette.Free;
|
||||||
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
|
||||||
|
@ -63,17 +63,20 @@ type
|
|||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
// For BIFF8 format, writes all background colors in A1..A16
|
// For BIFF8 format, writes all background colors in A1..A16
|
||||||
procedure TestBiff8CellBackgroundColor;
|
procedure TestBiff8CellBackgroundColor;
|
||||||
|
|
||||||
|
procedure TestNumberFormats;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
implementation
|
implementation
|
||||||
|
|
||||||
uses
|
uses
|
||||||
fpstypes, fpsUtils, rpnFormulaUnit;
|
fpstypes, fpsUtils, fpsPalette, rpnFormulaUnit;
|
||||||
|
|
||||||
const
|
const
|
||||||
COLORSHEETNAME='color_sheet'; //for background color tests
|
COLORSHEETNAME='color_sheet'; //for background color tests
|
||||||
RPNSHEETNAME='rpn_formula_sheet'; //for rpn formula tests
|
RPNSHEETNAME='rpn_formula_sheet'; //for rpn formula tests
|
||||||
FORMULASHEETNAME='formula_sheet'; // for string formula tests
|
FORMULASHEETNAME='formula_sheet'; // for string formula tests
|
||||||
|
NUMBERFORMATSHEETNAME='number format sheet'; // for number format tests
|
||||||
OUTPUT_FORMAT = sfExcel8; //change manually if you want to test different formats. To do: automatically output all formats
|
OUTPUT_FORMAT = sfExcel8; //change manually if you want to test different formats. To do: automatically output all formats
|
||||||
|
|
||||||
var
|
var
|
||||||
@ -184,6 +187,7 @@ var
|
|||||||
Cell : PCell;
|
Cell : PCell;
|
||||||
i: cardinal;
|
i: cardinal;
|
||||||
RowOffset: cardinal;
|
RowOffset: cardinal;
|
||||||
|
palette: TsPalette;
|
||||||
begin
|
begin
|
||||||
if OUTPUT_FORMAT <> sfExcel8 then
|
if OUTPUT_FORMAT <> sfExcel8 then
|
||||||
Ignore('This test only applies to BIFF8 XLS output format.');
|
Ignore('This test only applies to BIFF8 XLS output format.');
|
||||||
@ -196,15 +200,74 @@ begin
|
|||||||
if Workbook = nil then
|
if Workbook = nil then
|
||||||
Workbook := TsWorkbook.Create;
|
Workbook := TsWorkbook.Create;
|
||||||
|
|
||||||
|
palette := TsPalette.Create;
|
||||||
|
try
|
||||||
|
palette.AddBuiltinColors;
|
||||||
|
palette.AddExcelColors;
|
||||||
|
|
||||||
Worksheet := Workbook.AddWorksheet(COLORSHEETNAME);
|
Worksheet := Workbook.AddWorksheet(COLORSHEETNAME);
|
||||||
WorkSheet.WriteUTF8Text(0,1,'TSpreadManualTests.TestBiff8CellBackgroundColor');
|
WorkSheet.WriteUTF8Text(0, 1, 'TSpreadManualTests.TestBiff8CellBackgroundColor');
|
||||||
RowOffset := 1;
|
RowOffset := 1;
|
||||||
for i:=0 to Workbook.GetPaletteSize-1 do begin
|
for i:=0 to palette.Count-1 do begin
|
||||||
WorkSheet.WriteUTF8Text(i+RowOffset,0,'BACKGROUND COLOR TEST');
|
cell := WorkSheet.WriteUTF8Text(i+RowOffset,0,'BACKGROUND COLOR TEST');
|
||||||
Cell := Worksheet.GetCell(i+RowOffset, 0);
|
Worksheet.WriteBackgroundColor(Cell, palette[i]);
|
||||||
Worksheet.WriteBackgroundColor(Cell, TsColor(i));
|
Worksheet.WriteFontColor(cell, HighContrastColor(palette[i]));
|
||||||
WorkSheet.WriteUTF8Text(i+RowOffset,1,'Cell to the left should be '+Workbook.GetColorName(i)+'. Please check.');
|
WorkSheet.WriteUTF8Text(i+RowOffset,1,'Cell to the left should be '+GetColorName(palette[i])+'. Please check.');
|
||||||
end;
|
end;
|
||||||
|
Worksheet.WriteColWidth(0, 30);
|
||||||
|
Worksheet.WriteColWidth(1, 60);
|
||||||
|
finally
|
||||||
|
palette.Free;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
|
procedure TSpreadManualTests.TestNumberFormats();
|
||||||
|
// source: forum post
|
||||||
|
// http://forum.lazarus.freepascal.org/index.php/topic,19887.msg134114.html#msg134114
|
||||||
|
// possible fix for values there too
|
||||||
|
const
|
||||||
|
Values: Array[0..4] of Double = (12000.34, -12000.34, 0.0001234, -0.0001234, 0.0);
|
||||||
|
FormatStrings: array[0..24] of String = (
|
||||||
|
'General',
|
||||||
|
'0', '0.00', '0.0000',
|
||||||
|
'#,##0', '#,##0.00', '#,##0.0000',
|
||||||
|
'0%', '0.00%', '0.0000%',
|
||||||
|
'0,', '0.00,', '0.0000,',
|
||||||
|
'0E+00', '0.00E+00', '0.0000E+00',
|
||||||
|
'0E-00', '0.00E-00', '0.0000E-00',
|
||||||
|
'# ?/?', '# ??/??', '# ????/????',
|
||||||
|
'?/?', '??/??', '????/????'
|
||||||
|
);
|
||||||
|
var
|
||||||
|
Worksheet: TsWorksheet;
|
||||||
|
Cell : PCell;
|
||||||
|
i: cardinal;
|
||||||
|
r, c: Cardinal;
|
||||||
|
palette: TsPalette;
|
||||||
|
nfs: String;
|
||||||
|
begin
|
||||||
|
if OUTPUT_FORMAT <> sfExcel8 then
|
||||||
|
Ignore('This test only applies to BIFF8 XLS output format.');
|
||||||
|
|
||||||
|
// No worksheets in BIFF2. Since main interest is here in formulas we just jump
|
||||||
|
// off here - need to change this in the future...
|
||||||
|
if OUTPUT_FORMAT = sfExcel2 then
|
||||||
|
Ignore('BIFF2 does not support worksheets. Ignoring manual tests for now');
|
||||||
|
|
||||||
|
if Workbook = nil then
|
||||||
|
Workbook := TsWorkbook.Create;
|
||||||
|
|
||||||
|
Worksheet := Workbook.AddWorksheet(NUMBERFORMATSHEETNAME);
|
||||||
|
WorkSheet.WriteUTF8Text(0, 1, 'Number format tests');
|
||||||
|
|
||||||
|
for r:=0 to High(FormatStrings) do
|
||||||
|
begin
|
||||||
|
Worksheet.WriteUTF8Text(r+2, 0, FormatStrings[r]);
|
||||||
|
for c:=0 to High(Values) do
|
||||||
|
Worksheet.WriteNumber(r+2, c+1, values[c], nfCustom, FormatStrings[r]);
|
||||||
|
end;
|
||||||
|
|
||||||
|
Worksheet.WriteColWidth(0, 20);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{$IFDEF FPSPREAD_HAS_NEWRPNSUPPORT}
|
{$IFDEF FPSPREAD_HAS_NEWRPNSUPPORT}
|
||||||
|
@ -270,7 +270,8 @@ begin
|
|||||||
if copy(lFormatstr, 1, 6) = 'color:' then
|
if copy(lFormatstr, 1, 6) = 'color:' then
|
||||||
begin
|
begin
|
||||||
lColorstr := Copy(lFormatstr, 7, Length(lFormatStr));
|
lColorstr := Copy(lFormatstr, 7, Length(lFormatStr));
|
||||||
lCurBackgroundColor := FWorkbook.AddColorToPalette(HTMLColorStrToColor(lColorStr));
|
lCurBackgroundColor := HTMLColorStrToColor(lColorStr);
|
||||||
|
// lCurBackgroundColor := FWorkbook.AddColorToPalette(HTMLColorStrToColor(lColorStr));
|
||||||
lUseBackgroundColor := True;
|
lUseBackgroundColor := True;
|
||||||
lFormatStr := '';
|
lFormatStr := '';
|
||||||
end;
|
end;
|
||||||
@ -381,7 +382,8 @@ procedure TsWikiTableWriter.WriteToStrings_WikiMedia(AStrings: TStrings);
|
|||||||
clr := fmt^.BorderStyles[ABorder].Color;
|
clr := fmt^.BorderStyles[ABorder].Color;
|
||||||
Result := Format('border-%s:%s', [BORDERNAMES[ABorder], LINESTYLES[ls]]);
|
Result := Format('border-%s:%s', [BORDERNAMES[ABorder], LINESTYLES[ls]]);
|
||||||
if clr <> scBlack then
|
if clr <> scBlack then
|
||||||
Result := Result + ' ' + FWorkbook.GetPaletteColorAsHTMLStr(clr) + '; ';
|
Result := Result + ' ' + ColorToHTMLColorStr(clr) + '; ';
|
||||||
|
// Result := Result + ' ' + FWorkbook.GetPaletteColorAsHTMLStr(clr) + '; ';
|
||||||
end;
|
end;
|
||||||
|
|
||||||
const
|
const
|
||||||
@ -499,8 +501,10 @@ begin
|
|||||||
begin
|
begin
|
||||||
lCurColor := FWorksheet.ReadBackgroundColor(lCell);
|
lCurColor := FWorksheet.ReadBackgroundColor(lCell);
|
||||||
lStyleStr := Format('background-color:%s;color:%s;', [
|
lStyleStr := Format('background-color:%s;color:%s;', [
|
||||||
FWorkbook.GetPaletteColorAsHTMLStr(lCurColor),
|
ColorToHTMLColorStr(lCurColor),
|
||||||
FWorkbook.GetPaletteColorAsHTMLStr(lFont.Color)
|
ColorToHTMLColorStr(lFont.Color)
|
||||||
|
// FWorkbook.GetPaletteColorAsHTMLStr(lCurColor),
|
||||||
|
// FWorkbook.GetPaletteColorAsHTMLStr(lFont.Color)
|
||||||
]);
|
]);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
@ -144,7 +144,7 @@ var
|
|||||||
|
|
||||||
var
|
var
|
||||||
{ the palette of the default BIFF2 colors as "big-endian color" values }
|
{ the palette of the default BIFF2 colors as "big-endian color" values }
|
||||||
PALETTE_BIFF2: array[$0..$07] of TsColorValue = (
|
PALETTE_BIFF2: array[$0..$07] of TsColor = (
|
||||||
$000000, // $00: black
|
$000000, // $00: black
|
||||||
$FFFFFF, // $01: white
|
$FFFFFF, // $01: white
|
||||||
$FF0000, // $02: red
|
$FF0000, // $02: red
|
||||||
@ -159,7 +159,7 @@ var
|
|||||||
implementation
|
implementation
|
||||||
|
|
||||||
uses
|
uses
|
||||||
Math, fpsStrings, fpsReaderWriter;
|
Math, fpsStrings, fpsReaderWriter, fpsPalette;
|
||||||
|
|
||||||
const
|
const
|
||||||
{ Excel record IDs }
|
{ Excel record IDs }
|
||||||
@ -419,8 +419,12 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TsSpreadBIFF2Reader.ReadFONTCOLOR(AStream: TStream);
|
procedure TsSpreadBIFF2Reader.ReadFONTCOLOR(AStream: TStream);
|
||||||
|
var
|
||||||
|
lColor: Word;
|
||||||
begin
|
begin
|
||||||
FFont.Color := WordLEToN(AStream.ReadWord);
|
lColor := WordLEToN(AStream.ReadWord); // Palette index
|
||||||
|
FFont.Color := IfThen(lColor = SYS_DEFAULT_WINDOW_TEXT_COLOR,
|
||||||
|
scBlack, FPalette[lColor]);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
@ -1533,7 +1537,7 @@ begin
|
|||||||
AStream.WriteWord(WordToLE(2));
|
AStream.WriteWord(WordToLE(2));
|
||||||
|
|
||||||
{ Font color index, only first 8 palette entries allowed! }
|
{ Font color index, only first 8 palette entries allowed! }
|
||||||
AStream.WriteWord(WordToLE(word(FixColor(font.Color))));
|
AStream.WriteWord(WordToLE(PaletteIndex(font.Color)));
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
@ -1987,6 +1991,6 @@ initialization
|
|||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
|
|
||||||
RegisterSpreadFormat(TsSpreadBIFF2Reader, TsSpreadBIFF2Writer, sfExcel2);
|
RegisterSpreadFormat(TsSpreadBIFF2Reader, TsSpreadBIFF2Writer, sfExcel2);
|
||||||
MakeLEPalette(@PALETTE_BIFF2, Length(PALETTE_BIFF2));
|
MakeLEPalette(PALETTE_BIFF2);
|
||||||
|
|
||||||
end.
|
end.
|
||||||
|
@ -77,6 +77,7 @@ type
|
|||||||
FWorksheetNames: TStringList;
|
FWorksheetNames: TStringList;
|
||||||
FCurrentWorksheet: Integer;
|
FCurrentWorksheet: Integer;
|
||||||
protected
|
protected
|
||||||
|
procedure PopulatePalette; override;
|
||||||
{ Record writing methods }
|
{ Record writing methods }
|
||||||
procedure ReadBoundsheet(AStream: TStream);
|
procedure ReadBoundsheet(AStream: TStream);
|
||||||
procedure ReadFONT(const AStream: TStream);
|
procedure ReadFONT(const AStream: TStream);
|
||||||
@ -137,7 +138,7 @@ var
|
|||||||
|
|
||||||
var
|
var
|
||||||
// the palette of the default BIFF5 colors as "big-endian color" values
|
// the palette of the default BIFF5 colors as "big-endian color" values
|
||||||
PALETTE_BIFF5: array[$00..$3F] of TsColorValue = (
|
PALETTE_BIFF5: array[$00..$3F] of TsColor = (
|
||||||
$000000, // $00: black
|
$000000, // $00: black
|
||||||
$FFFFFF, // $01: white
|
$FFFFFF, // $01: white
|
||||||
$FF0000, // $02: red
|
$FF0000, // $02: red
|
||||||
@ -213,7 +214,7 @@ var
|
|||||||
implementation
|
implementation
|
||||||
|
|
||||||
uses
|
uses
|
||||||
fpsStrings, fpsStreams, fpsReaderWriter;
|
Math, fpsStrings, fpsStreams, fpsReaderWriter, fpsPalette;
|
||||||
|
|
||||||
const
|
const
|
||||||
{ Excel record IDs }
|
{ Excel record IDs }
|
||||||
@ -337,6 +338,15 @@ type
|
|||||||
|
|
||||||
{ TsSpreadBIFF5Reader }
|
{ TsSpreadBIFF5Reader }
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Populates the reader's default palette using the BIFF5 default colors.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsSpreadBIFF5Reader.PopulatePalette;
|
||||||
|
begin
|
||||||
|
FPalette.Clear;
|
||||||
|
FPalette.UseColors(PALETTE_BIFF5);
|
||||||
|
end;
|
||||||
|
|
||||||
procedure TsSpreadBIFF5Reader.ReadWorkbookGlobals(AStream: TStream);
|
procedure TsSpreadBIFF5Reader.ReadWorkbookGlobals(AStream: TStream);
|
||||||
var
|
var
|
||||||
SectionEOF: Boolean = False;
|
SectionEOF: Boolean = False;
|
||||||
@ -370,6 +380,9 @@ begin
|
|||||||
// Check for the end of the file
|
// Check for the end of the file
|
||||||
if AStream.Position >= AStream.Size then SectionEOF := True;
|
if AStream.Position >= AStream.Size then SectionEOF := True;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
// Convert palette indexes to rgb colors
|
||||||
|
FixColors;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TsSpreadBIFF5Reader.ReadWorksheet(AStream: TStream);
|
procedure TsSpreadBIFF5Reader.ReadWorksheet(AStream: TStream);
|
||||||
@ -606,8 +619,7 @@ procedure TsSpreadBIFF5Reader.ReadXF(AStream: TStream);
|
|||||||
var
|
var
|
||||||
rec: TBIFF5_XFRecord;
|
rec: TBIFF5_XFRecord;
|
||||||
fmt: TsCellFormat;
|
fmt: TsCellFormat;
|
||||||
// nfidx: Integer;
|
i, cidx: Integer;
|
||||||
i: Integer;
|
|
||||||
nfparams: TsNumFormatParams;
|
nfparams: TsNumFormatParams;
|
||||||
nfs: String;
|
nfs: String;
|
||||||
b: Byte;
|
b: Byte;
|
||||||
@ -646,28 +658,7 @@ begin
|
|||||||
Include(fmt.UsedFormattingFields, uffNumberFormat);
|
Include(fmt.UsedFormattingFields, uffNumberFormat);
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
{
|
|
||||||
// Number format index
|
|
||||||
nfparams := Workbook.GetNumberFormat(rec.NumFormatIndex);
|
|
||||||
nfs := nfParams.NumFormatStr[nfdDefault];
|
|
||||||
if nfs <> '' then begin
|
|
||||||
fmt.NumberFormatIndex := Workbook.AddNumberFormat(nfs);
|
|
||||||
fmt.NumberFormat := nfParams.NumFormat;
|
|
||||||
fmt.NumberFormatStr := nfs;
|
|
||||||
Include(fmt.UsedFormattingFields, uffNumberFormat);
|
|
||||||
end;
|
|
||||||
}
|
|
||||||
{
|
|
||||||
nfidx := WordLEToN(rec.NumFormatIndex);
|
|
||||||
i := NumFormatList.FindByIndex(nfidx);
|
|
||||||
if i > -1 then begin
|
|
||||||
nfdata := NumFormatList.Items[i];
|
|
||||||
fmt.NumberFormat := nfdata.NumFormat;
|
|
||||||
fmt.NumberFormatStr := nfdata.FormatString;
|
|
||||||
if nfdata.NumFormat <> nfGeneral then
|
|
||||||
Include(fmt.UsedFormattingFields, uffNumberFormat);
|
|
||||||
end;
|
|
||||||
}
|
|
||||||
// Horizontal text alignment
|
// Horizontal text alignment
|
||||||
b := rec.Align_TextBreak AND MASK_XF_HOR_ALIGN;
|
b := rec.Align_TextBreak AND MASK_XF_HOR_ALIGN;
|
||||||
if (b <= ord(High(TsHorAlignment))) then
|
if (b <= ord(High(TsHorAlignment))) then
|
||||||
@ -742,10 +733,17 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
// Border line colors
|
// Border line colors
|
||||||
fmt.BorderStyles[cbWest].Color := (rec.Border_BkGr2 and MASK_XF_BORDER_LEFT_COLOR) shr 16;
|
// NOTE: It is possible that the palette is not yet known at this moment.
|
||||||
fmt.BorderStyles[cbEast].Color := (rec.Border_BkGr2 and MASK_XF_BORDER_RIGHT_COLOR) shr 23;
|
// Therefore we store the palette index encoded into the colors.
|
||||||
fmt.BorderStyles[cbNorth].Color := (rec.Border_BkGr2 and MASK_XF_BORDER_TOP_COLOR) shr 9;
|
// They will be converted to rgb in "FixColors".
|
||||||
fmt.BorderStyles[cbSouth].Color := (rec.Border_BkGr1 and MASK_XF_BORDER_BOTTOM_COLOR) shr 25;
|
cidx := (rec.Border_BkGr2 and MASK_XF_BORDER_LEFT_COLOR) shr 16;
|
||||||
|
fmt.BorderStyles[cbWest].Color := IfThen(cidx >= 64, scBlack, SetAsPaletteIndex(cidx));
|
||||||
|
cidx := (rec.Border_BkGr2 and MASK_XF_BORDER_RIGHT_COLOR) shr 23;
|
||||||
|
fmt.BorderStyles[cbEast].Color := IfThen(cidx >= 64, scBlack, SetAsPaletteIndex(cidx));
|
||||||
|
cidx := (rec.Border_BkGr2 and MASK_XF_BORDER_TOP_COLOR) shr 9;
|
||||||
|
fmt.BorderStyles[cbNorth].Color := IfThen(cidx >= 64, scBlack, SetAsPaletteIndex(cidx));
|
||||||
|
cidx := (rec.Border_BkGr1 and MASK_XF_BORDER_BOTTOM_COLOR) shr 25;
|
||||||
|
fmt.BorderStyles[cbSouth].Color := IfThen(cidx >= 64, scBlack, SetAsPaletteIndex(cidx));
|
||||||
|
|
||||||
// Background
|
// Background
|
||||||
fill := (rec.Border_BkGr1 and MASK_XF_BKGR_FILLPATTERN) shr 16;
|
fill := (rec.Border_BkGr1 and MASK_XF_BKGR_FILLPATTERN) shr 16;
|
||||||
@ -758,12 +756,12 @@ begin
|
|||||||
// Fill style
|
// Fill style
|
||||||
fmt.Background.Style := fs;
|
fmt.Background.Style := fs;
|
||||||
// Pattern color
|
// Pattern color
|
||||||
fmt.Background.FgColor := rec.Border_BkGr1 and MASK_XF_BKGR_PATTERN_COLOR;
|
cidx := rec.Border_BkGr1 and MASK_XF_BKGR_PATTERN_COLOR; // Palette index
|
||||||
if fmt.Background.FgColor = SYS_DEFAULT_FOREGROUND_COLOR then
|
fmt.Background.FgColor := IfThen(cidx = SYS_DEFAULT_FOREGROUND_COLOR,
|
||||||
fmt.Background.FgColor := scBlack;
|
scBlack, SetAsPaletteIndex(cidx));
|
||||||
fmt.Background.BgColor := (rec.Border_BkGr1 and MASK_XF_BKGR_BACKGROUND_COLOR) shr 7;
|
cidx := (rec.Border_BkGr1 and MASK_XF_BKGR_BACKGROUND_COLOR) shr 7;
|
||||||
if fmt.Background.BgColor = SYS_DEFAULT_BACKGROUND_COLOR then
|
fmt.Background.BgColor := IfThen(cidx = SYS_DEFAULT_BACKGROUND_COLOR,
|
||||||
fmt.Background.BgColor := scTransparent;
|
scTransparent, SetAsPaletteIndex(cidx));
|
||||||
Include(fmt.UsedFormattingFields, uffBackground);
|
Include(fmt.UsedFormattingFields, uffBackground);
|
||||||
break;
|
break;
|
||||||
end;
|
end;
|
||||||
@ -785,14 +783,12 @@ begin
|
|||||||
BIFF5EOF := False;
|
BIFF5EOF := False;
|
||||||
|
|
||||||
{ Read workbook globals }
|
{ Read workbook globals }
|
||||||
|
|
||||||
ReadWorkbookGlobals(AStream);
|
ReadWorkbookGlobals(AStream);
|
||||||
|
|
||||||
// Check for the end of the file
|
{ Check for the end of the file }
|
||||||
if AStream.Position >= AStream.Size then BIFF5EOF := True;
|
if AStream.Position >= AStream.Size then BIFF5EOF := True;
|
||||||
|
|
||||||
{ Now read all worksheets }
|
{ Now read all worksheets }
|
||||||
|
|
||||||
while (not BIFF5EOF) do
|
while (not BIFF5EOF) do
|
||||||
begin
|
begin
|
||||||
ReadWorksheet(AStream);
|
ReadWorksheet(AStream);
|
||||||
@ -807,11 +803,7 @@ begin
|
|||||||
// at the end of the file.
|
// at the end of the file.
|
||||||
end;
|
end;
|
||||||
|
|
||||||
if not FPaletteFound then
|
{ Finalization }
|
||||||
FWorkbook.UsePalette(@PALETTE_BIFF5, Length(PALETTE_BIFF5));
|
|
||||||
|
|
||||||
{ Finalizations }
|
|
||||||
|
|
||||||
FWorksheetNames.Free;
|
FWorksheetNames.Free;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -840,10 +832,21 @@ begin
|
|||||||
if lOptions and $0004 <> 0 then Include(font.Style, fssUnderline);
|
if lOptions and $0004 <> 0 then Include(font.Style, fssUnderline);
|
||||||
if lOptions and $0008 <> 0 then Include(font.Style, fssStrikeout);
|
if lOptions and $0008 <> 0 then Include(font.Style, fssStrikeout);
|
||||||
|
|
||||||
{ Colour index }
|
{ Color index }
|
||||||
|
// The problem is that the palette is loaded after the font list; therefore
|
||||||
|
// we do not know the rgb color of the font here. We store the palette index
|
||||||
|
// ("SetAsPaletteIndex") and replace it by the rgb color at the end of the
|
||||||
|
// workbook globals records. As an indicator that the font does not yet
|
||||||
|
// contain an rgb color a control bit is set in the high-byte of the TsColor.
|
||||||
lColor := WordLEToN(AStream.ReadWord);
|
lColor := WordLEToN(AStream.ReadWord);
|
||||||
//font.Color := TsColor(lColor - 8); // Palette colors have an offset 8
|
if lColor < 8 then
|
||||||
font.Color := tsColor(lColor);
|
// Use built-in colors directly otherwise the Workbook's FindFont would not find the font in ReadXF
|
||||||
|
font.Color := FPalette[lColor]
|
||||||
|
else
|
||||||
|
if lColor = SYS_DEFAULT_WINDOW_TEXT_COLOR then
|
||||||
|
font.Color := scBlack
|
||||||
|
else
|
||||||
|
font.Color := SetAsPaletteIndex(lColor);
|
||||||
|
|
||||||
{ Font weight }
|
{ Font weight }
|
||||||
lWeight := WordLEToN(AStream.ReadWord);
|
lWeight := WordLEToN(AStream.ReadWord);
|
||||||
@ -1197,6 +1200,7 @@ procedure TsSpreadBIFF5Writer.WriteFont(AStream: TStream; AFont: TsFont);
|
|||||||
var
|
var
|
||||||
Len: Byte;
|
Len: Byte;
|
||||||
optn: Word;
|
optn: Word;
|
||||||
|
cidx: Integer;
|
||||||
begin
|
begin
|
||||||
if AFont = nil then // this happens for FONT4 in case of BIFF
|
if AFont = nil then // this happens for FONT4 in case of BIFF
|
||||||
exit;
|
exit;
|
||||||
@ -1222,8 +1226,8 @@ begin
|
|||||||
if fssStrikeout in AFont.Style then optn := optn or $0008;
|
if fssStrikeout in AFont.Style then optn := optn or $0008;
|
||||||
AStream.WriteWord(WordToLE(optn));
|
AStream.WriteWord(WordToLE(optn));
|
||||||
|
|
||||||
{ Colour index }
|
{ Color index }
|
||||||
AStream.WriteWord(WordToLE(ord(FixColor(AFont.Color))));
|
AStream.WriteWord(WordToLE(PaletteIndex(AFont.Color)));
|
||||||
|
|
||||||
{ Font weight }
|
{ Font weight }
|
||||||
if fssBold in AFont.Style then
|
if fssBold in AFont.Style then
|
||||||
@ -1574,19 +1578,19 @@ begin
|
|||||||
begin
|
begin
|
||||||
if (AFormatRecord^.Background.FgColor = scTransparent)
|
if (AFormatRecord^.Background.FgColor = scTransparent)
|
||||||
then dw1 := dw1 or (SYS_DEFAULT_FOREGROUND_COLOR and $0000007F)
|
then dw1 := dw1 or (SYS_DEFAULT_FOREGROUND_COLOR and $0000007F)
|
||||||
else dw1 := dw1 or (FixColor(AFormatRecord^.Background.FgColor) and $0000007F);
|
else dw1 := dw1 or (PaletteIndex(AFormatRecord^.Background.FgColor) and $0000007F);
|
||||||
if AFormatRecord^.Background.BgColor = scTransparent
|
if AFormatRecord^.Background.BgColor = scTransparent
|
||||||
then dw1 := dw1 or (SYS_DEFAULT_BACKGROUND_COLOR shl 7)
|
then dw1 := dw1 or (SYS_DEFAULT_BACKGROUND_COLOR shl 7)
|
||||||
else dw1 := dw1 or (FixColor(AFormatRecord^.Background.BgColor) shl 7);
|
else dw1 := dw1 or (PaletteIndex(AFormatRecord^.Background.BgColor) shl 7);
|
||||||
dw1 := dw1 or (MASK_XF_FILL_PATT[AFormatRecord^.Background.Style] shl 16);
|
dw1 := dw1 or (MASK_XF_FILL_PATT[AFormatRecord^.Background.Style] shl 16);
|
||||||
end;
|
end;
|
||||||
// Border lines
|
// Border lines
|
||||||
if (uffBorder in AFormatRecord^.UsedFormattingFields) then
|
if (uffBorder in AFormatRecord^.UsedFormattingFields) then
|
||||||
begin
|
begin
|
||||||
dw1 := dw1 or (AFormatRecord^.BorderStyles[cbSouth].Color shl 25); // Bottom line color
|
dw1 := dw1 or PaletteIndex(AFormatRecord^.BorderStyles[cbSouth].Color) shl 25; // Bottom line color
|
||||||
dw2 := (FixColor(AFormatRecord^.BorderStyles[cbNorth].Color) shl 9) or // Top line color
|
dw2 := (PaletteIndex(AFormatRecord^.BorderStyles[cbNorth].Color) shl 9) or // Top line color
|
||||||
(FixColor(AFormatRecord^.BorderStyles[cbWest].Color) shl 16) or // Left line color
|
(PaletteIndex(AFormatRecord^.BorderStyles[cbWest].Color) shl 16) or // Left line color
|
||||||
(FixColor(AFormatRecord^.BorderStyles[cbEast].Color) shl 23); // Right line color
|
(PaletteIndex(AFormatRecord^.BorderStyles[cbEast].Color) shl 23); // Right line color
|
||||||
if cbSouth in AFormatRecord^.Border then
|
if cbSouth in AFormatRecord^.Border then
|
||||||
dw1 := dw1 or ((DWord(AFormatRecord^.BorderStyles[cbSouth].LineStyle)+1) shl 22);
|
dw1 := dw1 or ((DWord(AFormatRecord^.BorderStyles[cbSouth].LineStyle)+1) shl 22);
|
||||||
if cbNorth in AFormatRecord^.Border then
|
if cbNorth in AFormatRecord^.Border then
|
||||||
@ -1612,7 +1616,7 @@ initialization
|
|||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
|
|
||||||
RegisterSpreadFormat(TsSpreadBIFF5Reader, TsSpreadBIFF5Writer, sfExcel5);
|
RegisterSpreadFormat(TsSpreadBIFF5Reader, TsSpreadBIFF5Writer, sfExcel5);
|
||||||
MakeLEPalette(@PALETTE_BIFF5, Length(PALETTE_BIFF5));
|
MakeLEPalette(PALETTE_BIFF5);
|
||||||
|
|
||||||
end.
|
end.
|
||||||
|
|
||||||
|
@ -84,6 +84,7 @@ type
|
|||||||
procedure ReadBoundsheet(AStream: TStream);
|
procedure ReadBoundsheet(AStream: TStream);
|
||||||
function ReadString(const AStream: TStream; const ALength: WORD): String;
|
function ReadString(const AStream: TStream; const ALength: WORD): String;
|
||||||
protected
|
protected
|
||||||
|
procedure PopulatePalette; override;
|
||||||
procedure ReadCONTINUE(const AStream: TStream);
|
procedure ReadCONTINUE(const AStream: TStream);
|
||||||
procedure ReadFONT(const AStream: TStream);
|
procedure ReadFONT(const AStream: TStream);
|
||||||
procedure ReadFORMAT(AStream: TStream); override;
|
procedure ReadFORMAT(AStream: TStream); override;
|
||||||
@ -181,7 +182,7 @@ var
|
|||||||
|
|
||||||
var
|
var
|
||||||
// the palette of the 64 default BIFF8 colors as "big-endian color" values
|
// the palette of the 64 default BIFF8 colors as "big-endian color" values
|
||||||
PALETTE_BIFF8: array[$00..$3F] of TsColorValue = (
|
PALETTE_BIFF8: array[$00..$3F] of TsColor = (
|
||||||
$000000, // $00: black // 8 built-in default colors
|
$000000, // $00: black // 8 built-in default colors
|
||||||
$FFFFFF, // $01: white
|
$FFFFFF, // $01: white
|
||||||
$FF0000, // $02: red
|
$FF0000, // $02: red
|
||||||
@ -191,72 +192,73 @@ var
|
|||||||
$FF00FF, // $06: magenta
|
$FF00FF, // $06: magenta
|
||||||
$00FFFF, // $07: cyan
|
$00FFFF, // $07: cyan
|
||||||
|
|
||||||
$000000, // $08: EGA black
|
$000000, // $08: EGA black 1
|
||||||
$FFFFFF, // $09: EGA white
|
$FFFFFF, // $09: EGA white 2
|
||||||
$FF0000, // $0A: EGA red
|
$FF0000, // $0A: EGA red 3
|
||||||
$00FF00, // $0B: EGA green
|
$00FF00, // $0B: EGA green 4
|
||||||
$0000FF, // $0C: EGA blue
|
$0000FF, // $0C: EGA blue 5
|
||||||
$FFFF00, // $0D: EGA yellow
|
$FFFF00, // $0D: EGA yellow 6
|
||||||
$FF00FF, // $0E: EGA magenta
|
$FF00FF, // $0E: EGA magenta 7 pink
|
||||||
$00FFFF, // $0F: EGA cyan
|
$00FFFF, // $0F: EGA cyan 8 turqoise
|
||||||
|
|
||||||
$800000, // $10: EGA dark red
|
$800000, // $10=16: EGA dark red 9
|
||||||
$008000, // $11: EGA dark green
|
$008000, // $11=17: EGA dark green 10
|
||||||
$000080, // $12: EGA dark blue
|
$000080, // $12=18: EGA dark blue 11
|
||||||
$808000, // $13: EGA olive
|
$808000, // $13=19: EGA olive 12 dark yellow
|
||||||
$800080, // $14: EGA purple
|
$800080, // $14=20: EGA purple 13 violet
|
||||||
$008080, // $15: EGA teal
|
$008080, // $15=21: EGA teal 14
|
||||||
$C0C0C0, // $16: EGA silver
|
$C0C0C0, // $16=22: EGA silver 15 gray 25%
|
||||||
$808080, // $17: EGA gray
|
$808080, // $17=23: EGA gray 16 gray 50%
|
||||||
$9999FF, // $18:
|
$9999FF, // $18=24: Periwinkle
|
||||||
$993366, // $19:
|
$993366, // $19=25: Plum
|
||||||
$FFFFCC, // $1A:
|
$FFFFCC, // $1A=26: Ivory
|
||||||
$CCFFFF, // $1B:
|
$CCFFFF, // $1B=27: Light turquoise
|
||||||
$660066, // $1C:
|
$660066, // $1C=28: Dark purple
|
||||||
$FF8080, // $1D:
|
$FF8080, // $1D=29: Coral
|
||||||
$0066CC, // $1E:
|
$0066CC, // $1E=30: Ocean blue
|
||||||
$CCCCFF, // $1F:
|
$CCCCFF, // $1F=31: Ice blue
|
||||||
|
|
||||||
$000080, // $20:
|
$000080, // $20=32: Navy (repeated)
|
||||||
$FF00FF, // $21:
|
$FF00FF, // $21=33: Pink (magenta repeated)
|
||||||
$FFFF00, // $22:
|
$FFFF00, // $22=34: Yellow (repeated)
|
||||||
$00FFFF, // $23:
|
$00FFFF, // $23=35: Turqoise (=cyan repeated)
|
||||||
$800080, // $24:
|
$800080, // $24=36: Purple (repeated)
|
||||||
$800000, // $25:
|
$800000, // $25=37: Dark red (repeated)
|
||||||
$008080, // $26:
|
$008080, // $26=38: Teal (repeated)
|
||||||
$0000FF, // $27:
|
$0000FF, // $27=39: Blue (repeated)
|
||||||
$00CCFF, // $28:
|
$00CCFF, // $28=40: Sky blue
|
||||||
$CCFFFF, // $29:
|
$CCFFFF, // $29=41: Light turquoise (repeated)
|
||||||
$CCFFCC, // $2A:
|
$CCFFCC, // $2A=42: Light green
|
||||||
$FFFF99, // $2B:
|
$FFFF99, // $2B=43: Light yellow
|
||||||
$99CCFF, // $2C:
|
$99CCFF, // $2C=44: Pale blue
|
||||||
$FF99CC, // $2D:
|
$FF99CC, // $2D=45: rose
|
||||||
$CC99FF, // $2E:
|
$CC99FF, // $2E=46: lavander
|
||||||
$FFCC99, // $2F:
|
$FFCC99, // $2F=47: tan
|
||||||
|
|
||||||
$3366FF, // $30:
|
$3366FF, // $30=48: Light blue
|
||||||
$33CCCC, // $31:
|
$33CCCC, // $31=49: Aqua
|
||||||
$99CC00, // $32:
|
$99CC00, // $32=50: Lime
|
||||||
$FFCC00, // $33:
|
$FFCC00, // $33=51: Gold
|
||||||
$FF9900, // $34:
|
$FF9900, // $34=52: Light orange
|
||||||
$FF6600, // $35:
|
$FF6600, // $35=53: Orange
|
||||||
$666699, // $36:
|
$666699, // $36=54: Blue gray
|
||||||
$969696, // $37:
|
$969696, // $37=55: Gray 40%
|
||||||
$003366, // $38:
|
$003366, // $38=56: Dark teal
|
||||||
$339966, // $39:
|
$339966, // $39=57: Sea green
|
||||||
$003300, // $3A:
|
$003300, // $3A=58: very dark green
|
||||||
$333300, // $3B:
|
$333300, // $3B=59: olive green
|
||||||
$993300, // $3C:
|
$993300, // $3C=60: brown
|
||||||
$993366, // $3D:
|
$993366, // $3D=61: plum
|
||||||
$333399, // $3E:
|
$333399, // $3E=62: indigo
|
||||||
$333333 // $3F:
|
$333333 // $3F=63: gray 80%
|
||||||
);
|
);
|
||||||
|
// color names according to http://dmcritchie.mvps.org/EXCEL/COLORS.HTM
|
||||||
|
|
||||||
implementation
|
implementation
|
||||||
|
|
||||||
uses
|
uses
|
||||||
Math, lconvencoding, LazFileUtils, URIParser,
|
Math, lconvencoding, LazFileUtils, URIParser,
|
||||||
fpsStrings, fpsStreams, fpsReaderWriter, fpsExprParser, xlsEscher;
|
fpsStrings, fpsStreams, fpsReaderWriter, fpsPalette, fpsExprParser, xlsEscher;
|
||||||
|
|
||||||
const
|
const
|
||||||
{ Excel record IDs }
|
{ Excel record IDs }
|
||||||
@ -429,10 +431,21 @@ begin
|
|||||||
inherited;
|
inherited;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ Reads a CONTINUE record. If the Flag "FCommentPending" is active then this
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Populates the reader's default palette using the BIFF8 default colors.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsSpreadBIFF8Reader.PopulatePalette;
|
||||||
|
begin
|
||||||
|
FPalette.Clear;
|
||||||
|
FPalette.UseColors(PALETTE_BIFF8);
|
||||||
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Reads a CONTINUE record. If the Flag "FCommentPending" is active then this
|
||||||
record contains the text of a comment assigned to a cell. The length of the
|
record contains the text of a comment assigned to a cell. The length of the
|
||||||
string is taken from the preceeding TXO record, and the ID of the comment is
|
string is taken from the preceeding TXO record, and the ID of the comment is
|
||||||
extracted in another preceeding record, an OBJ record. }
|
extracted in another preceeding record, an OBJ record.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
procedure TsSpreadBIFF8Reader.ReadCONTINUE(const AStream: TStream);
|
procedure TsSpreadBIFF8Reader.ReadCONTINUE(const AStream: TStream);
|
||||||
var
|
var
|
||||||
commentStr: String;
|
commentStr: String;
|
||||||
@ -657,6 +670,9 @@ begin
|
|||||||
// Check for the end of the file
|
// Check for the end of the file
|
||||||
if AStream.Position >= AStream.Size then SectionEOF := True;
|
if AStream.Position >= AStream.Size then SectionEOF := True;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
// Convert palette indexes to rgb colors
|
||||||
|
FixColors;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TsSpreadBIFF8Reader.ReadWorksheet(AStream: TStream);
|
procedure TsSpreadBIFF8Reader.ReadWorksheet(AStream: TStream);
|
||||||
@ -839,9 +855,6 @@ begin
|
|||||||
// at the end of the file.
|
// at the end of the file.
|
||||||
end;
|
end;
|
||||||
|
|
||||||
if not FPaletteFound then
|
|
||||||
FWorkbook.UsePalette(@PALETTE_BIFF8, Length(PALETTE_BIFF8));
|
|
||||||
|
|
||||||
{ Finalizations }
|
{ Finalizations }
|
||||||
FWorksheetNames.Free;
|
FWorksheetNames.Free;
|
||||||
end;
|
end;
|
||||||
@ -1206,6 +1219,7 @@ var
|
|||||||
nfs: String;
|
nfs: String;
|
||||||
nfParams: TsNumFormatParams;
|
nfParams: TsNumFormatParams;
|
||||||
i: Integer;
|
i: Integer;
|
||||||
|
iclr: Integer;
|
||||||
fnt: TsFont;
|
fnt: TsFont;
|
||||||
begin
|
begin
|
||||||
InitFormatRecord(fmt);
|
InitFormatRecord(fmt);
|
||||||
@ -1326,29 +1340,39 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
// Border line colors
|
// Border line colors
|
||||||
fmt.BorderStyles[cbWest].Color := (rec.Border_BkGr1 and MASK_XF_BORDER_LEFT_COLOR) shr 16;
|
// NOTE: It is possible that the palette is not yet known at this moment.
|
||||||
fmt.BorderStyles[cbEast].Color := (rec.Border_BkGr1 and MASK_XF_BORDER_RIGHT_COLOR) shr 23;
|
// Therefore we store the palette index encoded into the colorx.
|
||||||
fmt.BorderStyles[cbNorth].Color := (rec.Border_BkGr2 and MASK_XF_BORDER_TOP_COLOR);
|
// They will be converted to rgb in "FixColors".
|
||||||
fmt.BorderStyles[cbSouth].Color := (rec.Border_BkGr2 and MASK_XF_BORDER_BOTTOM_COLOR) shr 7;
|
iclr := (rec.Border_BkGr1 and MASK_XF_BORDER_LEFT_COLOR) shr 16;
|
||||||
fmt.BorderStyles[cbDiagUp].Color := (rec.Border_BkGr2 and MASK_XF_BORDER_DIAGONAL_COLOR) shr 14;
|
fmt.BorderStyles[cbWest].Color := IfThen(iclr >= 64, scBlack, SetAsPaletteIndex(iclr));
|
||||||
|
iclr := (rec.Border_BkGr1 and MASK_XF_BORDER_RIGHT_COLOR) shr 23;
|
||||||
|
fmt.BorderStyles[cbEast].Color := IfThen(iclr >= 64, scBlack, SetAsPaletteIndex(iclr));
|
||||||
|
iclr := (rec.Border_BkGr2 and MASK_XF_BORDER_TOP_COLOR);
|
||||||
|
fmt.BorderStyles[cbNorth].Color := IfThen(iclr >= 64, scBlack, SetAsPaletteIndex(iclr));
|
||||||
|
iclr := (rec.Border_BkGr2 and MASK_XF_BORDER_BOTTOM_COLOR) shr 7;
|
||||||
|
fmt.BorderStyles[cbSouth].Color := IfThen(iclr >= 64, scBlack, SetAsPaletteIndex(iclr));
|
||||||
|
iclr := (rec.Border_BkGr2 and MASK_XF_BORDER_DIAGONAL_COLOR) shr 14;
|
||||||
|
fmt.BorderStyles[cbDiagUp].Color := IfThen(iclr >= 64, scBlack, SetAsPaletteIndex(iclr));
|
||||||
fmt.BorderStyles[cbDiagDown].Color := fmt.BorderStyles[cbDiagUp].Color;
|
fmt.BorderStyles[cbDiagDown].Color := fmt.BorderStyles[cbDiagUp].Color;
|
||||||
|
|
||||||
// Background fill pattern and color
|
// Background fill pattern and color
|
||||||
fill := (rec.Border_BkGr2 and MASK_XF_BACKGROUND_PATTERN) shr 26;
|
fill := (rec.Border_BkGr2 and MASK_XF_BACKGROUND_PATTERN) shr 26;
|
||||||
if fill <> MASK_XF_FILL_PATT_EMPTY then
|
if fill <> MASK_XF_FILL_PATT_EMPTY then
|
||||||
begin
|
begin
|
||||||
|
rec.BkGr3 := DWordLEToN(rec.BkGr3);
|
||||||
for fs in TsFillStyle do
|
for fs in TsFillStyle do
|
||||||
if fill = MASK_XF_FILL_PATT[fs] then
|
if fill = MASK_XF_FILL_PATT[fs] then
|
||||||
begin
|
begin
|
||||||
rec.BkGr3 := DWordLEToN(rec.BkGr3);
|
|
||||||
// Pattern color
|
// Pattern color
|
||||||
fmt.Background.FgColor := rec.BkGr3 and $007F;
|
iclr := rec.BkGr3 and $007F;
|
||||||
if fmt.Background.FgColor = SYS_DEFAULT_FOREGROUND_COLOR then
|
fmt.Background.FgColor := IfThen(iclr = SYS_DEFAULT_FOREGROUND_COLOR,
|
||||||
fmt.Background.FgColor := scBlack;
|
scBlack, SetAsPaletteIndex(iclr));
|
||||||
|
|
||||||
// Background color
|
// Background color
|
||||||
fmt.Background.BgColor := (rec.BkGr3 and $3F80) shr 7;
|
iclr := (rec.BkGr3 and $3F80) shr 7;
|
||||||
if fmt.Background.BgColor = SYS_DEFAULT_BACKGROUND_COLOR then
|
fmt.Background.BgColor := IfThen(iclr = SYS_DEFAULT_BACKGROUND_COLOR,
|
||||||
fmt.Background.BgColor := scTransparent;
|
scTransparent, SetAsPaletteIndex(iclr));
|
||||||
|
|
||||||
// Fill style
|
// Fill style
|
||||||
fmt.Background.Style := fs;
|
fmt.Background.Style := fs;
|
||||||
Include(fmt.UsedFormattingFields, uffBackground);
|
Include(fmt.UsedFormattingFields, uffBackground);
|
||||||
@ -1374,7 +1398,7 @@ begin
|
|||||||
font := TsFont.Create;
|
font := TsFont.Create;
|
||||||
|
|
||||||
{ Height of the font in twips = 1/20 of a point }
|
{ Height of the font in twips = 1/20 of a point }
|
||||||
lHeight := WordLEToN(AStream.ReadWord); // WordToLE(200)
|
lHeight := WordLEToN(AStream.ReadWord);
|
||||||
font.Size := lHeight/20;
|
font.Size := lHeight/20;
|
||||||
|
|
||||||
{ Option flags }
|
{ Option flags }
|
||||||
@ -1385,10 +1409,21 @@ begin
|
|||||||
if lOptions and $0004 <> 0 then Include(font.Style, fssUnderline);
|
if lOptions and $0004 <> 0 then Include(font.Style, fssUnderline);
|
||||||
if lOptions and $0008 <> 0 then Include(font.Style, fssStrikeout);
|
if lOptions and $0008 <> 0 then Include(font.Style, fssStrikeout);
|
||||||
|
|
||||||
{ Colour index }
|
{ Color index }
|
||||||
|
// The problem is that the palette is loaded after the font list; therefore
|
||||||
|
// we do not know the rgb color of the font here. We store the palette index
|
||||||
|
// ("SetAsPaletteIndex") and replace it by the rgb color at the end of the
|
||||||
|
// workbook globals records. As an indicator that the font does not yet
|
||||||
|
// contain an rgb color a control bit is set in the high-byte of the TsColor.
|
||||||
lColor := WordLEToN(AStream.ReadWord);
|
lColor := WordLEToN(AStream.ReadWord);
|
||||||
//font.Color := TsColor(lColor - 8); // Palette colors have an offset 8
|
if lColor < 8 then
|
||||||
font.Color := tsColor(lColor);
|
// Use built-in colors directly otherwise the Workbook's FindFont would not find the font in ReadXF
|
||||||
|
font.Color := FPalette[lColor]
|
||||||
|
else
|
||||||
|
if lColor = SYS_DEFAULT_WINDOW_TEXT_COLOR then
|
||||||
|
font.Color := scBlack
|
||||||
|
else
|
||||||
|
font.Color := SetAsPaletteIndex(lColor);
|
||||||
|
|
||||||
{ Font weight }
|
{ Font weight }
|
||||||
lWeight := WordLEToN(AStream.ReadWord);
|
lWeight := WordLEToN(AStream.ReadWord);
|
||||||
@ -1983,8 +2018,8 @@ begin
|
|||||||
if fssStrikeout in AFont.Style then optn := optn or $0008;
|
if fssStrikeout in AFont.Style then optn := optn or $0008;
|
||||||
AStream.WriteWord(WordToLE(optn));
|
AStream.WriteWord(WordToLE(optn));
|
||||||
|
|
||||||
{ Colour index }
|
{ Color index }
|
||||||
AStream.WriteWord(WordToLE(ord(FixColor(AFont.Color))));
|
AStream.WriteWord(WordToLE(PaletteIndex(AFont.Color)));
|
||||||
|
|
||||||
{ Font weight }
|
{ Font weight }
|
||||||
if fssBold in AFont.Style then
|
if fssBold in AFont.Style then
|
||||||
@ -3005,8 +3040,8 @@ begin
|
|||||||
if (AFormatRecord <> nil) and (uffBorder in AFormatRecord^.UsedFormattingFields) then
|
if (AFormatRecord <> nil) and (uffBorder in AFormatRecord^.UsedFormattingFields) then
|
||||||
begin
|
begin
|
||||||
// Left and right line colors
|
// Left and right line colors
|
||||||
dw1 := AFormatRecord^.BorderStyles[cbWest].Color shl 16 +
|
dw1 := PaletteIndex(AFormatRecord^.BorderStyles[cbWest].Color) shl 16 +
|
||||||
AFormatRecord^.BorderStyles[cbEast].Color shl 23;
|
PaletteIndex(AFormatRecord^.BorderStyles[cbEast].Color) shl 23;
|
||||||
// Border line styles
|
// Border line styles
|
||||||
if cbWest in AFormatRecord^.Border then
|
if cbWest in AFormatRecord^.Border then
|
||||||
dw1 := dw1 or (DWord(AFormatRecord^.BorderStyles[cbWest].LineStyle)+1);
|
dw1 := dw1 or (DWord(AFormatRecord^.BorderStyles[cbWest].LineStyle)+1);
|
||||||
@ -3022,9 +3057,9 @@ begin
|
|||||||
dw1 := dw1 or $80000000;
|
dw1 := dw1 or $80000000;
|
||||||
|
|
||||||
// Top, bottom and diagonal line colors
|
// Top, bottom and diagonal line colors
|
||||||
dw2 := FixColor(AFormatRecord^.BorderStyles[cbNorth].Color) +
|
dw2 := PaletteIndex(AFormatRecord^.BorderStyles[cbNorth].Color) +
|
||||||
FixColor(AFormatRecord^.BorderStyles[cbSouth].Color) shl 7 +
|
PaletteIndex(AFormatRecord^.BorderStyles[cbSouth].Color) shl 7 +
|
||||||
FixColor(AFormatRecord^.BorderStyles[cbDiagUp].Color) shl 14;
|
PaletteIndex(AFormatRecord^.BorderStyles[cbDiagUp].Color) shl 14;
|
||||||
// In BIFF8 both diagonals have the same color - we use the color of the up-diagonal.
|
// In BIFF8 both diagonals have the same color - we use the color of the up-diagonal.
|
||||||
|
|
||||||
// Diagonal line style
|
// Diagonal line style
|
||||||
@ -3041,11 +3076,11 @@ begin
|
|||||||
// Pattern color
|
// Pattern color
|
||||||
if AFormatRecord^.Background.FgColor = scTransparent
|
if AFormatRecord^.Background.FgColor = scTransparent
|
||||||
then w3 := w3 or SYS_DEFAULT_FOREGROUND_COLOR
|
then w3 := w3 or SYS_DEFAULT_FOREGROUND_COLOR
|
||||||
else w3 := w3 or FixColor(AFormatRecord^.Background.FgColor);
|
else w3 := w3 or PaletteIndex(AFormatRecord^.Background.FgColor);
|
||||||
// Background color
|
// Background color
|
||||||
if AFormatRecord^.Background.BgColor = scTransparent
|
if AFormatRecord^.Background.BgColor = scTransparent
|
||||||
then w3 := w3 or SYS_DEFAULT_BACKGROUND_COLOR shl 7
|
then w3 := w3 or SYS_DEFAULT_BACKGROUND_COLOR shl 7
|
||||||
else w3 := w3 or (FixColor(AFormatRecord^.Background.BgColor) shl 7);
|
else w3 := w3 or (PaletteIndex(AFormatRecord^.Background.BgColor) shl 7);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
rec.Border_BkGr1 := DWordToLE(dw1);
|
rec.Border_BkGr1 := DWordToLE(dw1);
|
||||||
@ -3063,7 +3098,7 @@ initialization
|
|||||||
RegisterSpreadFormat(TsSpreadBIFF8Reader, TsSpreadBIFF8Writer, sfExcel8);
|
RegisterSpreadFormat(TsSpreadBIFF8Reader, TsSpreadBIFF8Writer, sfExcel8);
|
||||||
|
|
||||||
// Converts the palette to litte-endian
|
// Converts the palette to litte-endian
|
||||||
MakeLEPalette(@PALETTE_BIFF8, Length(PALETTE_BIFF8));
|
MakeLEPalette(PALETTE_BIFF8);
|
||||||
|
|
||||||
end.
|
end.
|
||||||
|
|
||||||
|
@ -11,7 +11,7 @@ interface
|
|||||||
|
|
||||||
uses
|
uses
|
||||||
Classes, SysUtils, DateUtils, lconvencoding,
|
Classes, SysUtils, DateUtils, lconvencoding,
|
||||||
fpsTypes, fpSpreadsheet, fpsUtils, fpsNumFormatParser,
|
fpsTypes, fpSpreadsheet, fpsUtils, fpsNumFormatParser, fpsPalette,
|
||||||
fpsReaderWriter;
|
fpsReaderWriter;
|
||||||
|
|
||||||
const
|
const
|
||||||
@ -211,7 +211,7 @@ const
|
|||||||
{ System colors, for BIFF5-BIFF8 }
|
{ System colors, for BIFF5-BIFF8 }
|
||||||
SYS_DEFAULT_FOREGROUND_COLOR = $0040;
|
SYS_DEFAULT_FOREGROUND_COLOR = $0040;
|
||||||
SYS_DEFAULT_BACKGROUND_COLOR = $0041;
|
SYS_DEFAULT_BACKGROUND_COLOR = $0041;
|
||||||
|
SYS_DEFAULT_WINDOW_TEXT_COLOR = $7FFF;
|
||||||
|
|
||||||
{ Error codes }
|
{ Error codes }
|
||||||
ERR_INTERSECTION_EMPTY = $00; // #NULL!
|
ERR_INTERSECTION_EMPTY = $00; // #NULL!
|
||||||
@ -348,11 +348,11 @@ type
|
|||||||
RecordSize: Word;
|
RecordSize: Word;
|
||||||
FCodepage: string; // in a format prepared for lconvencoding.ConvertEncoding
|
FCodepage: string; // in a format prepared for lconvencoding.ConvertEncoding
|
||||||
FDateMode: TDateMode;
|
FDateMode: TDateMode;
|
||||||
FPaletteFound: Boolean;
|
|
||||||
FIncompleteCell: PCell;
|
FIncompleteCell: PCell;
|
||||||
FIncompleteNote: String;
|
FIncompleteNote: String;
|
||||||
FIncompleteNoteLength: Word;
|
FIncompleteNoteLength: Word;
|
||||||
FFirstNumFormatIndexInFile: Integer;
|
FFirstNumFormatIndexInFile: Integer;
|
||||||
|
FPalette: TsPalette;
|
||||||
procedure AddBuiltinNumFormats; override;
|
procedure AddBuiltinNumFormats; override;
|
||||||
procedure ApplyCellFormatting(ACell: PCell; XFIndex: Word); virtual; //overload;
|
procedure ApplyCellFormatting(ACell: PCell; XFIndex: Word); virtual; //overload;
|
||||||
// Extracts a number out of an RK value
|
// Extracts a number out of an RK value
|
||||||
@ -360,9 +360,12 @@ type
|
|||||||
// Returns the numberformat for a given XF record
|
// Returns the numberformat for a given XF record
|
||||||
procedure ExtractNumberFormat(AXFIndex: WORD;
|
procedure ExtractNumberFormat(AXFIndex: WORD;
|
||||||
out ANumberFormat: TsNumberFormat; out ANumberFormatStr: String); virtual;
|
out ANumberFormat: TsNumberFormat; out ANumberFormatStr: String); virtual;
|
||||||
|
procedure FixColors;
|
||||||
// Tries to find if a number cell is actually a date/datetime/time cell and retrieves the value
|
// Tries to find if a number cell is actually a date/datetime/time cell and retrieves the value
|
||||||
function IsDateTime(Number: Double; ANumberFormat: TsNumberFormat;
|
function IsDateTime(Number: Double; ANumberFormat: TsNumberFormat;
|
||||||
ANumberFormatStr: String; out ADateTime: TDateTime): Boolean;
|
ANumberFormatStr: String; out ADateTime: TDateTime): Boolean;
|
||||||
|
procedure PopulatePalette; virtual;
|
||||||
|
|
||||||
// Here we can add reading of records which didn't change across BIFF5-8 versions
|
// Here we can add reading of records which didn't change across BIFF5-8 versions
|
||||||
// Read a blank cell
|
// Read a blank cell
|
||||||
procedure ReadBlank(AStream: TStream); override;
|
procedure ReadBlank(AStream: TStream); override;
|
||||||
@ -433,6 +436,7 @@ type
|
|||||||
|
|
||||||
public
|
public
|
||||||
constructor Create(AWorkbook: TsWorkbook); override;
|
constructor Create(AWorkbook: TsWorkbook); override;
|
||||||
|
destructor Destroy; override;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
|
||||||
@ -443,12 +447,13 @@ type
|
|||||||
FDateMode: TDateMode;
|
FDateMode: TDateMode;
|
||||||
FCodePage: String; // in a format prepared for lconvencoding.ConvertEncoding
|
FCodePage: String; // in a format prepared for lconvencoding.ConvertEncoding
|
||||||
FFirstNumFormatIndexInFile: Integer;
|
FFirstNumFormatIndexInFile: Integer;
|
||||||
|
FPalette: TsPalette;
|
||||||
procedure AddBuiltinNumFormats; override;
|
procedure AddBuiltinNumFormats; override;
|
||||||
function FindXFIndex(ACell: PCell): Integer; virtual;
|
function FindXFIndex(ACell: PCell): Integer; virtual;
|
||||||
function FixColor(AColor: TsColor): TsColor; override;
|
|
||||||
function GetLastRowIndex(AWorksheet: TsWorksheet): Integer;
|
function GetLastRowIndex(AWorksheet: TsWorksheet): Integer;
|
||||||
function GetLastColIndex(AWorksheet: TsWorksheet): Word;
|
function GetLastColIndex(AWorksheet: TsWorksheet): Word;
|
||||||
function GetPrintOptions: Word; virtual;
|
function GetPrintOptions: Word; virtual;
|
||||||
|
function PaletteIndex(AColor: TsColor): Word;
|
||||||
|
|
||||||
// Helper function for writing the BIFF header
|
// Helper function for writing the BIFF header
|
||||||
procedure WriteBIFFHeader(AStream: TStream; ARecID, ARecSize: Word);
|
procedure WriteBIFFHeader(AStream: TStream; ARecID, ARecSize: Word);
|
||||||
@ -548,6 +553,8 @@ type
|
|||||||
|
|
||||||
public
|
public
|
||||||
constructor Create(AWorkbook: TsWorkbook); override;
|
constructor Create(AWorkbook: TsWorkbook); override;
|
||||||
|
destructor Destroy; override;
|
||||||
|
procedure CheckLimitations; override;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure AddBuiltinBiffFormats(AList: TStringList;
|
procedure AddBuiltinBiffFormats(AList: TStringList;
|
||||||
@ -773,16 +780,31 @@ end;
|
|||||||
constructor TsSpreadBIFFReader.Create(AWorkbook: TsWorkbook);
|
constructor TsSpreadBIFFReader.Create(AWorkbook: TsWorkbook);
|
||||||
begin
|
begin
|
||||||
inherited Create(AWorkbook);
|
inherited Create(AWorkbook);
|
||||||
|
|
||||||
|
FPalette := TsPalette.Create;
|
||||||
|
PopulatePalette;
|
||||||
|
|
||||||
FCellFormatList := TsCellFormatList.Create(true);
|
FCellFormatList := TsCellFormatList.Create(true);
|
||||||
// Allow duplicates! XF indexes get out of sync if not all format records are in list
|
// true = allow duplicates! XF indexes get out of sync if not all format records are in list
|
||||||
|
|
||||||
// Initial base date in case it won't be read from file
|
// Initial base date in case it won't be read from file
|
||||||
FDateMode := dm1900;
|
FDateMode := dm1900;
|
||||||
|
|
||||||
// Limitations of BIFF5 and BIFF8 file format
|
// Limitations of BIFF5 and BIFF8 file format
|
||||||
FLimitations.MaxColCount := 256;
|
FLimitations.MaxColCount := 256;
|
||||||
FLimitations.MaxRowCount := 65536;
|
FLimitations.MaxRowCount := 65536;
|
||||||
FLimitations.MaxPaletteSize := 64;
|
FLimitations.MaxPaletteSize := 64;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Destructor of the reader class
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
destructor TsSpreadBIFFReader.Destroy;
|
||||||
|
begin
|
||||||
|
FPalette.Free;
|
||||||
|
inherited Destroy;
|
||||||
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Adds the built-in number formats to the NumFormatList.
|
Adds the built-in number formats to the NumFormatList.
|
||||||
Valid for BIFF5...BIFF8. Needs to be overridden for BIFF2.
|
Valid for BIFF5...BIFF8. Needs to be overridden for BIFF2.
|
||||||
@ -814,7 +836,6 @@ begin
|
|||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Extracts a number out of an RK value.
|
Extracts a number out of an RK value.
|
||||||
Valid since BIFF3.
|
Valid since BIFF3.
|
||||||
@ -871,6 +892,47 @@ begin
|
|||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
It is a problem of the biff file structure that the font is loaded before the
|
||||||
|
palette. Therefore, when reading the font, we cannot determine its rgb color.
|
||||||
|
We had stored temporarily the palette index in the font color member and
|
||||||
|
are replacing it here by the corresponding rgb color. This is possible because
|
||||||
|
FixFontColors is called at the end of the workbook globals records when
|
||||||
|
everything is known.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsSpreadBIFFReader.FixColors;
|
||||||
|
var
|
||||||
|
i: Integer;
|
||||||
|
fnt: TsFont;
|
||||||
|
fmt: PsCellFormat;
|
||||||
|
|
||||||
|
procedure FixColor(var AColor: TsColor);
|
||||||
|
begin
|
||||||
|
if IsPaletteIndex(AColor) then
|
||||||
|
AColor := FPalette[AColor and $00FFFFFF];
|
||||||
|
end;
|
||||||
|
|
||||||
|
begin
|
||||||
|
for i:=0 to FWorkbook.GetFontCount - 1 do
|
||||||
|
begin
|
||||||
|
fnt := FWorkbook.GetFont(i);
|
||||||
|
FixColor(fnt.Color);
|
||||||
|
end;
|
||||||
|
|
||||||
|
for i:=0 to FCellFormatList.Count-1 do
|
||||||
|
begin
|
||||||
|
fmt := FCellFormatList[i];
|
||||||
|
FixColor(fmt^.Background.BgColor);
|
||||||
|
FixColor(fmt^.Background.FgColor);
|
||||||
|
FixColor(fmt^.BorderStyles[cbEast].Color);
|
||||||
|
FixColor(fmt^.BorderStyles[cbWest].Color);
|
||||||
|
FixColor(fmt^.BorderStyles[cbNorth].Color);
|
||||||
|
FixColor(fmt^.BorderStyles[cbSouth].Color);
|
||||||
|
FixColor(fmt^.BorderStyles[cbDiagUp].Color);
|
||||||
|
FixColor(fmt^.BorderStyles[cbDiagDown].Color);
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Converts the number to a date/time and return that if it is
|
Converts the number to a date/time and return that if it is
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
@ -1463,17 +1525,15 @@ end;
|
|||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
procedure TsSpreadBIFFReader.ReadPalette(AStream: TStream);
|
procedure TsSpreadBIFFReader.ReadPalette(AStream: TStream);
|
||||||
var
|
var
|
||||||
i, n: Word;
|
n: Word;
|
||||||
pal: Array of TsColorValue;
|
|
||||||
begin
|
begin
|
||||||
|
// Read palette size
|
||||||
n := WordLEToN(AStream.ReadWord) + 8;
|
n := WordLEToN(AStream.ReadWord) + 8;
|
||||||
SetLength(pal, n);
|
FPalette.Clear;
|
||||||
for i:=0 to 7 do
|
FPalette.AddBuiltinColors;
|
||||||
pal[i] := Workbook.GetPaletteColor(i);
|
// Read palette colors and add them to the palette
|
||||||
for i:=8 to n-1 do
|
while FPalette.Count < n do
|
||||||
pal[i] := DWordLEToN(AStream.ReadDWord);
|
FPalette.AddColor(DWordLEToN(AStream.ReadDWord));
|
||||||
Workbook.UsePalette(@pal[0], n, false);
|
|
||||||
FPaletteFound := true;
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
@ -2129,6 +2189,15 @@ begin
|
|||||||
FWorksheet.Options := FWorksheet.Options - [soHasFrozenPanes];
|
FWorksheet.Options := FWorksheet.Options - [soHasFrozenPanes];
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Populates the reader's palette by default colors. Will be overwritten if the
|
||||||
|
file contains a palette on its own
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsSpreadBIFFReader.PopulatePalette;
|
||||||
|
begin
|
||||||
|
FPalette.AddBuiltinColors;
|
||||||
|
end;
|
||||||
|
|
||||||
|
|
||||||
{------------------------------------------------------------------------------}
|
{------------------------------------------------------------------------------}
|
||||||
{ TsSpreadBIFFWriter }
|
{ TsSpreadBIFFWriter }
|
||||||
@ -2142,14 +2211,25 @@ constructor TsSpreadBIFFWriter.Create(AWorkbook: TsWorkbook);
|
|||||||
begin
|
begin
|
||||||
inherited Create(AWorkbook);
|
inherited Create(AWorkbook);
|
||||||
|
|
||||||
// Initial base date in case it won't be set otherwise.
|
|
||||||
// Use 1900 to get a bit more range between 1900..1904.
|
|
||||||
FDateMode := dm1900;
|
|
||||||
|
|
||||||
// Limitations of BIFF5 and BIFF8 file formats
|
// Limitations of BIFF5 and BIFF8 file formats
|
||||||
FLimitations.MaxColCount := 256;
|
FLimitations.MaxColCount := 256;
|
||||||
FLimitations.MaxRowCount := 65536;
|
FLimitations.MaxRowCount := 65536;
|
||||||
FLimitations.MaxPaletteSize := 64;
|
FLimitations.MaxPaletteSize := 64;
|
||||||
|
|
||||||
|
// Initial base date in case it won't be set otherwise.
|
||||||
|
// Use 1900 to get a bit more range between 1900..1904.
|
||||||
|
FDateMode := dm1900;
|
||||||
|
|
||||||
|
// Color palette
|
||||||
|
FPalette := TsPalette.Create;
|
||||||
|
FPalette.AddBuiltinColors;
|
||||||
|
FPalette.CollectFromWorkbook(AWorkbook);
|
||||||
|
end;
|
||||||
|
|
||||||
|
destructor TsSpreadBIFFWriter.Destroy;
|
||||||
|
begin
|
||||||
|
FPalette.Free;
|
||||||
|
inherited Destroy;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
@ -2164,6 +2244,21 @@ begin
|
|||||||
);
|
);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Checks limitations of the file format. Overridden to take care of the
|
||||||
|
color palette which can only contain a given number of entries.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
procedure TsSpreadBIFFWriter.CheckLimitations;
|
||||||
|
begin
|
||||||
|
inherited CheckLimitations;
|
||||||
|
// Check color count.
|
||||||
|
if FPalette.Count > FLimitations.MaxPaletteSize then
|
||||||
|
begin
|
||||||
|
Workbook.AddErrorMsg(rsTooManyPaletteColors, [FPalette.Count, FLimitations.MaxPaletteSize]);
|
||||||
|
FPalette.Trim(FLimitations.MaxPaletteSize);
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Determines the index of the XF record, according to formatting of the
|
Determines the index of the XF record, according to formatting of the
|
||||||
given cell
|
given cell
|
||||||
@ -2173,17 +2268,6 @@ begin
|
|||||||
Result := LAST_BUILTIN_XF + ACell^.FormatIndex;
|
Result := LAST_BUILTIN_XF + ACell^.FormatIndex;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TsSpreadBIFFWriter.FixColor(AColor: TsColor): TsColor;
|
|
||||||
var
|
|
||||||
rgb: TsColorValue;
|
|
||||||
begin
|
|
||||||
if AColor >= Limitations.MaxPaletteSize then begin
|
|
||||||
rgb := Workbook.GetPaletteColor(AColor);
|
|
||||||
Result := Workbook.FindClosestColor(rgb, FLimitations.MaxPaletteSize);
|
|
||||||
end else
|
|
||||||
Result := AColor;
|
|
||||||
end;
|
|
||||||
|
|
||||||
function TsSpreadBIFFWriter.GetLastRowIndex(AWorksheet: TsWorksheet): Integer;
|
function TsSpreadBIFFWriter.GetLastRowIndex(AWorksheet: TsWorksheet): Integer;
|
||||||
begin
|
begin
|
||||||
Result := AWorksheet.GetLastRowIndex;
|
Result := AWorksheet.GetLastRowIndex;
|
||||||
@ -2234,6 +2318,20 @@ begin
|
|||||||
Result := Result or $0080;
|
Result := Result or $0080;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
{@@ ----------------------------------------------------------------------------
|
||||||
|
Determines the index of the specified color in the writer's palette, or, if
|
||||||
|
not found, gets the index of the "closest" color.
|
||||||
|
-------------------------------------------------------------------------------}
|
||||||
|
function TsSpreadBIFFWriter.PaletteIndex(AColor: TsColor): Word;
|
||||||
|
var
|
||||||
|
idx: Integer;
|
||||||
|
begin
|
||||||
|
idx := FPalette.FindColor(AColor, Limitations.MaxPaletteSize);
|
||||||
|
if idx = -1 then
|
||||||
|
idx := FPalette.FindClosestColorIndex(AColor, Limitations.MaxPaletteSize);
|
||||||
|
Result := word(idx);
|
||||||
|
end;
|
||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Writes the BIFF record header consisting of the record ID and the size of
|
Writes the BIFF record header consisting of the record ID and the size of
|
||||||
data to be written immediately afterwards.
|
data to be written immediately afterwards.
|
||||||
@ -2695,14 +2793,14 @@ end;
|
|||||||
|
|
||||||
{@@ ----------------------------------------------------------------------------
|
{@@ ----------------------------------------------------------------------------
|
||||||
Writes the PALETTE record for the color palette.
|
Writes the PALETTE record for the color palette.
|
||||||
Valid for BIFF3-BIFF8. BIFF2 has no palette in file.
|
Valid for BIFF3-BIFF8. BIFF2 has no palette in the file.
|
||||||
-------------------------------------------------------------------------------}
|
-------------------------------------------------------------------------------}
|
||||||
procedure TsSpreadBIFFWriter.WritePalette(AStream: TStream);
|
procedure TsSpreadBIFFWriter.WritePalette(AStream: TStream);
|
||||||
const
|
const
|
||||||
NUM_COLORS = 56;
|
NUM_COLORS = 56;
|
||||||
var
|
var
|
||||||
i, n: Integer;
|
i, n: Integer;
|
||||||
rgb: TsColorValue;
|
rgb: TsColor;
|
||||||
begin
|
begin
|
||||||
{ BIFF Record header }
|
{ BIFF Record header }
|
||||||
WriteBIFFHeader(AStream, INT_EXCEL_ID_PALETTE, 2 + 4*NUM_COLORS);
|
WriteBIFFHeader(AStream, INT_EXCEL_ID_PALETTE, 2 + 4*NUM_COLORS);
|
||||||
@ -2710,13 +2808,13 @@ begin
|
|||||||
{ Number of colors }
|
{ Number of colors }
|
||||||
AStream.WriteWord(WordToLE(NUM_COLORS));
|
AStream.WriteWord(WordToLE(NUM_COLORS));
|
||||||
|
|
||||||
{ Take the colors from the palette of the Worksheet }
|
{ Take the colors from the internal palette of the writer }
|
||||||
n := Workbook.GetPaletteSize;
|
n := FPalette.Count;
|
||||||
|
|
||||||
{ Skip the first 8 entries - they are hard-coded into Excel }
|
{ Skip the first 8 entries - they are hard-coded into Excel }
|
||||||
for i := 8 to 8 + NUM_COLORS - 1 do
|
for i := 8 to 8 + NUM_COLORS - 1 do
|
||||||
begin
|
begin
|
||||||
rgb := Math.IfThen(i < n, Workbook.GetPaletteColor(i), $FFFFFF);
|
rgb := Math.IfThen(i < n, FPalette[i], $FFFFFF);
|
||||||
AStream.WriteDWord(DWordToLE(rgb))
|
AStream.WriteDWord(DWordToLE(rgb))
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
@ -43,7 +43,7 @@ uses
|
|||||||
{$ELSE}
|
{$ELSE}
|
||||||
fpszipper,
|
fpszipper,
|
||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
fpsTypes, fpSpreadsheet, fpsUtils, fpsReaderWriter, fpsNumFormat,
|
fpsTypes, fpSpreadsheet, fpsUtils, fpsReaderWriter, fpsNumFormat, fpsPalette,
|
||||||
fpsxmlcommon, xlsCommon;
|
fpsxmlcommon, xlsCommon;
|
||||||
|
|
||||||
type
|
type
|
||||||
@ -59,7 +59,8 @@ type
|
|||||||
FBorderList: TFPList;
|
FBorderList: TFPList;
|
||||||
FHyperlinkList: TFPList;
|
FHyperlinkList: TFPList;
|
||||||
FSharedFormulaBaseList: TFPList;
|
FSharedFormulaBaseList: TFPList;
|
||||||
FThemeColors: array of TsColorValue;
|
FPalette: TsPalette;
|
||||||
|
FThemeColors: array of TsColor;
|
||||||
FWrittenByFPS: Boolean;
|
FWrittenByFPS: Boolean;
|
||||||
procedure ApplyCellFormatting(ACell: PCell; XfIndex: Integer);
|
procedure ApplyCellFormatting(ACell: PCell; XfIndex: Integer);
|
||||||
procedure ApplyHyperlinks(AWorksheet: TsWorksheet);
|
procedure ApplyHyperlinks(AWorksheet: TsWorksheet);
|
||||||
@ -255,81 +256,7 @@ const
|
|||||||
MIME_COMMENTS = MIME_SPREADML + '.comments+xml';
|
MIME_COMMENTS = MIME_SPREADML + '.comments+xml';
|
||||||
MIME_VMLDRAWING = MIME_OFFICEDOCUMENT + '.vmlDrawing';
|
MIME_VMLDRAWING = MIME_OFFICEDOCUMENT + '.vmlDrawing';
|
||||||
|
|
||||||
LAST_PALETTE_COLOR = $3F; // 63
|
LAST_PALETTE_INDEX = 63;
|
||||||
|
|
||||||
var
|
|
||||||
// the palette of the 64 default colors as "big-endian color" values
|
|
||||||
// (identical to BIFF8)
|
|
||||||
PALETTE_OOXML: array[$00..LAST_PALETTE_COLOR] of TsColorValue = (
|
|
||||||
$000000, // $00: black // 8 built-in default colors
|
|
||||||
$FFFFFF, // $01: white
|
|
||||||
$FF0000, // $02: red
|
|
||||||
$00FF00, // $03: green
|
|
||||||
$0000FF, // $04: blue
|
|
||||||
$FFFF00, // $05: yellow
|
|
||||||
$FF00FF, // $06: magenta
|
|
||||||
$00FFFF, // $07: cyan
|
|
||||||
|
|
||||||
$000000, // $08: EGA black
|
|
||||||
$FFFFFF, // $09: EGA white
|
|
||||||
$FF0000, // $0A: EGA red
|
|
||||||
$00FF00, // $0B: EGA green
|
|
||||||
$0000FF, // $0C: EGA blue
|
|
||||||
$FFFF00, // $0D: EGA yellow
|
|
||||||
$FF00FF, // $0E: EGA magenta
|
|
||||||
$00FFFF, // $0F: EGA cyan
|
|
||||||
|
|
||||||
$800000, // $10: EGA dark red
|
|
||||||
$008000, // $11: EGA dark green
|
|
||||||
$000080, // $12: EGA dark blue
|
|
||||||
$808000, // $13: EGA olive
|
|
||||||
$800080, // $14: EGA purple
|
|
||||||
$008080, // $15: EGA teal
|
|
||||||
$C0C0C0, // $16: EGA silver
|
|
||||||
$808080, // $17: EGA gray
|
|
||||||
$9999FF, // $18:
|
|
||||||
$993366, // $19:
|
|
||||||
$FFFFCC, // $1A:
|
|
||||||
$CCFFFF, // $1B:
|
|
||||||
$660066, // $1C:
|
|
||||||
$FF8080, // $1D:
|
|
||||||
$0066CC, // $1E:
|
|
||||||
$CCCCFF, // $1F:
|
|
||||||
|
|
||||||
$000080, // $20:
|
|
||||||
$FF00FF, // $21:
|
|
||||||
$FFFF00, // $22:
|
|
||||||
$00FFFF, // $23:
|
|
||||||
$800080, // $24:
|
|
||||||
$800000, // $25:
|
|
||||||
$008080, // $26:
|
|
||||||
$0000FF, // $27:
|
|
||||||
$00CCFF, // $28:
|
|
||||||
$CCFFFF, // $29:
|
|
||||||
$CCFFCC, // $2A:
|
|
||||||
$FFFF99, // $2B:
|
|
||||||
$99CCFF, // $2C:
|
|
||||||
$FF99CC, // $2D:
|
|
||||||
$CC99FF, // $2E:
|
|
||||||
$FFCC99, // $2F:
|
|
||||||
|
|
||||||
$3366FF, // $30:
|
|
||||||
$33CCCC, // $31:
|
|
||||||
$99CC00, // $32:
|
|
||||||
$FFCC00, // $33:
|
|
||||||
$FF9900, // $34:
|
|
||||||
$FF6600, // $35:
|
|
||||||
$666699, // $36:
|
|
||||||
$969696, // $37:
|
|
||||||
$003366, // $38:
|
|
||||||
$339966, // $39:
|
|
||||||
$003300, // $3A:
|
|
||||||
$333300, // $3B:
|
|
||||||
$993300, // $3C:
|
|
||||||
$993366, // $3D:
|
|
||||||
$333399, // $3E:
|
|
||||||
$333333 // $3F:
|
|
||||||
);
|
|
||||||
|
|
||||||
type
|
type
|
||||||
TFillListData = class
|
TFillListData = class
|
||||||
@ -384,8 +311,6 @@ constructor TsSpreadOOXMLReader.Create(AWorkbook: TsWorkbook);
|
|||||||
begin
|
begin
|
||||||
inherited Create(AWorkbook);
|
inherited Create(AWorkbook);
|
||||||
FDateMode := XlsxSettings.DateMode;
|
FDateMode := XlsxSettings.DateMode;
|
||||||
// Set up the default palette in order to have the default color names correct.
|
|
||||||
Workbook.UseDefaultPalette;
|
|
||||||
|
|
||||||
FSharedStrings := TStringList.Create;
|
FSharedStrings := TStringList.Create;
|
||||||
FFillList := TFPList.Create;
|
FFillList := TFPList.Create;
|
||||||
@ -395,6 +320,8 @@ begin
|
|||||||
// Allow duplicates because xf indexes used in cell records cannot be found any more.
|
// Allow duplicates because xf indexes used in cell records cannot be found any more.
|
||||||
FSharedFormulaBaseList := TFPList.Create;
|
FSharedFormulaBaseList := TFPList.Create;
|
||||||
|
|
||||||
|
FPalette := TsPalette.Create;
|
||||||
|
|
||||||
FPointSeparatorSettings := DefaultFormatSettings;
|
FPointSeparatorSettings := DefaultFormatSettings;
|
||||||
FPointSeparatorSettings.DecimalSeparator := '.';
|
FPointSeparatorSettings.DecimalSeparator := '.';
|
||||||
end;
|
end;
|
||||||
@ -417,6 +344,7 @@ begin
|
|||||||
|
|
||||||
// FCellFormatList, FNumFormatList and FFontList are destroyed by ancestor
|
// FCellFormatList, FNumFormatList and FFontList are destroyed by ancestor
|
||||||
|
|
||||||
|
FPalette.Free;
|
||||||
inherited Destroy;
|
inherited Destroy;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -894,7 +822,7 @@ end;
|
|||||||
function TsSpreadOOXMLReader.ReadColor(ANode: TDOMNode): TsColor;
|
function TsSpreadOOXMLReader.ReadColor(ANode: TDOMNode): TsColor;
|
||||||
var
|
var
|
||||||
s: String;
|
s: String;
|
||||||
rgb: TsColorValue;
|
rgb: TsColor;
|
||||||
idx: Integer;
|
idx: Integer;
|
||||||
tint: Double;
|
tint: Double;
|
||||||
n: Integer;
|
n: Integer;
|
||||||
@ -912,16 +840,19 @@ begin
|
|||||||
|
|
||||||
s := GetAttrValue(ANode, 'rgb');
|
s := GetAttrValue(ANode, 'rgb');
|
||||||
if s <> '' then begin
|
if s <> '' then begin
|
||||||
Result := FWorkbook.AddColorToPalette(HTMLColorStrToColor('#' + s));
|
Result := HTMLColorStrToColor('#' + s);
|
||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
s := GetAttrValue(ANode, 'indexed');
|
s := GetAttrValue(ANode, 'indexed');
|
||||||
if s <> '' then begin
|
if s <> '' then begin
|
||||||
Result := StrToInt(s);
|
Result := StrToInt(s);
|
||||||
n := FWorkbook.GetPaletteSize;
|
n := FPalette.Count;
|
||||||
if (Result <= LAST_PALETTE_COLOR) and (Result < n) then
|
if (Result <= LAST_PALETTE_INDEX) and (Result < n) then
|
||||||
|
begin
|
||||||
|
Result := FPalette[Result];
|
||||||
exit;
|
exit;
|
||||||
|
end;
|
||||||
// System colors
|
// System colors
|
||||||
// taken from OpenOffice docs
|
// taken from OpenOffice docs
|
||||||
case Result of
|
case Result of
|
||||||
@ -956,7 +887,7 @@ begin
|
|||||||
tint := StrToFloat(s, FPointSeparatorSettings);
|
tint := StrToFloat(s, FPointSeparatorSettings);
|
||||||
rgb := TintedColor(rgb, tint);
|
rgb := TintedColor(rgb, tint);
|
||||||
end;
|
end;
|
||||||
Result := FWorkBook.AddColorToPalette(rgb);
|
Result := rgb;
|
||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
@ -1465,36 +1396,42 @@ var
|
|||||||
node, colornode: TDOMNode;
|
node, colornode: TDOMNode;
|
||||||
nodename: String;
|
nodename: String;
|
||||||
s: string;
|
s: string;
|
||||||
clr: TsColor;
|
cidx: Integer; // color index
|
||||||
rgb: TsColorValue;
|
rgb: TsColor;
|
||||||
n: Integer;
|
n: Integer;
|
||||||
begin
|
begin
|
||||||
// OOXML sometimes specifies color by index even if a palette ("indexedColors")
|
// OOXML sometimes specifies color by index even if a palette ("indexedColors")
|
||||||
// is not loaeded. Therefore, we use the BIFF8 palette as default because
|
// is not loaeded. Therefore, we use the BIFF8 palette as default because
|
||||||
// the default indexedColors are identical to it.
|
// the default indexedColors are identical to it.
|
||||||
n := Length(PALETTE_OOXML);
|
FPalette.Clear;
|
||||||
FWorkbook.UsePalette(@PALETTE_OOXML, n);
|
FPalette.AddBuiltinColors; // This adds the BIFF2 colors 0..7
|
||||||
|
FPalette.AddExcelColors; // This adds the BIFF8 colors 8..63
|
||||||
|
n := FPalette.Count;
|
||||||
|
|
||||||
if ANode = nil then
|
if ANode = nil then
|
||||||
exit;
|
exit;
|
||||||
|
|
||||||
clr := 0;
|
cidx := 0;
|
||||||
node := ANode.FirstChild;
|
node := ANode.FirstChild;
|
||||||
while Assigned(node) do begin
|
while Assigned(node) do
|
||||||
|
begin
|
||||||
nodename := node.NodeName;
|
nodename := node.NodeName;
|
||||||
if nodename = 'indexedColors' then begin
|
if nodename = 'indexedColors' then
|
||||||
|
begin
|
||||||
colornode := node.FirstChild;
|
colornode := node.FirstChild;
|
||||||
while Assigned(colornode) do begin
|
while Assigned(colornode) do
|
||||||
|
begin
|
||||||
nodename := colornode.NodeName;
|
nodename := colornode.NodeName;
|
||||||
if nodename = 'rgbColor' then begin
|
if nodename = 'rgbColor' then begin
|
||||||
s := GetAttrValue(colornode, 'rgb');
|
s := GetAttrValue(colornode, 'rgb');
|
||||||
if s <> '' then begin
|
if s <> '' then begin
|
||||||
rgb := HTMLColorStrToColor('#' + s);
|
rgb := HTMLColorStrToColor('#' + s);
|
||||||
if clr < n then begin
|
if cidx < n then begin
|
||||||
FWorkbook.SetPaletteColor(clr, rgb);
|
FPalette[cidx] := rgb;
|
||||||
inc(clr);
|
inc(cidx);
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
FWorkbook.AddColorToPalette(rgb);
|
FPalette.AddColor(rgb);
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
colornode := colorNode.NextSibling;
|
colornode := colorNode.NextSibling;
|
||||||
@ -2078,20 +2015,19 @@ const
|
|||||||
"slantDashDot", "mediumDashDot", "mediumDashed", "medium", "thick", "double" }
|
"slantDashDot", "mediumDashDot", "mediumDashed", "medium", "thick", "double" }
|
||||||
var
|
var
|
||||||
styleName: String;
|
styleName: String;
|
||||||
colorName: String;
|
colorStr: String;
|
||||||
rgb: TsColorValue;
|
rgb: TsColor;
|
||||||
begin
|
begin
|
||||||
if (ABorder in AFormatRecord^.Border) then begin
|
if (ABorder in AFormatRecord^.Border) then begin
|
||||||
// Line style
|
// Line style
|
||||||
styleName := LINESTYLE_NAME[AFormatRecord^.BorderStyles[ABorder].LineStyle];
|
styleName := LINESTYLE_NAME[AFormatRecord^.BorderStyles[ABorder].LineStyle];
|
||||||
|
|
||||||
// Border color
|
// Border color
|
||||||
rgb := Workbook.GetPaletteColor(AFormatRecord^.BorderStyles[ABorder].Color);
|
rgb := AFormatRecord^.BorderStyles[ABorder].Color;
|
||||||
//rgb := Workbook.GetPaletteColor(ACell^.BorderStyles[ABorder].Color);
|
colorStr := ColorToHTMLColorStr(rgb, true);
|
||||||
colorName := ColorToHTMLColorStr(rgb, true);
|
|
||||||
AppendToStream(AStream, Format(
|
AppendToStream(AStream, Format(
|
||||||
'<%s style="%s"><color rgb="%s" /></%s>',
|
'<%s style="%s"><color rgb="%s" /></%s>',
|
||||||
[ABorderName, styleName, colorName, ABorderName]
|
[ABorderName, styleName, colorStr, ABorderName]
|
||||||
));
|
));
|
||||||
end else
|
end else
|
||||||
AppendToStream(AStream, Format(
|
AppendToStream(AStream, Format(
|
||||||
@ -2255,11 +2191,11 @@ begin
|
|||||||
if FFillList[i]^.Background.FgColor = scTransparent then
|
if FFillList[i]^.Background.FgColor = scTransparent then
|
||||||
fc := 'auto="1"'
|
fc := 'auto="1"'
|
||||||
else
|
else
|
||||||
fc := Format('rgb="%s"', [Copy(Workbook.GetPaletteColorAsHTMLStr(FFillList[i]^.Background.FgColor), 2, 255)]);
|
fc := Format('rgb="%s"', [Copy(ColorToHTMLColorStr(FFillList[i]^.Background.FgColor), 2, MaxInt)]);
|
||||||
if FFillList[i]^.Background.BgColor = scTransparent then
|
if FFillList[i]^.Background.BgColor = scTransparent then
|
||||||
bc := 'auto="1"'
|
bc := 'auto="1"'
|
||||||
else
|
else
|
||||||
bc := Format('rgb="%s"', [Copy(Workbook.GetPaletteColorAsHTMLStr(FFillList[i]^.Background.BgColor), 2, 255)]);
|
bc := Format('rgb="%s"', [Copy(ColorToHTMLColorStr(FFillList[i]^.Background.BgColor), 2, MaxInt)]);
|
||||||
AppendToStream(AStream,
|
AppendToStream(AStream,
|
||||||
'<fill>');
|
'<fill>');
|
||||||
AppendToStream(AStream, Format(
|
AppendToStream(AStream, Format(
|
||||||
@ -2283,19 +2219,11 @@ var
|
|||||||
i: Integer;
|
i: Integer;
|
||||||
font: TsFont;
|
font: TsFont;
|
||||||
s: String;
|
s: String;
|
||||||
rgb: TsColorValue;
|
|
||||||
begin
|
begin
|
||||||
AppendToStream(FSStyles, Format(
|
AppendToStream(FSStyles, Format(
|
||||||
'<fonts count="%d">', [Workbook.GetFontCount]));
|
'<fonts count="%d">', [Workbook.GetFontCount]));
|
||||||
for i:=0 to Workbook.GetFontCount-1 do begin
|
for i:=0 to Workbook.GetFontCount-1 do begin
|
||||||
font := Workbook.GetFont(i);
|
font := Workbook.GetFont(i);
|
||||||
{
|
|
||||||
if font = 4 then
|
|
||||||
// if font = nil then
|
|
||||||
AppendToStream(AStream, '<font />')
|
|
||||||
// Font #4 is missing in fpspreadsheet due to BIFF compatibility. We write
|
|
||||||
// an empty node to keep the numbers in sync with the stored font index.
|
|
||||||
else begin}
|
|
||||||
s := Format('<sz val="%g" /><name val="%s" />', [font.Size, font.FontName], FPointSeparatorSettings);
|
s := Format('<sz val="%g" /><name val="%s" />', [font.Size, font.FontName], FPointSeparatorSettings);
|
||||||
if (fssBold in font.Style) then
|
if (fssBold in font.Style) then
|
||||||
s := s + '<b />';
|
s := s + '<b />';
|
||||||
@ -2305,17 +2233,10 @@ begin
|
|||||||
s := s + '<u />';
|
s := s + '<u />';
|
||||||
if (fssStrikeout in font.Style) then
|
if (fssStrikeout in font.Style) then
|
||||||
s := s + '<strike />';
|
s := s + '<strike />';
|
||||||
if font.Color <> scBlack then begin
|
if font.Color <> scBlack then
|
||||||
if font.Color < 64 then
|
s := s + Format('<color rgb="%s" />', [Copy(ColorToHTMLColorStr(font.Color), 2, MaxInt)]);
|
||||||
s := s + Format('<color indexed="%d" />', [font.Color])
|
|
||||||
else begin
|
|
||||||
rgb := Workbook.GetPaletteColor(font.Color);
|
|
||||||
s := s + Format('<color rgb="%s" />', [Copy(ColorToHTMLColorStr(rgb), 2, 255)]);
|
|
||||||
end;
|
|
||||||
end;
|
|
||||||
AppendToStream(AStream,
|
AppendToStream(AStream,
|
||||||
'<font>', s, '</font>');
|
'<font>', s, '</font>');
|
||||||
// end;
|
|
||||||
end;
|
end;
|
||||||
AppendToStream(AStream,
|
AppendToStream(AStream,
|
||||||
'</fonts>');
|
'</fonts>');
|
||||||
@ -2481,27 +2402,11 @@ begin
|
|||||||
);
|
);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ Writes the workbook's color palette to the file }
|
{ In older versions, the workbook had a color palette which was written here.
|
||||||
|
Now there is no palette any more. }
|
||||||
procedure TsSpreadOOXMLWriter.WritePalette(AStream: TStream);
|
procedure TsSpreadOOXMLWriter.WritePalette(AStream: TStream);
|
||||||
var
|
|
||||||
rgb: TsColorValue;
|
|
||||||
i: Integer;
|
|
||||||
begin
|
begin
|
||||||
AppendToStream(AStream,
|
// just keep it here in case we'd need it later...
|
||||||
'<colors>' +
|
|
||||||
'<indexedColors>');
|
|
||||||
|
|
||||||
// There must not be more than 64 palette entries because the next colors
|
|
||||||
// are system colors.
|
|
||||||
for i:=0 to Min(LAST_PALETTE_COLOR, Workbook.GetPaletteSize-1) do begin
|
|
||||||
rgb := Workbook.GetPaletteColor(i);
|
|
||||||
AppendToStream(AStream,
|
|
||||||
'<rgbColor rgb="'+ColorToHTMLColorStr(rgb, true) + '" />');
|
|
||||||
end;
|
|
||||||
|
|
||||||
AppendToStream(AStream,
|
|
||||||
'</indexedColors>' +
|
|
||||||
'</colors>');
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TsSpreadOOXMLWriter.WritePageMargins(AStream: TStream;
|
procedure TsSpreadOOXMLWriter.WritePageMargins(AStream: TStream;
|
||||||
@ -3636,8 +3541,5 @@ initialization
|
|||||||
// Registers this reader / writer on fpSpreadsheet
|
// Registers this reader / writer on fpSpreadsheet
|
||||||
RegisterSpreadFormat(TsSpreadOOXMLReader, TsSpreadOOXMLWriter, sfOOXML);
|
RegisterSpreadFormat(TsSpreadOOXMLReader, TsSpreadOOXMLWriter, sfOOXML);
|
||||||
|
|
||||||
// Create color palette for OOXML file format
|
|
||||||
MakeLEPalette(@PALETTE_OOXML, Length(PALETTE_OOXML));
|
|
||||||
|
|
||||||
end.
|
end.
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user