Implemented proper hiding and showing of dock widgets

This commit is contained in:
Uwe Kindler 2017-03-23 10:23:53 +01:00
parent b6ee26adc2
commit 16bd1a3bd2
13 changed files with 3130 additions and 2690 deletions

313
.cproject Normal file
View File

@ -0,0 +1,313 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<?fileVersion 4.0.0?><cproject storage_type_id="org.eclipse.cdt.core.XmlProjectDescriptionStorage">
<storageModule moduleId="org.eclipse.cdt.core.settings">
<cconfiguration id="cdt.managedbuild.toolchain.gnu.mingw.base.1119687795">
<storageModule buildSystemId="org.eclipse.cdt.managedbuilder.core.configurationDataProvider" id="cdt.managedbuild.toolchain.gnu.mingw.base.1119687795" moduleId="org.eclipse.cdt.core.settings" name="Default">
<externalSettings/>
<extensions>
<extension id="org.eclipse.cdt.core.PE" point="org.eclipse.cdt.core.BinaryParser"/>
<extension id="org.eclipse.cdt.core.GASErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
<extension id="org.eclipse.cdt.core.GmakeErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
<extension id="org.eclipse.cdt.core.GLDErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
<extension id="org.eclipse.cdt.core.CWDLocator" point="org.eclipse.cdt.core.ErrorParser"/>
<extension id="org.eclipse.cdt.core.GCCErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
</extensions>
</storageModule>
<storageModule moduleId="cdtBuildSystem" version="4.0.0">
<configuration artifactName="${ProjName}" buildProperties="" description="" id="cdt.managedbuild.toolchain.gnu.mingw.base.1119687795" name="Default" parent="org.eclipse.cdt.build.core.emptycfg">
<folderInfo id="cdt.managedbuild.toolchain.gnu.mingw.base.1119687795.1949777584" name="/" resourcePath="">
<toolChain id="cdt.managedbuild.toolchain.gnu.mingw.base.88699815" name="MinGW GCC" superClass="cdt.managedbuild.toolchain.gnu.mingw.base">
<targetPlatform archList="all" binaryParser="org.eclipse.cdt.core.PE" id="cdt.managedbuild.target.gnu.platform.mingw.base.519267520" name="Debug Platform" osList="win32" superClass="cdt.managedbuild.target.gnu.platform.mingw.base"/>
<builder id="cdt.managedbuild.toolchain.gnu.mingw.base.1119687795.1200539104" keepEnvironmentInBuildfile="false" managedBuildOn="false" name="Gnu Make Builder" superClass="org.eclipse.cdt.build.core.settings.default.builder"/>
<tool id="cdt.managedbuild.tool.gnu.assembler.mingw.base.1438677059" name="GCC Assembler" superClass="cdt.managedbuild.tool.gnu.assembler.mingw.base">
<option id="gnu.both.asm.option.include.paths.403127333" name="Include paths (-I)" superClass="gnu.both.asm.option.include.paths" valueType="includePath">
<listOptionValue builtIn="false" value="&quot;${workspace_loc:/QtAdvancedDockingSystem/demo}&quot;"/>
<listOptionValue builtIn="false" value="&quot;${workspace_loc:/QtAdvancedDockingSystem/src}&quot;"/>
<listOptionValue builtIn="false" value="&quot;${QTDIR}/include&quot;"/>
</option>
<inputType id="cdt.managedbuild.tool.gnu.assembler.input.1249325593" superClass="cdt.managedbuild.tool.gnu.assembler.input"/>
</tool>
<tool id="cdt.managedbuild.tool.gnu.archiver.mingw.base.933824900" name="GCC Archiver" superClass="cdt.managedbuild.tool.gnu.archiver.mingw.base"/>
<tool id="cdt.managedbuild.tool.gnu.cpp.compiler.mingw.base.1947822681" name="GCC C++ Compiler" superClass="cdt.managedbuild.tool.gnu.cpp.compiler.mingw.base">
<option id="gnu.cpp.compiler.option.include.paths.349616932" name="Include paths (-I)" superClass="gnu.cpp.compiler.option.include.paths" useByScannerDiscovery="false" valueType="includePath">
<listOptionValue builtIn="false" value="&quot;${workspace_loc:/QtAdvancedDockingSystem/src}&quot;"/>
<listOptionValue builtIn="false" value="&quot;${workspace_loc:/QtAdvancedDockingSystem/demo}&quot;"/>
<listOptionValue builtIn="false" value="&quot;${QTDIR}/include&quot;"/>
</option>
<inputType id="cdt.managedbuild.tool.gnu.cpp.compiler.input.1318830536" superClass="cdt.managedbuild.tool.gnu.cpp.compiler.input"/>
</tool>
<tool id="cdt.managedbuild.tool.gnu.c.compiler.mingw.base.389117097" name="GCC C Compiler" superClass="cdt.managedbuild.tool.gnu.c.compiler.mingw.base">
<option id="gnu.c.compiler.option.include.paths.1871729602" name="Include paths (-I)" superClass="gnu.c.compiler.option.include.paths" useByScannerDiscovery="false" valueType="includePath">
<listOptionValue builtIn="false" value="&quot;${workspace_loc:/QtAdvancedDockingSystem/demo}&quot;"/>
<listOptionValue builtIn="false" value="&quot;${workspace_loc:/QtAdvancedDockingSystem/src}&quot;"/>
<listOptionValue builtIn="false" value="&quot;${QTDIR}/include&quot;"/>
</option>
<inputType id="cdt.managedbuild.tool.gnu.c.compiler.input.1568363924" superClass="cdt.managedbuild.tool.gnu.c.compiler.input"/>
</tool>
<tool id="cdt.managedbuild.tool.gnu.c.linker.mingw.base.1734874312" name="MinGW C Linker" superClass="cdt.managedbuild.tool.gnu.c.linker.mingw.base"/>
<tool id="cdt.managedbuild.tool.gnu.cpp.linker.mingw.base.985493173" name="MinGW C++ Linker" superClass="cdt.managedbuild.tool.gnu.cpp.linker.mingw.base">
<inputType id="cdt.managedbuild.tool.gnu.cpp.linker.input.266071128" superClass="cdt.managedbuild.tool.gnu.cpp.linker.input">
<additionalInput kind="additionalinputdependency" paths="$(USER_OBJS)"/>
<additionalInput kind="additionalinput" paths="$(LIBS)"/>
</inputType>
</tool>
</toolChain>
</folderInfo>
</configuration>
</storageModule>
<storageModule moduleId="org.eclipse.cdt.core.externalSettings"/>
</cconfiguration>
</storageModule>
<storageModule moduleId="cdtBuildSystem" version="4.0.0">
<project id="QtAdvancedDockingSystem.null.1346550114" name="QtAdvancedDockingSystem"/>
</storageModule>
<storageModule moduleId="org.eclipse.cdt.core.LanguageSettingsProviders"/>
<storageModule moduleId="refreshScope"/>
<storageModule moduleId="org.eclipse.cdt.make.core.buildtargets">
<buildTargets>
<target name="Build all" path=" build" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j</buildArguments>
<buildTarget>all</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Clean" path=" build" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>make</buildCommand>
<buildTarget>clean</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>true</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Debug Build" path=" build" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j6</buildArguments>
<buildTarget>debug</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="qmake" path=" build" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>qmake</buildCommand>
<buildArguments>-recursive ../ads.pro</buildArguments>
<buildTarget/>
<stopOnError>true</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Release Build" path=" build" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j4</buildArguments>
<buildTarget>release</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Build all" path=" build/src" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j</buildArguments>
<buildTarget>all</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Clean" path=" build/src" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>make</buildCommand>
<buildArguments/>
<buildTarget>clean</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>true</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Debug Build" path=" build/src" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j6</buildArguments>
<buildTarget>debug</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="qmake" path=" build/src" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>qmake</buildCommand>
<buildArguments>-recursive ../../src/src.pro</buildArguments>
<buildTarget/>
<stopOnError>true</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Release Build" path=" build/src" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j4</buildArguments>
<buildTarget>release</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Build all" path=" build/demo" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j</buildArguments>
<buildTarget>all</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Clean" path=" build/demo" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>make</buildCommand>
<buildArguments/>
<buildTarget>clean</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>true</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Debug Build" path=" build/demo" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j6</buildArguments>
<buildTarget>debug</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="qmake" path=" build/demo" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>qmake</buildCommand>
<buildArguments>-recursive ../../demo/demo.pro</buildArguments>
<buildTarget/>
<stopOnError>true</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Release Build" path=" build/demo" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j4</buildArguments>
<buildTarget>release</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Build all" path=" build/AdvancedDockingSystemDemo" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j</buildArguments>
<buildTarget>all</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Clean" path=" build/AdvancedDockingSystemDemo" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>make</buildCommand>
<buildTarget>clean</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>true</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Debug Build" path=" build/AdvancedDockingSystemDemo" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j6</buildArguments>
<buildTarget>debug</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="qmake" path=" build/AdvancedDockingSystemDemo" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>qmake</buildCommand>
<buildArguments>-recursive ../../AdvancedDockingSystemDemo/AdvancedDockingSystemDemo.pro</buildArguments>
<stopOnError>true</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Release Build" path=" build/AdvancedDockingSystemDemo" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j4</buildArguments>
<buildTarget>release</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Build all" path=" build/AdvancedDockingSystemDemo_v2" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j</buildArguments>
<buildTarget>all</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Clean" path=" build/AdvancedDockingSystemDemo_v2" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>make</buildCommand>
<buildTarget>clean</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>true</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Debug Build" path=" build/AdvancedDockingSystemDemo_v2" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j6</buildArguments>
<buildTarget>debug</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="qmake" path=" build/AdvancedDockingSystemDemo_v2" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>qmake</buildCommand>
<buildArguments>-recursive ../../AdvancedDockingSystemDemo_v2/AdvancedDockingSystemDemo_v2.pro</buildArguments>
<stopOnError>true</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Release Build" path=" build/AdvancedDockingSystemDemo_v2" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j4</buildArguments>
<buildTarget>release</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Build all" path=" build/AdvancedDockingSystem" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j</buildArguments>
<buildTarget>all</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Clean" path=" build/AdvancedDockingSystem" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>make</buildCommand>
<buildTarget>clean</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>true</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Debug Build" path=" build/AdvancedDockingSystem" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j6</buildArguments>
<buildTarget>debug</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="qmake" path=" build/AdvancedDockingSystem" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>qmake</buildCommand>
<buildArguments>-recursive ../../AdvancedDockingSystem/src.pro</buildArguments>
<buildTarget/>
<stopOnError>true</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
<target name="Release Build" path=" build/AdvancedDockingSystem" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
<buildCommand>mingw32-make</buildCommand>
<buildArguments>-j4</buildArguments>
<buildTarget>release</buildTarget>
<stopOnError>false</stopOnError>
<useDefaultCommand>false</useDefaultCommand>
<runAllBuilders>false</runAllBuilders>
</target>
</buildTargets>
</storageModule>
<storageModule moduleId="scannerConfiguration">
<autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId=""/>
<scannerConfigBuildInfo instanceId="cdt.managedbuild.toolchain.gnu.mingw.base.1119687795;cdt.managedbuild.toolchain.gnu.mingw.base.1119687795.1949777584;cdt.managedbuild.tool.gnu.cpp.compiler.mingw.base.1947822681;cdt.managedbuild.tool.gnu.cpp.compiler.input.1318830536">
<autodiscovery enabled="false" problemReportingEnabled="true" selectedProfileId="org.eclipse.cdt.make.core.GCCStandardMakePerFileProfile"/>
</scannerConfigBuildInfo>
<scannerConfigBuildInfo instanceId="cdt.managedbuild.toolchain.gnu.mingw.base.1119687795;cdt.managedbuild.toolchain.gnu.mingw.base.1119687795.1949777584;cdt.managedbuild.tool.gnu.c.compiler.mingw.base.389117097;cdt.managedbuild.tool.gnu.c.compiler.input.1568363924">
<autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId=""/>
</scannerConfigBuildInfo>
</storageModule>
</cproject>

