论坛风格切换切换到宽版
  • 1999阅读
  • 4回复

请问Inno的补丁包可以制作成,将要覆盖的文件保存至另个文件夹里吗 [复制链接]

上一主题 下一主题
离线373723699
 

发帖
38
金钱
380
威望
38
只看楼主 倒序阅读 0 发表于: 2016-10-12
请问Inno的补丁包可以制作成,将要覆盖替换的路径下这个文件,先保存至另个文件夹里,再替换补丁包里的吗
离线wanfu

发帖
2728
金钱
12110
威望
1211
只看该作者 1 发表于: 2016-10-13
试试下面的脚本,我测试通过:
  1. [Setup]
  2. AppName=My Program
  3. AppVerName=My Program version 1.5
  4. DefaultDirName={pf}\My Program
  5. DisableProgramGroupPage=yes
  6. UninstallDisplayIcon={app}\MyProg.exe
  7. OutputDir=userdocs:Inno Setup Examples Output
  8. [Files]
  9. ; Install our DLL to {app} so we can access it at uninstall time
  10. Source: "MyDll.dll"; DestDir: "{app}"
  11. [Code]
  12. //Mode = False 备份文件到 {App}\Backup 文件夹下,保留原文件的相对路径
  13. //Mode = True 还原备份文件到 {App} 文件夹下,保留原文件的相对路径
  14. //DelFile = True 时,复制成功则删除原始文件
  15. Function Backup(Files: TArrayOfString; DelFile: Boolean; Mode: Boolean): Boolean;
  16. var
  17.   i,k,n: Integer;
  18.   s: string;
  19. begin
  20.   //获取 {App} 字符串长度
  21.   k := Length(ExpandConstant('{app}'));
  22.   //获取 Files 列表项数
  23.   n := GetArrayLength(Files) - 1;
  24.   //复制文件到目标文件夹
  25.   if Mode = False then begin
  26.      for i := 0 to n do
  27.          begin
  28.          if FileExists(Files[i]) then
  29.             s := Files[i];
  30.             Insert('\Backup',Files[i],k + 1);
  31.             if not DirExists(Files[i]) then ForceDirectories(ExtractFileDir(Files[i]));
  32.             if FileCopy(s,Files[i],False) then
  33.                if DelFile = True then DeleteFile(s);
  34.          end;
  35.      end
  36.   else begin
  37.      for i := 0 to n do
  38.          begin
  39.          s := Files[i];
  40.          Insert('\Backup',Files[i],k + 1);
  41.          if FileExists(Files[i]) then
  42.             if FileCopy(Files[i],s,False) then
  43.                if DelFile = True then DeleteFile(Files[i]);
  44.          end;
  45.      end
  46. end;
  47. //当安装准备就绪时备份文件
  48. procedure CurPageChanged(CurPageID: Integer);
  49. var
  50.   Files: TArrayOfString;
  51. begin
  52.   if CurPageID = wpReady then begin
  53.     // 准备要备份的文件列表
  54.     SetArrayLength(Files,3)
  55.     Files[0] := ExpandConstant('{app}\A.exe');
  56.     Files[1] := ExpandConstant('{app}\B.dll');
  57.     Files[2] := ExpandConstant('{app}\C.ocx');
  58.     Backup(Files,True,False);
  59.   end;
  60. end;
  61. //卸载时还原备份文件
  62. procedure CurUninstallStepChanged(CurUninstallStep: TUninstallStep);
  63. Var
  64.   Files: TArrayOfString;
  65. begin
  66.   if CurUninstallStep = usUninstall then begin
  67.     // 准备要备份的文件列表
  68.     SetArrayLength(Files,3)
  69.     Files[0] := ExpandConstant('{app}\A.exe');
  70.     Files[1] := ExpandConstant('{app}\B.dll');
  71.     Files[2] := ExpandConstant('{app}\C.ocx');
  72.     Backup(Files,True,True);
  73.     DelTree(ExpandConstant('{app}\Backup'), True, True, True);
  74.   end;
  75. end;

离线wanfu

发帖
2728
金钱
12110
威望
1211
只看该作者 2 发表于: 2016-10-13
上面的脚本太复杂,而且适用性有局限,改一下,可以自定义任意文件夹中的备份文件:

