mirror of
https://gitlab.com/freepascal.org/lazarus/lazarus.git
synced 2025-08-18 08:19:29 +02:00
anchordocking: restore custom dock site
git-svn-id: trunk@26034 -
This commit is contained in:
parent
7e1ac4fe1a
commit
f987a5217d
@ -350,6 +350,8 @@ type
|
||||
property Controls[Index: integer]: TControl read GetControls;
|
||||
function IndexOfControl(const aName: string): integer;
|
||||
function FindControl(const aName: string): TControl;
|
||||
function IsSite(AControl: TControl): boolean;
|
||||
function IsCustomSite(AControl: TControl): boolean;
|
||||
|
||||
// show / make a control dockable
|
||||
procedure MakeDockable(AControl: TControl; Show: boolean = true;
|
||||
@ -501,8 +503,7 @@ begin
|
||||
i:=ControlCount-1;
|
||||
while i>=0 do begin
|
||||
AControl:=Controls[i];
|
||||
if (AControl.HostDockSite is TAnchorDockHostSite)
|
||||
and GetParentForm(AControl).IsVisible
|
||||
if GetParentForm(AControl).IsVisible
|
||||
and (Tree.Root.FindChildNode(AControl.Name,true)=nil)
|
||||
and (Application.MainForm<>AControl) then begin
|
||||
// AControl is currently on a visible site, but not in the Tree
|
||||
@ -563,7 +564,7 @@ procedure TAnchorDockMaster.MapTreeToControls(Tree: TAnchorDockLayoutTree;
|
||||
TreeNameToDocker: TADNameToControl);
|
||||
|
||||
procedure MapHostDockSites(Node: TAnchorDockLayoutTreeNode);
|
||||
// map in TreeNameToDocker each control name to its HostDockSite
|
||||
// map in TreeNameToDocker each control name to its HostDockSite or custom dock site
|
||||
var
|
||||
i: Integer;
|
||||
AControl: TControl;
|
||||
@ -573,9 +574,16 @@ procedure TAnchorDockMaster.MapTreeToControls(Tree: TAnchorDockLayoutTree;
|
||||
AControl:=FindControl(Node.Name);
|
||||
if (AControl<>nil) and (AControl.HostDockSite is TAnchorDockHostSite) then
|
||||
TreeNameToDocker[Node.Name]:=AControl.HostDockSite;
|
||||
end else
|
||||
for i:=0 to Node.Count-1 do
|
||||
MapHostDockSites(Node[i]); // recursive
|
||||
// ignore kids
|
||||
exit;
|
||||
end;
|
||||
if (Node.NodeType=adltnCustomSite) then begin
|
||||
AControl:=FindControl(Node.Name);
|
||||
if IsCustomSite(AControl) then
|
||||
TreeNameToDocker[Node.Name]:=AControl;
|
||||
end;
|
||||
for i:=0 to Node.Count-1 do
|
||||
MapHostDockSites(Node[i]); // recursive
|
||||
end;
|
||||
|
||||
procedure MapTopLevelSites(Node: TAnchorDockLayoutTreeNode);
|
||||
@ -587,12 +595,12 @@ procedure TAnchorDockMaster.MapTreeToControls(Tree: TAnchorDockLayoutTree;
|
||||
// flickering.
|
||||
|
||||
function FindMappedControl(ChildNode: TAnchorDockLayoutTreeNode
|
||||
): TAnchorDockHostSite;
|
||||
): TCustomForm;
|
||||
var
|
||||
i: Integer;
|
||||
begin
|
||||
if ChildNode.NodeType=adltnControl then
|
||||
Result:=TAnchorDockHostSite(TreeNameToDocker[ChildNode.Name])
|
||||
if ChildNode.NodeType in [adltnControl,adltnCustomSite] then
|
||||
Result:=TCustomForm(TreeNameToDocker[ChildNode.Name])
|
||||
else
|
||||
for i:=0 to ChildNode.Count-1 do begin
|
||||
Result:=FindMappedControl(ChildNode[i]); // search recursive
|
||||
@ -603,18 +611,18 @@ procedure TAnchorDockMaster.MapTreeToControls(Tree: TAnchorDockLayoutTree;
|
||||
var
|
||||
i: Integer;
|
||||
RootSite: TCustomForm;
|
||||
Site: TAnchorDockHostSite;
|
||||
Site: TCustomForm;
|
||||
begin
|
||||
if Node.IsSplitter then exit;
|
||||
if Node.IsRootWindow then begin
|
||||
if Node.Name='' then exit;
|
||||
if Node.NodeType=adltnControl then exit;
|
||||
// not is a complex site
|
||||
// Node is a complex site
|
||||
if TreeNameToDocker[Node.Name]<>nil then exit;
|
||||
// and not yet mapped to a site
|
||||
Site:=FindMappedControl(Node);
|
||||
if Site=nil then exit;
|
||||
// and there is sub node mapped to a site
|
||||
// and there is sub node mapped to a site (anchor or custom)
|
||||
RootSite:=GetParentForm(Site);
|
||||
if not (RootSite is TAnchorDockHostSite) then exit;
|
||||
// and the mapped site has a root site
|
||||
@ -707,13 +715,14 @@ end;
|
||||
function TAnchorDockMaster.RestoreLayout(Tree: TAnchorDockLayoutTree;
|
||||
TreeNameToDocker: TADNameToControl): boolean;
|
||||
|
||||
procedure SetupSite(Site: TAnchorDockHostSite;
|
||||
procedure SetupSite(Site: TCustomForm;
|
||||
Node: TAnchorDockLayoutTreeNode; Parent: TWinControl);
|
||||
begin
|
||||
Site.BoundsRect:=Node.BoundsRect;
|
||||
Site.Visible:=true;
|
||||
Site.Parent:=Parent;
|
||||
Site.Header.HeaderPosition:=Node.HeaderPosition;
|
||||
if Site is TAnchorDockHostSite then
|
||||
TAnchorDockHostSite(Site).Header.HeaderPosition:=Node.HeaderPosition;
|
||||
if Parent=nil then begin
|
||||
Site.WindowState:=Node.WindowState;
|
||||
if (Node.Monitor>=0) and (Node.Monitor<Screen.MonitorCount) then
|
||||
@ -753,6 +762,21 @@ function TAnchorDockMaster.RestoreLayout(Tree: TAnchorDockLayoutTree;
|
||||
AControl.Visible:=true;
|
||||
SetupSite(Site,Node,Parent);
|
||||
Result:=Site;
|
||||
end else if Node.NodeType=adltnCustomSite then begin
|
||||
// restore custom dock site
|
||||
// the control was already created
|
||||
// => position it
|
||||
AControl:=FindControl(Node.Name);
|
||||
if AControl=nil then begin
|
||||
debugln(['TAnchorDockMaster.RestoreLayout.Restore WARNING: can not find control ',Node.Name]);
|
||||
exit;
|
||||
end;
|
||||
if not IsCustomSite(AControl) then begin
|
||||
debugln(['TAnchorDockMaster.RestoreLayout.Restore WARNING: ',Node.Name,' is not a custom dock site ',DbgSName(AControl)]);
|
||||
exit;
|
||||
end;
|
||||
SetupSite(TCustomForm(AControl),Node,nil);
|
||||
Result:=AControl;
|
||||
end else if Node.IsSplitter then begin
|
||||
// restore splitter
|
||||
Splitter:=TAnchorDockSplitter(TreeNameToDocker[Node.Name]);
|
||||
@ -962,6 +986,18 @@ begin
|
||||
Result:=nil;
|
||||
end;
|
||||
|
||||
function TAnchorDockMaster.IsSite(AControl: TControl): boolean;
|
||||
begin
|
||||
Result:=(AControl is TAnchorDockHostSite) or IsCustomSite(AControl);
|
||||
end;
|
||||
|
||||
function TAnchorDockMaster.IsCustomSite(AControl: TControl): boolean;
|
||||
begin
|
||||
Result:=(AControl is TCustomForm) // also checks for nil
|
||||
and (AControl.Parent=nil)
|
||||
and (TCustomForm(AControl).DockManager is TAnchorDockManager);
|
||||
end;
|
||||
|
||||
procedure TAnchorDockMaster.MakeDockable(AControl: TControl; Show: boolean;
|
||||
BringToFront: boolean; AddDockHeader: boolean);
|
||||
var
|
||||
@ -1032,6 +1068,10 @@ begin
|
||||
raise Exception.Create('TAnchorDockMaster.MakeDockSite Parent='+DbgSName(AForm.Parent));
|
||||
AForm.DisableAutoSizing;
|
||||
try
|
||||
if FControls.IndexOf(AForm)<0 then begin
|
||||
FControls.Add(AForm);
|
||||
AForm.FreeNotification(Self);
|
||||
end;
|
||||
AManager:=TAnchorDockManager.Create(AForm);
|
||||
AManager.DockableSites:=Sites;
|
||||
AForm.DockManager:=AManager;
|
||||
@ -1110,8 +1150,7 @@ begin
|
||||
Site:=TAnchorDockHostSite(AForm);
|
||||
LayoutNode:=LayoutTree.NewNode(LayoutTree.Root);
|
||||
Site.SaveLayout(LayoutTree,LayoutNode);
|
||||
end else if (AForm.DockManager is TAnchorDockManager)
|
||||
and (AForm.Parent=nil) then begin
|
||||
end else if IsCustomSite(AForm) then begin
|
||||
// custom dock site
|
||||
LayoutNode:=LayoutTree.NewNode(LayoutTree.Root);
|
||||
LayoutNode.NodeType:=adltnCustomSite;
|
||||
@ -1615,8 +1654,7 @@ begin
|
||||
end;
|
||||
BoundsRect:=NewBounds;
|
||||
BoundsIncreased:=true;
|
||||
end else if (Parent.DockManager is TAnchorDockManager)
|
||||
and (Parent.Parent=nil) then begin
|
||||
end else if DockMaster.IsCustomSite(Parent) then begin
|
||||
// Parent is a custom docksite
|
||||
// => expand Self and Parent
|
||||
// expand Parent (the custom docksite)
|
||||
@ -1953,11 +1991,9 @@ procedure TAnchorDockHostSite.RemoveControlFromLayout(AControl: TControl);
|
||||
p:=ClientOrigin;
|
||||
OffsetRect(NewBounds,p.x,p.y);
|
||||
BoundsRect:=NewBounds;
|
||||
end else if ((not (Parent is TAnchorDockHostSite))
|
||||
and (Parent.DockManager is TAnchorDockManager)
|
||||
and (Parent.Parent=nil))
|
||||
then begin
|
||||
// shrink this site and the parent (which is a custom dock site)
|
||||
end else if DockMaster.IsCustomSite(Parent) then begin
|
||||
// parent is a custom dock site
|
||||
// shrink this site and the parent
|
||||
NewParentBounds:=Parent.BoundsRect;
|
||||
case Align of
|
||||
alTop:
|
||||
@ -2748,11 +2784,7 @@ var
|
||||
begin
|
||||
GetWindowRect(Handle, InfluenceRect);
|
||||
|
||||
if (Parent=nil)
|
||||
or ((not (Parent is TAnchorDockHostSite))
|
||||
and (Parent.DockManager is TAnchorDockManager)
|
||||
and (Parent.Parent=nil))
|
||||
then begin
|
||||
if (Parent=nil) or DockMaster.IsCustomSite(Parent) then begin
|
||||
// allow docking outside => enlarge margins
|
||||
ADockMargin:=DockMaster.DockOutsideMargin;
|
||||
InfluenceRect.Left := InfluenceRect.Left-ADockMargin;
|
||||
|
@ -1078,6 +1078,13 @@ var
|
||||
Side: TAnchorKind;
|
||||
Sibling: TAnchorDockLayoutTreeNode;
|
||||
begin
|
||||
// check parent
|
||||
if (NodeType=adltnNone) and (Parent<>nil) then
|
||||
raise EAnchorDockLayoutError.Create('invalid parent');
|
||||
if (NodeType=adltnCustomSite) and (Parent.NodeType<>adltnNone) then
|
||||
raise EAnchorDockLayoutError.Create('invalid parent');
|
||||
|
||||
// check sides
|
||||
for Side:=low(TAnchorKind) to high(TAnchorKind) do begin
|
||||
if Anchors[Side]<>'' then begin
|
||||
// anchor must be a sibling
|
||||
@ -1116,6 +1123,7 @@ begin
|
||||
dbgs(Side), '"', Anchors[Side], '"']));
|
||||
end;
|
||||
end;
|
||||
|
||||
// only the root node, pages, layouts and customsite can have children
|
||||
if (Parent<>nil) and (Count>0)
|
||||
and (not (NodeType in [adltnLayout,adltnPages,adltnCustomSite]))
|
||||
@ -1123,9 +1131,11 @@ begin
|
||||
raise EAnchorDockLayoutError.Create(
|
||||
Format(adrsNoChildrenAllowedForNodeType, ['"', Name, '"',
|
||||
ADLTreeNodeTypeNames[NodeType]]));
|
||||
if (NodeType=adltnCustomSite) and (Count>1) then
|
||||
raise EAnchorDockLayoutError.Create(Format(
|
||||
adrsCustomDockSiteCanHaveOnlyOneSite, ['"', Name, '"']));
|
||||
if (NodeType=adltnCustomSite) then begin
|
||||
if (Count>1) then
|
||||
raise EAnchorDockLayoutError.Create(Format(
|
||||
adrsCustomDockSiteCanHaveOnlyOneSite, ['"', Name, '"']));
|
||||
end;
|
||||
|
||||
// check grandchild
|
||||
for i:=0 to Count-1 do begin
|
||||
@ -1372,7 +1382,7 @@ end;
|
||||
|
||||
function TAnchorDockLayoutTreeNode.IsRootWindow: boolean;
|
||||
begin
|
||||
Result:=(NodeType in [adltnLayout,adltnPages,adltnControl])
|
||||
Result:=(NodeType in [adltnLayout,adltnPages,adltnControl,adltnCustomSite])
|
||||
and ((Parent=nil) or (Parent.NodeType in [adltnNone]));
|
||||
end;
|
||||
|
||||
|
@ -15,7 +15,6 @@ uses
|
||||
begin
|
||||
Application.Initialize;
|
||||
Application.CreateForm(TMainIDE, MainIDE);
|
||||
DockMaster.MakeDockSite(MainIDE,[akBottom]);
|
||||
Application.Run;
|
||||
end.
|
||||
|
||||
|
@ -112,6 +112,7 @@ begin
|
||||
SaveLayoutToolButton.Hint:='Save Layout to layout.xml';
|
||||
LoadLayoutToolButton.Hint:='Load layout from layout.xml';
|
||||
|
||||
DockMaster.MakeDockSite(Self,[akBottom]);
|
||||
DockMaster.OnCreateControl:=@DockMasterCreateControl;
|
||||
|
||||
SetBounds(100,50,600,80);
|
||||
|
Loading…
Reference in New Issue
Block a user