27
.project Normal file
View File

@ -0,0 +1,27 @@
<?xml version="1.0" encoding="UTF-8"?>
<projectDescription>
<name>QtAdvancedDockingSystem</name>
<comment></comment>
<projects>
</projects>
<buildSpec>
<buildCommand>
<name>org.eclipse.cdt.managedbuilder.core.genmakebuilder</name>
<triggers>clean,full,incremental,</triggers>
<arguments>
</arguments>
</buildCommand>
<buildCommand>
<name>org.eclipse.cdt.managedbuilder.core.ScannerConfigBuilder</name>
<triggers>full,incremental,</triggers>
<arguments>
</arguments>
</buildCommand>
</buildSpec>
<natures>
<nature>org.eclipse.cdt.core.cnature</nature>
<nature>org.eclipse.cdt.core.ccnature</nature>
<nature>org.eclipse.cdt.managedbuilder.core.managedBuildNature</nature>
<nature>org.eclipse.cdt.managedbuilder.core.ScannerConfigNature</nature>
</natures>
</projectDescription>

View File

@ -0,0 +1,15 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<project>
<configuration id="cdt.managedbuild.toolchain.gnu.mingw.base.1119687795" name="Default">
<extension point="org.eclipse.cdt.core.LanguageSettingsProvider">
<provider copy-of="extension" id="org.eclipse.cdt.ui.UserLanguageSettingsProvider"/>
<provider-reference id="org.eclipse.cdt.core.ReferencedProjectsLanguageSettingsProvider" ref="shared-provider"/>
<provider class="org.eclipse.cdt.managedbuilder.language.settings.providers.GCCBuildCommandParser" id="org.eclipse.cdt.managedbuilder.core.GCCBuildCommandParser" keep-relative-paths="false" name="CDT GCC Build Output Parser" parameter="(g?cc)|([gc]\+\+)|(clang)" prefer-non-shared="true"/>
<provider class="org.eclipse.cdt.managedbuilder.internal.language.settings.providers.GCCBuiltinSpecsDetectorMinGW" console="false" env-hash="-797032510223863550" id="org.eclipse.cdt.managedbuilder.core.GCCBuiltinSpecsDetectorMinGW" keep-relative-paths="false" name="CDT GCC Built-in Compiler Settings MinGW" parameter="${COMMAND} ${FLAGS} -E -P -v -dD &quot;${INPUTS}&quot;" prefer-non-shared="true">
<language-scope id="org.eclipse.cdt.core.gcc"/>
<language-scope id="org.eclipse.cdt.core.g++"/>
</provider>
<provider-reference id="org.eclipse.cdt.managedbuilder.core.MBSLanguageSettingsProvider" ref="shared-provider"/>
</extension>
</configuration>
</project>

BIN
ContainerWidget.dat Normal file

Binary file not shown.

BIN
MainWindow.dat Normal file

Binary file not shown.

File diff suppressed because it is too large Load Diff

View File

@ -1,202 +1,198 @@
#ifndef DockAreaWidgetH
#define DockAreaWidgetH
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file DockAreaWidget.h
/// \author Uwe Kindler
/// \date 24.02.2017
/// \brief Declaration of CDockAreaWidget class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include <QFrame>
namespace ads
{
struct DockAreaWidgetPrivate;
class CDockManager;
class CDockContainerWidget;
class CDockWidget;
/**
* DockAreaWidget manages multiple instances of DckWidgets.
* It displays a title tab, which is clickable and will switch to
* the contents associated to the title when clicked.
*/
class CDockAreaWidget : public QFrame
{
Q_OBJECT
private:
DockAreaWidgetPrivate* d; ///< private data (pimpl)
friend class DockAreaWidgetPrivate;
private slots:
void onDockWidgetTitleClicked();
void onTabsMenuActionTriggered(QAction* Action);
void onCloseButtonClicked();
protected:
virtual void hideEvent(QHideEvent *) override;
virtual void showEvent(QShowEvent *) override;
public:
/**
* Default Constructor
*/
CDockAreaWidget(CDockManager* DockManager, CDockContainerWidget* parent);
/**
* Virtual Destructor
*/
virtual ~CDockAreaWidget();
/**
* Returns the dock manager object this dock area belongs to
*/
CDockManager* dockManager() const;
/**
* Returns the dock container widget this dock area widget belongs to or 0
* if there is no
*/
CDockContainerWidget* dockContainer() const;
/**
* Inserts a dock widget into dock area.
* All dockwidgets in the dock area tabified in a stacked layout with tabs.
* The index indicates the index of the new dockwidget in the tabbar and
* in the stacked layout. If the Activate parameter is true, the new
* DockWidget will be the active one in the stacked layout
*/
void insertDockWidget(int index, CDockWidget* DockWidget, bool Activate = true);
/**
* Add a new dock widget to dock area.
* All dockwidgets in the dock area tabified in a stacked layout with tabs
*/
void addDockWidget(CDockWidget* DockWidget);
/**
* Removes the given dock widget from the dock area
*/
void removeDockWidget(CDockWidget* DockWidget);
/**
* Returns the rectangle of the title area
*/
QRect titleAreaGeometry() const;
/**
* Returns the rectangle of the content
*/
QRect contentAreaGeometry() const;
/**
* Returns the tab index of the given DockWidget
*/
int tabIndex(CDockWidget* DockWidget);
/**
* Returns the index of contents of the title widget that is located at
* mouse position pos
*/
int indexOfContentByTitlePos(const QPoint& pos, QWidget* exclude = nullptr) const;
/**
* Returns a list of all dock widgets in this dock area.
* This list contains open and closed dock widgets.
*/
QList<CDockWidget*> dockWidgets() const;
/**
* Returns a list of dock widgets that are not closed
*/
QList<CDockWidget*> openDockWidgets() const;
/**
* Returns the number of dock widgets in this area
*/
int count() const;
/**
* Returns a dock widget by its index
*/
CDockWidget* dockWidget(int Index) const;
/**
* Reorder the index position of DockWidget at fromIndx to toIndex.
*/
void reorderDockWidget(int fromIndex, int toIndex);
/**
* Returns the index of the current active dock widget
*/
int currentIndex() const;
/**
* Returns the current active dock widget
*/
CDockWidget* currentDockWidget() const;
/**
* Shows the tab with tghe given dock widget
*/
void setCurrentDockWidget(CDockWidget* DockWidget);
public slots:
/**
* This sets the index position of the current tab page.
*/
void setCurrentIndex(int index);
/**
* Updates the dock area layout and components visibility
*/
void updateDockArea();
signals:
/**
* This signal is emitted when user clicks on a tab at an index.
*/
void tabBarClicked(int index);
/**
* This signal is emitted when the tab bar's current tab changes. The new
* current has the given index, or -1 if there isn't a new one
* @param index
*/
void currentChanged(int index);
/**
* This signal is emitted if a dock areas visibility changed.
* The visibility changes, if the last dock widget in a dock area is closed
* or if one dock widget in a dock area with only closed dock widgets
* becomes visible
*/
void visibilityChanged(bool Visible);
}; // class DockAreaWidget
}
// namespace ads
//-----------------------------------------------------------------------------
#endif // DockAreaWidgetH
#ifndef DockAreaWidgetH
#define DockAreaWidgetH
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file DockAreaWidget.h
/// \author Uwe Kindler
/// \date 24.02.2017
/// \brief Declaration of CDockAreaWidget class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include <QFrame>
namespace ads
{
struct DockAreaWidgetPrivate;
class CDockManager;
class CDockContainerWidget;
class CDockWidget;
/**
* DockAreaWidget manages multiple instances of DckWidgets.
* It displays a title tab, which is clickable and will switch to
* the contents associated to the title when clicked.
*/
class CDockAreaWidget : public QFrame
{
Q_OBJECT
private:
DockAreaWidgetPrivate* d; ///< private data (pimpl)
friend class DockAreaWidgetPrivate;
private slots:
void onDockWidgetTitleClicked();
void onTabsMenuActionTriggered(QAction* Action);
void onCloseButtonClicked();
void onDockWidgetViewToggled(bool Open);
public:
/**
* Default Constructor
*/
CDockAreaWidget(CDockManager* DockManager, CDockContainerWidget* parent);
/**
* Virtual Destructor
*/
virtual ~CDockAreaWidget();
/**
* Returns the dock manager object this dock area belongs to
*/
CDockManager* dockManager() const;
/**
* Returns the dock container widget this dock area widget belongs to or 0
* if there is no
*/
CDockContainerWidget* dockContainer() const;
/**
* Inserts a dock widget into dock area.
* All dockwidgets in the dock area tabified in a stacked layout with tabs.
* The index indicates the index of the new dockwidget in the tabbar and
* in the stacked layout. If the Activate parameter is true, the new
* DockWidget will be the active one in the stacked layout
*/
void insertDockWidget(int index, CDockWidget* DockWidget, bool Activate = true);
/**
* Add a new dock widget to dock area.
* All dockwidgets in the dock area tabified in a stacked layout with tabs
*/
void addDockWidget(CDockWidget* DockWidget);
/**
* Removes the given dock widget from the dock area
*/
void removeDockWidget(CDockWidget* DockWidget);
/**
* Returns the rectangle of the title area
*/
QRect titleAreaGeometry() const;
/**
* Returns the rectangle of the content
*/
QRect contentAreaGeometry() const;
/**
* Returns the tab index of the given DockWidget
*/
int tabIndex(CDockWidget* DockWidget);
/**
* Returns the index of contents of the title widget that is located at
* mouse position pos
*/
int indexOfContentByTitlePos(const QPoint& pos, QWidget* exclude = nullptr) const;
/**
* Returns a list of all dock widgets in this dock area.
* This list contains open and closed dock widgets.
*/
QList<CDockWidget*> dockWidgets() const;
/**
* Returns a list of dock widgets that are not closed
*/
QList<CDockWidget*> openedDockWidgets() const;
/**
* Returns the number of dock widgets in this area
*/
int count() const;
/**
* Returns a dock widget by its index
*/
CDockWidget* dockWidget(int Index) const;
/**
* Reorder the index position of DockWidget at fromIndx to toIndex.
*/
void reorderDockWidget(int fromIndex, int toIndex);
/**
* Returns the index of the current active dock widget
*/
int currentIndex() const;
/**
* Returns the current active dock widget
*/
CDockWidget* currentDockWidget() const;
/**
* Shows the tab with tghe given dock widget
*/
void setCurrentDockWidget(CDockWidget* DockWidget);
public slots:
/**
* This sets the index position of the current tab page.
*/
void setCurrentIndex(int index);
/**
* Updates the dock area layout and components visibility
*/
void updateDockArea();
signals:
/**
* This signal is emitted when user clicks on a tab at an index.
*/
void tabBarClicked(int index);
/**
* This signal is emitted when the tab bar's current tab changes. The new
* current has the given index, or -1 if there isn't a new one
* @param index
*/
void currentChanged(int index);
/**
* This signal is emitted if the dock area is closed or opened.
* The dock area will be closed, if all dock widgets in the dock area are
* closed and will be opened, when the first dock widget is opened
*/
void viewToggled(bool Open);
}; // class DockAreaWidget
}
// namespace ads
//-----------------------------------------------------------------------------
#endif // DockAreaWidgetH

