mirror of
https://github.com/doublecmd/doublecmd.git
synced 2026-06-21 09:58:13 +00:00
690 lines
21 KiB
ObjectPascal
690 lines
21 KiB
ObjectPascal
{
|
|
Double Commander
|
|
-------------------------------------------------------------------------
|
|
File packing window
|
|
|
|
Copyright (C) 2007-2022 Alexander Koblov (alexx2000@mail.ru)
|
|
|
|
This program is free software; you can redistribute it and/or modify
|
|
it under the terms of the GNU General Public License as published by
|
|
the Free Software Foundation; either version 2 of the License, or
|
|
(at your option) any later version.
|
|
|
|
This program is distributed in the hope that it will be useful,
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
GNU General Public License for more details.
|
|
|
|
You should have received a copy of the GNU General Public License
|
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
}
|
|
|
|
unit fPackDlg;
|
|
|
|
{$mode objfpc}{$H+}
|
|
|
|
interface
|
|
|
|
uses
|
|
SysUtils, Forms, Controls, Dialogs, StdCtrls, EditBtn, ExtCtrls, Buttons,
|
|
Menus, DividerBevel, uWcxArchiveFileSource, uArchiveFileSource, uFile,
|
|
uFileSource, Classes, fButtonForm, uFileSourceOperation;
|
|
|
|
type
|
|
|
|
{ TfrmPackDlg }
|
|
|
|
TfrmPackDlg = class(TfrmButtonForm)
|
|
btnConfig: TButton;
|
|
btnHelp: TButton;
|
|
cbCreateSeparateArchives: TCheckBox;
|
|
cbCreateSFX: TCheckBox;
|
|
cbEncrypt: TCheckBox;
|
|
cbMoveToArchive: TCheckBox;
|
|
cbMultivolume: TCheckBox;
|
|
cbPackerList: TComboBox;
|
|
cbOtherPlugins: TCheckBox;
|
|
cbPutInTarFirst: TCheckBox;
|
|
DividerBevel: TDividerBevel;
|
|
edtPackCmd: TDirectoryEdit;
|
|
lblPrompt: TLabel;
|
|
cbStoreDir: TCheckBox;
|
|
rgPacker: TRadioGroup;
|
|
pnlOptions: TPanel;
|
|
procedure btnConfigClick(Sender: TObject);
|
|
procedure cbCreateSeparateArchivesChange(Sender: TObject);
|
|
procedure cbCreateSFXClick(Sender: TObject);
|
|
procedure cbOtherPluginsChange(Sender: TObject);
|
|
procedure cbPutInTarFirstChange(Sender: TObject);
|
|
procedure edtPackCmdAcceptDirectory(Sender: TObject; var Value: String);
|
|
procedure FormShow(Sender: TObject);
|
|
procedure arbChange(Sender: TObject);
|
|
|
|
private
|
|
FArchiveExt,
|
|
FArchiveName,
|
|
FArchiveType: String;
|
|
FArchiveTypeCount: Integer;
|
|
FHasFolder,
|
|
FNewArchive,
|
|
FExistsArchive : Boolean;
|
|
FSourceFileSource: IFileSource;
|
|
FTargetFileSource: IArchiveFileSource;
|
|
FPlugin: Boolean;
|
|
FPassword: String;
|
|
FVolumeSize: String;
|
|
FCustomParams: String;
|
|
FTargetPathInArchive: String;
|
|
procedure SwitchOptions(ArcTypeChange: Boolean);
|
|
procedure ChangeArchiveExt(const NewArcExt: String);
|
|
procedure AddArchiveType(const FileExt, ArcType: String);
|
|
procedure OnPackCopyOutStateChanged(Operation: TFileSourceOperation;
|
|
State: TFileSourceOperationState);
|
|
procedure PackFiles(const SourceFileSource: IFileSource; var Files: TFiles);
|
|
public
|
|
{ public declarations }
|
|
end;
|
|
|
|
// Frees 'Files'.
|
|
procedure ShowPackDlg(TheOwner: TComponent;
|
|
const SourceFileSource: IFileSource;
|
|
const TargetFileSource: IArchiveFileSource;
|
|
var Files: TFiles;
|
|
TargetArchivePath: String;
|
|
TargetPathInArchive: String;
|
|
bNewArchive : Boolean = True);
|
|
|
|
implementation
|
|
|
|
{$R *.lfm}
|
|
|
|
uses
|
|
StrUtils, WcxPlugin, uGlobs, uDCUtils, uLng, uOSUtils,
|
|
uOperationsManager, uArchiveFileSourceUtil, uMultiArchiveFileSource,
|
|
uWcxArchiveCopyInOperation, uMultiArchiveCopyInOperation, uMasks,
|
|
DCStrUtils, uMultiArc, uWcxModule, uTempFileSystemFileSource,
|
|
uFileSourceCopyOperation, uShowForm, uShowMsg;
|
|
|
|
procedure ShowPackDlg(TheOwner: TComponent;
|
|
const SourceFileSource: IFileSource;
|
|
const TargetFileSource: IArchiveFileSource;
|
|
var Files: TFiles;
|
|
TargetArchivePath: String;
|
|
TargetPathInArchive: String;
|
|
bNewArchive : Boolean = True);
|
|
var
|
|
I: Integer;
|
|
PackDialog: TfrmPackDlg;
|
|
begin
|
|
PackDialog := TfrmPackDlg.Create(TheOwner);
|
|
{$IF DEFINED(LCLGTK2)}
|
|
// TRadioGroup.ItemIndex:= -1 will not work under Gtk2
|
|
// if items have been added dynamically, this workaround fixes it
|
|
PackDialog.rgPacker.Items.Add(EmptyStr);
|
|
PackDialog.rgPacker.Items.Clear;
|
|
{$ENDIF}
|
|
try
|
|
with PackDialog do
|
|
begin
|
|
FArchiveType:= 'none';
|
|
FNewArchive:= bNewArchive;
|
|
FSourceFileSource:= SourceFileSource;
|
|
FTargetFileSource:= TargetFileSource;
|
|
FTargetPathInArchive:= TargetPathInArchive;
|
|
FArchiveExt:= ExtensionSeparator + FArchiveType;
|
|
if bNewArchive then // create new archive
|
|
begin
|
|
if Files.Count = 1 then // if one file selected
|
|
begin
|
|
FArchiveName:= Files[0].NameNoExt;
|
|
FHasFolder:= Files[0].IsDirectory or Files[0].IsLinkToDirectory;
|
|
edtPackCmd.Text := TargetArchivePath + FArchiveName + ExtensionSeparator + FArchiveType;
|
|
end
|
|
else // if some files selected
|
|
begin
|
|
FHasFolder:= False;
|
|
for I:= 0 to Files.Count - 1 do
|
|
begin
|
|
if Files[I].IsDirectory or Files[I].IsLinkToDirectory then
|
|
begin
|
|
FHasFolder:= True;
|
|
Break;
|
|
end;
|
|
end;
|
|
FArchiveName:= MakeFileName(Files.Path, 'archive');
|
|
edtPackCmd.Text := TargetArchivePath + FArchiveName + ExtensionSeparator + FArchiveType;
|
|
end
|
|
end
|
|
else // pack in exsists archive
|
|
begin
|
|
if Assigned(TargetFileSource) then
|
|
edtPackCmd.Text := TargetFileSource.ArchiveFileName;
|
|
end;
|
|
|
|
if (ShowModal = mrOK) then
|
|
begin
|
|
case PrepareData(SourceFileSource, Files, @OnPackCopyOutStateChanged) of
|
|
pdrInCallback:
|
|
PackDialog:= nil;
|
|
pdrSynchronous:
|
|
PackFiles(SourceFileSource, Files);
|
|
end;
|
|
end;
|
|
end;
|
|
finally
|
|
FreeAndNil(PackDialog);
|
|
FreeAndNil(Files);
|
|
end;
|
|
end;
|
|
|
|
const
|
|
TAR_EXT = '.tar';
|
|
|
|
{ TfrmPackDlg }
|
|
|
|
procedure TfrmPackDlg.FormShow(Sender: TObject);
|
|
var
|
|
I, J : Integer;
|
|
sExt : String;
|
|
begin
|
|
FArchiveTypeCount := 0;
|
|
FExistsArchive := (FArchiveType <> 'none');
|
|
|
|
// WCX plugins
|
|
for I:=0 to gWCXPlugins.Count - 1 do
|
|
if gWCXPlugins.Enabled[I] then
|
|
begin
|
|
if (gWCXPlugins.Flags[I] and PK_CAPS_NEW) = PK_CAPS_NEW then
|
|
begin
|
|
AddArchiveType(FArchiveType, gWCXPlugins.Ext[I]);
|
|
end;
|
|
end;
|
|
// MultiArc addons
|
|
for I:= 0 to gMultiArcList.Count - 1 do
|
|
if gMultiArcList[I].FEnabled and (gMultiArcList[I].FAdd <> EmptyStr) then
|
|
begin
|
|
J:= 1;
|
|
repeat
|
|
sExt:= ExtractDelimited(J, gMultiArcList[I].FExtension, [',']);
|
|
if Length(sExt) = 0 then Break;
|
|
AddArchiveType(FArchiveType, sExt);
|
|
Inc(J);
|
|
until False;
|
|
end;
|
|
|
|
if (rgPacker.Items.Count > 0) and (rgPacker.ItemIndex < 0) and (not cbOtherPlugins.Checked) then
|
|
rgPacker.ItemIndex := 0;
|
|
if cbPackerList.Items.Count > 0 then
|
|
begin
|
|
cbOtherPlugins.Visible := True;
|
|
cbPackerList.Visible := True;
|
|
|
|
if FExistsArchive then
|
|
cbPackerList.Enabled:= False
|
|
else
|
|
cbOtherPlugins.Enabled := True;
|
|
|
|
if cbPackerList.ItemIndex < 0 then
|
|
cbPackerList.ItemIndex := 0;
|
|
end
|
|
else
|
|
btnConfig.AnchorToCompanion(akTop, 6, rgPacker);
|
|
end;
|
|
|
|
procedure TfrmPackDlg.btnConfigClick(Sender: TObject);
|
|
var
|
|
WcxFileSource: IWcxArchiveFileSource;
|
|
begin
|
|
try
|
|
WcxFileSource := TWcxArchiveFileSource.CreateByArchiveName(FSourceFileSource, edtPackCmd.Text, True);
|
|
if Assigned(WcxFileSource) then // WCX plugin
|
|
try
|
|
WcxFileSource.WcxModule.VFSConfigure(Handle);
|
|
finally
|
|
WcxFileSource := nil; // free interface
|
|
end
|
|
else // MultiArc addon
|
|
begin
|
|
FCustomParams:= InputBox(Caption, rsMsgArchiverCustomParams, FCustomParams);
|
|
end;
|
|
except
|
|
on e: Exception do
|
|
MessageDlg(e.Message, mtError, [mbOK], 0);
|
|
end;
|
|
end;
|
|
|
|
procedure TfrmPackDlg.cbCreateSeparateArchivesChange(Sender: TObject);
|
|
begin
|
|
if cbCreateSeparateArchives.Checked then
|
|
edtPackCmd.Text:= ExtractFilePath(edtPackCmd.Text) + '*.*' + FArchiveExt
|
|
else
|
|
edtPackCmd.Text:= ExtractFilePath(edtPackCmd.Text) + FArchiveName + FArchiveExt;
|
|
end;
|
|
|
|
procedure TfrmPackDlg.cbCreateSFXClick(Sender: TObject);
|
|
var
|
|
State: Boolean;
|
|
ANewExt: String;
|
|
begin
|
|
if cbCreateSFX.Tag = 0 then
|
|
begin
|
|
cbCreateSFX.Tag:= 1;
|
|
// Save check box state
|
|
State:= cbCreateSFX.Checked;
|
|
if State then
|
|
ANewExt:= GetSfxExt
|
|
else begin
|
|
ANewExt:= ExtensionSeparator + FArchiveType;
|
|
end;
|
|
ChangeArchiveExt(ANewExt);
|
|
// Switch archiver options
|
|
SwitchOptions(False);
|
|
// Restore check box state
|
|
cbCreateSFX.Checked:= State;
|
|
cbCreateSFX.Tag:= 0;
|
|
end;
|
|
end;
|
|
|
|
procedure TfrmPackDlg.cbOtherPluginsChange(Sender: TObject);
|
|
begin
|
|
if cbOtherPlugins.Checked then
|
|
begin
|
|
FArchiveType:= cbPackerList.Text;
|
|
SwitchOptions(True);
|
|
ChangeArchiveExt(FArchiveType);
|
|
rgPacker.ItemIndex := -1;
|
|
end
|
|
else begin
|
|
if rgPacker.ItemIndex = -1 then
|
|
rgPacker.ItemIndex := 0;
|
|
end;
|
|
FCustomParams:= EmptyStr;
|
|
cbPackerList.Enabled := cbOtherPlugins.Checked;
|
|
end;
|
|
|
|
procedure TfrmPackDlg.cbPutInTarFirstChange(Sender: TObject);
|
|
begin
|
|
if cbPutInTarFirst.Checked then
|
|
ChangeArchiveExt(FArchiveExt)
|
|
else if AnsiStartsText(TAR_EXT, FArchiveExt) then begin
|
|
ChangeArchiveExt(Copy(FArchiveExt, Length(TAR_EXT) + 1, MaxInt));
|
|
end;
|
|
end;
|
|
|
|
procedure TfrmPackDlg.edtPackCmdAcceptDirectory(Sender: TObject; var Value: String);
|
|
begin
|
|
Value := IncludeTrailingPathDelimiter(Value) + ExtractFileName(edtPackCmd.Text);
|
|
end;
|
|
|
|
procedure TfrmPackDlg.arbChange(Sender: TObject);
|
|
begin
|
|
if rgPacker.ItemIndex >= 0 then
|
|
begin
|
|
FArchiveType:= rgPacker.Items[rgPacker.ItemIndex];
|
|
SwitchOptions(True);
|
|
ChangeArchiveExt(FArchiveType);
|
|
cbOtherPlugins.Checked := False;
|
|
end;
|
|
FCustomParams:= EmptyStr;
|
|
end;
|
|
|
|
procedure TfrmPackDlg.SwitchOptions(ArcTypeChange: Boolean); // Ugly but working
|
|
var
|
|
I: LongInt;
|
|
sCmd: String;
|
|
begin
|
|
cbPutInTarFirst.OnChange:= nil;
|
|
|
|
try
|
|
if ArcTypeChange then
|
|
begin
|
|
// Reset some options
|
|
cbCreateSFX.Checked:= False;
|
|
end;
|
|
|
|
// WCX plugins
|
|
for I:= 0 to gWCXPlugins.Count - 1 do
|
|
begin
|
|
if gWCXPlugins.Enabled[I] and (gWCXPlugins.Ext[I] = FArchiveType) then
|
|
begin
|
|
// If plugin supports packing with password
|
|
EnableControl(cbEncrypt, ((gWCXPlugins.Flags[I] and PK_CAPS_ENCRYPT) <> 0));
|
|
// If archive can not contain multiple files
|
|
if ((gWCXPlugins.Flags[I] and PK_CAPS_MULTIPLE) = 0) then
|
|
begin
|
|
// If file list contain directory then
|
|
// put to the tar archive first is needed
|
|
if not FHasFolder then
|
|
cbCreateSeparateArchives.Checked:= True
|
|
else
|
|
begin
|
|
cbPutInTarFirst.Checked:= True;
|
|
EnableControl(cbPutInTarFirst, False);
|
|
end;
|
|
end
|
|
else
|
|
begin
|
|
sCmd:= LowerCase(FArchiveType);
|
|
cbPutInTarFirst.Checked:= False;
|
|
EnableControl(cbPutInTarFirst, not ((sCmd = 'tar') or StrBegins(sCmd, 'tar.')));
|
|
cbCreateSeparateArchives.Checked:= False;
|
|
end;
|
|
FPlugin:= True;
|
|
// Options that supported by plugins
|
|
EnableControl(cbStoreDir, True);
|
|
// Options that don't supported by plugins
|
|
cbMultivolume.Checked:= False;
|
|
EnableControl(cbMultivolume, False);
|
|
Exit;
|
|
end;
|
|
end;
|
|
|
|
// MultiArc addons
|
|
for I := 0 to gMultiArcList.Count - 1 do
|
|
begin
|
|
with gMultiArcList.Items[I] do
|
|
begin
|
|
if FEnabled and MatchesMaskList(FArchiveType, FExtension, ',') then
|
|
begin
|
|
// Archive can contain multiple files
|
|
cbCreateSeparateArchives.Checked:= False;
|
|
// If addon supports create self extracting archive
|
|
EnableControl(cbCreateSFX, (Length(FAddSelfExtract) <> 0));
|
|
|
|
if cbCreateSFX.Enabled and cbCreateSFX.Checked then
|
|
sCmd:= FAddSelfExtract
|
|
else
|
|
sCmd:= FAdd;
|
|
|
|
// If addon supports create multi volume archive
|
|
EnableControl(cbMultivolume, (Pos('%V', sCmd) <> 0));
|
|
// If addon supports packing with password
|
|
EnableControl(cbEncrypt, (Pos('%W', sCmd) <> 0));
|
|
|
|
// If archive can not contain multiple files
|
|
if (mafFileNameList in FFlags) then
|
|
begin
|
|
// If file list contain directory then
|
|
// put to the tar archive first is needed
|
|
if not FHasFolder then
|
|
cbCreateSeparateArchives.Checked:= True
|
|
else
|
|
begin
|
|
cbPutInTarFirst.Checked:= True;
|
|
EnableControl(cbPutInTarFirst, False);
|
|
end;
|
|
end
|
|
else begin
|
|
sCmd:= LowerCase(FArchiveType);
|
|
cbPutInTarFirst.Checked:= False;
|
|
EnableControl(cbPutInTarFirst, not ((sCmd = 'tar') or StrBegins(sCmd, 'tar.')));
|
|
cbCreateSeparateArchives.Checked:= False;
|
|
end;
|
|
FPlugin:= False;
|
|
// Options that don't supported by addons
|
|
cbStoreDir.Checked:= True;
|
|
EnableControl(cbStoreDir, False);
|
|
Exit;
|
|
end;
|
|
end;
|
|
end;
|
|
finally
|
|
cbPutInTarFirst.OnChange:= @cbPutInTarFirstChange;
|
|
end;
|
|
end;
|
|
|
|
procedure TfrmPackDlg.ChangeArchiveExt(const NewArcExt: String);
|
|
var
|
|
AOldExt, ATarExt: String;
|
|
begin
|
|
AOldExt:= FArchiveExt;
|
|
ATarExt:= IfThen(cbPutInTarFirst.Checked, TAR_EXT);
|
|
if StrBegins(NewArcExt, ExtensionSeparator) then
|
|
begin
|
|
if AnsiStartsText(ATarExt, NewArcExt) then
|
|
FArchiveExt:= NewArcExt
|
|
else
|
|
FArchiveExt:= ATarExt + NewArcExt;
|
|
end
|
|
else begin
|
|
FArchiveExt:= ATarExt + ExtensionSeparator + NewArcExt;
|
|
end;
|
|
if AnsiEndsText(AOldExt, edtPackCmd.Text) then
|
|
begin
|
|
edtPackCmd.Text:= Copy(edtPackCmd.Text, 1, Length(edtPackCmd.Text) - Length(AOldExt)) + FArchiveExt;
|
|
end;
|
|
end;
|
|
|
|
procedure TfrmPackDlg.AddArchiveType(const FileExt, ArcType: String);
|
|
var
|
|
iIndex: Integer;
|
|
begin
|
|
// First 9 plugins we display as RadioButtons
|
|
if FArchiveTypeCount < 9 then
|
|
begin
|
|
iIndex := rgPacker.Items.Add(ArcType);
|
|
if FExistsArchive then
|
|
begin
|
|
if (FileExt = ArcType) then
|
|
rgPacker.ItemIndex := iIndex
|
|
else
|
|
rgPacker.Controls[iIndex + 1].Enabled := False;
|
|
end
|
|
else if (gLastUsedPacker = ArcType) then
|
|
begin
|
|
rgPacker.ItemIndex := iIndex;
|
|
end;
|
|
FArchiveTypeCount := FArchiveTypeCount + 1;
|
|
end
|
|
else // Other plugins we add in ComboBox
|
|
begin
|
|
iIndex := cbPackerList.Items.Add(ArcType);
|
|
if (gLastUsedPacker = ArcType) or (FExistsArchive and (FileExt = ArcType)) then
|
|
begin
|
|
cbPackerList.ItemIndex := iIndex;
|
|
cbOtherPlugins.Checked := True;
|
|
end;
|
|
end;
|
|
end;
|
|
|
|
procedure TfrmPackDlg.OnPackCopyOutStateChanged(Operation: TFileSourceOperation;
|
|
State: TFileSourceOperationState);
|
|
var
|
|
aFiles: TFiles;
|
|
aFileSource: ITempFileSystemFileSource;
|
|
aCopyOutOperation: TFileSourceCopyOperation absolute Operation;
|
|
begin
|
|
if (State = fsosStopped) then
|
|
try
|
|
if (Operation.Result = fsorFinished) then
|
|
begin
|
|
aFileSource := aCopyOutOperation.TargetFileSource as ITempFileSystemFileSource;
|
|
aFiles := aCopyOutOperation.SourceFiles.Clone;
|
|
ChangeFileListRoot(aFileSource.FileSystemRoot, aFiles);
|
|
PackFiles(aFileSource, aFiles);
|
|
end;
|
|
finally
|
|
Free;
|
|
end;
|
|
end;
|
|
|
|
procedure TfrmPackDlg.PackFiles(const SourceFileSource: IFileSource;
|
|
var Files: TFiles);
|
|
var
|
|
I: Integer;
|
|
aFlags : PtrInt;
|
|
aFile: TFile = nil;
|
|
aFiles: TFiles = nil;
|
|
Operation: TFileSourceOperation;
|
|
NewTargetFileSource: IArchiveFileSource = nil;
|
|
|
|
procedure Pack(var FilesToPack: TFiles; QueueId: TOperationsManagerQueueIdentifier);
|
|
begin
|
|
if Assigned(NewTargetFileSource) then
|
|
begin
|
|
// Set flags according to user selection in the pack dialog.
|
|
aFlags := 0;
|
|
if cbMoveToArchive.Checked then aFlags := aFlags or PK_PACK_MOVE_FILES;
|
|
if cbStoreDir.Checked then aFlags := aFlags or PK_PACK_SAVE_PATHS;
|
|
if cbEncrypt.Checked then aFlags := aFlags or PK_PACK_ENCRYPT;
|
|
|
|
Operation := NewTargetFileSource.CreateCopyInOperation(
|
|
SourceFileSource,
|
|
FilesToPack,
|
|
FTargetPathInArchive);
|
|
|
|
if Assigned(Operation) then
|
|
begin
|
|
if NewTargetFileSource.IsInterface(IWcxArchiveFileSource) then
|
|
begin
|
|
with Operation as TWcxArchiveCopyInOperation do
|
|
begin
|
|
PackingFlags:= aFlags;
|
|
CreateNew:= FNewArchive;
|
|
TarBefore:= cbPutInTarFirst.Checked;
|
|
end;
|
|
end
|
|
else if NewTargetFileSource.IsInterface(IMultiArchiveFileSource) then
|
|
begin
|
|
with Operation as TMultiArchiveCopyInOperation do
|
|
begin
|
|
if cbEncrypt.Checked then
|
|
Password:= FPassword;
|
|
if cbMultivolume.Checked then
|
|
VolumeSize:= FVolumeSize;
|
|
PackingFlags := aFlags;
|
|
CreateNew:= FNewArchive;
|
|
CustomParams:= FCustomParams;
|
|
TarBefore:= cbPutInTarFirst.Checked;
|
|
end;
|
|
end;
|
|
|
|
// Start operation.
|
|
OperationsManager.AddOperation(Operation, QueueId, False, True);
|
|
end;
|
|
end;
|
|
end;
|
|
|
|
var
|
|
sPassword, sPasswordTmp: String;
|
|
QueueId: TOperationsManagerQueueIdentifier;
|
|
begin
|
|
if Assigned(FTargetFileSource) then
|
|
begin
|
|
// Already have a target file source.
|
|
// It must be an archive file source.
|
|
if not (FTargetFileSource.IsClass(TArchiveFileSource)) then
|
|
raise Exception.Create('Invalid target file source type');
|
|
|
|
NewTargetFileSource := FTargetFileSource;
|
|
end
|
|
else // Create a new target file source.
|
|
begin
|
|
if not FPlugin then
|
|
begin
|
|
if cbEncrypt.Checked then
|
|
begin
|
|
sPassword:= EmptyStr;
|
|
sPasswordTmp:= EmptyStr;
|
|
repeat
|
|
if not InputQuery(Caption, rsMsgPasswordEnter, True, sPassword) then
|
|
Exit;
|
|
if gRepeatPassword then
|
|
begin
|
|
if not InputQuery(Caption, rsMsgPasswordVerify, True, sPasswordTmp) then
|
|
Exit;
|
|
end
|
|
else
|
|
sPasswordTmp:= sPassword;
|
|
if sPassword <> sPasswordTmp then
|
|
ShowMessage(rsMsgPasswordDiff)
|
|
else
|
|
FPassword:= sPassword;
|
|
until sPassword = sPasswordTmp;
|
|
end;
|
|
|
|
if cbMultivolume.Checked then
|
|
begin
|
|
if not ShowInputComboBox(Caption, rsMsgVolumeSizeEnter, glsVolumeSizeHistory, FVolumeSize) then
|
|
Exit;
|
|
end;
|
|
end;
|
|
|
|
// If create separate archives, one per selected file/dir
|
|
if cbCreateSeparateArchives.Checked then
|
|
begin
|
|
// If files count > 1 then put to queue
|
|
if (Files.Count > 1) and (QueueIdentifier = FreeOperationsQueueId) then
|
|
QueueId := OperationsManager.GetNewQueueIdentifier
|
|
else begin
|
|
QueueId := QueueIdentifier;
|
|
end;
|
|
// Pack all selected files
|
|
for I:= 0 to Files.Count - 1 do
|
|
begin
|
|
// Fill files to pack
|
|
aFiles:= TFiles.Create(Files.Path);
|
|
try
|
|
aFiles.Add(Files[I].Clone);
|
|
FArchiveName:= GetAbsoluteFileName(Files.Path, edtPackCmd.Text);
|
|
try
|
|
// Check if there is an ArchiveFileSource for possible archive.
|
|
aFile := SourceFileSource.CreateFileObject(ExtractFilePath(FArchiveName));
|
|
try
|
|
aFile.Name := Files[I].Name + FArchiveExt;
|
|
NewTargetFileSource := GetArchiveFileSource(SourceFileSource, aFile, FArchiveType, False, True);
|
|
finally
|
|
FreeAndNil(aFile);
|
|
end;
|
|
except
|
|
on E: Exception do
|
|
begin
|
|
if (E is EFileSourceException) or (E is EWcxModuleException) then
|
|
begin
|
|
if MessageDlg(E.Message, mtError, [mbIgnore, mbAbort], 0) = mrIgnore then
|
|
Continue;
|
|
Exit;
|
|
end;
|
|
raise;
|
|
end;
|
|
end;
|
|
// Pack current item
|
|
Pack(aFiles, QueueId);
|
|
finally
|
|
FreeAndNil(aFiles);
|
|
end;
|
|
end; // for
|
|
end
|
|
else
|
|
begin
|
|
FArchiveName:= GetAbsoluteFileName(Files.Path, edtPackCmd.Text);
|
|
try
|
|
// Check if there is an ArchiveFileSource for possible archive.
|
|
aFile := SourceFileSource.CreateFileObject(ExtractFilePath(FArchiveName));
|
|
try
|
|
aFile.Name := ExtractFileName(FArchiveName);
|
|
NewTargetFileSource := GetArchiveFileSource(SourceFileSource, aFile, FArchiveType, False, True);
|
|
finally
|
|
FreeAndNil(aFile);
|
|
end;
|
|
except
|
|
on E: Exception do
|
|
begin
|
|
if (E is EFileSourceException) or (E is EWcxModuleException) then
|
|
begin
|
|
MessageDlg(E.Message, mtError, [mbOK], 0);
|
|
Exit;
|
|
end;
|
|
raise;
|
|
end;
|
|
end;
|
|
// Pack files
|
|
Pack(Files, QueueIdentifier);
|
|
end;
|
|
end;
|
|
// Save last used packer
|
|
gLastUsedPacker:= FArchiveType;
|
|
end;
|
|
|
|
end.
|
|
|