Moving/dragging TPanel in TForm lazarus / 31-LCL ---------------------------------------------------------------------- asdf · 2010-10-30 11:58 I have made a calculator, all buttons and displays are on a TPanel. I'd like the user can move/drag to some place they may need. But I could not do, kindly help. ---------------------------------------------------------------------- jixian.yang · 2010-10-30 12:39 The code for form, it is easy to be panel: unit Unit1; {$mode objfpc}{$H+} interface uses   Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs; type   { TForm1 }   TForm1 = class(TForm)     procedure FormMouseDown(Sender: TObject; Button: TMouseButton;       Shift: TShiftState; X, Y: Integer);     procedure FormMouseMove(Sender: TObject; Shift: TShiftState; X, Y: Integer);     procedure FormMouseUp(Sender: TObject; Button: TMouseButton;       Shift: TShiftState; X, Y: Integer);   private     { private declarations }   public     { public declarations }   end; var   Form1: TForm1;   oldx,oldy,isMove: integer; implementation {$R *.lfm} { TForm1 } procedure TForm1.FormMouseMove(Sender: TObject; Shift: TShiftState; X,   Y: Integer); begin   if isMove=1 then   begin     left:=left +x-oldx;     top:=top +y-oldy;   end; end; procedure TForm1.FormMouseDown(Sender: TObject; Button: TMouseButton;   Shift: TShiftState; X, Y: Integer); begin   oldx:=x;   oldy:=y;   isMove:=1; end; procedure TForm1.FormMouseUp(Sender: TObject; Button: TMouseButton;   Shift: TShiftState; X, Y: Integer); begin   isMove:=0; end; end. ---------------------------------------------------------------------- asdf · 2010-10-31 02:22 Dear jixian.yang Your code moved the TForm, it did not move the TPanel. I just need to move the TPanel in the TForm, not the TForm. Could you help me please? ---------------------------------------------------------------------- w135n03 · 2010-10-31 04:00 try this, i fix some code from jixian.yang unit Unit1; {$mode objfpc}{$H+} interface uses   Classes, SysUtils, FileUtil, LResources, Forms, Controls, Graphics, Dialogs,   ExtCtrls; type   { TForm1 }   TForm1 = class(TForm)     Panel1: TPanel;     procedure Panel1MouseDown(Sender: TObject; Button: TMouseButton;       Shift: TShiftState; X, Y: Integer);     procedure Panel1MouseMove(Sender: TObject; Shift: TShiftState; X, Y: Integer       );     procedure Panel1MouseUp(Sender: TObject; Button: TMouseButton;       Shift: TShiftState; X, Y: Integer);   private     { private declarations }   public     { public declarations }   end; var   Form1: TForm1;   oldX, oldY, isMove : Integer; implementation { TForm1 } procedure TForm1.Panel1MouseDown(Sender: TObject; Button: TMouseButton;   Shift: TShiftState; X, Y: Integer); begin   oldX := X;   oldY := Y;   isMove := 1; end; procedure TForm1.Panel1MouseMove(Sender: TObject; Shift: TShiftState; X,   Y: Integer); begin   if isMove = 1 then begin     Panel1.Left := Panel1.Left + X - oldX;     Panel1.Top := Panel1.Top + Y - oldY;   end; end; procedure TForm1.Panel1MouseUp(Sender: TObject; Button: TMouseButton;   Shift: TShiftState; X, Y: Integer); begin   isMove := 0; end; initialization   {$I unit1.lrs} end. ---------------------------------------------------------------------- asdf · 2010-10-31 05:29 One more feature please. Is there any way to make it like "AlwayShowOnTop"? Since it was sometimes hidden by some displaying controls. ---------------------------------------------------------------------- jixian.yang · 2010-10-31 12:15 If there must be a "AlwayShowOnTop" feature, we prefer TForm to TPanel. Here the Form1 worked as a "AlwayShowOnTop" TPanel: program project1; {$mode objfpc}{$H+} uses   {$IFDEF UNIX}{$IFDEF UseCThreads}   cthreads,   {$ENDIF}{$ENDIF}   Interfaces, // this includes the LCL widgetset   Controls, Forms, Unit1, Unit2   { you can add units after this }; {$R *.res} begin   Application.Initialize;   Application.CreateForm(TForm2, Form2);   Application.CreateForm(TForm1, Form1);   Form1.Parent := Form2;   Form1.Top:=0;   Form1.Left:=0;   Form1.BorderStyle:=bsNone;   Form1.FormStyle:=fsStayOnTop;   Form1.Show;   Application.Run; end. ---------------------------------------------------------------------- asdf · 2010-10-31 14:15 Now the calculator can be moved/dragged perfect. But if I click to show the calculator before showing the TPageControl, the calculator was always hidden behind the TPageControl. On the other hand, if I I click to show the calculator "after" showing the TPageControl, the calculator was always on top of everything (Sorry, I don't need to create another form). Help me please. ---------------------------------------------------------------------- w135n03 · 2010-10-31 20:28 Code: [Select]unit Unit1; {$mode objfpc}{$H+} interface uses   Classes, SysUtils, FileUtil, LResources, Forms, Controls, Graphics, Dialogs,   ExtCtrls, ComCtrls, StdCtrls; type   { TForm1 }   TForm1 = class(TForm)     Button1: TButton;     PageControl1: TPageControl;     Panel1: TPanel;     TabSheet1: TTabSheet;     procedure Button1Click(Sender: TObject);     procedure Panel1MouseDown(Sender: TObject; Button: TMouseButton;       Shift: TShiftState; X, Y: Integer);     procedure Panel1MouseMove(Sender: TObject; Shift: TShiftState; X, Y: Integer       );     procedure Panel1MouseUp(Sender: TObject; Button: TMouseButton;       Shift: TShiftState; X, Y: Integer);   private     { private declarations }   public     { public declarations }   end; var   Form1: TForm1;   oldX, oldY, isMove, isTop : Integer; implementation { TForm1 } procedure TForm1.Panel1MouseDown(Sender: TObject; Button: TMouseButton;   Shift: TShiftState; X, Y: Integer); begin   oldX := X;   oldY := Y;   isMove := 1; end; procedure TForm1.Button1Click(Sender: TObject); begin   if isTop = 0 then begin     Panel1.SendToBack;     isTop := 1;   end   else if isTop = 1 then begin     PageControl1.SendToBack;     isTop := 0;   end; end; procedure TForm1.Panel1MouseMove(Sender: TObject; Shift: TShiftState; X,   Y: Integer); begin   if isMove = 1 then begin     Panel1.Left := Panel1.Left + X - oldX;     Panel1.Top := Panel1.Top + Y - oldY;   end; end; procedure TForm1.Panel1MouseUp(Sender: TObject; Button: TMouseButton;   Shift: TShiftState; X, Y: Integer); begin   isMove := 0; end; initialization   {$I unit1.lrs} end. I add some lines of code, may be it help. Sorry for my English ---------------------------------------------------------------------- arbelest · 2010-11-01 00:46 The code is OK, but i think it better if you create your own components. It will make your code more modular and reuseable. About the code, you can modify w135n03's code like this Code: [Select]..... procedure TForm1.Button1Click(Sender: TObject); begin     Panel1.visible=not Panel1.visible;     if Panel1.visible then        Panel1.BringToFront; end; ... It will make your calculator panel show on top when toggle visible. ---------------------------------------------------------------------- asdf · 2010-11-01 11:28 Quote from: arbelest on November 01, 2010, 01:46:58 am    Panel1.visible=not Panel1.visible; There is an error message against this line. Error: Illegal Expression ---------------------------------------------------------------------- typo · 2010-11-01 11:37 You are missing the ':' before the '='. Code: [Select]Panel1.visible := not Panel1.visible; ---------------------------------------------------------------------- asdf · 2010-11-01 12:53 The result is the same ... If I click to show the calculator before showing the TPageControl, the calculator was always hidden behind the TPageControl. Why the calculator could not brought'ToFront? On the other hand, if I I click to show the calculator "after" showing the TPageControl, the calculator was always on top of everything. Very strange! I tried to use the code posted by: w135n03 (and I created a procedure to hide the TPageControl ...... Procedure TMajorForm_Form.SendToBackTPageControl;   begin   for i := 0 to MajorForm_Form.ControlCount - 1 do   if MajorForm_Form.Controls is TPageControl then   //MajorForm_Form.Controls.Visible:= false;   MajorForm_Form.Controls.SendToBack; end;                                  But still not perfect, I'm afraid that ... MajorForm_Form.Controls.SendToBack; is still wrong. ---------------------------------------------------------------------- arbelest · 2010-11-02 01:09 Quote from: asdf on November 01, 2010, 01:53:32 pmOn the other hand, if I I click to show the calculator "after" showing the TPageControl, the calculator was always on top of everything. Very strange! Sorry i confuse about "always on top of everything". Did you mean overlap all other panel, including top panel contain toggle button etc ? What is calculator's control parent ? If it is Main Form, of course it will overlap all other control inside main form. Assuming it's OK if calculator always on top of everything and PageControl is toggle too, you can try : Code: [Select]... procedure TMainForm.ButtonToggleCalculatorClick(Sender: TObject); begin     PanelCalculator.visible:=not PanelCalculator.visible;     if PanelCalculator.visible then        PanelCalculator.BringToFront; end; ... procedure TMainForm.ButtonTogglePageControlClick(Sender: TObject); begin    PageControl1.visible:=not PageControl1.visible    // force bring calculator to front if it visible    if PanelCalculator.visible then       PanelCalculator.BringToFront; end; ... @typo: thanks for your correction ---------------------------------------------------------------------- asdf · 2010-11-03 03:38 Everything is in only one form. When a TPageControl shows, it will fit the width and  height of Form except TMenu and TToolbar. ---------------------------------------------------------------------- asdf · 2010-11-08 07:37 Quote from: typo on November 01, 2010, 12:37:39 pmCode: [Select]Panel1.visible := not Panel1.visible; Could anybody explain the meaning of this syntax please? ---------------------------------------------------------------------- Mando · 2010-11-08 07:46 Hello: This code toggles the visibility of Panel1. If Panel1 is visible, the code hides it. If It's hidden,  making it visible. Regards ---------------------------------------------------------------------- asdf · 2010-11-08 08:00 Thank you so much