File diff suppressed because it is too large Load Diff

View File

@ -1,146 +1,152 @@
#ifndef DockContainerWidgetH
#define DockContainerWidgetH
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file DockContainerWidget.h
/// \author Uwe Kindler
/// \date 24.02.2017
/// \brief Declaration of CDockContainerWidget class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include <QFrame>
#include "ads_globals.h"
namespace ads
{
struct DockContainerWidgetPrivate;
class CDockAreaWidget;
class CDockWidget;
class CDockManager;
class CFloatingDockContainer;
/**
* Container that manages a number of dock areas with single dock widgets
* or tabyfied dock widgets in each area
*/
class CDockContainerWidget : public QFrame
{
Q_OBJECT
private:
DockContainerWidgetPrivate* d; ///< private data (pimpl)
friend class DockContainerWidgetPrivate;
protected:
/**
* Handles activation events to update zOrderIndex
*/
virtual bool event(QEvent *e) override;
public:
/**
* Default Constructor
*/
CDockContainerWidget(CDockManager* DockManager, QWidget* parent = 0);
/**
* Virtual Destructor
*/
virtual ~CDockContainerWidget();
/**
* Drop floating widget into the container
*/
void dropFloatingWidget(CFloatingDockContainer* FloatingWidget, const QPoint& TargetPos);
/**
* Adds dockwidget into the given area.
* If DockAreaWidget is not null, then the area parameter indicates the area
* into the DockAreaWidget. If DockAreaWidget is null, the Dockwidget will
* be dropped into the container.
* \return Returns the dock area widget that contains the new DockWidget
*/
CDockAreaWidget* addDockWidget(DockWidgetArea area, CDockWidget* Dockwidget,
CDockAreaWidget* DockAreaWidget = nullptr);
/**
* Adds the given dock area to this container widget
*/
void addDockArea(CDockAreaWidget* DockAreaWidget, DockWidgetArea area = CenterDockWidgetArea);
/**
* Removes the given dock area from this container
*/
void removeDockArea(CDockAreaWidget* area);
/**
* Returns the current zOrderIndex
*/
virtual unsigned int zOrderIndex() const;
/**
* This function returns true if this container widgets z order index is
* higher than the index of the container widget given in Other parameter
*/
bool isInFrontOf(CDockContainerWidget* Other) const;
/**
* Returns the dock area at teh given global position or 0 if there is no
* dock area at this position
*/
CDockAreaWidget* dockAreaAt(const QPoint& GlobalPos) const;
/**
* Returns the dock area at the given Index or 0 if the index is out of
* range
*/
CDockAreaWidget* dockArea(int Index) const;
/**
* Returns the number of dock areas in this container
*/
int dockAreaCount() const;
/**
* This function returns true, if this container is in a floating widget
*/
bool isFloating() const;
signals:
/**
* This signal is emitted if one or multiple dock areas has been added to
* the internal list of dock areas.
* If multiple dock areas are inserted, this signal is emitted only once
*/
void dockAreasAdded();
/**
* This signal is emitted if one or multiple dock areas has been removed
*/
void dockAreasRemoved();
}; // class DockContainerWidget
} // namespace ads
//-----------------------------------------------------------------------------
#endif // DockContainerWidgetH
#ifndef DockContainerWidgetH
#define DockContainerWidgetH
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file DockContainerWidget.h
/// \author Uwe Kindler
/// \date 24.02.2017
/// \brief Declaration of CDockContainerWidget class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include <QFrame>
#include "ads_globals.h"
namespace ads
{
struct DockContainerWidgetPrivate;
class CDockAreaWidget;
class CDockWidget;
class CDockManager;
class CFloatingDockContainer;
/**
* Container that manages a number of dock areas with single dock widgets
* or tabyfied dock widgets in each area
*/
class CDockContainerWidget : public QFrame
{
Q_OBJECT
private:
DockContainerWidgetPrivate* d; ///< private data (pimpl)
friend class DockContainerWidgetPrivate;
protected:
/**
* Handles activation events to update zOrderIndex
*/
virtual bool event(QEvent *e) override;
public:
/**
* Default Constructor
*/
CDockContainerWidget(CDockManager* DockManager, QWidget* parent = 0);
/**
* Virtual Destructor
*/
virtual ~CDockContainerWidget();
/**
* Drop floating widget into the container
*/
void dropFloatingWidget(CFloatingDockContainer* FloatingWidget, const QPoint& TargetPos);
/**
* Adds dockwidget into the given area.
* If DockAreaWidget is not null, then the area parameter indicates the area
* into the DockAreaWidget. If DockAreaWidget is null, the Dockwidget will
* be dropped into the container.
* \return Returns the dock area widget that contains the new DockWidget
*/
CDockAreaWidget* addDockWidget(DockWidgetArea area, CDockWidget* Dockwidget,
CDockAreaWidget* DockAreaWidget = nullptr);
/**
* Adds the given dock area to this container widget
*/
void addDockArea(CDockAreaWidget* DockAreaWidget, DockWidgetArea area = CenterDockWidgetArea);
/**
* Removes the given dock area from this container
*/
void removeDockArea(CDockAreaWidget* area);
/**
* Returns the current zOrderIndex
*/
virtual unsigned int zOrderIndex() const;
/**
* This function returns true if this container widgets z order index is
* higher than the index of the container widget given in Other parameter
*/
bool isInFrontOf(CDockContainerWidget* Other) const;
/**
* Returns the dock area at teh given global position or 0 if there is no
* dock area at this position
*/
CDockAreaWidget* dockAreaAt(const QPoint& GlobalPos) const;
/**
* Returns the dock area at the given Index or 0 if the index is out of
* range
*/
CDockAreaWidget* dockArea(int Index) const;
/**
* Returns the list of dock areas that are not closed
* If all dock widgets in a dock area are closed, the dock area will be closed
*/
QList<CDockAreaWidget*> openedDockAreas() const;
/**
* Returns the number of dock areas in this container
*/
int dockAreaCount() const;
/**
* This function returns true, if this container is in a floating widget
*/
bool isFloating() const;
signals:
/**
* This signal is emitted if one or multiple dock areas has been added to
* the internal list of dock areas.
* If multiple dock areas are inserted, this signal is emitted only once
*/
void dockAreasAdded();
/**
* This signal is emitted if one or multiple dock areas has been removed
*/
void dockAreasRemoved();
}; // class DockContainerWidget
} // namespace ads
//-----------------------------------------------------------------------------
#endif // DockContainerWidgetH

