diff --git a/doc/how_to_build_linux.md b/doc/how_to_build_linux.md
index 6bfa621..6212a2c 100644
--- a/doc/how_to_build_linux.md
+++ b/doc/how_to_build_linux.md
@@ -1,42 +1,43 @@
-# Setting up the development environment for GNU/Linux and Unix
+# Setting up the development environment for GNU/Linux
## Required software
-You will need to install some dependencies before you can build. Depending on your distribution you will be able to install the packages directly with the command lines below or will have to manually install:
+Building OpenToonz from source requires the following dependencies:
- Git
-- GCC
-- CMake
- - confirmed to work with 3.4.1.
-- Qt5
- - http://download.qt.io/official_releases/qt/5.5/5.5.1/
-- Boost
- - http://www.boost.org/users/history/version_1_55_0.html
+- GCC or Clang
+- CMake (3.4.1 or newer).
+- Qt5 (5.5 or newer)
+- Boost (1.55 or newer)
- SDL2
+- LibPNG
+- SuperLU
+- Lzo2
+- FreeType
-### Installing required packages on Debian / Ubuntu
+### Installing Dependencies on Debian / Ubuntu
```
-$ sudo apt-get install build-essential git cmake pkg-config libboost-all-dev qt5-default qtbase5-dev libqt5svg5-dev qtscript5-dev qttools5-dev-tools libqt5opengl5-dev qtmultimedia5-dev libsuperlu-dev liblz4-dev libusb-1.0-0-dev liblzo2-dev libpng-dev libjpeg-dev libglew-dev freeglut3-dev libsdl2-dev libfreetype6-dev
+$ sudo apt-get install build-essential git cmake pkg-config libboost-all-dev qt5-default qtbase5-dev libqt5svg5-dev qtscript5-dev qttools5-dev qttools5-dev-tools libqt5opengl5-dev qtmultimedia5-dev libsuperlu-dev liblz4-dev libusb-1.0-0-dev liblzo2-dev libpng-dev libjpeg-dev libglew-dev freeglut3-dev libsdl2-dev libfreetype6-dev
```
Notes:
-* It's possible we also need libgsl2 (or maybe libopenbias-dev)
+* It's possible we also need `libgsl2` (or maybe `libopenblas-dev`)
-### Installing required packages on RedHat / Mageia
+### Installing Dependencies on RedHat / CentOS
TODO
```
$ rpm ...
```
-### Installing required packages on Fedora
+### Installing Dependencies on Fedora
(it may include some useless packages)
```
-dnf install gcc gcc-c++ automake git cmake boost boost-devel SuperLU SuperLU-devel lz4-devel libusb-devel lzo-devel libjpeg-turbo-devel GLEW libGLEW freeglut-devel freeglut SDL2 SDL2-devel freetype-devel libpng-devel qt5-base qt5-qtbase-devel qt5-qtsvg qt5-qtsvg-devel qt5-qtscript qt5-qtscript-devel qt5-qttools qt5-qttools-devel blas blas-devel
+$ dnf install gcc gcc-c++ automake git cmake boost boost-devel SuperLU SuperLU-devel lz4-devel lzma libusb-devel lzo-devel libjpeg-turbo-devel libGLEW glew-devel freeglut-devel freeglut SDL2 SDL2-devel freetype-devel libpng-devel qt5-qtbase-devel qt5-qtsvg qt5-qtsvg-devel qt5-qtscript qt5-qtscript-devel qt5-qttools qt5-qttools-devel qt5-qtmultimedia-devel blas blas-devel
```
-### Installing required packages on ArchLinux
+### Installing Dependencies on ArchLinux
```
$ sudo pacman -S base-devel git cmake boost boost-libs qt5-base qt5-svg qt5-script qt5-tools qt5-multimedia lz4 libusb lzo libjpeg-turbo glew freeglut sdl2 freetype2
@@ -48,38 +49,40 @@ $ yaourt -S superlu
```
Notes:
-* ArchLinux had BLAS splitted in blas and cblas
+* ArchLinux has `blas` split into `blas` and `cblas`.
-### Installing required packages on openSUSE
+### Installing Dependencies on openSUSE
```
-zypper in boost-devel cmake freeglut-devel freetype2-devel gcc-c++ glew-devel libQt5OpenGL-devel libSDL2-devel libjpeg-devel liblz4-devel libpng16-compat-devel libqt5-linguist-devel libqt5-qtbase-devel libqt5-qtmultimedia-devel libqt5-qtscript-devel libqt5-qtsvg-devel libtiff-devel libusb-devel lzo-devel openblas-devel pkgconfig sed superlu-devel zlib-devel
+$ zypper in boost-devel cmake freeglut-devel freetype2-devel gcc-c++ glew-devel libQt5OpenGL-devel libSDL2-devel libjpeg-devel liblz4-devel libpng16-compat-devel libqt5-linguist-devel libqt5-qtbase-devel libqt5-qtmultimedia-devel libqt5-qtscript-devel libqt5-qtsvg-devel libtiff-devel libusb-devel lzo-devel openblas-devel pkgconfig sed superlu-devel zlib-devel
```
## Build instructions
-### cloning the git tree
+### Cloning the GIT Tree
```
$ git clone https://github.com/opentoonz/opentoonz
```
-### Copying the stuff directory
+### Copying the 'stuff' Directory
TODO: some parts should really be installed in $prefix/ instead... and some other in various cache or user-local places.
cf. https://specifications.freedesktop.org/basedir-spec/basedir-spec-latest.html
Until then we just follow the Win32/OSX layout.
-It is supposedly optional but some files are actually required to run the executable properly.
+The `~/.config/OpenToonz/` directory contains your settings, work and other files.
-The .config/OpenToonz/ directory in your home folder will contain your settings, work and other files. We need to create it from the command-line:
+Initialize this path with the folling commands:
```
$ mkdir -p $HOME/.config/OpenToonz
$ cp -r opentoonz/stuff $HOME/.config/OpenToonz/
```
-### Creating a default ini file for stuff folders
+*Currently this is required to run OpenToonz.*
+
+### Creating SystemVar.ini
TODO: fix the code to discover it automatically
@@ -98,20 +101,21 @@ TOONZROOT="$HOME/.config/OpenToonz/stuff"
TOONZSTUDIOPALETTE="$HOME/.config/OpenToonz/stuff/projects/studiopalette"
EOF
```
-Note the generated file must not actually contain "$HOME", this shell command repaces it with /home/youraccount in the generated file.
+Note the generated file must not actually contain `$HOME`, this expands to an absolute path in the generated file.
-### Building the tiff library from thirdparty
+### Building LibTIFF
TODO: make sure we can use the system libtiff instead and remove this section.
Features from the modified libtiff and needed currently, so this isn't a simple switch.
```
$ cd opentoonz/thirdparty/tiff-4.0.3
-$ CFLAGS="-fPIC" ./configure && make
+$ ./configure --with-pic --disable-jbig
+$ make
$ cd -
```
-### Compiling the actual application
+### Building OpenToonz
```
$ cd ../../toonz
@@ -123,18 +127,18 @@ $ make
The build takes a lot of time, be patient.
-### Debugging the build
+### Troubleshooting Build Errors
If something doesn't compile or link, please run `make` this way to help spot the problem:
```
-LANG=C make VERBOSE=1
+$ LANG=C make VERBOSE=1
```
-#### Debug build
+#### Debug Build
If you need to debug the application, you should be able to use `cmake -DCMAKE_BUILD_TYPE=Debug`.
-### Running the application
+### Running OpenToonz
You can now run the application:
@@ -143,7 +147,7 @@ $ cd bin
$ LD_LIBRARY_PATH=./lib/opentoonz:$LD_LIBRARY_PATH ./bin/OpenToonz_1.0
```
-### Performing a system installation
+### Performing a System Installation
The steps above show how to run OpenToonz from the build directory,
however you may wish to install OpenToonz onto your system.
@@ -158,3 +162,15 @@ Then you can launch OpenToonz by running `/opt/opentoonz/bin/opentoonz`.
You can change the installation path by modifying the `CMAKE_INSTALL_PREFIX` CMake variable.
+----
+
+# Linux Package Definitions
+
+It may be helpful to use existing packages as a reference when creating a package for your own distribution.
+
+- ArchLinux (AUR):
+ https://aur.archlinux.org/packages/opentoonz-git/
+
+- App-Image (Portable):
+ https://github.com/morevnaproject/morevna-builds
+
diff --git a/stuff/config/qss/gray_048/gray_048.less b/stuff/config/qss/gray_048/gray_048.less
index 0590e85..84eee18 100644
--- a/stuff/config/qss/gray_048/gray_048.less
+++ b/stuff/config/qss/gray_048/gray_048.less
@@ -1,4 +1,4 @@
-
+// out: gray_048.qss
/* LESS Definitions */
/*Image URL*/
@@ -748,7 +748,7 @@ DvDirTreeView {
/*---------------------------------------------------------------------------*/
#CleanupSettingsFrame,
#LoadLevelFrame,
-#SolidLineFrame{
+#SolidLineFrame {
border: 1px solid @m_baseTxtColor;
}
@@ -821,30 +821,29 @@ ParamsPage {
}
}
/* Customize QScrollBar vertical*/
-#XsheetScrollBar {
- .baseBG(light, 10%);
+QScrollBar {
border: 1px solid black;
&:vertical {
- width: 18px;
- .set_margin( 0px, 20px );
+ width: 16px;
+ .set_margin( 0px, 16px );
}
&:horizontal {
- height: 18px;
- .set_margin( 20px, 0px );
+ height: 16px;
+ .set_margin( 16px, 0px );
}
&::handle {
- border-width: 4;
+ border-width: 3;
image-position: center center;
&:vertical {
- border-image: url("@{image_url}/sb_g_vhandle.png")4;
+ border-image: url("@{image_url}/sb_g_vhandle.png")3;
image: url("@{image_url}/sb_g_vline.png");
min-height: 40px;
}
&:horizontal {
- border-image: url("@{image_url}/sb_g_hhandle.png")4;
+ border-image: url("@{image_url}/sb_g_hhandle.png")3;
image: url("@{image_url}/sb_g_hline.png");
min-width: 40px;
}
@@ -854,7 +853,7 @@ ParamsPage {
subcontrol-origin: margin;
&:vertical {
image: url("@{image_url}/sb_g_downarrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: bottom;
&:pressed {
image: url("@{image_url}/sb_g_downarrow_pressed.png");
@@ -862,7 +861,7 @@ ParamsPage {
}
&:horizontal {
image: url("@{image_url}/sb_g_rarrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: right;
&:pressed{
image: url("@{image_url}/sb_g_rarrow_pressed.png");
@@ -874,7 +873,7 @@ ParamsPage {
subcontrol-origin: margin;
&:vertical {
image: url("@{image_url}/sb_g_uparrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: top;
&:pressed {
image: url("@{image_url}/sb_g_uparrow_pressed.png");
@@ -882,7 +881,7 @@ ParamsPage {
}
&:horizontal {
image: url("@{image_url}/sb_g_larrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: left;
&:pressed{
image: url("@{image_url}/sb_g_larrow_pressed.png");
@@ -890,8 +889,8 @@ ParamsPage {
}
}
- &::add-page {
- background: none;
+ &::add-page, &::sub-page {
+ .baseBG(light, 10%);
}
}
@@ -1365,4 +1364,15 @@ QDialog #dialogButtonFrame {
#LargeSizedText {
font-size: 17px;
+}
+
+#GearButton {
+ qproperty-icon: url("@{image_url}/gear.png");
+}
+
+#StartupLabel {
+ padding: 3px;
+ &:hover {
+ .baseBG(light, 10%);
+ }
}
\ No newline at end of file
diff --git a/stuff/config/qss/gray_048/gray_048.qss b/stuff/config/qss/gray_048/gray_048.qss
index 6936166..b1a2239 100644
--- a/stuff/config/qss/gray_048/gray_048.qss
+++ b/stuff/config/qss/gray_048/gray_048.qss
@@ -841,79 +841,79 @@ ParamsPage {
background-color: #000080;
}
/* Customize QScrollBar vertical*/
-#XsheetScrollBar {
- background-color: #4a4a4a;
+QScrollBar {
border: 1px solid black;
/* buttons */
}
-#XsheetScrollBar:vertical {
- width: 18px;
+QScrollBar:vertical {
+ width: 16px;
margin-left: 0px;
margin-right: 0px;
- margin-top: 20px;
- margin-bottom: 20px;
+ margin-top: 16px;
+ margin-bottom: 16px;
}
-#XsheetScrollBar:horizontal {
- height: 18px;
- margin-left: 20px;
- margin-right: 20px;
+QScrollBar:horizontal {
+ height: 16px;
+ margin-left: 16px;
+ margin-right: 16px;
margin-top: 0px;
margin-bottom: 0px;
}
-#XsheetScrollBar::handle {
- border-width: 4;
+QScrollBar::handle {
+ border-width: 3;
image-position: center center;
}
-#XsheetScrollBar::handle:vertical {
- border-image: url("../gray_072/imgs/sb_g_vhandle.png") 4;
+QScrollBar::handle:vertical {
+ border-image: url("../gray_072/imgs/sb_g_vhandle.png") 3;
image: url("../gray_072/imgs/sb_g_vline.png");
min-height: 40px;
}
-#XsheetScrollBar::handle:horizontal {
- border-image: url("../gray_072/imgs/sb_g_hhandle.png") 4;
+QScrollBar::handle:horizontal {
+ border-image: url("../gray_072/imgs/sb_g_hhandle.png") 3;
image: url("../gray_072/imgs/sb_g_hline.png");
min-width: 40px;
}
-#XsheetScrollBar::add-line {
+QScrollBar::add-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::add-line:vertical {
+QScrollBar::add-line:vertical {
image: url("../gray_072/imgs/sb_g_downarrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: bottom;
}
-#XsheetScrollBar::add-line:vertical:pressed {
+QScrollBar::add-line:vertical:pressed {
image: url("../gray_072/imgs/sb_g_downarrow_pressed.png");
}
-#XsheetScrollBar::add-line:horizontal {
+QScrollBar::add-line:horizontal {
image: url("../gray_072/imgs/sb_g_rarrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: right;
}
-#XsheetScrollBar::add-line:horizontal:pressed {
+QScrollBar::add-line:horizontal:pressed {
image: url("../gray_072/imgs/sb_g_rarrow_pressed.png");
}
-#XsheetScrollBar::sub-line {
+QScrollBar::sub-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::sub-line:vertical {
+QScrollBar::sub-line:vertical {
image: url("../gray_072/imgs/sb_g_uparrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: top;
}
-#XsheetScrollBar::sub-line:vertical:pressed {
+QScrollBar::sub-line:vertical:pressed {
image: url("../gray_072/imgs/sb_g_uparrow_pressed.png");
}
-#XsheetScrollBar::sub-line:horizontal {
+QScrollBar::sub-line:horizontal {
image: url("../gray_072/imgs/sb_g_larrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: left;
}
-#XsheetScrollBar::sub-line:horizontal:pressed {
+QScrollBar::sub-line:horizontal:pressed {
image: url("../gray_072/imgs/sb_g_larrow_pressed.png");
}
-#XsheetScrollBar::add-page {
- background: none;
+QScrollBar::add-page,
+QScrollBar::sub-page {
+ background-color: #4a4a4a;
}
#noteTextEdit {
color: black;
@@ -1369,5 +1369,14 @@ QDialog #dialogButtonFrame {
#LargeSizedText {
font-size: 17px;
}
+#GearButton {
+ qproperty-icon: url("../gray_072/imgs/gear.png");
+}
+#StartupLabel {
+ padding: 3px;
+}
+#StartupLabel:hover {
+ background-color: #4a4a4a;
+}
//# sourceMappingURL=gray_048.qss.map
\ No newline at end of file
diff --git a/stuff/config/qss/gray_048/gray_048_mac.qss b/stuff/config/qss/gray_048/gray_048_mac.qss
index 7c6a503..23babcd 100644
--- a/stuff/config/qss/gray_048/gray_048_mac.qss
+++ b/stuff/config/qss/gray_048/gray_048_mac.qss
@@ -841,79 +841,79 @@ ParamsPage {
background-color: #000080;
}
/* Customize QScrollBar vertical*/
-#XsheetScrollBar {
- background-color: #4a4a4a;
+QScrollBar {
border: 1px solid black;
/* buttons */
}
-#XsheetScrollBar:vertical {
- width: 18px;
+QScrollBar:vertical {
+ width: 16px;
margin-left: 0px;
margin-right: 0px;
- margin-top: 20px;
- margin-bottom: 20px;
+ margin-top: 16px;
+ margin-bottom: 16px;
}
-#XsheetScrollBar:horizontal {
- height: 18px;
- margin-left: 20px;
- margin-right: 20px;
+QScrollBar:horizontal {
+ height: 16px;
+ margin-left: 16px;
+ margin-right: 16px;
margin-top: 0px;
margin-bottom: 0px;
}
-#XsheetScrollBar::handle {
- border-width: 4;
+QScrollBar::handle {
+ border-width: 3;
image-position: center center;
}
-#XsheetScrollBar::handle:vertical {
- border-image: url("../gray_072/imgs/sb_g_vhandle.png") 4;
+QScrollBar::handle:vertical {
+ border-image: url("../gray_072/imgs/sb_g_vhandle.png") 3;
image: url("../gray_072/imgs/sb_g_vline.png");
min-height: 40px;
}
-#XsheetScrollBar::handle:horizontal {
- border-image: url("../gray_072/imgs/sb_g_hhandle.png") 4;
+QScrollBar::handle:horizontal {
+ border-image: url("../gray_072/imgs/sb_g_hhandle.png") 3;
image: url("../gray_072/imgs/sb_g_hline.png");
min-width: 40px;
}
-#XsheetScrollBar::add-line {
+QScrollBar::add-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::add-line:vertical {
+QScrollBar::add-line:vertical {
image: url("../gray_072/imgs/sb_g_downarrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: bottom;
}
-#XsheetScrollBar::add-line:vertical:pressed {
+QScrollBar::add-line:vertical:pressed {
image: url("../gray_072/imgs/sb_g_downarrow_pressed.png");
}
-#XsheetScrollBar::add-line:horizontal {
+QScrollBar::add-line:horizontal {
image: url("../gray_072/imgs/sb_g_rarrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: right;
}
-#XsheetScrollBar::add-line:horizontal:pressed {
+QScrollBar::add-line:horizontal:pressed {
image: url("../gray_072/imgs/sb_g_rarrow_pressed.png");
}
-#XsheetScrollBar::sub-line {
+QScrollBar::sub-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::sub-line:vertical {
+QScrollBar::sub-line:vertical {
image: url("../gray_072/imgs/sb_g_uparrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: top;
}
-#XsheetScrollBar::sub-line:vertical:pressed {
+QScrollBar::sub-line:vertical:pressed {
image: url("../gray_072/imgs/sb_g_uparrow_pressed.png");
}
-#XsheetScrollBar::sub-line:horizontal {
+QScrollBar::sub-line:horizontal {
image: url("../gray_072/imgs/sb_g_larrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: left;
}
-#XsheetScrollBar::sub-line:horizontal:pressed {
+QScrollBar::sub-line:horizontal:pressed {
image: url("../gray_072/imgs/sb_g_larrow_pressed.png");
}
-#XsheetScrollBar::add-page {
- background: none;
+QScrollBar::add-page,
+QScrollBar::sub-page {
+ background-color: #4a4a4a;
}
#noteTextEdit {
color: black;
@@ -1369,5 +1369,14 @@ QDialog #dialogButtonFrame {
#LargeSizedText {
font-size: 17px;
}
+#GearButton {
+ qproperty-icon: url("../gray_072/imgs/gear.png");
+}
+#StartupLabel {
+ padding: 3px;
+}
+#StartupLabel:hover {
+ background-color: #4a4a4a;
+}
//# sourceMappingURL=gray_048_mac.qss.map
\ No newline at end of file
diff --git a/stuff/config/qss/gray_072/gray_072.less b/stuff/config/qss/gray_072/gray_072.less
index c918bcf..7cb9432 100644
--- a/stuff/config/qss/gray_072/gray_072.less
+++ b/stuff/config/qss/gray_072/gray_072.less
@@ -747,7 +747,7 @@ DvDirTreeView {
/*---------------------------------------------------------------------------*/
#CleanupSettingsFrame,
#LoadLevelFrame,
-#SolidLineFrame{
+#SolidLineFrame {
border: 1px solid @m_baseTxtColor;
}
@@ -821,30 +821,29 @@ ParamsPage {
}
}
/* Customize QScrollBar vertical*/
-#XsheetScrollBar {
- .baseBG(light, 10%);
+QScrollBar {
border: 1px solid black;
&:vertical {
- width: 18px;
- .set_margin( 0px, 20px );
+ width: 16px;
+ .set_margin( 0px, 16px );
}
&:horizontal {
- height: 18px;
- .set_margin( 20px, 0px );
+ height: 16px;
+ .set_margin( 16px, 0px );
}
&::handle {
- border-width: 4;
+ border-width: 3;
image-position: center center;
&:vertical {
- border-image: url("@{image_url}/sb_g_vhandle.png")4;
+ border-image: url("@{image_url}/sb_g_vhandle.png")3;
image: url("@{image_url}/sb_g_vline.png");
min-height: 40px;
}
&:horizontal {
- border-image: url("@{image_url}/sb_g_hhandle.png")4;
+ border-image: url("@{image_url}/sb_g_hhandle.png")3;
image: url("@{image_url}/sb_g_hline.png");
min-width: 40px;
}
@@ -854,7 +853,7 @@ ParamsPage {
subcontrol-origin: margin;
&:vertical {
image: url("@{image_url}/sb_g_downarrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: bottom;
&:pressed {
image: url("@{image_url}/sb_g_downarrow_pressed.png");
@@ -862,7 +861,7 @@ ParamsPage {
}
&:horizontal {
image: url("@{image_url}/sb_g_rarrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: right;
&:pressed{
image: url("@{image_url}/sb_g_rarrow_pressed.png");
@@ -874,7 +873,7 @@ ParamsPage {
subcontrol-origin: margin;
&:vertical {
image: url("@{image_url}/sb_g_uparrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: top;
&:pressed {
image: url("@{image_url}/sb_g_uparrow_pressed.png");
@@ -882,7 +881,7 @@ ParamsPage {
}
&:horizontal {
image: url("@{image_url}/sb_g_larrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: left;
&:pressed{
image: url("@{image_url}/sb_g_larrow_pressed.png");
@@ -890,8 +889,8 @@ ParamsPage {
}
}
- &::add-page {
- background: none;
+ &::add-page, &::sub-page {
+ .baseBG(light, 10%);
}
}
@@ -1365,4 +1364,15 @@ QDialog #dialogButtonFrame {
#LargeSizedText {
font-size: 17px;
+}
+
+#GearButton {
+ qproperty-icon: url("@{image_url}/gear.png");
+}
+
+#StartupLabel {
+ padding: 3px;
+ &:hover {
+ .baseBG(light, 10%);
+ }
}
\ No newline at end of file
diff --git a/stuff/config/qss/gray_072/gray_072.qss b/stuff/config/qss/gray_072/gray_072.qss
index 69c5a4d..84bb341 100644
--- a/stuff/config/qss/gray_072/gray_072.qss
+++ b/stuff/config/qss/gray_072/gray_072.qss
@@ -841,79 +841,79 @@ ParamsPage {
background-color: #000080;
}
/* Customize QScrollBar vertical*/
-#XsheetScrollBar {
- background-color: #626262;
+QScrollBar {
border: 1px solid black;
/* buttons */
}
-#XsheetScrollBar:vertical {
- width: 18px;
+QScrollBar:vertical {
+ width: 16px;
margin-left: 0px;
margin-right: 0px;
- margin-top: 20px;
- margin-bottom: 20px;
+ margin-top: 16px;
+ margin-bottom: 16px;
}
-#XsheetScrollBar:horizontal {
- height: 18px;
- margin-left: 20px;
- margin-right: 20px;
+QScrollBar:horizontal {
+ height: 16px;
+ margin-left: 16px;
+ margin-right: 16px;
margin-top: 0px;
margin-bottom: 0px;
}
-#XsheetScrollBar::handle {
- border-width: 4;
+QScrollBar::handle {
+ border-width: 3;
image-position: center center;
}
-#XsheetScrollBar::handle:vertical {
- border-image: url("imgs/sb_g_vhandle.png") 4;
+QScrollBar::handle:vertical {
+ border-image: url("imgs/sb_g_vhandle.png") 3;
image: url("imgs/sb_g_vline.png");
min-height: 40px;
}
-#XsheetScrollBar::handle:horizontal {
- border-image: url("imgs/sb_g_hhandle.png") 4;
+QScrollBar::handle:horizontal {
+ border-image: url("imgs/sb_g_hhandle.png") 3;
image: url("imgs/sb_g_hline.png");
min-width: 40px;
}
-#XsheetScrollBar::add-line {
+QScrollBar::add-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::add-line:vertical {
+QScrollBar::add-line:vertical {
image: url("imgs/sb_g_downarrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: bottom;
}
-#XsheetScrollBar::add-line:vertical:pressed {
+QScrollBar::add-line:vertical:pressed {
image: url("imgs/sb_g_downarrow_pressed.png");
}
-#XsheetScrollBar::add-line:horizontal {
+QScrollBar::add-line:horizontal {
image: url("imgs/sb_g_rarrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: right;
}
-#XsheetScrollBar::add-line:horizontal:pressed {
+QScrollBar::add-line:horizontal:pressed {
image: url("imgs/sb_g_rarrow_pressed.png");
}
-#XsheetScrollBar::sub-line {
+QScrollBar::sub-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::sub-line:vertical {
+QScrollBar::sub-line:vertical {
image: url("imgs/sb_g_uparrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: top;
}
-#XsheetScrollBar::sub-line:vertical:pressed {
+QScrollBar::sub-line:vertical:pressed {
image: url("imgs/sb_g_uparrow_pressed.png");
}
-#XsheetScrollBar::sub-line:horizontal {
+QScrollBar::sub-line:horizontal {
image: url("imgs/sb_g_larrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: left;
}
-#XsheetScrollBar::sub-line:horizontal:pressed {
+QScrollBar::sub-line:horizontal:pressed {
image: url("imgs/sb_g_larrow_pressed.png");
}
-#XsheetScrollBar::add-page {
- background: none;
+QScrollBar::add-page,
+QScrollBar::sub-page {
+ background-color: #626262;
}
#noteTextEdit {
color: black;
@@ -1369,5 +1369,14 @@ QDialog #dialogButtonFrame {
#LargeSizedText {
font-size: 17px;
}
+#GearButton {
+ qproperty-icon: url("imgs/gear.png");
+}
+#StartupLabel {
+ padding: 3px;
+}
+#StartupLabel:hover {
+ background-color: #626262;
+}
//# sourceMappingURL=gray_072.qss.map
\ No newline at end of file
diff --git a/stuff/config/qss/gray_072/gray_072_mac.qss b/stuff/config/qss/gray_072/gray_072_mac.qss
index 182e253..ec73907 100644
--- a/stuff/config/qss/gray_072/gray_072_mac.qss
+++ b/stuff/config/qss/gray_072/gray_072_mac.qss
@@ -841,79 +841,79 @@ ParamsPage {
background-color: #000080;
}
/* Customize QScrollBar vertical*/
-#XsheetScrollBar {
- background-color: #626262;
+QScrollBar {
border: 1px solid black;
/* buttons */
}
-#XsheetScrollBar:vertical {
- width: 18px;
+QScrollBar:vertical {
+ width: 16px;
margin-left: 0px;
margin-right: 0px;
- margin-top: 20px;
- margin-bottom: 20px;
+ margin-top: 16px;
+ margin-bottom: 16px;
}
-#XsheetScrollBar:horizontal {
- height: 18px;
- margin-left: 20px;
- margin-right: 20px;
+QScrollBar:horizontal {
+ height: 16px;
+ margin-left: 16px;
+ margin-right: 16px;
margin-top: 0px;
margin-bottom: 0px;
}
-#XsheetScrollBar::handle {
- border-width: 4;
+QScrollBar::handle {
+ border-width: 3;
image-position: center center;
}
-#XsheetScrollBar::handle:vertical {
- border-image: url("imgs/sb_g_vhandle.png") 4;
+QScrollBar::handle:vertical {
+ border-image: url("imgs/sb_g_vhandle.png") 3;
image: url("imgs/sb_g_vline.png");
min-height: 40px;
}
-#XsheetScrollBar::handle:horizontal {
- border-image: url("imgs/sb_g_hhandle.png") 4;
+QScrollBar::handle:horizontal {
+ border-image: url("imgs/sb_g_hhandle.png") 3;
image: url("imgs/sb_g_hline.png");
min-width: 40px;
}
-#XsheetScrollBar::add-line {
+QScrollBar::add-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::add-line:vertical {
+QScrollBar::add-line:vertical {
image: url("imgs/sb_g_downarrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: bottom;
}
-#XsheetScrollBar::add-line:vertical:pressed {
+QScrollBar::add-line:vertical:pressed {
image: url("imgs/sb_g_downarrow_pressed.png");
}
-#XsheetScrollBar::add-line:horizontal {
+QScrollBar::add-line:horizontal {
image: url("imgs/sb_g_rarrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: right;
}
-#XsheetScrollBar::add-line:horizontal:pressed {
+QScrollBar::add-line:horizontal:pressed {
image: url("imgs/sb_g_rarrow_pressed.png");
}
-#XsheetScrollBar::sub-line {
+QScrollBar::sub-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::sub-line:vertical {
+QScrollBar::sub-line:vertical {
image: url("imgs/sb_g_uparrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: top;
}
-#XsheetScrollBar::sub-line:vertical:pressed {
+QScrollBar::sub-line:vertical:pressed {
image: url("imgs/sb_g_uparrow_pressed.png");
}
-#XsheetScrollBar::sub-line:horizontal {
+QScrollBar::sub-line:horizontal {
image: url("imgs/sb_g_larrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: left;
}
-#XsheetScrollBar::sub-line:horizontal:pressed {
+QScrollBar::sub-line:horizontal:pressed {
image: url("imgs/sb_g_larrow_pressed.png");
}
-#XsheetScrollBar::add-page {
- background: none;
+QScrollBar::add-page,
+QScrollBar::sub-page {
+ background-color: #626262;
}
#noteTextEdit {
color: black;
@@ -1369,5 +1369,14 @@ QDialog #dialogButtonFrame {
#LargeSizedText {
font-size: 17px;
}
+#GearButton {
+ qproperty-icon: url("imgs/gear.png");
+}
+#StartupLabel {
+ padding: 3px;
+}
+#StartupLabel:hover {
+ background-color: #626262;
+}
//# sourceMappingURL=gray_072_mac.qss.map
\ No newline at end of file
diff --git a/stuff/config/qss/gray_072/imgs/gear.png b/stuff/config/qss/gray_072/imgs/gear.png
new file mode 100644
index 0000000..7e07631
Binary files /dev/null and b/stuff/config/qss/gray_072/imgs/gear.png differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_downarrow.png b/stuff/config/qss/gray_072/imgs/sb_g_downarrow.png
index cb7c0de..406effb 100644
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_downarrow.png and b/stuff/config/qss/gray_072/imgs/sb_g_downarrow.png differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_downarrow_pressed.png b/stuff/config/qss/gray_072/imgs/sb_g_downarrow_pressed.png
index 04fe449..70df3a6 100644
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_downarrow_pressed.png and b/stuff/config/qss/gray_072/imgs/sb_g_downarrow_pressed.png differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_larrow.png b/stuff/config/qss/gray_072/imgs/sb_g_larrow.png
index 686f566..01d4162 100644
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_larrow.png and b/stuff/config/qss/gray_072/imgs/sb_g_larrow.png differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_larrow_pressed.png b/stuff/config/qss/gray_072/imgs/sb_g_larrow_pressed.png
index 1450404..0f83f2a 100644
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_larrow_pressed.png and b/stuff/config/qss/gray_072/imgs/sb_g_larrow_pressed.png differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_ls_downarrow.png b/stuff/config/qss/gray_072/imgs/sb_g_ls_downarrow.png
deleted file mode 100644
index 406effb..0000000
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_ls_downarrow.png and /dev/null differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_ls_downarrow_pressed.png b/stuff/config/qss/gray_072/imgs/sb_g_ls_downarrow_pressed.png
deleted file mode 100644
index 70df3a6..0000000
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_ls_downarrow_pressed.png and /dev/null differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_ls_uparrow.png b/stuff/config/qss/gray_072/imgs/sb_g_ls_uparrow.png
deleted file mode 100644
index 5979c72..0000000
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_ls_uparrow.png and /dev/null differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_ls_uparrow_pressed.png b/stuff/config/qss/gray_072/imgs/sb_g_ls_uparrow_pressed.png
deleted file mode 100644
index eb84176..0000000
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_ls_uparrow_pressed.png and /dev/null differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_rarrow.png b/stuff/config/qss/gray_072/imgs/sb_g_rarrow.png
index 29f6518..4c997fc 100644
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_rarrow.png and b/stuff/config/qss/gray_072/imgs/sb_g_rarrow.png differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_rarrow_pressed.png b/stuff/config/qss/gray_072/imgs/sb_g_rarrow_pressed.png
index 2fa0aef..579f8f9 100644
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_rarrow_pressed.png and b/stuff/config/qss/gray_072/imgs/sb_g_rarrow_pressed.png differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_uparrow.png b/stuff/config/qss/gray_072/imgs/sb_g_uparrow.png
index 16c8136..5979c72 100644
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_uparrow.png and b/stuff/config/qss/gray_072/imgs/sb_g_uparrow.png differ
diff --git a/stuff/config/qss/gray_072/imgs/sb_g_uparrow_pressed.png b/stuff/config/qss/gray_072/imgs/sb_g_uparrow_pressed.png
index 95224d9..eb84176 100644
Binary files a/stuff/config/qss/gray_072/imgs/sb_g_uparrow_pressed.png and b/stuff/config/qss/gray_072/imgs/sb_g_uparrow_pressed.png differ
diff --git a/stuff/config/qss/gray_128/gray_128.less b/stuff/config/qss/gray_128/gray_128.less
index 2c13e25..31fa3db 100644
--- a/stuff/config/qss/gray_128/gray_128.less
+++ b/stuff/config/qss/gray_128/gray_128.less
@@ -1,3 +1,4 @@
+// out: gray_128.qss
/* LESS Definitions */
/*Image URL*/
@@ -595,7 +596,7 @@ DvDirTreeView {
/*---------------------------------------------------------------------------*/
#CleanupSettingsFrame,
#LoadLevelFrame,
-#SolidLineFrame{
+#SolidLineFrame {
border: 1px solid rgb(20,20,20);
}
@@ -661,30 +662,29 @@ ParamsPage {
}
}
/* Customize QScrollBar vertical*/
-#XsheetScrollBar {
- background-color: rgb(160,160,160);
+QScrollBar {
border: 1px solid black;
&:vertical {
- width: 18px;
- .set_margin( 0px, 20px );
+ width: 16px;
+ .set_margin( 0px, 16px );
}
&:horizontal {
- height: 18px;
- .set_margin( 20px, 0px );
+ height: 16px;
+ .set_margin( 16px, 0px );
}
&::handle {
- border-width: 4;
+ border-width: 3;
image-position: center center;
&:vertical {
- border-image: url("@{image_url}/sb_g_vhandle.png")4;
+ border-image: url("@{image_url}/sb_g_vhandle.png")3;
image: url("@{image_url}/sb_g_vline.png");
min-height: 40px;
}
&:horizontal {
- border-image: url("@{image_url}/sb_g_hhandle.png")4;
+ border-image: url("@{image_url}/sb_g_hhandle.png")3;
image: url("@{image_url}/sb_g_hline.png");
min-width: 40px;
}
@@ -694,7 +694,7 @@ ParamsPage {
subcontrol-origin: margin;
&:vertical {
image: url("@{image_url}/sb_g_downarrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: bottom;
&:pressed {
image: url("@{image_url}/sb_g_downarrow_pressed.png");
@@ -702,7 +702,7 @@ ParamsPage {
}
&:horizontal {
image: url("@{image_url}/sb_g_rarrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: right;
&:pressed{
image: url("@{image_url}/sb_g_rarrow_pressed.png");
@@ -714,7 +714,7 @@ ParamsPage {
subcontrol-origin: margin;
&:vertical {
image: url("@{image_url}/sb_g_uparrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: top;
&:pressed {
image: url("@{image_url}/sb_g_uparrow_pressed.png");
@@ -722,7 +722,7 @@ ParamsPage {
}
&:horizontal {
image: url("@{image_url}/sb_g_larrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: left;
&:pressed{
image: url("@{image_url}/sb_g_larrow_pressed.png");
@@ -730,8 +730,8 @@ ParamsPage {
}
}
- &::add-page {
- background: none;
+ &::add-page, &::sub-page {
+ background-color: rgb(160,160,160);
}
}
@@ -1190,4 +1190,15 @@ QDialog #dialogButtonFrame {
#LargeSizedText {
font-size: 17px;
+}
+
+#GearButton {
+ qproperty-icon: url("@{image_url}/gear.png");
+}
+
+#StartupLabel {
+ padding: 3px;
+ &:hover {
+ .baseBG(light, 10%);
+ }
}
\ No newline at end of file
diff --git a/stuff/config/qss/gray_128/gray_128.qss b/stuff/config/qss/gray_128/gray_128.qss
index 1f3a66e..c8f42cd 100644
--- a/stuff/config/qss/gray_128/gray_128.qss
+++ b/stuff/config/qss/gray_128/gray_128.qss
@@ -591,79 +591,79 @@ ParamsPage {
background-color: #000080;
}
/* Customize QScrollBar vertical*/
-#XsheetScrollBar {
- background-color: #a0a0a0;
+QScrollBar {
border: 1px solid black;
/* buttons */
}
-#XsheetScrollBar:vertical {
- width: 18px;
+QScrollBar:vertical {
+ width: 16px;
margin-left: 0px;
margin-right: 0px;
- margin-top: 20px;
- margin-bottom: 20px;
+ margin-top: 16px;
+ margin-bottom: 16px;
}
-#XsheetScrollBar:horizontal {
- height: 18px;
- margin-left: 20px;
- margin-right: 20px;
+QScrollBar:horizontal {
+ height: 16px;
+ margin-left: 16px;
+ margin-right: 16px;
margin-top: 0px;
margin-bottom: 0px;
}
-#XsheetScrollBar::handle {
- border-width: 4;
+QScrollBar::handle {
+ border-width: 3;
image-position: center center;
}
-#XsheetScrollBar::handle:vertical {
- border-image: url("imgs/sb_g_vhandle.png") 4;
+QScrollBar::handle:vertical {
+ border-image: url("imgs/sb_g_vhandle.png") 3;
image: url("imgs/sb_g_vline.png");
min-height: 40px;
}
-#XsheetScrollBar::handle:horizontal {
- border-image: url("imgs/sb_g_hhandle.png") 4;
+QScrollBar::handle:horizontal {
+ border-image: url("imgs/sb_g_hhandle.png") 3;
image: url("imgs/sb_g_hline.png");
min-width: 40px;
}
-#XsheetScrollBar::add-line {
+QScrollBar::add-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::add-line:vertical {
+QScrollBar::add-line:vertical {
image: url("imgs/sb_g_downarrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: bottom;
}
-#XsheetScrollBar::add-line:vertical:pressed {
+QScrollBar::add-line:vertical:pressed {
image: url("imgs/sb_g_downarrow_pressed.png");
}
-#XsheetScrollBar::add-line:horizontal {
+QScrollBar::add-line:horizontal {
image: url("imgs/sb_g_rarrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: right;
}
-#XsheetScrollBar::add-line:horizontal:pressed {
+QScrollBar::add-line:horizontal:pressed {
image: url("imgs/sb_g_rarrow_pressed.png");
}
-#XsheetScrollBar::sub-line {
+QScrollBar::sub-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::sub-line:vertical {
+QScrollBar::sub-line:vertical {
image: url("imgs/sb_g_uparrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: top;
}
-#XsheetScrollBar::sub-line:vertical:pressed {
+QScrollBar::sub-line:vertical:pressed {
image: url("imgs/sb_g_uparrow_pressed.png");
}
-#XsheetScrollBar::sub-line:horizontal {
+QScrollBar::sub-line:horizontal {
image: url("imgs/sb_g_larrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: left;
}
-#XsheetScrollBar::sub-line:horizontal:pressed {
+QScrollBar::sub-line:horizontal:pressed {
image: url("imgs/sb_g_larrow_pressed.png");
}
-#XsheetScrollBar::add-page {
- background: none;
+QScrollBar::add-page,
+QScrollBar::sub-page {
+ background-color: #a0a0a0;
}
XsheetViewer {
qproperty-TextColor: black;
@@ -1108,5 +1108,14 @@ QDialog #dialogButtonFrame {
#LargeSizedText {
font-size: 17px;
}
+#GearButton {
+ qproperty-icon: url("imgs/gear.png");
+}
+#StartupLabel {
+ padding: 3px;
+}
+#StartupLabel:hover {
+ background-color: #9a9a9a;
+}
//# sourceMappingURL=gray_128.qss.map
\ No newline at end of file
diff --git a/stuff/config/qss/gray_128/gray_128_mac.qss b/stuff/config/qss/gray_128/gray_128_mac.qss
index f66c40d..8f53904 100644
--- a/stuff/config/qss/gray_128/gray_128_mac.qss
+++ b/stuff/config/qss/gray_128/gray_128_mac.qss
@@ -591,79 +591,79 @@ ParamsPage {
background-color: #000080;
}
/* Customize QScrollBar vertical*/
-#XsheetScrollBar {
- background-color: #a0a0a0;
+QScrollBar {
border: 1px solid black;
/* buttons */
}
-#XsheetScrollBar:vertical {
- width: 18px;
+QScrollBar:vertical {
+ width: 16px;
margin-left: 0px;
margin-right: 0px;
- margin-top: 20px;
- margin-bottom: 20px;
+ margin-top: 16px;
+ margin-bottom: 16px;
}
-#XsheetScrollBar:horizontal {
- height: 18px;
- margin-left: 20px;
- margin-right: 20px;
+QScrollBar:horizontal {
+ height: 16px;
+ margin-left: 16px;
+ margin-right: 16px;
margin-top: 0px;
margin-bottom: 0px;
}
-#XsheetScrollBar::handle {
- border-width: 4;
+QScrollBar::handle {
+ border-width: 3;
image-position: center center;
}
-#XsheetScrollBar::handle:vertical {
- border-image: url("imgs/sb_g_vhandle.png") 4;
+QScrollBar::handle:vertical {
+ border-image: url("imgs/sb_g_vhandle.png") 3;
image: url("imgs/sb_g_vline.png");
min-height: 40px;
}
-#XsheetScrollBar::handle:horizontal {
- border-image: url("imgs/sb_g_hhandle.png") 4;
+QScrollBar::handle:horizontal {
+ border-image: url("imgs/sb_g_hhandle.png") 3;
image: url("imgs/sb_g_hline.png");
min-width: 40px;
}
-#XsheetScrollBar::add-line {
+QScrollBar::add-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::add-line:vertical {
+QScrollBar::add-line:vertical {
image: url("imgs/sb_g_downarrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: bottom;
}
-#XsheetScrollBar::add-line:vertical:pressed {
+QScrollBar::add-line:vertical:pressed {
image: url("imgs/sb_g_downarrow_pressed.png");
}
-#XsheetScrollBar::add-line:horizontal {
+QScrollBar::add-line:horizontal {
image: url("imgs/sb_g_rarrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: right;
}
-#XsheetScrollBar::add-line:horizontal:pressed {
+QScrollBar::add-line:horizontal:pressed {
image: url("imgs/sb_g_rarrow_pressed.png");
}
-#XsheetScrollBar::sub-line {
+QScrollBar::sub-line {
subcontrol-origin: margin;
}
-#XsheetScrollBar::sub-line:vertical {
+QScrollBar::sub-line:vertical {
image: url("imgs/sb_g_uparrow.png");
- height: 20px;
+ height: 16px;
subcontrol-position: top;
}
-#XsheetScrollBar::sub-line:vertical:pressed {
+QScrollBar::sub-line:vertical:pressed {
image: url("imgs/sb_g_uparrow_pressed.png");
}
-#XsheetScrollBar::sub-line:horizontal {
+QScrollBar::sub-line:horizontal {
image: url("imgs/sb_g_larrow.png");
- width: 20px;
+ width: 16px;
subcontrol-position: left;
}
-#XsheetScrollBar::sub-line:horizontal:pressed {
+QScrollBar::sub-line:horizontal:pressed {
image: url("imgs/sb_g_larrow_pressed.png");
}
-#XsheetScrollBar::add-page {
- background: none;
+QScrollBar::add-page,
+QScrollBar::sub-page {
+ background-color: #a0a0a0;
}
XsheetViewer {
qproperty-TextColor: black;
@@ -1108,5 +1108,14 @@ QDialog #dialogButtonFrame {
#LargeSizedText {
font-size: 17px;
}
+#GearButton {
+ qproperty-icon: url("imgs/gear.png");
+}
+#StartupLabel {
+ padding: 3px;
+}
+#StartupLabel:hover {
+ background-color: #9a9a9a;
+}
//# sourceMappingURL=gray_128_mac.qss.map
\ No newline at end of file
diff --git a/stuff/config/qss/gray_128/imgs/gear.png b/stuff/config/qss/gray_128/imgs/gear.png
new file mode 100644
index 0000000..36477dd
Binary files /dev/null and b/stuff/config/qss/gray_128/imgs/gear.png differ
diff --git a/stuff/config/qss/gray_128/imgs/sb_g_downarrow.png b/stuff/config/qss/gray_128/imgs/sb_g_downarrow.png
index f5e678c..4747674 100644
Binary files a/stuff/config/qss/gray_128/imgs/sb_g_downarrow.png and b/stuff/config/qss/gray_128/imgs/sb_g_downarrow.png differ
diff --git a/stuff/config/qss/gray_128/imgs/sb_g_downarrow_pressed.png b/stuff/config/qss/gray_128/imgs/sb_g_downarrow_pressed.png
index ca150f6..0e10442 100644
Binary files a/stuff/config/qss/gray_128/imgs/sb_g_downarrow_pressed.png and b/stuff/config/qss/gray_128/imgs/sb_g_downarrow_pressed.png differ
diff --git a/stuff/config/qss/gray_128/imgs/sb_g_larrow.png b/stuff/config/qss/gray_128/imgs/sb_g_larrow.png
index db68d6d..44e406e 100644
Binary files a/stuff/config/qss/gray_128/imgs/sb_g_larrow.png and b/stuff/config/qss/gray_128/imgs/sb_g_larrow.png differ
diff --git a/stuff/config/qss/gray_128/imgs/sb_g_larrow_pressed.png b/stuff/config/qss/gray_128/imgs/sb_g_larrow_pressed.png
index 23acd01..c3b6701 100644
Binary files a/stuff/config/qss/gray_128/imgs/sb_g_larrow_pressed.png and b/stuff/config/qss/gray_128/imgs/sb_g_larrow_pressed.png differ
diff --git a/stuff/config/qss/gray_128/imgs/sb_g_rarrow.png b/stuff/config/qss/gray_128/imgs/sb_g_rarrow.png
index 17c8865..92b1e59 100644
Binary files a/stuff/config/qss/gray_128/imgs/sb_g_rarrow.png and b/stuff/config/qss/gray_128/imgs/sb_g_rarrow.png differ
diff --git a/stuff/config/qss/gray_128/imgs/sb_g_rarrow_pressed.png b/stuff/config/qss/gray_128/imgs/sb_g_rarrow_pressed.png
index 873e91b..cc9c423 100644
Binary files a/stuff/config/qss/gray_128/imgs/sb_g_rarrow_pressed.png and b/stuff/config/qss/gray_128/imgs/sb_g_rarrow_pressed.png differ
diff --git a/stuff/config/qss/gray_128/imgs/sb_g_uparrow.png b/stuff/config/qss/gray_128/imgs/sb_g_uparrow.png
index 3fd43db..e0c71f9 100644
Binary files a/stuff/config/qss/gray_128/imgs/sb_g_uparrow.png and b/stuff/config/qss/gray_128/imgs/sb_g_uparrow.png differ
diff --git a/stuff/config/qss/gray_128/imgs/sb_g_uparrow_pressed.png b/stuff/config/qss/gray_128/imgs/sb_g_uparrow_pressed.png
index 37b4e73..74d514b 100644
Binary files a/stuff/config/qss/gray_128/imgs/sb_g_uparrow_pressed.png and b/stuff/config/qss/gray_128/imgs/sb_g_uparrow_pressed.png differ
diff --git a/stuff/profiles/layouts/rooms/Default/menubar_template.xml b/stuff/profiles/layouts/rooms/Default/menubar_template.xml
index 5df924e..92a3b14 100644
--- a/stuff/profiles/layouts/rooms/Default/menubar_template.xml
+++ b/stuff/profiles/layouts/rooms/Default/menubar_template.xml
@@ -2,9 +2,9 @@
\ No newline at end of file
diff --git a/stuff/profiles/layouts/rooms/StudioGhibli/menubar_template.xml b/stuff/profiles/layouts/rooms/StudioGhibli/menubar_template.xml
index eee1faf..b78b58c 100644
--- a/stuff/profiles/layouts/rooms/StudioGhibli/menubar_template.xml
+++ b/stuff/profiles/layouts/rooms/StudioGhibli/menubar_template.xml
@@ -13,6 +13,7 @@
MI_NewLevel
MI_LoadLevel
+ MI_SaveAllLevels
MI_SaveLevel
MI_SaveLevelAs
MI_ExportLevel
diff --git a/stuff/profiles/layouts/shortcuts/defopentoonz.ini b/stuff/profiles/layouts/shortcuts/defopentoonz.ini
new file mode 100644
index 0000000..27ec312
--- /dev/null
+++ b/stuff/profiles/layouts/shortcuts/defopentoonz.ini
@@ -0,0 +1,366 @@
+[shortcuts]
+MI_Clear=Del
+MI_OnionSkin=/
+A_DecreaseBrushHardness=
+A_DecreaseMaxBrushThickness=U
+A_DecreaseMinBrushThickness=H
+A_FxSchematicToggle=
+A_IncreaseBrushHardness=
+A_IncreaseMaxBrushThickness=I
+A_IncreaseMinBrushThickness=J
+A_ToolOption_AutoGroup=
+A_ToolOption_AutoSelect%3AColumn=
+A_ToolOption_AutoSelect%3ANone=
+A_ToolOption_AutoSelect%3APegbar=
+A_ToolOption_AutoSelectDrawing=
+A_ToolOption_Autofill=
+A_ToolOption_BreakSharpAngles=
+A_ToolOption_BrushPreset=
+A_ToolOption_EditToolActiveAxis=
+A_ToolOption_EditToolActiveAxis%3ACenter=
+A_ToolOption_EditToolActiveAxis%3APosition=
+A_ToolOption_EditToolActiveAxis%3ARotation=
+A_ToolOption_EditToolActiveAxis%3AScale=
+A_ToolOption_EditToolActiveAxis%3AShear=
+A_ToolOption_FrameRange=F6
+A_ToolOption_GeometricEdge=
+A_ToolOption_GeometricShape=
+A_ToolOption_GlobalKey=
+A_ToolOption_IK=
+A_ToolOption_Invert=
+A_ToolOption_JoinVectors=
+A_ToolOption_Manual=
+A_ToolOption_Meshify=
+A_ToolOption_Mode=
+A_ToolOption_Mode%3AAreas=
+A_ToolOption_Mode%3ALines=
+A_ToolOption_Mode%3ALines%20%26%20Areas=
+A_ToolOption_OnionSkin=
+A_ToolOption_Orientation=
+A_ToolOption_PencilMode=
+A_ToolOption_PickScreen=
+A_ToolOption_PreserveThickness=
+A_ToolOption_PressureSensitivity=Shift+P
+A_ToolOption_SegmentInk=F8
+A_ToolOption_Selective=F7
+A_ToolOption_ShowOnlyActiveSkeleton=
+A_ToolOption_SkeletonMode%3AAnimate=
+A_ToolOption_SkeletonMode%3ABuild%20Skeleton=
+A_ToolOption_SkeletonMode%3AInverse%20Kinematics=
+A_ToolOption_Smooth=
+A_ToolOption_Snap=
+A_ToolOption_Type=
+A_ToolOption_Type%3AFreehand=
+A_ToolOption_Type%3ANormal=
+A_ToolOption_Type%3APolyline=
+A_ToolOption_Type%3ARectangular=F5
+A_ToolOption_TypeFont=
+A_ToolOption_TypeSize=
+A_ToolOption_TypeStyle=
+MI_ACheck=
+MI_About=
+MI_ActivateAllColumns=
+MI_ActivateSelectedColumns=
+MI_ActivateThisColumnOnly=
+MI_AddFrames=
+MI_AddToBatchCleanupList=
+MI_AddToBatchRenderList=
+MI_AdjustLevels=
+MI_AdjustThickness=
+MI_Antialias=
+MI_ApplyMatchLines=
+MI_AutoFillToggle=Shift+A
+MI_Autocenter=
+MI_Autorenumber=
+MI_BCheck=
+MI_Binarize=
+MI_BlendColors=
+MI_BlueChannel=
+MI_BlueChannelGreyscale=
+MI_BrightnessAndContrast=
+MI_BringForward=]
+MI_BringToFront=Ctrl+]
+MI_CameraSettings=
+MI_CameraStage=
+MI_CameraTest=
+MI_CanvasSize=
+MI_Cleanup=
+MI_CleanupPreview=
+MI_CleanupSettings=
+MI_ClearRecentImage=
+MI_ClearRecentLevel=
+MI_ClearRecentScene=
+MI_CloneChild=
+MI_CloneLevel=
+MI_ClonePreview=
+MI_CloseChild=
+MI_Collapse=
+MI_CollectAssets=
+MI_CompareToSnapshot=
+MI_ConvertFileWithInput=
+MI_ConvertFiles=
+MI_ConvertToVectors=
+MI_Copy=Ctrl+C
+MI_Cut=Ctrl+X
+MI_DeactivateAllColumns=
+MI_DeactivateSelectedColumns=
+MI_DeactivateUpperColumns=
+MI_DecreaseStep=";"
+MI_DefineScanner=
+MI_DeleteInk=
+MI_DeleteMatchLines=
+MI_DisableAllColumns=
+MI_DisableSelectedColumns=
+MI_DockingCheck=
+MI_DrawingSubBackward=Q
+MI_DrawingSubForward=W
+MI_DrawingSubGroupBackward=Alt+Q
+MI_DrawingSubGroupForward=Alt+W
+MI_Dup=
+MI_Duplicate=D
+MI_DuplicateFile=
+MI_Each2=
+MI_Each3=
+MI_Each4=
+MI_EditLevel=
+MI_EditShift=
+MI_EnableAllColumns=
+MI_EnableSelectedColumns=
+MI_EnableThisColumnOnly=
+MI_EnterGroup=
+MI_EraseUnusedStyles=
+MI_ExitGroup=
+MI_ExplodeChild=
+MI_ExportLevel=
+MI_ExportScenes=
+MI_ExposeResource=
+MI_FieldGuide=Shift+G
+MI_FileInfo=
+MI_FillAreas=
+MI_FillLines=
+MI_FirstFrame="Alt+,"
+MI_FoldColumns=
+MI_FrezzePreview=
+MI_FullScreenWindow=Ctrl+`
+MI_FxParamEditor=Ctrl+K
+MI_GCheck=
+MI_GetColorFromStudioPalette=
+MI_GreenChannel=
+MI_GreenChannelGreyscale=
+MI_Group=Ctrl+G
+MI_Histogram=
+MI_ICheck=
+MI_IOnly=
+MI_ImportMagpieFile=
+MI_ImportScenes=
+MI_IncreaseStep="'"
+MI_Increment=
+MI_Ink1Check=
+MI_Insert=Ins
+MI_InsertFx=Ctrl+F
+MI_InsertGlobalKeyframe=
+MI_InsertSceneFrame=
+MI_InvertKeyframeSelection=
+MI_InvertSelection=
+MI_LastFrame=Alt+.
+MI_LevelSettings=
+MI_LinesFade=
+MI_Link=
+MI_LoadColorModel=
+MI_LoadFolder=
+MI_LoadLevel=
+MI_LoadScene=Ctrl+L
+MI_LoadSubSceneFile=
+MI_LockAllColumns=Ctrl+Alt+Shift+L
+MI_LockSelectedColumns=Ctrl+Shift+L
+MI_LockThisColumnOnly=Shift+L
+MI_Loop=L
+MI_MatteChannel=
+MI_MaximizePanel=`
+MI_MergeCmapped=
+MI_MergeColumns=
+MI_MergeFrames=
+MI_NewLevel=Alt+N
+MI_NewOutputFx=
+MI_NewProject=
+MI_NewScene=Ctrl+N
+MI_NextDrawing=.
+MI_NextFrame=Shift+.
+MI_NextStep=
+MI_NoShift=
+MI_OpacityCheck=Alt+1
+MI_OpenBatchServers=
+MI_OpenChild=
+MI_OpenCleanupSettings=
+MI_OpenColorModel=
+MI_OpenComboViewer=
+MI_OpenFileBrowser=
+MI_OpenFileBrowser2=
+MI_OpenFileViewer=
+MI_OpenFilmStrip=
+MI_OpenFunctionEditor=
+MI_OpenHistoryPanel=Ctrl+H
+MI_OpenLevelView=
+MI_OpenPalette=
+MI_OpenPltGizmo=
+MI_OpenRecentLevel=
+MI_OpenRecentScene=
+MI_OpenSchematic=
+MI_OpenScriptConsole=
+MI_OpenStudioPalette=
+MI_OpenStyleControl=
+MI_OpenTMessage=
+MI_OpenTasks=
+MI_OpenToolOptionBar=
+MI_OpenToolbar=
+MI_OpenXshView=
+MI_OutputSettings=Ctrl+O
+MI_OverwritePalette=
+MI_PCheck=
+MI_Paste=Ctrl+V
+MI_PasteColors=
+MI_PasteInto=
+MI_PasteNames=
+MI_PasteValues=
+MI_Pause=
+MI_PencilTest=
+MI_PickStyleAreas=
+MI_PickStyleLines=
+MI_Play=P
+MI_Preferences=Ctrl+U
+MI_PrevDrawing=","
+MI_PrevFrame="Shift+,"
+MI_PrevStep=
+MI_Preview=Ctrl+R
+MI_PreviewFx=
+MI_PreviewSettings=
+MI_Print=Ctrl+P
+MI_PrintXsheet=
+MI_ProjectSettings=
+MI_Quit=Ctrl+Q
+MI_Random=
+MI_RasterizePli=
+MI_RedChannel=
+MI_RedChannelGreyscale=
+MI_Redo=Ctrl+Y
+MI_Reframe1=
+MI_Reframe2=
+MI_Reframe3=
+MI_Reframe4=
+MI_RefreshTree=
+MI_RegenerateFramePr=
+MI_RegeneratePreview=
+MI_ReloadStyle=
+MI_RemoveEndpoints=
+MI_RemoveGlobalKeyframe=
+MI_RemoveLevel=
+MI_RemoveSceneFrame=
+MI_RemoveUnused=
+MI_Render=Ctrl+Shift+R
+MI_Renumber=
+MI_ReplaceLevel=
+MI_ReplaceParentDirectory=
+MI_Resequence=
+MI_ResetInterpolation=
+MI_ResetRoomLayout=
+MI_ResetScanCropbox=
+MI_ResetShift=
+MI_ResetStep=
+MI_Reverse=
+MI_RevertScene=
+MI_RevertToCleanedUp=
+MI_RevertToLastSaved=
+MI_Rolldown=
+MI_Rollup=
+MI_RunScript=
+MI_SafeArea=
+MI_SaveAll=Ctrl+S
+MI_SaveDefaultSettings=
+MI_SaveLevel=
+MI_SaveLevelAs=
+MI_SavePaletteAs=
+MI_SavePreset=
+MI_SavePreviewedFrames=
+MI_SaveScene=Ctrl+Shift+S
+MI_SaveSceneAs=
+MI_SaveSubxsheetAs=
+MI_Scan=
+MI_ScanSettings=
+MI_SceneSettings=
+MI_SelectAll=Ctrl+A
+MI_SelectAllKeyframes=
+MI_SelectAllKeyframesNotAfter=
+MI_SelectAllKeyframesNotBefore=
+MI_SelectColumnKeyframes=
+MI_SelectFollowingKeysInColumn=
+MI_SelectFollowingKeysInRow=
+MI_SelectPreviousKeysInColumn=
+MI_SelectPreviousKeysInRow=
+MI_SelectRowKeyframes=
+MI_SendBack=Ctrl+[
+MI_SendBackward=[
+MI_SetAcceleration=
+MI_SetConstantSpeed=
+MI_SetDeceleration=
+MI_SetKeyframes=Z
+MI_SetScanCropbox=
+MI_ShiftTrace=
+MI_ShortcutPopup=
+MI_ShowFolderContents=
+MI_Step2=
+MI_Step3=
+MI_Step4=
+MI_SwapEnabledColumns=
+MI_Swing=
+MI_TCheck=
+MI_TimeStretch=
+MI_ToggleColumnLocks=
+MI_ToggleColumnsActivation=
+MI_ToggleEditInPlace=
+MI_Tracking=
+MI_Undo=Ctrl+Z
+MI_Ungroup=Ctrl+Shift+G
+MI_UnlockAllColumns=Ctrl+Alt+Shift+U
+MI_UnlockSelectedColumns=Ctrl+Shift+U
+MI_ViewBBox=
+MI_ViewCamera=
+MI_ViewColorcard=
+MI_ViewFile=
+MI_ViewGuide=
+MI_ViewRuler=
+MI_ViewTable=
+MI_ZeroThick=Shift+/
+T_ActualPixelSize=N
+T_Bender=
+T_Brush=B
+T_ControlPointEditor=C
+T_Cutter=
+T_Edit=E
+T_Eraser=A
+T_Fill=F
+T_Finger=
+T_Geometric=G
+T_Hand=Space
+T_Hook=O
+T_Iron=
+T_Magnet=
+T_PaintBrush=
+T_Pinch=M
+T_Plastic=X
+T_Pump=
+T_RGBPicker=R
+T_Rotate=Ctrl+Space
+T_Ruler=
+T_Selection=S
+T_ShowHideFullScreen=Alt+F
+T_Skeleton=V
+T_StylePicker=K
+T_Tape=T
+T_Tracker=
+T_Type=Y
+T_Zoom=Shift+Space
+T_ZoomFit=Alt+9
+T_ZoomReset=Alt+0
+T_Zoomin=+
+T_Zoomout=-
+MI_LoadRecentImage=
diff --git a/stuff/profiles/layouts/shortcuts/otadobe.ini b/stuff/profiles/layouts/shortcuts/otadobe.ini
new file mode 100644
index 0000000..7a1b172
--- /dev/null
+++ b/stuff/profiles/layouts/shortcuts/otadobe.ini
@@ -0,0 +1,366 @@
+[shortcuts]
+MI_LoadRecentImage=
+A_ToolOption_FrameRange=
+A_ToolOption_SegmentInk=
+A_ToolOption_Selective=
+A_ToolOption_Type%3ARectangular=
+MI_BringForward=Ctrl+Up
+MI_BringToFront=Ctrl+Shift+Up
+MI_Clear=Delete
+MI_Copy=Ctrl+C
+MI_Cut=Ctrl+X
+MI_DrawingSubBackward=[
+MI_DrawingSubForward=]
+MI_DrawingSubGroupBackward=Ctrl+[
+MI_DrawingSubGroupForward=Ctrl+]
+MI_Duplicate=
+MI_FullScreenWindow=Ctrl+F
+MI_FxParamEditor=
+MI_Group=Ctrl+G
+MI_Insert=Ins
+MI_InsertFx=
+MI_LoadScene=Ctrl+O
+MI_MaximizePanel=
+MI_NewScene=Ctrl+N
+MI_NextDrawing=G
+MI_NextFrame=.
+MI_OpacityCheck=
+MI_Paste=Ctrl+V
+MI_PrevDrawing=F
+MI_PrevFrame=","
+MI_Preview=Alt+P
+MI_Quit=Ctrl+Q
+MI_Redo=Ctrl+Y
+MI_SaveScene=Ctrl+Shift+S
+MI_SaveSceneAs=Ctrl+Alt+Shift+S
+MI_SelectAll=Shift+A
+MI_SendBack=Ctrl+Shift+Down
+MI_SendBackward=Ctrl+Down
+MI_Undo=Ctrl+Z
+MI_ZeroThick=D
+T_ActualPixelSize=
+T_Brush=Alt+B
+T_ControlPointEditor=Alt+A
+T_Edit=Alt+Q
+T_Eraser=Alt+E
+T_Fill=Alt+K
+T_Geometric=Atl+R
+T_Hand=
+T_Pinch=
+T_Rotate=
+T_Selection=Alt+V
+T_StylePicker=Alt+I
+T_Tape=Alt+C
+T_Type=
+T_Zoom=Alt+Z
+T_ZoomReset=Shift+Z
+T_Zoomin=Ctrl+=
+T_Zoomout=Ctrl+-
+A_DecreaseBrushHardness=
+A_DecreaseMaxBrushThickness=
+A_DecreaseMinBrushThickness=
+A_FxSchematicToggle=
+A_IncreaseBrushHardness=
+A_IncreaseMaxBrushThickness=
+A_IncreaseMinBrushThickness=
+A_ToolOption_AutoGroup=
+A_ToolOption_AutoSelect%3AColumn=
+A_ToolOption_AutoSelect%3ANone=
+A_ToolOption_AutoSelect%3APegbar=
+A_ToolOption_AutoSelectDrawing=
+A_ToolOption_Autofill=
+A_ToolOption_BreakSharpAngles=
+A_ToolOption_BrushPreset=
+A_ToolOption_EditToolActiveAxis=
+A_ToolOption_EditToolActiveAxis%3ACenter=
+A_ToolOption_EditToolActiveAxis%3APosition=
+A_ToolOption_EditToolActiveAxis%3ARotation=
+A_ToolOption_EditToolActiveAxis%3AScale=
+A_ToolOption_EditToolActiveAxis%3AShear=
+A_ToolOption_GeometricEdge=
+A_ToolOption_GeometricShape=
+A_ToolOption_GlobalKey=
+A_ToolOption_IK=Alt+8
+A_ToolOption_Invert=
+A_ToolOption_JoinVectors=
+A_ToolOption_Manual=
+A_ToolOption_Meshify=
+A_ToolOption_Mode=
+A_ToolOption_Mode%3AAreas=
+A_ToolOption_Mode%3ALines=
+A_ToolOption_Mode%3ALines%20%26%20Areas=
+A_ToolOption_OnionSkin=
+A_ToolOption_Orientation=
+A_ToolOption_PencilMode=
+A_ToolOption_PickScreen=
+A_ToolOption_PreserveThickness=
+A_ToolOption_PressureSensitivity=
+A_ToolOption_ShowOnlyActiveSkeleton=
+A_ToolOption_SkeletonMode%3AAnimate=
+A_ToolOption_SkeletonMode%3ABuild%20Skeleton=
+A_ToolOption_SkeletonMode%3AInverse%20Kinematics=
+A_ToolOption_Smooth=
+A_ToolOption_Snap=
+A_ToolOption_Type=
+A_ToolOption_Type%3AFreehand=
+A_ToolOption_Type%3ANormal=
+A_ToolOption_Type%3APolyline=
+A_ToolOption_TypeFont=
+A_ToolOption_TypeSize=
+A_ToolOption_TypeStyle=
+MI_ACheck=
+MI_About=
+MI_ActivateAllColumns=
+MI_ActivateSelectedColumns=
+MI_ActivateThisColumnOnly=
+MI_AddFrames=Ctrl+H
+MI_AddToBatchCleanupList=
+MI_AddToBatchRenderList=
+MI_AdjustLevels=
+MI_AdjustThickness=
+MI_Antialias=
+MI_ApplyMatchLines=
+MI_AutoFillToggle=
+MI_Autocenter=
+MI_Autorenumber=
+MI_BCheck=
+MI_Binarize=
+MI_BlendColors=
+MI_BlueChannel=
+MI_BlueChannelGreyscale=
+MI_BrightnessAndContrast=
+MI_CameraSettings=
+MI_CameraStage=
+MI_CameraTest=
+MI_CanvasSize=
+MI_Cleanup=
+MI_CleanupPreview=
+MI_CleanupSettings=
+MI_ClearRecentImage=
+MI_ClearRecentLevel=
+MI_ClearRecentScene=
+MI_CloneChild=
+MI_CloneLevel=
+MI_ClonePreview=
+MI_CloseChild=
+MI_Collapse=
+MI_CollectAssets=
+MI_CompareToSnapshot=
+MI_ConvertFileWithInput=
+MI_ConvertFiles=
+MI_ConvertToVectors=
+MI_DeactivateAllColumns=
+MI_DeactivateSelectedColumns=Alt+H
+MI_DeactivateUpperColumns=
+MI_DecreaseStep=
+MI_DefineScanner=
+MI_DeleteInk=
+MI_DeleteMatchLines=
+MI_DisableAllColumns=
+MI_DisableSelectedColumns=
+MI_DockingCheck=
+MI_Dup=
+MI_DuplicateFile=
+MI_Each2=
+MI_Each3=
+MI_Each4=
+MI_EditLevel=
+MI_EditShift=
+MI_EnableAllColumns=Alt+Shift+H
+MI_EnableSelectedColumns=
+MI_EnableThisColumnOnly=
+MI_EnterGroup=Ctrl+Return
+MI_EraseUnusedStyles=
+MI_ExitGroup=Backspace
+MI_ExplodeChild=Ctrl+B
+MI_ExportLevel=
+MI_ExportScenes=
+MI_ExposeResource=
+MI_FieldGuide="Ctrl+'"
+MI_FileInfo=
+MI_FillAreas=
+MI_FillLines=
+MI_FirstFrame=Home
+MI_FoldColumns=
+MI_FrezzePreview=
+MI_GCheck=
+MI_GetColorFromStudioPalette=
+MI_GreenChannel=
+MI_GreenChannelGreyscale=
+MI_Histogram=
+MI_ICheck=
+MI_IOnly=
+MI_ImportMagpieFile=
+MI_ImportScenes=
+MI_IncreaseStep="+"
+MI_Increment=
+MI_Ink1Check=
+MI_InsertGlobalKeyframe=
+MI_InsertSceneFrame=
+MI_InvertKeyframeSelection=
+MI_InvertSelection=
+MI_LastFrame=End
+MI_LevelSettings=
+MI_LinesFade=
+MI_Link=
+MI_LoadColorModel=
+MI_LoadFolder=
+MI_LoadLevel=
+MI_LoadSubSceneFile=
+MI_LockAllColumns=
+MI_LockSelectedColumns=
+MI_LockThisColumnOnly=
+MI_Loop=
+MI_MatteChannel=
+MI_MergeCmapped=
+MI_MergeColumns=
+MI_MergeFrames=
+MI_NewLevel=
+MI_NewOutputFx=
+MI_NewProject=
+MI_NextStep=
+MI_NoShift=
+MI_OnionSkin=Ctrl+Alt+O
+MI_OpenBatchServers=
+MI_OpenChild=
+MI_OpenCleanupSettings=
+MI_OpenColorModel=
+MI_OpenComboViewer=
+MI_OpenFileBrowser=
+MI_OpenFileBrowser2=
+MI_OpenFileViewer=
+MI_OpenFilmStrip=
+MI_OpenFunctionEditor=Alt+F
+MI_OpenHistoryPanel=
+MI_OpenLevelView=
+MI_OpenPalette=
+MI_OpenPltGizmo=
+MI_OpenRecentScene=
+MI_OpenSchematic=
+MI_OpenScriptConsole=
+MI_OpenStudioPalette=
+MI_OpenStyleControl=
+MI_OpenTMessage=
+MI_OpenTasks=
+MI_OpenToolOptionBar=
+MI_OpenToolbar=
+MI_OpenXshView=
+MI_OutputSettings=
+MI_OverwritePalette=
+MI_PCheck=
+MI_PasteColors=
+MI_PasteInto=
+MI_PasteNames=
+MI_PasteValues=
+MI_Pause=
+MI_PencilTest=
+MI_PickStyleAreas=
+MI_PickStyleLines=
+MI_Play=Return
+MI_Preferences=Ctrl+U
+MI_PrevStep=
+MI_PreviewFx=
+MI_PreviewSettings=
+MI_Print=
+MI_PrintXsheet=
+MI_ProjectSettings=
+MI_Random=
+MI_RasterizePli=
+MI_RedChannel=
+MI_RedChannelGreyscale=
+MI_Reframe1=
+MI_Reframe2=
+MI_Reframe3=
+MI_Reframe4=
+MI_RefreshTree=
+MI_RegenerateFramePr=
+MI_RegeneratePreview=
+MI_ReloadStyle=
+MI_RemoveEndpoints=
+MI_RemoveGlobalKeyframe=
+MI_RemoveLevel=
+MI_RemoveSceneFrame=
+MI_RemoveUnused=
+MI_Render=Ctrl+Alt+Shift+S
+MI_Renumber=
+MI_ReplaceLevel=
+MI_ReplaceParentDirectory=
+MI_Resequence=
+MI_ResetInterpolation=
+MI_ResetRoomLayout=
+MI_ResetScanCropbox=
+MI_ResetShift=
+MI_ResetStep=
+MI_Reverse=
+MI_RevertScene=
+MI_RevertToCleanedUp=
+MI_RevertToLastSaved=
+MI_Rolldown=
+MI_Rollup=
+MI_RunScript=
+MI_SafeArea=
+MI_SaveAll=Ctrl+S
+MI_SaveDefaultSettings=
+MI_SaveLevel=
+MI_SaveLevelAs=
+MI_SavePaletteAs=
+MI_SavePreset=
+MI_SavePreviewedFrames=
+MI_SaveSubxsheetAs=
+MI_Scan=
+MI_ScanSettings=
+MI_SceneSettings=Ctrl+F3
+MI_SelectAllKeyframes=
+MI_SelectAllKeyframesNotAfter=
+MI_SelectAllKeyframesNotBefore=
+MI_SelectColumnKeyframes=
+MI_SelectFollowingKeysInColumn=
+MI_SelectFollowingKeysInRow=
+MI_SelectPreviousKeysInColumn=
+MI_SelectPreviousKeysInRow=
+MI_SelectRowKeyframes=
+MI_SetAcceleration=
+MI_SetConstantSpeed=
+MI_SetDeceleration=
+MI_SetKeyframes=Ctrl+F6
+MI_SetScanCropbox=
+MI_ShiftTrace=
+MI_ShortcutPopup=
+MI_ShowFolderContents=
+MI_Step2=
+MI_Step3=
+MI_Step4=
+MI_SwapEnabledColumns=
+MI_Swing=
+MI_TCheck=
+MI_TimeStretch=
+MI_ToggleColumnLocks=
+MI_ToggleColumnsActivation=
+MI_ToggleEditInPlace=
+MI_Tracking=
+MI_Ungroup=Ctrl+Shift+G
+MI_UnlockAllColumns=Ctrl+Alt+Shift+L
+MI_UnlockSelectedColumns=Ctrl+Shift+K
+MI_ViewBBox=
+MI_ViewCamera=
+MI_ViewColorcard=
+MI_ViewFile=
+MI_ViewGuide=
+MI_ViewRuler=Ctrl+Alt+Shift+R
+MI_ViewTable=
+T_Bender=
+T_Cutter=Alt+T
+T_Finger=
+T_Hook=
+T_Iron=
+T_Magnet=
+T_PaintBrush=
+T_Plastic=
+T_Pump=
+T_RGBPicker=
+T_Ruler=
+T_ShowHideFullScreen=F4
+T_Skeleton=
+T_Tracker=
+T_ZoomFit=
+MI_OpenRecentLevel=
diff --git a/stuff/profiles/layouts/shortcuts/otharmony.ini b/stuff/profiles/layouts/shortcuts/otharmony.ini
new file mode 100644
index 0000000..3675e6d
--- /dev/null
+++ b/stuff/profiles/layouts/shortcuts/otharmony.ini
@@ -0,0 +1,366 @@
+[shortcuts]
+MI_LoadRecentImage=
+A_ToolOption_FrameRange=
+A_ToolOption_SegmentInk=
+A_ToolOption_Selective=
+A_ToolOption_Type%3ARectangular=
+MI_BringForward=Ctrl+PgUp
+MI_BringToFront=Ctrl+Shift+PgUp
+MI_Clear=Delete
+MI_Copy=Ctrl+C
+MI_Cut=Ctrl+X
+MI_DrawingSubBackward=[
+MI_DrawingSubForward=]
+MI_DrawingSubGroupBackward=Ctrl+[
+MI_DrawingSubGroupForward=Ctrl+]
+MI_Duplicate=
+MI_FullScreenWindow=Ctrl+F
+MI_FxParamEditor=
+MI_Group=Ctrl+G
+MI_Insert=Ins
+MI_InsertFx=
+MI_LoadScene=Ctrl+O
+MI_MaximizePanel=`
+MI_NewScene=Ctrl+N
+MI_NextDrawing=G
+MI_NextFrame=.
+MI_OpacityCheck=
+MI_Paste=Ctrl+V
+MI_PrevDrawing=F
+MI_PrevFrame=","
+MI_Preview=
+MI_Quit=Ctrl+Q
+MI_Redo=Ctrl+Shift+Z
+MI_SaveScene=Ctrl+Shift+S
+MI_SaveSceneAs=Ctrl+Shift+Alt+S
+MI_SelectAll=Ctrl+A
+MI_SendBack=Ctrl+PgDown
+MI_SendBackward=Ctrl+Shift+PgDown
+MI_Undo=Ctrl+Z
+MI_ZeroThick=
+T_ActualPixelSize=
+T_Brush=Alt+B
+T_ControlPointEditor=Alt+Q
+T_Edit=Shift+T
+T_Eraser=Alt+E
+T_Fill=Alt+I
+T_Geometric=Alt+7
+T_Hand=
+T_Pinch=
+T_Rotate=
+T_Selection=Alt+S
+T_StylePicker=Alt+D
+T_Tape=Alt+C
+T_Type=Alt+9
+T_Zoom=Alt+Z
+T_ZoomReset=
+T_Zoomin=Alt+2
+T_Zoomout=Alt+1
+A_DecreaseBrushHardness=
+A_DecreaseMaxBrushThickness=
+A_DecreaseMinBrushThickness=
+A_FxSchematicToggle=
+A_IncreaseBrushHardness=
+A_IncreaseMaxBrushThickness=
+A_IncreaseMinBrushThickness=
+A_ToolOption_AutoGroup=
+A_ToolOption_AutoSelect%3AColumn=
+A_ToolOption_AutoSelect%3ANone=
+A_ToolOption_AutoSelect%3APegbar=
+A_ToolOption_AutoSelectDrawing=
+A_ToolOption_Autofill=
+A_ToolOption_BreakSharpAngles=
+A_ToolOption_BrushPreset=
+A_ToolOption_EditToolActiveAxis=
+A_ToolOption_EditToolActiveAxis%3ACenter=
+A_ToolOption_EditToolActiveAxis%3APosition=Alt+2
+A_ToolOption_EditToolActiveAxis%3ARotation=Alt+3
+A_ToolOption_EditToolActiveAxis%3AScale=Alt+4
+A_ToolOption_EditToolActiveAxis%3AShear=Alt+5
+A_ToolOption_GeometricEdge=
+A_ToolOption_GeometricShape=
+A_ToolOption_GlobalKey=
+A_ToolOption_IK=
+A_ToolOption_Invert=
+A_ToolOption_JoinVectors=
+A_ToolOption_Manual=
+A_ToolOption_Meshify=
+A_ToolOption_Mode=
+A_ToolOption_Mode%3AAreas=
+A_ToolOption_Mode%3ALines=
+A_ToolOption_Mode%3ALines%20%26%20Areas=
+A_ToolOption_OnionSkin=
+A_ToolOption_Orientation=
+A_ToolOption_PencilMode=
+A_ToolOption_PickScreen=
+A_ToolOption_PreserveThickness=
+A_ToolOption_PressureSensitivity=
+A_ToolOption_ShowOnlyActiveSkeleton=
+A_ToolOption_SkeletonMode%3AAnimate=
+A_ToolOption_SkeletonMode%3ABuild%20Skeleton=
+A_ToolOption_SkeletonMode%3AInverse%20Kinematics=
+A_ToolOption_Smooth=
+A_ToolOption_Snap=
+A_ToolOption_Type=
+A_ToolOption_Type%3AFreehand=
+A_ToolOption_Type%3ANormal=
+A_ToolOption_Type%3APolyline=
+A_ToolOption_TypeFont=
+A_ToolOption_TypeSize=
+A_ToolOption_TypeStyle=
+MI_ACheck=
+MI_About=
+MI_ActivateAllColumns=
+MI_ActivateSelectedColumns=
+MI_ActivateThisColumnOnly=
+MI_AddFrames=
+MI_AddToBatchCleanupList=
+MI_AddToBatchRenderList=
+MI_AdjustLevels=
+MI_AdjustThickness=
+MI_Antialias=
+MI_ApplyMatchLines=
+MI_AutoFillToggle=
+MI_Autocenter=
+MI_Autorenumber=
+MI_BCheck=
+MI_Binarize=
+MI_BlendColors=
+MI_BlueChannel=
+MI_BlueChannelGreyscale=
+MI_BrightnessAndContrast=
+MI_CameraSettings=
+MI_CameraStage=
+MI_CameraTest=
+MI_CanvasSize=
+MI_Cleanup=
+MI_CleanupPreview=
+MI_CleanupSettings=
+MI_ClearRecentImage=
+MI_ClearRecentLevel=
+MI_ClearRecentScene=
+MI_CloneChild=
+MI_CloneLevel=
+MI_ClonePreview=
+MI_CloseChild=
+MI_Collapse=Alt+0
+MI_CollectAssets=
+MI_CompareToSnapshot=
+MI_ConvertFileWithInput=
+MI_ConvertFiles=
+MI_ConvertToVectors=
+MI_DeactivateAllColumns=
+MI_DeactivateSelectedColumns=
+MI_DeactivateUpperColumns=
+MI_DecreaseStep=-
+MI_DefineScanner=
+MI_DeleteInk=
+MI_DeleteMatchLines=
+MI_DisableAllColumns=
+MI_DisableSelectedColumns=Alt+H
+MI_DockingCheck=
+MI_Dup=
+MI_DuplicateFile=
+MI_Each2=
+MI_Each3=
+MI_Each4=
+MI_EditLevel=
+MI_EditShift=
+MI_EnableAllColumns=Alt+Shift+H
+MI_EnableSelectedColumns=
+MI_EnableThisColumnOnly=
+MI_EnterGroup=Ctrl+Return
+MI_EraseUnusedStyles=
+MI_ExitGroup=Backspace
+MI_ExplodeChild=Ctrl+B
+MI_ExportLevel=
+MI_ExportScenes=
+MI_ExposeResource=
+MI_FieldGuide="Ctrl+'"
+MI_FileInfo=
+MI_FillAreas=
+MI_FillLines=
+MI_FirstFrame="Shift+<"
+MI_FoldColumns=
+MI_FrezzePreview=
+MI_GCheck=
+MI_GetColorFromStudioPalette=
+MI_GreenChannel=
+MI_GreenChannelGreyscale=
+MI_Histogram=
+MI_ICheck=
+MI_IOnly=
+MI_ImportMagpieFile=
+MI_ImportScenes=
+MI_IncreaseStep="+"
+MI_Increment=
+MI_Ink1Check=
+MI_InsertGlobalKeyframe=
+MI_InsertSceneFrame=
+MI_InvertKeyframeSelection=
+MI_InvertSelection=
+MI_LastFrame="Shift+>"
+MI_LevelSettings=
+MI_LinesFade=
+MI_Link=
+MI_LoadColorModel=
+MI_LoadFolder=
+MI_LoadLevel=
+MI_LoadSubSceneFile=
+MI_LockAllColumns=Ctrl+Shift+L
+MI_LockSelectedColumns=Ctrl+Alt+L
+MI_LockThisColumnOnly=
+MI_Loop=
+MI_MatteChannel=
+MI_MergeCmapped=
+MI_MergeColumns=
+MI_MergeFrames=
+MI_NewLevel=
+MI_NewOutputFx=
+MI_NewProject=
+MI_NextStep=
+MI_NoShift=
+MI_OnionSkin=Alt+O
+MI_OpenBatchServers=
+MI_OpenChild=
+MI_OpenCleanupSettings=
+MI_OpenColorModel=
+MI_OpenComboViewer=
+MI_OpenFileBrowser=
+MI_OpenFileBrowser2=
+MI_OpenFileViewer=
+MI_OpenFilmStrip=
+MI_OpenFunctionEditor=Alt+F
+MI_OpenHistoryPanel=
+MI_OpenLevelView=
+MI_OpenPalette=
+MI_OpenPltGizmo=
+MI_OpenRecentScene=
+MI_OpenSchematic=
+MI_OpenScriptConsole=
+MI_OpenStudioPalette=
+MI_OpenStyleControl=
+MI_OpenTMessage=
+MI_OpenTasks=
+MI_OpenToolOptionBar=
+MI_OpenToolbar=
+MI_OpenXshView=
+MI_OutputSettings=
+MI_OverwritePalette=
+MI_PCheck=
+MI_PasteColors=
+MI_PasteInto=
+MI_PasteNames=
+MI_PasteValues=
+MI_Pause=
+MI_PencilTest=
+MI_PickStyleAreas=
+MI_PickStyleLines=
+MI_Play=Ctrl+Return
+MI_Preferences=Ctrl+U
+MI_PrevStep=
+MI_PreviewFx=
+MI_PreviewSettings=
+MI_Print=
+MI_PrintXsheet=
+MI_ProjectSettings=
+MI_Random=
+MI_RasterizePli=
+MI_RedChannel=
+MI_RedChannelGreyscale=
+MI_Reframe1=
+MI_Reframe2=
+MI_Reframe3=
+MI_Reframe4=
+MI_RefreshTree=
+MI_RegenerateFramePr=
+MI_RegeneratePreview=
+MI_ReloadStyle=
+MI_RemoveEndpoints=
+MI_RemoveGlobalKeyframe=
+MI_RemoveLevel=
+MI_RemoveSceneFrame=
+MI_RemoveUnused=
+MI_Render=
+MI_Renumber=
+MI_ReplaceLevel=
+MI_ReplaceParentDirectory=
+MI_Resequence=
+MI_ResetInterpolation=
+MI_ResetRoomLayout=
+MI_ResetScanCropbox=
+MI_ResetShift=
+MI_ResetStep=
+MI_Reverse=
+MI_RevertScene=
+MI_RevertToCleanedUp=
+MI_RevertToLastSaved=
+MI_Rolldown=
+MI_Rollup=
+MI_RunScript=
+MI_SafeArea=
+MI_SaveAll=Ctrl+S
+MI_SaveDefaultSettings=
+MI_SaveLevel=
+MI_SaveLevelAs=
+MI_SavePaletteAs=
+MI_SavePreset=
+MI_SavePreviewedFrames=
+MI_SaveSubxsheetAs=
+MI_Scan=Ctrl+Shift+S
+MI_ScanSettings=
+MI_SceneSettings=
+MI_SelectAllKeyframes=
+MI_SelectAllKeyframesNotAfter=
+MI_SelectAllKeyframesNotBefore=
+MI_SelectColumnKeyframes=
+MI_SelectFollowingKeysInColumn=
+MI_SelectFollowingKeysInRow=
+MI_SelectPreviousKeysInColumn=
+MI_SelectPreviousKeysInRow=
+MI_SelectRowKeyframes=
+MI_SetAcceleration=
+MI_SetConstantSpeed=
+MI_SetDeceleration=
+MI_SetKeyframes=F6
+MI_SetScanCropbox=
+MI_ShiftTrace=
+MI_ShortcutPopup=
+MI_ShowFolderContents=
+MI_Step2=
+MI_Step3=
+MI_Step4=
+MI_SwapEnabledColumns=
+MI_Swing=
+MI_TCheck=
+MI_TimeStretch=
+MI_ToggleColumnLocks=
+MI_ToggleColumnsActivation=
+MI_ToggleEditInPlace=
+MI_Tracking=
+MI_Ungroup=Ctrl+Shift+G
+MI_UnlockAllColumns=Ctrl+Alt+Shift+K
+MI_UnlockSelectedColumns=Ctrl+Shift+K
+MI_ViewBBox=
+MI_ViewCamera=
+MI_ViewColorcard=
+MI_ViewFile=
+MI_ViewGuide="Ctrl+'"
+MI_ViewRuler=
+MI_ViewTable=
+T_Bender=
+T_Cutter=Alt+T
+T_Finger=
+T_Hook=
+T_Iron=
+T_Magnet=
+T_PaintBrush=
+T_Plastic=
+T_Pump=
+T_RGBPicker=
+T_Ruler=
+T_ShowHideFullScreen=
+T_Skeleton=
+T_Tracker=
+T_ZoomFit=
+MI_OpenRecentLevel=
diff --git a/stuff/profiles/layouts/shortcuts/otretas.ini b/stuff/profiles/layouts/shortcuts/otretas.ini
new file mode 100644
index 0000000..7a1b172
--- /dev/null
+++ b/stuff/profiles/layouts/shortcuts/otretas.ini
@@ -0,0 +1,366 @@
+[shortcuts]
+MI_LoadRecentImage=
+A_ToolOption_FrameRange=
+A_ToolOption_SegmentInk=
+A_ToolOption_Selective=
+A_ToolOption_Type%3ARectangular=
+MI_BringForward=Ctrl+Up
+MI_BringToFront=Ctrl+Shift+Up
+MI_Clear=Delete
+MI_Copy=Ctrl+C
+MI_Cut=Ctrl+X
+MI_DrawingSubBackward=[
+MI_DrawingSubForward=]
+MI_DrawingSubGroupBackward=Ctrl+[
+MI_DrawingSubGroupForward=Ctrl+]
+MI_Duplicate=
+MI_FullScreenWindow=Ctrl+F
+MI_FxParamEditor=
+MI_Group=Ctrl+G
+MI_Insert=Ins
+MI_InsertFx=
+MI_LoadScene=Ctrl+O
+MI_MaximizePanel=
+MI_NewScene=Ctrl+N
+MI_NextDrawing=G
+MI_NextFrame=.
+MI_OpacityCheck=
+MI_Paste=Ctrl+V
+MI_PrevDrawing=F
+MI_PrevFrame=","
+MI_Preview=Alt+P
+MI_Quit=Ctrl+Q
+MI_Redo=Ctrl+Y
+MI_SaveScene=Ctrl+Shift+S
+MI_SaveSceneAs=Ctrl+Alt+Shift+S
+MI_SelectAll=Shift+A
+MI_SendBack=Ctrl+Shift+Down
+MI_SendBackward=Ctrl+Down
+MI_Undo=Ctrl+Z
+MI_ZeroThick=D
+T_ActualPixelSize=
+T_Brush=Alt+B
+T_ControlPointEditor=Alt+A
+T_Edit=Alt+Q
+T_Eraser=Alt+E
+T_Fill=Alt+K
+T_Geometric=Atl+R
+T_Hand=
+T_Pinch=
+T_Rotate=
+T_Selection=Alt+V
+T_StylePicker=Alt+I
+T_Tape=Alt+C
+T_Type=
+T_Zoom=Alt+Z
+T_ZoomReset=Shift+Z
+T_Zoomin=Ctrl+=
+T_Zoomout=Ctrl+-
+A_DecreaseBrushHardness=
+A_DecreaseMaxBrushThickness=
+A_DecreaseMinBrushThickness=
+A_FxSchematicToggle=
+A_IncreaseBrushHardness=
+A_IncreaseMaxBrushThickness=
+A_IncreaseMinBrushThickness=
+A_ToolOption_AutoGroup=
+A_ToolOption_AutoSelect%3AColumn=
+A_ToolOption_AutoSelect%3ANone=
+A_ToolOption_AutoSelect%3APegbar=
+A_ToolOption_AutoSelectDrawing=
+A_ToolOption_Autofill=
+A_ToolOption_BreakSharpAngles=
+A_ToolOption_BrushPreset=
+A_ToolOption_EditToolActiveAxis=
+A_ToolOption_EditToolActiveAxis%3ACenter=
+A_ToolOption_EditToolActiveAxis%3APosition=
+A_ToolOption_EditToolActiveAxis%3ARotation=
+A_ToolOption_EditToolActiveAxis%3AScale=
+A_ToolOption_EditToolActiveAxis%3AShear=
+A_ToolOption_GeometricEdge=
+A_ToolOption_GeometricShape=
+A_ToolOption_GlobalKey=
+A_ToolOption_IK=Alt+8
+A_ToolOption_Invert=
+A_ToolOption_JoinVectors=
+A_ToolOption_Manual=
+A_ToolOption_Meshify=
+A_ToolOption_Mode=
+A_ToolOption_Mode%3AAreas=
+A_ToolOption_Mode%3ALines=
+A_ToolOption_Mode%3ALines%20%26%20Areas=
+A_ToolOption_OnionSkin=
+A_ToolOption_Orientation=
+A_ToolOption_PencilMode=
+A_ToolOption_PickScreen=
+A_ToolOption_PreserveThickness=
+A_ToolOption_PressureSensitivity=
+A_ToolOption_ShowOnlyActiveSkeleton=
+A_ToolOption_SkeletonMode%3AAnimate=
+A_ToolOption_SkeletonMode%3ABuild%20Skeleton=
+A_ToolOption_SkeletonMode%3AInverse%20Kinematics=
+A_ToolOption_Smooth=
+A_ToolOption_Snap=
+A_ToolOption_Type=
+A_ToolOption_Type%3AFreehand=
+A_ToolOption_Type%3ANormal=
+A_ToolOption_Type%3APolyline=
+A_ToolOption_TypeFont=
+A_ToolOption_TypeSize=
+A_ToolOption_TypeStyle=
+MI_ACheck=
+MI_About=
+MI_ActivateAllColumns=
+MI_ActivateSelectedColumns=
+MI_ActivateThisColumnOnly=
+MI_AddFrames=Ctrl+H
+MI_AddToBatchCleanupList=
+MI_AddToBatchRenderList=
+MI_AdjustLevels=
+MI_AdjustThickness=
+MI_Antialias=
+MI_ApplyMatchLines=
+MI_AutoFillToggle=
+MI_Autocenter=
+MI_Autorenumber=
+MI_BCheck=
+MI_Binarize=
+MI_BlendColors=
+MI_BlueChannel=
+MI_BlueChannelGreyscale=
+MI_BrightnessAndContrast=
+MI_CameraSettings=
+MI_CameraStage=
+MI_CameraTest=
+MI_CanvasSize=
+MI_Cleanup=
+MI_CleanupPreview=
+MI_CleanupSettings=
+MI_ClearRecentImage=
+MI_ClearRecentLevel=
+MI_ClearRecentScene=
+MI_CloneChild=
+MI_CloneLevel=
+MI_ClonePreview=
+MI_CloseChild=
+MI_Collapse=
+MI_CollectAssets=
+MI_CompareToSnapshot=
+MI_ConvertFileWithInput=
+MI_ConvertFiles=
+MI_ConvertToVectors=
+MI_DeactivateAllColumns=
+MI_DeactivateSelectedColumns=Alt+H
+MI_DeactivateUpperColumns=
+MI_DecreaseStep=
+MI_DefineScanner=
+MI_DeleteInk=
+MI_DeleteMatchLines=
+MI_DisableAllColumns=
+MI_DisableSelectedColumns=
+MI_DockingCheck=
+MI_Dup=
+MI_DuplicateFile=
+MI_Each2=
+MI_Each3=
+MI_Each4=
+MI_EditLevel=
+MI_EditShift=
+MI_EnableAllColumns=Alt+Shift+H
+MI_EnableSelectedColumns=
+MI_EnableThisColumnOnly=
+MI_EnterGroup=Ctrl+Return
+MI_EraseUnusedStyles=
+MI_ExitGroup=Backspace
+MI_ExplodeChild=Ctrl+B
+MI_ExportLevel=
+MI_ExportScenes=
+MI_ExposeResource=
+MI_FieldGuide="Ctrl+'"
+MI_FileInfo=
+MI_FillAreas=
+MI_FillLines=
+MI_FirstFrame=Home
+MI_FoldColumns=
+MI_FrezzePreview=
+MI_GCheck=
+MI_GetColorFromStudioPalette=
+MI_GreenChannel=
+MI_GreenChannelGreyscale=
+MI_Histogram=
+MI_ICheck=
+MI_IOnly=
+MI_ImportMagpieFile=
+MI_ImportScenes=
+MI_IncreaseStep="+"
+MI_Increment=
+MI_Ink1Check=
+MI_InsertGlobalKeyframe=
+MI_InsertSceneFrame=
+MI_InvertKeyframeSelection=
+MI_InvertSelection=
+MI_LastFrame=End
+MI_LevelSettings=
+MI_LinesFade=
+MI_Link=
+MI_LoadColorModel=
+MI_LoadFolder=
+MI_LoadLevel=
+MI_LoadSubSceneFile=
+MI_LockAllColumns=
+MI_LockSelectedColumns=
+MI_LockThisColumnOnly=
+MI_Loop=
+MI_MatteChannel=
+MI_MergeCmapped=
+MI_MergeColumns=
+MI_MergeFrames=
+MI_NewLevel=
+MI_NewOutputFx=
+MI_NewProject=
+MI_NextStep=
+MI_NoShift=
+MI_OnionSkin=Ctrl+Alt+O
+MI_OpenBatchServers=
+MI_OpenChild=
+MI_OpenCleanupSettings=
+MI_OpenColorModel=
+MI_OpenComboViewer=
+MI_OpenFileBrowser=
+MI_OpenFileBrowser2=
+MI_OpenFileViewer=
+MI_OpenFilmStrip=
+MI_OpenFunctionEditor=Alt+F
+MI_OpenHistoryPanel=
+MI_OpenLevelView=
+MI_OpenPalette=
+MI_OpenPltGizmo=
+MI_OpenRecentScene=
+MI_OpenSchematic=
+MI_OpenScriptConsole=
+MI_OpenStudioPalette=
+MI_OpenStyleControl=
+MI_OpenTMessage=
+MI_OpenTasks=
+MI_OpenToolOptionBar=
+MI_OpenToolbar=
+MI_OpenXshView=
+MI_OutputSettings=
+MI_OverwritePalette=
+MI_PCheck=
+MI_PasteColors=
+MI_PasteInto=
+MI_PasteNames=
+MI_PasteValues=
+MI_Pause=
+MI_PencilTest=
+MI_PickStyleAreas=
+MI_PickStyleLines=
+MI_Play=Return
+MI_Preferences=Ctrl+U
+MI_PrevStep=
+MI_PreviewFx=
+MI_PreviewSettings=
+MI_Print=
+MI_PrintXsheet=
+MI_ProjectSettings=
+MI_Random=
+MI_RasterizePli=
+MI_RedChannel=
+MI_RedChannelGreyscale=
+MI_Reframe1=
+MI_Reframe2=
+MI_Reframe3=
+MI_Reframe4=
+MI_RefreshTree=
+MI_RegenerateFramePr=
+MI_RegeneratePreview=
+MI_ReloadStyle=
+MI_RemoveEndpoints=
+MI_RemoveGlobalKeyframe=
+MI_RemoveLevel=
+MI_RemoveSceneFrame=
+MI_RemoveUnused=
+MI_Render=Ctrl+Alt+Shift+S
+MI_Renumber=
+MI_ReplaceLevel=
+MI_ReplaceParentDirectory=
+MI_Resequence=
+MI_ResetInterpolation=
+MI_ResetRoomLayout=
+MI_ResetScanCropbox=
+MI_ResetShift=
+MI_ResetStep=
+MI_Reverse=
+MI_RevertScene=
+MI_RevertToCleanedUp=
+MI_RevertToLastSaved=
+MI_Rolldown=
+MI_Rollup=
+MI_RunScript=
+MI_SafeArea=
+MI_SaveAll=Ctrl+S
+MI_SaveDefaultSettings=
+MI_SaveLevel=
+MI_SaveLevelAs=
+MI_SavePaletteAs=
+MI_SavePreset=
+MI_SavePreviewedFrames=
+MI_SaveSubxsheetAs=
+MI_Scan=
+MI_ScanSettings=
+MI_SceneSettings=Ctrl+F3
+MI_SelectAllKeyframes=
+MI_SelectAllKeyframesNotAfter=
+MI_SelectAllKeyframesNotBefore=
+MI_SelectColumnKeyframes=
+MI_SelectFollowingKeysInColumn=
+MI_SelectFollowingKeysInRow=
+MI_SelectPreviousKeysInColumn=
+MI_SelectPreviousKeysInRow=
+MI_SelectRowKeyframes=
+MI_SetAcceleration=
+MI_SetConstantSpeed=
+MI_SetDeceleration=
+MI_SetKeyframes=Ctrl+F6
+MI_SetScanCropbox=
+MI_ShiftTrace=
+MI_ShortcutPopup=
+MI_ShowFolderContents=
+MI_Step2=
+MI_Step3=
+MI_Step4=
+MI_SwapEnabledColumns=
+MI_Swing=
+MI_TCheck=
+MI_TimeStretch=
+MI_ToggleColumnLocks=
+MI_ToggleColumnsActivation=
+MI_ToggleEditInPlace=
+MI_Tracking=
+MI_Ungroup=Ctrl+Shift+G
+MI_UnlockAllColumns=Ctrl+Alt+Shift+L
+MI_UnlockSelectedColumns=Ctrl+Shift+K
+MI_ViewBBox=
+MI_ViewCamera=
+MI_ViewColorcard=
+MI_ViewFile=
+MI_ViewGuide=
+MI_ViewRuler=Ctrl+Alt+Shift+R
+MI_ViewTable=
+T_Bender=
+T_Cutter=Alt+T
+T_Finger=
+T_Hook=
+T_Iron=
+T_Magnet=
+T_PaintBrush=
+T_Plastic=
+T_Pump=
+T_RGBPicker=
+T_Ruler=
+T_ShowHideFullScreen=F4
+T_Skeleton=
+T_Tracker=
+T_ZoomFit=
+MI_OpenRecentLevel=
diff --git a/thirdparty/libpng-1.6.21/lib/libpng16_2015.lib b/thirdparty/libpng-1.6.21/lib/libpng16_2015.lib
index ca4827f..1e7bbcf 100644
--- a/thirdparty/libpng-1.6.21/lib/libpng16_2015.lib
+++ b/thirdparty/libpng-1.6.21/lib/libpng16_2015.lib
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:1d6be973caafd36b6dcf9b8fcb2d030ad2e0c3c523527fad7bbf7da9f9ba5b6e
-size 56118
+oid sha256:e005a1c28ab5a1f8ed57793a79c883f0b44cd5d2b25152544e3dca5fbdd616bc
+size 374568
diff --git a/thirdparty/libpng-1.6.21/lib/libpng16_2015d.lib b/thirdparty/libpng-1.6.21/lib/libpng16_2015d.lib
index a94d492..1859771 100644
--- a/thirdparty/libpng-1.6.21/lib/libpng16_2015d.lib
+++ b/thirdparty/libpng-1.6.21/lib/libpng16_2015d.lib
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
-oid sha256:be7784d0f86cf87b9dd965a32707e1a999b059d57fbeddb4066a033200e0fbc9
-size 56118
+oid sha256:f61acffbae2925d60a61bd11b6d5b09502843c89c8b3f20b89f240e050a1e916
+size 858596
diff --git a/thirdparty/tiff-4.0.3/libtiff/Makefile.am b/thirdparty/tiff-4.0.3/libtiff/Makefile.am
index 82fa31d..0a47dab 100644
--- a/thirdparty/tiff-4.0.3/libtiff/Makefile.am
+++ b/thirdparty/tiff-4.0.3/libtiff/Makefile.am
@@ -74,6 +74,7 @@ libtiff_la_SOURCES = \
tif_fax3sm.c \
tif_flush.c \
tif_getimage.c \
+ tif_getimage_64.c \
tif_jbig.c \
tif_jpeg.c \
tif_jpeg_12.c \
diff --git a/toonz/sources/CMakeLists.txt b/toonz/sources/CMakeLists.txt
index af8ea55..b06a20d 100644
--- a/toonz/sources/CMakeLists.txt
+++ b/toonz/sources/CMakeLists.txt
@@ -92,7 +92,7 @@ elseif(UNIX)
else()
set(PLATFORM 32)
endif()
- if (CMAKE_SYSTEM_NAME MATCHES "Linux")
+ if(CMAKE_SYSTEM_NAME MATCHES "Linux")
add_definitions(-DLINUX)
else()
message(WARNING "Support for generic Unix (Not Apple or Linux) isn't yet working!")
diff --git a/toonz/sources/common/tsystem/tfilepath.cpp b/toonz/sources/common/tsystem/tfilepath.cpp
index 215a042..d16a1a3 100644
--- a/toonz/sources/common/tsystem/tfilepath.cpp
+++ b/toonz/sources/common/tsystem/tfilepath.cpp
@@ -480,6 +480,7 @@ bool TFilePath::isRoot() const {
// ritorna ""(niente tipo, niente punto), "." (file con tipo) o ".." (file con
// tipo e frame)
std::string TFilePath::getDots() const {
+ if (isFfmpegType()) return ".";
int i = getLastSlash(m_path);
std::wstring str = m_path.substr(i + 1);
// potrei anche avere a.b.c.d dove d e' l'estensione
@@ -561,7 +562,7 @@ std::string TFilePath::getLevelName() const {
std::wstring TFilePath::getLevelNameW() const {
int i = getLastSlash(m_path); // cerco l'ultimo slash
std::wstring str = m_path.substr(i + 1); // str e' m_path senza directory
-
+ if (isFfmpegType()) return str;
int j = str.rfind(L"."); // str[j..] = ".type"
if (j == (int)std::wstring::npos) return str; // no frame; no type
i = str.substr(0, j).rfind(L'.');
@@ -597,6 +598,7 @@ TFilePath TFilePath::getParentDir() const // noSlash!
//-----------------------------------------------------------------------------
bool TFilePath::isLevelName() const {
+ if (isFfmpegType()) return false;
try {
return getFrame() == TFrameId(TFrameId::EMPTY_FRAME);
}
@@ -638,6 +640,15 @@ TFrameId TFilePath::getFrame() const {
//-----------------------------------------------------------------------------
+bool TFilePath::isFfmpegType() const {
+ QString type = QString::fromStdString(getType()).toLower();
+ if (type == "gif" || type == "mp4" || type == "webm")
+ return true;
+ else
+ return false;
+}
+
+//-----------------------------------------------------------------------------
TFilePath TFilePath::withType(const std::string &type) const {
assert(type.length() < 2 || type.substr(0, 2) != "..");
int i = getLastSlash(m_path); // cerco l'ultimo slash
diff --git a/toonz/sources/common/tvrender/tcolorstyles.cpp b/toonz/sources/common/tvrender/tcolorstyles.cpp
index 3b18ce5..a67f8f1 100644
--- a/toonz/sources/common/tvrender/tcolorstyles.cpp
+++ b/toonz/sources/common/tvrender/tcolorstyles.cpp
@@ -50,7 +50,8 @@ TColorStyle::TColorStyle()
, m_enabled(true)
, m_icon(0)
, m_validIcon(false)
- , m_isEditedFromOriginal(false) {}
+ , m_isEditedFromOriginal(false)
+ , m_pickedPosition() {}
//-------------------------------------------------------------------
@@ -66,7 +67,8 @@ TColorStyle::TColorStyle(const TColorStyle &other)
, m_flags(other.m_flags)
, m_enabled(other.m_enabled)
, m_validIcon(false)
- , m_isEditedFromOriginal(other.m_isEditedFromOriginal) {}
+ , m_isEditedFromOriginal(other.m_isEditedFromOriginal)
+ , m_pickedPosition(other.m_pickedPosition) {}
//-------------------------------------------------------------------
@@ -79,6 +81,7 @@ TColorStyle &TColorStyle::operator=(const TColorStyle &other) {
m_enabled = other.m_enabled;
m_validIcon = false;
m_isEditedFromOriginal = other.m_isEditedFromOriginal;
+ m_pickedPosition = other.m_pickedPosition;
return *this;
}
@@ -100,6 +103,7 @@ bool TColorStyle::operator==(const TColorStyle &cs) const {
if (m_originalName != cs.getOriginalName()) return false;
if (m_globalName != cs.getGlobalName()) return false;
if (m_isEditedFromOriginal != cs.getIsEditedFlag()) return false;
+ if (m_pickedPosition != cs.getPickedPosition()) return false;
for (int p = 0; p < colorParamCount; ++p)
if (getColorParamValue(p) != cs.getColorParamValue(p)) return false;
diff --git a/toonz/sources/common/tvrender/tpalette.cpp b/toonz/sources/common/tvrender/tpalette.cpp
index e301908..ad236ef 100644
--- a/toonz/sources/common/tvrender/tpalette.cpp
+++ b/toonz/sources/common/tvrender/tpalette.cpp
@@ -15,6 +15,7 @@
#include "tpalette.h"
#include
+#include
PERSIST_IDENTIFIER(TPalette, "palette")
@@ -30,6 +31,21 @@ namespace {
const int maxStyleIndex = 32765;
+const std::string pointToString(const TPoint &point) {
+ return std::to_string(point.x) + "," + std::to_string(point.y);
+}
+
+// splitting string with ','
+const TPoint stringToPoint(const std::string &string) {
+ std::string buffer;
+ std::stringstream ss(string);
+ std::getline(ss, buffer, ','); // getting the first part of string
+ int x = std::stoi(buffer);
+ std::getline(ss, buffer); // getting the second part of string
+ int y = std::stoi(buffer);
+ return TPoint(x, y);
+}
+
} // namespace
//===================================================================
@@ -168,7 +184,8 @@ TPalette::TPalette()
, m_dirtyFlag(false)
, m_mutex(QMutex::Recursive)
, m_isLocked(false)
- , m_askOverwriteFlag(false) {
+ , m_askOverwriteFlag(false)
+ , m_shortcutScopeIndex(0) {
QString tempName(QObject::tr("colors"));
std::wstring pageName = tempName.toStdWString();
Page *page = addPage(pageName);
@@ -563,10 +580,17 @@ void TPalette::saveData(TOStream &os) {
os.openChild("styles");
{
for (int i = 0; i < getStyleCount(); ++i) {
- os.openChild("style");
+ TColorStyleP style = m_styles[i].second;
+ if (style->getPickedPosition() == TPoint())
+ os.openChild("style");
+ else {
+ std::map attr;
+ attr["pickedpos"] = pointToString(style->getPickedPosition());
+ os.openChild("style", attr);
+ }
{
StyleWriter w(os, i);
- m_styles[i].second->save(w);
+ style->save(w);
}
os.closeChild();
}
@@ -680,6 +704,10 @@ void TPalette::loadData(TIStream &is) {
StyleReader r(is, version);
TColorStyle *cs = TColorStyle::load(r);
+ std::string pickedPosStr;
+ if (is.getTagParam("pickedpos", pickedPosStr))
+ cs->setPickedPosition(stringToPoint(pickedPosStr));
+
addStyle(cs);
}
@@ -851,9 +879,10 @@ void TPalette::assign(const TPalette *src, bool isFromStudioPalette) {
j->second = j->second->clone();
m_styleAnimationTable[cit->first] = cit->second;
}
- m_globalName = src->getGlobalName();
- m_shortcuts = src->m_shortcuts;
- m_currentFrame = src->m_currentFrame;
+ m_globalName = src->getGlobalName();
+ m_shortcuts = src->m_shortcuts;
+ m_currentFrame = src->m_currentFrame;
+ m_shortcutScopeIndex = src->m_shortcutScopeIndex;
// setDirtyFlag(true);
}
@@ -1053,22 +1082,26 @@ void TPalette::clearKeyframe(int styleId, int frame) {
//-------------------------------------------------------------------
int TPalette::getShortcutValue(int key) const {
- assert('0' <= key && key <= '9');
- std::map::const_iterator it;
- it = m_shortcuts.find(key);
- if (it == m_shortcuts.end()) return -1;
- int styleId = it->second;
- return 0 <= styleId && styleId < getStyleCount() ? styleId : -1;
+ assert(Qt::Key_0 <= key && key <= Qt::Key_9);
+
+ int shortcutIndex = (key == Qt::Key_0) ? 9 : key - Qt::Key_1;
+ int indexInPage = m_shortcutScopeIndex * 10 + shortcutIndex;
+ // shortcut is available only in the first page
+ return getPage(0)->getStyleId(indexInPage);
}
//-------------------------------------------------------------------
int TPalette::getStyleShortcut(int styleId) const {
assert(0 <= styleId && styleId < getStyleCount());
- std::map::const_iterator it;
- for (it = m_shortcuts.begin(); it != m_shortcuts.end(); ++it)
- if (it->second == styleId) return it->first;
- return -1;
+
+ Page *page = getStylePage(styleId);
+ // shortcut is available only in the first page
+ if (!page || page->getIndex() != 0) return -1;
+ int indexInPage = page->search(styleId);
+ int shortcutIndex = indexInPage - m_shortcutScopeIndex * 10;
+ if (shortcutIndex < 0 || shortcutIndex > 9) return -1;
+ return (shortcutIndex == 9) ? Qt::Key_0 : Qt::Key_1 + shortcutIndex;
}
//-------------------------------------------------------------------
@@ -1088,3 +1121,31 @@ void TPalette::setShortcutValue(int key, int styleId) {
m_shortcuts[key] = styleId;
}
}
+
+//-------------------------------------------------------------------
+// Returns true if there is at least one style with picked pos value
+//-------------------------------------------------------------------
+
+bool TPalette::hasPickedPosStyle() {
+ for (int i = 0; i < getStyleCount(); ++i) {
+ TColorStyleP style = m_styles[i].second;
+ if (style->getPickedPosition() != TPoint()) return true;
+ }
+ return false;
+}
+
+//-------------------------------------------------------------------
+
+void TPalette::nextShortcutScope(bool invert) {
+ if (invert) {
+ if (m_shortcutScopeIndex > 0)
+ m_shortcutScopeIndex -= 1;
+ else
+ m_shortcutScopeIndex = getPage(0)->getStyleCount() / 10;
+ } else {
+ if ((m_shortcutScopeIndex + 1) * 10 < getPage(0)->getStyleCount())
+ m_shortcutScopeIndex += 1;
+ else
+ m_shortcutScopeIndex = 0;
+ }
+}
diff --git a/toonz/sources/image/ffmpeg/tiio_ffmpeg.cpp b/toonz/sources/image/ffmpeg/tiio_ffmpeg.cpp
index 3f35abe..9dd86a1 100644
--- a/toonz/sources/image/ffmpeg/tiio_ffmpeg.cpp
+++ b/toonz/sources/image/ffmpeg/tiio_ffmpeg.cpp
@@ -6,6 +6,7 @@
#include
#include
#include
+#include
#include "toonz/preferences.h"
#include "toonz/toonzfolders.h"
@@ -98,8 +99,9 @@ void Ffmpeg::setFrameRate(double fps) { m_frameRate = fps; }
void Ffmpeg::setPath(TFilePath path) { m_path = path; }
void Ffmpeg::createIntermediateImage(const TImageP &img, int frameIndex) {
+ m_frameCount++;
QString tempPath = m_path.getQString() + "tempOut" +
- QString::number(frameIndex) + "." + m_intermediateFormat;
+ QString::number(m_frameCount) + "." + m_intermediateFormat;
std::string saveStatus = "";
TRasterImageP tempImage(img);
TRasterImage *image = (TRasterImage *)tempImage->cloneImage();
@@ -127,7 +129,7 @@ void Ffmpeg::createIntermediateImage(const TImageP &img, int frameIndex) {
qi->save(tempPath, format, -1);
free(buffer);
m_cleanUpList.push_back(tempPath);
- m_frameCount++;
+
delete qi;
delete image;
}
@@ -217,9 +219,9 @@ void Ffmpeg::saveSoundTrack(TSoundTrack *st) {
bool Ffmpeg::checkFilesExist() {
QString ffmpegCachePath = getFfmpegCache().getQString();
QString tempPath = ffmpegCachePath + "//" +
- QString::fromStdString(m_path.getName()) +
- QString::fromStdString(m_path.getType()) + "In0001." +
- m_intermediateFormat;
+ m_path.getQString().remove(QRegExp(QString::fromUtf8(
+ "[-`~!@#$%^&*()_�+=|:;<>��,.?/{}\'\"\\[\\]\\\\]"))) +
+ "In0001." + m_intermediateFormat;
if (TSystem::doesExistFileOrLevel(TFilePath(tempPath))) {
return true;
} else
@@ -229,8 +231,9 @@ bool Ffmpeg::checkFilesExist() {
ffmpegFileInfo Ffmpeg::getInfo() {
QString ffmpegCachePath = getFfmpegCache().getQString();
QString tempPath = ffmpegCachePath + "//" +
- QString::fromStdString(m_path.getName()) +
- QString::fromStdString(m_path.getType()) + ".txt";
+ m_path.getQString().remove(QRegExp(QString::fromUtf8(
+ "[-`~!@#$%^&*()_�+=|:;<>��,.?/{}\'\"\\[\\]\\\\]"))) +
+ ".txt";
if (QFile::exists(tempPath)) {
QFile infoText(tempPath);
infoText.open(QIODevice::ReadOnly);
@@ -264,8 +267,8 @@ ffmpegFileInfo Ffmpeg::getInfo() {
TRasterImageP Ffmpeg::getImage(int frameIndex) {
QString ffmpegCachePath = getFfmpegCache().getQString();
QString tempPath = ffmpegCachePath + "//" +
- QString::fromStdString(m_path.getName()) +
- QString::fromStdString(m_path.getType());
+ m_path.getQString().remove(QRegExp(QString::fromUtf8(
+ "[-`~!@#$%^&*()_�+=|:;<>��,.?/{}\'\"\\[\\]\\\\]")));
std::string tmpPath = tempPath.toStdString();
// QString tempPath= m_path.getQString();
QString number = QString("%1").arg(frameIndex, 4, 10, QChar('0'));
@@ -356,8 +359,8 @@ int Ffmpeg::getFrameCount() {
void Ffmpeg::getFramesFromMovie(int frame) {
QString ffmpegCachePath = getFfmpegCache().getQString();
QString tempPath = ffmpegCachePath + "//" +
- QString::fromStdString(m_path.getName()) +
- QString::fromStdString(m_path.getType());
+ m_path.getQString().remove(QRegExp(QString::fromUtf8(
+ "[-`~!@#$%^&*()_�+=|:;<>��,.?/{}\'\"\\[\\]\\\\]")));
std::string tmpPath = tempPath.toStdString();
QString tempName = "In%04d." + m_intermediateFormat;
tempName = tempPath + tempName;
@@ -399,6 +402,26 @@ void Ffmpeg::getFramesFromMovie(int frame) {
}
}
+int Ffmpeg::getGifFrameCount() {
+ int frame = 1;
+ QString ffmpegCachePath = getFfmpegCache().getQString();
+ QString tempPath = ffmpegCachePath + "//" +
+ QString::fromStdString(m_path.getName()) +
+ QString::fromStdString(m_path.getType());
+ std::string tmpPath = tempPath.toStdString();
+ QString tempName = "In%04d." + m_intermediateFormat;
+ tempName = tempPath + tempName;
+ QString tempStart;
+ tempStart = "In0001." + m_intermediateFormat;
+ tempStart = tempPath + tempStart;
+ while (TSystem::doesExistFileOrLevel(TFilePath(tempStart))) {
+ frame++;
+ QString number = QString("%1").arg(frame, 4, 10, QChar('0'));
+ tempStart = tempPath + "In" + number + "." + m_intermediateFormat;
+ }
+ return frame - 1;
+}
+
void Ffmpeg::addToCleanUp(QString path) {
if (TSystem::doesExistFileOrLevel(TFilePath(path))) {
m_cleanUpList.push_back(path);
diff --git a/toonz/sources/image/ffmpeg/tiio_ffmpeg.h b/toonz/sources/image/ffmpeg/tiio_ffmpeg.h
index 4b3fe4f..853110a 100644
--- a/toonz/sources/image/ffmpeg/tiio_ffmpeg.h
+++ b/toonz/sources/image/ffmpeg/tiio_ffmpeg.h
@@ -41,6 +41,7 @@ public:
TFilePath getFfmpegCache();
ffmpegFileInfo getInfo();
void disablePrecompute();
+ int getGifFrameCount();
private:
QString m_intermediateFormat, m_ffmpegPath, m_audioPath, m_audioFormat;
diff --git a/toonz/sources/image/ffmpeg/tiio_gif.cpp b/toonz/sources/image/ffmpeg/tiio_gif.cpp
index 089461d..0676b91 100644
--- a/toonz/sources/image/ffmpeg/tiio_gif.cpp
+++ b/toonz/sources/image/ffmpeg/tiio_gif.cpp
@@ -3,6 +3,7 @@
#include "tiio_gif.h"
#include "trasterimage.h"
#include "timageinfo.h"
+#include "toonz/stage.h"
#include
//===========================================================
@@ -151,8 +152,9 @@ class TImageReaderGif final : public TImageReader {
public:
int m_frameIndex;
- TImageReaderGif(const TFilePath &path, int index, TLevelReaderGif *lra)
- : TImageReader(path), m_lra(lra), m_frameIndex(index) {
+ TImageReaderGif(const TFilePath &path, int index, TLevelReaderGif *lra,
+ TImageInfo *info)
+ : TImageReader(path), m_lra(lra), m_frameIndex(index), m_info(info) {
m_lra->addRef();
}
~TImageReaderGif() { m_lra->release(); }
@@ -160,9 +162,11 @@ public:
TImageP load() override { return m_lra->load(m_frameIndex); }
TDimension getSize() const { return m_lra->getSize(); }
TRect getBBox() const { return TRect(); }
+ const TImageInfo *getImageInfo() const override { return m_info; }
private:
TLevelReaderGif *m_lra;
+ TImageInfo *m_info;
// not implemented
TImageReaderGif(const TImageReaderGif &);
@@ -190,7 +194,7 @@ TLevelReaderGif::TLevelReaderGif(const TFilePath &path)
m_ly = m_size.ly;
ffmpegReader->getFramesFromMovie();
-
+ m_frameCount = ffmpegReader->getGifFrameCount();
// set values
m_info = new TImageInfo();
m_info->m_frameRate = fps;
@@ -198,6 +202,8 @@ TLevelReaderGif::TLevelReaderGif(const TFilePath &path)
m_info->m_ly = m_ly;
m_info->m_bitsPerSample = 8;
m_info->m_samplePerPixel = 4;
+ m_info->m_dpix = Stage::standardDpi;
+ m_info->m_dpiy = Stage::standardDpi;
}
//-----------------------------------------------------------
@@ -220,9 +226,8 @@ TImageReaderP TLevelReaderGif::getFrameReader(TFrameId fid) {
// if (IOError != 0)
// throw TImageException(m_path, buildAVIExceptionString(IOError));
if (fid.getLetter() != 0) return TImageReaderP(0);
- int index = fid.getNumber();
-
- TImageReaderGif *irm = new TImageReaderGif(m_path, index, this);
+ int index = fid.getNumber();
+ TImageReaderGif *irm = new TImageReaderGif(m_path, index, this, m_info);
return TImageReaderP(irm);
}
diff --git a/toonz/sources/image/ffmpeg/tiio_mp4.cpp b/toonz/sources/image/ffmpeg/tiio_mp4.cpp
index fb7d9a1..1e83e1a 100644
--- a/toonz/sources/image/ffmpeg/tiio_mp4.cpp
+++ b/toonz/sources/image/ffmpeg/tiio_mp4.cpp
@@ -4,6 +4,7 @@
#include "trasterimage.h"
#include "timageinfo.h"
#include "tsound.h"
+#include "toonz/stage.h"
#include
//===========================================================
@@ -38,11 +39,16 @@ private:
TLevelWriterMp4::TLevelWriterMp4(const TFilePath &path, TPropertyGroup *winfo)
: TLevelWriter(path, winfo) {
if (!m_properties) m_properties = new Tiio::Mp4WriterProperties();
- std::string scale = m_properties->getProperty("Scale")->getValueAsString();
- m_scale = QString::fromStdString(scale).toInt();
- std::string quality =
- m_properties->getProperty("Quality")->getValueAsString();
- m_vidQuality = QString::fromStdString(quality).toInt();
+ if (m_properties->getPropertyCount() == 0) {
+ m_scale = 100;
+ m_vidQuality = 100;
+ } else {
+ std::string scale = m_properties->getProperty("Scale")->getValueAsString();
+ m_scale = QString::fromStdString(scale).toInt();
+ std::string quality =
+ m_properties->getProperty("Quality")->getValueAsString();
+ m_vidQuality = QString::fromStdString(quality).toInt();
+ }
ffmpegWriter = new Ffmpeg();
ffmpegWriter->setPath(m_path);
if (TSystem::doesExistFileOrLevel(m_path)) TSystem::deleteFile(m_path);
@@ -129,8 +135,9 @@ class TImageReaderMp4 final : public TImageReader {
public:
int m_frameIndex;
- TImageReaderMp4(const TFilePath &path, int index, TLevelReaderMp4 *lra)
- : TImageReader(path), m_lra(lra), m_frameIndex(index) {
+ TImageReaderMp4(const TFilePath &path, int index, TLevelReaderMp4 *lra,
+ TImageInfo *info)
+ : TImageReader(path), m_lra(lra), m_frameIndex(index), m_info(info) {
m_lra->addRef();
}
~TImageReaderMp4() { m_lra->release(); }
@@ -138,9 +145,11 @@ public:
TImageP load() override { return m_lra->load(m_frameIndex); }
TDimension getSize() const { return m_lra->getSize(); }
TRect getBBox() const { return TRect(); }
+ const TImageInfo *getImageInfo() const override { return m_info; }
private:
TLevelReaderMp4 *m_lra;
+ TImageInfo *m_info;
// not implemented
TImageReaderMp4(const TImageReaderMp4 &);
@@ -173,6 +182,8 @@ TLevelReaderMp4::TLevelReaderMp4(const TFilePath &path) : TLevelReader(path) {
m_info->m_ly = m_ly;
m_info->m_bitsPerSample = 8;
m_info->m_samplePerPixel = 4;
+ m_info->m_dpix = Stage::standardDpi;
+ m_info->m_dpiy = Stage::standardDpi;
}
//-----------------------------------------------------------
@@ -197,7 +208,7 @@ TImageReaderP TLevelReaderMp4::getFrameReader(TFrameId fid) {
if (fid.getLetter() != 0) return TImageReaderP(0);
int index = fid.getNumber();
- TImageReaderMp4 *irm = new TImageReaderMp4(m_path, index, this);
+ TImageReaderMp4 *irm = new TImageReaderMp4(m_path, index, this, m_info);
return TImageReaderP(irm);
}
diff --git a/toonz/sources/image/ffmpeg/tiio_webm.cpp b/toonz/sources/image/ffmpeg/tiio_webm.cpp
index 0d9e2b2..d780061 100644
--- a/toonz/sources/image/ffmpeg/tiio_webm.cpp
+++ b/toonz/sources/image/ffmpeg/tiio_webm.cpp
@@ -4,6 +4,7 @@
#include "trasterimage.h"
#include "tsound.h"
#include "timageinfo.h"
+#include "toonz/stage.h"
#include
//===========================================================
@@ -133,8 +134,9 @@ class TImageReaderWebm final : public TImageReader {
public:
int m_frameIndex;
- TImageReaderWebm(const TFilePath &path, int index, TLevelReaderWebm *lra)
- : TImageReader(path), m_lra(lra), m_frameIndex(index) {
+ TImageReaderWebm(const TFilePath &path, int index, TLevelReaderWebm *lra,
+ TImageInfo *info)
+ : TImageReader(path), m_lra(lra), m_frameIndex(index), m_info(info) {
m_lra->addRef();
}
~TImageReaderWebm() { m_lra->release(); }
@@ -142,9 +144,11 @@ public:
TImageP load() override { return m_lra->load(m_frameIndex); }
TDimension getSize() const { return m_lra->getSize(); }
TRect getBBox() const { return TRect(); }
+ const TImageInfo *getImageInfo() const override { return m_info; }
private:
TLevelReaderWebm *m_lra;
+ TImageInfo *m_info;
// not implemented
TImageReaderWebm(const TImageReaderWebm &);
@@ -177,6 +181,8 @@ TLevelReaderWebm::TLevelReaderWebm(const TFilePath &path) : TLevelReader(path) {
m_info->m_ly = m_ly;
m_info->m_bitsPerSample = 8;
m_info->m_samplePerPixel = 4;
+ m_info->m_dpix = Stage::standardDpi;
+ m_info->m_dpiy = Stage::standardDpi;
}
//-----------------------------------------------------------
@@ -201,7 +207,7 @@ TImageReaderP TLevelReaderWebm::getFrameReader(TFrameId fid) {
if (fid.getLetter() != 0) return TImageReaderP(0);
int index = fid.getNumber();
- TImageReaderWebm *irm = new TImageReaderWebm(m_path, index, this);
+ TImageReaderWebm *irm = new TImageReaderWebm(m_path, index, this, m_info);
return TImageReaderP(irm);
}
diff --git a/toonz/sources/include/tcolorstyles.h b/toonz/sources/include/tcolorstyles.h
index 1b999e7..2aecdad 100644
--- a/toonz/sources/include/tcolorstyles.h
+++ b/toonz/sources/include/tcolorstyles.h
@@ -118,6 +118,9 @@ private:
// This flag will be set when the
//! style is edited from the original one.
+ TPoint m_pickedPosition; // picked position from color model by using style
+ // picker tool with "organize palette" option.
+
protected:
TRaster32P m_icon; //!< Icon shown on TPalette viewers.
bool m_validIcon; //!< Icon's validity status.
@@ -212,6 +215,9 @@ The \a global name contains information about palette id.
m_flags = flags;
} //!< Returns color attributes.
+ void setPickedPosition(const TPoint &pos) { m_pickedPosition = pos; }
+ TPoint getPickedPosition() const { return m_pickedPosition; }
+
// Color-related functions
/*! \detail
diff --git a/toonz/sources/include/tfilepath.h b/toonz/sources/include/tfilepath.h
index ee04a45..0d58b5a 100644
--- a/toonz/sources/include/tfilepath.h
+++ b/toonz/sources/include/tfilepath.h
@@ -177,7 +177,7 @@ If the path is ":" a slash will be added*/
TFilePath getParentDir() const; // noSlash!;
TFrameId getFrame() const;
-
+ bool isFfmpegType() const;
bool isLevelName()
const; //{return getFrame() == TFrameId(TFrameId::EMPTY_FRAME);};
bool isAbsolute() const;
diff --git a/toonz/sources/include/tools/cursors.h b/toonz/sources/include/tools/cursors.h
index a912ffa..16eec82 100644
--- a/toonz/sources/include/tools/cursors.h
+++ b/toonz/sources/include/tools/cursors.h
@@ -66,6 +66,8 @@ enum {
PickerCursorWhite,
PickerCursorWhiteLine,
PickerCursorWhiteArea,
+ PickerCursorOrganize,
+ PickerCursorWhiteOrganize,
PickerRGB,
PickerRGBWhite,
diff --git a/toonz/sources/include/tools/tooloptions.h b/toonz/sources/include/tools/tooloptions.h
index b06a86d..abded96 100644
--- a/toonz/sources/include/tools/tooloptions.h
+++ b/toonz/sources/include/tools/tooloptions.h
@@ -647,7 +647,9 @@ public slots:
void onToolChanged();
void onStageObjectChange();
- // signals:
+signals:
+ // used in ComboViewer to handle Tab focus
+ void newPanelCreated();
// void toolOptionChange();
};
diff --git a/toonz/sources/include/toonz/Naa2TlvConverter.h b/toonz/sources/include/toonz/Naa2TlvConverter.h
index efe5765..e15fd38 100644
--- a/toonz/sources/include/toonz/Naa2TlvConverter.h
+++ b/toonz/sources/include/toonz/Naa2TlvConverter.h
@@ -146,7 +146,8 @@ public:
return -1;
}
- TToonzImageP makeTlv(bool transparentSyntheticInks);
+ TToonzImageP makeTlv(bool transparentSyntheticInks,
+ bool removeUnusedStyles = false);
TVectorImageP vectorize(const TToonzImageP &ti);
TVectorImageP vectorize(const TRaster32P &ras);
diff --git a/toonz/sources/include/toonz/palettecmd.h b/toonz/sources/include/toonz/palettecmd.h
index bca5440..ada5ee4 100644
--- a/toonz/sources/include/toonz/palettecmd.h
+++ b/toonz/sources/include/toonz/palettecmd.h
@@ -88,6 +88,17 @@ DVAPI void renamePalettePage(TPaletteHandle *paletteHandle, int pageIndex,
DVAPI void renamePaletteStyle(TPaletteHandle *paletteHandle,
const std::wstring &newName);
+/* called in ColorModelViewer::pick() - move selected style to the first page */
+DVAPI void organizePaletteStyle(TPaletteHandle *paletteHandle, int styleId,
+ const TPoint &point);
+
+/*
+called in ColorModelViewer::repickFromColorModel().
+Pick color from the img for all styles with "picked position" value.
+*/
+DVAPI void pickColorByUsingPickedPosition(TPaletteHandle *paletteHandle,
+ TImageP img);
+
} // namespace
#endif
diff --git a/toonz/sources/include/toonz/preferences.h b/toonz/sources/include/toonz/preferences.h
index 7b8c6e4..4e3e30d 100644
--- a/toonz/sources/include/toonz/preferences.h
+++ b/toonz/sources/include/toonz/preferences.h
@@ -99,6 +99,14 @@ public:
void setAutosavePeriod(int minutes);
int getAutosavePeriod() const { return m_autosavePeriod; } // minutes
+ void enableAutosaveScene(bool on);
+ bool isAutosaveSceneEnabled() const { return m_autosaveSceneEnabled; }
+
+ void enableAutosaveOtherFiles(bool on);
+ bool isAutosaveOtherFilesEnabled() const {
+ return m_autosaveOtherFilesEnabled;
+ }
+
void enableLevelsBackup(bool enabled);
bool isLevelsBackupEnabled() const { return m_levelsBackupEnabled; }
@@ -110,6 +118,9 @@ public:
return m_replaceAfterSaveLevelAs;
}
+ void enableStartupPopup(bool on);
+ bool isStartupPopupEnabled() { return m_startupPopupEnabled; }
+
void setProjectRoot(int index);
int getProjectRoot() { return m_projectRoot; }
@@ -296,6 +307,11 @@ public:
return m_multiLayerStylePickerEnabled;
}
+ void enableUseNumpadForSwitchingStyles(bool on);
+ bool isUseNumpadForSwitchingStylesEnabled() const {
+ return m_useNumpadForSwitchingStyles;
+ }
+
// Xsheet tab
void setXsheetStep(int step); //!< Sets the step used for the next/prev
@@ -395,7 +411,8 @@ public:
bool getPrecompute() { return m_precompute; }
void setFfmpegTimeout(int seconds);
int getFfmpegTimeout() { return m_ffmpegTimeout; }
-
+ void setFastRenderPath(std::string path);
+ QString getFastRenderPath() const { return m_fastRenderPath; }
// Uncategorized - internals
void setAskForOverrideRender(bool on);
@@ -407,6 +424,9 @@ public:
int getTextureSize() const { return m_textureSize; }
bool useDrawPixel() { return m_textureSize == 0; }
+ void setShortcutPreset(std::string preset);
+ QString getShortcutPreset() { return m_shortcutPreset; }
+
int getShmMax() const {
return m_shmmax;
} //! \sa The \p sysctl unix command.
@@ -434,7 +454,9 @@ private:
std::vector m_levelFormats;
QString m_units, m_cameraUnits, m_scanLevelType, m_currentRoomChoice,
- m_oldUnits, m_oldCameraUnits, m_ffmpegPath, m_customProjectRoot;
+ m_oldUnits, m_oldCameraUnits, m_ffmpegPath, m_shortcutPreset,
+ m_customProjectRoot;
+ QString m_fastRenderPath;
double m_defLevelWidth, m_defLevelHeight, m_defLevelDpi;
@@ -457,11 +479,13 @@ private:
m_generatedMovieViewEnabled, m_xsheetAutopanEnabled,
m_ignoreAlphaonColumn1Enabled, m_previewAlwaysOpenNewFlipEnabled,
m_rewindAfterPlaybackEnabled, m_fitToFlipbookEnabled, m_autosaveEnabled,
+ m_autosaveSceneEnabled, m_autosaveOtherFilesEnabled,
m_defaultViewerEnabled, m_pixelsOnly;
bool m_rasterOptimizedMemory, m_saveUnpaintedInCleanup,
m_askForOverrideRender, m_automaticSVNFolderRefreshEnabled, m_SVNEnabled,
m_levelsBackupEnabled, m_minimizeSaveboxAfterEditing,
- m_sceneNumberingEnabled, m_animationSheetEnabled, m_inksOnly;
+ m_sceneNumberingEnabled, m_animationSheetEnabled, m_inksOnly,
+ m_startupPopupEnabled;
bool m_fillOnlySavebox, m_show0ThickLines, m_regionAntialias;
bool m_onionSkinDuringPlayback;
TPixel32 m_viewerBGColor, m_previewBGColor, m_chessboardColor1,
@@ -499,6 +523,8 @@ private:
std::string m_layerNameEncoding = "SJIS"; // Fixed to SJIS for now. You can
// add interface if you wanna
// change encoding.
+ // whether to use numpad and tab key shortcut for selecting styles
+ bool m_useNumpadForSwitchingStyles;
private:
Preferences();
diff --git a/toonz/sources/include/toonz/tproject.h b/toonz/sources/include/toonz/tproject.h
index 399f5f6..0898213 100644
--- a/toonz/sources/include/toonz/tproject.h
+++ b/toonz/sources/include/toonz/tproject.h
@@ -57,7 +57,7 @@ public:
bool isConstantFolder(int index) const;
TFilePath getFolder(int index) const;
- TFilePath getFolder(std::string name) const;
+ TFilePath getFolder(std::string name, bool absolute = false) const;
TFilePath getScenesPath() const;
diff --git a/toonz/sources/include/toonz/tscenehandle.h b/toonz/sources/include/toonz/tscenehandle.h
index bc8ded5..75ad8cf 100644
--- a/toonz/sources/include/toonz/tscenehandle.h
+++ b/toonz/sources/include/toonz/tscenehandle.h
@@ -52,7 +52,9 @@ public:
}
void notifyNameSceneChange() { emit nameSceneChanged(); }
- void notifyPreferenceChanged() { emit preferenceChanged(); }
+ void notifyPreferenceChanged(const QString &prefName) {
+ emit preferenceChanged(prefName);
+ }
void notifyPixelUnitSelected(bool on) { emit pixelUnitSelected(on); }
@@ -76,7 +78,7 @@ signals:
void castChanged();
void castFolderAdded(const TFilePath &path);
void nameSceneChanged();
- void preferenceChanged();
+ void preferenceChanged(const QString &prefName);
void pixelUnitSelected(bool on);
};
diff --git a/toonz/sources/include/toonzqt/camerasettingswidget.h b/toonz/sources/include/toonzqt/camerasettingswidget.h
index 18fc23b..1b2a995 100644
--- a/toonz/sources/include/toonzqt/camerasettingswidget.h
+++ b/toonz/sources/include/toonzqt/camerasettingswidget.h
@@ -71,6 +71,7 @@ protected:
//---------------------------------------------------------------
class DVAPI CameraSettingsWidget final : public QFrame {
+ friend class StartupPopup;
Q_OBJECT
bool m_forCleanup;
diff --git a/toonz/sources/include/toonzqt/dvdialog.h b/toonz/sources/include/toonzqt/dvdialog.h
index b61e366..6184bf5 100644
--- a/toonz/sources/include/toonzqt/dvdialog.h
+++ b/toonz/sources/include/toonzqt/dvdialog.h
@@ -58,10 +58,11 @@ void DVAPI MsgBoxInPopup(MsgType type, const QString &text);
// ATTENZIONE: Valore di ritorno
// 0 = l'utente ha chiuso la finestra (dovrebbe corrispondere ad un cancel o ad
-// un NO)
-// 1 = primo bottone da sx premuto
-// 2 = secondo bottone da sx premuto
-// 3 = terzo bottone da sx premuto
+// un NO) - closed window
+// 1 = primo bottone da sx premuto - first button selected
+// 2 = secondo bottone da sx premuto - second button
+// 3 = terzo bottone da sx premuto - third button
+// 4 = fourth button
int DVAPI MsgBox(MsgType type, const QString &text,
const std::vector &buttons,
@@ -77,6 +78,12 @@ int DVAPI MsgBox(const QString &text, const QString &button1,
const QString &button2, const QString &button3,
int defaultButtonIndex = 0, QWidget *parent = 0);
+// QUESTION: four botton user defined
+int DVAPI MsgBox(const QString &text, const QString &button1,
+ const QString &button2, const QString &button3,
+ const QString &button4, int defaultButtonIndex = 0,
+ QWidget *parent = 0);
+
Dialog DVAPI *createMsgBox(MsgType type, const QString &text,
const QStringList &buttons, int defaultButtonIndex,
QWidget *parent = 0);
@@ -229,6 +236,8 @@ public:
void addButtonBarWidget(QWidget *widget);
void addButtonBarWidget(QWidget *first, QWidget *second);
void addButtonBarWidget(QWidget *first, QWidget *second, QWidget *third);
+ void addButtonBarWidget(QWidget *first, QWidget *second, QWidget *third,
+ QWidget *fourth);
void hideEvent(QHideEvent *event) override;
diff --git a/toonz/sources/include/toonzqt/filefield.h b/toonz/sources/include/toonzqt/filefield.h
index f5a65f8..944f2d1 100644
--- a/toonz/sources/include/toonzqt/filefield.h
+++ b/toonz/sources/include/toonzqt/filefield.h
@@ -53,6 +53,8 @@ class DVAPI FileField : public QWidget {
QStringList m_filters;
QFileDialog::FileMode m_fileMode;
QString m_windowTitle;
+ QString m_descriptionText; // if the initial text is not path, set the string
+ // here and prevent browsing
protected: // used in the child class for CleanupSettings
QPushButton *m_fileBrowseButton;
@@ -73,7 +75,7 @@ public:
static BrowserPopupController *m_browserPopupController;
FileField(QWidget *parent = 0, QString path = QString(),
- bool readOnly = false);
+ bool readOnly = false, bool doNotBrowseInitialPath = false);
~FileField() {}
/*! Set what the user may select in the file dialog:
diff --git a/toonz/sources/include/toonzqt/flipconsole.h b/toonz/sources/include/toonzqt/flipconsole.h
index f7d54e6..93e493f 100644
--- a/toonz/sources/include/toonzqt/flipconsole.h
+++ b/toonz/sources/include/toonzqt/flipconsole.h
@@ -214,7 +214,8 @@ public:
eFilledRaster = 0x4000000, // Used only in LineTest
eDefineLoadBox = 0x8000000,
eUseLoadBox = 0x10000000,
- eEnd = 0x20000000
+ eLocator = 0x20000000,
+ eEnd = 0x40000000
};
static const UINT cFullConsole = eEnd - 1;
@@ -249,6 +250,7 @@ public:
void enableButton(UINT button, bool enable, bool doShowHide = true);
void showCurrentFrame();
int getCurrentFrame() const { return m_currentFrame; }
+ int getCurrentFps() const { return m_fps; }
void setChecked(UINT button, bool state);
bool isChecked(UINT button) const;
void setCurrentFrame(int frame, bool forceResetting = false);
diff --git a/toonz/sources/include/toonzqt/imageutils.h b/toonz/sources/include/toonzqt/imageutils.h
index 357706d..6c73ebe 100644
--- a/toonz/sources/include/toonzqt/imageutils.h
+++ b/toonz/sources/include/toonzqt/imageutils.h
@@ -111,8 +111,10 @@ void DVAPI convertNaa2Tlv(
FrameTaskNotifier
*frameNotifier, //!< Observer class for frame success notifications.
TPalette *palette =
- 0); //!< Special conversion function from an antialiased level to tlv.
- //! \sa Function ImageUtils::convert().
+ 0, //!< Special conversion function from an antialiased level to tlv.
+ //! \sa Function ImageUtils::convert().
+ bool removeUnusedStyles =
+ false); //! Remove unused styles from input palette.
double DVAPI getQuantizedZoomFactor(double zf, bool forward);
diff --git a/toonz/sources/include/toonzqt/menubarcommand.h b/toonz/sources/include/toonzqt/menubarcommand.h
index 869b1be..b1b677b 100644
--- a/toonz/sources/include/toonzqt/menubarcommand.h
+++ b/toonz/sources/include/toonzqt/menubarcommand.h
@@ -145,7 +145,8 @@ public:
std::string getShortcutFromId(CommandId id);
int getKeyFromShortcut(const std::string &shortcut);
int getKeyFromId(CommandId id);
- void setShortcut(QAction *action, std::string shortcutString);
+ void setShortcut(QAction *action, std::string shortcutString,
+ bool keepDefault = true);
QAction *getAction(CommandId id, bool createIfNeeded = false);
diff --git a/toonz/sources/include/toonzqt/paletteviewergui.h b/toonz/sources/include/toonzqt/paletteviewergui.h
index 390722c..e853458 100644
--- a/toonz/sources/include/toonzqt/paletteviewergui.h
+++ b/toonz/sources/include/toonzqt/paletteviewergui.h
@@ -199,11 +199,7 @@ protected:
void zoomInChip();
void zoomOutChip();
-protected slots:
-
- void toggleLink();
- void eraseToggleLink();
- void removeLink();
+ bool hasShortcut(int indexInPage);
private:
DVGui::LineEdit *m_renameTextField;
diff --git a/toonz/sources/include/toonzqt/selectioncommandids.h b/toonz/sources/include/toonzqt/selectioncommandids.h
index 0dd6b73..99ebe5e 100644
--- a/toonz/sources/include/toonzqt/selectioncommandids.h
+++ b/toonz/sources/include/toonzqt/selectioncommandids.h
@@ -12,6 +12,8 @@
#define MI_PasteColors "MI_PasteColors"
#define MI_PasteNames "MI_PasteNames"
#define MI_GetColorFromStudioPalette "MI_GetColorFromStudioPalette"
+#define MI_ToggleLinkToStudioPalette "MI_ToggleLinkToStudioPalette"
+#define MI_RemoveReferenceToStudioPalette "MI_RemoveReferenceToStudioPalette"
#define MI_Clear "MI_Clear"
#define MI_SelectAll "MI_SelectAll"
#define MI_InvertSelection "MI_InvertSelection"
diff --git a/toonz/sources/include/toonzqt/styleselection.h b/toonz/sources/include/toonzqt/styleselection.h
index fb78637..6e5099e 100644
--- a/toonz/sources/include/toonzqt/styleselection.h
+++ b/toonz/sources/include/toonzqt/styleselection.h
@@ -95,9 +95,11 @@ public:
void toggleKeyframe(int frame);
// remove link from the studio palette (if linked)
- bool removeLink();
+ void removeLink();
// get back the style from the studio palette (if linked)
void getBackOriginalStyle();
+ // return true if there is at least one linked style in the selection
+ bool hasLinkedStyle();
};
#endif // STYLESELECTION_INCLUDED
diff --git a/toonz/sources/include/tpalette.h b/toonz/sources/include/tpalette.h
index bf16794..e883e6d 100644
--- a/toonz/sources/include/tpalette.h
+++ b/toonz/sources/include/tpalette.h
@@ -211,6 +211,9 @@ private:
//! The confirmation dialog will not be opened unless the palette is edited
//! again,
//! even if the palette's dirtyflag is true.
+
+ int m_shortcutScopeIndex;
+
public:
TPalette();
~TPalette();
@@ -417,6 +420,11 @@ between RGBA color components.
m_isLocked = lock;
}
+ bool hasPickedPosStyle(); // Returns true if there is at least one style with
+ // picked pos value
+
+ void nextShortcutScope(bool invert);
+
public:
// Deprecated functions
diff --git a/toonz/sources/tnztools/CMakeLists.txt b/toonz/sources/tnztools/CMakeLists.txt
index b3d5525..c597e31 100644
--- a/toonz/sources/tnztools/CMakeLists.txt
+++ b/toonz/sources/tnztools/CMakeLists.txt
@@ -11,6 +11,7 @@ set(MOC_HEADERS
../include/tools/screenpicker.h
rgbpickertool.h
rulertool.h
+ stylepickertool.h
)
set(HEADERS ${MOC_HEADERS}
diff --git a/toonz/sources/tnztools/Resources/picker_style_organize.png b/toonz/sources/tnztools/Resources/picker_style_organize.png
new file mode 100644
index 0000000..c502b37
Binary files /dev/null and b/toonz/sources/tnztools/Resources/picker_style_organize.png differ
diff --git a/toonz/sources/tnztools/Resources/picker_style_white_organize.png b/toonz/sources/tnztools/Resources/picker_style_white_organize.png
new file mode 100644
index 0000000..b905466
Binary files /dev/null and b/toonz/sources/tnztools/Resources/picker_style_white_organize.png differ
diff --git a/toonz/sources/tnztools/brushtool.cpp b/toonz/sources/tnztools/brushtool.cpp
index 3272da2..1585aa8 100644
--- a/toonz/sources/tnztools/brushtool.cpp
+++ b/toonz/sources/tnztools/brushtool.cpp
@@ -45,7 +45,7 @@ using namespace ToolUtils;
TEnv::DoubleVar VectorBrushMinSize("InknpaintVectorBrushMinSize", 1);
TEnv::DoubleVar VectorBrushMaxSize("InknpaintVectorBrushMaxSize", 5);
-TEnv::IntVar VectorCapStyle("InknpaintVectorCapStyle", 0);
+TEnv::IntVar VectorCapStyle("InknpaintVectorCapStyle", 1);
TEnv::IntVar VectorJoinStyle("InknpaintVectorJoinStyle", 0);
TEnv::IntVar VectorMiterValue("InknpaintVectorMiterValue", 4);
TEnv::DoubleVar RasterBrushMinSize("InknpaintRasterBrushMinSize", 1);
diff --git a/toonz/sources/tnztools/cursormanager.cpp b/toonz/sources/tnztools/cursormanager.cpp
index 126610f..323ba47 100644
--- a/toonz/sources/tnztools/cursormanager.cpp
+++ b/toonz/sources/tnztools/cursormanager.cpp
@@ -73,6 +73,9 @@ const struct {
{ToolCursor::PickerCursorWhiteLine, "picker_style_white_line", 7, 22},
{ToolCursor::PickerCursorWhiteArea, "picker_style_white_area", 7, 22},
{ToolCursor::PickerCursorWhite, "picker_style_white", 7, 22},
+ {ToolCursor::PickerCursorOrganize, "picker_style_organize", 7, 22},
+ {ToolCursor::PickerCursorWhiteOrganize, "picker_style_white_organize", 7,
+ 22},
{ToolCursor::PickerRGB, "picker_rgb", 7, 22},
{ToolCursor::PickerRGBWhite, "picker_rgb_white", 7, 22},
{ToolCursor::FillCursorF, "fill_f", 6, 23},
diff --git a/toonz/sources/tnztools/stylepickertool.cpp b/toonz/sources/tnztools/stylepickertool.cpp
index e73625c..4c21641 100644
--- a/toonz/sources/tnztools/stylepickertool.cpp
+++ b/toonz/sources/tnztools/stylepickertool.cpp
@@ -1,238 +1,307 @@
+#include "stylepickertool.h"
-
+// TnzTools includes
#include "tools/tool.h"
#include "tools/cursors.h"
#include "tools/stylepicker.h"
-#include "toonz/txshsimplelevel.h"
-#include "toonz/txshlevelhandle.h"
+#include "tools/toolhandle.h"
-#include "drawutil.h"
-#include "tvectorimage.h"
-#include "ttoonzimage.h"
-#include "tundo.h"
+// TnzQt includes
+#include "toonzqt/tselectionhandle.h"
+#include "toonzqt/styleselection.h"
+// TnzLib includes
+#include "toonz/txshsimplelevel.h"
+#include "toonz/txshlevelhandle.h"
#include "toonz/tpalettehandle.h"
-
#include "toonz/stage2.h"
-#include "tproperty.h"
-#include "toonzqt/tselectionhandle.h"
-#include "toonzqt/styleselection.h"
-#include "tools/toolhandle.h"
#include "toonz/tframehandle.h"
#include "toonz/txsheethandle.h"
#include "toonz/preferences.h"
#include "toonz/tcolumnhandle.h"
#include "toonz/dpiscale.h"
#include "toonz/palettecontroller.h"
+#include "toonz/txshleveltypes.h"
+#include "toonz/txshpalettelevel.h"
+
+// TnzCore includes
+#include "drawutil.h"
+#include "tvectorimage.h"
+#include "ttoonzimage.h"
+#include "tundo.h"
+#include "tmsgcore.h"
#define LINES L"Lines"
#define AREAS L"Areas"
#define ALL L"Lines & Areas"
-namespace {
-
//========================================================================
// Pick Style Tool
//------------------------------------------------------------------------
-class StylePickerTool final : public TTool {
- int m_oldStyleId, m_currentStyleId;
-
- TEnumProperty m_colorType;
- TPropertyGroup m_prop;
-
- TBoolProperty m_passivePick;
+StylePickerTool::StylePickerTool()
+ : TTool("T_StylePicker")
+ , m_currentStyleId(0)
+ , m_colorType("Mode:")
+ , m_passivePick("Passive Pick", false)
+ , m_organizePalette("Organize Palette", false)
+ , m_paletteToBeOrganized(NULL) {
+ m_prop.bind(m_colorType);
+ m_colorType.addValue(AREAS);
+ m_colorType.addValue(LINES);
+ m_colorType.addValue(ALL);
+ m_colorType.setId("Mode");
+ bind(TTool::CommonLevels);
+
+ m_prop.bind(m_passivePick);
+ m_passivePick.setId("PassivePick");
+
+ m_prop.bind(m_organizePalette);
+ m_organizePalette.setId("OrganizePalette");
+}
-public:
- TPropertyGroup *getProperties(int targetType) override { return &m_prop; }
+void StylePickerTool::leftButtonDown(const TPointD &pos, const TMouseEvent &e) {
+ m_oldStyleId = m_currentStyleId =
+ getApplication()->getCurrentLevelStyleIndex();
+ pick(pos, e);
+}
- StylePickerTool()
- : TTool("T_StylePicker")
- , m_currentStyleId(0)
- , m_colorType("Mode:")
- , m_passivePick("Passive Pick", false) {
- m_prop.bind(m_colorType);
- m_colorType.addValue(AREAS);
- m_colorType.addValue(LINES);
- m_colorType.addValue(ALL);
- m_colorType.setId("Mode");
- bind(TTool::CommonLevels);
+void StylePickerTool::leftButtonDrag(const TPointD &pos, const TMouseEvent &e) {
+ pick(pos, e);
+}
- m_prop.bind(m_passivePick);
- m_passivePick.setId("PassivePick");
+void StylePickerTool::pick(const TPointD &pos, const TMouseEvent &e) {
+ // Area = 0, Line = 1, All = 2
+ int modeValue = m_colorType.getIndex();
+
+ //------------------------------------
+ // MultiLayerStylePicker
+ /*---
+ PickしたStyleId = 0、かつ
+ Preference で MultiLayerStylePickerが有効、かつ
+ Scene編集モード、かつ
+ 下のカラムから拾った色がTransparentでない場合、
+ → カレントLevelを移動する。
+ ---*/
+ if (Preferences::instance()->isMultiLayerStylePickerEnabled() &&
+ getApplication()->getCurrentFrame()->isEditingScene()) {
+ int superPickedColumnId = getViewer()->posToColumnIndex(
+ e.m_pos, getPixelSize() * getPixelSize(), false);
+
+ if (superPickedColumnId >= 0 /*-- 何かColumnに当たった場合 --*/
+ &&
+ getApplication()->getCurrentColumn()->getColumnIndex() !=
+ superPickedColumnId) /*-- かつ、Current Columnでない場合 --*/
+ {
+ /*-- そのColumnからPickを試みる --*/
+ int currentFrame = getApplication()->getCurrentFrame()->getFrame();
+ TXshCell pickedCell =
+ getApplication()->getCurrentXsheet()->getXsheet()->getCell(
+ currentFrame, superPickedColumnId);
+ TImageP pickedImage = pickedCell.getImage(false).getPointer();
+ TToonzImageP picked_ti = pickedImage;
+ TVectorImageP picked_vi = pickedImage;
+ TXshSimpleLevel *picked_level = pickedCell.getSimpleLevel();
+ if ((picked_ti || picked_vi) && picked_level) {
+ TPointD tmpMousePosition = getColumnMatrix(superPickedColumnId).inv() *
+ getViewer()->winToWorld(e.m_pos);
+
+ TPointD tmpDpiScale = getCurrentDpiScale(picked_level, getCurrentFid());
+
+ tmpMousePosition.x /= tmpDpiScale.x;
+ tmpMousePosition.y /= tmpDpiScale.y;
+
+ StylePicker superPicker(pickedImage);
+ int picked_subsampling =
+ picked_level->getImageSubsampling(pickedCell.getFrameId());
+ int superPicked_StyleId = superPicker.pickStyleId(
+ TScale(1.0 / picked_subsampling) * tmpMousePosition +
+ TPointD(-0.5, -0.5),
+ getPixelSize() * getPixelSize(), modeValue);
+ /*-- 何かStyleが拾えて、Transparentでない場合 --*/
+ if (superPicked_StyleId > 0) {
+ /*-- Levelの移動 --*/
+ getApplication()->getCurrentLevel()->setLevel(picked_level);
+ /*-- Columnの移動 --*/
+ getApplication()->getCurrentColumn()->setColumnIndex(
+ superPickedColumnId);
+ /*-- 選択の解除 --*/
+ if (getApplication()->getCurrentSelection()->getSelection())
+ getApplication()
+ ->getCurrentSelection()
+ ->getSelection()
+ ->selectNone();
+ /*-- StyleIdの移動 --*/
+ getApplication()->setCurrentLevelStyleIndex(superPicked_StyleId);
+ return;
+ }
+ }
+ }
+ }
+ /*-- MultiLayerStylePicker ここまで --*/
+ //------------------------------------
+ TImageP image = getImage(false);
+ TToonzImageP ti = image;
+ TVectorImageP vi = image;
+ TXshSimpleLevel *level =
+ getApplication()->getCurrentLevel()->getSimpleLevel();
+ if ((!ti && !vi) || !level) return;
+
+ /*-- 画面外をpickしても拾えないようにする --*/
+ if (!m_viewer->getGeometry().contains(pos)) return;
+
+ int subsampling = level->getImageSubsampling(getCurrentFid());
+ StylePicker picker(image);
+ int styleId =
+ picker.pickStyleId(TScale(1.0 / subsampling) * pos + TPointD(-0.5, -0.5),
+ getPixelSize() * getPixelSize(), modeValue);
+
+ if (styleId < 0) return;
+
+ if (modeValue == 1) // LINES
+ {
+ /*-- pickLineモードのとき、取得Styleが0の場合はカレントStyleを変えない。
+ * --*/
+ if (styleId == 0) return;
+ /*--
+ * pickLineモードのとき、PurePaintの部分をクリックしてもカレントStyleを変えない
+ * --*/
+ if (ti &&
+ picker.pickTone(TScale(1.0 / subsampling) * pos +
+ TPointD(-0.5, -0.5)) == 255)
+ return;
}
- ToolType getToolType() const override { return TTool::LevelReadTool; }
+ /*--- Styleを選択している場合は選択を解除する ---*/
+ TSelection *selection =
+ TTool::getApplication()->getCurrentSelection()->getSelection();
+ if (selection) {
+ TStyleSelection *styleSelection =
+ dynamic_cast(selection);
+ if (styleSelection) styleSelection->selectNone();
+ }
- void draw() override {}
+ getApplication()->setCurrentLevelStyleIndex(styleId);
+}
- void leftButtonDown(const TPointD &pos, const TMouseEvent &e) override {
- m_oldStyleId = m_currentStyleId =
- getApplication()->getCurrentLevelStyleIndex();
- pick(pos, e);
- }
- void leftButtonDrag(const TPointD &pos, const TMouseEvent &e) override {
- pick(pos, e);
+void StylePickerTool::mouseMove(const TPointD &pos, const TMouseEvent &e) {
+ if (!m_passivePick.getValue()) return;
+ /*--- PassiveにStyleを拾う機能 ---*/
+ PaletteController *controller =
+ TTool::getApplication()->getPaletteController();
+
+ TImageP image = getImage(false);
+ TToonzImageP ti = image;
+ TVectorImageP vi = image;
+ TXshSimpleLevel *level =
+ getApplication()->getCurrentLevel()->getSimpleLevel();
+ if ((!ti && !vi) || !level || !m_viewer->getGeometry().contains(pos)) {
+ controller->notifyStylePassivePicked(-1, -1, -1);
+ return;
}
- void pick(const TPointD &pos, const TMouseEvent &e) {
- // Area = 0, Line = 1, All = 2
- int modeValue = m_colorType.getIndex();
-
- //------------------------------------
- // MultiLayerStylePicker
- /*---
- PickしたStyleId = 0、かつ
- Preference で MultiLayerStylePickerが有効、かつ
- Scene編集モード、かつ
- 下のカラムから拾った色がTransparentでない場合、
- → カレントLevelを移動する。
- ---*/
- if (Preferences::instance()->isMultiLayerStylePickerEnabled() &&
- getApplication()->getCurrentFrame()->isEditingScene()) {
- int superPickedColumnId = getViewer()->posToColumnIndex(
- e.m_pos, getPixelSize() * getPixelSize(), false);
-
- if (superPickedColumnId >= 0 /*-- 何かColumnに当たった場合 --*/
- &&
- getApplication()->getCurrentColumn()->getColumnIndex() !=
- superPickedColumnId) /*-- かつ、Current Columnでない場合 --*/
- {
- /*-- そのColumnからPickを試みる --*/
- int currentFrame = getApplication()->getCurrentFrame()->getFrame();
- TXshCell pickedCell =
- getApplication()->getCurrentXsheet()->getXsheet()->getCell(
- currentFrame, superPickedColumnId);
- TImageP pickedImage = pickedCell.getImage(false).getPointer();
- TToonzImageP picked_ti = pickedImage;
- TVectorImageP picked_vi = pickedImage;
- TXshSimpleLevel *picked_level = pickedCell.getSimpleLevel();
- if ((picked_ti || picked_vi) && picked_level) {
- TPointD tmpMousePosition =
- getColumnMatrix(superPickedColumnId).inv() *
- getViewer()->winToWorld(e.m_pos);
-
- TPointD tmpDpiScale =
- getCurrentDpiScale(picked_level, getCurrentFid());
-
- tmpMousePosition.x /= tmpDpiScale.x;
- tmpMousePosition.y /= tmpDpiScale.y;
-
- StylePicker superPicker(pickedImage);
- int picked_subsampling =
- picked_level->getImageSubsampling(pickedCell.getFrameId());
- int superPicked_StyleId = superPicker.pickStyleId(
- TScale(1.0 / picked_subsampling) * tmpMousePosition +
- TPointD(-0.5, -0.5),
- getPixelSize() * getPixelSize(), modeValue);
- /*-- 何かStyleが拾えて、Transparentでない場合 --*/
- if (superPicked_StyleId > 0) {
- /*-- Levelの移動 --*/
- getApplication()->getCurrentLevel()->setLevel(picked_level);
- /*-- Columnの移動 --*/
- getApplication()->getCurrentColumn()->setColumnIndex(
- superPickedColumnId);
- /*-- 選択の解除 --*/
- if (getApplication()->getCurrentSelection()->getSelection())
- getApplication()
- ->getCurrentSelection()
- ->getSelection()
- ->selectNone();
- /*-- StyleIdの移動 --*/
- getApplication()->setCurrentLevelStyleIndex(superPicked_StyleId);
- return;
- }
- }
- }
- }
- /*-- MultiLayerStylePicker ここまで --*/
- //------------------------------------
- TImageP image = getImage(false);
- TToonzImageP ti = image;
- TVectorImageP vi = image;
- TXshSimpleLevel *level =
- getApplication()->getCurrentLevel()->getSimpleLevel();
- if ((!ti && !vi) || !level) return;
-
- /*-- 画面外をpickしても拾えないようにする --*/
- if (!m_viewer->getGeometry().contains(pos)) return;
-
- int subsampling = level->getImageSubsampling(getCurrentFid());
- StylePicker picker(image);
- int styleId = picker.pickStyleId(
- TScale(1.0 / subsampling) * pos + TPointD(-0.5, -0.5),
- getPixelSize() * getPixelSize(), modeValue);
-
- if (styleId < 0) return;
-
- if (modeValue == 1) // LINES
- {
- /*-- pickLineモードのとき、取得Styleが0の場合はカレントStyleを変えない。
- * --*/
- if (styleId == 0) return;
- /*--
- * pickLineモードのとき、PurePaintの部分をクリックしてもカレントStyleを変えない
- * --*/
- if (ti &&
- picker.pickTone(TScale(1.0 / subsampling) * pos +
- TPointD(-0.5, -0.5)) == 255)
- return;
- }
-
- /*--- Styleを選択している場合は選択を解除する ---*/
- TSelection *selection =
- TTool::getApplication()->getCurrentSelection()->getSelection();
- if (selection) {
- TStyleSelection *styleSelection =
- dynamic_cast(selection);
- if (styleSelection) styleSelection->selectNone();
- }
+ int subsampling = level->getImageSubsampling(getCurrentFid());
+ StylePicker picker(image);
+ TPointD pickPos(TScale(1.0 / subsampling) * pos + TPointD(-0.5, -0.5));
+ int inkStyleId =
+ picker.pickStyleId(pickPos, getPixelSize() * getPixelSize(), 1);
+ int paintStyleId =
+ picker.pickStyleId(pickPos, getPixelSize() * getPixelSize(), 0);
+ int tone = picker.pickTone(pickPos);
+ controller->notifyStylePassivePicked(inkStyleId, paintStyleId, tone);
+}
- getApplication()->setCurrentLevelStyleIndex(styleId);
- }
+int StylePickerTool::getCursorId() const {
+ bool isBlackBG = ToonzCheck::instance()->getChecks() & ToonzCheck::eBlackBg;
+
+ /* in case the "organize palette" option is active */
+ if (m_organizePalette.getValue())
+ return (isBlackBG) ? ToolCursor::PickerCursorWhiteOrganize
+ : ToolCursor::PickerCursorOrganize;
+
+ if (m_colorType.getValue() == LINES)
+ return (isBlackBG) ? ToolCursor::PickerCursorWhiteLine
+ : ToolCursor::PickerCursorLine;
+ else if (m_colorType.getValue() == AREAS)
+ return (isBlackBG) ? ToolCursor::PickerCursorWhiteArea
+ : ToolCursor::PickerCursorArea;
+ else // line&areas
+ return (isBlackBG) ? ToolCursor::PickerCursorWhite
+ : ToolCursor::PickerCursor;
+}
- void mouseMove(const TPointD &pos, const TMouseEvent &e) override {
- if (!m_passivePick.getValue()) return;
- /*--- PassiveにStyleを拾う機能 ---*/
- PaletteController *controller =
- TTool::getApplication()->getPaletteController();
-
- TImageP image = getImage(false);
- TToonzImageP ti = image;
- TVectorImageP vi = image;
- TXshSimpleLevel *level =
- getApplication()->getCurrentLevel()->getSimpleLevel();
- if ((!ti && !vi) || !level || !m_viewer->getGeometry().contains(pos)) {
- controller->notifyStylePassivePicked(-1, -1, -1);
- return;
+bool StylePickerTool::onPropertyChanged(std::string propertyName) {
+ if (propertyName == m_organizePalette.getName()) {
+ if (m_organizePalette.getValue()) {
+ if (!startOrganizePalette()) {
+ m_organizePalette.setValue(false);
+ getApplication()->getCurrentTool()->notifyToolChanged();
+ return false;
+ }
+ } else {
+ std::cout << "End Organize Palette" << std::endl;
+ m_paletteToBeOrganized = NULL;
}
+ }
+ return true;
+}
- int subsampling = level->getImageSubsampling(getCurrentFid());
- StylePicker picker(image);
- TPointD pickPos(TScale(1.0 / subsampling) * pos + TPointD(-0.5, -0.5));
- int inkStyleId =
- picker.pickStyleId(pickPos, getPixelSize() * getPixelSize(), 1);
- int paintStyleId =
- picker.pickStyleId(pickPos, getPixelSize() * getPixelSize(), 0);
- int tone = picker.pickTone(pickPos);
- controller->notifyStylePassivePicked(inkStyleId, paintStyleId, tone);
+bool StylePickerTool::startOrganizePalette() {
+ /* Check if the organizing operation is available */
+ TXshLevel *level = getApplication()->getCurrentLevel()->getLevel();
+ if (!level) {
+ DVGui::error(tr("No current level."));
+ return false;
+ }
+ if (level->getType() != PLI_XSHLEVEL && level->getType() != TZP_XSHLEVEL &&
+ level->getType() != PLT_XSHLEVEL) {
+ DVGui::error(tr("Current level has no available palette."));
+ return false;
+ }
+ /* palette should have more than one page to organize */
+ TPalette *pal = NULL;
+ if (level->getType() == PLT_XSHLEVEL)
+ pal = level->getPaletteLevel()->getPalette();
+ else
+ pal = level->getSimpleLevel()->getPalette();
+ if (!pal || pal->getPageCount() < 2) {
+ DVGui::error(
+ tr("Palette must have more than one palette to be organized."));
+ return false;
}
- void onActivate() override {}
+ m_paletteToBeOrganized = pal;
- int getCursorId() const override {
- bool isBlackBG = ToonzCheck::instance()->getChecks() & ToonzCheck::eBlackBg;
+ std::cout << "Start Organize Palette" << std::endl;
- if (m_colorType.getValue() == LINES)
- return (isBlackBG) ? ToolCursor::PickerCursorWhiteLine
- : ToolCursor::PickerCursorLine;
- else if (m_colorType.getValue() == AREAS)
- return (isBlackBG) ? ToolCursor::PickerCursorWhiteArea
- : ToolCursor::PickerCursorArea;
- else // line&areas
- return (isBlackBG) ? ToolCursor::PickerCursorWhite
- : ToolCursor::PickerCursor;
- }
+ return true;
+}
-} stylePickerTool;
+/*
+ If the working palette is changed, then deactivate the "organize palette"
+ toggle.
+*/
+void StylePickerTool::onImageChanged() {
+ std::cout << "StylePickerTool::onImageChanged" << std::endl;
+ if (!m_organizePalette.getValue() || !m_paletteToBeOrganized) return;
+
+ TXshLevel *level = getApplication()->getCurrentLevel()->getLevel();
+ if (!level) {
+ m_organizePalette.setValue(false);
+ getApplication()->getCurrentTool()->notifyToolChanged();
+ return;
+ }
+ TPalette *pal = NULL;
+ if (level->getType() == PLT_XSHLEVEL)
+ pal = level->getPaletteLevel()->getPalette();
+ else if (level->getSimpleLevel()) {
+ pal = level->getSimpleLevel()->getPalette();
+ }
+ if (!pal || pal != m_paletteToBeOrganized) {
+ m_organizePalette.setValue(false);
+ getApplication()->getCurrentTool()->notifyToolChanged();
+ return;
+ }
}
+
+StylePickerTool stylePickerTool;
diff --git a/toonz/sources/tnztools/stylepickertool.h b/toonz/sources/tnztools/stylepickertool.h
new file mode 100644
index 0000000..2a6982a
--- /dev/null
+++ b/toonz/sources/tnztools/stylepickertool.h
@@ -0,0 +1,54 @@
+#pragma once
+
+#ifndef STYLEPICKERTOOL_H
+#define STYLEPICKERTOOL_H
+
+#include "tools/tool.h"
+#include "tproperty.h"
+#include
+
+class StylePickerTool final : public TTool, public QObject {
+ int m_oldStyleId, m_currentStyleId;
+
+ TEnumProperty m_colorType;
+ TPropertyGroup m_prop;
+ TBoolProperty m_passivePick;
+
+ TBoolProperty m_organizePalette;
+ TPalette *m_paletteToBeOrganized;
+
+ bool startOrganizePalette();
+
+public:
+ TPropertyGroup *getProperties(int targetType) override { return &m_prop; }
+
+ StylePickerTool();
+
+ ToolType getToolType() const override { return TTool::LevelReadTool; }
+
+ void draw() override {}
+
+ void leftButtonDown(const TPointD &pos, const TMouseEvent &e) override;
+
+ void leftButtonDrag(const TPointD &pos, const TMouseEvent &e) override;
+
+ void pick(const TPointD &pos, const TMouseEvent &e);
+
+ void mouseMove(const TPointD &pos, const TMouseEvent &e) override;
+
+ int getCursorId() const override;
+
+ bool onPropertyChanged(std::string propertyName);
+
+ bool isOrganizePaletteActive() { return m_organizePalette.getValue(); }
+
+ /*
+ This function is called when either frame/column/level/scene is switched or
+ either scene/level/object is changed (see tapp.cpp).
+ If the working palette is changed, then deactivate the "organize palette"
+ toggle.
+ */
+ void onImageChanged() override;
+};
+
+#endif
\ No newline at end of file
diff --git a/toonz/sources/tnztools/tnztools.qrc b/toonz/sources/tnztools/tnztools.qrc
index 98087dc..1b5b91b 100644
--- a/toonz/sources/tnztools/tnztools.qrc
+++ b/toonz/sources/tnztools/tnztools.qrc
@@ -50,6 +50,8 @@
Resources/picker_style_white_line.png
Resources/picker_style_white_area.png
Resources/picker_style_white.png
+ Resources/picker_style_organize.png
+ Resources/picker_style_white_organize.png
Resources/picker_rgb.png
Resources/picker_rgb_white.png
Resources/fill_f.png
diff --git a/toonz/sources/tnztools/tooloptions.cpp b/toonz/sources/tnztools/tooloptions.cpp
index f19ee3b..399b876 100644
--- a/toonz/sources/tnztools/tooloptions.cpp
+++ b/toonz/sources/tnztools/tooloptions.cpp
@@ -2182,6 +2182,17 @@ StylePickerToolOptionsBox::StylePickerToolOptionsBox(
m_layout->addWidget(m_currentStyleLabel, 0);
m_layout->addStretch(1);
+ // retrieve the "organize palette" checkbox from the layout and insert
+ // into rightmost of the tool option bar
+ ToolOptionCheckbox *organizePaletteCB =
+ dynamic_cast(m_controls.value("Organize Palette"));
+ m_layout->removeWidget(organizePaletteCB);
+ m_layout->addWidget(new ToolOptionsBarSeparator(this), 0);
+ m_layout->addWidget(organizePaletteCB);
+ organizePaletteCB->setToolTip(
+ tr("With this option being activated, the picked style will be\nmoved to "
+ "the end of the first page of the palette."));
+
if (m_realTimePickMode) {
connect(m_realTimePickMode, SIGNAL(toggled(bool)), m_currentStyleLabel,
SLOT(setVisible(bool)));
@@ -2340,6 +2351,7 @@ un po' di codice... */
m_panels[tool] = panel;
layout()->addWidget(panel);
+ emit newPanelCreated();
} else {
// il panel c'e' gia'.
panel = it->second;
diff --git a/toonz/sources/toonz/CMakeLists.txt b/toonz/sources/toonz/CMakeLists.txt
index 0215c13..c6849a1 100644
--- a/toonz/sources/toonz/CMakeLists.txt
+++ b/toonz/sources/toonz/CMakeLists.txt
@@ -100,6 +100,7 @@ set(MOC_HEADERS
selectionutils.h
shifttracetool.h
shortcutpopup.h
+ startuppopup.h
subcameramanager.h
subscenecommand.h
svncleanupdialog.h
@@ -140,6 +141,8 @@ set(MOC_HEADERS
historypane.h
cleanupsettingspane.h
penciltestpopup.h
+ locatorpopup.h
+ styleshortcutswitchablepanel.h
# Tracker file
dummyprocessor.h
metnum.h
@@ -232,6 +235,7 @@ set(SOURCES
scriptconsolepanel.cpp
shifttracetool.cpp
shortcutpopup.cpp
+ startuppopup.cpp
subcameramanager.cpp
timestretchpopup.cpp
trackerpopup.cpp
@@ -298,6 +302,8 @@ set(SOURCES
historypane.cpp
cleanupsettingspane.cpp
penciltestpopup.cpp
+ locatorpopup.cpp
+ styleshortcutswitchablepanel.cpp
# Tracker file
dummyprocessor.cpp
metnum.cpp
@@ -378,7 +384,7 @@ if(WIN32)
target_link_libraries(OpenToonz_${VERSION}
Qt5::WinMain Qt5::Core Qt5::Gui Qt5::Network Qt5::OpenGL Qt5::Svg Qt5::Xml
Qt5::Script Qt5::Widgets Qt5::PrintSupport Qt5::Multimedia
- ${GL_LIB} ${GLUT_LIB}
+ ${GL_LIB} ${GLUT_LIB} strmiids
tnzcore tnzbase toonzlib colorfx tnzext image sound toonzqt tnztools tnzstdfx tfarm
)
elseif(APPLE)
@@ -430,10 +436,10 @@ if(APPLE)
get_target_property(loc OpenToonz_${VERSION} MACOSX_BUNDLE_NAME)
message(" ==> App Bundle: " ${loc})
message(" ==> Mach-o: " ${bin})
- foreach (lib ${EXTRA_LIBS})
+ foreach(lib ${EXTRA_LIBS})
message(" copy:" ${lib} "==>" ${CMAKE_CURRENT_BINARY_DIR}/OpenToonz_${VERSION}.app/Contents/MacOS/)
add_custom_command(TARGET OpenToonz_${VERSION} POST_BUILD COMMAND cp ${lib} ${CMAKE_CURRENT_BINARY_DIR}/OpenToonz_${VERSION}.app/Contents/MacOS/)
- endforeach ()
+ endforeach()
add_custom_command(TARGET OpenToonz_${VERSION}
POST_BUILD COMMAND
diff --git a/toonz/sources/toonz/Resources/locator.png b/toonz/sources/toonz/Resources/locator.png
new file mode 100644
index 0000000..439df63
Binary files /dev/null and b/toonz/sources/toonz/Resources/locator.png differ
diff --git a/toonz/sources/toonz/Resources/locator_click.png b/toonz/sources/toonz/Resources/locator_click.png
new file mode 100644
index 0000000..8045221
Binary files /dev/null and b/toonz/sources/toonz/Resources/locator_click.png differ
diff --git a/toonz/sources/toonz/Resources/locator_over.png b/toonz/sources/toonz/Resources/locator_over.png
new file mode 100644
index 0000000..8045221
Binary files /dev/null and b/toonz/sources/toonz/Resources/locator_over.png differ
diff --git a/toonz/sources/toonz/Resources/startup.png b/toonz/sources/toonz/Resources/startup.png
new file mode 100644
index 0000000..10757e0
Binary files /dev/null and b/toonz/sources/toonz/Resources/startup.png differ
diff --git a/toonz/sources/toonz/cellselectioncommand.cpp b/toonz/sources/toonz/cellselectioncommand.cpp
index a670e73..fa3c108 100644
--- a/toonz/sources/toonz/cellselectioncommand.cpp
+++ b/toonz/sources/toonz/cellselectioncommand.cpp
@@ -1292,6 +1292,7 @@ TXshSimpleLevel *CloneLevelUndo::cloneLevel(
assert(palette);
dstSl->setPalette(palette->clone());
+ dstSl->getPalette()->setDirtyFlag(true);
}
// The level clone shell was created. Now, clone the associated frames found
@@ -1306,6 +1307,8 @@ TXshSimpleLevel *CloneLevelUndo::cloneLevel(
dstSl->setFrame(*ft, img->cloneImage());
}
+ dstSl->setDirtyFlag(true);
+
return dstSl;
}
diff --git a/toonz/sources/toonz/cleanupsettingspane.cpp b/toonz/sources/toonz/cleanupsettingspane.cpp
index d7e5579..30756ba 100644
--- a/toonz/sources/toonz/cleanupsettingspane.cpp
+++ b/toonz/sources/toonz/cleanupsettingspane.cpp
@@ -26,6 +26,7 @@
#include
#include
#include
+#include
#include "cleanupsettingspane.h"
@@ -80,6 +81,10 @@ void CleanupSaveInField::browseDirectory() {
CleanupSettingsPane::CleanupSettingsPane(QWidget *parent)
: QFrame(parent), m_attached(false) {
+ // Autocenter
+ m_autocenterBox = new QGroupBox(tr("Autocenter"), this);
+ m_pegHolesOm = new QComboBox(this);
+ m_fieldGuideOm = new QComboBox(this);
// Rotate&Flip
QFrame *rotFlipFrame = new QFrame(this);
m_rotateOm = new QComboBox(this);
@@ -103,6 +108,19 @@ CleanupSettingsPane::CleanupSettingsPane(QWidget *parent)
QPushButton *loadBtn = new QPushButton(tr("Load"));
QPushButton *resetBtn = new QPushButton(tr("Reset"));
+ // Autocenter
+ m_autocenterBox->setCheckable(true);
+ QStringList pegbarHoles;
+ pegbarHoles << "Bottom"
+ << "Top"
+ << "Left"
+ << "Right";
+ m_pegHolesOm->addItems(pegbarHoles);
+ std::vector fdgNames;
+ CleanupParameters::getFdgNames(fdgNames);
+ for (int i = 0; i < (int)fdgNames.size(); i++)
+ m_fieldGuideOm->addItem(QString(fdgNames[i].c_str()));
+
// Rotate&Flip
rotFlipFrame->setObjectName("CleanupSettingsFrame");
QStringList rotate;
@@ -137,6 +155,23 @@ CleanupSettingsPane::CleanupSettingsPane(QWidget *parent)
mainLay->setSpacing(2);
mainLay->setMargin(5);
{
+ // Autocenter
+ QGridLayout *autocenterLay = new QGridLayout();
+ autocenterLay->setMargin(5);
+ autocenterLay->setSpacing(3);
+ {
+ autocenterLay->addWidget(new QLabel(tr("Pegbar Holes")), 0, 0,
+ Qt::AlignRight | Qt::AlignVCenter);
+ autocenterLay->addWidget(m_pegHolesOm, 0, 1);
+ autocenterLay->addWidget(new QLabel(tr("Field Guide")), 1, 0,
+ Qt::AlignRight | Qt::AlignVCenter);
+ autocenterLay->addWidget(m_fieldGuideOm, 1, 1);
+ }
+ autocenterLay->setColumnStretch(0, 0);
+ autocenterLay->setColumnStretch(1, 1);
+ m_autocenterBox->setLayout(autocenterLay);
+ mainLay->addWidget(m_autocenterBox, 0);
+
// Rotate&Flip
QGridLayout *rotFlipLay = new QGridLayout();
rotFlipLay->setMargin(5);
@@ -226,7 +261,14 @@ CleanupSettingsPane::CleanupSettingsPane(QWidget *parent)
//-----signal-slot connections
bool ret = true;
- ret = ret && connect(m_rotateOm, SIGNAL(activated(int)),
+ ret = ret && connect(m_autocenterBox, SIGNAL(toggled(bool)),
+ SLOT(onGenericSettingsChange()));
+ ret = ret && connect(m_pegHolesOm, SIGNAL(activated(int)),
+ SLOT(onGenericSettingsChange()));
+ ret = ret && connect(m_fieldGuideOm, SIGNAL(activated(int)),
+ SLOT(onGenericSettingsChange()));
+
+ ret = ret && connect(m_rotateOm, SIGNAL(activated(int)),
SLOT(onGenericSettingsChange()));
ret = ret && connect(m_flipX, SIGNAL(stateChanged(int)),
SLOT(onGenericSettingsChange()));
@@ -336,6 +378,15 @@ void CleanupSettingsPane::updateGui(bool needsPostProcess) {
void CleanupSettingsPane::updateGui(CleanupParameters *params,
CleanupParameters *oldParams) {
+ m_autocenterBox->setChecked(params->m_autocenterType ==
+ CleanupTypes::AUTOCENTER_FDG);
+ m_pegHolesOm->setCurrentIndex(params->m_pegSide - 1);
+
+ QString fieldName = QString::fromStdString(params->getFdgName());
+ int index = (fieldName.isEmpty()) ? 0 : m_fieldGuideOm->findText(fieldName);
+ assert(index != -1);
+ m_fieldGuideOm->setCurrentIndex(index);
+
m_rotateOm->setCurrentIndex(params->m_rotate / 90);
m_flipX->setChecked(params->m_flipx);
m_flipY->setChecked(params->m_flipy);
@@ -462,6 +513,13 @@ void CleanupSettingsPane::onGenericSettingsChange() {
CleanupSettingsModel *model = CleanupSettingsModel::instance();
CleanupParameters *params = model->getCurrentParameters();
+ params->m_autocenterType = m_autocenterBox->isChecked()
+ ? CleanupTypes::AUTOCENTER_FDG
+ : CleanupTypes::AUTOCENTER_NONE;
+ params->m_pegSide =
+ (CleanupTypes::PEGS_SIDE)(m_pegHolesOm->currentIndex() + 1);
+ params->setFdgByName(m_fieldGuideOm->currentText().toStdString());
+
params->m_rotate = m_rotateOm->currentIndex() * 90;
params->m_flipx = m_flipX->isChecked();
params->m_flipy = m_flipY->isChecked();
diff --git a/toonz/sources/toonz/cleanupsettingspane.h b/toonz/sources/toonz/cleanupsettingspane.h
index b0069d8..75da278 100644
--- a/toonz/sources/toonz/cleanupsettingspane.h
+++ b/toonz/sources/toonz/cleanupsettingspane.h
@@ -18,6 +18,7 @@ class QComboBox;
class QLabel;
class QCheckBox;
class CleanupPaletteViewer;
+class QGroupBox;
namespace DVGui {
@@ -47,6 +48,9 @@ public:
CleanupCameraSettingsWidget *m_cameraWidget;
private:
+ //----Autocenter
+ QGroupBox *m_autocenterBox;
+ QComboBox *m_pegHolesOm, *m_fieldGuideOm;
//----Rotate & Flip
QComboBox *m_rotateOm;
QCheckBox *m_flipX;
diff --git a/toonz/sources/toonz/colormodelviewer.cpp b/toonz/sources/toonz/colormodelviewer.cpp
index 2e063b5..e4b0085 100644
--- a/toonz/sources/toonz/colormodelviewer.cpp
+++ b/toonz/sources/toonz/colormodelviewer.cpp
@@ -14,6 +14,7 @@
#include "tools/toolcommandids.h"
#include "tools/tool.h"
#include "tools/toolhandle.h"
+#include "../tnztools/stylepickertool.h"
// TnzQt includes
#include "toonzqt/menubarcommand.h"
@@ -84,7 +85,7 @@ ColorModelViewer::ColorModelViewer(QWidget *parent)
FlipConsole::eCompare | FlipConsole::eCustomize |
FlipConsole::eSave | FlipConsole::eFilledRaster |
FlipConsole::eDefineLoadBox | FlipConsole::eUseLoadBox |
- FlipConsole::eDefineSubCamera)),
+ FlipConsole::eDefineSubCamera | FlipConsole::eLocator)),
eDontKeepFilesOpened, true)
, m_mode(0)
, m_currentRefImgPath(TFilePath()) {
@@ -222,11 +223,28 @@ void ColorModelViewer::contextMenuEvent(QContextMenuEvent *event) {
connect(loadCurrentFrame, SIGNAL(triggered()), SLOT(loadCurrentFrame()));
menu.addAction(loadCurrentFrame);
+ if (!m_imageViewer->getImage()) {
+ menu.exec(event->globalPos());
+ return;
+ }
+
QAction *removeColorModel =
new QAction(QString(tr("Remove Color Model")), this);
connect(removeColorModel, SIGNAL(triggered()), SLOT(removeColorModel()));
menu.addAction(removeColorModel);
+ /* If there is at least one style with "picked pos" parameter, then enable
+ * repick command */
+ TRasterImageP ri = m_imageViewer->getImage();
+ if (ri && currentPalette->hasPickedPosStyle()) {
+ menu.addSeparator();
+ QAction *repickFromColorModelAct = new QAction(
+ QString(tr("Update Colors by Using Picked Positions")), this);
+ connect(repickFromColorModelAct, SIGNAL(triggered()),
+ SLOT(repickFromColorModel()));
+ menu.addAction(repickFromColorModelAct);
+ }
+
menu.addSeparator();
QString shortcut = QString::fromStdString(
@@ -306,6 +324,19 @@ void ColorModelViewer::pick(const QPoint &p) {
if (styleSelection) styleSelection->selectNone();
}
+ /*
+ if the Style Picker tool is current and "organize palette" is activated,
+ then move the picked style to the first page of the palette.
+ */
+ TTool *tool = TApp::instance()->getCurrentTool()->getTool();
+ if (tool->getName() == "T_StylePicker") {
+ StylePickerTool *spTool = dynamic_cast(tool);
+ if (spTool && spTool->isOrganizePaletteActive()) {
+ TPoint point = picker.getRasterPoint(pos);
+ PaletteCmd::organizePaletteStyle(ph, styleIndex, point);
+ }
+ }
+
ph->setStyleIndex(styleIndex);
}
@@ -356,8 +387,16 @@ void ColorModelViewer::showEvent(QShowEvent *e) {
//-----------------------------------------------------------------------------
/*- ツールのTypeに合わせてPickのタイプも変え、カーソルも切り替える -*/
void ColorModelViewer::changePickType() {
- TPropertyGroup *propGroup =
- TApp::instance()->getCurrentTool()->getTool()->getProperties(0);
+ TTool *tool = TApp::instance()->getCurrentTool()->getTool();
+ if (tool->getName() == T_StylePicker) {
+ StylePickerTool *stylePickerTool = dynamic_cast(tool);
+ if (stylePickerTool->isOrganizePaletteActive()) {
+ setToolCursor(m_imageViewer, ToolCursor::PickerCursorOrganize);
+ return;
+ }
+ }
+
+ TPropertyGroup *propGroup = tool->getProperties(0);
/*- Propertyの無いツールの場合 -*/
if (!propGroup) {
m_mode = 2;
@@ -573,6 +612,17 @@ void ColorModelViewer::onRefImageNotFound() {
"level."));
}
+//-----------------------------------------------------------------------------
+
+void ColorModelViewer::repickFromColorModel() {
+ TImageP img = m_imageViewer->getImage();
+ if (!img) return;
+ TPaletteHandle *ph =
+ TApp::instance()->getPaletteController()->getCurrentLevelPalette();
+
+ PaletteCmd::pickColorByUsingPickedPosition(ph, img);
+}
+
//=============================================================================
OpenFloatingPanel openColorModelCommand(MI_OpenColorModel, "ColorModel",
diff --git a/toonz/sources/toonz/colormodelviewer.h b/toonz/sources/toonz/colormodelviewer.h
index e068080..833a62d 100644
--- a/toonz/sources/toonz/colormodelviewer.h
+++ b/toonz/sources/toonz/colormodelviewer.h
@@ -48,6 +48,7 @@ protected:
* UseCurrentFrameのLevelに移動してきたときに、改めてCurrentFrameを格納しなおす
* -*/
void reloadCurrentFrame();
+
protected slots:
void showCurrentImage();
@@ -62,6 +63,8 @@ protected slots:
* -*/
void changePickType();
+ void repickFromColorModel();
+
signals:
void refImageNotFound();
};
diff --git a/toonz/sources/toonz/comboviewerpane.cpp b/toonz/sources/toonz/comboviewerpane.cpp
index 6a10ad9..c592005 100644
--- a/toonz/sources/toonz/comboviewerpane.cpp
+++ b/toonz/sources/toonz/comboviewerpane.cpp
@@ -86,7 +86,7 @@ ComboViewerPanel::ComboViewerPanel(QWidget *parent, Qt::WindowFlags flags)
#else
ComboViewerPanel::ComboViewerPanel(QWidget *parent, Qt::WFlags flags)
#endif
- : TPanel(parent) {
+ : StyleShortcutSwitchablePanel(parent) {
TApp *app = TApp::instance();
QFrame *hbox = new QFrame(this);
@@ -103,6 +103,7 @@ ComboViewerPanel::ComboViewerPanel(QWidget *parent, Qt::WFlags flags)
ImageUtils::FullScreenWidget *fsWidget =
new ImageUtils::FullScreenWidget(this);
fsWidget->setWidget(m_sceneViewer = new SceneViewer(fsWidget));
+ m_sceneViewer->setIsStyleShortcutSwitchable();
#if defined(Q_OS_WIN) && (QT_VERSION >= 0x050500) && (QT_VERSION < 0x050600)
// Workaround for QTBUG-48288
@@ -189,6 +190,9 @@ ComboViewerPanel::ComboViewerPanel(QWidget *parent, Qt::WFlags flags)
SLOT(update()));
ret = ret && connect(app->getCurrentScene(), SIGNAL(sceneSwitched()), this,
SLOT(onSceneSwitched()));
+ ret = ret && connect(m_toolOptions, SIGNAL(newPanelCreated()), this,
+ SLOT(updateTabFocus()));
+
assert(ret);
// note: initializeTitleBar() refers to m_sceneViewer
@@ -336,7 +340,8 @@ ComboViewerPanel::~ComboViewerPanel() {
//-----------------------------------------------------------------------------
-void ComboViewerPanel::showEvent(QShowEvent *) {
+void ComboViewerPanel::showEvent(QShowEvent *event) {
+ StyleShortcutSwitchablePanel::showEvent(event);
TApp *app = TApp::instance();
TFrameHandle *frameHandle = app->getCurrentFrame();
TSceneHandle *sceneHandle = app->getCurrentScene();
@@ -388,9 +393,6 @@ void ComboViewerPanel::showEvent(QShowEvent *) {
ret = ret && connect(app->getCurrentTool(), SIGNAL(toolSwitched()),
m_sceneViewer, SLOT(onToolSwitched()));
- ret = ret && connect(sceneHandle, SIGNAL(preferenceChanged()), m_flipConsole,
- SLOT(onPreferenceChanged()));
- m_flipConsole->onPreferenceChanged();
assert(ret);
@@ -403,7 +405,8 @@ void ComboViewerPanel::showEvent(QShowEvent *) {
//-----------------------------------------------------------------------------
-void ComboViewerPanel::hideEvent(QHideEvent *) {
+void ComboViewerPanel::hideEvent(QHideEvent *event) {
+ StyleShortcutSwitchablePanel::hideEvent(event);
TApp *app = TApp::instance();
disconnect(app->getCurrentScene());
disconnect(app->getCurrentLevel());
@@ -781,3 +784,12 @@ bool ComboViewerPanel::isFrameAlreadyCached(int frame) {
}
//-----------------------------------------------------------------------------
+
+void ComboViewerPanel::onPreferenceChanged(const QString &prefName) {
+ // if no name specified (on showEvent), then process all updates
+ if (prefName == "BlankCount" || prefName == "BlankColor" ||
+ prefName.isEmpty())
+ m_flipConsole->onPreferenceChanged();
+
+ StyleShortcutSwitchablePanel::onPreferenceChanged(prefName);
+}
diff --git a/toonz/sources/toonz/comboviewerpane.h b/toonz/sources/toonz/comboviewerpane.h
index 8f935ca..d7f2ea0 100644
--- a/toonz/sources/toonz/comboviewerpane.h
+++ b/toonz/sources/toonz/comboviewerpane.h
@@ -3,7 +3,7 @@
#ifndef COMBOVIEWER_PANE_INCLUDED
#define COMBOVIEWER_PANE_INCLUDED
-#include "pane.h"
+#include "styleshortcutswitchablepanel.h"
#include "sceneviewer.h"
#include "toonzqt/intfield.h"
#include "toonzqt/keyframenavigator.h"
@@ -37,7 +37,8 @@ enum CV_Parts {
};
//-----------------------------------------------------------------------------
-class ComboViewerPanel final : public TPanel, public FlipConsoleOwner {
+class ComboViewerPanel final : public StyleShortcutSwitchablePanel,
+ public FlipConsoleOwner {
Q_OBJECT
SceneViewer *m_sceneViewer;
@@ -118,6 +119,8 @@ protected slots:
void onSceneSwitched();
void enableFullPreview(bool enabled);
void enableSubCameraPreview(bool enabled);
+
+ void onPreferenceChanged(const QString &prefName) override;
};
#endif
diff --git a/toonz/sources/toonz/convertpopup.cpp b/toonz/sources/toonz/convertpopup.cpp
index 97ac0e6..7ed582e 100644
--- a/toonz/sources/toonz/convertpopup.cpp
+++ b/toonz/sources/toonz/convertpopup.cpp
@@ -55,6 +55,8 @@ TEnv::IntVar ConvertPopupRemoveDot("ConvertPopupRemoveDot", 1);
TEnv::IntVar ConvertPopupSaveToNopaint("ConvertPopupSaveToNopaint", 1);
TEnv::IntVar ConvertPopupAppendDefaultPalette(
"ConvertPopupAppendDefaultPalette", 0);
+TEnv::IntVar ConvertPopupRemoveUnusedStyles("ConvertPopupRemoveUnusedStyles",
+ 0);
//=============================================================================
// convertPopup
@@ -200,7 +202,8 @@ void ConvertPopup::Converter::convertLevel(
// no AA source (retas)
TPaletteP palette = popup->readUserProvidedPalette();
ImageUtils::convertNaa2Tlv(sourceFileFullPath, dstFileFullPath, from, to,
- m_parent->m_notifier, palette.getPointer());
+ m_parent->m_notifier, palette.getPointer(),
+ m_parent->m_removeUnusedStyles->isChecked());
} else {
convertLevelWithConvert2Tlv(sourceFileFullPath);
}
@@ -441,6 +444,7 @@ ConvertPopup::ConvertPopup(bool specifyInput)
m_removeDotBeforeFrameNumber->setChecked(ConvertPopupRemoveDot != 0);
m_saveBackupToNopaint->setChecked(ConvertPopupSaveToNopaint != 0);
m_appendDefaultPalette->setChecked(ConvertPopupAppendDefaultPalette != 0);
+ m_removeUnusedStyles->setChecked(ConvertPopupRemoveUnusedStyles != 0);
//--- signal-slot connections
qRegisterMetaType("TFilePath");
@@ -470,6 +474,9 @@ ConvertPopup::ConvertPopup(bool specifyInput)
ret = ret && connect(m_convertFileFld, SIGNAL(pathChanged()), this,
SLOT(onFileInChanged()));
+ // update unable/enable of checkboxes
+ onTlvModeSelected(m_tlvMode->currentText());
+
assert(ret);
}
@@ -522,7 +529,7 @@ QFrame *ConvertPopup::createTlvSettings() {
m_tlvMode = new QComboBox();
m_unpaintedFolderLabel = new QLabel(tr("Unpainted File Folder:"));
m_unpaintedFolder =
- new DVGui::FileField(0, QString(tr("Same as Painted")), true);
+ new DVGui::FileField(0, QString(tr("Same as Painted")), true, true);
m_suffixLabel = new QLabel(tr(" Unpainted File Suffix:"));
m_unpaintedSuffix = new DVGui::LineEdit("_np");
m_applyAutoclose = new QCheckBox(tr("Apply Autoclose"));
@@ -531,8 +538,12 @@ QFrame *ConvertPopup::createTlvSettings() {
m_appendDefaultPalette = new QCheckBox(tr("Append Default Palette"));
m_antialias = new QComboBox();
m_antialiasIntensity = new DVGui::IntLineEdit(0, 50, 0, 100);
- m_palettePath = new DVGui::FileField(0, QString(CreateNewPalette), true);
- m_tolerance = new DVGui::IntLineEdit(0, 0, 0, 255);
+ m_palettePath =
+ new DVGui::FileField(0, QString(CreateNewPalette), true, true);
+ m_tolerance = new DVGui::IntLineEdit(0, 0, 0, 255);
+
+ m_removeUnusedStyles =
+ new QCheckBox(tr("Remove Unused Styles from Input Palette"));
m_unpaintedFolder->setFileMode(QFileDialog::DirectoryOnly);
m_unpaintedSuffix->setMaximumWidth(40);
@@ -585,8 +596,9 @@ QFrame *ConvertPopup::createTlvSettings() {
Qt::AlignRight | Qt::AlignVCenter);
gridLay->addWidget(m_tolerance, 4, 3);
- gridLay->addWidget(m_appendDefaultPalette, 5, 1, 1, 3);
- gridLay->addWidget(m_saveBackupToNopaint, 6, 1, 1, 3);
+ gridLay->addWidget(m_removeUnusedStyles, 5, 1, 1, 3);
+ gridLay->addWidget(m_appendDefaultPalette, 6, 1, 1, 3);
+ gridLay->addWidget(m_saveBackupToNopaint, 7, 1, 1, 3);
}
gridLay->setColumnStretch(0, 0);
gridLay->setColumnStretch(1, 1);
@@ -597,6 +609,9 @@ QFrame *ConvertPopup::createTlvSettings() {
bool ret = true;
ret = ret && connect(m_antialias, SIGNAL(currentIndexChanged(int)), this,
SLOT(onAntialiasSelected(int)));
+ ret = ret && connect(m_palettePath, SIGNAL(pathChanged()), this,
+ SLOT(onPalettePathChanged()));
+
assert(ret);
frame->setVisible(false);
@@ -652,8 +667,13 @@ void ConvertPopup::onTlvModeSelected(const QString &tlvMode) {
m_suffixLabel->setEnabled(usesTwoImages);
m_unpaintedSuffix->setEnabled(usesTwoImages);
m_antialias->setEnabled(TlvMode_PaintedFromNonAA != tlvMode);
- m_palettePath->setEnabled(TlvMode_PaintedFromNonAA != tlvMode);
+ // m_palettePath->setEnabled(TlvMode_PaintedFromNonAA != tlvMode);
m_tolerance->setEnabled(TlvMode_PaintedFromNonAA != tlvMode);
+ m_appendDefaultPalette->setEnabled(TlvMode_PaintedFromNonAA != tlvMode);
+
+ m_removeUnusedStyles->setEnabled(TlvMode_PaintedFromNonAA == tlvMode &&
+ m_palettePath->getPath() !=
+ CreateNewPalette);
m_saveBackupToNopaint->setEnabled(TlvMode_Unpainted == tlvMode);
}
@@ -1057,6 +1077,7 @@ void ConvertPopup::apply() {
ConvertPopupSaveToNopaint = m_saveBackupToNopaint->isChecked() ? 1 : 0;
ConvertPopupAppendDefaultPalette =
m_appendDefaultPalette->isChecked() ? 1 : 0;
+ ConvertPopupRemoveUnusedStyles = m_removeUnusedStyles->isChecked() ? 1 : 0;
// parameters are ok: close the dialog first
close();
@@ -1174,6 +1195,14 @@ void ConvertPopup::onFormatChanged(const QString &ext) {
//-------------------------------------------------------------------
+void ConvertPopup::onPalettePathChanged() {
+ m_removeUnusedStyles->setEnabled(
+ m_tlvMode->currentText() == TlvMode_PaintedFromNonAA &&
+ m_palettePath->getPath() != CreateNewPalette);
+}
+
+//-------------------------------------------------------------------
+
bool ConvertPopup::isSaveTlvBackupToNopaintActive() {
return m_fileFormat->currentText() ==
TlvExtension /*-- tlvが選択されている --*/
diff --git a/toonz/sources/toonz/convertpopup.h b/toonz/sources/toonz/convertpopup.h
index cc4ff5a..b779a07 100644
--- a/toonz/sources/toonz/convertpopup.h
+++ b/toonz/sources/toonz/convertpopup.h
@@ -87,6 +87,7 @@ public slots:
void onLevelConverted(const TFilePath &fullPath);
void onFormatChanged(const QString &);
+ void onPalettePathChanged();
protected:
Convert2Tlv *makeTlvConverter(const TFilePath &sourceFilePath);
@@ -104,7 +105,7 @@ private:
DVGui::ColorField *m_bgColorField;
QFrame *m_tlvFrame;
QCheckBox *m_applyAutoclose, *m_removeDotBeforeFrameNumber,
- *m_saveBackupToNopaint, *m_appendDefaultPalette;
+ *m_saveBackupToNopaint, *m_appendDefaultPalette, *m_removeUnusedStyles;
DVGui::CheckBox *m_skip;
QComboBox *m_antialias, *m_tlvMode, *m_fileFormat;
QLabel *m_bgColorLabel, *m_suffixLabel, *m_unpaintedFolderLabel,
diff --git a/toonz/sources/toonz/filebrowser.cpp b/toonz/sources/toonz/filebrowser.cpp
index f4f06e8..73f7f9a 100644
--- a/toonz/sources/toonz/filebrowser.cpp
+++ b/toonz/sources/toonz/filebrowser.cpp
@@ -148,7 +148,8 @@ QMutex levelFileMutex;
inline bool isMultipleFrameType(std::string type) {
return (type == "tlv" || type == "tzl" || type == "pli" || type == "mov" ||
- type == "avi" || type == "3gp");
+ type == "avi" || type == "3gp" || type == "gif" || type == "mp4" ||
+ type == "webm");
}
//=============================================================================
diff --git a/toonz/sources/toonz/filebrowserpopup.cpp b/toonz/sources/toonz/filebrowserpopup.cpp
index 8bbda39..6ab99c7 100644
--- a/toonz/sources/toonz/filebrowserpopup.cpp
+++ b/toonz/sources/toonz/filebrowserpopup.cpp
@@ -485,17 +485,15 @@ bool LoadScenePopup::execute() {
void LoadScenePopup::initFolder() { setInitialFolderByCurrentRoom(); }
void LoadScenePopup::setInitialFolderByCurrentRoom() {
- QString roomName = TApp::instance()->getCurrentRoomName();
+ QString roomName = TApp::instance()->getCurrentRoomName();
+ TProjectP project = TProjectManager::instance()->getCurrentProject();
TFilePath scenePath;
if (roomName == "Cleanup" || roomName == "InknPaint")
- scenePath = TProjectManager::instance()->getCurrentProject()->getFolder(
- TProject::Drawings);
+ scenePath = project->getFolder(TProject::Drawings, true);
else if (roomName == "PltEdit")
- scenePath = TProjectManager::instance()->getCurrentProject()->getFolder(
- TProject::Palettes);
+ scenePath = project->getFolder(TProject::Palettes, true);
else
- scenePath = TProjectManager::instance()->getCurrentProject()->getFolder(
- TProject::Scenes);
+ scenePath = project->getFolder(TProject::Scenes, true);
setFolder(scenePath);
}
diff --git a/toonz/sources/toonz/flipbook.h b/toonz/sources/toonz/flipbook.h
index a116f3c..b9e13ee 100644
--- a/toonz/sources/toonz/flipbook.h
+++ b/toonz/sources/toonz/flipbook.h
@@ -179,7 +179,8 @@ public:
FlipBook(QWidget *parent = 0, QString viewerTitle = QString(),
UINT flipConsoleButtonMask = FlipConsole::cFullConsole &
(~(FlipConsole::eFilledRaster |
- FlipConsole::eDefineSubCamera)),
+ FlipConsole::eDefineSubCamera |
+ FlipConsole::eLocator)),
UCHAR flags = 0, bool isColorModel = false);
~FlipBook();
void setLevel(const TFilePath &path, TPalette *palette = 0, int from = -1,
diff --git a/toonz/sources/toonz/iocommand.cpp b/toonz/sources/toonz/iocommand.cpp
index 00b9df1..2cb728d 100644
--- a/toonz/sources/toonz/iocommand.cpp
+++ b/toonz/sources/toonz/iocommand.cpp
@@ -1176,17 +1176,21 @@ bool IoCmd::saveSceneIfNeeded(QString msg) {
QString question;
question = QObject::tr(
"%1: the current scene has been modified.\n"
- "Do you want to save your changes?")
+ "What would you like to do?")
.arg(msg);
- int ret = DVGui::MsgBox(question, QObject::tr("Save"),
- QObject::tr("Discard"), QObject::tr("Cancel"), 0);
- if (ret == 0 || ret == 3) {
+ int ret = DVGui::MsgBox(
+ question, QObject::tr("Save All"), QObject::tr("Save Scene Only"),
+ QObject::tr("Discard Changes"), QObject::tr("Cancel"), 0);
+ if (ret == 0 || ret == 4) {
// cancel (or closed message box window)
return false;
} else if (ret == 1) {
+ // save all
+ if (!IoCmd::saveAll()) return false;
+ } else if (ret == 2) {
// save
if (!IoCmd::saveScene()) return false;
- } else if (ret == 2) {
+ } else if (ret == 3) {
}
isLevelOrSceneIsDirty = true;
@@ -1203,21 +1207,25 @@ bool IoCmd::saveSceneIfNeeded(QString msg) {
if (!dirtyResources.empty()) {
QString question;
- question =
- msg + ":" + QObject::tr(" Following file(s) are modified.\n\n");
+ question = msg + ":" +
+ QObject::tr(" The following file(s) have been modified.\n\n");
for (int i = 0; i < dirtyResources.size(); i++) {
question += " " + dirtyResources[i] + "\n";
}
- question +=
- QObject::tr("\nAre you sure to ") + msg + QObject::tr(" anyway ?");
+ question += QObject::tr("\nWhat would you like to do? ");
int ret =
- DVGui::MsgBox(question, QObject::tr("OK"), QObject::tr("Cancel"), 0);
- if (ret == 0 || ret == 2) {
+ DVGui::MsgBox(question, QObject::tr("Save Changes"),
+ msg + QObject::tr(" Anyway"), QObject::tr("Cancel"), 0);
+ if (ret == 0 || ret == 3) {
// cancel (or closed message box window)
return false;
} else if (ret == 1) {
- // ok
+ // save non scene files
+ IoCmd::saveNonSceneFiles();
+ return false;
+ } else if (ret == 2) {
+ // quit
}
isLevelOrSceneIsDirty = true;
@@ -1604,7 +1612,7 @@ bool IoCmd::saveLevel(TXshSimpleLevel *sl) {
}
//===========================================================================
-// IoCmd::saveSound(soundPath, soundColumn, overwrite)
+// IoCmd::saveAll()
//---------------------------------------------------------------------------
bool IoCmd::saveAll() {
@@ -1627,6 +1635,26 @@ bool IoCmd::saveAll() {
}
//===========================================================================
+// IoCmd::saveNonSceneFiles()
+//---------------------------------------------------------------------------
+
+void IoCmd::saveNonSceneFiles() {
+ // try to save non scene files
+
+ TApp *app = TApp::instance();
+ ToonzScene *scene = app->getCurrentScene()->getScene();
+ bool untitled = scene->isUntitled();
+ SceneResources resources(scene, 0);
+ resources.save(scene->getScenePath());
+ if (untitled) scene->setUntitled();
+ resources.updatePaths();
+
+ // for update title bar
+ app->getCurrentLevel()->notifyLevelTitleChange();
+ app->getCurrentPalette()->notifyPaletteTitleChanged();
+}
+
+//===========================================================================
// IoCmd::saveSound(soundPath, soundColumn, overwrite)
//---------------------------------------------------------------------------
@@ -2738,3 +2766,12 @@ public:
SaveAllCommandHandler() : MenuItemHandler(MI_SaveAll) {}
void execute() override { IoCmd::saveAll(); }
} saveAllCommandHandler;
+
+//=============================================================================
+// Save all levels
+//-----------------------------------------------------------------------------
+class SaveAllLevelsCommandHandler : public MenuItemHandler {
+public:
+ SaveAllLevelsCommandHandler() : MenuItemHandler(MI_SaveAllLevels) {}
+ void execute() { IoCmd::saveNonSceneFiles(); }
+} saveAllLevelsCommandHandler;
diff --git a/toonz/sources/toonz/iocommand.h b/toonz/sources/toonz/iocommand.h
index 17f6fdb..2415e85 100644
--- a/toonz/sources/toonz/iocommand.h
+++ b/toonz/sources/toonz/iocommand.h
@@ -197,6 +197,8 @@ bool saveLevel(TXshSimpleLevel *sl);
bool saveAll();
+void saveNonSceneFiles();
+
bool saveSound(const TFilePath &fp, TXshSoundLevel *sc, bool overwrite);
bool saveSound(TXshSoundLevel *sc);
diff --git a/toonz/sources/toonz/locatorpopup.cpp b/toonz/sources/toonz/locatorpopup.cpp
new file mode 100644
index 0000000..434ca52
--- /dev/null
+++ b/toonz/sources/toonz/locatorpopup.cpp
@@ -0,0 +1,117 @@
+#include "locatorpopup.h"
+
+// TnzLib includes
+#include "toonz/txshlevelhandle.h"
+#include "toonz/tframehandle.h"
+#include "toonz/preferences.h"
+#include "toonz/stage2.h"
+
+// Tnz6 includes
+#include "tapp.h"
+#include "sceneviewer.h"
+
+#include
+
+LocatorPopup::LocatorPopup(QWidget *parent)
+ : QDialog(parent), m_initialZoom(true) {
+ m_viewer = new SceneViewer(NULL);
+ m_viewer->setParent(parent);
+ m_viewer->setIsLocator();
+
+ //---- layout
+ QVBoxLayout *mainLayout = new QVBoxLayout();
+ mainLayout->setMargin(0);
+ mainLayout->addWidget(m_viewer, 1);
+ setLayout(mainLayout);
+
+ bool ret = true;
+ // When zoom changed, change window title.
+ ret = connect(m_viewer, SIGNAL(onZoomChanged()), SLOT(changeWindowTitle()));
+ ret = ret &&
+ connect(m_viewer, SIGNAL(previewToggled()), SLOT(changeWindowTitle()));
+ assert(ret);
+
+ resize(400, 400);
+}
+
+//-----------------------------------------------------------------------------
+
+void LocatorPopup::onChangeViewAff(const TPointD &pos) {
+ TAffine curAff = m_viewer->getSceneMatrix();
+ TAffine newAff(curAff.a11, 0, -pos.x * curAff.a11, 0, curAff.a22,
+ -pos.y * curAff.a22);
+ m_viewer->setViewMatrix(newAff, 0);
+ m_viewer->setViewMatrix(newAff, 1);
+ m_viewer->update();
+}
+
+//-----------------------------------------------------------------------------
+
+void LocatorPopup::showEvent(QShowEvent *) {
+ // zoom the locator for the first time
+ if (m_initialZoom) {
+ for (int z = 0; z < 4; z++) m_viewer->zoomQt(true, false);
+ m_initialZoom = false;
+ }
+
+ TApp *app = TApp::instance();
+ TFrameHandle *frameHandle = app->getCurrentFrame();
+ TXshLevelHandle *levelHandle = app->getCurrentLevel();
+
+ bool ret = true;
+ ret = ret && connect(frameHandle, SIGNAL(frameSwitched()), this,
+ SLOT(changeWindowTitle()));
+ ret = ret && connect(levelHandle, SIGNAL(xshLevelSwitched(TXshLevel *)), this,
+ SLOT(changeWindowTitle()));
+ assert(ret);
+
+ changeWindowTitle();
+}
+
+//-----------------------------------------------------------------------------
+
+void LocatorPopup::hideEvent(QHideEvent *) {
+ TApp *app = TApp::instance();
+ disconnect(app->getCurrentLevel());
+ disconnect(app->getCurrentFrame());
+}
+
+//-----------------------------------------------------------------------------
+
+void LocatorPopup::changeWindowTitle() {
+ TApp *app = TApp::instance();
+ // put the titlebar texts in this string
+ QString name = tr("Locator");
+
+ bool showZoomFactor = false;
+
+ // if the frame type is "scene editing"
+ if (app->getCurrentFrame()->isEditingScene()) {
+ if (m_viewer->isPreviewEnabled()) showZoomFactor = true;
+
+ // If the current level exists and some option is set in the preference,
+ // set the zoom value to the current level's dpi
+ else if (Preferences::instance()
+ ->isActualPixelViewOnSceneEditingModeEnabled() &&
+ app->getCurrentLevel()->getSimpleLevel() &&
+ !CleanupPreviewCheck::instance()
+ ->isEnabled() // cleanup preview must be OFF
+ &&
+ !CameraTestCheck::instance()
+ ->isEnabled()) // camera test mode must be OFF neither
+ showZoomFactor = true;
+ }
+ // if the frame type is "level editing"
+ else {
+ TXshLevel *level = app->getCurrentLevel()->getLevel();
+ if (level) showZoomFactor = true;
+ }
+
+ if (showZoomFactor) {
+ name = name + " Zoom : " +
+ QString::number((int)(100.0 * sqrt(m_viewer->getViewMatrix().det()) *
+ m_viewer->getDpiFactor())) +
+ "%";
+ }
+ setWindowTitle(name);
+}
\ No newline at end of file
diff --git a/toonz/sources/toonz/locatorpopup.h b/toonz/sources/toonz/locatorpopup.h
new file mode 100644
index 0000000..2dc3448
--- /dev/null
+++ b/toonz/sources/toonz/locatorpopup.h
@@ -0,0 +1,34 @@
+#pragma once
+
+#ifndef LOCATORPOPUP_H
+#define LOCATORPOPUP_H
+
+#include "tgeometry.h"
+#include
+
+class SceneViewer;
+
+//=============================================================================
+// LoactorPopup
+//-----------------------------------------------------------------------------
+
+class LocatorPopup : public QDialog {
+ Q_OBJECT
+ SceneViewer* m_viewer;
+ bool m_initialZoom;
+
+public:
+ LocatorPopup(QWidget* parent = 0);
+ SceneViewer* viewer() { return m_viewer; }
+
+ void onChangeViewAff(const TPointD& curPos);
+
+protected:
+ void showEvent(QShowEvent*);
+ void hideEvent(QHideEvent*);
+
+protected slots:
+ void changeWindowTitle();
+};
+
+#endif
\ No newline at end of file
diff --git a/toonz/sources/toonz/magpiefileimportpopup.cpp b/toonz/sources/toonz/magpiefileimportpopup.cpp
index 5134d72..72a90ab 100644
--- a/toonz/sources/toonz/magpiefileimportpopup.cpp
+++ b/toonz/sources/toonz/magpiefileimportpopup.cpp
@@ -124,7 +124,7 @@ MagpieFileImportPopup::MagpieFileImportPopup()
FlipConsole::eRed | FlipConsole::eGreen | FlipConsole::eBlue |
FlipConsole::eMatte | FlipConsole::eDefineSubCamera |
FlipConsole::eDefineLoadBox | FlipConsole::eUseLoadBox |
- FlipConsole::eFilledRaster));
+ FlipConsole::eFilledRaster | FlipConsole::eLocator));
m_flipbook = new FlipBook(this, tr("Import Magpie File"), buttonMask);
m_flipbook->setFixedHeight(250);
frameLayout->addWidget(m_flipbook);
diff --git a/toonz/sources/toonz/mainwindow.cpp b/toonz/sources/toonz/mainwindow.cpp
index e0acfec..1a070a6 100644
--- a/toonz/sources/toonz/mainwindow.cpp
+++ b/toonz/sources/toonz/mainwindow.cpp
@@ -12,6 +12,7 @@
#include "iocommand.h"
#include "tapp.h"
#include "comboviewerpane.h"
+#include "startuppopup.h"
// TnzTools includes
#include "tools/toolcommandids.h"
@@ -1275,6 +1276,12 @@ void MainWindow::onMenuCheckboxChanged() {
void MainWindow::showEvent(QShowEvent *event) {
getCurrentRoom()->layout()->setEnabled(true); // See main function in
// main.cpp
+ if (Preferences::instance()->isStartupPopupEnabled() &&
+ !m_startupPopupShown) {
+ StartupPopup *startupPopup = new StartupPopup();
+ startupPopup->show();
+ m_startupPopupShown = true;
+ }
}
extern const char *applicationName;
extern const char *applicationVersion;
@@ -1558,9 +1565,9 @@ QAction *MainWindow::createToolAction(const char *id, const char *iconName,
void MainWindow::defineActions() {
createMenuFileAction(MI_NewScene, tr("&New Scene"), "Ctrl+N");
createMenuFileAction(MI_LoadScene, tr("&Load Scene..."), "Ctrl+L");
- createMenuFileAction(MI_SaveScene, tr("&Save Scene"), "Ctrl+S");
- createMenuFileAction(MI_SaveSceneAs, tr("&Save Scene As..."), "Ctrl+Shift+S");
- createMenuFileAction(MI_SaveAll, tr("&Save All"), "");
+ createMenuFileAction(MI_SaveScene, tr("&Save Scene"), "Ctrl+Shift+S");
+ createMenuFileAction(MI_SaveSceneAs, tr("&Save Scene As..."), "");
+ createMenuFileAction(MI_SaveAll, tr("&Save All"), "Ctrl+S");
createMenuFileAction(MI_RevertScene, tr("&Revert Scene"), "");
QAction *act = CommandManager::instance()->getAction(MI_RevertScene);
@@ -1576,9 +1583,10 @@ void MainWindow::defineActions() {
"");
createMenuFileAction(MI_ClearRecentLevel, tr("&Clear Recent level File List"),
"");
- createMenuFileAction(MI_NewLevel, tr("&New Level..."), "");
+ createMenuFileAction(MI_NewLevel, tr("&New Level..."), "Alt+N");
createMenuFileAction(MI_LoadLevel, tr("&Load Level..."), "");
createMenuFileAction(MI_SaveLevel, tr("&Save Level"), "");
+ createMenuFileAction(MI_SaveAllLevels, tr("&Save All Levels"), "");
createMenuFileAction(MI_SaveLevelAs, tr("&Save Level As..."), "");
createMenuFileAction(MI_ExportLevel, tr("&Export Level..."), "");
createMenuFileAction(MI_ConvertFileWithInput, tr("&Convert File..."), "");
@@ -1590,9 +1598,10 @@ void MainWindow::defineActions() {
createMenuFileAction(MI_ProjectSettings, tr("&Project Settings..."), "");
createMenuFileAction(MI_SaveDefaultSettings, tr("&Save Default Settings"),
"");
- createMenuFileAction(MI_OutputSettings, tr("&Output Settings..."), "");
+ createMenuFileAction(MI_OutputSettings, tr("&Output Settings..."), "Ctrl+O");
createMenuFileAction(MI_PreviewSettings, tr("&Preview Settings..."), "");
- createMenuFileAction(MI_Render, tr("&Render"), "");
+ createMenuFileAction(MI_Render, tr("&Render"), "Ctrl+Shift+R");
+ createMenuFileAction(MI_FastRender, tr("&Fast Render to MP4"), "Alt+R");
createMenuFileAction(MI_Preview, tr("&Preview"), "Ctrl+R");
createRightClickMenuAction(MI_SavePreviewedFrames,
tr("&Save Previewed Frames"), "");
@@ -1607,13 +1616,13 @@ void MainWindow::defineActions() {
MI_FreezePreview, tr("Freeze Preview"), tr("Unfreeze Preview"));
// createAction(MI_SavePreview, "&Save Preview", "");
createRightClickMenuAction(MI_SavePreset, tr("&Save As Preset"), "");
- createMenuFileAction(MI_Preferences, tr("&Preferences..."), "");
+ createMenuFileAction(MI_Preferences, tr("&Preferences..."), "Ctrl+U");
createMenuFileAction(MI_ShortcutPopup, tr("&Configure Shortcuts..."), "");
createMenuFileAction(MI_PrintXsheet, tr("&Print Xsheet"), "");
createMenuFileAction("MI_RunScript", tr("Run Script..."), "");
createMenuFileAction("MI_OpenScriptConsole", tr("Open Script Console..."),
"");
- createMenuFileAction(MI_Print, tr("&Print Current Frame..."), "");
+ createMenuFileAction(MI_Print, tr("&Print Current Frame..."), "Ctrl+P");
createMenuFileAction(MI_Quit, tr("&Quit"), "Ctrl+Q");
#ifndef NDEBUG
createMenuFileAction("MI_ReloadStyle", tr("Reload qss"), "");
@@ -1639,10 +1648,14 @@ void MainWindow::defineActions() {
createRightClickMenuAction(MI_PasteNames, tr("Paste Name"), "");
createRightClickMenuAction(MI_GetColorFromStudioPalette,
tr("Get Color from Studio Palette"), "");
+ createRightClickMenuAction(MI_ToggleLinkToStudioPalette,
+ tr("Toggle Link to Studio Palette"), "");
+ createRightClickMenuAction(MI_RemoveReferenceToStudioPalette,
+ tr("Remove Reference to Studio Palette"), "");
createMenuEditAction(MI_Clear, tr("&Delete"), "Delete");
createMenuEditAction(MI_Insert, tr("&Insert"), "Ins");
createMenuEditAction(MI_Group, tr("&Group"), "Ctrl+G");
- createMenuEditAction(MI_Ungroup, tr("&Ungroup"), "");
+ createMenuEditAction(MI_Ungroup, tr("&Ungroup"), "Ctrl+Shift+G");
createMenuEditAction(MI_BringToFront, tr("&Bring to Front"), "Ctrl+]");
createMenuEditAction(MI_BringForward, tr("&Bring Forward"), "]");
createMenuEditAction(MI_SendBack, tr("&Send Back"), "Ctrl+[");
@@ -1677,7 +1690,7 @@ void MainWindow::defineActions() {
MenuScanCleanupCommandType);
CameraTestCheck::instance()->setToggle(toggle);
- createToggle(MI_OpacityCheck, tr("&Opacity Check"), "1", false,
+ createToggle(MI_OpacityCheck, tr("&Opacity Check"), "Alt+1", false,
MenuScanCleanupCommandType);
createMenuScanCleanupAction(MI_Cleanup, tr("&Cleanup"), "");
@@ -1747,8 +1760,8 @@ void MainWindow::defineActions() {
createMenuCellsAction(MI_Increment, tr("&Autoexpose"), "");
createMenuCellsAction(MI_Dup, tr("&Repeat..."), "");
createMenuCellsAction(MI_ResetStep, tr("&Reset Step"), "");
- createMenuCellsAction(MI_IncreaseStep, tr("&Increase Step"), "");
- createMenuCellsAction(MI_DecreaseStep, tr("&Decrease Step"), "");
+ createMenuCellsAction(MI_IncreaseStep, tr("&Increase Step"), "'");
+ createMenuCellsAction(MI_DecreaseStep, tr("&Decrease Step"), ";");
createMenuCellsAction(MI_Step2, tr("&Step 2"), "");
createMenuCellsAction(MI_Step3, tr("&Step 3"), "");
createMenuCellsAction(MI_Step4, tr("&Step 4"), "");
@@ -1762,26 +1775,26 @@ void MainWindow::defineActions() {
createMenuCellsAction(MI_Autorenumber, tr("&Autorenumber"), "");
createMenuCellsAction(MI_CloneLevel, tr("&Clone"), "");
createMenuCellsAction(MI_DrawingSubForward,
- tr("Drawing Substitution Forward"), ".");
+ tr("Drawing Substitution Forward"), "W");
createMenuCellsAction(MI_DrawingSubBackward,
- tr("Drawing Substitution Backward"), ",");
+ tr("Drawing Substitution Backward"), "Q");
createMenuCellsAction(MI_DrawingSubGroupForward,
- tr("Similar Drawing Substitution Forward"), "Ctrl+.");
+ tr("Similar Drawing Substitution Forward"), "Alt+W");
createMenuCellsAction(MI_DrawingSubGroupBackward,
- tr("Similar Drawing Substitution Backward"), "Ctrl+,");
+ tr("Similar Drawing Substitution Backward"), "Alt+Q");
createMenuCellsAction(MI_Reframe1, tr("1's"), "");
createMenuCellsAction(MI_Reframe2, tr("2's"), "");
createMenuCellsAction(MI_Reframe3, tr("3's"), "");
createMenuCellsAction(MI_Reframe4, tr("4's"), "");
- createRightClickMenuAction(MI_SetKeyframes, tr("&Set Key"), "");
+ createRightClickMenuAction(MI_SetKeyframes, tr("&Set Key"), "Z");
createToggle(MI_ViewCamera, tr("&Camera Box"), "",
ViewCameraToggleAction ? 1 : 0, MenuViewCommandType);
createToggle(MI_ViewTable, tr("&Table"), "", ViewTableToggleAction ? 1 : 0,
MenuViewCommandType);
- createToggle(MI_FieldGuide, tr("&Field Guide"), "",
+ createToggle(MI_FieldGuide, tr("&Field Guide"), "Shift+G",
FieldGuideToggleAction ? 1 : 0, MenuViewCommandType);
createToggle(MI_ViewBBox, tr("&Raster Bounding Box"), "",
ViewBBoxToggleAction ? 1 : 0, MenuViewCommandType);
@@ -1840,18 +1853,16 @@ void MainWindow::defineActions() {
createToggle(MI_Link, tr("Link Flipbooks"), "", LinkToggleAction ? 1 : 0,
MenuViewCommandType);
- createPlaybackAction(MI_Play, tr("Play"), "");
- createPlaybackAction(MI_Loop, tr("Loop"), "");
+ createPlaybackAction(MI_Play, tr("Play"), "P");
+ createPlaybackAction(MI_Loop, tr("Loop"), "L");
createPlaybackAction(MI_Pause, tr("Pause"), "");
- createPlaybackAction(MI_FirstFrame, tr("First Frame"), "");
- createPlaybackAction(MI_LastFrame, tr("Last Frame"), "");
- createPlaybackAction(MI_PrevFrame, tr("Previous Frame"), "Shift+A");
- createPlaybackAction(MI_NextFrame, tr("Next Frame"), "Shift+S");
-
- createAction(MI_NextDrawing, tr("Next Drawing"), "Shift+X",
- PlaybackCommandType);
- createAction(MI_PrevDrawing, tr("Prev Drawing"), "Shift+Z",
- PlaybackCommandType);
+ createPlaybackAction(MI_FirstFrame, tr("First Frame"), "Alt+,");
+ createPlaybackAction(MI_LastFrame, tr("Last Frame"), "Alt+.");
+ createPlaybackAction(MI_PrevFrame, tr("Previous Frame"), "Shift+,");
+ createPlaybackAction(MI_NextFrame, tr("Next Frame"), "Shift+.");
+
+ createAction(MI_NextDrawing, tr("Next Drawing"), ".", PlaybackCommandType);
+ createAction(MI_PrevDrawing, tr("Prev Drawing"), ",", PlaybackCommandType);
createAction(MI_NextStep, tr("Next Step"), "", PlaybackCommandType);
createAction(MI_PrevStep, tr("Prev Step"), "", PlaybackCommandType);
@@ -1866,7 +1877,7 @@ void MainWindow::defineActions() {
createViewerAction(MI_CompareToSnapshot, tr("Compare to Snapshot"), "");
createFillAction(MI_AutoFillToggle,
- tr("Toggle Autofill on Current Palette Color"), "");
+ tr("Toggle Autofill on Current Palette Color"), "Shift+A");
toggle =
createToggle(MI_DockingCheck, tr("&Lock Room Panes"), "",
@@ -1908,7 +1919,7 @@ void MainWindow::defineActions() {
// createAction(MI_Export, "Export", "Ctrl+E");
createMenuWindowsAction(MI_OpenComboViewer, tr("&ComboViewer"), "");
- createMenuWindowsAction(MI_OpenHistoryPanel, tr("&History"), "");
+ createMenuWindowsAction(MI_OpenHistoryPanel, tr("&History"), "Ctrl+H");
createMenuWindowsAction(MI_ResetRoomLayout, tr("&Reset to Default Rooms"),
"");
@@ -1917,10 +1928,10 @@ void MainWindow::defineActions() {
tr("Toggle Main Window's Full Screen Mode"),
"Ctrl+`");
createMenuWindowsAction(MI_About, tr("&About OpenToonz..."), "");
-
+ createMenuWindowsAction(MI_StartupPopup, tr("&Startup Popup..."), "Alt+S");
createRightClickMenuAction(MI_BlendColors, tr("&Blend colors"), "");
- createToggle(MI_OnionSkin, tr("Onion Skin Toggle"), "//", false,
+ createToggle(MI_OnionSkin, tr("Onion Skin Toggle"), "/", false,
RightClickMenuCommandType);
createToggle(MI_ZeroThick, tr("Zero Thick Lines"), "Shift+/", false,
RightClickMenuCommandType);
@@ -1991,12 +2002,16 @@ void MainWindow::defineActions() {
createRightClickMenuAction(MI_DisableAllColumns, tr("OFF All"), "");
createRightClickMenuAction(MI_DisableSelectedColumns, tr("OFF Selected"), "");
createRightClickMenuAction(MI_SwapEnabledColumns, tr("Swap ON/OFF"), "");
- createRightClickMenuAction(MI_LockThisColumnOnly, tr("Lock This Only"), "");
- createRightClickMenuAction(MI_LockSelectedColumns, tr("Lock Selected"), "");
- createRightClickMenuAction(MI_LockAllColumns, tr("Lock All"), "");
+ createRightClickMenuAction(MI_LockThisColumnOnly, tr("Lock This Only"),
+ "Shift+L");
+ createRightClickMenuAction(MI_LockSelectedColumns, tr("Lock Selected"),
+ "Ctrl+Shift+L");
+ createRightClickMenuAction(MI_LockAllColumns, tr("Lock All"),
+ "Ctrl+Alt+Shift+L");
createRightClickMenuAction(MI_UnlockSelectedColumns, tr("Unlock Selected"),
- "");
- createRightClickMenuAction(MI_UnlockAllColumns, tr("Unlock All"), "");
+ "Ctrl+Shift+U");
+ createRightClickMenuAction(MI_UnlockAllColumns, tr("Unlock All"),
+ "Ctrl+Alt+Shift+U");
createRightClickMenuAction(MI_ToggleColumnLocks, tr("Swap Lock/Unlock"), "");
/*-- カレントカラムの右側のカラムを全て非表示にするコマンド --*/
createRightClickMenuAction(MI_DeactivateUpperColumns,
@@ -2012,31 +2027,32 @@ void MainWindow::defineActions() {
createToolAction(T_Eraser, "eraser", tr("Eraser Tool"), "A");
createToolAction(T_Tape, "tape", tr("Tape Tool"), "T");
createToolAction(T_StylePicker, "stylepicker", tr("Style Picker Tool"), "K");
- createToolAction(T_RGBPicker, "RGBpicker", tr("RGB Picker Tool"), "");
+ createToolAction(T_RGBPicker, "RGBpicker", tr("RGB Picker Tool"), "R");
createToolAction(T_ControlPointEditor, "controlpointeditor",
tr("Control Point Editor Tool"), "C");
- createToolAction(T_Pinch, "pinch", tr("Pinch Tool"), "P");
+ createToolAction(T_Pinch, "pinch", tr("Pinch Tool"), "M");
createToolAction(T_Pump, "pump", tr("Pump Tool"), "");
createToolAction(T_Magnet, "magnet", tr("Magnet Tool"), "");
createToolAction(T_Bender, "bender", tr("Bender Tool"), "");
createToolAction(T_Iron, "iron", tr("Iron Tool"), "");
createToolAction(T_Cutter, "cutter", tr("Cutter Tool"), "");
- createToolAction(T_Skeleton, "skeleton", tr("Skeleton Tool"), "");
+ createToolAction(T_Skeleton, "skeleton", tr("Skeleton Tool"), "V");
createToolAction(T_Tracker, "tracker", tr("Tracker Tool"), "");
- createToolAction(T_Hook, "hook", tr("Hook Tool"), "");
+ createToolAction(T_Hook, "hook", tr("Hook Tool"), "O");
createToolAction(T_Zoom, "zoom", tr("Zoom Tool"), "Shift+Space");
createToolAction(T_Rotate, "rotate", tr("Rotate Tool"), "Ctrl+Space");
createToolAction(T_Hand, "hand", tr("Hand Tool"), "Space");
- createToolAction(T_Plastic, "plastic", tr("Plastic Tool"), "");
+ createToolAction(T_Plastic, "plastic", tr("Plastic Tool"), "X");
createToolAction(T_Ruler, "ruler", tr("Ruler Tool"), "");
createToolAction(T_Finger, "finger", tr("Finger Tool"), "");
createViewerAction(V_ZoomIn, tr("Zoom In"), "+");
createViewerAction(V_ZoomOut, tr("Zoom Out"), "-");
- createViewerAction(V_ZoomReset, tr("Reset View"), "0");
- createViewerAction(V_ZoomFit, tr("Fit to Window"), "");
+ createViewerAction(V_ZoomReset, tr("Reset View"), "Alt+0");
+ createViewerAction(V_ZoomFit, tr("Fit to Window"), "Alt+9");
createViewerAction(V_ActualPixelSize, tr("Actual Pixel Size"), "N");
- createViewerAction(V_ShowHideFullScreen, tr("Show//Hide Full Screen"), "");
+ createViewerAction(V_ShowHideFullScreen, tr("Show//Hide Full Screen"),
+ "Alt+F");
CommandManager::instance()->setToggleTexts(V_ShowHideFullScreen,
tr("Full Screen Mode"),
tr("Exit Full Screen Mode"));
@@ -2046,13 +2062,13 @@ void MainWindow::defineActions() {
createToolOptionsAction("A_ToolOption_GlobalKey", tr("Global Key"), "");
createToolOptionsAction("A_IncreaseMaxBrushThickness",
- tr("Brush size - Increase max"), "");
+ tr("Brush size - Increase max"), "I");
createToolOptionsAction("A_DecreaseMaxBrushThickness",
- tr("Brush size - Decrease max"), "");
+ tr("Brush size - Decrease max"), "U");
createToolOptionsAction("A_IncreaseMinBrushThickness",
- tr("Brush size - Increase min"), "");
+ tr("Brush size - Increase min"), "J");
createToolOptionsAction("A_DecreaseMinBrushThickness",
- tr("Brush size - Decrease min"), "");
+ tr("Brush size - Decrease min"), "H");
createToolOptionsAction("A_IncreaseBrushHardness",
tr("Brush hardness - Increase"), "");
createToolOptionsAction("A_DecreaseBrushHardness",
@@ -2071,7 +2087,7 @@ void MainWindow::defineActions() {
createToolOptionsAction("A_ToolOption_PreserveThickness",
tr("Preserve Thickness"), "");
createToolOptionsAction("A_ToolOption_PressureSensitivity",
- tr("Pressure Sensitivity"), "");
+ tr("Pressure Sensitivity"), "Shift+P");
createToolOptionsAction("A_ToolOption_SegmentInk", tr("Segment Ink"), "F8");
createToolOptionsAction("A_ToolOption_Selective", tr("Selective"), "F7");
createToolOptionsAction("A_ToolOption_Smooth", tr("Smooth"), "");
diff --git a/toonz/sources/toonz/mainwindow.h b/toonz/sources/toonz/mainwindow.h
index 8efc118..4eb088a 100644
--- a/toonz/sources/toonz/mainwindow.h
+++ b/toonz/sources/toonz/mainwindow.h
@@ -67,6 +67,7 @@ class MainWindow final : public QMainWindow {
Q_OBJECT
bool m_saveSettingsOnQuit;
+ bool m_startupPopupShown = false;
int m_oldRoomIndex;
QString m_currentRoomsChoice;
UpdateChecker *m_updateChecker;
@@ -212,6 +213,7 @@ signals:
};
class RecentFiles {
+ friend class StartupPopup;
QList m_recentScenes;
QList m_recentLevels;
QList m_recentFlipbookImages;
diff --git a/toonz/sources/toonz/menubar.cpp b/toonz/sources/toonz/menubar.cpp
index 512c136..97b4398 100644
--- a/toonz/sources/toonz/menubar.cpp
+++ b/toonz/sources/toonz/menubar.cpp
@@ -1077,6 +1077,7 @@ QMenuBar *StackedMenuBar::createFullMenuBar() {
fileMenu->addSeparator();
addMenuItem(fileMenu, MI_NewLevel);
addMenuItem(fileMenu, MI_LoadLevel);
+ addMenuItem(fileMenu, MI_SaveAllLevels);
addMenuItem(fileMenu, MI_SaveLevel);
addMenuItem(fileMenu, MI_SaveLevelAs);
addMenuItem(fileMenu, MI_ExportLevel);
@@ -1098,6 +1099,7 @@ QMenuBar *StackedMenuBar::createFullMenuBar() {
fileMenu->addSeparator();
addMenuItem(fileMenu, MI_OutputSettings);
addMenuItem(fileMenu, MI_Render);
+ addMenuItem(fileMenu, MI_FastRender);
// addMenuItem(fileMenu, MI_SavePreviewedFrames);
fileMenu->addSeparator();
addMenuItem(fileMenu, MI_PrintXsheet);
@@ -1343,6 +1345,7 @@ QMenuBar *StackedMenuBar::createFullMenuBar() {
//---Help Menu
QMenu *helpMenu = addMenu(tr("Help"), fullMenuBar);
+ addMenuItem(helpMenu, MI_StartupPopup);
addMenuItem(helpMenu, MI_About);
return fullMenuBar;
diff --git a/toonz/sources/toonz/menubarcommandids.h b/toonz/sources/toonz/menubarcommandids.h
index ac9a5bf..0b7f96b 100644
--- a/toonz/sources/toonz/menubarcommandids.h
+++ b/toonz/sources/toonz/menubarcommandids.h
@@ -16,6 +16,7 @@
#define MI_SaveScene "MI_SaveScene"
#define MI_SaveSceneAs "MI_SaveSceneAs"
#define MI_SaveAll "MI_SaveAll"
+#define MI_SaveAllLevels "MI_SaveAllLevels"
#define MI_RevertScene "MI_RevertScene"
#define MI_LoadSubSceneFile "MI_LoadSubSceneFile"
@@ -40,6 +41,7 @@
#define MI_OutputSettings "MI_OutputSettings"
#define MI_PreviewSettings "MI_PreviewSettings"
#define MI_Render "MI_Render"
+#define MI_FastRender "MI_FastRender"
#define MI_Preview "MI_Preview"
#define MI_RegeneratePreview "MI_RegeneratePreview"
#define MI_RegenerateFramePr "MI_RegenerateFramePr"
@@ -310,5 +312,6 @@
#define MI_PreviewFx "MI_PreviewFx"
#define MI_About "MI_About"
+#define MI_StartupPopup "MI_StartupPopup"
#define MI_PencilTest "MI_PencilTest"
#endif
diff --git a/toonz/sources/toonz/penciltestpopup.cpp b/toonz/sources/toonz/penciltestpopup.cpp
index 2a74e88..02fb1b2 100644
--- a/toonz/sources/toonz/penciltestpopup.cpp
+++ b/toonz/sources/toonz/penciltestpopup.cpp
@@ -65,6 +65,11 @@
#include
#include
#include
+#include
+
+#ifdef _WIN32
+#include
+#endif
using namespace DVGui;
@@ -305,6 +310,90 @@ int letterToNum(QChar appendix) {
return 0;
}
+#ifdef _WIN32
+void openCaptureFilterSettings(const QWidget* parent,
+ const QString& cameraName) {
+ HRESULT hr;
+
+ ICreateDevEnum* createDevEnum = NULL;
+ IEnumMoniker* enumMoniker = NULL;
+ IMoniker* moniker = NULL;
+
+ IBaseFilter* deviceFilter;
+
+ ISpecifyPropertyPages* specifyPropertyPages;
+ CAUUID cauuid;
+ // set parent's window handle in order to make the dialog modal
+ HWND ghwndApp = (HWND)(parent->winId());
+
+ // initialize COM
+ CoInitialize(NULL);
+
+ // get device list
+ CoCreateInstance(CLSID_SystemDeviceEnum, NULL, CLSCTX_INPROC_SERVER,
+ IID_ICreateDevEnum, (PVOID*)&createDevEnum);
+
+ // create EnumMoniker
+ createDevEnum->CreateClassEnumerator(CLSID_VideoInputDeviceCategory,
+ &enumMoniker, 0);
+ if (enumMoniker == NULL) {
+ // if no connected devices found
+ return;
+ }
+
+ // reset EnumMoniker
+ enumMoniker->Reset();
+
+ // find target camera
+ ULONG fetched = 0;
+ bool isCameraFound = false;
+ while (hr = enumMoniker->Next(1, &moniker, &fetched), hr == S_OK) {
+ // get friendly name (= device name) of the camera
+ IPropertyBag* pPropertyBag;
+ moniker->BindToStorage(0, 0, IID_IPropertyBag, (void**)&pPropertyBag);
+ VARIANT var;
+ var.vt = VT_BSTR;
+ VariantInit(&var);
+
+ pPropertyBag->Read(L"FriendlyName", &var, 0);
+
+ QString deviceName = QString::fromWCharArray(var.bstrVal);
+
+ VariantClear(&var);
+
+ if (deviceName == cameraName) {
+ // bind monkier to the filter
+ moniker->BindToObject(0, 0, IID_IBaseFilter, (void**)&deviceFilter);
+
+ // release moniker etc.
+ moniker->Release();
+ enumMoniker->Release();
+ createDevEnum->Release();
+
+ isCameraFound = true;
+ break;
+ }
+ }
+
+ // if no matching camera found
+ if (!isCameraFound) return;
+
+ // open capture filter popup
+ hr = deviceFilter->QueryInterface(IID_ISpecifyPropertyPages,
+ (void**)&specifyPropertyPages);
+ if (hr == S_OK) {
+ hr = specifyPropertyPages->GetPages(&cauuid);
+
+ hr = OleCreatePropertyFrame(ghwndApp, 30, 30, NULL, 1,
+ (IUnknown**)&deviceFilter, cauuid.cElems,
+ (GUID*)cauuid.pElems, 0, 0, NULL);
+
+ CoTaskMemFree(cauuid.pElems);
+ specifyPropertyPages->Release();
+ }
+}
+#endif
+
} // namespace
//=============================================================================
@@ -547,6 +636,12 @@ PencilTestPopup::PencilTestPopup()
m_captureButton = new QPushButton(tr("Capture\n[Return key]"), this);
QPushButton* closeButton = new QPushButton(tr("Close"), this);
+
+#ifdef _WIN32
+ m_captureFilterSettingsBtn = new QPushButton(this);
+#else
+ m_captureFilterSettingsBtn = 0;
+#endif
//----
m_resolutionCombo->setMaximumWidth(fontMetrics().width("0000 x 0000") + 25);
@@ -598,6 +693,14 @@ PencilTestPopup::PencilTestPopup()
m_captureButton->setIcon(style.standardIcon(QStyle::SP_DialogOkButton));
m_captureButton->setIconSize(QSize(30, 30));
+ if (m_captureFilterSettingsBtn) {
+ m_captureFilterSettingsBtn->setObjectName("GearButton");
+ m_captureFilterSettingsBtn->setFixedSize(23, 23);
+ m_captureFilterSettingsBtn->setIconSize(QSize(15, 15));
+ m_captureFilterSettingsBtn->setToolTip(
+ tr("Video Capture Filter Settings..."));
+ }
+
//---- layout ----
QHBoxLayout* mainLay = new QHBoxLayout();
mainLay->setMargin(0);
@@ -617,6 +720,12 @@ PencilTestPopup::PencilTestPopup()
camLay->addSpacing(10);
camLay->addWidget(new QLabel(tr("Resolution:"), this), 0);
camLay->addWidget(m_resolutionCombo, 1);
+
+ if (m_captureFilterSettingsBtn) {
+ camLay->addSpacing(10);
+ camLay->addWidget(m_captureFilterSettingsBtn);
+ }
+
camLay->addStretch(0);
}
leftLay->addLayout(camLay, 0);
@@ -788,6 +897,9 @@ PencilTestPopup::PencilTestPopup()
ret = ret && connect(closeButton, SIGNAL(clicked()), this, SLOT(reject()));
ret = ret && connect(m_captureButton, SIGNAL(clicked(bool)), this,
SLOT(onCaptureButtonClicked(bool)));
+ if (m_captureFilterSettingsBtn)
+ ret = ret && connect(m_captureFilterSettingsBtn, SIGNAL(pressed()), this,
+ SLOT(onCaptureFilterSettingsBtnPressed()));
assert(ret);
refreshCameraList();
@@ -1403,4 +1515,20 @@ bool PencilTestPopup::importImage(QImage& image) {
//-----------------------------------------------------------------------------
+void PencilTestPopup::onCaptureFilterSettingsBtnPressed() {
+ if (!m_currentCamera || m_deviceName.isNull()) return;
+
+ QList cameras = QCameraInfo::availableCameras();
+ for (int c = 0; c < cameras.size(); c++) {
+ if (cameras.at(c).deviceName() == m_deviceName) {
+#ifdef _WIN32
+ openCaptureFilterSettings(this, cameras.at(c).description());
+#endif
+ return;
+ }
+ }
+}
+
+//-----------------------------------------------------------------------------
+
OpenPopupCommandHandler openPencilTestPopup(MI_PencilTest);
\ No newline at end of file
diff --git a/toonz/sources/toonz/penciltestpopup.h b/toonz/sources/toonz/penciltestpopup.h
index 94b1172..0ff31f4 100644
--- a/toonz/sources/toonz/penciltestpopup.h
+++ b/toonz/sources/toonz/penciltestpopup.h
@@ -21,6 +21,7 @@ class QVideoFrame;
class QTimer;
class QIntValidator;
class QRegExpValidator;
+class QPushButton;
namespace DVGui {
class FileField;
@@ -147,6 +148,9 @@ class PencilTestPopup : public DVGui::Dialog {
QImage m_whiteBGImg;
+ // used only for Windows
+ QPushButton* m_captureFilterSettingsBtn;
+
int m_timerId;
QString m_cacheImagePath;
bool m_captureWhiteBGCue;
@@ -183,6 +187,7 @@ protected slots:
void onCountDown();
void onCaptureButtonClicked(bool);
+ void onCaptureFilterSettingsBtnPressed();
};
#endif
\ No newline at end of file
diff --git a/toonz/sources/toonz/preferencespopup.cpp b/toonz/sources/toonz/preferencespopup.cpp
index 09064aa..2b518ae 100644
--- a/toonz/sources/toonz/preferencespopup.cpp
+++ b/toonz/sources/toonz/preferencespopup.cpp
@@ -359,7 +359,7 @@ void PreferencesPopup::onChunkSizeChanged() {
void PreferencesPopup::onBlankCountChanged() {
if (m_blanksCount && m_blankColor)
m_pref->setBlankValues(m_blanksCount->getValue(), m_blankColor->getColor());
- TApp::instance()->getCurrentScene()->notifyPreferenceChanged();
+ TApp::instance()->getCurrentScene()->notifyPreferenceChanged("BlankCount");
}
//-----------------------------------------------------------------------------
@@ -378,7 +378,7 @@ void PreferencesPopup::onBlankColorChanged(const TPixel32 &, bool isDragging) {
if (m_blanksCount && m_blankColor)
m_pref->setBlankValues(m_blanksCount->getValue(), m_blankColor->getColor());
- TApp::instance()->getCurrentScene()->notifyPreferenceChanged();
+ TApp::instance()->getCurrentScene()->notifyPreferenceChanged("BlankColor");
}
//-----------------------------------------------------------------------------
@@ -554,9 +554,37 @@ void PreferencesPopup::onDefaultViewerChanged(int index) {
//-----------------------------------------------------------------------------
-void PreferencesPopup::onAutoSaveChanged(int index) {
- m_minuteFld->setEnabled(index == Qt::Checked);
- m_pref->enableAutosave(index == Qt::Checked);
+void PreferencesPopup::onAutoSaveChanged(bool on) {
+ m_pref->enableAutosave(on);
+ if (on && !m_autoSaveSceneCB->isChecked() &&
+ !m_autoSaveOtherFilesCB->isChecked()) {
+ m_autoSaveSceneCB->setChecked(true);
+ m_autoSaveOtherFilesCB->setChecked(true);
+ }
+}
+
+//-----------------------------------------------------------------------------
+
+void PreferencesPopup::onAutoSaveSceneChanged(int index) {
+ m_pref->enableAutosaveScene(index == Qt::Checked);
+ if (!m_autoSaveOtherFilesCB->isChecked() && index == Qt::Unchecked) {
+ m_autoSaveGroup->setChecked(false);
+ }
+}
+
+//-----------------------------------------------------------------------------
+
+void PreferencesPopup::onAutoSaveOtherFilesChanged(int index) {
+ m_pref->enableAutosaveOtherFiles(index == Qt::Checked);
+ if (!m_autoSaveSceneCB->isChecked() && index == Qt::Unchecked) {
+ m_autoSaveGroup->setChecked(false);
+ }
+}
+
+//-----------------------------------------------------------------------------
+
+void PreferencesPopup::onStartupPopupChanged(int index) {
+ m_pref->enableStartupPopup(index == Qt::Checked);
}
//-----------------------------------------------------------------------------
@@ -895,10 +923,58 @@ void PreferencesPopup::onFfmpegPathChanged() {
//-----------------------------------------------------------------------------
+void PreferencesPopup::onFastRenderPathChanged() {
+ QString text = m_fastRenderPathFileField->getPath();
+ m_pref->setFastRenderPath(text.toStdString());
+}
+
+//-----------------------------------------------------------------------------
+
void PreferencesPopup::onFfmpegTimeoutChanged() {
m_pref->setFfmpegTimeout(m_ffmpegTimeout->getValue());
}
+//-----------------------------------------------------------------------------
+
+void PreferencesPopup::onUseNumpadForSwitchingStylesClicked(bool checked) {
+ if (checked) {
+ // check if there are any commands with numpadkey shortcuts
+ CommandManager *cm = CommandManager::instance();
+ QList actionsList;
+ for (int key = Qt::Key_0; key <= Qt::Key_9; key++) {
+ std::string str = QKeySequence(key).toString().toStdString();
+ QAction *action = cm->getActionFromShortcut(str);
+ if (action) actionsList.append(action);
+ }
+ QAction *tabAction = cm->getActionFromShortcut("Tab");
+ if (tabAction) actionsList.append(tabAction);
+ tabAction = cm->getActionFromShortcut("Shift+Tab");
+ if (tabAction) actionsList.append(tabAction);
+ // if there are actions using numpad shortcuts, notify to release them.
+ if (!actionsList.isEmpty()) {
+ QString msgStr =
+ tr("Numpad keys are assigned to the following commands.\nIs it OK to "
+ "release these shortcuts?");
+ for (int a = 0; a < actionsList.size(); a++) {
+ msgStr += "\n" + actionsList.at(a)->iconText() + " (" +
+ actionsList.at(a)->shortcut().toString() + ")";
+ }
+ int ret = DVGui::MsgBox(msgStr, tr("OK"), tr("Cancel"), 1);
+ if (ret == 2 || ret == 0) { // canceled
+ m_useNumpadForSwitchingStyles->setChecked(false);
+ return;
+ } else { // accepted, then release shortcuts
+ for (int a = 0; a < actionsList.size(); a++)
+ cm->setShortcut(actionsList[a], "");
+ }
+ }
+ }
+ m_pref->enableUseNumpadForSwitchingStyles(checked);
+ // emit signal to update Palette and Viewer
+ TApp::instance()->getCurrentScene()->notifyPreferenceChanged(
+ "NumpadForSwitchingStyles");
+}
+
//**********************************************************************************
// PrefencesPopup's constructor
//**********************************************************************************
@@ -926,8 +1002,14 @@ PreferencesPopup::PreferencesPopup()
new CheckBox(tr("Use Default Viewer for Movie Formats"), this);
CheckBox *minimizeRasterMemoryCB =
new CheckBox(tr("Minimize Raster Memory Fragmentation *"), this);
- CheckBox *autoSaveCB = new CheckBox(tr("Save Automatically Every Minutes"));
- m_minuteFld = new DVGui::IntLineEdit(this, 15, 1, 60);
+ m_autoSaveGroup = new QGroupBox(tr("Save Automatically"), this);
+ m_autoSaveGroup->setCheckable(true);
+ m_autoSaveSceneCB = new CheckBox(tr("Automatically Save the Scene File"));
+ m_autoSaveOtherFilesCB =
+ new CheckBox(tr("Automatically Save Non-Scene Files"));
+ CheckBox *startupPopupCB =
+ new CheckBox(tr("Show Startup Window when OpenToonz Starts"));
+ m_minuteFld = new DVGui::IntLineEdit(this, 15, 1, 60);
CheckBox *replaceAfterSaveLevelAsCB =
new CheckBox(tr("Replace Toonz Level after SaveLevelAs command"), this);
@@ -1043,7 +1125,9 @@ PreferencesPopup::PreferencesPopup()
//--- Import/Export ------------------------------
categoryList->addItem(tr("Import/Export"));
m_ffmpegPathFileFld = new DVGui::FileField(this, QString(""));
- m_ffmpegTimeout = new DVGui::IntLineEdit(this, 30, 1);
+ m_fastRenderPathFileField =
+ new DVGui::FileField(this, QString("desktop"), false, true);
+ m_ffmpegTimeout = new DVGui::IntLineEdit(this, 30, 1);
//--- Drawing ------------------------------
categoryList->addItem(tr("Drawing"));
@@ -1063,6 +1147,8 @@ PreferencesPopup::PreferencesPopup()
new CheckBox(tr("Use the TLV Savebox to Limit Filling Operations"), this);
CheckBox *minimizeSaveboxAfterEditingCB =
new CheckBox(tr("Minimize Savebox after Editing"), this);
+ m_useNumpadForSwitchingStyles =
+ new CheckBox(tr("Use Numpad and Tab keys for Switching Styles"), this);
//--- Xsheet ------------------------------
categoryList->addItem(tr("Xsheet"));
@@ -1137,9 +1223,11 @@ PreferencesPopup::PreferencesPopup()
//--- General ------------------------------
useDefaultViewerCB->setChecked(m_pref->isDefaultViewerEnabled());
minimizeRasterMemoryCB->setChecked(m_pref->isRasterOptimizedMemory());
- autoSaveCB->setChecked(m_pref->isAutosaveEnabled());
+ m_autoSaveGroup->setChecked(m_pref->isAutosaveEnabled());
+ m_autoSaveSceneCB->setChecked(m_pref->isAutosaveSceneEnabled());
+ m_autoSaveOtherFilesCB->setChecked(m_pref->isAutosaveOtherFilesEnabled());
m_minuteFld->setValue(m_pref->getAutosavePeriod());
- m_minuteFld->setEnabled(m_pref->isAutosaveEnabled());
+ startupPopupCB->setChecked(m_pref->isStartupPopupEnabled());
replaceAfterSaveLevelAsCB->setChecked(
m_pref->isReplaceAfterSaveLevelAsEnabled());
@@ -1263,6 +1351,8 @@ PreferencesPopup::PreferencesPopup()
//--- Import/Export ------------------------------
QString path = m_pref->getFfmpegPath();
m_ffmpegPathFileFld->setPath(path);
+ path = m_pref->getFastRenderPath();
+ m_fastRenderPathFileField->setPath(path);
m_ffmpegTimeout->setValue(m_pref->getFfmpegTimeout());
//--- Drawing ------------------------------
@@ -1271,6 +1361,8 @@ PreferencesPopup::PreferencesPopup()
minimizeSaveboxAfterEditingCB->setChecked(
m_pref->isMinimizeSaveboxAfterEditing());
useSaveboxToLimitFillingOpCB->setChecked(m_pref->getFillOnlySavebox());
+ m_useNumpadForSwitchingStyles->setChecked(
+ m_pref->isUseNumpadForSwitchingStylesEnabled());
QStringList scanLevelTypes;
scanLevelTypes << "tif"
@@ -1384,16 +1476,29 @@ PreferencesPopup::PreferencesPopup()
Qt::AlignLeft | Qt::AlignVCenter);
generalFrameLay->addWidget(minimizeRasterMemoryCB, 0,
Qt::AlignLeft | Qt::AlignVCenter);
- QHBoxLayout *saveAutoLay = new QHBoxLayout();
- saveAutoLay->setMargin(0);
- saveAutoLay->setSpacing(15);
+
+ QVBoxLayout *autoSaveOptionsLay = new QVBoxLayout();
+ autoSaveOptionsLay->setMargin(10);
{
- saveAutoLay->addWidget(autoSaveCB, 0);
- saveAutoLay->addWidget(m_minuteFld, 0);
- saveAutoLay->addStretch(1);
- }
- generalFrameLay->addLayout(saveAutoLay, 0);
+ QHBoxLayout *saveAutoLay = new QHBoxLayout();
+ saveAutoLay->setMargin(0);
+ saveAutoLay->setSpacing(5);
+ {
+ saveAutoLay->addWidget(new QLabel(tr("Interval(Minutes): "), this));
+ saveAutoLay->addWidget(m_minuteFld, 0);
+ saveAutoLay->addStretch(1);
+ }
+ autoSaveOptionsLay->addLayout(saveAutoLay, 0);
+ autoSaveOptionsLay->addWidget(m_autoSaveSceneCB, 0,
+ Qt::AlignLeft | Qt::AlignVCenter);
+ autoSaveOptionsLay->addWidget(m_autoSaveOtherFilesCB, 0,
+ Qt::AlignLeft | Qt::AlignVCenter);
+ }
+ m_autoSaveGroup->setLayout(autoSaveOptionsLay);
+ generalFrameLay->addWidget(m_autoSaveGroup);
+ generalFrameLay->addWidget(startupPopupCB, 0,
+ Qt::AlignLeft | Qt::AlignVCenter);
// Unit, CameraUnit
QGridLayout *unitLay = new QGridLayout();
unitLay->setMargin(0);
@@ -1661,6 +1766,14 @@ PreferencesPopup::PreferencesPopup()
ioGridLay->addWidget(new QLabel(tr("FFmpeg Timeout:")), 4, 0,
Qt::AlignRight);
ioGridLay->addWidget(m_ffmpegTimeout, 4, 1, 1, 3);
+ ioGridLay->addWidget(new QLabel(" "), 5, 0);
+ ioGridLay->addWidget(
+ new QLabel(tr("Please indicate where you would like "
+ "exports from Fast Render(MP4) to go.")),
+ 6, 0, 1, 4);
+ ioGridLay->addWidget(new QLabel(tr("Fast Render Path: ")), 7, 0,
+ Qt::AlignRight);
+ ioGridLay->addWidget(m_fastRenderPathFileField, 7, 1, 1, 3);
}
ioLay->addLayout(ioGridLay);
ioLay->addStretch(1);
@@ -1711,6 +1824,9 @@ PreferencesPopup::PreferencesPopup()
Qt::AlignLeft | Qt::AlignVCenter);
drawingFrameLay->addWidget(multiLayerStylePickerCB, 0,
Qt::AlignLeft | Qt::AlignVCenter);
+ drawingFrameLay->addWidget(m_useNumpadForSwitchingStyles, 0,
+ Qt::AlignLeft | Qt::AlignVCenter);
+
drawingFrameLay->addStretch(1);
}
drawingBox->setLayout(drawingFrameLay);
@@ -1903,10 +2019,16 @@ PreferencesPopup::PreferencesPopup()
SLOT(onDefaultViewerChanged(int)));
ret = ret && connect(minimizeRasterMemoryCB, SIGNAL(stateChanged(int)), this,
SLOT(onRasterOptimizedMemoryChanged(int)));
- ret = ret && connect(autoSaveCB, SIGNAL(stateChanged(int)),
- SLOT(onAutoSaveChanged(int)));
+ ret = ret && connect(m_autoSaveGroup, SIGNAL(toggled(bool)),
+ SLOT(onAutoSaveChanged(bool)));
+ ret = ret && connect(m_autoSaveSceneCB, SIGNAL(stateChanged(int)),
+ SLOT(onAutoSaveSceneChanged(int)));
+ ret = ret && connect(m_autoSaveOtherFilesCB, SIGNAL(stateChanged(int)),
+ SLOT(onAutoSaveOtherFilesChanged(int)));
ret = ret && connect(m_minuteFld, SIGNAL(editingFinished()),
SLOT(onMinuteChanged()));
+ ret = ret && connect(startupPopupCB, SIGNAL(stateChanged(int)),
+ SLOT(onStartupPopupChanged(int)));
ret = ret && connect(m_cellsDragBehaviour, SIGNAL(currentIndexChanged(int)),
SLOT(onDragCellsBehaviourChanged(int)));
ret = ret && connect(m_undoMemorySize, SIGNAL(editingFinished()),
@@ -2025,6 +2147,8 @@ PreferencesPopup::PreferencesPopup()
//--- Import/Export ----------------------
ret = ret && connect(m_ffmpegPathFileFld, SIGNAL(pathChanged()), this,
SLOT(onFfmpegPathChanged()));
+ ret = ret && connect(m_fastRenderPathFileField, SIGNAL(pathChanged()), this,
+ SLOT(onFastRenderPathChanged()));
ret = ret && connect(m_ffmpegTimeout, SIGNAL(editingFinished()), this,
SLOT(onFfmpegTimeoutChanged()));
@@ -2050,6 +2174,8 @@ PreferencesPopup::PreferencesPopup()
SLOT(onDefLevelParameterChanged()));
ret = ret && connect(m_defLevelDpi, SIGNAL(valueChanged()),
SLOT(onDefLevelParameterChanged()));
+ ret = ret && connect(m_useNumpadForSwitchingStyles, SIGNAL(clicked(bool)),
+ SLOT(onUseNumpadForSwitchingStylesClicked(bool)));
//--- Xsheet ----------------------
ret = ret && connect(xsheetAutopanDuringPlaybackCB, SIGNAL(stateChanged(int)),
diff --git a/toonz/sources/toonz/preferencespopup.h b/toonz/sources/toonz/preferencespopup.h
index 74290c8..ddc1be1 100644
--- a/toonz/sources/toonz/preferencespopup.h
+++ b/toonz/sources/toonz/preferencespopup.h
@@ -24,6 +24,7 @@
class QLineEdit;
class QPushButton;
class QLabel;
+class QGroupBox;
//==============================================================
@@ -70,11 +71,14 @@ private:
DVGui::CheckBox *m_inksOnly, *m_enableVersionControl, *m_levelsBackup,
*m_onionSkinVisibility, *m_pixelsOnlyCB, *m_projectRootDocuments,
*m_projectRootDesktop, *m_projectRootCustom, *m_projectRootStuff,
- *m_onionSkinDuringPlayback;
+ *m_onionSkinDuringPlayback, *m_autoSaveSceneCB, *m_autoSaveOtherFilesCB,
+ *m_useNumpadForSwitchingStyles;
DVGui::FileField *m_customProjectRootFileField;
- DVGui::FileField *m_ffmpegPathFileFld;
+ DVGui::FileField *m_ffmpegPathFileFld, *m_fastRenderPathFileField;
+
+ QGroupBox *m_autoSaveGroup;
private:
// QWidget* create(const QString& lbl, bool def, const char* slot);
@@ -104,7 +108,10 @@ private slots:
void onRasterOptimizedMemoryChanged(int index);
void onSaveUnpaintedInCleanupChanged(int index);
void onMinimizeSaveboxAfterEditing(int index);
- void onAutoSaveChanged(int index);
+ void onAutoSaveChanged(bool on);
+ void onAutoSaveSceneChanged(int index);
+ void onAutoSaveOtherFilesChanged(int index);
+ void onStartupPopupChanged(int index);
void onDefaultViewerChanged(int index);
void onBlankCountChanged();
void onBlankColorChanged(const TPixel32 &, bool isDragging);
@@ -161,6 +168,8 @@ private slots:
void onShowKeyframesOnCellAreaChanged(int);
void onFfmpegPathChanged();
void onFfmpegTimeoutChanged();
+ void onFastRenderPathChanged();
+ void onUseNumpadForSwitchingStylesClicked(bool);
};
//**********************************************************************************
diff --git a/toonz/sources/toonz/rendercommand.cpp b/toonz/sources/toonz/rendercommand.cpp
index adaf9f8..5af6af1 100644
--- a/toonz/sources/toonz/rendercommand.cpp
+++ b/toonz/sources/toonz/rendercommand.cpp
@@ -214,6 +214,7 @@ public:
, m_timeStretchFactor(1)
, m_multimediaRender(0) {
setCommandHandler("MI_Render", this, &RenderCommand::onRender);
+ setCommandHandler("MI_FastRender", this, &RenderCommand::onFastRender);
setCommandHandler("MI_Preview", this, &RenderCommand::onPreview);
}
@@ -222,6 +223,7 @@ public:
void rasterRender(bool isPreview);
void multimediaRender();
void onRender();
+ void onFastRender();
void onPreview();
static void resetBgColor();
void doRender(bool isPreview);
@@ -788,6 +790,38 @@ void RenderCommand::multimediaRender() {
void RenderCommand::onRender() { doRender(false); }
+void RenderCommand::onFastRender() {
+ TOutputProperties *prop = TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getProperties()
+ ->getOutputProperties();
+ QString sceneName = QString::fromStdWString(
+ TApp::instance()->getCurrentScene()->getScene()->getSceneName());
+ QString location = Preferences::instance()->getFastRenderPath();
+ if (location == "desktop" || location == "Desktop") {
+ location =
+ QStandardPaths::writableLocation(QStandardPaths::DesktopLocation);
+ }
+ TFilePath path = TFilePath(location) + TFilePath(sceneName + ".mp4");
+ TFilePath currPath = prop->getPath();
+
+ QStringList formats;
+ TImageWriter::getSupportedFormats(formats, true);
+ TLevelWriter::getSupportedFormats(formats, true);
+ Tiio::Writer::getSupportedFormats(formats, true);
+ if (!formats.contains("mp4")) {
+ QString msg = QObject::tr(
+ "FFmpeg not found, please set the location in the Preferences and "
+ "restart.");
+ DVGui::warning(msg);
+ return;
+ }
+ prop->setPath(path);
+ doRender(false);
+ prop->setPath(currPath);
+}
+
void RenderCommand::onPreview() { doRender(true); }
//---------------------------------------------------------
diff --git a/toonz/sources/toonz/sceneviewer.cpp b/toonz/sources/toonz/sceneviewer.cpp
index d039b34..1b521a2 100644
--- a/toonz/sources/toonz/sceneviewer.cpp
+++ b/toonz/sources/toonz/sceneviewer.cpp
@@ -10,6 +10,7 @@
#include "viewerdraw.h"
#include "menubarcommandids.h"
#include "ruler.h"
+#include "locatorpopup.h"
// TnzTools includes
#include "tools/cursors.h"
@@ -501,9 +502,9 @@ SceneViewer::SceneViewer(ImageUtils::FullScreenWidget *parent)
, m_sideRasterPos()
, m_topRasterPos()
, m_toolDisableReason("")
- , m_editPreviewSubCamera(false) {
- assert(parent);
-
+ , m_editPreviewSubCamera(false)
+ , m_locator(NULL)
+ , m_isLocator(false) {
m_visualSettings.m_sceneProperties =
TApp::instance()->getCurrentScene()->getScene()->getProperties();
// Enables multiple key input.
@@ -880,6 +881,9 @@ void SceneViewer::hideEvent(QHideEvent *) {
ToolHandle *toolHandle = app->getCurrentTool();
if (toolHandle) toolHandle->disconnect(this);
+
+ // hide locator
+ if (m_locator && m_locator->isVisible()) m_locator->hide();
}
//-----------------------------------------------------------------------------
@@ -967,7 +971,7 @@ void SceneViewer::drawBuildVars() {
}
TTool *tool = app->getCurrentTool()->getTool();
- if (tool) tool->setViewer(this);
+ if (tool && !m_isLocator) tool->setViewer(this);
}
//-----------------------------------------------------------------------------
@@ -1100,7 +1104,7 @@ void SceneViewer::drawCameraStand() {
// Show white background when level editing mode.
TTool *tool = TApp::instance()->getCurrentTool()->getTool();
if (m_drawEditingLevel && tool && tool->isEnabled()) {
- tool->setViewer(this);
+ if (!m_isLocator) tool->setViewer(this);
glPushMatrix();
if (m_referenceMode == CAMERA3D_REFERENCE) {
mult3DMatrix();
@@ -1358,6 +1362,13 @@ void SceneViewer::drawOverlay() {
// use
// another glContext
if (tool->getName() == "T_RGBPicker") tool->onImageChanged();
+
+ // draw cross at the center of the locator window
+ if (m_isLocator) {
+ glColor3d(1.0, 0.0, 0.0);
+ tglDrawSegment(TPointD(-4, 0), TPointD(5, 0));
+ tglDrawSegment(TPointD(0, -4), TPointD(0, 5));
+ }
}
}
diff --git a/toonz/sources/toonz/sceneviewer.h b/toonz/sources/toonz/sceneviewer.h
index 68ed8de..10276dc 100644
--- a/toonz/sources/toonz/sceneviewer.h
+++ b/toonz/sources/toonz/sceneviewer.h
@@ -33,6 +33,7 @@
class Ruler;
class QMenu;
class SceneViewer;
+class LocatorPopup;
namespace ImageUtils {
class FullScreenWidget;
@@ -135,6 +136,10 @@ class SceneViewer final : public QGLWidget,
TOP_3D,
} m_current3DDevice;
+ LocatorPopup *m_locator;
+ bool m_isLocator;
+ bool m_isStyleShortcutSwitchable;
+
// iwsw commented out temporarily
// Ghibli3DLutUtil * m_ghibli3DLutUtil;
public:
@@ -230,6 +235,9 @@ public:
void setFocus(Qt::FocusReason reason) { QWidget::setFocus(reason); };
+ void setIsLocator() { m_isLocator = true; }
+ void setIsStyleShortcutSwitchable() { m_isStyleShortcutSwitchable = true; }
+
public:
// SceneViewer's gadget public functions
TPointD winToWorld(const QPoint &pos) const;
diff --git a/toonz/sources/toonz/sceneviewerevents.cpp b/toonz/sources/toonz/sceneviewerevents.cpp
index 17f3f3d..7a7a924 100644
--- a/toonz/sources/toonz/sceneviewerevents.cpp
+++ b/toonz/sources/toonz/sceneviewerevents.cpp
@@ -14,6 +14,11 @@
#include "onionskinmaskgui.h"
#include "ruler.h"
#include "comboviewerpane.h"
+#include "locatorpopup.h"
+
+// TnzQt includes
+#include "toonzqt/tselectionhandle.h"
+#include "toonzqt/styleselection.h"
// TnzTools includes
#include "tools/cursors.h"
@@ -180,6 +185,14 @@ void SceneViewer::onButtonPressed(FlipConsole::EGadget button) {
m_editPreviewSubCamera = !m_editPreviewSubCamera;
update();
break;
+
+ // open locator. Create one for the first time
+ case FlipConsole::eLocator:
+ if (!m_locator) m_locator = new LocatorPopup(this);
+ m_locator->show();
+ m_locator->raise();
+ m_locator->activateWindow();
+ break;
}
}
@@ -347,7 +360,12 @@ void SceneViewer::mouseMoveEvent(QMouseEvent *event) {
TMouseEvent toonzEvent;
initToonzEvent(toonzEvent, event, height(), m_pressure, m_tabletEvent,
false);
- TPointD pos = tool->getMatrix().inv() * winToWorld(curPos);
+ TPointD worldPos = winToWorld(curPos);
+ TPointD pos = tool->getMatrix().inv() * worldPos;
+
+ if (m_locator) {
+ m_locator->onChangeViewAff(worldPos);
+ }
TObjectHandle *objHandle = TApp::instance()->getCurrentObject();
if (tool->getToolType() & TTool::LevelTool && !objHandle->isSpline()) {
@@ -375,6 +393,7 @@ void SceneViewer::mouseMoveEvent(QMouseEvent *event) {
// panning
panQt(curPos - m_pos);
m_pos = curPos;
+
return;
}
}
@@ -753,6 +772,19 @@ void SceneViewer::keyPressEvent(QKeyEvent *event) {
tool->setViewer(this);
+ // If this object is child of Viewer or ComboViewer
+ // (m_isStyleShortcutSelective = true),
+ // then consider about shortcut for the current style selection.
+ if (m_isStyleShortcutSwitchable &&
+ Preferences::instance()->isUseNumpadForSwitchingStylesEnabled() &&
+ (!isTextToolActive) && (event->modifiers() == Qt::NoModifier ||
+ event->modifiers() == Qt::KeypadModifier) &&
+ ((Qt::Key_0 <= key && key <= Qt::Key_9) || key == Qt::Key_Tab ||
+ key == Qt::Key_Backtab)) {
+ event->ignore();
+ return;
+ }
+
if (key == Qt::Key_Shift)
modifiers |= Qt::SHIFT;
else if (key == Qt::Key_Control)
@@ -973,6 +1005,7 @@ void SceneViewer::contextMenuEvent(QContextMenuEvent *e) {
#endif
if (m_freezedStatus != NO_FREEZED) return;
+ if (m_isLocator) return;
TPoint winPos(e->pos().x(), height() - e->pos().y());
std::vector columnIndices;
diff --git a/toonz/sources/toonz/shortcutpopup.cpp b/toonz/sources/toonz/shortcutpopup.cpp
index 911a11f..b51b020 100644
--- a/toonz/sources/toonz/shortcutpopup.cpp
+++ b/toonz/sources/toonz/shortcutpopup.cpp
@@ -5,11 +5,19 @@
// Tnz6 includes
#include "menubarcommandids.h"
#include "tapp.h"
+#include "tenv.h"
+#include "tsystem.h"
+#include "toonz/preferences.h"
+#include "toonz/toonzfolders.h"
// TnzQt includes
+#include "toonzqt/gutil.h"
#include "toonzqt/menubarcommand.h"
#include "toonzqt/dvdialog.h"
+// TnzLib includes
+#include "toonz/preferences.h"
+
// Qt includes
#include
#include
@@ -24,6 +32,9 @@
#include
#include
#include
+#include
+#include
+#include
// STD includes
#include
@@ -128,6 +139,14 @@ void ShortcutViewer::keyPressEvent(QKeyEvent *event) {
modifiers = 0;
}
+ // If "Use Numpad and Tab keys for Switching Styles" option is activated,
+ // then prevent to assign such keys
+ if (Preferences::instance()->isUseNumpadForSwitchingStylesEnabled() &&
+ modifiers == 0 && (key >= Qt::Key_0 && key <= Qt::Key_9)) {
+ event->ignore();
+ return;
+ }
+
if (m_action) {
CommandManager *cm = CommandManager::instance();
QKeySequence keySequence(key + modifiers);
@@ -155,7 +174,7 @@ void ShortcutViewer::keyPressEvent(QKeyEvent *event) {
void ShortcutViewer::removeShortcut() {
if (m_action) {
- CommandManager::instance()->setShortcut(m_action, "");
+ CommandManager::instance()->setShortcut(m_action, "", false);
emit shortcutChanged();
update();
}
@@ -339,14 +358,32 @@ void ShortcutTree::onShortcutChanged() {
ShortcutPopup::ShortcutPopup()
: Dialog(TApp::instance()->getMainWindow(), false, false, "Shortcut") {
setWindowTitle(tr("Configure Shortcuts"));
+ m_presetChoiceCB = new QComboBox(this);
+ buildPresets();
+ m_presetChoiceCB->setCurrentIndex(0);
m_list = new ShortcutTree(this);
m_list->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
m_list->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
m_list->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOn);
- m_sViewer = new ShortcutViewer(this);
- m_removeBtn = new QPushButton(tr("Remove"), this);
+ m_sViewer = new ShortcutViewer(this);
+ m_removeBtn = new QPushButton(tr("Remove"), this);
+ m_loadShortcutsPopup = NULL;
+ m_saveShortcutsPopup = NULL;
+ m_dialog = NULL;
+ m_exportButton = new QPushButton(tr("Export Current Shortcuts"), this);
+ m_exportButton->setToolTip(tr("Export Current Shortcuts"));
+ m_deletePresetButton = new QPushButton("Delete", this);
+ m_deletePresetButton->setToolTip(tr("Delete Current Preset"));
+ m_deletePresetButton->setIcon(QIcon(":Resources/delete_on.png"));
+ m_savePresetButton = new QPushButton("Save As", this);
+ m_savePresetButton->setToolTip(tr("Save Current Shortcuts as New Preset"));
+ m_savePresetButton->setIcon(QIcon(":Resources/saveas_on.png"));
+ m_loadPresetButton = new QPushButton(tr("Apply"));
+ m_loadPresetButton->setToolTip(tr("Use selected preset as shortcuts"));
+ m_loadPresetButton->setIcon(QIcon(":Resources/green.png"));
+ m_clearAllShortcutsButton = new QPushButton(tr("Clear All Shortcuts"));
QLabel *noSearchResultLabel =
new QLabel(tr("Couldn't find any matching command."), this);
noSearchResultLabel->setHidden(true);
@@ -383,6 +420,28 @@ ShortcutPopup::ShortcutPopup()
bottomLayout->addWidget(m_removeBtn, 0);
}
m_topLayout->addLayout(bottomLayout, 0);
+ m_topLayout->addSpacing(10);
+ QHBoxLayout *presetLay = new QHBoxLayout();
+ presetLay->setMargin(0);
+ presetLay->setSpacing(5);
+ {
+ presetLay->addWidget(new QLabel("Preset:", this), 0);
+ presetLay->addWidget(m_presetChoiceCB, 1);
+ presetLay->addWidget(m_loadPresetButton, 0);
+ presetLay->addWidget(m_savePresetButton, 0);
+ presetLay->addWidget(m_deletePresetButton, 0);
+ }
+ m_topLayout->addLayout(presetLay, 0);
+ m_topLayout->addSpacing(10);
+ QHBoxLayout *exportLay = new QHBoxLayout();
+ exportLay->setMargin(0);
+ exportLay->setSpacing(5);
+ {
+ exportLay->addWidget(m_exportButton, 0);
+ exportLay->addWidget(m_clearAllShortcutsButton, 0);
+ }
+ m_topLayout->addLayout(exportLay, 0);
+ // m_topLayout->addWidget(m_exportButton, 0);
}
connect(m_list, SIGNAL(actionSelected(QAction *)), m_sViewer,
@@ -397,6 +456,14 @@ ShortcutPopup::ShortcutPopup()
SLOT(setHidden(bool)));
connect(searchEdit, SIGNAL(textChanged(const QString &)), this,
SLOT(onSearchTextChanged(const QString &)));
+ connect(m_presetChoiceCB, SIGNAL(currentIndexChanged(int)),
+ SLOT(onPresetChanged(int)));
+ connect(m_exportButton, SIGNAL(clicked()), SLOT(onExportButton()));
+ connect(m_deletePresetButton, SIGNAL(clicked()), SLOT(onDeletePreset()));
+ connect(m_savePresetButton, SIGNAL(clicked()), SLOT(onSavePreset()));
+ connect(m_loadPresetButton, SIGNAL(clicked()), SLOT(onLoadPreset()));
+ connect(m_clearAllShortcutsButton, SIGNAL(clicked()),
+ SLOT(clearAllShortcuts()));
}
//-----------------------------------------------------------------------------
@@ -415,4 +482,324 @@ void ShortcutPopup::onSearchTextChanged(const QString &text) {
//-----------------------------------------------------------------------------
+void ShortcutPopup::onPresetChanged(int index) {
+ if (m_presetChoiceCB->currentText() == "Load from file...") {
+ importPreset();
+ }
+}
+
+//-----------------------------------------------------------------------------
+
+void ShortcutPopup::clearAllShortcuts(bool warning) {
+ if (warning) {
+ QString question(tr("This will erase ALL shortcuts. Continue?"));
+ int ret =
+ DVGui::MsgBox(question, QObject::tr("OK"), QObject::tr("Cancel"), 0);
+ if (ret == 0 || ret == 2) {
+ // cancel (or closed message box window)
+ return;
+ }
+ showDialog("Clearing All Shortcuts");
+ }
+ for (int commandType = UndefinedCommandType; commandType <= MenuCommandType;
+ commandType++) {
+ std::vector actions;
+ CommandManager::instance()->getActions((CommandType)commandType, actions);
+ for (QAction *action : actions) {
+ qApp->processEvents();
+ m_sViewer->setAction(action);
+ m_sViewer->removeShortcut();
+ }
+ }
+ setCurrentPresetPref("DELETED");
+ // if warning is true, this was called directly- need to hide the dialog after
+ if (warning) m_dialog->hide();
+}
+
+//-----------------------------------------------------------------------------
+
+void ShortcutPopup::setPresetShortcuts(TFilePath fp) {
+ QSettings preset(toQString(fp), QSettings::IniFormat);
+ preset.beginGroup("shortcuts");
+ QStringList allIds = preset.allKeys();
+ QAction *action;
+ for (QString id : allIds) {
+ QByteArray ba = id.toLatin1();
+ const char *charId = ba.data();
+ action = CommandManager::instance()->getAction((CommandId)charId);
+ CommandManager::instance()->setShortcut(
+ action, preset.value(id).toString().toStdString(), false);
+ }
+ preset.endGroup();
+ emit m_sViewer->shortcutChanged();
+ m_dialog->hide();
+ buildPresets();
+ setCurrentPresetPref(QString::fromStdString(fp.getName()));
+}
+
+//-----------------------------------------------------------------------------
+
+bool ShortcutPopup::showConfirmDialog() {
+ QString question(tr("This will overwrite all current shortcuts. Continue?"));
+ int ret =
+ DVGui::MsgBox(question, QObject::tr("OK"), QObject::tr("Cancel"), 0);
+ if (ret == 0 || ret == 2) {
+ // cancel (or closed message box window)
+ return false;
+ } else
+ return true;
+}
+
+//-----------------------------------------------------------------------------
+
+bool ShortcutPopup::showOverwriteDialog(QString name) {
+ QString question(tr("A file named ") + name +
+ tr(" already exists. Do you want to replace it?"));
+ int ret = DVGui::MsgBox(question, QObject::tr("Yes"), QObject::tr("No"), 0);
+ if (ret == 0 || ret == 2) {
+ // cancel (or closed message box window)
+ return false;
+ } else
+ return true;
+}
+
+//-----------------------------------------------------------------------------
+
+void ShortcutPopup::showDialog(QString text) {
+ if (m_dialog == NULL) {
+ m_dialogLabel = new QLabel("", this);
+ m_dialog = new DVGui::Dialog(this, false, false);
+ m_dialog->setWindowTitle(tr("OpenToonz - Setting Shortcuts"));
+ m_dialog->setModal(false);
+
+ m_dialog->setTopMargin(10);
+ m_dialog->setTopSpacing(10);
+ m_dialog->setLabelWidth(500);
+ m_dialog->beginVLayout();
+ m_dialog->addWidget(m_dialogLabel, false);
+ m_dialog->endVLayout();
+ }
+ m_dialogLabel->setText(text);
+ m_dialog->show();
+}
+
+//-----------------------------------------------------------------------------
+
+void ShortcutPopup::onExportButton(TFilePath fp) {
+ if (fp == TFilePath()) {
+ m_saveShortcutsPopup = new GenericSaveFilePopup("Save Current Shortcuts");
+ m_saveShortcutsPopup->addFilterType("ini");
+ fp = m_saveShortcutsPopup->getPath();
+ if (fp == TFilePath()) return;
+ }
+ showDialog("Saving Shortcuts");
+ QString shortcutString = "[shortcuts]\n";
+ for (int commandType = UndefinedCommandType; commandType <= MenuCommandType;
+ commandType++) {
+ std::vector actions;
+ CommandManager::instance()->getActions((CommandType)commandType, actions);
+ for (QAction *action : actions) {
+ qApp->processEvents();
+ std::string id = CommandManager::instance()->getIdFromAction(action);
+ std::string shortcut =
+ CommandManager::instance()->getShortcutFromAction(action);
+ if (shortcut != "") {
+ shortcutString = shortcutString + QString::fromStdString(id) + "=" +
+ QString::fromStdString(shortcut) + "\n";
+ }
+ }
+ }
+ QFile file(fp.getQString());
+ file.open(QIODevice::WriteOnly | QIODevice::Text);
+ QTextStream out(&file);
+ out << shortcutString;
+ file.close();
+ m_dialog->hide();
+}
+
+//-----------------------------------------------------------------------------
+
+void ShortcutPopup::onDeletePreset() {
+ // change this to 4 once RETAS shortcuts are updated
+ if (m_presetChoiceCB->currentIndex() <= 3) {
+ DVGui::MsgBox(DVGui::CRITICAL, tr("Included presets cannot be deleted."));
+ return;
+ }
+
+ QString question(tr("Are you sure you want to delete the preset: ") +
+ m_presetChoiceCB->currentText() + tr("?"));
+ int ret = DVGui::MsgBox(question, QObject::tr("Yes"), QObject::tr("No"), 0);
+ if (ret == 0 || ret == 2) {
+ // cancel (or closed message box window)
+ return;
+ }
+ TFilePath presetDir =
+ ToonzFolder::getMyModuleDir() + TFilePath("shortcutpresets");
+ QString presetName = m_presetChoiceCB->currentText();
+ if (TSystem::doesExistFileOrLevel(presetDir +
+ TFilePath(presetName + ".ini"))) {
+ TSystem::deleteFile(presetDir + TFilePath(presetName + ".ini"));
+ buildPresets();
+ m_presetChoiceCB->setCurrentIndex(0);
+ }
+ if (Preferences::instance()->getShortcutPreset() == presetName)
+ setCurrentPresetPref("DELETED");
+ getCurrentPresetPref();
+}
+
+//-----------------------------------------------------------------------------
+
+void ShortcutPopup::importPreset() {
+ m_loadShortcutsPopup = new GenericLoadFilePopup("Load Shortcuts File");
+ m_loadShortcutsPopup->addFilterType("ini");
+ TFilePath shortcutPath = m_loadShortcutsPopup->getPath();
+ if (shortcutPath == TFilePath()) {
+ m_presetChoiceCB->setCurrentIndex(0);
+ return;
+ }
+ if (!showConfirmDialog()) return;
+
+ TFilePath presetDir =
+ ToonzFolder::getMyModuleDir() + TFilePath("shortcutpresets");
+ if (!TSystem::doesExistFileOrLevel(presetDir)) {
+ TSystem::mkDir(presetDir);
+ }
+ QString name = shortcutPath.withoutParentDir().getQString();
+ std::string strName = name.toStdString();
+ if (TSystem::doesExistFileOrLevel(presetDir + TFilePath(name))) {
+ if (!showOverwriteDialog(name)) return;
+ }
+ showDialog("Importing Shortcuts");
+ TSystem::copyFile(presetDir + TFilePath(name), shortcutPath, true);
+ clearAllShortcuts(false);
+ setPresetShortcuts(presetDir + TFilePath(name));
+ return;
+}
+
+//-----------------------------------------------------------------------------
+
+void ShortcutPopup::onLoadPreset() {
+ QString preset = m_presetChoiceCB->currentText();
+ TFilePath presetDir =
+ ToonzFolder::getMyModuleDir() + TFilePath("shortcutpresets");
+ TFilePath defaultPresetDir =
+ ToonzFolder::getProfileFolder() + TFilePath("layouts/shortcuts");
+ if (preset == "") return;
+ if (preset == "Load from file...") {
+ importPreset();
+ return;
+ }
+
+ if (!showConfirmDialog()) return;
+ showDialog("Setting Shortcuts");
+ if (preset == "OpenToonz") {
+ clearAllShortcuts(false);
+ TFilePath fp = defaultPresetDir + TFilePath("defopentoonz.ini");
+ setPresetShortcuts(fp);
+ return;
+ } else if (preset == "Toon Boom Harmony") {
+ clearAllShortcuts(false);
+ TFilePath fp = defaultPresetDir + TFilePath("otharmony.ini");
+ setPresetShortcuts(fp);
+ return;
+ } else if (preset == "Adobe Animate(Flash)") {
+ clearAllShortcuts(false);
+ TFilePath fp = defaultPresetDir + TFilePath("otadobe.ini");
+ setPresetShortcuts(fp);
+ return;
+ } else if (preset == "RETAS PaintMan") {
+ clearAllShortcuts(false);
+ TFilePath fp = defaultPresetDir + TFilePath("otretas.ini");
+ setPresetShortcuts(fp);
+ return;
+ } else if (TSystem::doesExistFileOrLevel(presetDir +
+ TFilePath(preset + ".ini"))) {
+ clearAllShortcuts(false);
+ TFilePath fp = presetDir + TFilePath(preset + ".ini");
+ setPresetShortcuts(fp);
+ return;
+ }
+ m_dialog->hide();
+}
+
+//-----------------------------------------------------------------------------
+
+QStringList ShortcutPopup::buildPresets() {
+ QStringList presets;
+ presets << ""
+ << "OpenToonz"
+ //<< "RETAS PaintMan"
+ << "Toon Boom Harmony"
+ << "Adobe Animate(Flash)";
+ TFilePath presetDir =
+ ToonzFolder::getMyModuleDir() + TFilePath("shortcutpresets");
+ if (TSystem::doesExistFileOrLevel(presetDir)) {
+ TFilePathSet fps = TSystem::readDirectory(presetDir, true, true, false);
+ QStringList customPresets;
+ for (TFilePath fp : fps) {
+ if (fp.getType() == "ini") {
+ customPresets << QString::fromStdString(fp.getName());
+ std::string name = fp.getName();
+ }
+ }
+ customPresets.sort();
+ presets = presets + customPresets;
+ }
+ presets << tr("Load from file...");
+ m_presetChoiceCB->clear();
+ m_presetChoiceCB->addItems(presets);
+ return presets;
+}
+
+//-----------------------------------------------------------------------------
+
+void ShortcutPopup::onSavePreset() {
+ QString presetName = DVGui::getText("Enter Preset Name", "Preset Name:", "");
+ if (presetName == "") return;
+ TFilePath presetDir =
+ ToonzFolder::getMyModuleDir() + TFilePath("shortcutpresets");
+ if (!TSystem::doesExistFileOrLevel(presetDir)) {
+ TSystem::mkDir(presetDir);
+ }
+ TFilePath fp;
+ fp = presetDir + TFilePath(presetName + ".ini");
+ if (TSystem::doesExistFileOrLevel(fp)) {
+ if (!showOverwriteDialog(QString::fromStdString(fp.getName()))) return;
+ }
+ onExportButton(fp);
+
+ buildPresets();
+ setCurrentPresetPref(presetName);
+}
+
+//-----------------------------------------------------------------------------
+
+void ShortcutPopup::showEvent(QShowEvent *se) { getCurrentPresetPref(); }
+
+//-----------------------------------------------------------------------------
+
+void ShortcutPopup::setCurrentPresetPref(QString name) {
+ Preferences::instance()->setShortcutPreset(name.toStdString());
+ getCurrentPresetPref();
+}
+
+//-----------------------------------------------------------------------------
+
+void ShortcutPopup::getCurrentPresetPref() {
+ QString name = Preferences::instance()->getShortcutPreset();
+ if (name == "DELETED")
+ m_presetChoiceCB->setCurrentText("");
+ else if (name == "defopentoonz")
+ m_presetChoiceCB->setCurrentText("OpenToonz");
+ else if (name == "otharmony")
+ m_presetChoiceCB->setCurrentText("Toon Boom Harmony");
+ else if (name == "otadobe")
+ m_presetChoiceCB->setCurrentText("Adobe Animate(Flash)");
+ else if (name == "otretas")
+ m_presetChoiceCB->setCurrentText("RETAS PaintMan");
+
+ else
+ m_presetChoiceCB->setCurrentText(name);
+}
+
OpenPopupCommandHandler openShortcutPopup(MI_ShortcutPopup);
diff --git a/toonz/sources/toonz/shortcutpopup.h b/toonz/sources/toonz/shortcutpopup.h
index 2044ac6..142d04f 100644
--- a/toonz/sources/toonz/shortcutpopup.h
+++ b/toonz/sources/toonz/shortcutpopup.h
@@ -5,7 +5,8 @@
#include
#include
-
+#include
+#include "filebrowserpopup.h"
#include "toonzqt/dvdialog.h"
// forward declaration
@@ -92,13 +93,40 @@ class ShortcutPopup final : public DVGui::Dialog {
QPushButton *m_removeBtn;
ShortcutViewer *m_sViewer;
ShortcutTree *m_list;
+ QComboBox *m_presetChoiceCB;
+ DVGui::Dialog *m_dialog;
+ GenericLoadFilePopup *m_loadShortcutsPopup;
+ GenericSaveFilePopup *m_saveShortcutsPopup;
+ QPushButton *m_exportButton;
+ QPushButton *m_deletePresetButton;
+ QPushButton *m_savePresetButton;
+ QPushButton *m_loadPresetButton;
+ QPushButton *m_clearAllShortcutsButton;
+ QLabel *m_dialogLabel;
public:
ShortcutPopup();
~ShortcutPopup();
+private:
+ void setPresetShortcuts(TFilePath fp);
+ void showDialog(QString text);
+ bool showConfirmDialog();
+ bool showOverwriteDialog(QString name);
+ void importPreset();
+ QStringList buildPresets();
+ void showEvent(QShowEvent *se) override;
+ void setCurrentPresetPref(QString preset);
+ void getCurrentPresetPref();
+
protected slots:
+ void clearAllShortcuts(bool warning = true);
void onSearchTextChanged(const QString &text);
+ void onPresetChanged(int index);
+ void onExportButton(TFilePath fp = TFilePath());
+ void onDeletePreset();
+ void onSavePreset();
+ void onLoadPreset();
};
#endif // SHORTCUTPOPUP_H
diff --git a/toonz/sources/toonz/startuppopup.cpp b/toonz/sources/toonz/startuppopup.cpp
new file mode 100644
index 0000000..bf8c375
--- /dev/null
+++ b/toonz/sources/toonz/startuppopup.cpp
@@ -0,0 +1,917 @@
+
+
+#include "startuppopup.h"
+
+// Tnz6 includes
+#include "mainwindow.h"
+#include "tapp.h"
+#include "iocommand.h"
+#include "toutputproperties.h"
+#include "toonzqt/flipconsole.h"
+#include "menubarcommandids.h"
+#include "tenv.h"
+#include "toonz/stage.h"
+
+// TnzQt includes
+#include "toonzqt/menubarcommand.h"
+#include "toonzqt/gutil.h"
+#include "toonzqt/doublefield.h"
+
+// TnzLib includes
+#include "toonz/toonzscene.h"
+#include "toonz/txsheet.h"
+#include "toonz/levelproperties.h"
+#include "toonz/sceneproperties.h"
+#include "toonz/tcamera.h"
+#include "toonz/tscenehandle.h"
+#include "toonz/txsheethandle.h"
+#include "toonz/preferences.h"
+#include "toonz/tproject.h"
+
+// TnzCore includes
+#include "tsystem.h"
+#include "filebrowsermodel.h"
+
+// Qt includes
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+using namespace std;
+using namespace DVGui;
+
+namespace {
+
+// the first value in the preset list
+const QString custom = QObject::tr("");
+
+QString removeZeros(QString srcStr) {
+ if (!srcStr.contains('.')) return srcStr;
+
+ for (int i = srcStr.length() - 1; i >= 0; i--) {
+ if (srcStr.at(i) == '0')
+ srcStr.chop(1);
+ else if (srcStr.at(i) == '.') {
+ srcStr.chop(1);
+ break;
+ } else
+ break;
+ }
+ return srcStr;
+}
+} // namespace
+
+//=============================================================================
+/*! \class StartupPopup
+ \brief The StartupPopup class provides a modal dialog to
+ bring up recent files or create a new scene.
+
+ Inherits \b Dialog.
+*/
+//-----------------------------------------------------------------------------
+
+StartupPopup::StartupPopup()
+ : Dialog(TApp::instance()->getMainWindow(), true, true, "StartupPopup") {
+ setWindowTitle(tr("OpenToonz Startup"));
+
+ m_projectBox = new QGroupBox(tr("Choose Project"), this);
+ m_sceneBox = new QGroupBox(tr("Create a New Scene"), this);
+ m_recentBox = new QGroupBox(tr("Open Scene"), this);
+ m_projectBox->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
+ m_nameFld = new LineEdit(this);
+ m_pathFld = new FileField(this);
+ m_sceneNameLabel = new QLabel(tr("Scene Name:"));
+ m_widthLabel = new QLabel(tr("Width:"), this);
+ m_widthFld = new MeasuredDoubleLineEdit(this);
+ m_heightLabel = new QLabel(tr("Height:"), this);
+ m_heightFld = new MeasuredDoubleLineEdit(this);
+ m_dpiLabel = new QLabel(tr("DPI:"), this);
+ m_dpiFld = new DoubleLineEdit(this, 120);
+ m_resXLabel = new QLabel(tr("X"), this);
+ m_resXFld = new DoubleLineEdit(this);
+ m_resYFld = new DoubleLineEdit(this);
+ m_resTextLabel = new QLabel(tr("Resolution:"), this);
+ m_fpsLabel = new QLabel(tr("Frame Rate:"), this);
+ m_fpsFld = new DoubleLineEdit(this, 24.0);
+ m_cameraSettingsWidget = new CameraSettingsWidget(false);
+ m_presetCombo = new QComboBox(this);
+ m_unitsCB = new QComboBox(this);
+ m_addPresetBtn = new QPushButton(tr("Add"), this);
+ m_removePresetBtn = new QPushButton(tr("Remove"), this);
+ m_showAtStartCB = new QCheckBox(tr("Show this at startup"), this);
+ QPushButton *createButton = new QPushButton(tr("Create Scene"), this);
+ QPushButton *newProjectButton = new QPushButton(tr("New Project..."), this);
+ QPushButton *loadOtherSceneButton =
+ new QPushButton(tr("Open Another Scene..."), this);
+ m_projectsCB = new QComboBox(this);
+ QStringList type;
+ type << tr("pixel") << tr("cm") << tr("mm") << tr("inch") << tr("field");
+ m_unitsCB->addItems(type);
+
+ // Exclude all character which cannot fit in a filepath (Win).
+ // Dots are also prohibited since they are internally managed by Toonz.
+ QRegExp rx("[^\\\\/:?*.\"<>|]+");
+ m_nameFld->setValidator(new QRegExpValidator(rx, this));
+
+ m_widthFld->setMeasure("camera.lx");
+ m_heightFld->setMeasure("camera.ly");
+
+ m_widthFld->setRange(0.1, (std::numeric_limits::max)());
+ m_heightFld->setRange(0.1, (std::numeric_limits::max)());
+ m_fpsFld->setRange(1.0, (std::numeric_limits::max)());
+ m_dpiFld->setRange(1.0, (std::numeric_limits::max)());
+ m_resXFld->setRange(0.1, (std::numeric_limits::max)());
+ m_resYFld->setRange(0.1, (std::numeric_limits::max)());
+ m_showAtStartCB->setChecked(Preferences::instance()->isStartupPopupEnabled());
+ m_showAtStartCB->setStyleSheet("QCheckBox{ background-color: none; }");
+ m_addPresetBtn->setStyleSheet(
+ "QPushButton { padding-left: 4px; padding-right: 4px;}");
+ m_removePresetBtn->setStyleSheet(
+ "QPushButton { padding-left: 4px; padding-right: 4px;}");
+ QLabel *label = new QLabel();
+ label->setPixmap(QPixmap(":Resources/startup.png"));
+ m_projectBox->setObjectName("SolidLineFrame");
+ m_sceneBox->setObjectName("SolidLineFrame");
+ m_recentBox->setObjectName("SolidLineFrame");
+ m_projectBox->setContentsMargins(10, 10, 10, 10);
+ m_sceneBox->setContentsMargins(10, 10, 10, 10);
+ m_recentBox->setContentsMargins(10, 10, 10, 10);
+ m_recentBox->setFixedWidth(200);
+ m_sceneBox->setMinimumWidth(480);
+ m_projectBox->setMinimumWidth(480);
+ m_buttonFrame->setFixedHeight(30);
+ //--- layout
+ m_topLayout->setMargin(0);
+ m_topLayout->setSpacing(0);
+ {
+ QGridLayout *guiLay = new QGridLayout();
+ QHBoxLayout *projectLay = new QHBoxLayout();
+ QGridLayout *newSceneLay = new QGridLayout();
+ m_recentSceneLay = new QVBoxLayout();
+ guiLay->setMargin(10);
+ guiLay->setVerticalSpacing(10);
+ guiLay->setHorizontalSpacing(10);
+
+ guiLay->addWidget(label, 0, 0, 1, 2, Qt::AlignLeft);
+
+ projectLay->setSpacing(8);
+ projectLay->setMargin(8);
+ {
+ projectLay->addWidget(m_projectsCB, 1);
+ projectLay->addWidget(newProjectButton, 0);
+ }
+ m_projectBox->setLayout(projectLay);
+ guiLay->addWidget(m_projectBox, 1, 0, 1, 1, Qt::AlignCenter);
+
+ newSceneLay->setMargin(8);
+ newSceneLay->setVerticalSpacing(8);
+ newSceneLay->setHorizontalSpacing(8);
+ {
+ // Scene Name
+ newSceneLay->addWidget(m_sceneNameLabel, 0, 0,
+ Qt::AlignRight | Qt::AlignVCenter);
+ newSceneLay->addWidget(m_nameFld, 0, 1, 1, 3);
+
+ // Save In
+ newSceneLay->addWidget(new QLabel(tr("Save In:")), 1, 0,
+ Qt::AlignRight | Qt::AlignVCenter);
+ newSceneLay->addWidget(m_pathFld, 1, 1, 1, 3);
+ newSceneLay->addWidget(new QLabel(tr("Camera Size:")), 2, 0,
+ Qt::AlignRight | Qt::AlignVCenter);
+ QHBoxLayout *resListLay = new QHBoxLayout();
+ resListLay->setSpacing(3);
+ resListLay->setMargin(1);
+ {
+ resListLay->addWidget(m_presetCombo, 1);
+ resListLay->addWidget(m_addPresetBtn, 0);
+ resListLay->addWidget(m_removePresetBtn, 0);
+ }
+ newSceneLay->addLayout(resListLay, 2, 1, 1, 3, Qt::AlignLeft);
+
+ // Width - Height
+ newSceneLay->addWidget(m_widthLabel, 3, 0,
+ Qt::AlignRight | Qt::AlignVCenter);
+ newSceneLay->addWidget(m_widthFld, 3, 1);
+ newSceneLay->addWidget(m_heightLabel, 3, 2,
+ Qt::AlignRight | Qt::AlignVCenter);
+ newSceneLay->addWidget(m_heightFld, 3, 3);
+
+ newSceneLay->addWidget(m_resTextLabel, 4, 0, 1, 1, Qt::AlignRight);
+ newSceneLay->addWidget(m_resXFld, 4, 1);
+ newSceneLay->addWidget(m_resXLabel, 4, 2, 1, 1, Qt::AlignCenter);
+ newSceneLay->addWidget(m_resYFld, 4, 3);
+ newSceneLay->addWidget(new QLabel(tr("Units:")), 5, 0,
+ Qt::AlignRight | Qt::AlignVCenter);
+ newSceneLay->addWidget(m_unitsCB, 5, 1, 1, 1);
+ newSceneLay->addWidget(m_dpiLabel, 5, 2,
+ Qt::AlignRight | Qt::AlignVCenter);
+ newSceneLay->addWidget(m_dpiFld, 5, 3, 1, 1);
+ newSceneLay->addWidget(m_fpsLabel, 6, 0,
+ Qt::AlignRight | Qt::AlignVCenter);
+ newSceneLay->addWidget(m_fpsFld, 6, 1, 1, 1);
+ newSceneLay->addWidget(createButton, 7, 1, 1, 3, Qt::AlignLeft);
+ }
+ m_sceneBox->setLayout(newSceneLay);
+ guiLay->addWidget(m_sceneBox, 2, 0, 4, 1, Qt::AlignLeft);
+
+ m_recentSceneLay->setMargin(5);
+ m_recentSceneLay->setSpacing(2);
+ {
+ // Recent Scene List
+ m_recentBox->setLayout(m_recentSceneLay);
+ guiLay->addWidget(m_recentBox, 1, 1, 4, 1, Qt::AlignTop);
+ guiLay->addWidget(loadOtherSceneButton, 5, 1, 1, 1, Qt::AlignRight);
+ }
+ m_topLayout->addLayout(guiLay, 0);
+ }
+
+ m_buttonLayout->setMargin(0);
+ m_buttonLayout->setSpacing(10);
+ { m_buttonLayout->addWidget(m_showAtStartCB, Qt::AlignLeft); }
+
+ TApp *app = TApp::instance();
+ TSceneHandle *sceneHandle = app->getCurrentScene();
+
+ //---- signal-slot connections
+ bool ret = true;
+ ret = ret && connect(sceneHandle, SIGNAL(sceneChanged()), this,
+ SLOT(onSceneChanged()));
+ ret = ret && connect(sceneHandle, SIGNAL(sceneSwitched()), this,
+ SLOT(onSceneChanged()));
+ ret = ret && connect(newProjectButton, SIGNAL(clicked()), this,
+ SLOT(onNewProjectButtonPressed()));
+ ret = ret && connect(loadOtherSceneButton, SIGNAL(clicked()), this,
+ SLOT(onLoadSceneButtonPressed()));
+ ret = ret && connect(m_projectsCB, SIGNAL(currentIndexChanged(int)),
+ SLOT(onProjectChanged(int)));
+ ret = ret &&
+ connect(createButton, SIGNAL(clicked()), this, SLOT(onCreateButton()));
+ ret = ret && connect(m_showAtStartCB, SIGNAL(stateChanged(int)), this,
+ SLOT(onShowAtStartChanged(int)));
+ ret = ret && connect(m_widthFld, SIGNAL(valueChanged()), this,
+ SLOT(updateResolution()));
+ ret = ret && connect(m_heightFld, SIGNAL(valueChanged()), this,
+ SLOT(updateResolution()));
+ ret = ret &&
+ connect(m_resXFld, SIGNAL(valueChanged()), this, SLOT(updateSize()));
+ ret = ret &&
+ connect(m_resYFld, SIGNAL(valueChanged()), this, SLOT(updateSize()));
+ ret = ret && connect(m_dpiFld, SIGNAL(editingFinished()), this,
+ SLOT(onDpiChanged()));
+ ret = ret && connect(m_presetCombo, SIGNAL(activated(const QString &)),
+ SLOT(onPresetSelected(const QString &)));
+ ret = ret && connect(m_addPresetBtn, SIGNAL(clicked()), SLOT(addPreset()));
+ ret = ret && connect(m_unitsCB, SIGNAL(currentIndexChanged(int)),
+ SLOT(onCameraUnitChanged(int)));
+ ret = ret &&
+ connect(m_removePresetBtn, SIGNAL(clicked()), SLOT(removePreset()));
+ ret = ret && connect(m_nameFld, SIGNAL(returnPressedNow()), createButton,
+ SLOT(animateClick()));
+ assert(ret);
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::showEvent(QShowEvent *) {
+ loadPresetList();
+ updateProjectCB();
+ m_nameFld->setFocus();
+ m_pathFld->setPath(TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getProject()
+ ->getScenesPath()
+ .getQString());
+ TDimensionD cameraSize = TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getCurrentCamera()
+ ->getSize();
+ TDimension cameraRes = TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getCurrentCamera()
+ ->getRes();
+ double fps = TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getProperties()
+ ->getOutputProperties()
+ ->getFrameRate();
+ m_widthFld->setValue(cameraSize.lx);
+ m_heightFld->setValue(cameraSize.ly);
+ if (Preferences::instance()->getCameraUnits() == "pixel") {
+ m_widthFld->setDecimals(0);
+ m_heightFld->setDecimals(0);
+ m_resTextLabel->hide();
+ m_resXFld->hide();
+ m_resYFld->hide();
+ m_resXLabel->hide();
+ m_dpiFld->hide();
+ m_dpiLabel->hide();
+ } else {
+ m_widthFld->setDecimals(4);
+ m_heightFld->setDecimals(4);
+ m_resXFld->show();
+ m_resYFld->show();
+ m_resXLabel->show();
+ m_resTextLabel->show();
+ m_dpiFld->show();
+ m_dpiLabel->show();
+ }
+
+ m_fpsFld->setValue(fps);
+ m_unitsCB->setCurrentText(Preferences::instance()->getCameraUnits());
+ m_dpi = cameraRes.lx / cameraSize.lx;
+ m_xRes = cameraRes.lx;
+ m_yRes = cameraRes.ly;
+ m_resXFld->setValue(m_xRes);
+ m_resYFld->setValue(m_yRes);
+ m_resXFld->setDecimals(0);
+ m_resYFld->setDecimals(0);
+ m_dpiFld->setValue(m_dpi);
+
+ int boxWidth = m_sceneBox->width();
+ int boxHeight = m_sceneBox->height();
+ m_sceneBox->setFixedWidth(boxWidth);
+ m_projectBox->setFixedWidth(boxWidth);
+ m_recentBox->setMinimumHeight(boxHeight);
+
+ // update recent scenes
+ // clear items if they exist first
+
+ if (m_recentSceneLay->count() > 0) {
+ QLayoutItem *child;
+ while (m_recentSceneLay->count() != 0) {
+ child = m_recentSceneLay->takeAt(0);
+ delete child;
+ }
+ }
+
+ m_sceneNames = RecentFiles::instance()->getFilesNameList(RecentFiles::Scene);
+ m_recentNamesLabels = QVector(m_sceneNames.count());
+
+ if (m_sceneNames.count() <= 0) {
+ m_recentSceneLay->addWidget(new QLabel(tr("No Recent Scenes"), this), 1,
+ Qt::AlignTop);
+ } else {
+ int i = 0;
+ for (QString name : m_sceneNames) {
+ if (i > 9) break; // box can hold 10 scenes
+ QString justName = QString::fromStdString(TFilePath(name).getName());
+ m_recentNamesLabels[i] = new StartupLabel(justName, this, i);
+ m_recentNamesLabels[i]->setToolTip(
+ name.remove(0, name.indexOf(" ") + 1)); // remove "#. " prefix
+ m_recentSceneLay->addWidget(m_recentNamesLabels[i], i, Qt::AlignTop);
+ i++;
+ }
+ m_recentSceneLay->addStretch(100);
+ }
+
+ bool ret = true;
+ for (int i = 0; i < m_recentNamesLabels.count() && i < 7; i++) {
+ ret = ret && connect(m_recentNamesLabels[i], SIGNAL(wasClicked(int)), this,
+ SLOT(onRecentSceneClicked(int)));
+ }
+ assert(ret);
+ // center window
+ this->move(QApplication::desktop()->screen()->rect().center() -
+ this->rect().center());
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::onCreateButton() {
+ if (m_nameFld->text().trimmed() == "") {
+ DVGui::warning(tr("The name cannot be empty."));
+ m_nameFld->setFocus();
+ return;
+ }
+ if (!TSystem::doesExistFileOrLevel(TFilePath(m_pathFld->getPath()))) {
+ DVGui::warning(tr("The chosen file path is not valid."));
+ m_pathFld->setFocus();
+ return;
+ }
+
+ if (m_widthFld->getValue() < 1) {
+ DVGui::warning(tr("The width must be 1 or more."));
+ m_widthFld->setFocus();
+ return;
+ }
+ if (m_heightFld->getValue() < 1) {
+ DVGui::warning(tr("The height must be 1 or more."));
+ m_heightFld->setFocus();
+ return;
+ }
+ if (m_fpsFld->getValue() < 1) {
+ DVGui::warning(tr("The frame rate must be 1 or more."));
+ m_fpsFld->setFocus();
+ return;
+ }
+ if (TSystem::doesExistFileOrLevel(
+ TFilePath(m_pathFld->getPath()) +
+ TFilePath(m_nameFld->text().trimmed().toStdWString() + L".tnz"))) {
+ QString question;
+ question = QObject::tr(
+ "The file name already exists."
+ "\nDo you want to overwrite it?");
+ int ret = DVGui::MsgBox(question, QObject::tr("Yes"), QObject::tr("No"), 0);
+ if (ret == 0 || ret == 2) {
+ // no (or closed message box window)
+ return;
+ ;
+ }
+ }
+ CommandManager::instance()->execute(MI_NewScene);
+ TApp::instance()->getCurrentScene()->getScene()->setScenePath(
+ TFilePath(m_pathFld->getPath()) +
+ TFilePath(m_nameFld->text().trimmed().toStdWString()));
+ TDimensionD size =
+ TDimensionD(m_widthFld->getValue(), m_heightFld->getValue());
+ TDimension res = TDimension(m_xRes, m_yRes);
+ double fps = m_fpsFld->getValue();
+ TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getProperties()
+ ->getOutputProperties()
+ ->setFrameRate(fps);
+ TApp::instance()->getCurrentScene()->getScene()->getCurrentCamera()->setSize(
+ size);
+ TApp::instance()->getCurrentScene()->getScene()->getCurrentCamera()->setRes(
+ res);
+ // this one is debatable - should the scene be saved right away?
+ // IoCmd::saveScene();
+ // this makes sure the scene viewers update to the right fps
+ TApp::instance()->getCurrentScene()->notifySceneSwitched();
+
+ hide();
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::updateProjectCB() {
+ m_updating = true;
+ m_projectPaths.clear();
+ m_projectsCB->clear();
+
+ TFilePath sandboxFp = TProjectManager::instance()->getSandboxProjectFolder() +
+ "sandbox_otprj.xml";
+ m_projectPaths.push_back(sandboxFp);
+ m_projectsCB->addItem("sandbox");
+
+ std::vector prjRoots;
+ TProjectManager::instance()->getProjectRoots(prjRoots);
+ for (int i = 0; i < prjRoots.size(); i++) {
+ TFilePathSet fps;
+ TSystem::readDirectory_Dir_ReadExe(fps, prjRoots[i]);
+
+ TFilePathSet::iterator it;
+ for (it = fps.begin(); it != fps.end(); ++it) {
+ TFilePath fp(*it);
+ if (TProjectManager::instance()->isProject(fp)) {
+ m_projectPaths.push_back(
+ TProjectManager::instance()->projectFolderToProjectPath(fp));
+ m_projectsCB->addItem(QString::fromStdString(fp.getName()));
+ }
+ }
+ }
+ int i;
+ for (i = 0; i < m_projectPaths.size(); i++) {
+ if (TProjectManager::instance()->getCurrentProjectPath() ==
+ m_projectPaths[i]) {
+ m_projectsCB->setCurrentIndex(i);
+ break;
+ }
+ }
+ m_pathFld->setPath(TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getProject()
+ ->getScenesPath()
+ .getQString());
+ m_updating = false;
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::onProjectChanged(int index) {
+ if (m_updating) return;
+ TFilePath projectFp = m_projectPaths[index];
+
+ TProjectManager::instance()->setCurrentProjectPath(projectFp);
+
+ IoCmd::newScene();
+ m_pathFld->setPath(TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getProject()
+ ->getScenesPath()
+ .getQString());
+ m_fpsFld->setValue(TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getProperties()
+ ->getOutputProperties()
+ ->getFrameRate());
+ TDimension res = TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getCurrentCamera()
+ ->getRes();
+ m_xRes = res.lx;
+ m_yRes = res.ly;
+ m_resXFld->setValue(m_xRes);
+ m_resYFld->setValue(m_yRes);
+ TDimensionD size = TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getCurrentCamera()
+ ->getSize();
+ m_widthFld->setValue(size.lx);
+ m_heightFld->setValue(size.ly);
+ m_dpi = m_xRes / size.lx;
+ m_dpiFld->setValue(m_dpi);
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::loadPresetList() {
+ m_presetCombo->clear();
+ m_presetCombo->addItem("...");
+ m_presetListFile = ToonzFolder::getReslistPath(false).getQString();
+ QFile file(m_presetListFile);
+ if (file.open(QIODevice::ReadOnly | QIODevice::Text)) {
+ QTextStream in(&file);
+ while (!in.atEnd()) {
+ QString line = in.readLine().trimmed();
+ if (line != "") m_presetCombo->addItem(line);
+ }
+ }
+ m_presetCombo->setCurrentIndex(0);
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::savePresetList() {
+ QFile file(m_presetListFile);
+ if (!file.open(QIODevice::WriteOnly | QIODevice::Text)) return;
+ QTextStream out(&file);
+ int n = m_presetCombo->count();
+ for (int i = 1; i < n; i++) out << m_presetCombo->itemText(i) << "\n";
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::addPreset() {
+ int xRes = (int)(m_widthFld->getValue() * m_dpi);
+ int yRes = (int)(m_heightFld->getValue() * m_dpi);
+ double lx = m_widthFld->getValue();
+ double ly = m_heightFld->getValue();
+ double ar = m_widthFld->getValue() / m_heightFld->getValue();
+
+ QString presetString;
+ presetString = QString::number(xRes) + "x" + QString::number(yRes) + ", " +
+ removeZeros(QString::number(lx)) + "x" +
+ removeZeros(QString::number(ly)) + ", " +
+ aspectRatioValueToString(ar);
+
+ bool ok;
+ QString qs;
+ while (1) {
+ qs = DVGui::getText(tr("Preset name"),
+ tr("Enter the name for %1").arg(presetString), "", &ok);
+
+ if (!ok) return;
+
+ if (qs.indexOf(",") != -1)
+ QMessageBox::warning(this, tr("Error : Preset Name is Invalid"),
+ tr("The preset name must not use ','(comma)."));
+ else
+ break;
+ }
+
+ int oldn = m_presetCombo->count();
+ m_presetCombo->addItem(qs + "," + presetString);
+ int newn = m_presetCombo->count();
+ m_presetCombo->blockSignals(true);
+ m_presetCombo->setCurrentIndex(m_presetCombo->count() - 1);
+ m_presetCombo->blockSignals(false);
+
+ savePresetList();
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::removePreset() {
+ int index = m_presetCombo->currentIndex();
+ if (index <= 0) return;
+
+ // confirmation dialog
+ int ret = DVGui::MsgBox(QObject::tr("Deleting \"%1\".\nAre you sure?")
+ .arg(m_presetCombo->currentText()),
+ QObject::tr("Delete"), QObject::tr("Cancel"));
+ if (ret == 0 || ret == 2) return;
+
+ m_presetCombo->removeItem(index);
+ m_presetCombo->setCurrentIndex(0);
+ savePresetList();
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::onPresetSelected(const QString &str) {
+ if (str == custom || str.isEmpty()) return;
+ QString name, arStr;
+ int xres = 0, yres = 0;
+ double fx = -1.0, fy = -1.0;
+ QString xoffset = "", yoffset = "";
+ double ar;
+
+ if (parsePresetString(str, name, xres, yres, fx, fy, xoffset, yoffset, ar,
+ false)) {
+ m_xRes = xres;
+ m_yRes = yres;
+ // The current solution is to preserve the DPI so that scenes are less
+ // likely to become incompatible with pixels only mode in the future
+ // Commented below is the default behavior of the camera settings widget
+ // m_widthFld->setValue(m_heightFld->getValue() * ar);
+ // m_dpiFld->setValue(m_xRes / m_widthFld->getValue());
+
+ // here is the system that preserves dpi
+ m_widthFld->setValue((double)xres / (double)m_dpi);
+ m_heightFld->setValue((double)yres / (double)m_dpi);
+ if (Preferences::instance()->getPixelsOnly()) {
+ m_widthFld->setValue((double)xres / Stage::standardDpi);
+ m_heightFld->setValue((double)yres / Stage::standardDpi);
+ m_dpiFld->setValue(Stage::standardDpi);
+ }
+ m_resXFld->setValue(m_xRes);
+ m_resYFld->setValue(m_yRes);
+ } else {
+ QMessageBox::warning(
+ this, tr("Bad camera preset"),
+ tr("'%1' doesn't seem to be a well formed camera preset. \n"
+ "Possibly the preset file has been corrupted")
+ .arg(str));
+ }
+}
+
+//--------------------------------------------------------------------------
+
+bool StartupPopup::parsePresetString(const QString &str, QString &name,
+ int &xres, int &yres, double &fx,
+ double &fy, QString &xoffset,
+ QString &yoffset, double &ar,
+ bool forCleanup) {
+ /*
+ parsing preset string with QString::split().
+ !NOTE! fx/fy (camera size in inch) and xoffset/yoffset (camera offset used in
+ cleanup camera) are optional,
+ in order to keep compatibility with default (Harlequin's) reslist.txt
+ */
+
+ QStringList tokens = str.split(",", QString::SkipEmptyParts);
+
+ if (!(tokens.count() == 3 ||
+ (!forCleanup && tokens.count() == 4) || /*- with "fx x fy" token -*/
+ (forCleanup &&
+ tokens.count() ==
+ 6))) /*- with "fx x fy", xoffset and yoffset tokens -*/
+ return false;
+ /*- name -*/
+ name = tokens[0];
+
+ /*- xres, yres (like: 1024x768) -*/
+ QStringList values = tokens[1].split("x");
+ if (values.count() != 2) return false;
+ bool ok;
+ xres = values[0].toInt(&ok);
+ if (!ok) return false;
+ yres = values[1].toInt(&ok);
+ if (!ok) return false;
+
+ if (tokens.count() >= 4) {
+ /*- fx, fy -*/
+ values = tokens[2].split("x");
+ if (values.count() != 2) return false;
+ fx = values[0].toDouble(&ok);
+ if (!ok) return false;
+ fy = values[1].toDouble(&ok);
+ if (!ok) return false;
+
+ /*- xoffset, yoffset -*/
+ if (forCleanup) {
+ xoffset = tokens[3];
+ yoffset = tokens[4];
+ /*- remove single space -*/
+ if (xoffset.startsWith(' ')) xoffset.remove(0, 1);
+ if (yoffset.startsWith(' ')) yoffset.remove(0, 1);
+ }
+ }
+
+ /*- AR -*/
+ ar = aspectRatioStringToValue(tokens.last());
+
+ return true;
+}
+
+//-----------------------------------------------------------------------------
+
+double StartupPopup::aspectRatioStringToValue(const QString &s) {
+ if (s == "") {
+ return 1;
+ }
+ int i = s.indexOf("/");
+ if (i <= 0 || i + 1 >= s.length()) return s.toDouble();
+ int num = s.left(i).toInt();
+ int den = s.mid(i + 1).toInt();
+ if (den <= 0) den = 1;
+ return (double)num / (double)den;
+}
+
+//-----------------------------------------------------------------------------
+
+// A/R : value => string (e.g. '4/3' or '1.23')
+QString StartupPopup::aspectRatioValueToString(double value, int width,
+ int height) {
+ double v = value;
+
+ if (width != 0 && height != 0) {
+ if (areAlmostEqual(value, (double)width / (double)height, 1e-3))
+ return QString("%1/%2").arg(width).arg(height);
+ }
+
+ double iv = tround(v);
+ if (fabs(iv - v) > 0.01) {
+ for (int d = 2; d < 20; d++) {
+ int n = tround(v * d);
+ if (fabs(n - v * d) <= 0.01)
+ return QString::number(n) + "/" + QString::number(d);
+ }
+ return QString::number(value, 'f', 5);
+ } else {
+ return QString::number((int)iv);
+ }
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::onNewProjectButtonPressed() {
+ CommandManager::instance()->execute(MI_NewProject);
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::onSceneChanged() {
+ // close the box if a recent scene has been selected
+ if (!TApp::instance()->getCurrentScene()->getScene()->isUntitled()) {
+ hide();
+ } else {
+ updateProjectCB();
+ }
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::onDpiChanged() {
+ if (Preferences::instance()->getPixelsOnly()) {
+ m_dpi = Stage::standardDpi;
+ m_dpiFld->setValue(Stage::standardDpi);
+ updateResolution();
+ } else {
+ m_dpi = m_dpiFld->getValue();
+ updateResolution();
+ }
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::onLoadSceneButtonPressed() {
+ CommandManager::instance()->execute(MI_LoadScene);
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::onRecentSceneClicked(int index) {
+ if (index < 0) return;
+ QString path =
+ RecentFiles::instance()->getFilePath(index, RecentFiles::Scene);
+ IoCmd::loadScene(TFilePath(path.toStdWString()), false);
+ RecentFiles::instance()->moveFilePath(index, 0, RecentFiles::Scene);
+ RecentFiles::instance()->refreshRecentFilesMenu(RecentFiles::Scene);
+ hide();
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::onCameraUnitChanged(int index) {
+ Preferences *pref = Preferences::instance();
+ QStringList type;
+ type << tr("pixel") << tr("cm") << tr("mm") << tr("inch") << tr("field");
+
+ double width = m_widthFld->getValue();
+ double height = m_heightFld->getValue();
+ if (index != 0) {
+ pref->setPixelsOnly(false);
+ pref->setCameraUnits(type[index].toStdString());
+ m_widthFld->setDecimals(4);
+ m_heightFld->setDecimals(4);
+ m_resTextLabel->show();
+ m_resXFld->show();
+ m_resYFld->show();
+ m_resXLabel->show();
+ m_dpiFld->show();
+ m_dpiLabel->show();
+ m_widthFld->setMeasure("camera.lx");
+ m_heightFld->setMeasure("camera.ly");
+ m_widthFld->setValue(width);
+ m_heightFld->setValue(height);
+ } else {
+ pref->setPixelsOnly(true);
+ pref->setUnits("pixel");
+ pref->setCameraUnits("pixel");
+ m_widthFld->setDecimals(0);
+ m_heightFld->setDecimals(0);
+ m_resTextLabel->hide();
+ m_resXFld->hide();
+ m_resYFld->hide();
+ m_resXLabel->hide();
+ m_dpiFld->hide();
+ m_dpiLabel->hide();
+ m_dpiFld->setValue(Stage::standardDpi);
+ m_widthFld->setMeasure("camera.lx");
+ m_heightFld->setMeasure("camera.ly");
+ m_widthFld->setValue(m_xRes / Stage::standardDpi);
+ m_heightFld->setValue(m_yRes / Stage::standardDpi);
+ }
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::onShowAtStartChanged(int index) {
+ Preferences::instance()->enableStartupPopup(index);
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::updateResolution() {
+ if (Preferences::instance()->getPixelsOnly()) {
+ if (m_dpiFld->getValue() != Stage::standardDpi) {
+ m_dpiFld->setValue(Stage::standardDpi);
+ }
+ m_xRes = m_widthFld->getValue() * Stage::standardDpi;
+ m_yRes = m_heightFld->getValue() * Stage::standardDpi;
+ m_resXFld->setValue(m_xRes);
+ m_resYFld->setValue(m_yRes);
+ } else {
+ m_xRes = m_widthFld->getValue() * m_dpi;
+ m_yRes = m_heightFld->getValue() * m_dpi;
+ m_resXFld->setValue(m_xRes);
+ m_resYFld->setValue(m_yRes);
+ }
+ m_presetCombo->setCurrentIndex(0);
+}
+
+//-----------------------------------------------------------------------------
+
+void StartupPopup::updateSize() {
+ m_xRes = m_resXFld->getValue();
+ m_yRes = m_resYFld->getValue();
+ if (Preferences::instance()->getPixelsOnly()) {
+ if (m_dpiFld->getValue() != Stage::standardDpi) {
+ m_dpiFld->setValue(Stage::standardDpi);
+ }
+ m_widthFld->setValue((double)m_xRes / Stage::standardDpi);
+ m_heightFld->setValue((double)m_yRes / Stage::standardDpi);
+ } else {
+ m_widthFld->setValue((double)m_xRes / m_dpi);
+ m_heightFld->setValue((double)m_yRes / m_dpi);
+ }
+ m_presetCombo->setCurrentIndex(0);
+}
+
+//-----------------------------------------------------------------------------
+
+StartupLabel::StartupLabel(const QString &text, QWidget *parent, int index)
+ : QLabel(parent), m_index(index) {
+ setText(text);
+ setObjectName("StartupLabel");
+}
+
+StartupLabel::~StartupLabel() {}
+
+void StartupLabel::mousePressEvent(QMouseEvent *event) {
+ m_text = text();
+ std::string strText = m_text.toStdString();
+ emit wasClicked(m_index);
+}
+
+OpenPopupCommandHandler openStartupPopup(MI_StartupPopup);
diff --git a/toonz/sources/toonz/startuppopup.h b/toonz/sources/toonz/startuppopup.h
new file mode 100644
index 0000000..cd1e33d
--- /dev/null
+++ b/toonz/sources/toonz/startuppopup.h
@@ -0,0 +1,109 @@
+#pragma once
+
+#ifndef STARTUPPOPUP_H
+#define STARTUPPOPUP_H
+
+#include "toonzqt/dvdialog.h"
+#include "toonzqt/doublefield.h"
+#include "toonzqt/intfield.h"
+#include "toonzqt/filefield.h"
+#include "toonzqt/camerasettingswidget.h"
+#include
+#include
+#include
+#include
+
+// forward declaration
+class QLabel;
+class QComboBox;
+class StartupLabel;
+
+//=============================================================================
+// LevelCreatePopup
+//-----------------------------------------------------------------------------
+
+class StartupPopup final : public DVGui::Dialog {
+ Q_OBJECT
+
+ DVGui::LineEdit *m_nameFld;
+ DVGui::FileField *m_pathFld;
+ QLabel *m_widthLabel;
+ QLabel *m_heightLabel;
+ QLabel *m_fpsLabel;
+ QLabel *m_resXLabel;
+ QLabel *m_resTextLabel;
+ QLabel *m_dpiLabel;
+ QLabel *m_sceneNameLabel;
+ DVGui::DoubleLineEdit *m_dpiFld;
+ DVGui::MeasuredDoubleLineEdit *m_widthFld;
+ DVGui::MeasuredDoubleLineEdit *m_heightFld;
+ DVGui::DoubleLineEdit *m_fpsFld;
+ DVGui::DoubleLineEdit *m_resXFld;
+ DVGui::DoubleLineEdit *m_resYFld;
+ QList m_sceneNames;
+ QList m_projectPaths;
+ QCheckBox *m_showAtStartCB;
+ QComboBox *m_projectsCB;
+ QComboBox *m_unitsCB;
+ QPushButton *m_loadOtherSceneButton;
+ QPushButton *m_newProjectButton;
+ QComboBox *m_presetCombo;
+ QPushButton *m_addPresetBtn, *m_removePresetBtn;
+ CameraSettingsWidget *m_cameraSettingsWidget;
+ double m_dpi;
+ int m_xRes, m_yRes;
+ bool m_updating = false;
+ QString m_presetListFile;
+ QGroupBox *m_projectBox;
+ QGroupBox *m_sceneBox;
+ QGroupBox *m_recentBox;
+ QVBoxLayout *m_recentSceneLay;
+ QVector m_recentNamesLabels;
+
+public:
+ StartupPopup();
+
+protected:
+ void showEvent(QShowEvent *) override;
+ void loadPresetList();
+ void savePresetList();
+ QString aspectRatioValueToString(double value, int width = 0, int height = 0);
+ double aspectRatioStringToValue(const QString &s);
+ bool parsePresetString(const QString &str, QString &name, int &xres,
+ int &yres, double &fx, double &fy, QString &xoffset,
+ QString &yoffset, double &ar, bool forCleanup = false);
+
+public slots:
+ void onRecentSceneClicked(int index);
+ void onCreateButton();
+ void onShowAtStartChanged(int index);
+ void updateProjectCB();
+ void onProjectChanged(int index);
+ void onNewProjectButtonPressed();
+ void onLoadSceneButtonPressed();
+ void onSceneChanged();
+ void updateResolution();
+ void updateSize();
+ void onDpiChanged();
+ void addPreset();
+ void removePreset();
+ void onPresetSelected(const QString &str);
+ void onCameraUnitChanged(int index);
+};
+
+class StartupLabel : public QLabel {
+ Q_OBJECT
+public:
+ explicit StartupLabel(const QString &text = "", QWidget *parent = 0,
+ int index = -1);
+ ~StartupLabel();
+ QString m_text;
+ int m_index;
+signals:
+ void wasClicked(int index);
+
+protected:
+ void mousePressEvent(QMouseEvent *event);
+};
+
+#endif // STARTUPPOPUP_H
diff --git a/toonz/sources/toonz/styleshortcutswitchablepanel.cpp b/toonz/sources/toonz/styleshortcutswitchablepanel.cpp
new file mode 100644
index 0000000..d680521
--- /dev/null
+++ b/toonz/sources/toonz/styleshortcutswitchablepanel.cpp
@@ -0,0 +1,112 @@
+#include "styleshortcutswitchablepanel.h"
+
+// TnzLib includes
+#include "toonz/tscenehandle.h"
+#include "toonz/preferences.h"
+#include "toonz/palettecontroller.h"
+#include "toonz/tpalettehandle.h"
+
+// TnzTools includes
+#include "tools/toolhandle.h"
+#include "tools/toolcommandids.h"
+
+// TnzQt includes
+#include "toonzqt/tselectionhandle.h"
+#include "toonzqt/styleselection.h"
+
+// Tnz6 includes
+#include "tapp.h"
+
+#include
+
+//-----------------------------------------------------------------------------
+
+void StyleShortcutSwitchablePanel::keyPressEvent(QKeyEvent *event) {
+ if (!Preferences::instance()->isUseNumpadForSwitchingStylesEnabled()) return;
+ TTool *tool = TApp::instance()->getCurrentTool()->getTool();
+ if (!tool) return;
+ if (tool->getName() == T_Type && tool->isActive()) return;
+ if (event->modifiers() != Qt::NoModifier &&
+ event->modifiers() != Qt::KeypadModifier)
+ return;
+ int key = event->key();
+ if (Qt::Key_0 <= key && key <= Qt::Key_9) {
+ TPaletteHandle *ph =
+ TApp::instance()->getPaletteController()->getCurrentLevelPalette();
+
+ TPalette *palette = ph->getPalette();
+ if (palette) {
+ int styleId = palette->getShortcutValue(key);
+ if (styleId >= 0) {
+ ph->setStyleIndex(styleId);
+ TStyleSelection *selection = dynamic_cast(
+ TApp::instance()->getCurrentSelection()->getSelection());
+ if (selection) selection->selectNone();
+ }
+ }
+ event->accept();
+ } else if (key == Qt::Key_Tab || key == Qt::Key_Backtab) {
+ TPaletteHandle *ph =
+ TApp::instance()->getPaletteController()->getCurrentLevelPalette();
+
+ TPalette *palette = ph->getPalette();
+ if (palette) {
+ palette->nextShortcutScope(key == Qt::Key_Backtab);
+ ph->notifyPaletteChanged();
+ }
+ event->accept();
+ }
+}
+
+//-----------------------------------------------------------------------------
+
+void StyleShortcutSwitchablePanel::showEvent(QShowEvent *event) {
+ TPanel::showEvent(event);
+ bool ret = connect(TApp::instance()->getCurrentScene(),
+ SIGNAL(preferenceChanged(const QString &)), this,
+ SLOT(onPreferenceChanged(const QString &)));
+ onPreferenceChanged("");
+ assert(ret);
+}
+
+//-----------------------------------------------------------------------------
+
+void StyleShortcutSwitchablePanel::hideEvent(QHideEvent *event) {
+ TPanel::hideEvent(event);
+ disconnect(TApp::instance()->getCurrentScene(),
+ SIGNAL(preferenceChanged(const QString &)), this,
+ SLOT(onPreferenceChanged(const QString &)));
+}
+
+//-----------------------------------------------------------------------------
+
+void StyleShortcutSwitchablePanel::onPreferenceChanged(
+ const QString &prefName) {
+ if (prefName == "NumpadForSwitchingStyles" || prefName.isEmpty())
+ updateTabFocus();
+}
+
+//-----------------------------------------------------------------------------
+
+void StyleShortcutSwitchablePanel::updateTabFocus() {
+ QList widgets = findChildren();
+ if (Preferences::instance()->isUseNumpadForSwitchingStylesEnabled()) {
+ // disable tab focus
+ foreach (QWidget *widget, widgets) {
+ Qt::FocusPolicy policy = widget->focusPolicy();
+ if (policy == Qt::TabFocus || policy == Qt::StrongFocus ||
+ policy == Qt::WheelFocus) {
+ m_childrenFocusPolicies[widget] = policy;
+ widget->setFocusPolicy((policy == Qt::TabFocus) ? Qt::NoFocus
+ : Qt::ClickFocus);
+ }
+ }
+ } else {
+ // revert tab focus
+ QHashIterator i(m_childrenFocusPolicies);
+ while (i.hasNext()) {
+ i.next();
+ i.key()->setFocusPolicy(i.value());
+ }
+ }
+}
\ No newline at end of file
diff --git a/toonz/sources/toonz/styleshortcutswitchablepanel.h b/toonz/sources/toonz/styleshortcutswitchablepanel.h
new file mode 100644
index 0000000..ce68933
--- /dev/null
+++ b/toonz/sources/toonz/styleshortcutswitchablepanel.h
@@ -0,0 +1,39 @@
+#pragma once
+
+#ifndef STYLE_SHORTCUT_SWITCHABLE_PANEL_H
+#define STYLE_SHORTCUT_SWITCHABLE_PANEL_H
+
+#include "pane.h"
+
+//=============================================================================
+// StyleShortcutSwitchablePanel
+//-----------------------------------------------------------------------------
+// StyleShortcutSwitchablePanel class is subclass of TPanel and
+// inherited by panels which can select the current style by 0-9
+// number keys if the Preferences option
+// "Use Numpad and Tab keys for Switching Styles" is active.
+// Currently inherited by ComboViewer, Viewer and Palette
+//-----------------------------------------------------------------------------
+
+class StyleShortcutSwitchablePanel : public TPanel {
+ Q_OBJECT
+
+ QHash m_childrenFocusPolicies;
+
+public:
+ StyleShortcutSwitchablePanel(
+ QWidget *parent = 0, Qt::WindowFlags flags = 0,
+ TDockWidget::Orientation orientation = TDockWidget::vertical)
+ : TPanel(parent, flags, orientation) {}
+
+protected:
+ void keyPressEvent(QKeyEvent *event) override;
+ void showEvent(QShowEvent *) override;
+ void hideEvent(QHideEvent *) override;
+
+protected slots:
+ virtual void onPreferenceChanged(const QString &prefName);
+ void updateTabFocus();
+};
+
+#endif
\ No newline at end of file
diff --git a/toonz/sources/toonz/tapp.cpp b/toonz/sources/toonz/tapp.cpp
index a6ef8b2..698fe26 100644
--- a/toonz/sources/toonz/tapp.cpp
+++ b/toonz/sources/toonz/tapp.cpp
@@ -673,16 +673,25 @@ void TApp::autosave() {
} else
m_autosaveSuspended = false;
- if (scene->isUntitled()) {
+ if (scene->isUntitled() &&
+ Preferences::instance()->isAutosaveSceneEnabled()) {
DVGui::warning(
- tr("It is not possible to save automatically an untitled scene."));
+ tr("It is not possible to automatically save an untitled scene."));
return;
}
DVGui::ProgressDialog pb(
"Autosaving scene..." + toQString(scene->getScenePath()), 0, 0, 1);
pb.show();
- IoCmd::saveScene();
+ Preferences *pref = Preferences::instance();
+ if (pref->isAutosaveSceneEnabled() && pref->isAutosaveOtherFilesEnabled()) {
+ IoCmd::saveAll();
+ } else if (pref->isAutosaveSceneEnabled()) {
+ IoCmd::saveScene();
+ } else if (pref->isAutosaveOtherFilesEnabled()) {
+ IoCmd::saveNonSceneFiles();
+ }
+
pb.setValue(1);
}
@@ -705,7 +714,7 @@ void TApp::onStartAutoSave() {
//-----------------------------------------------------------------------------
void TApp::onStopAutoSave() {
- assert(!Preferences::instance()->isAutosaveEnabled());
+ // assert(!Preferences::instance()->isAutosaveEnabled());
m_autosaveTimer->stop();
}
diff --git a/toonz/sources/toonz/toonz.qrc b/toonz/sources/toonz/toonz.qrc
index 75aa7a1..3ad3f78 100644
--- a/toonz/sources/toonz/toonz.qrc
+++ b/toonz/sources/toonz/toonz.qrc
@@ -264,6 +264,7 @@
Resources/standard.png
Resources/standard_on.png
Resources/standard_over.png
+ Resources/startup.png
Resources/start_off.png
Resources/start_on.png
Resources/stop_off.png
@@ -442,5 +443,8 @@
Resources/finger_rollover.svg
Resources/ruler.svg
Resources/ruler_rollover.svg
+ Resources/locator.png
+ Resources/locator_click.png
+ Resources/locator_over.png
diff --git a/toonz/sources/toonz/tpanels.cpp b/toonz/sources/toonz/tpanels.cpp
index 74fee6a..8ed5795 100644
--- a/toonz/sources/toonz/tpanels.cpp
+++ b/toonz/sources/toonz/tpanels.cpp
@@ -402,7 +402,8 @@ public:
// PaletteViewer
//-----------------------------------------------------------------------------
-PaletteViewerPanel::PaletteViewerPanel(QWidget *parent) : TPanel(parent) {
+PaletteViewerPanel::PaletteViewerPanel(QWidget *parent)
+ : StyleShortcutSwitchablePanel(parent) {
m_paletteHandle = new TPaletteHandle();
connect(m_paletteHandle, SIGNAL(colorStyleSwitched()),
SLOT(onColorStyleSwitched()));
diff --git a/toonz/sources/toonz/tpanels.h b/toonz/sources/toonz/tpanels.h
index ed6cbf8..d6501d8 100644
--- a/toonz/sources/toonz/tpanels.h
+++ b/toonz/sources/toonz/tpanels.h
@@ -4,6 +4,7 @@
#define TPANELS_INCLUDED
#include "pane.h"
+#include "styleshortcutswitchablepanel.h"
#include "tpalette.h"
#include "trenderer.h"
@@ -27,7 +28,7 @@ class ToolOptions;
// PaletteViewerPanel
//---------------------------------------------------------
-class PaletteViewerPanel final : public TPanel {
+class PaletteViewerPanel final : public StyleShortcutSwitchablePanel {
Q_OBJECT
TPaletteHandle *m_paletteHandle;
diff --git a/toonz/sources/toonz/viewerpane.cpp b/toonz/sources/toonz/viewerpane.cpp
index 819a466..6fc4ef7 100644
--- a/toonz/sources/toonz/viewerpane.cpp
+++ b/toonz/sources/toonz/viewerpane.cpp
@@ -77,7 +77,7 @@ SceneViewerPanel::SceneViewerPanel(QWidget *parent, Qt::WindowFlags flags)
#else
SceneViewerPanel::SceneViewerPanel(QWidget *parent, Qt::WFlags flags)
#endif
- : TPanel(parent) {
+ : StyleShortcutSwitchablePanel(parent) {
QFrame *hbox = new QFrame(this);
hbox->setFrameStyle(QFrame::StyledPanel);
hbox->setObjectName("ViewerPanel");
@@ -94,6 +94,7 @@ SceneViewerPanel::SceneViewerPanel(QWidget *parent, Qt::WFlags flags)
new ImageUtils::FullScreenWidget(viewer);
fsWidget->setWidget(m_sceneViewer = new SceneViewer(fsWidget));
+ m_sceneViewer->setIsStyleShortcutSwitchable();
bool ret = true;
ret = ret && connect(m_sceneViewer, SIGNAL(onZoomChanged()),
@@ -120,7 +121,7 @@ SceneViewerPanel::SceneViewerPanel(QWidget *parent, Qt::WFlags flags)
int buttons = FlipConsole::cFullConsole;
- buttons &= (~FlipConsole::eSound);
+ // buttons &= (~FlipConsole::eSound);
buttons &= (~FlipConsole::eFilledRaster);
buttons &= (~FlipConsole::eDefineLoadBox);
buttons &= (~FlipConsole::eUseLoadBox);
@@ -150,6 +151,10 @@ SceneViewerPanel::SceneViewerPanel(QWidget *parent, Qt::WFlags flags)
connect(m_flipConsole, SIGNAL(buttonPressed(FlipConsole::EGadget)),
m_sceneViewer, SLOT(onButtonPressed(FlipConsole::EGadget)));
+ ret =
+ ret && connect(m_flipConsole, SIGNAL(buttonPressed(FlipConsole::EGadget)),
+ this, SLOT(onButtonPressed(FlipConsole::EGadget)));
+
ret = ret && connect(m_sceneViewer, SIGNAL(previewStatusChanged()), this,
SLOT(update()));
@@ -157,7 +162,8 @@ SceneViewerPanel::SceneViewerPanel(QWidget *parent, Qt::WFlags flags)
SLOT(onSceneSwitched()));
assert(ret);
-
+ m_flipConsole->setChecked(FlipConsole::eSound, true);
+ m_playSound = m_flipConsole->isChecked(FlipConsole::eSound);
m_flipConsole->setFrameRate(app->getCurrentScene()
->getScene()
->getProperties()
@@ -220,7 +226,8 @@ SceneViewerPanel::~SceneViewerPanel() {}
//-----------------------------------------------------------------------------
-void SceneViewerPanel::showEvent(QShowEvent *) {
+void SceneViewerPanel::showEvent(QShowEvent *event) {
+ StyleShortcutSwitchablePanel::showEvent(event);
TApp *app = TApp::instance();
TFrameHandle *frameHandle = app->getCurrentFrame();
TSceneHandle *sceneHandle = app->getCurrentScene();
@@ -259,10 +266,6 @@ void SceneViewerPanel::showEvent(QShowEvent *) {
ret = ret && connect(app->getCurrentTool(), SIGNAL(toolSwitched()),
m_sceneViewer, SLOT(onToolSwitched()));
- ret = ret && connect(sceneHandle, SIGNAL(preferenceChanged()), m_flipConsole,
- SLOT(onPreferenceChanged()));
- m_flipConsole->onPreferenceChanged();
-
assert(ret);
// Aggiorno FPS al valore definito nel viewer corrente.
@@ -272,7 +275,8 @@ void SceneViewerPanel::showEvent(QShowEvent *) {
//-----------------------------------------------------------------------------
-void SceneViewerPanel::hideEvent(QHideEvent *) {
+void SceneViewerPanel::hideEvent(QHideEvent *event) {
+ StyleShortcutSwitchablePanel::hideEvent(event);
TApp *app = TApp::instance();
TFrameHandle *frameHandle = app->getCurrentFrame();
TSceneHandle *sceneHandle = app->getCurrentScene();
@@ -305,9 +309,6 @@ void SceneViewerPanel::hideEvent(QHideEvent *) {
disconnect(app->getCurrentTool(), SIGNAL(toolSwitched()), m_sceneViewer,
SLOT(onToolSwitched()));
- disconnect(sceneHandle, SIGNAL(preferenceChanged()), m_flipConsole,
- SLOT(onPreferenceChanged()));
-
m_flipConsole->setActive(false);
}
@@ -326,25 +327,49 @@ void SceneViewerPanel::initializeTitleBar(TPanelTitleBar *titleBar) {
TPanelTitleBarButtonSet *viewModeButtonSet;
m_referenceModeBs = viewModeButtonSet = new TPanelTitleBarButtonSet();
- int x = -188;
+ int x = -232;
int iconWidth = 17;
TPanelTitleBarButton *button;
- button = new TPanelTitleBarButton(titleBar, ":Resources/freeze.png",
- ":Resources/freeze_over.png",
- ":Resources/freeze_on.png");
- button->setToolTip(tr("Freeze"));
- titleBar->add(QPoint(x, 2), button);
- ret = ret && connect(button, SIGNAL(toggled(bool)), m_sceneViewer,
- SLOT(freeze(bool)));
- ret = ret && connect(m_sceneViewer, SIGNAL(freezeStateChanged(bool)), button,
- SLOT(setPressed(bool)));
+ // buttons for show / hide toggle for the field guide and the safe area
+ TPanelTitleBarButtonForSafeArea *safeAreaButton =
+ new TPanelTitleBarButtonForSafeArea(titleBar, ":Resources/safearea.png",
+ ":Resources/safearea_over.png",
+ ":Resources/safearea_on.png");
+ safeAreaButton->setToolTip(tr("Safe Area (Right Click to Select)"));
+ titleBar->add(QPoint(x, 1), safeAreaButton);
+ ret = ret && connect(safeAreaButton, SIGNAL(toggled(bool)),
+ CommandManager::instance()->getAction(MI_SafeArea),
+ SLOT(trigger()));
+ ret = ret && connect(CommandManager::instance()->getAction(MI_SafeArea),
+ SIGNAL(triggered(bool)), safeAreaButton,
+ SLOT(setPressed(bool)));
+ // initialize state
+ safeAreaButton->setPressed(
+ CommandManager::instance()->getAction(MI_SafeArea)->isChecked());
+
+ button = new TPanelTitleBarButton(titleBar, ":Resources/fieldguide.png",
+ ":Resources/fieldguide_over.png",
+ ":Resources/fieldguide_on.png");
+ button->setToolTip(tr("Field Guide"));
+ x += 5 + iconWidth;
+ titleBar->add(QPoint(x, 1), button);
+ ret = ret && connect(button, SIGNAL(toggled(bool)),
+ CommandManager::instance()->getAction(MI_FieldGuide),
+ SLOT(trigger()));
+ ret = ret && connect(CommandManager::instance()->getAction(MI_FieldGuide),
+ SIGNAL(triggered(bool)), button, SLOT(setPressed(bool)));
+ // initialize state
+ button->setPressed(
+ CommandManager::instance()->getAction(MI_FieldGuide)->isChecked());
+
+ // view mode toggles
button = new TPanelTitleBarButton(titleBar, ":Resources/standard.png",
":Resources/standard_over.png",
":Resources/standard_on.png");
button->setToolTip(tr("Camera Stand View"));
- x += 18 + iconWidth;
- titleBar->add(QPoint(x, 2), button);
+ x += 10 + iconWidth;
+ titleBar->add(QPoint(x, 1), button);
button->setButtonSet(viewModeButtonSet, SceneViewer::NORMAL_REFERENCE);
button->setPressed(true);
@@ -352,25 +377,37 @@ void SceneViewerPanel::initializeTitleBar(TPanelTitleBar *titleBar) {
":Resources/3D_over.png",
":Resources/3D_on.png");
button->setToolTip(tr("3D View"));
- x += 5 + iconWidth;
- titleBar->add(QPoint(x, 2), button);
+ x += 19; // width of standard.png = 18pixels
+ titleBar->add(QPoint(x, 1), button);
button->setButtonSet(viewModeButtonSet, SceneViewer::CAMERA3D_REFERENCE);
button = new TPanelTitleBarButton(titleBar, ":Resources/view_camera.png",
":Resources/view_camera_over.png",
":Resources/view_camera_on.png");
button->setToolTip(tr("Camera View"));
- x += 5 + iconWidth;
- titleBar->add(QPoint(x, 2), button);
+ x += 18; // width of 3D.png = 18pixels
+ titleBar->add(QPoint(x, 1), button);
button->setButtonSet(viewModeButtonSet, SceneViewer::CAMERA_REFERENCE);
ret = ret && connect(viewModeButtonSet, SIGNAL(selected(int)), m_sceneViewer,
SLOT(setReferenceMode(int)));
+ // freeze button
+ button = new TPanelTitleBarButton(titleBar, ":Resources/freeze.png",
+ ":Resources/freeze_over.png",
+ ":Resources/freeze_on.png");
+ x += 10 + 19; // width of viewcamera.png = 18pixels
+
+ button->setToolTip(tr("Freeze")); // RC1
+ titleBar->add(QPoint(x, 1), button);
+ ret = ret && connect(button, SIGNAL(toggled(bool)), m_sceneViewer,
+ SLOT(freeze(bool)));
+
+ // preview toggles
m_previewButton = new TPanelTitleBarButton(
titleBar, ":Resources/viewpreview.png", ":Resources/viewpreview_over.png",
":Resources/viewpreview_on.png");
- x += 18 + iconWidth;
- titleBar->add(QPoint(x, 2), m_previewButton);
+ x += 5 + iconWidth;
+ titleBar->add(QPoint(x, 1), m_previewButton);
m_previewButton->setToolTip(tr("Preview"));
ret = ret && connect(m_previewButton, SIGNAL(toggled(bool)),
SLOT(enableFullPreview(bool)));
@@ -379,8 +416,9 @@ void SceneViewerPanel::initializeTitleBar(TPanelTitleBar *titleBar) {
new TPanelTitleBarButton(titleBar, ":Resources/subcamera_preview.png",
":Resources/subcamera_preview_over.png",
":Resources/subcamera_preview_on.png");
- x += 5 + iconWidth;
- titleBar->add(QPoint(x, 2), m_subcameraPreviewButton);
+ x += 28; // width of viewpreview.png =28pixels
+
+ titleBar->add(QPoint(x, 1), m_subcameraPreviewButton);
m_subcameraPreviewButton->setToolTip(tr("Sub-camera Preview"));
ret = ret && connect(m_subcameraPreviewButton, SIGNAL(toggled(bool)),
SLOT(enableSubCameraPreview(bool)));
@@ -437,6 +475,12 @@ void SceneViewerPanel::onXshLevelSwitched(TXshLevel *) { changeWindowTitle(); }
//-----------------------------------------------------------------------------
void SceneViewerPanel::onPlayingStatusChanged(bool playing) {
+ if (playing) {
+ m_playing = true;
+ } else {
+ m_playing = false;
+ m_first = true;
+ }
if (Preferences::instance()->getOnionSkinDuringPlayback()) return;
OnionSkinMask osm =
TApp::instance()->getCurrentOnionSkin()->getOnionSkinMask();
@@ -541,7 +585,6 @@ void SceneViewerPanel::onSceneChanged() {
updateFrameRange();
updateFrameMarkers();
changeWindowTitle();
-
TApp *app = TApp::instance();
ToonzScene *scene = app->getCurrentScene()->getScene();
assert(scene);
@@ -551,6 +594,7 @@ void SceneViewerPanel::onSceneChanged() {
int frameIndex = TApp::instance()->getCurrentFrame()->getFrameIndex();
if (m_keyFrameButton->getCurrentFrame() != frameIndex)
m_keyFrameButton->setCurrentFrame(frameIndex);
+ hasSoundtrack();
}
//-----------------------------------------------------------------------------
@@ -578,6 +622,14 @@ void SceneViewerPanel::onFrameSwitched() {
m_flipConsole->setCurrentFrame(frameIndex + 1);
if (m_keyFrameButton->getCurrentFrame() != frameIndex)
m_keyFrameButton->setCurrentFrame(frameIndex);
+
+ if (m_playing && m_playSound) {
+ if (m_first == true && hasSoundtrack()) {
+ playAudioFrame(frameIndex);
+ } else if (m_hasSoundtrack) {
+ playAudioFrame(frameIndex);
+ }
+ }
}
//-----------------------------------------------------------------------------
@@ -601,3 +653,64 @@ void SceneViewerPanel::onFrameTypeChanged() {
updateFrameRange();
updateFrameMarkers();
}
+
+//-----------------------------------------------------------------------------
+
+void SceneViewerPanel::onPreferenceChanged(const QString &prefName) {
+ // if no name specified (on StyleShortcutSelectivePanel::showEvent),
+ // then process all updates
+ if (prefName == "BlankCount" || prefName == "BlankColor" ||
+ prefName.isEmpty())
+ m_flipConsole->onPreferenceChanged();
+
+ StyleShortcutSwitchablePanel::onPreferenceChanged(prefName);
+}
+
+//-----------------------------------------------------------------------------
+
+void SceneViewerPanel::playAudioFrame(int frame) {
+ if (m_first) {
+ m_first = false;
+ m_fps = TApp::instance()
+ ->getCurrentScene()
+ ->getScene()
+ ->getProperties()
+ ->getOutputProperties()
+ ->getFrameRate();
+ m_samplesPerFrame = m_sound->getSampleRate() / abs(m_fps);
+ }
+ if (!m_sound) return;
+ m_viewerFps = m_flipConsole->getCurrentFps();
+ double s0 = frame * m_samplesPerFrame, s1 = s0 + m_samplesPerFrame;
+
+ // make the sound stop if the viewerfps is higher so the next sound can play
+ // on time.
+ if (m_fps < m_viewerFps)
+ TApp::instance()->getCurrentXsheet()->getXsheet()->stopScrub();
+ TApp::instance()->getCurrentXsheet()->getXsheet()->play(m_sound, s0, s1,
+ false);
+}
+
+bool SceneViewerPanel::hasSoundtrack() {
+ if (m_sound != NULL) {
+ m_sound = NULL;
+ m_hasSoundtrack = false;
+ m_first = true;
+ }
+ TXsheetHandle *xsheetHandle = TApp::instance()->getCurrentXsheet();
+ TXsheet::SoundProperties *prop = new TXsheet::SoundProperties();
+ m_sound = xsheetHandle->getXsheet()->makeSound(prop);
+ if (m_sound == NULL) {
+ m_hasSoundtrack = false;
+ return false;
+ } else {
+ m_hasSoundtrack = true;
+ return true;
+ }
+}
+
+void SceneViewerPanel::onButtonPressed(FlipConsole::EGadget button) {
+ if (button == FlipConsole::eSound) {
+ m_playSound = !m_playSound;
+ }
+}
diff --git a/toonz/sources/toonz/viewerpane.h b/toonz/sources/toonz/viewerpane.h
index d308604..48e5c11 100644
--- a/toonz/sources/toonz/viewerpane.h
+++ b/toonz/sources/toonz/viewerpane.h
@@ -3,7 +3,7 @@
#ifndef VIEWER_PANE_INCLUDED
#define VIEWER_PANE_INCLUDED
-#include "pane.h"
+#include "styleshortcutswitchablepanel.h"
#include "sceneviewer.h"
#include "toonzqt/intfield.h"
#include "toonzqt/keyframenavigator.h"
@@ -25,7 +25,8 @@ class Ruler;
class FlipConsole;
class TXshLevel;
-class SceneViewerPanel final : public TPanel, public FlipConsoleOwner {
+class SceneViewerPanel final : public StyleShortcutSwitchablePanel,
+ public FlipConsoleOwner {
Q_OBJECT
friend class SceneViewer;
@@ -37,6 +38,14 @@ class SceneViewerPanel final : public TPanel, public FlipConsoleOwner {
TPanelTitleBarButton *m_previewButton;
TPanelTitleBarButton *m_subcameraPreviewButton;
bool m_onionSkinActive = false;
+ bool m_playSound = true;
+ bool m_hasSoundtrack = false;
+ bool m_playing = false;
+ double m_fps;
+ int m_viewerFps;
+ double m_samplesPerFrame;
+ bool m_first = true;
+ TSoundTrack *m_sound = NULL;
public:
#if QT_VERSION >= 0x050500
@@ -58,6 +67,8 @@ protected:
void createPlayToolBar();
void addColorMaskButton(QWidget *parent, const char *iconSVGName, int id);
void enableFlipConsoleForCamerastand(bool on);
+ void playAudioFrame(int frame);
+ bool hasSoundtrack();
public slots:
@@ -66,6 +77,7 @@ public slots:
void onXshLevelSwitched(TXshLevel *);
void updateFrameRange();
void updateFrameMarkers();
+ void onButtonPressed(FlipConsole::EGadget button);
protected slots:
@@ -75,6 +87,7 @@ protected slots:
void onPlayingStatusChanged(bool playing);
void enableFullPreview(bool enabled);
void enableSubCameraPreview(bool enabled);
+ void onPreferenceChanged(const QString &prefName) override;
};
#endif
diff --git a/toonz/sources/toonz/xsheetviewer.cpp b/toonz/sources/toonz/xsheetviewer.cpp
index 6c243fd..6e45023 100644
--- a/toonz/sources/toonz/xsheetviewer.cpp
+++ b/toonz/sources/toonz/xsheetviewer.cpp
@@ -184,8 +184,8 @@ XsheetViewer::XsheetViewer(QWidget *parent, Qt::WFlags flags)
m_cellScrollArea->setWidget(m_cellArea);
m_cellScrollArea->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOn);
m_cellScrollArea->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOn);
- m_cellScrollArea->horizontalScrollBar()->setObjectName("XsheetScrollBar");
- m_cellScrollArea->verticalScrollBar()->setObjectName("XsheetScrollBar");
+ // m_cellScrollArea->horizontalScrollBar()->setObjectName("XsheetScrollBar");
+ // m_cellScrollArea->verticalScrollBar()->setObjectName("XsheetScrollBar");
m_columnArea = new XsheetGUI::ColumnArea(this);
m_columnScrollArea = new XsheetScrollArea(this);
@@ -694,13 +694,13 @@ void XsheetViewer::paintEvent(QPaintEvent*)
//-----------------------------------------------------------------------------
void XsheetViewer::resizeEvent(QResizeEvent *event) {
- int w = width();
- int h = height();
-
+ int w = width();
+ int h = height();
+ int scrollBarWidth = 16;
m_noteScrollArea->setGeometry(3, 1, m_x0 - 4, m_y0 - 3);
m_cellScrollArea->setGeometry(m_x0, m_y0, w - m_x0, h - m_y0);
- m_columnScrollArea->setGeometry(m_x0, 1, w - m_x0 - 20, m_y0 - 3);
- m_rowScrollArea->setGeometry(1, m_y0, m_x0 - 1, h - m_y0 - 20);
+ m_columnScrollArea->setGeometry(m_x0, 1, w - m_x0 - scrollBarWidth, m_y0 - 3);
+ m_rowScrollArea->setGeometry(1, m_y0, m_x0 - 1, h - m_y0 - scrollBarWidth);
//(Nuovo Layout Manager) Reintrodotto per il refresh automatico
refreshContentSize(
diff --git a/toonz/sources/toonzlib/Naa2TlvConverter.cpp b/toonz/sources/toonzlib/Naa2TlvConverter.cpp
index f740f7b..d0a5e6e 100644
--- a/toonz/sources/toonzlib/Naa2TlvConverter.cpp
+++ b/toonz/sources/toonzlib/Naa2TlvConverter.cpp
@@ -1005,7 +1005,8 @@ int Naa2TlvConverter::measureThickness(int x0, int y0) {
//-----------------------------------------------------------------------------
-TToonzImageP Naa2TlvConverter::makeTlv(bool transparentSyntheticInks) {
+TToonzImageP Naa2TlvConverter::makeTlv(bool transparentSyntheticInks,
+ bool removeUnusedStyles) {
if (!m_valid || m_colors.empty() || m_regions.empty() || !m_regionRas)
return TToonzImageP();
int lx = m_regionRas->getLx();
@@ -1025,8 +1026,9 @@ TToonzImageP Naa2TlvConverter::makeTlv(bool transparentSyntheticInks) {
if (cs->getMainColor() != color) cs = 0;
}
if (cs == 0) {
- styleId = palette->getPage(0)->addStyle(color);
- cs = palette->getStyle(styleId);
+ styleId = palette->addStyle(color);
+ palette->getPage(0)->addStyle(styleId);
+ cs = palette->getStyle(styleId);
}
styleIds.append(styleId);
}
@@ -1035,6 +1037,21 @@ TToonzImageP Naa2TlvConverter::makeTlv(bool transparentSyntheticInks) {
// int synteticInkStyleId = palette->getPage(0)->addStyle(TPixel32(0,0,0,0));
// styleIds.append(synteticInkStyleId);
+ // Remove unused styles from input palette
+ if (removeUnusedStyles) {
+ for (int p = palette->getPageCount() - 1; p >= 0; p--) {
+ TPalette::Page *page = palette->getPage(p);
+ for (int s = page->getStyleCount() - 1; s >= 0; s--) {
+ int styleId = page->getStyleId(s);
+ if (styleId == -1) continue;
+ // check if the style is used or not
+ if (!styleIds.contains(styleId)) page->removeStyle(s);
+ }
+ // erase empty page
+ if (page->getStyleCount() == 0) palette->erasePage(p);
+ }
+ }
+
for (int y = 0; y < ly; y++) {
unsigned short *workScanLine = m_regionRas->pixels(y);
TPixelCM32 *outScanLine = ras->pixels(y);
diff --git a/toonz/sources/toonzlib/convert2tlv.cpp b/toonz/sources/toonzlib/convert2tlv.cpp
index 8e9c529..2fbed64 100644
--- a/toonz/sources/toonzlib/convert2tlv.cpp
+++ b/toonz/sources/toonzlib/convert2tlv.cpp
@@ -566,6 +566,18 @@ TPalette *Convert2Tlv::buildPalette() {
page->addStyle(stylesToBeAddedToPage.at(s));
}
+ /*
+ If the palette path is empty, an initial palette with four colors are set in
+ the palette here.
+ ( see Convert2Tlv::init() ) So here I make the latter three styles in the
+ initial palette to set
+ "AutoPaint" options.
+ */
+ if (m_palettePath.isEmpty()) {
+ assert(m_palette->getStyleCount() >= 5);
+ for (int id = 2; id <= 4; id++) m_palette->getStyle(id)->setFlags(1);
+ }
+
if (!m_appendDefaultPalette) return m_palette;
/*-- Adding styles in the default palette to the result palette, starts here
@@ -810,11 +822,17 @@ bool Convert2Tlv::init(std::string &errorMessage) {
m_it = m_level1->begin();
- /*- 既定のパレットを作る。黒、赤、青、緑の順 -*/
- m_colorMap[TPixel::Black] = ++m_lastIndex;
- m_colorMap[TPixel::Red] = ++m_lastIndex;
- m_colorMap[TPixel::Blue] = ++m_lastIndex;
- m_colorMap[TPixel::Green] = ++m_lastIndex;
+ /*-
+ If the palette is empty, make an initial palette with black, red, blue and
+ green styles.
+ For the latter three styles the "autopaint" option should be set.
+ -*/
+ if (m_lastIndex == 0) {
+ m_colorMap[TPixel::Black] = ++m_lastIndex;
+ m_colorMap[TPixel::Red] = ++m_lastIndex;
+ m_colorMap[TPixel::Blue] = ++m_lastIndex;
+ m_colorMap[TPixel::Green] = ++m_lastIndex;
+ }
return true;
}
diff --git a/toonz/sources/toonzlib/movierenderer.cpp b/toonz/sources/toonzlib/movierenderer.cpp
index 924ce5b..e9f4ed4 100644
--- a/toonz/sources/toonzlib/movierenderer.cpp
+++ b/toonz/sources/toonzlib/movierenderer.cpp
@@ -209,7 +209,6 @@ void MovieRenderer::Imp::prepareForStart() {
if (TSystem::doesExistFileOrLevel(fp)) {
bool remove = false;
-
// In case the raster specifics are different from those of a currently
// existing movie, erase it
try {
@@ -217,7 +216,8 @@ void MovieRenderer::Imp::prepareForStart() {
lr->loadInfo();
const TImageInfo *info = lr->getImageInfo();
- if (!info || info->m_lx != imageSize.lx || info->m_ly != imageSize.ly)
+ if (!info || info->m_lx != imageSize.lx ||
+ info->m_ly != imageSize.ly || fp.isFfmpegType())
TSystem::removeFileOrLevel(fp); // nothrow
} catch (...) {
// Same if the level could not be read/opened
diff --git a/toonz/sources/toonzlib/outputproperties.cpp b/toonz/sources/toonzlib/outputproperties.cpp
index 3951752..0ea61b2 100644
--- a/toonz/sources/toonzlib/outputproperties.cpp
+++ b/toonz/sources/toonzlib/outputproperties.cpp
@@ -97,7 +97,7 @@ TOutputProperties &TOutputProperties::operator=(const TOutputProperties &src) {
std::map::const_iterator sft,
sfEnd = src.m_formatProperties.end();
- for (sft = src.m_formatProperties.end(); sft != sfEnd; ++sft)
+ for (sft = src.m_formatProperties.begin(); sft != sfEnd; ++sft)
m_formatProperties[sft->first] = sft->second->clone();
return *this;
diff --git a/toonz/sources/toonzlib/palettecmd.cpp b/toonz/sources/toonzlib/palettecmd.cpp
index 5e16930..c23f12e 100644
--- a/toonz/sources/toonzlib/palettecmd.cpp
+++ b/toonz/sources/toonzlib/palettecmd.cpp
@@ -33,6 +33,7 @@
#include "tstroke.h"
#include "tregion.h"
#include "tlevel_io.h"
+#include "tpixelutils.h"
#include "historytypes.h"
@@ -45,6 +46,8 @@
#include
#include
+#include
+
//===================================================================
void findPaletteLevels(set &levels, int &rowIndex,
@@ -1168,3 +1171,177 @@ void PaletteCmd::renamePaletteStyle(TPaletteHandle *paletteHandle,
paletteHandle->notifyColorStyleChanged(false);
TUndoManager::manager()->add(undo);
}
+
+//=============================================================================
+// organizePaletteStyle
+// called in ColorModelViewer::pick() - move selected style to the first page
+//-----------------------------------------------------------------------------
+namespace {
+
+class setStylePickedPositionUndo final : public TUndo {
+ TPaletteHandle *m_paletteHandle; // Used in undo and redo to notify change
+ int m_styleId;
+ TPaletteP m_palette;
+ TPoint m_newPos;
+ TPoint m_oldPos;
+
+public:
+ setStylePickedPositionUndo(TPaletteHandle *paletteHandle, int styleId,
+ const TPoint &newPos)
+ : m_paletteHandle(paletteHandle), m_styleId(styleId), m_newPos(newPos) {
+ m_palette = paletteHandle->getPalette();
+ assert(m_palette);
+ TColorStyle *style = m_palette->getStyle(m_styleId);
+ assert(style);
+ m_oldPos = style->getPickedPosition();
+ }
+ void undo() const override {
+ TColorStyle *style = m_palette->getStyle(m_styleId);
+ assert(style);
+ style->setPickedPosition(m_oldPos);
+ m_paletteHandle->notifyColorStyleChanged(false);
+ }
+ void redo() const override {
+ TColorStyle *style = m_palette->getStyle(m_styleId);
+ assert(style);
+ style->setPickedPosition(m_newPos);
+ m_paletteHandle->notifyColorStyleChanged(false);
+ }
+ int getSize() const override { return sizeof *this; }
+ QString getHistoryString() override {
+ return QObject::tr("Set Picked Position of Style#%1 in Palette%2 : %3,%4")
+ .arg(QString::number(m_styleId))
+ .arg(QString::fromStdWString(m_palette->getPaletteName()))
+ .arg(QString::number(m_newPos.x))
+ .arg(QString::number(m_newPos.y));
+ }
+ int getHistoryType() override { return HistoryType::Palette; }
+};
+}
+
+void PaletteCmd::organizePaletteStyle(TPaletteHandle *paletteHandle,
+ int styleId, const TPoint &point) {
+ if (!paletteHandle) return;
+ TPalette *palette = paletteHandle->getPalette();
+ if (!palette) return;
+ // if the style is already in the first page, then do nothing
+ TPalette::Page *page = palette->getStylePage(styleId);
+ if (!page || page->getIndex() == 0) return;
+
+ int indexInPage = page->search(styleId);
+
+ TUndoManager::manager()->beginBlock();
+
+ // call arrangeStyles() to move style to the first page
+ arrangeStyles(paletteHandle, 0, palette->getPage(0)->getStyleCount(),
+ page->getIndex(), {indexInPage});
+ // then set the picked position
+ setStylePickedPositionUndo *undo =
+ new setStylePickedPositionUndo(paletteHandle, styleId, point);
+ undo->redo();
+ TUndoManager::manager()->add(undo);
+
+ TUndoManager::manager()->endBlock();
+}
+
+//=============================================================================
+// called in ColorModelViewer::repickFromColorModel().
+// Pick color from the img for all styles with "picked position" value.
+//-----------------------------------------------------------------------------
+namespace {
+
+class pickColorByUsingPickedPositionUndo final : public TUndo {
+ TPaletteHandle *m_paletteHandle; // Used in undo and redo to notify change
+ TPaletteP m_palette;
+ QHash> m_styleList;
+
+public:
+ pickColorByUsingPickedPositionUndo(
+ TPaletteHandle *paletteHandle,
+ QHash> styleList)
+ : m_paletteHandle(paletteHandle), m_styleList(styleList) {
+ m_palette = paletteHandle->getPalette();
+ assert(m_palette);
+ }
+ void undo() const override {
+ QHash>::const_iterator i =
+ m_styleList.constBegin();
+ while (i != m_styleList.constEnd()) {
+ TColorStyle *style = m_palette->getStyle(i.key());
+ assert(style);
+ style->setMainColor(i.value().first);
+ ++i;
+ }
+ m_paletteHandle->notifyColorStyleChanged(false);
+ }
+ void redo() const override {
+ QHash>::const_iterator i =
+ m_styleList.constBegin();
+ while (i != m_styleList.constEnd()) {
+ TColorStyle *style = m_palette->getStyle(i.key());
+ assert(style);
+ style->setMainColor(i.value().second);
+ ++i;
+ }
+ m_paletteHandle->notifyColorStyleChanged(false);
+ }
+ int getSize() const override { return sizeof *this; }
+ QString getHistoryString() override {
+ return QObject::tr("Update Colors by Using Picked Positions in Palette %1")
+ .arg(QString::fromStdWString(m_palette->getPaletteName()));
+ }
+ int getHistoryType() override { return HistoryType::Palette; }
+};
+
+TPixel32 pickColor(TRasterImageP ri, const TPoint &rasterPoint) {
+ TRasterP raster;
+ raster = ri->getRaster();
+
+ if (!TRect(raster->getSize()).contains(rasterPoint))
+ return TPixel32::Transparent;
+
+ TRaster32P raster32 = raster;
+ if (raster32) return raster32->pixels(rasterPoint.y)[rasterPoint.x];
+
+ TRasterGR8P rasterGR8 = raster;
+ if (rasterGR8)
+ return toPixel32(rasterGR8->pixels(rasterPoint.y)[rasterPoint.x]);
+
+ return TPixel32::Transparent;
+}
+}
+
+void PaletteCmd::pickColorByUsingPickedPosition(TPaletteHandle *paletteHandle,
+ TImageP img) {
+ TRasterImageP ri = img;
+ if (!ri) return;
+
+ TPalette *currentPalette = paletteHandle->getPalette();
+ if (!currentPalette) return;
+
+ TDimension imgSize = ri->getRaster()->getSize();
+ QHash> styleList;
+
+ // For all styles (starting from #1 as #0 is reserved for the transparent)
+ for (int sId = 1; sId < currentPalette->getStyleCount(); sId++) {
+ TColorStyle *style = currentPalette->getStyle(sId);
+ TPoint pp = style->getPickedPosition();
+ // If style has a valid picked position
+ if (pp != TPoint() && pp.x >= 0 && pp.x < imgSize.lx && pp.y >= 0 &&
+ pp.y < imgSize.ly && style->hasMainColor()) {
+ TPixel32 beforeColor = style->getMainColor();
+ TPixel32 afterColor = pickColor(ri, pp);
+ style->setMainColor(afterColor);
+ //... store the style in the list for undo
+ styleList.insert(sId, QPair(beforeColor, afterColor));
+ }
+ }
+
+ // if some style has been changed, then register undo and notify changes
+ if (!styleList.isEmpty()) {
+ pickColorByUsingPickedPositionUndo *undo =
+ new pickColorByUsingPickedPositionUndo(paletteHandle, styleList);
+ TUndoManager::manager()->add(undo);
+ paletteHandle->notifyColorStyleChanged(false, true); // set dirty flag here
+ }
+}
\ No newline at end of file
diff --git a/toonz/sources/toonzlib/preferences.cpp b/toonz/sources/toonzlib/preferences.cpp
index e7da85d..3d63618 100644
--- a/toonz/sources/toonzlib/preferences.cpp
+++ b/toonz/sources/toonzlib/preferences.cpp
@@ -23,6 +23,7 @@
// Qt includes
#include
#include
+#include
// boost includes
#include
@@ -255,6 +256,9 @@ Preferences::Preferences()
, m_fitToFlipbookEnabled(false)
, m_previewAlwaysOpenNewFlipEnabled(false)
, m_autosaveEnabled(false)
+ , m_autosaveSceneEnabled(true)
+ , m_autosaveOtherFilesEnabled(true)
+ , m_startupPopupEnabled(true)
, m_defaultViewerEnabled(false)
, m_saveUnpaintedInCleanup(true)
, m_askForOverrideRender(true)
@@ -290,7 +294,10 @@ Preferences::Preferences()
, m_projectRoot(0x08)
, m_customProjectRoot("")
, m_precompute(true)
- , m_ffmpegTimeout(30) {
+ , m_fastRenderPath("desktop")
+ , m_ffmpegTimeout(30)
+ , m_shortcutPreset("defopentoonz")
+ , m_useNumpadForSwitchingStyles(true) {
TCamera camera;
m_defLevelType = PLI_XSHLEVEL;
m_defLevelWidth = camera.getSize().lx;
@@ -324,6 +331,10 @@ Preferences::Preferences()
getValue(*m_settings, "sceneNumberingEnabled", m_sceneNumberingEnabled);
getValue(*m_settings, "animationSheetEnabled", m_animationSheetEnabled);
getValue(*m_settings, "autosaveEnabled", m_autosaveEnabled);
+ getValue(*m_settings, "autosaveSceneEnabled", m_autosaveSceneEnabled);
+ getValue(*m_settings, "autosaveOtherFilesEnabled",
+ m_autosaveOtherFilesEnabled);
+ getValue(*m_settings, "startupPopupEnabled", m_startupPopupEnabled);
getValue(*m_settings, "defaultViewerEnabled", m_defaultViewerEnabled);
getValue(*m_settings, "rasterOptimizedMemory", m_rasterOptimizedMemory);
getValue(*m_settings, "saveUnpaintedInCleanup", m_saveUnpaintedInCleanup);
@@ -551,7 +562,15 @@ Preferences::Preferences()
QString ffmpegPath = m_settings->value("ffmpegPath").toString();
if (ffmpegPath != "") m_ffmpegPath = ffmpegPath;
setFfmpegPath(m_ffmpegPath.toStdString());
+ QString fastRenderPath = m_settings->value("fastRenderPath").toString();
+ if (fastRenderPath != "") m_fastRenderPath = fastRenderPath;
+ setFastRenderPath(m_fastRenderPath.toStdString());
getValue(*m_settings, "ffmpegTimeout", m_ffmpegTimeout);
+ QString shortcutPreset = m_settings->value("shortcutPreset").toString();
+ if (shortcutPreset != "") m_shortcutPreset = shortcutPreset;
+ setShortcutPreset(m_shortcutPreset.toStdString());
+ getValue(*m_settings, "useNumpadForSwitchingStyles",
+ m_useNumpadForSwitchingStyles);
}
//-----------------------------------------------------------------
@@ -644,6 +663,27 @@ void Preferences::enableAutosave(bool on) {
//-----------------------------------------------------------------
+void Preferences::enableAutosaveScene(bool on) {
+ m_autosaveSceneEnabled = on;
+ m_settings->setValue("autosaveSceneEnabled", on ? "1" : "0");
+}
+
+//-----------------------------------------------------------------
+
+void Preferences::enableAutosaveOtherFiles(bool on) {
+ m_autosaveOtherFilesEnabled = on;
+ m_settings->setValue("autosaveOtherFilesEnabled", on ? "1" : "0");
+}
+
+//-----------------------------------------------------------------
+
+void Preferences::enableStartupPopup(bool on) {
+ m_startupPopupEnabled = on;
+ m_settings->setValue("startupPopupEnabled", on ? "1" : "0");
+}
+
+//-----------------------------------------------------------------
+
void Preferences::setAskForOverrideRender(bool on) {
m_autosaveEnabled = on;
m_settings->setValue("askForOverrideRender", on ? "1" : "0");
@@ -1223,6 +1263,21 @@ void Preferences::setFfmpegPath(std::string path) {
//-----------------------------------------------------------------
+void Preferences::setFastRenderPath(std::string path) {
+ m_fastRenderPath = QString::fromStdString(path);
+ std::string strPath = m_ffmpegPath.toStdString();
+ m_settings->setValue("fastRenderPath", m_fastRenderPath);
+}
+
+//-----------------------------------------------------------------
+
+void Preferences::setShortcutPreset(std::string preset) {
+ m_shortcutPreset = QString::fromStdString(preset);
+ m_settings->setValue("shortcutPreset", m_shortcutPreset);
+}
+
+//-----------------------------------------------------------------
+
void Preferences::setPrecompute(bool enabled) { m_precompute = enabled; }
//-----------------------------------------------------------------
@@ -1281,3 +1336,10 @@ int Preferences::matchLevelFormat(const TFilePath &fp) const {
return (lft != m_levelFormats.end()) ? lft - m_levelFormats.begin() : -1;
}
+
+//-----------------------------------------------------------------
+
+void Preferences::enableUseNumpadForSwitchingStyles(bool on) {
+ m_useNumpadForSwitchingStyles = on;
+ m_settings->setValue("useNumpadForSwitchingStyles", on ? "1" : "0");
+}
\ No newline at end of file
diff --git a/toonz/sources/toonzlib/sceneproperties.cpp b/toonz/sources/toonzlib/sceneproperties.cpp
index 154bfd5..76b6e25 100644
--- a/toonz/sources/toonzlib/sceneproperties.cpp
+++ b/toonz/sources/toonzlib/sceneproperties.cpp
@@ -80,8 +80,6 @@ void TSceneProperties::assign(const TSceneProperties *sprop) {
for (int i = 0; i < (int)m_cameras.size(); i++)
m_cameras[i] = new TCamera(*m_cameras[i]);
}
- *m_outputProp = *sprop->m_outputProp;
- *m_previewProp = *sprop->m_previewProp;
m_bgColor = sprop->m_bgColor;
m_markerDistance = sprop->m_markerDistance;
m_markerOffset = sprop->m_markerOffset;
diff --git a/toonz/sources/toonzlib/stagevisitor.cpp b/toonz/sources/toonzlib/stagevisitor.cpp
index f3746ab..dc256db 100644
--- a/toonz/sources/toonzlib/stagevisitor.cpp
+++ b/toonz/sources/toonzlib/stagevisitor.cpp
@@ -602,6 +602,9 @@ void RasterPainter::flushRasterImages() {
glDisable(GL_DITHER);
glDisable(GL_LOGIC_OP);
+/* disable, since these features are never enabled, and cause OpenGL to assert
+ * on systems that don't support them: see #591 */
+#if 0
#ifdef GL_EXT_convolution
glDisable(GL_CONVOLUTION_1D_EXT);
glDisable(GL_CONVOLUTION_2D_EXT);
@@ -612,6 +615,7 @@ void RasterPainter::flushRasterImages() {
glDisable(GL_HISTOGRAM_EXT);
glDisable(GL_MINMAX_EXT);
#endif
+#endif
#ifdef GL_EXT_texture3D
glDisable(GL_TEXTURE_3D_EXT);
diff --git a/toonz/sources/toonzlib/studiopalettecmd.cpp b/toonz/sources/toonzlib/studiopalettecmd.cpp
index 8cf07e9..c8023ec 100644
--- a/toonz/sources/toonzlib/studiopalettecmd.cpp
+++ b/toonz/sources/toonzlib/studiopalettecmd.cpp
@@ -501,7 +501,11 @@ void StudioPaletteCmd::loadIntoCurrentPalette(TPaletteHandle *paletteHandle,
// keep the color model path unchanged
TFilePath oldRefImagePath = current->getRefImgPath();
+ std::wstring oldGlobalName = current->getGlobalName();
current->assign(palette, true);
+ // keep global name unchanged
+ current->setGlobalName(oldGlobalName);
+
current->setDirtyFlag(true);
current->setRefImgPath(oldRefImagePath);
diff --git a/toonz/sources/toonzlib/tproject.cpp b/toonz/sources/toonzlib/tproject.cpp
index ec9ef5a..0a6b82e 100644
--- a/toonz/sources/toonzlib/tproject.cpp
+++ b/toonz/sources/toonzlib/tproject.cpp
@@ -298,13 +298,15 @@ void TProject::setFolder(string name) { setFolder(name, TFilePath(name)); }
//-------------------------------------------------------------------
/*! Returns the path of the folder named with \b name.\n
Returns TFilePath() if there isn't a folder named with \b name.
- \note The returned path could be a relative path.
+ \note The returned path could be a relative path if \b absolute is
+ false.
*/
-TFilePath TProject::getFolder(string name) const {
+TFilePath TProject::getFolder(string name, bool absolute) const {
std::map::const_iterator it;
it = m_folders.find(name);
if (it != m_folders.end())
- return it->second;
+ return (absolute) ? makeAbsolute(getProjectFolder(), it->second)
+ : it->second;
else
return TFilePath();
}
diff --git a/toonz/sources/toonzqt/dvdialog.cpp b/toonz/sources/toonzqt/dvdialog.cpp
index 281586e..59cfbd8 100644
--- a/toonz/sources/toonzqt/dvdialog.cpp
+++ b/toonz/sources/toonzqt/dvdialog.cpp
@@ -729,6 +729,23 @@ void Dialog::addButtonBarWidget(QWidget *first, QWidget *second,
}
}
+//-----------------------------------------------------------------------------
+/*! Add four widget to the button part of dialog.
+*/
+void Dialog::addButtonBarWidget(QWidget *first, QWidget *second, QWidget *third,
+ QWidget *fourth) {
+ first->setMinimumSize(65, 25);
+ second->setMinimumSize(65, 25);
+ third->setMinimumSize(65, 25);
+ assert(m_hasButton);
+ if (m_hasButton) {
+ m_buttonLayout->addWidget(first);
+ m_buttonLayout->addWidget(second);
+ m_buttonLayout->addWidget(third);
+ m_buttonLayout->addWidget(fourth);
+ }
+}
+
//=============================================================================
RadioButtonDialog::RadioButtonDialog(const QString &labelText,
@@ -1060,6 +1077,65 @@ int DVGui::MsgBox(const QString &text, const QString &button1Text,
//-----------------------------------------------------------------------------
+int DVGui::MsgBox(const QString &text, const QString &button1Text,
+ const QString &button2Text, const QString &button3Text,
+ const QString &button4Text, int defaultButtonIndex,
+ QWidget *parent) {
+ Dialog dialog(parent, true);
+ dialog.setWindowFlags(dialog.windowFlags() | Qt::WindowStaysOnTopHint);
+ dialog.setAlignment(Qt::AlignLeft);
+ QString msgBoxTitle = getMsgBoxTitle(QUESTION);
+ dialog.setWindowTitle(msgBoxTitle);
+
+ QLabel *mainTextLabel = new QLabel(text, &dialog);
+ QPixmap iconPixmap = getMsgBoxPixmap(QUESTION);
+ if (!iconPixmap.isNull()) {
+ QLabel *iconLabel = new QLabel(&dialog);
+ iconLabel->setPixmap(iconPixmap);
+
+ QHBoxLayout *mainLayout = new QHBoxLayout;
+ mainLayout->addWidget(iconLabel);
+ mainLayout->addSpacing(16);
+ mainLayout->addWidget(mainTextLabel);
+ dialog.addLayout(mainLayout);
+ } else
+ dialog.addWidget(mainTextLabel);
+
+ // ButtonGroup: is used only to retrieve the clicked button
+ QButtonGroup *buttonGroup = new QButtonGroup(&dialog);
+
+ QPushButton *button1 = new QPushButton(button1Text, &dialog);
+ button1->setDefault(false);
+ if (defaultButtonIndex == 0) button1->setDefault(true);
+ dialog.addButtonBarWidget(button1);
+ buttonGroup->addButton(button1, 1);
+
+ QPushButton *button2 = new QPushButton(button2Text, &dialog);
+ button2->setDefault(false);
+ if (defaultButtonIndex == 1) button2->setDefault(true);
+ dialog.addButtonBarWidget(button2);
+ buttonGroup->addButton(button2, 2);
+
+ QPushButton *button3 = new QPushButton(button3Text, &dialog);
+ button3->setDefault(false);
+ if (defaultButtonIndex == 2) button3->setDefault(true);
+ dialog.addButtonBarWidget(button3);
+ buttonGroup->addButton(button3, 3);
+
+ QPushButton *button4 = new QPushButton(button4Text, &dialog);
+ button4->setDefault(false);
+ if (defaultButtonIndex == 3) button4->setDefault(true);
+ dialog.addButtonBarWidget(button4);
+ buttonGroup->addButton(button4, 4);
+
+ QObject::connect(buttonGroup, SIGNAL(buttonPressed(int)), &dialog,
+ SLOT(done(int)));
+ dialog.raise();
+ return dialog.exec();
+}
+
+//-----------------------------------------------------------------------------
+
int DVGui::MsgBox(const QString &text, const QString &button1,
const QString &button2, int defaultButtonIndex,
QWidget *parent) {
diff --git a/toonz/sources/toonzqt/filefield.cpp b/toonz/sources/toonzqt/filefield.cpp
index 3a32da2..1832f08 100644
--- a/toonz/sources/toonzqt/filefield.cpp
+++ b/toonz/sources/toonzqt/filefield.cpp
@@ -18,7 +18,8 @@ FileField::BrowserPopupController *FileField::m_browserPopupController = 0;
// FileField
//-----------------------------------------------------------------------------
-FileField::FileField(QWidget *parent, QString path, bool readOnly)
+FileField::FileField(QWidget *parent, QString path, bool readOnly,
+ bool doNotBrowseInitialPath)
: QWidget(parent)
, m_filters(QStringList())
, m_fileMode(QFileDialog::DirectoryOnly)
@@ -33,6 +34,9 @@ FileField::FileField(QWidget *parent, QString path, bool readOnly)
m_fileBrowseButton->setMinimumSize(20, WidgetHeight);
m_fileBrowseButton->setObjectName("PushButton_NoPadding");
+ // if the initial text is not path, set the string here and prevent browsing
+ if (doNotBrowseInitialPath) m_descriptionText = path;
+
QHBoxLayout *mainLayout = new QHBoxLayout();
mainLayout->setMargin(0);
mainLayout->setSpacing(1);
@@ -90,7 +94,7 @@ void FileField::browseDirectory() {
if (!m_browserPopupController) return;
m_browserPopupController->openPopup(
m_filters, (m_fileMode == QFileDialog::DirectoryOnly),
- m_lastSelectedPath);
+ (m_lastSelectedPath == m_descriptionText) ? "" : m_lastSelectedPath);
if (m_browserPopupController->isExecute())
directory = m_browserPopupController->getPath();
diff --git a/toonz/sources/toonzqt/flipconsole.cpp b/toonz/sources/toonzqt/flipconsole.cpp
index 706bb6e..1caa5ac 100644
--- a/toonz/sources/toonzqt/flipconsole.cpp
+++ b/toonz/sources/toonzqt/flipconsole.cpp
@@ -1234,16 +1234,19 @@ void FlipConsole::createPlayToolBar(bool withCustomWidget) {
if (m_gadgetsMask & eRed || m_gadgetsMask & eGRed)
m_colorFilterSep = m_playToolBar->addSeparator();
- // Sound & Histogram
- if (m_gadgetsMask & eSound || m_gadgetsMask & eHisto) {
+ // Sound & Histogram & Locator
+ if (m_gadgetsMask & eSound || m_gadgetsMask & eHisto ||
+ m_gadgetsMask & eLocator) {
if (m_gadgetsMask & eSound) {
createButton(eSound, "sound", tr("&Soundtrack "), true);
m_soundSep = m_playToolBar->addSeparator();
}
- if (m_gadgetsMask & eHisto) {
+ if (m_gadgetsMask & eHisto)
createButton(eHisto, "histograms", tr("&Histogram"), false);
+ if (m_gadgetsMask & eLocator)
+ createButton(eLocator, "locator", tr("&Locator"), false);
+ if (m_gadgetsMask & eHisto || m_gadgetsMask & eLocator)
m_histoSep = m_playToolBar->addSeparator();
- }
}
if (m_gadgetsMask & eFilledRaster) {
@@ -1572,6 +1575,7 @@ void FlipConsole::doButtonPressed(UINT button) {
case eHisto:
case eSaveImg:
case eSave:
+ case eLocator:
// nothing to do
return;
diff --git a/toonz/sources/toonzqt/functiontreeviewer.cpp b/toonz/sources/toonzqt/functiontreeviewer.cpp
index bcfcd2c..58be7a8 100644
--- a/toonz/sources/toonzqt/functiontreeviewer.cpp
+++ b/toonz/sources/toonzqt/functiontreeviewer.cpp
@@ -1184,11 +1184,14 @@ void FunctionTreeModel::onChange(const TParamChange &tpc) {
struct Func final : public TFunctorInvoker::BaseFunctor {
FunctionTreeModel *m_obj;
- const TParamChange *m_tpc;
+ // Use a copy of 'TParamChange' since callers declare
+ // and free this value on the stack,
+ // so we can't ensure its valid later on when the notifier executes.
+ const TParamChange m_tpc;
Func(FunctionTreeModel *obj, const TParamChange *tpc)
- : m_obj(obj), m_tpc(tpc) {}
- void operator()() override { m_obj->onParamChange(m_tpc->m_dragging); }
+ : m_obj(obj), m_tpc(*tpc) {}
+ void operator()() override { m_obj->onParamChange(m_tpc.m_dragging); }
};
QMetaObject::invokeMethod(TFunctorInvoker::instance(), "invoke",
diff --git a/toonz/sources/toonzqt/imageutils.cpp b/toonz/sources/toonzqt/imageutils.cpp
index 24fcf11..06b67b6 100644
--- a/toonz/sources/toonzqt/imageutils.cpp
+++ b/toonz/sources/toonzqt/imageutils.cpp
@@ -632,7 +632,8 @@ void convert(const TFilePath &source, const TFilePath &dest,
void convertNaa2Tlv(const TFilePath &source, const TFilePath &dest,
const TFrameId &from, const TFrameId &to,
- FrameTaskNotifier *frameNotifier, TPalette *palette) {
+ FrameTaskNotifier *frameNotifier, TPalette *palette,
+ bool removeUnusedStyles) {
std::string dstExt = dest.getType(), srcExt = source.getType();
// Load source level structure
@@ -671,8 +672,8 @@ void convertNaa2Tlv(const TFilePath &source, const TFilePath &dest,
converter.process(raster);
- if (TToonzImageP dstImg =
- converter.makeTlv(false)) // Opaque synthetic inks
+ if (TToonzImageP dstImg = converter.makeTlv(
+ false, removeUnusedStyles)) // Opaque synthetic inks
{
if (converter.getPalette() == 0)
converter.setPalette(dstImg->getPalette());
diff --git a/toonz/sources/toonzqt/menubarcommand.cpp b/toonz/sources/toonzqt/menubarcommand.cpp
index 5e9612f..723cfda 100644
--- a/toonz/sources/toonzqt/menubarcommand.cpp
+++ b/toonz/sources/toonzqt/menubarcommand.cpp
@@ -279,7 +279,8 @@ int CommandManager::getKeyFromId(const char *id) {
//---------------------------------------------------------
-void CommandManager::setShortcut(QAction *action, std::string shortcutString) {
+void CommandManager::setShortcut(QAction *action, std::string shortcutString,
+ bool keepDefault) {
QString shortcut = QString::fromStdString(shortcutString);
std::string oldShortcutString = action->shortcut().toString().toStdString();
@@ -296,7 +297,7 @@ void CommandManager::setShortcut(QAction *action, std::string shortcutString) {
if (node->m_type == ZoomCommandType && ks.count() > 1) {
DVGui::warning(
- QObject::tr("It is not possible to assing a shortcut with modifiers to "
+ QObject::tr("It is not possible to assign a shortcut with modifiers to "
"the visualization commands."));
return;
}
@@ -328,7 +329,9 @@ void CommandManager::setShortcut(QAction *action, std::string shortcutString) {
settings.beginGroup("shortcuts");
settings.setValue(QString::fromStdString(node->m_id),
QString::fromStdString(shortcutString));
- if (oldActionId != "") settings.remove(oldActionId);
+ if (keepDefault) {
+ if (oldActionId != "") settings.remove(oldActionId);
+ }
settings.endGroup();
}
diff --git a/toonz/sources/toonzqt/paletteviewer.cpp b/toonz/sources/toonzqt/paletteviewer.cpp
index faace8b..b7a59ea 100644
--- a/toonz/sources/toonzqt/paletteviewer.cpp
+++ b/toonz/sources/toonzqt/paletteviewer.cpp
@@ -911,10 +911,7 @@ void PaletteViewer::saveStudioPalette() {
if (ret == 2 || ret == 0) return;
sp->setPalette(fp, getPalette(), false);
- question = "Do you want to update all linked styles in current scene ?";
- ret = DVGui::MsgBox(question, tr("Update"), tr("Don't Update"), 0);
- if (ret == 1)
- StudioPaletteCmd::updateAllLinkedStyles(m_paletteHandle, m_xsheetHandle);
+ StudioPaletteCmd::updateAllLinkedStyles(m_paletteHandle, m_xsheetHandle);
palette->setDirtyFlag(false);
}
diff --git a/toonz/sources/toonzqt/paletteviewergui.cpp b/toonz/sources/toonzqt/paletteviewergui.cpp
index b22622c..4cabe0d 100644
--- a/toonz/sources/toonzqt/paletteviewergui.cpp
+++ b/toonz/sources/toonzqt/paletteviewergui.cpp
@@ -454,6 +454,10 @@ void PageViewer::drawColorName(QPainter &p, QRect &nameRect, TColorStyle *style,
name += " " + toQString(g.first) + ":" + QString::number(g.second);
if (style->getFlags() != 0) name += "(autopaint)";
+ TPoint pickedPos = style->getPickedPosition();
+ if (pickedPos != TPoint())
+ name += QString(" (%1,%2)").arg(pickedPos.x).arg(pickedPos.y);
+
p.drawText(nameRect.adjusted(6, 4, -6, -4), name);
QColor borderCol(getTextColor());
@@ -587,6 +591,18 @@ void PageViewer::paintEvent(QPaintEvent *e) {
QRect nameRect = getColorNameRect(i);
drawColorName(p, nameRect, style, styleIndex);
+ // if numpad shortcut is activated, draw shortcut scope
+ if (Preferences::instance()->isUseNumpadForSwitchingStylesEnabled() &&
+ m_viewType == LEVEL_PALETTE &&
+ palette->getStyleShortcut(styleIndex) >= 0) {
+ p.setPen(QPen(QColor(0, 0, 0, 128), 2));
+ p.drawLine(nameRect.topLeft() + QPoint(2, 1),
+ nameRect.bottomLeft() + QPoint(2, 0));
+ p.setPen(QPen(QColor(255, 255, 255, 128), 2));
+ p.drawLine(nameRect.topLeft() + QPoint(4, 1),
+ nameRect.bottomLeft() + QPoint(4, 0));
+ }
+
// selezione
if (m_styleSelection->isSelected(m_page->getIndex(), i)) {
p.setPen(Qt::white);
@@ -622,10 +638,37 @@ void PageViewer::paintEvent(QPaintEvent *e) {
TColorStyle *style = m_page->getStyle(i);
int styleIndex = m_page->getStyleId(i);
+ // if numpad shortcut is activated, draw shortcut scope
+ if (Preferences::instance()->isUseNumpadForSwitchingStylesEnabled() &&
+ m_viewType == LEVEL_PALETTE &&
+ palette->getStyleShortcut(styleIndex) >= 0) {
+ QRect itemRect = getItemRect(i);
+ // paint dark
+ p.setPen(Qt::NoPen);
+ p.setBrush(QColor(0, 0, 0, 64));
+ p.drawRect(itemRect);
+ // check the neighbours and draw light lines
+ p.setPen(QPen(QColor(255, 255, 255, 128), 2));
+ // top
+ if (!hasShortcut(i - m_chipPerRow))
+ p.drawLine(itemRect.topLeft(), itemRect.topRight() - QPoint(1, 0));
+ // left
+ if (i % m_chipPerRow == 0 || !hasShortcut(i - 1))
+ p.drawLine(itemRect.topLeft() + QPoint(0, 1), itemRect.bottomLeft());
+ // bottom
+ if (!hasShortcut(i + m_chipPerRow))
+ p.drawLine(itemRect.bottomLeft() + QPoint(1, 0),
+ itemRect.bottomRight());
+ // right
+ if ((i + 1) % m_chipPerRow == 0 || !hasShortcut(i + 1))
+ p.drawLine(itemRect.topRight(),
+ itemRect.bottomRight() - QPoint(0, 1));
+ }
+
// draw white frame if the style is selected or current
if (m_styleSelection->isSelected(m_page->getIndex(), i) ||
currentStyleIndex == styleIndex) {
- QRect itemRect = getItemRect(i).adjusted(-1, -2, 1, 2);
+ QRect itemRect = getItemRect(i).adjusted(0, -1, 0, 1);
p.setPen(Qt::NoPen);
p.setBrush(Qt::white);
p.drawRoundRect(itemRect, 7, 25);
@@ -772,10 +815,39 @@ void PageViewer::paintEvent(QPaintEvent *e) {
p.drawText(indexRect, Qt::AlignCenter, QString().setNum(styleIndex));
// draw "Autopaint for lines" indicator
+ int offset = 0;
if (style->getFlags() != 0) {
QRect aflRect(chipRect.bottomLeft() + QPoint(0, -14), QSize(12, 15));
p.drawRect(aflRect);
p.drawText(aflRect, Qt::AlignCenter, "A");
+ offset += 12;
+ }
+
+ // draw "Picked Position" indicator (not show on small chip mode)
+ if (style->getPickedPosition() != TPoint() && m_viewMode != SmallChips) {
+ QRect ppRect(chipRect.bottomLeft() + QPoint(offset, -14),
+ QSize(12, 15));
+ p.drawRect(ppRect);
+ QPoint markPos = ppRect.center() + QPoint(1, 0);
+ p.drawEllipse(markPos, 3, 3);
+ p.drawLine(markPos - QPoint(5, 0), markPos + QPoint(5, 0));
+ p.drawLine(markPos - QPoint(0, 5), markPos + QPoint(0, 5));
+ }
+
+ // if numpad shortcut is activated, draw shortcut number on top
+ if (Preferences::instance()->isUseNumpadForSwitchingStylesEnabled() &&
+ m_viewType == LEVEL_PALETTE &&
+ palette->getStyleShortcut(styleIndex) >= 0 &&
+ m_viewMode != SmallChips) {
+ int key = palette->getStyleShortcut(styleIndex);
+ int shortcut = key - Qt::Key_0;
+ QRect ssRect(chipRect.center().x() - 8, chipRect.top() - 11, 16, 20);
+ p.setBrush(Qt::gray);
+ p.drawChord(ssRect, 0, -180 * 16);
+ tmpFont.setPointSize(6);
+ p.setFont(tmpFont);
+ p.drawText(ssRect.adjusted(0, 10, 0, 0), Qt::AlignCenter,
+ QString().setNum(shortcut));
}
// revert font set
@@ -1023,27 +1095,21 @@ void PageViewer::contextMenuEvent(QContextMenuEvent *event) {
// remove links from studio palette
if (m_viewType == LEVEL_PALETTE && m_styleSelection &&
- !m_styleSelection->isEmpty() && !isLocked) {
+ !m_styleSelection->isEmpty() && !isLocked &&
+ m_styleSelection->hasLinkedStyle()) {
menu.addSeparator();
- QAction *removeLinkAct = menu.addAction(tr("Remove Links"));
- connect(removeLinkAct, SIGNAL(triggered()), this, SLOT(removeLink()));
+ QAction *toggleStyleLink = cmd->getAction("MI_ToggleLinkToStudioPalette");
+ menu.addAction(toggleStyleLink);
+ QAction *removeStyleLink =
+ cmd->getAction("MI_RemoveReferenceToStudioPalette");
+ menu.addAction(removeStyleLink);
+ QAction *getBackOriginalAct =
+ cmd->getAction("MI_GetColorFromStudioPalette");
+ menu.addAction(getBackOriginalAct);
}
if (((indexPage == 0 && index > 0) || (indexPage > 0 && index >= 0)) &&
index < getChipCount() && !isLocked) {
- // iwsw commented out temporarly
- /*
- wstring globalName = m_page->getStyle(index)->getGlobalName();
- if (m_viewType != STUDIO_PALETTE &&
- globalName != L"" &&
- (globalName[0] == L'-' || globalName[0] == L'+'))
- {
- createMenuAction(menu, "MI_ToggleLinkToStudioPalette", tr("Toggle
- Link to Studio Palette"), "toggleLink()");
- createMenuAction(menu, "MI_RemoveReferenceToStudioPalette",
- tr("Remove Reference to Studio Palette"), "eraseToggleLink()");
- }
- */
if (pasteValueAct) pasteValueAct->setEnabled(true);
if (pasteColorsAct) pasteColorsAct->setEnabled(true);
@@ -1061,29 +1127,20 @@ void PageViewer::contextMenuEvent(QContextMenuEvent *event) {
clearAct->setEnabled(false);
}
- // get color from the original studio palette
- if (m_viewType == LEVEL_PALETTE && m_styleSelection &&
- !m_styleSelection->isEmpty() && !isLocked) {
+ if (m_page) {
menu.addSeparator();
- QAction *getBackOriginalAct =
- cmd->getAction("MI_GetColorFromStudioPalette");
- menu.addAction(getBackOriginalAct);
+ QAction *newStyle = menu.addAction(tr("New Style"));
+ connect(newStyle, SIGNAL(triggered()), SLOT(addNewColor()));
+ QAction *newPage = menu.addAction(tr("New Page"));
+ connect(newPage, SIGNAL(triggered()), SLOT(addNewPage()));
}
- // iwsw commented out temporarly
/*
- if (m_viewType != STUDIO_PALETTE)
- {
- menu.addSeparator();
+ if (m_viewType != STUDIO_PALETTE) {
menu.addAction(cmd->getAction(MI_EraseUnusedStyles));
}
*/
- if (m_page) {
- QAction *newStyle = menu.addAction(tr("New Style"));
- connect(newStyle, SIGNAL(triggered()), SLOT(addNewColor()));
- QAction *newPage = menu.addAction(tr("New Page"));
- connect(newPage, SIGNAL(triggered()), SLOT(addNewPage()));
- }
+
menu.exec(event->globalPos());
}
@@ -1371,22 +1428,12 @@ void PageViewer::onStyleRenamed() {
}
//-----------------------------------------------------------------------------
-/*! Recall \b TStyleSelection::toggleLink() to current page style selection.
-*/
-void PageViewer::toggleLink() {
- if (!m_page || !m_styleSelection || m_styleSelection->isEmpty()) return;
- m_styleSelection->toggleLink();
- update();
- emit changeWindowTitleSignal();
-}
-//-----------------------------------------------------------------------------
-/*! Recall \b TStyleSelection::eraseToggleLink() to current page style
- * selection.
-*/
-void PageViewer::eraseToggleLink() {
- if (!m_page || !m_styleSelection || m_styleSelection->isEmpty()) return;
- m_styleSelection->eraseToggleLink();
+bool PageViewer::hasShortcut(int indexInPage) {
+ if (!m_page) return false;
+ if (indexInPage < 0 || indexInPage >= m_page->getStyleCount()) return false;
+ int styleIndex = m_page->getStyleId(indexInPage);
+ return (m_page->getPalette()->getStyleShortcut(styleIndex) >= 0);
}
//=============================================================================
@@ -1652,13 +1699,6 @@ void PageViewer::updateCommandLocks() {
cmd->getAction("MI_BlendColors")->setEnabled(!isLocked);
cmd->getAction("MI_PasteNames")->setEnabled(!isLocked);
cmd->getAction("MI_GetColorFromStudioPalette")->setEnabled(!isLocked);
-}
-
-//-----------------------------------------------------------------------------
-/*! remove link and revert to the normal style
-*/
-void PageViewer::removeLink() {
- if (!m_page || !m_styleSelection || m_styleSelection->isEmpty()) return;
-
- if (m_styleSelection->removeLink()) emit changeWindowTitleSignal();
+ cmd->getAction("MI_ToggleLinkToStudioPalette")->setEnabled(!isLocked);
+ cmd->getAction("MI_RemoveReferenceToStudioPalette")->setEnabled(!isLocked);
}
diff --git a/toonz/sources/toonzqt/spreadsheetviewer.cpp b/toonz/sources/toonzqt/spreadsheetviewer.cpp
index 353a0b5..8c375e9 100644
--- a/toonz/sources/toonzqt/spreadsheetviewer.cpp
+++ b/toonz/sources/toonzqt/spreadsheetviewer.cpp
@@ -413,8 +413,8 @@ SpreadsheetViewer::SpreadsheetViewer(QWidget *parent)
m_cellScrollArea->setObjectName("ScrollArea");
m_cellScrollArea->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOn);
m_cellScrollArea->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOn);
- m_cellScrollArea->horizontalScrollBar()->setObjectName("XsheetScrollBar");
- m_cellScrollArea->verticalScrollBar()->setObjectName("XsheetScrollBar");
+ // m_cellScrollArea->horizontalScrollBar()->setObjectName("XsheetScrollBar");
+ // m_cellScrollArea->verticalScrollBar()->setObjectName("XsheetScrollBar");
m_cellScrollArea->setFocusPolicy(Qt::NoFocus);
m_columnScrollArea->setSizePolicy(
@@ -435,14 +435,15 @@ SpreadsheetViewer::SpreadsheetViewer(QWidget *parent)
layout->addWidget(m_rowScrollArea, 1, 0);
layout->addWidget(m_cellScrollArea, 1, 1, 2, 2);
+ int scrollBarWidth = 16;
// upper-right
QWidget *w = new QWidget(this);
- w->setFixedSize(QSize(20, m_rowHeight * 3 + 60 - 63));
+ w->setFixedSize(QSize(scrollBarWidth, m_rowHeight * 3 + 60 - 63));
layout->addWidget(w, 0, 2);
// lower-left
w = new QWidget(this);
- w->setFixedSize(QSize(30, 20));
+ w->setFixedSize(QSize(30, scrollBarWidth));
layout->addWidget(w, 2, 0);
layout->setColumnStretch(0, 0);
diff --git a/toonz/sources/toonzqt/studiopaletteviewer.cpp b/toonz/sources/toonzqt/studiopaletteviewer.cpp
index 052335e..1ba4e37 100644
--- a/toonz/sources/toonzqt/studiopaletteviewer.cpp
+++ b/toonz/sources/toonzqt/studiopaletteviewer.cpp
@@ -497,6 +497,7 @@ void StudioPaletteTreeViewer::onCurrentItemChanged(QTreeWidgetItem *current,
m_currentPalette = StudioPalette::instance()->getPalette(newPath, false);
m_studioPaletteHandle->setPalette(m_currentPalette.getPointer());
m_studioPaletteHandle->notifyPaletteSwitched();
+ StudioPaletteCmd::updateAllLinkedStyles(m_levelPaletteHandle, m_xsheetHandle);
}
//-----------------------------------------------------------------------------
@@ -1049,6 +1050,8 @@ void StudioPaletteTreeViewer::dropEvent(QDropEvent *event) {
resetDropItem();
+ if (newPath.isEmpty()) return;
+
const QMimeData *mimeData = event->mimeData();
const PaletteData *paletteData = dynamic_cast(mimeData);
if (paletteData) {
diff --git a/toonz/sources/toonzqt/styleeditor.cpp b/toonz/sources/toonzqt/styleeditor.cpp
index 107db3e..361b879 100644
--- a/toonz/sources/toonzqt/styleeditor.cpp
+++ b/toonz/sources/toonzqt/styleeditor.cpp
@@ -3060,9 +3060,13 @@ void StyleEditor::onStyleSwitched() {
QString::fromStdWString(L" Palette : " + palette->getPaletteName());
// style name
- statusText += QString::fromStdWString(L" | Style#");
+ statusText += QString::fromStdWString(L" | #");
statusText += QString::number(styleIndex);
statusText += QString::fromStdWString(L" : " + m_editedStyle->getName());
+ TPoint pickedPos = m_editedStyle->getPickedPosition();
+ if (pickedPos != TPoint())
+ statusText +=
+ QString(" (Picked from %1,%2)").arg(pickedPos.x).arg(pickedPos.y);
m_statusLabel->setText(statusText);
} else
diff --git a/toonz/sources/toonzqt/styleselection.cpp b/toonz/sources/toonzqt/styleselection.cpp
index 024ace0..99f9bb9 100644
--- a/toonz/sources/toonzqt/styleselection.cpp
+++ b/toonz/sources/toonzqt/styleselection.cpp
@@ -505,9 +505,14 @@ void TStyleSelection::enableCommands() {
enableCommand(this, MI_PasteNames, &TStyleSelection::pasteStylesName);
// available only for level palette
- if (m_paletteHandle->getPalette()->getGlobalName() == L"")
+ if (m_paletteHandle->getPalette()->getGlobalName() == L"") {
enableCommand(this, MI_GetColorFromStudioPalette,
&TStyleSelection::getBackOriginalStyle);
+ enableCommand(this, MI_ToggleLinkToStudioPalette,
+ &TStyleSelection::toggleLink);
+ enableCommand(this, MI_RemoveReferenceToStudioPalette,
+ &TStyleSelection::removeLink);
+ }
}
enableCommand(this, MI_Clear, &TStyleSelection::deleteStyles);
enableCommand(this, MI_EraseUnusedStyles, &TStyleSelection::eraseUnsedStyle);
@@ -1408,14 +1413,15 @@ public:
void TStyleSelection::toggleLink() {
TPalette *palette = getPalette();
if (!palette || m_pageIndex < 0) return;
+ if (isEmpty() || palette->isLocked()) return;
int n = m_styleIndicesInPage.size();
if (n <= 0) return;
std::vector> oldColorStylesLinked;
std::vector> newColorStylesLinked;
- bool somethingHasBeenLinked = false;
-
+ bool somethingHasBeenLinked = false;
+ bool somethingChanged = false;
bool currentStyleIsInSelection = false;
TPalette::Page *page = palette->getPage(m_pageIndex);
@@ -1435,6 +1441,7 @@ void TStyleSelection::toggleLink() {
name[0] = name[0] == L'-' ? L'+' : L'-';
cs->setGlobalName(name);
if (name[0] == L'+') somethingHasBeenLinked = true;
+ somethingChanged = true;
}
undo->setColorStyle(index, oldCs, name);
@@ -1442,6 +1449,13 @@ void TStyleSelection::toggleLink() {
palette->getPage(m_pageIndex)->search(m_paletteHandle->getStyleIndex()))
currentStyleIsInSelection = true;
}
+
+ // if nothing changed, do not set dirty flag, nor register undo
+ if (!somethingChanged) {
+ delete undo;
+ return;
+ }
+
if (somethingHasBeenLinked)
StudioPalette::instance()->updateLinkedColors(palette);
@@ -1460,6 +1474,7 @@ void TStyleSelection::toggleLink() {
void TStyleSelection::eraseToggleLink() {
TPalette *palette = getPalette();
if (!palette || m_pageIndex < 0) return;
+ if (isEmpty() || palette->isLocked()) return;
int n = m_styleIndicesInPage.size();
if (n <= 0) return;
@@ -1575,7 +1590,7 @@ public:
int getSize() const override { return sizeof(*this); }
QString getHistoryString() override {
- return QObject::tr("Remove Link in Palette : %1")
+ return QObject::tr("Remove Reference in Palette : %1")
.arg(QString::fromStdWString(m_palette->getPaletteName()));
}
int getHistoryType() override { return HistoryType::Palette; }
@@ -1585,11 +1600,11 @@ public:
/*! remove link from studio palette. Delete the global and the orginal names.
* return true if something changed
*/
-bool TStyleSelection::removeLink() {
+void TStyleSelection::removeLink() {
TPalette *palette = getPalette();
- if (!palette || m_pageIndex < 0) return false;
+ if (!palette || m_pageIndex < 0) return;
int n = m_styleIndicesInPage.size();
- if (n <= 0) return false;
+ if (n <= 0) return;
TPalette::Page *page = palette->getPage(m_pageIndex);
assert(page);
@@ -1614,12 +1629,10 @@ bool TStyleSelection::removeLink() {
}
if (somethingChanged) {
- palette->setDirtyFlag(true);
+ m_paletteHandle->notifyColorStyleChanged(false);
TUndoManager::manager()->add(undo);
} else
delete undo;
-
- return somethingChanged;
}
//=============================================================================
@@ -1781,3 +1794,26 @@ void TStyleSelection::getBackOriginalStyle() {
} else
delete undo;
}
+
+//-----------------------------------------------------------------------------
+/*! return true if there is at least one linked style in the selection
+*/
+
+bool TStyleSelection::hasLinkedStyle() {
+ TPalette *palette = getPalette();
+ if (!palette || m_pageIndex < 0 || isEmpty()) return false;
+ if (m_styleIndicesInPage.size() <= 0) return false;
+
+ TPalette::Page *page = palette->getPage(m_pageIndex);
+ assert(page);
+
+ // for each selected style
+ for (std::set::iterator it = m_styleIndicesInPage.begin();
+ it != m_styleIndicesInPage.end(); ++it) {
+ TColorStyle *cs = page->getStyle(*it);
+ std::wstring gname = cs->getGlobalName();
+ // if the style has link, return true
+ if (gname != L"" && (gname[0] == L'-' || gname[0] == L'+')) return true;
+ }
+ return false;
+}