Canvas line disappearing - lazarus

Let's say i draw a green rectangle with TPaintBox on a panel(FillRect method). On this rectangle I make horizontal lines(lineTo method). Then on those lines I put TShape(e.g a square). Now when I change the visibility of the TShape to false part of the line in which there was previously the TShape disappears leaving me with the effect like this:
How do I do that this part of the line doesn't disappear?
Here's the code + I noticed an odd thing while I was writing this code: if I do not put the showMessage method in the code the line and the tShape will not display. Why is that?
var
Panel1 : TPanel;
PaintBox1 : TPaintBox;
procedure TForm1.Button1Click(Sender: TObject);
var t : TShape;
begin
Panel1 := TPanel.Create(form1);
Panel1.parent := form1;
Panel1.Color := clGreen;
Panel1.Width := 500;
Panel1.Height := 500;
Panel1.Top := 0;
Panel1.Left := 0;
PaintBox1 := TPaintBox.Create(form1);
PaintBox1.parent := Panel1;
PaintBox1.Width := 500;
PaintBox1.Height := 500;
PaintBox1.Top := 0;
PaintBox1.Left := 0;
//showMessage('eee');
PaintBox1.Canvas.Pen.Color := clWhite;
PaintBox1.Canvas.line(0,50,PaintBox1.Width,50);
t := TShape.Create(form1);
t.parent := Panel1;
t.Brush.Color := clRed;
t.Width := 50;
t.Height := 50;
t.Top := 25;
t.Left := 200;
t.Visible :=false;
end;

The problem you have is because you are painting at the wrong point in your program. Painting to a paint box control must happen in the OnPaint event handler. The content of a paint box is re-painted on demand. The system does this when it needs to by firing the OnPaint event. You need to move the painting code into such an event handler.
If you wish to draw to a persistent canvas then you could consider using a TImage instead.

Related

Why is my Delphi code not executing in order?

I am creating a program, and I need to display an image and then block input for a few seconds before allowing it again. The problem I am running into is that Delphi is not running the code in order and is executing the Sleep() command before the image command. I have run into this problem before when using Sleep() with a video before displaying a message.
The code looks as follows:
procedure TtForm.WindowsMediaPlayer2Click(ASender: TObject;
nButton, nShiftState: SmallInt; fX, fY: Integer);
Var
buttonSelected: Integer;
begin
buttonSelected := MessageDlg('Well done Monkey!-_-', mtError, mbOKCancel, 0);
if buttonSelected = mrOK then
begin
Pages.Visible := False;
WindowsMediaPlayer2.Visible := False;
imgEroor.BringToFront;
BorderStyle := bsNone;
WindowState := wsMaximized;
imgEroor.Top := 0;
imgEroor.Left := 0;
imgEroor.Width := Screen.Width;
imgEroor.Height := Screen.Height;
imgEroor.BringToFront;
BlockInput(True);
Sleep(10000);
BlockInput(False);
end;
if buttonSelected = mrCancel then
begin
Pages.Visible := False;
WindowsMediaPlayer2.Visible := False;
imgEroor.BringToFront;
BorderStyle := bsNone;
WindowState := wsMaximized;
imgEroor.Top := 0;
imgEroor.Left := 0;
imgEroor.Width := Screen.Width;
imgEroor.Height := Screen.Height;
imgEroor.BringToFront;
BlockInput(True);
Sleep(10000);
BlockInput(False);
end;
end;

FireDAC under connecting freeze GUI

I'm facing with an issue, here is my code
constructor TORAThread.Create;
begin
inherited Create(True);
ORAFDcon_Ora := TFDConnection.Create(nil);
ORAFDPhysOracleDriverLink := TFDPhysOracleDriverLink.Create(nil);
ORAFDGUIxWaitCursor := TFDGUIxWaitCursor.Create(nil);
ORAStorPRoc := TFDStoredProc.Create(nil);
ORAFDcon_Ora.DriverName := 'ora';
ORAFDcon_Ora.LoginPrompt := False;
ORAFDcon_Ora.Params.LoadFromFile('ORAconfig.ini');
ORAFDcon_Ora.CheckConnectionDef;
ORAFDcon_Ora.ResourceOptions.AutoConnect := True;
ORAFDcon_Ora.ResourceOptions.AutoReconnect := True;
ORAFDcon_Ora.ResourceOptions.KeepConnection := True;
ORAFDcon_Ora.ResourceOptions.CmdExecMode := amNonBlocking;
procedure TORAThread.Execute;
begin
ORAFDcon_Ora.Connected := True;
while not terminated do
begin
//somejobs
end;
When I start the thread and VPN connection is not alive, my GUI freezes
Whats wrong?
Regards,