View File

@ -1,358 +1,404 @@
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file DockWidget.cpp
/// \author Uwe Kindler
/// \date 26.02.2017
/// \brief Implementation of CDockWidget class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include "DockWidget.h"
#include <QBoxLayout>
#include <QAction>
#include <QSplitter>
#include <QStack>
#include <QTextStream>
#include <QPointer>
#include <iostream>
#include "DockWidgetTitleBar.h"
#include "DockContainerWidget.h"
#include "DockAreaWidget.h"
#include "DockManager.h"
#include "FloatingDockContainer.h"
#include "ads_globals.h"
namespace ads
{
/**
* Private data class of CDockWidget class (pimpl)
*/
struct DockWidgetPrivate
{
CDockWidget* _this;
QBoxLayout* Layout;
QWidget* Widget = nullptr;
CDockWidgetTitleBar* TitleWidget;
CDockWidget::DockWidgetFeatures Features = CDockWidget::AllDockWidgetFeatures;
CDockManager* DockManager = nullptr;
CDockAreaWidget* DockArea = nullptr;
QAction* ToggleViewAction;
bool Closed = false;
struct CapturedState
{
QString DockTreePosition;
QRect GlobalGeometry;
QPointer<CDockContainerWidget> DockContainer;
} CapturedState;
/**
* Private data constructor
*/
DockWidgetPrivate(CDockWidget* _public);
/**
* Saves the current state into CapturedState variable
*/
void capturedState();
/**
* Show dock widget
*/
void showDockWidget();
/**
* Hides a parent splitter if all dock widgets in the splitter are closed
*/
void hideEmptyParentSplitter();
/**
* Hides a dock area if all dock widgets in the area are closed
*/
void hideEmptyParentDockArea();
};
// struct DockWidgetPrivate
//============================================================================
DockWidgetPrivate::DockWidgetPrivate(CDockWidget* _public) :
_this(_public)
{
}
//============================================================================
void DockWidgetPrivate::capturedState()
{
QString DockTreePosition;
QTextStream stream(&DockTreePosition);
QPoint GlobalTopLeft = _this->mapToGlobal(_this->geometry().topLeft());
QRect Rect(GlobalTopLeft, _this->geometry().size());
CapturedState.GlobalGeometry = Rect;
CapturedState.DockContainer = _this->dockContainer();
QWidget* Widget = DockArea;
QSplitter* splitter = internal::findParent<QSplitter*>(Widget);
QStack<QString> SplitterData;
while (splitter)
{
SplitterData.push(QString("%1%2")
.arg((splitter->orientation() == Qt::Horizontal) ? "H" : "V")
.arg(splitter->indexOf(Widget)));
Widget = splitter;
splitter = internal::findParent<QSplitter*>(Widget);
}
QString Separator;
while (!SplitterData.isEmpty())
{
stream << Separator << SplitterData.pop();
Separator = " ";
}
this->CapturedState.DockTreePosition = DockTreePosition;
std::cout << "SerializedPosition: " << DockTreePosition.toStdString() << std::endl;
}
//============================================================================
void DockWidgetPrivate::showDockWidget()
{
DockArea->show();
DockArea->setCurrentIndex(DockArea->tabIndex(_this));
QSplitter* Splitter = internal::findParent<QSplitter*>(_this);
if (Splitter)
{
Splitter->show();
}
}
//============================================================================
void DockWidgetPrivate::hideEmptyParentSplitter()
{
QSplitter* Splitter = internal::findParent<QSplitter*>(_this);
if (!Splitter)
{
return;
}
for (int i = 0; i < Splitter->count(); ++i)
{
if (Splitter->widget(i)->isVisible())
{
return;
}
}
Splitter->hide();
}
//============================================================================
void DockWidgetPrivate::hideEmptyParentDockArea()
{
auto OpenDockWidgets = DockArea->openDockWidgets();
if (OpenDockWidgets.count() > 1)
{
CDockWidget* NextDockWidget;
if (OpenDockWidgets.last() == _this)
{
NextDockWidget = OpenDockWidgets[OpenDockWidgets.count() - 2];
}
else
{
int NextIndex = OpenDockWidgets.indexOf(_this) + 1;
NextDockWidget = OpenDockWidgets[NextIndex];
}
DockArea->setCurrentDockWidget(NextDockWidget);
}
else
{
DockArea->hide();
}
}
//============================================================================
CDockWidget::CDockWidget(const QString &title, QWidget *parent) :
QFrame(parent),
d(new DockWidgetPrivate(this))
{
d->Layout = new QBoxLayout(QBoxLayout::TopToBottom);
d->Layout->setContentsMargins(0, 0, 0, 0);
d->Layout->setSpacing(0);
setLayout(d->Layout);
setWindowTitle(title);
d->TitleWidget = new CDockWidgetTitleBar(this);
d->ToggleViewAction = new QAction(title);
d->ToggleViewAction->setCheckable(true);
connect(d->ToggleViewAction, SIGNAL(triggered(bool)), this,
SLOT(toggleView(bool)));
}
//============================================================================
CDockWidget::~CDockWidget()
{
std::cout << "~CDockWidget()" << std::endl;
delete d;
}
//============================================================================
void CDockWidget::setWidget(QWidget* widget)
{
if (d->Widget)
{
d->Layout->replaceWidget(d->Widget, widget);
}
else
{
d->Layout->addWidget(widget);
}
d->Widget = widget;
}
//============================================================================
QWidget* CDockWidget::widget() const
{
return d->Widget;
}
//============================================================================
CDockWidgetTitleBar* CDockWidget::titleBar() const
{
return d->TitleWidget;
}
//============================================================================
void CDockWidget::setFeatures(DockWidgetFeatures features)
{
d->Features = features;
}
//============================================================================
CDockWidget::DockWidgetFeatures CDockWidget::features() const
{
return d->Features;
}
//============================================================================
CDockManager* CDockWidget::dockManager() const
{
return d->DockManager;
}
//============================================================================
void CDockWidget::setDockManager(CDockManager* DockManager)
{
d->DockManager = DockManager;
}
//============================================================================
CDockContainerWidget* CDockWidget::dockContainer() const
{
return internal::findParent<CDockContainerWidget*>(this);
}
//============================================================================
CDockAreaWidget* CDockWidget::dockAreaWidget() const
{
return internal::findParent<CDockAreaWidget*>(this);
}
//============================================================================
bool CDockWidget::isFloating() const
{
return dockContainer() ? dockContainer()->isFloating() : false;
}
//============================================================================
bool CDockWidget::isClosed() const
{
return d->Closed;
}
//============================================================================
QAction* CDockWidget::toggleViewAction() const
{
return d->ToggleViewAction;
}
//============================================================================
void CDockWidget::toggleView(bool Open)
{
if (Open)
{
d->showDockWidget();
}
else
{
hideDockWidget();
}
d->Closed = !Open;
}
//============================================================================
void CDockWidget::setDockArea(CDockAreaWidget* DockArea)
{
d->DockArea = DockArea;
d->ToggleViewAction->setChecked(DockArea != nullptr);
}
//============================================================================
void CDockWidget::hideDockWidget()
{
CDockAreaWidget* DockArea = d->DockArea;
d->ToggleViewAction->setChecked(false);
d->TitleWidget->hide();
d->hideEmptyParentDockArea();
d->hideEmptyParentSplitter();
}
} // namespace ads
//---------------------------------------------------------------------------
// EOF DockWidget.cpp
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file DockWidget.cpp
/// \author Uwe Kindler
/// \date 26.02.2017
/// \brief Implementation of CDockWidget class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include "DockWidget.h"
#include <QBoxLayout>
#include <QAction>
#include <QSplitter>
#include <QStack>
#include <QTextStream>
#include <QPointer>
#include <iostream>
#include "DockWidgetTitleBar.h"
#include "DockContainerWidget.h"
#include "DockAreaWidget.h"
#include "DockManager.h"
#include "FloatingDockContainer.h"
#include "ads_globals.h"
namespace ads
{
/**
* Private data class of CDockWidget class (pimpl)
*/
struct DockWidgetPrivate
{
CDockWidget* _this;
QBoxLayout* Layout;
QWidget* Widget = nullptr;
CDockWidgetTitleBar* TitleWidget;
CDockWidget::DockWidgetFeatures Features = CDockWidget::AllDockWidgetFeatures;
CDockManager* DockManager = nullptr;
CDockAreaWidget* DockArea = nullptr;
QAction* ToggleViewAction;
bool Closed = false;
struct CapturedState
{
QString DockTreePosition;
QRect GlobalGeometry;
QPointer<CDockContainerWidget> DockContainer;
} CapturedState;
/**
* Private data constructor
*/
DockWidgetPrivate(CDockWidget* _public);
/**
* Saves the current state into CapturedState variable
*/
void capturedState();
/**
* Show dock widget
*/
void showDockWidget();
/**
* Hide dock widget.
*/
void hideDockWidget();
/**
* Hides a parent splitter if all dock widgets in the splitter are closed
*/
void hideEmptyParentSplitter();
/**
* Hides a dock area if all dock widgets in the area are closed
*/
void hideEmptyParentDockArea();
/**
* Hides a floating widget if all dock areas are empty - that means,
* if all dock widgets in all dock areas are closed
*/
void hideEmptyFloatingWidget();
};
// struct DockWidgetPrivate
//============================================================================
DockWidgetPrivate::DockWidgetPrivate(CDockWidget* _public) :
_this(_public)
{
}
//============================================================================
void DockWidgetPrivate::capturedState()
{
QString DockTreePosition;
QTextStream stream(&DockTreePosition);
QPoint GlobalTopLeft = _this->mapToGlobal(_this->geometry().topLeft());
QRect Rect(GlobalTopLeft, _this->geometry().size());
CapturedState.GlobalGeometry = Rect;
CapturedState.DockContainer = _this->dockContainer();
QWidget* Widget = DockArea;
QSplitter* splitter = internal::findParent<QSplitter*>(Widget);
QStack<QString> SplitterData;
while (splitter)
{
SplitterData.push(QString("%1%2")
.arg((splitter->orientation() == Qt::Horizontal) ? "H" : "V")
.arg(splitter->indexOf(Widget)));
Widget = splitter;
splitter = internal::findParent<QSplitter*>(Widget);
}
QString Separator;
while (!SplitterData.isEmpty())
{
stream << Separator << SplitterData.pop();
Separator = " ";
}
this->CapturedState.DockTreePosition = DockTreePosition;
std::cout << "SerializedPosition: " << DockTreePosition.toStdString() << std::endl;
}
//============================================================================
void DockWidgetPrivate::showDockWidget()
{
DockArea->show();
DockArea->setCurrentIndex(DockArea->tabIndex(_this));
QSplitter* Splitter = internal::findParent<QSplitter*>(_this);
if (Splitter)
{
Splitter->show();
}
CDockContainerWidget* Container = DockArea->dockContainer();
if (Container->isFloating())
{
CFloatingDockContainer* FloatingWidget = internal::findParent<
CFloatingDockContainer*>(Container);
FloatingWidget->show();
}
}
//============================================================================
void DockWidgetPrivate::hideDockWidget()
{
ToggleViewAction->setChecked(false);
TitleWidget->hide();
hideEmptyParentDockArea();
hideEmptyParentSplitter();
hideEmptyFloatingWidget();
}
//============================================================================
void DockWidgetPrivate::hideEmptyParentSplitter()
{
QSplitter* Splitter = internal::findParent<QSplitter*>(_this);
if (!Splitter)
{
return;
}
for (int i = 0; i < Splitter->count(); ++i)
{
if (Splitter->widget(i)->isVisible())
{
return;
}
}
Splitter->hide();
}
//============================================================================
void DockWidgetPrivate::hideEmptyParentDockArea()
{
auto OpenDockWidgets = DockArea->openedDockWidgets();
if (OpenDockWidgets.count() > 1)
{
CDockWidget* NextDockWidget;
if (OpenDockWidgets.last() == _this)
{
NextDockWidget = OpenDockWidgets[OpenDockWidgets.count() - 2];
}
else
{
int NextIndex = OpenDockWidgets.indexOf(_this) + 1;
NextDockWidget = OpenDockWidgets[NextIndex];
}
DockArea->setCurrentDockWidget(NextDockWidget);
}
else
{
DockArea->hide();
}
}
//============================================================================
void DockWidgetPrivate::hideEmptyFloatingWidget()
{
CDockContainerWidget* Container = _this->dockContainer();
if (Container->isFloating() && Container->openedDockAreas().isEmpty())
{
CFloatingDockContainer* FloatingWidget = internal::findParent<CFloatingDockContainer*>(Container);
FloatingWidget->hide();
}
}
//============================================================================
CDockWidget::CDockWidget(const QString &title, QWidget *parent) :
QFrame(parent),
d(new DockWidgetPrivate(this))
{
d->Layout = new QBoxLayout(QBoxLayout::TopToBottom);
d->Layout->setContentsMargins(0, 0, 0, 0);
d->Layout->setSpacing(0);
setLayout(d->Layout);
setWindowTitle(title);
d->TitleWidget = new CDockWidgetTitleBar(this);
d->ToggleViewAction = new QAction(title);
d->ToggleViewAction->setCheckable(true);
connect(d->ToggleViewAction, SIGNAL(triggered(bool)), this,
SLOT(toggleView(bool)));
}
//============================================================================
CDockWidget::~CDockWidget()
{
std::cout << "~CDockWidget()" << std::endl;
delete d;
}
//============================================================================
void CDockWidget::setToggleViewActionChecked(bool Checked)
{
QAction* Action = d->ToggleViewAction;
Action->blockSignals(true);
Action->setChecked(Checked);
Action->blockSignals(false);
}
//============================================================================
void CDockWidget::setWidget(QWidget* widget)
{
if (d->Widget)
{
d->Layout->replaceWidget(d->Widget, widget);
}
else
{
d->Layout->addWidget(widget);
}
d->Widget = widget;
}
//============================================================================
QWidget* CDockWidget::widget() const
{
return d->Widget;
}
//============================================================================
CDockWidgetTitleBar* CDockWidget::titleBar() const
{
return d->TitleWidget;
}
//============================================================================
void CDockWidget::setFeatures(DockWidgetFeatures features)
{
d->Features = features;
}
//============================================================================
CDockWidget::DockWidgetFeatures CDockWidget::features() const
{
return d->Features;
}
//============================================================================
CDockManager* CDockWidget::dockManager() const
{
return d->DockManager;
}
//============================================================================
void CDockWidget::setDockManager(CDockManager* DockManager)
{
d->DockManager = DockManager;
}
//============================================================================
CDockContainerWidget* CDockWidget::dockContainer() const
{
return internal::findParent<CDockContainerWidget*>(this);
}
//============================================================================
CDockAreaWidget* CDockWidget::dockAreaWidget() const
{
return internal::findParent<CDockAreaWidget*>(this);
}
//============================================================================
bool CDockWidget::isFloating() const
{
return dockContainer() ? dockContainer()->isFloating() : false;
}
//============================================================================
bool CDockWidget::isClosed() const
{
return d->Closed;
}
//============================================================================
QAction* CDockWidget::toggleViewAction() const
{
return d->ToggleViewAction;
}
//============================================================================
void CDockWidget::toggleView(bool Open)
{
if (Open)
{
d->showDockWidget();
}
else
{
d->hideDockWidget();
}
d->Closed = !Open;
if (!Open)
{
emit closed();
}
emit viewToggled(Open);
}
//============================================================================
void CDockWidget::setDockArea(CDockAreaWidget* DockArea)
{
d->DockArea = DockArea;
d->ToggleViewAction->setChecked(DockArea != nullptr);
}
} // namespace ads
//---------------------------------------------------------------------------
// EOF DockWidget.cpp

View File

@ -1,180 +1,192 @@
#ifndef DockWidgetH
#define DockWidgetH
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file DockWidget.h
/// \author Uwe Kindler
/// \date 26.02.2017
/// \brief Declaration of CDockWidget class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include <QFrame>
namespace ads
{
struct DockWidgetPrivate;
class CDockWidgetTitleBar;
class CDockManager;
class CDockContainerWidget;
class CDockAreaWidget;
/**
* The QDockWidget class provides a widget that can be docked inside a
* CDockManager or floated as a top-level window on the desktop.
*/
class CDockWidget : public QFrame
{
Q_OBJECT
private:
DockWidgetPrivate* d; ///< private data (pimpl)
friend class DockWidgetPrivate;
protected:
friend class CDockContainerWidget;
friend class CDockAreaWidget;
friend class CFloatingDockContainer;
/**
* Assigns the dock manager that manages this dock widget
*/
void setDockManager(CDockManager* DockManager);
/**
* If this dock widget is inserted into a dock area, the dock area will
* be registered on this widget via this function. If a dock widget is
* removed from a dock area, this function will be called with nullptr
* value.
*/
void setDockArea(CDockAreaWidget* DockArea);
/**
* Hide dock widget.
*/
void hideDockWidget();
public:
enum DockWidgetFeature
{
DockWidgetClosable = 0x01,
DockWidgetMovable = 0x02,
DockWidgetFloatable = 0x04,
AllDockWidgetFeatures = DockWidgetClosable | DockWidgetMovable | DockWidgetFloatable,
NoDockWidgetFeatures = 0x00
};
Q_DECLARE_FLAGS(DockWidgetFeatures, DockWidgetFeature)
enum eState
{
StateHidden,
StateDocked,
StateFloating
};
/**
* Default Constructor
*/
CDockWidget(const QString &title, QWidget* parent = 0);
/**
* Virtual Destructor
*/
virtual ~CDockWidget();
/**
* Sets the widget for the dock widget to widget.
*/
void setWidget(QWidget* widget);
/**
* Returns the widget for the dock widget. This function returns zero if
* the widget has not been set.
*/
QWidget* widget() const;
/**
* Returns the title bar widget of this dock widget
*/
CDockWidgetTitleBar* titleBar() const;
/**
* Sets, whether the dock widget is movable, closable, and floatable.
*/
void setFeatures(DockWidgetFeatures features);
/**
* This property holds whether the dock widget is movable, closable, and
* floatable.
* By default, this property is set to a combination of DockWidgetClosable,
* DockWidgetMovable and DockWidgetFloatable.
*/
DockWidgetFeatures features() const;
/**
* Returns the dock manager that manages the dock widget or 0 if the widget
* has not been assigned to any dock manager yet
*/
CDockManager* dockManager() const;
/**
* Returns the dock container widget this dock area widget belongs to or 0
* if this dock widget has nt been docked yet
*/
CDockContainerWidget* dockContainer() const;
/**
* Returns the dock area widget this dock widget belongs to or 0
* if this dock widget has not been docked yet
*/
CDockAreaWidget* dockAreaWidget() const;
/**
* This property holds whether the dock widget is floating.
*/
bool isFloating() const;
/**
* Returns true, if this dock widget is closed.
*/
bool isClosed() const;
/**
* Returns a checkable action that can be used to show or close this dock widget.
* The action's text is set to the dock widget's window title.
*/
QAction* toggleViewAction() const;
public slots:
/**
* This property controls whether the dock widget is open or closed.
* The toogleViewAction triggers this slot
*/
void toggleView(bool Open);
}; // class DockWidget
}
// namespace ads
//-----------------------------------------------------------------------------
#endif // DockWidgetH
#ifndef DockWidgetH
#define DockWidgetH
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file DockWidget.h
/// \author Uwe Kindler
/// \date 26.02.2017
/// \brief Declaration of CDockWidget class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include <QFrame>
namespace ads
{
struct DockWidgetPrivate;
class CDockWidgetTitleBar;
class CDockManager;
class CDockContainerWidget;
class CDockAreaWidget;
/**
* The QDockWidget class provides a widget that can be docked inside a
* CDockManager or floated as a top-level window on the desktop.
*/
class CDockWidget : public QFrame
{
Q_OBJECT
private:
DockWidgetPrivate* d; ///< private data (pimpl)
friend class DockWidgetPrivate;
protected:
friend class CDockContainerWidget;
friend class CDockAreaWidget;
friend class CFloatingDockContainer;
/**
* Assigns the dock manager that manages this dock widget
*/
void setDockManager(CDockManager* DockManager);
/**
* If this dock widget is inserted into a dock area, the dock area will
* be registered on this widget via this function. If a dock widget is
* removed from a dock area, this function will be called with nullptr
* value.
*/
void setDockArea(CDockAreaWidget* DockArea);
/**
* This function changes the toggle view action without emitting any
* signal
*/
void setToggleViewActionChecked(bool Checked);
public:
enum DockWidgetFeature
{
DockWidgetClosable = 0x01,
DockWidgetMovable = 0x02,
DockWidgetFloatable = 0x04,
AllDockWidgetFeatures = DockWidgetClosable | DockWidgetMovable | DockWidgetFloatable,
NoDockWidgetFeatures = 0x00
};
Q_DECLARE_FLAGS(DockWidgetFeatures, DockWidgetFeature)
enum eState
{
StateHidden,
StateDocked,
StateFloating
};
/**
* Default Constructor
*/
CDockWidget(const QString &title, QWidget* parent = 0);
/**
* Virtual Destructor
*/
virtual ~CDockWidget();
/**
* Sets the widget for the dock widget to widget.
*/
void setWidget(QWidget* widget);
/**
* Returns the widget for the dock widget. This function returns zero if
* the widget has not been set.
*/
QWidget* widget() const;
/**
* Returns the title bar widget of this dock widget
*/
CDockWidgetTitleBar* titleBar() const;
/**
* Sets, whether the dock widget is movable, closable, and floatable.
*/
void setFeatures(DockWidgetFeatures features);
/**
* This property holds whether the dock widget is movable, closable, and
* floatable.
* By default, this property is set to a combination of DockWidgetClosable,
* DockWidgetMovable and DockWidgetFloatable.
*/
DockWidgetFeatures features() const;
/**
* Returns the dock manager that manages the dock widget or 0 if the widget
* has not been assigned to any dock manager yet
*/
CDockManager* dockManager() const;
/**
* Returns the dock container widget this dock area widget belongs to or 0
* if this dock widget has nt been docked yet
*/
CDockContainerWidget* dockContainer() const;
/**
* Returns the dock area widget this dock widget belongs to or 0
* if this dock widget has not been docked yet
*/
CDockAreaWidget* dockAreaWidget() const;
/**
* This property holds whether the dock widget is floating.
*/
bool isFloating() const;
/**
* Returns true, if this dock widget is closed.
*/
bool isClosed() const;
/**
* Returns a checkable action that can be used to show or close this dock widget.
* The action's text is set to the dock widget's window title.
*/
QAction* toggleViewAction() const;
public slots:
/**
* This property controls whether the dock widget is open or closed.
* The toogleViewAction triggers this slot
*/
void toggleView(bool Open);
signals:
/**
* This signal is emitted if the dock widget is opened or closed
*/
void viewToggled(bool Open);
/**
* This signal is emitted if the dock widget is closed
*/
void closed();
}; // class DockWidget
}
// namespace ads
//-----------------------------------------------------------------------------
#endif // DockWidgetH