[Setup]
AppName=My Program
AppVerName=My Program version 1.5
DefaultDirName={pf}\My Program
DisableProgramGroupPage=yes
UninstallDisplayIcon={app}\MyProg.exe
OutputDir=userdocs:Inno Setup Examples Output

[Files]
; Install our DLL to {app} so we can access it at uninstall time
; Source: "MyDll.dll"; DestDir: "{app}"

[Code]
//备份文件
//复制 ExistFile 到 NewFile,保留时间戳和文件属性,成功返回 True,否则返回 False。
//FailIfExists = True 时,NewFile 存在时不覆盖,否则覆盖。
//DelFile = True 时,复制成功后删除 ExistFile 文件
Function Backup(ExistFile, NewFile: String; FailIfExists, DelFile: Boolean): Boolean;
Var
  NewDir: string;
begin
   if FileExists(ExistFile) then
      NewDir := ExtractFileDir(NewFile); //提取文件路径中的路径(不含文件名)
      if not DirExists(NewDir) then ForceDirectories(NewDir); //目标路径不存在时创建
      Result := FileCopy(ExistFile,NewFile,FailIfExists); //复制文件
      if Result then begin
          if DelFile = True then DeleteFile(ExistFile); //DelFile = True 时删除已备份的源文件
      end;
end;

//在安装准备就绪,实际安装开始之前备份文件
procedure CurStepChanged(CurStep: TSetupStep );
begin
  if CurStep = ssInstall then
    Backup(ExpandConstant('{app}\A.exe'),ExpandConstant('{app}\Backup\A.exe'),True,False);
    Backup(ExpandConstant('{app}\B.dll'),ExpandConstant('{app}\Backup\B.dll'),True,False);
    Backup(ExpandConstant('{app}\C.dll'),ExpandConstant('{app}\Backup\C.dll'),True,False);
end;

//卸载时还原备份文件
procedure CurUninstallStepChanged(CurUninstallStep: TUninstallStep);
begin
  if CurUninstallStep = usUninstall then
    Backup(ExpandConstant('{app}\Backup\A.exe'),ExpandConstant('{app}\A.exe'),False,True);
    Backup(ExpandConstant('{app}\Backup\B.dll'),ExpandConstant('{app}\B.dll'),False,True);
    Backup(ExpandConstant('{app}\Backup\C.dll'),ExpandConstant('{app}\C.dll'),False,True);
    DelTree(ExpandConstant('{app}\Backup'), True, True, True); //删除 Backup 文件夹及其子文件夹
end;
离线373723699

发帖
38
金钱
380
威望
38
只看该作者 3 发表于: 2016-12-01
回 2楼(wanfu) 的帖子
wanfu:上面的脚本太复杂,而且适用性有局限,改一下,可以自定义任意文件夹中的备份文件:[Setup]AppName=My ProgramAppVerName=My Program version 1.5....... (2016-10-13 23:24) 

补充问一下,这个只能备份文件吗
SetArrayLength(Files,3)
   Files[0] := ExpandConstant('{app}\A.exe');
   Files[1] := ExpandConstant('{app}\B.dll');
   Files[2] := ExpandConstant('{app}\C.ocx');

能不能文件夹备份?
我试了下
Files[0] := ExpandConstant('{app}\1213\*');好像不行。有办法吗
离线lovelost

发帖
140
金钱
1060
威望
106
只看该作者 4 发表于: 2016-12-02
如果仅要备份完整的文件夹,可以自己写段简单的代码来实现:
[CODE]
Procedure BackupFld(OldFldrName,NewFldrName:string);
begin
  if
DirExists(OldFldrName) then
    begin
      if not
DirExists(NewFldrName) then
       begin

          RenameFile(OldFldrName,NewFldrName);
          CreateDir(OldFldrName);
        end
      else
        MsgBox
('备份文件夹已存在!',mbError,mb_OK);
    end;
end;

如果你还想把原文件夹里原部份文件保留过来,自己在中间加条复制命令就可以了。
BTW:如果你要备份的文件夹是在Program Files文件夹里,安装程序是需要管理员身份运行的,不然会失败。