Localized string values for the size strings KB, MB, GB etc.?

Where is this strins resources is stored on the Windows?
I need to show size corectly on native language of installed Windows.
Strings are very specific to the application that is using it. There are no generic string resouce in windows that an application can use. Of course you can write a program to search the resource in the windows folder to see which resource dll has the string that you are looking for and then use that resource dll in your application, but that is unadvisable. The reason being that, any new update of the windows that brings in resource dll changes can break your application.
As the other poster advises, you are better of writing your own resource dll and localize it in the languages that you want to support your application.
This is possible with disk quota library which is available since Windows XP:
function FindStringResourceEx(AInstance: HINST; AStringID: UINT; ALangID: UINT): PWideChar;
var
Res: HRSRC;
LoadedRes: HGLOBAL;
I: Integer;
begin
Result := nil;
Res := FindResourceEx(AInstance, RT_STRING, MAKEINTRESOURCE(AStringID div 16 + 1), ALangID);
if Res <> 0 then begin
LoadedRes := LoadResource(AInstance, Res);
if LoadedRes <> 0 then
try
Result := PChar(LockResource(LoadedRes));
if Assigned(Result) then
try
for I := 0 to (AStringID and 15) - 1 do
Inc(Result, PWord(Result)^ + 1);
finally
UnlockResource(THandle(Result));
end;
finally
FreeResource(LoadedRes);
end;
end;
end;
function GetSizeStrings(out sBytes, sKB, sMB, sGB, sTB, sPB, sEB: string): Boolean;
var
hLib: HMODULE;
sRes: string;
I: Integer;
SL: TStringList;
begin
Result := False;
hLib := LoadLibrary('dskquoui.dll');
if hLib > 0 then
try
SL := TStringList.Create;
try
sRes := FindStringResourceEx(hLib, 14472, MAKELANGID(LANG_NEUTRAL, SUBLANG_NEUTRAL));
Result := sRes <> '';
if Result then begin
sRes := sRes.Remove(0, 1);
I := sRes.IndexOf(#$B);
if I > -1 then
sRes := sRes.Remove(I);
SL.Delimiter := #2;
SL.DelimitedText := sRes;
sBytes := SL[0]; // bytes
sKB := SL[1]; // KB
sMB := SL[2]; // MB
sGB := SL[3]; // GB
sTB := SL[4]; // TB
sPB := SL[5]; // PB
sEB := SL[6]; // EB
end;
finally
SL.Free;
end;
finally
FreeLibrary(hLib);
end;
if not Result then begin
sBytes := 'bytes';
sKB := 'KB';
sMB := 'MB';
sGB := 'GB';
sTB := 'TB';
sPB := 'PB';
sEB := 'EB';
end;
end;

Inno Setup - How to change a label caption [or other controls in general], when selected value in combox box changes

When changing a language in combo box (without clicking ok), I want to change texts of the dialog (label, form caption, button caption)
procedure SelectLanguage();
var
LanguageForm: TSetupForm;
CancelButton: TNewButton;
OKButton: TNewButton;
LangCombo: TNewComboBox;
SelectLabel: TNewStaticText;
Languages: TStrings;
Params: string;
Instance: THandle;
P, I: Integer;
S, L: string;
begin
Languages := TStringList.Create();
Languages.Add('en=English');
Languages.Add('cs='+#$010C+'e'+#$0161+'tina');
LanguageForm := CreateCustomForm;
LanguageForm.Caption := SetupMessage(msgSelectLanguageTitle);
LanguageForm.ClientWidth := ScaleX(297);
LanguageForm.ClientHeight := ScaleY(125);
LanguageForm.BorderStyle := bsDialog;
LanguageForm.Center;
CancelButton := TNewButton.Create(LanguageForm);
CancelButton.Parent := LanguageForm;
CancelButton.Left := ScaleX(214);
CancelButton.Top := ScaleY(93);
CancelButton.Width := ScaleY(75);
CancelButton.Height := ScaleY(23);
CancelButton.TabOrder := 3;
CancelButton.ModalResult := mrCancel;
CancelButton.Caption := SetupMessage(msgButtonCancel);
OKButton := TNewButton.Create(LanguageForm);
OKButton.Parent := LanguageForm;
OKButton.Left := ScaleX(133);
OKButton.Top := ScaleY(93);
OKButton.Width := ScaleX(75);
OKButton.Height := ScaleY(23);
OKButton.Caption := SetupMessage(msgButtonOK);
OKButton.Default := True
OKButton.ModalResult := mrOK;
OKButton.TabOrder := 2;
LangCombo := TNewComboBox.Create(LanguageForm);
LangCombo.Parent := LanguageForm;
LangCombo.Left := ScaleX(16);
LangCombo.Top := ScaleY(56);
LangCombo.Width := ScaleX(273);
LangCombo.Height := ScaleY(21);
LangCombo.Style := csDropDownList;
LangCombo.DropDownCount := 16;
LangCombo.TabOrder := 1;
SelectLabel := TNewStaticText.Create(LanguageForm);
SelectLabel.Parent := LanguageForm;
SelectLabel.Left := ScaleX(16);
SelectLabel.Top := ScaleY(8);
SelectLabel.Width := ScaleX(273);
SelectLabel.Height := ScaleY(39);
SelectLabel.AutoSize := False
SelectLabel.Caption := SetupMessage(msgSelectLanguageLabel);
SelectLabel.TabOrder := 0;
SelectLabel.WordWrap := True;
for I := 0 to Languages.Count - 1 do
begin
P := Pos('=', Languages.Strings[I]);
L := Copy(Languages.Strings[I], 0, P - 1);
S := Copy(Languages.Strings[I], P + 1, Length(Languages.Strings[I]) - P);
LangCombo.Items.Add(S);
if L = ActiveLanguage then
LangCombo.ItemIndex := I;
end;
if LanguageForm.ShowModal = mrOK then
begin
{ ... }
end;
end;
function InitializeSetup(): Boolean;
begin
SelectLanguage();
{ ... }
end;
Spanish: first language.
I select English and no change the language of the language selector.
You have the code already. You just need to make some local variables in the SelectLanguage function global, so they can be used in the LangChange function:
var
LanguageForm: TSetupForm;
SelectLabel: TNewStaticText;
CancelButton: TNewButton;
procedure LangChange(Sender : TObject);
begin
case TNewComboBox(Sender).ItemIndex of
0: { English }
begin
SelectLabel.Caption := 'Select the language to use during the installation:';
CancelButton.Caption := 'Cancel';
LanguageForm.Caption := 'Select setup language';
end;
1: { Czech }
begin
SelectLabel.Caption := 'Zvolte jazyk, kter'+#$FD+' se m'+#$E1+' pou'+#$17E+#$ED+'t b'+#$11B+'hem instalace:';
CancelButton.Caption := 'Storno';
LanguageForm.Caption := 'V'+#$FD+'b'+#$11B+'r jazyka pr'+#$16F+'vodce instalac'+#$ED+'';
end;
end;
end;
In the SelectLanguage, remove these the declarations of local variables:
LanguageForm: TSetupForm;
SelectLabel: TNewStaticText;
CancelButton: TNewButton;
And assign the LangChange event handler:
LangCombo.OnChange := #LangChange;

How to remove the bottom panel in inno set up..and replace it with a custom panel

i want to replace the bottom panel where we show Next,Back buttons with a custom panel which includes the installation progress bar..once the installation is completed,then page should automatically redirected to next page.
Below is mockup image,how i want to make this page.
Here is the script including also the main panel header from your previous question as well. Save it into your ..\InnoSetup\Examples\ folder as well as the following images which you need to convert to BMP files since I couldn't find any trusted file sharing site which wouldn't convert the images to PNG or JPG format:
this one convert to BMP and save as Logo.bmp
this one convert to BMP and save as InstallBackground.bmp
Here is the script (you should follow the commented version of this script first):
[Setup]
AppName=ERPBO
AppVersion=1.5
DefaultDirName={pf}\My Program
DefaultGroupName=My Program
UninstallDisplayIcon={app}\MyProg.exe
Compression=lzma2
SolidCompression=yes
OutputDir=userdocs:Inno Setup Examples Output
WizardSmallImageFile=Logo.bmp
[Files]
Source: "MyProg.exe"; DestDir: "{app}"
Source: "MyProg.chm"; DestDir: "{app}"
Source: "InstallBackground.bmp"; Flags: dontcopy
[Icons]
Name: "{group}\My Program"; Filename: "{app}\MyProg.exe"
[Run]
Filename: "{app}\MyProg.chm"; Check: JustBlockTheInstallPage
[Messages]
SetupWindowTitle=Installere - %1
WizardInstalling=Installasjon pågår...
[Code]
function JustBlockTheInstallPage: Boolean;
begin
Result := False;
WizardForm.StatusLabel.Caption := 'Pakker ut filer...';
WizardForm.FilenameLabel.Caption :='C:\dnpr\Crystal reports setup\WindowShoppingNet.msi';
MsgBox('Message just to see the install page :-)', mbInformation, MB_OK);
end;
var
InnerNotebookBounds: TRect;
OuterNotebookBounds: TRect;
InstallBottomPanel: TPanel;
InstallBackground: TBitmapImage;
function Rect(const ALeft, ATop, ARight, ABottom: Integer): TRect;
begin
Result.Left := ALeft;
Result.Top := ATop;
Result.Bottom := ABottom;
Result.Right := ARight;
end;
function GetBoundsRect(AControl: TControl): TRect;
begin
Result.Left := AControl.Left;
Result.Top := AControl.Top;
Result.Right := AControl.Left + AControl.Width;
Result.Bottom := AControl.Top + AControl.Height;
end;
procedure SetBoundsRect(AControl: TControl; const ARect: TRect);
begin
AControl.Left := ARect.Left;
AControl.Top := ARect.Top;
AControl.Width := ARect.Right - ARect.Left
AControl.Height := ARect.Bottom - ARect.Top;
end;
procedure CenterHorizontally(ASource, ATarget: TControl);
begin
ATarget.Left := (ASource.Width - ATarget.Width) div 2;
end;
procedure CenterVertically(ASource, ATarget: TControl);
begin
ATarget.Top := (ASource.Height - ATarget.Height) div 2;
end;
procedure InitializeWizard;
begin
WizardForm.PageDescriptionLabel.Visible := False;
WizardForm.PageNameLabel.Font.Size := 18;
WizardForm.PageNameLabel.Font.Name := 'Comic Sans MS';
WizardForm.PageNameLabel.AutoSize := True;
WizardForm.PageNameLabel.Left := 18;
CenterVertically(WizardForm.MainPanel, WizardForm.PageNameLabel);
WizardForm.WizardSmallBitmapImage.AutoSize := True;
WizardForm.WizardSmallBitmapImage.Left := WizardForm.ClientWidth - WizardForm.WizardSmallBitmapImage.Width - 18;
CenterVertically(WizardForm.MainPanel, WizardForm.WizardSmallBitmapImage);
WizardForm.InstallingPage.Color := clWhite;
InstallBottomPanel := TPanel.Create(WizardForm);
InstallBottomPanel.Parent := WizardForm.InstallingPage;
InstallBottomPanel.BevelOuter := bvNone;
InstallBottomPanel.Align := alBottom;
InstallBottomPanel.Caption := '';
InstallBottomPanel.Color := $00C7CFD3;
InstallBottomPanel.Height := 79;
InstallBottomPanel.ParentBackground := False;
ExtractTemporaryFile('InstallBackground.bmp');
InstallBackground := TBitmapImage.Create(WizardForm);
InstallBackground.Parent := WizardForm.InstallingPage;
InstallBackground.AutoSize := True;
InstallBackground.Bitmap.LoadFromFile(ExpandConstant('{tmp}\InstallBackground.bmp'));
WizardForm.StatusLabel.Parent := InstallBottomPanel;
WizardForm.StatusLabel.Left := 8;
WizardForm.StatusLabel.Top := 8;
WizardForm.FilenameLabel.Parent := InstallBottomPanel;
WizardForm.FilenameLabel.Left := 8;
WizardForm.FilenameLabel.Top := WizardForm.StatusLabel.Top + 16;
WizardForm.ProgressGauge.Parent := InstallBottomPanel;
WizardForm.ProgressGauge.Left := 8;
WizardForm.ProgressGauge.Top := WizardForm.FilenameLabel.Top + 26;
InnerNotebookBounds := GetBoundsRect(WizardForm.InnerNotebook);
OuterNotebookBounds := GetBoundsRect(WizardForm.OuterNotebook);
end;
procedure CurPageChanged(CurPageID: Integer);
begin
if CurPageID = wpInstalling then
begin
SetBoundsRect(WizardForm.OuterNotebook, Rect(OuterNotebookBounds.Left,
OuterNotebookBounds.Top, OuterNotebookBounds.Right, WizardForm.ClientHeight));
SetBoundsRect(WizardForm.InnerNotebook, Rect(OuterNotebookBounds.Left,
WizardForm.Bevel1.Top + WizardForm.Bevel1.Height, OuterNotebookBounds.Right,
WizardForm.ClientHeight));
CenterHorizontally(WizardForm.InstallingPage, InstallBackground);
InstallBackground.Top := InstallBottomPanel.Top - InstallBackground.Height;
WizardForm.ProgressGauge.Width := InstallBottomPanel.Width - 16;
end
else
begin
SetBoundsRect(WizardForm.OuterNotebook, OuterNotebookBounds);
SetBoundsRect(WizardForm.InnerNotebook, InnerNotebookBounds);
end;
end;
And the result how the installation page looks like (and yes, I have used Comic Sans :-)

Resources