View File

@ -1,385 +1,397 @@
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file FloatingDockContainer.cpp
/// \author Uwe Kindler
/// \date 01.03.2017
/// \brief Implementation of CFloatingDockContainer class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include "FloatingDockContainer.h"
#include <QBoxLayout>
#include <QApplication>
#include <QMouseEvent>
#include <QPointer>
#include <iostream>
#include "DockContainerWidget.h"
#include "DockAreaWidget.h"
#include "DockManager.h"
#include "DockWidget.h"
#include "DockOverlay.h"
namespace ads
{
static unsigned int zOrderCounter = 0;
/**
* Private data class of CFloatingDockContainer class (pimpl)
*/
struct FloatingDockContainerPrivate
{
CFloatingDockContainer* _this;
CDockContainerWidget* DockContainer;
unsigned int zOrderIndex = ++zOrderCounter;
QPointer<CDockManager> DockManager;
bool DraggingActive = false;
QPoint DragStartMousePosition;
CDockContainerWidget* DropContainer = nullptr;
CDockAreaWidget* SingleDockArea = nullptr;
/**
* Private data constructor
*/
FloatingDockContainerPrivate(CFloatingDockContainer* _public);
void titleMouseReleaseEvent();
void updateDropOverlays(const QPoint& GlobalPos);
void setDraggingActive(bool Active);
};
// struct FloatingDockContainerPrivate
//============================================================================
FloatingDockContainerPrivate::FloatingDockContainerPrivate(CFloatingDockContainer* _public) :
_this(_public)
{
}
//============================================================================
void FloatingDockContainerPrivate::titleMouseReleaseEvent()
{
setDraggingActive(false);
if (!DropContainer)
{
return;
}
std::cout << "Dropped" << std::endl;
DropContainer->dropFloatingWidget(_this, QCursor::pos());
DockManager->containerOverlay()->hideOverlay();
DockManager->dockAreaOverlay()->hideOverlay();
}
//============================================================================
void FloatingDockContainerPrivate::updateDropOverlays(const QPoint& GlobalPos)
{
if (!_this->isVisible() || !DockManager)
{
return;
}
auto Containers = DockManager->dockContainers();
CDockContainerWidget* TopContainer = nullptr;
for (auto ContainerWidget : Containers)
{
if (!ContainerWidget->isVisible())
{
continue;
}
if (DockContainer == ContainerWidget)
{
continue;
}
QPoint MappedPos = ContainerWidget->mapFromGlobal(GlobalPos);
if (ContainerWidget->rect().contains(MappedPos))
{
if (!TopContainer || ContainerWidget->isInFrontOf(TopContainer))
{
TopContainer = ContainerWidget;
}
}
}
DropContainer = TopContainer;
auto ContainerOverlay = DockManager->containerOverlay();
auto DockAreaOverlay = DockManager->dockAreaOverlay();
if (!TopContainer)
{
ContainerOverlay->hideOverlay();
DockAreaOverlay->hideOverlay();
return;
}
ContainerOverlay->setAllowedAreas(TopContainer->dockAreaCount() > 1 ?
OuterDockAreas : AllDockAreas);
ContainerOverlay->showOverlay(TopContainer);
ContainerOverlay->raise();
auto DockArea = TopContainer->dockAreaAt(GlobalPos);
if (DockArea && TopContainer->dockAreaCount() > 1)
{
DockAreaOverlay->setAllowedAreas(AllDockAreas);
DockAreaOverlay->showOverlay(DockArea);
}
else
{
DockAreaOverlay->hideOverlay();
}
}
//============================================================================
void FloatingDockContainerPrivate::setDraggingActive(bool Active)
{
DraggingActive = Active;
}
//============================================================================
CFloatingDockContainer::CFloatingDockContainer(CDockManager* DockManager) :
QWidget(DockManager, Qt::Window),
d(new FloatingDockContainerPrivate(this))
{
//setAttribute(Qt::WA_DeleteOnClose);
d->DockManager = DockManager;
QBoxLayout* l = new QBoxLayout(QBoxLayout::TopToBottom);
l->setContentsMargins(0, 0, 0, 0);
l->setSpacing(0);
setLayout(l);
d->DockContainer = new CDockContainerWidget(DockManager, this);
connect(d->DockContainer, SIGNAL(dockAreasAdded()), this, SLOT(onDockAreasAddedOrRemoved()));
connect(d->DockContainer, SIGNAL(dockAreasRemoved()), this, SLOT(onDockAreasAddedOrRemoved()));
l->addWidget(d->DockContainer);
DockManager->registerFloatingWidget(this);
// We install an event filter to detect mouse release events because we
// do not receive mouse release event if the floating widget is behind
// the drop overlay cross
qApp->installEventFilter(this);
}
//============================================================================
CFloatingDockContainer::CFloatingDockContainer(CDockAreaWidget* DockArea) :
CFloatingDockContainer(DockArea->dockManager())
{
d->DockContainer->addDockArea(DockArea);
}
//============================================================================
CFloatingDockContainer::CFloatingDockContainer(CDockWidget* DockWidget) :
CFloatingDockContainer(DockWidget->dockManager())
{
d->DockContainer->addDockWidget(CenterDockWidgetArea, DockWidget);
}
//============================================================================
CFloatingDockContainer::~CFloatingDockContainer()
{
std::cout << "~CFloatingDockContainer" << std::endl;
if (d->DockManager)
{
d->DockManager->removeFloatingWidget(this);
}
delete d;
}
//============================================================================
CDockContainerWidget* CFloatingDockContainer::dockContainer() const
{
return d->DockContainer;
}
//============================================================================
void CFloatingDockContainer::changeEvent(QEvent *event)
{
QWidget::changeEvent(event);
if ((event->type() == QEvent::ActivationChange) && isActiveWindow())
{
std::cout << "FloatingWidget::changeEvent QEvent::ActivationChange " << std::endl;
d->zOrderIndex = ++zOrderCounter;
return;
}
}
//============================================================================
void CFloatingDockContainer::moveEvent(QMoveEvent *event)
{
QWidget::moveEvent(event);
if (!qApp->mouseButtons().testFlag(Qt::LeftButton))
{
if (d->DraggingActive)
{
d->setDraggingActive(false);
}
return;
}
if (d->DraggingActive)
{
d->updateDropOverlays(QCursor::pos());
}
}
//============================================================================
void CFloatingDockContainer::closeEvent(QCloseEvent *event)
{
d->setDraggingActive(false);
if (dockContainer()->dockAreaCount() > 1 || dockContainer()->dockArea(0)->count() == 1)
{
for (int i = 0; i < dockContainer()->dockAreaCount(); ++i)
{
auto DockWidgets = dockContainer()->dockArea(i)->dockWidgets();
for (auto DockWidget : DockWidgets)
{
DockWidget->hideDockWidget();
}
}
QWidget::closeEvent(event);
}
else
{
auto DockArea = dockContainer()->dockArea(0);
DockArea->currentDockWidget()->hideDockWidget();
// As long as there are open dock widgets, we do not close the floating
// window
if (DockArea->openDockWidgets().count())
{
event->ignore();
}
}
}
//============================================================================
bool CFloatingDockContainer::event(QEvent *e)
{
if ((e->type() == QEvent::NonClientAreaMouseButtonPress))
{
if (QGuiApplication::mouseButtons() == Qt::LeftButton)
{
std::cout << "FloatingWidget::event Event::NonClientAreaMouseButtonPress" << e->type() << std::endl;
d->setDraggingActive(true);
}
}
else if (e->type() == QEvent::NonClientAreaMouseButtonDblClick)
{
std::cout << "FloatingWidget::event QEvent::NonClientAreaMouseButtonDblClick" << std::endl;
d->setDraggingActive(false);
}
else if ((e->type() == QEvent::NonClientAreaMouseButtonRelease) && d->DraggingActive)
{
std::cout << "FloatingWidget::event QEvent::NonClientAreaMouseButtonRelease" << std::endl;
d->titleMouseReleaseEvent();
}
return QWidget::event(e);
}
//============================================================================
bool CFloatingDockContainer::eventFilter(QObject *watched, QEvent *event)
{
if (event->type() == QEvent::MouseButtonRelease && d->DraggingActive)
{
std::cout << "FloatingWidget::eventFilter QEvent::MouseButtonRelease" << std::endl;
d->titleMouseReleaseEvent();
}
return false;
}
//============================================================================
void CFloatingDockContainer::startFloating(const QPoint& Pos, const QSize& Size)
{
resize(Size);
d->setDraggingActive(true);
QPoint TargetPos = QCursor::pos() - Pos;
move(TargetPos);
show();
d->DragStartMousePosition = Pos;
}
//============================================================================
void CFloatingDockContainer::moveFloating()
{
int BorderSize = (frameSize().width() - size().width()) / 2;
const QPoint moveToPos = QCursor::pos() - d->DragStartMousePosition - QPoint(BorderSize, 0);
move(moveToPos);
}
//============================================================================
void CFloatingDockContainer::onDockAreasAddedOrRemoved()
{
if (d->DockContainer->dockAreaCount() == 1)
{
d->SingleDockArea = d->DockContainer->dockArea(0);
this->setWindowTitle(d->SingleDockArea->currentDockWidget()->windowTitle());
connect(d->SingleDockArea, SIGNAL(currentChanged(int)), this,
SLOT(onDockAreaCurrentChanged(int)));
}
else
{
if (d->SingleDockArea)
{
disconnect(d->SingleDockArea, SIGNAL(currentChanged(int)), this,
SLOT(onDockAreaCurrentChanged(int)));
d->SingleDockArea = nullptr;
}
this->setWindowTitle(qApp->applicationDisplayName());
}
}
//============================================================================
void CFloatingDockContainer::onDockAreaCurrentChanged(int Index)
{
this->setWindowTitle(d->SingleDockArea->currentDockWidget()->windowTitle());
}
} // namespace ads
//---------------------------------------------------------------------------
// EOF FloatingDockContainer.cpp
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file FloatingDockContainer.cpp
/// \author Uwe Kindler
/// \date 01.03.2017
/// \brief Implementation of CFloatingDockContainer class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include "FloatingDockContainer.h"
#include <QBoxLayout>
#include <QApplication>
#include <QMouseEvent>
#include <QPointer>
#include <QAction>
#include <iostream>
#include "DockContainerWidget.h"
#include "DockAreaWidget.h"
#include "DockManager.h"
#include "DockWidget.h"
#include "DockOverlay.h"
namespace ads
{
static unsigned int zOrderCounter = 0;
/**
* Private data class of CFloatingDockContainer class (pimpl)
*/
struct FloatingDockContainerPrivate
{
CFloatingDockContainer* _this;
CDockContainerWidget* DockContainer;
unsigned int zOrderIndex = ++zOrderCounter;
QPointer<CDockManager> DockManager;
bool DraggingActive = false;
QPoint DragStartMousePosition;
CDockContainerWidget* DropContainer = nullptr;
CDockAreaWidget* SingleDockArea = nullptr;
/**
* Private data constructor
*/
FloatingDockContainerPrivate(CFloatingDockContainer* _public);
void titleMouseReleaseEvent();
void updateDropOverlays(const QPoint& GlobalPos);
void setDraggingActive(bool Active);
};
// struct FloatingDockContainerPrivate
//============================================================================
FloatingDockContainerPrivate::FloatingDockContainerPrivate(CFloatingDockContainer* _public) :
_this(_public)
{
}
//============================================================================
void FloatingDockContainerPrivate::titleMouseReleaseEvent()
{
setDraggingActive(false);
if (!DropContainer)
{
return;
}
std::cout << "Dropped" << std::endl;
DropContainer->dropFloatingWidget(_this, QCursor::pos());
DockManager->containerOverlay()->hideOverlay();
DockManager->dockAreaOverlay()->hideOverlay();
}
//============================================================================
void FloatingDockContainerPrivate::updateDropOverlays(const QPoint& GlobalPos)
{
if (!_this->isVisible() || !DockManager)
{
return;
}
auto Containers = DockManager->dockContainers();
CDockContainerWidget* TopContainer = nullptr;
for (auto ContainerWidget : Containers)
{
if (!ContainerWidget->isVisible())
{
continue;
}
if (DockContainer == ContainerWidget)
{
continue;
}
QPoint MappedPos = ContainerWidget->mapFromGlobal(GlobalPos);
if (ContainerWidget->rect().contains(MappedPos))
{
if (!TopContainer || ContainerWidget->isInFrontOf(TopContainer))
{
TopContainer = ContainerWidget;
}
}
}
DropContainer = TopContainer;
auto ContainerOverlay = DockManager->containerOverlay();
auto DockAreaOverlay = DockManager->dockAreaOverlay();
if (!TopContainer)
{
ContainerOverlay->hideOverlay();
DockAreaOverlay->hideOverlay();
return;
}
ContainerOverlay->setAllowedAreas(TopContainer->dockAreaCount() > 1 ?
OuterDockAreas : AllDockAreas);
ContainerOverlay->showOverlay(TopContainer);
ContainerOverlay->raise();
auto DockArea = TopContainer->dockAreaAt(GlobalPos);
if (DockArea && TopContainer->dockAreaCount() > 1)
{
DockAreaOverlay->setAllowedAreas(AllDockAreas);
DockAreaOverlay->showOverlay(DockArea);
}
else
{
DockAreaOverlay->hideOverlay();
}
}
//============================================================================
void FloatingDockContainerPrivate::setDraggingActive(bool Active)
{
DraggingActive = Active;
}
//============================================================================
CFloatingDockContainer::CFloatingDockContainer(CDockManager* DockManager) :
QWidget(DockManager, Qt::Window),
d(new FloatingDockContainerPrivate(this))
{
//setAttribute(Qt::WA_DeleteOnClose);
d->DockManager = DockManager;
QBoxLayout* l = new QBoxLayout(QBoxLayout::TopToBottom);
l->setContentsMargins(0, 0, 0, 0);
l->setSpacing(0);
setLayout(l);
d->DockContainer = new CDockContainerWidget(DockManager, this);
connect(d->DockContainer, SIGNAL(dockAreasAdded()), this, SLOT(onDockAreasAddedOrRemoved()));
connect(d->DockContainer, SIGNAL(dockAreasRemoved()), this, SLOT(onDockAreasAddedOrRemoved()));
l->addWidget(d->DockContainer);
DockManager->registerFloatingWidget(this);
// We install an event filter to detect mouse release events because we
// do not receive mouse release event if the floating widget is behind
// the drop overlay cross
qApp->installEventFilter(this);
}
//============================================================================
CFloatingDockContainer::CFloatingDockContainer(CDockAreaWidget* DockArea) :
CFloatingDockContainer(DockArea->dockManager())
{
d->DockContainer->addDockArea(DockArea);
}
//============================================================================
CFloatingDockContainer::CFloatingDockContainer(CDockWidget* DockWidget) :
CFloatingDockContainer(DockWidget->dockManager())
{
d->DockContainer->addDockWidget(CenterDockWidgetArea, DockWidget);
}
//============================================================================
CFloatingDockContainer::~CFloatingDockContainer()
{
std::cout << "~CFloatingDockContainer" << std::endl;
if (d->DockManager)
{
d->DockManager->removeFloatingWidget(this);
}
delete d;
}
//============================================================================
CDockContainerWidget* CFloatingDockContainer::dockContainer() const
{
return d->DockContainer;
}
//============================================================================
void CFloatingDockContainer::changeEvent(QEvent *event)
{
QWidget::changeEvent(event);
if ((event->type() == QEvent::ActivationChange) && isActiveWindow())
{
std::cout << "FloatingWidget::changeEvent QEvent::ActivationChange " << std::endl;
d->zOrderIndex = ++zOrderCounter;
return;
}
}
//============================================================================
void CFloatingDockContainer::moveEvent(QMoveEvent *event)
{
QWidget::moveEvent(event);
if (!qApp->mouseButtons().testFlag(Qt::LeftButton))
{
if (d->DraggingActive)
{
d->setDraggingActive(false);
}
return;
}
if (d->DraggingActive)
{
d->updateDropOverlays(QCursor::pos());
}
}
//============================================================================
void CFloatingDockContainer::closeEvent(QCloseEvent *event)
{
d->setDraggingActive(false);
QWidget::closeEvent(event);
}
//============================================================================
void CFloatingDockContainer::hideEvent(QHideEvent *event)
{
QWidget::hideEvent(event);
auto OpenDockAreas = d->DockContainer->openedDockAreas();
for (auto DockArea : OpenDockAreas)
{
auto OpenDockWidgets = DockArea->openedDockWidgets();
for (auto DockWidget : OpenDockWidgets)
{
DockWidget->setToggleViewActionChecked(false);
}
}
}
//============================================================================
void CFloatingDockContainer::showEvent(QShowEvent *event)
{
QWidget::showEvent(event);
CDockContainerWidget* DockContainer = dockContainer();
for (int i = 0; i < DockContainer->dockAreaCount(); ++i)
{
auto DockArea = DockContainer->dockArea(i);
for (auto DockWidget : DockArea->openedDockWidgets())
{
DockWidget->setToggleViewActionChecked(true);
}
}
}
//============================================================================
bool CFloatingDockContainer::event(QEvent *e)
{
if ((e->type() == QEvent::NonClientAreaMouseButtonPress))
{
if (QGuiApplication::mouseButtons() == Qt::LeftButton)
{
std::cout << "FloatingWidget::event Event::NonClientAreaMouseButtonPress" << e->type() << std::endl;
d->setDraggingActive(true);
}
}
else if (e->type() == QEvent::NonClientAreaMouseButtonDblClick)
{
std::cout << "FloatingWidget::event QEvent::NonClientAreaMouseButtonDblClick" << std::endl;
d->setDraggingActive(false);
}
else if ((e->type() == QEvent::NonClientAreaMouseButtonRelease) && d->DraggingActive)
{
std::cout << "FloatingWidget::event QEvent::NonClientAreaMouseButtonRelease" << std::endl;
d->titleMouseReleaseEvent();
}
return QWidget::event(e);
}
//============================================================================
bool CFloatingDockContainer::eventFilter(QObject *watched, QEvent *event)
{
if (event->type() == QEvent::MouseButtonRelease && d->DraggingActive)
{
std::cout << "FloatingWidget::eventFilter QEvent::MouseButtonRelease" << std::endl;
d->titleMouseReleaseEvent();
}
return false;
}
//============================================================================
void CFloatingDockContainer::startFloating(const QPoint& Pos, const QSize& Size)
{
resize(Size);
d->setDraggingActive(true);
QPoint TargetPos = QCursor::pos() - Pos;
move(TargetPos);
show();
d->DragStartMousePosition = Pos;
}
//============================================================================
void CFloatingDockContainer::moveFloating()
{
int BorderSize = (frameSize().width() - size().width()) / 2;
const QPoint moveToPos = QCursor::pos() - d->DragStartMousePosition - QPoint(BorderSize, 0);
move(moveToPos);
}
//============================================================================
void CFloatingDockContainer::onDockAreasAddedOrRemoved()
{
if (d->DockContainer->dockAreaCount() == 1)
{
d->SingleDockArea = d->DockContainer->dockArea(0);
this->setWindowTitle(d->SingleDockArea->currentDockWidget()->windowTitle());
connect(d->SingleDockArea, SIGNAL(currentChanged(int)), this,
SLOT(onDockAreaCurrentChanged(int)));
}
else
{
if (d->SingleDockArea)
{
disconnect(d->SingleDockArea, SIGNAL(currentChanged(int)), this,
SLOT(onDockAreaCurrentChanged(int)));
d->SingleDockArea = nullptr;
}
this->setWindowTitle(qApp->applicationDisplayName());
}
}
//============================================================================
void CFloatingDockContainer::onDockAreaCurrentChanged(int Index)
{
this->setWindowTitle(d->SingleDockArea->currentDockWidget()->windowTitle());
}
} // namespace ads
//---------------------------------------------------------------------------
// EOF FloatingDockContainer.cpp

