📄 uescherrecords.pas
字号:
if DwgCache.Solver<>nil then DwgCache.Solver.DeleteRef(Self);
if DwgCache.Shape<>nil then
if DwgCache.Shape.Find(ShapeId^,Index) then
DwgCache.Shape.Delete(Index);
if FParent <> nil then (FParent as TEscherSpContainerRecord).SP:=nil;
end;
//MADE: Delete all references in connectors with shapedest= self;
inherited;
end;
function TEscherSPRecord.DoCopyTo(const NewDwgCache: PEscherDwgCache; const RowOfs, ColOfs: integer): TEscherRecord;
begin
Result:=inherited DoCopyTo(NewDwgCache, RowOfs, ColOfs);
if NewDwgCache=DwgCache then (Result as TEscherSPRecord).ShapeId^:=DwgCache.Dg.IncMaxShapeId;
end;
{ TEscherDggRecord }
constructor TEscherDggRecord.Create(
const aEscherHeader: TEscherRecordHeader;
const aDwgGroupCache: PEscherDwgGroupCache;
const aDwgCache: PEscherDwgCache; const aParent: TEscherContainerRecord);
begin
inherited;
FDgg:= PDgg(Data);
if (DwgGroupCache.Dgg=nil) then DwgGroupCache.Dgg:=Self else raise Exception.Create(ErrDggDuplicated);
end;
constructor TEscherDggRecord.CreateFromData(
const aDwgGroupCache: PEscherDwgGroupCache;
const aDwgCache: PEscherDwgCache; const aParent: TEscherContainerRecord);
var
RecordHeader: TEscherRecordHeader;
begin
RecordHeader.Id:=MsofbtDgg;
RecordHeader.Pre:=0;
RecordHeader.Size:=24;
Create(RecordHeader, aDwgGroupCache, aDwgCache, aParent);
FillChar(Data^, RecordHeader.Size, 0);
FDgg.MaxShapeId:=1;
FDgg.FIDclCount:=2;
FDgg.ShapesSaved:=1;
FDgg.DwgSaved:=1;
Data[16]:=1;
Data[20]:=1;
LoadedDataSize:=RecordHeader.Size;
end;
destructor TEscherDggRecord.Destroy;
begin
DwgGroupCache.Dgg:=nil;
inherited;
end;
{ TEscherSpgrContainerRecord }
constructor TEscherSpgrContainerRecord.Create(
const aEscherHeader: TEscherRecordHeader;
const aDwgGroupCache: PEscherDwgGroupCache;
const aDwgCache: PEscherDwgCache; const aParent: TEscherContainerRecord);
begin
inherited;
if (DwgCache.Patriarch=nil) then DwgCache.Patriarch:=Self;
end;
destructor TEscherSpgrContainerRecord.Destroy;
begin
if DwgCache.Patriarch=Self then DwgCache.Patriarch:=nil;
inherited;
end;
{ TEscherSolverContainerRecord }
procedure TEscherSolverContainerRecord.ArrangeCopyRowsAndCols;
var
i: integer;
begin
for i:=0 to FContainedRecords.Count-1 do
(FContainedRecords[i] as TRuleRecord).ArrangeCopyRowsAndCols;
end;
procedure TEscherSolverContainerRecord.CheckMax(const aRuleId: LongWord);
begin
if MaxRuleId<aRuleId then MaxRuleId:=aRuleId;
end;
constructor TEscherSolverContainerRecord.Create(
const aEscherHeader: TEscherRecordHeader;
const aDwgGroupCache: PEscherDwgGroupCache;
const aDwgCache: PEscherDwgCache; const aParent: TEscherContainerRecord);
begin
inherited;
if (DwgCache.Solver=nil) then DwgCache.Solver:=Self else raise Exception.Create(ErrSolverDuplicated);
end;
procedure TEscherSolverContainerRecord.DeleteRef(
const Shape: TEscherSPRecord);
var
i: integer;
begin
for i:=FContainedRecords.Count-1 downto 0 do
if (FContainedRecords[i] as TRuleRecord).DeleteRef(Shape) then FContainedRecords.Delete(i);
end;
destructor TEscherSolverContainerRecord.Destroy;
begin
DwgCache.Solver:=nil;
inherited;
end;
procedure TEscherSolverContainerRecord.FixPointers;
var
i: integer;
begin
for i:=0 to FContainedRecords.Count-1 do
(FContainedRecords[i] as TRuleRecord).FixPointers;
end;
function TEscherSolverContainerRecord.IncMaxRuleId: LongWord;
begin
inc(MaxRuleId,2);
Result:=MaxRuleId;
end;
{ TEscherSpContainerRecord }
function TEscherSpContainerRecord.Col: integer;
begin
if ClientAnchor<>nil then Result:=ClientAnchor.Col else Result:=0;
end;
function TEscherSpContainerRecord.Row: integer;
begin
if ClientAnchor<>nil then Result:=ClientAnchor.Row else Result:=0;
end;
{ TEscherOPTRecord }
function TEscherOPTRecord.Col: integer;
var
Fr: TEscherRecord;
begin
Fr:=FindRoot;
if (DwgCache.Patriarch=nil) or (Fr=nil) or ((Fr as TEscherSpContainerRecord).ClientAnchor=nil) then Result:=0
else Result:=(Fr as TEscherSpContainerRecord).ClientAnchor.Col;
end;
constructor TEscherOPTRecord.Create(
const aEscherHeader: TEscherRecordHeader;
const aDwgGroupCache: PEscherDwgGroupCache;
const aDwgCache: PEscherDwgCache; const aParent: TEscherContainerRecord);
begin
inherited;
if (FParent <> nil) and (FParent is TEscherSpContainerRecord) then (FParent as TEscherSpContainerRecord).OPT:=self;
end;
destructor TEscherOPTRecord.Destroy;
var
i: integer;
begin
if (Length(BlipPtr)>0) and not DwgCache.Destroying then
begin
for i:=0 to Length(BlipPtr)-1 do
BlipPtr[i].Release;
if DwgCache.Blip<>nil then DwgCache.Blip.Remove(Self);
end;
if (FParent <> nil) and (FParent is TEscherSpContainerRecord) then (FParent as TEscherSpContainerRecord).Opt:=nil;
inherited;
end;
function TEscherOPTRecord.DoCopyTo(const NewDwgCache: PEscherDwgCache; const RowOfs, ColOfs: integer): TEscherRecord;
var
i: integer;
begin
Result:= inherited DoCopyTo(NewDwgCache, RowOfs, ColOfs);
if (DwgCache.Blip<>nil) and (Length(BlipPos)>0) then NewDwgCache.Blip.Add(Result as TEscherOptRecord);
(Result as TEscherOPTRecord).BlipPtr:= copy(BlipPtr, Low(BlipPtr), 1+High(BlipPtr)-Low(BlipPtr));
(Result as TEscherOPTRecord).BlipPos:= copy(BlipPos, Low(BlipPos), 1+High(BlipPos)-Low(BlipPos));
(Result as TEscherOPTRecord).FShapeName:=FShapeName;
if Length(BlipPtr)>0 then for i:=0 to Length(BlipPtr)-1 do
BlipPtr[i].AddRef;
end;
function TEscherOPTRecord.GetShapeName: WideString;
begin
Result:=FShapeName;
end;
function TEscherOPTRecord.Row: integer;
var
Fr: TEscherRecord;
begin
Fr:=FindRoot;
if (DwgCache.Patriarch=nil) or (Fr=nil) or ((Fr as TEscherSpContainerRecord).ClientAnchor=nil) then Result:=0
else Result:=(Fr as TEscherSpContainerRecord).ClientAnchor.Row;
end;
procedure TEscherOPTRecord.SaveToStream(const DataStream: TStream;
const BreakList: TBreakList);
var
i: integer;
begin
//Fix Blip ids
Assert(Length(BlipPtr)=Length(BlipPos), ErrInternal);
for i:=0 to Length(BlipPos)-1 do
PLongWord(PChar(Data)+ BlipPos[i])^:= BlipPtr[i].BStorePos;
inherited;
end;
procedure TEscherOPTRecord.AfterCreate;
var
i, tPos: integer;
Pid: word;
ComplexOfs: LongWord;
NameLen: PLongWord;
NameOfs: LongWord;
begin
if DwgCache.Blip=nil then exit;
tPos:=0; ComplexOfs:=0;
for i:=0 to Instance-1 do
begin
if tPos+6> TotalDataSize then Raise Exception.Create(ErrLoadingEscher);
Pid:= GetWord(Data, tPos);
if ((Pid and (1 shl 15)) = 0)and ((Pid and (1 shl 14))=(1 shl 14)) then //blip
begin
SetLength(BlipPtr, Length(BlipPtr)+1);
BlipPtr[Length(BlipPtr)-1]:= DwgGroupCache.Bstore.ContainedRecords[PLongWord(PChar(Data)+ tPos+2)^-1] as TEscherBSERecord;
SetLength(BlipPos, Length(BlipPos)+1);
BlipPos[Length(BlipPos)-1]:= tPos+2;
if (DwgCache.Blip<>nil) and (Length(BlipPos)=1) then DwgCache.Blip.Add(Self);
end;
if (Pid and ($FFFF shr 2))=896 then //Shape Name
begin
NameLen:= PLongWord(PChar(Data)+ tPos+2);
NameOfs:= ComplexOfs;
SetLength(FShapeName, NameLen^ div 2-1);
Move((PChar(Data)+NameOfs+Instance*6)^, FShapeName[1], NameLen^-2);
end;
if Pid and (1 shl 15) = 1 shl 15 then //Complex property
inc(ComplexOfs, PLongWord(PChar(Data)+ tPos+2)^);
//Goto Next
inc(tPos, 6)
end;
end;
procedure TEscherOPTRecord.ChangeRef(const aBSE: TEscherBSERecord);
begin
if Length(BlipPtr)<>1 then raise Exception.Create(ErrChangingEscher);
if BlipPtr[0]=aBSE then exit;
aBSE.AddRef;
BlipPtr[0].Release;
BlipPtr[0]:=aBSE;
end;
function TEscherOPTRecord.AddImg(const Data: string; const DataType: TXlsImgTypes): integer;
var
BSE: TEscherBSERecord;
BStore: TEscherBStoreRecord;
begin
BStore:=DwgGroupCache.BStore;
Assert(BStore<>nil, 'BStore can''t be nil');
BSE:= ConvertGraphicToBSE(Data, DataType, DwgGroupCache, DwgCache);
if not BStore.ContainedRecords.Find( BSE, Result)
then BStore.ContainedRecords.Insert(Result, BSE) else FreeAndNil(BSE);
(BStore.ContainedRecords[Result] as TEscherBSERecord).AddRef;
end;
procedure TEscherOPTRecord.ReplaceImg(const Data: string; const DataType: TXlsImgTypes);
var
BSE: TEscherBSERecord;
BStore: TEscherBStoreRecord;
Index: integer;
begin
BStore:=DwgGroupCache.BStore;
Assert(BStore<>nil, 'BStore can''t be nil');
BSE:= ConvertGraphicToBSE(Data, DataType, DwgGroupCache, DwgCache);
if not BStore.ContainedRecords.Find( BSE, Index)
then BStore.ContainedRecords.Insert(Index, BSE) else FreeAndNil(BSE);
ChangeRef(BStore.ContainedRecords[Index] as TEscherBSERecord);
end;
procedure TEscherOPTRecord.GetImageFromStream(const Data: TStream; var DataType: TXlsImgTypes);
begin
if Length(BlipPtr)<>1 then raise Exception.Create(ErrChangingEscher);
BlipPtr[0].SaveGraphicToStream(Data, DataType);
end;
function TEscherOPTRecord.GetAnchor: TClientAnchor;
var
Fr: TEscherRecord;
begin
Fr:=FindRoot;
if (DwgCache.Patriarch=nil) or (Fr=nil) or not( Fr is TEscherSpContainerRecord) or ((Fr as TEscherSpContainerRecord).ClientAnchor=nil) then
FillChar(Result, SizeOf(Result), 0)
else Result:=(Fr as TEscherSpContainerRecord).ClientAnchor.GetAnchor;
end;
procedure TEscherOPTRecord.SetAnchor(const aAnchor: TClientAnchor);
var
Fr: TEscherRecord;
begin
Fr:=FindRoot;
if (DwgCache.Patriarch=nil) or (Fr=nil) or not( Fr is TEscherSpContainerRecord) or ((Fr as TEscherSpContainerRecord).ClientAnchor=nil) then exit;
(Fr as TEscherSpContainerRecord).ClientAnchor.SetAnchor(aAnchor);
end;
constructor TEscherOPTRecord.CreateFromDataImg(
const aPict: string; const aPicType: TXlsImgTypes; const PicName: widestring;
const aDwgGroupCache: PEscherDwgGroupCache;
const aDwgCache: PEscherDwgCache; const aParent: TEscherContainerRecord);
var
aEscherHeader: TEscherRecordHeader;
begin
aEscherHeader.Id:=MsofbtOPT;
aEscherHeader.Pre:=$0043; //4 properties, id, name, NoFillHitTest, fPrint
aEscherHeader.Size:=6 + //blip
6 + Length(PicName)*2+ 2+ //Name
12; //NoFillHitTest, fPrint
Create(aEscherHeader, aDwgGroupCache, aDwgCache, aParent);
SetWord(Data, 0, $4104); //blip=260, is blip=1, complex=0
SetLongWord(Data, 2, AddImg(aPict, aPicType)+1);
SetWord(Data,6, $C105); //Name prop... it is a complex one... data goes at the end.
SetLongWord(Data, 8, Length(PicName)*2+2);
SetWord(Data, 12, $1BF); //NoFilHitTest... select on not filled areas.
SetLongWord(Data, 14, $10000);
SetWord(Data, 18, $3BF); //fPrint... print this shape.
SetLongWord(Data, 20, $80000);
// set the string data.
move(PicName[1], Data[24], Length(PicName)*2);
SetWord(Data,24+Length(PicName)*2,0); //00 at the end
AfterCreate;
LoadedDataSize:=TotalDataSize;
end;
constructor TEscherOPTRecord.GroupCreateFromData(
const aDwgGroupCache: PEscherDwgGroupCache;
const aDwgCache: PEscherDwgCache; const aParent: TEscherContainerRecord);
const
DefaultData: array [0..17] of byte=($BF, $00, $08, $00, $08, $00, $81, $01, $09, $00, $00, $08, $C0, $01, $40, $00, $00, $08);
var
aEscherHeader: TEscherRecordHeader;
begin
aEscherHeader.Id:=MsofbtOPT;
aEscherHeader.Pre:=$0033; //5 properties
aEscherHeader.Size:=18;
Create(aEscherHeader, aDwgGroupCache, aDwgCache, aParent);
move(DefaultData, Data^, SizeOf(DefaultData));
AfterCreate;
LoadedDataSize:=TotalDataSize;
end;
constructor TEscherOPTRecord.CreateFromDataNote(
const aDwgGroupCache: PEscherDwgGroupCache;
const aDwgCache: PEscherDwgCache; const aParent: TEscherContainerRecord;
const Dummy: integer);
const
DefaultData: array [0..53] of byte=(
$80, $00, $00, $00, $00, $00, //IdText. Nothing, as we dont know what goes here
$BF, $00, $08, $00, $08, $00, //fFitTextToShape
$58, $01, $00, $00, $00, $00, //unknown
$81, $01, $50, $00, $00, $08, //fillcolor
$83, $01, $50, $00, $00, $08, //fillbackcolor
$BF, $01, $10, $00, $11, $00, //fNoFillHitTest
$01, $02, $00, $00, $00, $00, //shadow color
$3F, $02, $03, $00, $03, $00, //shadowObscured
$BF, $03, $02, $00, $0A, $00); //Print
var
aEscherHeader: TEscherRecordHeader;
begin
aEscherHeader.Id:=MsofbtOPT;
aEscherHeader.Pre:=$0093; //9 properties
aEscherHeader.Size:=6*9;
Create(aEscherHeader, aDwgGroupCache, aDwgCache, aParent);
move(DefaultData, Data^, SizeOf(DefaultData));
AfterCreate;
LoadedDataSize:=TotalDataSize;
end;
{ TEscherObjCache }
procedure TEscherObjCache.ArrangeCopySheet(const SheetInfo: TSheetInfo);
var
i: integer;
begin
for i:=0 to Count-1 do Items[i].ClientData.ArrangeCopySheet(SheetInfo);
end;
{ TEscherSplitMenuRecord }
constructor TEscherSplitMenuRecord.CreateFromData(
const aDwgGroupCache: PEscherDwgGroupCache;
const aDwgCache: PEscherDwgCache; const aParent: TEscherContainerRecord);
const
DefaultData: array [0..15] of byte=($0D, $00, $00, $08, $0C, $00, $00, $08, $17, $00, $00, $08, $F7, $00, $00, $10);
var
aEscherHeader: TEscherRecordHeader;
begin
aEscherHeader.Id:=MsofbtSplitMenuColors;
aEscherHeader.Pre:=$0040;
aEscherHeader.Size:=16;
Create(aEscherHeader, aDwgGroupCache, aDwgCache, aParent);
move(DefaultData, Data^, SizeOf(DefaultData));
LoadedDataSize:=TotalDataSize;
end;
end.
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -