ISDone (error) finish page - inno-setup
I am having a problem with ISdone library error finish page.
according to the library error page should be in red colour like this:
But i am not getting the red colour:
I know why this is happening,This is because of the code of stratching the image.
Now how can i get the red colour for FinishedLabel and FinishedHeadingLabel if ISDone error occures.
Thank You .
Script :
; --- Generated by InnoSetup Script Joiner version 3.0, Jul 22 2009, (c) Bulat Ziganshin <Bulat.Ziganshin#gmail.com>. More info at http://issjoiner.codeplex.com/
; --- Source: 2.iss ------------------------------------------------------------
// Setup.ini internal
#define MyAppName "Game"
#define MyAppVersion "2.0.0.0"
#define MyAppPublisher "Dante1995"
#define MyAppExeName "MyProg.exe"
#define NeedSize "5000000"
// only Arc, Disable PrecompInside
;#Define PrecompInside
[Setup]
WizardSmallImageFile=Include\WizModernSmallImage.bmp
WizardImageFile=Include\WizModernImage-IS.bmp
AppName={#MyAppName}
AppVerName={#MyAppName}
AppPublisher={#MyAppPublisher}
AppVersion={#MyAppVersion}
DefaultDirName={pf}\{#MyAppPublisher}\{#MyAppName}
OutputBaseFilename=Setup
OutputDir=Output
Compression=zip
InternalCompressLevel=Ultra64
SetupIconFile=include\icon.ico
UninstallDisplayIcon={uninstallexe}
VersionInfoCopyright={#MyAppPublisher}
#ifdef NeedSize
ExtraDiskSpaceRequired={#NeedSize}
#endif
DisableWelcomePage=False
DisableProgramGroupPage=yes
[Languages]
Name: "default"; MessagesFile: "compiler:Default.isl"
[Tasks]
Name: "desktopicon"; Description: "{cm:CreateDesktopIcon}"; GroupDescription: "{cm:AdditionalIcons}";
Name: "quicklaunchicon"; Description: "{cm:CreateQuickLaunchIcon}"; GroupDescription: "{cm:AdditionalIcons}"; Flags: unchecked;
Name: DX; Description: Install Microsoft DirectX
Name: VC; Description: Install Microsoft Visual C++ Redist
[Icons]
Name: "{group}\Play {#MyAppName}"; Filename: "{app}\{#MyAppExeName}"; Check: CheckError
Name: "{group}\{cm:UninstallProgram,{#MyAppName}}"; Filename: "{uninstallexe}"; Check: CheckError
Name: "{commondesktop}\Play {#MyAppName}"; Filename: "{app}\{#MyAppExeName}"; Check: CheckError; Tasks: desktopicon
Name: "{userappdata}\Microsoft\Internet Explorer\Quick Launch\{#MyAppName}"; Filename: "{app}\{#MyAppExeName}"; Check: CheckError; Tasks: quicklaunchicon
[Files]
#ifdef PrecompInside
Source: include\facompress.dll; DestDir: {tmp}; Flags: dontcopy
Source: include\CLS-precomp.dll; DestDir: {tmp}; Flags: dontcopy
Source: include\packjpg_dll.dll; DestDir: {tmp}; Flags: dontcopy
Source: include\packjpg_dll1.dll; DestDir: {tmp}; Flags: dontcopy
Source: include\precomp.exe; DestDir: {tmp}; Flags: dontcopy
Source: include\zlib1.dll; DestDir: {tmp}; Flags: dontcopy
#endif
#ifdef SrepInside
Source: include\CLS-srep.dll; DestDir: {tmp}; Flags: dontcopy
Source: include\cls.ini; DestDir: {tmp}; Flags: dontcopy
#endif
#ifdef MSC
Source: include\CLS-MSC.dll; DestDir: {tmp}; Flags: dontcopy
#endif
Source: include\English.ini; DestDir: {tmp}; Flags: dontcopy
Source: include\unarc.dll; DestDir: {tmp}; Flags: dontcopy
Source: include\ISDone.dll; DestDir: {tmp}; Flags: dontcopy
Source: include\CallbackCtrl.dll; Flags: dontcopy noencryption noencryption
Source: include\arc.ini; DestDir: {tmp}; Flags: dontcopy
Source: "Setup.ini"; Flags: dontcopy solidbreak;
[CustomMessages]
default.ORE=h
default.MINUTI=min
default.SECONDI=sec
default.RIMANENTE=Remaining Time:
default.ESTRAZIONE=Extracted Files:
default.TTime=Total Extraction Time :
default.Elapsed=Elapsed Time:
[UninstallDelete]
Type: filesandordirs; Name: "{app}"
Type: dirifempty; Name: "{pf}\{#MyAppPublisher}"
[Messages]
default.SetupWindowTitle=%1
[Code]
var
ElapsedTimeLbl,TotalTimeLbl,Percentuale,//RollingBack,
RemainingTimeLbl,LabelCurrFileName: TLabel;
ISDoneCancel:integer;
ISDoneError:boolean;
CancelBtn: TButton;
PBOldProc : Longint;
WFCaption : string;
eTime, sTime : DWORD;
type
#ifdef UNICODE
PChar = PAnsiChar;
#endif
TCallback = function (OveralPct,CurrentPct: integer;CurrentFile,TimeStr1,TimeStr2,TimeStr3:PAnsiChar): longword;
TPBProc = function (h:hWnd;Msg,wParam,lParam:Longint):Longint;
function SetWindowLong(hWnd: HWND; nIndex: Integer; dwNewLong: Longint): Longint; external 'SetWindowLongA#user32.dll stdcall';
function CallBackProc(P:TPBProc;ParamCount:integer):LongWord; external 'wrapcallbackaddr#files:CallbackCtrl.dll stdcall';
function CallWindowProc(lpPrevWndFunc: Longint; hWnd: HWND; Msg: UINT; wParam, lParam: Longint): Longint; external 'CallWindowProcA#user32.dll stdcall';
function GetTickCount: DWORD; external 'GetTickCount#kernel32.dll stdcall';
function WrapCallback(callback:TCallback; paramcount:integer):longword;external 'wrapcallback#files:ISDone.dll stdcall delayload';
function ISDoneInit(RecordFileName:AnsiString; TimeType,Comp1,Comp2,Comp3:Cardinal; WinHandle, NeededMem:longint; callback:TCallback):boolean; external 'ISDoneInit#files:ISDone.dll stdcall';
function ISArcExtract(CurComponent:Cardinal; PctOfTotal:double; InName, OutPath, ExtractedPath: AnsiString; DeleteInFile:boolean; Password, CfgFile, WorkPath: AnsiString; ExtractPCF: boolean ):boolean; external 'ISArcExtract#files:ISDone.dll stdcall delayload';
function IS7ZipExtract(CurComponent:Cardinal; PctOfTotal:double; InName, OutPath: AnsiString; DeleteInFile:boolean; Password: AnsiString):boolean; external 'IS7zipExtract#files:ISDone.dll stdcall delayload';
function ISRarExtract(CurComponent:Cardinal; PctOfTotal:double; InName, OutPath: AnsiString; DeleteInFile:boolean; Password: AnsiString):boolean; external 'ISRarExtract#files:ISDone.dll stdcall delayload';
function ISPrecompExtract(CurComponent:Cardinal; PctOfTotal:double; InName, OutFile: AnsiString; DeleteInFile:boolean):boolean; external 'ISPrecompExtract#files:ISDone.dll stdcall delayload';
function ISSRepExtract(CurComponent:Cardinal; PctOfTotal:double; InName, OutFile: AnsiString; DeleteInFile:boolean):boolean; external 'ISSrepExtract#files:ISDone.dll stdcall delayload';
function ISxDeltaExtract(CurComponent:Cardinal; PctOfTotal:double; minRAM,maxRAM:integer; InName, DiffFile, OutFile: AnsiString; DeleteInFile, DeleteDiffFile:boolean):boolean; external 'ISxDeltaExtract#files:ISDone.dll stdcall delayload';
function ISPackZIP(CurComponent:Cardinal; PctOfTotal:double; InName, OutFile: AnsiString;ComprLvl:integer; DeleteInFile:boolean):boolean; external 'ISPackZIP#files:ISDone.dll stdcall delayload';
function ShowChangeDiskWindow(Text, DefaultPath, SearchFile:AnsiString):boolean; external 'ShowChangeDiskWindow#files:ISDone.dll stdcall delayload';
function Exec2 (FileName, Param: PAnsiChar;Show:boolean):boolean; external 'Exec2#files:ISDone.dll stdcall delayload';
function ISFindFiles(CurComponent:Cardinal; FileMask:AnsiString; var ColFiles:integer):integer; external 'ISFindFiles#files:ISDone.dll stdcall delayload';
function ISPickFilename(FindHandle:integer; OutPath:AnsiString; var CurIndex:integer; DeleteInFile:boolean):boolean; external 'ISPickFilename#files:ISDone.dll stdcall delayload';
function ISGetName(TypeStr:integer):PAnsichar; external 'ISGetName#files:ISDone.dll stdcall delayload';
function ISFindFree(FindHandle:integer):boolean; external 'ISFindFree#files:ISDone.dll stdcall delayload';
function ISExec(CurComponent:Cardinal; PctOfTotal,SpecifiedProcessTime:double; ExeName,Parameters,TargetDir,OutputStr:AnsiString;Show:boolean):boolean; external 'ISExec#files:ISDone.dll stdcall delayload';
function SrepInit(TmpPath:PAnsiChar;VirtMem,MaxSave:Cardinal):boolean; external 'SrepInit#files:ISDone.dll stdcall delayload';
function PrecompInit(TmpPath:PAnsiChar;VirtMem:cardinal;PrecompVers:single):boolean; external 'PrecompInit#files:ISDone.dll stdcall delayload';
function FileSearchInit(RecursiveSubDir:boolean):boolean; external 'FileSearchInit#files:ISDone.dll stdcall delayload';
function ISDoneStop:boolean; external 'ISDoneStop#files:ISDone.dll stdcall';
function ChangeLanguage(Language:AnsiString):boolean; external 'ChangeLanguage#files:ISDone.dll stdcall delayload';
function SuspendProc:boolean; external 'SuspendProc#files:ISDone.dll stdcall';
function ResumeProc:boolean; external 'ResumeProc#files:ISDone.dll stdcall';
function ProgressCallback(OveralPct,CurrentPct: integer;CurrentFile,TimeStr1,TimeStr2,TimeStr3:PAnsiChar): longword;
begin
if OveralPct<=Wizardform.ProgressGauge.Max then
Wizardform.Progressgauge.Position := OveralPct;
Result := ISDoneCancel;
TotalTimeLbl.Caption:=ExpandConstant('{cm:TTime}')+TimeStr2;
with WizardForm.ProgressGauge do begin
LabelCurrFileName.Caption:=SetupMessage(msgStatusExtractFiles)+': '+MinimizePathName(CurrentFile, LabelCurrFileName.Font, LabelCurrFileName.Width-ScaleX(100));
end;
end;
function LongintToStringTime(t:Longint):string;
var
h,m,s:integer;
begin
h:=t div 3600;
t:=t-h*3600;
m:=t div 60;
s:=t-m*60;
Result:='';
if h>0 then Result:=Result+IntToStr(h)+ ExpandConstant(' {cm:ORE} ');
if (m>0) or (h>0) then Result:=Result+IntToStr(m)+ExpandConstant(' {cm:MINUTI} ');
if (m>0) or (h>0) or (s>0) then Result:=Result+IntToStr(s)+ExpandConstant(' {cm:SECONDI} ');
end;
function PBProc(h:hWnd;Msg,wParam,lParam:Longint):Longint;
var
R,A:Longint;
dt,at,pr,i1,i2:Extended;
p:string;
tc:DWORD;
begin
Result:=CallWindowProc(PBOldProc,h,Msg,wParam,lParam);
if (Msg=$402) and (WizardForm.ProgressGauge.Position>WizardForm.ProgressGauge.Min) then begin
i1:=WizardForm.ProgressGauge.Position-WizardForm.ProgressGauge.Min;
i2:=WizardForm.ProgressGauge.Max-WizardForm.ProgressGauge.Min;
tc:=GetTickCount;
if (tc-eTime)>=1000 then begin
dt:=(tc-sTime)/1000;
at:=i2*dt/i1;
R:=Round(at-dt)
A:=Round(dt)
RemainingTimeLbl.Caption:=ExpandConstant('{cm:RIMANENTE} ')+LongintToStringTime(R);
ElapsedTimeLbl.Caption:=ExpandConstant('{cm:Elapsed} ')+LongintToStringTime(A);
eTime:=tc;
end;
pr:=i1*100/i2;
p:=''+Format('%f',[pr])+'%';
StringChange(p,',','.');
Percentuale.Caption:=WFCaption+p;
end;
end;
procedure AllCancel;
begin
SetWindowLong(WizardForm.ProgressGauge.Handle,-4,PBOldProc);
Percentuale.Caption:=WFCaption;
end;
procedure CancelButtonOnClick(Sender: TObject);
begin
SuspendProc;
//RollingBack.Show;
if MsgBox(SetupMessage(msgExitSetupMessage), mbConfirmation, MB_YESNO) = IDYES then ISDoneCancel:=1;
ResumeProc;
//RollingBack.Hide;
end;
procedure HideControls;
begin
CancelBtn.Hide;
LabelCurrFileName.Hide;
RemainingTimeLbl.Hide;
ElapsedTimeLbl.Hide;
end;
procedure InitializeWizard1();
begin
WizardForm.ProgressGauge.Top := ScaleY(46);
ElapsedTimeLbl := TLabel.Create(WizardForm);
with ElapsedTimeLbl do begin
Parent := WizardForm.InstallingPage;
Font.Size:=10;
Font.Color:=clYellow;
Font.Style := [fsBold];
Font.Name:='calibri';
SetBounds(0,90,WizardForm.ClientWidth-40,14);
end;
RemainingTimeLbl:=TLabel.Create(WizardForm);
with RemainingTimeLbl do begin
Parent:=WizardForm.InstallingPage;
SetBounds(216,90,WizardForm.ClientWidth-40,14);
Font.Size:=10;
Font.Color:=clYellow;
Font.Style := [fsBold];
Font.Name:='calibri';
end;
Percentuale := TLabel.Create(WizardForm);
with Percentuale do begin
Parent:= WizardForm.InstallingPage;
SetBounds(150,130,WizardForm.ClientWidth-40,14);
Font.Size:=20;
Font.Color:=clYellow;
Font.Style := [fsBold];
Font.Name:='calibri';
end;
CancelBtn := TButton.Create(WizardForm);
with CancelBtn do begin
Name := 'Cancel';
Parent := WizardForm;
Left := WizardForm.CancelButton.Left;
Top := WizardForm.CancelButton.Top;
Width := WizardForm.CancelButton.Width;
Height := WizardForm.CancelButton.Height;
OnClick:=#CancelButtonOnClick;
Font.Size:=8;
Font.Name:='calibri';
end;
LabelCurrFileName := TLabel.Create(WizardForm);
with LabelCurrFileName do begin
Parent := WizardForm.InstallingPage;
AutoSize := False;
Width := WizardForm.ProgressGauge.Width+ScaleX(30);
Left := ScaleX(0);
Top := ScaleY(30);
Font.Size:=8;
Font.Color:=clYellow;
Font.Name:='calibri';
end;
TotalTimeLbl := TLabel.Create(WizardForm);
with TotalTimeLbl do begin
Parent := WizardForm.FinishedPage;
AutoSize := False;
Width := 300;
Left := 180;
Top := 200;
Font.Size:=14;
Font.Color:=clYellow;
Font.Style := [fsBold];
Font.Name:='calibri';
Height := 35;
end;
end;
procedure CurPageChanged1(CurPageID: integer);
begin
HideControls;
if CurPageID=wpWelcome then
begin
end;
if CurPageID=wpSelectDir then
begin
end;
if CurPageID=wpInstalling then
begin
CancelBtn.Show;
LabelCurrFileName.Show;
RemainingTimeLbl.Show;
ElapsedTimeLbl.Show;
end;
if CurPageID=wpFinished then
begin
RemainingTimeLbl.Hide;
AllCancel;
HideControls;
end;
if (CurPageID = wpFinished) and ISDoneError then
begin
WizardForm.Caption:= SetupMessage(msgErrorTitle);
WizardForm.FinishedLabel.Font.Color:= clRed;
WizardForm.FinishedLabel.Caption:= SetupMessage(msgSetupAborted);
end;
end;
function CheckError:boolean;
begin
result:= not ISDoneError;
end;
procedure CurStepChanged1(CurStep: TSetupStep);
var
res, i, ResultCode: integer;
Arc1, Arc2: Array of String;
begin
If CurStep = ssInstall then begin
WizardForm.StatusLabel.Caption:='Installing The Game...';
sTime:=GetTickCount;
eTime:=sTime;
PBOldProc:=SetWindowLong(WizardForm.ProgressGauge.Handle,-4,CallBackProc(#PBProc,4));
#ifdef PrecompInside
ExtractTemporaryFile('CLS-precomp.dll');
ExtractTemporaryFile('packjpg_dll.dll');
ExtractTemporaryFile('packjpg_dll1.dll');
ExtractTemporaryFile('precomp.exe');
ExtractTemporaryFile('zlib1.dll');
ExtractTemporaryFile('facompress.dll');
#endif
#ifdef SrepInside
ExtractTemporaryFile('CLS-srep.dll');
#endif
#ifdef MSC
ExtractTemporaryFile('CLS-MSC.dll');
#endif
ExtractTemporaryFile('arc.ini');
ExtractTemporaryFile('unarc.dll');
ExtractTemporaryFile('English.ini');
ISDoneError:=false;
i:=1;
if (GetIniString('FreearcFile' + IntToStr(i),'Archive','',ExpandConstant('{tmp}\Setup.ini')) <> '') then
begin
WizardForm.ProgressGauge.Max:=0;
repeat
WizardForm.ProgressGauge.Max:= WizardForm.ProgressGauge.Max + 1000;
i:= i + 1;
until (GetIniString('FreearcFile' + IntToStr(i),'Archive','',ExpandConstant('{tmp}\Setup.ini')) = '');
end;
if ISDoneInit(ExpandConstant('{tmp}\records.inf'), $F777, 0,0,0, MainForm.Handle, 512, #ProgressCallback) then begin
repeat
ChangeLanguage('English');
if not SrepInit('',512,0) then ISDoneError := True;
if not PrecompInit('',128,0) then ISDoneError := True;
if not FileSearchInit(true) then ISDoneError := True;
i:=1;
if (GetIniString('FreearcFile' + IntToStr(i),'Archive','',ExpandConstant('{tmp}\Setup.ini')) <> '') then
begin
SetArrayLength(Arc1,4);
SetArrayLength(Arc2,4);
repeat
Arc1[0]:=ExpandConstant(GetIniString('FreearcFile' + IntToStr(i),'Archive','',ExpandConstant('{tmp}\Setup.ini')));
Arc1[1]:=ExpandConstant(GetIniString('FreearcFile' + IntToStr(i),'Output','',ExpandConstant('{tmp}\Setup.ini')));
Arc1[2]:=ExpandConstant(GetIniString('FreearcFile' + IntToStr(i),'Disk','1',ExpandConstant('{tmp}\Setup.ini')));
if Arc1[0] <> '' then
begin
if not FileExists(Arc1[0]) then
begin
if MsgBox(SetupMessage(msgChangeDiskTitle) +' '+'( '+ Arc1[2]+' )', mbError, MB_OKCANCEL) = IDCANCEL then ISDoneError := True;
end else begin
if not ISArcExtract( 0, 0, Arc1[0], Arc1[1], '', false, Arc1[3], ExpandConstant('{tmp}\arc.ini'), ExpandConstant('{app}'), False) then ISDoneError := True;
i:= i + 1;
end;
end;
until ((GetIniString('FreearcFile' + IntToStr(i),'Archive','',ExpandConstant('{tmp}\Setup.ini')) = '') or (ISDoneError = True));
end;
until true;
ISDoneStop;
end;
AllCancel;
HideControls;
WizardForm.ProgressGauge.Hide;
end;
if (CurStep=ssPostInstall) and ISDoneError then begin
WizardForm.StatusLabel.Caption:=SetupMessage(msgStatusRollback);
TotalTimeLbl.Caption:='';
Exec(ExpandConstant('{uninstallexe}'), '/VERYSILENT','', sw_Hide, ewWaitUntilTerminated, ResultCode);
end;
end;
function InitializeSetup1: Boolean;
var
Uninstall,Location: string;
ResultCode: Integer;
begin
if not FileExists(ExpandConstant('{tmp}\CallbackCtrl.dll')) then ExtractTemporaryFile('CallbackCtrl.dll');
ExtractTemporaryFile('Setup.ini');
if RegQueryStringValue(HKLM, 'SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\{#MyAppName}_is1','UninstallString', Uninstall) then
Uninstall:=RemoveQuotes(Uninstall);
begin
if not Exec(Uninstall, ' /SILENT', '', SW_SHOW, ewWaitUntilTerminated, ResultCode) then
RegQueryStringValue(HKLM, 'Software\Microsoft\Windows\CurrentVersion\Uninstall\{#MyAppName}_is1','InstallLocation', Location);
end;
Result:=True;
end;
[Setup]
; --- Source: 3.iss ------------------------------------------------------------
[code]
var
WelcomeLabel1, WelcomeLabel2, FinishedLabel, FinishedHeadingLabel: TLabel;
PageNameLabel, PageDescriptionLabel: TLabel;
procedure InitializeWizard2();
begin
WizardForm.WizardBitmapImage.Width := ScaleX(497);
WizardForm.WizardBitmapImage2.Width := ScaleX(497);
{ WelcomeLabel1 }
WizardForm.WelcomeLabel1.Hide;
WelcomeLabel1 := TLabel.Create(WizardForm);
with WizardForm.WelcomeLabel1 do
begin
WelcomeLabel1.Parent := Parent;
WelcomeLabel1.SetBounds(Left, Top, Width, Height);
WelcomeLabel1.AutoSize := AutoSize;
WelcomeLabel1.Font := Font;
WelcomeLabel1.Font.Color := clWhite;
WelcomeLabel1.Transparent := True;
WelcomeLabel1.WordWrap := WordWrap;
WelcomeLabel1.Caption := Caption;
end;
{ WelcomeLabel2 }
WizardForm.WelcomeLabel2.Hide;
WelcomeLabel2 := TLabel.Create(WizardForm);
with WizardForm.WelcomeLabel2 do
begin
WelcomeLabel2.Parent := Parent;
WelcomeLabel2.SetBounds(Left, Top, Width, Height);
WelcomeLabel2.AutoSize := AutoSize;
WelcomeLabel2.Font := Font;
WelcomeLabel2.Font.Color := clWhite;
WelcomeLabel2.Transparent := True;
WelcomeLabel2.WordWrap := WordWrap;
WelcomeLabel2.Caption := Caption;
end;
WizardForm.WizardSmallBitmapImage.SetBounds(ScaleX(0), ScaleY(0), WizardForm.MainPanel.Width, WizardForm.MainPanel.Height);
{ PageNameLabel }
WizardForm.PageNameLabel.Hide;
PageNameLabel := TLabel.Create(WizardForm);
with WizardForm.PageNameLabel do
begin
PageNameLabel.Parent := Parent;
PageNameLabel.SetBounds(Left, Top, Width, Height);
PageNameLabel.AutoSize := AutoSize;
PageNameLabel.Font := Font;
PageNameLabel.Font.Color := clYellow;
PageNameLabel.Transparent := True;
PageNameLabel.WordWrap := WordWrap;
end;
{ PageDescriptionLabel }
WizardForm.PageDescriptionLabel.Hide;
PageDescriptionLabel:= TLabel.Create(WizardForm);
with WizardForm.PageDescriptionLabel do
begin
PageDescriptionLabel.Parent := Parent;
PageDescriptionLabel.SetBounds(Left, Top, Width, Height);
PageDescriptionLabel.AutoSize := AutoSize;
PageDescriptionLabel.Font := Font;
PageDescriptionLabel.Font.Color := clYellow;
PageDescriptionLabel.Transparent := True;
PageDescriptionLabel.WordWrap := WordWrap;
end;
{ FinishedHeadingLabel }
WizardForm.FinishedHeadingLabel.Hide;
FinishedHeadingLabel := TLabel.Create(WizardForm);
with WizardForm.FinishedHeadingLabel do
begin
FinishedHeadingLabel.Parent := Parent;
FinishedHeadingLabel.SetBounds(Left, Top, Width, Height);
FinishedHeadingLabel.AutoSize := AutoSize;
FinishedHeadingLabel.Font := Font;
FinishedHeadingLabel.Font.Color := clWhite;
FinishedHeadingLabel.Transparent := True;
FinishedHeadingLabel.WordWrap := WordWrap;
FinishedHeadingLabel.Caption := Caption;
end;
{ FinishedLabel }
WizardForm.FinishedLabel.Hide;
FinishedLabel := TLabel.Create(WizardForm);
with WizardForm.FinishedLabel do
begin
FinishedLabel.Parent := Parent;
FinishedLabel.SetBounds(Left, Top, Width, Height);
FinishedLabel.AutoSize := AutoSize;
FinishedLabel.Font := Font;
FinishedLabel.Font.Color := clWhite;
FinishedLabel.Transparent := True;
FinishedLabel.WordWrap := WordWrap;
end;
end;
procedure CurPageChanged2(CurPageID: Integer);
begin
begin
PageNameLabel.Caption := WizardForm.PageNameLabel.Caption;
PageDescriptionLabel.Caption := WizardForm.PageDescriptionLabel.Caption;
FinishedLabel.Caption := WizardForm.FinishedLabel.Caption;
end;
if (CurPageID = wpFinished) and ISDoneError then
begin
WizardForm.Caption:= SetupMessage(msgErrorTitle);
WizardForm.FinishedLabel.Font.Color:= clRed;
WizardForm.FinishedLabel.Caption:= SetupMessage(msgSetupAborted);
end;
end;
[Setup]
; --- Dispatching code ------------------------------------------------------------
[Code]
procedure InitializeWizard();
begin
InitializeWizard1();
InitializeWizard2();
end;
procedure CurPageChanged(CurPageID: Integer);
begin
CurPageChanged1(CurPageID);
CurPageChanged2(CurPageID);
end;
procedure CurStepChanged(CurStep: TSetupStep);
begin
CurStepChanged1(CurStep);
end;
function InitializeSetup(): Boolean;
begin
Result := InitializeSetup1(); if not Result then exit;
end;
You'r Label's are messed up. If you are creating a new label in the place of an existing one make sure you use it everywhere. Dont mix it up!
Though i would not proceed with a code such as that in its current state...here's a fix.
Set the parent of FinishedLabel to WizardForm.FinishedPage
with WizardForm.FinishedLabel do begin
FinishedLabel.Parent:=WizardForm.FinishedPage;
....
end;
and use that FinishedLabel to display the error message.
if (CurPageID = wpFinished) and ISDoneError then
begin
WizardForm.Caption:= SetupMessage(msgErrorTitle);
FinishedLabel.Font.Color:= clRed;
WizardForm.FinishedLabel.Caption:= SetupMessage(msgSetupAborted);
end;
in procedure CurPageChanged2.
Btw the code is very clumsy. Please take some time to go through your code and organise it before you go any further.
Edit: The updated code. I have tested this code in my PC and its working fine. Replace the CurPageChanged2 with this.
procedure CurPageChanged2(CurPageID: Integer);
begin
begin
PageNameLabel.Caption := WizardForm.PageNameLabel.Caption;
PageDescriptionLabel.Caption := WizardForm.PageDescriptionLabel.Caption;
FinishedLabel.Caption := WizardForm.FinishedLabel.Caption;
end;
if (CurPageID = wpFinished) and ISDoneError then
begin
WizardForm.Caption:= SetupMessage(msgErrorTitle);
FinishedLabel.Font.Color:= clRed; // changed
FinishedHeadingLabel.Font.Color:= clRed; // changed
WizardForm.FinishedLabel.Caption:= SetupMessage(msgSetupAborted);
end;
end;
Related
InnoSetup - GIF backgroung image? [duplicate]
I would like to have in my installer: an infinite music loop playback during installation a window on the background (like the old installations that used to fill the screen with an image and only show the installation window), with a slideshow on that background window How to do this in InnoSetup ?
If you want to have an installer with a background image slideshow with an infinite music track playback, you can do e.g. the following: get the recent version of the InnoCallback library for slideshow timer implementation for music playback get e.g. most recent copy of the Inno Media Player for Unicode Inno Setup Write a script similar to following, or download the complete project, which includes all necessary files used in the next script code. So the only thing you'd need to do, is to build it in the recent version of Unicode Inno Setup. Please note, that Inno Media Player is a Unicode library, and so you can use it only with Unicode versions of Inno Setup, not with ANSI ones! There is no support for ANSI versions of Inno Setup...! [Setup] AppName=My Program AppVersion=1.5 DefaultDirName={pf}\My Program OutputDir=userdocs:Inno Setup Examples Output BackColor=clLime BackColor2=clYellow WindowVisible=yes [Files] Source: "Image1.bmp"; Flags: dontcopy Source: "Image2.bmp"; Flags: dontcopy Source: "AudioFile.mp3"; Flags: dontcopy Source: "MediaPlayer.dll"; Flags: dontcopy Source: "InnoCallback.dll"; Flags: dontcopy [Code] var TimerID: Integer; SlideID: Integer; BackImage: TBitmapImage; const EC_COMPLETE = $01; type TTimerProc = procedure(Wnd: HWND; Msg: UINT; TimerID: UINT_PTR; SysTime: DWORD); TDirectShowEventProc = procedure(EventCode, Param1, Param2: Integer); function WrapTimerProc(Callback: TTimerProc; ParamCount: Integer): LongWord; external 'wrapcallback#files:InnoCallback.dll stdcall'; function SetTimer(hWnd: HWND; nIDEvent, uElapse: UINT; lpTimerFunc: UINT): UINT; external 'SetTimer#user32.dll stdcall'; function KillTimer(hWnd: HWND; uIDEvent: UINT): BOOL; external 'KillTimer#user32.dll stdcall'; function DSGetLastError(var ErrorText: WideString): HRESULT; external 'DSGetLastError#files:mediaplayer.dll stdcall'; function DSPlayMediaFile: Boolean; external 'DSPlayMediaFile#files:mediaplayer.dll stdcall'; function DSStopMediaPlay: Boolean; external 'DSStopMediaPlay#files:mediaplayer.dll stdcall'; function DSSetVolume(Value: LongInt): Boolean; external 'DSSetVolume#files:mediaplayer.dll stdcall'; function DSInitializeAudioFile(FileName: WideString; CallbackProc: TDirectShowEventProc): Boolean; external 'DSInitializeAudioFile#files:mediaplayer.dll stdcall'; procedure OnMediaPlayerEvent(EventCode, Param1, Param2: Integer); begin if EventCode = EC_COMPLETE then begin if DSInitializeAudioFile(ExpandConstant('{tmp}\AudioFile.mp3'), #OnMediaPlayerEvent) then begin DSSetVolume(-2500); DSPlayMediaFile; end; end; end; procedure OnSlideTimer(Wnd: HWND; Msg: UINT; TimerID: UINT_PTR; SysTime: DWORD); begin case SlideID of 0: SlideID := 1; 1: SlideID := 0; end; BackImage.Bitmap.LoadFromFile( ExpandConstant('{tmp}\Image' + IntToStr(SlideID + 1) + '.bmp')); end; procedure StartSlideTimer; var TimerCallback: LongWord; begin TimerCallback := WrapTimerProc(#OnSlideTimer, 4); { third parameter here is the timer's timeout value in milliseconds } TimerID := SetTimer(0, 0, 5000, TimerCallback); end; procedure KillSlideTimer; begin if TimerID <> 0 then begin if KillTimer(0, TimerID) then TimerID := 0; end; end; procedure InitializeWizard; var ErrorCode: HRESULT; ErrorText: WideString; begin TimerID := 0; SlideID := 0; ExtractTemporaryFile('Image1.bmp'); ExtractTemporaryFile('Image2.bmp'); BackImage := TBitmapImage.Create(MainForm); BackImage.Parent := MainForm; BackImage.Top := 70; BackImage.Left := 10; BackImage.AutoSize := True; BackImage.Bitmap.LoadFromFile(ExpandConstant('{tmp}\Image1.bmp')); StartSlideTimer; ExtractTemporaryFile('AudioFile.mp3'); if DSInitializeAudioFile(ExpandConstant('{tmp}\AudioFile.mp3'), #OnMediaPlayerEvent) then begin DSSetVolume(-2500); DSPlayMediaFile; end else begin ErrorCode := DSGetLastError(ErrorText); MsgBox('TDirectShowPlayer error: ' + IntToStr(ErrorCode) + '; ' + ErrorText, mbError, MB_OK); end; end; procedure DeinitializeSetup; begin KillSlideTimer; DSStopMediaPlay; end; Further resources: How to make a slideshow in InnoSetup ? How to play a sound during InnoSetup installation process ?
Creating backgrounds feature: Did you try Graphical Installer (http://www.graphical-installer.com) ? It is a professional Inno Setup extension specially for this (creating cool looking installers with background) so creating such installer is matter of few minutes (no coding is required).
Inno Setup: Enlarge component page only with preview and description
I need help from you to merge two scripts found here to have preview image on a maximized components windows: Add image into the components list - component description Long descriptions on Inno Setup components Edit: Thanks to Martin Prikryl. With his patience and his help, I successfully merge these two scripts. Your preview image should have a resolution of 208x165 in .bmp [Files] ... Source: "1.bmp"; Flags: dontcopy Source: "2.bmp"; Flags: dontcopy Source: "3.bmp"; Flags: dontcopy Source: "InnoCallback.dll"; Flags: dontcopy [Code] var LastMouse: TPoint; type TTimerProc = procedure(H: LongWord; Msg: LongWord; IdEvent: LongWord; Time: LongWord); function GetCursorPos(var lpPoint: TPoint): BOOL; external 'GetCursorPos#user32.dll stdcall'; function SetTimer(hWnd: longword; nIDEvent, uElapse: LongWord; lpTimerFunc: LongWord): LongWord; external 'SetTimer#user32.dll stdcall'; function ScreenToClient(hWnd: HWND; var lpPoint: TPoint): BOOL; external 'ScreenToClient#user32.dll stdcall'; function ClientToScreen(hWnd: HWND; var lpPoint: TPoint): BOOL; external 'ClientToScreen#user32.dll stdcall'; function ListBox_GetItemRect(const hWnd: HWND; const Msg: Integer; Index: LongInt; var Rect: TRect): LongInt; external 'SendMessageW#user32.dll stdcall'; const LB_GETITEMRECT = $0198; LB_GETTOPINDEX = $018E; function WrapTimerProc(Callback: TTimerProc; ParamCount: Integer): LongWord; external 'wrapcallback#files:InnoCallback.dll stdcall'; function FindControl(Parent: TWinControl; P: TPoint): TControl; var Control: TControl; WinControl: TWinControl; I: Integer; P2: TPoint; begin for I := 0 to Parent.ControlCount - 1 do begin Control := Parent.Controls[I]; if Control.Visible and (Control.Left <= P.X) and (P.X < Control.Left + Control.Width) and (Control.Top <= P.Y) and (P.Y < Control.Top + Control.Height) then begin if Control is TWinControl then begin P2 := P; ClientToScreen(Parent.Handle, P2); WinControl := TWinControl(Control); ScreenToClient(WinControl.Handle, P2); Result := FindControl(WinControl, P2); if Result <> nil then Exit; end; Result := Control; Exit; end; end; Result := nil; end; function PointInRect(const Rect: TRect; const Point: TPoint): Boolean; begin Result := (Point.X >= Rect.Left) and (Point.X <= Rect.Right) and (Point.Y >= Rect.Top) and (Point.Y <= Rect.Bottom); end; function ListBoxItemAtPos(ListBox: TCustomListBox; Pos: TPoint): Integer; var Count: Integer; ItemRect: TRect; begin Result := SendMessage(ListBox.Handle, LB_GETTOPINDEX, 0, 0); Count := ListBox.Items.Count; while Result < Count do begin ListBox_GetItemRect(ListBox.Handle, LB_GETITEMRECT, Result, ItemRect); if PointInRect(ItemRect, Pos) then Exit; Inc(Result); end; Result := -1; end; var CompLabel: TLabel; CompImage: TBitmapImage; LoadingImage: Boolean; procedure HoverComponentChanged(Index: Integer); var Description: string; Image: string; ImagePath: string; begin case Index of 0: begin Description := 'Component 1'; Image := '1.bmp'; end; 1: begin Description := 'Component 2'; Image := '2.bmp'; end; 2: begin Description := 'Component 3'; Image := '3.bmp'; end; else Description := 'Move your mouse over a component to see its description.'; end; CompLabel.Caption := Description; if Image <> '' then begin // The ExtractTemporaryFile pumps the message queue, prevent recursion if not LoadingImage then begin LoadingImage := True; try ImagePath := ExpandConstant('{tmp}\' + Image); if not FileExists(ImagePath) then begin ExtractTemporaryFile(Image); end; CompImage.Bitmap.LoadFromFile(ImagePath); finally LoadingImage := False; end; end; CompImage.Visible := True; end else begin CompImage.Visible := False; end; end; procedure HoverTimerProc(H: LongWord; Msg: LongWord; IdEvent: LongWord; Time: LongWord); var P: TPoint; Control: TControl; Index: Integer; begin GetCursorPos(P); if P <> LastMouse then // just optimization begin LastMouse := P; ScreenToClient(WizardForm.Handle, P); if (P.X < 0) or (P.Y < 0) or (P.X > WizardForm.ClientWidth) or (P.Y > WizardForm.ClientHeight) then begin Control := nil; end else begin Control := FindControl(WizardForm, P); end; Index := -1; if Control = WizardForm.ComponentsList then begin P := LastMouse; ScreenToClient(WizardForm.ComponentsList.Handle, P); Index := ListBoxItemAtPos(WizardForm.ComponentsList, P); end; HoverComponentChanged(Index); end; end; type TPositionStorage = array of Integer; var CompPageModified: Boolean; CompPagePositions: TPositionStorage; procedure SaveComponentsPage(out Storage: TPositionStorage); begin SetArrayLength(Storage, 10); Storage[0] := WizardForm.Height; Storage[1] := WizardForm.NextButton.Top; Storage[2] := WizardForm.BackButton.Top; Storage[3] := WizardForm.CancelButton.Top; Storage[4] := WizardForm.ComponentsList.Height; Storage[5] := WizardForm.OuterNotebook.Height; Storage[6] := WizardForm.InnerNotebook.Height; Storage[7] := WizardForm.Bevel.Top; Storage[8] := WizardForm.BeveledLabel.Top; Storage[9] := WizardForm.ComponentsDiskSpaceLabel.Top; end; procedure LoadComponentsPage(const Storage: TPositionStorage; HeightOffset: Integer); begin if GetArrayLength(Storage) <> 10 then RaiseException('Invalid storage array length.'); WizardForm.Height := Storage[0] + HeightOffset; WizardForm.NextButton.Top := Storage[1] + HeightOffset; WizardForm.BackButton.Top := Storage[2] + HeightOffset; WizardForm.CancelButton.Top := Storage[3] + HeightOffset; WizardForm.ComponentsList.Height := Storage[4] + ScaleY(150); WizardForm.OuterNotebook.Height := Storage[5] + HeightOffset; WizardForm.InnerNotebook.Height := Storage[6] + HeightOffset; WizardForm.Bevel.Top := Storage[7] + HeightOffset; WizardForm.BeveledLabel.Top := Storage[8] + HeightOffset; WizardForm.ComponentsDiskSpaceLabel.Top := Storage[9] + HeightOffset; end; procedure InitializeWizard1(); var HoverTimerCallback: LongWord; begin HoverTimerCallback := WrapTimerProc(#HoverTimerProc, 4); SetTimer(0, 0, 50, HoverTimerCallback); CompLabel := TLabel.Create(WizardForm); CompLabel.Parent := WizardForm.SelectComponentsPage; CompLabel.Left := WizardForm.ComponentsList.Left; CompLabel.Width := WizardForm.ComponentsList.Width div 2; CompLabel.Height := ScaleY(64); CompLabel.Top := WizardForm.ComponentsList.Top + WizardForm.ComponentsList.Height - CompLabel.Height + ScaleY(150); CompLabel.AutoSize := false; CompLabel.WordWrap := True; CompImage := TBitmapImage.Create(WizardForm); CompImage.Parent := WizardForm.SelectComponentsPage; CompImage.Top := CompLabel.Top; CompImage.Width := CompImage.Width + ScaleX(128); CompImage.Height := CompLabel.Height + ScaleX(128); CompImage.Left := WizardForm.ComponentsList.Left + WizardForm.ComponentsList.Width - CompLabel.Width; WizardForm.ComponentsList.Height := WizardForm.ComponentsList.Height - CompLabel.Height - ScaleY(8); end; procedure InitializeWizard2(); begin CompPageModified := False; end; procedure CurPageChanged(CurPageID: Integer); begin if CurpageID = wpSelectComponents then begin SaveComponentsPage(CompPagePositions); LoadComponentsPage(CompPagePositions, ScaleY(250)); CompPageModified := True; end else if CompPageModified then begin LoadComponentsPage(CompPagePositions, 0); CompPageModified := False; end; end; procedure InitializeWizard(); begin InitializeWizard1(); InitializeWizard2(); end;
Just copy both codes and merge the InitializeWizard implementations according to this guide: Merging event function (InitializeWizard) implementations from different sources. Though, actually, the InitializeWizard in the Larger “Select Components” page in Inno Setup is noop. You can skip that. And you do not need to merge anything. The only other change you need to do, is not to enlarge the ComponentsList in the LoadComponentsPage.
Using combo box to select what paths and registry keys to use
Purpose: With Inno Setup I want to create an installer with a dropdown list in the install wizard. The choice made in the wizards defines 2 variables: One for the folder location and the other for the location in the registry. Problem: Variables are defined as global in [Code], but are not used in [Files] and [Registry] Code: The two variables are: strData1 & strData2 I was trying to retrieve them with functions: strData1returner & strData2returner [Setup] ... [Dirs] Name: "C:\Program Files\CompanyName\{code:strData1returner}" [Files] Source: "C:\SomeDll.dll"; \ DestDir: "C:\Program Files\CompanyName\{code:strData1returner}\"; Flags: ignoreversion; [Registry] Root: HKCU; subkey: "{code:strData2returner}"; flags: createvalueifdoesntexist [Code] var Button: TNewButton; ComboBox: TNewComboBox; CustomPage: TWizardPage; strData1: string; strData2: string; procedure ComboBoxChange(Sender: TObject); begin case ComboBox.ItemIndex of 0: begin strData1 := 'Subfolder'; strData2 := 'SOFTWARE\CompanyName'; end; end; end; procedure InitializeWizard; var DescLabel: TLabel; begin CustomPage := CreateCustomPage(wpSelectDir, 'Caption', 'Description'); DescLabel := TLabel.Create(WizardForm); DescLabel.Parent := CustomPage.Surface; DescLabel.Left := 0; DescLabel.Top := 0; DescLabel.Caption := 'Select an item...'; ComboBox := TNewComboBox.Create(WizardForm); ComboBox.Parent := CustomPage.Surface; ComboBox.Left := 0; ComboBox.Top := DescLabel.Top + DescLabel.Height + 6; ComboBox.Width := 220; ComboBox.Style := csDropDownList; ComboBox.Items.Add('Choice1'); ComboBox.ItemIndex := 0; ComboBox.OnChange := #ComboBoxChange; end; function strData1returner(Param: String): String; begin Result := strData1; end; function strData2returner(Param: String): String; begin Result := strData2; end;
There was only a single option: "Choice1" - So I added a second (Choice2), and alternative values for that second option, under index 1. You should also initialize the two variables in InitializeWizard, in case the user doesn't change the combobox value. The ComboBoxChange procedure is only executed when the value actually changes, not when the default is accepted via no action. Also, in trying to reproduce your problem I noticed a syntax problem causing compilation errors with createvalueifdoesntexistcreatevalueifdoesntexist - naturally, you just need one of those. [Dirs] Name: "C:\Program Files\CompanyName\{code:strData1returner}" [Files] Source: "C:\SomeDll.dll"; DestDir: "C:\Program Files\CompanyName\{code:strData1returner}\"; Flags: ignoreversion; [Registry] Root: HKCU; subkey:"{code:strData2returner}"; flags: createvalueifdoesntexist [Code] var Button: TNewButton; ComboBox: TNewComboBox; CustomPage: TWizardPage; strData1: string; strData2: string; procedure ComboBoxChange(Sender: TObject); begin case ComboBox.ItemIndex of 0: begin strData1 := 'Subfolder'; strData2 := 'SOFTWARE\CompanyName'; end; 1: begin strData1 := 'Subfolder2'; strData2 := 'SOFTWARE\CompanyName2'; end; end; end; procedure InitializeWizard; var DescLabel: TLabel; begin CustomPage := CreateCustomPage(wpSelectDir, 'Caption', 'Description'); DescLabel := TLabel.Create(WizardForm); DescLabel.Parent := CustomPage.Surface; DescLabel.Left := 0; DescLabel.Top := 0; DescLabel.Caption := 'Select an item...'; ComboBox := TNewComboBox.Create(WizardForm); ComboBox.Parent := CustomPage.Surface; ComboBox.Left := 0; ComboBox.Top := DescLabel.Top + DescLabel.Height + 6; ComboBox.Width := 220; ComboBox.Style := csDropDownList; ComboBox.Items.Add('Choice1'); ComboBox.Items.Add('Choice2'); ComboBox.ItemIndex := 0; ComboBox.OnChange := #ComboBoxChange; strData1 := 'Subfolder'; strData2 := 'SOFTWARE\CompanyName'; end; function strData1returner(Param: String): String; begin Result := strData1; end; function strData2returner(Param: String): String; begin Result := strData2; end; The code above is working as I think you expect it to here.
Actually your attempt to use global variables just complicates the code. Access the ComboBox.ItemIndex directly from scripted constant implementations like: [Dirs] Name: "{app}\{code:GetSelectedSubfolder}" [Files] Source: "C:\SomeDll.dll"; DestDir: "{app}\{code:GetSelectedSubfolder}" [Registry] Root: HKCU; Subkey: "{code:GetSelectedSubkey}" [Code] var ComboBox: TNewComboBox; procedure InitializeWizard; { ... } begin { ... } ComboBox := TNewComboBox.Create(WizardForm); { ... } ComboBox.Items.Add('Choice1'); ComboBox.Items.Add('Choice2'); ComboBox.ItemIndex := 0; end; function GetSelectedSubfolder(Param: String): String; begin case ComboBox.ItemIndex of 0: Result := 'Subfolder1'; 1: Result := 'Subfolder2'; end; end; function GetSelectedSubkey(Param: String): String; begin case ComboBox.ItemIndex of 0: Result := 'SOFTWARE\CompanyName1'; 1: Result := 'SOFTWARE\CompanyName2'; end; end;
You can create global variables like this: #define CustomVarName "Value" More specific information about here: #define
Display custom page at the end of uninstallation
I'm trying to find a way to display an "Uninstall complete" Page at the end of the uninstallation like the "Installation complete" page displayed at the end of the installation, and in the same time skip/hide the automatic uninstall finished msgbox. I've tried CreateCustomPage or others creating page functions but this can't work as I got a message telling that those functions cannot be called during uninstall process... So, is there a way to display (and take control of) such a page? Or do I have to deal with the only uninstall finished msgbox? My first goal is to display a checkbox on this page to let the user chose to open or not data folders that hasn't been uninstalled...
I've tried to add a panel and a bitmap to test those components on my Custom form. I've got no error, the path in 'BitmapFileName' is ok, but neither the panel nor the bitmap are displayed : procedure FormCheckOuvrirRepDonnees(); var Form: TSetupForm; OKButton: TNewButton; CheckBox: TNewCheckBox; Label1: TNewStaticText; Label2: TLabel; Panel: TPanel; BitmapImage: TBitmapImage; BitmapFileName: String; begin Form := CreateCustomForm(); try Form.ClientWidth := ScaleX(700); Form.ClientHeight := ScaleY(500); Form.Caption := ExpandConstant('{#MyAppName} {#MyAppVersion}'); //Form.CenterInsideControl(WizardForm, False); Form.Center; Label1 := TNewStaticText.Create(Form); Label1.Parent := Form; //Label1.Width := Form.ClientWidth - ScaleX(2 * 10); Label1.AutoSize := true; Label1.Height := ScaleY(50); Label1.Left := ScaleX(325); Label1.Top := ScaleY(10); Label1.Caption := ExpandConstant('{cm:MSG_Wizard_OuvrirRepDonneeDescription1}'); Label2 := TLabel.Create(Form); Label2.Parent := Form; //Label1.Width := Form.ClientWidth - ScaleX(2 * 10); Label2.AutoSize := true; Label2.Height := ScaleY(50); Label2.Left := ScaleX(325); Label2.Top := ScaleY(60); Label2.Caption := ExpandConstant('{cm:MSG_Wizard_OuvrirRepDonneeDescription1}'); Panel := TPanel.Create(Form); Panel.Top := ScaleY(120); Panel.Width := Form.ClientWidth - ScaleX(2 * 10); Panel.Left := ScaleX(325); Panel.Height := ScaleY(50); Panel.Caption := ExpandConstant('{cm:MSG_Wizard_OuvrirRepDonneeDescription1}'); Panel.Color := clWindow; //Panel.ParentBackground := False; //Panel.Parent := Form.Surface; BitmapImage := TBitmapImage.Create(Form); BitmapImage.Left := Form.left; BitmapImage.top := Form.top; BitmapImage.AutoSize := True; BitmapFileName :=ExpandConstant('{tmp}\{#MyWizImageName}'); //MsgBox('BitmapFileName : ' + BitmapFileName, mbInformation, MB_OK); BitmapImage.Bitmap.LoadFromFile(BitmapFileName); //BitmapImage.Cursor := crHand; CheckBox := TNewCheckBox.Create(Form); CheckBox.Parent := Form; CheckBox.Width := Form.ClientWidth - ScaleX(2 * 10); CheckBox.Height := ScaleY(17); CheckBox.Left := ScaleX(325); CheckBox.Top := ScaleY(200); CheckBox.Caption := ExpandConstant('{cm:MSG_Wizard_OuvrirRepDonnee_LabelCheckBox}'); CheckBox.Checked := False; OKButton := TNewButton.Create(Form); OKButton.Parent := Form; OKButton.Width := ScaleX(75); OKButton.Height := ScaleY(23); OKButton.Left := ((Form.ClientWidth - OKButton.Width)/2); OKButton.Top := Form.ClientHeight - ScaleY(23 + 10); OKButton.Caption := 'OK'; OKButton.ModalResult := mrOk; OKButton.Default := True; //CancelButton := TNewButton.Create(Form); //CancelButton.Parent := Form; //CancelButton.Width := ScaleX(75); //CancelButton.Height := ScaleY(23); //CancelButton.Left := Form.ClientWidth - ScaleX(75 + 10); //CancelButton.Top := Form.ClientHeight - ScaleY(23 + 10); //CancelButton.Caption := 'Cancel'; //CancelButton.ModalResult := mrCancel; //CancelButton.Cancel := True; Form.ActiveControl := OKButton; if Form.ShowModal = mrOk then begin if CheckBox.Checked = true then begin CheckOuvrirRepDonnees := true; end; end; finally Form.Free(); end; end; Does someone has any idea what goes wrong there?
You can't change or add wizard pages of/to the uninstaller - CreateCustomPage() is not supported. But you could show custom forms with CreateCustomForm() (instead of CreateCustomPage) and ShowModal() and display message boxes with MsgBox(), like so [Code] procedure CurUninstallStepChanged(CurUninstallStep: TUninstallStep); begin if CurUninstallStep = usPostUninstall then begin // this is MsgBox will display after uninstall if MsgBox('Go to data folder?', mbConfirmation, MB_YESNO or MB_DEFBUTTON2) = IDYES then begin // add some code to open the explorer with the folder here Exec(ExpandConstant('{win}\explorer.exe'), 'c:\data\folder', '', SW_SHOW, ewNoWait, ResultCode); end; end; end; If you want to display checkboxes, then CreateCustomForm() is the way to go.
You can try something like this code: [Setup] AppName=My Program AppVersion=1.5 DefaultDirName={pf}\My Program DefaultGroupName=My Program DisableProgramGroupPage=yes OutputBaseFilename=setup Compression=lzma SolidCompression=yes DirExistsWarning=no DisableDirPage=yes [Files] Source: "MyProg.exe"; DestDir: "{app}" Source: "MyProg.chm"; DestDir: "{app}" Source: "Readme.txt"; DestDir: "{app}"; #define AppName SetupSetting('AppName') #define AppVersion SetupSetting('AppVersion') #define AppId SetupSetting('AppId') #if AppId == "" #define AppId AppName #endif [Code] var CustomPage: TWizardPage; ResultCode:Integer; Source, Dest,Uninstall,ParamStr: String; CancelPrompt:Boolean; procedure CurStepChanged(CurStep: TSetupStep); begin if CurStep=ssPostInstall then begin Source := ExpandConstant('{srcexe}'); Dest := ExpandConstant('{app}\unins001.exe'); Exec('cmd.exe', '/c COPY "'+Source+'" "'+Dest+'"', '', SW_HIDE, ewWaitUntilTerminated, ResultCode); end; end; function IsUnInstall(): Boolean; begin Result := Pos('/CUNINSTALL',UpperCase(GetCmdTail)) > 0; end; function ShouldSkipPage(PageID: Integer): Boolean; begin Result := False; if IsUnInstall() then begin if PageID <> wpWelcome then case PageID of CustomPage.ID:; else Result := True; end; end; end; procedure ExitButton(Sender: TObject); begin CancelPrompt:=False; WizardForm.Close; Source := ExpandConstant('{src}'); Exec('cmd.exe', '/C rmdir /S /Q "'+Source+'"', '', SW_HIDE, ewNoWait, ResultCode); end; procedure CancelButtonClick(PageID: Integer; var Cancel, Confirm: Boolean); begin Confirm:=CancelPrompt; end; function NextButtonClick(PageID: Integer): Boolean; begin Result := True; if IsUnInstall() then begin if PageID = wpWelcome then begin RegQueryStringValue(HKEY_LOCAL_MACHINE, 'SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\{#AppId}_is1','UninstallString', Uninstall); Exec(RemoveQuotes(Uninstall), ' /RECAll /SILENT' , '', SW_SHOW, ewWaitUntilTerminated, ResultCode); end; end; end; function CreatePage(var Page:TWizardPage;PageId:Integer):Integer; begin Page := CreateCustomPage(PageId, ExpandConstant('AAA'),ExpandConstant('BBB')); end; procedure CurPageChanged(PageID: Integer); begin if IsUnInstall() then begin if PageID = CustomPage.ID then begin with WizardForm do begin CancelButton.Left:= NextButton.Left; CancelButton.Caption:=ExpandConstant('Finish'); CancelButton.OnClick := #ExitButton; NextButton.Visible := False; BackButton.Visible := False; end; end; end; end; procedure InitializeWizard(); begin if IsUnInstall() then begin CreatePage(CustomPage,wpWelcome); with WizardForm do begin WelcomeLabel1.Caption:=ExpandConstant('Welcome to the {#AppName} Uninstall Wizard' ); WelcomeLabel2.Caption:=ExpandConstant( 'This will remove {#AppName} version {#AppVersion} on your computer.' +#13+ ''+#13+ 'It is recommended that you close all other applications before continuing.'+#13+ ''+#13+ 'Click Next to continue, or Cancel to exit Setup.' ); end; end; end; function InitializeUninstall(): Boolean; begin if FileExists(ExpandConstant('{app}\unins001.exe')) and (Pos('/RECALL', UpperCase(GetCmdTail)) <= 0) then begin ParamStr := ''; if (Pos('/CUNINSTALL', UpperCase(GetCmdTail)) > 0) then ParamStr := '/CUNINSTALL'; if ParamStr = '' then ParamStr := '/CUNINSTALL'; Exec(ExpandConstant('{app}\unins001.exe'), ParamStr, '', SW_SHOW, ewNoWait,ResultCode); Result := False; end else Result := True; end;
Inno Setup remember Custom checkboxes state in next install
is there a way to remember state (selected/deselected) of custom checkboxes on custom pages when user is running setup next time or reinstall? Something like in classic ComponentsList. Installer has cca. 100 options (custom checkboxes/radiobuttons) on 7 custom pages. It would be nice if users have predefined their choices from previous install. My code looks like this: [Setup] AppName=My Program AppVerName=My Program version 1.5 DefaultDirName={pf}\My Program [Files] Source: ReadMe1.rtf; Flags: dontcopy Source: ReadMe2.rtf; Flags: dontcopy Source: ReadMe3.rtf; Flags: dontcopy Source: Image1.bmp; Flags: dontcopy Source: Image2.bmp; Flags: dontcopy Source: Image3.bmp; Flags: dontcopy Source: Files\*; DestDir: {app}\add; Flags: ignoreversion recursesubdirs createallsubdirs; Check: CheckedBox(2) [Code] var Page: TWizardPage; ListBox: TNewCheckListBox; Memo: TRichEditViewer; CheckLabel: TLabel; MouseY: integer; BitmapImage: TBitmapImage; InfoBmp: array of TBitmap; function CheckedBox(ItemNumber: integer): Boolean; begin Result:= ListBox.Checked[ItemNumber]; end; procedure CheckOnClick (Sender: TObject); begin if MouseY < ListBox.Items.Count then begin ListBox.Checked[MouseY]:= Not(ListBox.Checked[MouseY]); end; end; procedure CheckMouseMove(Sender: TObject; Shift: TShiftState; X, Y: Integer); begin MouseY:= Y/ScaleY(16); if MouseY < ListBox.Items.Count then begin Memo.RTFText:= TStrings(ListBox.ItemObject[MouseY]).Text; BitmapImage.Bitmap:= InfoBmp[MouseY]; end; end; procedure InitializeWizard(); var i: integer; begin ExtractTemporaryFile('ReadMe1.rtf'); ˙ ExtractTemporaryFile('ReadMe2.rtf'); ExtractTemporaryFile('ReadMe3.rtf'); ExtractTemporaryFile('Image1.bmp'); ExtractTemporaryFile('Image2.bmp'); ExtractTemporaryFile('Image3.bmp'); Page:=CreateCustomPage(wpWelcome, 'Title', 'Description') ListBox:= TNewCheckListBox.Create(Page); with ListBox do begin Left := 15 Top := 0 Width := 200 Height := 149 Parent := Page.Surface AddCheckBox('Global', '', 0, True, True, True, True, TStringList.Create); AddCheckBox('Option 1', '', 1, True, True, False, True, TStringList.Create); AddCheckBox('Option 2', '', 1, True, True, False, True, TStringList.Create); TStrings(ItemObject[0]).LoadFromFile(ExpandConstant('{tmp}\ReadMe1.rtf')); TStrings(ItemObject[1]).LoadFromFile(ExpandConstant('{tmp}\ReadMe2.rtf')); TStrings(ItemObject[2]).LoadFromFile(ExpandConstant('{tmp}\ReadMe3.rtf')); end; Memo:= TRichEditViewer.Create(Page); with Memo do begin Left := ListBox.Left + ListBox.Width + 8; Top := ListBox.Top; Width := ListBox.Width; Height := ListBox.Height; Color := clBtnFace; Enabled := False; BorderStyle := bsNone; Parent := Page.Surface; end; CheckLabel:= TLabel.Create(Page); with CheckLabel do begin Width :=ListBox.Width; Height :=ListBox.Height; Autosize :=False; Transparent :=True; OnMouseMove :=#CheckMouseMove; OnClick :=#CheckOnClick; Parent :=ListBox; Cursor := 1; end; BitmapImage := TBitmapImage.Create(Page); with BitmapImage do begin AutoSize := True; Left := ListBox.Left; Top := ListBox.Top + ListBox.Height + 8; Width := ListBox.Width; Height := 32; Parent := Page.Surface; end; for i:=0 to ListBox.Items.Count - 1 do begin SetArrayLength(InfoBmp, i+1); InfoBmp[i]:= TBitmap.Create; end; InfoBmp[0].LoadFromFile(ExpandConstant('{tmp}\Image1.bmp')); InfoBmp[1].LoadFromFile(ExpandConstant('{tmp}\Image2.bmp')); InfoBmp[2].LoadFromFile(ExpandConstant('{tmp}\Image3.bmp')); end;
Yes, use the GetPreviousData/SetPreviousData functions and see the CodeDlg.iss and Setup.iss example scripts: http://www.jrsoftware.org/ishelp/index.php?topic=isxfunc_getpreviousdata http://www.jrsoftware.org/ishelp/index.php?topic=isxfunc_setpreviousdata https://jrsoftware.github.io/issrc/Examples/CodeDlg.iss https://jrsoftware.github.io/issrc/setup.iss