?? asciiinsert.pas
字號:
unit ASCIIInsert;
interface
uses CarrierFile, DataFile, Classes
{$IFDEF CLX}
,QForms
{$ELSE}
,Forms
{$ENDIF}
;
type
TASCIIInsert = class(TCarrierFile)
public
constructor Create; override;
destructor Destroy; override;
function GetAvailSize: Longint; virtual;
function CreateFromCarrierFile(cf: TCarrierFile): Boolean; virtual;
function ExportToCarrierFile(cf: TCarrierFile): Boolean; virtual;
function EnoughSpaceToHide(n: Longint): Boolean; virtual;
function Encode(ToHide: TDataFile): Boolean; virtual;
function Decode(ResultFile: TDataFile): Boolean; virtual;
end;
implementation
constructor TASCIIInsert.Create;
begin
inherited Create;
end;
destructor TASCIIInsert.Destroy;
begin
inherited Create;
end;
function TASCIIInsert.GetAvailSize: Longint;
var
Buffer: Array[0..1023] of Byte;
BytesRead: Integer;
LineFeeds: Integer;
i: Integer;
LFFound: Boolean;
p: Integer;
Cancel: Boolean;
begin
inherited GetAvailSize;
Cancel:=False;
LineFeeds:=0;
LFFound:=False;
BytesRead:=1024;
Data.Seek(0,soFromBeginning);
p:=Trunc(Data.Size/1024);
if Assigned(FPercentChange) then FPercentChange(self,Percent);
Application.ProcessMessages;
while (BytesRead=1024) and not(Cancel) do begin
BytesRead:=Data.Read(Buffer,1024);
for i:=0 to BytesRead-1 do begin
if ((Buffer[i]=$0d) or (Buffer[i]=$0a)) then begin
if not(LFFound) then begin
Inc(LineFeeds);
if (Buffer[i]=$0d) then LFFound:=True;
end
else LFFound:=False;
end
else LFFound:=False;
end;
Percent:=Percent+p;
if Assigned(FPercentChange) then FPercentChange(self,Percent);
if Assigned(FWantCancel) then FWantCancel(self,Cancel);
Application.ProcessMessages;
end;
Percent:=100;
if Assigned(FPercentChange) then FPercentChange(self,Percent);
Application.ProcessMessages;
GetAvailSize:=LineFeeds;
end;
function TASCIIInsert.CreateFromCarrierFile(cf: TCarrierFile): Boolean;
begin
if cf.GetFileType='TXT' then begin
Data.Clear;
cf.SaveToStream(Data);
SetFileType(cf.GetFileType,cf.GetColorDepth);
Percent:=cf.Percent;
CreateFromCarrierFile:=True;
end
else CreateFromCarrierFile:=False;
end;
function TASCIIInsert.ExportToCarrierFile(cf: TCarrierFile): Boolean;
begin
cf.LoadFromStream(Data);
cf.SetFileType('TXT',0);
ExportToCarrierFile:=True;
end;
function TASCIIInsert.EnoughSpaceToHide(n: Longint): Boolean;
begin
if n>GetAvailSize then EnoughSpaceToHide:=False else EnoughSpaceToHide:=True;
end;
function TASCIIInsert.Encode(ToHide: TDataFile): Boolean;
var
newData: TMemoryStream;
Buffer: Array[0..1023] of Byte;
BytesRead: Integer;
HideStream: TMemoryStream;
HideBuffer: Array[0..1023] of Byte;
Insert: Array[0..7] of Byte;
HideRead: Integer;
CPos: Integer;
i,j: Integer;
val: Byte;
lastwritten: Integer;
last0d: Boolean;
Buffer2: Array[0..1023] of Byte;
p: Integer;
Cancel: Boolean;
begin
if EnoughSpaceToHide(ToHide.GetSize) then begin
Cancel:=False;
HideStream:=TMemoryStream.Create;
ToHide.SaveToStream(HideStream);
newData:=TMemoryStream.Create;
Data.Seek(0,soFromBeginning);
BytesRead:=Data.Read(Buffer,1024);
CPos:=0;
lastwritten:=-1;
HideRead:=1024;
HideStream.Seek(0,soFromBeginning);
last0d:=False;
Percent:=0;
p:=Trunc(HideStream.Size/1024);
if Assigned(FPercentChange) then FPercentChange(self,Percent);
Application.ProcessMessages;
while (HideRead=1024) and not(Cancel) do begin
HideRead:=HideStream.Read(HideBuffer,1024);
for i:=0 to HideRead-1 do begin
for j:=7 downto 0 do begin
if (HideBuffer[i] and (1 shl j))<>0 then Insert[7-j]:=$09 else Insert[7-j]:=$20;
end;
while ((Buffer[CPos]<>$0d) and ((Buffer[CPos]<>$0a) or ((Buffer[CPos]=$0a) and (last0d)))) do begin
last0d:=False;
if CPos<BytesRead-1 then Inc(CPos)
else begin
for j:=0 to CPos-lastwritten-1 do Buffer2[j]:=Buffer[j+lastwritten+1];
newData.Write(Buffer2,CPos-lastwritten);
BytesRead:=Data.Read(Buffer,1024);
CPos:=0;
lastwritten:=-1;
end;
end;
if (Buffer[CPos]=$0d) then last0d:=True;
for j:=0 to CPos-lastwritten-2 do Buffer2[j]:=Buffer[j+lastwritten+1];
newData.Write(Buffer2,CPos-lastwritten-1);
newData.Write(Insert,8);
lastwritten:=CPos-1;
if CPos<BytesRead-1 then Inc(CPos)
else begin
for j:=0 to CPos-lastwritten-1 do Buffer2[j]:=Buffer[j+lastwritten+1];
newData.Write(Buffer2,CPos-lastwritten);
BytesRead:=Data.Read(Buffer,1024);
CPos:=0;
lastwritten:=-1;
end;
end;
Percent:=Percent+p;
if Assigned(FPercentChange) then FPercentChange(self,Percent);
if Assigned(FWantCancel) then FWantCancel(self,Cancel);
Application.ProcessMessages;
end;
for j:=lastwritten+1 to BytesRead-1 do Buffer2[j-lastwritten-1]:=Buffer[j];
newData.Write(Buffer2,BytesRead-1-lastwritten);
if Data.Size>Data.Position then newData.CopyFrom(Data,Data.Size-Data.Position);
Data.Free;
Data:=newData;
Percent:=100;
if Assigned(FPercentChange) then FPercentChange(self,Percent);
Application.ProcessMessages;
end
else Encode:=False;
end;
function TASCIIInsert.Decode(ResultFile: TDataFile): Boolean;
var
S24: Array[0..2] of Byte;
Size: Integer;
outStrm: TMemoryStream;
DataBuffer: Array[0..1023] of Byte;
DataWritten: Integer;
CarrierBuffer: Array[0..1023] of Byte;
CarrierRead: Integer;
i,j: Integer;
d,c: Integer;
val: Integer;
linefeed: Boolean;
Cancel: Boolean;
begin
// decode first 3 bytes
Cancel:=False;
Data.Seek(0,soFromBeginning);
i:=0;
d:=0;
c:=0;
CarrierRead:=Data.Read(CarrierBuffer,1024);
linefeed:=False;
Percent:=0;
if Assigned(FPercentChange) then FPercentChange(self,Percent);
Application.ProcessMessages;
while i<3 do begin
val:=0;
while ((CarrierBuffer[c]<>$d) and ((CarrierBuffer[c]<>$0a) or ((CarrierBuffer[c]=$0a) and (linefeed)))) do begin
linefeed:=False;
if ((c>CarrierRead-2) and (CarrierRead=1024)) then begin
CarrierRead:=Data.Read(CarrierBuffer,1024);
c:=0;
end
else Inc(c);
end;
if CarrierBuffer[c]=$d then linefeed:=True;
for j:=7 downto 0 do begin
if CarrierBuffer[c-j-1]=$09 then val:=val+(1 shl j);
end;
if c<CarrierRead-1 then Inc(c)
else begin
CarrierRead:=Data.Read(CarrierBuffer,1024);
c:=0;
end;
S24[d]:=val;
Inc(DataWritten);
Inc(d);
Inc(i);
end;
// then decode other data
Size:=S24[0]+(S24[1] Shl 8)+(S24[2] Shl 16);
outStrm:=TMemoryStream.Create;
DataWritten:=0;
i:=0;
d:=0;
while (i<Size) and not(Cancel) do begin
if (d=1024) then begin
outStrm.Write(DataBuffer,1024);
DataWritten:=0;
d:=0;
end;
val:=0;
val:=0;
while ((CarrierBuffer[c]<>$d) and ((CarrierBuffer[c]<>$0a) or ((CarrierBuffer[c]=$0a) and (linefeed)))) do begin
linefeed:=False;
if ((c=CarrierRead) and (CarrierRead=1024)) then begin
CarrierRead:=Data.Read(CarrierBuffer,1024);
c:=0;
if CarrierRead=0 then begin
Cancel:=True;
break;
end;
end
else Inc(c);
end;
if CarrierBuffer[c]=$d then linefeed:=True;
for j:=7 downto 0 do begin
if CarrierBuffer[c-j-1]=$09 then val:=val+(1 shl j);
end;
if c<CarrierRead-1 then Inc(c)
else begin
CarrierRead:=Data.Read(CarrierBuffer,1024);
c:=0;
end;
DataBuffer[d]:=val;
Inc(DataWritten);
Inc(d);
Inc(i);
Percent:=Trunc(i/Size);
if Assigned(FPercentChange) then FPercentChange(self,Percent);
if Assigned(FWantCancel) then FWantCancel(self,Cancel);
Application.ProcessMessages;
end;
outStrm.Write(DataBuffer,DataWritten);
ResultFile.LoadFromStream(outStrm);
outStrm.Free;
Percent:=100;
if Assigned(FPercentChange) then FPercentChange(self,Percent);
Application.ProcessMessages;
Decode:=True;
end;
end.
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -