下面代码是我从网上找到的,是用来把DestExeFile的图标替换成SourceExeFile的图标,但替换出来的图标与原图标效果相差很远,为什么?
function ReplIcon(const SourceExeFile,DestExeFile :AnsiString):Boolean;
const
Readlen=10; //每次读取字节数,可改变
icolen=766;//32*32图标长度,根据研究前126为图标头,后640为图标数据
var
i,j,itemp,nPos:int64;// nPos为目的图标在目的文件的位置
ci,cj:array[0..readlen-1] of char;
bOK:boolean;
SourceIcon,DestIcon:TIcon;
SIconStream,sDest,s:TMemoryStream;
begin
bOK:=false;
Result :=False;
if AnsiUpperCase(ExtractFileExt(SourceExeFile))<>'.EXE' then
begin
ShowMessage(AnsiUpperCase(ExtractFileExt(SourceExeFile)));
Exit;
end;
if AnsiUpperCase(ExtractFileExt(DestExeFile))<>'.EXE' then
Exit; try
SourceIcon:=TIcon.Create;
DestIcon:=TIcon.Create;
SIconStream:=TMemoryStream.Create;
SDest:=TMemoryStream.Create;
s:=TMemoryStream.Create;
//选择第一个图标,选择第N个图标为 ExtractIcon(handle,PChar(SourceFile),N-1)
SourceIcon.Handle:=ExtractIcon(Application.Handle,PChar(SourceExeFile),0);
DestIcon.Handle:=ExtractIcon(Application.Handle,PChar(DestExeFile),0);
DestIcon.SaveToStream(sIconStream);
sDest.LoadFromFile(DestExeFile);
i:=0;
j:=0; //以下程序查找目的图标在目的程序中的位置
while i< sDest.size do
begin
itemp:=i;
j:=126;
{repeat
SDest.Position:=i;
sDest.read(ci,Readlen);
SiconStream.Position:=j;
SIconStream.Read(cj,Readlen);
i:=i+Readlen;
j:=j+Readlen;
until (String(ci)=String(cj)) and (i<sDest.size) and (j<icolen);
}
ci:='';
cj:='';
while (String(ci)=String(cj)) and (i<SDest.size) and (j<icolen) do
begin
i:=i+readlen;
j:=j+readlen;
SDest.Position:=i;
SDest.read(ci,readlen);
SiconStream.Position:=j;
SiconStream.Read(cj,readlen);
end;
if j<icolen then
i:=itemp+1 //没找到
else
begin
nPos:=itemp; //找到
bOK:=true;
break;
end;
end;
if bOK=false then
exit;//目标文件二进制码中未找到图标
SIconStream.Clear;//将源程序图标存入
SourceIcon.SaveToStream(SIconStream); SIconStream.position:=126;
sDest.Position:=0;
s.CopyFrom(sDest,nPos);//将目的程序图标前数据拷入
s.CopyFrom(SIconStream,640); //将源程序图标拷入
if sDest.size>sDest.Position+640 then //将目的程序剩余数据拷入
begin
sDest.Position:=sDest.Position+640;
s.CopyFrom(sDest,sDest.Size-sDest.Position);
end;
s.SaveToFile(DestExeFile);
Result :=True;
finally
SourceIcon.Free;
DestIcon.Free; //改造好的程序存放在本目录Result.exe文件中
SIconStream.Free;
s.Free;
sDest.Free;
end;
end;
function ReplIcon(const SourceExeFile,DestExeFile :AnsiString):Boolean;
const
Readlen=10; //每次读取字节数,可改变
icolen=766;//32*32图标长度,根据研究前126为图标头,后640为图标数据
var
i,j,itemp,nPos:int64;// nPos为目的图标在目的文件的位置
ci,cj:array[0..readlen-1] of char;
bOK:boolean;
SourceIcon,DestIcon:TIcon;
SIconStream,sDest,s:TMemoryStream;
begin
bOK:=false;
Result :=False;
if AnsiUpperCase(ExtractFileExt(SourceExeFile))<>'.EXE' then
begin
ShowMessage(AnsiUpperCase(ExtractFileExt(SourceExeFile)));
Exit;
end;
if AnsiUpperCase(ExtractFileExt(DestExeFile))<>'.EXE' then
Exit; try
SourceIcon:=TIcon.Create;
DestIcon:=TIcon.Create;
SIconStream:=TMemoryStream.Create;
SDest:=TMemoryStream.Create;
s:=TMemoryStream.Create;
//选择第一个图标,选择第N个图标为 ExtractIcon(handle,PChar(SourceFile),N-1)
SourceIcon.Handle:=ExtractIcon(Application.Handle,PChar(SourceExeFile),0);
DestIcon.Handle:=ExtractIcon(Application.Handle,PChar(DestExeFile),0);
DestIcon.SaveToStream(sIconStream);
sDest.LoadFromFile(DestExeFile);
i:=0;
j:=0; //以下程序查找目的图标在目的程序中的位置
while i< sDest.size do
begin
itemp:=i;
j:=126;
{repeat
SDest.Position:=i;
sDest.read(ci,Readlen);
SiconStream.Position:=j;
SIconStream.Read(cj,Readlen);
i:=i+Readlen;
j:=j+Readlen;
until (String(ci)=String(cj)) and (i<sDest.size) and (j<icolen);
}
ci:='';
cj:='';
while (String(ci)=String(cj)) and (i<SDest.size) and (j<icolen) do
begin
i:=i+readlen;
j:=j+readlen;
SDest.Position:=i;
SDest.read(ci,readlen);
SiconStream.Position:=j;
SiconStream.Read(cj,readlen);
end;
if j<icolen then
i:=itemp+1 //没找到
else
begin
nPos:=itemp; //找到
bOK:=true;
break;
end;
end;
if bOK=false then
exit;//目标文件二进制码中未找到图标
SIconStream.Clear;//将源程序图标存入
SourceIcon.SaveToStream(SIconStream); SIconStream.position:=126;
sDest.Position:=0;
s.CopyFrom(sDest,nPos);//将目的程序图标前数据拷入
s.CopyFrom(SIconStream,640); //将源程序图标拷入
if sDest.size>sDest.Position+640 then //将目的程序剩余数据拷入
begin
sDest.Position:=sDest.Position+640;
s.CopyFrom(sDest,sDest.Size-sDest.Position);
end;
s.SaveToFile(DestExeFile);
Result :=True;
finally
SourceIcon.Free;
DestIcon.Free; //改造好的程序存放在本目录Result.exe文件中
SIconStream.Free;
s.Free;
sDest.Free;
end;
end;
解决方案 »
免费领取超大流量手机卡,每月29元包185G流量+100分钟通话, 中国电信官方发货