Compare commits
219 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
44dc76bd19 | ||
|
|
aedbaec497 | ||
|
|
04aa622111 | ||
|
|
3564229482 | ||
|
|
637db7f4f9 | ||
|
|
f6d3d6d34a | ||
|
|
92369bdb26 | ||
|
|
8f95447108 | ||
|
|
0e3c3bab45 | ||
|
|
3a5c965306 | ||
|
|
0c88457037 | ||
|
|
46fa22dc6a | ||
|
|
f3d32399e5 | ||
|
|
b320bb17d1 | ||
|
|
81afe2d3cb | ||
|
|
5fad43377b | ||
|
|
f543318232 | ||
|
|
ab385a782a | ||
|
|
c370875128 | ||
|
|
1c261515db | ||
|
|
37cbae84ca | ||
|
|
f5759716b4 | ||
|
|
f645fe725a | ||
|
|
fdedd7d92a | ||
|
|
044a43d793 | ||
|
|
6846c96146 | ||
|
|
8fe9461872 | ||
|
|
fbde4edcd2 | ||
|
|
68742681f7 | ||
|
|
bbb3f99bc3 | ||
|
|
e0f6f3013f | ||
|
|
6eb497fb64 | ||
|
|
ae15757765 | ||
|
|
be294b4867 | ||
|
|
70738f7549 | ||
|
|
42dc529ce1 | ||
|
|
65058d3a48 | ||
|
|
48c4106b7f | ||
|
|
175b48569f | ||
|
|
89c6abb5ce | ||
|
|
55f23799bc | ||
|
|
646211cc4c | ||
|
|
423bab9954 | ||
|
|
831d90ebf5 | ||
|
|
abdc0dc0dd | ||
|
|
175c836c93 | ||
|
|
76304172ab | ||
|
|
0eb3978aee | ||
|
|
73f42d55ca | ||
|
|
059a055483 | ||
|
|
dcf1ee393e | ||
|
|
04aecb3693 | ||
|
|
533d174abc | ||
|
|
48fb999bd0 | ||
|
|
5443e5f998 | ||
|
|
543d226ba3 | ||
|
|
03b1848b43 | ||
|
|
05ab8d2067 | ||
|
|
c28a27c81c | ||
|
|
1b42048135 | ||
|
|
bfe6b9bd26 | ||
|
|
08a8cee1c6 | ||
|
|
835a532e75 | ||
|
|
d383ade03c | ||
|
|
6d9c4cee02 | ||
|
|
a565239c4a | ||
|
|
ba69f3e6b9 | ||
|
|
14c29f695c | ||
|
|
703a9b3e12 | ||
|
|
0eca1b0433 | ||
|
|
691c9683ce | ||
|
|
1a11e5ddcd | ||
|
|
a4d281dbb6 | ||
|
|
8361f90dce | ||
|
|
04b4ff8b4b | ||
|
|
121248c3c5 | ||
|
|
c44d0c87e3 | ||
|
|
c6cf9487ba | ||
|
|
c78cc17730 | ||
|
|
81a0234b05 | ||
|
|
f72a8568c5 | ||
|
|
11aec65967 | ||
|
|
40636d1e05 | ||
|
|
75841415a3 | ||
|
|
edc799bc54 | ||
|
|
1d0b20337f | ||
|
|
4a6d2d3514 | ||
|
|
8443414ae3 | ||
|
|
81c99745d4 | ||
|
|
d6831caea4 | ||
|
|
aa25e1fd56 | ||
|
|
0459aff34f | ||
|
|
aeb0a27401 | ||
|
|
50e3ef3dd8 | ||
|
|
9974256d71 | ||
|
|
8cf4134125 | ||
|
|
ef5b22c616 | ||
|
|
42161c807a | ||
|
|
acfc96f57c | ||
|
|
e6e83d5775 | ||
|
|
5b2bc2297b | ||
|
|
2de3e7e3be | ||
|
|
0d242297ff | ||
|
|
e2080b5cfc | ||
|
|
679fa81f6d | ||
|
|
6d0f14e1a5 | ||
|
|
281127c2c3 | ||
|
|
8e621f1f20 | ||
|
|
0948f73bf8 | ||
|
|
4bc1a18db2 | ||
|
|
80eb628ea3 | ||
|
|
d811915a0c | ||
|
|
0225563b46 | ||
|
|
da20405a6a | ||
|
|
ace6d69695 | ||
|
|
7baf0f90e8 | ||
|
|
2ad92ce958 | ||
|
|
50c4a8ed48 | ||
|
|
59d6a64098 | ||
|
|
3de877fe56 | ||
|
|
e2cebd9dcf | ||
|
|
58744408f0 | ||
|
|
e36655a7ab | ||
|
|
ffed6a9c5f | ||
|
|
38d8e6aa25 | ||
|
|
c109ef836a | ||
|
|
caa1a9f330 | ||
|
|
e71884b23d | ||
|
|
d04c386948 | ||
|
|
6a25de327c | ||
|
|
e63d1b1683 | ||
|
|
fa2ab356e1 | ||
|
|
80f92e5697 | ||
|
|
0c13402516 | ||
|
|
97e3d72566 | ||
|
|
682aaf66eb | ||
|
|
c939df73fa | ||
|
|
fdf169ce9a | ||
|
|
4b730a4949 | ||
|
|
788c357cc0 | ||
|
|
e3844b8d6c | ||
|
|
ff3fcdcacd | ||
|
|
a9268e6bf7 | ||
|
|
0227bd1786 | ||
|
|
227037e42a | ||
|
|
cd495a14ec | ||
|
|
312a8cf500 | ||
|
|
2fc8bbe9c9 | ||
|
|
f5c4b26aab | ||
|
|
c4d2d72e92 | ||
|
|
f90f0b0427 | ||
|
|
d360b4ced2 | ||
|
|
f074ea9d67 | ||
|
|
2e8137ad85 | ||
|
|
a65b1bdcaf | ||
|
|
4041aa72cc | ||
|
|
4d2de7bb2a | ||
|
|
bcb7118710 | ||
|
|
45390506dd | ||
|
|
f58a3d4401 | ||
|
|
a3e979a8ad | ||
|
|
adb72737e8 | ||
|
|
e626a7e302 | ||
|
|
8b6df4aaa5 | ||
|
|
ccf8ea9d1e | ||
|
|
dfb8543aee | ||
|
|
277e06627b | ||
|
|
ea9b39a9dd | ||
|
|
1848ffa35a | ||
|
|
c53be0e97d | ||
|
|
ae999f132e | ||
|
|
9aa958e8b0 | ||
|
|
5652c8440e | ||
|
|
26f4c9b049 | ||
|
|
ce11fa9d10 | ||
|
|
6a393955cd | ||
|
|
6b5f364864 | ||
|
|
333d2920db | ||
|
|
25eb02d07c | ||
|
|
3b2f940efa | ||
|
|
9dcbe91f02 | ||
|
|
4da810ba7c | ||
|
|
819f1effc5 | ||
|
|
ba94ef3493 | ||
|
|
36bcbded54 | ||
|
|
0127fd89a3 | ||
|
|
eee9ebb41d | ||
|
|
79cb889d83 | ||
|
|
cdb8926673 | ||
|
|
b3307d81ca | ||
|
|
40374178c9 | ||
|
|
516465aefb | ||
|
|
e760d3e967 | ||
|
|
c5333a2414 | ||
|
|
0d406ece7c | ||
|
|
7c03b1b936 | ||
|
|
427b5a0be0 | ||
|
|
3011c0c030 | ||
|
|
b8b6db632c | ||
|
|
04ca4ae674 | ||
|
|
3a0c2a3113 | ||
|
|
789f78354a | ||
|
|
14f5426299 | ||
|
|
d418d92ef4 | ||
|
|
726d73b2c2 | ||
|
|
115e67edc4 | ||
|
|
4a8b5dd7ab | ||
|
|
4c75168152 | ||
|
|
64a2024513 | ||
|
|
056e1ef947 | ||
|
|
a9965bf6dc | ||
|
|
f54869fbf7 | ||
|
|
835a20f03f | ||
|
|
aa7976dac6 | ||
|
|
067338ef23 | ||
|
|
b7e7c0ccc3 | ||
|
|
cb18bc0d91 | ||
|
|
07464ce05c | ||
|
|
62ce9dca5d |
@@ -1,36 +1,28 @@
|
||||
version: '2.3.2.{build}'
|
||||
version: '{build}'
|
||||
branches:
|
||||
only:
|
||||
- master
|
||||
|
||||
image: Visual Studio 2015
|
||||
clone_depth: 1
|
||||
image: Visual Studio 2017
|
||||
|
||||
environment:
|
||||
global:
|
||||
# Appveyor doesn't have Qt 12 yet
|
||||
LatestLTSQtVersion: 5.9
|
||||
LatestQtVersion: 5.11
|
||||
LatestQtVersion: 5.13
|
||||
matrix:
|
||||
# Latest version of Qt, dll, 64bit, MSVC 2015, qmake
|
||||
- QT5: C:\Qt\%LatestQtVersion%\msvc2015_64
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC
|
||||
targetPlatform: amd64
|
||||
use_mingw: "false"
|
||||
use_static: "false"
|
||||
use_cmake: "false"
|
||||
# 32 bit builds
|
||||
# MSVC 2015 builds
|
||||
# Dynamic Library builds
|
||||
# LTS version of Qt, dll, 32bit, MSVC 2015, qmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\msvc2015
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC
|
||||
- QT5: C:\Qt\%LatestQtVersion%\msvc2017
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build
|
||||
targetPlatform: x86
|
||||
use_mingw: "false"
|
||||
use_static: "false"
|
||||
use_cmake: "false"
|
||||
# LTS version of Qt, dll, 32bit, MSVC 2015, cmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\msvc2015
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC
|
||||
- QT5: C:\Qt\%LatestQtVersion%\msvc2017
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build
|
||||
targetPlatform: x86
|
||||
use_mingw: "false"
|
||||
use_static: "false"
|
||||
@@ -38,15 +30,15 @@ environment:
|
||||
# end Dynamic Library builds
|
||||
# Static Library builds
|
||||
# LTS version of Qt, static, 32bit, MSVC 2015, qmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\msvc2015
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC
|
||||
- QT5: C:\Qt\%LatestQtVersion%\msvc2017
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build
|
||||
targetPlatform: x86
|
||||
use_mingw: "false"
|
||||
use_static: "true"
|
||||
use_cmake: "false"
|
||||
# LTS version of Qt, static, 32bit, MSVC 2015, cmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\msvc2015
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC
|
||||
- QT5: C:\Qt\%LatestQtVersion%\msvc2017
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build
|
||||
targetPlatform: x86
|
||||
use_mingw: "false"
|
||||
use_static: "true"
|
||||
@@ -56,15 +48,15 @@ environment:
|
||||
# MinGW builds
|
||||
# Dynamic Library builds
|
||||
# LTS version of Qt, dll, 32bit, MinGW, qmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\mingw53_32
|
||||
COMPILER: C:\Qt\Tools\mingw530_32
|
||||
- QT5: C:\Qt\%LatestQtVersion%\mingw73_32
|
||||
COMPILER: C:\Qt\Tools\mingw730_32
|
||||
targetPlatform: x86
|
||||
use_mingw: "true"
|
||||
use_static: "false"
|
||||
use_cmake: "false"
|
||||
# LTS version of Qt, dll, 32bit, MinGW, cmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\mingw53_32
|
||||
COMPILER: C:\Qt\Tools\mingw530_32
|
||||
- QT5: C:\Qt\%LatestQtVersion%\mingw73_32
|
||||
COMPILER: C:\Qt\Tools\mingw730_32
|
||||
targetPlatform: x86
|
||||
use_mingw: "true"
|
||||
use_static: "false"
|
||||
@@ -72,15 +64,15 @@ environment:
|
||||
# end Dynamic Library builds
|
||||
# Static Library builds
|
||||
# LTS version of Qt, static, 32bit, MinGW, qmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\mingw53_32
|
||||
COMPILER: C:\Qt\Tools\mingw530_32
|
||||
- QT5: C:\Qt\%LatestQtVersion%\mingw73_32
|
||||
COMPILER: C:\Qt\Tools\mingw730_32
|
||||
targetPlatform: x86
|
||||
use_mingw: "true"
|
||||
use_static: "true"
|
||||
use_cmake: "false"
|
||||
# LTS version of Qt, static, 32bit, MinGW, cmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\mingw53_32
|
||||
COMPILER: C:\Qt\Tools\mingw530_32
|
||||
- QT5: C:\Qt\%LatestQtVersion%\mingw73_32
|
||||
COMPILER: C:\Qt\Tools\mingw730_32
|
||||
targetPlatform: x86
|
||||
use_mingw: "true"
|
||||
use_static: "true"
|
||||
@@ -92,15 +84,15 @@ environment:
|
||||
# MSVC 2015 builds
|
||||
# Dynamic Library builds
|
||||
# LTS version of Qt, dll, 64bit, MSVC 2015, qmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\msvc2015_64
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC
|
||||
- QT5: C:\Qt\%LatestQtVersion%\msvc2017_64
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build
|
||||
targetPlatform: amd64
|
||||
use_mingw: "false"
|
||||
use_static: "false"
|
||||
use_cmake: "false"
|
||||
# LTS version of Qt, dll, 64bit, MSVC 2015, cmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\msvc2015_64
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC
|
||||
- QT5: C:\Qt\%LatestQtVersion%\msvc2017_64
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build
|
||||
targetPlatform: amd64
|
||||
use_mingw: "false"
|
||||
use_static: "false"
|
||||
@@ -108,15 +100,15 @@ environment:
|
||||
# end Dynamic Library builds
|
||||
# Static Library builds
|
||||
# LTS version of Qt, static, 64bit, MSVC 2015, qmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\msvc2015_64
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC
|
||||
- QT5: C:\Qt\%LatestQtVersion%\msvc2017_64
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build
|
||||
targetPlatform: amd64
|
||||
use_mingw: "false"
|
||||
use_static: "true"
|
||||
use_cmake: "false"
|
||||
# LTS version of Qt, static, 64bit, MSVC 2015, cmake
|
||||
- QT5: C:\Qt\%LatestLTSQtVersion%\msvc2015_64
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC
|
||||
- QT5: C:\Qt\%LatestQtVersion%\msvc2017_64
|
||||
COMPILER: C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build
|
||||
targetPlatform: amd64
|
||||
use_mingw: "false"
|
||||
use_static: "true"
|
||||
@@ -129,10 +121,9 @@ matrix:
|
||||
fast_finish: true
|
||||
|
||||
before_build:
|
||||
- set PATH=%COMPILER%\bin;%QT5%\bin;%PATH%
|
||||
- set originalWD=%CD%
|
||||
- call "%QT5%\bin\qtenv2.bat"
|
||||
- cd %originalWD%
|
||||
- cd /D %originalWD%
|
||||
- if %use_mingw%==false call "%COMPILER%\vcvarsall.bat" %targetPlatform%
|
||||
- if %use_static%==true (set USESTATIC=ON) else (set USESTATIC=OFF)
|
||||
- if %use_mingw%==true (set CMAKEGENERATOR="MinGW Makefiles") else (set CMAKEGENERATOR="NMake Makefiles")
|
||||
@@ -140,8 +131,8 @@ before_build:
|
||||
- if %use_mingw%==true set PATH=%PATH:C:\Program Files\Git\usr\bin;=%
|
||||
|
||||
build_script:
|
||||
- if %use_cmake%==true mkdir .\build
|
||||
- if %use_cmake%==true cd .\build
|
||||
- if %use_cmake%==true mkdir build
|
||||
- if %use_cmake%==true cd build
|
||||
- if %use_cmake%==true cmake --version
|
||||
- if %use_cmake%==true cmake -G %CMAKEGENERATOR% -DCMAKE_BUILD_TYPE=DEBUG -DBUILD_EXAMPLES=ON -DCMAKE_DEBUG_POSTFIX=d -DBUILD_STATIC=%USESTATIC% -DCMAKE_INSTALL_PREFIX="./installed" ../
|
||||
- if %use_cmake%==true cmake --build .
|
||||
|
||||
359
.cproject
@@ -1,359 +0,0 @@
|
||||
<?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=""${workspace_loc:/QtAdvancedDockingSystem/demo}""/>
|
||||
<listOptionValue builtIn="false" value=""${workspace_loc:/QtAdvancedDockingSystem/src}""/>
|
||||
<listOptionValue builtIn="false" value=""${QTDIR}/include""/>
|
||||
<listOptionValue builtIn="false" value=""${QTDIR}/include/QtCore""/>
|
||||
<listOptionValue builtIn="false" value=""${QTDIR}/include/QtWidgets""/>
|
||||
</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=""${workspace_loc:/QtAdvancedDockingSystem/src}""/>
|
||||
<listOptionValue builtIn="false" value=""${workspace_loc:/QtAdvancedDockingSystem/demo}""/>
|
||||
<listOptionValue builtIn="false" value=""${QTDIR}/include""/>
|
||||
<listOptionValue builtIn="false" value=""${QTDIR}/include/QtCore""/>
|
||||
<listOptionValue builtIn="false" value=""${QTDIR}/include/QtWidgets""/>
|
||||
</option>
|
||||
<option id="gnu.cpp.compiler.option.preprocessor.def.56223209" name="Defined symbols (-D)" superClass="gnu.cpp.compiler.option.preprocessor.def" useByScannerDiscovery="false"/>
|
||||
<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=""${workspace_loc:/QtAdvancedDockingSystem/demo}""/>
|
||||
<listOptionValue builtIn="false" value=""${workspace_loc:/QtAdvancedDockingSystem/src}""/>
|
||||
<listOptionValue builtIn="false" value=""${QTDIR}/include""/>
|
||||
<listOptionValue builtIn="false" value=""${QTDIR}/include/QtCore""/>
|
||||
<listOptionValue builtIn="false" value=""${QTDIR}/include/QtWidgets""/>
|
||||
</option>
|
||||
<option id="gnu.c.compiler.option.preprocessor.def.symbols.806805509" name="Defined symbols (-D)" superClass="gnu.c.compiler.option.preprocessor.def.symbols" useByScannerDiscovery="false"/>
|
||||
<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>
|
||||
<buildArguments/>
|
||||
<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>
|
||||
<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>
|
||||
<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>
|
||||
<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/example" 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/example" 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/example" 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/example" targetID="org.eclipse.cdt.build.MakeTargetBuilder">
|
||||
<buildCommand>qmake</buildCommand>
|
||||
<buildArguments>-recursive ../../example/example.pro</buildArguments>
|
||||
<buildTarget/>
|
||||
<stopOnError>true</stopOnError>
|
||||
<useDefaultCommand>false</useDefaultCommand>
|
||||
<runAllBuilders>false</runAllBuilders>
|
||||
</target>
|
||||
<target name="Release Build" path=" build/example" 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>
|
||||
<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>
|
||||
<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>
|
||||
<buildArguments/>
|
||||
<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>
|
||||
<buildArguments/>
|
||||
<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>
|
||||
<buildArguments/>
|
||||
<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>
|
||||
<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>
|
||||
1
.github/workflows/linux-builds.yml
vendored
@@ -16,6 +16,7 @@ jobs:
|
||||
run: |
|
||||
sudo apt-get update --fix-missing
|
||||
sudo apt-get install qt5-default
|
||||
sudo apt-get install libqt5x11extras5-dev
|
||||
- name: qmake
|
||||
run: qmake
|
||||
- name: make
|
||||
|
||||
366
.gitignore
vendored
@@ -17,3 +17,369 @@ Makefile
|
||||
*.pyd
|
||||
__pycache__
|
||||
PyQtAds/rc.py
|
||||
/.cproject
|
||||
|
||||
|
||||
## Ignore Visual Studio temporary files, build results, and
|
||||
## files generated by popular Visual Studio add-ons.
|
||||
##
|
||||
## Get latest from https://github.com/github/gitignore/blob/master/VisualStudio.gitignore
|
||||
|
||||
# User-specific files
|
||||
*.rsuser
|
||||
*.suo
|
||||
*.user
|
||||
*.userosscache
|
||||
*.sln.docstates
|
||||
|
||||
# User-specific files (MonoDevelop/Xamarin Studio)
|
||||
*.userprefs
|
||||
|
||||
# Mono auto generated files
|
||||
mono_crash.*
|
||||
|
||||
# Build results
|
||||
[Dd]ebug/
|
||||
[Dd]ebugPublic/
|
||||
[Rr]elease/
|
||||
[Rr]eleases/
|
||||
x64/
|
||||
x86/
|
||||
[Ww][Ii][Nn]32/
|
||||
[Aa][Rr][Mm]/
|
||||
[Aa][Rr][Mm]64/
|
||||
bld/
|
||||
[Bb]in/
|
||||
[Oo]bj/
|
||||
[Ll]og/
|
||||
[Ll]ogs/
|
||||
|
||||
# Visual Studio 2015/2017 cache/options directory
|
||||
.vs/
|
||||
# Uncomment if you have tasks that create the project's static files in wwwroot
|
||||
#wwwroot/
|
||||
|
||||
# Visual Studio 2017 auto generated files
|
||||
Generated\ Files/
|
||||
|
||||
# MSTest test Results
|
||||
[Tt]est[Rr]esult*/
|
||||
[Bb]uild[Ll]og.*
|
||||
|
||||
# NUnit
|
||||
*.VisualState.xml
|
||||
TestResult.xml
|
||||
nunit-*.xml
|
||||
|
||||
# Build Results of an ATL Project
|
||||
[Dd]ebugPS/
|
||||
[Rr]eleasePS/
|
||||
dlldata.c
|
||||
|
||||
# Benchmark Results
|
||||
BenchmarkDotNet.Artifacts/
|
||||
|
||||
# .NET Core
|
||||
project.lock.json
|
||||
project.fragment.lock.json
|
||||
artifacts/
|
||||
|
||||
# ASP.NET Scaffolding
|
||||
ScaffoldingReadMe.txt
|
||||
|
||||
# StyleCop
|
||||
StyleCopReport.xml
|
||||
|
||||
# Files built by Visual Studio
|
||||
*_i.c
|
||||
*_p.c
|
||||
*_h.h
|
||||
*.ilk
|
||||
*.meta
|
||||
*.obj
|
||||
*.iobj
|
||||
*.pch
|
||||
*.pdb
|
||||
*.ipdb
|
||||
*.pgc
|
||||
*.pgd
|
||||
*.rsp
|
||||
*.sbr
|
||||
*.tlb
|
||||
*.tli
|
||||
*.tlh
|
||||
*.tmp
|
||||
*.tmp_proj
|
||||
*_wpftmp.csproj
|
||||
*.log
|
||||
*.vspscc
|
||||
*.vssscc
|
||||
.builds
|
||||
*.pidb
|
||||
*.svclog
|
||||
*.scc
|
||||
|
||||
# Chutzpah Test files
|
||||
_Chutzpah*
|
||||
|
||||
# Visual C++ cache files
|
||||
ipch/
|
||||
*.aps
|
||||
*.ncb
|
||||
*.opendb
|
||||
*.opensdf
|
||||
*.sdf
|
||||
*.cachefile
|
||||
*.VC.db
|
||||
*.VC.VC.opendb
|
||||
|
||||
# Visual Studio profiler
|
||||
*.psess
|
||||
*.vsp
|
||||
*.vspx
|
||||
*.sap
|
||||
|
||||
# Visual Studio Trace Files
|
||||
*.e2e
|
||||
|
||||
# TFS 2012 Local Workspace
|
||||
$tf/
|
||||
|
||||
# Guidance Automation Toolkit
|
||||
*.gpState
|
||||
|
||||
# ReSharper is a .NET coding add-in
|
||||
_ReSharper*/
|
||||
*.[Rr]e[Ss]harper
|
||||
*.DotSettings.user
|
||||
|
||||
# TeamCity is a build add-in
|
||||
_TeamCity*
|
||||
|
||||
# DotCover is a Code Coverage Tool
|
||||
*.dotCover
|
||||
|
||||
# AxoCover is a Code Coverage Tool
|
||||
.axoCover/*
|
||||
!.axoCover/settings.json
|
||||
|
||||
# Coverlet is a free, cross platform Code Coverage Tool
|
||||
coverage*[.json, .xml, .info]
|
||||
|
||||
# Visual Studio code coverage results
|
||||
*.coverage
|
||||
*.coveragexml
|
||||
|
||||
# NCrunch
|
||||
_NCrunch_*
|
||||
.*crunch*.local.xml
|
||||
nCrunchTemp_*
|
||||
|
||||
# MightyMoose
|
||||
*.mm.*
|
||||
AutoTest.Net/
|
||||
|
||||
# Web workbench (sass)
|
||||
.sass-cache/
|
||||
|
||||
# Installshield output folder
|
||||
[Ee]xpress/
|
||||
|
||||
# DocProject is a documentation generator add-in
|
||||
DocProject/buildhelp/
|
||||
DocProject/Help/*.HxT
|
||||
DocProject/Help/*.HxC
|
||||
DocProject/Help/*.hhc
|
||||
DocProject/Help/*.hhk
|
||||
DocProject/Help/*.hhp
|
||||
DocProject/Help/Html2
|
||||
DocProject/Help/html
|
||||
|
||||
# Click-Once directory
|
||||
publish/
|
||||
|
||||
# Publish Web Output
|
||||
*.[Pp]ublish.xml
|
||||
*.azurePubxml
|
||||
# Note: Comment the next line if you want to checkin your web deploy settings,
|
||||
# but database connection strings (with potential passwords) will be unencrypted
|
||||
*.pubxml
|
||||
*.publishproj
|
||||
|
||||
# Microsoft Azure Web App publish settings. Comment the next line if you want to
|
||||
# checkin your Azure Web App publish settings, but sensitive information contained
|
||||
# in these scripts will be unencrypted
|
||||
PublishScripts/
|
||||
|
||||
# NuGet Packages
|
||||
*.nupkg
|
||||
# NuGet Symbol Packages
|
||||
*.snupkg
|
||||
# The packages folder can be ignored because of Package Restore
|
||||
**/[Pp]ackages/*
|
||||
# except build/, which is used as an MSBuild target.
|
||||
!**/[Pp]ackages/build/
|
||||
# Uncomment if necessary however generally it will be regenerated when needed
|
||||
#!**/[Pp]ackages/repositories.config
|
||||
# NuGet v3's project.json files produces more ignorable files
|
||||
*.nuget.props
|
||||
*.nuget.targets
|
||||
|
||||
# Microsoft Azure Build Output
|
||||
csx/
|
||||
*.build.csdef
|
||||
|
||||
# Microsoft Azure Emulator
|
||||
ecf/
|
||||
rcf/
|
||||
|
||||
# Windows Store app package directories and files
|
||||
AppPackages/
|
||||
BundleArtifacts/
|
||||
Package.StoreAssociation.xml
|
||||
_pkginfo.txt
|
||||
*.appx
|
||||
*.appxbundle
|
||||
*.appxupload
|
||||
|
||||
# Visual Studio cache files
|
||||
# files ending in .cache can be ignored
|
||||
*.[Cc]ache
|
||||
# but keep track of directories ending in .cache
|
||||
!?*.[Cc]ache/
|
||||
|
||||
# Others
|
||||
ClientBin/
|
||||
~$*
|
||||
*~
|
||||
*.dbmdl
|
||||
*.dbproj.schemaview
|
||||
*.jfm
|
||||
*.pfx
|
||||
*.publishsettings
|
||||
orleans.codegen.cs
|
||||
|
||||
# Including strong name files can present a security risk
|
||||
# (https://github.com/github/gitignore/pull/2483#issue-259490424)
|
||||
#*.snk
|
||||
|
||||
# Since there are multiple workflows, uncomment next line to ignore bower_components
|
||||
# (https://github.com/github/gitignore/pull/1529#issuecomment-104372622)
|
||||
#bower_components/
|
||||
|
||||
# RIA/Silverlight projects
|
||||
Generated_Code/
|
||||
|
||||
# Backup & report files from converting an old project file
|
||||
# to a newer Visual Studio version. Backup files are not needed,
|
||||
# because we have git ;-)
|
||||
_UpgradeReport_Files/
|
||||
Backup*/
|
||||
UpgradeLog*.XML
|
||||
UpgradeLog*.htm
|
||||
ServiceFabricBackup/
|
||||
*.rptproj.bak
|
||||
|
||||
# SQL Server files
|
||||
*.mdf
|
||||
*.ldf
|
||||
*.ndf
|
||||
|
||||
# Business Intelligence projects
|
||||
*.rdl.data
|
||||
*.bim.layout
|
||||
*.bim_*.settings
|
||||
*.rptproj.rsuser
|
||||
*- [Bb]ackup.rdl
|
||||
*- [Bb]ackup ([0-9]).rdl
|
||||
*- [Bb]ackup ([0-9][0-9]).rdl
|
||||
|
||||
# Microsoft Fakes
|
||||
FakesAssemblies/
|
||||
|
||||
# GhostDoc plugin setting file
|
||||
*.GhostDoc.xml
|
||||
|
||||
# Node.js Tools for Visual Studio
|
||||
.ntvs_analysis.dat
|
||||
node_modules/
|
||||
|
||||
# Visual Studio 6 build log
|
||||
*.plg
|
||||
|
||||
# Visual Studio 6 workspace options file
|
||||
*.opt
|
||||
|
||||
# Visual Studio 6 auto-generated workspace file (contains which files were open etc.)
|
||||
*.vbw
|
||||
|
||||
# Visual Studio LightSwitch build output
|
||||
**/*.HTMLClient/GeneratedArtifacts
|
||||
**/*.DesktopClient/GeneratedArtifacts
|
||||
**/*.DesktopClient/ModelManifest.xml
|
||||
**/*.Server/GeneratedArtifacts
|
||||
**/*.Server/ModelManifest.xml
|
||||
_Pvt_Extensions
|
||||
|
||||
# Paket dependency manager
|
||||
.paket/paket.exe
|
||||
paket-files/
|
||||
|
||||
# FAKE - F# Make
|
||||
.fake/
|
||||
|
||||
# CodeRush personal settings
|
||||
.cr/personal
|
||||
|
||||
# Python Tools for Visual Studio (PTVS)
|
||||
__pycache__/
|
||||
*.pyc
|
||||
|
||||
# Cake - Uncomment if you are using it
|
||||
# tools/**
|
||||
# !tools/packages.config
|
||||
|
||||
# Tabs Studio
|
||||
*.tss
|
||||
|
||||
# Telerik's JustMock configuration file
|
||||
*.jmconfig
|
||||
|
||||
# BizTalk build output
|
||||
*.btp.cs
|
||||
*.btm.cs
|
||||
*.odx.cs
|
||||
*.xsd.cs
|
||||
|
||||
# OpenCover UI analysis results
|
||||
OpenCover/
|
||||
|
||||
# Azure Stream Analytics local run output
|
||||
ASALocalRun/
|
||||
|
||||
# MSBuild Binary and Structured Log
|
||||
*.binlog
|
||||
|
||||
# NVidia Nsight GPU debugger configuration file
|
||||
*.nvuser
|
||||
|
||||
# MFractors (Xamarin productivity tool) working folder
|
||||
.mfractor/
|
||||
|
||||
# Local History for Visual Studio
|
||||
.localhistory/
|
||||
|
||||
# BeatPulse healthcheck temp database
|
||||
healthchecksdb
|
||||
|
||||
# Backup folder for Package Reference Convert tool in Visual Studio 2017
|
||||
MigrationBackup/
|
||||
|
||||
# Ionide (cross platform F# VS Code tools) working folder
|
||||
.ionide/
|
||||
|
||||
# Fody - auto-generated XML schema
|
||||
FodyWeavers.xsd
|
||||
/ build
|
||||
/Settings.ini
|
||||
.vscode/settings.json
|
||||
|
||||
164
.travis.yml
@@ -2,9 +2,6 @@ language: cpp
|
||||
# gcc is clang on mac
|
||||
compiler: gcc
|
||||
|
||||
git:
|
||||
depth: 1
|
||||
|
||||
matrix:
|
||||
fast_finish: true
|
||||
include:
|
||||
@@ -12,6 +9,8 @@ matrix:
|
||||
os: linux
|
||||
dist: trusty
|
||||
group: stable
|
||||
before_install:
|
||||
- sudo apt-get -y install libqt5x11extras5-dev
|
||||
addons:
|
||||
apt:
|
||||
sources:
|
||||
@@ -21,74 +20,170 @@ matrix:
|
||||
packages:
|
||||
- qt55base
|
||||
- qt55tools
|
||||
- gcc-6
|
||||
- g++-6
|
||||
- libc6-i386
|
||||
- qt55x11extras
|
||||
- libqt5x11extras5-dev
|
||||
- gcc-9
|
||||
- g++-9
|
||||
script:
|
||||
- PATH="/opt/qt55/bin:$PATH"
|
||||
- CXX="g++-6"
|
||||
- CC="gcc-6"
|
||||
- CXX="g++-9"
|
||||
- CC="gcc-9"
|
||||
- qt55-env.sh
|
||||
- qmake
|
||||
- make
|
||||
- make install
|
||||
- name: Ubuntu qmake dll
|
||||
os: linux
|
||||
dist: xenial
|
||||
dist: bionic
|
||||
group: stable
|
||||
services:
|
||||
- xvfb
|
||||
compiler: gcc
|
||||
before_install:
|
||||
- sudo apt-get -y install libqt5x11extras5-dev
|
||||
addons:
|
||||
apt:
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
- sourceline: 'ppa:beineri/opt-qt-5.12.0-xenial'
|
||||
- sourceline: 'ppa:beineri/opt-qt-5.14.2-bionic'
|
||||
update: true
|
||||
packages:
|
||||
- qt512base
|
||||
- qt512tools
|
||||
- gcc-6
|
||||
- g++-6
|
||||
- qt514base
|
||||
- qt514tools
|
||||
- qt514x11extras
|
||||
- libqt5x11extras5-dev
|
||||
- gcc-9
|
||||
- g++-9
|
||||
- libc6-i386
|
||||
- libgl-dev
|
||||
- libgl1-mesa-dev
|
||||
- mesa-common-dev
|
||||
script:
|
||||
- PATH="/opt/qt512/bin:$PATH"
|
||||
- CXX="g++-6"
|
||||
- CC="gcc-6"
|
||||
- qt512-env.sh
|
||||
- PATH="/opt/qt514/bin:$PATH"
|
||||
- CXX="g++-9"
|
||||
- CC="gcc-9"
|
||||
- qt514-env.sh
|
||||
- qmake
|
||||
- make
|
||||
- make install
|
||||
- name: Ubuntu qmake static
|
||||
os: linux
|
||||
dist: xenial
|
||||
dist: bionic
|
||||
group: stable
|
||||
addons:
|
||||
services:
|
||||
- xvfb
|
||||
compiler: gcc
|
||||
before_install:
|
||||
- sudo apt-get -y install libqt5x11extras5-dev
|
||||
addons:
|
||||
apt:
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
- sourceline: 'ppa:beineri/opt-qt-5.12.0-xenial'
|
||||
- sourceline: 'ppa:beineri/opt-qt-5.14.2-bionic'
|
||||
update: true
|
||||
packages:
|
||||
- qt512base
|
||||
- qt512tools
|
||||
- gcc-6
|
||||
- g++-6
|
||||
- qt514base
|
||||
- qt514tools
|
||||
- qt514x11extras
|
||||
- libqt5x11extras5-dev
|
||||
- gcc-9
|
||||
- g++-9
|
||||
- libc6-i386
|
||||
- libgl-dev
|
||||
- libgl1-mesa-dev
|
||||
- mesa-common-dev
|
||||
script:
|
||||
- PATH="/opt/qt512/bin:$PATH"
|
||||
- CXX="g++-6"
|
||||
- CC="gcc-6"
|
||||
- qt512-env.sh
|
||||
- PATH="/opt/qt514/bin:$PATH"
|
||||
- CXX="g++-9"
|
||||
- CC="gcc-9"
|
||||
- qt514-env.sh
|
||||
- qmake "CONFIG+=adsBuildStatic"
|
||||
- make
|
||||
- make install
|
||||
- name: Ubuntu CMake dll
|
||||
os: linux
|
||||
dist: bionic
|
||||
group: stable
|
||||
services:
|
||||
- xvfb
|
||||
compiler: gcc
|
||||
before_install:
|
||||
- sudo apt-get -y install libqt5x11extras5-dev
|
||||
addons:
|
||||
apt:
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
- sourceline: 'ppa:beineri/opt-qt-5.14.2-bionic'
|
||||
update: true
|
||||
packages:
|
||||
- qt514base
|
||||
- qt514tools
|
||||
- qt514x11extras
|
||||
- libqt5x11extras5-dev
|
||||
- gcc-9
|
||||
- g++-9
|
||||
- libc6-i386
|
||||
- libgl-dev
|
||||
- libgl1-mesa-dev
|
||||
- mesa-common-dev
|
||||
script:
|
||||
- PATH="/opt/qt514/bin:$PATH"
|
||||
- CXX="g++-9"
|
||||
- CC="gcc-9"
|
||||
- qt514-env.sh
|
||||
- mkdir ./build
|
||||
- cd ./build
|
||||
- cmake --version
|
||||
- cmake -G"Unix Makefiles" -DCMAKE_BUILD_TYPE=RELEASE -DBUILD_STATIC=OFF -DBUILD_EXAMPLES=ON -DCMAKE_INSTALL_PREFIX="./installed" ../
|
||||
- cmake --build .
|
||||
- cmake --build . --target install
|
||||
- cmake -G"Unix Makefiles" -DCMAKE_BUILD_TYPE=DEBUG -DBUILD_STATIC=OFF -DBUILD_EXAMPLES=ON -DCMAKE_DEBUG_POSTFIX=d -DCMAKE_INSTALL_PREFIX="./installed" ../
|
||||
- cmake --build .
|
||||
- cmake --build . --target install
|
||||
- name: Ubuntu CMake Static
|
||||
os: linux
|
||||
dist: bionic
|
||||
group: stable
|
||||
services:
|
||||
- xvfb
|
||||
compiler: gcc
|
||||
before_install:
|
||||
- sudo apt-get -y install libqt5x11extras5-dev
|
||||
addons:
|
||||
apt:
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
- sourceline: 'ppa:beineri/opt-qt-5.14.2-bionic'
|
||||
update: true
|
||||
packages:
|
||||
- qt514base
|
||||
- qt514tools
|
||||
- qt514x11extras
|
||||
- libqt5x11extras5-dev
|
||||
- gcc-9
|
||||
- g++-9
|
||||
- libc6-i386
|
||||
- libgl-dev
|
||||
- libgl1-mesa-dev
|
||||
- mesa-common-dev
|
||||
script:
|
||||
- PATH="/opt/qt514/bin:$PATH"
|
||||
- CXX="g++-9"
|
||||
- CC="gcc-9"
|
||||
- qt514-env.sh
|
||||
- mkdir ./build
|
||||
- cd ./build
|
||||
- cmake --version
|
||||
- cmake -G"Unix Makefiles" -DCMAKE_BUILD_TYPE=RELEASE -DBUILD_STATIC=ON -DBUILD_EXAMPLES=ON -DCMAKE_INSTALL_PREFIX="./installed" ../
|
||||
- cmake --build .
|
||||
- cmake --build . --target install
|
||||
- cmake -G"Unix Makefiles" -DCMAKE_BUILD_TYPE=DEBUG -DBUILD_STATIC=ON -DBUILD_EXAMPLES=ON -DCMAKE_DEBUG_POSTFIX=d -DCMAKE_INSTALL_PREFIX="./installed" ../
|
||||
- cmake --build .
|
||||
- cmake --build . --target install
|
||||
- name: macOS CMake dll
|
||||
os: osx
|
||||
osx_image: xcode10.1
|
||||
osx_image: xcode11.3
|
||||
compiler: clang
|
||||
addons:
|
||||
homebrew:
|
||||
packages:
|
||||
@@ -107,7 +202,8 @@ matrix:
|
||||
- cmake --build . --target install
|
||||
- name: macOS CMake static
|
||||
os: osx
|
||||
osx_image: xcode10.1
|
||||
osx_image: xcode11.3
|
||||
compiler: clang
|
||||
addons:
|
||||
homebrew:
|
||||
packages:
|
||||
@@ -126,7 +222,8 @@ matrix:
|
||||
- cmake --build . --target install
|
||||
- name: macOS qmake dll
|
||||
os: osx
|
||||
osx_image: xcode10.1
|
||||
osx_image: xcode11.3
|
||||
compiler: clang
|
||||
addons:
|
||||
homebrew:
|
||||
packages:
|
||||
@@ -139,7 +236,8 @@ matrix:
|
||||
- make install
|
||||
- name: macOS qmake static
|
||||
os: osx
|
||||
osx_image: xcode10.1
|
||||
osx_image: xcode11.3
|
||||
compiler: clang
|
||||
addons:
|
||||
homebrew:
|
||||
packages:
|
||||
|
||||
129
CMakeLists.txt
@@ -1,129 +1,22 @@
|
||||
cmake_minimum_required(VERSION 3.3)
|
||||
set(ads_VERSION "2.3.2")
|
||||
set(CMAKE_CXX_STANDARD 14)
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
set(CMAKE_CXX_EXTENSIONS OFF)
|
||||
set(CMAKE_AUTOMOC ON)
|
||||
set(CMAKE_AUTORCC ON)
|
||||
project(QtAdvancedDockingSystem VERSION ${ads_VERSION})
|
||||
cmake_minimum_required(VERSION 3.5)
|
||||
set(CMAKE_MODULE_PATH ${CMAKE_CURRENT_SOURCE_DIR}/cmake/modules ${CMAKE_MODULE_PATH})
|
||||
include(GetGitRevisionDescription)
|
||||
git_describe(GitTagVersion --tags)
|
||||
string(REGEX REPLACE "^([0-9]+)\\..*" "\\1" VERSION_MAJOR "${GitTagVersion}")
|
||||
string(REGEX REPLACE "^[0-9]+\\.([0-9]+).*" "\\1" VERSION_MINOR "${GitTagVersion}")
|
||||
string(REGEX REPLACE "^[0-9]+\\.[0-9]+\\.([0-9]+).*" "\\1" VERSION_PATCH "${GitTagVersion}")
|
||||
set(VERSION_SHORT "${VERSION_MAJOR}.${VERSION_MINOR}.${VERSION_PATCH}")
|
||||
project(QtADS LANGUAGES CXX VERSION ${VERSION_SHORT})
|
||||
option(BUILD_STATIC "Build the static library" OFF)
|
||||
option(BUILD_EXAMPLES "Build the examples" ON)
|
||||
set(REQUIRED_QT_VERSION 5.5.0)
|
||||
find_package(Qt5Core ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
find_package(Qt5Gui ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
find_package(Qt5Widgets ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
message(STATUS "Found Qt ${Qt5Core_VERSION}")
|
||||
set(ads_INCLUDE ${ads_INCLUDE} ${Qt5Core_INCLUDE_DIRS})
|
||||
set(ads_INCLUDE ${ads_INCLUDE} "${CMAKE_CURRENT_SOURCE_DIR}/src")
|
||||
set(ads_LIBS ${ads_LIBS} ${Qt5Core_LIBRARIES})
|
||||
set(ads_COMPILE_DEFINE ${ads_COMPILE_DEFINE} ${Qt5Core_COMPILE_DEFINITIONS})
|
||||
set(ads_LIBS ${ads_LIBS} ${Qt5Gui_LIBRARIES})
|
||||
set(ads_INCLUDE ${ads_INCLUDE} ${Qt5Gui_INCLUDE_DIRS})
|
||||
set(ads_COMPILE_DEFINE ${ads_COMPILE_DEFINE} ${Qt5Gui_COMPILE_DEFINITIONS})
|
||||
set(ads_LIBS ${ads_LIBS} ${Qt5Widgets_LIBRARIES})
|
||||
set(ads_INCLUDE ${ads_INCLUDE} ${Qt5Widgets_INCLUDE_DIRS})
|
||||
set(ads_COMPILE_DEFINE ${ads_COMPILE_DEFINE} ${Qt5Widgets_COMPILE_DEFINITIONS})
|
||||
if(BUILD_STATIC)
|
||||
set(CMAKE_STATIC_LIBRARY_SUFFIX "_static${CMAKE_STATIC_LIBRARY_SUFFIX}")
|
||||
endif()
|
||||
set(ads_SRCS
|
||||
src/ads_globals.cpp
|
||||
src/DockAreaTabBar.cpp
|
||||
src/DockAreaTitleBar.cpp
|
||||
src/DockAreaWidget.cpp
|
||||
src/DockContainerWidget.cpp
|
||||
src/DockManager.cpp
|
||||
src/DockOverlay.cpp
|
||||
src/DockSplitter.cpp
|
||||
src/DockWidget.cpp
|
||||
src/DockWidgetTab.cpp
|
||||
src/DockingStateReader.cpp
|
||||
src/ElidingLabel.cpp
|
||||
src/FloatingDockContainer.cpp
|
||||
src/FloatingDragPreview.cpp
|
||||
src/IconProvider.cpp
|
||||
src/DockComponentsFactory.cpp
|
||||
src/ads.qrc
|
||||
src/linux/FloatingWidgetTitleBar.cpp
|
||||
)
|
||||
set(ads_INSTALL_INCLUDE
|
||||
src/ads_globals.h
|
||||
src/DockAreaTabBar.h
|
||||
src/DockAreaTitleBar.h
|
||||
src/DockAreaWidget.h
|
||||
src/DockContainerWidget.h
|
||||
src/DockManager.h
|
||||
src/DockOverlay.h
|
||||
src/DockSplitter.h
|
||||
src/DockWidget.h
|
||||
src/DockWidgetTab.h
|
||||
src/DockingStateReader.h
|
||||
src/ElidingLabel.h
|
||||
src/FloatingDockContainer.h
|
||||
src/FloatingDragPreview.h
|
||||
src/IconProvider.h
|
||||
src/DockComponentsFactory.h
|
||||
src/linux/FloatingWidgetTitleBar.h
|
||||
)
|
||||
if("${CMAKE_SIZEOF_VOID_P}" STREQUAL "4")
|
||||
set(ads_PlatformDir "x86")
|
||||
else()
|
||||
set(ads_PlatformDir "x64")
|
||||
endif()
|
||||
if(BUILD_STATIC)
|
||||
add_library(qtadvanceddocking STATIC ${ads_SRCS})
|
||||
target_compile_definitions(qtadvanceddocking PUBLIC ADS_STATIC)
|
||||
else()
|
||||
add_library(qtadvanceddocking SHARED ${ads_SRCS})
|
||||
set(ads_COMPILE_DEFINE ${ads_COMPILE_DEFINE} ADS_SHARED_EXPORT)
|
||||
endif()
|
||||
install(FILES ${ads_INSTALL_INCLUDE}
|
||||
DESTINATION include
|
||||
COMPONENT headers
|
||||
)
|
||||
install(FILES
|
||||
"${CMAKE_CURRENT_SOURCE_DIR}/LICENSE"
|
||||
"${CMAKE_CURRENT_SOURCE_DIR}/gnu-lgpl-v2.1.md"
|
||||
DESTINATION license
|
||||
COMPONENT license
|
||||
)
|
||||
install(TARGETS qtadvanceddocking
|
||||
EXPORT adsTargets
|
||||
RUNTIME DESTINATION bin
|
||||
LIBRARY DESTINATION lib
|
||||
ARCHIVE DESTINATION lib
|
||||
INCLUDES DESTINATION include
|
||||
)
|
||||
|
||||
include(CMakePackageConfigHelpers)
|
||||
write_basic_package_version_file("adsConfigVersion.cmake"
|
||||
VERSION ${ads_VERSION}
|
||||
COMPATIBILITY SameMajorVersion
|
||||
)
|
||||
install(EXPORT adsTargets
|
||||
FILE adsTargets.cmake
|
||||
NAMESPACE ads::
|
||||
DESTINATION lib/cmake/ads
|
||||
)
|
||||
install(FILES "adsConfig.cmake" "${CMAKE_BINARY_DIR}/adsConfigVersion.cmake"
|
||||
DESTINATION lib/cmake/ads
|
||||
)
|
||||
|
||||
target_include_directories(qtadvanceddocking PUBLIC
|
||||
"$<BUILD_INTERFACE:${ads_INCLUDE}>"
|
||||
$<INSTALL_INTERFACE:include>
|
||||
)
|
||||
target_link_libraries(qtadvanceddocking PUBLIC ${ads_LIBS})
|
||||
target_compile_definitions(qtadvanceddocking PRIVATE ${ads_COMPILE_DEFINE})
|
||||
set_target_properties(qtadvanceddocking PROPERTIES
|
||||
VERSION ${ads_VERSION}
|
||||
EXPORT_NAME "QtAdvancedDockingSystem"
|
||||
ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/bin"
|
||||
)
|
||||
add_subdirectory(src)
|
||||
if(BUILD_EXAMPLES)
|
||||
add_subdirectory(example)
|
||||
add_subdirectory(examples)
|
||||
add_subdirectory(demo)
|
||||
endif()
|
||||
|
||||
|
||||
100
README.md
@@ -1,32 +1,48 @@
|
||||
# Advanced Docking System for Qt
|
||||
|
||||
[](https://travis-ci.org/githubuser0xFFFF/Qt-Advanced-Docking-System)
|
||||
[](https://github.com/githubuser0xFFFF/Qt-Advanced-Docking-System/actions?query=workflow%3Alinux-builds)
|
||||
[](https://ci.appveyor.com/project/githubuser0xFFFF/qt-advanced-docking-system/branch/master)
|
||||
[](gnu-lgpl-v2.1.md)
|
||||
|
||||
[What's new](https://github.com/githubuser0xFFFF/Qt-Advanced-Docking-System/releases/latest) •
|
||||
[Documentation](doc/user-guide.md)
|
||||
|
||||
Qt Advanced Docking System lets you create customizable layouts using a full
|
||||
featured window docking system similar to what is found in many popular
|
||||
integrated development environments (IDEs) such as Visual Studio.
|
||||
Qt Advanced Docking System lets you create customizable layouts using a full
|
||||
featured window docking system similar to what is found in many popular
|
||||
integrated development environments (IDEs) such as Visual Studio.
|
||||
|
||||
[](https://www.youtube.com/watch?v=7pdNfafg3Qc)
|
||||
|
||||
Everything is implemented with standard Qt functionality without any
|
||||
platform specific code. Basic usage of QWidgets and QLayouts and using basic
|
||||
styles as much as possible.
|
||||
## New and Noteworthy
|
||||
|
||||
This work is based on and inspired by the
|
||||
[Advanced Docking System for Qt](https://github.com/mfreiholz/Qt-Advanced-Docking-System)
|
||||
from Manuel Freiholz. I did an almost complete rewrite of his code to improve
|
||||
code quality, readibility and to fix all issues from the issue tracker
|
||||
of his docking system project.
|
||||
The [release 3.6.0](https://github.com/githubuser0xFFFF/Qt-Advanced-Docking-System/releases/tag/3.6.0)
|
||||
adds some nice new features:
|
||||
|
||||
- support for [central widget](doc/user-guide.md#central-widget) concept
|
||||
|
||||

|
||||
|
||||
- support for [native floating widgets](doc/user-guide.md#floatingcontainerforcenativetitlebar-linux-only) on Linux
|
||||
|
||||

|
||||
|
||||
Both features are contributions from ADS users. Read the [documentation](doc/user-guide.md)
|
||||
to learn more about both new features.
|
||||
|
||||
The [release 3.5.0](https://github.com/githubuser0xFFFF/Qt-Advanced-Docking-System/releases/tag/3.5.0)
|
||||
adds the new [focus highlighting](doc/user-guide.md#focushighlighting) feature.
|
||||
This optional feature enables highlighting of the focused dock widget like you
|
||||
know it from Visual Studio.
|
||||
|
||||

|
||||
|
||||
[learn more...](doc/user-guide.md#focushighlighting)
|
||||
|
||||
## Features
|
||||
|
||||
### Overview
|
||||
|
||||
- [New and Noteworthy](#new-and-noteworthy)
|
||||
- [Features](#features)
|
||||
- [Overview](#overview)
|
||||
- [Docking everywhere - no central widget](#docking-everywhere---no-central-widget)
|
||||
@@ -38,6 +54,7 @@ of his docking system project.
|
||||
- [Tab-menu for easy handling of many tabbed dock widgets](#tab-menu-for-easy-handling-of-many-tabbed-dock-widgets)
|
||||
- [Many different ways to detach dock widgets](#many-different-ways-to-detach-dock-widgets)
|
||||
- [Supports deletion of dynamically created dock widgets](#supports-deletion-of-dynamically-created-dock-widgets)
|
||||
- [Python PyQt5 Bindings](#python-pyqt5-bindings)
|
||||
- [Tested Compatible Environments](#tested-compatible-environments)
|
||||
- [Windows](#windows)
|
||||
- [macOS](#macos)
|
||||
@@ -54,6 +71,9 @@ of his docking system project.
|
||||
- [Qt Creator IDE](#qt-creator-ide)
|
||||
- [Qt Design Studio](#qt-design-studio)
|
||||
- [QmixElements](#qmixelements)
|
||||
- [ezEditor](#ezeditor)
|
||||
- [D-Tect X](#d-tect-x)
|
||||
- [HiveWE](#hivewe)
|
||||
|
||||
### Docking everywhere - no central widget
|
||||
|
||||
@@ -135,6 +155,20 @@ You can detach dock widgets and also dock areas in the following ways:
|
||||
|
||||
Normally clicking the close button of a dock widget will just hide the widget and the user can show it again using the toggleView() action of the dock widget. This is meant for user interfaces with a static amount of widgets. But the advanced docking system also supports dynamic dock widgets that will get deleted on close. If you set the dock widget flag `DockWidgetDeleteOnClose` for a certain dock widget, then it will be deleted as soon as you close this dock widget. This enables the implementation of user interfaces with dynamically created editors, like in word processing applications or source code development tools.
|
||||
|
||||
### Python PyQt5 Bindings
|
||||
|
||||

|
||||
|
||||
The Advanced Docking System comes with a complete Python integration based on
|
||||
PyQt5 bindings. The package is available via [conda-forge](https://github.com/conda-forge/pyqtads-feedstock). The python integration has been contributed to this project
|
||||
by the following people:
|
||||
|
||||
- [n-elie](https://github.com/n-elie)
|
||||
- [Hugo Slepicka](https://github.com/hhslepicka)
|
||||
- [K Lauer](https://github.com/klauer)
|
||||
|
||||
Latest working version: [3.5.2](https://github.com/githubuser0xFFFF/Qt-Advanced-Docking-System/releases/tag/3.5.2)
|
||||
|
||||
## Tested Compatible Environments
|
||||
|
||||
### Windows
|
||||
@@ -246,7 +280,13 @@ MainWindow::~MainWindow()
|
||||
## Developers
|
||||
|
||||
- Uwe Kindler, Project Maintainer
|
||||
- Manuel Freiholz
|
||||
- Manuel Freiholz
|
||||
|
||||
This work is based on and inspired by the
|
||||
[Advanced Docking System for Qt](https://github.com/mfreiholz/Qt-Advanced-Docking-System)
|
||||
from Manuel Freiholz. I did an almost complete rewrite of his code to improve
|
||||
code quality, readibility and to fix all issues from the issue tracker
|
||||
of his docking system project.
|
||||
|
||||
## License information
|
||||
|
||||
@@ -287,7 +327,7 @@ If this project help you reduce time to develop or if you just like it, you can
|
||||
From version 4.12 on, Qt Creator uses the Advanced Docking Framework for its
|
||||
Qt Quick Designer. This improves the usability when using multiple screens.
|
||||
|
||||

|
||||

|
||||
|
||||
### [Qt Design Studio](https://www.qt.io/ui-design-tools)
|
||||
|
||||
@@ -295,7 +335,7 @@ Taken from the [Qt Blog](https://www.qt.io/blog/qt-design-studio-1.5-beta-releas
|
||||
|
||||
> The most obvious change in [Qt Design Studio 1.5](https://www.qt.io/blog/qt-design-studio-1.5-beta-released) is the integration of dock widgets using the Qt Advanced Docking System. This allows the user to fully customize the workspace and also to undock any view into its own top level window. This especially improves the usability when using multiple screens.
|
||||
|
||||

|
||||

|
||||
|
||||
### [QmixElements](https://www.cetoni.com/products/qmixelements/)
|
||||
|
||||
@@ -303,4 +343,32 @@ The QmixElements software from [CETONI](https://www.cetoni.com) is a comprehensi
|
||||
plugin-based and modular laboratory automation software for controlling CETONI devices using a joint graphical user interface. The software features a powerful script system to automate processes. This [blog post](https://www.cetoni.com/blog/qmixelements-advanced-docking-system/) gives a nice overview about the use of the Qt
|
||||
Advanced Docking System in the QmixElements sofware.
|
||||
|
||||

|
||||

|
||||
|
||||
### [ezEditor](https://github.com/ezEngine/ezEngine)
|
||||
|
||||
The ezEditor is a full blown graphical editor used for editing scenes and
|
||||
importing and authoring assets for the [ezEngine](https://github.com/ezEngine/ezEngine) -
|
||||
an open source C++ game engine in active development.
|
||||
|
||||

|
||||
|
||||
### [D-Tect X](https://www.duerr-ndt.com/products/ndt-software/d-tect-xray-inspection-software.html)
|
||||
|
||||
D-Tect X is a X-ray inspection software for industrial radiography. It is a state-of-the-art 64-bit application which supports GPU (Graphics Processing Unit) acceleration and takes full advantage of computers with multiple CPU cores. A large set of tools assist the user in image analysis and evaluation. Thanks to the Qt Advanced Docking System the flexible and intuitive user interface can be completely customized to each user’s preference.
|
||||
|
||||
[learn more...](https://www.duerr-ndt.com/products/ndt-software/d-tect-xray-inspection-software.html)
|
||||
|
||||

|
||||
|
||||
### [HiveWE](https://github.com/stijnherfst/HiveWE)
|
||||
|
||||
HiveWE is a Warcraft III world editor. It focusses on speed and ease of use,
|
||||
especially for large maps where the regular World Editor is often too slow and clunky.
|
||||
It has a JASS editor with syntax hightlighting, tabs, code completion and more.
|
||||
The JASS editor uses the Qt Advanced Docking System for the management and layout
|
||||
of the open editor windows.
|
||||
|
||||
[learn more...](https://github.com/stijnherfst/HiveWE)
|
||||
|
||||

|
||||
|
||||
4
ads.pro
@@ -3,7 +3,7 @@ TEMPLATE = subdirs
|
||||
SUBDIRS = \
|
||||
src \
|
||||
demo \
|
||||
example
|
||||
examples
|
||||
|
||||
demo.depends = src
|
||||
example.depends = src
|
||||
examples.depends = src
|
||||
|
||||
@@ -2,4 +2,7 @@ include(CMakeFindDependencyMacro)
|
||||
find_dependency(Qt5Core ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
find_dependency(Qt5Gui ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
find_dependency(Qt5Widgets ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
if(UNIX AND NOT APPLE)
|
||||
find_dependency(Qt5X11Extras ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
endif()
|
||||
include("${CMAKE_CURRENT_LIST_DIR}/adsTargets.cmake")
|
||||
172
cmake/modules/GetGitRevisionDescription.cmake
Normal file
@@ -0,0 +1,172 @@
|
||||
# - Returns a version string from Git
|
||||
#
|
||||
# These functions force a re-configure on each git commit so that you can
|
||||
# trust the values of the variables in your build system.
|
||||
#
|
||||
# get_git_head_revision(<refspecvar> <hashvar> [<additional arguments to git describe> ...])
|
||||
#
|
||||
# Returns the refspec and sha hash of the current head revision
|
||||
#
|
||||
# git_describe(<var> [<additional arguments to git describe> ...])
|
||||
#
|
||||
# Returns the results of git describe on the source tree, and adjusting
|
||||
# the output so that it tests false if an error occurs.
|
||||
#
|
||||
# git_get_exact_tag(<var> [<additional arguments to git describe> ...])
|
||||
#
|
||||
# Returns the results of git describe --exact-match on the source tree,
|
||||
# and adjusting the output so that it tests false if there was no exact
|
||||
# matching tag.
|
||||
#
|
||||
# git_local_changes(<var>)
|
||||
#
|
||||
# Returns either "CLEAN" or "DIRTY" with respect to uncommitted changes.
|
||||
# Uses the return code of "git diff-index --quiet HEAD --".
|
||||
# Does not regard untracked files.
|
||||
#
|
||||
# Requires CMake 2.6 or newer (uses the 'function' command)
|
||||
#
|
||||
# Original Author:
|
||||
# 2009-2010 Ryan Pavlik <rpavlik@iastate.edu> <abiryan@ryand.net>
|
||||
# http://academic.cleardefinition.com
|
||||
# Iowa State University HCI Graduate Program/VRAC
|
||||
#
|
||||
# Copyright Iowa State University 2009-2010.
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at
|
||||
# http://www.boost.org/LICENSE_1_0.txt)
|
||||
|
||||
if(__get_git_revision_description)
|
||||
return()
|
||||
endif()
|
||||
set(__get_git_revision_description YES)
|
||||
|
||||
# We must run the following at "include" time, not at function call time,
|
||||
# to find the path to this module rather than the path to a calling list file
|
||||
get_filename_component(_gitdescmoddir ${CMAKE_CURRENT_LIST_FILE} PATH)
|
||||
|
||||
function(get_git_head_revision _refspecvar _hashvar)
|
||||
set(GIT_PARENT_DIR "${CMAKE_CURRENT_SOURCE_DIR}")
|
||||
set(GIT_DIR "${GIT_PARENT_DIR}/.git")
|
||||
while(NOT EXISTS "${GIT_DIR}") # .git dir not found, search parent directories
|
||||
set(GIT_PREVIOUS_PARENT "${GIT_PARENT_DIR}")
|
||||
get_filename_component(GIT_PARENT_DIR ${GIT_PARENT_DIR} PATH)
|
||||
if(GIT_PARENT_DIR STREQUAL GIT_PREVIOUS_PARENT)
|
||||
# We have reached the root directory, we are not in git
|
||||
set(${_refspecvar} "GITDIR-NOTFOUND" PARENT_SCOPE)
|
||||
set(${_hashvar} "GITDIR-NOTFOUND" PARENT_SCOPE)
|
||||
return()
|
||||
endif()
|
||||
set(GIT_DIR "${GIT_PARENT_DIR}/.git")
|
||||
endwhile()
|
||||
# check if this is a submodule
|
||||
if(NOT IS_DIRECTORY ${GIT_DIR})
|
||||
file(READ ${GIT_DIR} submodule)
|
||||
string(REGEX REPLACE "gitdir: (.*)\n$" "\\1" GIT_DIR_RELATIVE ${submodule})
|
||||
get_filename_component(SUBMODULE_DIR ${GIT_DIR} PATH)
|
||||
get_filename_component(GIT_DIR ${SUBMODULE_DIR}/${GIT_DIR_RELATIVE} ABSOLUTE)
|
||||
endif()
|
||||
if(NOT IS_DIRECTORY "${GIT_DIR}")
|
||||
file(READ ${GIT_DIR} worktree)
|
||||
string(REGEX REPLACE "gitdir: (.*)worktrees(.*)\n$" "\\1" GIT_DIR ${worktree})
|
||||
endif()
|
||||
set(GIT_DATA "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/git-data")
|
||||
if(NOT EXISTS "${GIT_DATA}")
|
||||
file(MAKE_DIRECTORY "${GIT_DATA}")
|
||||
endif()
|
||||
|
||||
if(NOT EXISTS "${GIT_DIR}/HEAD")
|
||||
return()
|
||||
endif()
|
||||
set(HEAD_FILE "${GIT_DATA}/HEAD")
|
||||
configure_file("${GIT_DIR}/HEAD" "${HEAD_FILE}" COPYONLY)
|
||||
|
||||
configure_file("${_gitdescmoddir}/GetGitRevisionDescription.cmake.in"
|
||||
"${GIT_DATA}/grabRef.cmake"
|
||||
@ONLY)
|
||||
include("${GIT_DATA}/grabRef.cmake")
|
||||
|
||||
set(${_refspecvar} "${HEAD_REF}" PARENT_SCOPE)
|
||||
set(${_hashvar} "${HEAD_HASH}" PARENT_SCOPE)
|
||||
endfunction()
|
||||
|
||||
function(git_describe _var)
|
||||
if(NOT GIT_FOUND)
|
||||
find_package(Git QUIET)
|
||||
endif()
|
||||
get_git_head_revision(refspec hash)
|
||||
if(NOT GIT_FOUND)
|
||||
set(${_var} "GIT-NOTFOUND" PARENT_SCOPE)
|
||||
return()
|
||||
endif()
|
||||
if(NOT hash)
|
||||
set(${_var} "HEAD-HASH-NOTFOUND" PARENT_SCOPE)
|
||||
return()
|
||||
endif()
|
||||
|
||||
# TODO sanitize
|
||||
#if((${ARGN}" MATCHES "&&") OR
|
||||
# (ARGN MATCHES "||") OR
|
||||
# (ARGN MATCHES "\\;"))
|
||||
# message("Please report the following error to the project!")
|
||||
# message(FATAL_ERROR "Looks like someone's doing something nefarious with git_describe! Passed arguments ${ARGN}")
|
||||
#endif()
|
||||
|
||||
#message(STATUS "Arguments to execute_process: ${ARGN}")
|
||||
|
||||
execute_process(COMMAND
|
||||
"${GIT_EXECUTABLE}"
|
||||
describe
|
||||
${hash}
|
||||
${ARGN}
|
||||
WORKING_DIRECTORY
|
||||
"${CMAKE_CURRENT_SOURCE_DIR}"
|
||||
RESULT_VARIABLE
|
||||
res
|
||||
OUTPUT_VARIABLE
|
||||
out
|
||||
ERROR_QUIET
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE)
|
||||
if(NOT res EQUAL 0)
|
||||
set(out "${out}-${res}-NOTFOUND")
|
||||
endif()
|
||||
|
||||
set(${_var} "${out}" PARENT_SCOPE)
|
||||
endfunction()
|
||||
|
||||
function(git_get_exact_tag _var)
|
||||
git_describe(out --exact-match ${ARGN})
|
||||
set(${_var} "${out}" PARENT_SCOPE)
|
||||
endfunction()
|
||||
|
||||
function(git_local_changes _var)
|
||||
if(NOT GIT_FOUND)
|
||||
find_package(Git QUIET)
|
||||
endif()
|
||||
get_git_head_revision(refspec hash)
|
||||
if(NOT GIT_FOUND)
|
||||
set(${_var} "GIT-NOTFOUND" PARENT_SCOPE)
|
||||
return()
|
||||
endif()
|
||||
if(NOT hash)
|
||||
set(${_var} "HEAD-HASH-NOTFOUND" PARENT_SCOPE)
|
||||
return()
|
||||
endif()
|
||||
|
||||
execute_process(COMMAND
|
||||
"${GIT_EXECUTABLE}"
|
||||
diff-index --quiet HEAD --
|
||||
WORKING_DIRECTORY
|
||||
"${CMAKE_CURRENT_SOURCE_DIR}"
|
||||
RESULT_VARIABLE
|
||||
res
|
||||
OUTPUT_VARIABLE
|
||||
out
|
||||
ERROR_QUIET
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE)
|
||||
if(res EQUAL 0)
|
||||
set(${_var} "CLEAN" PARENT_SCOPE)
|
||||
else()
|
||||
set(${_var} "DIRTY" PARENT_SCOPE)
|
||||
endif()
|
||||
endfunction()
|
||||
41
cmake/modules/GetGitRevisionDescription.cmake.in
Normal file
@@ -0,0 +1,41 @@
|
||||
#
|
||||
# Internal file for GetGitRevisionDescription.cmake
|
||||
#
|
||||
# Requires CMake 2.6 or newer (uses the 'function' command)
|
||||
#
|
||||
# Original Author:
|
||||
# 2009-2010 Ryan Pavlik <rpavlik@iastate.edu> <abiryan@ryand.net>
|
||||
# http://academic.cleardefinition.com
|
||||
# Iowa State University HCI Graduate Program/VRAC
|
||||
#
|
||||
# Copyright Iowa State University 2009-2010.
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at
|
||||
# http://www.boost.org/LICENSE_1_0.txt)
|
||||
|
||||
set(HEAD_HASH)
|
||||
|
||||
file(READ "@HEAD_FILE@" HEAD_CONTENTS LIMIT 1024)
|
||||
|
||||
string(STRIP "${HEAD_CONTENTS}" HEAD_CONTENTS)
|
||||
if(HEAD_CONTENTS MATCHES "ref")
|
||||
# named branch
|
||||
string(REPLACE "ref: " "" HEAD_REF "${HEAD_CONTENTS}")
|
||||
if(EXISTS "@GIT_DIR@/${HEAD_REF}")
|
||||
configure_file("@GIT_DIR@/${HEAD_REF}" "@GIT_DATA@/head-ref" COPYONLY)
|
||||
else()
|
||||
configure_file("@GIT_DIR@/packed-refs" "@GIT_DATA@/packed-refs" COPYONLY)
|
||||
file(READ "@GIT_DATA@/packed-refs" PACKED_REFS)
|
||||
if(${PACKED_REFS} MATCHES "([0-9a-z]*) ${HEAD_REF}")
|
||||
set(HEAD_HASH "${CMAKE_MATCH_1}")
|
||||
endif()
|
||||
endif()
|
||||
else()
|
||||
# detached HEAD
|
||||
configure_file("@GIT_DIR@/HEAD" "@GIT_DATA@/head-ref" COPYONLY)
|
||||
endif()
|
||||
|
||||
if(NOT HEAD_HASH)
|
||||
file(READ "@GIT_DATA@/head-ref" HEAD_HASH LIMIT 1024)
|
||||
string(STRIP "${HEAD_HASH}" HEAD_HASH)
|
||||
endif()
|
||||
@@ -1,29 +1,9 @@
|
||||
cmake_minimum_required(VERSION 3.3)
|
||||
set (CMAKE_CXX_STANDARD 14)
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
set(CMAKE_CXX_EXTENSIONS OFF)
|
||||
set(CMAKE_AUTOMOC ON)
|
||||
set(CMAKE_AUTOUIC ON)
|
||||
set(CMAKE_AUTORCC ON)
|
||||
project(ads_demo VERSION "1.0")
|
||||
set(REQUIRED_QT_VERSION 5.5.0)
|
||||
find_package(Qt5Core ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
find_package(Qt5Gui ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
find_package(Qt5Widgets ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
set(ads_demo_LIBS ${ads_demo_LIBS} ${Qt5Core_LIBRARIES})
|
||||
set(ads_demo_INCLUDE ${ads_demo_INCLUDE} ${Qt5Core_INCLUDE_DIRS})
|
||||
set(ads_demo_COMPILE_DEFINE ${ads_demo_COMPILE_DEFINE} ${Qt5Core_COMPILE_DEFINITIONS} )
|
||||
set(ads_demo_LIBS ${ads_demo_LIBS} ${Qt5Gui_LIBRARIES})
|
||||
set(ads_demo_INCLUDE ${ads_demo_INCLUDE} ${Qt5Gui_INCLUDE_DIRS})
|
||||
set(ads_demo_COMPILE_DEFINE ${ads_demo_COMPILE_DEFINE} ${Qt5Gui_COMPILE_DEFINITIONS})
|
||||
set(ads_demo_LIBS ${ads_demo_LIBS} ${Qt5Widgets_LIBRARIES})
|
||||
set(ads_demo_INCLUDE ${ads_demo_INCLUDE} ${Qt5Widgets_INCLUDE_DIRS})
|
||||
set(ads_demo_COMPILE_DEFINE ${ads_demo_COMPILE_DEFINE} ${Qt5Widgets_COMPILE_DEFINITIONS})
|
||||
cmake_minimum_required(VERSION 3.5)
|
||||
project(ads_demo VERSION ${VERSION_SHORT})
|
||||
|
||||
find_package(Qt5 5.5 COMPONENTS Core Gui Widgets REQUIRED)
|
||||
if(WIN32)
|
||||
find_package(Qt5AxContainer ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
set(ads_demo_LIBS ${ads_demo_LIBS} ${Qt5AxContainer_LIBRARIES})
|
||||
set(ads_demo_INCLUDE ${ads_demo_INCLUDE} ${Qt5AxContainer_INCLUDE_DIRS})
|
||||
set(ads_demo_COMPILE_DEFINE ${ads_demo_COMPILE_DEFINE} ${Qt5AxContainer_COMPILE_DEFINITIONS})
|
||||
find_package(Qt5 5.5 COMPONENTS AxContainer REQUIRED)
|
||||
endif()
|
||||
set(CMAKE_INCLUDE_CURRENT_DIR ON)
|
||||
set(ads_demo_SRCS
|
||||
@@ -35,22 +15,26 @@ set(ads_demo_SRCS
|
||||
demo.qrc
|
||||
)
|
||||
add_executable(AdvancedDockingSystemDemo WIN32 ${ads_demo_SRCS})
|
||||
if(BUILD_STATIC)
|
||||
set(ads_demo_DEFINE ${ads_demo_DEFINE} ADS_STATIC)
|
||||
target_include_directories(AdvancedDockingSystemDemo PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/../src")
|
||||
target_link_libraries(AdvancedDockingSystemDemo PUBLIC Qt5::Core Qt5::Gui Qt5::Widgets)
|
||||
if(WIN32)
|
||||
target_link_libraries(AdvancedDockingSystemDemo PUBLIC Qt5::AxContainer)
|
||||
endif()
|
||||
add_dependencies(AdvancedDockingSystemDemo qtadvanceddocking)
|
||||
target_include_directories(AdvancedDockingSystemDemo PUBLIC
|
||||
$<BUILD_INTERFACE:${ads_demo_INCLUDE}>
|
||||
$<INSTALL_INTERFACE:include>
|
||||
)
|
||||
target_include_directories(AdvancedDockingSystemDemo PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/../src" ${ads_demo_INCLUDE})
|
||||
target_link_libraries(AdvancedDockingSystemDemo PRIVATE qtadvanceddocking ${ads_demo_LIBS})
|
||||
target_compile_definitions(AdvancedDockingSystemDemo PRIVATE ${ads_demo_DEFINE})
|
||||
target_link_libraries(AdvancedDockingSystemDemo PRIVATE qtadvanceddocking)
|
||||
set_target_properties(AdvancedDockingSystemDemo PROPERTIES
|
||||
VERSION "1.0"
|
||||
SOVERSION 1
|
||||
AUTOMOC ON
|
||||
AUTORCC ON
|
||||
AUTOUIC ON
|
||||
CXX_STANDARD 14
|
||||
CXX_STANDARD_REQUIRED ON
|
||||
CXX_EXTENSIONS OFF
|
||||
VERSION ${VERSION_SHORT}
|
||||
EXPORT_NAME "Qt Advanced Docking System Demo"
|
||||
ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/bin"
|
||||
)
|
||||
#if(BUILD_STATIC)
|
||||
# target_compile_definitions(AdvancedDockingSystemDemo PRIVATE ADS_STATIC)
|
||||
#endif()
|
||||
|
||||
|
||||
@@ -78,35 +78,6 @@
|
||||
|
||||
|
||||
|
||||
//============================================================================
|
||||
static ads::CDockWidget* createLongTextLabelDockWidget(QMenu* ViewMenu)
|
||||
{
|
||||
static int LabelCount = 0;
|
||||
QLabel* l = new QLabel();
|
||||
l->setWordWrap(true);
|
||||
l->setAlignment(Qt::AlignTop | Qt::AlignLeft);
|
||||
l->setText(QString("Label %1 %2 - Lorem ipsum dolor sit amet, consectetuer adipiscing elit. "
|
||||
"Aenean commodo ligula eget dolor. Aenean massa. Cum sociis natoque "
|
||||
"penatibus et magnis dis parturient montes, nascetur ridiculus mus. "
|
||||
"Donec quam felis, ultricies nec, pellentesque eu, pretium quis, sem. "
|
||||
"Nulla consequat massa quis enim. Donec pede justo, fringilla vel, "
|
||||
"aliquet nec, vulputate eget, arcu. In enim justo, rhoncus ut, "
|
||||
"imperdiet a, venenatis vitae, justo. Nullam dictum felis eu pede "
|
||||
"mollis pretium. Integer tincidunt. Cras dapibus. Vivamus elementum "
|
||||
"semper nisi. Aenean vulputate eleifend tellus. Aenean leo ligula, "
|
||||
"porttitor eu, consequat vitae, eleifend ac, enim. Aliquam lorem ante, "
|
||||
"dapibus in, viverra quis, feugiat a, tellus. Phasellus viverra nulla "
|
||||
"ut metus varius laoreet.")
|
||||
.arg(LabelCount)
|
||||
.arg(QTime::currentTime().toString("hh:mm:ss:zzz")));
|
||||
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Label %1").arg(LabelCount++));
|
||||
DockWidget->setWidget(l);
|
||||
ViewMenu->addAction(DockWidget->toggleViewAction());
|
||||
return DockWidget;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Function returns a features string with closable (c), movable (m) and floatable (f)
|
||||
* features. i.e. The following string is for a not closable but movable and floatable
|
||||
@@ -138,7 +109,7 @@ static void appendFeaturStringToWindowTitle(ads::CDockWidget* DockWidget)
|
||||
static QIcon svgIcon(const QString& File)
|
||||
{
|
||||
// This is a workaround, because in item views SVG icons are not
|
||||
// properly scaled an look blurry or pixelate
|
||||
// properly scaled and look blurry or pixelate
|
||||
QIcon SvgIcon(File);
|
||||
SvgIcon.addPixmap(SvgIcon.pixmap(92));
|
||||
return SvgIcon;
|
||||
@@ -164,71 +135,6 @@ public:
|
||||
};
|
||||
|
||||
|
||||
//============================================================================
|
||||
static ads::CDockWidget* createCalendarDockWidget(QMenu* ViewMenu)
|
||||
{
|
||||
static int CalendarCount = 0;
|
||||
QCalendarWidget* w = new QCalendarWidget();
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Calendar %1").arg(CalendarCount++));
|
||||
// The following lines are for testing the setWidget() and takeWidget()
|
||||
// functionality
|
||||
DockWidget->setWidget(w);
|
||||
DockWidget->setWidget(w); // what happens if we set a widget if a widget is already set
|
||||
DockWidget->takeWidget(); // we remove the widget
|
||||
DockWidget->setWidget(w); // and set the widget again - there should be no error
|
||||
DockWidget->setToggleViewActionMode(ads::CDockWidget::ActionModeShow);
|
||||
DockWidget->setIcon(svgIcon(":/adsdemo/images/date_range.svg"));
|
||||
ViewMenu->addAction(DockWidget->toggleViewAction());
|
||||
return DockWidget;
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
static ads::CDockWidget* createFileSystemTreeDockWidget(QMenu* ViewMenu)
|
||||
{
|
||||
static int FileSystemCount = 0;
|
||||
QTreeView* w = new QTreeView();
|
||||
w->setFrameShape(QFrame::NoFrame);
|
||||
QFileSystemModel* m = new QFileSystemModel(w);
|
||||
m->setRootPath(QDir::currentPath());
|
||||
w->setModel(m);
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Filesystem %1")
|
||||
.arg(FileSystemCount++));
|
||||
DockWidget->setWidget(w);
|
||||
ViewMenu->addAction(DockWidget->toggleViewAction());
|
||||
return DockWidget;
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
static ads::CDockWidget* createEditorWidget(QMenu* ViewMenu)
|
||||
{
|
||||
static int EditorCount = 0;
|
||||
QPlainTextEdit* w = new QPlainTextEdit();
|
||||
w->setPlaceholderText("This is an editor. If you close the editor, it will be "
|
||||
"deleted. Enter your text here.");
|
||||
w->setStyleSheet("border: none");
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Editor %1").arg(EditorCount++));
|
||||
DockWidget->setWidget(w);
|
||||
DockWidget->setIcon(svgIcon(":/adsdemo/images/edit.svg"));
|
||||
DockWidget->setFeature(ads::CDockWidget::CustomCloseHandling, true);
|
||||
ViewMenu->addAction(DockWidget->toggleViewAction());
|
||||
|
||||
QMenu* OptionsMenu = new QMenu(DockWidget);
|
||||
OptionsMenu->setTitle(QObject::tr("Options"));
|
||||
OptionsMenu->setToolTip(OptionsMenu->title());
|
||||
OptionsMenu->setIcon(svgIcon(":/adsdemo/images/custom-menu-button.svg"));
|
||||
auto MenuAction = OptionsMenu->menuAction();
|
||||
// The object name of the action will be set for the QToolButton that
|
||||
// is created in the dock area title bar. You can use this name for CSS
|
||||
// styling
|
||||
MenuAction->setObjectName("optionsMenu");
|
||||
DockWidget->setTitleBarActions({OptionsMenu->menuAction()});
|
||||
auto a = OptionsMenu->addAction(QObject::tr("Clear Editor"));
|
||||
w->connect(a, SIGNAL(triggered()), SLOT(clear()));
|
||||
|
||||
return DockWidget;
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
/**
|
||||
@@ -246,58 +152,6 @@ public:
|
||||
};
|
||||
|
||||
|
||||
//============================================================================
|
||||
static ads::CDockWidget* createTableWidget(QMenu* ViewMenu)
|
||||
{
|
||||
static int TableCount = 0;
|
||||
auto w = new CMinSizeTableWidget();
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Table %1").arg(TableCount++));
|
||||
static int colCount = 5;
|
||||
static int rowCount = 30;
|
||||
w->setColumnCount(colCount);
|
||||
w->setRowCount(rowCount);
|
||||
for (int col = 0; col < colCount; ++col)
|
||||
{
|
||||
w->setHorizontalHeaderItem(col, new QTableWidgetItem(QString("Col %1").arg(col+1)));
|
||||
for (int row = 0; row < rowCount; ++row)
|
||||
{
|
||||
w->setItem(row, col, new QTableWidgetItem(QString("T %1-%2").arg(row + 1).arg(col+1)));
|
||||
}
|
||||
}
|
||||
DockWidget->setWidget(w);
|
||||
DockWidget->setIcon(svgIcon(":/adsdemo/images/grid_on.svg"));
|
||||
DockWidget->setMinimumSizeHintMode(ads::CDockWidget::MinimumSizeHintFromContent);
|
||||
auto ToolBar = DockWidget->createDefaultToolBar();
|
||||
auto Action = ToolBar->addAction(svgIcon(":/adsdemo/images/fullscreen.svg"), "Toggle Fullscreen");
|
||||
QObject::connect(Action, &QAction::triggered, [=]()
|
||||
{
|
||||
if (DockWidget->isFullScreen())
|
||||
{
|
||||
DockWidget->showNormal();
|
||||
}
|
||||
else
|
||||
{
|
||||
DockWidget->showFullScreen();
|
||||
}
|
||||
});
|
||||
ViewMenu->addAction(DockWidget->toggleViewAction());
|
||||
return DockWidget;
|
||||
}
|
||||
|
||||
|
||||
#ifdef Q_OS_WIN
|
||||
//============================================================================
|
||||
static ads::CDockWidget* createActiveXWidget(QMenu* ViewMenu, QWidget* parent = nullptr)
|
||||
{
|
||||
static int ActiveXCount = 0;
|
||||
QAxWidget* w = new QAxWidget("{6bf52a52-394a-11d3-b153-00c04f79faa6}", parent);
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Active X %1").arg(ActiveXCount++));
|
||||
DockWidget->setWidget(w);
|
||||
ViewMenu->addAction(DockWidget->toggleViewAction());
|
||||
return DockWidget;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
//============================================================================
|
||||
/**
|
||||
@@ -311,6 +165,8 @@ struct MainWindowPrivate
|
||||
QWidgetAction* PerspectiveListAction = nullptr;
|
||||
QComboBox* PerspectiveComboBox = nullptr;
|
||||
ads::CDockManager* DockManager = nullptr;
|
||||
ads::CDockWidget* WindowTitleTestDockWidget = nullptr;
|
||||
ads::CDockWidget* LastDockedEditor = nullptr;
|
||||
|
||||
MainWindowPrivate(CMainWindow* _public) : _this(_public) {}
|
||||
|
||||
@@ -343,14 +199,181 @@ struct MainWindowPrivate
|
||||
* Restore the perspective listo of the dock manager
|
||||
*/
|
||||
void restorePerspectives();
|
||||
|
||||
/**
|
||||
* Creates a dock widget with a file system tree view
|
||||
*/
|
||||
ads::CDockWidget* createFileSystemTreeDockWidget()
|
||||
{
|
||||
static int FileSystemCount = 0;
|
||||
QTreeView* w = new QTreeView();
|
||||
w->setFrameShape(QFrame::NoFrame);
|
||||
QFileSystemModel* m = new QFileSystemModel(w);
|
||||
m->setRootPath(QDir::currentPath());
|
||||
w->setModel(m);
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Filesystem %1")
|
||||
.arg(FileSystemCount++));
|
||||
DockWidget->setWidget(w);
|
||||
ui.menuView->addAction(DockWidget->toggleViewAction());
|
||||
// We disable focus to test focus highlighting if the dock widget content
|
||||
// does not support focus
|
||||
w->setFocusPolicy(Qt::NoFocus);
|
||||
auto ToolBar = DockWidget->createDefaultToolBar();
|
||||
ToolBar->addAction(ui.actionSaveState);
|
||||
ToolBar->addAction(ui.actionRestoreState);
|
||||
return DockWidget;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a dock widget with a QCalendarWidget
|
||||
*/
|
||||
ads::CDockWidget* createCalendarDockWidget()
|
||||
{
|
||||
static int CalendarCount = 0;
|
||||
QCalendarWidget* w = new QCalendarWidget();
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Calendar %1").arg(CalendarCount++));
|
||||
// The following lines are for testing the setWidget() and takeWidget()
|
||||
// functionality
|
||||
DockWidget->setWidget(w);
|
||||
DockWidget->setWidget(w); // what happens if we set a widget if a widget is already set
|
||||
DockWidget->takeWidget(); // we remove the widget
|
||||
DockWidget->setWidget(w); // and set the widget again - there should be no error
|
||||
DockWidget->setToggleViewActionMode(ads::CDockWidget::ActionModeShow);
|
||||
DockWidget->setIcon(svgIcon(":/adsdemo/images/date_range.svg"));
|
||||
ui.menuView->addAction(DockWidget->toggleViewAction());
|
||||
auto ToolBar = DockWidget->createDefaultToolBar();
|
||||
ToolBar->addAction(ui.actionSaveState);
|
||||
ToolBar->addAction(ui.actionRestoreState);
|
||||
return DockWidget;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Create dock widget with a text label
|
||||
*/
|
||||
ads::CDockWidget* createLongTextLabelDockWidget()
|
||||
{
|
||||
static int LabelCount = 0;
|
||||
QLabel* l = new QLabel();
|
||||
l->setWordWrap(true);
|
||||
l->setAlignment(Qt::AlignTop | Qt::AlignLeft);
|
||||
l->setText(QString("Label %1 %2 - Lorem ipsum dolor sit amet, consectetuer adipiscing elit. "
|
||||
"Aenean commodo ligula eget dolor. Aenean massa. Cum sociis natoque "
|
||||
"penatibus et magnis dis parturient montes, nascetur ridiculus mus. "
|
||||
"Donec quam felis, ultricies nec, pellentesque eu, pretium quis, sem. "
|
||||
"Nulla consequat massa quis enim. Donec pede justo, fringilla vel, "
|
||||
"aliquet nec, vulputate eget, arcu. In enim justo, rhoncus ut, "
|
||||
"imperdiet a, venenatis vitae, justo. Nullam dictum felis eu pede "
|
||||
"mollis pretium. Integer tincidunt. Cras dapibus. Vivamus elementum "
|
||||
"semper nisi. Aenean vulputate eleifend tellus. Aenean leo ligula, "
|
||||
"porttitor eu, consequat vitae, eleifend ac, enim. Aliquam lorem ante, "
|
||||
"dapibus in, viverra quis, feugiat a, tellus. Phasellus viverra nulla "
|
||||
"ut metus varius laoreet.")
|
||||
.arg(LabelCount)
|
||||
.arg(QTime::currentTime().toString("hh:mm:ss:zzz")));
|
||||
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Label %1").arg(LabelCount++));
|
||||
DockWidget->setWidget(l);
|
||||
ui.menuView->addAction(DockWidget->toggleViewAction());
|
||||
return DockWidget;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Creates as imple editor widget
|
||||
*/
|
||||
ads::CDockWidget* createEditorWidget()
|
||||
{
|
||||
static int EditorCount = 0;
|
||||
QPlainTextEdit* w = new QPlainTextEdit();
|
||||
w->setPlaceholderText("This is an editor. If you close the editor, it will be "
|
||||
"deleted. Enter your text here.");
|
||||
w->setStyleSheet("border: none");
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Editor %1").arg(EditorCount++));
|
||||
DockWidget->setWidget(w);
|
||||
DockWidget->setIcon(svgIcon(":/adsdemo/images/edit.svg"));
|
||||
DockWidget->setFeature(ads::CDockWidget::CustomCloseHandling, true);
|
||||
ui.menuView->addAction(DockWidget->toggleViewAction());
|
||||
|
||||
QMenu* OptionsMenu = new QMenu(DockWidget);
|
||||
OptionsMenu->setTitle(QObject::tr("Options"));
|
||||
OptionsMenu->setToolTip(OptionsMenu->title());
|
||||
OptionsMenu->setIcon(svgIcon(":/adsdemo/images/custom-menu-button.svg"));
|
||||
auto MenuAction = OptionsMenu->menuAction();
|
||||
// The object name of the action will be set for the QToolButton that
|
||||
// is created in the dock area title bar. You can use this name for CSS
|
||||
// styling
|
||||
MenuAction->setObjectName("optionsMenu");
|
||||
DockWidget->setTitleBarActions({OptionsMenu->menuAction()});
|
||||
auto a = OptionsMenu->addAction(QObject::tr("Clear Editor"));
|
||||
w->connect(a, SIGNAL(triggered()), SLOT(clear()));
|
||||
|
||||
return DockWidget;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a table widget
|
||||
*/
|
||||
ads::CDockWidget* createTableWidget()
|
||||
{
|
||||
static int TableCount = 0;
|
||||
auto w = new CMinSizeTableWidget();
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Table %1").arg(TableCount++));
|
||||
static int colCount = 5;
|
||||
static int rowCount = 30;
|
||||
w->setColumnCount(colCount);
|
||||
w->setRowCount(rowCount);
|
||||
for (int col = 0; col < colCount; ++col)
|
||||
{
|
||||
w->setHorizontalHeaderItem(col, new QTableWidgetItem(QString("Col %1").arg(col+1)));
|
||||
for (int row = 0; row < rowCount; ++row)
|
||||
{
|
||||
w->setItem(row, col, new QTableWidgetItem(QString("T %1-%2").arg(row + 1).arg(col+1)));
|
||||
}
|
||||
}
|
||||
DockWidget->setWidget(w);
|
||||
DockWidget->setIcon(svgIcon(":/adsdemo/images/grid_on.svg"));
|
||||
DockWidget->setMinimumSizeHintMode(ads::CDockWidget::MinimumSizeHintFromContent);
|
||||
auto ToolBar = DockWidget->createDefaultToolBar();
|
||||
auto Action = ToolBar->addAction(svgIcon(":/adsdemo/images/fullscreen.svg"), "Toggle Fullscreen");
|
||||
QObject::connect(Action, &QAction::triggered, [=]()
|
||||
{
|
||||
if (DockWidget->isFullScreen())
|
||||
{
|
||||
DockWidget->showNormal();
|
||||
}
|
||||
else
|
||||
{
|
||||
DockWidget->showFullScreen();
|
||||
}
|
||||
});
|
||||
ui.menuView->addAction(DockWidget->toggleViewAction());
|
||||
return DockWidget;
|
||||
}
|
||||
|
||||
|
||||
#ifdef Q_OS_WIN
|
||||
/**
|
||||
* Creates an ActiveX widget on windows
|
||||
*/
|
||||
ads::CDockWidget* createActiveXWidget(QWidget* parent = nullptr)
|
||||
{
|
||||
static int ActiveXCount = 0;
|
||||
QAxWidget* w = new QAxWidget("{6bf52a52-394a-11d3-b153-00c04f79faa6}", parent);
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget(QString("Active X %1").arg(ActiveXCount++));
|
||||
DockWidget->setWidget(w);
|
||||
ui.menuView->addAction(DockWidget->toggleViewAction());
|
||||
return DockWidget;
|
||||
}
|
||||
#endif
|
||||
|
||||
};
|
||||
|
||||
//============================================================================
|
||||
void MainWindowPrivate::createContent()
|
||||
{
|
||||
// Test container docking
|
||||
QMenu* ViewMenu = ui.menuView;
|
||||
auto DockWidget = createCalendarDockWidget(ViewMenu);
|
||||
auto DockWidget = createCalendarDockWidget();
|
||||
DockWidget->setFeature(ads::CDockWidget::DockWidgetClosable, false);
|
||||
auto SpecialDockArea = DockManager->addDockWidget(ads::LeftDockWidgetArea, DockWidget);
|
||||
|
||||
@@ -360,19 +383,16 @@ void MainWindowPrivate::createContent()
|
||||
//SpecialDockArea->setAllowedAreas({ads::LeftDockWidgetArea, ads::RightDockWidgetArea}); // just for testing
|
||||
}
|
||||
|
||||
DockManager->addDockWidget(ads::LeftDockWidgetArea, createLongTextLabelDockWidget(ViewMenu));
|
||||
auto FileSystemWidget = createFileSystemTreeDockWidget(ViewMenu);
|
||||
auto ToolBar = FileSystemWidget->createDefaultToolBar();
|
||||
ToolBar->addAction(ui.actionSaveState);
|
||||
ToolBar->addAction(ui.actionRestoreState);
|
||||
DockWidget = createLongTextLabelDockWidget();
|
||||
WindowTitleTestDockWidget = DockWidget;
|
||||
DockWidget->setFeature(ads::CDockWidget::DockWidgetFocusable, false);
|
||||
DockManager->addDockWidget(ads::LeftDockWidgetArea, DockWidget);
|
||||
auto FileSystemWidget = createFileSystemTreeDockWidget();
|
||||
FileSystemWidget->setFeature(ads::CDockWidget::DockWidgetFloatable, false);
|
||||
appendFeaturStringToWindowTitle(FileSystemWidget);
|
||||
DockManager->addDockWidget(ads::BottomDockWidgetArea, FileSystemWidget);
|
||||
|
||||
FileSystemWidget = createFileSystemTreeDockWidget(ViewMenu);
|
||||
ToolBar = FileSystemWidget->createDefaultToolBar();
|
||||
ToolBar->addAction(ui.actionSaveState);
|
||||
ToolBar->addAction(ui.actionRestoreState);
|
||||
FileSystemWidget = createFileSystemTreeDockWidget();
|
||||
FileSystemWidget->setFeature(ads::CDockWidget::DockWidgetMovable, false);
|
||||
FileSystemWidget->setFeature(ads::CDockWidget::DockWidgetFloatable, false);
|
||||
appendFeaturStringToWindowTitle(FileSystemWidget);
|
||||
@@ -380,11 +400,14 @@ void MainWindowPrivate::createContent()
|
||||
// Test custom factory - we inject a help button into the title bar
|
||||
ads::CDockComponentsFactory::setFactory(new CCustomComponentsFactory());
|
||||
auto TopDockArea = DockManager->addDockWidget(ads::TopDockWidgetArea, FileSystemWidget);
|
||||
// Uncomment the next line if you would like to test the
|
||||
// HideSingleWidgetTitleBar functionality
|
||||
// TopDockArea->setDockAreaFlag(ads::CDockAreaWidget::HideSingleWidgetTitleBar, true);
|
||||
ads::CDockComponentsFactory::resetDefaultFactory();
|
||||
|
||||
// We create a calendar widget and clear all flags to prevent the dock area
|
||||
// from closing
|
||||
DockWidget = createCalendarDockWidget(ViewMenu);
|
||||
DockWidget = createCalendarDockWidget();
|
||||
DockWidget->setTabToolTip(QString("Tab ToolTip\nHodie est dies magna"));
|
||||
auto DockArea = DockManager->addDockWidget(ads::CenterDockWidgetArea, DockWidget, TopDockArea);
|
||||
|
||||
@@ -400,18 +423,18 @@ void MainWindowPrivate::createContent()
|
||||
TitleBar->insertWidget(Index + 1, CustomButton);
|
||||
QObject::connect(CustomButton, &QToolButton::clicked, [=]()
|
||||
{
|
||||
auto DockWidget = createEditorWidget(ui.menuView);
|
||||
auto DockWidget = createEditorWidget();
|
||||
DockWidget->setFeature(ads::CDockWidget::DockWidgetDeleteOnClose, true);
|
||||
DockManager->addDockWidgetTabToArea(DockWidget, DockArea);
|
||||
_this->connect(DockWidget, SIGNAL(closeRequested()), SLOT(onEditorCloseRequested()));
|
||||
});
|
||||
|
||||
// Test dock area docking
|
||||
auto RighDockArea = DockManager->addDockWidget(ads::RightDockWidgetArea, createLongTextLabelDockWidget(ViewMenu), TopDockArea);
|
||||
DockManager->addDockWidget(ads::TopDockWidgetArea, createLongTextLabelDockWidget(ViewMenu), RighDockArea);
|
||||
auto BottomDockArea = DockManager->addDockWidget(ads::BottomDockWidgetArea, createLongTextLabelDockWidget(ViewMenu), RighDockArea);
|
||||
DockManager->addDockWidget(ads::CenterDockWidgetArea, createLongTextLabelDockWidget(ViewMenu), RighDockArea);
|
||||
DockManager->addDockWidget(ads::CenterDockWidgetArea, createLongTextLabelDockWidget(ViewMenu), BottomDockArea);
|
||||
auto RighDockArea = DockManager->addDockWidget(ads::RightDockWidgetArea, createLongTextLabelDockWidget(), TopDockArea);
|
||||
DockManager->addDockWidget(ads::TopDockWidgetArea, createLongTextLabelDockWidget(), RighDockArea);
|
||||
auto BottomDockArea = DockManager->addDockWidget(ads::BottomDockWidgetArea, createLongTextLabelDockWidget(), RighDockArea);
|
||||
DockManager->addDockWidget(ads::CenterDockWidgetArea, createLongTextLabelDockWidget(), RighDockArea);
|
||||
DockManager->addDockWidget(ads::CenterDockWidgetArea, createLongTextLabelDockWidget(), BottomDockArea);
|
||||
|
||||
auto Action = ui.menuTests->addAction(QString("Set %1 Floating").arg(DockWidget->windowTitle()));
|
||||
DockWidget->connect(Action, SIGNAL(triggered()), SLOT(setFloating()));
|
||||
@@ -421,9 +444,9 @@ void MainWindowPrivate::createContent()
|
||||
DockWidget->connect(Action, SIGNAL(triggered()), SLOT(raise()));
|
||||
|
||||
#ifdef Q_OS_WIN
|
||||
if (!DockManager->configFlags().testFlag(ads::CDockManager::OpaqueUndocking))
|
||||
if (!ads::CDockManager::testConfigFlag(ads::CDockManager::OpaqueUndocking))
|
||||
{
|
||||
DockManager->addDockWidget(ads::CenterDockWidgetArea, createActiveXWidget(ViewMenu), RighDockArea);
|
||||
DockManager->addDockWidget(ads::CenterDockWidgetArea, createActiveXWidget(), RighDockArea);
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -456,13 +479,21 @@ void MainWindowPrivate::createActions()
|
||||
ui.toolBar->addAction(PerspectiveListAction);
|
||||
ui.toolBar->addAction(SavePerspectiveAction);
|
||||
|
||||
QAction* a = ui.toolBar->addAction("Create Editor");
|
||||
QAction* a = ui.toolBar->addAction("Create Floating Editor");
|
||||
a->setProperty("Floating", true);
|
||||
a->setToolTip("Creates floating dynamic dockable editor windows that are deleted on close");
|
||||
a->setIcon(svgIcon(":/adsdemo/images/note_add.svg"));
|
||||
_this->connect(a, SIGNAL(triggered()), SLOT(createEditor()));
|
||||
ui.menuTests->addAction(a);
|
||||
|
||||
a = ui.toolBar->addAction("Create Table");
|
||||
a = ui.toolBar->addAction("Create Docked Editor");
|
||||
a->setProperty("Floating", false);
|
||||
a->setToolTip("Creates a docked editor windows that are deleted on close");
|
||||
a->setIcon(svgIcon(":/adsdemo/images/docked_editor.svg"));
|
||||
_this->connect(a, SIGNAL(triggered()), SLOT(createEditor()));
|
||||
ui.menuTests->addAction(a);
|
||||
|
||||
a = ui.toolBar->addAction("Create Floating Table");
|
||||
a->setToolTip("Creates floating dynamic dockable table with millions of entries");
|
||||
a->setIcon(svgIcon(":/adsdemo/images/grid_on.svg"));
|
||||
_this->connect(a, SIGNAL(triggered()), SLOT(createTable()));
|
||||
@@ -471,6 +502,9 @@ void MainWindowPrivate::createActions()
|
||||
ui.menuTests->addSeparator();
|
||||
a = ui.menuTests->addAction("Show Status Dialog");
|
||||
_this->connect(a, SIGNAL(triggered()), SLOT(showStatusDialog()));
|
||||
|
||||
a = ui.menuTests->addAction("Toggle Label 0 Window Title");
|
||||
_this->connect(a, SIGNAL(triggered()), SLOT(toggleDockWidgetWindowTitle()));
|
||||
ui.menuTests->addSeparator();
|
||||
}
|
||||
|
||||
@@ -563,6 +597,14 @@ CMainWindow::CMainWindow(QWidget *parent) :
|
||||
// dock widget.
|
||||
// CDockManager::setConfigFlag(CDockManager::HideSingleCentralWidgetTitleBar, true);
|
||||
|
||||
// uncomment the following line to enable focus highlighting of the dock
|
||||
// widget that has the focus
|
||||
CDockManager::setConfigFlag(CDockManager::FocusHighlighting, true);
|
||||
|
||||
// uncomment if you would like to enable an equal distribution of the
|
||||
// available size of a splitter to all contained dock widgets
|
||||
// CDockManager::setConfigFlag(CDockManager::EqualSplitOnInsertion, true);
|
||||
|
||||
// Now create the dock manager and its content
|
||||
d->DockManager = new CDockManager(this);
|
||||
|
||||
@@ -593,6 +635,9 @@ CMainWindow::~CMainWindow()
|
||||
void CMainWindow::closeEvent(QCloseEvent* event)
|
||||
{
|
||||
d->saveState();
|
||||
// Delete dock manager here to delete all floating widgets. This ensures
|
||||
// that all top level windows of the dock manager are properly closed
|
||||
d->DockManager->deleteLater();
|
||||
QMainWindow::closeEvent(event);
|
||||
}
|
||||
|
||||
@@ -648,24 +693,47 @@ void CMainWindow::onViewToggled(bool Open)
|
||||
//============================================================================
|
||||
void CMainWindow::onViewVisibilityChanged(bool Visible)
|
||||
{
|
||||
Q_UNUSED(Visible);
|
||||
auto DockWidget = qobject_cast<ads::CDockWidget*>(sender());
|
||||
if (!DockWidget)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
qDebug() << DockWidget->objectName() << " visibilityChanged(" << Visible << ")";
|
||||
//qDebug() << DockWidget->objectName() << " visibilityChanged(" << Visible << ")";
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CMainWindow::createEditor()
|
||||
{
|
||||
auto DockWidget = createEditorWidget(d->ui.menuView);
|
||||
QObject* Sender = sender();
|
||||
QVariant vFloating = Sender->property("Floating");
|
||||
bool Floating = vFloating.isValid() ? vFloating.toBool() : true;
|
||||
auto DockWidget = d->createEditorWidget();
|
||||
DockWidget->setFeature(ads::CDockWidget::DockWidgetDeleteOnClose, true);
|
||||
auto FloatingWidget = d->DockManager->addDockWidgetFloating(DockWidget);
|
||||
FloatingWidget->move(QPoint(20, 20));
|
||||
DockWidget->setFeature(ads::CDockWidget::DockWidgetForceCloseWithArea, true);
|
||||
connect(DockWidget, SIGNAL(closeRequested()), SLOT(onEditorCloseRequested()));
|
||||
|
||||
if (Floating)
|
||||
{
|
||||
auto FloatingWidget = d->DockManager->addDockWidgetFloating(DockWidget);
|
||||
FloatingWidget->move(QPoint(20, 20));
|
||||
}
|
||||
else
|
||||
{
|
||||
ads::CDockAreaWidget* EditorArea = d->LastDockedEditor ? d->LastDockedEditor->dockAreaWidget() : nullptr;
|
||||
if (EditorArea)
|
||||
{
|
||||
d->DockManager->setConfigFlag(ads::CDockManager::EqualSplitOnInsertion, true);
|
||||
d->DockManager->addDockWidget(ads::RightDockWidgetArea, DockWidget, EditorArea);
|
||||
}
|
||||
else
|
||||
{
|
||||
d->DockManager->addDockWidget(ads::TopDockWidgetArea, DockWidget);
|
||||
}
|
||||
d->LastDockedEditor = DockWidget;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -686,7 +754,7 @@ void CMainWindow::onEditorCloseRequested()
|
||||
//============================================================================
|
||||
void CMainWindow::createTable()
|
||||
{
|
||||
auto DockWidget = createTableWidget(d->ui.menuView);
|
||||
auto DockWidget = d->createTableWidget();
|
||||
DockWidget->setFeature(ads::CDockWidget::DockWidgetDeleteOnClose, true);
|
||||
auto FloatingWidget = d->DockManager->addDockWidgetFloating(DockWidget);
|
||||
FloatingWidget->move(QPoint(40, 40));
|
||||
@@ -700,3 +768,20 @@ void CMainWindow::showStatusDialog()
|
||||
Dialog.exec();
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CMainWindow::toggleDockWidgetWindowTitle()
|
||||
{
|
||||
QString Title = d->WindowTitleTestDockWidget->windowTitle();
|
||||
int i = Title.indexOf(" (Test)");
|
||||
if (-1 == i)
|
||||
{
|
||||
Title += " (Test)";
|
||||
}
|
||||
else
|
||||
{
|
||||
Title = Title.left(i);
|
||||
}
|
||||
d->WindowTitleTestDockWidget->setWindowTitle(Title);
|
||||
}
|
||||
|
||||
|
||||
@@ -64,6 +64,7 @@ private slots:
|
||||
void createTable();
|
||||
void onEditorCloseRequested();
|
||||
void showStatusDialog();
|
||||
void toggleDockWidgetWindowTitle();
|
||||
};
|
||||
|
||||
#endif // MAINWINDOW_H
|
||||
|
||||
@@ -23,7 +23,7 @@ class CStatusDialog : public QDialog
|
||||
Q_OBJECT
|
||||
private:
|
||||
StatusDialogPrivate* d; ///< private data (pimpl)
|
||||
friend class StatusDialogPrivate;
|
||||
friend struct StatusDialogPrivate;
|
||||
|
||||
private slots:
|
||||
void on_dockWidgetsComboBox_currentIndexChanged(int index);
|
||||
|
||||
@@ -34,6 +34,7 @@ RESOURCES += demo.qrc
|
||||
|
||||
LIBS += -L$${ADS_OUT_ROOT}/lib
|
||||
|
||||
|
||||
# Dependency: AdvancedDockingSystem (shared)
|
||||
CONFIG(debug, debug|release){
|
||||
win32 {
|
||||
@@ -50,5 +51,10 @@ else{
|
||||
LIBS += -lqtadvanceddocking
|
||||
}
|
||||
|
||||
unix:!macx {
|
||||
LIBS += -lxcb
|
||||
QT += x11extras
|
||||
}
|
||||
|
||||
INCLUDEPATH += ../src
|
||||
DEPENDPATH += ../src
|
||||
|
||||
412
demo/demo.py
@@ -7,14 +7,14 @@ from PyQt5 import uic
|
||||
from PyQt5.QtCore import (QCoreApplication, QDir, Qt, QSettings, QSignalBlocker,
|
||||
QRect, QPoint, qDebug, qInstallMessageHandler,
|
||||
QtDebugMsg, QtInfoMsg, QtWarningMsg,
|
||||
QtCriticalMsg, QtFatalMsg)
|
||||
QtCriticalMsg, QtFatalMsg, QSize)
|
||||
from PyQt5.QtGui import (QGuiApplication, QIcon, QCloseEvent)
|
||||
from PyQt5.QtWidgets import (QCalendarWidget, QFileSystemModel, QFrame, QLabel,
|
||||
QMenu, QTreeView, QAction, QWidgetAction,
|
||||
QComboBox, QStyle, QSizePolicy, QInputDialog, QMenu,
|
||||
QToolButton, QWidget, QPlainTextEdit,
|
||||
QTableWidget, QTableWidgetItem, QApplication,
|
||||
QMessageBox)
|
||||
QMenu, QTreeView, QAction, QWidgetAction,
|
||||
QComboBox, QStyle, QSizePolicy, QInputDialog, QMenu,
|
||||
QToolButton, QWidget, QPlainTextEdit,
|
||||
QTableWidget, QTableWidgetItem, QApplication,
|
||||
QMessageBox)
|
||||
try:
|
||||
from PyQt5.QAxContainer import QAxWidget
|
||||
except ImportError:
|
||||
@@ -25,6 +25,7 @@ else:
|
||||
from PyQtAds import QtAds
|
||||
|
||||
import rc # pyrcc5 demo.qrc -o rc.py
|
||||
from status_dialog import CStatusDialog
|
||||
|
||||
UI_FILE = os.path.join(os.path.dirname(__file__), 'mainwindow.ui')
|
||||
MainWindowUI, MainWindowBase = uic.loadUiType(UI_FILE)
|
||||
@@ -47,7 +48,7 @@ def features_string(dock_widget: QtAds.CDockWidget) -> str:
|
||||
f = dock_widget.features()
|
||||
closable = f & QtAds.CDockWidget.DockWidgetClosable
|
||||
movable = f & QtAds.CDockWidget.DockWidgetMovable
|
||||
floatable = f &QtAds.CDockWidget.DockWidgetFloatable
|
||||
floatable = f & QtAds.CDockWidget.DockWidgetFloatable
|
||||
|
||||
return "c{} m{} f{}".format("+" if closable else "-",
|
||||
"+" if movable else "-",
|
||||
@@ -64,122 +65,21 @@ def append_feature_string_to_window_title(dock_widget: QtAds.CDockWidget):
|
||||
def svg_icon(filename: str):
|
||||
'''Helper function to create an SVG icon'''
|
||||
# This is a workaround, because because in item views SVG icons are not
|
||||
# properly scaled an look blurry or pixelate
|
||||
# properly scaled and look blurry or pixelate
|
||||
icon = QIcon(filename)
|
||||
icon.addPixmap(icon.pixmap(92))
|
||||
return icon
|
||||
|
||||
|
||||
class CMinSizeTableWidget(QTableWidget):
|
||||
"""Custom QTableWidget with a minimum size hint to test CDockWidget
|
||||
setMinimumSizeHintMode() function of CDockWidget"""
|
||||
|
||||
def minimumSizeHint(self) -> QSize:
|
||||
return QSize(300, 100)
|
||||
|
||||
def create_long_text_label_dock_widget(view_menu: QMenu) -> QtAds.CDockWidget:
|
||||
label = QLabel()
|
||||
label.setWordWrap(True)
|
||||
label.setAlignment(Qt.AlignTop | Qt.AlignLeft)
|
||||
label.setText('''\
|
||||
Label {} {} - Lorem ipsum dolor sit amet, consectetuer
|
||||
adipiscing elit. Aenean commodo ligula eget dolor. Aenean massa. Cum
|
||||
sociis natoque penatibus et magnis dis parturient montes, nascetur
|
||||
ridiculus mus. Donec quam felis, ultricies nec, pellentesque eu, pretium
|
||||
quis, sem. Nulla consequat massa quis enim. Donec pede justo, fringilla
|
||||
vel, aliquet nec, vulputate eget, arcu. In enim justo, rhoncus ut,
|
||||
imperdiet a, venenatis vitae, justo. Nullam dictum felis eu pede mollis
|
||||
pretium. Integer tincidunt. Cras dapibus. Vivamus elementum semper nisi.
|
||||
Aenean vulputate eleifend tellus. Aenean leo ligula, porttitor eu,
|
||||
consequat vitae, eleifend ac, enim. Aliquam lorem ante, dapibus in, viverra
|
||||
quis, feugiat a, tellus. Phasellus viverra nulla ut metus varius laoreet.
|
||||
'''.format(_State.label_count, datetime.datetime.now().strftime("%H:%M:%S:%f")))
|
||||
dock_widget = QtAds.CDockWidget("Label {}".format(_State.label_count))
|
||||
_State.label_count += 1
|
||||
dock_widget.setWidget(label)
|
||||
|
||||
view_menu.addAction(dock_widget.toggleViewAction())
|
||||
return dock_widget
|
||||
|
||||
|
||||
def create_calendar_dock_widget(view_menu: QMenu) -> QtAds.CDockWidget:
|
||||
widget = QCalendarWidget()
|
||||
|
||||
dock_widget = QtAds.CDockWidget("Calendar {}".format(_State.calendar_count))
|
||||
_State.calendar_count += 1
|
||||
dock_widget.setWidget(widget)
|
||||
dock_widget.setToggleViewActionMode(QtAds.CDockWidget.ActionModeShow)
|
||||
dock_widget.setIcon(svg_icon(":/adsdemo/images/date_range.svg"))
|
||||
view_menu.addAction(dock_widget.toggleViewAction())
|
||||
return dock_widget
|
||||
|
||||
|
||||
def create_file_system_tree_dock_widget(view_menu: QMenu) -> QtAds.CDockWidget:
|
||||
widget = QTreeView()
|
||||
widget.setFrameShape(QFrame.NoFrame)
|
||||
|
||||
m = QFileSystemModel(widget)
|
||||
m.setRootPath(QDir.currentPath())
|
||||
widget.setModel(m)
|
||||
|
||||
dock_widget = QtAds.CDockWidget("Filesystem {}".format(_State.file_system_count))
|
||||
_State.file_system_count += 1
|
||||
dock_widget.setWidget(widget)
|
||||
view_menu.addAction(dock_widget.toggleViewAction())
|
||||
return dock_widget
|
||||
|
||||
|
||||
def create_editor_widget(view_menu: QMenu) -> QtAds.CDockWidget:
|
||||
widget = QPlainTextEdit()
|
||||
widget.setPlaceholderText("This is an editor. If you close the editor, it will be "
|
||||
"deleted. Enter your text here.")
|
||||
widget.setStyleSheet("border: none")
|
||||
dock_widget = QtAds.CDockWidget("Editor {}".format(_State.editor_count))
|
||||
_State.editor_count += 1
|
||||
dock_widget.setWidget(widget)
|
||||
dock_widget.setIcon(svg_icon(":/adsdemo/images/edit.svg"))
|
||||
dock_widget.setFeature(QtAds.CDockWidget.CustomCloseHandling, True)
|
||||
view_menu.addAction(dock_widget.toggleViewAction())
|
||||
|
||||
options_menu = QMenu(dock_widget)
|
||||
options_menu.setTitle("Options")
|
||||
options_menu.setToolTip(options_menu.title())
|
||||
options_menu.setIcon(svg_icon(":/adsdemo/images/custom-menu-button.svg"))
|
||||
menu_action = options_menu.menuAction()
|
||||
# The object name of the action will be set for the QToolButton that
|
||||
# is created in the dock area title bar. You can use this name for CSS
|
||||
# styling
|
||||
menu_action.setObjectName("options_menu")
|
||||
dock_widget.setTitleBarActions([options_menu.menuAction()])
|
||||
a = options_menu.addAction("Clear Editor")
|
||||
a.triggered.connect(widget.clear)
|
||||
|
||||
return dock_widget
|
||||
|
||||
|
||||
def create_table_widget(view_menu: QMenu) -> QtAds.CDockWidget:
|
||||
widget = QTableWidget()
|
||||
dock_widget = QtAds.CDockWidget("Table {}".format(_State.table_count))
|
||||
_State.table_count += 1
|
||||
COLCOUNT = 5
|
||||
ROWCOUNT = 30
|
||||
widget.setColumnCount(COLCOUNT)
|
||||
widget.setRowCount(ROWCOUNT)
|
||||
for col in range(ROWCOUNT):
|
||||
widget.setHorizontalHeaderItem(col, QTableWidgetItem("Col {}".format(col+1)))
|
||||
for row in range(ROWCOUNT):
|
||||
widget.setItem(row, col, QTableWidgetItem("T {:}-{:}".format(row+1, col+1)))
|
||||
|
||||
dock_widget.setWidget(widget)
|
||||
dock_widget.setIcon(svg_icon(":/adsdemo/images/grid_on.svg"))
|
||||
view_menu.addAction(dock_widget.toggleViewAction())
|
||||
return dock_widget
|
||||
|
||||
|
||||
if ACTIVEX_AVAILABLE:
|
||||
def create_activex_widget(view_menu: QMenu, parent: QWidget = None) -> QtAds.CDockWidget:
|
||||
widget = QAxWidget("{6bf52a52-394a-11d3-b153-00c04f79faa6}", parent)
|
||||
dock_widget = QtAds.CDockWidget("Active X {}".format(_State.activex_count))
|
||||
_State.activex_count += 1
|
||||
dock_widget.setWidget(widget)
|
||||
view_menu.addAction(dock_widget.toggleViewAction())
|
||||
return dock_widget
|
||||
|
||||
|
||||
class CustomComponentsFactory(QtAds.CDockComponentsFactory):
|
||||
class CCustomComponentsFactory(QtAds.CDockComponentsFactory):
|
||||
|
||||
def createDockAreaTitleBar(self, dock_area: QtAds.CDockAreaWidget) -> QtAds.CDockAreaTitleBar:
|
||||
title_bar = QtAds.CDockAreaTitleBar(dock_area)
|
||||
@@ -192,7 +92,6 @@ class CustomComponentsFactory(QtAds.CDockComponentsFactory):
|
||||
return title_bar
|
||||
|
||||
|
||||
|
||||
class MainWindow(MainWindowUI, MainWindowBase):
|
||||
save_perspective_action: QAction
|
||||
perspective_list_action: QWidgetAction
|
||||
@@ -205,6 +104,8 @@ class MainWindow(MainWindowUI, MainWindowBase):
|
||||
self.perspective_list_action = None
|
||||
self.perspective_combo_box = None
|
||||
self.dock_manager = None
|
||||
self.window_title_test_dock_widget = None
|
||||
self.last_docked_editor = None
|
||||
|
||||
self.setupUi(self)
|
||||
self.create_actions()
|
||||
@@ -213,13 +114,47 @@ class MainWindow(MainWindowUI, MainWindowBase):
|
||||
# a QToolButton instead of a QPushButton
|
||||
# QtAds.CDockManager.setConfigFlags(QtAds.CDockManager.configFlags() | QtAds.CDockManager.TabCloseButtonIsToolButton)
|
||||
|
||||
# uncomment the following line if you want to use opaque undocking and
|
||||
# opaque splitter resizing
|
||||
#QtAds.CDockManager.setConfigFlags(QtAds.CDockManager.DefaultOpaqueConfig)
|
||||
|
||||
# uncomment the following line if you want a fixed tab width that does
|
||||
# not change if the visibility of the close button changes
|
||||
# QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.RetainTabSizeWhenCloseButtonHidden, True)
|
||||
#QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.RetainTabSizeWhenCloseButtonHidden, True)
|
||||
|
||||
# uncomment the follwing line if you want to use non opaque undocking and splitter
|
||||
# movements
|
||||
# QtAds.CDockManager.setConfigFlags(QtAds.CDockManager.DefaultNonOpaqueConfig)
|
||||
# uncomment the following line if you don't want close button on DockArea's title bar
|
||||
#QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.DockAreaHasCloseButton, False)
|
||||
|
||||
# uncomment the following line if you don't want undock button on DockArea's title bar
|
||||
#QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.DockAreaHasUndockButton, False)
|
||||
|
||||
# uncomment the following line if you don't want tabs menu button on DockArea's title bar
|
||||
#QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.DockAreaHasTabsMenuButton, False)
|
||||
|
||||
# uncomment the following line if you don't want disabled buttons to appear on DockArea's title bar
|
||||
#QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.DockAreaHideDisabledButtons, True)
|
||||
|
||||
# uncomment the following line if you want to show tabs menu button on DockArea's title bar only when there are more than one tab and at least of them has elided title
|
||||
#QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.DockAreaDynamicTabsMenuButtonVisibility, True)
|
||||
|
||||
# uncomment the following line if you want floating container to always show application title instead of active dock widget's title
|
||||
#QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.FloatingContainerHasWidgetTitle, False)
|
||||
|
||||
# uncomment the following line if you want floating container to show active dock widget's icon instead of always showing application icon
|
||||
#QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.FloatingContainerHasWidgetIcon, True)
|
||||
|
||||
# uncomment the following line if you want a central widget in the main dock container (the dock manager) without a titlebar
|
||||
# If you enable this code, you can test it in the demo with the Calendar 0
|
||||
# dock widget.
|
||||
#QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.HideSingleCentralWidgetTitleBar, True)
|
||||
|
||||
# uncomment the following line to enable focus highlighting of the dock
|
||||
# widget that has the focus
|
||||
QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.FocusHighlighting, True)
|
||||
|
||||
# uncomment if you would like to enable an equal distribution of the
|
||||
# available size of a splitter to all contained dock widgets
|
||||
# QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.EqualSplitOnInsertion, True)
|
||||
|
||||
# Now create the dock manager and its content
|
||||
self.dock_manager = QtAds.CDockManager(self)
|
||||
@@ -242,19 +177,19 @@ class MainWindow(MainWindowUI, MainWindowBase):
|
||||
|
||||
def create_content(self):
|
||||
# Test container docking
|
||||
view_menu = self.menuView
|
||||
dock_widget = create_calendar_dock_widget(view_menu)
|
||||
dock_widget = self.create_calendar_dock_widget()
|
||||
dock_widget.setFeature(QtAds.CDockWidget.DockWidgetClosable, False)
|
||||
dock_widget.setFeature(QtAds.CDockWidget.DockWidgetMovable, False)
|
||||
dock_widget.setFeature(QtAds.CDockWidget.DockWidgetFloatable, False)
|
||||
special_dock_area = self.dock_manager.addDockWidget(QtAds.LeftDockWidgetArea, dock_widget)
|
||||
|
||||
# For this Special Dock Area we want to avoid dropping on the center of it (i.e. we don't want this widget to be ever tabbified):
|
||||
special_dock_area.setAllowedAreas(QtAds.OuterDockAreas)
|
||||
# special_dock_area.setAllowedAreas(QtAds.LeftDockWidgetArea | QtAds.RightDockWidgetArea) # just for testing
|
||||
|
||||
self.dock_manager.addDockWidget(QtAds.LeftDockWidgetArea, create_long_text_label_dock_widget(view_menu))
|
||||
file_system_widget = create_file_system_tree_dock_widget(view_menu)
|
||||
dock_widget = self.create_long_text_label_dock_widget()
|
||||
self.window_title_test_dock_widget = dock_widget
|
||||
dock_widget.setFeature(QtAds.CDockWidget.DockWidgetFocusable, False)
|
||||
self.dock_manager.addDockWidget(QtAds.LeftDockWidgetArea, dock_widget)
|
||||
file_system_widget = self.create_file_system_tree_dock_widget()
|
||||
tool_bar = file_system_widget.createDefaultToolBar()
|
||||
tool_bar.addAction(self.actionSaveState)
|
||||
tool_bar.addAction(self.actionRestoreState)
|
||||
@@ -262,27 +197,22 @@ class MainWindow(MainWindowUI, MainWindowBase):
|
||||
append_feature_string_to_window_title(file_system_widget)
|
||||
self.dock_manager.addDockWidget(QtAds.BottomDockWidgetArea, file_system_widget)
|
||||
|
||||
file_system_widget = create_file_system_tree_dock_widget(view_menu)
|
||||
tool_bar = file_system_widget.createDefaultToolBar()
|
||||
tool_bar.addAction(self.actionSaveState)
|
||||
tool_bar.addAction(self.actionRestoreState)
|
||||
file_system_widget = self.create_file_system_tree_dock_widget()
|
||||
file_system_widget.setFeature(QtAds.CDockWidget.DockWidgetMovable, False)
|
||||
file_system_widget.setFeature(QtAds.CDockWidget.DockWidgetFloatable, False)
|
||||
append_feature_string_to_window_title(file_system_widget)
|
||||
|
||||
# Test custom factory - we inject a help button into the title bar
|
||||
self.factory = CustomComponentsFactory()
|
||||
QtAds.CDockComponentsFactory.setFactory(self.factory)
|
||||
QtAds.CDockComponentsFactory.setFactory(CCustomComponentsFactory())
|
||||
top_dock_area = self.dock_manager.addDockWidget(QtAds.TopDockWidgetArea, file_system_widget)
|
||||
# Uncomment the next line if you would like to test the
|
||||
# HideSingleWidgetTitleBar functionality
|
||||
# top_dock_area.setDockAreaFlag(QtAds.CDockAreaWidget.HideSingleWidgetTitleBar, True)
|
||||
QtAds.CDockComponentsFactory.resetDefaultFactory()
|
||||
|
||||
|
||||
# We create a calendar widget and clear all flags to prevent the dock area
|
||||
# from closing
|
||||
dock_widget = create_calendar_dock_widget(view_menu)
|
||||
dock_widget.setFeature(QtAds.CDockWidget.DockWidgetClosable, False)
|
||||
dock_widget.setFeature(QtAds.CDockWidget.DockWidgetMovable, False)
|
||||
dock_widget.setFeature(QtAds.CDockWidget.DockWidgetFloatable, False)
|
||||
dock_widget = self.create_calendar_dock_widget()
|
||||
dock_widget.setTabToolTip("Tab ToolTip\nHodie est dies magna")
|
||||
dock_area = self.dock_manager.addDockWidget(QtAds.CenterDockWidgetArea, dock_widget, top_dock_area)
|
||||
|
||||
@@ -292,11 +222,12 @@ class MainWindow(MainWindowUI, MainWindowBase):
|
||||
custom_button.setToolTip("Create Editor")
|
||||
custom_button.setIcon(svg_icon(":/adsdemo/images/plus.svg"))
|
||||
custom_button.setAutoRaise(True)
|
||||
|
||||
title_bar = dock_area.titleBar()
|
||||
index = title_bar.indexOf(title_bar.tabBar())
|
||||
title_bar.insertWidget(index + 1, custom_button)
|
||||
def on_button_clicked():
|
||||
dock_widget = create_editor_widget(self.menuView)
|
||||
dock_widget = self.create_editor_widget()
|
||||
dock_widget.setFeature(QtAds.CDockWidget.DockWidgetDeleteOnClose, True)
|
||||
self.dock_manager.addDockWidgetTabToArea(dock_widget, dock_area)
|
||||
dock_widget.closeRequested.connect(self.on_editor_close_requested)
|
||||
@@ -305,30 +236,35 @@ class MainWindow(MainWindowUI, MainWindowBase):
|
||||
# Test dock area docking
|
||||
right_dock_area = self.dock_manager.addDockWidget(
|
||||
QtAds.RightDockWidgetArea,
|
||||
create_long_text_label_dock_widget(view_menu), top_dock_area)
|
||||
self.create_long_text_label_dock_widget(), top_dock_area)
|
||||
self.dock_manager.addDockWidget(
|
||||
QtAds.TopDockWidgetArea,
|
||||
create_long_text_label_dock_widget(view_menu), right_dock_area)
|
||||
|
||||
self.create_long_text_label_dock_widget(), right_dock_area)
|
||||
|
||||
bottom_dock_area = self.dock_manager.addDockWidget(
|
||||
QtAds.BottomDockWidgetArea,
|
||||
create_long_text_label_dock_widget(view_menu), right_dock_area)
|
||||
self.create_long_text_label_dock_widget(), right_dock_area)
|
||||
|
||||
self.dock_manager.addDockWidget(
|
||||
QtAds.CenterDockWidgetArea,
|
||||
create_long_text_label_dock_widget(view_menu), right_dock_area)
|
||||
self.create_long_text_label_dock_widget(), right_dock_area)
|
||||
self.dock_manager.addDockWidget(
|
||||
QtAds.CenterDockWidgetArea,
|
||||
create_long_text_label_dock_widget(view_menu), bottom_dock_area)
|
||||
|
||||
action = self.menuView.addAction("Set {} floating".format(dock_widget.windowTitle()))
|
||||
self.create_long_text_label_dock_widget(), bottom_dock_area)
|
||||
|
||||
|
||||
action = self.menuTests.addAction("Set {} Floating".format(dock_widget.windowTitle()))
|
||||
action.triggered.connect(dock_widget.setFloating)
|
||||
action = self.menuTests.addAction("Set {} As Current Tab".format(dock_widget.windowTitle()))
|
||||
action.triggered.connect(dock_widget.setAsCurrentTab)
|
||||
action = self.menuTests.addAction("Raise {}".format(dock_widget.windowTitle()))
|
||||
action.triggered.connect(dock_widget.raise_)
|
||||
|
||||
if ACTIVEX_AVAILABLE:
|
||||
flags = self.dock_manager.configFlags()
|
||||
if flags & QtAds.CDockManager.OpaqueUndocking:
|
||||
self.dock_manager.addDockWidget(QtAds.CenterDockWidgetArea,
|
||||
create_activex_widget(view_menu), right_dock_area)
|
||||
self.create_activex_widget(), right_dock_area)
|
||||
|
||||
for dock_widget in self.dock_manager.dockWidgetsMap().values():
|
||||
dock_widget.viewToggled.connect(self.on_view_toggled)
|
||||
@@ -353,25 +289,41 @@ class MainWindow(MainWindowUI, MainWindowBase):
|
||||
self.toolBar.addAction(self.perspective_list_action)
|
||||
self.toolBar.addAction(self.save_perspective_action)
|
||||
|
||||
a = self.toolBar.addAction("Create Editor")
|
||||
a = self.toolBar.addAction("Create Floating Editor")
|
||||
a.setProperty("Floating", True)
|
||||
a.setToolTip("Creates floating dynamic dockable editor windows that are deleted on close")
|
||||
a.setIcon(svg_icon(":/adsdemo/images/note_add.svg"))
|
||||
a.triggered.connect(self.create_editor)
|
||||
self.menuTests.addAction(a)
|
||||
|
||||
a = self.toolBar.addAction("Create Docked Editor")
|
||||
a.setProperty("Floating", False)
|
||||
a.setToolTip("Creates a docked editor windows that are deleted on close")
|
||||
a.setIcon(svg_icon(":/adsdemo/images/docked_editor.svg"))
|
||||
a.triggered.connect(self.create_editor)
|
||||
self.menuTests.addAction(a)
|
||||
|
||||
a = self.toolBar.addAction("Create Table")
|
||||
a = self.toolBar.addAction("Create Floating Table")
|
||||
a.setToolTip("Creates floating dynamic dockable table with millions of entries")
|
||||
a.setIcon(svg_icon(":/adsdemo/images/grid_on.svg"))
|
||||
a.triggered.connect(self.create_table)
|
||||
self.menuTests.addAction(a)
|
||||
|
||||
self.menuTests.addSeparator()
|
||||
a = self.menuTests.addAction("Show Status Dialog")
|
||||
a.triggered.connect(self.show_status_dialog)
|
||||
self.menuTests.addSeparator()
|
||||
|
||||
def closeEvent(self, event: QCloseEvent):
|
||||
self.save_state()
|
||||
self.dock_manager.deleteLater()
|
||||
super().closeEvent(event)
|
||||
|
||||
def on_action_save_state_triggered(state: bool):
|
||||
def on_actionSaveState_triggered(self, state: bool):
|
||||
qDebug("MainWindow::on_action_save_state_triggered")
|
||||
self.save_state()
|
||||
|
||||
def on_action_restore_state_triggered(state: bool):
|
||||
def on_actionRestoreState_triggered(self, state: bool):
|
||||
qDebug("MainWindow::on_action_restore_state_triggered")
|
||||
self.restore_state()
|
||||
|
||||
@@ -400,14 +352,26 @@ class MainWindow(MainWindowUI, MainWindowBase):
|
||||
if dock_widget is None:
|
||||
return
|
||||
|
||||
qDebug("{} visibility_changed({})".format(dock_widget.objectName(), visible))
|
||||
# qDebug("{} visibility_changed({})".format(dock_widget.objectName(), visible))
|
||||
|
||||
def create_editor(self):
|
||||
dock_widget = create_editor_widget(self.menuView)
|
||||
sender = self.sender()
|
||||
floating = sender.property("Floating")
|
||||
dock_widget = self.create_editor_widget()
|
||||
dock_widget.setFeature(QtAds.CDockWidget.DockWidgetDeleteOnClose, True)
|
||||
floating_widget = self.dock_manager.addDockWidgetFloating(dock_widget)
|
||||
floating_widget.move(QPoint(20, 20))
|
||||
dock_widget.closeRequested.connect(self.on_editor_close_requested)
|
||||
|
||||
if floating:
|
||||
floating_widget = self.dock_manager.addDockWidgetFloating(dock_widget)
|
||||
floating_widget.move(QPoint(20, 20))
|
||||
else:
|
||||
editor_area = self.last_docked_editor.dockAreaWidget() if self.last_docked_editor is not None else None
|
||||
if editor_area is not None:
|
||||
self.dock_manager.setConfigFlag(QtAds.CDockManager.EqualSplitOnInsertion, True)
|
||||
self.dock_manager.addDockWidget(QtAds.RightDockWidgetArea, dock_widget, editor_area)
|
||||
else:
|
||||
self.dock_manager.addDockWidget(QtAds.TopDockWidgetArea, dock_widget)
|
||||
self.last_docked_editor = dock_widget
|
||||
|
||||
def on_editor_close_requested(self):
|
||||
dock_widget = self.sender()
|
||||
@@ -417,10 +381,24 @@ class MainWindow(MainWindowUI, MainWindowBase):
|
||||
dock_widget.closeDockWidget()
|
||||
|
||||
def create_table(self):
|
||||
dock_widget = create_table_widget(self.menuView)
|
||||
dock_widget = self.create_table_widget()
|
||||
dock_widget.setFeature(QtAds.CDockWidget.DockWidgetDeleteOnClose, True)
|
||||
floating_widget = self.dock_manager.addDockWidgetFloating(dock_widget)
|
||||
floating_widget.move(QPoint(40, 40))
|
||||
|
||||
def show_status_dialog(self):
|
||||
dialog = CStatusDialog(self.dock_manager)
|
||||
dialog.exec_()
|
||||
|
||||
|
||||
def toggle_dock_widget_window_title(self):
|
||||
title = self.window_title_test_dock_widget.windowTitle()
|
||||
i = title.find(" (Test) ")
|
||||
if i == -1:
|
||||
title += " (Test) "
|
||||
else:
|
||||
title = title[i]
|
||||
self.window_title_test_dock_widget.setWindowTitle(title)
|
||||
|
||||
def save_state(self):
|
||||
'''
|
||||
@@ -474,6 +452,124 @@ class MainWindow(MainWindowUI, MainWindowBase):
|
||||
self.perspective_combo_box.setCurrentText(perspective_name)
|
||||
self.save_perspectives()
|
||||
|
||||
def create_long_text_label_dock_widget(self) -> QtAds.CDockWidget:
|
||||
label = QLabel()
|
||||
label.setWordWrap(True)
|
||||
label.setAlignment(Qt.AlignTop | Qt.AlignLeft)
|
||||
label.setText('''Label {} {} - Lorem ipsum dolor sit amet, consectetuer
|
||||
adipiscing elit. Aenean commodo ligula eget dolor. Aenean massa. Cum
|
||||
sociis natoque penatibus et magnis dis parturient montes, nascetur
|
||||
ridiculus mus. Donec quam felis, ultricies nec, pellentesque eu, pretium
|
||||
quis, sem. Nulla consequat massa quis enim. Donec pede justo, fringilla
|
||||
vel, aliquet nec, vulputate eget, arcu. In enim justo, rhoncus ut,
|
||||
imperdiet a, venenatis vitae, justo. Nullam dictum felis eu pede mollis
|
||||
pretium. Integer tincidunt. Cras dapibus. Vivamus elementum semper nisi.
|
||||
Aenean vulputate eleifend tellus. Aenean leo ligula, porttitor eu,
|
||||
consequat vitae, eleifend ac, enim. Aliquam lorem ante, dapibus in, viverra
|
||||
quis, feugiat a, tellus. Phasellus viverra nulla ut metus varius laoreet.
|
||||
'''.format(_State.label_count, datetime.datetime.now().strftime("%H:%M:%S:%f")))
|
||||
dock_widget = QtAds.CDockWidget("Label {}".format(_State.label_count))
|
||||
_State.label_count += 1
|
||||
dock_widget.setWidget(label)
|
||||
|
||||
self.menuView.addAction(dock_widget.toggleViewAction())
|
||||
return dock_widget
|
||||
|
||||
def create_calendar_dock_widget(self) -> QtAds.CDockWidget:
|
||||
widget = QCalendarWidget()
|
||||
|
||||
dock_widget = QtAds.CDockWidget("Calendar {}".format(_State.calendar_count))
|
||||
_State.calendar_count += 1
|
||||
# The following lines are for testing the setWidget() and takeWidget()
|
||||
# functionality
|
||||
dock_widget.setWidget(widget)
|
||||
dock_widget.setWidget(widget) # what happens if we set a widget if a widget is already set
|
||||
dock_widget.takeWidget() # we remove the widget
|
||||
dock_widget.setWidget(widget) # and set the widget again - there should be no error
|
||||
dock_widget.setToggleViewActionMode(QtAds.CDockWidget.ActionModeShow)
|
||||
dock_widget.setIcon(svg_icon(":/adsdemo/images/date_range.svg"))
|
||||
self.menuView.addAction(dock_widget.toggleViewAction())
|
||||
return dock_widget
|
||||
|
||||
def create_file_system_tree_dock_widget(self) -> QtAds.CDockWidget:
|
||||
widget = QTreeView()
|
||||
widget.setFrameShape(QFrame.NoFrame)
|
||||
|
||||
m = QFileSystemModel(widget)
|
||||
m.setRootPath(QDir.currentPath())
|
||||
widget.setModel(m)
|
||||
|
||||
dock_widget = QtAds.CDockWidget("Filesystem {}".format(_State.file_system_count))
|
||||
_State.file_system_count += 1
|
||||
dock_widget.setWidget(widget)
|
||||
self.menuView.addAction(dock_widget.toggleViewAction())
|
||||
return dock_widget
|
||||
|
||||
def create_editor_widget(self) -> QtAds.CDockWidget:
|
||||
widget = QPlainTextEdit()
|
||||
widget.setPlaceholderText("This is an editor. If you close the editor, it will be "
|
||||
"deleted. Enter your text here.")
|
||||
widget.setStyleSheet("border: none")
|
||||
dock_widget = QtAds.CDockWidget("Editor {}".format(_State.editor_count))
|
||||
_State.editor_count += 1
|
||||
dock_widget.setWidget(widget)
|
||||
dock_widget.setIcon(svg_icon(":/adsdemo/images/edit.svg"))
|
||||
dock_widget.setFeature(QtAds.CDockWidget.CustomCloseHandling, True)
|
||||
self.menuView.addAction(dock_widget.toggleViewAction())
|
||||
|
||||
options_menu = QMenu(dock_widget)
|
||||
options_menu.setTitle("Options")
|
||||
options_menu.setToolTip(options_menu.title())
|
||||
options_menu.setIcon(svg_icon(":/adsdemo/images/custom-menu-button.svg"))
|
||||
menu_action = options_menu.menuAction()
|
||||
# The object name of the action will be set for the QToolButton that
|
||||
# is created in the dock area title bar. You can use this name for CSS
|
||||
# styling
|
||||
menu_action.setObjectName("options_menu")
|
||||
dock_widget.setTitleBarActions([options_menu.menuAction()])
|
||||
a = options_menu.addAction("Clear Editor")
|
||||
a.triggered.connect(widget.clear)
|
||||
|
||||
return dock_widget
|
||||
|
||||
|
||||
def create_table_widget(self) -> QtAds.CDockWidget:
|
||||
widget = CMinSizeTableWidget()
|
||||
dock_widget = QtAds.CDockWidget("Table {}".format(_State.table_count))
|
||||
_State.table_count += 1
|
||||
COLCOUNT = 5
|
||||
ROWCOUNT = 30
|
||||
widget.setColumnCount(COLCOUNT)
|
||||
widget.setRowCount(ROWCOUNT)
|
||||
for col in range(ROWCOUNT):
|
||||
widget.setHorizontalHeaderItem(col, QTableWidgetItem("Col {}".format(col + 1)))
|
||||
for row in range(ROWCOUNT):
|
||||
widget.setItem(row, col, QTableWidgetItem("T {:}-{:}".format(row + 1, col + 1)))
|
||||
|
||||
dock_widget.setWidget(widget)
|
||||
dock_widget.setIcon(svg_icon(":/adsdemo/images/grid_on.svg"))
|
||||
dock_widget.setMinimumSizeHintMode(QtAds.CDockWidget.MinimumSizeHintFromContent)
|
||||
toolbar = dock_widget.createDefaultToolBar()
|
||||
action = toolbar.addAction(svg_icon(":/adsdemo/images/fullscreen.svg"), "Toggle Fullscreen")
|
||||
|
||||
def on_toggle_fullscreen():
|
||||
if dock_widget.isFullScreen():
|
||||
dock_widget.showNormal()
|
||||
else:
|
||||
dock_widget.showFullScreen()
|
||||
|
||||
action.triggered.connect(on_toggle_fullscreen)
|
||||
self.menuView.addAction(dock_widget.toggleViewAction())
|
||||
return dock_widget
|
||||
|
||||
def create_activex_widget(self, parent: QWidget = None) -> QtAds.CDockWidget:
|
||||
widget = QAxWidget("{6bf52a52-394a-11d3-b153-00c04f79faa6}", parent)
|
||||
dock_widget = QtAds.CDockWidget("Active X {}".format(_State.activex_count))
|
||||
_State.activex_count += 1
|
||||
dock_widget.setWidget(widget)
|
||||
self.menuView.addAction(dock_widget.toggleViewAction())
|
||||
return dock_widget
|
||||
|
||||
|
||||
def my_message_output(type, context, msg):
|
||||
if type == QtDebugMsg:
|
||||
|
||||
@@ -14,5 +14,8 @@
|
||||
<file>images/plus.svg</file>
|
||||
<file>images/help_outline.svg</file>
|
||||
<file>images/fullscreen.svg</file>
|
||||
<file>images/create_floating_editor.svg</file>
|
||||
<file>images/create_floating_table.svg</file>
|
||||
<file>images/docked_editor.svg</file>
|
||||
</qresource>
|
||||
</RCC>
|
||||
|
||||
80
demo/images/create_floating_editor.svg
Normal file
@@ -0,0 +1,80 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<svg
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
version="1.1"
|
||||
viewBox="0,0,1024,1024"
|
||||
id="svg2562"
|
||||
sodipodi:docname="create_floating_editor.svg"
|
||||
inkscape:version="0.92.4 (5da689c313, 2019-01-14)">
|
||||
<metadata
|
||||
id="metadata2568">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<defs
|
||||
id="defs2566" />
|
||||
<sodipodi:namedview
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1"
|
||||
objecttolerance="10"
|
||||
gridtolerance="10"
|
||||
guidetolerance="10"
|
||||
inkscape:pageopacity="0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:window-width="1920"
|
||||
inkscape:window-height="1017"
|
||||
id="namedview2564"
|
||||
showgrid="false"
|
||||
inkscape:zoom="0.23046875"
|
||||
inkscape:cx="512"
|
||||
inkscape:cy="512"
|
||||
inkscape:window-x="-8"
|
||||
inkscape:window-y="-8"
|
||||
inkscape:window-maximized="1"
|
||||
inkscape:current-layer="svg2562" />
|
||||
<desc
|
||||
id="desc2556">note_add icon - Licensed under Apache License v2.0 (http://www.apache.org/licenses/LICENSE-2.0) - Created with Iconfu.com - Derivative work of Material icons (Copyright Google Inc.)</desc>
|
||||
<g
|
||||
style="mix-blend-mode:normal;fill:#03b8e5;fill-rule:nonzero"
|
||||
id="g2560"
|
||||
transform="matrix(0.73242903,0,0,0.73242903,136.99634,136.99634)">
|
||||
<path
|
||||
d="m 853.33,341.33 v 512 c 0,46.93 -38.4,85.34 -85.33,85.34 H 255.57 c -46.93,0 -84.9,-38.41 -84.9,-85.34 l 0.42,-682.66 c 0,-46.93 37.98,-85.34 84.91,-85.34 h 341.33 z m -170.66,256 h -128 v -128 h -85.34 v 128 h -128 v 85.34 h 128 v 128 h 85.34 v -128 h 128 z M 789.33,384 554.67,149.33 V 384 Z"
|
||||
id="path2558"
|
||||
inkscape:connector-curvature="0" />
|
||||
</g>
|
||||
<path
|
||||
style="mix-blend-mode:normal;fill:#03b8e5;fill-rule:nonzero"
|
||||
d="M 426.6699,917.33988 512.4297,1024 597.3301,917.33988 Z"
|
||||
id="path3115"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
style="mix-blend-mode:normal;fill:#03b8e5;fill-rule:nonzero"
|
||||
d="M 426.6699,106.66012 512.4297,0 597.3301,106.66012 Z"
|
||||
id="path3115-7"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
style="mix-blend-mode:normal;fill:#03b8e5;fill-rule:nonzero"
|
||||
d="M 917.33988,426.6699 1024,512.4297 917.33988,597.3301 Z"
|
||||
id="path3115-7-9"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
style="mix-blend-mode:normal;fill:#03b8e5;fill-rule:nonzero"
|
||||
d="M 106.66016,426.6699 0,512.4297 106.66016,597.3301 Z"
|
||||
id="path3115-7-9-4"
|
||||
inkscape:connector-curvature="0" />
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 3.0 KiB |
80
demo/images/create_floating_table.svg
Normal file
@@ -0,0 +1,80 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<svg
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
version="1.1"
|
||||
viewBox="0,0,1024,1024"
|
||||
id="svg2562"
|
||||
sodipodi:docname="create_floating_table.svg"
|
||||
inkscape:version="0.92.4 (5da689c313, 2019-01-14)">
|
||||
<metadata
|
||||
id="metadata2568">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<defs
|
||||
id="defs2566" />
|
||||
<sodipodi:namedview
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1"
|
||||
objecttolerance="10"
|
||||
gridtolerance="10"
|
||||
guidetolerance="10"
|
||||
inkscape:pageopacity="0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:window-width="1920"
|
||||
inkscape:window-height="1017"
|
||||
id="namedview2564"
|
||||
showgrid="false"
|
||||
inkscape:zoom="0.23046875"
|
||||
inkscape:cx="512"
|
||||
inkscape:cy="512"
|
||||
inkscape:window-x="-8"
|
||||
inkscape:window-y="-8"
|
||||
inkscape:window-maximized="1"
|
||||
inkscape:current-layer="svg2562" />
|
||||
<desc
|
||||
id="desc2556">note_add icon - Licensed under Apache License v2.0 (http://www.apache.org/licenses/LICENSE-2.0) - Created with Iconfu.com - Derivative work of Material icons (Copyright Google Inc.)</desc>
|
||||
<path
|
||||
style="mix-blend-mode:normal;fill:#03b8e5;fill-rule:nonzero"
|
||||
d="M 426.6699,917.33988 512.4297,1024 597.3301,917.33988 Z"
|
||||
id="path3115"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
style="mix-blend-mode:normal;fill:#03b8e5;fill-rule:nonzero"
|
||||
d="M 426.6699,106.66012 512.4297,0 597.3301,106.66012 Z"
|
||||
id="path3115-7"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
style="mix-blend-mode:normal;fill:#03b8e5;fill-rule:nonzero"
|
||||
d="M 917.33988,426.6699 1024,512.4297 917.33988,597.3301 Z"
|
||||
id="path3115-7-9"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
style="mix-blend-mode:normal;fill:#03b8e5;fill-rule:nonzero"
|
||||
d="M 106.66016,426.6699 0,512.4297 106.66016,597.3301 Z"
|
||||
id="path3115-7-9-4"
|
||||
inkscape:connector-curvature="0" />
|
||||
<g
|
||||
id="g3198"
|
||||
style="mix-blend-mode:normal;fill:#03b8e5;fill-rule:nonzero"
|
||||
transform="matrix(0.73241615,0,0,0.73241615,137.00293,137.00293)">
|
||||
<path
|
||||
id="path3196"
|
||||
d="m 938.67,170.67 v 682.66 c 0,46.93 -38.41,85.34 -85.34,85.34 H 170.67 c -46.93,0 -85.34,-38.41 -85.34,-85.34 V 170.67 c 0,-46.93 38.41,-85.34 85.34,-85.34 h 682.66 c 46.93,0 85.34,38.41 85.34,85.34 z m -597.34,0 H 170.67 v 170.66 h 170.66 z m 0,512 H 170.67 v 170.66 h 170.66 z m 0,-256 H 170.67 v 170.66 h 170.66 z m 256,-256 H 426.67 v 170.66 h 170.66 z m 256,0 H 682.67 v 170.66 h 170.66 z m -256,512 H 426.67 v 170.66 h 170.66 z m 0,-256 H 426.67 v 170.66 h 170.66 z m 256,256 H 682.67 v 170.66 h 170.66 z m 0,-256 H 682.67 v 170.66 h 170.66 z"
|
||||
inkscape:connector-curvature="0" />
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 3.2 KiB |
6
demo/images/docked_editor.svg
Normal file
@@ -0,0 +1,6 @@
|
||||
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0,0,1024,1024">
|
||||
<desc>chrome_reader_mode icon - Licensed under Apache License v2.0 (http://www.apache.org/licenses/LICENSE-2.0) - Created with Iconfu.com - Derivative work of Material icons (Copyright Google Inc.)</desc>
|
||||
<g fill="#03b8e5" fill-rule="nonzero" style="mix-blend-mode: normal">
|
||||
<path d="M981.33,256v554.67c0,46.93 -38.4,85.33 -85.33,85.33h-768c-46.93,0 -85.33,-38.4 -85.33,-85.33v-554.67c0,-46.93 38.4,-85.33 85.33,-85.33h768c46.93,0 85.33,38.4 85.33,85.33zM896,256h-384v554.67h384zM554.67,512h298.66v64h-298.66zM554.67,405.33h298.66v64h-298.66zM554.67,618.67h298.66v64h-298.66z"/>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 717 B |
38
demo/status_dialog.py
Normal file
@@ -0,0 +1,38 @@
|
||||
import os
|
||||
import sys
|
||||
|
||||
from PyQt5 import uic
|
||||
from PyQtAds import QtAds
|
||||
|
||||
UI_FILE = os.path.join(os.path.dirname(__file__), 'StatusDialog.ui')
|
||||
StatusDialogUI, StatusDialogBase = uic.loadUiType(UI_FILE)
|
||||
|
||||
class CStatusDialog(StatusDialogUI, StatusDialogBase):
|
||||
|
||||
def __init__(self, dock_manager: QtAds.CDockManager, parent=None):
|
||||
super().__init__(parent)
|
||||
|
||||
self.setupUi(self)
|
||||
|
||||
self.dock_manager = dock_manager
|
||||
self.dock_widgets = self.dock_manager.dockWidgetsMap()
|
||||
|
||||
for key, widget in self.dock_widgets.items():
|
||||
self.dockWidgetsComboBox.addItem(key, widget)
|
||||
|
||||
def on_dockWidgetsComboBox_currentIndexChanged(self, index: int):
|
||||
if not isinstance(index, int):
|
||||
return
|
||||
if index < 0:
|
||||
return
|
||||
|
||||
dock_widget = self.dockWidgetsComboBox.currentData()
|
||||
self.isClosedCheckBox.setChecked(dock_widget.isClosed())
|
||||
self.isFloatingCheckBox.setChecked(dock_widget.isFloating())
|
||||
self.tabbedCheckBox.setChecked(dock_widget.isTabbed())
|
||||
self.isCurrentTabCheckBox.setChecked(dock_widget.isCurrentTab())
|
||||
self.closableCheckBox.setChecked(dock_widget.features() & QtAds.CDockWidget.DockWidgetClosable)
|
||||
self.movableCheckBox.setChecked(dock_widget.features() & QtAds.CDockWidget.DockWidgetMovable)
|
||||
self.floatableCheckBox.setChecked(dock_widget.features() & QtAds.CDockWidget.DockWidgetFloatable)
|
||||
self.deleteOnCloseCheckBox.setChecked(dock_widget.features() & QtAds.CDockWidget.DockWidgetDeleteOnClose)
|
||||
self.customCloseHandlingCheckBox.setChecked(dock_widget.features() & QtAds.CDockWidget.CustomCloseHandling)
|
||||
BIN
doc/central_widget.gif
Normal file
|
After Width: | Height: | Size: 572 KiB |
BIN
doc/cfg_flag_EqualSplitOnInsertion_false.png
Normal file
|
After Width: | Height: | Size: 5.2 KiB |
BIN
doc/cfg_flag_EqualSplitOnInsertion_true.png
Normal file
|
After Width: | Height: | Size: 5.1 KiB |
BIN
doc/cfg_flag_FloatingContainerForceNativeTitleBar_false.png
Normal file
|
After Width: | Height: | Size: 9.4 KiB |
BIN
doc/cfg_flag_FloatingContainerForceNativeTitleBar_true.png
Normal file
|
After Width: | Height: | Size: 9.3 KiB |
BIN
doc/cfg_flag_FocusHighlighting.gif
Normal file
|
After Width: | Height: | Size: 158 KiB |
BIN
doc/python_logo.png
Normal file
|
After Width: | Height: | Size: 35 KiB |
BIN
doc/showcase_d-tect-x.jpg
Normal file
|
After Width: | Height: | Size: 97 KiB |
BIN
doc/showcase_ezEngine_editor.png
Normal file
|
After Width: | Height: | Size: 385 KiB |
BIN
doc/showcase_hivewe.png
Normal file
|
After Width: | Height: | Size: 208 KiB |
|
Before Width: | Height: | Size: 539 KiB After Width: | Height: | Size: 539 KiB |
|
Before Width: | Height: | Size: 157 KiB After Width: | Height: | Size: 157 KiB |
|
Before Width: | Height: | Size: 98 KiB After Width: | Height: | Size: 98 KiB |
@@ -23,11 +23,19 @@
|
||||
- [`FloatingContainerHasWidgetTitle`](#floatingcontainerhaswidgettitle)
|
||||
- [`FloatingContainerHasWidgetIcon`](#floatingcontainerhaswidgeticon)
|
||||
- [`HideSingleCentralWidgetTitleBar`](#hidesinglecentralwidgettitlebar)
|
||||
- [`FocusHighlighting`](#focushighlighting)
|
||||
- [`EqualSplitOnInsertion`](#equalsplitoninsertion)
|
||||
- [`FloatingContainerForceNativeTitleBar` (Linux only)](#floatingcontainerforcenativetitlebar-linux-only)
|
||||
- [`FloatingContainerForceQWidgetTitleBar` (Linux only)](#floatingcontainerforceqwidgettitlebar-linux-only)
|
||||
- [Central Widget](#central-widget)
|
||||
- [Custom Close Handling](#custom-close-handling)
|
||||
- [Styling](#styling)
|
||||
- [Disabling the Internal Style Sheet](#disabling-the-internal-style-sheet)
|
||||
|
||||
## Configuration Flags
|
||||
|
||||
The Advanced Docking System has a number of global configuration options to
|
||||
configure the design and the functionality of the docking system. Each
|
||||
configure the design and the functionality of the docking system. Eachs
|
||||
configuration will be explained in detail in the following sections.
|
||||
|
||||
### Setting Configuration Flags
|
||||
@@ -282,7 +290,8 @@ otherwise (default setting) it displays application icon.
|
||||
|
||||
### `HideSingleCentralWidgetTitleBar`
|
||||
|
||||
If there is only one single visible dock widget in the main dock container (the dock manager) and if this flag is set, then the titlebar of this dock widget will be hidden.
|
||||
If there is only one single visible dock widget in the main dock container (the dock manager)
|
||||
and if this flag is set, then the titlebar of this dock widget will be hidden.
|
||||
This only makes sense for non draggable and non floatable dock widgets and enables
|
||||
the creation of some kind of "central" static widget. Because the titlebar is
|
||||
hidden, it is not possible to drag out the central widget to make it floating
|
||||
@@ -297,3 +306,219 @@ still has a titlebar to drag it out of the main window.
|
||||
|
||||

|
||||
|
||||
### `FocusHighlighting`
|
||||
|
||||
If this is enabled, the docking system is able to highlight the tab and the
|
||||
components of a dock area with a different style (i.e. a different color).
|
||||
This option is disabled by default and needs to be enabled explicitely
|
||||
because it adds some overhead. The dock manager needs to react on focus
|
||||
changes and dock widget dragging to highlight the right dock widget. You should
|
||||
enable it only, if you really need it for your application.
|
||||
|
||||
If the feature is enabled, you can also connect to the new dock manager
|
||||
signal `focusedDockWidgetChanged(CDockWidget* old, CDockWidget* now)` to
|
||||
react on focus changes and to prepare the content of the focused dock
|
||||
widget.
|
||||
|
||||
You can click into the tab, the titlebar or the content of a dock widget
|
||||
to focus it.
|
||||
|
||||

|
||||
|
||||
For the focused dock widget and dock widget tab, the property `focused` will
|
||||
be set to true and you can use this property to style the focused dock
|
||||
widget differently. The picture above uses the following styling:
|
||||
|
||||
```css
|
||||
/* Color the tab with the nhighlight color */
|
||||
ads--CDockWidgetTab[focused="true"]
|
||||
{
|
||||
background: palette(highlight);
|
||||
border-color: palette(highlight);
|
||||
}
|
||||
|
||||
/* Use a different colored close button icon to match the test color */
|
||||
ads--CDockWidgetTab[focused="true"] > #tabCloseButton
|
||||
{
|
||||
qproperty-icon: url(:/ads/images/close-button-focused.svg)
|
||||
}
|
||||
|
||||
/* Make a hovered focused close button a little bit lighter */
|
||||
ads--CDockWidgetTab[focused="true"] > #tabCloseButton:hover
|
||||
{
|
||||
background: rgba(255, 255, 255, 48);
|
||||
}
|
||||
|
||||
/* Make a pressed focused close button even more lighter */
|
||||
ads--CDockWidgetTab[focused="true"] > #tabCloseButton:pressed
|
||||
{
|
||||
background: rgba(255, 255, 255, 92);
|
||||
}
|
||||
|
||||
/* Use a different color for the tab label */
|
||||
ads--CDockWidgetTab[focused="true"] QLabel
|
||||
{
|
||||
color: palette(light);
|
||||
}
|
||||
|
||||
/* Paint a nice solid line for the whole title bar to create the illusion
|
||||
of an active tab */
|
||||
ads--CDockAreaWidget[focused="true"] ads--CDockAreaTitleBar
|
||||
{
|
||||
background: transparent;
|
||||
border-bottom: 2px solid palette(highlight);
|
||||
padding-bottom: 0px;
|
||||
}
|
||||
```
|
||||
|
||||
If you have a content widget that does not support focussing for some reason
|
||||
(like `QVTKOpenGLStereoWidget` from the [VTK library](https://github.com/Kitware/VTK)),
|
||||
then you can manually switch the focus by reacting on mouse events. The
|
||||
following code shows, how to install en event filter on the `QVTKOpenGLStereoWidget`
|
||||
to properly switch the focus on `QEvent::MouseButtonPress`:
|
||||
|
||||
```c++
|
||||
static ads::CDockWidget* createVTK2DWindow(QMenu* ViewMenu, QObject* EventFilter)
|
||||
{
|
||||
QVTKOpenGLStereoWidget* qvtkOpenGLStereoWidget = new QVTKOpenGLStereoWidget;
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget("2D Window");
|
||||
DockWidget->setWidget(qvtkOpenGLStereoWidget);
|
||||
qvtkOpenGLStereoWidget->installEventFilter(EventFilter);
|
||||
qvtkOpenGLStereoWidget->setProperty("DockWidget", QVariant::fromValue(DockWidget));
|
||||
return DockWidget;
|
||||
}
|
||||
```
|
||||
|
||||
Now we can use the event filter function to react on mouse events and then
|
||||
use the dock manager function `setDockWidgetFocused()` to switch the focus:
|
||||
|
||||
```c++
|
||||
bool CMainWindow::eventFilter(QObject *watched, QEvent *event)
|
||||
{
|
||||
if (event->type() == QEvent::MouseButtonPress)
|
||||
{
|
||||
QVTKOpenGLStereoWidget* vtkWidget = qobject_cast<QVTKOpenGLStereoWidget*>(watched);
|
||||
auto vDockWidget = vtkWidget->property("DockWidget");
|
||||
ads::CDockWidget* DockWidget = nullptr;
|
||||
if (vDockWidget.isValid())
|
||||
{
|
||||
DockWidget = qvariant_cast<ads::CDockWidget*>(vDockWidget);
|
||||
}
|
||||
|
||||
if (DockWidget)
|
||||
{
|
||||
d->DockManager->setDockWidgetFocused(DockWidget);
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
```
|
||||
|
||||
### `EqualSplitOnInsertion`
|
||||
|
||||
This flag configures how the space is distributed if a new dock widget is
|
||||
inserted into an existing dock area. The flag is disabled by default. If 3
|
||||
dock widgets are inserted with the following code
|
||||
|
||||
```c++
|
||||
d->DockManager->addDockWidget(ads::RightDockWidgetArea, DockWidget, EditorArea);
|
||||
```
|
||||
|
||||
then this is the result, if the flag is disabled:
|
||||
|
||||

|
||||
|
||||
If the flag is enabled, then the space is equally distributed to all widgets
|
||||
in a splitter:
|
||||
|
||||

|
||||
|
||||
|
||||
### `FloatingContainerForceNativeTitleBar` (Linux only)
|
||||
|
||||
Since release 3.6 the library supports native title bars and window decorations
|
||||
for floating widgets on Linux (thanks to a user contribution).
|
||||
Native title bars and window decorations are supported by most Linux window
|
||||
managers, such as Compiz or Xfwm. Some window managers like KWin do not properly
|
||||
support this feature. Native floating widgets look better because of the native
|
||||
styling and the support all window manager features like snapping to window
|
||||
borders or maximizing. The library tries to detect the window manager during
|
||||
runtime and activates native window decorations if possible:
|
||||
|
||||

|
||||
|
||||
If you would like to overwrite this autodetection, then you can activate this
|
||||
flag to force native window titlebars. You can overwrite autodetection and this
|
||||
flag, if you set the environment variable `ADS_UseNativeTitle` to 0 or 1.
|
||||
|
||||
### `FloatingContainerForceQWidgetTitleBar` (Linux only)
|
||||
|
||||
If your window manager (i.e. KWin) does not properly support native floating
|
||||
windows, the docking library falls back to QWidget based floating widget
|
||||
title bars.
|
||||
|
||||

|
||||
|
||||
If you would like to overwrite autodetection, then you can activate this flag
|
||||
to force QWidget based title bars. You can overwrite autodetection and this
|
||||
flag, if you set the environment variable `ADS_UseNativeTitle` to 0 or 1.
|
||||
|
||||
## Central Widget
|
||||
|
||||
The Advanced Docking System has been developed to overcome the limitations of
|
||||
the native Qt docking system with its central widget concept. This was the
|
||||
reason that until version 3.6 of the library, there was no support for such
|
||||
thing like a central widget. Thanks to the contribution of a user the library
|
||||
now supports a central widget.
|
||||
|
||||
In the Advanced Docking System a central widget is a docking widget that is
|
||||
neither closable nor movable or floatable. A central widget has no title bar
|
||||
and so it is not possible for the user to hide, close or drag the central
|
||||
widget. If there is a central widget, then also the distribution of the sizes
|
||||
for the dock widgets around the central widget is different:
|
||||
|
||||
- **no central widget (default)** - on resizing the available space is
|
||||
distributed to all dock widgets - the size of all dock widgets
|
||||
shrinks or grows
|
||||
- **with central widget** - on resizing only the central widget is resized - the
|
||||
dock widgets around the central widget keep their size (see the animation below)
|
||||
|
||||

|
||||
|
||||
To set a central widget, you just need to pass your central dock widget
|
||||
to the dock manager `setCentralWidget` function:
|
||||
|
||||
```c++
|
||||
auto* CentralDockArea = DockManager->setCentralWidget(CentralDockWidget);
|
||||
```
|
||||
|
||||
See the `centralwidget` example to learn how it works.
|
||||
|
||||
> ##### Note
|
||||
> The central widget needs to be the first dock widget that is added to the
|
||||
> dock manager. The function does not work and returns a `nullptr` if there
|
||||
> are already other dock widgets registered. So `setCentralWidget` should be
|
||||
> the first function that you call when adding dock widgets.
|
||||
|
||||
## Custom Close Handling
|
||||
|
||||
Normally clicking the close button of a dock widget will just hide the widget and the user can show it again using the `toggleView()` action of the dock widget. This is meant for user interfaces with a static amount of widgets. But the advanced docking system also supports dynamic dock widgets that will get deleted on close. If you set the dock widget flag `DockWidgetDeleteOnClose` for a certain dock widget, then it will be deleted as soon as you close this dock widget. This enables the implementation of user interfaces with dynamically created editors, like in word processing applications or source code development tools.
|
||||
|
||||
When an entire area is closed, the default behavior is to hide the dock widgets it contains regardless of the `DockWidgetDeleteOnClose` flag except if there is only one dock widget. In this special case, the `DockWidgetDeleteOnClose` flag is followed. This behavior can be changed by setting the `DockWidgetForceCloseWithArea` flag to all the dock widgets that needs to be closed with their area.
|
||||
|
||||
## Styling
|
||||
|
||||
The Advanced Docking System supports styling via [Qt Style Sheets](https://doc.qt.io/qt-5/stylesheet.html). All components like splitters, tabs, buttons, titlebar and
|
||||
icons are styleable this way.
|
||||
|
||||
### Disabling the Internal Style Sheet
|
||||
|
||||
The dock manager uses an internal stylesheet to style its components. That
|
||||
means, the style that you see in the demo application comes from the
|
||||
internal stylesheets that you will find in `src/stylesheets` folder. If you want
|
||||
to disable this internal stylesheet because your application uses its own,
|
||||
just call the function for settings the stylesheet with an empty string.
|
||||
|
||||
```c++
|
||||
DockManager->setStyleSheet("");
|
||||
```
|
||||
|
||||
@@ -1,46 +0,0 @@
|
||||
cmake_minimum_required(VERSION 3.3)
|
||||
set (CMAKE_CXX_STANDARD 14)
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
set(CMAKE_CXX_EXTENSIONS OFF)
|
||||
set(CMAKE_AUTOMOC ON)
|
||||
set(CMAKE_AUTOUIC ON)
|
||||
project(ads_example VERSION "1.0")
|
||||
set(REQUIRED_QT_VERSION 5.5.0)
|
||||
find_package(Qt5Core ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
find_package(Qt5Gui ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
find_package(Qt5Widgets ${REQUIRED_QT_VERSION} REQUIRED)
|
||||
set(ads_example_LIBS ${ads_example_LIBS} ${Qt5Core_LIBRARIES})
|
||||
set(ads_example_INCLUDE ${ads_example_INCLUDE} ${Qt5Core_INCLUDE_DIRS})
|
||||
set(ads_example_COMPILE_DEFINE ${ads_example_COMPILE_DEFINE} ${Qt5Core_COMPILE_DEFINITIONS} )
|
||||
set(ads_example_LIBS ${ads_example_LIBS} ${Qt5Gui_LIBRARIES})
|
||||
set(ads_example_INCLUDE ${ads_example_INCLUDE} ${Qt5Gui_INCLUDE_DIRS})
|
||||
set(ads_example_COMPILE_DEFINE ${ads_example_COMPILE_DEFINE} ${Qt5Gui_COMPILE_DEFINITIONS})
|
||||
set(ads_example_LIBS ${ads_example_LIBS} ${Qt5Widgets_LIBRARIES})
|
||||
set(ads_example_INCLUDE ${ads_example_INCLUDE} ${Qt5Widgets_INCLUDE_DIRS})
|
||||
set(ads_example_COMPILE_DEFINE ${ads_example_COMPILE_DEFINE} ${Qt5Widgets_COMPILE_DEFINITIONS})
|
||||
set(CMAKE_INCLUDE_CURRENT_DIR ON)
|
||||
set(ads_example_SRCS
|
||||
main.cpp
|
||||
MainWindow.cpp
|
||||
MainWindow.ui
|
||||
)
|
||||
add_executable(Example1 WIN32 ${ads_example_SRCS})
|
||||
if(BUILD_STATIC)
|
||||
set(ads_example_DEFINE ${ads_example_DEFINE} ADS_STATIC)
|
||||
endif()
|
||||
add_dependencies(Example1 qtadvanceddocking)
|
||||
target_include_directories(Example1 PUBLIC
|
||||
$<BUILD_INTERFACE:${ads_example_INCLUDE}>
|
||||
$<INSTALL_INTERFACE:include>
|
||||
)
|
||||
target_include_directories(Example1 PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/../src" ${ads_example_INCLUDE})
|
||||
target_link_libraries(Example1 PRIVATE qtadvanceddocking ${ads_example_LIBS})
|
||||
target_compile_definitions(Example1 PRIVATE ${ads_example_DEFINE})
|
||||
set_target_properties(Example1 PROPERTIES
|
||||
VERSION "1.0"
|
||||
SOVERSION 1
|
||||
EXPORT_NAME "Qt Advanced Docking System Example"
|
||||
ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/bin"
|
||||
)
|
||||
6
examples/CMakeLists.txt
Normal file
@@ -0,0 +1,6 @@
|
||||
cmake_minimum_required(VERSION 3.5)
|
||||
project(QtADSExamples LANGUAGES CXX VERSION ${VERSION_SHORT})
|
||||
add_subdirectory(simple)
|
||||
add_subdirectory(sidebar)
|
||||
add_subdirectory(deleteonclose)
|
||||
add_subdirectory(centralwidget)
|
||||
25
examples/centralwidget/CMakeLists.txt
Normal file
@@ -0,0 +1,25 @@
|
||||
cmake_minimum_required(VERSION 3.5)
|
||||
project(ads_example_centralwidget VERSION ${VERSION_SHORT})
|
||||
find_package(Qt5 5.5 COMPONENTS Core Gui Widgets REQUIRED)
|
||||
set(CMAKE_INCLUDE_CURRENT_DIR ON)
|
||||
add_executable(CentralWidgetExample WIN32
|
||||
main.cpp
|
||||
mainwindow.cpp
|
||||
mainwindow.ui
|
||||
)
|
||||
target_include_directories(CentralWidgetExample PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/../../src")
|
||||
target_link_libraries(CentralWidgetExample PRIVATE qtadvanceddocking)
|
||||
target_link_libraries(CentralWidgetExample PUBLIC Qt5::Core Qt5::Gui Qt5::Widgets)
|
||||
set_target_properties(CentralWidgetExample PROPERTIES
|
||||
AUTOMOC ON
|
||||
AUTORCC ON
|
||||
AUTOUIC ON
|
||||
CXX_STANDARD 14
|
||||
CXX_STANDARD_REQUIRED ON
|
||||
CXX_EXTENSIONS OFF
|
||||
VERSION ${VERSION_SHORT}
|
||||
EXPORT_NAME "Qt Advanced Docking System Central Widget Example"
|
||||
ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/bin"
|
||||
)
|
||||
115
examples/centralwidget/centralWidget.py
Normal file
@@ -0,0 +1,115 @@
|
||||
import os
|
||||
import sys
|
||||
|
||||
from PyQt5 import uic
|
||||
from PyQt5.QtCore import Qt, QTimer, QDir, QSignalBlocker
|
||||
from PyQt5.QtGui import QCloseEvent, QIcon
|
||||
from PyQt5.QtWidgets import (QApplication, QLabel, QCalendarWidget, QFrame, QTreeView,
|
||||
QTableWidget, QFileSystemModel, QPlainTextEdit, QToolBar,
|
||||
QWidgetAction, QComboBox, QAction, QSizePolicy, QInputDialog)
|
||||
|
||||
from PyQtAds import QtAds
|
||||
|
||||
UI_FILE = os.path.join(os.path.dirname(__file__), 'mainwindow.ui')
|
||||
MainWindowUI, MainWindowBase = uic.loadUiType(UI_FILE)
|
||||
|
||||
import demo_rc # pyrcc5 demo\demo.qrc -o examples\centralWidget\demo_rc.py
|
||||
|
||||
|
||||
def svg_icon(filename: str):
|
||||
'''Helper function to create an SVG icon'''
|
||||
# This is a workaround, because because in item views SVG icons are not
|
||||
# properly scaled and look blurry or pixelate
|
||||
icon = QIcon(filename)
|
||||
icon.addPixmap(icon.pixmap(92))
|
||||
return icon
|
||||
|
||||
|
||||
class MainWindow(MainWindowUI, MainWindowBase):
|
||||
|
||||
def __init__(self, parent=None):
|
||||
super().__init__(parent)
|
||||
|
||||
self.setupUi(self)
|
||||
|
||||
QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.OpaqueSplitterResize, True)
|
||||
QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.XmlCompressionEnabled, False)
|
||||
QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.FocusHighlighting, True)
|
||||
self.dock_manager = QtAds.CDockManager(self)
|
||||
|
||||
# Set central widget
|
||||
text_edit = QPlainTextEdit()
|
||||
text_edit.setPlaceholderText("This is the central editor. Enter your text here.")
|
||||
central_dock_widget = QtAds.CDockWidget("CentralWidget")
|
||||
central_dock_widget.setWidget(text_edit)
|
||||
central_dock_area = self.dock_manager.setCentralWidget(central_dock_widget)
|
||||
central_dock_area.setAllowedAreas(QtAds.DockWidgetArea.OuterDockAreas)
|
||||
|
||||
# create other dock widgets
|
||||
file_tree = QTreeView()
|
||||
file_tree.setFrameShape(QFrame.NoFrame)
|
||||
file_model = QFileSystemModel(file_tree)
|
||||
file_model.setRootPath(QDir.currentPath())
|
||||
file_tree.setModel(file_model)
|
||||
data_dock_widget = QtAds.CDockWidget("File system")
|
||||
data_dock_widget.setWidget(file_tree)
|
||||
data_dock_widget.resize(150, 250)
|
||||
data_dock_widget.setMinimumSize(100, 250)
|
||||
file_area = self.dock_manager.addDockWidget(QtAds.DockWidgetArea.LeftDockWidgetArea, data_dock_widget, central_dock_area)
|
||||
self.menuView.addAction(data_dock_widget.toggleViewAction())
|
||||
|
||||
table = QTableWidget()
|
||||
table.setColumnCount(3)
|
||||
table.setRowCount(10)
|
||||
table_dock_widget = QtAds.CDockWidget("Table")
|
||||
table_dock_widget.setWidget(table)
|
||||
table_dock_widget.setMinimumSizeHintMode(QtAds.CDockWidget.MinimumSizeHintFromDockWidget)
|
||||
table_dock_widget.resize(250, 150)
|
||||
table_dock_widget.setMinimumSize(200, 150)
|
||||
self.dock_manager.addDockWidget(QtAds.DockWidgetArea.BottomDockWidgetArea, table_dock_widget, file_area)
|
||||
self.menuView.addAction(table_dock_widget.toggleViewAction())
|
||||
|
||||
properties_table = QTableWidget()
|
||||
properties_table.setColumnCount(3)
|
||||
properties_table.setRowCount(10)
|
||||
properties_dock_widget = QtAds.CDockWidget("Properties")
|
||||
properties_dock_widget.setWidget(properties_table)
|
||||
properties_dock_widget.setMinimumSizeHintMode(QtAds.CDockWidget.MinimumSizeHintFromDockWidget)
|
||||
properties_dock_widget.resize(250, 150)
|
||||
properties_dock_widget.setMinimumSize(200,150)
|
||||
self.dock_manager.addDockWidget(QtAds.DockWidgetArea.RightDockWidgetArea, properties_dock_widget, central_dock_area)
|
||||
self.menuView.addAction(properties_dock_widget.toggleViewAction())
|
||||
|
||||
self.create_perspective_ui()
|
||||
|
||||
def create_perspective_ui(self):
|
||||
save_perspective_action = QAction("Create Perspective", self)
|
||||
save_perspective_action.setIcon(svg_icon(":/adsdemo/images/picture_in_picture.svg"))
|
||||
save_perspective_action.triggered.connect(self.save_perspective)
|
||||
perspective_list_action = QWidgetAction(self)
|
||||
self.perspective_combobox = QComboBox(self)
|
||||
self.perspective_combobox.setSizeAdjustPolicy(QComboBox.AdjustToContents)
|
||||
self.perspective_combobox.setSizePolicy(QSizePolicy.Preferred, QSizePolicy.Preferred)
|
||||
self.perspective_combobox.activated[str].connect(self.dock_manager.openPerspective)
|
||||
perspective_list_action.setDefaultWidget(self.perspective_combobox)
|
||||
self.toolBar.addSeparator()
|
||||
self.toolBar.addAction(perspective_list_action)
|
||||
self.toolBar.addAction(save_perspective_action)
|
||||
|
||||
def save_perspective(self):
|
||||
perspective_name, ok = QInputDialog.getText(self, "Save Perspective", "Enter Unique name:")
|
||||
if not ok or not perspective_name:
|
||||
return
|
||||
|
||||
self.dock_manager.addPerspective(perspective_name)
|
||||
blocker = QSignalBlocker(self.perspective_combobox)
|
||||
self.perspective_combobox.clear()
|
||||
self.perspective_combobox.addItems(self.dock_manager.perspectiveNames())
|
||||
self.perspective_combobox.setCurrentText(perspective_name)
|
||||
|
||||
if __name__ == '__main__':
|
||||
app = QApplication(sys.argv)
|
||||
|
||||
w = MainWindow()
|
||||
w.show()
|
||||
app.exec_()
|
||||
55
examples/centralwidget/centralwidget.pro
Normal file
@@ -0,0 +1,55 @@
|
||||
ADS_OUT_ROOT = $${OUT_PWD}/../..
|
||||
|
||||
QT += core gui widgets
|
||||
|
||||
TARGET = CentralWidgetExample
|
||||
DESTDIR = $${ADS_OUT_ROOT}/lib
|
||||
TEMPLATE = app
|
||||
CONFIG += c++14
|
||||
CONFIG += debug_and_release
|
||||
adsBuildStatic {
|
||||
DEFINES += ADS_STATIC
|
||||
}
|
||||
|
||||
# The following define makes your compiler emit warnings if you use
|
||||
# any Qt feature that has been marked deprecated (the exact warnings
|
||||
# depend on your compiler). Please consult the documentation of the
|
||||
# deprecated API in order to know how to port your code away from it.
|
||||
DEFINES += QT_DEPRECATED_WARNINGS
|
||||
|
||||
SOURCES += \
|
||||
main.cpp \
|
||||
mainwindow.cpp
|
||||
|
||||
HEADERS += \
|
||||
mainwindow.h
|
||||
|
||||
FORMS += \
|
||||
mainwindow.ui
|
||||
|
||||
LIBS += -L$${ADS_OUT_ROOT}/lib
|
||||
|
||||
# Dependency: AdvancedDockingSystem (shared)
|
||||
CONFIG(debug, debug|release){
|
||||
win32 {
|
||||
LIBS += -lqtadvanceddockingd
|
||||
}
|
||||
else:mac {
|
||||
LIBS += -lqtadvanceddocking_debug
|
||||
}
|
||||
else {
|
||||
LIBS += -lqtadvanceddocking
|
||||
}
|
||||
}
|
||||
else{
|
||||
LIBS += -lqtadvanceddocking
|
||||
}
|
||||
|
||||
unix:!macx {
|
||||
LIBS += -lxcb
|
||||
QT += x11extras
|
||||
}
|
||||
|
||||
INCLUDEPATH += ../../src
|
||||
DEPENDPATH += ../../src
|
||||
|
||||
10
examples/centralwidget/main.cpp
Normal file
@@ -0,0 +1,10 @@
|
||||
#include <mainwindow.h>
|
||||
#include <QApplication>
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
QApplication a(argc, argv);
|
||||
CMainWindow w;
|
||||
w.show();
|
||||
return a.exec();
|
||||
}
|
||||
135
examples/centralwidget/mainwindow.cpp
Normal file
@@ -0,0 +1,135 @@
|
||||
#include "mainwindow.h"
|
||||
|
||||
#include "ui_mainwindow.h"
|
||||
|
||||
#include <QWidgetAction>
|
||||
#include <QLabel>
|
||||
#include <QCalendarWidget>
|
||||
#include <QTreeView>
|
||||
#include <QFileSystemModel>
|
||||
#include <QTableWidget>
|
||||
#include <QHBoxLayout>
|
||||
#include <QRadioButton>
|
||||
#include <QPushButton>
|
||||
#include <QInputDialog>
|
||||
#include <QFileDialog>
|
||||
#include <QSettings>
|
||||
#include <QMessageBox>
|
||||
#include <QPlainTextEdit>
|
||||
#include <QToolBar>
|
||||
|
||||
#include "DockAreaWidget.h"
|
||||
#include "DockAreaTitleBar.h"
|
||||
#include "DockAreaTabBar.h"
|
||||
#include "FloatingDockContainer.h"
|
||||
#include "DockComponentsFactory.h"
|
||||
|
||||
using namespace ads;
|
||||
|
||||
/**
|
||||
* Helper function to create an SVG icon
|
||||
*/
|
||||
static QIcon svgIcon(const QString& File)
|
||||
{
|
||||
// This is a workaround, because in item views SVG icons are not
|
||||
// properly scaled and look blurry or pixelate
|
||||
QIcon SvgIcon(File);
|
||||
SvgIcon.addPixmap(SvgIcon.pixmap(92));
|
||||
return SvgIcon;
|
||||
}
|
||||
|
||||
CMainWindow::CMainWindow(QWidget *parent)
|
||||
: QMainWindow(parent)
|
||||
, ui(new Ui::CMainWindow)
|
||||
{
|
||||
ui->setupUi(this);
|
||||
CDockManager::setConfigFlag(CDockManager::OpaqueSplitterResize, true);
|
||||
CDockManager::setConfigFlag(CDockManager::XmlCompressionEnabled, false);
|
||||
CDockManager::setConfigFlag(CDockManager::FocusHighlighting, true);
|
||||
DockManager = new CDockManager(this);
|
||||
|
||||
// Set central widget
|
||||
QPlainTextEdit* w = new QPlainTextEdit();
|
||||
w->setPlaceholderText("This is the central editor. Enter your text here.");
|
||||
CDockWidget* CentralDockWidget = new CDockWidget("CentralWidget");
|
||||
CentralDockWidget->setWidget(w);
|
||||
auto* CentralDockArea = DockManager->setCentralWidget(CentralDockWidget);
|
||||
CentralDockArea->setAllowedAreas(DockWidgetArea::OuterDockAreas);
|
||||
|
||||
// create other dock widgets
|
||||
QTreeView* fileTree = new QTreeView();
|
||||
fileTree->setFrameShape(QFrame::NoFrame);
|
||||
QFileSystemModel* fileModel = new QFileSystemModel(fileTree);
|
||||
fileModel->setRootPath(QDir::currentPath());
|
||||
fileTree->setModel(fileModel);
|
||||
CDockWidget* DataDockWidget = new CDockWidget("File system");
|
||||
DataDockWidget->setWidget(fileTree);
|
||||
DataDockWidget->resize(150, 250);
|
||||
DataDockWidget->setMinimumSize(100, 250);
|
||||
auto* fileArea = DockManager->addDockWidget(DockWidgetArea::LeftDockWidgetArea, DataDockWidget, CentralDockArea);
|
||||
ui->menuView->addAction(DataDockWidget->toggleViewAction());
|
||||
|
||||
QTableWidget* table = new QTableWidget();
|
||||
table->setColumnCount(3);
|
||||
table->setRowCount(10);
|
||||
CDockWidget* TableDockWidget = new CDockWidget("Table");
|
||||
TableDockWidget->setWidget(table);
|
||||
TableDockWidget->setMinimumSizeHintMode(CDockWidget::MinimumSizeHintFromDockWidget);
|
||||
TableDockWidget->resize(250, 150);
|
||||
TableDockWidget->setMinimumSize(200,150);
|
||||
DockManager->addDockWidget(DockWidgetArea::BottomDockWidgetArea, TableDockWidget, fileArea);
|
||||
ui->menuView->addAction(TableDockWidget->toggleViewAction());
|
||||
|
||||
QTableWidget* propertiesTable = new QTableWidget();
|
||||
propertiesTable->setColumnCount(3);
|
||||
propertiesTable->setRowCount(10);
|
||||
CDockWidget* PropertiesDockWidget = new CDockWidget("Properties");
|
||||
PropertiesDockWidget->setWidget(propertiesTable);
|
||||
PropertiesDockWidget->setMinimumSizeHintMode(CDockWidget::MinimumSizeHintFromDockWidget);
|
||||
PropertiesDockWidget->resize(250, 150);
|
||||
PropertiesDockWidget->setMinimumSize(200,150);
|
||||
DockManager->addDockWidget(DockWidgetArea::RightDockWidgetArea, PropertiesDockWidget, CentralDockArea);
|
||||
ui->menuView->addAction(PropertiesDockWidget->toggleViewAction());
|
||||
|
||||
createPerspectiveUi();
|
||||
}
|
||||
|
||||
CMainWindow::~CMainWindow()
|
||||
{
|
||||
delete ui;
|
||||
}
|
||||
|
||||
|
||||
void CMainWindow::createPerspectiveUi()
|
||||
{
|
||||
SavePerspectiveAction = new QAction("Create Perspective", this);
|
||||
SavePerspectiveAction->setIcon(svgIcon(":/adsdemo/images/picture_in_picture.svg"));
|
||||
connect(SavePerspectiveAction, SIGNAL(triggered()), SLOT(savePerspective()));
|
||||
PerspectiveListAction = new QWidgetAction(this);
|
||||
PerspectiveComboBox = new QComboBox(this);
|
||||
PerspectiveComboBox->setSizeAdjustPolicy(QComboBox::AdjustToContents);
|
||||
PerspectiveComboBox->setSizePolicy(QSizePolicy::Preferred, QSizePolicy::Preferred);
|
||||
connect(PerspectiveComboBox, SIGNAL(activated(const QString&)),
|
||||
DockManager, SLOT(openPerspective(const QString&)));
|
||||
PerspectiveListAction->setDefaultWidget(PerspectiveComboBox);
|
||||
ui->toolBar->addSeparator();
|
||||
ui->toolBar->addAction(PerspectiveListAction);
|
||||
ui->toolBar->addAction(SavePerspectiveAction);
|
||||
}
|
||||
|
||||
|
||||
void CMainWindow::savePerspective()
|
||||
{
|
||||
QString PerspectiveName = QInputDialog::getText(this, "Save Perspective", "Enter unique name:");
|
||||
if (PerspectiveName.isEmpty())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
DockManager->addPerspective(PerspectiveName);
|
||||
QSignalBlocker Blocker(PerspectiveComboBox);
|
||||
PerspectiveComboBox->clear();
|
||||
PerspectiveComboBox->addItems(DockManager->perspectiveNames());
|
||||
PerspectiveComboBox->setCurrentText(PerspectiveName);
|
||||
}
|
||||
|
||||
40
examples/centralwidget/mainwindow.h
Normal file
@@ -0,0 +1,40 @@
|
||||
#ifndef MAINWINDOW_H
|
||||
#define MAINWINDOW_H
|
||||
|
||||
#include <QMainWindow>
|
||||
#include <QComboBox>
|
||||
#include <QWidgetAction>
|
||||
|
||||
#include "DockManager.h"
|
||||
#include "DockAreaWidget.h"
|
||||
#include "DockWidget.h"
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
namespace Ui { class CMainWindow; }
|
||||
QT_END_NAMESPACE
|
||||
|
||||
class CMainWindow : public QMainWindow
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
CMainWindow(QWidget *parent = nullptr);
|
||||
~CMainWindow();
|
||||
|
||||
private:
|
||||
QAction* SavePerspectiveAction = nullptr;
|
||||
QWidgetAction* PerspectiveListAction = nullptr;
|
||||
QComboBox* PerspectiveComboBox = nullptr;
|
||||
|
||||
Ui::CMainWindow *ui;
|
||||
|
||||
ads::CDockManager* DockManager;
|
||||
ads::CDockAreaWidget* StatusDockArea;
|
||||
ads::CDockWidget* TimelineDockWidget;
|
||||
|
||||
void createPerspectiveUi();
|
||||
|
||||
private slots:
|
||||
void savePerspective();
|
||||
};
|
||||
#endif // MAINWINDOW_H
|
||||
47
examples/centralwidget/mainwindow.ui
Normal file
@@ -0,0 +1,47 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<ui version="4.0">
|
||||
<class>CMainWindow</class>
|
||||
<widget class="QMainWindow" name="CMainWindow">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>1284</width>
|
||||
<height>757</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>MainWindow</string>
|
||||
</property>
|
||||
<widget class="QWidget" name="centralwidget"/>
|
||||
<widget class="QMenuBar" name="menubar">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>1284</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<widget class="QMenu" name="menuView">
|
||||
<property name="title">
|
||||
<string>View</string>
|
||||
</property>
|
||||
</widget>
|
||||
<addaction name="menuView"/>
|
||||
</widget>
|
||||
<widget class="QToolBar" name="toolBar">
|
||||
<property name="windowTitle">
|
||||
<string>toolBar</string>
|
||||
</property>
|
||||
<attribute name="toolBarArea">
|
||||
<enum>TopToolBarArea</enum>
|
||||
</attribute>
|
||||
<attribute name="toolBarBreak">
|
||||
<bool>false</bool>
|
||||
</attribute>
|
||||
</widget>
|
||||
</widget>
|
||||
<resources/>
|
||||
<connections/>
|
||||
</ui>
|
||||
21
examples/deleteonclose/CMakeLists.txt
Normal file
@@ -0,0 +1,21 @@
|
||||
cmake_minimum_required(VERSION 3.5)
|
||||
project(ads_example_deleteonclose VERSION ${VERSION_SHORT})
|
||||
find_package(Qt5 5.5 COMPONENTS Core Gui Widgets REQUIRED)
|
||||
set(CMAKE_INCLUDE_CURRENT_DIR ON)
|
||||
add_executable(DeleteOnCloseTest WIN32
|
||||
main.cpp
|
||||
)
|
||||
target_include_directories(DeleteOnCloseTest PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/../../src")
|
||||
target_link_libraries(DeleteOnCloseTest PRIVATE qtadvanceddocking)
|
||||
target_link_libraries(DeleteOnCloseTest PUBLIC Qt5::Core Qt5::Gui Qt5::Widgets)
|
||||
set_target_properties(DeleteOnCloseTest PROPERTIES
|
||||
AUTOMOC ON
|
||||
CXX_STANDARD 14
|
||||
CXX_STANDARD_REQUIRED ON
|
||||
CXX_EXTENSIONS OFF
|
||||
VERSION ${VERSION_SHORT}
|
||||
EXPORT_NAME "Qt Advanced Docking System Delete on Close Example"
|
||||
ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/bin"
|
||||
)
|
||||
44
examples/deleteonclose/deleteonclose.pro
Normal file
@@ -0,0 +1,44 @@
|
||||
ADS_OUT_ROOT = $${OUT_PWD}/../..
|
||||
|
||||
QT += core gui widgets
|
||||
|
||||
TARGET = DeleteOnCloseTest
|
||||
DESTDIR = $${ADS_OUT_ROOT}/lib
|
||||
TEMPLATE = app
|
||||
CONFIG += c++14
|
||||
CONFIG += debug_and_release
|
||||
adsBuildStatic {
|
||||
DEFINES += ADS_STATIC
|
||||
}
|
||||
|
||||
DEFINES += QT_DEPRECATED_WARNINGS
|
||||
|
||||
SOURCES += main.cpp
|
||||
|
||||
|
||||
LIBS += -L$${ADS_OUT_ROOT}/lib
|
||||
|
||||
# Dependency: AdvancedDockingSystem (shared)
|
||||
CONFIG(debug, debug|release){
|
||||
win32 {
|
||||
LIBS += -lqtadvanceddockingd
|
||||
}
|
||||
else:mac {
|
||||
LIBS += -lqtadvanceddocking_debug
|
||||
}
|
||||
else {
|
||||
LIBS += -lqtadvanceddocking
|
||||
}
|
||||
}
|
||||
else{
|
||||
LIBS += -lqtadvanceddocking
|
||||
}
|
||||
|
||||
unix:!macx {
|
||||
LIBS += -lxcb
|
||||
QT += x11extras
|
||||
}
|
||||
|
||||
INCLUDEPATH += ../../src
|
||||
DEPENDPATH += ../../src
|
||||
|
||||
73
examples/deleteonclose/deleteonclose.py
Normal file
@@ -0,0 +1,73 @@
|
||||
import sys
|
||||
|
||||
from PyQtAds import QtAds
|
||||
from PyQt5.QtGui import QCloseEvent
|
||||
from PyQt5.QtCore import (qDebug, pyqtSlot, QObject, pyqtSignal)
|
||||
from PyQt5.QtWidgets import (QMainWindow, QAction, QTextEdit, QApplication,
|
||||
QMenuBar)
|
||||
|
||||
|
||||
class MainWindow(QMainWindow):
|
||||
dock_manager = None
|
||||
|
||||
def closeEvent(self, event: QCloseEvent):
|
||||
super().closeEvent(event)
|
||||
if self.dock_manager is not None:
|
||||
self.dock_manager.deleteLater()
|
||||
|
||||
def setDockManager(self, dock_manager: QtAds.CDockManager):
|
||||
self.dock_manager = dock_manager
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
app = QApplication(sys.argv)
|
||||
w = MainWindow()
|
||||
|
||||
QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.FocusHighlighting, True)
|
||||
QtAds.CDockManager.setConfigFlag(QtAds.CDockManager.AllTabsHaveCloseButton, True)
|
||||
dock_manager = QtAds.CDockManager(w)
|
||||
w.setDockManager(dock_manager)
|
||||
|
||||
count = 0
|
||||
|
||||
def on_focused_dock_widget_changed(old: QtAds.CDockWidget, now: QtAds.CDockWidget):
|
||||
global count
|
||||
qDebug( "{:d} CDockManager::focusedDockWidgetChanged old: {} now: {} visible: {}".format(
|
||||
count,
|
||||
old.objectName() if old else "-",
|
||||
now.objectName(),
|
||||
now.isVisible()))
|
||||
count += 1
|
||||
now.widget().setFocus()
|
||||
|
||||
dock_manager.focusedDockWidgetChanged.connect(on_focused_dock_widget_changed)
|
||||
|
||||
action = QAction("New Delete On Close", w)
|
||||
w.menuBar().addAction(action)
|
||||
|
||||
i = 0
|
||||
def on_action_triggered():
|
||||
global i
|
||||
dw = QtAds.CDockWidget("test doc {:d}".format(i))
|
||||
i += 1
|
||||
editor = QTextEdit("lorem ipsum...", dw)
|
||||
dw.setWidget(editor)
|
||||
dw.setFeature(QtAds.CDockWidget.DockWidgetDeleteOnClose, True)
|
||||
area = dock_manager.addDockWidgetTab(QtAds.CenterDockWidgetArea, dw)
|
||||
qDebug("doc dock widget created! {} {}".format(dw, area))
|
||||
action.triggered.connect(on_action_triggered)
|
||||
|
||||
action = QAction("New", w)
|
||||
w.menuBar().addAction(action)
|
||||
def on_action2_triggered():
|
||||
global i
|
||||
dw = QtAds.CDockWidget("test {:d}".format(i))
|
||||
i += 1
|
||||
editor = QTextEdit("lorem ipsum...", dw)
|
||||
dw.setWidget(editor)
|
||||
area = dock_manager.addDockWidgetTab(QtAds.CenterDockWidgetArea, dw)
|
||||
qDebug("dock widget created! {} {}".format(dw, area))
|
||||
action.triggered.connect(on_action2_triggered)
|
||||
|
||||
w.show()
|
||||
app.exec_()
|
||||
70
examples/deleteonclose/main.cpp
Normal file
@@ -0,0 +1,70 @@
|
||||
#include <QMainWindow>
|
||||
#include <QAction>
|
||||
#include <QTextEdit>
|
||||
#include <QApplication>
|
||||
#include <QMenuBar>
|
||||
#include "DockManager.h"
|
||||
|
||||
|
||||
class MainWindow : public QMainWindow
|
||||
{
|
||||
private:
|
||||
ads::CDockManager* m_DockManager = nullptr;
|
||||
|
||||
protected:
|
||||
virtual void closeEvent(QCloseEvent *event) override
|
||||
{
|
||||
QMainWindow::closeEvent(event);
|
||||
if (m_DockManager)
|
||||
{
|
||||
m_DockManager->deleteLater();
|
||||
}
|
||||
}
|
||||
|
||||
public:
|
||||
void setDockManager(ads::CDockManager* DockManager) {m_DockManager = DockManager;}
|
||||
};
|
||||
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
QApplication a(argc, argv);
|
||||
MainWindow w;
|
||||
|
||||
ads::CDockManager::setConfigFlag(ads::CDockManager::FocusHighlighting, true);
|
||||
ads::CDockManager::setConfigFlag(ads::CDockManager::AllTabsHaveCloseButton, true);
|
||||
auto dockManager = new ads::CDockManager(&w);
|
||||
w.setDockManager(dockManager);
|
||||
QObject::connect(dockManager, &ads::CDockManager::focusedDockWidgetChanged, [] (ads::CDockWidget* old, ads::CDockWidget* now) {
|
||||
static int Count = 0;
|
||||
qDebug() << Count++ << " CDockManager::focusedDockWidgetChanged old: " << (old ? old->objectName() : "-") << " now: " << now->objectName() << " visible: " << now->isVisible();
|
||||
now->widget()->setFocus();
|
||||
});
|
||||
|
||||
QAction *action = new QAction("New Delete On Close", &w);
|
||||
w.menuBar()->addAction(action);
|
||||
|
||||
int i = 0;
|
||||
QObject::connect(action, &QAction::triggered, [&]() {
|
||||
auto dw = new ads::CDockWidget(QStringLiteral("test doc %1").arg(i++), &w);
|
||||
auto editor = new QTextEdit(QStringLiteral("lorem ipsum..."), dw);
|
||||
dw->setWidget(editor);
|
||||
dw->setFeature(ads::CDockWidget::DockWidgetDeleteOnClose, true);
|
||||
auto area = dockManager->addDockWidgetTab(ads::CenterDockWidgetArea, dw);
|
||||
qDebug() << "doc dock widget created!" << dw << area;
|
||||
});
|
||||
|
||||
action = new QAction("New", &w);
|
||||
w.menuBar()->addAction(action);
|
||||
QObject::connect(action, &QAction::triggered, [&]() {
|
||||
auto dw = new ads::CDockWidget(QStringLiteral("test %1").arg(i++), &w);
|
||||
auto editor = new QTextEdit(QStringLiteral("lorem ipsum..."), dw);
|
||||
dw->setWidget(editor);
|
||||
auto area = dockManager->addDockWidgetTab(ads::CenterDockWidgetArea, dw);
|
||||
qDebug() << "dock widget created!" << dw << area;
|
||||
});
|
||||
|
||||
w.show();
|
||||
|
||||
return a.exec();
|
||||
}
|
||||
7
examples/examples.pro
Normal file
@@ -0,0 +1,7 @@
|
||||
TEMPLATE = subdirs
|
||||
|
||||
SUBDIRS = \
|
||||
centralwidget \
|
||||
simple \
|
||||
sidebar \
|
||||
deleteonclose
|
||||
25
examples/sidebar/CMakeLists.txt
Normal file
@@ -0,0 +1,25 @@
|
||||
cmake_minimum_required(VERSION 3.5)
|
||||
project(ads_example_sidebar VERSION ${VERSION_SHORT})
|
||||
find_package(Qt5 5.5 COMPONENTS Core Gui Widgets REQUIRED)
|
||||
set(CMAKE_INCLUDE_CURRENT_DIR ON)
|
||||
add_executable(SidebarExample WIN32
|
||||
main.cpp
|
||||
MainWindow.cpp
|
||||
MainWindow.ui
|
||||
)
|
||||
target_include_directories(SidebarExample PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/../../src")
|
||||
target_link_libraries(SidebarExample PRIVATE qtadvanceddocking)
|
||||
target_link_libraries(SidebarExample PUBLIC Qt5::Core Qt5::Gui Qt5::Widgets)
|
||||
set_target_properties(SidebarExample PROPERTIES
|
||||
AUTOMOC ON
|
||||
AUTORCC ON
|
||||
AUTOUIC ON
|
||||
CXX_STANDARD 14
|
||||
CXX_STANDARD_REQUIRED ON
|
||||
CXX_EXTENSIONS OFF
|
||||
VERSION ${VERSION_SHORT}
|
||||
EXPORT_NAME "Qt Advanced Docking System Sidebar Example"
|
||||
ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/bin"
|
||||
)
|
||||
63
examples/sidebar/MainWindow.cpp
Normal file
@@ -0,0 +1,63 @@
|
||||
#include "MainWindow.h"
|
||||
|
||||
#include "ui_MainWindow.h"
|
||||
|
||||
#include <QLabel>
|
||||
#include <QVBoxLayout>
|
||||
#include <QPlainTextEdit>
|
||||
|
||||
MainWindow::MainWindow(QWidget *parent) :
|
||||
QMainWindow(parent),
|
||||
ui(new Ui::MainWindow)
|
||||
{
|
||||
ui->setupUi(this);
|
||||
|
||||
// Create the dock manager. Because the parent parameter is a QMainWindow
|
||||
// the dock manager registers itself as the central widget.
|
||||
QVBoxLayout* Layout = new QVBoxLayout(ui->dockContainer);
|
||||
Layout->setContentsMargins(QMargins(0, 0, 0, 0));
|
||||
m_DockManager = new ads::CDockManager(ui->dockContainer);
|
||||
Layout->addWidget(m_DockManager);
|
||||
|
||||
// Create example content label - this can be any application specific
|
||||
// widget
|
||||
QLabel* l = new QLabel();
|
||||
l->setWordWrap(true);
|
||||
l->setAlignment(Qt::AlignTop | Qt::AlignLeft);
|
||||
l->setText("Lorem ipsum dolor sit amet, consectetuer adipiscing elit. ");
|
||||
|
||||
// Create a dock widget with the title Label 1 and set the created label
|
||||
// as the dock widget content
|
||||
ads::CDockWidget* DockWidget = new ads::CDockWidget("Label 1");
|
||||
DockWidget->setWidget(l);
|
||||
|
||||
// Add the toggleViewAction of the dock widget to the menu to give
|
||||
// the user the possibility to show the dock widget if it has been closed
|
||||
ui->menuView->addAction(DockWidget->toggleViewAction());
|
||||
|
||||
|
||||
// Add the dock widget to the top dock widget area
|
||||
m_DockManager->addDockWidget(ads::TopDockWidgetArea, DockWidget);
|
||||
|
||||
// Create an example editor
|
||||
QPlainTextEdit* te = new QPlainTextEdit();
|
||||
te->setPlaceholderText("Please enter your text here into this QPlainTextEdit...");
|
||||
DockWidget = new ads::CDockWidget("Editor 1");
|
||||
ui->menuView->addAction(DockWidget->toggleViewAction());
|
||||
m_DockManager->addDockWidget(ads::BottomDockWidgetArea, DockWidget);
|
||||
}
|
||||
|
||||
MainWindow::~MainWindow()
|
||||
{
|
||||
delete ui;
|
||||
}
|
||||
|
||||
|
||||
void MainWindow::closeEvent(QCloseEvent *event)
|
||||
{
|
||||
QMainWindow::closeEvent(event);
|
||||
if (m_DockManager)
|
||||
{
|
||||
m_DockManager->deleteLater();
|
||||
}
|
||||
}
|
||||
33
examples/sidebar/MainWindow.h
Normal file
@@ -0,0 +1,33 @@
|
||||
#ifndef MAINWINDOW_H
|
||||
#define MAINWINDOW_H
|
||||
|
||||
#include <QMainWindow>
|
||||
#include "DockManager.h"
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
namespace Ui {
|
||||
class MainWindow;
|
||||
}
|
||||
QT_END_NAMESPACE
|
||||
|
||||
/**
|
||||
* This example shows, how to place a dock widget container and a static
|
||||
* sidebar into a QMainWindow
|
||||
*/
|
||||
class MainWindow : public QMainWindow
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
explicit MainWindow(QWidget *parent = 0);
|
||||
~MainWindow();
|
||||
|
||||
protected:
|
||||
virtual void closeEvent(QCloseEvent *event) override;
|
||||
|
||||
private:
|
||||
Ui::MainWindow *ui;
|
||||
ads::CDockManager* m_DockManager;
|
||||
};
|
||||
|
||||
#endif // MAINWINDOW_H
|
||||
85
examples/sidebar/MainWindow.ui
Normal file
@@ -0,0 +1,85 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<ui version="4.0">
|
||||
<class>MainWindow</class>
|
||||
<widget class="QMainWindow" name="MainWindow">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>650</width>
|
||||
<height>376</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>MainWindow</string>
|
||||
</property>
|
||||
<widget class="QWidget" name="centralWidget">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout">
|
||||
<item>
|
||||
<layout class="QVBoxLayout" name="verticalLayout">
|
||||
<item>
|
||||
<widget class="QComboBox" name="comboBox"/>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="pushButton">
|
||||
<property name="text">
|
||||
<string>PushButton</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QLineEdit" name="lineEdit">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPlainTextEdit" name="plainTextEdit">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Expanding">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QWidget" name="dockContainer" native="true">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<widget class="QMenuBar" name="menuBar">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>650</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<widget class="QMenu" name="menuView">
|
||||
<property name="title">
|
||||
<string>View</string>
|
||||
</property>
|
||||
</widget>
|
||||
<addaction name="menuView"/>
|
||||
</widget>
|
||||
<widget class="QStatusBar" name="statusBar"/>
|
||||
</widget>
|
||||
<layoutdefault spacing="6" margin="11"/>
|
||||
<resources/>
|
||||
<connections/>
|
||||
</ui>
|
||||
@@ -1,5 +1,5 @@
|
||||
#include "MainWindow.h"
|
||||
#include <QApplication>
|
||||
#include "../../examples/simple/MainWindow.h"
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
52
examples/sidebar/sidebar.pro
Normal file
@@ -0,0 +1,52 @@
|
||||
ADS_OUT_ROOT = $${OUT_PWD}/../..
|
||||
|
||||
QT += core gui widgets
|
||||
|
||||
TARGET = SidebarExample
|
||||
DESTDIR = $${ADS_OUT_ROOT}/lib
|
||||
TEMPLATE = app
|
||||
CONFIG += c++14
|
||||
CONFIG += debug_and_release
|
||||
adsBuildStatic {
|
||||
DEFINES += ADS_STATIC
|
||||
}
|
||||
|
||||
DEFINES += QT_DEPRECATED_WARNINGS
|
||||
|
||||
SOURCES += \
|
||||
main.cpp \
|
||||
MainWindow.cpp
|
||||
|
||||
HEADERS += \
|
||||
MainWindow.h
|
||||
|
||||
FORMS += \
|
||||
MainWindow.ui
|
||||
|
||||
|
||||
LIBS += -L$${ADS_OUT_ROOT}/lib
|
||||
|
||||
# Dependency: AdvancedDockingSystem (shared)
|
||||
CONFIG(debug, debug|release){
|
||||
win32 {
|
||||
LIBS += -lqtadvanceddockingd
|
||||
}
|
||||
else:mac {
|
||||
LIBS += -lqtadvanceddocking_debug
|
||||
}
|
||||
else {
|
||||
LIBS += -lqtadvanceddocking
|
||||
}
|
||||
}
|
||||
else{
|
||||
LIBS += -lqtadvanceddocking
|
||||
}
|
||||
|
||||
unix:!macx {
|
||||
LIBS += -lxcb
|
||||
QT += x11extras
|
||||
}
|
||||
|
||||
INCLUDEPATH += ../../src
|
||||
DEPENDPATH += ../../src
|
||||
|
||||
60
examples/sidebar/sidebar.py
Normal file
@@ -0,0 +1,60 @@
|
||||
import os
|
||||
import sys
|
||||
|
||||
from PyQt5 import uic
|
||||
from PyQt5.QtCore import Qt, QMargins
|
||||
from PyQt5.QtWidgets import QApplication, QLabel, QVBoxLayout, QPlainTextEdit
|
||||
|
||||
from PyQtAds import QtAds
|
||||
|
||||
UI_FILE = os.path.join(os.path.dirname(__file__), 'MainWindow.ui')
|
||||
MainWindowUI, MainWindowBase = uic.loadUiType(UI_FILE)
|
||||
|
||||
|
||||
class MainWindow(MainWindowUI, MainWindowBase):
|
||||
|
||||
def __init__(self, parent=None):
|
||||
super().__init__(parent)
|
||||
|
||||
self.setupUi(self)
|
||||
|
||||
# Create the dock manager. Because the parent parameter is a QMainWindow
|
||||
# the dock manager registers itself as the central widget.
|
||||
layout = QVBoxLayout(self.dockContainer);
|
||||
layout.setContentsMargins(QMargins(0, 0, 0, 0))
|
||||
self.dock_manager = QtAds.CDockManager(self.dockContainer)
|
||||
layout.addWidget(self.dock_manager)
|
||||
|
||||
# Create example content label - this can be any application specific
|
||||
# widget
|
||||
l = QLabel()
|
||||
l.setWordWrap(True)
|
||||
l.setAlignment(Qt.AlignTop | Qt.AlignLeft);
|
||||
l.setText("Lorem ipsum dolor sit amet, consectetuer adipiscing elit. ")
|
||||
|
||||
# Create a dock widget with the title Label 1 and set the created label
|
||||
# as the dock widget content
|
||||
dock_widget = QtAds.CDockWidget("Label 1")
|
||||
dock_widget.setWidget(l)
|
||||
|
||||
# Add the toggleViewAction of the dock widget to the menu to give
|
||||
# the user the possibility to show the dock widget if it has been closed
|
||||
self.menuView.addAction(dock_widget.toggleViewAction())
|
||||
|
||||
# Add the dock widget to the top dock widget area
|
||||
self.dock_manager.addDockWidget(QtAds.TopDockWidgetArea, dock_widget)
|
||||
|
||||
# Create an example editor
|
||||
te = QPlainTextEdit()
|
||||
te.setPlaceholderText("Please enter your text here into this QPlainTextEdit...")
|
||||
dock_widget = QtAds.CDockWidget("Editor 1")
|
||||
self.menuView.addAction(dock_widget.toggleViewAction())
|
||||
self.dock_manager.addDockWidget(QtAds.BottomDockWidgetArea, dock_widget)
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
app = QApplication(sys.argv)
|
||||
|
||||
w = MainWindow()
|
||||
w.show()
|
||||
app.exec_()
|
||||
25
examples/simple/CMakeLists.txt
Normal file
@@ -0,0 +1,25 @@
|
||||
cmake_minimum_required(VERSION 3.5)
|
||||
project(ads_example_simple VERSION ${VERSION_SHORT})
|
||||
find_package(Qt5 5.5 COMPONENTS Core Gui Widgets REQUIRED)
|
||||
set(CMAKE_INCLUDE_CURRENT_DIR ON)
|
||||
add_executable(SimpleExample WIN32
|
||||
main.cpp
|
||||
MainWindow.cpp
|
||||
MainWindow.ui
|
||||
)
|
||||
target_include_directories(SimpleExample PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/../../src")
|
||||
target_link_libraries(SimpleExample PRIVATE qtadvanceddocking)
|
||||
target_link_libraries(SimpleExample PUBLIC Qt5::Core Qt5::Gui Qt5::Widgets)
|
||||
set_target_properties(SimpleExample PROPERTIES
|
||||
AUTOMOC ON
|
||||
AUTORCC ON
|
||||
AUTOUIC ON
|
||||
CXX_STANDARD 14
|
||||
CXX_STANDARD_REQUIRED ON
|
||||
CXX_EXTENSIONS OFF
|
||||
VERSION ${VERSION_SHORT}
|
||||
EXPORT_NAME "Qt Advanced Docking System Simple Example"
|
||||
ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/bin"
|
||||
)
|
||||
@@ -1,7 +1,9 @@
|
||||
#include "MainWindow.h"
|
||||
#include "../../examples/simple/MainWindow.h"
|
||||
|
||||
#include "ui_MainWindow.h"
|
||||
|
||||
#include <QLabel>
|
||||
#include <QTimer>
|
||||
|
||||
MainWindow::MainWindow(QWidget *parent) :
|
||||
QMainWindow(parent),
|
||||
@@ -37,3 +39,4 @@ MainWindow::~MainWindow()
|
||||
{
|
||||
delete ui;
|
||||
}
|
||||
|
||||
@@ -4,9 +4,11 @@
|
||||
#include <QMainWindow>
|
||||
#include "DockManager.h"
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
namespace Ui {
|
||||
class MainWindow;
|
||||
}
|
||||
QT_END_NAMESPACE
|
||||
|
||||
class MainWindow : public QMainWindow
|
||||
{
|
||||
11
examples/simple/main.cpp
Normal file
@@ -0,0 +1,11 @@
|
||||
#include <QApplication>
|
||||
#include "../../examples/simple/MainWindow.h"
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
QApplication a(argc, argv);
|
||||
MainWindow w;
|
||||
w.show();
|
||||
|
||||
return a.exec();
|
||||
}
|
||||
@@ -1,8 +1,8 @@
|
||||
ADS_OUT_ROOT = $${OUT_PWD}/..
|
||||
ADS_OUT_ROOT = $${OUT_PWD}/../..
|
||||
|
||||
QT += core gui widgets
|
||||
|
||||
TARGET = Example1
|
||||
TARGET = SimpleExample
|
||||
DESTDIR = $${ADS_OUT_ROOT}/lib
|
||||
TEMPLATE = app
|
||||
CONFIG += c++14
|
||||
@@ -42,6 +42,11 @@ else{
|
||||
LIBS += -lqtadvanceddocking
|
||||
}
|
||||
|
||||
INCLUDEPATH += ../src
|
||||
DEPENDPATH += ../src
|
||||
unix:!macx {
|
||||
LIBS += -lxcb
|
||||
QT += x11extras
|
||||
}
|
||||
|
||||
INCLUDEPATH += ../../src
|
||||
DEPENDPATH += ../../src
|
||||
|
||||
@@ -1,10 +1,9 @@
|
||||
import datetime
|
||||
import logging
|
||||
import os
|
||||
import sys
|
||||
|
||||
from PyQt5 import uic
|
||||
from PyQt5.QtCore import Qt
|
||||
from PyQt5.QtCore import Qt, QTimer
|
||||
from PyQt5.QtGui import QCloseEvent
|
||||
from PyQt5.QtWidgets import QApplication, QLabel
|
||||
|
||||
from PyQtAds import QtAds
|
||||
@@ -35,6 +34,7 @@ class MainWindow(MainWindowUI, MainWindowBase):
|
||||
# as the dock widget content
|
||||
dock_widget = QtAds.CDockWidget("Label 1")
|
||||
dock_widget.setWidget(l)
|
||||
|
||||
|
||||
# Add the toggleViewAction of the dock widget to the menu to give
|
||||
# the user the possibility to show the dock widget if it has been closed
|
||||
96
setup.py
@@ -1,6 +1,7 @@
|
||||
import os
|
||||
import sys
|
||||
import shlex
|
||||
import shutil
|
||||
import subprocess
|
||||
import glob
|
||||
|
||||
@@ -141,9 +142,37 @@ class build_ext(sipdistutils.build_ext):
|
||||
|
||||
def _find_sip(self):
|
||||
"""override _find_sip to allow for manually speficied sip path."""
|
||||
return self.sip_bin or super()._find_sip()
|
||||
|
||||
# 1. Manually specified sip_bin
|
||||
if self.sip_bin:
|
||||
return self.sip_bin
|
||||
|
||||
# 2. Path determined from sipconfig.Configuration()
|
||||
# This may not exist, depending on conda build configuration.
|
||||
sip_bin = super()._find_sip()
|
||||
if os.path.exists(sip_bin):
|
||||
return sip_bin
|
||||
|
||||
# 3. Finally, fall back to sip binary found in path
|
||||
sip_bin = shutil.which('sip')
|
||||
if sip_bin:
|
||||
return sip_bin
|
||||
|
||||
raise SystemExit('Could not find PyQt SIP binary.')
|
||||
|
||||
def _sip_sipfiles_dir(self):
|
||||
sip_dir = super()._sip_sipfiles_dir()
|
||||
if os.path.exists(sip_dir):
|
||||
return sip_dir
|
||||
|
||||
return os.path.join(sys.prefix, 'sip', 'PyQt5')
|
||||
|
||||
def _sip_compile(self, sip_bin, source, sbf):
|
||||
target_dir = os.path.dirname(__file__) if self.inplace else self.build_lib
|
||||
pyi = os.path.join(target_dir, "PyQtAds", "QtAds", "ads.pyi")
|
||||
if not os.path.exists(os.path.dirname(pyi)):
|
||||
os.makedirs(os.path.dirname(pyi))
|
||||
|
||||
cmd = [sip_bin]
|
||||
if hasattr(self, 'sip_opts'):
|
||||
cmd += self.sip_opts
|
||||
@@ -156,11 +185,20 @@ class build_ext(sipdistutils.build_ext):
|
||||
"-I", self.inc_dir,
|
||||
"-c", self._sip_output_dir(),
|
||||
"-b", sbf,
|
||||
"-y", pyi,
|
||||
"-w", "-o"]
|
||||
|
||||
cmd += shlex.split(self.pyqt_sip_flags) # use same SIP flags as for PyQt5
|
||||
cmd.append(source)
|
||||
self.spawn(cmd)
|
||||
|
||||
if os.path.exists(pyi):
|
||||
with open(pyi) as f:
|
||||
content = f.readlines()
|
||||
with open(pyi, "w") as f:
|
||||
for line in content:
|
||||
if not line.startswith("class ads"):
|
||||
f.write(line)
|
||||
|
||||
def swig_sources (self, sources, extension=None):
|
||||
if not self.extensions:
|
||||
@@ -189,12 +227,15 @@ class build_ext(sipdistutils.build_ext):
|
||||
extension.extra_link_args += ['-F' + self.qtconfig.QT_INSTALL_LIBS,
|
||||
'-mmacosx-version-min=10.9']
|
||||
elif sys.platform == 'linux':
|
||||
extension.extra_compile_args += ['-std=c++11']
|
||||
extension.extra_compile_args += ['-D', 'QT_X11EXTRAS_LIB', '-std=c++11']
|
||||
extension.include_dirs += [os.path.join(self.qt_include_dir, 'QtX11Extras')]
|
||||
extension.libraries += ['Qt5X11Extras' + self.qt_libinfix]
|
||||
|
||||
return super().swig_sources(sources, extension)
|
||||
|
||||
def build_extension(self, ext):
|
||||
def build_extension(self, ext):
|
||||
cppsources = [source for source in ext.sources if source.endswith(".cpp")]
|
||||
headersources = ['src/DockAreaTitleBar_p.h']
|
||||
|
||||
dir_util.mkpath(self.build_temp, dry_run=self.dry_run)
|
||||
|
||||
@@ -228,11 +269,57 @@ class build_ext(sipdistutils.build_ext):
|
||||
if os.path.getsize(out_file) > 0:
|
||||
ext.sources.append(out_file)
|
||||
|
||||
# Run moc on all orphan header files.
|
||||
for source in headersources:
|
||||
# *.cpp -> *.moc
|
||||
moc_file = os.path.basename(source).replace(".h", ".moc")
|
||||
out_file = os.path.join(self.build_temp, moc_file)
|
||||
|
||||
if newer(source, out_file) or self.force:
|
||||
spawn.spawn(get_moc_args(out_file, source),
|
||||
dry_run=self.dry_run)
|
||||
|
||||
header = source
|
||||
if os.path.exists(header):
|
||||
# *.h -> moc_*.cpp
|
||||
moc_file = "moc_" + os.path.basename(header).replace(
|
||||
".h", ".cpp")
|
||||
out_file = os.path.join(self.build_temp, moc_file)
|
||||
|
||||
if newer(header, out_file) or self.force:
|
||||
spawn.spawn(get_moc_args(out_file, header),
|
||||
dry_run=self.dry_run)
|
||||
|
||||
if os.path.getsize(out_file) > 0:
|
||||
ext.sources.append(out_file)
|
||||
|
||||
# Add the temp build directory to include path, for compiler to find
|
||||
# the created .moc files
|
||||
ext.include_dirs += [self._sip_output_dir()]
|
||||
|
||||
# Run rcc on all resource files
|
||||
resources = [source for source in ext.sources if source.endswith(".qrc")]
|
||||
for source in resources:
|
||||
ext.sources.remove(source)
|
||||
out_file = os.path.join(self.build_temp, "qrc_" + os.path.basename(source).replace(".qrc", ".cpp"))
|
||||
if newer(header, out_file) or self.force:
|
||||
spawn.spawn(["rcc", "-name", os.path.splitext(os.path.basename(source))[0], source, "-o", out_file], dry_run=self.dry_run)
|
||||
|
||||
if os.path.getsize(out_file) > 0:
|
||||
ext.sources.append(out_file)
|
||||
|
||||
sipdistutils.build_ext.build_extension(self, ext)
|
||||
|
||||
import inspect
|
||||
sys.path.append(os.path.join(self.build_lib, 'PyQtAds', 'QtAds'))
|
||||
import ads
|
||||
|
||||
with open(os.path.join(self.build_lib, 'PyQtAds', 'QtAds', '__init__.py'), 'w') as f:
|
||||
f.write('from .._version import *\n')
|
||||
f.write('from .ads import ads\n')
|
||||
for name, member in sorted(inspect.getmembers(ads.ads)):
|
||||
if not name.startswith('_'):
|
||||
f.write('{0} = ads.{0}\n'.format(name))
|
||||
|
||||
|
||||
class ProcessResourceCommand(cmd.Command):
|
||||
@@ -262,9 +349,10 @@ class BuildPyCommand(build_py):
|
||||
setup_requires = ["PyQt5"] if REQUIRE_PYQT else []
|
||||
cpp_sources = glob.glob(os.path.join('src', '*.cpp'))
|
||||
sip_sources = [os.path.join('sip', MODULE_NAME + '.sip')]
|
||||
resources = [os.path.join('src', MODULE_NAME + '.qrc')]
|
||||
if sys.platform == 'linux':
|
||||
cpp_sources += glob.glob(os.path.join('src', 'linux', '*.cpp'))
|
||||
ext_modules = [Extension('PyQtAds.QtAds.ads', cpp_sources + sip_sources)]
|
||||
ext_modules = [Extension('PyQtAds.QtAds.ads', cpp_sources + sip_sources + resources)]
|
||||
|
||||
install_requires = ["PyQt5"]
|
||||
if sys.platform == 'win32':
|
||||
|
||||
37
sip/DockAreaTitleBar_p.sip
Normal file
@@ -0,0 +1,37 @@
|
||||
%Import QtWidgets/QtWidgetsmod.sip
|
||||
|
||||
%If (Qt_5_0_0 -)
|
||||
|
||||
namespace ads
|
||||
{
|
||||
|
||||
class CTitleBarButton : QToolButton
|
||||
{
|
||||
%TypeHeaderCode
|
||||
#include <DockAreaTitleBar_p.h>
|
||||
%End
|
||||
|
||||
protected:
|
||||
bool event(QEvent *ev);
|
||||
|
||||
public:
|
||||
CTitleBarButton(bool visible = true, QWidget* parent /TransferThis/ = Q_NULLPTR );
|
||||
virtual void setVisible(bool visible);
|
||||
};
|
||||
|
||||
|
||||
class CSpacerWidget : QWidget
|
||||
{
|
||||
%TypeHeaderCode
|
||||
#include <DockAreaTitleBar_p.h>
|
||||
%End
|
||||
|
||||
public:
|
||||
CSpacerWidget(QWidget* Parent /TransferThis/ = 0 );
|
||||
virtual QSize sizeHint() const;
|
||||
virtual QSize minimumSizeHint() const;
|
||||
};
|
||||
|
||||
};
|
||||
|
||||
%End
|
||||
@@ -4,7 +4,7 @@
|
||||
|
||||
namespace ads
|
||||
{
|
||||
|
||||
|
||||
class CDockAreaWidget : QFrame
|
||||
{
|
||||
|
||||
@@ -28,10 +28,18 @@ protected slots:
|
||||
void toggleView(bool Open);
|
||||
|
||||
public:
|
||||
enum eDockAreaFlag
|
||||
{
|
||||
HideSingleWidgetTitleBar,
|
||||
DefaultFlags
|
||||
};
|
||||
typedef QFlags<ads::CDockAreaWidget::eDockAreaFlag> DockAreaFlags;
|
||||
|
||||
CDockAreaWidget(ads::CDockManager* DockManager /TransferThis/, ads::CDockContainerWidget* parent /TransferThis/);
|
||||
virtual ~CDockAreaWidget();
|
||||
ads::CDockManager* dockManager() const;
|
||||
ads::CDockContainerWidget* dockContainer() const;
|
||||
virtual QSize minimumSizeHint() const;
|
||||
QRect titleBarGeometry() const;
|
||||
QRect contentAreaGeometry() const;
|
||||
int dockWidgetsCount() const;
|
||||
@@ -51,6 +59,12 @@ public:
|
||||
void setAllowedAreas(DockWidgetAreas areas);
|
||||
DockWidgetAreas allowedAreas() const;
|
||||
CDockAreaTitleBar* titleBar() const;
|
||||
|
||||
DockAreaFlags dockAreaFlags() const;
|
||||
void setDockAreaFlags(DockAreaFlags Flags);
|
||||
void setDockAreaFlag(eDockAreaFlag Flag, bool On);
|
||||
|
||||
bool isCentralWidgetArea() const;
|
||||
|
||||
public slots:
|
||||
void setCurrentIndex(int index);
|
||||
|
||||
@@ -16,7 +16,7 @@ public:
|
||||
virtual CDockAreaTabBar* createDockAreaTabBar(CDockAreaWidget* DockArea /Transfer/ ) const;
|
||||
virtual CDockAreaTitleBar* createDockAreaTitleBar(CDockAreaWidget* DockArea /Transfer/ ) const;
|
||||
static const CDockComponentsFactory* factory();
|
||||
static void setFactory(CDockComponentsFactory* Factory);
|
||||
static void setFactory(CDockComponentsFactory* Factory /KeepReference/);
|
||||
static void resetDefaultFactory();
|
||||
|
||||
};
|
||||
|
||||
@@ -32,6 +32,7 @@ protected:
|
||||
ads::CDockWidget* topLevelDockWidget() const;
|
||||
ads::CDockAreaWidget* topLevelDockArea() const;
|
||||
QList<ads::CDockWidget*> dockWidgets() const;
|
||||
void updateSplitterHandles(QSplitter* splitter);
|
||||
|
||||
public:
|
||||
/**
|
||||
|
||||
32
sip/DockFocusController.sip
Normal file
@@ -0,0 +1,32 @@
|
||||
%Import QtWidgets/QtWidgetsmod.sip
|
||||
|
||||
%If (Qt_5_0_0 -)
|
||||
|
||||
namespace ads
|
||||
{
|
||||
|
||||
/**
|
||||
* Manages focus styling of dock widgets and handling of focus changes
|
||||
*/
|
||||
class CDockFocusController : QObject
|
||||
{
|
||||
%TypeHeaderCode
|
||||
#include <DockFocusController.h>
|
||||
%End
|
||||
|
||||
public:
|
||||
CDockFocusController(ads::CDockManager* DockManager);
|
||||
virtual ~CDockFocusController();
|
||||
|
||||
void notifyWidgetOrAreaRelocation(QWidget* RelocatedWidget);
|
||||
void notifyFloatingWidgetDrop(ads::CFloatingDockContainer* FloatingWidget);
|
||||
ads::CDockWidget* focusedDockWidget() const;
|
||||
|
||||
public slots:
|
||||
void setDockWidgetFocused(ads::CDockWidget* focusedNow);
|
||||
|
||||
}; // class DockFocusController
|
||||
};
|
||||
// namespace ads
|
||||
|
||||
%End
|
||||
@@ -1,7 +1,7 @@
|
||||
%Import QtWidgets/QtWidgetsmod.sip
|
||||
|
||||
%If (Qt_5_0_0 -)
|
||||
|
||||
|
||||
%MappedType QMap<QString, ads::CDockWidget*>
|
||||
/TypeHint="Dict[QString, CDockWidget*]", TypeHintValue="{}"/
|
||||
{
|
||||
@@ -133,6 +133,9 @@ protected:
|
||||
void removeDockContainer(ads::CDockContainerWidget* DockContainer /TransferBack/);
|
||||
ads::CDockOverlay* containerOverlay() const;
|
||||
ads::CDockOverlay* dockAreaOverlay() const;
|
||||
void notifyWidgetOrAreaRelocation(QWidget* RelocatedWidget);
|
||||
void notifyFloatingWidgetDrop(ads::CFloatingDockContainer* FloatingWidget);
|
||||
ads::CDockWidget* focusedDockWidget() const;
|
||||
|
||||
virtual void showEvent(QShowEvent *event);
|
||||
|
||||
@@ -165,12 +168,16 @@ public:
|
||||
DockAreaDynamicTabsMenuButtonVisibility,
|
||||
FloatingContainerHasWidgetTitle,
|
||||
FloatingContainerHasWidgetIcon,
|
||||
HideSingleCentralWidgetTitleBar,
|
||||
FocusHighlighting,
|
||||
EqualSplitOnInsertion,
|
||||
FloatingContainerForceNativeTitleBar,
|
||||
FloatingContainerForceQWidgetTitleBar,
|
||||
DefaultDockAreaButtons,
|
||||
DefaultBaseConfig,
|
||||
DefaultOpaqueConfig,
|
||||
DefaultNonOpaqueConfig,
|
||||
NonOpaqueWithWindowFrame,
|
||||
HideSingleCentralWidgetTitleBar,
|
||||
};
|
||||
typedef QFlags<ads::CDockManager::eConfigFlag> ConfigFlags;
|
||||
|
||||
@@ -194,14 +201,16 @@ public:
|
||||
const QList<ads::CDockContainerWidget*> dockContainers() const;
|
||||
const QList<ads::CFloatingDockContainer*> floatingWidgets() const;
|
||||
unsigned int zOrderIndex() const;
|
||||
QByteArray saveState(int version = 1) const;
|
||||
bool restoreState(const QByteArray &state, int version = 1);
|
||||
QByteArray saveState(int version = 0) const;
|
||||
bool restoreState(const QByteArray &state, int version = 0);
|
||||
void addPerspective(const QString& UniquePrespectiveName);
|
||||
void removePerspective(const QString& Name);
|
||||
void removePerspectives(const QStringList& Names);
|
||||
QStringList perspectiveNames() const;
|
||||
void savePerspectives(QSettings& Settings) const;
|
||||
void loadPerspectives(QSettings& Settings);
|
||||
CDockWidget* centralWidget() const;
|
||||
CDockAreaWidget* setCentralWidget(CDockWidget* widget /Transfer/);
|
||||
QAction* addToggleViewActionToMenu(QAction* ToggleViewAction /Transfer/,
|
||||
const QString& Group = QString(), const QIcon& GroupIcon = QIcon());
|
||||
QMenu* viewMenu() const;
|
||||
@@ -211,6 +220,7 @@ public:
|
||||
|
||||
public slots:
|
||||
void openPerspective(const QString& PerspectiveName);
|
||||
void setDockWidgetFocused(ads::CDockWidget* DockWidget);
|
||||
|
||||
signals:
|
||||
void perspectiveListChanged();
|
||||
@@ -219,10 +229,12 @@ signals:
|
||||
void stateRestored();
|
||||
void openingPerspective(const QString& PerspectiveName);
|
||||
void perspectiveOpened(const QString& PerspectiveName);
|
||||
void floatingWidgetCreated(CFloatingDockContainer* FloatingWidget);
|
||||
void dockAreaCreated(ads::CDockAreaWidget* DockArea);
|
||||
void dockWidgetAboutToBeRemoved(ads::CDockWidget* DockWidget);
|
||||
void dockWidgetRemoved(ads::CDockWidget* DockWidget);
|
||||
void floatingWidgetCreated(ads::CFloatingDockContainer*);
|
||||
void dockAreaCreated(ads::CDockAreaWidget*);
|
||||
void dockWidgetAdded(ads::CDockWidget* DockWidget);
|
||||
void dockWidgetAboutToBeRemoved(ads::CDockWidget*);
|
||||
void dockWidgetRemoved(ads::CDockWidget*);
|
||||
void focusedDockWidgetChanged(ads::CDockWidget*, ads::CDockWidget*);
|
||||
};
|
||||
|
||||
};
|
||||
|
||||
@@ -18,6 +18,7 @@ public:
|
||||
bool hasVisibleContent() const;
|
||||
QWidget* firstWidget() const;
|
||||
QWidget* lastWidget() const;
|
||||
bool isResizingWithContainer() const;
|
||||
|
||||
};
|
||||
|
||||
|
||||
@@ -31,6 +31,8 @@ public:
|
||||
DockWidgetFloatable,
|
||||
DockWidgetDeleteOnClose,
|
||||
CustomCloseHandling,
|
||||
DockWidgetFocusable,
|
||||
DockWidgetForceCloseWithArea,
|
||||
DefaultDockWidgetFeatures,
|
||||
AllDockWidgetFeatures,
|
||||
NoDockWidgetFeatures
|
||||
@@ -83,6 +85,7 @@ public:
|
||||
QAction* toggleViewAction() const;
|
||||
void setToggleViewActionMode(ads::CDockWidget::eToggleViewActionMode Mode);
|
||||
void setMinimumSizeHintMode(ads::CDockWidget::eMinimumSizeHintMode Mode);
|
||||
bool isCentralWidget() const;
|
||||
void setIcon(const QIcon& Icon);
|
||||
QIcon icon() const;
|
||||
QToolBar* toolBar() const;
|
||||
|
||||
@@ -33,7 +33,8 @@ public:
|
||||
bool isTitleElided() const;
|
||||
bool isClosable() const;
|
||||
virtual bool event(QEvent *e);
|
||||
|
||||
void setElideMode(Qt::TextElideMode mode);
|
||||
void updateStyle();
|
||||
|
||||
public slots:
|
||||
virtual void setVisible(bool visible);
|
||||
|
||||
@@ -27,6 +27,7 @@ public:
|
||||
|
||||
virtual void moveFloating() = 0;
|
||||
virtual void finishDragging() = 0;
|
||||
virtual ~IFloatingWidget();
|
||||
};
|
||||
|
||||
|
||||
@@ -51,11 +52,24 @@ protected:
|
||||
|
||||
protected:
|
||||
virtual void changeEvent(QEvent *event);
|
||||
virtual void moveEvent(QMoveEvent *event);
|
||||
virtual bool event(QEvent *e);
|
||||
virtual void closeEvent(QCloseEvent *event);
|
||||
virtual void hideEvent(QHideEvent *event);
|
||||
virtual void showEvent(QShowEvent *event);
|
||||
|
||||
%If (WS_MACX)
|
||||
virtual bool event(QEvent *e);
|
||||
virtual void moveEvent(QMoveEvent *event);
|
||||
%End
|
||||
|
||||
%If (WS_X11)
|
||||
virtual void moveEvent(QMoveEvent *event);
|
||||
virtual void resizeEvent(QResizeEvent *event);
|
||||
%End
|
||||
|
||||
%If (WS_WIN)
|
||||
virtual bool nativeEvent(const QByteArray &eventType, void *message, long *result);
|
||||
%End
|
||||
|
||||
|
||||
public:
|
||||
CFloatingDockContainer(ads::CDockManager* DockManager /TransferThis/);
|
||||
@@ -67,6 +81,15 @@ public:
|
||||
bool hasTopLevelDockWidget() const;
|
||||
ads::CDockWidget* topLevelDockWidget() const;
|
||||
QList<ads::CDockWidget*> dockWidgets() const;
|
||||
|
||||
%If (WS_X11)
|
||||
void onMaximizeRequest();
|
||||
void showNormal(bool fixGeometry);
|
||||
void showMaximized();
|
||||
bool isMaximized() const;
|
||||
void show();
|
||||
bool hasNativeTitleBar();
|
||||
%End
|
||||
};
|
||||
|
||||
};
|
||||
|
||||
@@ -13,7 +13,6 @@ class CFloatingDragPreview : QWidget, ads::IFloatingWidget
|
||||
%End
|
||||
|
||||
protected:
|
||||
virtual void moveEvent(QMoveEvent *event);
|
||||
virtual void paintEvent(QPaintEvent *e);
|
||||
CFloatingDragPreview(QWidget* Content /TransferThis/, QWidget* parent /TransferThis/);
|
||||
|
||||
|
||||
@@ -5,11 +5,13 @@
|
||||
%Include ads_globals.sip
|
||||
%Include DockWidget.sip
|
||||
%Include DockAreaTabBar.sip
|
||||
%Include DockAreaTitleBar_p.sip
|
||||
%Include DockAreaTitleBar.sip
|
||||
%Include DockAreaWidget.sip
|
||||
%Include DockComponentsFactory.sip
|
||||
%Include DockContainerWidget.sip
|
||||
%Include DockingStateReader.sip
|
||||
%Include DockFocusController.sip
|
||||
%Include DockManager.sip
|
||||
%Include DockOverlay.sip
|
||||
%Include DockSplitter.sip
|
||||
|
||||
@@ -8,13 +8,6 @@ namespace ads
|
||||
#include <ads_globals.h>
|
||||
%End
|
||||
|
||||
enum eStateFileVersion
|
||||
{
|
||||
InitialVerison,
|
||||
Version1,
|
||||
CurrentVersion
|
||||
};
|
||||
|
||||
enum DockWidgetArea
|
||||
{
|
||||
NoDockWidgetArea,
|
||||
|
||||
@@ -15,15 +15,24 @@ protected:
|
||||
virtual void mousePressEvent(QMouseEvent *ev);
|
||||
virtual void mouseReleaseEvent(QMouseEvent *ev);
|
||||
virtual void mouseMoveEvent(QMouseEvent *ev);
|
||||
virtual void mouseDoubleClickEvent(QMouseEvent *event);
|
||||
|
||||
void setMaximizeIcon(const QIcon& Icon);
|
||||
QIcon maximizeIcon() const;
|
||||
void setNormalIcon(const QIcon& Icon);
|
||||
QIcon normalIcon() const;
|
||||
|
||||
public:
|
||||
explicit CFloatingWidgetTitleBar(CFloatingDockContainer *parent /TransferThis/ = 0);
|
||||
virtual ~CFloatingWidgetTitleBar();
|
||||
void enableCloseButton(bool Enable);
|
||||
void setTitle(const QString &Text);
|
||||
void updateStyle();
|
||||
void setMaximizedIcon(bool maximized);
|
||||
|
||||
signals:
|
||||
void closeRequested();
|
||||
void maximizeRequested();
|
||||
};
|
||||
|
||||
};
|
||||
|
||||
115
src/CMakeLists.txt
Normal file
@@ -0,0 +1,115 @@
|
||||
cmake_minimum_required(VERSION 3.5)
|
||||
project(QtAdvancedDockingSystem LANGUAGES CXX VERSION ${VERSION_SHORT})
|
||||
find_package(Qt5 5.5 COMPONENTS Core Gui Widgets REQUIRED)
|
||||
if (UNIX AND NOT APPLE)
|
||||
find_package(Qt5 5.5 COMPONENTS X11Extras REQUIRED)
|
||||
endif()
|
||||
set(CMAKE_INCLUDE_CURRENT_DIR ON)
|
||||
if(BUILD_STATIC)
|
||||
set(CMAKE_STATIC_LIBRARY_SUFFIX "_static${CMAKE_STATIC_LIBRARY_SUFFIX}")
|
||||
endif()
|
||||
set(ads_SRCS
|
||||
ads_globals.cpp
|
||||
DockAreaTabBar.cpp
|
||||
DockAreaTitleBar.cpp
|
||||
DockAreaWidget.cpp
|
||||
DockContainerWidget.cpp
|
||||
DockManager.cpp
|
||||
DockOverlay.cpp
|
||||
DockSplitter.cpp
|
||||
DockWidget.cpp
|
||||
DockWidgetTab.cpp
|
||||
DockingStateReader.cpp
|
||||
DockFocusController.cpp
|
||||
ElidingLabel.cpp
|
||||
FloatingDockContainer.cpp
|
||||
FloatingDragPreview.cpp
|
||||
IconProvider.cpp
|
||||
DockComponentsFactory.cpp
|
||||
ads.qrc
|
||||
)
|
||||
set(ads_HEADERS
|
||||
ads_globals.h
|
||||
DockAreaTabBar.h
|
||||
DockAreaTitleBar.h
|
||||
DockAreaTitleBar_p.h
|
||||
DockAreaWidget.h
|
||||
DockContainerWidget.h
|
||||
DockManager.h
|
||||
DockOverlay.h
|
||||
DockSplitter.h
|
||||
DockWidget.h
|
||||
DockWidgetTab.h
|
||||
DockingStateReader.h
|
||||
DockFocusController.h
|
||||
ElidingLabel.h
|
||||
FloatingDockContainer.h
|
||||
FloatingDragPreview.h
|
||||
IconProvider.h
|
||||
DockComponentsFactory.h
|
||||
)
|
||||
if (UNIX AND NOT APPLE)
|
||||
set(ads_SRCS linux/FloatingWidgetTitleBar.cpp ${ads_SRCS})
|
||||
set(ads_HEADERS linux/FloatingWidgetTitleBar.h ${ads_HEADERS})
|
||||
endif()
|
||||
if(BUILD_STATIC)
|
||||
add_library(qtadvanceddocking STATIC ${ads_SRCS} ${ads_HEADERS})
|
||||
target_compile_definitions(qtadvanceddocking PUBLIC ADS_STATIC)
|
||||
else()
|
||||
add_library(qtadvanceddocking SHARED ${ads_SRCS} ${ads_HEADERS})
|
||||
target_compile_definitions(qtadvanceddocking PRIVATE ADS_SHARED_EXPORT)
|
||||
endif()
|
||||
target_link_libraries(qtadvanceddocking PUBLIC Qt5::Core Qt5::Gui Qt5::Widgets)
|
||||
if(UNIX AND NOT APPLE)
|
||||
target_link_libraries(qtadvanceddocking PUBLIC Qt5::X11Extras)
|
||||
target_link_libraries(qtadvanceddocking PRIVATE xcb)
|
||||
endif()
|
||||
set_target_properties(qtadvanceddocking PROPERTIES
|
||||
AUTOMOC ON
|
||||
AUTORCC ON
|
||||
CXX_STANDARD 14
|
||||
CXX_STANDARD_REQUIRED ON
|
||||
CXX_EXTENSIONS OFF
|
||||
VERSION ${VERSION_SHORT}
|
||||
EXPORT_NAME "qtadvanceddocking"
|
||||
ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/lib"
|
||||
RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${ads_PlatformDir}/bin"
|
||||
)
|
||||
include(CMakePackageConfigHelpers)
|
||||
write_basic_package_version_file(
|
||||
"qtadvanceddockingConfigVersion.cmake"
|
||||
VERSION ${VERSION_SHORT}
|
||||
COMPATIBILITY SameMajorVersion
|
||||
)
|
||||
install(FILES ${ads_HEADERS}
|
||||
DESTINATION include
|
||||
COMPONENT headers
|
||||
)
|
||||
install(FILES
|
||||
"${CMAKE_SOURCE_DIR}/LICENSE"
|
||||
"${CMAKE_SOURCE_DIR}/gnu-lgpl-v2.1.md"
|
||||
DESTINATION license
|
||||
COMPONENT license
|
||||
)
|
||||
install(TARGETS qtadvanceddocking
|
||||
EXPORT adsTargets
|
||||
RUNTIME DESTINATION bin
|
||||
LIBRARY DESTINATION lib
|
||||
ARCHIVE DESTINATION lib
|
||||
INCLUDES DESTINATION include
|
||||
)
|
||||
|
||||
install(EXPORT adsTargets
|
||||
FILE adsTargets.cmake
|
||||
NAMESPACE ads::
|
||||
DESTINATION lib/cmake/qtadvanceddocking
|
||||
)
|
||||
install(FILES qtadvanceddockingConfig.cmake "${CMAKE_CURRENT_BINARY_DIR}/qtadvanceddockingConfigVersion.cmake"
|
||||
DESTINATION lib/cmake/qtadvanceddocking
|
||||
)
|
||||
|
||||
target_include_directories(qtadvanceddocking PUBLIC
|
||||
$<INSTALL_INTERFACE:include>
|
||||
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}>
|
||||
)
|
||||
@@ -27,7 +27,7 @@
|
||||
//============================================================================
|
||||
// INCLUDES
|
||||
//============================================================================
|
||||
#include <FloatingDragPreview.h>
|
||||
#include "FloatingDragPreview.h"
|
||||
#include "DockAreaTabBar.h"
|
||||
|
||||
#include <QMouseEvent>
|
||||
@@ -138,6 +138,8 @@ CDockAreaTabBar::CDockAreaTabBar(CDockAreaWidget* parent) :
|
||||
d->TabsLayout->addStretch(1);
|
||||
d->TabsContainerWidget->setLayout(d->TabsLayout);
|
||||
setWidget(d->TabsContainerWidget);
|
||||
|
||||
setFocusPolicy(Qt::NoFocus);
|
||||
}
|
||||
|
||||
|
||||
@@ -205,10 +207,14 @@ void CDockAreaTabBar::insertTab(int Index, CDockWidgetTab* Tab)
|
||||
connect(Tab, SIGNAL(elidedChanged(bool)), this, SIGNAL(elidedChanged(bool)));
|
||||
Tab->installEventFilter(this);
|
||||
emit tabInserted(Index);
|
||||
if (Index <= d->CurrentIndex || d->CurrentIndex == -1)
|
||||
if (Index <= d->CurrentIndex)
|
||||
{
|
||||
setCurrentIndex(d->CurrentIndex + 1);
|
||||
}
|
||||
}
|
||||
else if (d->CurrentIndex == -1)
|
||||
{
|
||||
setCurrentIndex(Index);
|
||||
}
|
||||
|
||||
updateGeometry();
|
||||
}
|
||||
@@ -452,6 +458,11 @@ bool CDockAreaTabBar::eventFilter(QObject *watched, QEvent *event)
|
||||
updateGeometry();
|
||||
break;
|
||||
|
||||
// Setting the text of a tab will cause a LayoutRequest event
|
||||
case QEvent::LayoutRequest:
|
||||
updateGeometry();
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -39,6 +39,7 @@
|
||||
#include <QDebug>
|
||||
#include <QPointer>
|
||||
|
||||
#include "DockAreaTitleBar_p.h"
|
||||
#include "ads_globals.h"
|
||||
#include "FloatingDockContainer.h"
|
||||
#include "FloatingDragPreview.h"
|
||||
@@ -55,8 +56,6 @@
|
||||
|
||||
namespace ads
|
||||
{
|
||||
using tTitleBarButton = QToolButton;
|
||||
|
||||
|
||||
/**
|
||||
* Private data class of CDockAreaTitleBar class (pimpl)
|
||||
@@ -104,10 +103,11 @@ struct DockAreaTitleBarPrivate
|
||||
|
||||
/**
|
||||
* Returns true if the given config flag is set
|
||||
* Convenience function to ease config flag testing
|
||||
*/
|
||||
static bool testConfigFlag(CDockManager::eConfigFlag Flag)
|
||||
{
|
||||
return CDockManager::configFlags().testFlag(Flag);
|
||||
return CDockManager::testConfigFlag(Flag);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -130,86 +130,6 @@ struct DockAreaTitleBarPrivate
|
||||
IFloatingWidget* makeAreaFloating(const QPoint& Offset, eDragState DragState);
|
||||
};// struct DockAreaTitleBarPrivate
|
||||
|
||||
|
||||
/**
|
||||
* Title bar button of a dock area that customizes tTitleBarButton appearance/behaviour
|
||||
* according to various config flags such as:
|
||||
* CDockManager::DockAreaHas_xxx_Button - if set to 'false' keeps the button always invisible
|
||||
* CDockManager::DockAreaHideDisabledButtons - if set to 'true' hides button when it is disabled
|
||||
*/
|
||||
class CTitleBarButton : public tTitleBarButton
|
||||
{
|
||||
Q_OBJECT
|
||||
bool Visible = true;
|
||||
bool HideWhenDisabled = false;
|
||||
public:
|
||||
using Super = tTitleBarButton;
|
||||
CTitleBarButton(bool visible = true, QWidget* parent = nullptr)
|
||||
: tTitleBarButton(parent),
|
||||
Visible(visible),
|
||||
HideWhenDisabled(DockAreaTitleBarPrivate::testConfigFlag(CDockManager::DockAreaHideDisabledButtons))
|
||||
{}
|
||||
|
||||
|
||||
/**
|
||||
* Adjust this visibility change request with our internal settings:
|
||||
*/
|
||||
virtual void setVisible(bool visible) override
|
||||
{
|
||||
// 'visible' can stay 'true' if and only if this button is configured to generaly visible:
|
||||
visible = visible && this->Visible;
|
||||
|
||||
// 'visible' can stay 'true' unless: this button is configured to be invisible when it is disabled and it is currently disabled:
|
||||
if(visible && HideWhenDisabled)
|
||||
{
|
||||
visible = isEnabled();
|
||||
}
|
||||
|
||||
Super::setVisible(visible);
|
||||
}
|
||||
|
||||
protected:
|
||||
/**
|
||||
* Handle EnabledChanged signal to set button invisible if the configured
|
||||
*/
|
||||
bool event(QEvent *ev) override
|
||||
{
|
||||
if(QEvent::EnabledChange == ev->type() && HideWhenDisabled)
|
||||
{
|
||||
// force setVisible() call
|
||||
// Calling setVisible() directly here doesn't work well when button is expected to be shown first time
|
||||
QMetaObject::invokeMethod(this, "setVisible", Qt::QueuedConnection, Q_ARG(bool, isEnabled()));
|
||||
}
|
||||
|
||||
return Super::event(ev);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* This spacer widget is here because of the following problem.
|
||||
* The dock area title bar handles mouse dragging and moving the floating widget.
|
||||
* The problem is, that if the title bar becomes invisible, i.e. if the dock
|
||||
* area contains only one single dock widget and the dock area is moved
|
||||
* into a floating widget, then mouse events are not handled anymore and dragging
|
||||
* of the floating widget stops.
|
||||
*/
|
||||
class CSpacerWidget : public QWidget
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
using Super = QWidget;
|
||||
CSpacerWidget(QWidget* Parent = 0)
|
||||
: Super(Parent)
|
||||
{
|
||||
setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
|
||||
setStyleSheet("border: none; background: none;");
|
||||
}
|
||||
virtual QSize sizeHint() const override {return QSize(0, 0);}
|
||||
virtual QSize minimumSizeHint() const override {return QSize(0, 0);}
|
||||
};
|
||||
|
||||
|
||||
//============================================================================
|
||||
DockAreaTitleBarPrivate::DockAreaTitleBarPrivate(CDockAreaTitleBar* _public) :
|
||||
_this(_public)
|
||||
@@ -243,7 +163,7 @@ void DockAreaTitleBarPrivate::createButtons()
|
||||
|
||||
// Undock button
|
||||
UndockButton = new CTitleBarButton(testConfigFlag(CDockManager::DockAreaHasUndockButton));
|
||||
UndockButton->setObjectName("undockButton");
|
||||
UndockButton->setObjectName("detachGroupButton");
|
||||
UndockButton->setAutoRaise(true);
|
||||
internal::setToolTip(UndockButton, QObject::tr("Detach Group"));
|
||||
internal::setButtonIcon(UndockButton, QStyle::SP_TitleBarNormalButton, ads::DockAreaUndockIcon);
|
||||
@@ -253,7 +173,7 @@ void DockAreaTitleBarPrivate::createButtons()
|
||||
|
||||
// Close button
|
||||
CloseButton = new CTitleBarButton(testConfigFlag(CDockManager::DockAreaHasCloseButton));
|
||||
CloseButton->setObjectName("closeButton");
|
||||
CloseButton->setObjectName("dockAreaCloseButton");
|
||||
CloseButton->setAutoRaise(true);
|
||||
internal::setButtonIcon(CloseButton, QStyle::SP_TitleBarCloseButton, ads::DockAreaCloseIcon);
|
||||
if (testConfigFlag(CDockManager::DockAreaCloseButtonClosesTab))
|
||||
@@ -293,7 +213,7 @@ IFloatingWidget* DockAreaTitleBarPrivate::makeAreaFloating(const QPoint& Offset,
|
||||
{
|
||||
QSize Size = DockArea->size();
|
||||
this->DragState = DragState;
|
||||
bool OpaqueUndocking = CDockManager::configFlags().testFlag(CDockManager::OpaqueUndocking) ||
|
||||
bool OpaqueUndocking = CDockManager::testConfigFlag(CDockManager::OpaqueUndocking) ||
|
||||
(DraggingFloatingWidget != DragState);
|
||||
CFloatingDockContainer* FloatingDockContainer = nullptr;
|
||||
IFloatingWidget* FloatingWidget;
|
||||
@@ -349,6 +269,8 @@ CDockAreaTitleBar::CDockAreaTitleBar(CDockAreaWidget* parent) :
|
||||
d->createTabBar();
|
||||
d->Layout->addWidget(new CSpacerWidget(this));
|
||||
d->createButtons();
|
||||
|
||||
setFocusPolicy(Qt::NoFocus);
|
||||
}
|
||||
|
||||
|
||||
@@ -546,6 +468,11 @@ void CDockAreaTitleBar::mousePressEvent(QMouseEvent* ev)
|
||||
ev->accept();
|
||||
d->DragStartMousePos = ev->pos();
|
||||
d->DragState = DraggingMousePressed;
|
||||
|
||||
if (CDockManager::testConfigFlag(CDockManager::FocusHighlighting))
|
||||
{
|
||||
d->TabBar->currentTab()->setFocus(Qt::OtherFocusReason);
|
||||
}
|
||||
return;
|
||||
}
|
||||
Super::mousePressEvent(ev);
|
||||
@@ -566,6 +493,7 @@ void CDockAreaTitleBar::mouseReleaseEvent(QMouseEvent* ev)
|
||||
{
|
||||
d->FloatingWidget->finishDragging();
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
Super::mouseReleaseEvent(ev);
|
||||
@@ -589,7 +517,7 @@ void CDockAreaTitleBar::mouseMoveEvent(QMouseEvent* ev)
|
||||
return;
|
||||
}
|
||||
|
||||
// If this is the last dock area in a dock container it does not make
|
||||
// If this is the last dock area in a floating dock container it does not make
|
||||
// sense to move it to a new floating widget and leave this one
|
||||
// empty
|
||||
if (d->DockArea->dockContainer()->isFloating()
|
||||
@@ -612,7 +540,7 @@ void CDockAreaTitleBar::mouseMoveEvent(QMouseEvent* ev)
|
||||
int DragDistance = (d->DragStartMousePos - ev->pos()).manhattanLength();
|
||||
if (DragDistance >= CDockManager::startDragDistance())
|
||||
{
|
||||
ADS_PRINT("CTabsScrollArea::startFloating");
|
||||
ADS_PRINT("CDockAreaTitlBar::startFloating");
|
||||
d->startFloating(d->DragStartMousePos);
|
||||
auto Overlay = d->DockArea->dockManager()->containerOverlay();
|
||||
Overlay->setAllowedAreas(OuterDockAreas);
|
||||
@@ -651,12 +579,12 @@ void CDockAreaTitleBar::contextMenuEvent(QContextMenuEvent* ev)
|
||||
}
|
||||
|
||||
QMenu Menu(this);
|
||||
auto Action = Menu.addAction(tr("Detach Area"), this, SLOT(onUndockButtonClicked()));
|
||||
auto Action = Menu.addAction(tr("Detach Group"), this, SLOT(onUndockButtonClicked()));
|
||||
Action->setEnabled(d->DockArea->features().testFlag(CDockWidget::DockWidgetFloatable));
|
||||
Menu.addSeparator();
|
||||
Action = Menu.addAction(tr("Close Area"), this, SLOT(onCloseButtonClicked()));
|
||||
Action = Menu.addAction(tr("Close Group"), this, SLOT(onCloseButtonClicked()));
|
||||
Action->setEnabled(d->DockArea->features().testFlag(CDockWidget::DockWidgetClosable));
|
||||
Menu.addAction(tr("Close Other Areas"), d->DockArea, SLOT(closeOtherAreas()));
|
||||
Menu.addAction(tr("Close Other Groups"), d->DockArea, SLOT(closeOtherAreas()));
|
||||
Menu.exec(ev->globalPos());
|
||||
}
|
||||
|
||||
@@ -674,10 +602,51 @@ int CDockAreaTitleBar::indexOf(QWidget *widget) const
|
||||
return d->Layout->indexOf(widget);
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
CTitleBarButton::CTitleBarButton(bool visible, QWidget* parent)
|
||||
: tTitleBarButton(parent),
|
||||
Visible(visible),
|
||||
HideWhenDisabled(CDockManager::testConfigFlag(CDockManager::DockAreaHideDisabledButtons))
|
||||
{
|
||||
setFocusPolicy(Qt::NoFocus);
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
void CTitleBarButton::setVisible(bool visible)
|
||||
{
|
||||
// 'visible' can stay 'true' if and only if this button is configured to generaly visible:
|
||||
visible = visible && this->Visible;
|
||||
|
||||
// 'visible' can stay 'true' unless: this button is configured to be invisible when it is disabled and it is currently disabled:
|
||||
if (visible && HideWhenDisabled)
|
||||
{
|
||||
visible = isEnabled();
|
||||
}
|
||||
|
||||
Super::setVisible(visible);
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
bool CTitleBarButton::event(QEvent *ev)
|
||||
{
|
||||
if (QEvent::EnabledChange == ev->type() && HideWhenDisabled)
|
||||
{
|
||||
// force setVisible() call
|
||||
// Calling setVisible() directly here doesn't work well when button is expected to be shown first time
|
||||
QMetaObject::invokeMethod(this, "setVisible", Qt::QueuedConnection, Q_ARG(bool, isEnabled()));
|
||||
}
|
||||
|
||||
return Super::event(ev);
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
CSpacerWidget::CSpacerWidget(QWidget* Parent /*= 0*/) : Super(Parent)
|
||||
{
|
||||
setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
|
||||
setStyleSheet("border: none; background: none;");
|
||||
}
|
||||
|
||||
} // namespace ads
|
||||
|
||||
#include "DockAreaTitleBar.moc"
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
// EOF DockAreaTitleBar.cpp
|
||||
|
||||
@@ -34,7 +34,7 @@
|
||||
|
||||
#include "ads_globals.h"
|
||||
|
||||
class QAbstractButton;
|
||||
QT_FORWARD_DECLARE_CLASS(QAbstractButton)
|
||||
|
||||
namespace ads
|
||||
{
|
||||
@@ -86,7 +86,7 @@ protected:
|
||||
/**
|
||||
* Show context menu
|
||||
*/
|
||||
virtual void contextMenuEvent(QContextMenuEvent *event);
|
||||
virtual void contextMenuEvent(QContextMenuEvent *event) override;
|
||||
|
||||
public slots:
|
||||
/**
|
||||
@@ -155,6 +155,7 @@ signals:
|
||||
*/
|
||||
void tabBarClicked(int index);
|
||||
}; // class name
|
||||
|
||||
}
|
||||
// namespace ads
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
94
src/DockAreaTitleBar_p.h
Normal file
@@ -0,0 +1,94 @@
|
||||
#ifndef DockAreaTitleBar_pH
|
||||
#define DockAreaTitleBar_pH
|
||||
/*******************************************************************************
|
||||
** Qt Advanced Docking System
|
||||
** Copyright (C) 2017 Uwe Kindler
|
||||
**
|
||||
** This library is free software; you can redistribute it and/or
|
||||
** modify it under the terms of the GNU Lesser General Public
|
||||
** License as published by the Free Software Foundation; either
|
||||
** version 2.1 of the License, or (at your option) any later version.
|
||||
**
|
||||
** This library 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
|
||||
** Lesser General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU Lesser General Public
|
||||
** License along with this library; If not, see <http://www.gnu.org/licenses/>.
|
||||
******************************************************************************/
|
||||
|
||||
|
||||
//============================================================================
|
||||
/// \file DockAreaTitleBar_p.h
|
||||
/// \author Uwe Kindler
|
||||
/// \date 12.10.2018
|
||||
/// \brief Declaration of classes CTitleBarButton and CSpacerWidget
|
||||
//============================================================================
|
||||
|
||||
|
||||
//============================================================================
|
||||
// INCLUDES
|
||||
//============================================================================
|
||||
#include <QFrame>
|
||||
#include <QToolButton>
|
||||
|
||||
#include "ads_globals.h"
|
||||
|
||||
namespace ads
|
||||
{
|
||||
using tTitleBarButton = QToolButton;
|
||||
|
||||
/**
|
||||
* Title bar button of a dock area that customizes tTitleBarButton appearance/behaviour
|
||||
* according to various config flags such as:
|
||||
* CDockManager::DockAreaHas_xxx_Button - if set to 'false' keeps the button always invisible
|
||||
* CDockManager::DockAreaHideDisabledButtons - if set to 'true' hides button when it is disabled
|
||||
*/
|
||||
class CTitleBarButton : public tTitleBarButton
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
private:
|
||||
bool Visible = true;
|
||||
bool HideWhenDisabled = false;
|
||||
|
||||
public:
|
||||
using Super = tTitleBarButton;
|
||||
CTitleBarButton(bool visible = true, QWidget* parent = nullptr);
|
||||
|
||||
/**
|
||||
* Adjust this visibility change request with our internal settings:
|
||||
*/
|
||||
virtual void setVisible(bool visible) override;
|
||||
|
||||
protected:
|
||||
/**
|
||||
* Handle EnabledChanged signal to set button invisible if the configured
|
||||
*/
|
||||
bool event(QEvent *ev) override;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* This spacer widget is here because of the following problem.
|
||||
* The dock area title bar handles mouse dragging and moving the floating widget.
|
||||
* The problem is, that if the title bar becomes invisible, i.e. if the dock
|
||||
* area contains only one single dock widget and the dock area is moved
|
||||
* into a floating widget, then mouse events are not handled anymore and dragging
|
||||
* of the floating widget stops.
|
||||
*/
|
||||
class CSpacerWidget : public QWidget
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
using Super = QWidget;
|
||||
CSpacerWidget(QWidget* Parent = 0);
|
||||
virtual QSize sizeHint() const override {return QSize(0, 0);}
|
||||
virtual QSize minimumSizeHint() const override {return QSize(0, 0);}
|
||||
};
|
||||
|
||||
}
|
||||
// namespace ads
|
||||
//-----------------------------------------------------------------------------
|
||||
#endif // DockAreaTitleBar_pH
|
||||
@@ -30,8 +30,6 @@
|
||||
//============================================================================
|
||||
#include "DockAreaWidget.h"
|
||||
|
||||
#include <iostream>
|
||||
|
||||
#include <QStackedLayout>
|
||||
#include <QScrollBar>
|
||||
#include <QScrollArea>
|
||||
@@ -136,6 +134,10 @@ public:
|
||||
m_CurrentWidget = nullptr;
|
||||
m_CurrentIndex = -1;
|
||||
}
|
||||
else if (indexOf(Widget) < m_CurrentIndex)
|
||||
{
|
||||
--m_CurrentIndex;
|
||||
}
|
||||
m_Widgets.removeOne(Widget);
|
||||
}
|
||||
|
||||
@@ -173,6 +175,7 @@ public:
|
||||
{
|
||||
LayoutItem->widget()->setParent(nullptr);
|
||||
}
|
||||
delete LayoutItem;
|
||||
|
||||
m_ParentLayout->addWidget(next);
|
||||
if (prev)
|
||||
@@ -233,6 +236,7 @@ public:
|
||||
|
||||
|
||||
using DockAreaLayout = CDockAreaLayout;
|
||||
static const DockWidgetAreas DefaultAllowedAreas = AllDockAreas;
|
||||
|
||||
|
||||
/**
|
||||
@@ -246,8 +250,9 @@ struct DockAreaWidgetPrivate
|
||||
CDockAreaTitleBar* TitleBar = nullptr;
|
||||
CDockManager* DockManager = nullptr;
|
||||
bool UpdateTitleBarButtons = false;
|
||||
DockWidgetAreas AllowedAreas = AllDockAreas;
|
||||
DockWidgetAreas AllowedAreas = DefaultAllowedAreas;
|
||||
QSize MinSizeHint;
|
||||
CDockAreaWidget::DockAreaFlags Flags{CDockAreaWidget::DefaultFlags};
|
||||
|
||||
/**
|
||||
* Private data constructor
|
||||
@@ -413,6 +418,7 @@ void CDockAreaWidget::insertDockWidget(int index, CDockWidget* DockWidget,
|
||||
bool Activate)
|
||||
{
|
||||
d->ContentsLayout->insertWidget(index, DockWidget);
|
||||
DockWidget->setDockArea(this);
|
||||
DockWidget->tabWidget()->setDockAreaWidget(this);
|
||||
auto TabWidget = DockWidget->tabWidget();
|
||||
// Inserting the tab will change the current index which in turn will
|
||||
@@ -428,8 +434,14 @@ void CDockAreaWidget::insertDockWidget(int index, CDockWidget* DockWidget,
|
||||
{
|
||||
setCurrentIndex(index);
|
||||
}
|
||||
DockWidget->setDockArea(this);
|
||||
// If this dock area is hidden, then we need to make it visible again
|
||||
// by calling DockWidget->toggleViewInternal(true);
|
||||
if (!this->isVisible() && d->ContentsLayout->count() > 1 && !dockManager()->isRestoringState())
|
||||
{
|
||||
DockWidget->toggleViewInternal(true);
|
||||
}
|
||||
d->updateTitleBarButtonStates();
|
||||
updateTitleBarVisibility();
|
||||
}
|
||||
|
||||
|
||||
@@ -437,24 +449,35 @@ void CDockAreaWidget::insertDockWidget(int index, CDockWidget* DockWidget,
|
||||
void CDockAreaWidget::removeDockWidget(CDockWidget* DockWidget)
|
||||
{
|
||||
ADS_PRINT("CDockAreaWidget::removeDockWidget");
|
||||
auto NextOpenDockWidget = nextOpenDockWidget(DockWidget);
|
||||
auto CurrentDockWidget = currentDockWidget();
|
||||
auto NextOpenDockWidget = (DockWidget == CurrentDockWidget) ? nextOpenDockWidget(DockWidget) : nullptr;
|
||||
|
||||
d->ContentsLayout->removeWidget(DockWidget);
|
||||
auto TabWidget = DockWidget->tabWidget();
|
||||
TabWidget->hide();
|
||||
d->tabBar()->removeTab(TabWidget);
|
||||
TabWidget->setParent(DockWidget);
|
||||
DockWidget->setDockArea(nullptr);
|
||||
CDockContainerWidget* DockContainer = dockContainer();
|
||||
if (NextOpenDockWidget)
|
||||
{
|
||||
setCurrentDockWidget(NextOpenDockWidget);
|
||||
}
|
||||
else if (d->ContentsLayout->isEmpty() && DockContainer->dockAreaCount() > 1)
|
||||
else if (d->ContentsLayout->isEmpty() && DockContainer->dockAreaCount() >= 1)
|
||||
{
|
||||
ADS_PRINT("Dock Area empty");
|
||||
DockContainer->removeDockArea(this);
|
||||
this->deleteLater();
|
||||
if(DockContainer->dockAreaCount() == 0)
|
||||
{
|
||||
if(CFloatingDockContainer* FloatingDockContainer = DockContainer->floatingWidget())
|
||||
{
|
||||
FloatingDockContainer->hide();
|
||||
FloatingDockContainer->deleteLater();
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
else if (DockWidget == CurrentDockWidget)
|
||||
{
|
||||
// if contents layout is not empty but there are no more open dock
|
||||
// widgets, then we need to hide the dock area because it does not
|
||||
@@ -725,7 +748,7 @@ void CDockAreaWidget::updateTitleBarVisibility()
|
||||
return;
|
||||
}
|
||||
|
||||
if (CDockManager::configFlags().testFlag(CDockManager::AlwaysShowTabs))
|
||||
if (CDockManager::testConfigFlag(CDockManager::AlwaysShowTabs))
|
||||
{
|
||||
return;
|
||||
}
|
||||
@@ -733,7 +756,8 @@ void CDockAreaWidget::updateTitleBarVisibility()
|
||||
if (d->TitleBar)
|
||||
{
|
||||
bool Hidden = Container->hasTopLevelDockWidget() && (Container->isFloating()
|
||||
|| CDockManager::configFlags().testFlag(CDockManager::HideSingleCentralWidgetTitleBar));
|
||||
|| CDockManager::testConfigFlag(CDockManager::HideSingleCentralWidgetTitleBar));
|
||||
Hidden |= (d->Flags.testFlag(HideSingleWidgetTitleBar) && openDockWidgetsCount() == 1);
|
||||
d->TitleBar->setVisible(!Hidden);
|
||||
}
|
||||
}
|
||||
@@ -758,6 +782,17 @@ void CDockAreaWidget::saveState(QXmlStreamWriter& s) const
|
||||
auto CurrentDockWidget = currentDockWidget();
|
||||
QString Name = CurrentDockWidget ? CurrentDockWidget->objectName() : "";
|
||||
s.writeAttribute("Current", Name);
|
||||
// To keep the saved XML data small, we only save the allowed areas and the
|
||||
// dock area flags if the values are different from the default values
|
||||
if (d->AllowedAreas != DefaultAllowedAreas)
|
||||
{
|
||||
s.writeAttribute("AllowedAreas", QString::number(d->AllowedAreas, 16));
|
||||
}
|
||||
|
||||
if (d->Flags != DefaultFlags)
|
||||
{
|
||||
s.writeAttribute("Flags", QString::number(d->Flags, 16));
|
||||
}
|
||||
ADS_PRINT("CDockAreaWidget::saveState TabCount: " << d->ContentsLayout->count()
|
||||
<< " Current: " << Name);
|
||||
for (int i = 0; i < d->ContentsLayout->count(); ++i)
|
||||
@@ -837,16 +872,49 @@ void CDockAreaWidget::setVisible(bool Visible)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockAreaWidget::setAllowedAreas(DockWidgetAreas areas)
|
||||
{
|
||||
d->AllowedAreas = areas;
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
DockWidgetAreas CDockAreaWidget::allowedAreas() const
|
||||
{
|
||||
return d->AllowedAreas;
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
CDockAreaWidget::DockAreaFlags CDockAreaWidget::dockAreaFlags() const
|
||||
{
|
||||
return d->Flags;
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockAreaWidget::setDockAreaFlags(DockAreaFlags Flags)
|
||||
{
|
||||
auto ChangedFlags = d->Flags ^ Flags;
|
||||
d->Flags = Flags;
|
||||
if (ChangedFlags.testFlag(HideSingleWidgetTitleBar))
|
||||
{
|
||||
updateTitleBarVisibility();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockAreaWidget::setDockAreaFlag(eDockAreaFlag Flag, bool On)
|
||||
{
|
||||
auto flags = dockAreaFlags();
|
||||
internal::setFlag(flags, Flag, On);
|
||||
setDockAreaFlags(flags);
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
QAbstractButton* CDockAreaWidget::titleBarButton(TitleBarButton which) const
|
||||
{
|
||||
@@ -860,17 +928,20 @@ void CDockAreaWidget::closeArea()
|
||||
// If there is only one single dock widget and this widget has the
|
||||
// DeleteOnClose feature, then we delete the dock widget now
|
||||
auto OpenDockWidgets = openedDockWidgets();
|
||||
if (OpenDockWidgets.count() == 1 && OpenDockWidgets[0]->features().testFlag(CDockWidget::DockWidgetDeleteOnClose))
|
||||
if (OpenDockWidgets.count() == 1 && OpenDockWidgets[0]->features().testFlag(CDockWidget::DockWidgetDeleteOnClose))
|
||||
{
|
||||
OpenDockWidgets[0]->closeDockWidgetInternal();
|
||||
}
|
||||
else
|
||||
else
|
||||
{
|
||||
for (auto DockWidget : openedDockWidgets())
|
||||
{
|
||||
DockWidget->toggleView(false);
|
||||
}
|
||||
}
|
||||
for (auto DockWidget : openedDockWidgets())
|
||||
{
|
||||
if (DockWidget->features().testFlag(CDockWidget::DockWidgetDeleteOnClose) && DockWidget->features().testFlag(CDockWidget::DockWidgetForceCloseWithArea))
|
||||
DockWidget->closeDockWidgetInternal();
|
||||
else
|
||||
DockWidget->toggleView(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -888,11 +959,35 @@ CDockAreaTitleBar* CDockAreaWidget::titleBar() const
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
bool CDockAreaWidget::isCentralWidgetArea() const
|
||||
{
|
||||
if (dockWidgetsCount()!= 1)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return dockManager()->centralWidget() == dockWidgets()[0];
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
QSize CDockAreaWidget::minimumSizeHint() const
|
||||
{
|
||||
return d->MinSizeHint.isValid() ? d->MinSizeHint : Super::minimumSizeHint();
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockAreaWidget::onDockWidgetFeaturesChanged()
|
||||
{
|
||||
if (d->TitleBar)
|
||||
{
|
||||
d->updateTitleBarButtonStates();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
} // namespace ads
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
|
||||
@@ -35,8 +35,8 @@
|
||||
#include "ads_globals.h"
|
||||
#include "DockWidget.h"
|
||||
|
||||
class QXmlStreamWriter;
|
||||
class QAbstractButton;
|
||||
QT_FORWARD_DECLARE_CLASS(QXmlStreamWriter)
|
||||
QT_FORWARD_DECLARE_CLASS(QAbstractButton)
|
||||
|
||||
namespace ads
|
||||
{
|
||||
@@ -65,6 +65,7 @@ private:
|
||||
friend class CDockWidget;
|
||||
friend struct DockManagerPrivate;
|
||||
friend class CDockManager;
|
||||
void onDockWidgetFeaturesChanged();
|
||||
|
||||
private slots:
|
||||
void onTabCloseRequested(int Index);
|
||||
@@ -144,6 +145,16 @@ public:
|
||||
using Super = QFrame;
|
||||
|
||||
/**
|
||||
* Dock area related flags
|
||||
*/
|
||||
enum eDockAreaFlag
|
||||
{
|
||||
HideSingleWidgetTitleBar = 0x0001,
|
||||
DefaultFlags = 0x0000
|
||||
};
|
||||
Q_DECLARE_FLAGS(DockAreaFlags, eDockAreaFlag)
|
||||
|
||||
/**
|
||||
* Default Constructor
|
||||
*/
|
||||
CDockAreaWidget(CDockManager* DockManager, CDockContainerWidget* parent);
|
||||
@@ -277,6 +288,30 @@ public:
|
||||
*/
|
||||
CDockAreaTitleBar* titleBar() const;
|
||||
|
||||
/**
|
||||
* Returns the dock area flags - a combination of flags that configure the
|
||||
* appearance and features of the dock area.
|
||||
* \see setDockAreaFlasg()
|
||||
*/
|
||||
DockAreaFlags dockAreaFlags() const;
|
||||
|
||||
/**
|
||||
* Sets the dock area flags - a combination of flags that configure the
|
||||
* appearance and features of the dock area
|
||||
*/
|
||||
void setDockAreaFlags(DockAreaFlags Flags);
|
||||
|
||||
/**
|
||||
* Sets the dock area flag Flag on this widget if on is true; otherwise
|
||||
* clears the flag.
|
||||
*/
|
||||
void setDockAreaFlag(eDockAreaFlag Flag, bool On);
|
||||
|
||||
/**
|
||||
* Returns true if the area contains the central widget of it's manager.
|
||||
*/
|
||||
bool isCentralWidgetArea() const;
|
||||
|
||||
public slots:
|
||||
/**
|
||||
* This activates the tab for the given tab index.
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
//============================================================================
|
||||
// INCLUDES
|
||||
//============================================================================
|
||||
#include <DockComponentsFactory.h>
|
||||
#include "DockComponentsFactory.h"
|
||||
|
||||
#include <memory>
|
||||
|
||||
|
||||
@@ -147,12 +147,12 @@ public:
|
||||
* Adds dock widget to container and returns the dock area that contains
|
||||
* the inserted dock widget
|
||||
*/
|
||||
CDockAreaWidget* dockWidgetIntoContainer(DockWidgetArea area, CDockWidget* Dockwidget);
|
||||
CDockAreaWidget* addDockWidgetToContainer(DockWidgetArea area, CDockWidget* Dockwidget);
|
||||
|
||||
/**
|
||||
* Adds dock widget to a existing DockWidgetArea
|
||||
*/
|
||||
CDockAreaWidget* dockWidgetIntoDockArea(DockWidgetArea area, CDockWidget* Dockwidget,
|
||||
CDockAreaWidget* addDockWidgetToDockArea(DockWidgetArea area, CDockWidget* Dockwidget,
|
||||
CDockAreaWidget* TargetDockArea);
|
||||
|
||||
/**
|
||||
@@ -299,11 +299,41 @@ public:
|
||||
CDockSplitter* newSplitter(Qt::Orientation orientation, QWidget* parent = nullptr)
|
||||
{
|
||||
CDockSplitter* s = new CDockSplitter(orientation, parent);
|
||||
s->setOpaqueResize(CDockManager::configFlags().testFlag(CDockManager::OpaqueSplitterResize));
|
||||
s->setOpaqueResize(CDockManager::testConfigFlag(CDockManager::OpaqueSplitterResize));
|
||||
s->setChildrenCollapsible(false);
|
||||
return s;
|
||||
}
|
||||
|
||||
/**
|
||||
* Ensures equal distribution of the sizes of a splitter if an dock widget
|
||||
* is inserted from code
|
||||
*/
|
||||
void adjustSplitterSizesOnInsertion(QSplitter* Splitter, qreal LastRatio = 1.0)
|
||||
{
|
||||
int AreaSize = (Splitter->orientation() == Qt::Horizontal) ? Splitter->width() : Splitter->height();
|
||||
auto SplitterSizes = Splitter->sizes();
|
||||
|
||||
qreal TotRatio = SplitterSizes.size() - 1.0 + LastRatio;
|
||||
for(int i = 0; i < SplitterSizes.size() -1; i++)
|
||||
{
|
||||
SplitterSizes[i] = AreaSize / TotRatio;
|
||||
}
|
||||
SplitterSizes.back() = AreaSize * LastRatio / TotRatio;
|
||||
Splitter->setSizes(SplitterSizes);
|
||||
}
|
||||
|
||||
/**
|
||||
* This function forces the dock container widget to update handles of splitters
|
||||
* based if a central widget exists.
|
||||
*/
|
||||
void updateSplitterHandles(QSplitter* splitter);
|
||||
|
||||
/**
|
||||
* If no central widget exists, the widgets resize with the container.
|
||||
* If a central widget exists, the widgets surrounding the central widget
|
||||
* do not resize its height or width.
|
||||
*/
|
||||
bool widgetResizesWithContainer(QWidget* widget);
|
||||
|
||||
// private slots: ------------------------------------------------------------
|
||||
void onDockAreaViewToggled(bool Visible)
|
||||
@@ -403,7 +433,8 @@ void DockContainerWidgetPrivate::dropIntoContainer(CFloatingDockContainer* Float
|
||||
QSplitter* NewSplitter = newSplitter(InsertParam.orientation());
|
||||
QLayoutItem* li = Layout->replaceWidget(Splitter, NewSplitter);
|
||||
NewSplitter->addWidget(Splitter);
|
||||
Splitter = NewSplitter;
|
||||
updateSplitterHandles(NewSplitter);
|
||||
Splitter = NewSplitter;
|
||||
delete li;
|
||||
}
|
||||
|
||||
@@ -412,18 +443,21 @@ void DockContainerWidgetPrivate::dropIntoContainer(CFloatingDockContainer* Float
|
||||
if (FloatingSplitter->count() == 1)
|
||||
{
|
||||
insertWidgetIntoSplitter(Splitter, FloatingSplitter->widget(0), InsertParam.append());
|
||||
}
|
||||
updateSplitterHandles(Splitter);
|
||||
}
|
||||
else if (FloatingSplitter->orientation() == InsertParam.orientation())
|
||||
{
|
||||
int InsertIndex = InsertParam.append() ? Splitter->count() : 0;
|
||||
while (FloatingSplitter->count())
|
||||
{
|
||||
insertWidgetIntoSplitter(Splitter, FloatingSplitter->widget(0), InsertParam.append());
|
||||
}
|
||||
}
|
||||
Splitter->insertWidget(InsertIndex++, FloatingSplitter->widget(0));
|
||||
updateSplitterHandles(Splitter);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
insertWidgetIntoSplitter(Splitter, FloatingSplitter, InsertParam.append());
|
||||
}
|
||||
}
|
||||
|
||||
RootSplitter = Splitter;
|
||||
addDockAreasToList(NewDockAreas);
|
||||
@@ -434,7 +468,7 @@ void DockContainerWidgetPrivate::dropIntoContainer(CFloatingDockContainer* Float
|
||||
if (!Splitter->isVisible())
|
||||
{
|
||||
Splitter->show();
|
||||
}
|
||||
}
|
||||
_this->dumpLayout();
|
||||
}
|
||||
|
||||
@@ -496,7 +530,8 @@ void DockContainerWidgetPrivate::dropIntoSection(CFloatingDockContainer* Floatin
|
||||
QSplitter* Splitter = newSplitter(InsertParam.orientation());
|
||||
Layout->replaceWidget(TargetArea, Splitter);
|
||||
Splitter->addWidget(TargetArea);
|
||||
TargetAreaSplitter = Splitter;
|
||||
updateSplitterHandles(Splitter);
|
||||
TargetAreaSplitter = Splitter;
|
||||
}
|
||||
int AreaIndex = TargetAreaSplitter->indexOf(TargetArea);
|
||||
auto Widget = FloatingWidget->dockContainer()->findChild<QWidget*>(QString(), Qt::FindDirectChildrenOnly);
|
||||
@@ -510,7 +545,8 @@ void DockContainerWidgetPrivate::dropIntoSection(CFloatingDockContainer* Floatin
|
||||
if ((FloatingSplitter->orientation() != InsertParam.orientation()) && FloatingSplitter->count() > 1)
|
||||
{
|
||||
TargetAreaSplitter->insertWidget(AreaIndex + InsertParam.insertOffset(), Widget);
|
||||
}
|
||||
updateSplitterHandles(TargetAreaSplitter);
|
||||
}
|
||||
else
|
||||
{
|
||||
AdjustSplitterSizes = (FloatingSplitter->count() == 1);
|
||||
@@ -518,8 +554,9 @@ void DockContainerWidgetPrivate::dropIntoSection(CFloatingDockContainer* Floatin
|
||||
while (FloatingSplitter->count())
|
||||
{
|
||||
TargetAreaSplitter->insertWidget(InsertIndex++, FloatingSplitter->widget(0));
|
||||
}
|
||||
}
|
||||
updateSplitterHandles(TargetAreaSplitter);
|
||||
}
|
||||
}
|
||||
|
||||
if (AdjustSplitterSizes)
|
||||
{
|
||||
@@ -538,28 +575,32 @@ void DockContainerWidgetPrivate::dropIntoSection(CFloatingDockContainer* Floatin
|
||||
if ((FloatingSplitter->orientation() != InsertParam.orientation()) && FloatingSplitter->count() > 1)
|
||||
{
|
||||
NewSplitter->addWidget(Widget);
|
||||
}
|
||||
updateSplitterHandles(NewSplitter);
|
||||
}
|
||||
else
|
||||
{
|
||||
AdjustSplitterSizes = (FloatingSplitter->count() == 1);
|
||||
while (FloatingSplitter->count())
|
||||
{
|
||||
NewSplitter->addWidget(FloatingSplitter->widget(0));
|
||||
}
|
||||
}
|
||||
updateSplitterHandles(NewSplitter);
|
||||
}
|
||||
}
|
||||
|
||||
// Save the sizes before insertion and restore it later to prevent
|
||||
// shrinking of existing area
|
||||
auto Sizes = TargetAreaSplitter->sizes();
|
||||
insertWidgetIntoSplitter(NewSplitter, TargetArea, !InsertParam.append());
|
||||
if (AdjustSplitterSizes)
|
||||
updateSplitterHandles(NewSplitter);
|
||||
if (AdjustSplitterSizes)
|
||||
{
|
||||
int Size = TargetAreaSize / 2;
|
||||
NewSplitter->setSizes({Size, Size});
|
||||
}
|
||||
TargetAreaSplitter->insertWidget(AreaIndex, NewSplitter);
|
||||
TargetAreaSplitter->setSizes(Sizes);
|
||||
}
|
||||
updateSplitterHandles(TargetAreaSplitter);
|
||||
}
|
||||
|
||||
addDockAreasToList(NewDockAreas);
|
||||
_this->dumpLayout();
|
||||
@@ -575,6 +616,11 @@ void DockContainerWidgetPrivate::moveIntoCenterOfSection(QWidget* Widget, CDockA
|
||||
if (DroppedDockWidget)
|
||||
{
|
||||
CDockAreaWidget* OldDockArea = DroppedDockWidget->dockAreaWidget();
|
||||
if (OldDockArea == TargetArea)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (OldDockArea)
|
||||
{
|
||||
OldDockArea->removeDockWidget(DroppedDockWidget);
|
||||
@@ -639,7 +685,8 @@ void DockContainerWidgetPrivate::moveToNewSection(QWidget* Widget, CDockAreaWidg
|
||||
{
|
||||
int TargetAreaSize = (InsertParam.orientation() == Qt::Horizontal) ? TargetArea->width() : TargetArea->height();
|
||||
TargetAreaSplitter->insertWidget(AreaIndex + InsertParam.insertOffset(), NewDockArea);
|
||||
int Size = (TargetAreaSize - TargetAreaSplitter->handleWidth()) / 2;
|
||||
updateSplitterHandles(TargetAreaSplitter);
|
||||
int Size = (TargetAreaSize - TargetAreaSplitter->handleWidth()) / 2;
|
||||
Sizes[AreaIndex] = Size;
|
||||
Sizes.insert(AreaIndex, Size);
|
||||
}
|
||||
@@ -650,16 +697,58 @@ void DockContainerWidgetPrivate::moveToNewSection(QWidget* Widget, CDockAreaWidg
|
||||
QSplitter* NewSplitter = newSplitter(InsertParam.orientation());
|
||||
NewSplitter->addWidget(TargetArea);
|
||||
insertWidgetIntoSplitter(NewSplitter, NewDockArea, InsertParam.append());
|
||||
int Size = TargetAreaSize / 2;
|
||||
updateSplitterHandles(NewSplitter);
|
||||
int Size = TargetAreaSize / 2;
|
||||
NewSplitter->setSizes({Size, Size});
|
||||
TargetAreaSplitter->insertWidget(AreaIndex, NewSplitter);
|
||||
}
|
||||
updateSplitterHandles(TargetAreaSplitter);
|
||||
}
|
||||
TargetAreaSplitter->setSizes(Sizes);
|
||||
|
||||
addDockAreasToList({NewDockArea});
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void DockContainerWidgetPrivate::updateSplitterHandles( QSplitter* splitter )
|
||||
{
|
||||
if (!DockManager->centralWidget() || !splitter)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
for (int i = 0; i < splitter->count(); ++i)
|
||||
{
|
||||
splitter->setStretchFactor(i, widgetResizesWithContainer(splitter->widget(i)) ? 1 : 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
bool DockContainerWidgetPrivate::widgetResizesWithContainer(QWidget* widget)
|
||||
{
|
||||
if (!DockManager->centralWidget())
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
auto Area = qobject_cast<CDockAreaWidget*>(widget);
|
||||
if(Area)
|
||||
{
|
||||
return Area->isCentralWidgetArea();
|
||||
}
|
||||
|
||||
auto innerSplitter = qobject_cast<CDockSplitter*>(widget);
|
||||
if (innerSplitter)
|
||||
{
|
||||
return innerSplitter->isResizingWithContainer();
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//============================================================================
|
||||
void DockContainerWidgetPrivate::moveToContainer(QWidget* Widget, DockWidgetArea area)
|
||||
{
|
||||
@@ -868,6 +957,10 @@ bool DockContainerWidgetPrivate::restoreSplitter(CDockingStateReader& s,
|
||||
Splitter->addWidget(ChildNode);
|
||||
Visible |= ChildNode->isVisibleTo(Splitter);
|
||||
}
|
||||
if(!Testing)
|
||||
{
|
||||
updateSplitterHandles(Splitter);
|
||||
}
|
||||
|
||||
if (Sizes.count() != WidgetCount)
|
||||
{
|
||||
@@ -918,6 +1011,17 @@ bool DockContainerWidgetPrivate::restoreDockArea(CDockingStateReader& s,
|
||||
if (!Testing)
|
||||
{
|
||||
DockArea = new CDockAreaWidget(DockManager, _this);
|
||||
const auto AllowedAreasAttribute = s.attributes().value("AllowedAreas");
|
||||
if (!AllowedAreasAttribute.isEmpty())
|
||||
{
|
||||
DockArea->setAllowedAreas((DockWidgetArea)AllowedAreasAttribute.toInt(nullptr, 16));
|
||||
}
|
||||
|
||||
const auto FlagsAttribute = s.attributes().value("Flags");
|
||||
if (!FlagsAttribute.isEmpty())
|
||||
{
|
||||
DockArea->setDockAreaFlags((CDockAreaWidget::DockAreaFlags)FlagsAttribute.toInt(nullptr, 16));
|
||||
}
|
||||
}
|
||||
|
||||
while (s.readNextStartElement())
|
||||
@@ -1007,7 +1111,7 @@ bool DockContainerWidgetPrivate::restoreChildNodes(CDockingStateReader& s,
|
||||
|
||||
|
||||
//============================================================================
|
||||
CDockAreaWidget* DockContainerWidgetPrivate::dockWidgetIntoContainer(DockWidgetArea area,
|
||||
CDockAreaWidget* DockContainerWidgetPrivate::addDockWidgetToContainer(DockWidgetArea area,
|
||||
CDockWidget* Dockwidget)
|
||||
{
|
||||
CDockAreaWidget* NewDockArea = new CDockAreaWidget(DockManager, _this);
|
||||
@@ -1034,6 +1138,11 @@ void DockContainerWidgetPrivate::addDockArea(CDockAreaWidget* NewDockArea, DockW
|
||||
if (Splitter->orientation() == InsertParam.orientation())
|
||||
{
|
||||
insertWidgetIntoSplitter(Splitter, NewDockArea, InsertParam.append());
|
||||
updateSplitterHandles(Splitter);
|
||||
if (Splitter->isHidden())
|
||||
{
|
||||
Splitter->show();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -1043,14 +1152,16 @@ void DockContainerWidgetPrivate::addDockArea(CDockAreaWidget* NewDockArea, DockW
|
||||
QLayoutItem* li = Layout->replaceWidget(Splitter, NewSplitter);
|
||||
NewSplitter->addWidget(Splitter);
|
||||
NewSplitter->addWidget(NewDockArea);
|
||||
delete li;
|
||||
updateSplitterHandles(NewSplitter);
|
||||
delete li;
|
||||
}
|
||||
else
|
||||
{
|
||||
NewSplitter->addWidget(NewDockArea);
|
||||
QLayoutItem* li = Layout->replaceWidget(Splitter, NewSplitter);
|
||||
NewSplitter->addWidget(Splitter);
|
||||
delete li;
|
||||
updateSplitterHandles(NewSplitter);
|
||||
delete li;
|
||||
}
|
||||
RootSplitter = NewSplitter;
|
||||
}
|
||||
@@ -1096,7 +1207,7 @@ void DockContainerWidgetPrivate::dumpRecursive(int level, QWidget* widget)
|
||||
std::cout << (const char*)buf
|
||||
<< (DockArea->isHidden() ? " " : "v")
|
||||
<< (DockArea->openDockWidgetsCount() > 0 ? " " : "c")
|
||||
<< " DockArea" << std::endl;
|
||||
<< " DockArea " << "[hs: " << DockArea->sizePolicy().horizontalStretch() << ", vs: " << DockArea->sizePolicy().verticalStretch() << "]" << std::endl;
|
||||
buf.fill(' ', (level + 1) * 4);
|
||||
for (int i = 0; i < DockArea->dockWidgetsCount(); ++i)
|
||||
{
|
||||
@@ -1116,7 +1227,7 @@ void DockContainerWidgetPrivate::dumpRecursive(int level, QWidget* widget)
|
||||
|
||||
|
||||
//============================================================================
|
||||
CDockAreaWidget* DockContainerWidgetPrivate::dockWidgetIntoDockArea(DockWidgetArea area,
|
||||
CDockAreaWidget* DockContainerWidgetPrivate::addDockWidgetToDockArea(DockWidgetArea area,
|
||||
CDockWidget* Dockwidget, CDockAreaWidget* TargetDockArea)
|
||||
{
|
||||
if (CenterDockWidgetArea == area)
|
||||
@@ -1134,16 +1245,32 @@ CDockAreaWidget* DockContainerWidgetPrivate::dockWidgetIntoDockArea(DockWidgetAr
|
||||
int index = TargetAreaSplitter ->indexOf(TargetDockArea);
|
||||
if (TargetAreaSplitter->orientation() == InsertParam.orientation())
|
||||
{
|
||||
ADS_PRINT("TargetAreaSplitter->orientation() == InsertParam.orientation()");
|
||||
ADS_PRINT("TargetAreaSplitter->orientation() == InsertParam.orientation()");
|
||||
TargetAreaSplitter->insertWidget(index + InsertParam.insertOffset(), NewDockArea);
|
||||
updateSplitterHandles(TargetAreaSplitter);
|
||||
// do nothing, if flag is not enabled
|
||||
if (CDockManager::testConfigFlag(CDockManager::EqualSplitOnInsertion))
|
||||
{
|
||||
adjustSplitterSizesOnInsertion(TargetAreaSplitter);
|
||||
}
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
ADS_PRINT("TargetAreaSplitter->orientation() != InsertParam.orientation()");
|
||||
ADS_PRINT("TargetAreaSplitter->orientation() != InsertParam.orientation()");
|
||||
auto TargetAreaSizes = TargetAreaSplitter->sizes();
|
||||
QSplitter* NewSplitter = newSplitter(InsertParam.orientation());
|
||||
NewSplitter->addWidget(TargetDockArea);
|
||||
|
||||
insertWidgetIntoSplitter(NewSplitter, NewDockArea, InsertParam.append());
|
||||
TargetAreaSplitter->insertWidget(index, NewSplitter);
|
||||
updateSplitterHandles(NewSplitter);
|
||||
TargetAreaSplitter->insertWidget(index, NewSplitter);
|
||||
updateSplitterHandles(TargetAreaSplitter);
|
||||
if (CDockManager::testConfigFlag(CDockManager::EqualSplitOnInsertion))
|
||||
{
|
||||
TargetAreaSplitter->setSizes(TargetAreaSizes);
|
||||
adjustSplitterSizesOnInsertion(NewSplitter);
|
||||
}
|
||||
}
|
||||
|
||||
appendDockAreas({NewDockArea});
|
||||
@@ -1201,11 +1328,11 @@ CDockAreaWidget* CDockContainerWidget::addDockWidget(DockWidgetArea area, CDockW
|
||||
Dockwidget->setDockManager(d->DockManager);
|
||||
if (DockAreaWidget)
|
||||
{
|
||||
return d->dockWidgetIntoDockArea(area, Dockwidget, DockAreaWidget);
|
||||
return d->addDockWidgetToDockArea(area, Dockwidget, DockAreaWidget);
|
||||
}
|
||||
else
|
||||
{
|
||||
return d->dockWidgetIntoContainer(area, Dockwidget);
|
||||
return d->addDockWidgetToContainer(area, Dockwidget);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1278,9 +1405,9 @@ void CDockContainerWidget::removeDockArea(CDockAreaWidget* area)
|
||||
internal::hideEmptyParentSplitters(Splitter);
|
||||
|
||||
// Remove this area from cached areas
|
||||
const auto& cache = d->LastAddedAreaCache;
|
||||
if (auto p = std::find(cache, cache+sizeof(cache)/sizeof(cache[0]), area)) {
|
||||
d->LastAddedAreaCache[std::distance(cache, p)] = nullptr;
|
||||
auto p = std::find(std::begin(d->LastAddedAreaCache), std::end(d->LastAddedAreaCache), area);
|
||||
if (p != std::end(d->LastAddedAreaCache)) {
|
||||
*p = nullptr;
|
||||
}
|
||||
|
||||
// If splitter has more than 1 widgets, we are finished and can leave
|
||||
@@ -1329,9 +1456,11 @@ void CDockContainerWidget::removeDockArea(CDockAreaWidget* area)
|
||||
}
|
||||
|
||||
delete Splitter;
|
||||
Splitter = nullptr;
|
||||
|
||||
emitAndExit:
|
||||
CDockWidget* TopLevelWidget = topLevelDockWidget();
|
||||
updateSplitterHandles(Splitter);
|
||||
CDockWidget* TopLevelWidget = topLevelDockWidget();
|
||||
|
||||
// Updated the title bar visibility of the dock widget if there is only
|
||||
// one single visible dock widget
|
||||
@@ -1449,6 +1578,13 @@ void CDockContainerWidget::dropFloatingWidget(CFloatingDockContainer* FloatingWi
|
||||
// level widget anymore
|
||||
CDockWidget::emitTopLevelEventForWidget(SingleDockWidget, false);
|
||||
}
|
||||
|
||||
window()->activateWindow();
|
||||
if (SingleDroppedDockWidget)
|
||||
{
|
||||
d->DockManager->notifyWidgetOrAreaRelocation(SingleDroppedDockWidget);
|
||||
}
|
||||
d->DockManager->notifyFloatingWidgetDrop(FloatingWidget);
|
||||
}
|
||||
|
||||
|
||||
@@ -1468,6 +1604,9 @@ void CDockContainerWidget::dropWidget(QWidget* Widget, DockWidgetArea DropArea,
|
||||
// If there was a top level widget before the drop, then it is not top
|
||||
// level widget anymore
|
||||
CDockWidget::emitTopLevelEventForWidget(SingleDockWidget, false);
|
||||
|
||||
window()->activateWindow();
|
||||
d->DockManager->notifyWidgetOrAreaRelocation(Widget);
|
||||
}
|
||||
|
||||
|
||||
@@ -1670,6 +1809,13 @@ QList<CDockWidget*> CDockContainerWidget::dockWidgets() const
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockContainerWidget::updateSplitterHandles(QSplitter* splitter)
|
||||
{
|
||||
d->updateSplitterHandles(splitter);
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
CDockWidget::DockWidgetFeatures CDockContainerWidget::features() const
|
||||
{
|
||||
|
||||
@@ -35,7 +35,7 @@
|
||||
#include "ads_globals.h"
|
||||
#include "DockWidget.h"
|
||||
|
||||
class QXmlStreamWriter;
|
||||
QT_FORWARD_DECLARE_CLASS(QXmlStreamWriter)
|
||||
|
||||
|
||||
namespace ads
|
||||
@@ -155,6 +155,12 @@ protected:
|
||||
*/
|
||||
QList<CDockWidget*> dockWidgets() const;
|
||||
|
||||
/**
|
||||
* This function forces the dock container widget to update handles of splitters
|
||||
* based on resize modes of dock widgets contained in the container.
|
||||
*/
|
||||
void updateSplitterHandles(QSplitter* splitter);
|
||||
|
||||
public:
|
||||
/**
|
||||
* Default Constructor
|
||||
@@ -193,7 +199,7 @@ public:
|
||||
bool isInFrontOf(CDockContainerWidget* Other) const;
|
||||
|
||||
/**
|
||||
* Returns the dock area at teh given global position or 0 if there is no
|
||||
* Returns the dock area at the given global position or 0 if there is no
|
||||
* dock area at this position
|
||||
*/
|
||||
CDockAreaWidget* dockAreaAt(const QPoint& GlobalPos) const;
|
||||
@@ -276,7 +282,7 @@ signals:
|
||||
* This signal is emitted if a dock area is opened or closed via
|
||||
* toggleView() function
|
||||
*/
|
||||
void dockAreaViewToggled(CDockAreaWidget* DockArea, bool Open);
|
||||
void dockAreaViewToggled(ads::CDockAreaWidget* DockArea, bool Open);
|
||||
}; // class DockContainerWidget
|
||||
} // namespace ads
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
398
src/DockFocusController.cpp
Normal file
@@ -0,0 +1,398 @@
|
||||
//============================================================================
|
||||
/// \file DockFocusController.cpp
|
||||
/// \author Uwe Kindler
|
||||
/// \date 05.06.2020
|
||||
/// \brief Implementation of CDockFocusController class
|
||||
//============================================================================
|
||||
|
||||
//============================================================================
|
||||
// INCLUDES
|
||||
//============================================================================
|
||||
#include "DockFocusController.h"
|
||||
|
||||
#include <algorithm>
|
||||
#include <iostream>
|
||||
|
||||
#include <QPointer>
|
||||
#include <QApplication>
|
||||
#include <QAbstractButton>
|
||||
|
||||
#include "DockWidget.h"
|
||||
#include "DockAreaWidget.h"
|
||||
#include "DockWidgetTab.h"
|
||||
#include "DockContainerWidget.h"
|
||||
#include "FloatingDockContainer.h"
|
||||
#include "DockManager.h"
|
||||
#include "DockAreaTitleBar.h"
|
||||
|
||||
#ifdef Q_OS_LINUX
|
||||
#include "linux/FloatingWidgetTitleBar.h"
|
||||
#endif
|
||||
|
||||
namespace ads
|
||||
{
|
||||
/**
|
||||
* Private data class of CDockFocusController class (pimpl)
|
||||
*/
|
||||
struct DockFocusControllerPrivate
|
||||
{
|
||||
CDockFocusController *_this;
|
||||
QPointer<CDockWidget> FocusedDockWidget = nullptr;
|
||||
QPointer<CDockAreaWidget> FocusedArea = nullptr;
|
||||
CDockWidget* OldFocusedDockWidget = nullptr;
|
||||
#ifdef Q_OS_LINUX
|
||||
QPointer<CFloatingDockContainer> FloatingWidget = nullptr;
|
||||
#endif
|
||||
CDockManager* DockManager;
|
||||
bool ForceFocusChangedSignal = false;
|
||||
|
||||
/**
|
||||
* Private data constructor
|
||||
*/
|
||||
DockFocusControllerPrivate(CDockFocusController *_public);
|
||||
|
||||
/**
|
||||
* This function updates the focus style of the given dock widget and
|
||||
* the dock area that it belongs to
|
||||
*/
|
||||
void updateDockWidgetFocus(CDockWidget* DockWidget);
|
||||
};
|
||||
// struct DockFocusControllerPrivate
|
||||
|
||||
|
||||
//===========================================================================
|
||||
static void updateDockWidgetFocusStyle(CDockWidget* DockWidget, bool Focused)
|
||||
{
|
||||
DockWidget->setProperty("focused", Focused);
|
||||
DockWidget->tabWidget()->setProperty("focused", Focused);
|
||||
DockWidget->tabWidget()->updateStyle();
|
||||
internal::repolishStyle(DockWidget);
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
static void updateDockAreaFocusStyle(CDockAreaWidget* DockArea, bool Focused)
|
||||
{
|
||||
DockArea->setProperty("focused", Focused);
|
||||
internal::repolishStyle(DockArea);
|
||||
internal::repolishStyle(DockArea->titleBar());
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
#ifdef Q_OS_LINUX
|
||||
static void updateFloatingWidgetFocusStyle(CFloatingDockContainer* FloatingWidget, bool Focused)
|
||||
{
|
||||
if (FloatingWidget->hasNativeTitleBar())
|
||||
{
|
||||
return;
|
||||
}
|
||||
auto TitleBar = qobject_cast<CFloatingWidgetTitleBar*>(FloatingWidget->titleBarWidget());
|
||||
if (!TitleBar)
|
||||
{
|
||||
return;
|
||||
}
|
||||
TitleBar->setProperty("focused", Focused);
|
||||
TitleBar->updateStyle();
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
//============================================================================
|
||||
DockFocusControllerPrivate::DockFocusControllerPrivate(
|
||||
CDockFocusController *_public) :
|
||||
_this(_public)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void DockFocusControllerPrivate::updateDockWidgetFocus(CDockWidget* DockWidget)
|
||||
{
|
||||
if (!DockWidget->features().testFlag(CDockWidget::DockWidgetFocusable))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
CDockAreaWidget* NewFocusedDockArea = nullptr;
|
||||
if (FocusedDockWidget)
|
||||
{
|
||||
updateDockWidgetFocusStyle(FocusedDockWidget, false);
|
||||
}
|
||||
|
||||
CDockWidget* old = FocusedDockWidget;
|
||||
FocusedDockWidget = DockWidget;
|
||||
updateDockWidgetFocusStyle(FocusedDockWidget, true);
|
||||
NewFocusedDockArea = FocusedDockWidget->dockAreaWidget();
|
||||
if (NewFocusedDockArea && (FocusedArea != NewFocusedDockArea))
|
||||
{
|
||||
if (FocusedArea)
|
||||
{
|
||||
QObject::disconnect(FocusedArea, SIGNAL(viewToggled(bool)), _this, SLOT(onFocusedDockAreaViewToggled(bool)));
|
||||
updateDockAreaFocusStyle(FocusedArea, false);
|
||||
}
|
||||
|
||||
FocusedArea = NewFocusedDockArea;
|
||||
updateDockAreaFocusStyle(FocusedArea, true);
|
||||
QObject::connect(FocusedArea, SIGNAL(viewToggled(bool)), _this, SLOT(onFocusedDockAreaViewToggled(bool)));
|
||||
}
|
||||
|
||||
|
||||
auto NewFloatingWidget = FocusedDockWidget->dockContainer()->floatingWidget();
|
||||
if (NewFloatingWidget)
|
||||
{
|
||||
NewFloatingWidget->setProperty("FocusedDockWidget", QVariant::fromValue(DockWidget));
|
||||
}
|
||||
|
||||
|
||||
#ifdef Q_OS_LINUX
|
||||
// This code is required for styling the floating widget titlebar for linux
|
||||
// depending on the current focus state
|
||||
if (FloatingWidget == NewFloatingWidget)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (FloatingWidget)
|
||||
{
|
||||
updateFloatingWidgetFocusStyle(FloatingWidget, false);
|
||||
}
|
||||
FloatingWidget = NewFloatingWidget;
|
||||
|
||||
if (FloatingWidget)
|
||||
{
|
||||
updateFloatingWidgetFocusStyle(FloatingWidget, true);
|
||||
}
|
||||
#endif
|
||||
|
||||
if (old == DockWidget && !ForceFocusChangedSignal)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
ForceFocusChangedSignal = false;
|
||||
if (DockWidget->isVisible())
|
||||
{
|
||||
emit DockManager->focusedDockWidgetChanged(old, DockWidget);
|
||||
}
|
||||
else
|
||||
{
|
||||
OldFocusedDockWidget = old;
|
||||
QObject::connect(DockWidget, SIGNAL(visibilityChanged(bool)), _this, SLOT(onDockWidgetVisibilityChanged(bool)));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockFocusController::onDockWidgetVisibilityChanged(bool Visible)
|
||||
{
|
||||
auto Sender = sender();
|
||||
auto DockWidget = qobject_cast<ads::CDockWidget*>(Sender);
|
||||
disconnect(Sender, SIGNAL(visibilityChanged(bool)), this, SLOT(onDockWidgetVisibilityChanged(bool)));
|
||||
if (DockWidget && Visible)
|
||||
{
|
||||
emit d->DockManager->focusedDockWidgetChanged(d->OldFocusedDockWidget, DockWidget);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
CDockFocusController::CDockFocusController(CDockManager* DockManager) :
|
||||
Super(DockManager),
|
||||
d(new DockFocusControllerPrivate(this))
|
||||
{
|
||||
d->DockManager = DockManager;
|
||||
connect(QApplication::instance(), SIGNAL(focusChanged(QWidget*, QWidget*)),
|
||||
this, SLOT(onApplicationFocusChanged(QWidget*, QWidget*)));
|
||||
connect(d->DockManager, SIGNAL(stateRestored()), SLOT(onStateRestored()));
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
CDockFocusController::~CDockFocusController()
|
||||
{
|
||||
delete d;
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
void CDockFocusController::onApplicationFocusChanged(QWidget* focusedOld, QWidget* focusedNow)
|
||||
{
|
||||
if (d->DockManager->isRestoringState())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
ADS_PRINT("CDockFocusController::onApplicationFocusChanged "
|
||||
<< " old: " << focusedOld << " new: " << focusedNow);
|
||||
if (!focusedNow)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
// If the close button in another tab steals the focus from the current
|
||||
// active dock widget content, i.e. if the user clicks its close button,
|
||||
// then we immediately give the focus back to the previous focused widget
|
||||
// focusedOld
|
||||
if (CDockManager::testConfigFlag(CDockManager::AllTabsHaveCloseButton))
|
||||
{
|
||||
auto OtherDockWidgetTab = internal::findParent<CDockWidgetTab*>(focusedNow);
|
||||
if (OtherDockWidgetTab && focusedOld)
|
||||
{
|
||||
auto OldFocusedDockWidget = internal::findParent<CDockWidget*>(focusedOld);
|
||||
if (OldFocusedDockWidget)
|
||||
{
|
||||
focusedOld->setFocus();
|
||||
}
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
CDockWidget* DockWidget = nullptr;
|
||||
auto DockWidgetTab = qobject_cast<CDockWidgetTab*>(focusedNow);
|
||||
if (DockWidgetTab)
|
||||
{
|
||||
DockWidget = DockWidgetTab->dockWidget();
|
||||
// If the DockWidgetTab "steals" the focus from a widget in the same
|
||||
// DockWidget, then we immediately give the focus back to the previous
|
||||
// focused widget focusedOld
|
||||
if (focusedOld)
|
||||
{
|
||||
auto OldFocusedDockWidget = internal::findParent<CDockWidget*>(focusedOld);
|
||||
if (OldFocusedDockWidget && OldFocusedDockWidget == DockWidget)
|
||||
{
|
||||
focusedOld->setFocus();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!DockWidget)
|
||||
{
|
||||
DockWidget = qobject_cast<CDockWidget*>(focusedNow);
|
||||
}
|
||||
|
||||
if (!DockWidget)
|
||||
{
|
||||
DockWidget = internal::findParent<CDockWidget*>(focusedNow);
|
||||
}
|
||||
|
||||
#ifdef Q_OS_LINUX
|
||||
if (!DockWidget)
|
||||
{
|
||||
return;
|
||||
}
|
||||
#else
|
||||
if (!DockWidget || DockWidget->tabWidget()->isHidden())
|
||||
{
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
|
||||
d->updateDockWidgetFocus(DockWidget);
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
void CDockFocusController::setDockWidgetFocused(CDockWidget* focusedNow)
|
||||
{
|
||||
d->updateDockWidgetFocus(focusedNow);
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
void CDockFocusController::onFocusedDockAreaViewToggled(bool Open)
|
||||
{
|
||||
if (d->DockManager->isRestoringState())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
CDockAreaWidget* DockArea = qobject_cast<CDockAreaWidget*>(sender());
|
||||
if (!DockArea || Open)
|
||||
{
|
||||
return;
|
||||
}
|
||||
auto Container = DockArea->dockContainer();
|
||||
auto OpenedDockAreas = Container->openedDockAreas();
|
||||
if (OpenedDockAreas.isEmpty())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
CDockManager::setWidgetFocus(OpenedDockAreas[0]->currentDockWidget()->tabWidget());
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
void CDockFocusController::notifyWidgetOrAreaRelocation(QWidget* DroppedWidget)
|
||||
{
|
||||
if (d->DockManager->isRestoringState())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
CDockWidget* DockWidget = qobject_cast<CDockWidget*>(DroppedWidget);
|
||||
if (!DockWidget)
|
||||
{
|
||||
CDockAreaWidget* DockArea = qobject_cast<CDockAreaWidget*>(DroppedWidget);
|
||||
if (DockArea)
|
||||
{
|
||||
DockWidget = DockArea->currentDockWidget();
|
||||
}
|
||||
}
|
||||
|
||||
if (!DockWidget)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
d->ForceFocusChangedSignal = true;
|
||||
CDockManager::setWidgetFocus(DockWidget->tabWidget());
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
void CDockFocusController::notifyFloatingWidgetDrop(CFloatingDockContainer* FloatingWidget)
|
||||
{
|
||||
if (!FloatingWidget || d->DockManager->isRestoringState())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
auto vDockWidget = FloatingWidget->property("FocusedDockWidget");
|
||||
if (!vDockWidget.isValid())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
auto DockWidget = vDockWidget.value<CDockWidget*>();
|
||||
if (DockWidget)
|
||||
{
|
||||
d->FocusedDockWidget = nullptr;
|
||||
DockWidget->dockAreaWidget()->setCurrentDockWidget(DockWidget);
|
||||
CDockManager::setWidgetFocus(DockWidget->tabWidget());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//==========================================================================
|
||||
void CDockFocusController::onStateRestored()
|
||||
{
|
||||
if (d->FocusedDockWidget)
|
||||
{
|
||||
updateDockWidgetFocusStyle(d->FocusedDockWidget, false);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//==========================================================================
|
||||
CDockWidget* CDockFocusController::focusedDockWidget() const
|
||||
{
|
||||
return d->FocusedDockWidget.data();
|
||||
}
|
||||
|
||||
} // namespace ads
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
// EOF DockFocusController.cpp
|
||||
96
src/DockFocusController.h
Normal file
@@ -0,0 +1,96 @@
|
||||
#ifndef DockFocusControllerH
|
||||
#define DockFocusControllerH
|
||||
//============================================================================
|
||||
/// \file DockFocusController.h
|
||||
/// \author Uwe Kindler
|
||||
/// \date 05.06.2020
|
||||
/// \brief Declaration of CDockFocusController class
|
||||
//============================================================================
|
||||
|
||||
//============================================================================
|
||||
// INCLUDES
|
||||
//============================================================================
|
||||
#include <QObject>
|
||||
#include "ads_globals.h"
|
||||
#include "DockManager.h"
|
||||
|
||||
namespace ads
|
||||
{
|
||||
struct DockFocusControllerPrivate;
|
||||
class CDockManager;
|
||||
class CFloatingDockContainer;
|
||||
|
||||
/**
|
||||
* Manages focus styling of dock widgets and handling of focus changes
|
||||
*/
|
||||
class ADS_EXPORT CDockFocusController : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
private:
|
||||
DockFocusControllerPrivate* d; ///< private data (pimpl)
|
||||
friend struct DockFocusControllerPrivate;
|
||||
|
||||
private slots:
|
||||
void onApplicationFocusChanged(QWidget *old, QWidget *now);
|
||||
void onFocusedDockAreaViewToggled(bool Open);
|
||||
void onStateRestored();
|
||||
void onDockWidgetVisibilityChanged(bool Visible);
|
||||
|
||||
public:
|
||||
using Super = QObject;
|
||||
/**
|
||||
* Default Constructor
|
||||
*/
|
||||
CDockFocusController(CDockManager* DockManager);
|
||||
|
||||
/**
|
||||
* Virtual Destructor
|
||||
*/
|
||||
virtual ~CDockFocusController();
|
||||
|
||||
/**
|
||||
* Helper function to set focus depending on the configuration of the
|
||||
* FocusStyling flag
|
||||
*/
|
||||
template <class QWidgetPtr>
|
||||
static void setWidgetFocus(QWidgetPtr widget)
|
||||
{
|
||||
if (!CDockManager::testConfigFlag(CDockManager::FocusHighlighting))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
widget->setFocus(Qt::OtherFocusReason);
|
||||
}
|
||||
|
||||
/**
|
||||
* A container needs to call this function if a widget has been dropped
|
||||
* into it
|
||||
*/
|
||||
void notifyWidgetOrAreaRelocation(QWidget* RelocatedWidget);
|
||||
|
||||
/**
|
||||
* This function is called, if a floating widget has been dropped into
|
||||
* an new position.
|
||||
* When this function is called, all dock widgets of the FloatingWidget
|
||||
* are already inserted into its new position
|
||||
*/
|
||||
void notifyFloatingWidgetDrop(CFloatingDockContainer* FloatingWidget);
|
||||
|
||||
/**
|
||||
* Returns the dock widget that has focus style in the ui or a nullptr if
|
||||
* not dock widget is painted focused.
|
||||
*/
|
||||
CDockWidget* focusedDockWidget() const;
|
||||
|
||||
public slots:
|
||||
/**
|
||||
* Request a focus change to the given dock widget
|
||||
*/
|
||||
void setDockWidgetFocused(CDockWidget* focusedNow);
|
||||
}; // class DockFocusController
|
||||
}
|
||||
// namespace ads
|
||||
//-----------------------------------------------------------------------------
|
||||
#endif // DockFocusControllerH
|
||||
|
||||
@@ -53,6 +53,13 @@
|
||||
#include "DockAreaWidget.h"
|
||||
#include "IconProvider.h"
|
||||
#include "DockingStateReader.h"
|
||||
#include "DockAreaTitleBar.h"
|
||||
#include "DockFocusController.h"
|
||||
#include "DockSplitter.h"
|
||||
|
||||
#ifdef Q_OS_LINUX
|
||||
#include "linux/FloatingWidgetTitleBar.h"
|
||||
#endif
|
||||
|
||||
|
||||
/**
|
||||
@@ -60,7 +67,7 @@
|
||||
* name. Normally, when resources are built as part of the application, the
|
||||
* resources are loaded automatically at startup. The Q_INIT_RESOURCE() macro
|
||||
* is necessary on some platforms for resources stored in a static library.
|
||||
* Because GCC caues a linker error if we put Q_INIT_RESOURCE into the
|
||||
* Because GCC causes a linker error if we put Q_INIT_RESOURCE into the
|
||||
* loadStyleSheet() function, we place it into a function outside of the ads
|
||||
* namespace
|
||||
*/
|
||||
@@ -72,6 +79,16 @@ static void initResource()
|
||||
|
||||
namespace ads
|
||||
{
|
||||
/**
|
||||
* Internal file version in case the structure changes internally
|
||||
*/
|
||||
enum eStateFileVersion
|
||||
{
|
||||
InitialVersion = 0, //!< InitialVersion
|
||||
Version1 = 1, //!< Version1
|
||||
CurrentVersion = Version1//!< CurrentVersion
|
||||
};
|
||||
|
||||
static CDockManager::ConfigFlags StaticConfigFlags = CDockManager::DefaultNonOpaqueConfig;
|
||||
|
||||
/**
|
||||
@@ -91,6 +108,8 @@ struct DockManagerPrivate
|
||||
CDockManager::eViewMenuInsertionOrder MenuInsertionOrder = CDockManager::MenuAlphabeticallySorted;
|
||||
bool RestoringState = false;
|
||||
QVector<CFloatingDockContainer*> UninitializedFloatingWidgets;
|
||||
CDockFocusController* FocusController = nullptr;
|
||||
CDockWidget* CentralWidget = nullptr;
|
||||
|
||||
/**
|
||||
* Private data constructor
|
||||
@@ -164,11 +183,14 @@ void DockManagerPrivate::loadStylesheet()
|
||||
{
|
||||
initResource();
|
||||
QString Result;
|
||||
QString FileName = ":ads/stylesheets/";
|
||||
FileName += CDockManager::testConfigFlag(CDockManager::FocusHighlighting)
|
||||
? "focus_highlighting" : "default";
|
||||
#ifdef Q_OS_LINUX
|
||||
QFile StyleSheetFile(":ads/stylesheets/default_linux.css");
|
||||
#else
|
||||
QFile StyleSheetFile(":ads/stylesheets/default.css");
|
||||
FileName += "_linux";
|
||||
#endif
|
||||
FileName += ".css";
|
||||
QFile StyleSheetFile(FileName);
|
||||
StyleSheetFile.open(QIODevice::ReadOnly);
|
||||
QTextStream StyleSheetStream(&StyleSheetFile);
|
||||
Result = StyleSheetStream.readAll();
|
||||
@@ -239,13 +261,46 @@ bool DockManagerPrivate::restoreStateFromXml(const QByteArray &state, int versi
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
s.setFileVersion(v);
|
||||
|
||||
ADS_PRINT(s.attributes().value("UserVersion"));
|
||||
// Older files do not support UserVersion but we still want to load them so
|
||||
// we first test if the attribute exists
|
||||
if (!s.attributes().value("UserVersion").isEmpty())
|
||||
{
|
||||
v = s.attributes().value("UserVersion").toInt(&ok);
|
||||
if (!ok || v != version)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
bool Result = true;
|
||||
#ifdef ADS_DEBUG_PRINT
|
||||
int DockContainers = s.attributes().value("Containers").toInt();
|
||||
#endif
|
||||
ADS_PRINT(DockContainers);
|
||||
|
||||
if (CentralWidget)
|
||||
{
|
||||
const auto CentralWidgetAttribute = s.attributes().value("CentralWidget");
|
||||
// If we have a central widget but a state without central widget, then
|
||||
// something is wrong.
|
||||
if (CentralWidgetAttribute.isEmpty())
|
||||
{
|
||||
qWarning() << "Dock manager has central widget but saved state does not have central widget.";
|
||||
return false;
|
||||
}
|
||||
|
||||
// If the object name of the central widget does not match the name of the
|
||||
// saved central widget, the something is wrong
|
||||
if (CentralWidget->objectName() != CentralWidgetAttribute.toString())
|
||||
{
|
||||
qWarning() << "Object name of central widget does not match name of central widget in saved state.";
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
int DockContainerCount = 0;
|
||||
while (s.readNextStartElement())
|
||||
{
|
||||
@@ -264,11 +319,11 @@ bool DockManagerPrivate::restoreStateFromXml(const QByteArray &state, int versi
|
||||
{
|
||||
// Delete remaining empty floating widgets
|
||||
int FloatingWidgetIndex = DockContainerCount - 1;
|
||||
int DeleteCount = FloatingWidgets.count() - FloatingWidgetIndex;
|
||||
for (int i = 0; i < DeleteCount; ++i)
|
||||
for (int i = FloatingWidgetIndex; i < FloatingWidgets.count(); ++i)
|
||||
{
|
||||
FloatingWidgets[FloatingWidgetIndex + i]->deleteLater();
|
||||
_this->removeDockContainer(FloatingWidgets[FloatingWidgetIndex + i]->dockContainer());
|
||||
auto* floatingWidget = FloatingWidgets[i];
|
||||
_this->removeDockContainer(floatingWidget->dockContainer());
|
||||
floatingWidget->deleteLater();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -335,8 +390,6 @@ void DockManagerPrivate::restoreDockAreasIndices()
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
//============================================================================
|
||||
void DockManagerPrivate::emitTopLevelEvents()
|
||||
{
|
||||
@@ -387,6 +440,7 @@ bool DockManagerPrivate::restoreState(const QByteArray& State, int version)
|
||||
restoreDockWidgetsOpenState();
|
||||
restoreDockAreasIndices();
|
||||
emitTopLevelEvents();
|
||||
_this->dumpLayout();
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -437,6 +491,15 @@ CDockManager::CDockManager(QWidget *parent) :
|
||||
d->ContainerOverlay = new CDockOverlay(this, CDockOverlay::ModeContainerOverlay);
|
||||
d->Containers.append(this);
|
||||
d->loadStylesheet();
|
||||
|
||||
if (CDockManager::testConfigFlag(CDockManager::FocusHighlighting))
|
||||
{
|
||||
d->FocusController = new CDockFocusController(this);
|
||||
}
|
||||
|
||||
#ifdef Q_OS_LINUX
|
||||
window()->installEventFilter(this);
|
||||
#endif
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
@@ -450,6 +513,70 @@ CDockManager::~CDockManager()
|
||||
delete d;
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
#ifdef Q_OS_LINUX
|
||||
bool CDockManager::eventFilter(QObject *obj, QEvent *e)
|
||||
{
|
||||
// Emulate Qt:Tool behaviour.
|
||||
// Required because on some WMs Tool windows can't be maximized.
|
||||
|
||||
// Window always on top of the MainWindow.
|
||||
if (e->type() == QEvent::WindowActivate)
|
||||
{
|
||||
for (auto _window : floatingWidgets())
|
||||
{
|
||||
if (!_window->isVisible() || window()->isMinimized())
|
||||
{
|
||||
continue;
|
||||
}
|
||||
// setWindowFlags(Qt::WindowStaysOnTopHint) will hide the window and thus requires a show call.
|
||||
// This then leads to flickering and a nasty endless loop (also buggy behaviour on Ubuntu).
|
||||
// So we just do it ourself.
|
||||
internal::xcb_update_prop(true, _window->window()->winId(),
|
||||
"_NET_WM_STATE", "_NET_WM_STATE_ABOVE", "_NET_WM_STATE_STAYS_ON_TOP");
|
||||
}
|
||||
}
|
||||
else if (e->type() == QEvent::WindowDeactivate)
|
||||
{
|
||||
for (auto _window : floatingWidgets())
|
||||
{
|
||||
if (!_window->isVisible() || window()->isMinimized())
|
||||
{
|
||||
continue;
|
||||
}
|
||||
internal::xcb_update_prop(false, _window->window()->winId(),
|
||||
"_NET_WM_STATE", "_NET_WM_STATE_ABOVE", "_NET_WM_STATE_STAYS_ON_TOP");
|
||||
_window->raise();
|
||||
}
|
||||
}
|
||||
|
||||
// Sync minimize with MainWindow
|
||||
if (e->type() == QEvent::WindowStateChange)
|
||||
{
|
||||
for (auto _window : floatingWidgets())
|
||||
{
|
||||
if (! _window->isVisible())
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (window()->isMinimized())
|
||||
{
|
||||
_window->showMinimized();
|
||||
}
|
||||
else
|
||||
{
|
||||
_window->setWindowState(_window->windowState() & (~Qt::WindowMinimized));
|
||||
}
|
||||
}
|
||||
if (!window()->isMinimized())
|
||||
{
|
||||
QApplication::setActiveWindow(window());
|
||||
}
|
||||
}
|
||||
return Super::eventFilter(obj, e);
|
||||
}
|
||||
#endif
|
||||
|
||||
//============================================================================
|
||||
void CDockManager::registerFloatingWidget(CFloatingDockContainer* FloatingWidget)
|
||||
@@ -528,8 +655,13 @@ QByteArray CDockManager::saveState(int version) const
|
||||
s.setAutoFormatting(ConfigFlags.testFlag(XmlAutoFormattingEnabled));
|
||||
s.writeStartDocument();
|
||||
s.writeStartElement("QtAdvancedDockingSystem");
|
||||
s.writeAttribute("Version", QString::number(version));
|
||||
s.writeAttribute("Version", QString::number(CurrentVersion));
|
||||
s.writeAttribute("UserVersion", QString::number(version));
|
||||
s.writeAttribute("Containers", QString::number(d->Containers.count()));
|
||||
if (d->CentralWidget)
|
||||
{
|
||||
s.writeAttribute("CentralWidget", d->CentralWidget->objectName());
|
||||
}
|
||||
for (auto Container : d->Containers)
|
||||
{
|
||||
Container->saveState(s);
|
||||
@@ -570,12 +702,11 @@ bool CDockManager::restoreState(const QByteArray &state, int version)
|
||||
emit restoringState();
|
||||
bool Result = d->restoreState(state, version);
|
||||
d->RestoringState = false;
|
||||
emit stateRestored();
|
||||
if (!IsHidden)
|
||||
{
|
||||
show();
|
||||
}
|
||||
|
||||
emit stateRestored();
|
||||
return Result;
|
||||
}
|
||||
|
||||
@@ -601,6 +732,7 @@ CFloatingDockContainer* CDockManager::addDockWidgetFloating(CDockWidget* Dockwid
|
||||
{
|
||||
d->UninitializedFloatingWidgets.append(FloatingWidget);
|
||||
}
|
||||
emit dockWidgetAdded(Dockwidget);
|
||||
return FloatingWidget;
|
||||
}
|
||||
|
||||
@@ -627,7 +759,9 @@ CDockAreaWidget* CDockManager::addDockWidget(DockWidgetArea area,
|
||||
CDockWidget* Dockwidget, CDockAreaWidget* DockAreaWidget)
|
||||
{
|
||||
d->DockWidgetsMap.insert(Dockwidget->objectName(), Dockwidget);
|
||||
return CDockContainerWidget::addDockWidget(area, Dockwidget, DockAreaWidget);
|
||||
auto AreaOfAddedDockWidget = CDockContainerWidget::addDockWidget(area, Dockwidget, DockAreaWidget);
|
||||
emit dockWidgetAdded(Dockwidget);
|
||||
return AreaOfAddedDockWidget;
|
||||
}
|
||||
|
||||
|
||||
@@ -671,6 +805,7 @@ void CDockManager::removeDockWidget(CDockWidget* Dockwidget)
|
||||
emit dockWidgetAboutToBeRemoved(Dockwidget);
|
||||
d->DockWidgetsMap.remove(Dockwidget->objectName());
|
||||
CDockContainerWidget::removeDockWidget(Dockwidget);
|
||||
Dockwidget->setDockManager(nullptr);
|
||||
emit dockWidgetRemoved(Dockwidget);
|
||||
}
|
||||
|
||||
@@ -778,6 +913,50 @@ void CDockManager::loadPerspectives(QSettings& Settings)
|
||||
Settings.endArray();
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
CDockWidget* CDockManager::centralWidget() const
|
||||
{
|
||||
return d->CentralWidget;
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
CDockAreaWidget* CDockManager::setCentralWidget(CDockWidget* widget)
|
||||
{
|
||||
if (!widget)
|
||||
{
|
||||
d->CentralWidget = nullptr;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
// Setting a new central widget is now allowed if there is already a central
|
||||
// widget or if there are already other dock widgets
|
||||
if (d->CentralWidget)
|
||||
{
|
||||
qWarning("Setting a central widget not possible because there is already a central widget.");
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
// Setting a central widget is now allowed if there are already other
|
||||
// dock widgets.
|
||||
if (!d->DockWidgetsMap.isEmpty())
|
||||
{
|
||||
qWarning("Setting a central widget not possible - the central widget need to be the first "
|
||||
"dock widget that is added to the dock manager.");
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
|
||||
widget->setFeature(CDockWidget::DockWidgetClosable, false);
|
||||
widget->setFeature(CDockWidget::DockWidgetMovable, false);
|
||||
widget->setFeature(CDockWidget::DockWidgetFloatable, false);
|
||||
d->CentralWidget = widget;
|
||||
CDockAreaWidget* CentralArea = addDockWidget(CenterDockWidgetArea, widget);
|
||||
CentralArea->setDockAreaFlag(CDockAreaWidget::eDockAreaFlag::HideSingleWidgetTitleBar, true);
|
||||
return CentralArea;
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
QAction* CDockManager::addToggleViewActionToMenu(QAction* ToggleViewAction,
|
||||
const QString& Group, const QIcon& GroupIcon)
|
||||
@@ -872,6 +1051,78 @@ CIconProvider& CDockManager::iconProvider()
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
void CDockManager::notifyWidgetOrAreaRelocation(QWidget* DroppedWidget)
|
||||
{
|
||||
if (d->FocusController)
|
||||
{
|
||||
d->FocusController->notifyWidgetOrAreaRelocation(DroppedWidget);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
void CDockManager::notifyFloatingWidgetDrop(CFloatingDockContainer* FloatingWidget)
|
||||
{
|
||||
if (d->FocusController)
|
||||
{
|
||||
d->FocusController->notifyFloatingWidgetDrop(FloatingWidget);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
void CDockManager::setDockWidgetFocused(CDockWidget* DockWidget)
|
||||
{
|
||||
if (d->FocusController)
|
||||
{
|
||||
d->FocusController->setDockWidgetFocused(DockWidget);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//===========================================================================
|
||||
CDockWidget* CDockManager::focusedDockWidget() const
|
||||
{
|
||||
if (!d->FocusController)
|
||||
{
|
||||
return nullptr;
|
||||
}
|
||||
else
|
||||
{
|
||||
return d->FocusController->focusedDockWidget();
|
||||
}
|
||||
}
|
||||
|
||||
//===========================================================================
|
||||
QList<int> CDockManager::splitterSizes(CDockAreaWidget *ContainedArea) const
|
||||
{
|
||||
if (ContainedArea)
|
||||
{
|
||||
auto Splitter = internal::findParent<CDockSplitter*>(ContainedArea);
|
||||
if (Splitter)
|
||||
{
|
||||
return Splitter->sizes();
|
||||
}
|
||||
}
|
||||
return QList<int>();
|
||||
}
|
||||
|
||||
//===========================================================================
|
||||
void CDockManager::setSplitterSizes(CDockAreaWidget *ContainedArea, const QList<int>& sizes)
|
||||
{
|
||||
if (!ContainedArea)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
auto Splitter = internal::findParent<CDockSplitter*>(ContainedArea);
|
||||
if (Splitter && Splitter->count() == sizes.count())
|
||||
{
|
||||
Splitter->setSizes(sizes);
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace ads
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
|
||||
@@ -36,8 +36,8 @@
|
||||
#include "FloatingDockContainer.h"
|
||||
|
||||
|
||||
class QSettings;
|
||||
class QMenu;
|
||||
QT_FORWARD_DECLARE_CLASS(QSettings)
|
||||
QT_FORWARD_DECLARE_CLASS(QMenu)
|
||||
|
||||
namespace ads
|
||||
{
|
||||
@@ -84,6 +84,7 @@ private:
|
||||
friend struct FloatingDragPreviewPrivate;
|
||||
friend class CDockAreaTitleBar;
|
||||
|
||||
|
||||
protected:
|
||||
/**
|
||||
* Registers the given floating widget in the internal list of
|
||||
@@ -118,6 +119,22 @@ protected:
|
||||
*/
|
||||
CDockOverlay* dockAreaOverlay() const;
|
||||
|
||||
|
||||
/**
|
||||
* A container needs to call this function if a widget has been dropped
|
||||
* into it
|
||||
*/
|
||||
void notifyWidgetOrAreaRelocation(QWidget* RelocatedWidget);
|
||||
|
||||
/**
|
||||
* This function is called, if a floating widget has been dropped into
|
||||
* an new position.
|
||||
* When this function is called, all dock widgets of the FloatingWidget
|
||||
* are already inserted into its new position
|
||||
*/
|
||||
void notifyFloatingWidgetDrop(CFloatingDockContainer* FloatingWidget);
|
||||
|
||||
|
||||
/**
|
||||
* Show the floating widgets that has been created floating
|
||||
*/
|
||||
@@ -162,6 +179,15 @@ public:
|
||||
HideSingleCentralWidgetTitleBar = 0x100000, //!< If there is only one single visible dock widget in the main dock container (the dock manager) and if this flag is set, then the titlebar of this dock widget will be hidden
|
||||
//!< this only makes sense for non draggable and non floatable widgets and enables the creation of some kind of "central" widget
|
||||
|
||||
FocusHighlighting = 0x200000, //!< enables styling of focused dock widget tabs or floating widget titlebar
|
||||
EqualSplitOnInsertion = 0x400000, ///!< if enabled, the space is equally distributed to all widgets in a splitter
|
||||
|
||||
FloatingContainerForceNativeTitleBar = 0x800000, //!< Linux only ! Forces all FloatingContainer to use the native title bar. This might break docking for FloatinContainer on some Window Managers (like Kwin/KDE).
|
||||
//!< If neither this nor FloatingContainerForceCustomTitleBar is set (the default) native titlebars are used except on known bad systems.
|
||||
//! Users can overwrite this by setting the environment variable ADS_UseNativeTitle to "1" or "0".
|
||||
FloatingContainerForceQWidgetTitleBar = 0x1000000,//!< Linux only ! Forces all FloatingContainer to use a QWidget based title bar.
|
||||
//!< If neither this nor FloatingContainerForceNativeTitleBar is set (the default) native titlebars are used except on known bad systems.
|
||||
//! Users can overwrite this by setting the environment variable ADS_UseNativeTitle to "1" or "0".
|
||||
|
||||
DefaultDockAreaButtons = DockAreaHasCloseButton
|
||||
| DockAreaHasUndockButton
|
||||
@@ -308,8 +334,12 @@ public:
|
||||
* If auto formatting is enabled, the output is intended and line wrapped.
|
||||
* The XmlMode XmlAutoFormattingDisabled is better if you would like to have
|
||||
* a more compact XML output - i.e. for storage in ini files.
|
||||
* The version number is stored as part of the data.
|
||||
* To restore the saved state, pass the return value and version number
|
||||
* to restoreState().
|
||||
* \see restoreState()
|
||||
*/
|
||||
QByteArray saveState(int version = Version1) const;
|
||||
QByteArray saveState(int version = 0) const;
|
||||
|
||||
/**
|
||||
* Restores the state of this dockmanagers dockwidgets.
|
||||
@@ -317,8 +347,9 @@ public:
|
||||
* not match, the dockmanager's state is left unchanged, and this function
|
||||
* returns false; otherwise, the state is restored, and this function
|
||||
* returns true.
|
||||
* \see saveState()
|
||||
*/
|
||||
bool restoreState(const QByteArray &state, int version = Version1);
|
||||
bool restoreState(const QByteArray &state, int version = 0);
|
||||
|
||||
/**
|
||||
* Saves the current perspective to the internal list of perspectives.
|
||||
@@ -355,7 +386,31 @@ public:
|
||||
*/
|
||||
void loadPerspectives(QSettings& Settings);
|
||||
|
||||
/**
|
||||
/**
|
||||
* This function returns managers central widget or nullptr if no central widget is set.
|
||||
*/
|
||||
CDockWidget* centralWidget() const;
|
||||
|
||||
/**
|
||||
* Adds dockwidget widget into the central area and marks it as central widget.
|
||||
* If central widget is set, it will be the only dock widget
|
||||
* that will resize with the dock container. A central widget if not
|
||||
* movable, floatable or closable and the titlebar of the central
|
||||
* dock area is not visible.
|
||||
* If the given widget could be set as central widget, the function returns
|
||||
* the created dock area. If the widget could not be set, because there
|
||||
* is already a central widget, this function returns a nullptr.
|
||||
* To clear the central widget, pass a nullptr to the function.
|
||||
* \note Setting a central widget is only possible if no other dock widgets
|
||||
* have been registered before. That means, this function should be the
|
||||
* first function that you call before you add other dock widgets.
|
||||
* \retval != 0 The dock area that contains the central widget
|
||||
* \retval nullptr Indicates that the given widget can not be set as central
|
||||
* widget because there is already a central widget.
|
||||
*/
|
||||
CDockAreaWidget* setCentralWidget(CDockWidget* widget);
|
||||
|
||||
/**
|
||||
* Adds a toggle view action to the the internal view menu.
|
||||
* You can either manage the insertion of the toggle view actions in your
|
||||
* application or you can add the actions to the internal view menu and
|
||||
@@ -405,12 +460,65 @@ public:
|
||||
*/
|
||||
static int startDragDistance();
|
||||
|
||||
/**
|
||||
* Helper function to set focus depending on the configuration of the
|
||||
* FocusStyling flag
|
||||
*/
|
||||
template <class QWidgetPtr>
|
||||
static void setWidgetFocus(QWidgetPtr widget)
|
||||
{
|
||||
if (!CDockManager::testConfigFlag(CDockManager::FocusHighlighting))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
widget->setFocus(Qt::OtherFocusReason);
|
||||
}
|
||||
|
||||
#ifdef Q_OS_LINUX
|
||||
bool eventFilter(QObject *obj, QEvent *e) override;
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Returns the dock widget that has focus style in the ui or a nullptr if
|
||||
* not dock widget is painted focused.
|
||||
* If the flag FocusHighlighting is disabled, this function always returns
|
||||
* nullptr.
|
||||
*/
|
||||
CDockWidget* focusedDockWidget() const;
|
||||
|
||||
/**
|
||||
* Returns the sizes of the splitter that contains the dock area.
|
||||
*
|
||||
* If there is no splitter that contains the area, an empty list will be
|
||||
* returned.
|
||||
*/
|
||||
QList<int> splitterSizes(CDockAreaWidget *ContainedArea) const;
|
||||
|
||||
/**
|
||||
* Update the sizes of a splitter
|
||||
* Programmatically updates the sizes of a given splitter by calling
|
||||
* QSplitter::setSizes(). The splitter will be the splitter that
|
||||
* contains the supplied dock area widget. If there is not splitter
|
||||
* that contains the dock area, or the sizes supplied does not match
|
||||
* the number of children of the splitter, this method will have no
|
||||
* effect.
|
||||
*/
|
||||
void setSplitterSizes(CDockAreaWidget *ContainedArea, const QList<int>& sizes);
|
||||
|
||||
public slots:
|
||||
/**
|
||||
* Opens the perspective with the given name.
|
||||
*/
|
||||
void openPerspective(const QString& PerspectiveName);
|
||||
|
||||
/**
|
||||
* Request a focus change to the given dock widget.
|
||||
* This function only has an effect, if the flag CDockManager::FocusStyling
|
||||
* is enabled
|
||||
*/
|
||||
void setDockWidgetFocused(CDockWidget* DockWidget);
|
||||
|
||||
signals:
|
||||
/**
|
||||
* This signal is emitted if the list of perspectives changed
|
||||
@@ -457,20 +565,26 @@ signals:
|
||||
* An application can use this signal to e.g. subscribe to events of
|
||||
* the newly created window.
|
||||
*/
|
||||
void floatingWidgetCreated(CFloatingDockContainer* FloatingWidget);
|
||||
void floatingWidgetCreated(ads::CFloatingDockContainer* FloatingWidget);
|
||||
|
||||
/**
|
||||
* This signal is emitted, if a new DockArea has been created.
|
||||
* An application can use this signal to set custom icons or custom
|
||||
* tooltips for the DockArea buttons.
|
||||
*/
|
||||
void dockAreaCreated(CDockAreaWidget* DockArea);
|
||||
void dockAreaCreated(ads::CDockAreaWidget* DockArea);
|
||||
|
||||
/**
|
||||
* This signal is emitted if a dock widget has been added to this
|
||||
* dock manager instance.
|
||||
*/
|
||||
void dockWidgetAdded(ads::CDockWidget* DockWidget);
|
||||
|
||||
/**
|
||||
* This signal is emitted just before the given dock widget is removed
|
||||
* from the
|
||||
* from the dock manager
|
||||
*/
|
||||
void dockWidgetAboutToBeRemoved(CDockWidget* DockWidget);
|
||||
void dockWidgetAboutToBeRemoved(ads::CDockWidget* DockWidget);
|
||||
|
||||
/**
|
||||
* This signal is emitted if a dock widget has been removed with the remove
|
||||
@@ -478,7 +592,14 @@ signals:
|
||||
* If this signal is emitted, the dock widget has been removed from the
|
||||
* docking system but it is not deleted yet.
|
||||
*/
|
||||
void dockWidgetRemoved(CDockWidget* DockWidget);
|
||||
void dockWidgetRemoved(ads::CDockWidget* DockWidget);
|
||||
|
||||
/**
|
||||
* This signal is emitted if the focused dock widget changed.
|
||||
* Both old and now can be nullptr.
|
||||
* The focused dock widget is the one that is highlighted in the GUI
|
||||
*/
|
||||
void focusedDockWidgetChanged(ads::CDockWidget* old, ads::CDockWidget* now);
|
||||
}; // class DockManager
|
||||
} // namespace ads
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
@@ -26,10 +26,11 @@
|
||||
#include <QHash>
|
||||
#include <QRect>
|
||||
#include <QFrame>
|
||||
class QGridLayout;
|
||||
|
||||
#include "ads_globals.h"
|
||||
|
||||
QT_FORWARD_DECLARE_CLASS(QGridLayout)
|
||||
|
||||
namespace ads
|
||||
{
|
||||
struct DockOverlayPrivate;
|
||||
|
||||
@@ -102,6 +102,20 @@ QWidget* CDockSplitter::lastWidget() const
|
||||
return (count() > 0) ? widget(count() - 1) : nullptr;
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
bool CDockSplitter::isResizingWithContainer() const
|
||||
{
|
||||
for (auto area : findChildren<CDockAreaWidget*>())
|
||||
{
|
||||
if(area->isCentralWidgetArea())
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
} // namespace ads
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
|
||||
@@ -71,6 +71,11 @@ public:
|
||||
* Returns last widget of nullptr is splitter is empty
|
||||
*/
|
||||
QWidget* lastWidget() const;
|
||||
|
||||
/**
|
||||
* Returns true if the splitter contains central widget of dock manager.
|
||||
*/
|
||||
bool isResizingWithContainer() const;
|
||||
}; // class CDockSplitter
|
||||
|
||||
} // namespace ads
|
||||
|
||||
@@ -134,6 +134,7 @@ void DockWidgetPrivate::showDockWidget()
|
||||
{
|
||||
CFloatingDockContainer* FloatingWidget = new CFloatingDockContainer(_this);
|
||||
FloatingWidget->resize(_this->size());
|
||||
TabWidget->show();
|
||||
FloatingWidget->show();
|
||||
}
|
||||
else
|
||||
@@ -235,6 +236,11 @@ CDockWidget::CDockWidget(const QString &title, QWidget *parent) :
|
||||
connect(d->ToggleViewAction, SIGNAL(triggered(bool)), this,
|
||||
SLOT(toggleView(bool)));
|
||||
setToolbarFloatingStyle(false);
|
||||
|
||||
if (CDockManager::testConfigFlag(CDockManager::FocusHighlighting))
|
||||
{
|
||||
setFocusPolicy(Qt::ClickFocus);
|
||||
}
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
@@ -293,6 +299,7 @@ QWidget* CDockWidget::takeWidget()
|
||||
w = d->ScrollArea->takeWidget();
|
||||
delete d->ScrollArea;
|
||||
d->ScrollArea = nullptr;
|
||||
d->Widget = nullptr;
|
||||
}
|
||||
else if (d->Widget)
|
||||
{
|
||||
@@ -333,6 +340,8 @@ void CDockWidget::setFeatures(DockWidgetFeatures features)
|
||||
d->Features = features;
|
||||
emit featuresChanged(d->Features);
|
||||
d->TabWidget->onDockWidgetFeaturesChanged();
|
||||
if(CDockAreaWidget* DockArea = dockAreaWidget())
|
||||
DockArea->onDockWidgetFeaturesChanged();
|
||||
}
|
||||
|
||||
|
||||
@@ -454,6 +463,13 @@ void CDockWidget::setMinimumSizeHintMode(eMinimumSizeHintMode Mode)
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
bool CDockWidget::isCentralWidget() const
|
||||
{
|
||||
return dockManager()->centralWidget() == this;
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockWidget::toggleView(bool Open)
|
||||
{
|
||||
@@ -533,6 +549,7 @@ void CDockWidget::setDockArea(CDockAreaWidget* DockArea)
|
||||
{
|
||||
d->DockArea = DockArea;
|
||||
d->ToggleViewAction->setChecked(DockArea != nullptr && !this->isClosed());
|
||||
setParent(DockArea);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -34,8 +34,8 @@
|
||||
|
||||
#include "ads_globals.h"
|
||||
|
||||
class QToolBar;
|
||||
class QXmlStreamWriter;
|
||||
QT_FORWARD_DECLARE_CLASS(QToolBar)
|
||||
QT_FORWARD_DECLARE_CLASS(QXmlStreamWriter)
|
||||
|
||||
namespace ads
|
||||
{
|
||||
@@ -149,11 +149,14 @@ public:
|
||||
{
|
||||
DockWidgetClosable = 0x01,///< dock widget has a close button
|
||||
DockWidgetMovable = 0x02,///< dock widget is movable and can be moved to a new position in the current dock container
|
||||
DockWidgetFloatable = 0x04,
|
||||
DockWidgetFloatable = 0x04,///< dock widget can be dragged into a floating window
|
||||
DockWidgetDeleteOnClose = 0x08, ///< deletes the dock widget when it is closed
|
||||
CustomCloseHandling = 0x10,
|
||||
DefaultDockWidgetFeatures = DockWidgetClosable | DockWidgetMovable | DockWidgetFloatable,
|
||||
CustomCloseHandling = 0x10, ///< clicking the close button will not close the dock widget but emits the closeRequested() signal instead
|
||||
DockWidgetFocusable = 0x20, ///< if this is enabled, a dock widget can get focus highlighting
|
||||
DockWidgetForceCloseWithArea = 0x40, ///< dock widget will be closed when the dock area hosting it is closed
|
||||
DefaultDockWidgetFeatures = DockWidgetClosable | DockWidgetMovable | DockWidgetFloatable | DockWidgetFocusable,
|
||||
AllDockWidgetFeatures = DefaultDockWidgetFeatures | DockWidgetDeleteOnClose | CustomCloseHandling,
|
||||
DockWidgetAlwaysCloseAndDelete = DockWidgetForceCloseWithArea | DockWidgetDeleteOnClose,
|
||||
NoDockWidgetFeatures = 0x00
|
||||
};
|
||||
Q_DECLARE_FLAGS(DockWidgetFeatures, DockWidgetFeature)
|
||||
@@ -196,7 +199,7 @@ public:
|
||||
* To ensure, that a dock widget does not block resizing, the dock widget
|
||||
* reimplements minimumSizeHint() function to return a very small minimum
|
||||
* size hint. If you would like to adhere the minimumSizeHint() from the
|
||||
* content widget, the set the minimumSizeHintMode() to
|
||||
* content widget, then set the minimumSizeHintMode() to
|
||||
* MinimumSizeHintFromContent.
|
||||
*/
|
||||
enum eMinimumSizeHintMode
|
||||
@@ -359,6 +362,11 @@ public:
|
||||
*/
|
||||
void setMinimumSizeHintMode(eMinimumSizeHintMode Mode);
|
||||
|
||||
/**
|
||||
* Returns true if the dock widget is set as central widget of it's dock manager
|
||||
*/
|
||||
bool isCentralWidget() const;
|
||||
|
||||
/**
|
||||
* Sets the dock widget icon that is shown in tabs and in toggle view
|
||||
* actions
|
||||
@@ -576,7 +584,7 @@ signals:
|
||||
* This signal is emitted when the features property changes.
|
||||
* The features parameter gives the new value of the property.
|
||||
*/
|
||||
void featuresChanged(DockWidgetFeatures features);
|
||||
void featuresChanged(ads::CDockWidget::DockWidgetFeatures features);
|
||||
}; // class DockWidget
|
||||
}
|
||||
// namespace ads
|
||||
|
||||
@@ -28,7 +28,7 @@
|
||||
//============================================================================
|
||||
// INCLUDES
|
||||
//============================================================================
|
||||
#include <FloatingDragPreview.h>
|
||||
#include "FloatingDragPreview.h"
|
||||
#include "ElidingLabel.h"
|
||||
#include "DockWidgetTab.h"
|
||||
|
||||
@@ -51,7 +51,6 @@
|
||||
#include "DockManager.h"
|
||||
#include "IconProvider.h"
|
||||
|
||||
#include <iostream>
|
||||
|
||||
namespace ads
|
||||
{
|
||||
@@ -77,6 +76,7 @@ struct DockWidgetTabPrivate
|
||||
QAbstractButton* CloseButton = nullptr;
|
||||
QSpacerItem* IconTextSpacer;
|
||||
QPoint TabDragStartPosition;
|
||||
QSize IconSize;
|
||||
|
||||
/**
|
||||
* Private data constructor
|
||||
@@ -114,7 +114,7 @@ struct DockWidgetTabPrivate
|
||||
*/
|
||||
bool testConfigFlag(CDockManager::eConfigFlag Flag) const
|
||||
{
|
||||
return CDockManager::configFlags().testFlag(Flag);
|
||||
return CDockManager::testConfigFlag(Flag);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -134,6 +134,31 @@ struct DockWidgetTabPrivate
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Update the close button visibility from current feature/config
|
||||
*/
|
||||
void updateCloseButtonVisibility(bool active)
|
||||
{
|
||||
bool DockWidgetClosable = DockWidget->features().testFlag(CDockWidget::DockWidgetClosable);
|
||||
bool ActiveTabHasCloseButton = testConfigFlag(CDockManager::ActiveTabHasCloseButton);
|
||||
bool AllTabsHaveCloseButton = testConfigFlag(CDockManager::AllTabsHaveCloseButton);
|
||||
bool TabHasCloseButton = (ActiveTabHasCloseButton && active) | AllTabsHaveCloseButton;
|
||||
CloseButton->setVisible(DockWidgetClosable && TabHasCloseButton);
|
||||
}
|
||||
|
||||
/**
|
||||
* Update the size policy of the close button depending on the
|
||||
* RetainTabSizeWhenCloseButtonHidden feature
|
||||
*/
|
||||
void updateCloseButtonSizePolicy()
|
||||
{
|
||||
auto Features = DockWidget->features();
|
||||
auto SizePolicy = CloseButton->sizePolicy();
|
||||
SizePolicy.setRetainSizeWhenHidden(Features.testFlag(CDockWidget::DockWidgetClosable)
|
||||
&& testConfigFlag(CDockManager::RetainTabSizeWhenCloseButtonHidden));
|
||||
CloseButton->setSizePolicy(SizePolicy);
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
IFloatingWidget* createFloatingWidget(T* Widget, bool OpaqueUndocking)
|
||||
{
|
||||
@@ -160,6 +185,28 @@ struct DockWidgetTabPrivate
|
||||
GlobalDragStartMousePosition = GlobalPos;
|
||||
DragStartMousePosition = _this->mapFromGlobal(GlobalPos);
|
||||
}
|
||||
|
||||
/**
|
||||
* Update the icon in case the icon size changed
|
||||
*/
|
||||
void updateIcon()
|
||||
{
|
||||
if (!IconLabel || Icon.isNull())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (IconSize.isValid())
|
||||
{
|
||||
IconLabel->setPixmap(Icon.pixmap(IconSize));
|
||||
}
|
||||
else
|
||||
{
|
||||
IconLabel->setPixmap(Icon.pixmap(_this->style()->pixelMetric(QStyle::PM_SmallIconSize, nullptr, _this)));
|
||||
}
|
||||
IconLabel->setVisible(true);
|
||||
}
|
||||
|
||||
};
|
||||
// struct DockWidgetTabPrivate
|
||||
|
||||
@@ -187,7 +234,7 @@ void DockWidgetTabPrivate::createLayout()
|
||||
CloseButton->setObjectName("tabCloseButton");
|
||||
internal::setButtonIcon(CloseButton, QStyle::SP_TitleBarCloseButton, TabCloseIcon);
|
||||
CloseButton->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed);
|
||||
_this->onDockWidgetFeaturesChanged();
|
||||
updateCloseButtonSizePolicy();
|
||||
internal::setToolTip(CloseButton, QObject::tr("Close Tab"));
|
||||
_this->connect(CloseButton, SIGNAL(clicked()), SIGNAL(closeRequested()));
|
||||
|
||||
@@ -242,7 +289,7 @@ bool DockWidgetTabPrivate::startFloating(eDragState DraggingState)
|
||||
ADS_PRINT("startFloating");
|
||||
DragState = DraggingState;
|
||||
IFloatingWidget* FloatingWidget = nullptr;
|
||||
bool OpaqueUndocking = CDockManager::configFlags().testFlag(CDockManager::OpaqueUndocking) ||
|
||||
bool OpaqueUndocking = CDockManager::testConfigFlag(CDockManager::OpaqueUndocking) ||
|
||||
(DraggingFloatingWidget != DraggingState);
|
||||
|
||||
// If section widget has multiple tabs, we take only one tab
|
||||
@@ -284,6 +331,10 @@ CDockWidgetTab::CDockWidgetTab(CDockWidget* DockWidget, QWidget *parent) :
|
||||
setAttribute(Qt::WA_NoMousePropagation, true);
|
||||
d->DockWidget = DockWidget;
|
||||
d->createLayout();
|
||||
if (CDockManager::testConfigFlag(CDockManager::FocusHighlighting))
|
||||
{
|
||||
setFocusPolicy(Qt::ClickFocus);
|
||||
}
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
@@ -394,7 +445,7 @@ void CDockWidgetTab::mouseMoveEvent(QMouseEvent* ev)
|
||||
{
|
||||
// If we undock, we need to restore the initial position of this
|
||||
// tab because it looks strange if it remains on its dragged position
|
||||
if (d->isDraggingState(DraggingTab) && !CDockManager::configFlags().testFlag(CDockManager::OpaqueUndocking))
|
||||
if (d->isDraggingState(DraggingTab) && !CDockManager::testConfigFlag(CDockManager::OpaqueUndocking))
|
||||
{
|
||||
parentWidget()->layout()->update();
|
||||
}
|
||||
@@ -456,21 +507,34 @@ bool CDockWidgetTab::isActiveTab() const
|
||||
//============================================================================
|
||||
void CDockWidgetTab::setActiveTab(bool active)
|
||||
{
|
||||
bool DockWidgetClosable = d->DockWidget->features().testFlag(CDockWidget::DockWidgetClosable);
|
||||
bool ActiveTabHasCloseButton = d->testConfigFlag(CDockManager::ActiveTabHasCloseButton);
|
||||
bool AllTabsHaveCloseButton = d->testConfigFlag(CDockManager::AllTabsHaveCloseButton);
|
||||
bool TabHasCloseButton = (ActiveTabHasCloseButton && active) | AllTabsHaveCloseButton;
|
||||
d->CloseButton->setVisible(DockWidgetClosable && TabHasCloseButton);
|
||||
if (d->IsActiveTab == active)
|
||||
d->updateCloseButtonVisibility(active);
|
||||
|
||||
// Focus related stuff
|
||||
if (CDockManager::testConfigFlag(CDockManager::FocusHighlighting) && !d->DockWidget->dockManager()->isRestoringState())
|
||||
{
|
||||
bool UpdateFocusStyle = false;
|
||||
if (active && !hasFocus())
|
||||
{
|
||||
setFocus(Qt::OtherFocusReason);
|
||||
UpdateFocusStyle = true;
|
||||
}
|
||||
|
||||
if (d->IsActiveTab == active)
|
||||
{
|
||||
if (UpdateFocusStyle)
|
||||
{
|
||||
updateStyle();
|
||||
}
|
||||
return;
|
||||
}
|
||||
}
|
||||
else if (d->IsActiveTab == active)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
d->IsActiveTab = active;
|
||||
style()->unpolish(this);
|
||||
style()->polish(this);
|
||||
d->TitleLabel->style()->unpolish(d->TitleLabel);
|
||||
d->TitleLabel->style()->polish(d->TitleLabel);
|
||||
updateStyle();
|
||||
update();
|
||||
updateGeometry();
|
||||
|
||||
@@ -527,11 +591,7 @@ void CDockWidgetTab::setIcon(const QIcon& Icon)
|
||||
}
|
||||
|
||||
d->Icon = Icon;
|
||||
if (d->IconLabel)
|
||||
{
|
||||
d->IconLabel->setPixmap(Icon.pixmap(style()->pixelMetric(QStyle::PM_SmallIconSize, nullptr, this)));
|
||||
d->IconLabel->setVisible(true);
|
||||
}
|
||||
d->updateIcon();
|
||||
}
|
||||
|
||||
|
||||
@@ -570,7 +630,7 @@ void CDockWidgetTab::mouseDoubleClickEvent(QMouseEvent *event)
|
||||
void CDockWidgetTab::setVisible(bool visible)
|
||||
{
|
||||
// Just here for debugging to insert debug output
|
||||
Super::setVisible(visible);
|
||||
Super::setVisible(visible);
|
||||
}
|
||||
|
||||
|
||||
@@ -626,11 +686,8 @@ bool CDockWidgetTab::event(QEvent *e)
|
||||
//============================================================================
|
||||
void CDockWidgetTab::onDockWidgetFeaturesChanged()
|
||||
{
|
||||
auto Features = d->DockWidget->features();
|
||||
auto SizePolicy = d->CloseButton->sizePolicy();
|
||||
SizePolicy.setRetainSizeWhenHidden(Features.testFlag(CDockWidget::DockWidgetClosable)
|
||||
&& d->testConfigFlag(CDockManager::RetainTabSizeWhenCloseButtonHidden));
|
||||
d->CloseButton->setSizePolicy(SizePolicy);
|
||||
d->updateCloseButtonSizePolicy();
|
||||
d->updateCloseButtonVisibility(isActiveTab());
|
||||
}
|
||||
|
||||
|
||||
@@ -641,6 +698,28 @@ void CDockWidgetTab::setElideMode(Qt::TextElideMode mode)
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockWidgetTab::updateStyle()
|
||||
{
|
||||
internal::repolishStyle(this, internal::RepolishDirectChildren);
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
QSize CDockWidgetTab::iconSize() const
|
||||
{
|
||||
return d->IconSize;
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockWidgetTab::setIconSize(const QSize& Size)
|
||||
{
|
||||
d->IconSize = Size;
|
||||
d->updateIcon();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
} // namespace ads
|
||||
|
||||
@@ -31,6 +31,7 @@
|
||||
// INCLUDES
|
||||
//============================================================================
|
||||
#include <QFrame>
|
||||
#include <QSize>
|
||||
|
||||
#include "ads_globals.h"
|
||||
|
||||
@@ -39,6 +40,7 @@ namespace ads
|
||||
class CDockWidget;
|
||||
class CDockAreaWidget;
|
||||
struct DockWidgetTabPrivate;
|
||||
class CDockManager;
|
||||
|
||||
/**
|
||||
* A dock widget tab that shows a title and an icon.
|
||||
@@ -49,11 +51,13 @@ class ADS_EXPORT CDockWidgetTab : public QFrame
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(bool activeTab READ isActiveTab WRITE setActiveTab NOTIFY activeTabChanged)
|
||||
Q_PROPERTY(QSize iconSize READ iconSize WRITE setIconSize)
|
||||
|
||||
private:
|
||||
DockWidgetTabPrivate* d; ///< private data (pimpl)
|
||||
friend struct DockWidgetTabPrivate;
|
||||
friend class CDockWidget;
|
||||
friend class CDockManager;
|
||||
void onDockWidgetFeaturesChanged();
|
||||
|
||||
private slots:
|
||||
@@ -152,6 +156,24 @@ public:
|
||||
*/
|
||||
void setElideMode(Qt::TextElideMode mode);
|
||||
|
||||
/**
|
||||
* Update stylesheet style if a property changes
|
||||
*/
|
||||
void updateStyle();
|
||||
|
||||
/**
|
||||
* Returns the icon size.
|
||||
* If no explicit icon size has been set, the function returns an invalid
|
||||
* QSize
|
||||
*/
|
||||
QSize iconSize() const;
|
||||
|
||||
/**
|
||||
* Set an explicit icon size.
|
||||
* If no icon size has been set explicitely, than the tab sets the icon size
|
||||
* depending on the style
|
||||
*/
|
||||
void setIconSize(const QSize& Size);
|
||||
|
||||
public slots:
|
||||
virtual void setVisible(bool visible) override;
|
||||
|
||||