View File

@ -1,108 +1,110 @@
#ifndef FloatingDockContainerH
#define FloatingDockContainerH
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file FloatingDockContainer.h
/// \author Uwe Kindler
/// \date 01.03.2017
/// \brief Declaration of CFloatingDockContainer class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include <QWidget>
namespace ads
{
struct FloatingDockContainerPrivate;
class CDockAreaWidget;
class CDockContainerWidget;
class CDockWidget;
class CDockManager;
/**
* This implements a floating widget that is a dock container that accepts
* docking of dock widgets like the main window and that can be docked into
* another dock container
*/
class CFloatingDockContainer : public QWidget
{
Q_OBJECT
private:
FloatingDockContainerPrivate* d; ///< private data (pimpl)
friend class FloatingDockContainerPrivate;
private slots:
void onDockAreasAddedOrRemoved();
void onDockAreaCurrentChanged(int Index);
protected:
/**
* Private constructor that is called from public constructors
*/
CFloatingDockContainer(CDockManager* DockManager);
protected: // reimplements QWidget
virtual void changeEvent(QEvent *event) override;
virtual void moveEvent(QMoveEvent *event) override;
virtual bool event(QEvent *e) override;
virtual void closeEvent(QCloseEvent *event) override;
virtual bool eventFilter(QObject *watched, QEvent *event) override;
public:
/**
* Create floating widget with the given dock area
*/
CFloatingDockContainer(CDockAreaWidget* DockArea);
/**
* Create floating widget with the given dock widget
*/
CFloatingDockContainer(CDockWidget* DockWidget);
/**
* Virtual Destructor
*/
virtual ~CFloatingDockContainer();
/**
* Access function for the internal dock container
*/
CDockContainerWidget* dockContainer() const;
/**
* Starts floating at the given global position.
* Use moveToGlobalPos() to move the widget to a new position
* depending on the start position given in Pos parameter
*/
void startFloating(const QPoint& Pos, const QSize& Size = QSize());
/**
* Moves the widget to a new position relative to the position given when
* startFloating() was called
*/
void moveFloating();
}; // class FloatingDockContainer
}
// namespace ads
//-----------------------------------------------------------------------------
#endif // FloatingDockContainerH
#ifndef FloatingDockContainerH
#define FloatingDockContainerH
/*******************************************************************************
** QtAdcancedDockingSystem
** Copyright (C) 2017 Uwe Kindler
**
** 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 3 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/>.
******************************************************************************/
//============================================================================
/// \file FloatingDockContainer.h
/// \author Uwe Kindler
/// \date 01.03.2017
/// \brief Declaration of CFloatingDockContainer class
//============================================================================
//============================================================================
// INCLUDES
//============================================================================
#include <QWidget>
namespace ads
{
struct FloatingDockContainerPrivate;
class CDockAreaWidget;
class CDockContainerWidget;
class CDockWidget;
class CDockManager;
/**
* This implements a floating widget that is a dock container that accepts
* docking of dock widgets like the main window and that can be docked into
* another dock container
*/
class CFloatingDockContainer : public QWidget
{
Q_OBJECT
private:
FloatingDockContainerPrivate* d; ///< private data (pimpl)
friend class FloatingDockContainerPrivate;
private slots:
void onDockAreasAddedOrRemoved();
void onDockAreaCurrentChanged(int Index);
protected:
/**
* Private constructor that is called from public constructors
*/
CFloatingDockContainer(CDockManager* DockManager);
protected: // reimplements QWidget
virtual void changeEvent(QEvent *event) override;
virtual void moveEvent(QMoveEvent *event) override;
virtual bool event(QEvent *e) override;
virtual void closeEvent(QCloseEvent *event) override;
virtual void hideEvent(QHideEvent *event) override;
virtual void showEvent(QShowEvent *event) override;
virtual bool eventFilter(QObject *watched, QEvent *event) override;
public:
/**
* Create floating widget with the given dock area
*/
CFloatingDockContainer(CDockAreaWidget* DockArea);
/**
* Create floating widget with the given dock widget
*/
CFloatingDockContainer(CDockWidget* DockWidget);
/**
* Virtual Destructor
*/
virtual ~CFloatingDockContainer();
/**
* Access function for the internal dock container
*/
CDockContainerWidget* dockContainer() const;
/**
* Starts floating at the given global position.
* Use moveToGlobalPos() to move the widget to a new position
* depending on the start position given in Pos parameter
*/
void startFloating(const QPoint& Pos, const QSize& Size = QSize());
/**
* Moves the widget to a new position relative to the position given when
* startFloating() was called
*/
void moveFloating();
}; // class FloatingDockContainer
}
// namespace ads
//-----------------------------------------------------------------------------
#endif // FloatingDockContainerH