diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index bab7397a6..e483ace01 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -1,69 +1,96 @@ name: macOS build - on: - push - + push: + branches: + - dev + - patch** + - newlocallab + pull_request: + branches: + - dev + - newlocallab + release: + types: + - created jobs: build: - - runs-on: macos-latest - + runs-on: macos-10.15 steps: - - uses: actions/checkout@v1 - - name: Install dependencies - run: brew install gtk+3 gtkmm3 gtk-mac-integration adwaita-icon-theme libsigc++ little-cms2 libiptcdata fftw lensfun llvm expat pkgconfig libomp shared-mime-info - - name: patch libiconv - run: | - mkdir libiconv && cd libiconv - wget https://ftp.gnu.org/pub/gnu/libiconv/libiconv-1.16.tar.gz - tar xf libiconv-1.16.tar.gz - cd libiconv-1.16 - patch -p1 < "${GITHUB_WORKSPACE}/tools/osx/libiconv_1.16_rt.patch" - mkdir build && cd build - destDir="$(pwd)" - ../configure --prefix=/opt/local --disable-static 'CFLAGS=-arch x86_64 -mmacosx-version-min=10.9' 'LDFLAGS=-arch x86_64 -mmacosx-version-min=10.9' CXXFLAGS="-arch x86_64 -mmacosx-version-min=10.9" - make --jobs - make DESTDIR="${destDir}" install - sudo mv opt/local /usr/local/opt/libiconv - - name: cmake - env: - CMAKE_CXX_STANDARD: 11 - PKG_CONFIG_PATH: /usr/local/opt/libffi/lib/pkgconfig:/usr/local/opt/expat/lib/pkgconfig - RAW_THERAPEE_MAJOR: '5' - RAW_THERAPEE_MINOR: '7' - C_FLAGS: -Xpreprocessor -fopenmp /usr/local/lib/libomp.dylib -I/usr/local/include -I/usr/local/opt/gdk-pixbuf/include -I/usr/local/opt/libiconv/include -I/usr/local/opt/libxml2/include -I/usr/local/opt/expat/include -I/usr/local/opt/llvm/include - run: | - # GITHUB_REF is the ref that triggered the build, like refs/heads/new-feature - the next line parses that to REF: the branch name only (new-feature) - REF=${GITHUB_REF##*/} - mkdir build && cd build - cmake \ - -DCMAKE_BUILD_TYPE="release" \ - -DCMAKE_VERBOSE_MAKEFILE:BOOL=ON \ - -DCMAKE_EXE_LINKER_FLAGS="-L/usr/local/lib -L/usr/local/opt/llvm/lib -Wl,-rpath,/usr/local/opt/llvm/lib -L/usr/local/opt/gdk-pixbuf/lib -L/usr/local/opt/libiconv/lib -L/usr/local/opt/libffi/lib -L/usr/local/opt/libffi/lib -L/usr/local/opt/libxml2/lib -L/usr/local/opt/expat/lib" \ - -DCACHE_NAME_SUFFIX="${RAW_THERAPEE_MAJOR}.${RAW_THERAPEE_MINOR}-${REF}" \ - -DPROC_TARGET_NUMBER="2" \ - -DPROC_LABEL="generic processor" \ - -DWITH_LTO="OFF" \ - -DLENSFUNDBDIR="./share/lensfun" \ - -DOpenMP_C_FLAGS=-fopenmp=libomp \ - -DOpenMP_CXX_FLAGS=-fopenmp=libomp \ - -DOpenMP_C_LIB_NAMES="libomp" \ - -DOpenMP_CXX_LIB_NAMES="libomp" \ - -DOpenMP_libomp_LIBRARY="/usr/local/lib/libomp.dylib" \ - -DOpenMP_C_FLAGS="${C_FLAGS}" \ - -DOpenMP_CXX_FLAGS="${C_FLAGS}" \ - -DCMAKE_AR="/usr/local/opt/llvm/bin/llvm-ar" \ - -DCMAKE_RANLIB="/usr/local/opt/llvm/bin/llvm-ranlib" \ - .. - make --jobs - make install - sudo make macosx_bundle - ARTIFACT=(RawTherapee*.zip) - echo "=== artifact: ${ARTIFACT}" - # defining environment variables for next step as per https://github.com/actions/starter-workflows/issues/68 - echo "::set-env name=ARTIFACT_PATH::${GITHUB_WORKSPACE}/build/${ARTIFACT}" - echo "::set-env name=ARTIFACT_FILE::${ARTIFACT}" - - uses: actions/upload-artifact@v1 - with: - name: ${{env.ARTIFACT_FILE}} - path: ${{env.ARTIFACT_PATH}} + - uses: actions/checkout@v1 + - name: Install dependencies + run: | + date -u + mkdir build + date +%s > build/stamp + brew uninstall --ignore-dependencies libtiff + brew install libtiff gtk+3 gtkmm3 gtk-mac-integration adwaita-icon-theme libsigc++ little-cms2 libiptcdata fftw lensfun expat pkgconfig libomp shared-mime-info | tee -a depslog + date -u + echo "----====Pourage====----" + cat depslog | grep Pouring + zsh -c 'echo "Completed installation of dependencies in $(printf "%0.2f" $(($[$(date +%s)-$(cat build/stamp)]/$((60.))))) minutes"' + - name: Configure build system + env: + CMAKE_CXX_STANDARD: 11 + PKG_CONFIG_PATH: /usr/local/opt/libtiff/lib/pkgconfig:/usr/local/opt/libffi/lib/pkgconfig:/usr/local/opt/expat/lib/pkgconfig + RAW_THERAPEE_MAJOR: '5' + RAW_THERAPEE_MINOR: '8' + C_FLAGS: > + -arch x86_64 -mtune=generic -Xpreprocessor -fopenmp /usr/local/lib/libomp.dylib -I/usr/local/include -I/usr/local/opt/gdk-pixbuf/include -I/usr/local/opt/libiconv/include -I/usr/local/opt/libxml2/include -I/usr/local/opt/expat/include -I/usr/local/opt/libtiff/include + run: | + # GITHUB_REF is the ref that triggered the build, like + # refs/heads/new-feature - the next line parses that to REF: the branch + # name only (new-feature) + export REF=${GITHUB_REF##*/} + export C_FLAGS=$(echo -e $C_FLAGS | tr -d '\n') + cd build && date -u && date +%s > configstamp + cmake \ + -DCMAKE_BUILD_TYPE="Release" \ + -DCMAKE_VERBOSE_MAKEFILE:BOOL=ON \ + -DCMAKE_EXE_LINKER_FLAGS="-L. -L/usr/local/lib -Wl,-rpath -Wl,/usr/local/lib -L/usr/local/opt/gdk-pixbuf/lib -L/usr/local/opt/libiconv/lib -L/usr/local/opt/libffi/lib -L/usr/local/opt/libffi/lib -L/usr/local/opt/libxml2/lib -L/usr/local/opt/expat/lib" \ + -DCACHE_NAME_SUFFIX="${RAW_THERAPEE_MAJOR}.${RAW_THERAPEE_MINOR}-${REF}" \ + -DPROC_TARGET_NUMBER="1" \ + -DPROC_LABEL="generic processor" \ + -DWITH_LTO="OFF" \ + -DLENSFUNDBDIR="/Applications/RawTherapee.app/Contents/Resources/share/lensfun" \ + -DCMAKE_C_COMPILER=/usr/local/opt/llvm/bin/clang \ + -DCMAKE_CXX_COMPILER=/usr/local/opt/llvm/bin/clang++ \ + -DCMAKE_C_FLAGS="-arch x86_64 -Wno-pass-failed -Wno-deprecated-register -Wno-unused-command-line-argument" \ + -DCMAKE_CXX_FLAGS="-arch x86_64 -Wno-pass-failed -Wno-deprecated-register -Wno-unused-command-line-argument" \ + -DOpenMP_C_FLAGS="${C_FLAGS}" \ + -DOpenMP_CXX_FLAGS="${C_FLAGS}" \ + -DOpenMP_C_LIB_NAMES=libomp \ + -DOpenMP_CXX_LIB_NAMES=libomp \ + -DOpenMP_libomp_LIBRARY=/usr/local/lib/libomp.dylib \ + -DCMAKE_AR=/usr/bin/ar \ + -DCMAKE_RANLIB=/usr/bin/ranlib \ + -DCMAKE_OSX_DEPLOYMENT_TARGET=10.15 \ + .. + zsh -c 'echo "Configured in $(printf "%0.2f" $(($[$(date +%s)-$(cat configstamp)]/$((60.))))) minutes"' + - name: Compile RawTherapee + run: | + date -u && date +%s > build/compilestamp + cd build + export REF=${GITHUB_REF##*/} + make -j$(sysctl -a | grep machdep.cpu.thread_count | tail -c 2) install + zsh -c 'echo "Compiled in $(printf "%0.2f" $(($[$(date +%s)-$(cat compilestamp)]/$((60.))))) minutes"' + - name: Create application bundle + run: | + zsh + date +%s > build/bundlestamp && date -u && cd build + export REF=${GITHUB_REF##*/} && export LOCAL_PREFIX=/usr && sudo make macosx_bundle + export ARTIFACT=(RawTherapee*.zip) + echo "=== artifact: ${ARTIFACT}" + # defining environment variables for next step as per + # https://github.com/actions/starter-workflows/issues/68 + echo "::set-env name=ARTIFACT_PATH::${GITHUB_WORKSPACE}/build/${ARTIFACT}" + echo "::set-env name=ARTIFACT_FILE::${ARTIFACT}" + zsh -c 'echo "Bundled in $(printf "%0.2f" $(($[$(date +%s)-$(cat bundlestamp)]/$((60.))))) minutes"' + exit + - uses: actions/upload-artifact@v1 + with: + name: ${{env.ARTIFACT_FILE}} + path: ${{env.ARTIFACT_PATH}} + - name: Finish build + run: | + date -u + zsh -c 'echo "Build completed in $(printf "%0.2f" $(($[$(date +%s)-$(cat build/stamp)]/$((60.))))) minutes"' diff --git a/AboutThisBuild.txt.in b/AboutThisBuild.txt.in index f48d39b50..4d8f4f3fe 100644 --- a/AboutThisBuild.txt.in +++ b/AboutThisBuild.txt.in @@ -13,3 +13,7 @@ Build flags: ${CXX_FLAGS} Link flags: ${LFLAGS} OpenMP support: ${OPTION_OMP} MMAP support: ${WITH_MYFILE_MMAP} +Build OS: ${BUILDINFO_OS} +Build date: ${BUILDINFO_DATE} UTC +Build epoch: ${BUILDINFO_EPOCH} +Build UUID: ${BUILDINFO_UUID} diff --git a/CMakeLists.txt b/CMakeLists.txt index d7368f115..e3ae3b7ff 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,23 +1,34 @@ -cmake_minimum_required(VERSION 3.5) +# Use of SOURCE_DIR target property begins at cmake 3.7 +if(APPLE) + cmake_minimum_required(VERSION 3.7) +else() + cmake_minimum_required(VERSION 3.5) +endif() # Compiler id for Apple Clang if(APPLE) cmake_policy(SET CMP0025 NEW) + cmake_policy(SET CMP0037 NEW) endif() # Must stay before the project() command: if(${CMAKE_EXTRA_GENERATOR} MATCHES "Eclipse CDT4") - set(CMAKE_CXX_COMPILER_ARG1 "-std=c++11" CACHE STRING "C++ version for eclipse" FORCE) + set(CMAKE_CXX_COMPILER_ARG1 + "-std=c++11" + CACHE STRING "C++ version for eclipse" FORCE) # Users building with Eclipse should set CMAKE_ECLIPSE_VERSION through the # command line to their current version of Eclipse: - #set(CMAKE_ECLIPSE_VERSION "4.6.0" CACHE STRING "Eclipse version" FORCE) + # set(CMAKE_ECLIPSE_VERSION "4.6.0" CACHE STRING "Eclipse version" FORCE) endif() project(RawTherapee) # The default target is Debug: if(CMAKE_BUILD_TYPE STREQUAL "") - set(CMAKE_BUILD_TYPE Debug CACHE STRING "One of: None Debug Release RelWithDebInfo MinSizeRel" FORCE) + set(CMAKE_BUILD_TYPE + Debug + CACHE STRING "One of: None Debug Release RelWithDebInfo MinSizeRel" + FORCE) endif() string(TOUPPER ${CMAKE_BUILD_TYPE} UPPER_CMAKE_BUILD_TYPE) @@ -26,11 +37,15 @@ string(TOUPPER ${CMAKE_BUILD_TYPE} UPPER_CMAKE_BUILD_TYPE) set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=c11") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11") -if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU" AND CMAKE_CXX_COMPILER_VERSION VERSION_LESS "4.9") - message(FATAL_ERROR "Building RawTherapee requires using GCC version 4.9 or higher!") +if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU" AND CMAKE_CXX_COMPILER_VERSION + VERSION_LESS "4.9") + message( + FATAL_ERROR + "Building RawTherapee requires using GCC version 4.9 or higher!") endif() -# We might want to build using the old C++ ABI, even when using a new GCC version: +# We might want to build using the old C++ ABI, even when using a new GCC +# version: if(USE_OLD_CXX_ABI) add_definitions(-D_GLIBCXX_USE_CXX11_ABI=0) endif() @@ -46,30 +61,50 @@ message(STATUS "CMAKE_BUILD_TYPE: ${CMAKE_BUILD_TYPE}") set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/cmake/modules/") -# Cache name suffix examples: "" = ~/.config/RawTherapee, "5" = ~/.config/RawTherapee-5, "_testing" = ~/.config/RawTherapee_testing -# Use "" for stable releases and "5-dev" for anything else. -set(CACHE_NAME_SUFFIX "" CACHE STRING "RawTherapee's cache folder suffix") +# Cache name suffix examples: "" = ~/.config/RawTherapee, "5" = +# ~/.config/RawTherapee-5, "_testing" = ~/.config/RawTherapee_testing Use "" for +# stable releases and "5-dev" for anything else. +set(CACHE_NAME_SUFFIX + "" + CACHE STRING "RawTherapee's cache folder suffix") -# By default we don't use a specific processor target, so PROC_TARGET_NUMBER is set to 0. -# Specify other values to optimize for specific processor architecture as listed in ProcessorTargets.cmake: -set(PROC_TARGET_NUMBER 0 CACHE STRING "Selected target processor from the list above (taken from ProcessorTargets.cmake)") +# By default we don't use a specific processor target, so PROC_TARGET_NUMBER is +# set to 0. Specify other values to optimize for specific processor architecture +# as listed in ProcessorTargets.cmake: +set(PROC_TARGET_NUMBER + 0 + CACHE + STRING + "Selected target processor from the list above (taken from ProcessorTargets.cmake)" +) # Set special compilation flags for rtengine which get added to CMAKE_CXX_FLAGS: -# Some Linux distros build with -O2 instead of -O3. We explicitly enable auto vectorization by using -ftree-vectorize -set(RTENGINE_CXX_FLAGS "-ftree-vectorize" CACHE STRING "Special compilation flags for RTEngine") +# Some Linux distros build with -O2 instead of -O3. We explicitly enable auto +# vectorization by using -ftree-vectorize +set(RTENGINE_CXX_FLAGS + "-ftree-vectorize" + CACHE STRING "Special compilation flags for RTEngine") # Loads the ProcessorTargets list: include(ProcessorTargets.cmake) -set(PROC_LABEL "undefined" CACHE STRING "Target processor label, unused if PROC_TARGET_NUMBER = 0 or 2") -set(PROC_FLAGS "" CACHE STRING "Target processor related build/link flags") +set(PROC_LABEL + "undefined" + CACHE STRING + "Target processor label, unused if PROC_TARGET_NUMBER = 0 or 2") +set(PROC_FLAGS + "" + CACHE STRING "Target processor related build/link flags") if((NOT (PROC_TARGET_NUMBER EQUAL 0)) AND (NOT (PROC_TARGET_NUMBER EQUAL 2))) set(PROC_LABEL ${PROC_TARGET_${PROC_TARGET_NUMBER}_LABEL}) endif() -if(NOT(PROC_TARGET_NUMBER EQUAL 0)) +if(NOT (PROC_TARGET_NUMBER EQUAL 0)) set(PROC_FLAGS ${PROC_TARGET_${PROC_TARGET_NUMBER}_FLAGS}) endif() if(UNIX AND PROC_LABEL STREQUAL "undefined") - execute_process(COMMAND uname -p OUTPUT_STRIP_TRAILING_WHITESPACE OUTPUT_VARIABLE cpu) + execute_process( + COMMAND uname -p + OUTPUT_STRIP_TRAILING_WHITESPACE + OUTPUT_VARIABLE cpu) if("${cpu}" STREQUAL "unknown") set(PROC_LABEL "${CMAKE_SYSTEM_PROCESSOR}") else() @@ -77,7 +112,8 @@ if(UNIX AND PROC_LABEL STREQUAL "undefined") endif() endif() -# If PROC_FORCED_LABEL exists, its value is loaded in PROC_LABEL to override the one from ProcessorTargets: +# If PROC_FORCED_LABEL exists, its value is loaded in PROC_LABEL to override the +# one from ProcessorTargets: if(DEFINED PROC_FORCED_LABEL) set(PROC_LABEL ${PROC_FORCED_LABEL}) endif() @@ -87,7 +123,8 @@ set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${PROC_FLAGS}") set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${PROC_FLAGS}") set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} ${PROC_FLAGS}") -# Stop compilation on typos such as std:swap (missing colon will be detected as unused label): +# Stop compilation on typos such as std:swap (missing colon will be detected as +# unused label): set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Werror=unused-label") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Werror=delete-incomplete") @@ -106,21 +143,35 @@ endif() include(FindUnalignedMalloc) if(WIN32) - # Add additional paths. Look in the MinGW path first, then in the Gtkmm path. - # If you wish to build some dependent libraries, you have to install them in MinGW to use them: - set(CMAKE_PREFIX_PATH $ENV{MINGW_BASEPATH} $ENV{GTKMM_BASEPATH} CACHE STRING "Additional search paths") + # Add additional paths. Look in the MinGW path first, then in the Gtkmm + # path. If you wish to build some dependent libraries, you have to install + # them in MinGW to use them: + set(CMAKE_PREFIX_PATH + $ENV{MINGW_BASEPATH} $ENV{GTKMM_BASEPATH} + CACHE STRING "Additional search paths") endif() -if(APPLE) - if(CMAKE_CXX_COMPILER MATCHES "g\\+\\+-mp-4.[5-8]" OR CMAKE_CXX_COMPILER_ARG1 MATCHES "g\\+\\+-mp-4.[5-8]") - set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} /usr/lib/libstdc++.6.dylib") - message(STATUS "CMAKE_CXX_COMPILER is MacPorts GCC.\n CMAKE_EXE_LINKER_FLAGS: ${CMAKE_EXE_LINKER_FLAGS}") +if(APPLE) # TODO make -mtune generic conditional and/or specifiable. + if(CMAKE_CXX_COMPILER MATCHES "g\\+\\+-mp-4.[5-8]" + OR CMAKE_CXX_COMPILER_ARG1 MATCHES "g\\+\\+-mp-4.[5-8]") + set(CMAKE_EXE_LINKER_FLAGS + "${CMAKE_EXE_LINKER_FLAGS} /usr/lib/libstdc++.6.dylib -Wl,-headerpad_max_install_names -mtune=generic" + ) + message( + STATUS + "CMAKE_CXX_COMPILER is MacPorts GCC.\n CMAKE_EXE_LINKER_FLAGS: ${CMAKE_EXE_LINKER_FLAGS}" + ) endif() # Set minimum system version - set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -mmacosx-version-min=10.9") - set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -mmacosx-version-min=10.9") - set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -headerpad_max_install_names") + set(CMAKE_CXX_FLAGS + "${CMAKE_CXX_FLAGS} -mmacosx-version-min=${CMAKE_OSX_DEPLOYMENT_TARGET}" + ) + set(CMAKE_C_FLAGS + "${CMAKE_C_FLAGS} -mmacosx-version-min=${CMAKE_OSX_DEPLOYMENT_TARGET}") + set(CMAKE_EXE_LINKER_FLAGS + "${CMAKE_EXE_LINKER_FLAGS} -Wl,-headerpad_max_install_names -mtune=generic" + ) endif() option(USE_EXPERIMENTAL_LANG_VERSIONS "Build with -std=c++0x" OFF) @@ -132,33 +183,53 @@ option(WITH_SAN "Build with run-time sanitizer" OFF) option(WITH_PROF "Build with profiling instrumentation" OFF) option(WITH_SYSTEM_KLT "Build using system KLT library." OFF) option(OPTION_OMP "Build with OpenMP support" ON) -option(STRICT_MUTEX "True (recommended): MyMutex will behave like POSIX Mutex; False: MyMutex will behave like POSIX RecMutex; Note: forced to ON for Debug builds" ON) -option(TRACE_MYRWMUTEX "Trace custom R/W Mutex (Debug builds only); redirecting std::out to a file is strongly recommended!" OFF) -option(AUTO_GDK_FLUSH "Use gdk_flush on all gdk_thread_leave other than the GUI thread; set it ON if you experience X Server warning/errors" OFF) -#option(TARGET32BIT "Build for 32-bit architecture when ON, otherwise 64-bit. Default is OFF" OFF) +option( + STRICT_MUTEX + "True (recommended): MyMutex will behave like POSIX Mutex; False: MyMutex will behave like POSIX RecMutex; Note: forced to ON for Debug builds" + ON) +option( + TRACE_MYRWMUTEX + "Trace custom R/W Mutex (Debug builds only); redirecting std::out to a file is strongly recommended!" + OFF) +option( + AUTO_GDK_FLUSH + "Use gdk_flush on all gdk_thread_leave other than the GUI thread; set it ON if you experience X Server warning/errors" + OFF) +# option(TARGET32BIT "Build for 32-bit architecture when ON, otherwise 64-bit. +# Default is OFF" OFF) option(ENABLE_TCMALLOC "Use the tcmalloc library if available" OFF) -set(TCMALLOC_LIB_DIR "" CACHE PATH "Custom path for the tcmalloc library") +set(TCMALLOC_LIB_DIR + "" + CACHE PATH "Custom path for the tcmalloc library") # Set installation directories: if(WIN32 OR APPLE) if(BUILD_BUNDLE) - message(STATUS "You have set BUILD_BUNDLE=ON but this is not necessary - the option is forced to ON for Windows and macOS.") + message( + STATUS + "You have set BUILD_BUNDLE=ON but this is not necessary - the option is forced to ON for Windows and macOS." + ) endif() set(BUILD_BUNDLE ON FORCE) endif() if(NOT DEFINED BUNDLE_BASE_INSTALL_DIR) if(APPLE) - set(BUNDLE_BASE_INSTALL_DIR "${CMAKE_BINARY_DIR}/${CMAKE_BUILD_TYPE}/MacOS") + set(BUNDLE_BASE_INSTALL_DIR "${PROJECT_SOURCE_DIR}/build/${CMAKE_BUILD_TYPE}/MacOS") else() set(BUNDLE_BASE_INSTALL_DIR "${CMAKE_BINARY_DIR}/${CMAKE_BUILD_TYPE}") endif() endif() if(BUILD_BUNDLE) - set(BINDIR .) - set(CMAKE_INSTALL_PREFIX "${BUNDLE_BASE_INSTALL_DIR}") + if(APPLE) + set(BINDIR "${BUNDLE_BASE_INSTALL_DIR}") + set(CMAKE_INSTALL_PREFIX "${PROJECT_SOURCE_DIR}/build") + else() + set(BINDIR .) + set(CMAKE_INSTALL_PREFIX "${BUNDLE_BASE_INSTALL_DIR}") + endif() endif() if(NOT DEFINED BINDIR) @@ -168,7 +239,7 @@ endif() if(NOT DEFINED DATADIR) if(BUILD_BUNDLE) if(APPLE) - set(DATADIR "../../Resources") + set(DATADIR "${PROJECT_SOURCE_DIR}/build/${CMAKE_BUILD_TYPE}/Resources/share") else() set(DATADIR .) endif() @@ -180,7 +251,7 @@ endif() if(NOT DEFINED LIBDIR) if(BUILD_BUNDLE) if(APPLE) - set(LIBDIR "../../Frameworks") + set(LIBDIR "${PROJECT_SOURCE_DIR}/build/${CMAKE_BUILD_TYPE}/Frameworks") else() set(LIBDIR .) endif() @@ -200,7 +271,11 @@ endif() if(NOT DEFINED DOCDIR) if(BUILD_BUNDLE) - set(DOCDIR "${DATADIR}/share/doc") + if(APPLE) + set(DOCDIR "${DATADIR}/doc") + else() + set(DOCDIR "${DATADIR}/share/doc") + endif() else() set(DOCDIR "${CMAKE_INSTALL_PREFIX}/share/doc/rawtherapee") endif() @@ -208,7 +283,11 @@ endif() if(NOT DEFINED CREDITSDIR) if(BUILD_BUNDLE) - set(CREDITSDIR "${DATADIR}") + if(APPLE) + set(CREDITSDIR "${DATADIR}") + else() + set(CREDITSDIR "${DATADIR}") + endif() else() set(CREDITSDIR "${CMAKE_INSTALL_PREFIX}/share/doc/rawtherapee") endif() @@ -216,7 +295,11 @@ endif() if(NOT DEFINED LICENCEDIR) if(BUILD_BUNDLE) - set(LICENCEDIR "${DATADIR}") + if(APPLE) + set(LICENCEDIR "${CREDITSDIR}") + else() + set(LICENCEDIR "${DATADIR}") + endif() else() set(LICENCEDIR "${CMAKE_INSTALL_PREFIX}/share/doc/rawtherapee") endif() @@ -225,7 +308,11 @@ endif() if(NOT DEFINED DESKTOPDIR) if(UNIX) if(BUILD_BUNDLE) - set(DESKTOPDIR "${DATADIR}/share/applications") + if(APPLE) + set(DESKTOPDIR "${DATADIR}/applications") + else() + set(DESKTOPDIR "${DATADIR}/share/applications") + endif() else() set(DESKTOPDIR "${CMAKE_INSTALL_PREFIX}/share/applications") endif() @@ -235,7 +322,11 @@ endif() if(NOT DEFINED ICONSDIR) if(UNIX) if(BUILD_BUNDLE) - set(ICONSDIR "${DATADIR}/share/icons") + if(APPLE) + set(ICONSDIR "${DATADIR}/icons") + else() + set(ICONSDIR "${DATADIR}/share/icons") + endif() else() set(ICONSDIR "${CMAKE_INSTALL_PREFIX}/share/icons") endif() @@ -245,32 +336,59 @@ endif() if(NOT DEFINED APPDATADIR) if(UNIX) if(BUILD_BUNDLE) - set(APPDATADIR "${DATADIR}/share/metainfo") + if(APPLE) + set(APPDATADIR "${DATADIR}/metainfo") + else() + set(APPDATADIR "${DATADIR}/share/metainfo") + endif() else() set(APPDATADIR "${CMAKE_INSTALL_PREFIX}/share/metainfo") endif() endif() endif() -if(DEFINED LENSFUNDBDIR AND NOT IS_ABSOLUTE "${LENSFUNDBDIR}") - set(LENSFUNDBDIR "${DATADIR}/${LENSFUNDBDIR}") +if(NOT APPLE) + if(DEFINED LENSFUNDBDIR AND NOT IS_ABSOLUTE "${LENSFUNDBDIR}") + set(LENSFUNDBDIR "${DATADIR}/${LENSFUNDBDIR}") + endif() endif() if(APPLE) if("${CODESIGNID}") - set(CODESIGNID "${CODESIGNID}" CACHE STRING "Codesigning Identity") + set(CODESIGNID + "${CODESIGNID}" + CACHE STRING "Codesigning Identity") endif() if("${NOTARY}") - set(NOTARY "${NOTARY}" CACHE STRING "Notarization Identity") + set(NOTARY + "${NOTARY}" + CACHE STRING "Notarization Identity") + endif() + if("${LOCAL_PREFIX}") + set(LOCAL_PREFIX + "${LOCAL_PREFIX}" + CACHE STRING "macos/gtk parent directory ie /usr or /opt") + else() + set(LOCAL_PREFIX + /usr + CACHE STRING "macos/gtk parent directory ie /usr or /opt") + endif() + if("${FANCY_DMG}") + set(FANCY_DMG + ON + CACHE BOOL + "Use the andreyvit/create-dmg script to make a fancy .dmg") endif() - endif() # Enforce absolute paths for non-bundle builds: if(NOT BUILD_BUNDLE) foreach(path BINDIR DATADIR LIBDIR DOCDIR CREDITSDIR LICENCEDIR) if(NOT (IS_ABSOLUTE "${${path}}")) - message(FATAL_ERROR "The ${path} path has to be absolute when using -DBUILD_BUNDLE=OFF") + message( + FATAL_ERROR + "The ${path} path has to be absolute when using -DBUILD_BUNDLE=OFF" + ) endif() endforeach() endif() @@ -299,11 +417,11 @@ endif() find_package(PkgConfig) if(WIN32) - pkg_check_modules (GTK REQUIRED gtk+-3.0>=3.22.24) - pkg_check_modules (GTKMM REQUIRED gtkmm-3.0>=3.22) + pkg_check_modules(GTK REQUIRED gtk+-3.0>=3.22.24) + pkg_check_modules(GTKMM REQUIRED gtkmm-3.0>=3.22) else() - pkg_check_modules (GTK REQUIRED gtk+-3.0>=3.16) - pkg_check_modules (GTKMM REQUIRED gtkmm-3.0>=3.16) + pkg_check_modules(GTK REQUIRED gtk+-3.0>=3.16) + pkg_check_modules(GTKMM REQUIRED gtkmm-3.0>=3.16) endif() if(GTK_VERSION VERSION_GREATER "3.24.1" AND GTK_VERSION VERSION_LESS "3.24.7") @@ -312,19 +430,26 @@ if(GTK_VERSION VERSION_GREATER "3.24.1" AND GTK_VERSION VERSION_LESS "3.24.7") else() set(CERTAINTY "likely to") endif() - message(WARNING "\nWarning! You are using GTK+ version " ${GTK_VERSION} " which is " ${CERTAINTY} " have an issue where combobox menu scroll-arrows are missing when a Gtk::ComboBox list does not fit vertically on the screen. As a result, users of your build will not be able to select items in the following comboboxes: Processing Profiles, Film Simulation, and the camera and lens profiles in Profiled Lens Correction.\nIt is recommended that you either downgrade GTK+ to <= 3.24.1 or upgrade to >= 3.24.7.") + message( + WARNING + "\nWarning! You are using GTK+ version " + ${GTK_VERSION} + " which is " + ${CERTAINTY} + " have an issue where combobox menu scroll-arrows are missing when a Gtk::ComboBox list does not fit vertically on the screen. As a result, users of your build will not be able to select items in the following comboboxes: Processing Profiles, Film Simulation, and the camera and lens profiles in Profiled Lens Correction.\nIt is recommended that you either downgrade GTK+ to <= 3.24.1 or upgrade to >= 3.24.7." + ) endif() -pkg_check_modules (GLIB2 REQUIRED glib-2.0>=2.44) -pkg_check_modules (GLIBMM REQUIRED glibmm-2.4>=2.44) -pkg_check_modules (CAIROMM REQUIRED cairomm-1.0) -pkg_check_modules (GIO REQUIRED gio-2.0>=2.44) -pkg_check_modules (GIOMM REQUIRED giomm-2.4>=2.44) -pkg_check_modules (GTHREAD REQUIRED gthread-2.0>=2.44) -pkg_check_modules (GOBJECT REQUIRED gobject-2.0>=2.44) -pkg_check_modules (SIGC REQUIRED sigc++-2.0>=2.3.1) -pkg_check_modules (LENSFUN REQUIRED lensfun>=0.2) -pkg_check_modules (RSVG REQUIRED librsvg-2.0>=2.40) +pkg_check_modules(GLIB2 REQUIRED glib-2.0>=2.44) +pkg_check_modules(GLIBMM REQUIRED glibmm-2.4>=2.44) +pkg_check_modules(CAIROMM REQUIRED cairomm-1.0) +pkg_check_modules(GIO REQUIRED gio-2.0>=2.44) +pkg_check_modules(GIOMM REQUIRED giomm-2.4>=2.44) +pkg_check_modules(GTHREAD REQUIRED gthread-2.0>=2.44) +pkg_check_modules(GOBJECT REQUIRED gobject-2.0>=2.44) +pkg_check_modules(SIGC REQUIRED sigc++-2.0>=2.3.1) +pkg_check_modules(LENSFUN REQUIRED lensfun>=0.2) +pkg_check_modules(RSVG REQUIRED librsvg-2.0>=2.40) if(WIN32) add_definitions(-DWIN32) @@ -351,7 +476,7 @@ if(WITH_SYSTEM_KLT) endif() # Check for libcanberra-gtk3 (sound events on Linux): -if(UNIX AND(NOT APPLE)) +if(UNIX AND (NOT APPLE)) pkg_check_modules(CANBERRA-GTK REQUIRED libcanberra-gtk3) endif() @@ -362,9 +487,12 @@ endif() if(WITH_LTO) # Using LTO with older versions of binutils requires setting extra flags set(BINUTILS_VERSION_MININUM "2.29") - execute_process(COMMAND ar --version OUTPUT_VARIABLE BINUTILS_VERSION_DETECTED) - string(REGEX REPLACE ".* ([0-9.]+)\n.*" "\\1" BINUTILS_VERSION_DETECTED "${BINUTILS_VERSION_DETECTED}") - if("${BINUTILS_VERSION_DETECTED}" VERSION_LESS "${BINUTILS_VERSION_MININUM}") + execute_process(COMMAND ar --version + OUTPUT_VARIABLE BINUTILS_VERSION_DETECTED) + string(REGEX REPLACE ".* ([0-9.]+)\n.*" "\\1" BINUTILS_VERSION_DETECTED + "${BINUTILS_VERSION_DETECTED}") + if("${BINUTILS_VERSION_DETECTED}" VERSION_LESS + "${BINUTILS_VERSION_MININUM}") if(APPLE) if(!CMAKE_AR) set(CMAKE_AR "/opt/local/bin/ar") @@ -376,7 +504,15 @@ if(WITH_LTO) set(CMAKE_AR "/usr/bin/gcc-ar") set(CMAKE_RANLIB "/usr/bin/gcc-ranlib") endif() - message(STATUS "Binutils version detected as less than " ${BINUTILS_VERSION_MININUM} " - setting CMake parameters to enable LTO linking:\n CMAKE_AR=\"" ${CMAKE_AR} "\"\n CMAKE_RANLIB=\"" ${CMAKE_RANLIB} "\"") + message( + STATUS + "Binutils version detected as less than " + ${BINUTILS_VERSION_MININUM} + " - setting CMake parameters to enable LTO linking:\n CMAKE_AR=\"" + ${CMAKE_AR} + "\"\n CMAKE_RANLIB=\"" + ${CMAKE_RANLIB} + "\"") endif() set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -flto") @@ -387,7 +523,8 @@ endif() if(WITH_SAN) set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fsanitize=${WITH_SAN}") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fsanitize=${WITH_SAN}") - set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -fsanitize=${WITH_SAN}") + set(CMAKE_EXE_LINKER_FLAGS + "${CMAKE_EXE_LINKER_FLAGS} -fsanitize=${WITH_SAN}") endif() if(WITH_PROF) @@ -396,11 +533,14 @@ if(WITH_PROF) set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -pg") endif() -set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Wuninitialized -Wcast-qual -Wno-deprecated-declarations -Wno-unused-result") +set(CMAKE_CXX_FLAGS + "${CMAKE_CXX_FLAGS} -Wall -Wuninitialized -Wcast-qual -Wno-deprecated-declarations -Wno-unused-result -Wunused-macros" +) if(OPTION_OMP) find_package(OpenMP) if(OPENMP_FOUND) - set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${OpenMP_CXX_FLAGS} -Werror=unknown-pragmas") + set(CMAKE_CXX_FLAGS + "${CMAKE_CXX_FLAGS} ${OpenMP_CXX_FLAGS} -Werror=unknown-pragmas") endif() endif() @@ -414,13 +554,14 @@ if(OPENMP_FOUND) set(CMAKE_REQUIRED_LIBRARIES ${CMAKE_REQUIRED_LIBRARIES} ${_f}) endforeach() check_c_source_compiles( -"#include + "#include int main() { fftwf_init_threads(); fftwf_plan_with_nthreads(1); return 0; -}" _fftw3f_multithread) +}" + _fftw3f_multithread) if(_fftw3f_multithread) add_definitions(-DRT_FFTW3F_OMP) else() @@ -438,30 +579,41 @@ get_filename_component(ABS_BINARY_DIR "${CMAKE_BINARY_DIR}" ABSOLUTE) set(OUT_OF_SOURCE_BUILD TRUE) if(ABS_SOURCE_DIR STREQUAL ABS_BINARY_DIR) set(OUT_OF_SOURCE_BUILD FALSE) - message(WARNING "You are performing an in-source build. This is discouraged. For an explanation and the advantages of out-of-source builds, please refer to http://www.cmake.org/Wiki/CMake_FAQ#What_is_an_.22out-of-source.22_build.3F") + message( + WARNING + "You are performing an in-source build. This is discouraged. For an explanation and the advantages of out-of-source builds, please refer to http://www.cmake.org/Wiki/CMake_FAQ#What_is_an_.22out-of-source.22_build.3F" + ) endif() -# Remove files which could require manual work. -# We will remove this after some time to have a clean build system without file modifications in the source tree again. (?) -set(OOSB_FILES "${PROJECT_SOURCE_DIR}/rtdata/rawtherapee.desktop" "${PROJECT_SOURCE_DIR}/rtgui/version.h" "${PROJECT_SOURCE_DIR}/rtgui/config.h" "${PROJECT_SOURCE_DIR}/AboutThisBuild.txt") +# Remove files which could require manual work. We will remove this after some +# time to have a clean build system without file modifications in the source +# tree again. (?) +set(OOSB_FILES + "${PROJECT_SOURCE_DIR}/rtdata/rawtherapee.desktop" + "${PROJECT_SOURCE_DIR}/rtgui/version.h" + "${PROJECT_SOURCE_DIR}/rtgui/config.h" + "${PROJECT_SOURCE_DIR}/AboutThisBuild.txt") if(OUT_OF_SOURCE_BUILD) foreach(f ${OOSB_FILES}) file(REMOVE "${f}") endforeach() endif() -# Check for generated files in the source tree which should not be there when doing an out-of-source build. -# Without checking for this it might happen that old versions are used for the compilation: +# Check for generated files in the source tree which should not be there when +# doing an out-of-source build. Without checking for this it might happen that +# old versions are used for the compilation: if(OUT_OF_SOURCE_BUILD) foreach(f ${OOSB_FILES}) if(EXISTS "${f}") - message(SEND_ERROR "Generated \"${f}\" found inside the source tree. Please remove it as it is a relic of the old build system and prevents valid compilation now.") + message( + SEND_ERROR + "Generated \"${f}\" found inside the source tree. Please remove it as it is a relic of the old build system and prevents valid compilation now." + ) endif() endforeach() endif() -### Start generating AboutThisBuild.txt -# Set the platform bit-depth: +# Start generating AboutThisBuild.txt Set the platform bit-depth: if(CMAKE_SIZEOF_VOID_P EQUAL 4) set(PROC_BIT_DEPTH 32 bits) else() @@ -469,68 +621,91 @@ else() endif() # Get compiler name and version. -# Only CMake > 2.8.7 knows CMAKE_*_COMPILER_VERSION -if(CMAKE_VERSION VERSION_GREATER 2.8.7) get_filename_component(COMPILER_INFO ${CMAKE_C_COMPILER} NAME_WE) set(COMPILER_INFO "${COMPILER_INFO} ${CMAKE_C_COMPILER_VERSION}") -else() - execute_process(COMMAND gcc -dumpversion OUTPUT_VARIABLE GCC_VERSION OUTPUT_STRIP_TRAILING_WHITESPACE) +if(NOT APPLE) + execute_process( + COMMAND gcc -dumpversion + OUTPUT_VARIABLE GCC_VERSION OUTPUT_STRIP_TRAILING_WHITESPACE) set(COMPILER_INFO "gcc ${GCC_VERSION}") endif() -# Get C++ and linker flags for rtengine (the GUI's C++ flags may have fewer flags): -set(CXX_FLAGS "${CMAKE_CXX_FLAGS} ${CMAKE_CXX_FLAGS_${UPPER_CMAKE_BUILD_TYPE}} ${RTENGINE_CXX_FLAGS}") -set(LFLAGS "${CMAKE_EXE_LINKER_FLAGS} ${CMAKE_EXE_LINKER_FLAGS_${UPPER_CMAKE_BUILD_TYPE}}") +# Get C++ and linker flags for rtengine (the GUI's C++ flags may have fewer +# flags): +set(CXX_FLAGS + "${CMAKE_CXX_FLAGS} ${CMAKE_CXX_FLAGS_${UPPER_CMAKE_BUILD_TYPE}} ${RTENGINE_CXX_FLAGS}" +) +set(LFLAGS + "${CMAKE_EXE_LINKER_FLAGS} ${CMAKE_EXE_LINKER_FLAGS_${UPPER_CMAKE_BUILD_TYPE}}" +) -set(ABOUT_COMMAND_WITH_ARGS ${CMAKE_COMMAND} - -DPROJECT_SOURCE_DIR:STRING=${PROJECT_SOURCE_DIR} - -DCACHE_NAME_SUFFIX:STRING=${CACHE_NAME_SUFFIX} - -DPROC_LABEL:STRING="${PROC_LABEL}" - -DPROC_BIT_DEPTH:STRING="${PROC_BIT_DEPTH}" - -DBUILD_TYPE:STRING=${CMAKE_BUILD_TYPE} - -DGTKMM_VERSION:STRING=${GTKMM_VERSION} - -DOPTION_OMP:STRING=${OPTION_OMP} - -DWITH_MYFILE_MMAP:STRING=${WITH_MYFILE_MMAP} - -DLENSFUN_VERSION:STRING=${LENSFUN_VERSION}) +if(NOT APPLE) + set(ABOUT_COMMAND_WITH_ARGS + ${CMAKE_COMMAND} -DPROJECT_SOURCE_DIR:STRING=${PROJECT_SOURCE_DIR} + -DCACHE_NAME_SUFFIX:STRING=${CACHE_NAME_SUFFIX} + -DPROC_LABEL:STRING="${PROC_LABEL}" + -DPROC_BIT_DEPTH:STRING="${PROC_BIT_DEPTH}" + -DBUILD_TYPE:STRING=${CMAKE_BUILD_TYPE} + -DGTKMM_VERSION:STRING=${GTKMM_VERSION} + -DOPTION_OMP:STRING=${OPTION_OMP} + -DWITH_MYFILE_MMAP:STRING=${WITH_MYFILE_MMAP} + -DLENSFUN_VERSION:STRING=${LENSFUN_VERSION}) +endif() if(WIN32) - list(APPEND ABOUT_COMMAND_WITH_ARGS -DSYSTEM:STRING=Windows + list( + APPEND + ABOUT_COMMAND_WITH_ARGS + -DSYSTEM:STRING=Windows -DCXX_FLAGS:STRING="${CXX_FLAGS}" -DLFLAGS:STRING="${LFLAGS}" -DCOMPILER_INFO:STRING="${COMPILER_INFO}" -DCMAKE_INSTALL_PREFIX:STRING="${CMAKE_INSTALL_PREFIX}" -DBIT_DEPTH:STRING="${CMAKE_SIZEOF_VOID_P}") elseif(APPLE) - list(APPEND ABOUT_COMMAND_WITH_ARGS -DSYSTEM:STRING=Apple - -DCXX_FLAGS:STRING=${CXX_FLAGS} - -DLFLAGS:STRING=${LFLAGS} - -DCOMPILER_INFO:STRING=${COMPILER_INFO}) + set( + ABOUT_COMMAND_WITH_ARGS + cmake -DPROJECT_SOURCE_DIR:STRING=${PROJECT_SOURCE_DIR} -P ${PROJECT_SOURCE_DIR}/UpdateInfo.cmake -DSYSTEM:STRING=Apple -DCXX_FLAGS:STRING=${CXX_FLAGS} -DLFLAGS:STRING=${LFLAGS} -DCOMPILER_INFO:STRING=${COMPILER_INFO} -DCACHE_NAME_SUFFIX:STRING=${CACHE_NAME_SUFFIX}) else() list(APPEND ABOUT_COMMAND_WITH_ARGS -DSYSTEM:STRING=Linux - -DCXX_FLAGS:STRING=${CXX_FLAGS} - -DLFLAGS:STRING=${LFLAGS} - -DCOMPILER_INFO:STRING=${COMPILER_INFO}) + -DCXX_FLAGS:STRING=${CXX_FLAGS} -DLFLAGS:STRING=${LFLAGS} + -DCOMPILER_INFO:STRING=${COMPILER_INFO}) +endif() +if(NOT APPLE) + list(APPEND + ABOUT_COMMAND_WITH_ARGS + -P "${PROJECT_SOURCE_DIR}/UpdateInfo.cmake") endif() -list(APPEND ABOUT_COMMAND_WITH_ARGS -P "${PROJECT_SOURCE_DIR}/UpdateInfo.cmake") - -add_custom_target(UpdateInfo ALL +add_custom_target( + UpdateInfo ALL COMMAND ${ABOUT_COMMAND_WITH_ARGS} COMMENT "Creating AboutThisBuild.txt and other version-dependent files") -### End generating AboutThisBuild.txt +# End generating AboutThisBuild.txt install(FILES AUTHORS.txt DESTINATION "${CREDITSDIR}") install(FILES LICENSE.txt DESTINATION "${LICENCEDIR}") -install(FILES "${CMAKE_BINARY_DIR}/AboutThisBuild.txt" DESTINATION "${CREDITSDIR}") -install(FILES RELEASE_NOTES.txt DESTINATION "${CREDITSDIR}" OPTIONAL) +install(FILES "${CMAKE_BINARY_DIR}/AboutThisBuild.txt" + DESTINATION "${CREDITSDIR}") +install( + FILES RELEASE_NOTES.txt + DESTINATION "${CREDITSDIR}" + OPTIONAL) -# The standard location for man pages in Linux is /usr/share/man -# Use "manpath" to see the search paths for man pages on your system. +# The standard location for man pages in Linux is /usr/share/man Use "manpath" +# to see the search paths for man pages on your system. if(BUILD_BUNDLE) - install(FILES "${PROJECT_SOURCE_DIR}/doc/manpage/rawtherapee.1" DESTINATION "${DATADIR}/share/man/man1") + if(APPLE) + install(FILES "${PROJECT_SOURCE_DIR}/doc/manpage/rawtherapee.1" + DESTINATION "${DATADIR}/man/man1") + else() + install(FILES "${PROJECT_SOURCE_DIR}/doc/manpage/rawtherapee.1" + DESTINATION "${DATADIR}/share/man/man1") + endif() else() - install(FILES "${PROJECT_SOURCE_DIR}/doc/manpage/rawtherapee.1" DESTINATION "${CMAKE_INSTALL_PREFIX}/share/man/man1") + install(FILES "${PROJECT_SOURCE_DIR}/doc/manpage/rawtherapee.1" + DESTINATION "${CMAKE_INSTALL_PREFIX}/share/man/man1") endif() if(WIN32) @@ -538,7 +713,8 @@ if(WIN32) endif() if(UNIX) - install(FILES com.rawtherapee.RawTherapee.appdata.xml DESTINATION "${APPDATADIR}") + install(FILES com.rawtherapee.RawTherapee.appdata.xml + DESTINATION "${APPDATADIR}") endif() # check whether the used version of lensfun has lfDatabase::LoadDirectory @@ -566,26 +742,31 @@ int main() lfDatabase *db = 0; bool b = db->LoadDirectory(0); return 0; -}" LENSFUN_HAS_LOAD_DIRECTORY) +}" + LENSFUN_HAS_LOAD_DIRECTORY) set(TCMALLOC_LIB_DIR) if(ENABLE_TCMALLOC) if(TCMALLOC_LIB_DIR) - find_library(TCMALLOC_LIBRARIES tcmalloc PATHS ${TCMALLOC_LIB_DIR} NO_DEFAULT_PATH) + find_library(TCMALLOC_LIBRARIES tcmalloc PATHS ${TCMALLOC_LIB_DIR} + NO_DEFAULT_PATH) else() find_library(TCMALLOC_LIBRARIES tcmalloc) endif() if(TCMALLOC_LIBRARIES) message(STATUS "using tcmalloc library in ${TCMALLOC_LIBRARIES}") else() - set(TCMALLOC_LIBRARIES "" CACHE INTERNAL "" FORCE) + set(TCMALLOC_LIBRARIES + "" + CACHE INTERNAL "" FORCE) message(STATUS "tcmalloc not found") endif() else() - set(TCMALLOC_LIBRARIES "" CACHE INTERNAL "" FORCE) + set(TCMALLOC_LIBRARIES + "" + CACHE INTERNAL "" FORCE) endif() - add_subdirectory(rtexif) add_subdirectory(rtengine) add_subdirectory(rtgui) diff --git a/LICENSE.txt b/LICENSE.txt index 653f0ac50..2ba8256ab 100644 --- a/LICENSE.txt +++ b/LICENSE.txt @@ -1,6 +1,6 @@ RawTherapee - A powerful, cross-platform raw image processing program. Copyright (C) 2004-2012 Gabor Horvath - Copyright (C) 2010-2019 RawTherapee development team. + Copyright (C) 2010-2020 RawTherapee development team. RawTherapee is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by diff --git a/RELEASE_NOTES.txt b/RELEASE_NOTES.txt index 33a984c1c..eb8d96379 100644 --- a/RELEASE_NOTES.txt +++ b/RELEASE_NOTES.txt @@ -1,4 +1,4 @@ -RAWTHERAPEE 5.7-dev RELEASE NOTES +RAWTHERAPEE 5.8-dev RELEASE NOTES This is a development version of RawTherapee. We update the code almost daily. Every few months, once enough changes have accumulated and the code is stabilized, we make a new official release. Every code change between these releases is known as a "development" version, and this is one of them. @@ -8,7 +8,7 @@ https://rawpedia.rawtherapee.com/ While we only commit tested and relatively stable code and so the development versions should be fairly stable, you should be aware that: - Development versions only had limited testing, so there may be bugs unknown to us. - You should report these bugs so that they get fixed for the next stable release. See - www.rawpedia.rawtherapee.com/How_to_write_useful_bug_reports + https://rawpedia.rawtherapee.com/How_to_write_useful_bug_reports - The way new tools work in the development versions is likely to change as we tweak and tune them, so your processing profiles may produce different results when used in a future stable version. - Bugs present in the stable versions get fixed in the development versions, and make it into the next stable version when we make a new official release. That means that in some ways the development versions can be "more stable" than the latest stable release. At the same time, new features may introduce new bugs. This is a trade-off you should be aware of. @@ -26,14 +26,14 @@ In order to use RawTherapee efficiently you should know that: - All curves support the Shift and Ctrl keys while dragging a point. Shift+drag makes the point snap to a meaningful axis (top, bottom, diagonal, other), while Ctrl+drag makes your mouse movement super-fine for precise point positioning. - There are many keyboard shortcuts which make working with RawTherapee much faster and give you greater control. Make sure you familiarize yourself with them on RawPedia's "Keyboard Shortcuts" page! -New features since 5.7: +New features since 5.8: - TODO NEWS RELEVANT TO PACKAGE MAINTAINERS -New since 5.7: +New since 5.8: - TODO In general: diff --git a/UpdateInfo.cmake b/UpdateInfo.cmake index d1f532506..473c68364 100644 --- a/UpdateInfo.cmake +++ b/UpdateInfo.cmake @@ -1,5 +1,9 @@ # cmakefile executed within a makefile target +if(APPLE) + set(PROJECT_SOURCE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/..") +endif() + # If we find ReleaseInfo.cmake we use the info from there and don't need Git to be installed find_file(REL_INFO_FILE ReleaseInfo.cmake PATHS "${PROJECT_SOURCE_DIR}" NO_DEFAULT_PATH) if(REL_INFO_FILE STREQUAL REL_INFO_FILE-NOTFOUND) @@ -10,10 +14,10 @@ if(REL_INFO_FILE STREQUAL REL_INFO_FILE-NOTFOUND) find_program(GIT_CMD git PATHS "/opt/local/bin" "/usr/local/bin" "/usr/bin") find_program(GIT_CMD git) set(SHELL "/bin/bash") - else(WIN32) # Linux + else() # Linux find_program(GIT_CMD git) set(SHELL "/bin/bash") - endif(WIN32) + endif() # Fail if Git is not installed if(GIT_CMD STREQUAL GIT_CMD-NOTFOUND) @@ -64,14 +68,23 @@ if(REL_INFO_FILE STREQUAL REL_INFO_FILE-NOTFOUND) set(GIT_NUMERIC_VERSION_BS "${GIT_NUMERIC_VERSION_BS}.${GIT_COMMITS_SINCE_TAG}") endif() + execute_process(COMMAND uname -mrs OUTPUT_VARIABLE BUILDINFO_OS OUTPUT_STRIP_TRAILING_WHITESPACE) + execute_process(COMMAND date -Ru OUTPUT_VARIABLE BUILDINFO_DATE OUTPUT_STRIP_TRAILING_WHITESPACE) + execute_process(COMMAND date +%s OUTPUT_VARIABLE BUILDINFO_EPOCH OUTPUT_STRIP_TRAILING_WHITESPACE) + execute_process(COMMAND uuidgen COMMAND tr "A-Z" "a-z" OUTPUT_VARIABLE BUILDINFO_UUID OUTPUT_STRIP_TRAILING_WHITESPACE) message(STATUS "Git checkout information:") - message(STATUS " Commit description: ${GIT_DESCRIBE}") - message(STATUS " Branch: ${GIT_BRANCH}") - message(STATUS " Commit: ${GIT_COMMIT}") - message(STATUS " Commit date: ${GIT_COMMIT_DATE}") - message(STATUS " Commits since tag: ${GIT_COMMITS_SINCE_TAG}") - message(STATUS " Commits since branch: ${GIT_COMMITS_SINCE_BRANCH}") - message(STATUS " Version (unreliable): ${GIT_NUMERIC_VERSION_BS}") + message(STATUS " Commit description: ${GIT_DESCRIBE}") + message(STATUS " Branch: ${GIT_BRANCH}") + message(STATUS " Commit: ${GIT_COMMIT}") + message(STATUS " Commit date: ${GIT_COMMIT_DATE}") + message(STATUS " Commits since tag: ${GIT_COMMITS_SINCE_TAG}") + message(STATUS " Commits since branch: ${GIT_COMMITS_SINCE_BRANCH}") + message(STATUS " Version (unreliable): ${GIT_NUMERIC_VERSION_BS}") + message(STATUS "Build information:") + message(STATUS " Build OS: ${BUILDINFO_OS}") + message(STATUS " Build date: ${BUILDINFO_DATE} UTC") + message(STATUS " Epoch: ${BUILDINFO_EPOCH}") + message(STATUS " UUID: ${BUILDINFO_UUID}") if(NOT DEFINED CACHE_NAME_SUFFIX) set(CACHE_NAME_SUFFIX "${GIT_DESCRIBE}") @@ -79,10 +92,9 @@ if(REL_INFO_FILE STREQUAL REL_INFO_FILE-NOTFOUND) else() message(STATUS "CACHE_NAME_SUFFIX is \"${CACHE_NAME_SUFFIX}\"") endif() - -else(REL_INFO_FILE STREQUAL REL_INFO_FILE-NOTFOUND) +else() include("${PROJECT_SOURCE_DIR}/ReleaseInfo.cmake") -endif(REL_INFO_FILE STREQUAL REL_INFO_FILE-NOTFOUND) +endif() if(WIN32) if(BIT_DEPTH EQUAL 4) @@ -97,12 +109,12 @@ if(WIN32) set(ARCHITECTURE_ALLOWED "x64 ia64") # installing in 64 bits mode for all 64 bits processors, even for itanium architecture set(INSTALL_MODE "x64 ia64") - endif(BIT_DEPTH EQUAL 4) + endif() # set part of the output archive name set(SYSTEM_NAME "WinVista") configure_file("${PROJECT_SOURCE_DIR}/tools/win/InnoSetup/WindowsInnoSetup.iss.in" "${CMAKE_BINARY_DIR}/rtdata/WindowsInnoSetup.iss") -endif(WIN32) +endif() # build version.h from template configure_file("${PROJECT_SOURCE_DIR}/rtgui/version.h.in" "${CMAKE_BINARY_DIR}/rtgui/version.h") diff --git a/cmake/modules/FindMacIntegration.cmake b/cmake/modules/FindMacIntegration.cmake index a67c31baa..a6729ad7f 100644 --- a/cmake/modules/FindMacIntegration.cmake +++ b/cmake/modules/FindMacIntegration.cmake @@ -24,7 +24,7 @@ mark_as_advanced(MACINTEGRATION_LIBRARY) # handle the QUIETLY and REQUIRED arguments and set MACINTEGRATION_FOUND to TRUE if # all listed variables are TRUE include(FindPackageHandleStandardArgs) -find_package_handle_standard_args(MACINTEGRATION DEFAULT_MSG MACINTEGRATION_LIBRARY MACINTEGRATION_INCLUDE_DIR) +find_package_handle_standard_args(MacIntegration DEFAULT_MSG MACINTEGRATION_LIBRARY MACINTEGRATION_INCLUDE_DIR) if(MACINTEGRATION_FOUND) set(MacIntegration_LIBRARIES ${MACINTEGRATION_LIBRARY}) diff --git a/com.rawtherapee.RawTherapee.appdata.xml b/com.rawtherapee.RawTherapee.appdata.xml index 3a55109ba..f7d588684 100644 --- a/com.rawtherapee.RawTherapee.appdata.xml +++ b/com.rawtherapee.RawTherapee.appdata.xml @@ -19,13 +19,12 @@ https://www.paypal.me/rawtherapee https://rawpedia.rawtherapee.com https://www.rawtherapee.com - https://discuss.pixls.us/t/localization-how-to-translate-rawtherapee-and-rawpedia/2594 + https://rawpedia.rawtherapee.com/Main_Page#Localization rawtherapee.desktop + - - diff --git a/header b/header index 966153c0e..a98fbbac1 100644 --- a/header +++ b/header @@ -7,7 +7,7 @@ * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. - * + * * RawTherapee is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the diff --git a/rtdata/CMakeLists.txt b/rtdata/CMakeLists.txt index 46722ba01..00a32c0cc 100644 --- a/rtdata/CMakeLists.txt +++ b/rtdata/CMakeLists.txt @@ -29,9 +29,12 @@ if(UNIX) install(FILES "${CMAKE_CURRENT_BINARY_DIR}/rawtherapee.desktop" DESTINATION ${DESKTOPDIR}) install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/images/png/rawtherapee-logo-16.png" DESTINATION "${ICONSDIR}/hicolor/16x16/apps" RENAME rawtherapee.png) install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/images/png/rawtherapee-logo-24.png" DESTINATION "${ICONSDIR}/hicolor/24x24/apps" RENAME rawtherapee.png) + install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/images/png/rawtherapee-logo-32.png" DESTINATION "${ICONSDIR}/hicolor/32x32/apps" RENAME rawtherapee.png) install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/images/png/rawtherapee-logo-48.png" DESTINATION "${ICONSDIR}/hicolor/48x48/apps" RENAME rawtherapee.png) + install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/images/png/rawtherapee-logo-64.png" DESTINATION "${ICONSDIR}/hicolor/64x64/apps" RENAME rawtherapee.png) install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/images/png/rawtherapee-logo-128.png" DESTINATION "${ICONSDIR}/hicolor/128x128/apps" RENAME rawtherapee.png) install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/images/png/rawtherapee-logo-256.png" DESTINATION "${ICONSDIR}/hicolor/256x256/apps" RENAME rawtherapee.png) + install(FILES "${CMAKE_CURRENT_SOURCE_DIR}/images/svg/rt-logo.svg" DESTINATION "${ICONSDIR}/hicolor/scalable/apps" RENAME rawtherapee.svg) endif() install(FILES ${LANGUAGEFILES} DESTINATION "${DATADIR}/languages") @@ -44,8 +47,8 @@ if(WIN32) install(FILES ${FONTS} DESTINATION "${DATADIR}/fonts") endif() -install(DIRECTORY ${PROFILESDIR} DESTINATION "${DATADIR}" FILES_MATCHING PATTERN "*.pp3") -install(DIRECTORY ${THEMEDIR} DESTINATION "${DATADIR}") +install(DIRECTORY "${PROFILESDIR}" DESTINATION "${DATADIR}" FILES_MATCHING PATTERN "*.pp3") +install(DIRECTORY "${THEMEDIR}" DESTINATION "${DATADIR}") install(FILES ${IMG_SVG} DESTINATION "${DATADIR}/images") install(FILES ${IMG_PNG} DESTINATION "${DATADIR}/images") @@ -54,19 +57,15 @@ install(FILES ${IMG_ICO} DESTINATION "${DATADIR}/images") if(APPLE) # CMake escapes first item quote character. Do not remove 'DUMMY_VARIABLE=' set(MACOSX_BUNDLE_COMMAND DUMMY_VARIABLE= - PROJECT_NAME="${PROJECT_NAME}" + PROJECT_NAME=${PROJECT_NAME} PROJECT_SOURCE_DIR="${PROJECT_SOURCE_DIR}" - CMAKE_BUILD_TYPE="${CMAKE_BUILD_TYPE}" + CMAKE_BUILD_TYPE=${CMAKE_BUILD_TYPE} GTK_PREFIX="${GTK_PREFIX}") - if(PROC_BIT_DEPTH MATCHES 32) - list(APPEND MACOSX_BUNDLE_COMMAND PROC_BIT_DEPTH=32) - else() - list(APPEND MACOSX_BUNDLE_COMMAND PROC_BIT_DEPTH=64) - endif() - list(APPEND MACOSX_BUNDLE_COMMAND sh "${PROJECT_SOURCE_DIR}/tools/osx/macosx_bundle.sh") + list(APPEND MACOSX_BUNDLE_COMMAND PROC_BIT_DEPTH=64) + list(APPEND MACOSX_BUNDLE_COMMAND sh ${PROJECT_SOURCE_DIR}/tools/osx/macosx_bundle.sh) add_custom_target(macosx_bundle COMMAND ${MACOSX_BUNDLE_COMMAND} - WORKING_DIRECTORY "${CMAKE_BINARY_DIR}" + WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}/build COMMENT "Creating macOS bundle") endif() diff --git a/rtdata/dcpprofiles/CANON EOS 5D MARK IV.dcp b/rtdata/dcpprofiles/CANON EOS 5D MARK IV.dcp new file mode 100644 index 000000000..80407fb21 Binary files /dev/null and b/rtdata/dcpprofiles/CANON EOS 5D MARK IV.dcp differ diff --git a/rtdata/dcpprofiles/CANON EOS M6 MARK II.dcp b/rtdata/dcpprofiles/CANON EOS M6 MARK II.dcp new file mode 100644 index 000000000..9a877f02f Binary files /dev/null and b/rtdata/dcpprofiles/CANON EOS M6 MARK II.dcp differ diff --git a/rtdata/dcpprofiles/CANON EOS R.dcp b/rtdata/dcpprofiles/CANON EOS R.dcp new file mode 100644 index 000000000..6ea5302e2 Binary files /dev/null and b/rtdata/dcpprofiles/CANON EOS R.dcp differ diff --git a/rtdata/dcpprofiles/CANON POWERSHOT G1 X MARK II.dcp b/rtdata/dcpprofiles/CANON POWERSHOT G1 X MARK II.dcp new file mode 100644 index 000000000..656649fd9 Binary files /dev/null and b/rtdata/dcpprofiles/CANON POWERSHOT G1 X MARK II.dcp differ diff --git a/rtdata/dcpprofiles/Canon EOS RP.dcp b/rtdata/dcpprofiles/Canon EOS RP.dcp new file mode 100644 index 000000000..8379d9703 Binary files /dev/null and b/rtdata/dcpprofiles/Canon EOS RP.dcp differ diff --git a/rtdata/dcpprofiles/Canon PowerShot S120.dcp b/rtdata/dcpprofiles/Canon PowerShot S120.dcp new file mode 100644 index 000000000..8bb089c29 Binary files /dev/null and b/rtdata/dcpprofiles/Canon PowerShot S120.dcp differ diff --git a/rtdata/dcpprofiles/FUJIFILM X-A5.dcp b/rtdata/dcpprofiles/FUJIFILM X-A5.dcp new file mode 100644 index 000000000..c6e88d789 Binary files /dev/null and b/rtdata/dcpprofiles/FUJIFILM X-A5.dcp differ diff --git a/rtdata/dcpprofiles/FUJIFILM X-H1.dcp b/rtdata/dcpprofiles/FUJIFILM X-H1.dcp new file mode 100644 index 000000000..e3abc07f1 Binary files /dev/null and b/rtdata/dcpprofiles/FUJIFILM X-H1.dcp differ diff --git a/rtdata/dcpprofiles/FUJIFILM X-PRO3.dcp b/rtdata/dcpprofiles/FUJIFILM X-PRO3.dcp new file mode 100644 index 000000000..bfbaff9e5 Binary files /dev/null and b/rtdata/dcpprofiles/FUJIFILM X-PRO3.dcp differ diff --git a/rtdata/dcpprofiles/FUJIFILM X-T10.dcp b/rtdata/dcpprofiles/FUJIFILM X-T10.dcp new file mode 100644 index 000000000..e77837f3e Binary files /dev/null and b/rtdata/dcpprofiles/FUJIFILM X-T10.dcp differ diff --git a/rtdata/dcpprofiles/FUJIFILM X-T3.dcp b/rtdata/dcpprofiles/FUJIFILM X-T3.dcp new file mode 100644 index 000000000..5024f38a9 Binary files /dev/null and b/rtdata/dcpprofiles/FUJIFILM X-T3.dcp differ diff --git a/rtdata/dcpprofiles/FUJIFILM X-T30.dcp b/rtdata/dcpprofiles/FUJIFILM X-T30.dcp new file mode 100644 index 000000000..97917b810 Binary files /dev/null and b/rtdata/dcpprofiles/FUJIFILM X-T30.dcp differ diff --git a/rtdata/dcpprofiles/NIKON D500.dcp b/rtdata/dcpprofiles/NIKON D500.dcp new file mode 100644 index 000000000..c25294439 Binary files /dev/null and b/rtdata/dcpprofiles/NIKON D500.dcp differ diff --git a/rtdata/dcpprofiles/NIKON D5300.dcp b/rtdata/dcpprofiles/NIKON D5300.dcp new file mode 100644 index 000000000..2c7566c8c Binary files /dev/null and b/rtdata/dcpprofiles/NIKON D5300.dcp differ diff --git a/rtdata/dcpprofiles/NIKON D610.dcp b/rtdata/dcpprofiles/NIKON D610.dcp new file mode 100644 index 000000000..a5a05ca34 Binary files /dev/null and b/rtdata/dcpprofiles/NIKON D610.dcp differ diff --git a/rtdata/dcpprofiles/NIKON D7100.dcp b/rtdata/dcpprofiles/NIKON D7100.dcp new file mode 100644 index 000000000..332157fc9 Binary files /dev/null and b/rtdata/dcpprofiles/NIKON D7100.dcp differ diff --git a/rtdata/dcpprofiles/NIKON D7500.dcp b/rtdata/dcpprofiles/NIKON D7500.dcp new file mode 100644 index 000000000..5e6cb2c64 Binary files /dev/null and b/rtdata/dcpprofiles/NIKON D7500.dcp differ diff --git a/rtdata/dcpprofiles/NIKON D800.dcp b/rtdata/dcpprofiles/NIKON D800.dcp new file mode 100644 index 000000000..5f0ebba8c Binary files /dev/null and b/rtdata/dcpprofiles/NIKON D800.dcp differ diff --git a/rtdata/dcpprofiles/NIKON D850.dcp b/rtdata/dcpprofiles/NIKON D850.dcp new file mode 100644 index 000000000..806e1e9bb Binary files /dev/null and b/rtdata/dcpprofiles/NIKON D850.dcp differ diff --git a/rtdata/dcpprofiles/NIKON Z 50.dcp b/rtdata/dcpprofiles/NIKON Z 50.dcp new file mode 100644 index 000000000..beca667a7 Binary files /dev/null and b/rtdata/dcpprofiles/NIKON Z 50.dcp differ diff --git a/rtdata/dcpprofiles/NIKON Z 6.dcp b/rtdata/dcpprofiles/NIKON Z 6.dcp new file mode 100644 index 000000000..eeb45a6b8 Binary files /dev/null and b/rtdata/dcpprofiles/NIKON Z 6.dcp differ diff --git a/rtdata/dcpprofiles/NIKON Z 7.dcp b/rtdata/dcpprofiles/NIKON Z 7.dcp new file mode 100644 index 000000000..19fb7bba6 Binary files /dev/null and b/rtdata/dcpprofiles/NIKON Z 7.dcp differ diff --git a/rtdata/dcpprofiles/OLYMPUS E-M5MARKII.dcp b/rtdata/dcpprofiles/OLYMPUS E-M5MARKII.dcp new file mode 100644 index 000000000..c3f670bfb Binary files /dev/null and b/rtdata/dcpprofiles/OLYMPUS E-M5MARKII.dcp differ diff --git a/rtdata/dcpprofiles/PENTAX K-50.dcp b/rtdata/dcpprofiles/PENTAX K-50.dcp new file mode 100644 index 000000000..3205c7579 Binary files /dev/null and b/rtdata/dcpprofiles/PENTAX K-50.dcp differ diff --git a/rtdata/dcpprofiles/SONY ILCE-6300.dcp b/rtdata/dcpprofiles/SONY ILCE-6300.dcp new file mode 100644 index 000000000..53194d35d Binary files /dev/null and b/rtdata/dcpprofiles/SONY ILCE-6300.dcp differ diff --git a/rtdata/dcpprofiles/SONY ILCE-6400.dcp b/rtdata/dcpprofiles/SONY ILCE-6400.dcp new file mode 100644 index 000000000..8c5fcfec4 Binary files /dev/null and b/rtdata/dcpprofiles/SONY ILCE-6400.dcp differ diff --git a/rtdata/dcpprofiles/SONY ILCE-6500.dcp b/rtdata/dcpprofiles/SONY ILCE-6500.dcp new file mode 100644 index 000000000..66be8b1de Binary files /dev/null and b/rtdata/dcpprofiles/SONY ILCE-6500.dcp differ diff --git a/rtdata/dcpprofiles/SONY ILCE-6600.dcp b/rtdata/dcpprofiles/SONY ILCE-6600.dcp new file mode 100644 index 000000000..8c802d150 Binary files /dev/null and b/rtdata/dcpprofiles/SONY ILCE-6600.dcp differ diff --git a/rtdata/dcpprofiles/SONY ILCE-7RM4.dcp b/rtdata/dcpprofiles/SONY ILCE-7RM4.dcp new file mode 100644 index 000000000..e473fa496 Binary files /dev/null and b/rtdata/dcpprofiles/SONY ILCE-7RM4.dcp differ diff --git a/rtdata/dcpprofiles/SONY ILCE-9.dcp b/rtdata/dcpprofiles/SONY ILCE-9.dcp new file mode 100644 index 000000000..c07315812 Binary files /dev/null and b/rtdata/dcpprofiles/SONY ILCE-9.dcp differ diff --git a/rtdata/images/svg/splash.svg b/rtdata/images/svg/splash.svg index 0989bfdb6..5609a45c1 100644 --- a/rtdata/images/svg/splash.svg +++ b/rtdata/images/svg/splash.svg @@ -1,6 +1,4 @@ - - + inkscape:export-xdpi="96" + inkscape:export-filename="/tmp/splash.png" + sodipodi:docname="splash.svg" + inkscape:version="1.1-dev (4cd8f7c, 2020-02-06)" + id="svg783" + version="1.1" + viewBox="0 0 146.05 91.545836" + height="346" + width="552"> RawTherapee splash screen + id="stop3964-8" /> + id="stop3966-8" /> + id="stop3956-7" /> + id="stop3958-6" /> + inkscape:collect="always" + id="linearGradient4002-3"> + id="stop4004-0" /> + id="stop4006-3" /> + id="stop4026-2" /> + id="stop4028-5" /> + inkscape:collect="always" + id="linearGradient4018-0"> + id="stop4020-5" /> + id="stop4022-9" /> + style="stop-color:#f18e01;stop-opacity:1;" /> + id="stop3982-2" /> + inkscape:collect="always" + id="linearGradient3994-4"> + id="stop3996-7" /> + id="stop3998-7" /> + id="stop3972-8" /> + id="stop3974-1" /> + id="stop3948-9" /> + id="stop3950-3" /> + id="stop3988-0" /> + id="stop3990-2" /> - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + inkscape:window-maximized="1" + inkscape:window-y="0" + inkscape:window-x="0" + inkscape:window-height="1021" + inkscape:window-width="1920" + inkscape:snap-global="false" + inkscape:snap-nodes="true" + inkscape:object-nodes="false" + inkscape:snap-others="true" + inkscape:guide-bbox="true" + showguides="true" + inkscape:bbox-paths="false" + inkscape:snap-bbox-edge-midpoints="false" + inkscape:snap-bbox-midpoints="true" + inkscape:object-paths="false" + inkscape:snap-intersection-paths="false" + inkscape:snap-smooth-nodes="false" + inkscape:snap-midpoints="false" + inkscape:snap-object-midpoints="true" + inkscape:snap-center="false" + inkscape:snap-text-baseline="false" + inkscape:snap-page="false" + inkscape:bbox-nodes="true" + inkscape:snap-bbox="true" + units="px" + showgrid="false" + inkscape:current-layer="layer1" + inkscape:document-units="px" + inkscape:cy="209.17983" + inkscape:cx="275.82889" + inkscape:zoom="0.95596044" + inkscape:pageshadow="2" + inkscape:pageopacity="0.0" + borderopacity="1.0" + bordercolor="#666666" + pagecolor="#ffffff" + id="base"> - + + orientation="0,1" + position="27.648959,71.437501" /> - + + orientation="1,0" + position="138.12828,76.425406" /> - + - + - - + position="123.92422,11.509375" /> + + + orientation="1,0" + position="73.162242,39.921138" /> @@ -602,534 +570,375 @@ - - - Each logo element has a filter effect (ring*). Additionally, the logo as a whole (all elements grouped) also has a filter effect (logo glow)."Raw": font Eras Ultra ITC, 60pt, -3px spacing between characters."Therapee": font Eras Medium ITC, 60pt, +1px spacing between characters.Version: font Eras Bold ITC, 64pt, skewed -3°. RawTherapee splash screen design version 1.2 from 2019-02-27 | www.rawtherapee.com - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + inkscape:groupmode="layer" + inkscape:label="Layer 1"> - + GNU GPLv3 - - Development + d="m 9.4489751,288.85927 q 0.3352508,0.002 0.5154724,0.002 0.1918485,0 0.4321445,-0.002 -0.04263,0.57942 -0.06201,1.39914 -0.5871735,0.12596 -1.0038148,0.12596 -0.3081207,0 -0.5910491,-0.0795 -0.2809906,-0.0795 -0.4747773,-0.24224 -0.1937866,-0.16278 -0.2926178,-0.41858 -0.096893,-0.25579 -0.096893,-0.54066 0,-0.32362 0.1220856,-0.60849 0.1240234,-0.2868 0.346878,-0.48059 0.2228547,-0.19379 0.5019074,-0.27712 0.2790527,-0.0833 0.6181793,-0.0833 0.3720703,0 0.829407,0.0988 0.0039,0.14534 0.01938,0.31393 -0.271301,-0.0891 -0.4689632,-0.12208 -0.1976624,-0.0349 -0.3643189,-0.0349 -0.2616119,0 -0.4980316,0.0795 -0.2364196,0.0775 -0.405014,0.24029 -0.1685944,0.16084 -0.2557983,0.3992 -0.087204,0.23836 -0.087204,0.49222 0,0.22673 0.069763,0.42633 0.071701,0.19766 0.2151031,0.32362 0.1434021,0.12597 0.3488159,0.19379 0.2073517,0.0659 0.449585,0.0659 0.1317749,0 0.3139343,-0.0233 0.1821594,-0.0252 0.3681946,-0.0833 l 0.038757,-0.91661 H 9.855927 q -0.1821594,0 -0.4185791,0.01 0.011627,-0.13952 0.011627,-0.25773 z" /> + + + + + + + - Release Candidate 1 + style="filter:url(#filter173)" + id="g171"> + + + + + + + + + + + + + + + + + + + + + + + + + + - 5 - . 8 - Therapee - Raw - Therapee - Raw + transform="matrix(0.24127119,0,0.01264448,0.24127122,-4.8837849,265.42414)" + aria-label="5" /> + id="text3659" + style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;line-height:0%;font-family:'Eras Medium ITC';-inkscape-font-specification:'Eras Medium ITC';letter-spacing:1px;word-spacing:0px;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:1.07075834px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;filter:url(#filter4749);enable-background:new" + transform="matrix(0.24732122,0,0,0.24687704,-5.5339446,264.55152)" + aria-label="Therapee"> + id="path670" + style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:79.99999237px;line-height:1.25;font-family:'Eras Medium ITC';-inkscape-font-specification:'Eras Medium ITC';letter-spacing:0.99999994px;stroke-width:1.07075834px" + d="m 256.12553,-157.9659 0.78125,-11.95312 1.05469,-24.76562 0.35156,-11.44531 q -9.57031,0.0391 -16.75781,0.35156 0.23438,-3.125 0.27344,-5.50781 9.92187,0.0391 21.40625,0.0391 l 12.5,-0.0391 h 6.64062 q -0.27344,3.4375 -0.27344,5.46875 -6.05468,-0.35157 -13.39843,-0.35157 h -3.20313 l -0.82031,17.30469 -0.82031,24.375 v 6.52343 l -3.75,-0.0781 q -0.50782,0 -3.98438,0.0781 z" /> + id="path672" + style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:79.99999237px;line-height:1.25;font-family:'Eras Medium ITC';-inkscape-font-specification:'Eras Medium ITC';letter-spacing:0.99999994px;stroke-width:1.07075834px" + d="m 287.32084,-157.9659 0.97656,-16.99218 0.89844,-23.16406 0.23438,-13.16406 3.55468,0.0391 q 1.32813,0 3.47657,-0.0391 l -0.85938,13.55468 -0.3125,8.08594 q 0.9375,-1.67969 1.60156,-2.65625 0.70313,-1.01563 1.75782,-1.99219 1.09375,-1.01562 2.26562,-1.71875 1.17188,-0.70312 2.61719,-1.21094 1.44531,-0.54687 3.47656,-0.89843 2.03125,-0.35157 4.25781,-0.35157 3.32031,0 6.32813,0.74219 3.04687,0.74219 5.19531,2.46094 2.1875,1.71875 2.96875,4.10156 0.82031,2.38281 0.82031,4.84375 0,0.97656 -0.0391,2.57813 -0.11719,2.42187 -0.3125,5.66406 l -0.66406,14.375 q -0.11719,2.34375 -0.15625,5.74218 -2.26563,-0.0781 -3.47657,-0.0781 -1.32812,0 -3.71093,0.0781 0.42968,-4.21875 0.97656,-13.28125 0.58594,-9.06249 0.58594,-12.57812 0,-3.125 -1.13282,-5.15625 -1.13281,-2.07031 -3.75,-3.16406 -2.61718,-1.09375 -5.82031,-1.09375 -2.92968,0 -5.46875,0.89844 -2.30468,0.82031 -3.94531,2.30468 -1.60156,1.48438 -2.57812,3.63282 -1.05469,2.30468 -1.48438,4.64843 -0.66406,3.71094 -0.9375,10.3125 -0.15625,3.94531 -0.42969,13.47656 -2.1875,-0.0781 -3.28125,-0.0781 -1.01562,0 -3.63281,0.0781 z" /> + + + + + + + id="text3655" + style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;line-height:0%;font-family:'Eras Ultra ITC';-inkscape-font-specification:'Eras Ultra ITC';letter-spacing:0px;word-spacing:0px;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:1.08272994px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;filter:url(#filter4749);enable-background:new" + transform="matrix(0.24020317,0,0,0.23782112,-7.1514703,262.84505)" + aria-label="Raw"> + + + + + + + id="text1782" + style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;line-height:0%;font-family:'Eras Bold ITC';-inkscape-font-specification:'Eras Bold ITC Bold';letter-spacing:0px;word-spacing:0px;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;filter:url(#filter4749);enable-background:new" + transform="matrix(0.24127119,0,0.01264448,0.24127122,-57.800454,265.42414)" + aria-label="5"> + id="path1794" + style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:80px;line-height:1.25;font-family:'Eras Bold ITC';-inkscape-font-specification:'Eras Bold ITC Bold'" + d="m 290.0611,1.4557576 -0.27344,-3.9453125 q -0.11719,-1.9140625 -0.27344,-3.4765625 -0.11719,-1.5625 -0.50781,-5.0781246 8.08594,2.3046871 13.39844,2.3046871 2.85156,0 5.23437,-0.8984375 2.42188,-0.8984376 3.71094,-2.5390626 1.28906,-1.640625 1.28906,-3.59375 0,-2.851562 -2.65625,-4.296875 -2.61719,-1.484375 -8.24219,-1.484375 -2.5,0 -4.92187,0.195313 -2.38281,0.15625 -6.48438,0.703125 l 1.99219,-25.234375 q 0.11719,-1.875 0.23438,-5.195313 9.80468,0.07813 18.86718,0.07813 11.48438,0 19.14063,-0.07813 -0.35156,4.0625 -0.42969,6.445313 l -0.19531,5.3125 -5.19531,-0.195313 -2.42188,-0.03906 h -3.78906 q -2.42188,-0.03906 -6.01563,-0.03906 -1.21093,0 -3.98437,0.07813 l -0.78125,8.945313 q 2.61719,-0.195313 4.0625,-0.195313 6.09375,0 10.74219,1.953125 4.64843,1.914063 6.79687,5.390625 2.14844,3.476563 2.14844,7.851563 0,4.257812 -2.1875,8.2031246 -2.1875,3.90625 -6.01563,6.25 -3.78906,2.3046875 -8.82812,3.359375 -5,1.015625 -10.27344,1.015625 -1.99219,0 -4.72656,-0.2734375 -2.73438,-0.234375 -4.60938,-0.546875 -1.875,-0.3125 -4.80468,-0.9765625 z" /> + + + id="path1797" + style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:49.34799576px;line-height:1.25;font-family:'Eras Bold ITC';-inkscape-font-specification:'Eras Bold ITC Bold';letter-spacing:-7.09514618px" + d="m 286.21154,2.2370076 q 0.19276,-3.22882392 0.33734,-8.7226438 l 4.96371,0.072287 q 0.79516,0 4.19265,-0.072287 -0.19276,2.6264315 -0.43372,8.7226438 l -4.19265,-0.048191 q -0.45782,0 -4.86733,0.048191 z" /> - - - - - - - - + id="path1799" + style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:49.34799576px;line-height:1.25;font-family:'Eras Bold ITC';-inkscape-font-specification:'Eras Bold ITC Bold';letter-spacing:-7.09514618px" + d="m 305.49017,-14.629983 q -1.39755,-0.67468 -2.07223,-1.132498 -0.65058,-0.481914 -1.27707,-1.156594 -0.60239,-0.674679 -1.01202,-1.493933 -0.40963,-0.819254 -0.57829,-1.686699 -0.16867,-0.867445 -0.16867,-1.734891 0,-2.337283 1.06021,-4.216747 1.06021,-1.879465 3.13244,-3.08425 2.07223,-1.228881 4.43361,-1.686699 2.36137,-0.457819 4.96371,-0.457819 2.48186,0 4.79505,0.578297 2.31318,0.554201 3.95169,1.758986 1.6626,1.204786 2.43367,2.771006 0.77106,1.542125 0.77106,3.710738 0,1.036115 -0.21686,1.999943 -0.19277,0.963828 -0.62649,1.783082 -0.43372,0.795158 -1.06021,1.469838 -0.62649,0.674679 -1.32527,1.180689 -0.69877,0.50601 -2.33728,1.325264 1.54213,0.433722 2.36138,0.795158 0.81925,0.33734 1.56622,0.963828 0.77106,0.602392 1.30117,1.445742 0.5542,0.819254 0.79516,1.7589862 0.24095,0.9397323 0.24095,1.9758475 0,2.4095701 -1.18069,4.6022789 -1.18069,2.19270878 -3.22882,3.51797234 -2.02404,1.32526356 -4.72276,1.90356036 -2.69872,0.6023925 -5.51791,0.6023925 -2.69872,0 -5.20467,-0.5301054 -2.48186,-0.5301054 -4.43361,-1.75898615 -1.95175,-1.25297646 -2.8433,-2.93967555 -0.89154,-1.6866991 -0.89154,-3.8312165 0,-1.2529764 0.31325,-2.4336658 0.33734,-1.1806893 0.98792,-2.2168044 0.67468,-1.060211 1.54213,-1.758986 0.86744,-0.722871 1.6867,-1.108402 0.84334,-0.409627 2.36137,-0.915637 z m 7.90339,-9.999716 q -1.90356,0 -3.01196,1.060211 -1.1084,1.060211 -1.1084,2.602336 0,0.915636 0.48191,1.686699 0.48192,0.771062 1.34936,1.156593 0.86745,0.361436 1.87947,0.361436 1.75898,0 2.93967,-1.01202 1.18069,-1.036115 1.18069,-2.674623 0,-1.445742 -1.01202,-2.313187 -0.98792,-0.867445 -2.69872,-0.867445 z m -0.57829,13.22854 q -2.16862,0 -3.3975,1.108402 -1.20478,1.0843066 -1.20478,2.8191971 0,1.0120194 0.5301,1.8794647 0.5542,0.8674452 1.56622,1.3252635 1.03612,0.4337227 2.2409,0.4337227 1.25298,0 2.265,-0.4819141 1.03612,-0.481914 1.63851,-1.4216463 0.60239,-0.9638281 0.60239,-2.1927088 0,-1.6385077 -1.1325,-2.5541448 -1.1084,-0.915636 -3.10834,-0.915636 z" /> + transform="matrix(0.24804687,0,0,0.2480469,-16.632728,273.1232)" + id="g3926"> + + + + + + + + + + + + + + diff --git a/rtdata/images/svg/splash_template.svg b/rtdata/images/svg/splash_template.svg new file mode 100644 index 000000000..8044343c0 --- /dev/null +++ b/rtdata/images/svg/splash_template.svg @@ -0,0 +1,1078 @@ + + + + + RawTherapee splash screen + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + image/svg+xml + + RawTherapee splash screen + + + + Maciej Dworak + + + www.rawtherapee.com + + + + + + + + + + + + + + + + Each logo element has a filter effect (ring*). Additionally, the logo as a whole (all elements grouped) also has a filter effect (logo glow)."Raw": font Eras Ultra ITC, 60pt, -3px spacing between characters."Therapee": font Eras Medium ITC, 60pt, +1px spacing between characters.Version: font Eras Bold ITC, 64pt, skewed -3°. RawTherapee splash screen design version 1.2 from 2019-02-27 | www.rawtherapee.com + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + GNU GPLv3 + + Development + + + Release Candidate 1 + + 5 + . 9 + Therapee + Raw + Therapee + Raw + + + + + + + + + + + + diff --git a/rtdata/languages/Catala b/rtdata/languages/Catala index 31614c7b3..ac4c9565b 100644 --- a/rtdata/languages/Catala +++ b/rtdata/languages/Catala @@ -1354,6 +1354,7 @@ ZOOMPANEL_ZOOMOUT;Allunya\nDrecera: - !HISTORY_MSG_SOFTLIGHT_ENABLED;Soft light !HISTORY_MSG_SOFTLIGHT_STRENGTH;Soft light - Strength !HISTORY_MSG_TM_FATTAL_ANCHOR;DRC - Anchor +!HISTORY_MSG_TRANS_Method;Geometry - Method !HISTORY_NEWSNAPSHOT_TOOLTIP;Shortcut: Alt-s !ICCPROFCREATOR_COPYRIGHT;Copyright: !ICCPROFCREATOR_COPYRIGHT_RESET_TOOLTIP;Reset to the default copyright, granted to "RawTherapee, CC0" @@ -1920,6 +1921,8 @@ ZOOMPANEL_ZOOMOUT;Allunya\nDrecera: - !TP_LABCURVE_CURVEEDITOR_LH;LH !TP_LABCURVE_CURVEEDITOR_LH_TOOLTIP;Luminance according to hue L=f(H) !TP_LABCURVE_CURVEEDITOR_LL_TOOLTIP;Luminance according to luminance L=f(L) +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_LCPFILE;LCP file !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected diff --git a/rtdata/languages/Chinese (Simplified) b/rtdata/languages/Chinese (Simplified) index 5be2958e8..61cbd58ac 100644 --- a/rtdata/languages/Chinese (Simplified) +++ b/rtdata/languages/Chinese (Simplified) @@ -1401,6 +1401,7 @@ ZOOMPANEL_ZOOMOUT;缩放拉远\n快捷键: - !HISTORY_MSG_SOFTLIGHT_ENABLED;Soft light !HISTORY_MSG_SOFTLIGHT_STRENGTH;Soft light - Strength !HISTORY_MSG_TM_FATTAL_ANCHOR;DRC - Anchor +!HISTORY_MSG_TRANS_Method;Geometry - Method !ICCPROFCREATOR_COPYRIGHT;Copyright: !ICCPROFCREATOR_COPYRIGHT_RESET_TOOLTIP;Reset to the default copyright, granted to "RawTherapee, CC0" !ICCPROFCREATOR_CUSTOM;Custom @@ -1885,6 +1886,8 @@ ZOOMPANEL_ZOOMOUT;缩放拉远\n快捷键: - !TP_LABCURVE_LCREDSK_TIP;If enabled, the LC Curve affects only red and skin-tones.\nIf disabled, it applies to all tones. !TP_LABCURVE_RSTPROTECTION;Red and skin-tones protection !TP_LABCURVE_RSTPRO_TOOLTIP;Works on the Chromaticity slider and the CC curve. +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_LCPFILE;LCP file !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected diff --git a/rtdata/languages/Czech b/rtdata/languages/Czech index 25bcf2820..19182a1e5 100644 --- a/rtdata/languages/Czech +++ b/rtdata/languages/Czech @@ -2335,6 +2335,7 @@ ZOOMPANEL_ZOOMOUT;Oddálit\nZkratka: - !HISTORY_MSG_PDSHARPEN_ITERATIONS;CS - Iterations !HISTORY_MSG_PDSHARPEN_RADIUS;CS - Radius !HISTORY_MSG_PDSHARPEN_RADIUS_BOOST;CS - Corner radius boost +!HISTORY_MSG_TRANS_Method;Geometry - Method !PARTIALPASTE_FILMNEGATIVE;Film Negative !PREFERENCES_APPEARANCE_PSEUDOHIDPI;Pseudo-HiDPI mode !TP_DEHAZE_LUMINANCE;Luminance only @@ -2344,6 +2345,8 @@ ZOOMPANEL_ZOOMOUT;Oddálit\nZkratka: - !TP_FILMNEGATIVE_LABEL;Film Negative !TP_FILMNEGATIVE_PICK;Pick neutral spots !TP_FILMNEGATIVE_RED;Red ratio +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_PDSHARPENING_LABEL;Capture Sharpening !TP_SHARPENING_ITERCHECK;Auto limit iterations !TP_SHARPENING_RADIUS_BOOST;Corner radius boost diff --git a/rtdata/languages/Deutsch b/rtdata/languages/Deutsch index 592801054..99835591a 100644 --- a/rtdata/languages/Deutsch +++ b/rtdata/languages/Deutsch @@ -2392,4 +2392,7 @@ ZOOMPANEL_ZOOMOUT;Herauszoomen\nTaste: - !GENERAL_HELP;Help !HISTORY_MSG_PDSHARPEN_CHECKITER;CS - Auto limit iterations +!HISTORY_MSG_TRANS_Method;Geometry - Method +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_SHARPENING_ITERCHECK;Auto limit iterations diff --git a/rtdata/languages/English (UK) b/rtdata/languages/English (UK) index e30425b68..2cb1d526d 100644 --- a/rtdata/languages/English (UK) +++ b/rtdata/languages/English (UK) @@ -876,6 +876,7 @@ TP_WBALANCE_EQBLUERED_TOOLTIP;Allows to deviate from the normal behaviour of "wh !HISTORY_MSG_SOFTLIGHT_ENABLED;Soft light !HISTORY_MSG_SOFTLIGHT_STRENGTH;Soft light - Strength !HISTORY_MSG_TM_FATTAL_ANCHOR;DRC - Anchor +!HISTORY_MSG_TRANS_Method;Geometry - Method !HISTORY_NEWSNAPSHOT;Add !HISTORY_NEWSNAPSHOT_TOOLTIP;Shortcut: Alt-s !HISTORY_SNAPSHOT;Snapshot @@ -1792,6 +1793,8 @@ TP_WBALANCE_EQBLUERED_TOOLTIP;Allows to deviate from the normal behaviour of "wh !TP_LENSGEOM_AUTOCROP;Auto-Crop !TP_LENSGEOM_FILL;Auto-fill !TP_LENSGEOM_LABEL;Lens / Geometry +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_LCPFILE;LCP file !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected diff --git a/rtdata/languages/English (US) b/rtdata/languages/English (US) index a1e0050a8..d8c497f16 100644 --- a/rtdata/languages/English (US) +++ b/rtdata/languages/English (US) @@ -788,6 +788,7 @@ !HISTORY_MSG_SOFTLIGHT_ENABLED;Soft light !HISTORY_MSG_SOFTLIGHT_STRENGTH;Soft light - Strength !HISTORY_MSG_TM_FATTAL_ANCHOR;DRC - Anchor +!HISTORY_MSG_TRANS_Method;Geometry - Method !HISTORY_NEWSNAPSHOT;Add !HISTORY_NEWSNAPSHOT_TOOLTIP;Shortcut: Alt-s !HISTORY_SNAPSHOT;Snapshot @@ -1776,6 +1777,8 @@ !TP_LENSGEOM_AUTOCROP;Auto-Crop !TP_LENSGEOM_FILL;Auto-fill !TP_LENSGEOM_LABEL;Lens / Geometry +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_LCPFILE;LCP file !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected diff --git a/rtdata/languages/Espanol b/rtdata/languages/Espanol index ee8b0d17d..c1468a6d9 100644 --- a/rtdata/languages/Espanol +++ b/rtdata/languages/Espanol @@ -2334,6 +2334,7 @@ ZOOMPANEL_ZOOMOUT;Reducir Zoom\nTecla de Atajo: - !HISTORY_MSG_PDSHARPEN_RADIUS;CS - Radius !HISTORY_MSG_PDSHARPEN_RADIUS_BOOST;CS - Corner radius boost !HISTORY_MSG_SHARPENING_BLUR;Sharpening - Blur radius +!HISTORY_MSG_TRANS_Method;Geometry - Method !MAIN_FRAME_PLACES_DEL;Remove !MAIN_TAB_FAVORITES;Favorites !MAIN_TAB_FAVORITES_TOOLTIP;Shortcut: Alt-u @@ -2362,6 +2363,8 @@ ZOOMPANEL_ZOOMOUT;Reducir Zoom\nTecla de Atajo: - !TP_FILMNEGATIVE_LABEL;Film Negative !TP_FILMNEGATIVE_PICK;Pick neutral spots !TP_FILMNEGATIVE_RED;Red ratio +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected !TP_LENSPROFILE_MODE_HEADER;Lens Profile diff --git a/rtdata/languages/Francais b/rtdata/languages/Francais index 9ecf43733..a98b6eded 100644 --- a/rtdata/languages/Francais +++ b/rtdata/languages/Francais @@ -2278,6 +2278,7 @@ ZOOMPANEL_ZOOMOUT;Zoom Arrière\nRaccourci: - !HISTORY_MSG_PDSHARPEN_ITERATIONS;CS - Iterations !HISTORY_MSG_PDSHARPEN_RADIUS;CS - Radius !HISTORY_MSG_PDSHARPEN_RADIUS_BOOST;CS - Corner radius boost +!HISTORY_MSG_TRANS_Method;Geometry - Method !MAIN_FRAME_PLACES_DEL;Remove !PARTIALPASTE_FILMNEGATIVE;Film Negative !PROGRESSBAR_DECODING;Decoding... @@ -2295,6 +2296,8 @@ ZOOMPANEL_ZOOMOUT;Zoom Arrière\nRaccourci: - !TP_FILMNEGATIVE_LABEL;Film Negative !TP_FILMNEGATIVE_PICK;Pick neutral spots !TP_FILMNEGATIVE_RED;Red ratio +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected !TP_LENSPROFILE_MODE_HEADER;Lens Profile diff --git a/rtdata/languages/Italiano b/rtdata/languages/Italiano index 0fd256d7c..340309b9f 100644 --- a/rtdata/languages/Italiano +++ b/rtdata/languages/Italiano @@ -1579,6 +1579,7 @@ ZOOMPANEL_ZOOMOUT;Rimpicciolisci.\nScorciatoia: - !HISTORY_MSG_SOFTLIGHT_ENABLED;Soft light !HISTORY_MSG_SOFTLIGHT_STRENGTH;Soft light - Strength !HISTORY_MSG_TM_FATTAL_ANCHOR;DRC - Anchor +!HISTORY_MSG_TRANS_Method;Geometry - Method !ICCPROFCREATOR_COPYRIGHT;Copyright: !ICCPROFCREATOR_COPYRIGHT_RESET_TOOLTIP;Reset to the default copyright, granted to "RawTherapee, CC0" !ICCPROFCREATOR_CUSTOM;Custom @@ -1946,6 +1947,8 @@ ZOOMPANEL_ZOOMOUT;Rimpicciolisci.\nScorciatoia: - !TP_ICM_WORKING_TRC_NONE;None !TP_ICM_WORKING_TRC_SLOPE;Slope !TP_ICM_WORKING_TRC_TOOLTIP;Only for built-in profiles. +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_LCPFILE;LCP file !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected diff --git a/rtdata/languages/Japanese b/rtdata/languages/Japanese index 588a817f2..b7c0b7e22 100644 --- a/rtdata/languages/Japanese +++ b/rtdata/languages/Japanese @@ -2314,3 +2314,6 @@ ZOOMPANEL_ZOOMOUT;ズームアウト\nショートカット: - !!!!!!!!!!!!!!!!!!!!!!!!! !GENERAL_HELP;Help +!HISTORY_MSG_TRANS_Method;Geometry - Method +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic diff --git a/rtdata/languages/Magyar b/rtdata/languages/Magyar index 4b6f2811b..7ecdc6f3b 100644 --- a/rtdata/languages/Magyar +++ b/rtdata/languages/Magyar @@ -1288,6 +1288,7 @@ ZOOMPANEL_ZOOMOUT;Kicsinyítés - !HISTORY_MSG_SOFTLIGHT_ENABLED;Soft light !HISTORY_MSG_SOFTLIGHT_STRENGTH;Soft light - Strength !HISTORY_MSG_TM_FATTAL_ANCHOR;DRC - Anchor +!HISTORY_MSG_TRANS_Method;Geometry - Method !HISTORY_NEWSNAPSHOT_TOOLTIP;Shortcut: Alt-s !ICCPROFCREATOR_COPYRIGHT;Copyright: !ICCPROFCREATOR_COPYRIGHT_RESET_TOOLTIP;Reset to the default copyright, granted to "RawTherapee, CC0" @@ -1912,6 +1913,8 @@ ZOOMPANEL_ZOOMOUT;Kicsinyítés - !TP_LABCURVE_LCREDSK_TIP;If enabled, the LC Curve affects only red and skin-tones.\nIf disabled, it applies to all tones. !TP_LABCURVE_RSTPROTECTION;Red and skin-tones protection !TP_LABCURVE_RSTPRO_TOOLTIP;Works on the Chromaticity slider and the CC curve. +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_LCPFILE;LCP file !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected diff --git a/rtdata/languages/Nederlands b/rtdata/languages/Nederlands index c230323f5..c43f6314e 100644 --- a/rtdata/languages/Nederlands +++ b/rtdata/languages/Nederlands @@ -2076,6 +2076,7 @@ ZOOMPANEL_ZOOMOUT;Zoom uit\nSneltoets: - !HISTORY_MSG_SOFTLIGHT_ENABLED;Soft light !HISTORY_MSG_SOFTLIGHT_STRENGTH;Soft light - Strength !HISTORY_MSG_TM_FATTAL_ANCHOR;DRC - Anchor +!HISTORY_MSG_TRANS_Method;Geometry - Method !ICCPROFCREATOR_COPYRIGHT;Copyright: !ICCPROFCREATOR_COPYRIGHT_RESET_TOOLTIP;Reset to the default copyright, granted to "RawTherapee, CC0" !ICCPROFCREATOR_CUSTOM;Custom @@ -2256,6 +2257,8 @@ ZOOMPANEL_ZOOMOUT;Zoom uit\nSneltoets: - !TP_ICM_WORKING_TRC_NONE;None !TP_ICM_WORKING_TRC_SLOPE;Slope !TP_ICM_WORKING_TRC_TOOLTIP;Only for built-in profiles. +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_LCPFILE;LCP file !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected diff --git a/rtdata/languages/Polish b/rtdata/languages/Polish index 4e5d950fc..06a5136d6 100644 --- a/rtdata/languages/Polish +++ b/rtdata/languages/Polish @@ -7,13 +7,23 @@ #07 2012-04-02 DrSlony #08 2013-05-21 DrSlony #09 2014-10-16 DrSlony +#10 2020-02-02 Bartłomiej Wiśniowski +#11 2020-02-02 Bartłomiej Wiśniowski +#12 2020-02-15 Bartłomiej Wiśniowski +#13 2020-02-17 Bartłomiej Wiśniowski ABOUT_TAB_BUILD;Wersja ABOUT_TAB_CREDITS;Zasługi ABOUT_TAB_LICENSE;Licencja ABOUT_TAB_RELEASENOTES;Notatki eksploatacyjne ABOUT_TAB_SPLASH;Ekran powitalny +ADJUSTER_RESET_TO_DEFAULT;Klik - przywróć wartość domyślną.\nCtrl+klik - przywróć wartość początkową. BATCH_PROCESSING;Przetwarzanie wsadowe +CURVEEDITOR_AXIS_IN;We: +CURVEEDITOR_AXIS_LEFT_TAN;Lw: +CURVEEDITOR_AXIS_OUT;Wy: +CURVEEDITOR_AXIS_RIGHT_TAN;Pw: +CURVEEDITOR_CATMULLROM;Elastyczny CURVEEDITOR_CURVE;Krzywa CURVEEDITOR_CURVES;Krzywe CURVEEDITOR_CUSTOM;Własna @@ -34,6 +44,16 @@ CURVEEDITOR_TOOLTIPPASTE;Wstaw krzywą ze schowka CURVEEDITOR_TOOLTIPSAVE;Zapisz krzywą CURVEEDITOR_TYPE;Typ: DIRBROWSER_FOLDERS;Katalogi +DONT_SHOW_AGAIN;Nie pokazuj tej wiadomości ponownie. +DYNPROFILEEDITOR_DELETE;Usuń +DYNPROFILEEDITOR_EDIT;Edytuj +DYNPROFILEEDITOR_IMGTYPE_ANY;Każdy +DYNPROFILEEDITOR_IMGTYPE_HDR;HDR +DYNPROFILEEDITOR_IMGTYPE_STD;Standardowy +DYNPROFILEEDITOR_MOVE_DOWN;Przesuń w dół +DYNPROFILEEDITOR_MOVE_UP;Przesuń w górę +DYNPROFILEEDITOR_NEW;Nowy +DYNPROFILEEDITOR_PROFILE;Profil przetwarzania EDITWINDOW_TITLE;Edytor obrazu EDIT_OBJECT_TOOLTIP;Wyświetla widżet na podglądzie który ułatwia ustawienie narzędzia. EDIT_PIPETTE_TOOLTIP;Aby dodać punkt do krzywej należy trzymac wciśnięty klawisz Ctrl podczas kliknięcia lewym guzikiem myszki na danym obszarze głównego podglądu.\nAby zmienic ustawienie już istniejącego punktu, należy trzymać wduszony klawisz Ctrl podczas kliknięcia lewym guzikiem myszki na danym obszarze głównego podglądu, następnie należy puścić klawisz Ctrl (chyba że chodzi nam o bardzo precyzyjne ustawienie dzieki spowolnieniu jakie trzymanie klawisza Ctrl nam daje) i podczas trzymania lewego guzika myszki należy myszką ruszać w pionie aby odpowiednio manipulować punktem w pionie. @@ -42,6 +62,7 @@ EXIFFILTER_CAMERA;Aparat EXIFFILTER_EXPOSURECOMPENSATION;Korekcja ekspozycji (EV) EXIFFILTER_FILETYPE;Typ pliku EXIFFILTER_FOCALLEN;Wartość ogniskowej +EXIFFILTER_IMAGETYPE;Typ obrazu EXIFFILTER_ISO;ISO EXIFFILTER_LENS;Obiektyw EXIFFILTER_METADATAFILTER;Włącz filtry metadanych @@ -59,6 +80,7 @@ EXIFPANEL_RESET;Przywróć EXIFPANEL_RESETALL;Przywróć wszystkie EXIFPANEL_RESETALLHINT;Przywraca orginalne wartości etykiet EXIFPANEL_RESETHINT;Przywraca orginalne wartości wybranych etykiet +EXIFPANEL_SHOWALL;Pokaż wszystkie EXIFPANEL_SUBDIRECTORY;Podkatalog EXPORT_BYPASS_ALL;Zaznacz / Odznacz wszystkie EXPORT_BYPASS_DEFRINGE;Pomiń usuwanie widma @@ -90,6 +112,8 @@ FILEBROWSER_AUTODARKFRAME;Automatyczne użycie czarnej klatki FILEBROWSER_AUTOFLATFIELD;Automatyczne użycie klatki typu puste pole FILEBROWSER_BROWSEPATHHINT;Umożliwia przeglądanie wprowadzonej ścieżki\nCtrl-o zaznaczenie\nEnter, Ctrl-Enter (w menedżerze plików) przeglądanie\nSkróty:\n ~ - katalog domowy użytkownika\n ! - katalog z obrazami użytkownia FILEBROWSER_CACHE;Pamięć podręczna +FILEBROWSER_CACHECLEARFROMFULL;Wyczyść wszystkie profile +FILEBROWSER_CACHECLEARFROMPARTIAL;Wyczyść wszystkie, oprócz znajdujących się w pamięci podręcznej FILEBROWSER_CLEARPROFILE;Wyczyść profil FILEBROWSER_COLORLABEL_TOOLTIP;Kolorowe etykiety\n\nUżyj za pomocą rozwijanej listy lub skrótów:\nShift-Ctrl-0 No Color\nShift-Ctrl-1 Czerwona\nShift-Ctrl-2 Żółta\nShift-Ctrl-3 Zielona\nShift-Ctrl-4 Niebieska\nShift-Ctrl-5 Purpurowa FILEBROWSER_COPYPROFILE;Kopiuj profil @@ -97,6 +121,7 @@ FILEBROWSER_CURRENT_NAME;Obecna nazwa: FILEBROWSER_DARKFRAME;Czarna klatka FILEBROWSER_DELETEDIALOG_HEADER;Potwierdzenie usunięcia pliku FILEBROWSER_EMPTYTRASH;Wyczyść kosz +FILEBROWSER_EMPTYTRASHHINT;Usuwa na zawsze pliki znajdujące się w koszu. FILEBROWSER_EXTPROGMENU;Otwórz za pomocą FILEBROWSER_FLATFIELD;Puste pole FILEBROWSER_MOVETODARKFDIR;Przenieś do katalogu zawierającego czarne klatki @@ -130,6 +155,7 @@ FILEBROWSER_POPUPRANK2;Ocena 2 ** FILEBROWSER_POPUPRANK3;Ocena 3 *** FILEBROWSER_POPUPRANK4;Ocena 4 **** FILEBROWSER_POPUPRANK5;Ocena 5 ***** +FILEBROWSER_POPUPREMOVE;Usuń na zawsze FILEBROWSER_POPUPRENAME;Zmień nazwę FILEBROWSER_POPUPSELECTALL;Zaznacz wszystkie FILEBROWSER_POPUPTRASH;Przenieś do kosza @@ -144,6 +170,7 @@ FILEBROWSER_RANK3_TOOLTIP;Oceń 3 *\nSkrót: Shift-3 FILEBROWSER_RANK4_TOOLTIP;Oceń 4 *\nSkrót: Shift-4 FILEBROWSER_RANK5_TOOLTIP;Oceń 5 *\nSkrót: Shift-5 FILEBROWSER_RENAMEDLGLABEL;Zmień nazwę pliku +FILEBROWSER_RESETDEFAULTPROFILE;Przywróć domyślne FILEBROWSER_SELECTDARKFRAME;Wybierz czarną klatkę... FILEBROWSER_SELECTFLATFIELD;Wybierz puste pole... FILEBROWSER_SHOWCOLORLABEL1HINT;Pokazuje zdjęcia z czerwoną etykietą.\nSkrót: Alt-1 @@ -155,6 +182,7 @@ FILEBROWSER_SHOWDIRHINT;Wyłącza wyszstkie filtry.\nSkrót: d FILEBROWSER_SHOWEDITEDHINT;Pokazuje edytowane zdjęcia.\nSkrót: 7 FILEBROWSER_SHOWEDITEDNOTHINT;Pokazuje nieedytowane zdjęcia.\nSkrót: 6 FILEBROWSER_SHOWEXIFINFO;Pokaż dane Exif.\n\nSkróty:\ni - Tryb wielu zakładek,\nAlt-i - Tryb jednej zakładki. +FILEBROWSER_SHOWNOTTRASHHINT;Pokazuj tylko obrazy które nie znajdują się w koszu. FILEBROWSER_SHOWRANK1HINT;Pokazuje zdjęcia ocenione na 1 gwiazdkę.\nSkrót: 1 FILEBROWSER_SHOWRANK2HINT;Pokazuje zdjęcia ocenione na 2 gwiazdki.\nSkrót: 2 FILEBROWSER_SHOWRANK3HINT;Pokazuje zdjęcia ocenione na 3 gwiazdki.\nSkrót: 3 @@ -169,24 +197,39 @@ FILEBROWSER_THUMBSIZE;Rozmiar minaturek FILEBROWSER_UNRANK_TOOLTIP;Usuń ocenę.\nSkrót: Shift-0 FILEBROWSER_ZOOMINHINT;Zwiększa rozmiar miniaturek.\n\nSkróty:\n+ - Tryb wielu zakładek,\nAlt-+ - Tryb pojedyńczej zakładki. FILEBROWSER_ZOOMOUTHINT;Zmniejsza rozmiar miniaturek.\n\nSkróty:\n- - Tryb wielu zakładek,\nAlt-- - Tryb pojedyńczej zakładki. +FILECHOOSER_FILTER_ANY;Wszystkie pliki +FILECHOOSER_FILTER_COLPROF;Profile kolorów (*.icc) +FILECHOOSER_FILTER_CURVE;Pliki krzywych +FILECHOOSER_FILTER_LCP;Profile korekcyjne obiektywów +FILECHOOSER_FILTER_PP;Profile przetwarzania +FILECHOOSER_FILTER_SAME;Taki sam format jak aktualnego zdjęcia +FILECHOOSER_FILTER_TIFF;Pliki TIFF GENERAL_ABOUT;O programie GENERAL_AFTER;Po +GENERAL_APPLY;Zastosuj +GENERAL_ASIMAGE;Jako obraz GENERAL_AUTO;Automatyczne GENERAL_BEFORE;Przed GENERAL_CANCEL;Anuluj GENERAL_CLOSE;Zamknij +GENERAL_CURRENT;Obecny GENERAL_DISABLE;Wyłącz GENERAL_DISABLED;Wyłączone GENERAL_ENABLE;Włącz GENERAL_ENABLED;Włączone GENERAL_FILE;Plik +GENERAL_HELP;Pomoc GENERAL_LANDSCAPE;Poziomo GENERAL_NA;nd. GENERAL_NO;Nie GENERAL_NONE;Żaden GENERAL_OK;OK +GENERAL_OPEN;Otwórz GENERAL_PORTRAIT;Pionowo +GENERAL_RESET;Resetuj GENERAL_SAVE;Zapisz +GENERAL_SAVE_AS;Zapisz jako... +GENERAL_SLIDER;Suwak GENERAL_UNCHANGED;(Niezmienione) GENERAL_WARNING;Uwaga HISTOGRAM_TOOLTIP_B;Pokaż/Ukryj histogram błękitów. @@ -364,12 +407,14 @@ HISTORY_MSG_162;Tone Mapping HISTORY_MSG_163;Krzywe RGB - Czerwona HISTORY_MSG_164;Krzywe RGB - Zielona HISTORY_MSG_165;Krzywe RGB - Niebieska +HISTORY_MSG_166;Ekspozycja - Reset HISTORY_MSG_167;Algorytm demozaikowania HISTORY_MSG_168;L*a*b* - Krzywa CC HISTORY_MSG_169;L*a*b* - Krzywa CH HISTORY_MSG_170;Jaskrawość - Krzywa HH HISTORY_MSG_171;L*a*b* - Krzywa LC HISTORY_MSG_172;L*a*b* - Ogranicz LC +HISTORY_MSG_173;NR - Odzyskiwanie detali HISTORY_MSG_174;CIECAM02 HISTORY_MSG_175;CAM02 - Adaptacja CAT02 HISTORY_MSG_176;CAM02 - Otoczenie @@ -399,6 +444,7 @@ HISTORY_MSG_199;CAM02 - Histogramy wyjściowe HISTORY_MSG_200;CAMO2 - Tone mapping HISTORY_MSG_201;RS - Chrominancja - R&G HISTORY_MSG_202;RS - Chrominancja - B&Y +HISTORY_MSG_203;NR - Przestrzeń kolorów HISTORY_MSG_204;Kroki poprawy LMMSE HISTORY_MSG_205;CAM02 - Gorące/uszkodzone px HISTORY_MSG_206;CAT02 - Auto luminancja sceny @@ -448,6 +494,7 @@ HISTORY_MSG_252;KwgPS - Odcienie skóry HISTORY_MSG_253;KwgPS - Redukcja błędów HISTORY_MSG_254;KwgPS - Odcienie skóry HISTORY_MSG_255;RS - Filtr mediana +HISTORY_MSG_256;NR - Mediana - Typ HISTORY_MSG_257;Koloryzacja HISTORY_MSG_258;Koloryzacja - Kolor HISTORY_MSG_259;Koloryzacja - Przezroczystość @@ -487,35 +534,211 @@ HISTORY_MSG_293;Symulacja Kliszy HISTORY_MSG_294;Symulacja Kliszy - Siła HISTORY_MSG_295;Symulacja Kliszy - Klisza HISTORY_MSG_296;RS - Modulacja luminancji +HISTORY_MSG_297;NR - Tryb HISTORY_MSG_298;Filtrowanie martwych pikseli +HISTORY_MSG_299;NR - Krzywa chrominancji +HISTORY_MSG_300;- +HISTORY_MSG_301;NR - Kontrola luminancji +HISTORY_MSG_302;NR - Metoda chrominancji +HISTORY_MSG_303;NR - Metoda chrominancji +HISTORY_MSG_304;W - Poziomy kontrastu +HISTORY_MSG_306;W - Proces +HISTORY_MSG_307;W - Proces +HISTORY_MSG_308;W - Kierunek procesu +HISTORY_MSG_309;W - ES - Detale +HISTORY_MSG_312;W - Residual - Próg cieni +HISTORY_MSG_315;W - Residual - Kontrast +HISTORY_MSG_317;W - Gamut - Odcień skóry +HISTORY_MSG_318;W - Kontrast - Poziom podświetleń +HISTORY_MSG_319;W - Kontrast - Zakres podświetleń +HISTORY_MSG_320;W - Kontrast - Zakres cieni +HISTORY_MSG_321;W - Kontrast - Poziom cieni +HISTORY_MSG_322;W - Gamut - Unikaj przesunięcia kolorów +HISTORY_MSG_323;W - ES - Kontrast lokalny +HISTORY_MSG_324;W - Chroma - Pastelowe +HISTORY_MSG_325;W - Chroma - Nasycone +HISTORY_MSG_326;W - Chroma - Metoda +HISTORY_MSG_333;W - Residual - Cienie +HISTORY_MSG_334;W - Residual - Chrominancja +HISTORY_MSG_335;W - Residual - Podświetlenia +HISTORY_MSG_336;W - Residual - Próg podświetleń +HISTORY_MSG_337;W - Residual - Odcień nieba +HISTORY_MSG_338;W - ES - Promień +HISTORY_MSG_339;W - ES - Siła +HISTORY_MSG_340;W - Siła +HISTORY_MSG_343;W - Poziomy chrominancji +HISTORY_MSG_345;W - ES - Kontrast lokalny +HISTORY_MSG_346;W - ES - Tryb kontrastu lokalnego +HISTORY_MSG_347;W - Odszumianie - Poziom 1 +HISTORY_MSG_348;W - Odszumianie - Poziom 2 +HISTORY_MSG_349;W - Odszumianie - Poziom 3 +HISTORY_MSG_352;W - Tło +HISTORY_MSG_355;W - ES - Niski próg +HISTORY_MSG_356;W - ES - Wysoki próg +HISTORY_MSG_359;Hot/Dead - Próg +HISTORY_MSG_362;W - Residual - Metoda kompresji +HISTORY_MSG_363;W - Residual - Siła kompersji +HISTORY_MSG_364;W - Final - Balans kontrastu +HISTORY_MSG_368;W - Final - Balans kontrastu +HISTORY_MSG_369;W - Final - Metoda balansu +HISTORY_MSG_370;W - Final - Krzywa lokalnego kontrastu +HISTORY_MSG_372;PRS USM - Promień +HISTORY_MSG_373;PRS USM - Ilość +HISTORY_MSG_374;PRS USM - Próg +HISTORY_MSG_376;PRS USM - Promień wykrywania krawędzi +HISTORY_MSG_377;PRS USM - Tolerancja krawędzi +HISTORY_MSG_380;PRS - Metoda +HISTORY_MSG_381;PRS RLD - Promień +HISTORY_MSG_382;PRS RLD - Ilość +HISTORY_MSG_384;PRS RLD - Iteracje +HISTORY_MSG_385;W - Residual - Balans kolorów +HISTORY_MSG_392;W - Residual - Balans kolorów +HISTORY_MSG_405;W - Odszumianie - Poziom 4 +HISTORY_MSG_407;Retinex - Metoda +HISTORY_MSG_408;Retinex - Promień +HISTORY_MSG_409;Retinex - Contrast +HISTORY_MSG_410;Retinex - Przesunięcie +HISTORY_MSG_411;Retinex - Siła +HISTORY_MSG_413;Retinex - Kontrast +HISTORY_MSG_418;Retinex - Próg +HISTORY_MSG_419;Retinex - Przestrzeń kolorów +HISTORY_MSG_421;Retinex - Gamma +HISTORY_MSG_422;Retinex - Gamma +HISTORY_MSG_426;Retinex - Wyrównywanie odcieni +HISTORY_MSG_429;Retinex - Iteracje +HISTORY_MSG_432;Retinex - M - Podświetlenia +HISTORY_MSG_434;Retinex - M - Cienie +HISTORY_MSG_436;Retinex - M - Promień +HISTORY_MSG_437;Retinex - M - Metoda +HISTORY_MSG_438;Retinex - M - Wyrównywanie +HISTORY_MSG_439;Retinex - Proces +HISTORY_MSG_440;CbDL - Metoda +HISTORY_MSG_442;Retinex - Skala +HISTORY_MSG_449;PS - Adaptacja ISO +HISTORY_MSG_452;PS - Pokaż ruch +HISTORY_MSG_453;PS - Pokaż tylko maskę +HISTORY_MSG_465;PS - Promień rozmycia +HISTORY_MSG_468;PS - Wypełnij dziury +HISTORY_MSG_471;PS - Korekcja ruchu +HISTORY_MSG_472;PS - Miękkie przejścia +HISTORY_MSG_474;PS - Wyrównaj +HISTORY_MSG_475;PS - Wyrównaj kanał +HISTORY_MSG_485;Korekcja obiektywu +HISTORY_MSG_486;Korekcja obiektywu - Aparat +HISTORY_MSG_487;Korekcja obiektywu - Obiektyw +HISTORY_MSG_489;DRC - Detal +HISTORY_MSG_490;DRC - Ilość +HISTORY_MSG_491;Balans bieli +HISTORY_MSG_492;Krzywe RGB +HISTORY_MSG_CLAMPOOG;Ucinaj kolory spoza zakresu +HISTORY_MSG_COLORTONING_LABGRID_VALUE;CT - Korekcja koloru +HISTORY_MSG_COLORTONING_LABREGION_AB;CT - Korekcja koloru +HISTORY_MSG_COLORTONING_LABREGION_CHANNEL;CT - Kanał +HISTORY_MSG_COLORTONING_LABREGION_SATURATION;CT - Saturacja +HISTORY_MSG_DEHAZE_DEPTH;Usuwanie mgły - Głębia +HISTORY_MSG_DEHAZE_ENABLED;Usuwanie mgły +HISTORY_MSG_DEHAZE_LUMINANCE;Usuwanie mgły - Tylko luminancja +HISTORY_MSG_DEHAZE_SHOW_DEPTH_MAP;Usuwanie mgły - Pokaż mapę głębokości +HISTORY_MSG_DEHAZE_STRENGTH;Usuwanie mgły - Siła +HISTORY_MSG_LOCALCONTRAST_AMOUNT;Kontrast lokalny - Ilość +HISTORY_MSG_LOCALCONTRAST_DARKNESS;Kontrast lokalny - Ciemne miejsca +HISTORY_MSG_LOCALCONTRAST_ENABLED;Kontrast lokalny +HISTORY_MSG_LOCALCONTRAST_LIGHTNESS;Kontrast lokalny - Jasne miejsca +HISTORY_MSG_LOCALCONTRAST_RADIUS;Kontrast lokalny - Promień +HISTORY_MSG_MICROCONTRAST_CONTRAST;Mikrokontrast - Próg kontrastu +HISTORY_MSG_PDSHARPEN_AUTO_CONTRAST;CS - Automatyczny próg +HISTORY_MSG_PDSHARPEN_AUTO_RADIUS;CS - Automatyczny promień +HISTORY_MSG_PDSHARPEN_CHECKITER;CS - Automatycznie limituj iteracje +HISTORY_MSG_PDSHARPEN_CONTRAST;CS - Próg kontrastu +HISTORY_MSG_PDSHARPEN_ITERATIONS;CS - Iteracje +HISTORY_MSG_PDSHARPEN_RADIUS;CS - Promień +HISTORY_MSG_PRSHARPEN_CONTRAST;PRS - Próg kontrastu +HISTORY_MSG_RAWCACORR_AUTOIT;Korekcja aberracji chromatycznej - Iteracje +HISTORY_MSG_RAWCACORR_COLORSHIFT;Korekcja aberracji chromatycznej - Unikaj przesunięcia kolorów +HISTORY_MSG_SHARPENING_BLUR;Wyostrzanie - Promień rozmycia +HISTORY_MSG_SHARPENING_CONTRAST;Wyostrzanie - Próg kontrastu +HISTORY_MSG_SH_COLORSPACE;S/H - Przestrzeń kolorów +HISTORY_MSG_SOFTLIGHT_ENABLED;Miękkie światło +HISTORY_MSG_SOFTLIGHT_STRENGTH;Miękkie światło - Siła +HISTORY_MSG_TRANS_Method;Geometria - Metoda HISTORY_NEWSNAPSHOT;Nowa migawka HISTORY_NEWSNAPSHOT_TOOLTIP;Skrót: Alt-s HISTORY_SNAPSHOT;Migawka HISTORY_SNAPSHOTS;Migawki +ICCPROFCREATOR_COPYRIGHT;Prawa autorskie: +ICCPROFCREATOR_COPYRIGHT_RESET_TOOLTIP;Przywróć prawa autorskie do domyślnych, przyznanych dla "RawTherapee, CC0" +ICCPROFCREATOR_CUSTOM;Własny +ICCPROFCREATOR_DESCRIPTION;Opis: +ICCPROFCREATOR_GAMMA;Gamma +ICCPROFCREATOR_ICCVERSION;Wersja ICC: +ICCPROFCREATOR_ILL_41;D41 +ICCPROFCREATOR_ILL_50;D50 +ICCPROFCREATOR_ILL_55;D55 +ICCPROFCREATOR_ILL_60;D60 +ICCPROFCREATOR_ILL_65;D65 +ICCPROFCREATOR_ILL_80;D80 +ICCPROFCREATOR_ILL_DEF;Domyślne +ICCPROFCREATOR_ILL_INC;StdA 2856K +ICCPROFCREATOR_PRIM_ACESP0;ACES AP0 +ICCPROFCREATOR_PRIM_ACESP1;ACES AP1 +ICCPROFCREATOR_PRIM_ADOBE;Adobe RGB (1998) +ICCPROFCREATOR_PRIM_BEST;BestRGB +ICCPROFCREATOR_PRIM_BETA;BetaRGB +ICCPROFCREATOR_PRIM_BLUX;Niebieski X +ICCPROFCREATOR_PRIM_BLUY;Niebieski Y +ICCPROFCREATOR_PRIM_BRUCE;BruceRGB +ICCPROFCREATOR_PRIM_GREX;Zielony X +ICCPROFCREATOR_PRIM_GREY;Zielony Y +ICCPROFCREATOR_PRIM_PROPH;Prophoto +ICCPROFCREATOR_PRIM_REC2020;Rec2020 +ICCPROFCREATOR_PRIM_REDX;Czerwony X +ICCPROFCREATOR_PRIM_REDY;Czerwony Y +ICCPROFCREATOR_PRIM_SRGB;sRGB +ICCPROFCREATOR_PRIM_WIDEG;Szeroka gama +ICCPROFCREATOR_PROF_V2;ICC v2 +ICCPROFCREATOR_PROF_V4;ICC v4 +ICCPROFCREATOR_SAVEDIALOG_TITLE;Zapisz profil ICC jako... +ICCPROFCREATOR_SLOPE;Nachylenie +ICCPROFCREATOR_TRC_PRESET;Krzywa odpowiedzi tonalnej: IPTCPANEL_CATEGORY;Kategoria IPTCPANEL_CITY;Miasto +IPTCPANEL_CITYHINT;Wprowadź nazwę miasta uwiecznionego na zdjęciu. IPTCPANEL_COPYHINT;Kopiuje ustawienia IPTC do schowka +IPTCPANEL_COPYRIGHT;Informacja o prawach autorskich +IPTCPANEL_COPYRIGHTHINT;Wprowadź informację o aktualnym posiadaczu praw autorskich np. ©2008 Jane Doe. IPTCPANEL_COUNTRY;Kraj +IPTCPANEL_COUNTRYHINT;Wprowadź nazwę kraju uwiecznionego na tym obrazie. +IPTCPANEL_CREATOR;Twórca +IPTCPANEL_CREATORHINT;Wprowadź nazwę twórcy obrazu. IPTCPANEL_CREDIT;Zasługa IPTCPANEL_CREDITHINT;Identyfikuje dostawcę zdjęcia, niekoniecznie właściciela lub autora (Credit). IPTCPANEL_DATECREATED;Data utworzenia +IPTCPANEL_DATECREATEDHINT;Wprowadź datę zrobienia zdjęcia. +IPTCPANEL_DESCRIPTION;Opis +IPTCPANEL_DESCRIPTIONWRITER;Twórca opisu IPTCPANEL_EMBEDDED;Osadzony IPTCPANEL_EMBEDDEDHINT;Resetuje dane IPTC do domyślnych ustawień osadzonych w orginalnym zdjęciu IPTCPANEL_HEADLINE;Nagłówek IPTCPANEL_INSTRUCTIONS;Instrukcje IPTCPANEL_KEYWORDS;Słowa kluczowe IPTCPANEL_PASTEHINT;Wstawia ustawienia IPTC ze schowka +IPTCPANEL_PROVINCE;Województwo lub stan IPTCPANEL_RESET;Reset IPTCPANEL_RESETHINT;Resetuje do domyślnych ustawień profilu IPTCPANEL_SOURCE;Źródło +IPTCPANEL_SUPPCATEGORIES;Dodatkowe kategorie IPTCPANEL_TITLE;Tytuł +IPTCPANEL_TRANSREFERENCE;Numer pracy +IPTCPANEL_TRANSREFERENCEHINT;!IPTCPANEL_TRANSREFERENCEHINT;Wprowadź numer pracy, który umożliwi śledzenie obrazu. MAIN_BUTTON_FULLSCREEN;Pełen ekran +MAIN_BUTTON_ICCPROFCREATOR;Kreator profili ICC MAIN_BUTTON_NAVNEXT_TOOLTIP;Przejdź do następnego zdjęcia względem zdjęcia otwartego w Edytorze.\nSkrót: Shift-F4\n\nAby przejść do następnego zdjęcia względem miniaturki wybranej w Nawigatorze Zdjęć:\nSkrót: F4 MAIN_BUTTON_NAVPREV_TOOLTIP;Przejdź do poprzedniego zdjęcia wzgledem zdjęcia otwartego w Edytorze.\nSkrót: Shift-F3 \n\nAby przejść do poprzedniego zdjęcia względem miniaturki wybranej w Nawigatorze Zdjęć:\nSkrót: F3 MAIN_BUTTON_NAVSYNC_TOOLTIP;Synchronizuj Nawigator Zdjęć z Edytorem aby ukazać miniaturkę obecnie otwartego zdjęcia, oraz usuń filtry w Nawigatorze Zdjęć.\nSkrót: x\n\nJak wyżej, ale bez usuwania filtrów:\nSkrót: y\n(Miniaturka otwartego zdjęcia nie zostanie wyświetlona jesli filtr ją ukrywa). MAIN_BUTTON_PREFERENCES;Ustawienia MAIN_BUTTON_PUTTOQUEUE_TOOLTIP;Dodaj bieżące zdjęcie do kolejki przetwarzania Ctrl+B MAIN_BUTTON_SAVE_TOOLTIP;Zapisz bieżące zdjęcieCtrl+S +MAIN_BUTTON_SENDTOEDITOR;Edytuj obraz w zewnętrznym edytorze MAIN_BUTTON_SENDTOEDITOR_TOOLTIP;Otwórz bieżące zdjęcie w zewnętrznym edytorze.\nSkrót: Ctrl+e MAIN_BUTTON_SHOWHIDESIDEPANELS_TOOLTIP;Pokaż/Ukryj wszystkie panele boczne.\nSkrót: m MAIN_BUTTON_UNFULLSCREEN;Zwolnij ekran @@ -525,6 +748,7 @@ MAIN_FRAME_FILEBROWSER;Przeglądarka plików MAIN_FRAME_FILEBROWSER_TOOLTIP; Przeglądarka plików.\nSkrót: Ctrl-F2 MAIN_FRAME_PLACES;Miejsca MAIN_FRAME_PLACES_ADD;Dodaj +MAIN_FRAME_PLACES_DEL;Usuń MAIN_FRAME_QUEUE;Kolejka MAIN_FRAME_QUEUE_TOOLTIP;Przetwarzanie wsadowe\nSkrót: Ctrl-F3 MAIN_FRAME_RECENT;Ostatnio używane foldery @@ -540,7 +764,10 @@ MAIN_MSG_OPERATIONCANCELLED;Operację anulowano MAIN_MSG_PATHDOESNTEXIST;Ścieżka\n\n%1\n\nnie istnieje. Wybierz przawidłową ścieżkę w Ustawieniach. MAIN_MSG_QOVERWRITE;Zastąpić? MAIN_MSG_SETPATHFIRST;Aby użyć tej funkcji należy wpierw wybrać odpowiednią ścieżkę docelową w Ustawieniach! +MAIN_MSG_TOOMANYOPENEDITORS;Za duża liczba otwartych edytorów.\nZamknij edytor aby kontynuować. MAIN_MSG_WRITEFAILED;Zapis nie powiódł się:\n\n"%1"\n\nUpewnij się, że folder istnieje oraz że można do niego zapisywać. +MAIN_TAB_ADVANCED;Zaawansowane +MAIN_TAB_ADVANCED_TOOLTIP;Skrót: Alt-a MAIN_TAB_COLOR;Kolor MAIN_TAB_COLOR_TOOLTIP;Skrót: Alt-c MAIN_TAB_DETAIL;Szczegóły @@ -550,7 +777,10 @@ MAIN_TAB_EXIF;Exif MAIN_TAB_EXPORT; Szybki eksport MAIN_TAB_EXPOSURE;Ekspozycja MAIN_TAB_EXPOSURE_TOOLTIP;Skrót: Alt-e +MAIN_TAB_FAVORITES;Ulubione +MAIN_TAB_FAVORITES_TOOLTIP;Skrót: Alt-u MAIN_TAB_FILTER; Filtr +MAIN_TAB_INSPECT; Inspekcja MAIN_TAB_IPTC;IPTC MAIN_TAB_METADATA;Metadane MAIN_TAB_METADATA_TOOLTIP;Skrót: Alt-m @@ -576,6 +806,7 @@ MAIN_TOOLTIP_SHOWHIDERP1;Pokaż/Ukryj prawy panel.\nSkrót: Alt-l MAIN_TOOLTIP_SHOWHIDETP1;Pokaż/Ukryj górny panel.\nSkrót: Shift-l MAIN_TOOLTIP_THRESHOLD;Próg MAIN_TOOLTIP_TOGGLE;Przełącz widok Przed/Po.\nSkrót: Shift-b +MONITOR_PROFILE_SYSTEM;Ustawienia domyślne NAVIGATOR_B;B: NAVIGATOR_G;G: NAVIGATOR_H;H: @@ -588,6 +819,7 @@ NAVIGATOR_S;S: NAVIGATOR_V;V: NAVIGATOR_XY_FULL;Szerokość: %1, Wysokość: %2 NAVIGATOR_XY_NA;x: --, y: -- +PARTIALPASTE_ADVANCEDGROUP;Ustawienia zaawansowane PARTIALPASTE_BASICGROUP;Podstawowe ustawienia PARTIALPASTE_CACORRECTION;Korekcja aberacji chr. PARTIALPASTE_CHANNELMIXER;Mieszacz kanałów @@ -602,6 +834,7 @@ PARTIALPASTE_CROP;Kadrowanie PARTIALPASTE_DARKFRAMEAUTOSELECT;Auto-wybór czarnej klatki PARTIALPASTE_DARKFRAMEFILE;Wybór czarnej klatki PARTIALPASTE_DEFRINGE;Usuwanie widma +PARTIALPASTE_DEHAZE;Usuwanie mgły PARTIALPASTE_DETAILGROUP;Ustawienia szczegółowe PARTIALPASTE_DIALOGLABEL;Częściowe wklejenie profilu przetwarzania PARTIALPASTE_DIRPYRDENOISE;Redukcja szumu @@ -625,6 +858,7 @@ PARTIALPASTE_IPTCINFO;IPTC PARTIALPASTE_LABCURVE;Regulacje L*a*b* PARTIALPASTE_LENSGROUP;Ustawienia związane z obiektywem PARTIALPASTE_LENSPROFILE;Profil korekcji obiektywu LCP +PARTIALPASTE_LOCALCONTRAST;Kontrast lokalny PARTIALPASTE_METAGROUP;Metadane PARTIALPASTE_PCVIGNETTE;Winietowanie PARTIALPASTE_PERSPECTIVE;Perspektywa @@ -642,17 +876,26 @@ PARTIALPASTE_RAW_DMETHOD;Algorytm demozaikowania PARTIALPASTE_RAW_FALSECOLOR;Tłumienie fałszowania koloru PARTIALPASTE_RAW_LMMSEITERATIONS;Kroki poprawy LMMSE PARTIALPASTE_RESIZE;Zmiana rozmiaru +PARTIALPASTE_RETINEX;Retinex PARTIALPASTE_RGBCURVES;Krzywe RGB PARTIALPASTE_ROTATION;Obrót PARTIALPASTE_SHADOWSHIGHLIGHTS;Cienie/Podświetlenia PARTIALPASTE_SHARPENEDGE;Krawędzie PARTIALPASTE_SHARPENING;Wyostrzanie PARTIALPASTE_SHARPENMICRO;Mikrokontrast +PARTIALPASTE_SOFTLIGHT;Miękkie światło +PARTIALPASTE_TM_FATTAL;Kompresja zakresu dynamiki PARTIALPASTE_VIBRANCE;Jaskrawość PARTIALPASTE_VIGNETTING;Korekcja winietowania PARTIALPASTE_WHITEBALANCE;Balans bieli PREFERENCES_ADD;Dodaj +PREFERENCES_APPEARANCE;Wygląd +PREFERENCES_APPEARANCE_COLORPICKERFONT;Czcionka narzędzia do wybierania kolorów +PREFERENCES_APPEARANCE_CROPMASKCOLOR;Kolor maski kadrowania +PREFERENCES_APPEARANCE_MAINFONT;Główny font PREFERENCES_APPEARANCE_NAVGUIDECOLOR;Kolor ramki Nawigatora +PREFERENCES_APPEARANCE_PSEUDOHIDPI; Tryb pseudo-HiDPI +PREFERENCES_APPEARANCE_THEME;Motyw graficzny PREFERENCES_APPLNEXTSTARTUP;wymaga ponownego uruchomienia PREFERENCES_AUTOMONPROFILE;Automatycznie użyj systemowego profilu monitora PREFERENCES_BATCH_PROCESSING;Przetwarzanie wsadowe @@ -661,11 +904,33 @@ PREFERENCES_BEHADDALLHINT;Ustaw wszystkie narzędzia w tryb Dodaj.\nZmian PREFERENCES_BEHAVIOR;Zachowanie PREFERENCES_BEHSETALL;'Ustaw' wszystkie PREFERENCES_BEHSETALLHINT;Ustaw wszystkie narzędzia w tryb Ustaw.\nZmiany parametrów w panelu edycji zbiorczej zostaną traktowane jako absolutne, nie biorąc pod uwagę poprzednich wartości. +PREFERENCES_CACHECLEAR;Wyczyść +PREFERENCES_CACHECLEAR_ALL;Usuń wszystkie pliki z pamięci podręcznej: +PREFERENCES_CACHECLEAR_ONLYPROFILES;Usuń wszystkie profile przetwarzania z pamięci podręcznej: PREFERENCES_CACHEMAXENTRIES;Maksymalna liczba wpisów w pamięci podręcznej PREFERENCES_CACHEOPTS;Opcje pamięci podręcznej PREFERENCES_CACHETHUMBHEIGHT;Maksymalna wysokość miniatury +PREFERENCES_CHUNKSIZES;Liczba kafelków na wątek +PREFERENCES_CHUNKSIZE_RAW_AMAZE;Demozaikowanie AMaZE +PREFERENCES_CHUNKSIZE_RAW_CA;Korekcja aberracji chromatycznej +PREFERENCES_CHUNKSIZE_RAW_RCD;Demozaikowanie RCD +PREFERENCES_CHUNKSIZE_RAW_XT;Demozaikowanie Xtrans +PREFERENCES_CHUNKSIZE_RGB;Przetwarzanie RGB PREFERENCES_CLIPPINGIND;Pokazywanie obciętych prześwietleń/cieni +PREFERENCES_CLUTSCACHE;Cache HaldCLUT PREFERENCES_CLUTSDIR;Folder obrazów HaldCLUT +PREFERENCES_CMMBPC;Kompensacja punktu czerni +PREFERENCES_CROP;Kadrowanie +PREFERENCES_CROP_AUTO_FIT;Automatycznie przybliż aby dopasować do skadrowanego obrazu +PREFERENCES_CROP_GUIDES;Zawsze pokazuj ramkę kadrowania +PREFERENCES_CROP_GUIDES_FRAME;Ramka +PREFERENCES_CROP_GUIDES_FULL;Oryginał +PREFERENCES_CROP_GUIDES_NONE;Brak +PREFERENCES_CURVEBBOXPOS;Położenie przycisków kopiuj oraz wklej krzywą +PREFERENCES_CURVEBBOXPOS_ABOVE;Powyżej +PREFERENCES_CURVEBBOXPOS_BELOW;Poniżej +PREFERENCES_CURVEBBOXPOS_LEFT;Z lewej +PREFERENCES_CURVEBBOXPOS_RIGHT;Z prawej PREFERENCES_CUSTPROFBUILD;Zewnętrzny kreator profilów przetwarzania PREFERENCES_CUSTPROFBUILDHINT;Plik wykonywalny (lub skrypt) uruchamiany kiedy trzeba wygenerować profil przetwarzania dla zdjęcia.\n\nScieżka pliku nośnego (w stylu *.ini czyli sekcje i klucze/parametry) występuje jako parametr wiersza poleceń. Plik ten zawiera przeróżne parametry oraz dane Exif dzięki którym odpowiedni program bądź skrypt może wygenerować plik PP3 według reguł.\n\nUWAGA: Twoją odpowiedzialnością jest prawidłowe użycie cudzysłowiów w przypadku ścieżek zawierających spacje i znaki specjalne. PREFERENCES_CUSTPROFBUILDKEYFORMAT;Rodzaj kluczy @@ -678,14 +943,17 @@ PREFERENCES_DARKFRAMETEMPLATES;szablonów(ny) PREFERENCES_DATEFORMAT;Format daty PREFERENCES_DATEFORMATHINT;Dozwolone są następujące kody formatujące:\n%y - rok\n%m - miesiąc\n%d - dzień\n\nNa przykład według standardu ISO 8601 format daty wygląda następująco:\n%y-%m-%d PREFERENCES_DIRDARKFRAMES;Katalog z czarnymi klatkami +PREFERENCES_DIRECTORIES;Katalogi PREFERENCES_DIRHOME;Katalog domowy PREFERENCES_DIRLAST;Ostatnio odwiedzony katalog PREFERENCES_DIROTHER;Inny PREFERENCES_DIRSELECTDLG;Wybierz katalog z obrazami po uruchomieniu... PREFERENCES_DIRSOFTWARE;Katalog instalacyjny +PREFERENCES_EDITORCMDLINE;Własny wiersz poleceń PREFERENCES_EDITORLAYOUT;Układ edytora PREFERENCES_EXTERNALEDITOR;Zewnętrzny edytor PREFERENCES_FBROWSEROPTS;Opcje przeglądarki plików +PREFERENCES_FILEBROWSERTOOLBARSINGLEROW;Zwiń paski w przeglądarce plików PREFERENCES_FLATFIELDFOUND;Znaleziono PREFERENCES_FLATFIELDSDIR;Katalog z pustymi polami PREFERENCES_FLATFIELDSHOTS;kadry @@ -698,36 +966,57 @@ PREFERENCES_HISTOGRAM_TOOLTIP;Jeśli opcja jest włączona profil roboczy jest u PREFERENCES_HLTHRESHOLD;Próg dla prześwietleń PREFERENCES_ICCDIR;Katalog z profilami koloru ICC PREFERENCES_IMPROCPARAMS;Domyślne parametry przetwarzania obrazu +PREFERENCES_INSPECT_LABEL;Inspekcja +PREFERENCES_INSPECT_MAXBUFFERS_LABEL;Maksymalna liczba obrazów w pamięci podręcznej PREFERENCES_INTENT_ABSOLUTE;Absolutnie kolorymetryczny PREFERENCES_INTENT_PERCEPTUAL;Percepcyjny PREFERENCES_INTENT_RELATIVE;Względnie kolorymetryczny PREFERENCES_INTENT_SATURATION;Nasyceniowy PREFERENCES_INTERNALTHUMBIFUNTOUCHED;Pokaż osadzoną miniaturę JPEG jeśli plik raw jest nieedytowany +PREFERENCES_LANG;Język PREFERENCES_LANGAUTODETECT;Użyj języka systemowego +PREFERENCES_MAXRECENTFOLDERS;Maksymalna liczba ostatnio otwieranych folderów PREFERENCES_MENUGROUPEXTPROGS;Grupuj "Otwórz za pomocą" PREFERENCES_MENUGROUPFILEOPERATIONS;Grupuj operacje plików PREFERENCES_MENUGROUPLABEL;Grupuj operacje etykiet PREFERENCES_MENUGROUPPROFILEOPERATIONS;Grupuj operacje profili przetwarzania PREFERENCES_MENUGROUPRANK;Grupuj operacje oceny PREFERENCES_MENUOPTIONS;Opcje menu +PREFERENCES_MONITOR;Monitor +PREFERENCES_MONPROFILE;Domyślny profil kolorów +PREFERENCES_MONPROFILE_WARNOSX;Z powodu ograniczeń MacOS, dostępna jest tylko paleta sRGB. PREFERENCES_MULTITAB;Tryb wielu zakładek PREFERENCES_MULTITABDUALMON;Tryb wielu zakładek (na drugim monitorze jeśli dostępny) +PREFERENCES_NAVIGATIONFRAME;Nawigacja PREFERENCES_OVERLAY_FILENAMES;Nakładaj nazwy pliku na miniatury +PREFERENCES_OVERLAY_FILENAMES_FILMSTRIP;Nakładaj nazwy plików na miniaturki w przeglądarce PREFERENCES_OVERWRITEOUTPUTFILE;Nadpisuj istniejące pliki PREFERENCES_PANFACTORLABEL;Współczynnik PREFERENCES_PARSEDEXT;Przetwarzane rozszerzenia PREFERENCES_PARSEDEXTADD;Dodaj rozszerzenie PREFERENCES_PARSEDEXTADDHINT;Proszę wprowadzić rozszerzenie i zatwierdzić przyciskiem, by dodać do listy PREFERENCES_PARSEDEXTDELHINT;Skasuje wybrane rozszerzenie z listy +PREFERENCES_PARSEDEXTDOWNHINT;Przenieś wybrane rozszerzenie w dół. +PREFERENCES_PARSEDEXTUPHINT;Przenieś wybrane rozszerzenie w górę. +PREFERENCES_PERFORMANCE_MEASURE;Zmierz +PREFERENCES_PERFORMANCE_THREADS;Wątki +PREFERENCES_PREVDEMO;Metoda demozaikowania podglądu +PREFERENCES_PREVDEMO_FAST;Szybka +PREFERENCES_PREVDEMO_LABEL;Metoda demozaikowania podczas podglądu przy powiększeniu mniejszym niż 100%: +PREFERENCES_PREVDEMO_SIDECAR;Tak jak w PP3 PREFERENCES_PROFILEHANDLING;Obsługa profili PREFERENCES_PROFILELOADPR;Priorytet wczytywania profilu PREFERENCES_PROFILEPRCACHE;Profil w pamięci podręcznej PREFERENCES_PROFILEPRFILE;Profil przy pliku wejściowym PREFERENCES_PROFILESAVECACHE;Zapisz parametry przetwarzania w pamięci podręcznej PREFERENCES_PROFILESAVEINPUT;Zapisz parametry przetwarzania obok pliku wejściowego +PREFERENCES_PROFILESAVELOCATION;Miejsce zapisywania profilu przetwarzania +PREFERENCES_PROFILE_NONE;Żaden PREFERENCES_PROPERTY;Własność +PREFERENCES_PRTPROFILE;Profil kolorów PREFERENCES_PSPATH;Katalog w którym zainstalowany jest Adobe Photoshop PREFERENCES_SELECTLANG;Wybierz język +PREFERENCES_SERIALIZE_TIFF_READ;Ustawienia odczytu TIFF PREFERENCES_SET;Ustaw PREFERENCES_SHOWBASICEXIF;Pokaż podstawowe dane Exif PREFERENCES_SHOWDATETIME;Pokaż datę i czas @@ -744,7 +1033,9 @@ PREFERENCES_TAB_BROWSER;Przeglądarka plików PREFERENCES_TAB_COLORMGR;Zarządzanie kolorami PREFERENCES_TAB_GENERAL;Ogólne PREFERENCES_TAB_IMPROC;Przetwarzanie obrazu +PREFERENCES_TAB_PERFORMANCE;Wydajność PREFERENCES_TAB_SOUND;Dźwięki +PREFERENCES_THUMBNAIL_INSPECTOR_MODE;Image to show PREFERENCES_TP_LABEL;Panel narzędzi: PREFERENCES_TP_VSCROLLBAR;Ukry pionowy pasek przesuwania PREFERENCES_USEBUNDLEDPROFILES;Użyj załączone profile przetwarzania @@ -758,6 +1049,7 @@ PROFILEPANEL_MODE_TIP;Tryb wypełnienia parametrów przetwarzania.\n\nWduszone: PROFILEPANEL_MYPROFILES;Moje profile przetwarzania PROFILEPANEL_PASTEPPASTE;Parametry do wklejenia PROFILEPANEL_PCUSTOM;Własny +PROFILEPANEL_PDYNAMIC;Dynamika PROFILEPANEL_PFILE;Z pliku PROFILEPANEL_PINTERNAL;Neutralny PROFILEPANEL_PLASTSAVED;Ostatnio zapisany @@ -767,6 +1059,11 @@ PROFILEPANEL_TOOLTIPCOPY;Skopiuj aktualny profil do schowka PROFILEPANEL_TOOLTIPLOAD;Ładuj profil z pliku.\nCtrl+klik aby wybrać parametry do ładowania. PROFILEPANEL_TOOLTIPPASTE;Wklej profil ze schowka.\nCtrl+klik aby wybrać parametry do wklejenia. PROFILEPANEL_TOOLTIPSAVE;Zapisz aktualny profil.\nCtrl+klik aby wybrać parametry do zapisania. +PROGRESSBAR_DECODING;Dekodowanie... +PROGRESSBAR_GREENEQUIL;Równoważenie koloru zielonego... +PROGRESSBAR_HLREC;Rekonstrukcja podświetleń... +PROGRESSBAR_HOTDEADPIXELFILTER;Filtr gorących/martwych pikseli.. +PROGRESSBAR_LINEDENOISE;Liniowy filtr szumu... PROGRESSBAR_LOADING;Wczytywanie obrazu... PROGRESSBAR_LOADINGTHUMBS;Wczytywanie miniatur... PROGRESSBAR_LOADJPEG;Ładowanie pliku JPEG... @@ -775,14 +1072,18 @@ PROGRESSBAR_LOADTIFF;Ładowanie pliku TIFF... PROGRESSBAR_NOIMAGES;Nie znaleziono żadnych obrazów PROGRESSBAR_PROCESSING;Przetwarzanie obrazu... PROGRESSBAR_PROCESSING_PROFILESAVED;Zapisano profil przetwarzania +PROGRESSBAR_RAWCACORR;Korekcja aberracji chromatycznej... PROGRESSBAR_READY;Gotowe PROGRESSBAR_SAVEJPEG;Zapisywanie pliku JPEG... PROGRESSBAR_SAVEPNG;Zapisywanie pliku PNG... PROGRESSBAR_SAVETIFF;Zapisywanie pliku TIFF... PROGRESSBAR_SNAPSHOT_ADDED;Dodano migawkę PROGRESSDLG_PROFILECHANGEDINBROWSER;Profil zmieniony w przeglądarce +QINFO_FRAMECOUNT;%2 klatki +QINFO_HDR;HDR / %2 klatka/i QINFO_ISO;ISO QINFO_NOEXIF;Dane Exif niedostępne. +QINFO_PIXELSHIFT;Pixel Shift / %2 klatka/i QUEUE_AUTOSTART;Autostart QUEUE_AUTOSTART_TOOLTIP;Rozpocznij przetwarzanie automatycznie gdy pojawi się nowe zadanie. QUEUE_DESTFILENAME;Ścieżka i nazwa pliku @@ -790,8 +1091,18 @@ QUEUE_FORMAT_TITLE;Format pliku QUEUE_LOCATION_FOLDER;Zapisz do katalogu QUEUE_LOCATION_TEMPLATE;Użyj schemat QUEUE_LOCATION_TEMPLATE_TOOLTIP;Dozwolone są następujące kody formatujące:\n%f, %d1, %d2, ..., %p1, %p2, ..., %r, %s1, %s2, ...\n\nKody formatujące odnoszą się do różnych elementów ścieżki zdjęcia, atrybutów zdjęcia oraz do arbitralnego ciągu numerycznego operacji wsadowej.\n\nPrzykładowo, jeśli zdjęcie obrabiane ma następującą ścieżkę:\n/home/andrzej/zdjecia/2010-10-31/dsc0042.nef\nznaczenie kodów formatujących jest następujące:\n%d4 = home\n%d3 = andrzej\n%d2 = zdjecia\n%d1 = 2010-10-31\n%f = dsc0042\n%p1 = /home/tom/photos/2010-10-31/\n%p2 = /home/andrzej/zdjecia/\n%p3 = /home/andrzej/\n%p4 = /home/\n\n%r zostanie zastąpione oceną zdjęcia. Jeśli zdjęcie nie posiada oceny, %r zostanie zastąpione liczbą '0'. Jeśli zdjęcie leży w śmietniku, %r zostanie zastąpione znakiem 'x'.\n\n%s1, %s2, etc. zostanie zastąpione ciągniem numerycznym dopełnionym od jednej do dziewięciu cyfr. Ciąg ten zostanie rozpocznięty od "1" za każdym razem gdy kolejka przetwarzania zostanie uruchomiona, i liczba jest zwiększona o "1" dla każdego zapisanego obrazu.\n\nJeśli chcesz zapisać obraz wyjściowy obok obrazu wejściowego, napisz:\n%p1/%f\n\nJeśli chcesz zapisać obraz wyjściowy w folderze o nazwie "wywolane" znajdującego się w katalogu zawierającym otwarty obraz, napisz:\n%p1/wywolane/%f\n\nJeśli chcesz zapisać obraz wyjściowy w folderze o nazwie "/home/andrzej/zdjecia/wywolane/2010-10-31", napisz:\n%p2/wywolane/%d1/%f +QUEUE_LOCATION_TITLE;Lokalizacja wyjściowa +SAMPLEFORMAT_0;Nieznany typ pliku +SAMPLEFORMAT_1;8-bit bez znaku +SAMPLEFORMAT_2;16-bit bez znaku +SAMPLEFORMAT_4;24-bit LogLuv +SAMPLEFORMAT_8;32-bit LogLuv +SAMPLEFORMAT_16;16-bit zmiennoprzecinkowy +SAMPLEFORMAT_32;24-bit zmiennoprzecinkowy +SAMPLEFORMAT_64;32-bit zmiennoprzecinkowy SAVEDLG_AUTOSUFFIX;Automatycznie dodaj przyrostek, jeżeli plik już istnieje SAVEDLG_FILEFORMAT;Format pliku +SAVEDLG_FILEFORMAT_FLOAT; zmiennoprzecinkowy SAVEDLG_FORCEFORMATOPTS;Wymuś opcje zapisu SAVEDLG_JPEGQUAL;Jakość JPEG SAVEDLG_PUTTOQUEUE;Umieść w kolejce przetwarzania @@ -848,6 +1159,8 @@ TP_BWMIX_MET;Metoda TP_BWMIX_MET_CHANMIX;Mieszacz kanałów TP_BWMIX_MET_DESAT;Desaturacja TP_BWMIX_MET_LUMEQUAL;Ekwalizator luminancji +TP_BWMIX_MIXC;Mieszacz kanałów +TP_BWMIX_NEUTRAL;Reset TP_BWMIX_RGBLABEL;R: %1%% G: %2%% B: %3%% Total: %4%% TP_BWMIX_RGBLABEL_HINT;Ostateczne wartości RGB które uwzględniają wszystkie opcje mieszacza.\n"Total" wyświetla sumę wartości RGB:\n- zawsze 100% w trybie relatywnym,\n- ponad (jaśniej) lub poniżej (ciemniej) 100% w trybie absolutnym. TP_BWMIX_RGB_TOOLTIP;Miesza kanały RGB. Kieruj się gotowymi ustawieniami.\nNależy zwrócić uwagę na ujemne wartości ponieważ mogą pojawić się zniekształcenia sygnału w obrazie lub działać w sposób nieprzewidywalny. @@ -876,6 +1189,9 @@ TP_BWMIX_VAL;L TP_CACORRECTION_BLUE;Niebieski TP_CACORRECTION_LABEL;Korekcja aberracji chromatycznej TP_CACORRECTION_RED;Czerwony +TP_CBDL_AFT;Po zmianie na Cz-B +TP_CBDL_BEF;Przed zmianą na Cz-B +TP_CBDL_METHOD;Gdzie TP_CHMIXER_BLUE;Niebieski TP_CHMIXER_GREEN;Zielony TP_CHMIXER_LABEL;Mieszacz kanałów @@ -884,6 +1200,7 @@ TP_COARSETRAF_TOOLTIP_HFLIP;Odbij w poziomie TP_COARSETRAF_TOOLTIP_ROTLEFT;Obróć w lewo.\n\nSkróty:\n[ - Tryb wielu zakładek,\nAlt-[ - Tryb jednej zakładki. TP_COARSETRAF_TOOLTIP_ROTRIGHT;Obróć w prawo.\n\nSkróty:\n] - Tryb wielu zakładek,\nAlt-] - Tryb jednej zakładki. TP_COARSETRAF_TOOLTIP_VFLIP;Odbij w pionie +TP_COLORAPP_ABSOLUTELUMINANCE;Luminancja absolutna TP_COLORAPP_ALGO;Algorytm TP_COLORAPP_ALGO_ALL;Wszystkie TP_COLORAPP_ALGO_JC;Światłość + Chroma (JC) @@ -925,6 +1242,8 @@ TP_COLORAPP_LIGHT;Światłość (J) TP_COLORAPP_LIGHT_TOOLTIP;Światłość w CIECAM02 różni się od światłości CIELab oraz RGB TP_COLORAPP_MODEL;Model PB TP_COLORAPP_MODEL_TOOLTIP;Model punktu bieli.\n\nBB [RT] + [wyjściowy]:\nBalans bieli RawTherapee jest użyty dla sceny, CIECAM02 jest ustawione na D50, i balans bieli urządzenia wyjściowego ustawiony jest w Ustawieniach > Zarządzanie Kolorami\n\nBB [RT+CAT02] + [wyjściowe]:\nUstawienia balansu bieli RawTherapee są używane przez CAT02, i balans bieli urządzenia wyjściowego jest ustawione w Ustawieniach > Zarządzanie Kolorami. +TP_COLORAPP_NEUTRAL;Reset +TP_COLORAPP_NEUTRAL_TIP;Przywróć wszystkie suwaki oraz krzywe do wartości domyślnych TP_COLORAPP_RSTPRO;Ochrona odcieni skóry i czerwieni TP_COLORAPP_RSTPRO_TOOLTIP;Ochrona odcieni skóry i czerwieni (suwaki i krzywe) TP_COLORAPP_SURROUND;Otoczenie @@ -957,6 +1276,22 @@ TP_COLORTONING_HIGHLIGHT;Podświetlenia TP_COLORTONING_HUE;Odcień (hue) TP_COLORTONING_LAB;Mieszanie L*a*b* TP_COLORTONING_LABEL;Koloryzacja +TP_COLORTONING_LABREGION_CHANNEL;Kanał +TP_COLORTONING_LABREGION_CHANNEL_ALL;Wszystkie +TP_COLORTONING_LABREGION_CHANNEL_B;Niebieski +TP_COLORTONING_LABREGION_CHANNEL_G;Zielony +TP_COLORTONING_LABREGION_CHANNEL_R;Czerwony +TP_COLORTONING_LABREGION_CHROMATICITYMASK;C +TP_COLORTONING_LABREGION_HUEMASK;H +TP_COLORTONING_LABREGION_LIGHTNESSMASK;L +TP_COLORTONING_LABREGION_LIST_TITLE;Korekcja +TP_COLORTONING_LABREGION_MASK;Maska +TP_COLORTONING_LABREGION_MASKBLUR;Rozmycie maski +TP_COLORTONING_LABREGION_OFFSET;Przesunięcie +TP_COLORTONING_LABREGION_POWER;Moc +TP_COLORTONING_LABREGION_SATURATION;Saturacja +TP_COLORTONING_LABREGION_SHOWMASK;Pokaż maskę +TP_COLORTONING_LABREGION_SLOPE;Nachylenie TP_COLORTONING_LUMA;Luminancja TP_COLORTONING_LUMAMODE;Zachowaj luminancję TP_COLORTONING_LUMAMODE_TOOLTIP;Luminancja zostanie zachowana przy zmianie kolorów. @@ -969,7 +1304,7 @@ TP_COLORTONING_OPACITY;Przezroczystość TP_COLORTONING_RGBCURVES;RGB - Krzywe TP_COLORTONING_RGBSLIDERS;RGB - Suwaki TP_COLORTONING_SA;Ochrona przed przesyceniem -TP_COLORTONING_SATURATEDOPACITY;Śiła +TP_COLORTONING_SATURATEDOPACITY;Siła TP_COLORTONING_SATURATIONTHRESHOLD;Próg TP_COLORTONING_SHADOWS;Cienie TP_COLORTONING_SPLITCO;Cienie/półcienie/podświetlenia @@ -992,6 +1327,9 @@ TP_CROP_GTRULETHIRDS;Trójpodział TP_CROP_GUIDETYPE;Typ pomocy: TP_CROP_H;Wysokość TP_CROP_LABEL;Kadrowanie +TP_CROP_PPI;PPI +TP_CROP_RESETCROP;Reset +TP_CROP_SELECTCROP;Wybierz TP_CROP_W;Szerokość TP_CROP_X;X TP_CROP_Y;Y @@ -1000,13 +1338,28 @@ TP_DARKFRAME_LABEL;Czarna klatka TP_DEFRINGE_LABEL;Usuwanie widma TP_DEFRINGE_RADIUS;Promień TP_DEFRINGE_THRESHOLD;Próg +TP_DEHAZE_DEPTH;Głębia +TP_DEHAZE_LABEL;Usuwanie mgły +TP_DEHAZE_LUMINANCE;Tylko luminancja +TP_DEHAZE_SHOW_DEPTH_MAP;Pokaż mapę głębokości +TP_DEHAZE_STRENGTH;Siła +TP_DIRPYRDENOISE_CHROMINANCE_AUTOGLOBAL;Automatycznie TP_DIRPYRDENOISE_CHROMINANCE_BLUEYELLOW;Chrominancja - Błękit-żółć +TP_DIRPYRDENOISE_CHROMINANCE_CURVE;Krzywa chrominancji +TP_DIRPYRDENOISE_CHROMINANCE_FRAME;Chrominancja +TP_DIRPYRDENOISE_CHROMINANCE_MANUAL;Ręcznie TP_DIRPYRDENOISE_CHROMINANCE_MASTER;Chrominancja - Główna +TP_DIRPYRDENOISE_CHROMINANCE_METHOD;Metoda +TP_DIRPYRDENOISE_CHROMINANCE_PREVIEW;Podgląd TP_DIRPYRDENOISE_CHROMINANCE_REDGREEN;Chrominancja - Czerwień-zieleń +TP_DIRPYRDENOISE_LABEL;Redukcja szumu +TP_DIRPYRDENOISE_LUMINANCE_CONTROL;Kontrola luminancji TP_DIRPYRDENOISE_LUMINANCE_CURVE;Krzywa luminancji TP_DIRPYRDENOISE_LUMINANCE_DETAIL;Szczegółowość luminancji +TP_DIRPYRDENOISE_LUMINANCE_FRAME;Luminancja TP_DIRPYRDENOISE_LUMINANCE_SMOOTHING;Luminacja TP_DIRPYRDENOISE_MAIN_COLORSPACE;Metoda +TP_DIRPYRDENOISE_MAIN_COLORSPACE_LAB;L*a*b* TP_DIRPYRDENOISE_MAIN_COLORSPACE_RGB;RGB TP_DIRPYRDENOISE_MAIN_COLORSPACE_TOOLTIP;Dla obrazów raw można używać metody RGB oraz L*a*b*.\n\nDla obrazów nie-raw metoda L*a*b* zostanie użyta niezależnie od wyboru. TP_DIRPYRDENOISE_MAIN_GAMMA;Gamma @@ -1016,6 +1369,7 @@ TP_DIRPYRDENOISE_MAIN_MODE_AGGRESSIVE;Wysoka TP_DIRPYRDENOISE_MAIN_MODE_CONSERVATIVE;Standardowa TP_DIRPYRDENOISE_MAIN_MODE_TOOLTIP;Jakość może zostać dopasowana do wzoru szumów. Ustawienie "wysoka" ulepsza odszumianie około 20% wzrostu czasu przetwarzania. TP_DIRPYRDENOISE_MEDIAN_METHOD;Metoda mediana +TP_DIRPYRDENOISE_MEDIAN_METHOD_CHROMINANCE;Tylko Chroma TP_DIRPYRDENOISE_MEDIAN_METHOD_LAB;L*a*b* TP_DIRPYRDENOISE_MEDIAN_METHOD_LABEL;Filtr Mediana TP_DIRPYRDENOISE_MEDIAN_METHOD_LUMINANCE;Tylko luminancja @@ -1023,8 +1377,15 @@ TP_DIRPYRDENOISE_MEDIAN_METHOD_RGB;RGB TP_DIRPYRDENOISE_MEDIAN_METHOD_TOOLTIP;Przy użyciu metod "tylko luminancja" oraz "L*a*b*", filtrowanie mediana zostanie wykonane prosto po funkcji falki w procesie odszumiania.\nW trybie "RGB" filtrowanie to zostanie wykonana pod koniec calego procesu. TP_DIRPYRDENOISE_MEDIAN_PASSES;Liczba powtórzeń mediana TP_DIRPYRDENOISE_MEDIAN_TYPE;Rodzaj mediana +TP_DIRPYRDENOISE_TYPE_3X3;3×3 +TP_DIRPYRDENOISE_TYPE_3X3SOFT;3×3 miękko +TP_DIRPYRDENOISE_TYPE_5X5;5×5 +TP_DIRPYRDENOISE_TYPE_5X5SOFT;5×5 miękko +TP_DIRPYRDENOISE_TYPE_7X7;7×7 +TP_DIRPYRDENOISE_TYPE_9X9;9×9 TP_DIRPYREQUALIZER_ALGO;Zakres odcieni skóry TP_DIRPYREQUALIZER_ALGO_TOOLTIP;- +TP_DIRPYREQUALIZER_ARTIF;Usuń artefakty TP_DIRPYREQUALIZER_HUESKIN;Odcień skóry TP_DIRPYREQUALIZER_HUESKIN_TOOLTIP;Piramida wyznacza zakres kolorów uważany jako zakres odcieni skóry. Większość odcieni skóry - białej, czarnej, i pomiędzy - ma tę samą odcień. Małe poprawki są dopuszczalne, jednak jeśli potrzebna jest większa zmiana w lewo lub prawo, lub jeśli są widoczne artefakty, to najprawdopobniej balans bieli jest niepoprawny. TP_DIRPYREQUALIZER_LABEL;Kontrast wg. precyzji detali @@ -1040,6 +1401,7 @@ TP_DIRPYREQUALIZER_TOOLTIP;Zapobiega artefaktom w strefach przejścia pomiędzy TP_DISTORTION_AMOUNT;Siła TP_DISTORTION_LABEL;Dystorsja TP_EPD_EDGESTOPPING;Wyszukiwanie krawędzi +TP_EPD_GAMMA;Gamma TP_EPD_LABEL;Tone Mapping TP_EPD_REWEIGHTINGITERATES;Powtarzanie rozważania TP_EPD_SCALE;Skala @@ -1048,6 +1410,7 @@ TP_EXPOSURE_AUTOLEVELS;Wyrównaj poziomy TP_EXPOSURE_AUTOLEVELS_TIP;Dokonaj automatycznego ustawienia parametrów ekspozycji na podstawie analizy obrazu TP_EXPOSURE_BLACKLEVEL;Czerń TP_EXPOSURE_BRIGHTNESS;Jasność +TP_EXPOSURE_CLAMPOOG;Przytnij kolory spoza gamy kolorów TP_EXPOSURE_CLIP;Przytnij % TP_EXPOSURE_CLIP_TIP;Ułamek pikseli ktore mają zostać rozjaśnione do punktu prześwietlenia podczas automatycznego wyrównania poziomów. TP_EXPOSURE_COMPRHIGHLIGHTS;Kompresja podświetleń @@ -1064,11 +1427,17 @@ TP_EXPOSURE_SATURATION;Nasycenie TP_EXPOSURE_TCMODE_FILMLIKE;Klisza TP_EXPOSURE_TCMODE_LABEL1;Tryb krzywej 1 TP_EXPOSURE_TCMODE_LABEL2;Tryb krzywej 2 +TP_EXPOSURE_TCMODE_LUMINANCE;Luminancja +TP_EXPOSURE_TCMODE_PERCEPTUAL;Percepcyjny TP_EXPOSURE_TCMODE_SATANDVALBLENDING;Mieszanie nasycenia i mocy światła białego TP_EXPOSURE_TCMODE_STANDARD;Standardowa TP_EXPOSURE_TCMODE_WEIGHTEDSTD;Ważona standardowa TP_EXPOS_BLACKPOINT_LABEL;Punkt czerni raw TP_EXPOS_WHITEPOINT_LABEL;Punkt bieli raw +TP_FILMNEGATIVE_BLUE;Proporcja niebieskiego +TP_FILMNEGATIVE_LABEL;Negatyw - klisza +TP_FILMNEGATIVE_PICK;Wybierz miejsce neutralne +TP_FILMNEGATIVE_RED;Proporcja czerwonego TP_FILMSIMULATION_LABEL;Symulacja Kliszy TP_FILMSIMULATION_STRENGTH;Siła TP_FILMSIMULATION_ZEROCLUTSFOUND;Ustaw folder HaldCLUT w Ustawieniach @@ -1107,6 +1476,7 @@ TP_HSVEQUALIZER_HUE;H TP_HSVEQUALIZER_LABEL;Ekwalizator HSV TP_HSVEQUALIZER_SAT;S TP_HSVEQUALIZER_VAL;V +TP_ICM_BPC;Kompensacja punktu czerni TP_ICM_DCPILLUMINANT;Iluminant TP_ICM_DCPILLUMINANT_INTERPOLATED;Interpolowany TP_ICM_DCPILLUMINANT_TOOLTIP;Wybierz który osadzony iluminant DCP należy użyć. Domyślną opcją jest "interpolowany", czyli wartość jest mieszaniną pomiędzy dwoma osadzonymi wartościami iluminantu zależnie od balansu bieli. Ten wybór jest możliwy jedynie kiedy DCP zawiera dwa iluminanty z możliwościa interpolacji. @@ -1125,10 +1495,17 @@ TP_ICM_INPUTPROFILE;Profil wejściowy TP_ICM_LABEL;ICM TP_ICM_NOICM;Brak ICM: Wyjście sRGB TP_ICM_OUTPUTPROFILE;Profil wyjściowy +TP_ICM_SAVEREFERENCE_APPLYWB;Zastosuj balans bieli TP_ICM_SAVEREFERENCE_TOOLTIP;Zapisz liniowy obraz TIFF zanim profil wejściowy zostanie zastosowany. Obraz ten można użyć do kalibracji oraz do wytworzenia profilu aparatu. TP_ICM_TONECURVE;Użyj krzywą tonalną z DCP TP_ICM_TONECURVE_TOOLTIP;Włącz aby użyć krzywą tonalną znajdującą się w profilu DCP. Opcja ta jest tylko aktywna jeśli profil DCP zawiera krzywą tonalną. TP_ICM_WORKINGPROFILE;Profil roboczy +TP_ICM_WORKING_TRC;Krzywa odpowiedzi tonalnej: +TP_ICM_WORKING_TRC_CUSTOM;Własna +TP_ICM_WORKING_TRC_GAMMA;Gamma +TP_ICM_WORKING_TRC_NONE;Żadna +TP_ICM_WORKING_TRC_SLOPE;Nachylenie +TP_ICM_WORKING_TRC_TOOLTIP;Tylko dla wbudowanych profili. TP_IMPULSEDENOISE_LABEL;Redukcja Szumów Impulsowych TP_IMPULSEDENOISE_THRESH;Próg TP_LABCURVE_AVOIDCOLORSHIFT;Zapobiegaj zmianom koloru @@ -1171,7 +1548,27 @@ TP_LABCURVE_RSTPRO_TOOLTIP;Ma wpływ na suwak Chromatyczności oraz na krzywą C TP_LENSGEOM_AUTOCROP;Auto-kadrowanie TP_LENSGEOM_FILL;Auto-wypełnienie TP_LENSGEOM_LABEL;Obiektyw / Geometria +TP_LENSGEOM_LIN;Liniowo +TP_LENSGEOM_LOG;Logarytmicznie +TP_LENSPROFILE_CORRECTION_AUTOMATCH;Wybierz automatycznie +TP_LENSPROFILE_CORRECTION_LCPFILE;Plik LCP +TP_LENSPROFILE_CORRECTION_MANUAL;Wybierz ręcznie TP_LENSPROFILE_LABEL;Profil korekcji obiektywu LCP +TP_LENSPROFILE_MODE_HEADER;Profil obiektywu +TP_LENSPROFILE_USE_CA;Aberracja chromatyczna +TP_LENSPROFILE_USE_GEOMETRIC;Zniekształcenia geometryczne +TP_LENSPROFILE_USE_HEADER;Popraw +TP_LENSPROFILE_USE_VIGNETTING;Winietowanie +TP_LOCALCONTRAST_AMOUNT;Ilość +TP_LOCALCONTRAST_DARKNESS;Ciemne miejsca +TP_LOCALCONTRAST_LABEL;Kontrast lokalny +TP_LOCALCONTRAST_LIGHTNESS;Jasne miejsca +TP_LOCALCONTRAST_RADIUS;Promień +TP_METADATA_EDIT;Zastosuj modyfikacje +TP_METADATA_MODE;Tryb kopiowania metadanych +TP_METADATA_STRIP;Usuń wszystkie metadane +TP_METADATA_TUNNEL;Kopiuj niezmienione +TP_NEUTRAL;Reset TP_NEUTRAL_TIP;Zresetuj ustawienia do wartości neutralnych.\nDziała na tych samych suwakach na których funkcja "Wyrównaj poziomy" działa, niezależnie od tego czy funkcja ta była użyta czy nie. TP_PCVIGNETTE_FEATHER;Wtapianie TP_PCVIGNETTE_FEATHER_TOOLTIP;Wtapianie:\n0 = tylko brzegi,\n50 = w pół drogi do środka,\n100 = aż do środka. @@ -1192,8 +1589,15 @@ TP_PREPROCESS_HOTPIXFILT;Filtr gorących pikseli TP_PREPROCESS_HOTPIXFILT_TOOLTIP;Łata gorące piksele (pojedyńcze świecące, przesycone piksele). TP_PREPROCESS_LABEL;Przetwarzanie początkowe TP_PREPROCESS_LINEDENOISE;Filtr zakłóceń liniowych +TP_PREPROCESS_LINEDENOISE_DIRECTION;Kierunek +TP_PREPROCESS_LINEDENOISE_DIRECTION_BOTH;Oba +TP_PREPROCESS_LINEDENOISE_DIRECTION_HORIZONTAL;Poziomo +TP_PREPROCESS_LINEDENOISE_DIRECTION_VERTICAL;Pionowo TP_PREPROCESS_NO_FOUND;Nic nie znaleziono +TP_PRSHARPENING_LABEL;Wyostrzanie po zmianie rozmiaru TP_RAWCACORR_AUTO;Autokorekcja +TP_RAWCACORR_AUTOIT;Iteracje +TP_RAWCACORR_AVOIDCOLORSHIFT;Unikaj przesunięcia kolorów TP_RAWCACORR_CABLUE;Niebieski TP_RAWCACORR_CARED;Czerwony TP_RAWCACORR_LABEL;Korekcja aberracji chromatycznej @@ -1207,19 +1611,60 @@ TP_RAWEXPOS_BLACK_RED;Czerwony TP_RAWEXPOS_LINEAR;Liniowy współczynnik korekcji TP_RAWEXPOS_RGB;Czerwony, Zielony, Niebieski TP_RAWEXPOS_TWOGREEN;Połącz obie zielenie +TP_RAW_1PASSMEDIUM;1-pass (Markesteijn) +TP_RAW_2PASS;1-pass+fast +TP_RAW_3PASSBEST;3-pass (Markesteijn) +TP_RAW_4PASS;3-pass+fast +TP_RAW_AHD;AHD +TP_RAW_AMAZE;AMaZE +TP_RAW_AMAZEVNG4;AMaZE+VNG4 +TP_RAW_DCB;DCB TP_RAW_DCBENHANCE;Zastosuj poprawę DCB TP_RAW_DCBITERATIONS;Liczba powtórzeń DCB +TP_RAW_DCBVNG4;DCB+VNG4 TP_RAW_DMETHOD;Metoda TP_RAW_DMETHOD_PROGRESSBAR;Demozaikowanie %1... TP_RAW_DMETHOD_PROGRESSBAR_REFINE;Udoskonalanie demozaikowania... TP_RAW_DMETHOD_TOOLTIP;IGV oraz LMMSE są przeznaczone dla zdjęć raw o wysokim poziomie szumów (wysokie ISO) aby zapobiec utworzeniu się wzorków w kształcie małych labiryntów, posteryzacji oraz mydlanego wyglądu. +TP_RAW_DUALDEMOSAICAUTOCONTRAST;Próg automatyczny +TP_RAW_DUALDEMOSAICCONTRAST;Próg kontrastu +TP_RAW_EAHD;EAHD TP_RAW_FALSECOLOR;Kroki zapobiegające fałszowaniu kolorów +TP_RAW_FAST;Szybki +TP_RAW_HD;Próg +TP_RAW_HPHD;HPHD +TP_RAW_IGV;IGV TP_RAW_LABEL;Demozaikowanie +TP_RAW_LMMSE;LMMSE TP_RAW_LMMSEITERATIONS;Ilość kroków udoskonalenia LMMSE TP_RAW_LMMSE_TOOLTIP;Aby zmniejszyć ilość artefaktów i poprawić stosunek sygnału do szumów, można wykorzystać następujące ustawienia:\n1: Gamma\n2-4: Średnia mediana\n5-6: Rafinowanie +TP_RAW_MONO;Mono +TP_RAW_PIXELSHIFTBLUR;Maska rozmycia ruchu +TP_RAW_PIXELSHIFTDMETHOD;Metoda demozaikowania ruchu +TP_RAW_PIXELSHIFTEPERISO;Czułość +TP_RAW_PIXELSHIFTEQUALBRIGHT;Wyrównaj jasność klatek +TP_RAW_PIXELSHIFTHOLEFILL;Wypełnij dziury w masce ruchu +TP_RAW_PIXELSHIFTHOLEFILL_TOOLTIP;Wypełnia dziury w masce ruchu +TP_RAW_PIXELSHIFTMEDIAN;Użyj mediany dla poruszonych fragmentów +TP_RAW_PIXELSHIFTMM_AUTO;Automatyczny +TP_RAW_PIXELSHIFTMM_CUSTOM;Własny +TP_RAW_PIXELSHIFTMM_OFF;Wyłączony +TP_RAW_PIXELSHIFTMOTIONMETHOD;Korekcja ruchu +TP_RAW_PIXELSHIFTNONGREENCROSS;Szukaj ruchu w kanale niebieskim/czerwonym +TP_RAW_PIXELSHIFTSHOWMOTION;Pokaż maskę ruchu +TP_RAW_PIXELSHIFTSHOWMOTIONMASKONLY;Pokaż tylko maskę ruchu +TP_RAW_PIXELSHIFTSHOWMOTIONMASKONLY_TOOLTIP;Pokaż samą maskę ruchu (bez obrazu). +TP_RAW_PIXELSHIFTSIGMA;Promień rozmycia +TP_RAW_PIXELSHIFTSMOOTH;Miękkie przejścia +TP_RAW_RCD;RCD +TP_RAW_RCDVNG4;RCD+VNG4 TP_RAW_SENSOR_BAYER_LABEL;Matryca z filtrem Bayera TP_RAW_SENSOR_XTRANS_DMETHOD_TOOLTIP;Trzy powtórzenia prowadzą do najlepszych rezultatów (zalecane dla zdjęć o niskim ISO).\nJedno powtórzenie jest prawie nie do odróżnienia od trzech dla zdjęć o wysokim ISO a jest znacznie szybsze. TP_RAW_SENSOR_XTRANS_LABEL;Matryca z filtrem X-Trans +TP_RAW_VNG4;VNG4 +TP_RAW_XTRANS;X-Trans +TP_RAW_XTRANSFAST;Szybki X-Trans +TP_RESIZE_ALLOW_UPSCALING;Zezwól na zwiększenie rozdzielczości TP_RESIZE_APPLIESTO;Dotyczy: TP_RESIZE_CROPPEDAREA;Obszaru kadrowanego TP_RESIZE_FITBOX;Wymiary obwodu @@ -1234,6 +1679,46 @@ TP_RESIZE_SCALE;Skalę TP_RESIZE_SPECIFY;Określ: TP_RESIZE_W;Szerokość TP_RESIZE_WIDTH;Szerokość +TP_RETINEX_CONTEDIT_HSL;Histogram HSL +TP_RETINEX_CONTEDIT_LAB;Histogram L*a*b* +TP_RETINEX_CONTEDIT_LH;Odcień +TP_RETINEX_CONTEDIT_MAP;Wyrównywanie +TP_RETINEX_CURVEEDITOR_CD;L=f(L) +TP_RETINEX_CURVEEDITOR_LH;Siła=f(H) +TP_RETINEX_CURVEEDITOR_MAP;L=f(L) +TP_RETINEX_EQUAL;Wyrównywanie +TP_RETINEX_GAIN;Wzmocnienie +TP_RETINEX_GAMMA;Gamma +TP_RETINEX_GAMMA_FREE;Wolna +TP_RETINEX_GAMMA_HIGH;Wysoka +TP_RETINEX_GAMMA_LOW;Niska +TP_RETINEX_GAMMA_MID;Średnia +TP_RETINEX_GAMMA_NONE;Żaden +TP_RETINEX_HIGH;Wysoki +TP_RETINEX_HIGHLIGHT;Próg podświetleń +TP_RETINEX_HSLSPACE_LIN;HSL-Liniowa +TP_RETINEX_HSLSPACE_LOG;HSL-Logarytmiczna +TP_RETINEX_LABEL;Retinex +TP_RETINEX_LABEL_MASK;Maska +TP_RETINEX_LABSPACE;L*a*b* +TP_RETINEX_LOW;Niski +TP_RETINEX_MAP;Metoda +TP_RETINEX_MAP_GAUS;Maska Gaussa +TP_RETINEX_MAP_NONE;Żaden +TP_RETINEX_METHOD;Metoda +TP_RETINEX_NEIGHBOR;Promień +TP_RETINEX_NEUTRAL;Reset +TP_RETINEX_OFFSET;Przesunięcie (jasność) +TP_RETINEX_SETTINGS;Ustawienia +TP_RETINEX_SKAL;Skala +TP_RETINEX_STRENGTH;Siła +TP_RETINEX_THRESHOLD;Próg +TP_RETINEX_UNIFORM;Jednolity +TP_RETINEX_VARIANCE;Kontrast +TP_RETINEX_VIEW;Proces +TP_RETINEX_VIEW_MASK;Maska +TP_RETINEX_VIEW_NONE;Standardowy +TP_RETINEX_VIEW_UNSHARP;Maska wyostrzająca TP_RGBCURVES_BLUE;B TP_RGBCURVES_CHANNEL;Kanał TP_RGBCURVES_GREEN;G @@ -1256,6 +1741,8 @@ TP_SHARPENEDGE_LABEL;Krawędzie TP_SHARPENEDGE_PASSES;Powtórzenia TP_SHARPENEDGE_THREE;Tylko luminancja TP_SHARPENING_AMOUNT;Siła +TP_SHARPENING_BLUR;Promień rozmycia +TP_SHARPENING_CONTRAST;Próg kontrastu TP_SHARPENING_EDRADIUS;Promień TP_SHARPENING_EDTOLERANCE;Tolerancja krawędzi TP_SHARPENING_HALOCONTROL;Kontrola poświaty @@ -1271,9 +1758,14 @@ TP_SHARPENING_RLD_ITERATIONS;Powtórzenia TP_SHARPENING_THRESHOLD;Próg TP_SHARPENING_USM;Maska wyostrzająca TP_SHARPENMICRO_AMOUNT;Siła +TP_SHARPENMICRO_CONTRAST;Próg kontrastu TP_SHARPENMICRO_LABEL;Mikrokontrast TP_SHARPENMICRO_MATRIX;Matryca 3×3 zamiast 5×5 TP_SHARPENMICRO_UNIFORMITY;Jednolitość +TP_SOFTLIGHT_STRENGTH;Siła +TP_TM_FATTAL_AMOUNT;Ilość +TP_TM_FATTAL_LABEL;Kompresja zakresu dynamiki +TP_TM_FATTAL_THRESHOLD;Detale TP_VIBRANCE_AVOIDCOLORSHIFT;Zapobiegaj przesunięcia kolorów TP_VIBRANCE_CURVEEDITOR_SKINTONES;HH TP_VIBRANCE_CURVEEDITOR_SKINTONES_LABEL;Odcienie skóry @@ -1298,6 +1790,105 @@ TP_VIGNETTING_CENTER_Y;Środek Y TP_VIGNETTING_LABEL;Korekcja winietowania TP_VIGNETTING_RADIUS;Promień TP_VIGNETTING_STRENGTH;Siła +TP_WAVELET_1;Poziom 1 +TP_WAVELET_2;Poziom 2 +TP_WAVELET_3;Poziom 3 +TP_WAVELET_4;Poziom 4 +TP_WAVELET_5;Poziom 5 +TP_WAVELET_6;Poziom 6 +TP_WAVELET_7;Poziom 7 +TP_WAVELET_8;Poziom 8 +TP_WAVELET_9;Poziom 9 +TP_WAVELET_APPLYTO;Zastosuj do +TP_WAVELET_AVOID;Unikaj przesunięcia kolorów +TP_WAVELET_B0;Czarny +TP_WAVELET_B1;Szary +TP_WAVELET_BACKGROUND;Tło +TP_WAVELET_BACUR;Krzywa +TP_WAVELET_BALCHRO;Balans chrominancji +TP_WAVELET_BANONE;Żaden +TP_WAVELET_BASLI;Suwak +TP_WAVELET_BATYPE;Metoda balansu kontrastu +TP_WAVELET_CBENAB;Tonowanie i balans kolorów +TP_WAVELET_CCURVE;Kontrast lokalny +TP_WAVELET_CH1;Cały zakres chrominancji +TP_WAVELET_CH2;Nasycone/pastelowe +TP_WAVELET_CH3;Połącz poziomy kontrastu +TP_WAVELET_CHCU;Krzywa +TP_WAVELET_CHSL;Suwaki +TP_WAVELET_COMPCONT;Kontrast +TP_WAVELET_COMPGAMMA;Kompresja - Gamma +TP_WAVELET_CONTR;Gamut +TP_WAVELET_CONTRA;Kontrast +TP_WAVELET_CONTRAST_MINUS;Kontrast - +TP_WAVELET_CONTRAST_PLUS;Kontrast + +TP_WAVELET_CTYPE;Kontrola chrominancji +TP_WAVELET_CURVEEDITOR_CL;L +TP_WAVELET_CURVEEDITOR_HH;HH +TP_WAVELET_DALL;We wszystkich kierunkach +TP_WAVELET_DAUB2;D2 - niski +TP_WAVELET_DAUB4;D4 - standard +TP_WAVELET_DAUB6;D6 - standard plus +TP_WAVELET_DAUB10;D10 - średni +TP_WAVELET_DAUB14;D14 - wysoki +TP_WAVELET_DONE;Pionowo +TP_WAVELET_DTHR;Po przekątnej +TP_WAVELET_DTWO;Poziomo +TP_WAVELET_EDCU;Krzywa +TP_WAVELET_EDGCONT;Kontrast lokalny +TP_WAVELET_EDGE;Ostrość krawędzi +TP_WAVELET_EDGEDETECTTHR;Niski próg (szum) +TP_WAVELET_EDGEDETECTTHR2;Wysoki próg (wykrywanie) +TP_WAVELET_EDGTHRESH;Szczegółowość +TP_WAVELET_EDRAD;Promień +TP_WAVELET_EDSL;Suwaki progów +TP_WAVELET_EDTYPE;Metoda kontrastu lokalnego: +TP_WAVELET_EDVAL;Siła +TP_WAVELET_FINAL;Ostateczny retusz +TP_WAVELET_FINEST;Najdokładniej +TP_WAVELET_HIGHLIGHT;Zakres luminancji podświetleń +TP_WAVELET_HS1;Zakres luminancji +TP_WAVELET_HS2;Cienie/Podświetlenia +TP_WAVELET_HUESKIN;Odcień skóry +TP_WAVELET_HUESKY;Odcień nieba +TP_WAVELET_LEVCH;Chrominancja +TP_WAVELET_LEVF;Kontrast +TP_WAVELET_LEVONE;Poziom 2 +TP_WAVELET_LEVTHRE;Poziom 4 +TP_WAVELET_LEVTWO;Poziom 3 +TP_WAVELET_LEVZERO;Poziom 1 +TP_WAVELET_LINKEDG;Połącz z siłą 'Ostrość krawędzi' +TP_WAVELET_LIPST;Usprawniony algorytm +TP_WAVELET_LOWLIGHT;Zakres luminancji cieni +TP_WAVELET_MEDGREINF;Pierwszy poziom +TP_WAVELET_MEDI;Usuwaj artefakty niebieskiego nieba +TP_WAVELET_MEDILEV;Wykrywanie krawędzi +TP_WAVELET_NEUTRAL;Neutralny +TP_WAVELET_NOIS;Odszumianie +TP_WAVELET_NPHIGH;Wysoki +TP_WAVELET_NPLOW;Niski +TP_WAVELET_NPNONE;Brak +TP_WAVELET_NPTYPE;Piksele sąsiadujące +TP_WAVELET_PASTEL;Chrominancja kolorów pastelowych +TP_WAVELET_PROC;Proces +TP_WAVELET_RE1;Wzmocniony +TP_WAVELET_RE2;Niezmieniony +TP_WAVELET_RE3;Zmniejszony +TP_WAVELET_RESCHRO;Chrominancja +TP_WAVELET_RESCON;Cienie +TP_WAVELET_RESCONH;Podświetlenia +TP_WAVELET_SAT;Chrominancja kolorów nasyconych +TP_WAVELET_SKY;Odcień nieba - wybór/ochrona +TP_WAVELET_STREN;Siła +TP_WAVELET_STRENGTH;Siła +TP_WAVELET_SUPE;Ekstra +TP_WAVELET_THR;Próg cieni +TP_WAVELET_THRESHOLD;Poziom podświetleń +TP_WAVELET_THRESHOLD2;Poziom cieni +TP_WAVELET_THRH;Próg podświetleń +TP_WAVELET_TMSTRENGTH;Siła kompresji +TP_WAVELET_TMTYPE;Metoda kompresji +TP_WAVELET_TON;Tonowanie TP_WBALANCE_AUTO;Auto TP_WBALANCE_CAMERA;Z aparatu TP_WBALANCE_CLOUDY;Pochmurnie @@ -1332,6 +1923,7 @@ TP_WBALANCE_LED_CRS;CRS SP12 WWMR16 TP_WBALANCE_LED_HEADER;LED TP_WBALANCE_LED_LSI;LSI Lumelex 2040 TP_WBALANCE_METHOD;Metoda +TP_WBALANCE_PICKER;Wybierz TP_WBALANCE_SHADE;Ćień TP_WBALANCE_SIZE;Wielkość: TP_WBALANCE_SOLUX35;Solux 3500K @@ -1339,6 +1931,7 @@ TP_WBALANCE_SOLUX41;Solux 4100K TP_WBALANCE_SOLUX47;Solux 4700K (vendor) TP_WBALANCE_SOLUX47_NG;Solux 4700K (Nat. Gallery) TP_WBALANCE_SPOTWB;Punktowy +TP_WBALANCE_TEMPBIAS;Kompensacja automatycznego balansu bieli (AWB) TP_WBALANCE_TEMPERATURE;Temperatura TP_WBALANCE_TUNGSTEN;Wolfram TP_WBALANCE_WATER1;Pod wodą 1 @@ -1356,29 +1949,11 @@ ZOOMPANEL_ZOOMOUT;Oddal\nSkrót: - ! Untranslated keys follow; remove the ! prefix after an entry is translated. !!!!!!!!!!!!!!!!!!!!!!!!! -!ADJUSTER_RESET_TO_DEFAULT;Click - reset to default value.\nCtrl+click - reset to initial value. -!CURVEEDITOR_AXIS_IN;I: -!CURVEEDITOR_AXIS_LEFT_TAN;LT: -!CURVEEDITOR_AXIS_OUT;O: -!CURVEEDITOR_AXIS_RIGHT_TAN;RT: -!CURVEEDITOR_CATMULLROM;Flexible !CURVEEDITOR_EDITPOINT_HINT;Enable edition of node in/out values.\n\nRight-click on a node to select it.\nRight-click on empty space to de-select the node. -!DONT_SHOW_AGAIN;Don't show this message again. -!DYNPROFILEEDITOR_DELETE;Delete -!DYNPROFILEEDITOR_EDIT;Edit !DYNPROFILEEDITOR_EDIT_RULE;Edit Dynamic Profile Rule !DYNPROFILEEDITOR_ENTRY_TOOLTIP;The matching is case insensitive.\nUse the "re:" prefix to enter\na regular expression. -!DYNPROFILEEDITOR_IMGTYPE_ANY;Any -!DYNPROFILEEDITOR_IMGTYPE_HDR;HDR !DYNPROFILEEDITOR_IMGTYPE_PS;Pixel Shift -!DYNPROFILEEDITOR_IMGTYPE_STD;Standard -!DYNPROFILEEDITOR_MOVE_DOWN;Move Down -!DYNPROFILEEDITOR_MOVE_UP;Move Up -!DYNPROFILEEDITOR_NEW;New !DYNPROFILEEDITOR_NEW_RULE;New Dynamic Profile Rule -!DYNPROFILEEDITOR_PROFILE;Processing Profile -!EXIFFILTER_IMAGETYPE;Image type -!EXIFPANEL_SHOWALL;Show all !EXPORT_BYPASS;Processing steps to bypass !EXPORT_BYPASS_EQUALIZER;Bypass Wavelet Levels !EXPORT_PIPELINE;Processing pipeline @@ -1386,136 +1961,53 @@ ZOOMPANEL_ZOOMOUT;Oddal\nSkrót: - !EXPORT_USE_FAST_PIPELINE_TIP;Use a dedicated processing pipeline for images in Fast Export mode, that trades speed for quality. Resizing of the image is done as early as possible, instead of doing it at the end like in the normal pipeline. The speedup can be significant, but be prepared to see artifacts and a general degradation of output quality. !EXPORT_USE_NORMAL_PIPELINE;Standard (bypass some steps, resize at the end) !FILEBROWSER_BROWSEPATHBUTTONHINT;Click to open specified path, reload folder and apply "find" keywords. -!FILEBROWSER_CACHECLEARFROMFULL;Clear all including cached profiles -!FILEBROWSER_CACHECLEARFROMPARTIAL;Clear all except cached profiles !FILEBROWSER_DELETEDIALOG_ALL;Are you sure you want to permanently delete all %1 files in trash? !FILEBROWSER_DELETEDIALOG_SELECTED;Are you sure you want to permanently delete the selected %1 files? !FILEBROWSER_DELETEDIALOG_SELECTEDINCLPROC;Are you sure you want to permanently delete the selected %1 files, including a queue-processed version? -!FILEBROWSER_EMPTYTRASHHINT;Permanently delete all files in trash. -!FILEBROWSER_POPUPREMOVE;Delete permanently !FILEBROWSER_POPUPREMOVEINCLPROC;Delete permanently, including queue-processed version -!FILEBROWSER_RESETDEFAULTPROFILE;Reset to default -!FILEBROWSER_SHOWNOTTRASHHINT;Show only images not in trash. !FILEBROWSER_SHOWORIGINALHINT;Show only original images.\n\nWhen several images exist with the same filename but different extensions, the one considered original is the one whose extension is nearest the top of the parsed extensions list in Preferences > File Browser > Parsed Extensions. -!FILECHOOSER_FILTER_ANY;All files -!FILECHOOSER_FILTER_COLPROF;Color profiles (*.icc) -!FILECHOOSER_FILTER_CURVE;Curve files -!FILECHOOSER_FILTER_LCP;Lens correction profiles -!FILECHOOSER_FILTER_PP;Processing profiles -!FILECHOOSER_FILTER_SAME;Same format as current photo -!FILECHOOSER_FILTER_TIFF;TIFF files -!GENERAL_APPLY;Apply -!GENERAL_ASIMAGE;As Image -!GENERAL_CURRENT;Current -!GENERAL_HELP;Help -!GENERAL_OPEN;Open -!GENERAL_RESET;Reset -!GENERAL_SAVE_AS;Save as... -!GENERAL_SLIDER;Slider !GIMP_PLUGIN_INFO;Welcome to the RawTherapee GIMP plugin!\nOnce you are done editing, simply close the main RawTherapee window and the image will be automatically imported in GIMP. !HISTOGRAM_TOOLTIP_MODE;Toggle between linear, log-linear and log-log scaling of the histogram. -!HISTORY_MSG_166;Exposure - Reset -!HISTORY_MSG_173;NR - Detail recovery -!HISTORY_MSG_203;NR - Color space !HISTORY_MSG_235;B&W - CM - Auto !HISTORY_MSG_237;B&W - CM -!HISTORY_MSG_256;NR - Median - Type !HISTORY_MSG_273;CT - Color Balance SMH -!HISTORY_MSG_297;NR - Mode -!HISTORY_MSG_299;NR - Chrominance curve -!HISTORY_MSG_300;- -!HISTORY_MSG_301;NR - Luma control -!HISTORY_MSG_302;NR - Chroma method -!HISTORY_MSG_303;NR - Chroma method -!HISTORY_MSG_304;W - Contrast levels !HISTORY_MSG_305;Wavelet Levels -!HISTORY_MSG_306;W - Process -!HISTORY_MSG_307;W - Process -!HISTORY_MSG_308;W - Process direction -!HISTORY_MSG_309;W - ES - Detail !HISTORY_MSG_310;W - Residual - Sky tar/prot !HISTORY_MSG_311;W - Wavelet levels -!HISTORY_MSG_312;W - Residual - Shadows threshold !HISTORY_MSG_313;W - Chroma - Sat/past !HISTORY_MSG_314;W - Gamut - Reduce artifacts -!HISTORY_MSG_315;W - Residual - Contrast !HISTORY_MSG_316;W - Gamut - Skin tar/prot -!HISTORY_MSG_317;W - Gamut - Skin hue -!HISTORY_MSG_318;W - Contrast - Highlight levels -!HISTORY_MSG_319;W - Contrast - Highlight range -!HISTORY_MSG_320;W - Contrast - Shadow range -!HISTORY_MSG_321;W - Contrast - Shadow levels -!HISTORY_MSG_322;W - Gamut - Avoid color shift -!HISTORY_MSG_323;W - ES - Local contrast -!HISTORY_MSG_324;W - Chroma - Pastel -!HISTORY_MSG_325;W - Chroma - Saturated -!HISTORY_MSG_326;W - Chroma - Method !HISTORY_MSG_327;W - Contrast - Apply to !HISTORY_MSG_328;W - Chroma - Link strength !HISTORY_MSG_329;W - Toning - Opacity RG !HISTORY_MSG_330;W - Toning - Opacity BY !HISTORY_MSG_331;W - Contrast levels - Extra !HISTORY_MSG_332;W - Tiling method -!HISTORY_MSG_333;W - Residual - Shadows -!HISTORY_MSG_334;W - Residual - Chroma -!HISTORY_MSG_335;W - Residual - Highlights -!HISTORY_MSG_336;W - Residual - Highlights threshold -!HISTORY_MSG_337;W - Residual - Sky hue -!HISTORY_MSG_338;W - ES - Radius -!HISTORY_MSG_339;W - ES - Strength -!HISTORY_MSG_340;W - Strength !HISTORY_MSG_341;W - Edge performance !HISTORY_MSG_342;W - ES - First level -!HISTORY_MSG_343;W - Chroma levels !HISTORY_MSG_344;W - Meth chroma sl/cur -!HISTORY_MSG_345;W - ES - Local contrast -!HISTORY_MSG_346;W - ES - Local contrast method -!HISTORY_MSG_347;W - Denoise - Level 1 -!HISTORY_MSG_348;W - Denoise - Level 2 -!HISTORY_MSG_349;W - Denoise - Level 3 !HISTORY_MSG_350;W - ES - Edge detection !HISTORY_MSG_351;W - Residual - HH curve -!HISTORY_MSG_352;W - Background !HISTORY_MSG_353;W - ES - Gradient sensitivity !HISTORY_MSG_354;W - ES - Enhanced -!HISTORY_MSG_355;W - ES - Threshold low -!HISTORY_MSG_356;W - ES - Threshold high !HISTORY_MSG_357;W - Denoise - Link with ES !HISTORY_MSG_358;W - Gamut - CH -!HISTORY_MSG_359;Hot/Dead - Threshold !HISTORY_MSG_360;TM - Gamma !HISTORY_MSG_361;W - Final - Chroma balance -!HISTORY_MSG_362;W - Residual - Compression method -!HISTORY_MSG_363;W - Residual - Compression strength -!HISTORY_MSG_364;W - Final - Contrast balance !HISTORY_MSG_365;W - Final - Delta balance !HISTORY_MSG_366;W - Residual - Compression gamma !HISTORY_MSG_367;W - Final - 'After' contrast curve -!HISTORY_MSG_368;W - Final - Contrast balance -!HISTORY_MSG_369;W - Final - Balance method -!HISTORY_MSG_370;W - Final - Local contrast curve !HISTORY_MSG_371;Post-Resize Sharpening -!HISTORY_MSG_372;PRS USM - Radius -!HISTORY_MSG_373;PRS USM - Amount -!HISTORY_MSG_374;PRS USM - Threshold !HISTORY_MSG_375;PRS USM - Sharpen only edges -!HISTORY_MSG_376;PRS USM - Edge detection radius -!HISTORY_MSG_377;PRS USM - Edge tolerance !HISTORY_MSG_378;PRS USM - Halo control !HISTORY_MSG_379;PRS USM - Halo control amount -!HISTORY_MSG_380;PRS - Method -!HISTORY_MSG_381;PRS RLD - Radius -!HISTORY_MSG_382;PRS RLD - Amount !HISTORY_MSG_383;PRS RLD - Damping -!HISTORY_MSG_384;PRS RLD - Iterations -!HISTORY_MSG_385;W - Residual - Color Balance !HISTORY_MSG_386;W - Residual - CB green high !HISTORY_MSG_387;W - Residual - CB blue high !HISTORY_MSG_388;W - Residual - CB green mid !HISTORY_MSG_389;W - Residual - CB blue mid !HISTORY_MSG_390;W - Residual - CB green low !HISTORY_MSG_391;W - Residual - CB blue low -!HISTORY_MSG_392;W - Residual - Color Balance !HISTORY_MSG_393;DCP - Look table !HISTORY_MSG_394;DCP - Baseline exposure !HISTORY_MSG_395;DCP - Base table @@ -1528,61 +2020,31 @@ ZOOMPANEL_ZOOMOUT;Oddal\nSkrót: - !HISTORY_MSG_402;W - Denoise sub-tool !HISTORY_MSG_403;W - ES - Edge sensitivity !HISTORY_MSG_404;W - ES - Base amplification -!HISTORY_MSG_405;W - Denoise - Level 4 !HISTORY_MSG_406;W - ES - Neighboring pixels -!HISTORY_MSG_407;Retinex - Method -!HISTORY_MSG_408;Retinex - Radius -!HISTORY_MSG_409;Retinex - Contrast -!HISTORY_MSG_410;Retinex - Offset -!HISTORY_MSG_411;Retinex - Strength !HISTORY_MSG_412;Retinex - Gaussian gradient -!HISTORY_MSG_413;Retinex - Contrast !HISTORY_MSG_414;Retinex - Histogram - Lab !HISTORY_MSG_415;Retinex - Transmission !HISTORY_MSG_416;Retinex !HISTORY_MSG_417;Retinex - Transmission median -!HISTORY_MSG_418;Retinex - Threshold -!HISTORY_MSG_419;Retinex - Color space !HISTORY_MSG_420;Retinex - Histogram - HSL -!HISTORY_MSG_421;Retinex - Gamma -!HISTORY_MSG_422;Retinex - Gamma !HISTORY_MSG_423;Retinex - Gamma slope !HISTORY_MSG_424;Retinex - HL threshold !HISTORY_MSG_425;Retinex - Log base -!HISTORY_MSG_426;Retinex - Hue equalizer !HISTORY_MSG_427;Output rendering intent !HISTORY_MSG_428;Monitor rendering intent -!HISTORY_MSG_429;Retinex - Iterations !HISTORY_MSG_430;Retinex - Transmission gradient !HISTORY_MSG_431;Retinex - Strength gradient -!HISTORY_MSG_432;Retinex - M - Highlights !HISTORY_MSG_433;Retinex - M - Highlights TW -!HISTORY_MSG_434;Retinex - M - Shadows !HISTORY_MSG_435;Retinex - M - Shadows TW -!HISTORY_MSG_436;Retinex - M - Radius -!HISTORY_MSG_437;Retinex - M - Method -!HISTORY_MSG_438;Retinex - M - Equalizer -!HISTORY_MSG_439;Retinex - Process -!HISTORY_MSG_440;CbDL - Method !HISTORY_MSG_441;Retinex - Gain transmission -!HISTORY_MSG_442;Retinex - Scale !HISTORY_MSG_443;Output black point compensation !HISTORY_MSG_444;WB - Temp bias !HISTORY_MSG_445;Raw sub-image -!HISTORY_MSG_449;PS - ISO adaption -!HISTORY_MSG_452;PS - Show motion -!HISTORY_MSG_453;PS - Show mask only !HISTORY_MSG_457;PS - Check red/blue !HISTORY_MSG_462;PS - Check green !HISTORY_MSG_464;PS - Blur motion mask -!HISTORY_MSG_465;PS - Blur radius -!HISTORY_MSG_468;PS - Fill holes !HISTORY_MSG_469;PS - Median -!HISTORY_MSG_471;PS - Motion correction -!HISTORY_MSG_472;PS - Smooth transitions !HISTORY_MSG_473;PS - Use LMMSE -!HISTORY_MSG_474;PS - Equalize -!HISTORY_MSG_475;PS - Equalize channel !HISTORY_MSG_476;CAM02 - Temp out !HISTORY_MSG_477;CAM02 - Green out !HISTORY_MSG_478;CAM02 - Yb out @@ -1592,20 +2054,9 @@ ZOOMPANEL_ZOOMOUT;Oddal\nSkrót: - !HISTORY_MSG_482;CAM02 - Green scene !HISTORY_MSG_483;CAM02 - Yb scene !HISTORY_MSG_484;CAM02 - Auto Yb scene -!HISTORY_MSG_485;Lens Correction -!HISTORY_MSG_486;Lens Correction - Camera -!HISTORY_MSG_487;Lens Correction - Lens !HISTORY_MSG_488;Dynamic Range Compression -!HISTORY_MSG_489;DRC - Detail -!HISTORY_MSG_490;DRC - Amount -!HISTORY_MSG_491;White Balance -!HISTORY_MSG_492;RGB Curves !HISTORY_MSG_493;L*a*b* Adjustments !HISTORY_MSG_494;Capture Sharpening -!HISTORY_MSG_CLAMPOOG;Clip out-of-gamut colors -!HISTORY_MSG_COLORTONING_LABGRID_VALUE;CT - Color correction -!HISTORY_MSG_COLORTONING_LABREGION_AB;CT - Color correction -!HISTORY_MSG_COLORTONING_LABREGION_CHANNEL;CT - Channel !HISTORY_MSG_COLORTONING_LABREGION_CHROMATICITYMASK;CT - region C mask !HISTORY_MSG_COLORTONING_LABREGION_HUEMASK;CT - H mask !HISTORY_MSG_COLORTONING_LABREGION_LIGHTNESS;CT - Lightness @@ -1614,14 +2065,8 @@ ZOOMPANEL_ZOOMOUT;Oddal\nSkrót: - !HISTORY_MSG_COLORTONING_LABREGION_MASKBLUR;CT - region mask blur !HISTORY_MSG_COLORTONING_LABREGION_OFFSET;CT - region offset !HISTORY_MSG_COLORTONING_LABREGION_POWER;CT - region power -!HISTORY_MSG_COLORTONING_LABREGION_SATURATION;CT - Saturation !HISTORY_MSG_COLORTONING_LABREGION_SHOWMASK;CT - region show mask !HISTORY_MSG_COLORTONING_LABREGION_SLOPE;CT - region slope -!HISTORY_MSG_DEHAZE_DEPTH;Dehaze - Depth -!HISTORY_MSG_DEHAZE_ENABLED;Haze Removal -!HISTORY_MSG_DEHAZE_LUMINANCE;Dehaze - Luminance only -!HISTORY_MSG_DEHAZE_SHOW_DEPTH_MAP;Dehaze - Show depth map -!HISTORY_MSG_DEHAZE_STRENGTH;Dehaze - Strength !HISTORY_MSG_DUALDEMOSAIC_AUTO_CONTRAST;Dual demosaic - Auto threshold !HISTORY_MSG_DUALDEMOSAIC_CONTRAST;Dual demosaic - Contrast threshold !HISTORY_MSG_FILMNEGATIVE_ENABLED;Film Negative @@ -1633,120 +2078,39 @@ ZOOMPANEL_ZOOMOUT;Oddal\nSkrót: - !HISTORY_MSG_ICM_WORKING_GAMMA;Working - Gamma !HISTORY_MSG_ICM_WORKING_SLOPE;Working - Slope !HISTORY_MSG_ICM_WORKING_TRC_METHOD;Working - TRC method -!HISTORY_MSG_LOCALCONTRAST_AMOUNT;Local Contrast - Amount -!HISTORY_MSG_LOCALCONTRAST_DARKNESS;Local Contrast - Darkness -!HISTORY_MSG_LOCALCONTRAST_ENABLED;Local Contrast -!HISTORY_MSG_LOCALCONTRAST_LIGHTNESS;Local Contrast - Lightness -!HISTORY_MSG_LOCALCONTRAST_RADIUS;Local Contrast - Radius !HISTORY_MSG_METADATA_MODE;Metadata copy mode -!HISTORY_MSG_MICROCONTRAST_CONTRAST;Microcontrast - Contrast threshold -!HISTORY_MSG_PDSHARPEN_AUTO_CONTRAST;CS - Auto threshold -!HISTORY_MSG_PDSHARPEN_AUTO_RADIUS;CS - Auto radius -!HISTORY_MSG_PDSHARPEN_CHECKITER;CS - Auto limit iterations -!HISTORY_MSG_PDSHARPEN_CONTRAST;CS - Contrast threshold -!HISTORY_MSG_PDSHARPEN_ITERATIONS;CS - Iterations -!HISTORY_MSG_PDSHARPEN_RADIUS;CS - Radius !HISTORY_MSG_PDSHARPEN_RADIUS_BOOST;CS - Corner radius boost !HISTORY_MSG_PIXELSHIFT_DEMOSAIC;PS - Demosaic method for motion !HISTORY_MSG_PREPROCESS_LINEDENOISE_DIRECTION;Line noise filter direction !HISTORY_MSG_PREPROCESS_PDAFLINESFILTER;PDAF lines filter -!HISTORY_MSG_PRSHARPEN_CONTRAST;PRS - Contrast threshold -!HISTORY_MSG_RAWCACORR_AUTOIT;Raw CA Correction - Iterations -!HISTORY_MSG_RAWCACORR_COLORSHIFT;Raw CA Correction - Avoid color shift !HISTORY_MSG_RAW_BORDER;Raw border !HISTORY_MSG_RESIZE_ALLOWUPSCALING;Resize - Allow upscaling -!HISTORY_MSG_SHARPENING_BLUR;Sharpening - Blur radius -!HISTORY_MSG_SHARPENING_CONTRAST;Sharpening - Contrast threshold -!HISTORY_MSG_SH_COLORSPACE;S/H - Colorspace -!HISTORY_MSG_SOFTLIGHT_ENABLED;Soft light -!HISTORY_MSG_SOFTLIGHT_STRENGTH;Soft light - Strength !HISTORY_MSG_TM_FATTAL_ANCHOR;DRC - Anchor -!ICCPROFCREATOR_COPYRIGHT;Copyright: -!ICCPROFCREATOR_COPYRIGHT_RESET_TOOLTIP;Reset to the default copyright, granted to "RawTherapee, CC0" -!ICCPROFCREATOR_CUSTOM;Custom -!ICCPROFCREATOR_DESCRIPTION;Description: !ICCPROFCREATOR_DESCRIPTION_ADDPARAM;Append gamma and slope values to the description !ICCPROFCREATOR_DESCRIPTION_TOOLTIP;Leave empty to set the default description. -!ICCPROFCREATOR_GAMMA;Gamma -!ICCPROFCREATOR_ICCVERSION;ICC version: !ICCPROFCREATOR_ILL;Illuminant: -!ICCPROFCREATOR_ILL_41;D41 -!ICCPROFCREATOR_ILL_50;D50 -!ICCPROFCREATOR_ILL_55;D55 -!ICCPROFCREATOR_ILL_60;D60 -!ICCPROFCREATOR_ILL_65;D65 -!ICCPROFCREATOR_ILL_80;D80 -!ICCPROFCREATOR_ILL_DEF;Default -!ICCPROFCREATOR_ILL_INC;StdA 2856K !ICCPROFCREATOR_ILL_TOOLTIP;You can only set the illuminant for ICC v4 profiles. !ICCPROFCREATOR_PRIMARIES;Primaries: -!ICCPROFCREATOR_PRIM_ACESP0;ACES AP0 -!ICCPROFCREATOR_PRIM_ACESP1;ACES AP1 -!ICCPROFCREATOR_PRIM_ADOBE;Adobe RGB (1998) -!ICCPROFCREATOR_PRIM_BEST;BestRGB -!ICCPROFCREATOR_PRIM_BETA;BetaRGB -!ICCPROFCREATOR_PRIM_BLUX;Blue X -!ICCPROFCREATOR_PRIM_BLUY;Blue Y -!ICCPROFCREATOR_PRIM_BRUCE;BruceRGB -!ICCPROFCREATOR_PRIM_GREX;Green X -!ICCPROFCREATOR_PRIM_GREY;Green Y -!ICCPROFCREATOR_PRIM_PROPH;Prophoto -!ICCPROFCREATOR_PRIM_REC2020;Rec2020 -!ICCPROFCREATOR_PRIM_REDX;Red X -!ICCPROFCREATOR_PRIM_REDY;Red Y -!ICCPROFCREATOR_PRIM_SRGB;sRGB !ICCPROFCREATOR_PRIM_TOOLTIP;You can only set custom primaries for ICC v4 profiles. -!ICCPROFCREATOR_PRIM_WIDEG;Widegamut -!ICCPROFCREATOR_PROF_V2;ICC v2 -!ICCPROFCREATOR_PROF_V4;ICC v4 -!ICCPROFCREATOR_SAVEDIALOG_TITLE;Save ICC profile as... -!ICCPROFCREATOR_SLOPE;Slope -!ICCPROFCREATOR_TRC_PRESET;Tone response curve: !IPTCPANEL_CATEGORYHINT;Identifies the subject of the image in the opinion of the provider. -!IPTCPANEL_CITYHINT;Enter the name of the city pictured in this image. -!IPTCPANEL_COPYRIGHT;Copyright notice -!IPTCPANEL_COPYRIGHTHINT;Enter a Notice on the current owner of the Copyright for this image, such as ©2008 Jane Doe. -!IPTCPANEL_COUNTRYHINT;Enter the name of the country pictured in this image. -!IPTCPANEL_CREATOR;Creator -!IPTCPANEL_CREATORHINT;Enter the name of the person that created this image. !IPTCPANEL_CREATORJOBTITLE;Creator's job title !IPTCPANEL_CREATORJOBTITLEHINT;Enter the Job Title of the person listed in the Creator field. -!IPTCPANEL_DATECREATEDHINT;Enter the Date the image was taken. -!IPTCPANEL_DESCRIPTION;Description !IPTCPANEL_DESCRIPTIONHINT;Enter a "caption" describing the who, what, and why of what is happening in this image, this might include names of people, and/or their role in the action that is taking place within the image. -!IPTCPANEL_DESCRIPTIONWRITER;Description writer !IPTCPANEL_DESCRIPTIONWRITERHINT;Enter the name of the person involved in writing, editing or correcting the description of the image. !IPTCPANEL_HEADLINEHINT;Enter a brief publishable synopsis or summary of the contents of the image. !IPTCPANEL_INSTRUCTIONSHINT;Enter information about embargoes, or other restrictions not covered by the Copyright field. !IPTCPANEL_KEYWORDSHINT;Enter any number of keywords, terms or phrases used to express the subject matter in the image. -!IPTCPANEL_PROVINCE;Province or state !IPTCPANEL_PROVINCEHINT;Enter the name of the province or state pictured in this image. !IPTCPANEL_SOURCEHINT;Enter or edit the name of a person or party who has a role in the content supply chain, such as a person or entity from whom you received this image from. -!IPTCPANEL_SUPPCATEGORIES;Supplemental categories !IPTCPANEL_SUPPCATEGORIESHINT;Further refines the subject of the image. !IPTCPANEL_TITLEHINT;Enter a short verbal and human readable name for the image, this may be the file name. -!IPTCPANEL_TRANSREFERENCE;Job ID -!IPTCPANEL_TRANSREFERENCEHINT;Enter a number or identifier needed for workflow control or tracking. -!MAIN_BUTTON_ICCPROFCREATOR;ICC Profile Creator -!MAIN_BUTTON_SENDTOEDITOR;Edit image in external editor -!MAIN_FRAME_PLACES_DEL;Remove -!MAIN_MSG_TOOMANYOPENEDITORS;Too many open editors.\nPlease close an editor to continue. -!MAIN_TAB_ADVANCED;Advanced -!MAIN_TAB_ADVANCED_TOOLTIP;Shortcut: Alt-a -!MAIN_TAB_FAVORITES;Favorites -!MAIN_TAB_FAVORITES_TOOLTIP;Shortcut: Alt-u -!MAIN_TAB_INSPECT; Inspect !MAIN_TOOLTIP_BACKCOLOR3;Background color of the preview: middle grey\nShortcut: 9 !MAIN_TOOLTIP_PREVIEWSHARPMASK;Preview the sharpening contrast mask.\nShortcut: p\n\nOnly works when sharpening is enabled and zoom >= 100%. -!MONITOR_PROFILE_SYSTEM;System default !OPTIONS_BUNDLED_MISSING;The bundled profile "%1" could not be found!\n\nYour installation could be damaged.\n\nDefault internal values will be used instead. !OPTIONS_DEFIMG_MISSING;The default profile for non-raw photos could not be found or is not set.\n\nPlease check your profiles' directory, it may be missing or damaged.\n\n"%1" will be used instead. !OPTIONS_DEFRAW_MISSING;The default profile for raw photos could not be found or is not set.\n\nPlease check your profiles' directory, it may be missing or damaged.\n\n"%1" will be used instead. -!PARTIALPASTE_ADVANCEDGROUP;Advanced Settings -!PARTIALPASTE_DEHAZE;Haze removal !PARTIALPASTE_EQUALIZER;Wavelet levels !PARTIALPASTE_FILMNEGATIVE;Film Negative -!PARTIALPASTE_LOCALCONTRAST;Local contrast !PARTIALPASTE_METADATA;Metadata mode !PARTIALPASTE_PREPROCESS_PDAFLINESFILTER;PDAF lines filter !PARTIALPASTE_PRSHARPENING;Post-resize sharpening @@ -1755,200 +2119,65 @@ ZOOMPANEL_ZOOMOUT;Oddal\nSkrót: - !PARTIALPASTE_RAW_BORDER;Raw border !PARTIALPASTE_RAW_IMAGENUM;Sub-image !PARTIALPASTE_RAW_PIXELSHIFT;Pixel Shift -!PARTIALPASTE_RETINEX;Retinex -!PARTIALPASTE_SOFTLIGHT;Soft light -!PARTIALPASTE_TM_FATTAL;Dynamic range compression -!PREFERENCES_APPEARANCE;Appearance -!PREFERENCES_APPEARANCE_COLORPICKERFONT;Color picker font -!PREFERENCES_APPEARANCE_CROPMASKCOLOR;Crop mask color -!PREFERENCES_APPEARANCE_MAINFONT;Main font -!PREFERENCES_APPEARANCE_PSEUDOHIDPI;Pseudo-HiDPI mode -!PREFERENCES_APPEARANCE_THEME;Theme !PREFERENCES_AUTOSAVE_TP_OPEN;Save tool collapsed/expanded state on exit -!PREFERENCES_CACHECLEAR;Clear -!PREFERENCES_CACHECLEAR_ALL;Clear all cached files: !PREFERENCES_CACHECLEAR_ALLBUTPROFILES;Clear all cached files except for cached processing profiles: -!PREFERENCES_CACHECLEAR_ONLYPROFILES;Clear only cached processing profiles: !PREFERENCES_CACHECLEAR_SAFETY;Only files in the cache are cleared. Processing profiles stored alongside the source images are not touched. -!PREFERENCES_CHUNKSIZES;Tiles per thread -!PREFERENCES_CHUNKSIZE_RAW_AMAZE;AMaZE demosaic -!PREFERENCES_CHUNKSIZE_RAW_CA;Raw CA correction -!PREFERENCES_CHUNKSIZE_RAW_RCD;RCD demosaic -!PREFERENCES_CHUNKSIZE_RAW_XT;Xtrans demosaic -!PREFERENCES_CHUNKSIZE_RGB;RGB processing -!PREFERENCES_CLUTSCACHE;HaldCLUT Cache !PREFERENCES_CLUTSCACHE_LABEL;Maximum number of cached CLUTs -!PREFERENCES_CMMBPC;Black point compensation -!PREFERENCES_CROP;Crop Editing -!PREFERENCES_CROP_AUTO_FIT;Automatically zoom to fit the crop -!PREFERENCES_CROP_GUIDES;Guides shown when not editing the crop -!PREFERENCES_CROP_GUIDES_FRAME;Frame -!PREFERENCES_CROP_GUIDES_FULL;Original -!PREFERENCES_CROP_GUIDES_NONE;None -!PREFERENCES_CURVEBBOXPOS;Position of curve copy & paste buttons -!PREFERENCES_CURVEBBOXPOS_ABOVE;Above -!PREFERENCES_CURVEBBOXPOS_BELOW;Below -!PREFERENCES_CURVEBBOXPOS_LEFT;Left -!PREFERENCES_CURVEBBOXPOS_RIGHT;Right -!PREFERENCES_DIRECTORIES;Directories -!PREFERENCES_EDITORCMDLINE;Custom command line -!PREFERENCES_FILEBROWSERTOOLBARSINGLEROW;Compact toolbars in File Browser !PREFERENCES_FSTRIP_SAME_THUMB_HEIGHT;Same thumbnail height between the Filmstrip and the File Browser !PREFERENCES_FSTRIP_SAME_THUMB_HEIGHT_HINT;Having separate thumbnail size will require more processing time each time you'll switch between the single Editor tab and the File Browser. -!PREFERENCES_INSPECT_LABEL;Inspect -!PREFERENCES_INSPECT_MAXBUFFERS_LABEL;Maximum number of cached images !PREFERENCES_INSPECT_MAXBUFFERS_TOOLTIP;Set the maximum number of images stored in cache when hovering over them in the File Browser; systems with little RAM (2GB) should keep this value set to 1 or 2. -!PREFERENCES_LANG;Language -!PREFERENCES_MAXRECENTFOLDERS;Maximum number of recent folders !PREFERENCES_MONINTENT;Default rendering intent -!PREFERENCES_MONITOR;Monitor -!PREFERENCES_MONPROFILE;Default color profile -!PREFERENCES_MONPROFILE_WARNOSX;Due to MacOS limitations, only sRGB is supported. -!PREFERENCES_NAVIGATIONFRAME;Navigation -!PREFERENCES_OVERLAY_FILENAMES_FILMSTRIP;Overlay filenames on thumbnails in the editor pannel -!PREFERENCES_PARSEDEXTDOWNHINT;Move selected extension down in the list. -!PREFERENCES_PARSEDEXTUPHINT;Move selected extension up in the list. -!PREFERENCES_PERFORMANCE_MEASURE;Measure !PREFERENCES_PERFORMANCE_MEASURE_HINT;Logs processing times in console -!PREFERENCES_PERFORMANCE_THREADS;Threads !PREFERENCES_PERFORMANCE_THREADS_LABEL;Maximum number of threads for Noise Reduction and Wavelet Levels (0 = Automatic) -!PREFERENCES_PREVDEMO;Preview Demosaic Method -!PREFERENCES_PREVDEMO_FAST;Fast -!PREFERENCES_PREVDEMO_LABEL;Demosaicing method used for the preview at <100% zoom: -!PREFERENCES_PREVDEMO_SIDECAR;As in PP3 !PREFERENCES_PRINTER;Printer (Soft-Proofing) !PREFERENCES_PROFILESAVEBOTH;Save processing profile both to the cache and next to the input file -!PREFERENCES_PROFILESAVELOCATION;Processing profile saving location -!PREFERENCES_PROFILE_NONE;None !PREFERENCES_PRTINTENT;Rendering intent -!PREFERENCES_PRTPROFILE;Color profile !PREFERENCES_REMEMBERZOOMPAN;Remember zoom % and pan offset !PREFERENCES_REMEMBERZOOMPAN_TOOLTIP;Remember the zoom % and pan offset of the current image when opening a new image.\n\nThis option only works in "Single Editor Tab Mode" and when "Demosaicing method used for the preview at <100% zoom" is set to "As in PP3". !PREFERENCES_SAVE_TP_OPEN_NOW;Save tool collapsed/expanded state now -!PREFERENCES_SERIALIZE_TIFF_READ;TIFF Read Settings !PREFERENCES_SERIALIZE_TIFF_READ_LABEL;Serialize reading of TIFF files !PREFERENCES_SERIALIZE_TIFF_READ_TOOLTIP;Enabling this option when working with folders containing uncompressed TIFF files can increase performance of thumbnail generation. !PREFERENCES_SHOWFILMSTRIPTOOLBAR;Show Filmstrip toolbar !PREFERENCES_TAB_DYNAMICPROFILE;Dynamic Profile Rules -!PREFERENCES_TAB_PERFORMANCE;Performance !PREFERENCES_THUMBNAIL_INSPECTOR_JPEG;Embedded JPEG preview -!PREFERENCES_THUMBNAIL_INSPECTOR_MODE;Image to show !PREFERENCES_THUMBNAIL_INSPECTOR_RAW;Neutral raw rendering !PREFERENCES_THUMBNAIL_INSPECTOR_RAW_IF_NO_JPEG_FULLSIZE;Embedded JPEG if fullsize, neutral raw otherwise -!PROFILEPANEL_PDYNAMIC;Dynamic -!PROGRESSBAR_DECODING;Decoding... -!PROGRESSBAR_GREENEQUIL;Green equilibration... -!PROGRESSBAR_HLREC;Highlight reconstruction... -!PROGRESSBAR_HOTDEADPIXELFILTER;Hot/dead pixel filter... -!PROGRESSBAR_LINEDENOISE;Line noise filter... -!PROGRESSBAR_RAWCACORR;Raw CA correction... -!QINFO_FRAMECOUNT;%2 frames -!QINFO_HDR;HDR / %2 frame(s) -!QINFO_PIXELSHIFT;Pixel Shift / %2 frame(s) -!QUEUE_LOCATION_TITLE;Output Location !QUEUE_STARTSTOP_TOOLTIP;Start or stop processing the images in the queue.\n\nShortcut: Ctrl+s -!SAMPLEFORMAT_0;Unknown data format -!SAMPLEFORMAT_1;8-bit unsigned -!SAMPLEFORMAT_2;16-bit unsigned -!SAMPLEFORMAT_4;24-bit LogLuv -!SAMPLEFORMAT_8;32-bit LogLuv -!SAMPLEFORMAT_16;16-bit floating-point -!SAMPLEFORMAT_32;24-bit floating-point -!SAMPLEFORMAT_64;32-bit floating-point -!SAVEDLG_FILEFORMAT_FLOAT; floating-point !SAVEDLG_SUBSAMP_TOOLTIP;Best compression:\nJ:a:b 4:2:0\nh/v 2/2\nChroma halved horizontally and vertically.\n\nBalanced:\nJ:a:b 4:2:2\nh/v 2/1\nChroma halved horizontally.\n\nBest quality:\nJ:a:b 4:4:4\nh/v 1/1\nNo chroma subsampling. !SOFTPROOF_GAMUTCHECK_TOOLTIP;Highlight pixels with out-of-gamut colors with respect to:\n- the printer profile, if one is set and soft-proofing is enabled,\n- the output profile, if a printer profile is not set and soft-proofing is enabled,\n- the monitor profile, if soft-proofing is disabled. !SOFTPROOF_TOOLTIP;Soft-proofing simulates the appearance of the image:\n- when printed, if a printer profile is set in Preferences > Color Management,\n- when viewed on a display that uses the current output profile, if a printer profile is not set. !TOOLBAR_TOOLTIP_COLORPICKER;Lockable Color Picker\n\nWhen the tool is active:\n- Add a picker: left-click.\n- Drag a picker: left-click and drag.\n- Delete a picker: right-click.\n- Delete all pickers: Ctrl+Shift+right-click.\n- Revert to hand tool: right-click outside any picker. -!TP_BWMIX_MIXC;Channel Mixer -!TP_BWMIX_NEUTRAL;Reset -!TP_CBDL_AFT;After Black-and-White -!TP_CBDL_BEF;Before Black-and-White -!TP_CBDL_METHOD;Process located !TP_CBDL_METHOD_TOOLTIP;Choose whether the Contrast by Detail Levels tool is to be positioned after the Black-and-White tool, which makes it work in L*a*b* space, or before it, which makes it work in RGB space. -!TP_COLORAPP_ABSOLUTELUMINANCE;Absolute luminance !TP_COLORAPP_CAT02ADAPTATION_TOOLTIP;When setting manually, values above 65 are recommended. !TP_COLORAPP_FREE;Free temp+green + CAT02 + [output] !TP_COLORAPP_MEANLUMINANCE;Mean luminance (Yb%) -!TP_COLORAPP_NEUTRAL;Reset -!TP_COLORAPP_NEUTRAL_TIP;Reset all sliders checkbox and curves to their default values !TP_COLORAPP_TEMP_TOOLTIP;To select an illuminant, always set Tint=1.\n\nA temp=2856\nD50 temp=5003\nD55 temp=5503\nD65 temp=6504\nD75 temp=7504 !TP_COLORTONING_LABGRID;L*a*b* color correction grid !TP_COLORTONING_LABGRID_VALUES;HL: a=%1 b=%2\nS: a=%3 b=%4 !TP_COLORTONING_LABREGIONS;Color correction regions !TP_COLORTONING_LABREGION_ABVALUES;a=%1 b=%2 -!TP_COLORTONING_LABREGION_CHANNEL;Channel -!TP_COLORTONING_LABREGION_CHANNEL_ALL;All -!TP_COLORTONING_LABREGION_CHANNEL_B;Blue -!TP_COLORTONING_LABREGION_CHANNEL_G;Green -!TP_COLORTONING_LABREGION_CHANNEL_R;Red -!TP_COLORTONING_LABREGION_CHROMATICITYMASK;C -!TP_COLORTONING_LABREGION_HUEMASK;H !TP_COLORTONING_LABREGION_LIGHTNESS;Lightness -!TP_COLORTONING_LABREGION_LIGHTNESSMASK;L -!TP_COLORTONING_LABREGION_LIST_TITLE;Correction -!TP_COLORTONING_LABREGION_MASK;Mask -!TP_COLORTONING_LABREGION_MASKBLUR;Mask Blur -!TP_COLORTONING_LABREGION_OFFSET;Offset -!TP_COLORTONING_LABREGION_POWER;Power -!TP_COLORTONING_LABREGION_SATURATION;Saturation -!TP_COLORTONING_LABREGION_SHOWMASK;Show mask -!TP_COLORTONING_LABREGION_SLOPE;Slope !TP_CROP_GTHARMMEANS;Harmonic Means !TP_CROP_GTTRIANGLE1;Golden Triangles 1 !TP_CROP_GTTRIANGLE2;Golden Triangles 2 -!TP_CROP_PPI;PPI -!TP_CROP_RESETCROP;Reset -!TP_CROP_SELECTCROP;Select -!TP_DEHAZE_DEPTH;Depth -!TP_DEHAZE_LABEL;Haze Removal -!TP_DEHAZE_LUMINANCE;Luminance only -!TP_DEHAZE_SHOW_DEPTH_MAP;Show depth map -!TP_DEHAZE_STRENGTH;Strength !TP_DIRPYRDENOISE_CHROMINANCE_AMZ;Auto multi-zones -!TP_DIRPYRDENOISE_CHROMINANCE_AUTOGLOBAL;Automatic global -!TP_DIRPYRDENOISE_CHROMINANCE_CURVE;Chrominance curve !TP_DIRPYRDENOISE_CHROMINANCE_CURVE_TOOLTIP;Increase (multiply) the value of all chrominance sliders.\nThis curve lets you adjust the strength of chromatic noise reduction as a function of chromaticity, for instance to increase the action in areas of low saturation and to decrease it in those of high saturation. -!TP_DIRPYRDENOISE_CHROMINANCE_FRAME;Chrominance -!TP_DIRPYRDENOISE_CHROMINANCE_MANUAL;Manual -!TP_DIRPYRDENOISE_CHROMINANCE_METHOD;Method !TP_DIRPYRDENOISE_CHROMINANCE_METHODADVANCED_TOOLTIP;Manual\nActs on the full image.\nYou control the noise reduction settings manually.\n\nAutomatic global\nActs on the full image.\n9 zones are used to calculate a global chrominance noise reduction setting.\n\nPreview\nActs on the whole image.\nThe part of the image visible in the preview is used to calculate global chrominance noise reduction settings. !TP_DIRPYRDENOISE_CHROMINANCE_METHOD_TOOLTIP;Manual\nActs on the full image.\nYou control the noise reduction settings manually.\n\nAutomatic global\nActs on the full image.\n9 zones are used to calculate a global chrominance noise reduction setting.\n\nAutomatic multi-zones\nNo preview - works only during saving, but using the "Preview" method by matching the tile size and center to the preview size and center you can get an idea of the expected results.\nThe image is divided into tiles (about 10 to 70 depending on image size) and each tile receives its own chrominance noise reduction settings.\n\nPreview\nActs on the whole image.\nThe part of the image visible in the preview is used to calculate global chrominance noise reduction settings. !TP_DIRPYRDENOISE_CHROMINANCE_PMZ;Preview multi-zones -!TP_DIRPYRDENOISE_CHROMINANCE_PREVIEW;Preview !TP_DIRPYRDENOISE_CHROMINANCE_PREVIEWRESIDUAL_INFO_TOOLTIP;Displays the remaining noise levels of the part of the image visible in the preview after wavelet.\n\n>300 Very noisy\n100-300 Noisy\n50-100 A little noisy\n<50 Very low noise\n\nBeware, the values will differ between RGB and L*a*b* mode. The RGB values are less accurate because the RGB mode does not completely separate luminance and chrominance. !TP_DIRPYRDENOISE_CHROMINANCE_PREVIEW_INFO;Preview size=%1, Center: Px=%2 Py=%3 !TP_DIRPYRDENOISE_CHROMINANCE_PREVIEW_NOISEINFO;Preview noise: Mean=%1 High=%2 !TP_DIRPYRDENOISE_CHROMINANCE_PREVIEW_NOISEINFO_EMPTY;Preview noise: Mean= - High= - !TP_DIRPYRDENOISE_CHROMINANCE_PREVIEW_TILEINFO;Tile size=%1, Center: Tx=%2 Ty=%3 -!TP_DIRPYRDENOISE_LABEL;Noise Reduction -!TP_DIRPYRDENOISE_LUMINANCE_CONTROL;Luminance control -!TP_DIRPYRDENOISE_LUMINANCE_FRAME;Luminance -!TP_DIRPYRDENOISE_MAIN_COLORSPACE_LAB;L*a*b* -!TP_DIRPYRDENOISE_MEDIAN_METHOD_CHROMINANCE;Chroma only !TP_DIRPYRDENOISE_MEDIAN_METHOD_WEIGHTED;Weighted L* (little) + a*b* (normal) !TP_DIRPYRDENOISE_MEDIAN_PASSES_TOOLTIP;Applying three median filter iterations with a 3×3 window size often leads to better results than using one median filter iteration with a 7×7 window size. !TP_DIRPYRDENOISE_MEDIAN_TYPE_TOOLTIP;Apply a median filter of the desired window size. The larger the window's size, the longer it takes.\n\n3×3 soft: treats 5 pixels in a 3×3 pixel window.\n3×3: treats 9 pixels in a 3×3 pixel window.\n5×5 soft: treats 13 pixels in a 5×5 pixel window.\n5×5: treats 25 pixels in a 5×5 pixel window.\n7×7: treats 49 pixels in a 7×7 pixel window.\n9×9: treats 81 pixels in a 9×9 pixel window.\n\nSometimes it is possible to achieve higher quality running several iterations with a smaller window size than one iteration with a larger one. -!TP_DIRPYRDENOISE_TYPE_3X3;3×3 -!TP_DIRPYRDENOISE_TYPE_3X3SOFT;3×3 soft -!TP_DIRPYRDENOISE_TYPE_5X5;5×5 -!TP_DIRPYRDENOISE_TYPE_5X5SOFT;5×5 soft -!TP_DIRPYRDENOISE_TYPE_7X7;7×7 -!TP_DIRPYRDENOISE_TYPE_9X9;9×9 -!TP_DIRPYREQUALIZER_ARTIF;Reduce artifacts !TP_DISTORTION_AUTO_TIP;Automatically corrects lens distortion in raw files by matching it against the embedded JPEG image if one exists and has had its lens disortion auto-corrected by the camera. -!TP_EPD_GAMMA;Gamma -!TP_EXPOSURE_CLAMPOOG;Clip out-of-gamut colors !TP_EXPOSURE_HISTMATCHING;Auto-Matched Tone Curve !TP_EXPOSURE_HISTMATCHING_TOOLTIP;Automatically adjust sliders and curves (except exposure compensation) to match the look of the embedded JPEG thumbnail. -!TP_EXPOSURE_TCMODE_LUMINANCE;Luminance -!TP_EXPOSURE_TCMODE_PERCEPTUAL;Perceptual -!TP_FILMNEGATIVE_BLUE;Blue ratio !TP_FILMNEGATIVE_GREEN;Reference exponent (contrast) !TP_FILMNEGATIVE_GUESS_TOOLTIP;Automatically set the red and blue ratios by picking two patches which had a neutral hue (no color) in the original scene. The patches should differ in brightness. Set the white balance afterwards. -!TP_FILMNEGATIVE_LABEL;Film Negative -!TP_FILMNEGATIVE_PICK;Pick neutral spots -!TP_FILMNEGATIVE_RED;Red ratio !TP_FILMSIMULATION_SLOWPARSEDIR;RawTherapee is configured to look for Hald CLUT images, which are used for the Film Simulation tool, in a folder which is taking too long to load.\nGo to Preferences > Image Processing > Film Simulation\nto see which folder is being used. You should either point RawTherapee to a folder which contains only Hald CLUT images and nothing more, or to an empty folder if you don't want to use the Film Simulation tool.\n\nRead the Film Simulation article in RawPedia for more information.\n\nDo you want to cancel the scan now? !TP_ICM_APPLYBASELINEEXPOSUREOFFSET;Baseline exposure !TP_ICM_APPLYBASELINEEXPOSUREOFFSET_TOOLTIP;Employ the embedded DCP baseline exposure offset. The setting is only available if the selected DCP has one. @@ -1956,168 +2185,60 @@ ZOOMPANEL_ZOOMOUT;Oddal\nSkrót: - !TP_ICM_APPLYHUESATMAP_TOOLTIP;Employ the embedded DCP base table (HueSatMap). The setting is only available if the selected DCP has one. !TP_ICM_APPLYLOOKTABLE;Look table !TP_ICM_APPLYLOOKTABLE_TOOLTIP;Employ the embedded DCP look table. The setting is only available if the selected DCP has one. -!TP_ICM_BPC;Black Point Compensation !TP_ICM_PROFILEINTENT;Rendering Intent !TP_ICM_SAVEREFERENCE;Save Reference Image -!TP_ICM_SAVEREFERENCE_APPLYWB;Apply white balance !TP_ICM_SAVEREFERENCE_APPLYWB_TOOLTIP;Generally, apply the white balance when saving images to create ICC profiles, and do not apply the white balance to create DCP profiles. -!TP_ICM_WORKING_TRC;Tone response curve: -!TP_ICM_WORKING_TRC_CUSTOM;Custom -!TP_ICM_WORKING_TRC_GAMMA;Gamma -!TP_ICM_WORKING_TRC_NONE;None -!TP_ICM_WORKING_TRC_SLOPE;Slope -!TP_ICM_WORKING_TRC_TOOLTIP;Only for built-in profiles. -!TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected -!TP_LENSPROFILE_CORRECTION_LCPFILE;LCP file -!TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected !TP_LENSPROFILE_LENS_WARNING;Warning: the crop factor used for lens profiling is larger than the crop factor of the camera, the results might be wrong. -!TP_LENSPROFILE_MODE_HEADER;Lens Profile -!TP_LENSPROFILE_USE_CA;Chromatic aberration -!TP_LENSPROFILE_USE_GEOMETRIC;Geometric distortion -!TP_LENSPROFILE_USE_HEADER;Correct -!TP_LENSPROFILE_USE_VIGNETTING;Vignetting -!TP_LOCALCONTRAST_AMOUNT;Amount -!TP_LOCALCONTRAST_DARKNESS;Darkness level -!TP_LOCALCONTRAST_LABEL;Local Contrast -!TP_LOCALCONTRAST_LIGHTNESS;Lightness level -!TP_LOCALCONTRAST_RADIUS;Radius -!TP_METADATA_EDIT;Apply modifications -!TP_METADATA_MODE;Metadata copy mode -!TP_METADATA_STRIP;Strip all metadata -!TP_METADATA_TUNNEL;Copy unchanged -!TP_NEUTRAL;Reset !TP_PDSHARPENING_LABEL;Capture Sharpening -!TP_PREPROCESS_LINEDENOISE_DIRECTION;Direction -!TP_PREPROCESS_LINEDENOISE_DIRECTION_BOTH;Both -!TP_PREPROCESS_LINEDENOISE_DIRECTION_HORIZONTAL;Horizontal !TP_PREPROCESS_LINEDENOISE_DIRECTION_PDAF_LINES;Horizontal only on PDAF rows -!TP_PREPROCESS_LINEDENOISE_DIRECTION_VERTICAL;Vertical !TP_PREPROCESS_PDAFLINESFILTER;PDAF lines filter -!TP_PRSHARPENING_LABEL;Post-Resize Sharpening !TP_PRSHARPENING_TOOLTIP;Sharpens the image after resizing. Only works when the "Lanczos" resizing method is used. It is impossible to preview the effects of this tool. See RawPedia for usage instructions. -!TP_RAWCACORR_AUTOIT;Iterations !TP_RAWCACORR_AUTOIT_TOOLTIP;This setting is available if "Auto-correction" is checked.\nAuto-correction is conservative, meaning that it often does not correct all chromatic aberration.\nTo correct the remaining chromatic aberration, you can use up to five iterations of automatic chromatic aberration correction.\nEach iteration will reduce the remaining chromatic aberration from the last iteration at the cost of additional processing time. -!TP_RAWCACORR_AVOIDCOLORSHIFT;Avoid color shift -!TP_RAW_1PASSMEDIUM;1-pass (Markesteijn) -!TP_RAW_2PASS;1-pass+fast -!TP_RAW_3PASSBEST;3-pass (Markesteijn) -!TP_RAW_4PASS;3-pass+fast -!TP_RAW_AHD;AHD -!TP_RAW_AMAZE;AMaZE -!TP_RAW_AMAZEVNG4;AMaZE+VNG4 !TP_RAW_BORDER;Border -!TP_RAW_DCB;DCB -!TP_RAW_DCBVNG4;DCB+VNG4 -!TP_RAW_DUALDEMOSAICAUTOCONTRAST;Auto threshold !TP_RAW_DUALDEMOSAICAUTOCONTRAST_TOOLTIP;If the checkbox is checked (recommended), RawTherapee calculates an optimum value based on flat regions in the image.\nIf there is no flat region in the image or the image is too noisy, the value will be set to 0.\nTo set the value manually, uncheck the checkbox first (reasonable values depend on the image). -!TP_RAW_DUALDEMOSAICCONTRAST;Contrast threshold -!TP_RAW_EAHD;EAHD -!TP_RAW_FAST;Fast -!TP_RAW_HD;Threshold !TP_RAW_HD_TOOLTIP;Lower values make hot/dead pixel detection more aggressive, but false positives may lead to artifacts. If you notice any artifacts appearing when enabling the Hot/Dead Pixel Filters, gradually increase the threshold value until they disappear. -!TP_RAW_HPHD;HPHD -!TP_RAW_IGV;IGV !TP_RAW_IMAGENUM;Sub-image !TP_RAW_IMAGENUM_SN;SN mode !TP_RAW_IMAGENUM_TOOLTIP;Some raw files consist of several sub-images (Pentax/Sony Pixel Shift, Pentax 3-in-1 HDR, Canon Dual Pixel, Fuji EXR).\n\nWhen using any demosaicing method other than Pixel Shift, this selects which sub-image is used.\n\nWhen using the Pixel Shift demosaicing method on a Pixel Shift raw, all sub-images are used, and this selects which sub-image should be used for moving parts. -!TP_RAW_LMMSE;LMMSE -!TP_RAW_MONO;Mono !TP_RAW_NONE;None (Shows sensor pattern) !TP_RAW_PIXELSHIFT;Pixel Shift -!TP_RAW_PIXELSHIFTBLUR;Blur motion mask -!TP_RAW_PIXELSHIFTDMETHOD;Demosaic method for motion -!TP_RAW_PIXELSHIFTEPERISO;Sensitivity !TP_RAW_PIXELSHIFTEPERISO_TOOLTIP;The default value of 0 should work fine for base ISO.\nHigher values increase sensitivity of motion detection.\nChange in small steps and watch the motion mask while changing.\nIncrease sensitivity for underexposed or high ISO images. -!TP_RAW_PIXELSHIFTEQUALBRIGHT;Equalize brightness of frames !TP_RAW_PIXELSHIFTEQUALBRIGHTCHANNEL;Equalize per channel !TP_RAW_PIXELSHIFTEQUALBRIGHTCHANNEL_TOOLTIP;Enabled: Equalize the RGB channels individually.\nDisabled: Use same equalization factor for all channels. !TP_RAW_PIXELSHIFTEQUALBRIGHT_TOOLTIP;Equalize the brightness of the frames to the brightness of the selected frame.\nIf there are overexposed areas in the frames select the brightest frame to avoid magenta color cast in overexposed areas or enable motion correction. !TP_RAW_PIXELSHIFTGREEN;Check green channel for motion -!TP_RAW_PIXELSHIFTHOLEFILL;Fill holes in motion mask -!TP_RAW_PIXELSHIFTHOLEFILL_TOOLTIP;Fill holes in motion mask -!TP_RAW_PIXELSHIFTMEDIAN;Use median for moving parts !TP_RAW_PIXELSHIFTMEDIAN_TOOLTIP;Use median of all frames instead of selected frame for regions with motion.\nRemoves objects which are at different places in all frames.\nGives motion effect on slow moving (overlapping) objects. -!TP_RAW_PIXELSHIFTMM_AUTO;Automatic -!TP_RAW_PIXELSHIFTMM_CUSTOM;Custom -!TP_RAW_PIXELSHIFTMM_OFF;Off -!TP_RAW_PIXELSHIFTMOTIONMETHOD;Motion Correction -!TP_RAW_PIXELSHIFTNONGREENCROSS;Check red/blue channels for motion -!TP_RAW_PIXELSHIFTSHOWMOTION;Show motion mask -!TP_RAW_PIXELSHIFTSHOWMOTIONMASKONLY;Show only motion mask -!TP_RAW_PIXELSHIFTSHOWMOTIONMASKONLY_TOOLTIP;Shows the motion mask without the image. !TP_RAW_PIXELSHIFTSHOWMOTION_TOOLTIP;Overlays the image with a green mask showing the regions with motion. -!TP_RAW_PIXELSHIFTSIGMA;Blur radius !TP_RAW_PIXELSHIFTSIGMA_TOOLTIP;The default radius of 1.0 usually fits well for base ISO.\nIncrease the value for high ISO shots, 5.0 is a good starting point.\nWatch the motion mask while changing the value. -!TP_RAW_PIXELSHIFTSMOOTH;Smooth transitions !TP_RAW_PIXELSHIFTSMOOTH_TOOLTIP;Smooth transitions between areas with motion and areas without.\nSet to 0 to disable transition smoothing.\nSet to 1 to either get the AMaZE/LMMSE result of the selected frame (depending on whether "Use LMMSE" is selected), or the median of all four frames if "Use median" is selected. -!TP_RAW_RCD;RCD -!TP_RAW_RCDVNG4;RCD+VNG4 -!TP_RAW_VNG4;VNG4 -!TP_RAW_XTRANS;X-Trans -!TP_RAW_XTRANSFAST;Fast X-Trans -!TP_RESIZE_ALLOW_UPSCALING;Allow Upscaling -!TP_RETINEX_CONTEDIT_HSL;HSL histogram -!TP_RETINEX_CONTEDIT_LAB;L*a*b* histogram -!TP_RETINEX_CONTEDIT_LH;Hue -!TP_RETINEX_CONTEDIT_MAP;Equalizer -!TP_RETINEX_CURVEEDITOR_CD;L=f(L) !TP_RETINEX_CURVEEDITOR_CD_TOOLTIP;Luminance according to luminance L=f(L)\nCorrect raw data to reduce halos and artifacts. -!TP_RETINEX_CURVEEDITOR_LH;Strength=f(H) !TP_RETINEX_CURVEEDITOR_LH_TOOLTIP;Strength according to hue Strength=f(H)\nThis curve also acts on chroma when using the "Highlight" retinex method. -!TP_RETINEX_CURVEEDITOR_MAP;L=f(L) !TP_RETINEX_CURVEEDITOR_MAP_TOOLTIP;This curve can be applied alone or with a Gaussian mask or wavelet mask.\nBeware of artifacts! -!TP_RETINEX_EQUAL;Equalizer !TP_RETINEX_FREEGAMMA;Free gamma -!TP_RETINEX_GAIN;Gain !TP_RETINEX_GAINOFFS;Gain and Offset (brightness) !TP_RETINEX_GAINTRANSMISSION;Gain transmission !TP_RETINEX_GAINTRANSMISSION_TOOLTIP;Amplify or reduce the transmission map to achieve the desired luminance.\nThe x-axis is the transmission.\nThe y-axis is the gain. -!TP_RETINEX_GAMMA;Gamma -!TP_RETINEX_GAMMA_FREE;Free -!TP_RETINEX_GAMMA_HIGH;High -!TP_RETINEX_GAMMA_LOW;Low -!TP_RETINEX_GAMMA_MID;Middle -!TP_RETINEX_GAMMA_NONE;None !TP_RETINEX_GAMMA_TOOLTIP;Restore tones by applying gamma before and after Retinex. Different from Retinex curves or others curves (Lab, Exposure, etc.). !TP_RETINEX_GRAD;Transmission gradient !TP_RETINEX_GRADS;Strength gradient !TP_RETINEX_GRADS_TOOLTIP;If slider at 0, all iterations are identical.\nIf > 0 Strength is reduced when iterations increase, and conversely. !TP_RETINEX_GRAD_TOOLTIP;If slider at 0, all iterations are identical.\nIf > 0 Variance and Threshold are reduced when iterations increase, and conversely. -!TP_RETINEX_HIGH;High !TP_RETINEX_HIGHLIG;Highlight -!TP_RETINEX_HIGHLIGHT;Highlight threshold !TP_RETINEX_HIGHLIGHT_TOOLTIP;Increase action of High algorithm.\nMay require you to re-adjust "Neighboring pixels" and to increase the "White-point correction" in the Raw tab -> Raw White Points tool. -!TP_RETINEX_HSLSPACE_LIN;HSL-Linear -!TP_RETINEX_HSLSPACE_LOG;HSL-Logarithmic !TP_RETINEX_ITER;Iterations (Tone-mapping) !TP_RETINEX_ITERF;Tone mapping !TP_RETINEX_ITER_TOOLTIP;Simulate a tone-mapping operator.\nHigh values increase the processing time. -!TP_RETINEX_LABEL;Retinex -!TP_RETINEX_LABEL_MASK;Mask -!TP_RETINEX_LABSPACE;L*a*b* -!TP_RETINEX_LOW;Low -!TP_RETINEX_MAP;Method -!TP_RETINEX_MAP_GAUS;Gaussian mask !TP_RETINEX_MAP_MAPP;Sharp mask (wavelet partial) !TP_RETINEX_MAP_MAPT;Sharp mask (wavelet total) !TP_RETINEX_MAP_METHOD_TOOLTIP;Use the mask generated by the Gaussian function above (Radius, Method) to reduce halos and artifacts.\n\nCurve only: apply a diagonal contrast curve on the mask.\nBeware of artifacts!\n\nGaussian mask: generate and use a Gaussian blur of the original mask.\nQuick.\n\nSharp mask: generate and use a wavelet on the original mask.\nSlow. -!TP_RETINEX_MAP_NONE;None !TP_RETINEX_MEDIAN;Transmission median filter -!TP_RETINEX_METHOD;Method !TP_RETINEX_METHOD_TOOLTIP;Low = Reinforce low light.\nUniform = Equalize action.\nHigh = Reinforce high light.\nHighlights = Remove magenta in highlights. !TP_RETINEX_MLABEL;Restored haze-free Min=%1 Max=%2 !TP_RETINEX_MLABEL_TOOLTIP;Should be near min=0 max=32768\nRestored image with no mixture. -!TP_RETINEX_NEIGHBOR;Radius -!TP_RETINEX_NEUTRAL;Reset !TP_RETINEX_NEUTRAL_TIP;Reset all sliders and curves to their default values. -!TP_RETINEX_OFFSET;Offset (brightness) !TP_RETINEX_SCALES;Gaussian gradient !TP_RETINEX_SCALES_TOOLTIP;If slider at 0, all iterations are identical.\nIf > 0 Scale and radius are reduced when iterations increase, and conversely. -!TP_RETINEX_SETTINGS;Settings -!TP_RETINEX_SKAL;Scale !TP_RETINEX_SLOPE;Free gamma slope -!TP_RETINEX_STRENGTH;Strength -!TP_RETINEX_THRESHOLD;Threshold !TP_RETINEX_THRESHOLD_TOOLTIP;Limits in/out.\nIn = image source,\nOut = image gauss. !TP_RETINEX_TLABEL;TM Min=%1 Max=%2 Mean=%3 Sigma=%4 !TP_RETINEX_TLABEL2;TM Tm=%1 TM=%2 @@ -2125,190 +2246,76 @@ ZOOMPANEL_ZOOMOUT;Oddal\nSkrót: - !TP_RETINEX_TRANF;Transmission !TP_RETINEX_TRANSMISSION;Transmission map !TP_RETINEX_TRANSMISSION_TOOLTIP;Transmission according to transmission.\nAbscissa: transmission from negative values (min), mean, and positives values (max).\nOrdinate: amplification or reduction. -!TP_RETINEX_UNIFORM;Uniform -!TP_RETINEX_VARIANCE;Contrast !TP_RETINEX_VARIANCE_TOOLTIP;Low variance increase local contrast and saturation, but can lead to artifacts. -!TP_RETINEX_VIEW;Process -!TP_RETINEX_VIEW_MASK;Mask !TP_RETINEX_VIEW_METHOD_TOOLTIP;Standard - Normal display.\nMask - Displays the mask.\nUnsharp mask - Displays the image with a high radius unsharp mask.\nTransmission - Auto/Fixed - Displays the file transmission-map, before any action on contrast and brightness.\n\nAttention: the mask does not correspond to reality, but is amplified to make it more visible. -!TP_RETINEX_VIEW_NONE;Standard !TP_RETINEX_VIEW_TRAN;Transmission - Auto !TP_RETINEX_VIEW_TRAN2;Transmission - Fixed -!TP_RETINEX_VIEW_UNSHARP;Unsharp mask -!TP_SHARPENING_BLUR;Blur radius -!TP_SHARPENING_CONTRAST;Contrast threshold !TP_SHARPENING_ITERCHECK;Auto limit iterations !TP_SHARPENING_RADIUS_BOOST;Corner radius boost -!TP_SHARPENMICRO_CONTRAST;Contrast threshold !TP_SOFTLIGHT_LABEL;Soft Light -!TP_SOFTLIGHT_STRENGTH;Strength -!TP_TM_FATTAL_AMOUNT;Amount !TP_TM_FATTAL_ANCHOR;Anchor -!TP_TM_FATTAL_LABEL;Dynamic Range Compression -!TP_TM_FATTAL_THRESHOLD;Detail -!TP_WAVELET_1;Level 1 -!TP_WAVELET_2;Level 2 -!TP_WAVELET_3;Level 3 -!TP_WAVELET_4;Level 4 -!TP_WAVELET_5;Level 5 -!TP_WAVELET_6;Level 6 -!TP_WAVELET_7;Level 7 -!TP_WAVELET_8;Level 8 -!TP_WAVELET_9;Level 9 -!TP_WAVELET_APPLYTO;Apply To -!TP_WAVELET_AVOID;Avoid color shift -!TP_WAVELET_B0;Black -!TP_WAVELET_B1;Grey !TP_WAVELET_B2;Residual -!TP_WAVELET_BACKGROUND;Background -!TP_WAVELET_BACUR;Curve !TP_WAVELET_BALANCE;Contrast balance d/v-h !TP_WAVELET_BALANCE_TOOLTIP;Alters the balance between the wavelet directions: vertical-horizontal and diagonal.\nIf contrast, chroma or residual tone mapping are activated, the effect due to balance is amplified. -!TP_WAVELET_BALCHRO;Chroma balance !TP_WAVELET_BALCHRO_TOOLTIP;If enabled, the 'Contrast balance' curve or slider also modifies chroma balance. -!TP_WAVELET_BANONE;None -!TP_WAVELET_BASLI;Slider -!TP_WAVELET_BATYPE;Contrast balance method -!TP_WAVELET_CBENAB;Toning and Color Balance !TP_WAVELET_CB_TOOLTIP;For strong values product color-toning by combining it or not with levels decomposition 'toning'\nFor low values you can change the white balance of the background (sky, ...) without changing that of the front plane, generally more contrasted -!TP_WAVELET_CCURVE;Local contrast -!TP_WAVELET_CH1;Whole chroma range -!TP_WAVELET_CH2;Saturated/pastel -!TP_WAVELET_CH3;Link contrast levels -!TP_WAVELET_CHCU;Curve !TP_WAVELET_CHR;Chroma-contrast link strength !TP_WAVELET_CHRO;Saturated/pastel threshold !TP_WAVELET_CHRO_TOOLTIP;Sets the wavelet level which will be the threshold between saturated and pastel colors.\n1-x: saturated\nx-9: pastel\n\nIf the value exceeds the amount of wavelet levels you are using then it will be ignored. !TP_WAVELET_CHR_TOOLTIP;Adjusts chroma as a function of "contrast levels" and "chroma-contrast link strength" -!TP_WAVELET_CHSL;Sliders !TP_WAVELET_CHTYPE;Chrominance method !TP_WAVELET_COLORT;Opacity Red-Green -!TP_WAVELET_COMPCONT;Contrast -!TP_WAVELET_COMPGAMMA;Compression gamma !TP_WAVELET_COMPGAMMA_TOOLTIP;Adjusting the gamma of the residual image allows you to equilibrate the data and histogram. !TP_WAVELET_COMPTM;Tone mapping !TP_WAVELET_CONTEDIT;'After' contrast curve -!TP_WAVELET_CONTR;Gamut -!TP_WAVELET_CONTRA;Contrast -!TP_WAVELET_CONTRAST_MINUS;Contrast - -!TP_WAVELET_CONTRAST_PLUS;Contrast + !TP_WAVELET_CONTRA_TOOLTIP;Changes contrast of the residual image. -!TP_WAVELET_CTYPE;Chrominance control !TP_WAVELET_CURVEEDITOR_CC_TOOLTIP;Modifies local contrast as a function of the original local contrast (abscissa).\nLow abscissa values represent small local contrast (real values about 10..20).\n50% abscissa represents average local contrast (real value about 100..300).\n66% abscissa represents standard deviation of local contrast (real value about 300..800).\n100% abscissa represents maximum local contrast (real value about 3000..8000). !TP_WAVELET_CURVEEDITOR_CH;Contrast levels=f(Hue) !TP_WAVELET_CURVEEDITOR_CH_TOOLTIP;Modifies each level's contrast as a function of hue.\nTake care not to overwrite changes made with the Gamut sub-tool's hue controls.\nThe curve will only have an effect when wavelet contrast level sliders are non-zero. -!TP_WAVELET_CURVEEDITOR_CL;L !TP_WAVELET_CURVEEDITOR_CL_TOOLTIP;Applies a final contrast luminance curve at the end of the wavelet treatment. -!TP_WAVELET_CURVEEDITOR_HH;HH !TP_WAVELET_CURVEEDITOR_HH_TOOLTIP;Modifies the residual image's hue as a function of hue. -!TP_WAVELET_DALL;All directions !TP_WAVELET_DAUB;Edge performance -!TP_WAVELET_DAUB2;D2 - low -!TP_WAVELET_DAUB4;D4 - standard -!TP_WAVELET_DAUB6;D6 - standard plus -!TP_WAVELET_DAUB10;D10 - medium -!TP_WAVELET_DAUB14;D14 - high !TP_WAVELET_DAUB_TOOLTIP;Changes Daubechies coefficients:\nD4 = Standard,\nD14 = Often best performance, 10% more time-intensive.\n\nAffects edge detection as well as the general quality of the firsts levels. However the quality is not strictly related to this coefficient and can vary with images and uses. -!TP_WAVELET_DONE;Vertical -!TP_WAVELET_DTHR;Diagonal -!TP_WAVELET_DTWO;Horizontal -!TP_WAVELET_EDCU;Curve -!TP_WAVELET_EDGCONT;Local contrast !TP_WAVELET_EDGCONT_TOOLTIP;Adjusting the points to the left decreases contrast, and to the right increases it.\nBottom-left, top-left, top-right and bottom-right represent respectively local contrast for low values, mean, mean+stdev and maxima. -!TP_WAVELET_EDGE;Edge Sharpness !TP_WAVELET_EDGEAMPLI;Base amplification !TP_WAVELET_EDGEDETECT;Gradient sensitivity -!TP_WAVELET_EDGEDETECTTHR;Threshold low (noise) -!TP_WAVELET_EDGEDETECTTHR2;Threshold high (detection) !TP_WAVELET_EDGEDETECTTHR_TOOLTIP;This adjuster lets you target edge detection for example to avoid applying edge sharpness to fine details, such as noise in the sky. !TP_WAVELET_EDGEDETECT_TOOLTIP;Moving the slider to the right increases edge sensitivity. This affects local contrast, edge settings and noise. !TP_WAVELET_EDGESENSI;Edge sensitivity !TP_WAVELET_EDGREINF_TOOLTIP;Reinforce or reduce the action of the first level, do the opposite to the second level, and leave the rest unchanged. -!TP_WAVELET_EDGTHRESH;Detail !TP_WAVELET_EDGTHRESH_TOOLTIP;Change the repartition between the first levels and the others. The higher the threshold the more the action is centered on the first levels. Be careful with negative values, they increase the action of high levels and can introduce artifacts. -!TP_WAVELET_EDRAD;Radius !TP_WAVELET_EDRAD_TOOLTIP;This radius adjustment is very different from those in other sharpening tools. Its value is compared to each level through a complex function. In this sense, a value of zero still has an effect. -!TP_WAVELET_EDSL;Threshold Sliders -!TP_WAVELET_EDTYPE;Local contrast method -!TP_WAVELET_EDVAL;Strength -!TP_WAVELET_FINAL;Final Touchup -!TP_WAVELET_FINEST;Finest -!TP_WAVELET_HIGHLIGHT;Highlight luminance range -!TP_WAVELET_HS1;Whole luminance range -!TP_WAVELET_HS2;Shadows/Highlights -!TP_WAVELET_HUESKIN;Skin hue !TP_WAVELET_HUESKIN_TOOLTIP;The bottom points set the beginning of the transition zone, and the upper points the end of it, where the effect is at its maximum.\n\nIf you need to move the area significantly, or if there are artifacts, then the white balance is incorrect. -!TP_WAVELET_HUESKY;Sky hue !TP_WAVELET_HUESKY_TOOLTIP;The bottom points set the beginning of the transition zone, and the upper points the end of it, where the effect is at its maximum.\n\nIf you need to move the area significantly, or if there are artifacts, then the white balance is incorrect. !TP_WAVELET_ITER;Delta balance levels !TP_WAVELET_ITER_TOOLTIP;Left: increase low levels and reduce high levels,\nRight: reduce low levels and increase high levels. !TP_WAVELET_LABEL;Wavelet Levels !TP_WAVELET_LARGEST;Coarsest -!TP_WAVELET_LEVCH;Chroma !TP_WAVELET_LEVDIR_ALL;All levels in all directions !TP_WAVELET_LEVDIR_INF;Below or equal the level !TP_WAVELET_LEVDIR_ONE;One level !TP_WAVELET_LEVDIR_SUP;Above the level !TP_WAVELET_LEVELS;Wavelet levels !TP_WAVELET_LEVELS_TOOLTIP;Choose the number of detail levels the image is to be decomposed into. More levels require more RAM and require a longer processing time. -!TP_WAVELET_LEVF;Contrast !TP_WAVELET_LEVLABEL;Preview maximum possible levels = %1 -!TP_WAVELET_LEVONE;Level 2 -!TP_WAVELET_LEVTHRE;Level 4 -!TP_WAVELET_LEVTWO;Level 3 -!TP_WAVELET_LEVZERO;Level 1 -!TP_WAVELET_LINKEDG;Link with Edge Sharpness' Strength -!TP_WAVELET_LIPST;Enhanced algoritm -!TP_WAVELET_LOWLIGHT;Shadow luminance range -!TP_WAVELET_MEDGREINF;First level -!TP_WAVELET_MEDI;Reduce artifacts in blue sky -!TP_WAVELET_MEDILEV;Edge detection !TP_WAVELET_MEDILEV_TOOLTIP;When you enable Edge Detection, it is recommanded:\n- to disabled low contrast levels to avoid artifacts,\n- to use high values of gradient sensitivity.\n\nYou can modulate the strength with 'refine' from Denoise and Refine. -!TP_WAVELET_NEUTRAL;Neutral -!TP_WAVELET_NOIS;Denoise !TP_WAVELET_NOISE;Denoise and Refine -!TP_WAVELET_NPHIGH;High -!TP_WAVELET_NPLOW;Low -!TP_WAVELET_NPNONE;None -!TP_WAVELET_NPTYPE;Neighboring pixels !TP_WAVELET_NPTYPE_TOOLTIP;This algorithm uses the proximity of a pixel and eight of its neighbors. If less difference, edges are reinforced. !TP_WAVELET_OPACITY;Opacity Blue-Yellow !TP_WAVELET_OPACITYW;Contrast balance d/v-h curve !TP_WAVELET_OPACITYWL;Final local contrast !TP_WAVELET_OPACITYWL_TOOLTIP;Modify the final local contrast at the end of the wavelet treatment.\n\nThe left side represents the smallest local contrast, progressing to the largest local contrast on the right. -!TP_WAVELET_PASTEL;Pastel chroma -!TP_WAVELET_PROC;Process -!TP_WAVELET_RE1;Reinforced -!TP_WAVELET_RE2;Unchanged -!TP_WAVELET_RE3;Reduced -!TP_WAVELET_RESCHRO;Chroma -!TP_WAVELET_RESCON;Shadows -!TP_WAVELET_RESCONH;Highlights !TP_WAVELET_RESID;Residual Image -!TP_WAVELET_SAT;Saturated chroma !TP_WAVELET_SETTINGS;Wavelet Settings !TP_WAVELET_SKIN;Skin targetting/protection !TP_WAVELET_SKIN_TOOLTIP;At -100 skin-tones are targetted.\nAt 0 all tones are treated equally.\nAt +100 skin-tones are protected while all other tones are affected. -!TP_WAVELET_SKY;Sky targetting/protection !TP_WAVELET_SKY_TOOLTIP;At -100 sky-tones are targetted.\nAt 0 all tones are treated equally.\nAt +100 sky-tones are protected while all other tones are affected. -!TP_WAVELET_STREN;Strength -!TP_WAVELET_STRENGTH;Strength -!TP_WAVELET_SUPE;Extra -!TP_WAVELET_THR;Shadows threshold -!TP_WAVELET_THRESHOLD;Highlight levels -!TP_WAVELET_THRESHOLD2;Shadow levels !TP_WAVELET_THRESHOLD2_TOOLTIP;Only levels between 9 and 9 minus the value will be affected by the shadow luminance range. Other levels will be fully treated. The highest level possible is limited by the highlight level value (9 minus highlight level value). !TP_WAVELET_THRESHOLD_TOOLTIP;Only levels beyond the chosen value will be affected by the highlight luminance range. Other levels will be fully treated. The chosen value here limits the highest possible value of the shadow levels. -!TP_WAVELET_THRH;Highlights threshold !TP_WAVELET_TILESBIG;Big tiles !TP_WAVELET_TILESFULL;Full image !TP_WAVELET_TILESIZE;Tiling method !TP_WAVELET_TILESLIT;Little tiles !TP_WAVELET_TILES_TOOLTIP;Processing the full image leads to better quality and is the recommended option, while using tiles is a fall-back solution for users with little RAM. Refer to RawPedia for memory requirements. -!TP_WAVELET_TMSTRENGTH;Compression strength !TP_WAVELET_TMSTRENGTH_TOOLTIP;Control the strength of tone mapping or contrast compression of the residual image. When the value is different from 0, the Strength and Gamma sliders of the Tone Mapping tool in the Exposure tab will become grayed out. -!TP_WAVELET_TMTYPE;Compression method -!TP_WAVELET_TON;Toning -!TP_WBALANCE_PICKER;Pick -!TP_WBALANCE_TEMPBIAS;AWB temperature bias !TP_WBALANCE_TEMPBIAS_TOOLTIP;Allows to alter the computation of the "auto white balance"\nby biasing it towards warmer or cooler temperatures. The bias\nis expressed as a percentage of the computed temperature,\nso that the result is given by "computedTemp + computedTemp * bias". diff --git a/rtdata/languages/Portugues b/rtdata/languages/Portugues index 789d26cd6..0896214a0 100644 --- a/rtdata/languages/Portugues +++ b/rtdata/languages/Portugues @@ -2276,6 +2276,7 @@ ZOOMPANEL_ZOOMOUT;Afastar\nAtalho: - !HISTORY_MSG_PDSHARPEN_ITERATIONS;CS - Iterations !HISTORY_MSG_PDSHARPEN_RADIUS;CS - Radius !HISTORY_MSG_PDSHARPEN_RADIUS_BOOST;CS - Corner radius boost +!HISTORY_MSG_TRANS_Method;Geometry - Method !MAIN_FRAME_PLACES_DEL;Remove !PARTIALPASTE_FILMNEGATIVE;Film Negative !PREFERENCES_APPEARANCE_PSEUDOHIDPI;Pseudo-HiDPI mode @@ -2294,6 +2295,8 @@ ZOOMPANEL_ZOOMOUT;Afastar\nAtalho: - !TP_FILMNEGATIVE_LABEL;Film Negative !TP_FILMNEGATIVE_PICK;Pick neutral spots !TP_FILMNEGATIVE_RED;Red ratio +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected !TP_LENSPROFILE_MODE_HEADER;Lens Profile diff --git a/rtdata/languages/Portugues (Brasil) b/rtdata/languages/Portugues (Brasil) index d619356a9..85dbf377f 100644 --- a/rtdata/languages/Portugues (Brasil) +++ b/rtdata/languages/Portugues (Brasil) @@ -2283,6 +2283,7 @@ ZOOMPANEL_ZOOMOUT;Menos Zoom\nAtalho: - !HISTORY_MSG_PDSHARPEN_ITERATIONS;CS - Iterations !HISTORY_MSG_PDSHARPEN_RADIUS;CS - Radius !HISTORY_MSG_PDSHARPEN_RADIUS_BOOST;CS - Corner radius boost +!HISTORY_MSG_TRANS_Method;Geometry - Method !PARTIALPASTE_FILMNEGATIVE;Film Negative !PREFERENCES_CACHECLEAR_SAFETY;Only files in the cache are cleared. Processing profiles stored alongside the source images are not touched. !PROGRESSBAR_DECODING;Decoding... @@ -2295,6 +2296,8 @@ ZOOMPANEL_ZOOMOUT;Menos Zoom\nAtalho: - !TP_FILMNEGATIVE_GREEN;Reference exponent (contrast) !TP_FILMNEGATIVE_GUESS_TOOLTIP;Automatically set the red and blue ratios by picking two patches which had a neutral hue (no color) in the original scene. The patches should differ in brightness. Set the white balance afterwards. !TP_FILMNEGATIVE_LABEL;Film Negative +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_LENS_WARNING;Warning: the crop factor used for lens profiling is larger than the crop factor of the camera, the results might be wrong. !TP_LENSPROFILE_USE_HEADER;Correct !TP_PDSHARPENING_LABEL;Capture Sharpening diff --git a/rtdata/languages/Russian b/rtdata/languages/Russian index 4246ecbb6..27f4cff0c 100644 --- a/rtdata/languages/Russian +++ b/rtdata/languages/Russian @@ -1736,6 +1736,7 @@ ZOOMPANEL_ZOOMOUT;Отдалить\nГорячая клавиша: - !HISTORY_MSG_SHARPENING_BLUR;Sharpening - Blur radius !HISTORY_MSG_SHARPENING_CONTRAST;Sharpening - Contrast threshold !HISTORY_MSG_SH_COLORSPACE;S/H - Colorspace +!HISTORY_MSG_TRANS_Method;Geometry - Method !ICCPROFCREATOR_COPYRIGHT;Copyright: !ICCPROFCREATOR_COPYRIGHT_RESET_TOOLTIP;Reset to the default copyright, granted to "RawTherapee, CC0" !ICCPROFCREATOR_CUSTOM;Custom @@ -2014,6 +2015,8 @@ ZOOMPANEL_ZOOMOUT;Отдалить\nГорячая клавиша: - !TP_ICM_WORKING_TRC_NONE;None !TP_ICM_WORKING_TRC_SLOPE;Slope !TP_ICM_WORKING_TRC_TOOLTIP;Only for built-in profiles. +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected !TP_LENSPROFILE_MODE_HEADER;Lens Profile diff --git a/rtdata/languages/Serbian (Cyrilic Characters) b/rtdata/languages/Serbian (Cyrilic Characters) index 7fd0ca378..27da76acc 100644 --- a/rtdata/languages/Serbian (Cyrilic Characters) +++ b/rtdata/languages/Serbian (Cyrilic Characters) @@ -1554,6 +1554,7 @@ ZOOMPANEL_ZOOMOUT;Умањује приказ слике - !HISTORY_MSG_SOFTLIGHT_ENABLED;Soft light !HISTORY_MSG_SOFTLIGHT_STRENGTH;Soft light - Strength !HISTORY_MSG_TM_FATTAL_ANCHOR;DRC - Anchor +!HISTORY_MSG_TRANS_Method;Geometry - Method !ICCPROFCREATOR_COPYRIGHT;Copyright: !ICCPROFCREATOR_COPYRIGHT_RESET_TOOLTIP;Reset to the default copyright, granted to "RawTherapee, CC0" !ICCPROFCREATOR_CUSTOM;Custom @@ -1947,6 +1948,8 @@ ZOOMPANEL_ZOOMOUT;Умањује приказ слике - !TP_ICM_WORKING_TRC_NONE;None !TP_ICM_WORKING_TRC_SLOPE;Slope !TP_ICM_WORKING_TRC_TOOLTIP;Only for built-in profiles. +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_LCPFILE;LCP file !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected diff --git a/rtdata/languages/Slovenian b/rtdata/languages/Slovenian index 0afaa83e9..73c1bd2d1 100644 --- a/rtdata/languages/Slovenian +++ b/rtdata/languages/Slovenian @@ -2308,4 +2308,7 @@ ZOOMPANEL_ZOOMOUT;Zoom Out\nBližnjica: - !GENERAL_HELP;Help !HISTORY_MSG_PDSHARPEN_CHECKITER;CS - Auto limit iterations +!HISTORY_MSG_TRANS_Method;Geometry - Method +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_SHARPENING_ITERCHECK;Auto limit iterations diff --git a/rtdata/languages/Swedish b/rtdata/languages/Swedish index 6dbea54d8..f54b4de30 100644 --- a/rtdata/languages/Swedish +++ b/rtdata/languages/Swedish @@ -1903,6 +1903,7 @@ ZOOMPANEL_ZOOMOUT;Förminska.\nKortkommando: - !HISTORY_MSG_SOFTLIGHT_ENABLED;Soft light !HISTORY_MSG_SOFTLIGHT_STRENGTH;Soft light - Strength !HISTORY_MSG_TM_FATTAL_ANCHOR;DRC - Anchor +!HISTORY_MSG_TRANS_Method;Geometry - Method !ICCPROFCREATOR_COPYRIGHT;Copyright: !ICCPROFCREATOR_COPYRIGHT_RESET_TOOLTIP;Reset to the default copyright, granted to "RawTherapee, CC0" !ICCPROFCREATOR_CUSTOM;Custom @@ -2150,6 +2151,8 @@ ZOOMPANEL_ZOOMOUT;Förminska.\nKortkommando: - !TP_ICM_WORKING_TRC_NONE;None !TP_ICM_WORKING_TRC_SLOPE;Slope !TP_ICM_WORKING_TRC_TOOLTIP;Only for built-in profiles. +!TP_LENSGEOM_LIN;Linear +!TP_LENSGEOM_LOG;Logarithmic !TP_LENSPROFILE_CORRECTION_AUTOMATCH;Automatically selected !TP_LENSPROFILE_CORRECTION_LCPFILE;LCP file !TP_LENSPROFILE_CORRECTION_MANUAL;Manually selected diff --git a/rtdata/languages/default b/rtdata/languages/default index db90aea22..b22b00e52 100644 --- a/rtdata/languages/default +++ b/rtdata/languages/default @@ -735,6 +735,7 @@ HISTORY_MSG_499;Perspective - PCA - Rotation HISTORY_MSG_500;Perspective - PCA HISTORY_MSG_501;Perspective - Camera HISTORY_MSG_502;Perspective - Method +HISTORY_MSG_CAT02PRESET;Cat02 automatic preset HISTORY_MSG_CLAMPOOG;Clip out-of-gamut colors HISTORY_MSG_COLORTONING_LABGRID_VALUE;CT - Color correction HISTORY_MSG_COLORTONING_LABREGION_AB;CT - Color correction @@ -758,6 +759,7 @@ HISTORY_MSG_DEHAZE_STRENGTH;Dehaze - Strength HISTORY_MSG_DUALDEMOSAIC_AUTO_CONTRAST;Dual demosaic - Auto threshold HISTORY_MSG_DUALDEMOSAIC_CONTRAST;Dual demosaic - Contrast threshold HISTORY_MSG_FILMNEGATIVE_ENABLED;Film Negative +HISTORY_MSG_FILMNEGATIVE_FILMBASE;Film base color HISTORY_MSG_FILMNEGATIVE_VALUES;Film negative values HISTORY_MSG_HISTMATCHING;Auto-matched tone curve HISTORY_MSG_ICM_OUTPUT_PRIMARIES;Output - Primaries @@ -766,6 +768,7 @@ HISTORY_MSG_ICM_OUTPUT_TYPE;Output - Type HISTORY_MSG_ICM_WORKING_GAMMA;Working - Gamma HISTORY_MSG_ICM_WORKING_SLOPE;Working - Slope HISTORY_MSG_ICM_WORKING_TRC_METHOD;Working - TRC method +HISTORY_MSG_ILLUM;Illuminant HISTORY_MSG_LOCALCONTRAST_AMOUNT;Local Contrast - Amount HISTORY_MSG_LOCALCONTRAST_DARKNESS;Local Contrast - Darkness HISTORY_MSG_LOCALCONTRAST_ENABLED;Local Contrast @@ -793,8 +796,34 @@ HISTORY_MSG_SHARPENING_CONTRAST;Sharpening - Contrast threshold HISTORY_MSG_SH_COLORSPACE;S/H - Colorspace HISTORY_MSG_SOFTLIGHT_ENABLED;Soft light HISTORY_MSG_SOFTLIGHT_STRENGTH;Soft light - Strength +HISTORY_MSG_TEMPOUT;CAM02 automatic temperature HISTORY_MSG_TM_FATTAL_ANCHOR;DRC - Anchor HISTORY_MSG_TRANS_Method;Geometry - Method +HISTORY_MSG_WAVBALCHROM;Equalizer chrominance +HISTORY_MSG_WAVBALLUM;Equalizer luminance +HISTORY_MSG_WAVCHROMFI;Chroma fine +HISTORY_MSG_WAVCHROMCO;Chroma coarse +HISTORY_MSG_WAVCLARI;Clarity +HISTORY_MSG_WAVEDGS;Edge stopping +HISTORY_MSG_WAVMERGEC;Merge C +HISTORY_MSG_WAVMERGEL;Merge L +HISTORY_MSG_WAVRADIUS;Radius Shadows-Highlight +HISTORY_MSG_WAVSCALE;Scale +HISTORY_MSG_WAVSHOWMASK;Show wavelet mask +HISTORY_MSG_WAVSIGMA;Damper +HISTORY_MSG_WAVSOFTRAD;Soft radius clarity +HISTORY_MSG_WAVSOFTRADEND;Soft radius final +HISTORY_MSG_WAVUSHAMET;Clarity method +HISTORY_MSG_THRESWAV;Balance threshold +HISTORY_MSG_BLUWAV;Damper +HISTORY_MSG_WAVOLDSH;Old algorithm +HISTORY_MSG_WAVOFFSET;Offset +HISTORY_MSG_WAVLOWTHR;Threshold low contrast +HISTORY_MSG_BLSHAPE;Blur by level +HISTORY_MSG_WAVBL;Blur levels +HISTORY_MSG_BLURWAV;Blur luminance +HISTORY_MSG_BLURCWAV;Blur chroma +HISTORY_MSG_EDGEFFECT;Edge Damper HISTORY_NEWSNAPSHOT;Add HISTORY_NEWSNAPSHOT_TOOLTIP;Shortcut: Alt-s HISTORY_SNAPSHOT;Snapshot @@ -1432,6 +1461,16 @@ TP_COLORAPP_GAMUT;Gamut control (L*a*b*) TP_COLORAPP_GAMUT_TOOLTIP;Allow gamut control in L*a*b* mode. TP_COLORAPP_HUE;Hue (h) TP_COLORAPP_HUE_TOOLTIP;Hue (h) - angle between 0° and 360°. +TP_COLORAPP_ILLUM;Illuminant +TP_COLORAPP_ILLUM_TOOLTIP;Select the illuminant closest to the shooting conditions.\nIn general D50, but it can change depending on the time and lattitude. +TP_COLORAPP_ILA;Incandescent StdA 2856K +TP_COLORAPP_IL41;D41 +TP_COLORAPP_IL50;D50 +TP_COLORAPP_IL55;D55 +TP_COLORAPP_IL60;D60 +TP_COLORAPP_IL65;D65 +TP_COLORAPP_IL75;D75 +TP_COLORAPP_ILFREE;Free TP_COLORAPP_LABEL;CIE Color Appearance Model 2002 TP_COLORAPP_LABEL_CAM02;Image Adjustments TP_COLORAPP_LABEL_SCENE;Scene Conditions @@ -1443,6 +1482,8 @@ TP_COLORAPP_MODEL;WP Model TP_COLORAPP_MODEL_TOOLTIP;White-Point Model.\n\nWB [RT] + [output]: RT's white balance is used for the scene, CIECAM02 is set to D50, and the output device's white balance is set in Viewing Conditions.\n\nWB [RT+CAT02] + [output]: RT's white balance settings are used by CAT02 and the output device's white balance is set in Viewing Conditions.\n\nFree temp+green + CAT02 + [output]: temp and green are selected by the user, the output device's white balance is set in Viewing Conditions. TP_COLORAPP_NEUTRAL;Reset TP_COLORAPP_NEUTRAL_TIP;Reset all sliders checkbox and curves to their default values +TP_COLORAPP_PRESETCAT02;Preset cat02 automatic +TP_COLORAPP_PRESETCAT02_TIP;Set combobox, sliders, temp, green so that Cat02 automatic is preset.\nYou can change illuminant shooting conditions.\nYou must change Cat02 adaptation Viewing conditions if need.\nYou can change Temperature and Tint Viewing conditions if need, and other settings if need. TP_COLORAPP_RSTPRO;Red & skin-tones protection TP_COLORAPP_RSTPRO_TOOLTIP;Red & skin-tones protection affects both sliders and curves. TP_COLORAPP_SURROUND;Surround @@ -1459,7 +1500,9 @@ TP_COLORAPP_TCMODE_LABEL2;Curve mode 2 TP_COLORAPP_TCMODE_LABEL3;Curve chroma mode TP_COLORAPP_TCMODE_LIGHTNESS;Lightness TP_COLORAPP_TCMODE_SATUR;Saturation -TP_COLORAPP_TEMP_TOOLTIP;To select an illuminant, always set Tint=1.\n\nA temp=2856\nD50 temp=5003\nD55 temp=5503\nD65 temp=6504\nD75 temp=7504 +TP_COLORAPP_TEMP_TOOLTIP;To select an illuminant, always set Tint=1.\n\nA temp=2856\nD41 temp=4100\nD50 temp=5003\nD55 temp=5503\nD60 temp=6000\nD65 temp=6504\nD75 temp=7504 +TP_COLORAPP_TEMP2_TOOLTIP;Either symmetrical mode temp = White balance.\nEither select illuminant always set Tint=1.\n\nA temp=2856\nD41 temp=4100\nD50 temp=5003\nD55 temp=5503\nD60 temp=6000\nD65 temp=6504\nD75 temp=7504 +TP_COLORAPP_TEMPOUT_TOOLTIP;Disable to chnage temperature and tint TP_COLORAPP_TONECIE;Tone mapping using CIECAM02 TP_COLORAPP_TONECIE_TOOLTIP;If this option is disabled, tone mapping is done in L*a*b* space.\nIf this option is enabled, tone mapping is done using CIECAM02.\nThe Tone Mapping tool must be enabled for this setting to take effect. TP_COLORAPP_VIEWING_ABSOLUTELUMINANCE_TOOLTIP;Absolute luminance of the viewing environment\n(usually 16 cd/m²). @@ -1658,6 +1701,9 @@ TP_EXPOSURE_TCMODE_WEIGHTEDSTD;Weighted Standard TP_EXPOS_BLACKPOINT_LABEL;Raw Black Points TP_EXPOS_WHITEPOINT_LABEL;Raw White Points TP_FILMNEGATIVE_BLUE;Blue ratio +TP_FILMNEGATIVE_FILMBASE_PICK;Pick film base color +TP_FILMNEGATIVE_FILMBASE_TOOLTIP;Pick a spot of unexposed film (eg. the border between frames), to get the actual film base color values, and save them in the processing profile.\nThis makes it easy to get a more consistent color balance when batch-processing multiple pictures from the same roll.\nAlso use this when the converted image is extremely dark, bright, or color-unbalanced. +TP_FILMNEGATIVE_FILMBASE_VALUES;Film base RGB: TP_FILMNEGATIVE_GREEN;Reference exponent (contrast) TP_FILMNEGATIVE_GUESS_TOOLTIP;Automatically set the red and blue ratios by picking two patches which had a neutral hue (no color) in the original scene. The patches should differ in brightness. Set the white balance afterwards. TP_FILMNEGATIVE_LABEL;Film Negative @@ -2127,11 +2173,16 @@ TP_WAVELET_BACKGROUND;Background TP_WAVELET_BACUR;Curve TP_WAVELET_BALANCE;Contrast balance d/v-h TP_WAVELET_BALANCE_TOOLTIP;Alters the balance between the wavelet directions: vertical-horizontal and diagonal.\nIf contrast, chroma or residual tone mapping are activated, the effect due to balance is amplified. -TP_WAVELET_BALCHRO;Chroma balance +TP_WAVELET_BALCHRO;Chrominance balance TP_WAVELET_BALCHRO_TOOLTIP;If enabled, the 'Contrast balance' curve or slider also modifies chroma balance. +TP_WAVELET_BALCHROM;Denoise Equalizer Blue-Red +TP_WAVELET_BALLUM;Denoise Equalizer White-Black TP_WAVELET_BANONE;None TP_WAVELET_BASLI;Slider TP_WAVELET_BATYPE;Contrast balance method +TP_WAVELET_BLCURVE;Blur by levels +TP_WAVELET_BLURFRAME;Blur +TP_WAVELET_BLUWAV;Damper TP_WAVELET_CBENAB;Toning and Color Balance TP_WAVELET_CB_TOOLTIP;For strong values product color-toning by combining it or not with levels decomposition 'toning'\nFor low values you can change the white balance of the background (sky, ...) without changing that of the front plane, generally more contrasted TP_WAVELET_CCURVE;Local contrast @@ -2141,16 +2192,24 @@ TP_WAVELET_CH3;Link contrast levels TP_WAVELET_CHCU;Curve TP_WAVELET_CHR;Chroma-contrast link strength TP_WAVELET_CHRO;Saturated/pastel threshold +TP_WAVELET_CHROFRAME;Denoise Chrominance +TP_WAVELET_CHROMAFRAME;Chroma +TP_WAVELET_CHROMCO;Chrominance Coarse +TP_WAVELET_CHROMFI;Chrominance Fine TP_WAVELET_CHRO_TOOLTIP;Sets the wavelet level which will be the threshold between saturated and pastel colors.\n1-x: saturated\nx-9: pastel\n\nIf the value exceeds the amount of wavelet levels you are using then it will be ignored. TP_WAVELET_CHR_TOOLTIP;Adjusts chroma as a function of "contrast levels" and "chroma-contrast link strength" +TP_WAVELET_CHRWAV;Blur chroma TP_WAVELET_CHSL;Sliders TP_WAVELET_CHTYPE;Chrominance method +TP_WAVELET_CLA;Clarity +TP_WAVELET_CLARI;Sharp-mask and Clarity TP_WAVELET_COLORT;Opacity Red-Green TP_WAVELET_COMPCONT;Contrast TP_WAVELET_COMPGAMMA;Compression gamma TP_WAVELET_COMPGAMMA_TOOLTIP;Adjusting the gamma of the residual image allows you to equilibrate the data and histogram. TP_WAVELET_COMPTM;Tone mapping TP_WAVELET_CONTEDIT;'After' contrast curve +TP_WAVELET_CONTFRAME;Contrast - Compression TP_WAVELET_CONTR;Gamut TP_WAVELET_CONTRA;Contrast TP_WAVELET_CONTRAST_MINUS;Contrast - @@ -2185,6 +2244,8 @@ TP_WAVELET_EDGEDETECTTHR;Threshold low (noise) TP_WAVELET_EDGEDETECTTHR2;Threshold high (detection) TP_WAVELET_EDGEDETECTTHR_TOOLTIP;This adjuster lets you target edge detection for example to avoid applying edge sharpness to fine details, such as noise in the sky. TP_WAVELET_EDGEDETECT_TOOLTIP;Moving the slider to the right increases edge sensitivity. This affects local contrast, edge settings and noise. +TP_WAVELET_EDEFFECT;Damper +TP_WAVELET_EDEFFECT_TOOLTIP;This slider controls how wide the range of contrast values are that receive the maximum effect from the tool.\nMaximum value (2.5) disabled the tool TP_WAVELET_EDGESENSI;Edge sensitivity TP_WAVELET_EDGREINF_TOOLTIP;Reinforce or reduce the action of the first level, do the opposite to the second level, and leave the rest unchanged. TP_WAVELET_EDGTHRESH;Detail @@ -2223,10 +2284,13 @@ TP_WAVELET_LEVZERO;Level 1 TP_WAVELET_LINKEDG;Link with Edge Sharpness' Strength TP_WAVELET_LIPST;Enhanced algoritm TP_WAVELET_LOWLIGHT;Shadow luminance range +TP_WAVELET_LOWTHR_TOOLTIP;Prevents amplification of fine textures and noise TP_WAVELET_MEDGREINF;First level TP_WAVELET_MEDI;Reduce artifacts in blue sky TP_WAVELET_MEDILEV;Edge detection TP_WAVELET_MEDILEV_TOOLTIP;When you enable Edge Detection, it is recommanded:\n- to disabled low contrast levels to avoid artifacts,\n- to use high values of gradient sensitivity.\n\nYou can modulate the strength with 'refine' from Denoise and Refine. +TP_WAVELET_MERGEC;Merge Chroma +TP_WAVELET_MERGEL;Merge Luma TP_WAVELET_NEUTRAL;Neutral TP_WAVELET_NOIS;Denoise TP_WAVELET_NOISE;Denoise and Refine @@ -2235,25 +2299,35 @@ TP_WAVELET_NPLOW;Low TP_WAVELET_NPNONE;None TP_WAVELET_NPTYPE;Neighboring pixels TP_WAVELET_NPTYPE_TOOLTIP;This algorithm uses the proximity of a pixel and eight of its neighbors. If less difference, edges are reinforced. +TP_WAVELET_OLDSH;Algorithm using negatives values TP_WAVELET_OPACITY;Opacity Blue-Yellow TP_WAVELET_OPACITYW;Contrast balance d/v-h curve TP_WAVELET_OPACITYWL;Final local contrast TP_WAVELET_OPACITYWL_TOOLTIP;Modify the final local contrast at the end of the wavelet treatment.\n\nThe left side represents the smallest local contrast, progressing to the largest local contrast on the right. TP_WAVELET_PASTEL;Pastel chroma TP_WAVELET_PROC;Process +TP_WAVELET_RADIUS;Radius Shadows - Highlight TP_WAVELET_RE1;Reinforced TP_WAVELET_RE2;Unchanged TP_WAVELET_RE3;Reduced -TP_WAVELET_RESCHRO;Chroma +TP_WAVELET_RESBLUR;Blur Luminance +TP_WAVELET_RESBLURC;Blur Chroma +TP_WAVELET_RESCHRO;Intensity TP_WAVELET_RESCON;Shadows TP_WAVELET_RESCONH;Highlights TP_WAVELET_RESID;Residual Image TP_WAVELET_SAT;Saturated chroma TP_WAVELET_SETTINGS;Wavelet Settings +TP_WAVELET_SHA;Sharp mask +TP_WAVELET_SHFRAME;Shadows/Highlights +TP_WAVELET_SHOWMASK;Show wavelet 'mask' +TP_WAVELET_SIGMA;Damper +TP_WAVELET_SIGMA_TOOLTIP;The effect of the contrast sliders is stronger in medium contrast details, and weaker in high and low contrast details.\n With this slider you can control how quickly the effect dampens towards the extreme contrasts.\n The higher the slider is set, the wider the range of contrasts which will get a strong change, and the higher the risk to generate artifacts.\n The lower it is, the more pinpoint will the effect be applied to a narrow range of contrast values. TP_WAVELET_SKIN;Skin targetting/protection TP_WAVELET_SKIN_TOOLTIP;At -100 skin-tones are targetted.\nAt 0 all tones are treated equally.\nAt +100 skin-tones are protected while all other tones are affected. TP_WAVELET_SKY;Sky targetting/protection TP_WAVELET_SKY_TOOLTIP;At -100 sky-tones are targetted.\nAt 0 all tones are treated equally.\nAt +100 sky-tones are protected while all other tones are affected. +TP_WAVELET_SOFTRAD;Soft Radius TP_WAVELET_STREN;Strength TP_WAVELET_STRENGTH;Strength TP_WAVELET_SUPE;Extra @@ -2262,17 +2336,32 @@ TP_WAVELET_THRESHOLD;Highlight levels TP_WAVELET_THRESHOLD2;Shadow levels TP_WAVELET_THRESHOLD2_TOOLTIP;Only levels between 9 and 9 minus the value will be affected by the shadow luminance range. Other levels will be fully treated. The highest level possible is limited by the highlight level value (9 minus highlight level value). TP_WAVELET_THRESHOLD_TOOLTIP;Only levels beyond the chosen value will be affected by the highlight luminance range. Other levels will be fully treated. The chosen value here limits the highest possible value of the shadow levels. +TP_WAVELET_THRESWAV;Balance Threshold TP_WAVELET_THRH;Highlights threshold -TP_WAVELET_TILESBIG;Big tiles +TP_WAVELET_TILESBIG;Tiles TP_WAVELET_TILESFULL;Full image TP_WAVELET_TILESIZE;Tiling method TP_WAVELET_TILESLIT;Little tiles TP_WAVELET_TILES_TOOLTIP;Processing the full image leads to better quality and is the recommended option, while using tiles is a fall-back solution for users with little RAM. Refer to RawPedia for memory requirements. +TP_WAVELET_BL;Blur levels +TP_WAVELET_TMEDGS;Edge stopping +TP_WAVELET_TMSCALE;Scale TP_WAVELET_TMSTRENGTH;Compression strength -TP_WAVELET_TMSTRENGTH_TOOLTIP;Control the strength of tone mapping or contrast compression of the residual image. When the value is different from 0, the Strength and Gamma sliders of the Tone Mapping tool in the Exposure tab will become grayed out. -TP_WAVELET_TMTYPE;Compression method +TP_WAVELET_TMSTRENGTH_TOOLTIP;Control the strength of tone mapping or contrast compression of the residual image. +TP_WAVELET_TMEDGS;Edge stopping TP_WAVELET_TON;Toning +TP_WAVELET_TMTYPE;Compression method +TP_WAVELET_USH;None +TP_WAVELET_USHARP;Clarity method +TP_WAVELET_USHARP_TOOLTIP;Origin : the source file is the file before Wavelet.\nWavelet : the source file is the file including wavelet threatment +TP_WAVELET_USH_TOOLTIP;If you select Sharp-mask, wavelet settings will be automatically positioned :\nBackground=black, Process=below, level=3...you can change level between 1 and 4.\n\nIf you select Clarity, wavelet settings will be automatically positioned :\nBackground=residual, Process=above, level=7..you can change level between 5 and 10 and wavelet levels. +TP_WAVELET_WAVLOWTHR;Low contrast threshold +TP_WAVELET_WAVOFFSET;Offset +TP_WAVELET_OFFSET_TOOLTIP;Offset modifies the balance between shadows and highlights.\nHigh values here will amplify the contrast change of the highlights, whereas low values will amplify the contrast change of the shadows.\nAlong with a low Damper value you will able to select the contrasts that will be enhanced. TP_WBALANCE_AUTO;Auto +TP_WBALANCE_AUTOITCGREEN;Auto iterate temperature correlation +TP_WBALANCE_AUTOOLD;Auto RGB grey +TP_WBALANCE_AUTO_HEADER;Autos TP_WBALANCE_CAMERA;Camera TP_WBALANCE_CLOUDY;Cloudy TP_WBALANCE_CUSTOM;Custom @@ -2314,6 +2403,8 @@ TP_WBALANCE_SOLUX41;Solux 4100K TP_WBALANCE_SOLUX47;Solux 4700K (vendor) TP_WBALANCE_SOLUX47_NG;Solux 4700K (Nat. Gallery) TP_WBALANCE_SPOTWB;Use the pipette to pick the white balance from a neutral patch in the preview. +TP_WBALANCE_STUDLABEL;Student Itcwb: %1 +TP_WBALANCE_STUDLABEL_TOOLTIP;Display calculated Student correlation\nThe lower the student value, the better the correlation\nValues below 0.002 are excellent\nValues below 0.005 are very good\nValues below 0.01 are good\nValues below 0.05 are good enough\nValues above 0.5 are poor\nVery good Student test results does not mean that the WB is good, if the illuminant is non-standard the results are erratic.\nStudent=1000 means the calculations were not restarted but results are probably goods, use previous results TP_WBALANCE_TEMPBIAS;AWB temperature bias TP_WBALANCE_TEMPBIAS_TOOLTIP;Allows to alter the computation of the "auto white balance"\nby biasing it towards warmer or cooler temperatures. The bias\nis expressed as a percentage of the computed temperature,\nso that the result is given by "computedTemp + computedTemp * bias". TP_WBALANCE_TEMPERATURE;Temperature diff --git a/rtdata/options/options.osx b/rtdata/options/options.osx index 58e0a5604..c83aea179 100644 --- a/rtdata/options/options.osx +++ b/rtdata/options/options.osx @@ -9,6 +9,7 @@ # which can be useful if you want to keep the application and all the cache data in a single place, # an external HD for example MultiUser=true +UseSystemTheme=false [File Browser] # Image filename extensions to be looked for, and their corresponding search state (0/1 -> skip/include) @@ -38,5 +39,6 @@ CustomProfileBuilder= #ImgDefault=Neutral [GUI] -FontFamily=Helvetica Regular -CPFontFamily=Helvetica Regular +# Set the included font as default +FontFamily=Droid Sans Mono Slashed +CPFontFamily=Droid Sans Mono Slashed diff --git a/rtdata/themes/RawTherapee-GTK3-20_.css b/rtdata/themes/RawTherapee-GTK3-20_.css index a5f52a769..bdadc00db 100644 --- a/rtdata/themes/RawTherapee-GTK3-20_.css +++ b/rtdata/themes/RawTherapee-GTK3-20_.css @@ -565,7 +565,7 @@ button.text-button.toggle:hover:checked { .drawingarea { border-radius: 0; background-color: #2A2A2A; - border: 0.0833333333333333em solid #1D1D1D; + border: 0.0833333333333333em solid #888888; } .drawingarea:disabled { background-color: #444; diff --git a/rtengine/CA_correct_RT.cc b/rtengine/CA_correct_RT.cc index f4d082199..fa9788af0 100644 --- a/rtengine/CA_correct_RT.cc +++ b/rtengine/CA_correct_RT.cc @@ -790,12 +790,12 @@ float* RawImageSource::CA_correct_RT( for (int m = 0; m < polyord; m++) { double powHblock = powHblockInit; for (int n = 0; n < polyord; n++) { - polymat[c][dir][numpar * (polyord * i + j) + (polyord * m + n)] += powVblock * powHblock * blockwt[vblock * hblsz + hblock]; + polymat[c][dir][numpar * (polyord * i + j) + (polyord * m + n)] += powVblock * powHblock * static_cast(blockwt[vblock * hblsz + hblock]); powHblock *= hblock; } powVblock *= vblock; } - shiftmat[c][dir][(polyord * i + j)] += powVblockInit * powHblockInit * bstemp[dir] * blockwt[vblock * hblsz + hblock]; + shiftmat[c][dir][(polyord * i + j)] += powVblockInit * powHblockInit * static_cast(bstemp[dir]) * static_cast(blockwt[vblock * hblsz + hblock]); powHblockInit *= hblock; } powVblockInit *= vblock; @@ -848,7 +848,7 @@ float* RawImageSource::CA_correct_RT( for (int top = -border; top < height; top += ts - border2) { for (int left = -border; left < width - (W & 1); left += ts - border2) { memset(bufferThr, 0, buffersizePassTwo); - float lblockshifts[2][2]; + double lblockshifts[2][2]; const int vblock = ((top + border) / (ts - border2)) + 1; const int hblock = ((left + border) / (ts - border2)) + 1; const int bottom = min(top + ts, height + border); @@ -1036,8 +1036,8 @@ float* RawImageSource::CA_correct_RT( } if (!autoCA) { - float hfrac = -((float)(hblock - 0.5) / (hblsz - 2) - 0.5); - float vfrac = -((float)(vblock - 0.5) / (vblsz - 2) - 0.5) * height / width; + double hfrac = -((hblock - 0.5) / (hblsz - 2) - 0.5); + double vfrac = -((vblock - 0.5) / (vblsz - 2) - 0.5) * height / width; lblockshifts[0][0] = 2 * vfrac * cared; lblockshifts[0][1] = 2 * hfrac * cared; lblockshifts[1][0] = 2 * vfrac * cablue; @@ -1058,7 +1058,7 @@ float* RawImageSource::CA_correct_RT( } powVblock *= vblock; } - constexpr float bslim = 3.99; //max allowed CA shift + constexpr double bslim = 3.99f; //max allowed CA shift lblockshifts[0][0] = LIM(lblockshifts[0][0], -bslim, bslim); lblockshifts[0][1] = LIM(lblockshifts[0][1], -bslim, bslim); lblockshifts[1][0] = LIM(lblockshifts[1][0], -bslim, bslim); @@ -1070,14 +1070,14 @@ float* RawImageSource::CA_correct_RT( //some parameters for the bilinear interpolation shiftvfloor[c] = floor((float)lblockshifts[c>>1][0]); shiftvceil[c] = ceil((float)lblockshifts[c>>1][0]); - if (lblockshifts[c>>1][0] < 0.f) { + if (lblockshifts[c>>1][0] < 0.0) { std::swap(shiftvfloor[c], shiftvceil[c]); } shiftvfrac[c] = fabs(lblockshifts[c>>1][0] - shiftvfloor[c]); shifthfloor[c] = floor((float)lblockshifts[c>>1][1]); shifthceil[c] = ceil((float)lblockshifts[c>>1][1]); - if (lblockshifts[c>>1][1] < 0.f) { + if (lblockshifts[c>>1][1] < 0.0) { std::swap(shifthfloor[c], shifthceil[c]); } shifthfrac[c] = fabs(lblockshifts[c>>1][1] - shifthfloor[c]); diff --git a/rtengine/CMakeLists.txt b/rtengine/CMakeLists.txt index b19cad59d..749c31210 100644 --- a/rtengine/CMakeLists.txt +++ b/rtengine/CMakeLists.txt @@ -1,30 +1,60 @@ -include_directories(${EXTRA_INCDIR} - ${EXPAT_INCLUDE_DIRS} - ${FFTW3F_INCLUDE_DIRS} - ${GLIB2_INCLUDE_DIRS} - ${GLIBMM_INCLUDE_DIRS} - ${GOBJECT_INCLUDE_DIRS} - ${GTHREAD_INCLUDE_DIRS} - ${GTKMM_INCLUDE_DIRS} - ${GTK_INCLUDE_DIRS} - ${IPTCDATA_INCLUDE_DIRS} - ${LCMS_INCLUDE_DIRS} - ${LENSFUN_INCLUDE_DIRS} - ${RSVG_INCLUDE_DIRS} -) +if(EXTRA_INCDIR) + include_directories("${EXTRA_INCDIR}") +endif() +if(EXPAT_INCLUDE_DIRS) + include_directories("${EXPAT_INCLUDE_DIRS}") +endif() +if(FFTW3F_INCLUDE_DIRS) + include_directories("${FFTW3F_INCLUDE_DIRS}") +endif() +if(GLIB2_INCLUDE_DIRS) + include_directories("${GLIB2_INCLUDE_DIRS}") +endif() +if(GLIBMM_INCLUDE_DIRS) + include_directories("${GLIBMM_INCLUDE_DIRS}") +endif() +if(GOBJECT_INCLUDE_DIRS) + include_directories("${GOBJECT_INCLUDE_DIRS}") +endif() +if(GTHREAD_INCLUDE_DIRS) + include_directories("${GTHREAD_INCLUDE_DIRS}") +endif() +if(GTKMM_INCLUDE_DIRS) + include_directories("${GTKMM_INCLUDE_DIRS}") +endif() +if(GTK_INCLUDE_DIRS) + include_directories("${GTK_INCLUDE_DIRS}") +endif() +if(IPTCDATA_INCLUDE_DIRS) + include_directories("${IPTCDATA_INCLUDE_DIRS}") +endif() +if(LCMS_INCLUDE_DIRS) + include_directories("${LCMS_INCLUDE_DIRS}") +endif() +if(LENSFUN_INCLUDE_DIRS) + include_directories("${LENSFUN_INCLUDE_DIRS}") +endif() +if(RSVG_INCLUDE_DIRS) + include_directories("${RSVG_INCLUDE_DIRS}") +endif() +if(NOT WITH_SYSTEM_KLT) + include_directories("${CMAKE_SOURCE_DIR}/rtengine/klt") +else() + include_directories("${KLT_INCLUDE_DIRS}") +endif() link_directories("${PROJECT_SOURCE_DIR}/rtexif" - ${EXPAT_LIBRARY_DIRS} - ${EXTRA_LIBDIR} - ${FFTW3F_LIBRARY_DIRS} - ${GLIB2_LIBRARY_DIRS} - ${GLIBMM_LIBRARY_DIRS} - ${GOBJECT_LIBRARY_DIRS} - ${GTHREAD_LIBRARY_DIRS} - ${IPTCDATA_LIBRARY_DIRS} - ${LCMS_LIBRARY_DIRS} - ${LENSFUN_LIBRARY_DIRS} - ${RSVG_LIBRARY_DIRS} + "${EXPAT_LIBRARY_DIRS}" + "${EXTRA_LIBDIR}" + "${FFTW3F_LIBRARY_DIRS}" + "${GLIB2_LIBRARY_DIRS}" + "${GLIBMM_LIBRARY_DIRS}" + "${GOBJECT_LIBRARY_DIRS}" + "${GTHREAD_LIBRARY_DIRS}" + "${IPTCDATA_LIBRARY_DIRS}" + "${LCMS_LIBRARY_DIRS}" + "${LENSFUN_LIBRARY_DIRS}" + "${RSVG_LIBRARY_DIRS}" ) set(CAMCONSTSFILE "camconst.json") @@ -94,6 +124,7 @@ set(RTENGINESOURCEFILES ipretinex.cc ipshadowshighlights.cc ipsharpen.cc + ipsharpenedges.cc ipsoftlight.cc iptransform.cc ipvibrance.cc @@ -105,6 +136,7 @@ set(RTENGINESOURCEFILES lj92.c lmmse_demosaic.cc loadinitial.cc + munselllch.cc myfile.cc panasonic_decoders.cc pdaflinesfilter.cc @@ -159,13 +191,13 @@ endif() include_directories(BEFORE "${CMAKE_CURRENT_BINARY_DIR}") -add_library(rtengine STATIC ${RTENGINESOURCEFILES}) +add_library(rtengine STATIC "${RTENGINESOURCEFILES}") add_dependencies(rtengine UpdateInfo) # It may be nice to store library version too if(BUILD_SHARED_LIBS) - install(TARGETS rtengine DESTINATION ${LIBDIR}) + install(TARGETS rtengine DESTINATION "${LIBDIR}") endif() set_target_properties(rtengine PROPERTIES COMPILE_FLAGS "${RTENGINE_CXX_FLAGS}") @@ -186,6 +218,7 @@ target_link_libraries(rtengine rtexif ${ZLIB_LIBRARIES} ${LENSFUN_LIBRARIES} ${RSVG_LIBRARIES} + ${KLT_LIBRARIES} ) install(FILES ${CAMCONSTSFILE} DESTINATION "${DATADIR}" PERMISSIONS OWNER_WRITE OWNER_READ GROUP_READ WORLD_READ) diff --git a/rtengine/EdgePreservingDecomposition.cc b/rtengine/EdgePreservingDecomposition.cc index 700181e1d..04459e88a 100644 --- a/rtengine/EdgePreservingDecomposition.cc +++ b/rtengine/EdgePreservingDecomposition.cc @@ -55,7 +55,7 @@ float *SparseConjugateGradient(void Ax(float *Product, float *x, void *Pass), fl #endif for(int ii = 0; ii < n; ii++) { - rs += r[ii] * s[ii]; + rs += static_cast(r[ii]) * static_cast(s[ii]); } //Search direction d. @@ -84,15 +84,15 @@ float *SparseConjugateGradient(void Ax(float *Product, float *x, void *Pass), fl #endif for(int ii = 0; ii < n; ii++) { - ab += d[ii] * ax[ii]; + ab += static_cast(d[ii]) * static_cast(ax[ii]); } - if(ab == 0.0f) { + if(ab == 0.0) { break; //So unlikely. It means perfectly converged or singular, stop either way. } ab = rs / ab; - + float abf = ab; //Update x and r with this step size. double rms = 0.0; // use double precision for large summations #ifdef _OPENMP @@ -100,15 +100,15 @@ float *SparseConjugateGradient(void Ax(float *Product, float *x, void *Pass), fl #endif for(int ii = 0; ii < n; ii++) { - x[ii] += ab * d[ii]; - r[ii] -= ab * ax[ii]; //"Fast recursive formula", use explicit r = b - Ax occasionally? - rms += r[ii] * r[ii]; + x[ii] += abf * d[ii]; + r[ii] -= abf * ax[ii]; //"Fast recursive formula", use explicit r = b - Ax occasionally? + rms += rtengine::SQR(r[ii]); } rms = sqrtf(rms / n); //Quit? This probably isn't the best stopping condition, but ok. - if(rms < RMSResidual) { + if(rms < static_cast(RMSResidual)) { break; } @@ -129,20 +129,20 @@ float *SparseConjugateGradient(void Ax(float *Product, float *x, void *Pass), fl #endif for(int ii = 0; ii < n; ii++) { - rs += r[ii] * s[ii]; + rs += static_cast(r[ii]) * static_cast(s[ii]); } } ab = rs / ab; - + abf = ab; //Update search direction p. #ifdef _OPENMP #pragma omp parallel for #endif for(int ii = 0; ii < n; ii++) { - d[ii] = s[ii] + ab * d[ii]; + d[ii] = s[ii] + abf * d[ii]; } diff --git a/rtengine/FTblockDN.cc b/rtengine/FTblockDN.cc index 121c8189d..894c72ce2 100644 --- a/rtengine/FTblockDN.cc +++ b/rtengine/FTblockDN.cc @@ -56,7 +56,6 @@ #define TS 64 // Tile size #define offset 25 // shift between tiles -#define fTS ((TS/2+1)) // second dimension of Fourier tiles #define blkrad 1 // radius of block averaging #define epsilon 0.001f/(TS*TS) //tolerance @@ -64,8 +63,8 @@ namespace rtengine { -// %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -// %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +// %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +// %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% /* Structure of the algorithm: @@ -484,7 +483,6 @@ enum nrquality {QUALITY_STANDARD, QUALITY_HIGH}; void ImProcFunctions::RGB_denoise(int kall, Imagefloat * src, Imagefloat * dst, Imagefloat * calclum, float * ch_M, float *max_r, float *max_b, bool isRAW, const procparams::DirPyrDenoiseParams & dnparams, const double expcomp, const NoiseCurve & noiseLCurve, const NoiseCurve & noiseCCurve, float &nresi, float &highresi) { BENCHFUN - //#ifdef _DEBUG MyTime t1e, t2e; t1e.set(); @@ -548,7 +546,7 @@ BENCHFUN const bool denoiseMethodRgb = (dnparams.dmethod == "RGB"); // init luma noisevarL const float noiseluma = static_cast(dnparams.luma); - const float noisevarL = (useNoiseLCurve && (denoiseMethodRgb || !isRAW)) ? static_cast(SQR(((noiseluma + 1.0) / 125.0) * (10. + (noiseluma + 1.0) / 25.0))) : static_cast(SQR((noiseluma / 125.0) * (1.0 + noiseluma / 25.0))); + const float noisevarL = (useNoiseLCurve && (denoiseMethodRgb || !isRAW)) ? SQR(((noiseluma + 1.f) / 125.f) * (10.f + (noiseluma + 1.f) / 25.f)) : SQR((noiseluma / 125.f) * (1.f + noiseluma / 25.f)); const bool denoiseLuminance = (noisevarL > 0.00001f); //printf("NL=%f \n",noisevarL); @@ -635,20 +633,20 @@ BENCHFUN if (dnparams.luma != 0 || dnparams.chroma != 0 || dnparams.methodmed == "Lab" || dnparams.methodmed == "Lonly") { // gamma transform for input data - float gam = dnparams.gamma; - float gamthresh = 0.001f; + double gam = dnparams.gamma; + constexpr double gamthresh = 0.001; if (!isRAW) {//reduce gamma under 1 for Lab mode ==> TIF and JPG - if (gam < 1.9f) { - gam = 1.f - (1.9f - gam) / 3.f; //minimum gamma 0.7 - } else if (gam >= 1.9f && gam <= 3.f) { - gam = (1.4f / 1.1f) * gam - 1.41818f; + if (gam < 1.9) { + gam = 1.0 - (1.9 - gam) / 3.0; //minimum gamma 0.7 + } else if (gam >= 1.9 && gam <= 3.0) { + gam = (1.4 / 1.1) * gam - 1.41818; } } LUTf gamcurve(65536, LUT_CLIP_BELOW); - float gamslope = exp(log(static_cast(gamthresh)) / gam) / gamthresh; + const double gamslope = exp(log(gamthresh) / gam) / gamthresh; if (denoiseMethodRgb) { Color::gammaf2lut(gamcurve, gam, gamthresh, gamslope, 65535.f, 32768.f); @@ -657,9 +655,9 @@ BENCHFUN } // inverse gamma transform for output data - float igam = 1.f / gam; - float igamthresh = gamthresh * gamslope; - float igamslope = 1.f / gamslope; + const float igam = 1.0 / gam; + const float igamthresh = gamthresh * gamslope; + const float igamslope = 1.0 / gamslope; LUTf igamcurve(65536, LUT_CLIP_BELOW); @@ -669,9 +667,9 @@ BENCHFUN Color::gammanf2lut(igamcurve, igam, 32768.f, 65535.f); } - const float gain = pow(2.0f, float(expcomp)); - float params_Ldetail = min(float(dnparams.Ldetail), 99.9f); // max out to avoid div by zero when using noisevar_Ldetail as divisor - float noisevar_Ldetail = SQR(static_cast(SQR(100. - params_Ldetail) + 50.*(100. - params_Ldetail)) * TS * 0.5f); + const float gain = std::pow(2.0, expcomp); + const double params_Ldetail = std::min(dnparams.Ldetail, 99.9); // max out to avoid div by zero when using noisevar_Ldetail as divisor + const float noisevar_Ldetail = SQR(SQR(100. - params_Ldetail) + 50.0 * (100.0 - params_Ldetail) * TS * 0.5); array2D tilemask_in(TS, TS); array2D tilemask_out(TS, TS); @@ -681,13 +679,13 @@ BENCHFUN for (int i = 0; i < TS; ++i) { float i1 = abs((i > TS / 2 ? i - TS + 1 : i)); - float vmask = (i1 < border ? SQR(sin((rtengine::RT_PI * i1) / (2 * border))) : 1.0f); - float vmask2 = (i1 < 2 * border ? SQR(sin((rtengine::RT_PI * i1) / (2 * border))) : 1.0f); + float vmask = (i1 < border ? SQR(sin((rtengine::RT_PI_F * i1) / (2 * border))) : 1.f); + float vmask2 = (i1 < 2 * border ? SQR(sin((rtengine::RT_PI_F * i1) / (2 * border))) : 1.f); for (int j = 0; j < TS; ++j) { float j1 = abs((j > TS / 2 ? j - TS + 1 : j)); - tilemask_in[i][j] = (vmask * (j1 < border ? SQR(sin((rtengine::RT_PI * j1) / (2 * border))) : 1.0f)) + epsilon; - tilemask_out[i][j] = (vmask2 * (j1 < 2 * border ? SQR(sin((rtengine::RT_PI * j1) / (2 * border))) : 1.0f)) + epsilon; + tilemask_in[i][j] = (vmask * (j1 < border ? SQR(sin((rtengine::RT_PI_F * j1) / (2 * border))) : 1.0f)) + epsilon; + tilemask_out[i][j] = (vmask2 * (j1 < 2 * border ? SQR(sin((rtengine::RT_PI_F * j1) / (2 * border))) : 1.0f)) + epsilon; } } @@ -883,19 +881,19 @@ BENCHFUN int height = tilebottom - tiletop; int width2 = (width + 1) / 2; float realred, realblue; - float interm_med = static_cast(dnparams.chroma) / 10.0; + float interm_med = dnparams.chroma / 10.0; float intermred, intermblue; if (dnparams.redchro > 0.) { - intermred = (dnparams.redchro / 10.); + intermred = dnparams.redchro / 10.0; } else { - intermred = static_cast(dnparams.redchro) / 7.0; //increase slower than linear for more sensit + intermred = dnparams.redchro / 7.0; //increase slower than linear for more sensit } if (dnparams.bluechro > 0.) { - intermblue = (dnparams.bluechro / 10.); + intermblue = dnparams.bluechro / 10.0; } else { - intermblue = static_cast(dnparams.bluechro) / 7.0; //increase slower than linear for more sensit + intermblue = dnparams.bluechro / 7.0; //increase slower than linear for more sensit } if (ponder && kall == 2) { @@ -1096,7 +1094,7 @@ BENCHFUN //binary 1 or 0 for each level, eg subsampling = 0 means no subsampling, 1 means subsample //the first level only, 7 means subsample the first three levels, etc. //actual implementation only works with subsampling set to 1 - float interm_medT = static_cast(dnparams.chroma) / 10.0; + float interm_medT = dnparams.chroma / 10.0; bool execwavelet = true; if (!denoiseLuminance && interm_medT < 0.05f && dnparams.median && (dnparams.methodmed == "Lab" || dnparams.methodmed == "Lonly")) { @@ -1184,6 +1182,7 @@ BENCHFUN } else { madL[lvl][dir - 1] = SQR(MadRgb(WavCoeffs_L[dir], Wlvl_L * Hlvl_L)); } + } } } @@ -1201,16 +1200,16 @@ BENCHFUN if (!memoryAllocationFailed) { if (nrQuality == QUALITY_STANDARD) { - if (!WaveletDenoiseAllAB(*Ldecomp, *adecomp, noisevarchrom, madL, noisevarab_r, useNoiseCCurve, autoch, denoiseMethodRgb)) { //enhance mode + if (!WaveletDenoiseAllAB(*Ldecomp, *adecomp, noisevarchrom, madL, nullptr, 0, noisevarab_r, useNoiseCCurve, autoch, denoiseMethodRgb, denoiseNestedLevels)) { //enhance mode memoryAllocationFailed = true; } } else { /*if (nrQuality==QUALITY_HIGH)*/ - if (!WaveletDenoiseAll_BiShrinkAB(*Ldecomp, *adecomp, noisevarchrom, madL, noisevarab_r, useNoiseCCurve, autoch, denoiseMethodRgb)) { //enhance mode + if (!WaveletDenoiseAll_BiShrinkAB(*Ldecomp, *adecomp, noisevarchrom, madL, nullptr, 0, noisevarab_r, useNoiseCCurve, autoch, denoiseMethodRgb, denoiseNestedLevels)) { //enhance mode memoryAllocationFailed = true; } if (!memoryAllocationFailed) { - if (!WaveletDenoiseAllAB(*Ldecomp, *adecomp, noisevarchrom, madL, noisevarab_r, useNoiseCCurve, autoch, denoiseMethodRgb)) { + if (!WaveletDenoiseAllAB(*Ldecomp, *adecomp, noisevarchrom, madL, nullptr, 0, noisevarab_r, useNoiseCCurve, autoch, denoiseMethodRgb, denoiseNestedLevels)) { memoryAllocationFailed = true; } } @@ -1238,16 +1237,16 @@ BENCHFUN if (!memoryAllocationFailed) { if (nrQuality == QUALITY_STANDARD) { - if (!WaveletDenoiseAllAB(*Ldecomp, *bdecomp, noisevarchrom, madL, noisevarab_b, useNoiseCCurve, autoch, denoiseMethodRgb)) { //enhance mode + if (!WaveletDenoiseAllAB(*Ldecomp, *bdecomp, noisevarchrom, madL, nullptr, 0, noisevarab_b, useNoiseCCurve, autoch, denoiseMethodRgb, denoiseNestedLevels)) { //enhance mode memoryAllocationFailed = true; } } else { /*if (nrQuality==QUALITY_HIGH)*/ - if (!WaveletDenoiseAll_BiShrinkAB(*Ldecomp, *bdecomp, noisevarchrom, madL, noisevarab_b, useNoiseCCurve, autoch, denoiseMethodRgb)) { //enhance mode + if (!WaveletDenoiseAll_BiShrinkAB(*Ldecomp, *bdecomp, noisevarchrom, madL, nullptr, 0, noisevarab_b, useNoiseCCurve, autoch, denoiseMethodRgb, denoiseNestedLevels)) { //enhance mode memoryAllocationFailed = true; } if (!memoryAllocationFailed) { - if (!WaveletDenoiseAllAB(*Ldecomp, *bdecomp, noisevarchrom, madL, noisevarab_b, useNoiseCCurve, autoch, denoiseMethodRgb)) { + if (!WaveletDenoiseAllAB(*Ldecomp, *bdecomp, noisevarchrom, madL, nullptr, 0, noisevarab_b, useNoiseCCurve, autoch, denoiseMethodRgb, denoiseNestedLevels)) { memoryAllocationFailed = true; } } @@ -1274,16 +1273,16 @@ BENCHFUN int edge = 0; if (nrQuality == QUALITY_STANDARD) { - if (!WaveletDenoiseAllL(*Ldecomp, noisevarlum, madL, nullptr, edge)) { //enhance mode + if (!WaveletDenoiseAllL(*Ldecomp, noisevarlum, madL, nullptr, edge, denoiseNestedLevels)) { //enhance mode memoryAllocationFailed = true; } } else { /*if (nrQuality==QUALITY_HIGH)*/ - if (!WaveletDenoiseAll_BiShrinkL(*Ldecomp, noisevarlum, madL)) { //enhance mode + if (!WaveletDenoiseAll_BiShrinkL(*Ldecomp, noisevarlum, madL, nullptr, edge, denoiseNestedLevels)) { //enhance mode memoryAllocationFailed = true; } if (!memoryAllocationFailed) { - if (!WaveletDenoiseAllL(*Ldecomp, noisevarlum, madL, nullptr, edge)) { + if (!WaveletDenoiseAllL(*Ldecomp, noisevarlum, madL, nullptr, edge, denoiseNestedLevels)) { memoryAllocationFailed = true; } } @@ -1355,9 +1354,11 @@ BENCHFUN #else int subThread = 0; #endif +// float blurbuffer[TS * TS] ALIGNED64; float *Lblox = LbloxArray[subThread]; float *fLblox = fLbloxArray[subThread]; float pBuf[width + TS + 2 * blkrad * offset] ALIGNED16; +// float nbrwt[TS * TS] ALIGNED64; #ifdef _OPENMP #pragma omp for #endif @@ -1433,6 +1434,7 @@ BENCHFUN for (int hblk = 0; hblk < numblox_W; ++hblk) { RGBtile_denoise(fLblox, hblk, noisevar_Ldetail); + // RGBtile_denoise(fLblox, hblk, noisevar_Ldetail, nbrwt, blurbuffer); }//end of horizontal block loop //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% @@ -1449,8 +1451,14 @@ BENCHFUN //add row of blocks to output image tile RGBoutput_tile_row(Lblox, Ldetail, tilemask_out, height, width, topproc); + //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + }//end of vertical block loop + + //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + } + //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% #ifdef _OPENMP #pragma omp parallel for num_threads(denoiseNestedLevels) if (denoiseNestedLevels>1) @@ -2037,6 +2045,13 @@ BENCHFUN }//end of main RGB_denoise + +//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + + +//void ImProcFunctions::RGBtile_denoise(float * fLblox, int hblproc, float noisevar_Ldetail, float * nbrwt, float * blurbuffer) //for DCT void ImProcFunctions::RGBtile_denoise(float* fLblox, int hblproc, float noisevar_Ldetail) //for DCT { float nbrwt[TS * TS] ALIGNED64; @@ -2063,6 +2078,10 @@ void ImProcFunctions::RGBtile_denoise(float* fLblox, int hblproc, float noisevar } + +//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + void ImProcFunctions::RGBoutput_tile_row(float *bloxrow_L, float ** Ldetail, float ** tilemask_out, int height, int width, int top) { const int numblox_W = ceil((static_cast(width)) / (offset)); @@ -2121,7 +2140,7 @@ float ImProcFunctions::Mad(const float * DataList, const int datalen) int count_ = count - histo[median - 1]; // interpolate - return (((median - 1) + (datalen / 2 - count_) / (static_cast(count - count_))) / 0.6745); + return (((median - 1) + (datalen / 2 - count_) / (static_cast(count - count_))) / 0.6745f); } float ImProcFunctions::MadRgb(const float * DataList, const int datalen) @@ -2155,7 +2174,7 @@ float ImProcFunctions::MadRgb(const float * DataList, const int datalen) // interpolate delete[] histo; - return (((median - 1) + (datalen / 2 - count_) / (static_cast(count - count_))) / 0.6745); + return (((median - 1) + (datalen / 2 - count_) / (static_cast(count - count_))) / 0.6745f); } @@ -2190,11 +2209,19 @@ void ImProcFunctions::Noise_residualAB(const wavelet_decomposition &WaveletCoeff chmaxresid = maxresid; } -bool ImProcFunctions::WaveletDenoiseAll_BiShrinkL(const wavelet_decomposition &WaveletCoeffs_L, float *noisevarlum, float madL[8][3]) +bool ImProcFunctions::WaveletDenoiseAll_BiShrinkL(const wavelet_decomposition &WaveletCoeffs_L, float *noisevarlum, float madL[8][3], float * vari, int edge, int denoiseNestedLevels) { int maxlvl = min(WaveletCoeffs_L.maxlevel(), 5); const float eps = 0.01f; + if (edge == 1 || edge == 3 || edge == 4) { + maxlvl = 4; //for refine denoise edge wavelet + } + + if (edge == 2) { + maxlvl = 7; //for locallab denoise + } + int maxWL = 0, maxHL = 0; for (int lvl = 0; lvl < maxlvl; ++lvl) { @@ -2205,6 +2232,7 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkL(const wavelet_decomposition &W if (WaveletCoeffs_L.level_H(lvl) > maxHL) { maxHL = WaveletCoeffs_L.level_H(lvl); } + } bool memoryAllocationFailed = false; @@ -2235,14 +2263,52 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkL(const wavelet_decomposition &W float ** WavCoeffs_L = WaveletCoeffs_L.level_coeffs(lvl); if (lvl == maxlvl - 1) { - int edge = 0; - ShrinkAllL(WaveletCoeffs_L, buffer, lvl, dir, noisevarlum, madL[lvl], nullptr, edge); - } else { + // int edge = 0; + ShrinkAllL(WaveletCoeffs_L, buffer, lvl, dir, noisevarlum, madL[lvl], vari, edge); + } else { //simple wavelet shrinkage float * sfave = buffer[0] + 32; float * sfaved = buffer[2] + 96; float mad_Lr = madL[lvl][dir - 1]; + /* + if ((edge == 1 || edge == 2 || edge == 3) && vari) { + noisevarlum = blurBuffer; // we need one buffer, but fortunately we don't have to allocate a new one because we can use blurBuffer + + for (int i = 0; i < Wlvl_L * Hlvl_L; ++i) { + noisevarlum[i] = vari[lvl]; + } + } + */ + float *nvl = nullptr; + nvl = new float[Hlvl_L * Wlvl_L]; + + for (int i = 0; i < Hlvl_L * Wlvl_L; ++i) { + nvl[i] = 0.f; + } + if ((edge == 1 || edge == 2 || edge == 3) && vari) { + // nvl = blurBuffer; // we need one buffer, but fortunately we don't have to allocate a new one because we can use blurBuffer + if ((edge == 1 || edge == 3)) { + for (int i = 0; i < Hlvl_L * Wlvl_L; ++i) { + nvl[i] = vari[lvl]; + } + } + + if (edge == 2 || edge == 4) { + for (int i = 0; i < Hlvl_L * Wlvl_L; ++i) { + nvl[i] = vari[lvl] * SQR(noisevarlum[i]); + } + } + + } + + else { + for (int i = 0; i < Hlvl_L * Wlvl_L; ++i) { + nvl[i] = noisevarlum[i]; + } + + } + float levelFactor = mad_Lr * 5.f / (lvl + 1); #ifdef __SSE2__ @@ -2254,14 +2320,14 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkL(const wavelet_decomposition &W int coeffloc_L; for (coeffloc_L = 0; coeffloc_L < Hlvl_L * Wlvl_L - 3; coeffloc_L += 4) { - mad_Lv = LVFU(noisevarlum[coeffloc_L]) * levelFactorv; + mad_Lv = LVFU(nvl[coeffloc_L]) * levelFactorv; mag_Lv = SQRV(LVFU(WavCoeffs_L[dir][coeffloc_L])); STVFU(sfave[coeffloc_L], mag_Lv / (mag_Lv + mad_Lv * xexpf(-mag_Lv / (mad_Lv * ninev)) + epsv)); } for (; coeffloc_L < Hlvl_L * Wlvl_L; ++coeffloc_L) { float mag_L = SQR(WavCoeffs_L[dir][coeffloc_L]); - sfave[coeffloc_L] = mag_L / (mag_L + levelFactor * noisevarlum[coeffloc_L] * xexpf(-mag_L / (9.f * levelFactor * noisevarlum[coeffloc_L])) + eps); + sfave[coeffloc_L] = mag_L / (mag_L + levelFactor * nvl[coeffloc_L] * xexpf(-mag_L / (9.f * levelFactor * nvl[coeffloc_L])) + eps); } #else @@ -2271,12 +2337,13 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkL(const wavelet_decomposition &W int coeffloc_L = i * Wlvl_L + j; float mag_L = SQR(WavCoeffs_L[dir][coeffloc_L]); - sfave[coeffloc_L] = mag_L / (mag_L + levelFactor * noisevarlum[coeffloc_L] * xexpf(-mag_L / (9.f * levelFactor * noisevarlum[coeffloc_L])) + eps); + sfave[coeffloc_L] = mag_L / (mag_L + levelFactor * nvl[coeffloc_L] * xexpf(-mag_L / (9.f * levelFactor * nvl[coeffloc_L])) + eps); } } #endif boxblur(sfave, sfaved, lvl + 2, Wlvl_L, Hlvl_L, false); //increase smoothness by locally averaging shrinkage + #ifdef __SSE2__ vfloat sfavev; vfloat sf_Lv; @@ -2307,7 +2374,9 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkL(const wavelet_decomposition &W } #endif + delete [] nvl; } + } } } @@ -2322,11 +2391,20 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkL(const wavelet_decomposition &W return (!memoryAllocationFailed); } -bool ImProcFunctions::WaveletDenoiseAll_BiShrinkAB(const wavelet_decomposition &WaveletCoeffs_L, const wavelet_decomposition &WaveletCoeffs_ab, - float *noisevarchrom, float madL[8][3], float noisevar_ab, const bool useNoiseCCurve, bool autoch, bool denoiseMethodRgb) + +bool ImProcFunctions::WaveletDenoiseAll_BiShrinkAB(const wavelet_decomposition &WaveletCoeffs_L, const wavelet_decomposition &WaveletCoeffs_ab, float *noisevarchrom, float madL[8][3], float *variC, int local, float noisevar_ab, const bool useNoiseCCurve, bool autoch, bool denoiseMethodRgb, int denoiseNestedLevels) + { int maxlvl = WaveletCoeffs_L.maxlevel(); + if (local == 2) { + maxlvl = 7; //for local denoise + } + + if (local == 3) { + maxlvl = 4; //for shape detection + } + if (autoch && noisevar_ab <= 0.001f) { noisevar_ab = 0.02f; } @@ -2394,14 +2472,36 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkAB(const wavelet_decomposition & float ** WavCoeffs_ab = WaveletCoeffs_ab.level_coeffs(lvl); if (lvl == maxlvl - 1) { - ShrinkAllAB(WaveletCoeffs_L, WaveletCoeffs_ab, buffer, lvl, dir, noisevarchrom, noisevar_ab, useNoiseCCurve, autoch, denoiseMethodRgb, madL[lvl], madab[lvl], true); + ShrinkAllAB(WaveletCoeffs_L, WaveletCoeffs_ab, buffer, lvl, dir, noisevarchrom, noisevar_ab, useNoiseCCurve, autoch, denoiseMethodRgb, madL[lvl], nullptr, 0, madab[lvl], true); } else { //simple wavelet shrinkage + float noisevarfc; float mad_Lr = madL[lvl][dir - 1]; - float mad_abr = useNoiseCCurve ? noisevar_ab * madab[lvl][dir - 1] : SQR(noisevar_ab) * madab[lvl][dir - 1]; + float *nvc = nullptr; + nvc = new float[Hlvl_ab * Wlvl_ab]; - if (noisevar_ab > 0.001f) { + if ((local == 2 || local == 3) && variC && useNoiseCCurve) { + noisevarfc = variC[lvl]; + + for (int p = 0; p < Hlvl_ab * Wlvl_ab; p++) { + nvc[p] = 10.f * sqrt(variC[lvl]) * SQR(1.f + 4.f * noisevarchrom[p]); + } + + } else { + noisevarfc = noisevar_ab; + + for (int p = 0; p < Hlvl_ab * Wlvl_ab; p++) { + nvc[p] = noisevarchrom[p]; + } + + } + + + // float mad_abr = useNoiseCCurve ? noisevar_ab * madab[lvl][dir - 1] : SQR(noisevar_ab) * madab[lvl][dir - 1]; + float mad_abr = useNoiseCCurve ? noisevarfc * madab[lvl][dir - 1] : SQR(noisevarfc) * madab[lvl][dir - 1]; + + if (noisevarfc > 0.001f) { #ifdef __SSE2__ vfloat onev = F2V(1.f); @@ -2413,7 +2513,7 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkAB(const wavelet_decomposition & int coeffloc_ab; for (coeffloc_ab = 0; coeffloc_ab < Hlvl_ab * Wlvl_ab - 3; coeffloc_ab += 4) { - mad_abv = LVFU(noisevarchrom[coeffloc_ab]) * mad_abrv; + mad_abv = LVFU(nvc[coeffloc_ab]) * mad_abrv; tempabv = LVFU(WavCoeffs_ab[dir][coeffloc_ab]); mag_Lv = LVFU(WavCoeffs_L[dir][coeffloc_ab]); @@ -2426,7 +2526,7 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkAB(const wavelet_decomposition & for (; coeffloc_ab < Hlvl_ab * Wlvl_ab; ++coeffloc_ab) { float mag_L = SQR(WavCoeffs_L[dir][coeffloc_ab ]); float mag_ab = SQR(WavCoeffs_ab[dir][coeffloc_ab]); - WavCoeffs_ab[dir][coeffloc_ab] *= SQR(1.f - xexpf(-(mag_ab / (noisevarchrom[coeffloc_ab] * mad_abr)) - (mag_L / (9.f * mad_Lr)))/*satfactor_a*/); + WavCoeffs_ab[dir][coeffloc_ab] *= SQR(1.f - xexpf(-(mag_ab / (nvc[coeffloc_ab] * mad_abr)) - (mag_L / (9.f * mad_Lr)))/*satfactor_a*/); }//now chrominance coefficients are denoised #else @@ -2438,7 +2538,7 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkAB(const wavelet_decomposition & float mag_L = SQR(WavCoeffs_L[dir][coeffloc_ab ]); float mag_ab = SQR(WavCoeffs_ab[dir][coeffloc_ab]); - WavCoeffs_ab[dir][coeffloc_ab] *= SQR(1.f - xexpf(-(mag_ab / (noisevarchrom[coeffloc_ab] * mad_abr)) - (mag_L / (9.f * mad_Lr)))/*satfactor_a*/); + WavCoeffs_ab[dir][coeffloc_ab] *= SQR(1.f - xexpf(-(mag_ab / (nvc[coeffloc_ab] * mad_abr)) - (mag_L / (9.f * mad_Lr)))/*satfactor_a*/); } }//now chrominance coefficients are denoised @@ -2446,9 +2546,12 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkAB(const wavelet_decomposition & #endif } + delete [] nvc; + } } } + } for (int i = 2; i >= 0; i--) { @@ -2460,16 +2563,20 @@ bool ImProcFunctions::WaveletDenoiseAll_BiShrinkAB(const wavelet_decomposition & } -bool ImProcFunctions::WaveletDenoiseAllL(const wavelet_decomposition &WaveletCoeffs_L, float *noisevarlum, float madL[8][3], float * vari, int edge)//mod JD +bool ImProcFunctions::WaveletDenoiseAllL(const wavelet_decomposition &WaveletCoeffs_L, float *noisevarlum, float madL[8][3], float * vari, int edge, int denoiseNestedLevels)//mod JD { int maxlvl = min(WaveletCoeffs_L.maxlevel(), 5); - if (edge == 1) { + if (edge == 1 || edge == 3) { maxlvl = 4; //for refine denoise edge wavelet } + if (edge == 2) { + maxlvl = 7; //for locallab denoise + } + int maxWL = 0, maxHL = 0; for (int lvl = 0; lvl < maxlvl; ++lvl) { @@ -2518,11 +2625,20 @@ bool ImProcFunctions::WaveletDenoiseAllL(const wavelet_decomposition &WaveletCoe bool ImProcFunctions::WaveletDenoiseAllAB(const wavelet_decomposition &WaveletCoeffs_L, const wavelet_decomposition &WaveletCoeffs_ab, - float *noisevarchrom, float madL[8][3], float noisevar_ab, const bool useNoiseCCurve, bool autoch, bool denoiseMethodRgb)//mod JD + float *noisevarchrom, float madL[8][3], float *variC, int local, float noisevar_ab, const bool useNoiseCCurve, bool autoch, bool denoiseMethodRgb, int denoiseNestedLevels)//mod JD { int maxlvl = WaveletCoeffs_L.maxlevel(); + + if (local == 2) { + maxlvl = 7; //for local denoise + } + + if (local == 3) { + maxlvl = 4; //for shape detection + } + int maxWL = 0, maxHL = 0; for (int lvl = 0; lvl < maxlvl; ++lvl) { @@ -2556,7 +2672,7 @@ bool ImProcFunctions::WaveletDenoiseAllAB(const wavelet_decomposition &WaveletCo for (int lvl = 0; lvl < maxlvl; ++lvl) { for (int dir = 1; dir < 4; ++dir) { - ShrinkAllAB(WaveletCoeffs_L, WaveletCoeffs_ab, buffer, lvl, dir, noisevarchrom, noisevar_ab, useNoiseCCurve, autoch, denoiseMethodRgb, madL[lvl]); + ShrinkAllAB(WaveletCoeffs_L, WaveletCoeffs_ab, buffer, lvl, dir, noisevarchrom, noisevar_ab, useNoiseCCurve, autoch, denoiseMethodRgb, madL[lvl], variC, local, nullptr, 0); } } } @@ -2570,8 +2686,6 @@ bool ImProcFunctions::WaveletDenoiseAllAB(const wavelet_decomposition &WaveletCo return (!memoryAllocationFailed); } -//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% void ImProcFunctions::ShrinkAllL(const wavelet_decomposition &WaveletCoeffs_L, float **buffer, int level, int dir, @@ -2583,7 +2697,7 @@ void ImProcFunctions::ShrinkAllL(const wavelet_decomposition &WaveletCoeffs_L, f float * sfave = buffer[0] + 32; float * sfaved = buffer[1] + 64; - float * blurBuffer = buffer[2] + 96; +// float * blurBuffer = buffer[2] + 96; const int W_L = WaveletCoeffs_L.level_W(level); const int H_L = WaveletCoeffs_L.level_H(level); @@ -2592,30 +2706,54 @@ void ImProcFunctions::ShrinkAllL(const wavelet_decomposition &WaveletCoeffs_L, f const float mad_L = madL[dir - 1] ; const float levelFactor = mad_L * 5.f / static_cast(level + 1); - if (edge == 1 && vari) { - noisevarlum = blurBuffer; // we need one buffer, but fortunately we don't have to allocate a new one because we can use blurBuffer + float *nvl = nullptr; + nvl = new float[ H_L * W_L]; - for (int i = 0; i < W_L * H_L; ++i) { - noisevarlum[i] = vari[level]; - } + for (int i = 0; i < W_L * H_L; ++i) { + nvl[i] = 0.f; } + if ((edge == 1 || edge == 2 || edge == 3) && vari) { + // nvl = blurBuffer; // we need one buffer, but fortunately we don't have to allocate a new one because we can use blurBuffer + if ((edge == 1 || edge == 3)) { + for (int i = 0; i < W_L * H_L; ++i) { + nvl[i] = vari[level]; //* SQR(1.f + 4.f * noisevarchrom[p]); + } + } + + if (edge == 2 || edge == 4) { + for (int i = 0; i < W_L * H_L; ++i) { + nvl[i] = vari[level] * SQR(noisevarlum[i]); + } + } + + } + + else { + for (int i = 0; i < W_L * H_L; ++i) { + nvl[i] = noisevarlum[i]; + } + + } int i = 0; #ifdef __SSE2__ const vfloat levelFactorv = F2V(levelFactor); const vfloat ninev = F2V(9.f); const vfloat epsv = F2V(eps); - for (; i < W_L * H_L - 3; i += 4) { - const vfloat mad_Lv = LVFU(noisevarlum[i]) * levelFactorv; + + for (i = 0; i < W_L * H_L - 3; i += 4) { + // const vfloat mad_Lv = LVFU(noisevarlum[i]) * levelFactorv; + const vfloat mad_Lv = LVFU(nvl[i]) * levelFactorv; const vfloat magv = SQRV(LVFU(WavCoeffs_L[dir][i])); STVFU(sfave[i], magv / (magv + mad_Lv * xexpf(-magv / (ninev * mad_Lv)) + epsv)); } + #endif // few remaining pixels for (; i < W_L * H_L; ++i) { - const float mag = SQR(WavCoeffs_L[dir][i]); - sfave[i] = mag / (mag + levelFactor * noisevarlum[i] * xexpf(-mag / (9 * levelFactor * noisevarlum[i])) + eps); + float mag = SQR(WavCoeffs_L[dir][i]); + sfave[i] = mag / (mag + levelFactor * nvl[i] * xexpf(-mag / (9 * levelFactor * nvl[i])) + eps); } boxblur(sfave, sfaved, level + 2, W_L, H_L, false); //increase smoothness by locally averaging shrinkage @@ -2635,12 +2773,15 @@ void ImProcFunctions::ShrinkAllL(const wavelet_decomposition &WaveletCoeffs_L, f //use smoothed shrinkage unless local shrinkage is much less WavCoeffs_L[dir][i] *= (SQR(sfaved[i]) + SQR(sf)) / (sfaved[i] + sf + eps); }//now luminance coefficients are denoised + + delete [] nvl; + } -void ImProcFunctions::ShrinkAllAB(const wavelet_decomposition &WaveletCoeffs_L, const wavelet_decomposition &WaveletCoeffs_ab, float **buffer, int level, int dir, - float *noisevarchrom, float noisevar_ab, const bool useNoiseCCurve, bool autoch, - bool denoiseMethodRgb, float * madL, float * madaab, bool madCalculated) +void ImProcFunctions::ShrinkAllAB(const wavelet_decomposition & WaveletCoeffs_L, const wavelet_decomposition & WaveletCoeffs_ab, float **buffer, int level, int dir, + float * noisevarchrom, float noisevar_ab, const bool useNoiseCCurve, bool autoch, + bool denoiseMethodRgb, float * madL, float * variC, int local, float * madaab, bool madCalculated) { //simple wavelet shrinkage @@ -2652,6 +2793,7 @@ void ImProcFunctions::ShrinkAllAB(const wavelet_decomposition &WaveletCoeffs_L, float * sfaveab = buffer[0] + 32; float * sfaveabd = buffer[1] + 64; + // float * blurBuffer = buffer[2] + 96; int W_ab = WaveletCoeffs_ab.level_W(level); int H_ab = WaveletCoeffs_ab.level_H(level); @@ -2671,9 +2813,30 @@ void ImProcFunctions::ShrinkAllAB(const wavelet_decomposition &WaveletCoeffs_L, madab = SQR(MadRgb(WavCoeffs_ab[dir], W_ab * H_ab)); } } + float noisevarfc; - if (noisevar_ab > 0.001f) { - madab = useNoiseCCurve ? madab : madab * noisevar_ab; + float *nvc = nullptr; + nvc = new float[ H_ab * W_ab]; + + if ((local == 2 || local == 3) && variC && useNoiseCCurve) { + noisevarfc = variC[level]; + for (int p = 0; p < H_ab * W_ab; p++) { + nvc[p] = 10.f * sqrt(variC[level]) * SQR(1.f + 4.f * noisevarchrom[p]); + } + + } else { + noisevarfc = noisevar_ab; + + for (int p = 0; p < H_ab * W_ab; p++) { + nvc[p] = noisevarchrom[p]; + } + + } + + // printf("varfc=%f nvc0=%f nvc1=%f nvc2=%f\n", noisevarfc, nvc[10], nvc[H_ab * W_ab /3], nvc[H_ab * W_ab /2]); + if (noisevarfc > 0.001f) {//noisevar_ab + //madab = useNoiseCCurve ? madab : madab * noisevar_ab; + madab = useNoiseCCurve ? madab : madab * noisevarfc; #ifdef __SSE2__ vfloat onev = F2V(1.f); vfloat mad_abrv = F2V(madab); @@ -2681,10 +2844,11 @@ void ImProcFunctions::ShrinkAllAB(const wavelet_decomposition &WaveletCoeffs_L, vfloat rmadLm9v = onev / F2V(mad_L * 9.f); vfloat mad_abv ; vfloat mag_Lv, mag_abv; + int coeffloc_ab; for (coeffloc_ab = 0; coeffloc_ab < H_ab * W_ab - 3; coeffloc_ab += 4) { - mad_abv = LVFU(noisevarchrom[coeffloc_ab]) * mad_abrv; + mad_abv = LVFU(nvc[coeffloc_ab]) * mad_abrv; mag_Lv = LVFU(WavCoeffs_L[dir][coeffloc_ab]); mag_abv = SQRV(LVFU(WavCoeffs_ab[dir][coeffloc_ab])); @@ -2696,7 +2860,7 @@ void ImProcFunctions::ShrinkAllAB(const wavelet_decomposition &WaveletCoeffs_L, for (; coeffloc_ab < H_ab * W_ab; ++coeffloc_ab) { float mag_L = SQR(WavCoeffs_L[dir][coeffloc_ab]); float mag_ab = SQR(WavCoeffs_ab[dir][coeffloc_ab]); - sfaveab[coeffloc_ab] = (1.f - xexpf(-(mag_ab / (noisevarchrom[coeffloc_ab] * madab)) - (mag_L / (9.f * mad_L)))); + sfaveab[coeffloc_ab] = (1.f - xexpf(-(mag_ab / (nvc[coeffloc_ab] * madab)) - (mag_L / (9.f * mad_L)))); }//now chrominance coefficients are denoised #else @@ -2706,13 +2870,14 @@ void ImProcFunctions::ShrinkAllAB(const wavelet_decomposition &WaveletCoeffs_L, int coeffloc_ab = i * W_ab + j; float mag_L = SQR(WavCoeffs_L[dir][coeffloc_ab]); float mag_ab = SQR(WavCoeffs_ab[dir][coeffloc_ab]); - sfaveab[coeffloc_ab] = (1.f - xexpf(-(mag_ab / (noisevarchrom[coeffloc_ab] * madab)) - (mag_L / (9.f * mad_L)))); + sfaveab[coeffloc_ab] = (1.f - xexpf(-(mag_ab / (nvc[coeffloc_ab] * madab)) - (mag_L / (9.f * mad_L)))); } }//now chrominance coefficients are denoised #endif - boxblur(sfaveab, sfaveabd, level + 2, W_ab, H_ab, false); //increase smoothness by locally averaging shrinkage + +// boxblur(sfaveab, sfaveabd, blurBuffer, level + 2, level + 2, W_ab, H_ab); //increase smoothness by locally averaging shrinkage #ifdef __SSE2__ vfloat epsv = F2V(eps); vfloat sfabv; @@ -2750,12 +2915,13 @@ void ImProcFunctions::ShrinkAllAB(const wavelet_decomposition &WaveletCoeffs_L, #endif } + delete [] nvc; } void ImProcFunctions::ShrinkAll_info(float ** WavCoeffs_a, float ** WavCoeffs_b, - int W_ab, int H_ab, float **noisevarlum, float **noisevarchrom, float **noisevarhue, float &chaut, int &Nb, float &redaut, float &blueaut, - float &maxredaut, float &maxblueaut, float &minredaut, float &minblueaut, int schoice, int lvl, float &chromina, float &sigma, float &lumema, float &sigma_L, float &redyel, float &skinc, float &nsknc, - float &maxchred, float &maxchblue, float &minchred, float &minchblue, int &nb, float &chau, float &chred, float &chblue, bool denoiseMethodRgb) + int W_ab, int H_ab, float **noisevarlum, float **noisevarchrom, float **noisevarhue, float & chaut, int &Nb, float & redaut, float & blueaut, + float & maxredaut, float & maxblueaut, float & minredaut, float & minblueaut, int schoice, int lvl, float & chromina, float & sigma, float & lumema, float & sigma_L, float & redyel, float & skinc, float & nsknc, + float & maxchred, float & maxchblue, float & minchred, float & minchblue, int &nb, float & chau, float & chred, float & chblue, bool denoiseMethodRgb) { //simple wavelet shrinkage @@ -2870,9 +3036,9 @@ void ImProcFunctions::ShrinkAll_info(float ** WavCoeffs_a, float ** WavCoeffs_b, } -void ImProcFunctions::WaveletDenoiseAll_info(int levwav, const wavelet_decomposition &WaveletCoeffs_a, - const wavelet_decomposition &WaveletCoeffs_b, float **noisevarlum, float **noisevarchrom, float **noisevarhue, float &chaut, int &Nb, float &redaut, float &blueaut, float &maxredaut, float &maxblueaut, float &minredaut, float &minblueaut, int schoice, - float &chromina, float &sigma, float &lumema, float &sigma_L, float &redyel, float &skinc, float &nsknc, float &maxchred, float &maxchblue, float &minchred, float &minchblue, int &nb, float &chau, float &chred, float &chblue, bool denoiseMethodRgb) +void ImProcFunctions::WaveletDenoiseAll_info(int levwav, const wavelet_decomposition & WaveletCoeffs_a, + const wavelet_decomposition & WaveletCoeffs_b, float **noisevarlum, float **noisevarchrom, float **noisevarhue, float & chaut, int &Nb, float & redaut, float & blueaut, float & maxredaut, float & maxblueaut, float & minredaut, float & minblueaut, int schoice, + float & chromina, float & sigma, float & lumema, float & sigma_L, float & redyel, float & skinc, float & nsknc, float & maxchred, float & maxchblue, float & minchred, float & minchblue, int &nb, float & chau, float & chred, float & chblue, bool denoiseMethodRgb) { int maxlvl = levwav; @@ -2908,14 +3074,14 @@ void ImProcFunctions::RGB_denoise_infoGamCurve(const procparams::DirPyrDenoisePa bool denoiseMethodRgb = (dnparams.dmethod == "RGB"); if (denoiseMethodRgb) { - gamslope = exp(log(static_cast(gamthresh)) / gam) / gamthresh; + gamslope = exp(log(static_cast(gamthresh)) / static_cast(gam)) / static_cast(gamthresh); Color::gammaf2lut(gamcurve, gam, gamthresh, gamslope, 65535.f, 32768.f); } else { Color::gammanf2lut(gamcurve, gam, 65535.f, 32768.f); } } -void ImProcFunctions::calcautodn_info(float &chaut, float &delta, int Nb, int levaut, float maxmax, float lumema, float chromina, int mode, int lissage, float redyel, float skinc, float nsknc) +void ImProcFunctions::calcautodn_info(float & chaut, float & delta, int Nb, int levaut, float maxmax, float lumema, float chromina, int mode, int lissage, float redyel, float skinc, float nsknc) { float reducdelta = 1.f; @@ -3189,19 +3355,19 @@ void ImProcFunctions::RGB_denoise_info(Imagefloat * src, Imagefloat * provicalc, } float realred, realblue; - float interm_med = static_cast(dnparams.chroma) / 10.0; + float interm_med = dnparams.chroma / 10.0; float intermred, intermblue; if (dnparams.redchro > 0.) { - intermred = (dnparams.redchro / 10.); + intermred = dnparams.redchro / 10.0; } else { - intermred = static_cast(dnparams.redchro) / 7.0; //increase slower than linear for more sensit + intermred = dnparams.redchro / 7.0; //increase slower than linear for more sensit } if (dnparams.bluechro > 0.) { - intermblue = (dnparams.bluechro / 10.); + intermblue = dnparams.bluechro / 10.0; } else { - intermblue = static_cast(dnparams.bluechro) / 7.0; //increase slower than linear for more sensit + intermblue = dnparams.bluechro / 7.0; //increase slower than linear for more sensit } realred = interm_med + intermred; diff --git a/rtengine/LUT.h b/rtengine/LUT.h index a80e5996d..6ba7d570f 100644 --- a/rtengine/LUT.h +++ b/rtengine/LUT.h @@ -254,7 +254,6 @@ public: } // handy to sum up per thread histograms. #pragma omp simd speeds up the loop by about factor 3 for LUTu (uint32_t). - template::value>::type> LUT & operator+=(const LUT& rhs) { if (rhs.size == this->size) { diff --git a/rtengine/PF_correct_RT.cc b/rtengine/PF_correct_RT.cc index 9a95b8e2f..15b7b21ee 100644 --- a/rtengine/PF_correct_RT.cc +++ b/rtengine/PF_correct_RT.cc @@ -103,7 +103,7 @@ void ImProcFunctions::PF_correct_RT(LabImage * lab, double radius, int thresh) // no precalculated values without SSE => calculate const float HH = xatan2f(lab->b[i][j], lab->a[i][j]); #endif - float chparam = chCurve->getVal((Color::huelab_to_huehsv2(HH))) - 0.5f; // get C=f(H) + float chparam = chCurve->getVal((Color::huelab_to_huehsv2(HH))) - 0.5; // get C=f(H) if (chparam < 0.f) { chparam *= 2.f; // increased action if chparam < 0 @@ -113,25 +113,25 @@ void ImProcFunctions::PF_correct_RT(LabImage * lab, double radius, int thresh) } const float chroma = chromaChfactor * (SQR(lab->a[i][j] - tmpa[i][j]) + SQR(lab->b[i][j] - tmpb[i][j])); // modulate chroma function hue - chromave += chroma; + chromave += static_cast(chroma); fringe[i * width + j] = chroma; } } } chromave /= height * width; - if (chromave > 0.0) { // now as chromave is calculated, we postprocess fringe to reduce the number of divisions in future + const float chromavef = chromave; #ifdef _OPENMP #pragma omp parallel for simd #endif for (int j = 0; j < width * height; j++) { - fringe[j] = 1.f / (fringe[j] + chromave); + fringe[j] = 1.f / (fringe[j] + chromavef); } - const float threshfactor = 1.f / (SQR(thresh / 33.f) * chromave * 5.0f + chromave); + const float threshfactor = 1.f / (SQR(thresh / 33.f) * chromavef * 5.0f + chromavef); const int halfwin = std::ceil(2 * radius) + 1; // Issue 1674: @@ -297,7 +297,7 @@ void ImProcFunctions::PF_correct_RTcam(CieImage * ncie, double radius, int thres // no precalculated values without SSE => calculate const float HH = xatan2f(srbb[i][j], sraa[i][j]); #endif - float chparam = chCurve->getVal(Color::huelab_to_huehsv2(HH)) - 0.5f; //get C=f(H) + float chparam = chCurve->getVal(Color::huelab_to_huehsv2(HH)) - 0.5; //get C=f(H) if (chparam < 0.f) { chparam *= 2.f; // increase action if chparam < 0 @@ -307,7 +307,7 @@ void ImProcFunctions::PF_correct_RTcam(CieImage * ncie, double radius, int thres } const float chroma = chromaChfactor * (SQR(sraa[i][j] - tmaa[i][j]) + SQR(srbb[i][j] - tmbb[i][j])); //modulate chroma function hue - chromave += chroma; + chromave += static_cast(chroma); fringe[i * width + j] = chroma; } } @@ -317,15 +317,16 @@ void ImProcFunctions::PF_correct_RTcam(CieImage * ncie, double radius, int thres if (chromave > 0.0) { // now as chromave is calculated, we postprocess fringe to reduce the number of divisions in future + const float chromavef = chromave; #ifdef _OPENMP #pragma omp parallel for simd #endif for (int j = 0; j < width * height; j++) { - fringe[j] = 1.f / (fringe[j] + chromave); + fringe[j] = 1.f / (fringe[j] + chromavef); } - const float threshfactor = 1.f / (SQR(thresh / 33.f) * chromave * 5.0f + chromave); + const float threshfactor = 1.f / (SQR(thresh / 33.f) * chromavef * 5.0f + chromavef); const int halfwin = std::ceil(2 * radius) + 1; // Issue 1674: @@ -695,7 +696,7 @@ void ImProcFunctions::Badpixelscam(CieImage * ncie, double radius, int thresh, i for (int i = 0; i < height; i++) { for (int j = 0; j < width; j++) { const float chroma = SQR(sraa[i][j] - tmaa[i][j]) + SQR(srbb[i][j] - tmbb[i][j]); - chrommed += chroma; + chrommed += static_cast(chroma); badpix[i * width + j] = chroma; } } @@ -703,15 +704,16 @@ void ImProcFunctions::Badpixelscam(CieImage * ncie, double radius, int thresh, i chrommed /= height * width; if (chrommed > 0.0) { + const float chrommedf = chrommed; // now as chrommed is calculated, we postprocess badpix to reduce the number of divisions in future - const float threshfactor = 1.f / ((thresh * chrommed) / 33.f + chrommed); + const float threshfactor = 1.f / ((thresh * chrommedf) / 33.f + chrommedf); const int halfwin = std::ceil(2 * radius) + 1; #ifdef _OPENMP #pragma omp parallel #endif { #ifdef __SSE2__ - const vfloat chrommedv = F2V(chrommed); + const vfloat chrommedv = F2V(chrommedf); const vfloat onev = F2V(1.f); #endif #ifdef _OPENMP @@ -726,7 +728,7 @@ void ImProcFunctions::Badpixelscam(CieImage * ncie, double radius, int thresh, i } #endif for (; j < width; j++) { - badpix[i * width + j] = 1.f / (badpix[i * width + j] + chrommed); + badpix[i * width + j] = 1.f / (badpix[i * width + j] + chrommedf); } } @@ -1040,7 +1042,7 @@ void ImProcFunctions::BadpixelsLab(LabImage * lab, double radius, int thresh, fl for (int i = 0; i < height; i++) { for (int j = 0; j < width; j++) { const float chroma = SQR(lab->a[i][j] - tmaa[i][j]) + SQR(lab->b[i][j] - tmbb[i][j]); - chrommed += chroma; + chrommed += static_cast(chroma); badpix[i * width + j] = chroma; } } @@ -1049,13 +1051,13 @@ void ImProcFunctions::BadpixelsLab(LabImage * lab, double radius, int thresh, fl if (chrommed > 0.0) { // now as chrommed is calculated, we postprocess badpix to reduce the number of divisions in future - + const float chrommedf = chrommed; #ifdef _OPENMP #pragma omp parallel #endif { #ifdef __SSE2__ - const vfloat chrommedv = F2V(chrommed); + const vfloat chrommedv = F2V(chrommedf); const vfloat onev = F2V(1.f); #endif #ifdef _OPENMP @@ -1070,12 +1072,12 @@ void ImProcFunctions::BadpixelsLab(LabImage * lab, double radius, int thresh, fl } #endif for (; j < width; j++) { - badpix[i * width + j] = 1.f / (badpix[i * width + j] + chrommed); + badpix[i * width + j] = 1.f / (badpix[i * width + j] + chrommedf); } } } - const float threshfactor = 1.f / ((thresh * chrommed) / 33.f + chrommed); + const float threshfactor = 1.f / ((thresh * chrommedf) / 33.f + chrommedf); chrom *= 327.68f; chrom *= chrom; diff --git a/rtengine/ahd_demosaic_RT.cc b/rtengine/ahd_demosaic_RT.cc index 064dfd6e1..536726925 100644 --- a/rtengine/ahd_demosaic_RT.cc +++ b/rtengine/ahd_demosaic_RT.cc @@ -52,13 +52,13 @@ void RawImageSource::ahd_demosaic() int width = W, height = H; - constexpr double xyz_rgb[3][3] = { /* XYZ from RGB */ - { 0.412453, 0.357580, 0.180423 }, - { 0.212671, 0.715160, 0.072169 }, - { 0.019334, 0.119193, 0.950227 } + constexpr float xyz_rgb[3][3] = { /* XYZ from RGB */ + { 0.412453f, 0.357580f, 0.180423f }, + { 0.212671f, 0.715160f, 0.072169f }, + { 0.019334f, 0.119193f, 0.950227f } }; - constexpr float d65_white[3] = { 0.950456, 1, 1.088754 }; + constexpr float d65_white[3] = { 0.950456f, 1.f, 1.088754f }; double progress = 0.0; @@ -76,7 +76,7 @@ void RawImageSource::ahd_demosaic() for (unsigned int j = 0; j < 3; j++) { xyz_cam[i][j] = 0; for (int k = 0; k < 3; k++) { - xyz_cam[i][j] += xyz_rgb[i][k] * imatrices.rgb_cam[k][j] / d65_white[i]; + xyz_cam[i][j] += xyz_rgb[i][k] * static_cast(imatrices.rgb_cam[k][j]) / d65_white[i]; } } } diff --git a/rtengine/badpixels.cc b/rtengine/badpixels.cc index 0ae63a618..97294bdf7 100644 --- a/rtengine/badpixels.cc +++ b/rtengine/badpixels.cc @@ -477,7 +477,7 @@ int RawImageSource::interpolateBadPixelsXtrans(const PixelsMap &bitmapBads) int RawImageSource::findHotDeadPixels(PixelsMap &bpMap, const float thresh, const bool findHotPixels, const bool findDeadPixels) const { BENCHFUN - const float varthresh = (20.0 * (thresh / 100.0) + 1.0) / 24.f; + const float varthresh = (20.f * (thresh / 100.f) + 1.f) / 24.f; // counter for dead or hot pixels int counter = 0; diff --git a/rtengine/calc_distort.cc b/rtengine/calc_distort.cc index 7af47adb2..3a7a4a1c4 100644 --- a/rtengine/calc_distort.cc +++ b/rtengine/calc_distort.cc @@ -5,8 +5,8 @@ locations (before and after tracking) to text files and to PPM files, and prints the features to the screen. **********************************************************************/ -#include "klt/pnmio.h" -#include "klt/klt.h" +#include +#include #include #include diff --git a/rtengine/camconst.cc b/rtengine/camconst.cc index d136d6a21..aab2a252c 100644 --- a/rtengine/camconst.cc +++ b/rtengine/camconst.cc @@ -2,20 +2,25 @@ * This file is part of RawTherapee. */ #include "camconst.h" + +#include +#include +#include +#include +#include +#include +#include + #include #include #include + #include "settings.h" #include "rt_math.h" -#include -#include // cJSON is a very minimal JSON parser lib in C, not for threaded stuff etc, so if we're going to use JSON more than just // here we should probably replace cJSON with something beefier. #include "cJSON.h" -#include -#include -#include namespace rtengine { @@ -30,66 +35,70 @@ CameraConst::CameraConst() : pdafOffset(0) } -bool -CameraConst::parseApertureScaling(CameraConst *cc, void *ji_) +bool CameraConst::parseApertureScaling(CameraConst *cc, const void *ji_) { - cJSON *ji = (cJSON *)ji_; + const cJSON *ji = static_cast(ji_); if (ji->type != cJSON_Array) { fprintf(stderr, "\"ranges\":\"aperture_scaling\" must be an array\n"); return false; } - for (ji = ji->child; ji != nullptr; ji = ji->next) { - cJSON *js = cJSON_GetObjectItem(ji, "aperture"); + for (ji = ji->child; ji; ji = ji->next) { + const cJSON *js = cJSON_GetObjectItem(ji, "aperture"); if (!js) { fprintf(stderr, "missing \"ranges\":\"aperture_scaling\":\"aperture\" object item.\n"); return false; - } else if (js->type != cJSON_Number) { + } + + if (js->type != cJSON_Number) { fprintf(stderr, "\"ranges\":\"aperture_scaling\":\"aperture\" must be a number.\n"); return false; } - float aperture = (float)js->valuedouble; + const float aperture = js->valuedouble; js = cJSON_GetObjectItem(ji, "scale_factor"); if (!js) { fprintf(stderr, "missing \"ranges\":\"aperture_scaling\":\"scale_factor\" object item.\n"); return false; - } else if (js->type != cJSON_Number) { + } + + if (js->type != cJSON_Number) { fprintf(stderr, "\"ranges\":\"aperture_scaling\":\"scale_factor\" must be a number.\n"); return false; } - float scale_factor = (float)js->valuedouble; - cc->mApertureScaling.insert(std::pair(aperture, scale_factor)); + const float scale_factor = js->valuedouble; + cc->mApertureScaling.emplace(aperture, scale_factor); } return true; } -bool -CameraConst::parseLevels(CameraConst *cc, int bw, void *ji_) +bool CameraConst::parseLevels(CameraConst *cc, int bw, const void *ji_) { - cJSON *ji = (cJSON *)ji_; + const cJSON *ji = static_cast(ji_); if (ji->type == cJSON_Number) { - struct camera_const_levels lvl; + camera_const_levels lvl; lvl.levels[0] = lvl.levels[1] = lvl.levels[2] = lvl.levels[3] = ji->valueint; - cc->mLevels[bw].insert(std::pair(0, lvl)); + cc->mLevels[bw].emplace(0, lvl); return true; - } else if (ji->type != cJSON_Array) { + } + + if (ji->type != cJSON_Array) { fprintf(stderr, "\"ranges\":\"%s\" must be a number or an array\n", bw ? "white" : "black"); return false; } if (ji->child->type == cJSON_Number) { - struct camera_const_levels lvl; + camera_const_levels lvl; int i; - cJSON *js; + const cJSON *js; - for (js = ji->child, i = 0; js != nullptr && i < 4; js = js->next, i++) { + for (js = ji->child, i = 0; js && i < 4; js = js->next, i++) { lvl.levels[i] = js->valueint; } @@ -97,39 +106,36 @@ CameraConst::parseLevels(CameraConst *cc, int bw, void *ji_) lvl.levels[3] = lvl.levels[1]; // G2 = G1 } else if (i == 1) { lvl.levels[3] = lvl.levels[2] = lvl.levels[1] = lvl.levels[0]; - } else if (i != 4 || js != nullptr) { + } else if (i != 4 || js) { fprintf(stderr, "\"ranges\":\"%s\" array must have 1, 3 or 4 numbers.\n", bw ? "white" : "black"); return false; } - cc->mLevels[bw].insert(std::pair(0, lvl)); + cc->mLevels[bw].emplace(0, lvl); return true; } - for (ji = ji->child; ji != nullptr; ji = ji->next) { - int iso[1000] = { 0 }; - int iso_count = 0; - cJSON *js = cJSON_GetObjectItem(ji, "iso"); + for (ji = ji->child; ji; ji = ji->next) { + const cJSON *js = cJSON_GetObjectItem(ji, "iso"); if (!js) { fprintf(stderr, "missing \"ranges\":\"%s\":\"iso\" object item.\n", bw ? "white" : "black"); return false; - } else if (js->type == cJSON_Number) { - iso[0] = js->valueint; - iso_count = 1; - } else if (js->type == cJSON_Array) { - int i; + } - for (js = js->child, i = 0; js != nullptr && i < 1000; js = js->next, i++) { + std::vector isos; + + if (js->type == cJSON_Number) { + isos.push_back(js->valueint); + } else if (js->type == cJSON_Array) { + for (js = js->child; js; js = js->next) { if (js->type != cJSON_Number) { fprintf(stderr, "\"ranges\":\"%s\":\"iso\" must be a number or an array of numbers.\n", bw ? "white" : "black"); return false; } - iso[i] = js->valueint; + isos.push_back(js->valueint); } - - iso_count = i; } else { fprintf(stderr, "\"ranges\":\"%s\":\"iso\" must be an array or a number.\n", bw ? "white" : "black"); return false; @@ -142,14 +148,14 @@ CameraConst::parseLevels(CameraConst *cc, int bw, void *ji_) return false; } - struct camera_const_levels lvl; + camera_const_levels lvl; if (js->type == cJSON_Number) { lvl.levels[0] = lvl.levels[1] = lvl.levels[2] = lvl.levels[3] = js->valueint; } else if (js->type == cJSON_Array) { int i; - for (js = js->child, i = 0; js != nullptr && i < 4; js = js->next, i++) { + for (js = js->child, i = 0; js && i < 4; js = js->next, i++) { if (js->type != cJSON_Number) { fprintf(stderr, "\"ranges\":\"%s\":\"levels\" must be a number or an array of numbers.\n", bw ? "white" : "black"); return false; @@ -162,7 +168,7 @@ CameraConst::parseLevels(CameraConst *cc, int bw, void *ji_) lvl.levels[3] = lvl.levels[1]; // G2 = G1 } else if (i == 1) { lvl.levels[3] = lvl.levels[2] = lvl.levels[1] = lvl.levels[0]; - } else if (i != 4 || js != nullptr) { + } else if (i != 4 || js) { fprintf(stderr, "\"ranges\":\"%s\":\"levels\" array must have 1, 3 or 4 numbers.\n", bw ? "white" : "black"); return false; } @@ -171,40 +177,38 @@ CameraConst::parseLevels(CameraConst *cc, int bw, void *ji_) return false; } - for (int i = 0; i < iso_count; i++) { - cc->mLevels[bw].insert(std::pair(iso[i], lvl)); + for (auto iso : isos) { + cc->mLevels[bw].emplace(iso, lvl); } } return true; } -CameraConst * -CameraConst::parseEntry(void *cJSON_, const char *make_model) +CameraConst* CameraConst::parseEntry(const void *cJSON_, const char *make_model) { - cJSON *js, *ji, *jranges; - js = (cJSON *)cJSON_; + const cJSON *js = static_cast(cJSON_); - CameraConst *cc = new CameraConst; + std::unique_ptr cc(new CameraConst); cc->make_model = make_model; - ji = cJSON_GetObjectItem(js, "dcraw_matrix"); + const cJSON *ji = cJSON_GetObjectItem(js, "dcraw_matrix"); if (ji) { if (ji->type != cJSON_Array) { fprintf(stderr, "\"dcraw_matrix\" must be an array\n"); - goto parse_error; + return nullptr; } int i; - for (i = 0, ji = ji->child; i < 12 && ji != nullptr; i++, ji = ji->next) { + for (i = 0, ji = ji->child; i < 12 && ji; i++, ji = ji->next) { if (ji->type != cJSON_Number) { fprintf(stderr, "\"dcraw_matrix\" array must contain numbers\n"); - goto parse_error; + return nullptr; } - cc->dcraw_matrix[i] = (short)ji->valueint; + cc->dcraw_matrix[i] = ji->valueint; } } @@ -213,23 +217,23 @@ CameraConst::parseEntry(void *cJSON_, const char *make_model) if (ji) { if (ji->type != cJSON_Array) { fprintf(stderr, "\"raw_crop\" must be an array\n"); - goto parse_error; + return nullptr; } int i; - for (i = 0, ji = ji->child; i < 4 && ji != nullptr; i++, ji = ji->next) { + for (i = 0, ji = ji->child; i < 4 && ji; i++, ji = ji->next) { if (ji->type != cJSON_Number) { fprintf(stderr, "\"raw_crop\" array must contain numbers\n"); - goto parse_error; + return nullptr; } cc->raw_crop[i] = ji->valueint; } - if (i != 4 || ji != nullptr) { + if (i != 4 || ji) { fprintf(stderr, "\"raw_crop\" must contain 4 numbers\n"); - goto parse_error; + return nullptr; } } @@ -238,15 +242,15 @@ CameraConst::parseEntry(void *cJSON_, const char *make_model) if (ji) { if (ji->type != cJSON_Array) { fprintf(stderr, "\"masked_areas\" must be an array\n"); - goto parse_error; + return nullptr; } int i; - for (i = 0, ji = ji->child; i < 8 * 4 && ji != nullptr; i++, ji = ji->next) { + for (i = 0, ji = ji->child; i < 2 * 4 && ji; i++, ji = ji->next) { if (ji->type != cJSON_Number) { fprintf(stderr, "\"masked_areas\" array must contain numbers\n"); - goto parse_error; + return nullptr; } cc->raw_mask[i / 4][i % 4] = ji->valueint; @@ -254,27 +258,23 @@ CameraConst::parseEntry(void *cJSON_, const char *make_model) if (i % 4 != 0) { fprintf(stderr, "\"masked_areas\" array length must be divisible by 4\n"); - goto parse_error; + return nullptr; } } - jranges = cJSON_GetObjectItem(js, "ranges"); + const cJSON *jranges = cJSON_GetObjectItem(js, "ranges"); if (jranges) { ji = cJSON_GetObjectItem(jranges, "black"); - if (ji) { - if (!parseLevels(cc, 0, ji)) { - goto parse_error; - } + if (ji && !parseLevels(cc.get(), 0, ji)) { + return nullptr; } ji = cJSON_GetObjectItem(jranges, "white"); - if (ji) { - if (!parseLevels(cc, 1, ji)) { - goto parse_error; - } + if (ji && !parseLevels(cc.get(), 1, ji)) { + return nullptr; } ji = cJSON_GetObjectItem(jranges, "white_max"); @@ -282,32 +282,28 @@ CameraConst::parseEntry(void *cJSON_, const char *make_model) if (ji) { if (ji->type != cJSON_Number) { fprintf(stderr, "\"ranges\":\"white_max\" must be a number\n"); - goto parse_error; + return nullptr; } - cc->white_max = (int)ji->valueint; + cc->white_max = ji->valueint; } ji = cJSON_GetObjectItem(jranges, "aperture_scaling"); - if (ji) { - if (!parseApertureScaling(cc, ji)) { - goto parse_error; - } + if (ji && !parseApertureScaling(cc.get(), ji)) { + return nullptr; } } for (int bw = 0; bw < 2; bw++) { - struct camera_const_levels lvl; + camera_const_levels lvl; if (!cc->get_Levels(lvl, bw, 0, 0)) { - std::map::iterator it; - it = cc->mLevels[bw].begin(); + const auto it = cc->mLevels[bw].cbegin(); - if (it != cc->mLevels[bw].end()) { + if (it != cc->mLevels[bw].cend()) { // insert levels with lowest iso as the default (iso 0) - struct camera_const_levels lvl = it->second; - cc->mLevels[bw].insert(std::pair(0, lvl)); + cc->mLevels[bw].emplace(0, it->second); } } } @@ -317,13 +313,13 @@ CameraConst::parseEntry(void *cJSON_, const char *make_model) if (ji) { if (ji->type != cJSON_Array) { fprintf(stderr, "\"pdaf_pattern\" must be an array\n"); - goto parse_error; + return nullptr; } - for (ji = ji->child; ji != nullptr; ji = ji->next) { + for (ji = ji->child; ji; ji = ji->next) { if (ji->type != cJSON_Number) { fprintf(stderr, "\"pdaf_pattern\" array must contain numbers\n"); - goto parse_error; + return nullptr; } cc->pdafPattern.push_back(ji->valueint); @@ -335,7 +331,7 @@ CameraConst::parseEntry(void *cJSON_, const char *make_model) if (ji) { if (ji->type != cJSON_Number) { fprintf(stderr, "\"pdaf_offset\" must contain a number\n"); - goto parse_error; + return nullptr; } cc->pdafOffset = ji->valueint; @@ -346,27 +342,21 @@ CameraConst::parseEntry(void *cJSON_, const char *make_model) if (ji) { if (ji->type != cJSON_False && ji->type != cJSON_True) { fprintf(stderr, "\"global_green_equilibration\" must be a boolean\n"); - goto parse_error; + return nullptr; } cc->globalGreenEquilibration = (ji->type == cJSON_True); } - return cc; - -parse_error: - delete cc; - return nullptr; + return cc.release(); } -bool -CameraConst::has_dcrawMatrix() +bool CameraConst::has_dcrawMatrix() const { return dcraw_matrix[0] != 0; } -void -CameraConst::update_dcrawMatrix(const short *other) +void CameraConst::update_dcrawMatrix(const short *other) { if (!other) { return; @@ -377,8 +367,7 @@ CameraConst::update_dcrawMatrix(const short *other) } } -const short * -CameraConst::get_dcrawMatrix() +const short* CameraConst::get_dcrawMatrix() const { if (!has_dcrawMatrix()) { return nullptr; @@ -387,44 +376,35 @@ CameraConst::get_dcrawMatrix() return dcraw_matrix; } -bool -CameraConst::has_pdafPattern() -{ - return pdafPattern.size() > 0; -} - -std::vector -CameraConst::get_pdafPattern() +const std::vector& CameraConst::get_pdafPattern() const { return pdafPattern; } -void -CameraConst::update_pdafPattern(const std::vector &other) +void CameraConst::update_pdafPattern(const std::vector &other) { if (other.empty()) { return; } + pdafPattern = other; } -void -CameraConst::update_pdafOffset(int other) +void CameraConst::update_pdafOffset(int other) { if (other == 0) { return; } + pdafOffset = other; } -bool -CameraConst::has_rawCrop() +bool CameraConst::has_rawCrop() const { return raw_crop[0] != 0 || raw_crop[1] != 0 || raw_crop[2] != 0 || raw_crop[3] != 0; } -void -CameraConst::get_rawCrop(int& left_margin, int& top_margin, int& width, int& height) +void CameraConst::get_rawCrop(int& left_margin, int& top_margin, int& width, int& height) const { left_margin = raw_crop[0]; top_margin = raw_crop[1]; @@ -432,22 +412,20 @@ CameraConst::get_rawCrop(int& left_margin, int& top_margin, int& width, int& hei height = raw_crop[3]; } -bool -CameraConst::has_rawMask(int idx) +bool CameraConst::has_rawMask(int idx) const { - if (idx < 0 || idx > 7) { + if (idx < 0 || idx > 1) { return false; } return (raw_mask[idx][0] | raw_mask[idx][1] | raw_mask[idx][2] | raw_mask[idx][3]) != 0; } -void -CameraConst::get_rawMask(int idx, int& top, int& left, int& bottom, int& right) +void CameraConst::get_rawMask(int idx, int& top, int& left, int& bottom, int& right) const { top = left = bottom = right = 0; - if (idx < 0 || idx > 7) { + if (idx < 0 || idx > 1) { return; } @@ -457,38 +435,30 @@ CameraConst::get_rawMask(int idx, int& top, int& left, int& bottom, int& right) right = raw_mask[idx][3]; } -void -CameraConst::update_Levels(const CameraConst *other) +void CameraConst::update_Levels(const CameraConst *other) { if (!other) { return; } - if (other->mLevels[0].size()) { - mLevels[0].clear(); + if (!other->mLevels[0].empty()) { mLevels[0] = other->mLevels[0]; } - if (other->mLevels[1].size()) { - mLevels[1].clear(); + if (!other->mLevels[1].empty()) { mLevels[1] = other->mLevels[1]; } - if (other->mApertureScaling.size()) { - mApertureScaling.clear(); + if (!other->mApertureScaling.empty()) { mApertureScaling = other->mApertureScaling; } if (other->white_max) { white_max = other->white_max; } - -// for (std::map::iterator i=other->mLevels[0].begin(); i!=other->mLevels[0].end(); i++) { -// } } -void -CameraConst::update_Crop(CameraConst *other) +void CameraConst::update_Crop(CameraConst *other) { if (!other) { return; @@ -499,18 +469,16 @@ CameraConst::update_Crop(CameraConst *other) } } -bool -CameraConst::get_Levels(struct camera_const_levels & lvl, int bw, int iso, float fnumber) +bool CameraConst::get_Levels(camera_const_levels & lvl, int bw, int iso, float fnumber) const { - std::map::iterator it; - it = mLevels[bw].find(iso); + std::map::const_iterator it = mLevels[bw].find(iso); if (it == mLevels[bw].end()) { - std::map::iterator best_it = mLevels[bw].begin(); + auto best_it = mLevels[bw].cbegin(); if (iso > 0) { for (it = mLevels[bw].begin(); it != mLevels[bw].end(); ++it) { - if (abs(it->first - iso) <= abs(best_it->first - iso)) { + if (std::abs(it->first - iso) <= std::abs(best_it->first - iso)) { best_it = it; } else { break; @@ -527,35 +495,34 @@ CameraConst::get_Levels(struct camera_const_levels & lvl, int bw, int iso, float lvl = it->second; - if (bw == 1 && fnumber > 0 && mApertureScaling.size() > 0) { - std::map::iterator it; - it = mApertureScaling.find(fnumber); + if (bw == 1 && fnumber > 0 && !mApertureScaling.empty()) { + std::map::const_iterator scaleIt = mApertureScaling.find(fnumber); - if (it == mApertureScaling.end()) { + if (scaleIt == mApertureScaling.end()) { // fnumber may be an exact aperture, eg 1.414, or a rounded eg 1.4. In our map we // should have rounded numbers so we translate and retry the lookup // table with traditional 1/3 stop f-number rounding used by most cameras, we only // have in the range 0.7 - 10.0, but aperture scaling rarely happen past f/4.0 - const float fn_tab[8][3] = { - { 0.7, 0.8, 0.9 }, - { 1.0, 1.1, 1.2 }, - { 1.4, 1.6, 1.8 }, - { 2.0, 2.2, 2.5 }, - { 2.8, 3.2, 3.5 }, - { 4.0, 4.5, 5.0 }, - { 5.6, 6.3, 7.1 }, - { 8.0, 9.0, 10.0 } + constexpr float fn_tab[8][3] = { + { 0.7f, 0.8f, 0.9f }, + { 1.f, 1.1f, 1.2f }, + { 1.4f, 1.6f, 1.8f }, + { 2.f, 2.2f, 2.5f }, + { 2.8f, 3.2f, 3.5f }, + { 4.f, 4.5f, 5.f }, + { 5.6f, 6.3f, 7.1f }, + { 8.f, 9.f, 10.f } }; for (int avh = 0; avh < 8; avh++) { for (int k = 0; k < 3; k++) { - float av = (avh - 1) + (float)k / 3; - float aperture = sqrtf(powf(2, av)); + const float av = (avh - 1) + k / 3.f; + const float aperture = std::sqrt(std::pow(2.f, av)); - if (fnumber > aperture * 0.97 && fnumber < aperture / 0.97) { + if (fnumber > aperture * 0.97f && fnumber < aperture / 0.97f) { fnumber = fn_tab[avh][k]; - it = mApertureScaling.find(fnumber); + scaleIt = mApertureScaling.find(fnumber); avh = 7; break; } @@ -563,23 +530,21 @@ CameraConst::get_Levels(struct camera_const_levels & lvl, int bw, int iso, float } } - float scaling = 1.0; + float scaling = 1.f; - if (it == mApertureScaling.end()) { - std::map::reverse_iterator it; - - for (it = mApertureScaling.rbegin(); it != mApertureScaling.rend(); ++it) { - if (it->first > fnumber) { - scaling = it->second; + if (scaleIt == mApertureScaling.end()) { + for (auto entry = mApertureScaling.crbegin(); entry != mApertureScaling.crend(); ++entry) { + if (entry->first > fnumber) { + scaling = entry->second; } else { break; } } } else { - scaling = it->second; + scaling = scaleIt->second; } - if (scaling > 1.0) { + if (scaling > 1.f) { for (int i = 0; i < 4; i++) { lvl.levels[i] *= scaling; @@ -593,24 +558,22 @@ CameraConst::get_Levels(struct camera_const_levels & lvl, int bw, int iso, float return true; } -int -CameraConst::get_BlackLevel(const int idx, const int iso_speed) +int CameraConst::get_BlackLevel(const int idx, const int iso_speed) const { assert(idx >= 0 && idx <= 3); - struct camera_const_levels lvl; + camera_const_levels lvl; - if (!get_Levels(lvl, 0, iso_speed, 0.0)) { + if (!get_Levels(lvl, 0, iso_speed, 0.f)) { return -1; } return lvl.levels[idx]; } -int -CameraConst::get_WhiteLevel(const int idx, const int iso_speed, const float fnumber) +int CameraConst::get_WhiteLevel(const int idx, const int iso_speed, const float fnumber) const { assert(idx >= 0 && idx <= 3); - struct camera_const_levels lvl; + camera_const_levels lvl; if (!get_Levels(lvl, 1, iso_speed, fnumber)) { return -1; @@ -619,48 +582,44 @@ CameraConst::get_WhiteLevel(const int idx, const int iso_speed, const float fnum return lvl.levels[idx]; } -bool -CameraConst::has_globalGreenEquilibration() +bool CameraConst::has_globalGreenEquilibration() const { return globalGreenEquilibration >= 0; } -bool -CameraConst::get_globalGreenEquilibration() +bool CameraConst::get_globalGreenEquilibration() const { return globalGreenEquilibration > 0; } -void -CameraConst::update_globalGreenEquilibration(bool other) +void CameraConst::update_globalGreenEquilibration(bool other) { globalGreenEquilibration = (other ? 1 : 0); } -bool -CameraConstantsStore::parse_camera_constants_file(Glib::ustring filename_) +bool CameraConstantsStore::parse_camera_constants_file(const Glib::ustring& filename_) { // read the file into a single long string const char *filename = filename_.c_str(); FILE *stream = fopen(filename, "rt"); - if (stream == nullptr) { + if (!stream) { fprintf(stderr, "Could not open camera constants file \"%s\": %s\n", filename, strerror(errno)); return false; } - size_t bufsize = 16384; - size_t increment = 2 * bufsize; + size_t bufsize = 262144; + size_t increment = bufsize; size_t datasize = 0, ret; char *buf = (char *)malloc(bufsize); - while ((ret = fread(&buf[datasize], 1, bufsize - datasize, stream)) != 0) { + while ((ret = fread(&buf[datasize], 1, bufsize - datasize - 1, stream)) != 0) { datasize += ret; - if (datasize == bufsize) { // we need more memory + if (datasize == bufsize - 1) { // we need more memory bufsize += increment; void *temp = realloc(buf, bufsize); // try to realloc buffer with new size - if(!temp) { // realloc failed + if (!temp) { // realloc failed temp = malloc(bufsize); // alloc now buffer if (temp) { // alloc worked memcpy(temp, buf, bufsize - increment); // copy old buffer content to new buffer @@ -683,17 +642,13 @@ CameraConstantsStore::parse_camera_constants_file(Glib::ustring filename_) fclose(stream); - if(datasize == bufsize) { - buf = (char *)realloc(buf, datasize + 1); - } - buf[datasize] = '\0'; // remove comments cJSON_Minify(buf); // parse - cJSON *jsroot = cJSON_Parse(buf); + cJSON* const jsroot = cJSON_Parse(buf); if (!jsroot) { char str[128]; @@ -711,20 +666,16 @@ CameraConstantsStore::parse_camera_constants_file(Glib::ustring filename_) } free(buf); - /*{ - char *js_str = cJSON_Print(jsroot); - printf("%s\n", js_str); - free(js_str); - }*/ - cJSON *js = cJSON_GetObjectItem(jsroot, "camera_constants"); + + const cJSON *js = cJSON_GetObjectItem(jsroot, "camera_constants"); if (!js) { fprintf(stderr, "missing \"camera_constants\" object item\n"); goto parse_error; } - for (js = js->child; js != nullptr; js = js->next) { - cJSON *ji = cJSON_GetObjectItem(js, "make_model"); + for (js = js->child; js; js = js->next) { + const cJSON *ji = cJSON_GetObjectItem(js, "make_model"); if (!ji) { fprintf(stderr, "missing \"make_model\" object item\n"); @@ -738,30 +689,30 @@ CameraConstantsStore::parse_camera_constants_file(Glib::ustring filename_) is_array = true; } - while (ji != nullptr) { + while (ji) { if (ji->type != cJSON_String) { fprintf(stderr, "\"make_model\" must be a string or an array of strings\n"); goto parse_error; } - CameraConst *cc = CameraConst::parseEntry((void *)js, ji->valuestring); + CameraConst* const cc = CameraConst::parseEntry((const void *)js, ji->valuestring); if (!cc) { goto parse_error; } - Glib::ustring make_model(ji->valuestring); - make_model = make_model.uppercase(); + std::string make_model(ji->valuestring); + std::transform(make_model.begin(), make_model.end(), make_model.begin(), ::toupper); - const auto ret = mCameraConstants.emplace(make_model, cc); + const auto entry = mCameraConstants.emplace(make_model, cc); - if(ret.second) { // entry inserted into map + if (entry.second) { // entry inserted into map if (settings->verbose) { printf("Add camera constants for \"%s\"\n", make_model.c_str()); } } else { // The CameraConst already exist for this camera make/model -> we merge the values - CameraConst *existingcc = ret.first->second; + CameraConst* const existingcc = entry.first->second; // updating the dcraw matrix existingcc->update_dcrawMatrix(cc->get_dcrawMatrix()); @@ -809,33 +760,30 @@ CameraConstantsStore::~CameraConstantsStore() } } -void CameraConstantsStore::init(Glib::ustring baseDir, Glib::ustring userSettingsDir) +void CameraConstantsStore::init(const Glib::ustring& baseDir, const Glib::ustring& userSettingsDir) { parse_camera_constants_file(Glib::build_filename(baseDir, "camconst.json")); - Glib::ustring userFile(Glib::build_filename(userSettingsDir, "camconst.json")); + const Glib::ustring userFile(Glib::build_filename(userSettingsDir, "camconst.json")); if (Glib::file_test(userFile, Glib::FILE_TEST_EXISTS)) { parse_camera_constants_file(userFile); } } -CameraConstantsStore * -CameraConstantsStore::getInstance() +CameraConstantsStore* CameraConstantsStore::getInstance() { static CameraConstantsStore instance_; return &instance_; } -CameraConst * -CameraConstantsStore::get(const char make[], const char model[]) +const CameraConst* CameraConstantsStore::get(const char make[], const char model[]) const { - Glib::ustring key(make); + std::string key(make); key += " "; key += model; - key = key.uppercase(); - std::map::iterator it; - it = mCameraConstants.find(key); + std::transform(key.begin(), key.end(), key.begin(), ::toupper); + const auto it = mCameraConstants.find(key); if (it == mCameraConstants.end()) { return nullptr; diff --git a/rtengine/camconst.h b/rtengine/camconst.h index 1096e1767..aa0702439 100644 --- a/rtengine/camconst.h +++ b/rtengine/camconst.h @@ -3,10 +3,17 @@ */ #pragma once -#include #include +#include #include +namespace Glib +{ + +class ustring; + +} + namespace rtengine { @@ -14,41 +21,40 @@ struct camera_const_levels { int levels[4]; }; -class CameraConst +class CameraConst final { private: std::string make_model; short dcraw_matrix[12]; int raw_crop[4]; - int raw_mask[8][4]; + int raw_mask[2][4]; int white_max; - std::map mLevels[2]; + std::map mLevels[2]; std::map mApertureScaling; std::vector pdafPattern; int pdafOffset; int globalGreenEquilibration; CameraConst(); - static bool parseLevels(CameraConst *cc, int bw, void *ji); - static bool parseApertureScaling(CameraConst *cc, void *ji); - bool get_Levels(struct camera_const_levels & lvl, int bw, int iso, float fnumber); + static bool parseLevels(CameraConst *cc, int bw, const void *ji); + static bool parseApertureScaling(CameraConst *cc, const void *ji); + bool get_Levels(camera_const_levels & lvl, int bw, int iso, float fnumber) const; public: - static CameraConst *parseEntry(void *cJSON, const char *make_model); - bool has_dcrawMatrix(void); - bool has_pdafPattern(void); + static CameraConst *parseEntry(const void *cJSON, const char *make_model); + bool has_dcrawMatrix(void) const; void update_dcrawMatrix(const short *other); - const short *get_dcrawMatrix(void); - std::vector get_pdafPattern(); - int get_pdafOffset() {return pdafOffset;} - bool has_rawCrop(void); - void get_rawCrop(int& left_margin, int& top_margin, int& width, int& height); - bool has_rawMask(int idx); - void get_rawMask(int idx, int& top, int& left, int& bottom, int& right); - int get_BlackLevel(int idx, int iso_speed); - int get_WhiteLevel(int idx, int iso_speed, float fnumber); - bool has_globalGreenEquilibration(); - bool get_globalGreenEquilibration(); + const short *get_dcrawMatrix(void) const; + const std::vector& get_pdafPattern() const; + int get_pdafOffset() const {return pdafOffset;}; + bool has_rawCrop(void) const; + void get_rawCrop(int& left_margin, int& top_margin, int& width, int& height) const; + bool has_rawMask(int idx) const; + void get_rawMask(int idx, int& top, int& left, int& bottom, int& right) const; + int get_BlackLevel(int idx, int iso_speed) const; + int get_WhiteLevel(int idx, int iso_speed, float fnumber) const; + bool has_globalGreenEquilibration() const; + bool get_globalGreenEquilibration() const; void update_Levels(const CameraConst *other); void update_Crop(CameraConst *other); void update_pdafPattern(const std::vector &other); @@ -56,19 +62,19 @@ public: void update_globalGreenEquilibration(bool other); }; -class CameraConstantsStore +class CameraConstantsStore final { private: std::map mCameraConstants; CameraConstantsStore(); - bool parse_camera_constants_file(Glib::ustring filename); + bool parse_camera_constants_file(const Glib::ustring& filename); public: ~CameraConstantsStore(); - void init(Glib::ustring baseDir, Glib::ustring userSettingsDir); + void init(const Glib::ustring& baseDir, const Glib::ustring& userSettingsDir); static CameraConstantsStore *getInstance(void); - CameraConst *get(const char make[], const char model[]); + const CameraConst *get(const char make[], const char model[]) const; }; } diff --git a/rtengine/camconst.json b/rtengine/camconst.json index ab42f3d19..5fc7d4062 100644 --- a/rtengine/camconst.json +++ b/rtengine/camconst.json @@ -1221,7 +1221,7 @@ Camera constants: { // Quality A, changes for raw crop which is wrong (larger) in dcraw "make_model": "Canon PowerShot S120", - "dcraw_matrix": [ 6961,-1685,-695,-4625,12945,1836,-1114,2152,5518 ], + "dcraw_matrix": [ 6961, -1685, -695, -4625, 12945, 1836, -1114, 2152, 5518 ], // ColorMatrix2 using illuminant D65 from Adobe DNG Converter 12.2 "raw_crop": [ 120, 30, 4024, 3030 ], "masked_areas": [ 32, 2, 3028, 80 ], "ranges": { "white": 4050 } @@ -1240,6 +1240,12 @@ Camera constants: "ranges": { "white": 4050 } // nominal 4080-4093 }, + { // Quality C, only raw crop + "make_model": "Canon PowerShot SX70 HS", + "dcraw_matrix" : [18285, -8907, -1951, -1845, 10688, 1323, 364, 1101, 5139], // taken from ART + "raw_crop": [ 96, 17, 5248, 3932 ] + }, + { // Quality C "make_model": "Canon PowerShot SX150 IS", "dcraw_matrix": [ 13481, -4867, -1063, -2074, 9960, 2472, -170, 1474, 3894 ], // Adobe DNG Converter 11.1 ColorMatrix1 (there is only one matrix and illuminant, and it's for daylight) @@ -1265,6 +1271,7 @@ Camera constants: { // Quality C "make_model": "FUJIFILM GFX 100", + "dcraw_matrix" : [16212, -8423, -1583, -4336, 12583, 1937, -195, 726, 6199], // taken from ART "raw_crop": [ 0, 2, 11664, 8734 ] }, @@ -1288,6 +1295,12 @@ Camera constants: "ranges": { "white": 16100 } }, + { // Quality C + "make_model": [ "FUJIFILM X100V", "FUJIFILM X-T4" ], + "dcraw_matrix": [ 13426,-6334,-1177,-4244,12136,2371,-580,1303,5980 ], // DNG_v12.2 D65 + "raw_crop": [ 0, 5, 6252, 4140 ] + }, + { // Quality C "make_model": "Fujifilm X10", "ranges": { "white": 3788 } @@ -1345,6 +1358,7 @@ Camera constants: { // Quality C "make_model": [ "FUJIFILM X-T100" ], + "dcraw_matrix" : [11673, -4760, -1041, -3988, 12058, 2166, -771, 1417, 5568], // taken from ART "ranges": { "white": 16100 } }, @@ -1370,7 +1384,8 @@ Camera constants: }, { // Quality C, only raw crop - "make_model": [ "FUJIFILM X-T3", "FUJIFILM X-T30" ], + "make_model": [ "FUJIFILM X-T3", "FUJIFILM X-T30", "FUJIFILM X-PRO3" ], + "dcraw_matrix": [ 13426,-6334,-1177,-4244,12136,2371,-580,1303,5980 ], // DNG_v11, standard_v2 d65 "raw_crop": [ 0, 5, 6252, 4176] }, @@ -1386,6 +1401,11 @@ Camera constants: "ranges": { "white": 4040 } }, + { // Quality B, Matrix from ART + "make_model" : "LEICA D-LUX 7", + "dcraw_matrix" : [11577, -4230, -1106, -3967, 12211, 1957, -758, 1762, 5610] + }, + { // Quality B, Matrix from Adobe's dcp D65 instead of the internal in Leica's DNG "make_model": "LEICA Q (Typ 116)", "dcraw_matrix": [ 10068,-4043,-1068,-5319,14268,1044,-765,1701,6522 ], // DCP D65 @@ -1408,6 +1428,11 @@ Camera constants: "raw_crop": [ 0, 0, 0, -18 ] // 18 rows at bottom are garbage }, + { // Quality B, Matrix from ART + "make_model" : "LEICA V-LUX 5", + "dcraw_matrix" : [9803, -4185, -992, -4066, 12578, 1628, -838, 1824, 5288] + }, + { // Quality C "make_model": "LG mobile LG-H815", "dcraw_matrix": [ 5859,547,-1250,-6484,15547,547,-2422,5625,3906 ], // DNG D65 @@ -1515,7 +1540,7 @@ Camera constants: { // Quality B "make_model": "NIKON COOLPIX P1000", "dcraw_matrix": [ 14294, -6116, -1333, -1628, 10219, 1637, -14, 1158, 5022 ], // ColorMatrix2 from Adobe DNG Converter 11.4 - "ranges": { "black": 200, "white": 4093 } + "ranges": { "black": 200, "white": 4087 } }, { // Quality B, no LENR samples @@ -1768,6 +1793,7 @@ Camera constants: { // Quality C, only raw crop "make_model": "OLYMPUS TG-6", + "dcraw_matrix" : [10899, -3832, -1082, -2112, 10736, 1575, -267, 1452, 5269], // taken from ART "raw_crop": [ 0, 0, -24, 0 ] // 24 pixels at right are garbage }, diff --git a/rtengine/canon_cr3_decoder.cc b/rtengine/canon_cr3_decoder.cc index 6274154cb..d9a10900c 100644 --- a/rtengine/canon_cr3_decoder.cc +++ b/rtengine/canon_cr3_decoder.cc @@ -18,6 +18,7 @@ */ // Code adapted from ART +// https://bitbucket.org/agriggio/art/ /* * * This file is part of ART. @@ -37,11 +38,16 @@ */ // Code adapted from libraw -/* -*- C++ -*- - * Copyright 2019 LibRaw LLC (info@libraw.org) +// https://github.com/LibRaw/LibRaw/ +/* + * File: libraw_crxdec.cpp + * Copyright (C) 2018-2019 Alexey Danilchenko + * Copyright (C) 2019 Alex Tutubalin, LibRaw LLC * - LibRaw is free software; you can redistribute it and/or modify - it under the terms of the one of two licenses as you choose: + Canon CR3 file decoder + +LibRaw is free software; you can redistribute it and/or modify +it under the terms of the one of two licenses as you choose: 1. GNU LESSER GENERAL PUBLIC LICENSE version 2.1 (See file LICENSE.LGPL provided in LibRaw distribution archive for details). @@ -49,7 +55,7 @@ 2. COMMON DEVELOPMENT AND DISTRIBUTION LICENSE (CDDL) Version 1.0 (See file LICENSE.CDDL provided in LibRaw distribution archive for details). -*/ + */ #include #include diff --git a/rtengine/capturesharpening.cc b/rtengine/capturesharpening.cc index 072935dc2..4dcdd0734 100644 --- a/rtengine/capturesharpening.cc +++ b/rtengine/capturesharpening.cc @@ -33,6 +33,50 @@ namespace { +void compute13x13kernel(float sigma, float kernel[13][13]) { + + const double temp = -2.f * rtengine::SQR(sigma); + float sum = 0.f; + for (int i = -6; i <= 6; ++i) { + for (int j = -6; j <= 6; ++j) { + if((rtengine::SQR(i) + rtengine::SQR(j)) <= rtengine::SQR(3.0 * 2.0)) { + kernel[i + 6][j + 6] = std::exp((rtengine::SQR(i) + rtengine::SQR(j)) / temp); + sum += kernel[i + 6][j + 6]; + } else { + kernel[i + 6][j + 6] = 0.f; + } + } + } + + for (int i = 0; i < 13; ++i) { + for (int j = 0; j < 13; ++j) { + kernel[i][j] /= sum; + } + } +} + +void compute9x9kernel(float sigma, float kernel[9][9]) { + + const double temp = -2.f * rtengine::SQR(sigma); + float sum = 0.f; + for (int i = -4; i <= 4; ++i) { + for (int j = -4; j <= 4; ++j) { + if((rtengine::SQR(i) + rtengine::SQR(j)) <= rtengine::SQR(3.0 * 1.5)) { + kernel[i + 4][j + 4] = std::exp((rtengine::SQR(i) + rtengine::SQR(j)) / temp); + sum += kernel[i + 4][j + 4]; + } else { + kernel[i + 4][j + 4] = 0.f; + } + } + } + + for (int i = 0; i < 9; ++i) { + for (int j = 0; j < 9; ++j) { + kernel[i][j] /= sum; + } + } +} + void compute7x7kernel(float sigma, float kernel[7][7]) { const double temp = -2.f * rtengine::SQR(sigma); @@ -183,6 +227,105 @@ void gauss7x7div(float** RESTRICT src, float** RESTRICT dst, float** RESTRICT di } } +void gauss9x9div(float** RESTRICT src, float** RESTRICT dst, float** RESTRICT divBuffer, const int tileSize, const float kernel[9][9]) +{ + + const float c42 = kernel[0][2]; + const float c41 = kernel[0][3]; + const float c40 = kernel[0][4]; + const float c33 = kernel[1][1]; + const float c32 = kernel[1][2]; + const float c31 = kernel[1][3]; + const float c30 = kernel[1][4]; + const float c22 = kernel[2][2]; + const float c21 = kernel[2][3]; + const float c20 = kernel[2][4]; + const float c11 = kernel[3][3]; + const float c10 = kernel[3][4]; + const float c00 = kernel[4][4]; + + for (int i = 4; i < tileSize - 4; ++i) { + // I tried hand written SSE code but gcc vectorizes better +#if defined(__clang__) + #pragma clang loop vectorize(assume_safety) +#elif defined(__GNUC__) + #pragma GCC ivdep +#endif + for (int j = 4; j < tileSize - 4; ++j) { + const float val = c42 * ((src[i - 4][j - 2] + src[i - 4][j + 2]) + (src[i - 2][j - 4] + src[i - 2][j + 4]) + (src[i + 2][j - 4] + src[i + 2][j + 4]) + (src[i + 4][j - 2] + src[i + 4][j + 2])) + + c41 * ((src[i - 4][j - 1] + src[i - 4][j + 1]) + (src[i - 1][j - 4] + src[i - 1][j + 4]) + (src[i + 1][j - 4] + src[i + 1][j + 4]) + (src[i + 4][j - 1] + src[i + 4][j + 1])) + + c40 * (src[i - 4][j] + src[i][j - 4] + src[i][j + 4] + src[i + 4][j]) + + c33 * (src[i - 3][j - 3] + src[i - 3][j + 3] + src[i + 3][j - 3] + src[i + 3][j + 3]) + + c32 * ((src[i - 3][j - 2] + src[i - 3][j + 2]) + (src[i - 2][j - 3] + src[i - 2][j + 3]) + (src[i + 2][j - 3] + src[i + 2][j + 3]) + (src[i + 3][j - 2] + src[i + 3][j + 2])) + + c31 * ((src[i - 3][j - 1] + src[i - 3][j + 1]) + (src[i - 1][j - 3] + src[i - 1][j + 3]) + (src[i + 1][j - 3] + src[i + 1][j + 3]) + (src[i + 3][j - 1] + src[i + 3][j + 1])) + + c30 * (src[i - 3][j] + src[i][j - 3] + src[i][j + 3] + src[i + 3][j]) + + c22 * (src[i - 2][j - 2] + src[i - 2][j + 2] + src[i + 2][j - 2] + src[i + 2][j + 2]) + + c21 * ((src[i - 2][j - 1] + src[i - 2][j + 1]) + (src[i - 1][j - 2] + src[i - 1][j + 2]) + (src[i + 1][j - 2] + src[i + 1][j + 2]) + (src[i + 2][j - 1] + src[i + 2][j + 1])) + + c20 * (src[i - 2][j] + src[i][j - 2] + src[i][j + 2] + src[i + 2][j]) + + c11 * (src[i - 1][j - 1] + src[i - 1][j + 1] + src[i + 1][j - 1] + src[i + 1][j + 1]) + + c10 * (src[i - 1][j] + src[i][j - 1] + src[i][j + 1] + src[i + 1][j]) + + c00 * src[i][j]; + + dst[i][j] = divBuffer[i][j] / std::max(val, 0.00001f); + } + } +} + +void gauss13x13div(float** RESTRICT src, float** RESTRICT dst, float** RESTRICT divBuffer, const int tileSize, const float kernel[13][13]) +{ + const float c60 = kernel[0][6]; + const float c53 = kernel[1][3]; + const float c52 = kernel[1][4]; + const float c51 = kernel[1][5]; + const float c50 = kernel[1][6]; + const float c44 = kernel[2][2]; + const float c42 = kernel[2][4]; + const float c41 = kernel[2][5]; + const float c40 = kernel[2][6]; + const float c33 = kernel[3][3]; + const float c32 = kernel[3][4]; + const float c31 = kernel[3][5]; + const float c30 = kernel[3][6]; + const float c22 = kernel[4][4]; + const float c21 = kernel[4][5]; + const float c20 = kernel[4][6]; + const float c11 = kernel[5][5]; + const float c10 = kernel[5][6]; + const float c00 = kernel[6][6]; + + for (int i = 6; i < tileSize - 6; ++i) { + // I tried hand written SSE code but gcc vectorizes better +#if defined(__clang__) + #pragma clang loop vectorize(assume_safety) +#elif defined(__GNUC__) + #pragma GCC ivdep +#endif + for (int j = 6; j < tileSize - 6; ++j) { + const float val = c60 * (src[i - 6][j] + src[i][j - 6] + src[i][j + 6] + src[i + 6][j]) + + c53 * ((src[i - 5][j - 3] + src[i - 5][j + 3]) + (src[i - 3][j - 5] + src[i - 3][j + 5]) + (src[i + 3][j - 5] + src[i + 3][j + 5]) + (src[i + 5][j - 3] + src[i + 5][j + 3])) + + c52 * ((src[i - 5][j - 2] + src[i - 5][j + 2]) + (src[i - 2][j - 5] + src[i - 2][j + 5]) + (src[i + 2][j - 5] + src[i + 2][j + 5]) + (src[i + 5][j - 2] + src[i + 5][j + 2])) + + c51 * ((src[i - 5][j - 1] + src[i - 5][j + 1]) + (src[i - 1][j - 5] + src[i - 1][j + 5]) + (src[i + 1][j - 5] + src[i + 1][j + 5]) + (src[i + 5][j - 1] + src[i + 5][j + 1])) + + c50 * ((src[i - 5][j] + src[i][j - 5] + src[i][j + 5] + src[i + 5][j]) + ((src[i - 4][j - 3] + src[i - 4][j + 3]) + (src[i - 3][j - 4] + src[i - 3][j + 4]) + (src[i + 3][j - 4] + src[i + 3][j + 4]) + (src[i + 4][j - 3] + src[i + 4][j + 3]))) + + c44 * (src[i - 4][j - 4] + src[i - 4][j + 4] + src[i + 4][j - 4] + src[i + 4][j + 4]) + + c42 * ((src[i - 4][j - 2] + src[i - 4][j + 2]) + (src[i - 2][j - 4] + src[i - 2][j + 4]) + (src[i + 2][j - 4] + src[i + 2][j + 4]) + (src[i + 4][j - 2] + src[i + 4][j + 2])) + + c41 * ((src[i - 4][j - 1] + src[i - 4][j + 1]) + (src[i - 1][j - 4] + src[i - 1][j + 4]) + (src[i + 1][j - 4] + src[i + 1][j + 4]) + (src[i + 4][j - 1] + src[i + 4][j + 1])) + + c40 * (src[i - 4][j] + src[i][j - 4] + src[i][j + 4] + src[i + 4][j]) + + c33 * (src[i - 3][j - 3] + src[i - 3][j + 3] + src[i + 3][j - 3] + src[i + 3][j + 3]) + + c32 * ((src[i - 3][j - 2] + src[i - 3][j + 2]) + (src[i - 2][j - 3] + src[i - 2][j + 3]) + (src[i + 2][j - 3] + src[i + 2][j + 3]) + (src[i + 3][j - 2] + src[i + 3][j + 2])) + + c31 * ((src[i - 3][j - 1] + src[i - 3][j + 1]) + (src[i - 1][j - 3] + src[i - 1][j + 3]) + (src[i + 1][j - 3] + src[i + 1][j + 3]) + (src[i + 3][j - 1] + src[i + 3][j + 1])) + + c30 * (src[i - 3][j] + src[i][j - 3] + src[i][j + 3] + src[i + 3][j]) + + c22 * (src[i - 2][j - 2] + src[i - 2][j + 2] + src[i + 2][j - 2] + src[i + 2][j + 2]) + + c21 * ((src[i - 2][j - 1] + src[i - 2][j + 1]) + (src[i - 1][j - 2] + src[i - 1][j + 2]) + (src[i + 1][j - 2] + src[i + 1][j + 2]) + (src[i + 2][j - 1] + src[i + 2][j + 1])) + + c20 * (src[i - 2][j] + src[i][j - 2] + src[i][j + 2] + src[i + 2][j]) + + c11 * (src[i - 1][j - 1] + src[i - 1][j + 1] + src[i + 1][j - 1] + src[i + 1][j + 1]) + + c10 * (src[i - 1][j] + src[i][j - 1] + src[i][j + 1] + src[i + 1][j]) + + c00 * src[i][j]; + + dst[i][j] = divBuffer[i][j] / std::max(val, 0.00001f); + } + } +} + void gauss3x3mult(float** RESTRICT src, float** RESTRICT dst, const int tileSize, const float kernel[3][3]) { const float c11 = kernel[0][0]; @@ -267,6 +410,105 @@ void gauss7x7mult(float** RESTRICT src, float** RESTRICT dst, const int tileSize } } +void gauss9x9mult(float** RESTRICT src, float** RESTRICT dst, const int tileSize, const float kernel[9][9]) +{ + + const float c42 = kernel[0][2]; + const float c41 = kernel[0][3]; + const float c40 = kernel[0][4]; + const float c33 = kernel[1][1]; + const float c32 = kernel[1][2]; + const float c31 = kernel[1][3]; + const float c30 = kernel[1][4]; + const float c22 = kernel[2][2]; + const float c21 = kernel[2][3]; + const float c20 = kernel[2][4]; + const float c11 = kernel[3][3]; + const float c10 = kernel[3][4]; + const float c00 = kernel[4][4]; + + for (int i = 4; i < tileSize - 4; ++i) { + // I tried hand written SSE code but gcc vectorizes better +#if defined(__clang__) + #pragma clang loop vectorize(assume_safety) +#elif defined(__GNUC__) + #pragma GCC ivdep +#endif + for (int j = 4; j < tileSize - 4; ++j) { + const float val = c42 * ((src[i - 4][j - 2] + src[i - 4][j + 2]) + (src[i - 2][j - 4] + src[i - 2][j + 4]) + (src[i + 2][j - 4] + src[i + 2][j + 4]) + (src[i + 4][j - 2] + src[i + 4][j + 2])) + + c41 * ((src[i - 4][j - 1] + src[i - 4][j + 1]) + (src[i - 1][j - 4] + src[i - 1][j + 4]) + (src[i + 1][j - 4] + src[i + 1][j + 4]) + (src[i + 4][j - 1] + src[i + 4][j + 1])) + + c40 * (src[i - 4][j] + src[i][j - 4] + src[i][j + 4] + src[i + 4][j]) + + c33 * (src[i - 3][j - 3] + src[i - 3][j + 3] + src[i + 3][j - 3] + src[i + 3][j + 3]) + + c32 * ((src[i - 3][j - 2] + src[i - 3][j + 2]) + (src[i - 2][j - 3] + src[i - 2][j + 3]) + (src[i + 2][j - 3] + src[i + 2][j + 3]) + (src[i + 3][j - 2] + src[i + 3][j + 2])) + + c31 * ((src[i - 3][j - 1] + src[i - 3][j + 1]) + (src[i - 1][j - 3] + src[i - 1][j + 3]) + (src[i + 1][j - 3] + src[i + 1][j + 3]) + (src[i + 3][j - 1] + src[i + 3][j + 1])) + + c30 * (src[i - 3][j] + src[i][j - 3] + src[i][j + 3] + src[i + 3][j]) + + c22 * (src[i - 2][j - 2] + src[i - 2][j + 2] + src[i + 2][j - 2] + src[i + 2][j + 2]) + + c21 * ((src[i - 2][j - 1] + src[i - 2][j + 1]) + (src[i - 1][j - 2] + src[i - 1][j + 2]) + (src[i + 1][j - 2] + src[i + 1][j + 2]) + (src[i + 2][j - 1] + src[i + 2][j + 1])) + + c20 * (src[i - 2][j] + src[i][j - 2] + src[i][j + 2] + src[i + 2][j]) + + c11 * (src[i - 1][j - 1] + src[i - 1][j + 1] + src[i + 1][j - 1] + src[i + 1][j + 1]) + + c10 * (src[i - 1][j] + src[i][j - 1] + src[i][j + 1] + src[i + 1][j]) + + c00 * src[i][j]; + dst[i][j] *= val; + } + } +} + +void gauss13x13mult(float** RESTRICT src, float** RESTRICT dst, const int tileSize, const float kernel[13][13]) +{ + + const float c60 = kernel[0][6]; + const float c53 = kernel[1][3]; + const float c52 = kernel[1][4]; + const float c51 = kernel[1][5]; + const float c50 = kernel[1][6]; + const float c44 = kernel[2][2]; + const float c42 = kernel[2][4]; + const float c41 = kernel[2][5]; + const float c40 = kernel[2][6]; + const float c33 = kernel[3][3]; + const float c32 = kernel[3][4]; + const float c31 = kernel[3][5]; + const float c30 = kernel[3][6]; + const float c22 = kernel[4][4]; + const float c21 = kernel[4][5]; + const float c20 = kernel[4][6]; + const float c11 = kernel[5][5]; + const float c10 = kernel[5][6]; + const float c00 = kernel[6][6]; + + for (int i = 6; i < tileSize - 6; ++i) { + // I tried hand written SSE code but gcc vectorizes better +#if defined(__clang__) + #pragma clang loop vectorize(assume_safety) +#elif defined(__GNUC__) + #pragma GCC ivdep +#endif + for (int j = 6; j < tileSize - 6; ++j) { + const float val = c60 * (src[i - 6][j] + src[i][j - 6] + src[i][j + 6] + src[i + 6][j]) + + c53 * ((src[i - 5][j - 3] + src[i - 5][j + 3]) + (src[i - 3][j - 5] + src[i - 3][j + 5]) + (src[i + 3][j - 5] + src[i + 3][j + 5]) + (src[i + 5][j - 3] + src[i + 5][j + 3])) + + c52 * ((src[i - 5][j - 2] + src[i - 5][j + 2]) + (src[i - 2][j - 5] + src[i - 2][j + 5]) + (src[i + 2][j - 5] + src[i + 2][j + 5]) + (src[i + 5][j - 2] + src[i + 5][j + 2])) + + c51 * ((src[i - 5][j - 1] + src[i - 5][j + 1]) + (src[i - 1][j - 5] + src[i - 1][j + 5]) + (src[i + 1][j - 5] + src[i + 1][j + 5]) + (src[i + 5][j - 1] + src[i + 5][j + 1])) + + c50 * ((src[i - 5][j] + src[i][j - 5] + src[i][j + 5] + src[i + 5][j]) + ((src[i - 4][j - 3] + src[i - 4][j + 3]) + (src[i - 3][j - 4] + src[i - 3][j + 4]) + (src[i + 3][j - 4] + src[i + 3][j + 4]) + (src[i + 4][j - 3] + src[i + 4][j + 3]))) + + c44 * (src[i - 4][j - 4] + src[i - 4][j + 4] + src[i + 4][j - 4] + src[i + 4][j + 4]) + + c42 * ((src[i - 4][j - 2] + src[i - 4][j + 2]) + (src[i - 2][j - 4] + src[i - 2][j + 4]) + (src[i + 2][j - 4] + src[i + 2][j + 4]) + (src[i + 4][j - 2] + src[i + 4][j + 2])) + + c41 * ((src[i - 4][j - 1] + src[i - 4][j + 1]) + (src[i - 1][j - 4] + src[i - 1][j + 4]) + (src[i + 1][j - 4] + src[i + 1][j + 4]) + (src[i + 4][j - 1] + src[i + 4][j + 1])) + + c40 * (src[i - 4][j] + src[i][j - 4] + src[i][j + 4] + src[i + 4][j]) + + c33 * (src[i - 3][j - 3] + src[i - 3][j + 3] + src[i + 3][j - 3] + src[i + 3][j + 3]) + + c32 * ((src[i - 3][j - 2] + src[i - 3][j + 2]) + (src[i - 2][j - 3] + src[i - 2][j + 3]) + (src[i + 2][j - 3] + src[i + 2][j + 3]) + (src[i + 3][j - 2] + src[i + 3][j + 2])) + + c31 * ((src[i - 3][j - 1] + src[i - 3][j + 1]) + (src[i - 1][j - 3] + src[i - 1][j + 3]) + (src[i + 1][j - 3] + src[i + 1][j + 3]) + (src[i + 3][j - 1] + src[i + 3][j + 1])) + + c30 * (src[i - 3][j] + src[i][j - 3] + src[i][j + 3] + src[i + 3][j]) + + c22 * (src[i - 2][j - 2] + src[i - 2][j + 2] + src[i + 2][j - 2] + src[i + 2][j + 2]) + + c21 * ((src[i - 2][j - 1] + src[i - 2][j + 1]) + (src[i - 1][j - 2] + src[i - 1][j + 2]) + (src[i + 1][j - 2] + src[i + 1][j + 2]) + (src[i + 2][j - 1] + src[i + 2][j + 1])) + + c20 * (src[i - 2][j] + src[i][j - 2] + src[i][j + 2] + src[i + 2][j]) + + c11 * (src[i - 1][j - 1] + src[i - 1][j + 1] + src[i + 1][j - 1] + src[i + 1][j + 1]) + + c10 * (src[i - 1][j] + src[i][j - 1] + src[i][j + 1] + src[i + 1][j]) + + c00 * src[i][j]; + + dst[i][j] *= val; + } + } +} + void buildClipMaskBayer(const float * const *rawData, int W, int H, float** clipMask, const float whites[2][2]) { @@ -519,11 +761,15 @@ bool checkForStop(float** tmpIThr, float** iterCheck, int fullTileSize, int bord return false; } -void CaptureDeconvSharpening (float** luminance, const float* const * oldLuminance, const float * const * blend, int W, int H, double sigma, double sigmaCornerOffset, int iterations, bool checkIterStop, rtengine::ProgressListener* plistener, double startVal, double endVal) +void CaptureDeconvSharpening (float** luminance, const float* const * oldLuminance, const float * const * blend, int W, int H, float sigma, float sigmaCornerOffset, int iterations, bool checkIterStop, rtengine::ProgressListener* plistener, double startVal, double endVal) { BENCHFUN - const bool is5x5 = (sigma <= 0.84 && sigmaCornerOffset == 0.0); - const bool is3x3 = (sigma < 0.6 && sigmaCornerOffset == 0.0); + const bool is9x9 = (sigma <= 1.5f && sigmaCornerOffset == 0.f); + const bool is7x7 = (sigma <= 1.15f && sigmaCornerOffset == 0.f); + const bool is5x5 = (sigma <= 0.84f && sigmaCornerOffset == 0.f); + const bool is3x3 = (sigma < 0.6f && sigmaCornerOffset == 0.f); + float kernel13[13][13]; + float kernel9[9][9]; float kernel7[7][7]; float kernel5[5][5]; float kernel3[3][3]; @@ -531,14 +777,18 @@ BENCHFUN compute3x3kernel(sigma, kernel3); } else if (is5x5) { compute5x5kernel(sigma, kernel5); - } else { + } else if (is7x7) { compute7x7kernel(sigma, kernel7); + } else if (is9x9) { + compute9x9kernel(sigma, kernel9); + } else { + compute13x13kernel(sigma, kernel13); } constexpr int tileSize = 32; - const int border = iterations <= 30 ? 5 : 7; + const int border = (is3x3 || is5x5 || is7x7) ? iterations <= 30 ? 5 : 7 : 8; const int fullTileSize = tileSize + 2 * border; - const float cornerRadius = std::min(1.15f, sigma + sigmaCornerOffset); + const float cornerRadius = std::min(2.f, sigma + sigmaCornerOffset); const float cornerDistance = sqrt(rtengine::SQR(W * 0.5f) + rtengine::SQR(H * 0.5f)); const float distanceFactor = (cornerRadius - sigma) / cornerDistance; @@ -637,12 +887,52 @@ BENCHFUN break; } } + } else if (is7x7) { + for (int k = 0; k < iterations; ++k) { + // apply 5x5 gaussian blur and divide luminance by result of gaussian blur + gauss7x7div(tmpIThr, tmpThr, lumThr, fullTileSize, kernel7); + gauss7x7mult(tmpThr, tmpIThr, fullTileSize, kernel7); + if (checkIterStop && k < iterations - 1 && checkForStop(tmpIThr, iterCheck, fullTileSize, border)) { + break; + } + } + } else if (is9x9) { + for (int k = 0; k < iterations; ++k) { + // apply 5x5 gaussian blur and divide luminance by result of gaussian blur + gauss9x9div(tmpIThr, tmpThr, lumThr, fullTileSize, kernel9); + gauss9x9mult(tmpThr, tmpIThr, fullTileSize, kernel9); + if (checkIterStop && k < iterations - 1 && checkForStop(tmpIThr, iterCheck, fullTileSize, border)) { + break; + } + } } else { - if (sigmaCornerOffset != 0.0) { + if (sigmaCornerOffset != 0.f) { const float distance = sqrt(rtengine::SQR(i + tileSize / 2 - H / 2) + rtengine::SQR(j + tileSize / 2 - W / 2)); const float sigmaTile = static_cast(sigma) + distanceFactor * distance; if (sigmaTile >= 0.4f) { - if (sigmaTile > 0.84) { // have to use 7x7 kernel + if (sigmaTile > 1.5f) { // have to use 13x13 kernel + float lkernel13[13][13]; + compute13x13kernel(static_cast(sigma) + distanceFactor * distance, lkernel13); + for (int k = 0; k < iterations; ++k) { + // apply 13x13 gaussian blur and divide luminance by result of gaussian blur + gauss13x13div(tmpIThr, tmpThr, lumThr, fullTileSize, lkernel13); + gauss13x13mult(tmpThr, tmpIThr, fullTileSize, lkernel13); + if (checkIterStop && k < iterations - 1 && checkForStop(tmpIThr, iterCheck, fullTileSize, border)) { + break; + } + } + } else if (sigmaTile > 1.15f) { // have to use 9x9 kernel + float lkernel9[9][9]; + compute9x9kernel(static_cast(sigma) + distanceFactor * distance, lkernel9); + for (int k = 0; k < iterations; ++k) { + // apply 9x9 gaussian blur and divide luminance by result of gaussian blur + gauss9x9div(tmpIThr, tmpThr, lumThr, fullTileSize, lkernel9); + gauss9x9mult(tmpThr, tmpIThr, fullTileSize, lkernel9); + if (checkIterStop && k < iterations - 1 && checkForStop(tmpIThr, iterCheck, fullTileSize, border)) { + break; + } + } + } else if (sigmaTile > 0.84f) { // have to use 7x7 kernel float lkernel7[7][7]; compute7x7kernel(static_cast(sigma) + distanceFactor * distance, lkernel7); for (int k = 0; k < iterations; ++k) { @@ -668,9 +958,9 @@ BENCHFUN } } else { for (int k = 0; k < iterations; ++k) { - // apply 7x7 gaussian blur and divide luminance by result of gaussian blur - gauss7x7div(tmpIThr, tmpThr, lumThr, fullTileSize, kernel7); - gauss7x7mult(tmpThr, tmpIThr, fullTileSize, kernel7); + // apply 13x13 gaussian blur and divide luminance by result of gaussian blur + gauss13x13div(tmpIThr, tmpThr, lumThr, fullTileSize, kernel13); + gauss13x13mult(tmpThr, tmpIThr, fullTileSize, kernel13); if (checkIterStop && k < iterations - 1 && checkForStop(tmpIThr, iterCheck, fullTileSize, border)) { break; } @@ -731,7 +1021,7 @@ BENCHFUN { 0.019334, 0.119193, 0.950227 } }; - float contrast = conrastThreshold / 100.f; + float contrast = conrastThreshold / 100.0; const float clipVal = (ri->get_white(1) - ri->get_cblack(1)) * scale_mul[1]; @@ -741,7 +1031,7 @@ BENCHFUN array2D clipMask(W, H); constexpr float clipLimit = 0.95f; - constexpr float maxSigma = 1.15f; + constexpr float maxSigma = 2.f; if (getSensorType() == ST_BAYER) { const float whites[2][2] = { @@ -790,6 +1080,10 @@ BENCHFUN } } + if (std::isnan(radius)) { + return; + } + if (showMask) { array2D& L = blue; // blue will be overridden anyway => we can use its buffer to store L #ifdef _OPENMP diff --git a/rtengine/ciecam02.cc b/rtengine/ciecam02.cc index c7e49b2ed..208ed4366 100644 --- a/rtengine/ciecam02.cc +++ b/rtengine/ciecam02.cc @@ -28,7 +28,7 @@ #endif #undef CLIPD -#define CLIPD(a) ((a)>0.0?((a)<1.0?(a):1.0):0.0) +#define CLIPD(a) ((a)>0.f?((a)<1.f?(a):1.f):0.f) #define MAXR(a,b) ((a) > (b) ? (a) : (b)) namespace rtengine @@ -408,7 +408,7 @@ void Ciecam02::initcam1float (float yb, float pilotd, float f, float la, float x { n = yb / yw; - if (pilotd == 2.0) { + if (pilotd == 2.f) { d = d_factorfloat ( f, la ); } else { d = pilotd; @@ -434,7 +434,7 @@ void Ciecam02::initcam2float (float yb, float pilotd, float f, float la, float x { n = yb / yw; - if (pilotd == 2.0) { + if (pilotd == 2.f) { d = d_factorfloat ( f, la ); } else { d = pilotd; @@ -492,7 +492,7 @@ void Ciecam02::xyz2jchqms_ciecam02float ( float &J, float &C, float &h, float &Q myh = xatan2f ( cb, ca ); if ( myh < 0.0f ) { - myh += (2.f * rtengine::RT_PI); + myh += (2.f * rtengine::RT_PI_F); } a = ((2.0f * rpa) + gpa + (0.05f * bpa) - 0.305f) * nbb; @@ -620,7 +620,7 @@ void Ciecam02::xyz2jch_ciecam02float ( float &J, float &C, float &h, float aw, f myh = xatan2f ( cb, ca ); if ( myh < 0.0f ) { - myh += (2.f * rtengine::RT_PI); + myh += (2.f * rtengine::RT_PI_F); } a = ((2.0f * rpa) + gpa + (0.05f * bpa) - 0.305f) * nbb; diff --git a/rtengine/cieimage.h b/rtengine/cieimage.h index fea675cd4..329c0ba74 100644 --- a/rtengine/cieimage.h +++ b/rtengine/cieimage.h @@ -23,7 +23,7 @@ namespace rtengine { -class CieImage : +class CieImage final : public NonCopyable { private: diff --git a/rtengine/color.cc b/rtengine/color.cc index 8d20fb9ba..89be69e9d 100644 --- a/rtengine/color.cc +++ b/rtengine/color.cc @@ -16,6 +16,7 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . */ +#include #include "rtengine.h" #include "color.h" @@ -940,6 +941,17 @@ void Color::rgbxyz (float r, float g, float b, float &x, float &y, float &z, con z = ((xyz_rgb[2][0] * r + xyz_rgb[2][1] * g + xyz_rgb[2][2] * b)) ; } +void Color::rgbxyY(float r, float g, float b, float &x, float &y, float &Y, const float xyz_rgb[3][3]) +{ + const float xx = xyz_rgb[0][0] * r + xyz_rgb[0][1] * g + xyz_rgb[0][2] * b; + const float yy = xyz_rgb[1][0] * r + xyz_rgb[1][1] * g + xyz_rgb[1][2] * b; + const float zz = xyz_rgb[2][0] * r + xyz_rgb[2][1] * g + xyz_rgb[2][2] * b; + const float som = xx + yy + zz; + x = xx / som; + y = yy / som; + Y = yy / 65535.f; +} + void Color::rgbxyz (float r, float g, float b, float &x, float &y, float &z, const float xyz_rgb[3][3]) { x = ((xyz_rgb[0][0] * r + xyz_rgb[0][1] * g + xyz_rgb[0][2] * b)) ; @@ -1713,6 +1725,13 @@ void Color::Lab2XYZ(float L, float a, float b, float &x, float &y, float &z) y = (LL > epskap) ? 65535.0f * fy * fy * fy : 65535.0f * LL / kappa; } +float Color::L2Y(float L) +{ + const float LL = L / 327.68f; + const float fy = (c1By116 * LL) + c16By116; // (L+16)/116 + return (LL > epskapf) ? 65535.f * fy * fy * fy : 65535.f * LL / kappaf; +} + void Color::L2XYZ(float L, float &x, float &y, float &z) // for black & white { float LL = L / 327.68f; @@ -1755,19 +1774,6 @@ inline float Color::computeXYZ2Lab(float f) } } - -inline float Color::computeXYZ2LabY(float f) -{ - if (f < 0.f) { - return 327.68 * (kappa * f / MAXVALF); - } else if (f > 65535.f) { - return 327.68f * (116.f * xcbrtf(f / MAXVALF) - 16.f); - } else { - return cachefy[f]; - } -} - - void Color::RGB2Lab(float *R, float *G, float *B, float *L, float *a, float *b, const float wp[3][3], int width) { @@ -2997,1384 +3003,6 @@ void Color::LabGamutMunsell(float *labL, float *laba, float *labb, const int N, } -/* - * MunsellLch correction - * Copyright (c) 2012 Jacques Desmis - * - * Find the right LUT and calculate the correction - */ -void Color::MunsellLch (float lum, float hue, float chrom, float memChprov, float &correction, int zone, float &lbe, bool &correctL) -{ - - int x = int(memChprov); - int y = int(chrom); - - //begin PB correction + sky - if(zone == 1) { - if(lum > 5.0) { - if(lum < 15.0) { - if( (hue >= (_15PB10[x] - 0.035)) && (hue < (_15PB10[x] + 0.052) && x <= 45)) { - if(y > 49) { - y = 49; - } - - correction = _15PB10[y] - _15PB10[x] ; - lbe = _15PB10[y]; - correctL = true; - } else if (( hue >= ( _3PB10[x] - 0.052)) && (hue < (_45PB10[x] + _3PB10[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _3PB10[y] - _3PB10[x]; - lbe = _3PB10[y]; - correctL = true; - } else if (( hue >= (_45PB10[x] + _3PB10[x]) / 2.0) && (hue < (_45PB10[x] + 0.052)) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _45PB10[y] - _45PB10[x] ; - lbe = _45PB10[y]; - correctL = true; - } else if (( hue >= (_6PB10[x] - 0.052) && (hue < (_6PB10[x] + _75PB10[x]) / 2.0))) { - correction = _6PB10[y] - _6PB10[x] ; - lbe = _6PB10[y]; - correctL = true; - } else if (( hue >= (_6PB10[x] + _75PB10[x]) / 2.0) && (hue < (_9PB10[x] + _75PB10[x]) / 2.0)) { - correction = _75PB10[y] - _75PB10[x] ; - lbe = _75PB10[y]; - correctL = true; - } else if (( hue >= (_9PB10[x] + _75PB10[x]) / 2.0) && (hue < (_9PB10[x] + _10PB10[x]) / 2.0)) { - correction = _9PB10[y] - _9PB10[x] ; - lbe = _9PB10[y]; - correctL = true; - } else if (( hue >= (_10PB10[x] + _9PB10[x]) / 2.0) && (hue < (_1P10[x] + _10PB10[x]) / 2.0)) { - correction = _10PB10[y] - _10PB10[x] ; - lbe = _10PB10[y]; - correctL = true; - } else if (( hue >= (_10PB10[x] + _1P10[x]) / 2.0) && (hue < (_1P10[x] + _4P10[x]) / 2.0)) { - correction = _1P10[y] - _1P10[x]; - lbe = _1P10[y]; - correctL = true; - } else if (( hue >= (_1P10[x] + _4P10[x]) / 2.0) && (hue < (0.035 + _4P10[x]) / 2.0)) { - correction = _4P10[y] - _4P10[x] ; - lbe = _4P10[y]; - correctL = true; - } - } else if (lum < 25.0) { - if( (hue >= (_15PB20[x] - 0.035)) && (hue < (_15PB20[x] + _3PB20[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _15PB20[y] - _15PB20[x] ; - lbe = _15PB20[y]; - correctL = true; - } else if (( hue >= (_15PB20[x] + _3PB20[x]) / 2.0) && (hue < (_45PB20[x] + _3PB20[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _3PB20[y] - _3PB20[x] ; - lbe = _3PB20[y]; - correctL = true; - } else if (( hue >= (_45PB20[x] + _3PB20[x]) / 2.0) && (hue < ( _45PB20[x] + 0.052)) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _45PB20[y] - _45PB20[x] ; - lbe = _45PB20[y]; - correctL = true; - } else if (( hue >= (_45PB20[x] + 0.052)) && (hue < (_6PB20[x] + _75PB20[x]) / 2.0)) { - correction = _6PB20[y] - _6PB20[x]; - lbe = _6PB20[y]; - correctL = true; - } else if (( hue >= (_6PB20[x] + _75PB20[x]) / 2.0) && (hue < (_9PB20[x] + _75PB20[x]) / 2.0)) { - correction = _75PB20[y] - _75PB20[x] ; - lbe = _75PB20[y]; - correctL = true; - } else if (( hue >= (_9PB20[x] + _75PB20[x]) / 2.0) && (hue < (_9PB20[x] + _10PB20[x]) / 2.0)) { - correction = _9PB20[y] - _9PB20[x] ; - lbe = _9PB20[y]; - correctL = true; - } else if (( hue >= (_10PB20[x] + _9PB20[x]) / 2.0) && (hue < (_1P20[x] + _10PB20[x]) / 2.0)) { - correction = _10PB20[y] - _10PB20[x] ; - lbe = _10PB20[y]; - correctL = true; - } else if (( hue >= (_10PB20[x] + _1P20[x]) / 2.0) && (hue < (_1P20[x] + _4P20[x]) / 2.0)) { - correction = _1P20[y] - _1P20[x] ; - lbe = _1P20[y]; - correctL = true; - } else if (( hue >= (_1P20[x] + _4P20[x]) / 2.0) && (hue < (0.035 + _4P20[x]) / 2.0)) { - correction = _4P20[y] - _4P20[x] ; - lbe = _4P20[y]; - correctL = true; - } - } else if (lum < 35.0) { - if( (hue >= (_15PB30[x] - 0.035)) && (hue < (_15PB30[x] + _3PB30[x]) / 2.0) && x <= 85 ) { - if(y > 89) { - y = 89; - } - - correction = _15PB30[y] - _15PB30[x] ; - lbe = _15PB30[y]; - correctL = true; - } else if (( hue >= (_15PB30[x] + _3PB30[x]) / 2.0) && (hue < (_45PB30[x] + _3PB30[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _3PB30[y] - _3PB30[x] ; - lbe = _3PB30[y]; - correctL = true; - } else if (( hue >= (_45PB30[x] + _3PB30[x]) / 2.0) && (hue < (_45PB30[x] + 0.052)) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _45PB30[y] - _45PB30[x] ; - lbe = _45PB30[y]; - correctL = true; - } else if (( hue >= ( _45PB30[x] + 0.052)) && (hue < (_6PB30[x] + _75PB30[x]) / 2.0)) { - correction = _6PB30[y] - _6PB30[x] ; - lbe = _6PB30[y]; - correctL = true; - } else if (( hue >= (_6PB30[x] + _75PB30[x]) / 2.0) && (hue < (_9PB30[x] + _75PB30[x]) / 2.0)) { - correction = _75PB30[y] - _75PB30[x] ; - lbe = _75PB30[y] ; - correctL = true; - } else if (( hue >= (_9PB30[x] + _75PB30[x]) / 2.0) && (hue < (_9PB30[x] + _10PB30[x]) / 2.0)) { - correction = _9PB30[y] - _9PB30[x] ; - lbe = _9PB30[y]; - correctL = true; - } else if (( hue >= (_10PB30[x] + _9PB30[x]) / 2.0) && (hue < (_1P30[x] + _10PB30[x]) / 2.0)) { - correction = _10PB30[y] - _10PB30[x] ; - lbe = _10PB30[y]; - correctL = true; - } else if (( hue >= (_10PB30[x] + _1P30[x]) / 2.0) && (hue < (_1P30[x] + _4P30[x]) / 2.0)) { - correction = _1P30[y] - _1P30[x] ; - lbe = _1P30[y]; - correctL = true; - } else if (( hue >= (_1P30[x] + _4P30[x]) / 2.0) && (hue < (0.035 + _4P30[x]) / 2.0)) { - correction = _4P30[y] - _4P30[x] ; - lbe = _4P30[y]; - correctL = true; - } - } else if (lum < 45.0) { - if( (hue <= (_05PB40[x] + _15PB40[x]) / 2.0) && (hue > (_05PB40[x] + _10B40[x]) / 2.0) && x < 75 ) { - if(y > 75) { - y = 75; - } - - correction = _05PB40[y] - _05PB40[x] ; - lbe = _05PB40[y]; - correctL = true; - } else if( (hue <= (_05PB40[x] + _10B40[x]) / 2.0) && (hue > (_10B40[x] + _9B40[x]) / 2.0) && x < 70 ) { - if(y > 70) { - y = 70; - } - - correction = _10B40[y] - _10B40[x] ; - lbe = _10B40[y]; - correctL = true; - } else if( (hue <= (_10B40[x] + _9B40[x]) / 2.0) && (hue > (_9B40[x] + _7B40[x]) / 2.0) && x < 70 ) { - if(y > 70) { - y = 70; - } - - correction = _9B40[y] - _9B40[x] ; - lbe = _9B40[y]; - correctL = true; - } else if( (hue <= (_9B40[x] + _7B40[x]) / 2.0) && (hue > (_5B40[x] + _7B40[x]) / 2.0) && x < 70 ) { - if(y > 70) { - y = 70; - } - - correction = _7B40[y] - _7B40[x] ; - lbe = _7B40[y]; - correctL = true; - } else if (( hue <= (_5B40[x] + _7B40[x]) / 2.0) && (hue > (_5B40[x] - 0.035)) && x < 70) { - if(y > 70) { - y = 70; // - } - - correction = _5B40[y] - _5B40[x] ; - lbe = _5B40[y]; - correctL = true; - } - - else if( (hue >= (_15PB40[x] - 0.035)) && (hue < (_15PB40[x] + _3PB40[x]) / 2.0) && x <= 85 ) { - if(y > 89) { - y = 89; - } - - correction = _15PB40[y] - _15PB40[x] ; - lbe = _15PB40[y]; - correctL = true; - } else if (( hue >= (_15PB40[x] + _3PB40[x]) / 2.0) && (hue < (_45PB40[x] + _3PB40[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _3PB40[y] - _3PB40[x] ; - lbe = _3PB40[y]; - correctL = true; - } else if (( hue >= (_45PB40[x] + _3PB40[x]) / 2.0) && (hue < (_45PB40[x] + 0.052)) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _45PB40[y] - _45PB40[x] ; - lbe = _45PB40[y] ; - correctL = true; - } else if (( hue >= (_45PB40[x] + 0.052)) && (hue < (_6PB40[x] + _75PB40[x]) / 2.0)) { - correction = _6PB40[y] - _6PB40[x] ; - lbe = _6PB40[y]; - correctL = true; - } else if (( hue >= (_6PB40[x] + _75PB40[x]) / 2.0) && (hue < (_9PB40[x] + _75PB40[x]) / 2.0)) { - correction = _75PB40[y] - _75PB40[x] ; - lbe = _75PB40[y]; - correctL = true; - } else if (( hue >= (_9PB40[x] + _75PB40[x]) / 2.0) && (hue < (_9PB40[x] + _10PB40[x]) / 2.0)) { - correction = _9PB40[y] - _9PB40[x] ; - lbe = _9PB40[y]; - correctL = true; - } else if (( hue >= (_10PB40[x] + _9PB40[x]) / 2.0) && (hue < (_1P40[x] + _10PB40[x]) / 2.0)) { - correction = _10PB40[y] - _10PB40[x] ; - lbe = _10PB40[y]; - correctL = true; - } else if (( hue >= (_10PB40[x] + _1P40[x]) / 2.0) && (hue < (_1P40[x] + _4P40[x]) / 2.0)) { - correction = _1P40[y] - _1P40[x] ; - lbe = _1P40[y]; - correctL = true; - } else if (( hue >= (_1P40[x] + _4P40[x]) / 2.0) && (hue < (0.035 + _4P40[x]) / 2.0)) { - correction = _4P40[y] - _4P40[x] ; - lbe = _4P40[y]; - correctL = true; - } - } else if (lum < 55.0) { - if( (hue <= (_05PB50[x] + _15PB50[x]) / 2.0) && (hue > (_05PB50[x] + _10B50[x]) / 2.0) && x < 79 ) { - if(y > 79) { - y = 79; - } - - correction = _05PB50[y] - _05PB50[x] ; - lbe = _05PB50[y]; - correctL = true; - } else if( (hue <= (_05PB50[x] + _10B50[x]) / 2.0) && (hue > (_10B50[x] + _9B50[x]) / 2.0) && x < 79 ) { - if(y > 79) { - y = 79; - } - - correction = _10B50[y] - _10B50[x] ; - lbe = _10B50[y]; - correctL = true; - } else if( (hue <= (_10B50[x] + _9B50[x]) / 2.0) && (hue > (_9B50[x] + _7B50[x]) / 2.0) && x < 79 ) { - if(y > 79) { - y = 79; - } - - correction = _9B50[y] - _9B50[x] ; - lbe = _9B50[y]; - correctL = true; - } else if( (hue <= (_9B50[x] + _7B50[x]) / 2.0) && (hue > (_5B50[x] + _7B50[x]) / 2.0) && x < 79 ) { - if(y > 79) { - y = 79; - } - - correction = _7B50[y] - _7B50[x] ; - lbe = _7B50[y]; - correctL = true; - } else if (( hue <= (_5B50[x] + _7B50[x]) / 2.0) && (hue > (_5B50[x] - 0.035)) && x < 79) { - if(y > 79) { - y = 79; // - } - - correction = _5B50[y] - _5B50[x] ; - lbe = _5B50[y]; - correctL = true; - } - - else if( (hue >= (_15PB50[x] - 0.035)) && (hue < (_15PB50[x] + _3PB50[x]) / 2.0) && x <= 85 ) { - if(y > 89) { - y = 89; - } - - correction = _15PB50[y] - _15PB50[x] ; - lbe = _15PB50[y]; - correctL = true; - } else if (( hue >= (_15PB50[x] + _3PB50[x]) / 2.0) && (hue < (_45PB50[x] + _3PB50[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _3PB50[y] - _3PB50[x] ; - lbe = _3PB50[y]; - correctL = true; - } else if (( hue >= (_45PB50[x] + _3PB50[x]) / 2.0) && (hue < (_6PB50[x] + _45PB50[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _45PB50[y] - _45PB50[x] ; - lbe = _45PB50[y]; - correctL = true; - } else if (( hue >= (_6PB50[x] + _45PB50[x]) / 2.0) && (hue < (_6PB50[x] + _75PB50[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _6PB50[y] - _6PB50[x] ; - lbe = _6PB50[y]; - correctL = true; - } else if (( hue >= (_6PB50[x] + _75PB50[x]) / 2.0) && (hue < (_9PB50[x] + _75PB50[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _75PB50[y] - _75PB50[x] ; - lbe = _75PB50[y]; - correctL = true; - } else if (( hue >= (_9PB50[x] + _75PB50[x]) / 2.0) && (hue < (_9PB50[x] + _10PB50[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _9PB50[y] - _9PB50[x] ; - lbe = _9PB50[y]; - correctL = true; - } else if (( hue >= (_10PB50[x] + _9PB50[x]) / 2.0) && (hue < (_1P50[x] + _10PB50[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _10PB50[y] - _10PB50[x] ; - lbe = _10PB50[y]; - correctL = true; - } else if (( hue >= (_10PB50[x] + _1P50[x]) / 2.0) && (hue < (_1P50[x] + _4P50[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _1P50[y] - _1P50[x] ; - lbe = _1P50[y]; - correctL = true; - } else if (( hue >= (_1P50[x] + _4P50[x]) / 2.0) && (hue < (0.035 + _4P50[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _4P50[y] - _4P50[x] ; - lbe = _4P50[y]; - correctL = true; - } - } else if (lum < 65.0) { - if( (hue <= (_05PB60[x] + _15PB60[x]) / 2.0) && (hue > (_05PB60[x] + _10B60[x]) / 2.0) && x < 79 ) { - if(y > 79) { - y = 79; - } - - correction = _05PB60[y] - _05PB60[x] ; - lbe = _05PB60[y]; - correctL = true; - } else if( (hue <= (_05PB60[x] + _10B60[x]) / 2.0) && (hue > (_10B60[x] + _9B60[x]) / 2.0) && x < 79 ) { - if(y > 79) { - y = 79; - } - - correction = _10B60[y] - _10B60[x] ; - lbe = _10B60[y]; - correctL = true; - } else if( (hue <= (_10B60[x] + _9B60[x]) / 2.0) && (hue > (_9B60[x] + _7B60[x]) / 2.0) && x < 79 ) { - if(y > 79) { - y = 79; - } - - correction = _9B60[y] - _9B60[x] ; - lbe = _9B60[y]; - correctL = true; - } else if( (hue <= (_9B60[x] + _7B60[x]) / 2.0) && (hue > (_5B60[x] + _7B60[x]) / 2.0) && x < 79 ) { - if(y > 79) { - y = 79; - } - - correction = _7B60[y] - _7B60[x] ; - lbe = _7B60[y]; - correctL = true; - } else if (( hue <= (_5B60[x] + _7B60[x]) / 2.0) && (hue > (_5B60[x] - 0.035)) && x < 79) { - if(y > 79) { - y = 79; // - } - - correction = _5B60[y] - _5B60[x] ; - lbe = _5B60[y]; - correctL = true; - } - - else if( (hue >= (_15PB60[x] - 0.035)) && (hue < (_15PB60[x] + _3PB60[x]) / 2.0) && x <= 85 ) { - if(y > 89) { - y = 89; - } - - correction = _15PB60[y] - _15PB60[x] ; - lbe = _15PB60[y]; - correctL = true; - } else if (( hue >= (_15PB60[x] + _3PB60[x]) / 2.0) && (hue < (_45PB60[x] + _3PB60[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _3PB60[y] - _3PB60[x] ; - lbe = _3PB60[y]; - correctL = true; - } else if (( hue >= (_45PB60[x] + _3PB60[x]) / 2.0) && (hue < (_6PB60[x] + _45PB60[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _45PB60[y] - _45PB60[x] ; - lbe = _45PB60[y]; - correctL = true; - } else if (( hue >= (_6PB60[x] + _45PB60[x]) / 2.0) && (hue < (_6PB60[x] + _75PB60[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _6PB60[y] - _6PB60[x] ; - lbe = _6PB60[y]; - correctL = true; - } else if (( hue >= (_6PB60[x] + _75PB60[x]) / 2.0) && (hue < (_9PB60[x] + _75PB60[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _75PB60[y] - _75PB60[x] ; - lbe = _75PB60[y]; - correctL = true; - } else if (( hue >= (_9PB60[x] + _75PB60[x]) / 2.0) && (hue < (_9PB60[x] + _10PB60[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _9PB60[y] - _9PB60[x] ; - lbe = _9PB60[y]; - correctL = true; - } else if (( hue >= (_10PB60[x] + _9PB60[x]) / 2.0) && (hue < (_1P60[x] + _10PB60[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _10PB60[y] - _10PB60[x] ; - lbe = _10PB60[y]; - correctL = true; - } else if (( hue >= (_10PB60[x] + _1P60[x]) / 2.0) && (hue < (_1P60[x] + _4P60[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _1P60[y] - _1P60[x] ; - lbe = _1P60[y]; - correctL = true; - } else if (( hue >= (_1P60[x] + _4P60[x]) / 2.0) && (hue < (0.035 + _4P60[x]) / 2.0) && x <= 85) { - if(y > 89) { - y = 89; - } - - correction = _4P60[y] - _4P60[x] ; - lbe = _4P60[y]; - correctL = true; - } - } else if (lum < 75.0) { - if( (hue <= (_05PB70[x] + _15PB70[x]) / 2.0) && (hue > (_05PB70[x] + _10B70[x]) / 2.0) && x < 50 ) { - if(y > 49) { - y = 49; - } - - correction = _05PB70[y] - _05PB70[x] ; - lbe = _05PB70[y]; - correctL = true; - } else if( (hue <= (_05PB70[x] + _10B70[x]) / 2.0) && (hue > (_10B70[x] + _9B70[x]) / 2.0) && x < 50 ) { - if(y > 49) { - y = 49; - } - - correction = _10B70[y] - _10B70[x] ; - lbe = _10B70[y]; - correctL = true; - } else if( (hue <= (_10B70[x] + _9B70[x]) / 2.0) && (hue > (_9B70[x] + _7B70[x]) / 2.0) && x < 50 ) { - if(y > 49) { - y = 49; - } - - correction = _9B70[y] - _9B70[x] ; - lbe = _9B70[y]; - correctL = true; - } else if( (hue <= (_9B70[x] + _7B70[x]) / 2.0) && (hue > (_5B70[x] + _7B70[x]) / 2.0) && x < 50 ) { - if(y > 49) { - y = 49; - } - - correction = _7B70[y] - _7B70[x] ; - lbe = _7B70[y]; - correctL = true; - } else if (( hue <= (_5B70[x] + _7B70[x]) / 2.0) && (hue > (_5B70[x] - 0.035)) && x < 50) { - if(y > 49) { - y = 49; // - } - - correction = _5B70[y] - _5B70[x] ; - lbe = _5B70[y]; - correctL = true; - } - - else if( (hue >= (_15PB70[x] - 0.035)) && (hue < (_15PB70[x] + _3PB70[x]) / 2.0) && x < 50 ) { - if(y > 49) { - y = 49; - } - - correction = _15PB70[y] - _15PB70[x] ; - lbe = _15PB70[y]; - correctL = true; - } else if (( hue >= (_45PB70[x] + _3PB70[x]) / 2.0) && (hue < (_6PB70[x] + _45PB70[x]) / 2.0) && x < 50) { - if(y > 49) { - y = 49; - } - - correction = _45PB70[y] - _45PB70[x] ; - lbe = _45PB70[y]; - correctL = true; - } else if (( hue >= (_6PB70[x] + _45PB70[x]) / 2.0) && (hue < (_6PB70[x] + _75PB70[x]) / 2.0) && x < 50) { - if(y > 49) { - y = 49; - } - - correction = _6PB70[y] - _6PB70[x] ; - lbe = _6PB70[y]; - correctL = true; - } else if (( hue >= (_6PB70[x] + _75PB70[x]) / 2.0) && (hue < (_9PB70[x] + _75PB70[x]) / 2.0) && x < 50) { - if(y > 49) { - y = 49; - } - - correction = _75PB70[y] - _75PB70[x] ; - lbe = _75PB70[y]; - correctL = true; - } else if (( hue >= (_9PB70[x] + _75PB70[x]) / 2.0) && (hue < (_9PB70[x] + 0.035)) && x < 50) { - if(y > 49) { - y = 49; - } - - correction = _9PB70[y] - _9PB70[x] ; - lbe = _9PB70[y]; - correctL = true; - } - } else if (lum < 85.0) { - if( (hue <= (_05PB80[x] + _15PB80[x]) / 2.0) && (hue > (_05PB80[x] + _10B80[x]) / 2.0) && x < 40 ) { - if(y > 39) { - y = 39; - } - - correction = _05PB80[y] - _05PB80[x] ; - lbe = _05PB80[y] ; - correctL = true; - } else if( (hue <= (_05PB80[x] + _10B80[x]) / 2.0) && (hue > (_10B80[x] + _9B80[x]) / 2.0) && x < 40 ) { - if(y > 39) { - y = 39; - } - - correction = _10B80[y] - _10B80[x] ; - lbe = _10B80[y]; - correctL = true; - } else if( (hue <= (_10B80[x] + _9B80[x]) / 2.0) && (hue > (_9B80[x] + _7B80[x]) / 2.0) && x < 40 ) { - if(y > 39) { - y = 39; - } - - correction = _9B80[y] - _9B80[x] ; - lbe = _9B80[y]; - correctL = true; - } else if( (hue <= (_9B80[x] + _7B80[x]) / 2.0) && (hue > (_5B80[x] + _7B80[x]) / 2.0) && x < 50 ) { - if(y > 49) { - y = 49; - } - - correction = _7B80[y] - _7B80[x] ; - lbe = _7B80[y]; - correctL = true; - } else if (( hue <= (_5B80[x] + _7B80[x]) / 2.0) && (hue > (_5B80[x] - 0.035)) && x < 50) { - if(y > 49) { - y = 49; // - } - - correction = _5B80[y] - _5B80[x] ; - lbe = _5B80[y]; - correctL = true; - } - - else if( (hue >= (_15PB80[x] - 0.035)) && (hue < (_15PB80[x] + _3PB80[x]) / 2.0) && x < 50 ) { - if(y > 49) { - y = 49; - } - - correction = _15PB80[y] - _15PB80[x] ; - lbe = _15PB80[y]; - correctL = true; - } else if (( hue >= (_45PB80[x] + _3PB80[x]) / 2.0) && (hue < (_6PB80[x] + _45PB80[x]) / 2.0) && x < 50) { - if(y > 49) { - y = 49; - } - - correction = _45PB80[y] - _45PB80[x] ; - lbe = _45PB80[y]; - correctL = true; - } else if (( hue >= (_6PB80[x] + _45PB80[x]) / 2.0) && (hue < (_6PB80[x] + _75PB80[x]) / 2.0) && x < 50) { - if(y > 49) { - y = 49; - } - - correction = _6PB80[y] - _6PB80[x] ; - lbe = _6PB80[y]; - correctL = true; - } else if (( hue >= (_6PB80[x] + _75PB80[x]) / 2.0) && (hue < (_9PB80[x] + _75PB80[x]) / 2.0) && x < 50) { - if(y > 49) { - y = 49; - } - - correction = _75PB80[y] - _75PB80[x] ; - lbe = _75PB80[y]; - correctL = true; - } else if (( hue >= (_9PB80[x] + _75PB80[x]) / 2.0) && (hue < (_9PB80[x] + 0.035)) && x < 50) { - if(y > 49) { - y = 49; - } - - correction = _9PB80[y] - _9PB80[x] ; - lbe = _9PB80[y]; - correctL = true; - } - } - } - } - // end PB correction - - //red yellow correction - else if(zone == 2) { - if(lum > 15.0) { - if(lum < 25.0) { - if( (hue <= (_10YR20[x] + 0.035)) && (hue > (_10YR20[x] + _85YR20[x]) / 2.0) && x <= 45) { - if(y > 49) { - y = 49; - } - - correction = _10YR20[y] - _10YR20[x] ; - lbe = _10YR20[y]; - correctL = true; - } else if (( hue <= (_85YR20[x] + _10YR20[x]) / 2.0) && (hue > (_85YR20[x] + 0.035) && x <= 45)) { - if(y > 49) { - y = 49; - } - - correction = _85YR20[y] - _85YR20[x] ; - lbe = _85YR20[y]; - correctL = true; - } - } else if (lum < 35.0) { - if( (hue <= (_10YR30[x] + 0.035)) && (hue > (_10YR30[x] + _85YR30[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _10YR30[y] - _10YR30[x] ; - lbe = _10YR30[y]; - correctL = true; - } else if( (hue <= (_10YR30[x] + _85YR30[x]) / 2.0) && (hue > (_85YR30[x] + _7YR30[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _85YR30[y] - _85YR30[x] ; - lbe = _85YR30[y]; - correctL = true; - } else if (( hue <= (_85YR30[x] + _7YR30[x]) / 2.0) && (hue > (_7YR30[x] + _55YR30[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _7YR30[y] - _7YR30[x] ; - lbe = _7YR30[y]; - correctL = true; - } else if (( hue <= (_7YR30[x] + _55YR30[x]) / 2.0) && (hue > (_55YR30[x] + _4YR30[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _55YR30[y] - _55YR30[x] ; - lbe = _55YR30[y]; - correctL = true; - } else if (( hue <= (_55YR30[x] + _4YR30[x]) / 2.0) && (hue > (_4YR30[x] + _25YR30[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _4YR30[y] - _4YR30[x] ; - lbe = _4YR30[y]; - correctL = true; - } else if (( hue <= (_4YR30[x] + _25YR30[x]) / 2.0) && (hue > (_25YR30[x] + _10R30[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _25YR30[y] - _25YR30[x] ; - lbe = _25YR30[y]; - correctL = true; - } else if (( hue <= (_25YR30[x] + _10R30[x]) / 2.0) && (hue > (_10R30[x] + _9R30[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _10R30[y] - _10R30[x] ; - lbe = _10R30[y]; - correctL = true; - } else if (( hue <= (_10R30[x] + _9R30[x]) / 2.0) && (hue > (_9R30[x] + _7R30[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _9R30[y] - _9R30[x] ; - lbe = _9R30[y]; - correctL = true; - } else if (( hue <= (_9R30[x] + _7R30[x]) / 2.0) && (hue > (_7R30[x] - 0.035)) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _7R30[y] - _7R30[x] ; - lbe = _7R30[y] ; - correctL = true; - } - } else if (lum < 45.0) { - if( (hue <= (_10YR40[x] + 0.035)) && (hue > (_10YR40[x] + _85YR40[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _10YR40[y] - _10YR40[x] ; - lbe = _10YR40[y]; - correctL = true; - } else if( (hue <= (_10YR40[x] + _85YR40[x]) / 2.0) && (hue > (_85YR40[x] + _7YR40[x]) / 2.0) && x < 85 ) { - if(y > 89) { - y = 89; - } - - correction = _85YR40[y] - _85YR40[x] ; - lbe = _85YR40[y]; - correctL = true; - } else if (( hue <= (_85YR40[x] + _7YR40[x]) / 2.0) && (hue > (_7YR40[x] + _55YR40[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _7YR40[y] - _7YR40[x] ; - lbe = _7YR40[y]; - correctL = true; - } else if (( hue <= (_7YR40[x] + _55YR40[x]) / 2.0) && (hue > (_55YR40[x] + _4YR40[x]) / 2.0) && x < 85 ) { - if(y > 89) { - y = 89; - } - - correction = _55YR40[y] - _55YR40[x] ; - lbe = _55YR40[y]; - correctL = true; - } else if (( hue <= (_55YR40[x] + _4YR40[x]) / 2.0) && (hue > (_4YR40[x] + _25YR40[x]) / 2.0) && x < 85 ) { - if(y > 89) { - y = 89; - } - - correction = _4YR40[y] - _4YR40[x] ; - lbe = _4YR40[y]; - correctL = true; - } else if (( hue <= (_4YR40[x] + _25YR40[x]) / 2.0) && (hue > (_25YR40[x] + _10R40[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _25YR40[y] - _25YR40[x] ; - lbe = _25YR40[y] ; - correctL = true; - } else if (( hue <= (_25YR40[x] + _10R40[x]) / 2.0) && (hue > (_10R40[x] + _9R40[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _10R40[y] - _10R40[x] ; - lbe = _10R40[y]; - correctL = true; - } else if (( hue <= (_10R40[x] + _9R40[x]) / 2.0) && (hue > (_9R40[x] + _7R40[x]) / 2.0) && x < 85 ) { - if(y > 89) { - y = 89; - } - - correction = _9R40[y] - _9R40[x] ; - lbe = _9R40[y]; - correctL = true; - } else if (( hue <= (_9R40[x] + _7R40[x]) / 2.0) && (hue > (_7R40[x] - 0.035)) && x < 85 ) { - if(y > 89) { - y = 89; - } - - correction = _7R40[y] - _7R40[x] ; - lbe = _7R40[y]; - correctL = true; - } - } else if (lum < 55.0) { - if( (hue <= (_10YR50[x] + 0.035)) && (hue > (_10YR50[x] + _85YR50[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _10YR50[y] - _10YR50[x] ; - lbe = _10YR50[y]; - correctL = true; - } else if( (hue <= (_10YR50[x] + _85YR50[x]) / 2.0) && (hue > (_85YR50[x] + _7YR50[x]) / 2.0) && x < 85 ) { - if(y > 89) { - y = 89; - } - - correction = _85YR50[y] - _85YR50[x] ; - lbe = _85YR50[y]; - correctL = true; - } else if (( hue <= (_85YR50[x] + _7YR50[x]) / 2.0) && (hue > (_7YR50[x] + _55YR50[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _7YR50[y] - _7YR50[x] ; - lbe = _7YR50[y]; - correctL = true; - } else if (( hue <= (_7YR50[x] + _55YR50[x]) / 2.0) && (hue > (_55YR50[x] + _4YR50[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _55YR50[y] - _55YR50[x] ; - lbe = _55YR50[y]; - correctL = true; - } else if (( hue <= (_55YR50[x] + _4YR50[x]) / 2.0) && (hue > (_4YR50[x] + _25YR50[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _4YR50[y] - _4YR50[x] ; - lbe = _4YR50[y]; - correctL = true; - } else if (( hue <= (_4YR50[x] + _25YR50[x]) / 2.0) && (hue > (_25YR50[x] + _10R50[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _25YR50[y] - _25YR50[x] ; - lbe = _25YR50[y]; - correctL = true; - } else if (( hue <= (_25YR50[x] + _10R50[x]) / 2.0) && (hue > (_10R50[x] + _9R50[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _10R50[y] - _10R50[x] ; - lbe = _10R50[y]; - correctL = true; - } else if (( hue <= (_10R50[x] + _9R50[x]) / 2.0) && (hue > (_9R50[x] + _7R50[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _9R50[y] - _9R50[x] ; - lbe = _9R50[y]; - correctL = true; - } else if (( hue <= (_9R50[x] + _7R50[x]) / 2.0) && (hue > (_7R50[x] - 0.035)) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _7R50[y] - _7R50[x] ; - lbe = _7R50[y]; - correctL = true; - } - } else if (lum < 65.0) { - if( (hue <= (_10YR60[x] + 0.035)) && (hue > (_10YR60[x] + _85YR60[x]) / 2.0)) { - ; - correction = _10YR60[y] - _10YR60[x] ; - lbe = _10YR60[y]; - correctL = true; - } else if( (hue <= (_10YR60[x] + _85YR60[x]) / 2.0) && (hue > (_85YR60[x] + _7YR60[x]) / 2.0) ) { - ; - correction = _85YR60[y] - _85YR60[x] ; - lbe = _85YR60[y]; - correctL = true; - } else if (( hue <= (_85YR60[x] + _7YR60[x]) / 2.0) && (hue > (_7YR60[x] + _55YR60[x]) / 2.0)) { - correction = _7YR60[y] - _7YR60[x] ; - lbe = _7YR60[y]; - correctL = true; - } else if (( hue <= (_7YR60[x] + _55YR60[x]) / 2.0) && (hue > (_55YR60[x] + _4YR60[x]) / 2.0)) { - correction = _55YR60[y] - _55YR60[x] ; - lbe = _55YR60[y]; - correctL = true; - } else if (( hue <= (_55YR60[x] + _4YR60[x]) / 2.0) && (hue > (_4YR60[x] + _25YR60[x]) / 2.0)) { - correction = _4YR60[y] - _4YR60[x] ; - lbe = _4YR60[y]; - correctL = true; - } else if (( hue <= (_4YR60[x] + _25YR60[x]) / 2.0) && (hue > (_25YR60[x] + _10R60[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _25YR60[y] - _25YR60[x] ; - lbe = _25YR60[y]; - correctL = true; - } else if (( hue <= (_25YR60[x] + _10R60[x]) / 2.0) && (hue > (_10R60[x] + _9R60[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _10R60[y] - _10R60[x] ; - lbe = _10R60[y]; - correctL = true; - } else if (( hue <= (_10R60[x] + _9R60[x]) / 2.0) && (hue > (_9R60[x] + _7R60[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _9R60[y] - _9R60[x] ; - lbe = _9R60[y]; - correctL = true; - } else if (( hue <= (_9R60[x] + _7R60[x]) / 2.0) && (hue > (_7R60[x] - 0.035)) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _7R60[y] - _7R60[x] ; - lbe = _7R60[y]; - correctL = true; - } - } else if (lum < 75.0) { - if( (hue <= (_10YR70[x] + 0.035)) && (hue > (_10YR70[x] + _85YR70[x]) / 2.0)) { - correction = _10YR70[y] - _10YR70[x] ; - lbe = _10YR70[y]; - correctL = true; - } else if( (hue <= (_10YR70[x] + _85YR70[x]) / 2.0) && (hue > (_85YR70[x] + _7YR70[x]) / 2.0)) { - correction = _85YR70[y] - _85YR70[x] ; - lbe = _85YR70[y]; - correctL = true; - } - - if (( hue <= (_85YR70[x] + _7YR70[x]) / 2.0) && (hue > (_7YR70[x] + _55YR70[x]) / 2.0)) { - correction = _7YR70[y] - _7YR70[x] ; - lbe = _7YR70[y]; - correctL = true; - } else if (( hue <= (_7YR70[x] + _55YR70[x]) / 2.0) && (hue > (_55YR70[x] + _4YR70[x]) / 2.0)) { - correction = _55YR70[y] - _55YR70[x] ; - lbe = _55YR70[y]; - correctL = true; - } else if (( hue <= (_55YR70[x] + _4YR70[x]) / 2.0) && (hue > (_4YR70[x] + _25YR70[x]) / 2.0)) { - correction = _4YR70[y] - _4YR70[x] ; - lbe = _4YR70[y]; - correctL = true; - } else if (( hue <= (_4YR70[x] + _25YR70[x]) / 2.0) && (hue > (_25YR70[x] + _10R70[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _25YR70[y] - _25YR70[x] ; - lbe = _25YR70[y]; - correctL = true; - } else if (( hue <= (_25YR70[x] + _10R70[x]) / 2.0) && (hue > (_10R70[x] + _9R70[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _10R70[y] - _10R70[x] ; - lbe = _10R70[y]; - correctL = true; - } else if (( hue <= (_10R70[x] + _9R70[x]) / 2.0) && (hue > (_9R70[x] + _7R70[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _9R70[y] - _9R70[x] ; - lbe = _9R70[y] ; - correctL = true; - } else if (( hue <= (_9R70[x] + _7R70[x]) / 2.0) && (hue > (_7R70[x] - 0.035)) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _7R70[y] - _7R70[x] ; - lbe = _7R70[y]; - correctL = true; - } - } else if (lum < 85.0) { - if( (hue <= (_10YR80[x] + 0.035)) && (hue > (_10YR80[x] + _85YR80[x]) / 2.0)) { - correction = _10YR80[y] - _10YR80[x] ; - lbe = _10YR80[y]; - correctL = true; - } else if( (hue <= (_10YR80[x] + _85YR80[x]) / 2.0) && (hue > (_85YR80[x] + _7YR80[x]) / 2.0)) { - correction = _85YR80[y] - _85YR80[x] ; - lbe = _85YR80[y]; - } else if (( hue <= (_85YR80[x] + _7YR80[x]) / 2.0) && (hue > (_7YR80[x] + _55YR80[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _7YR80[y] - _7YR80[x] ; - lbe = _7YR80[y]; - correctL = true; - } else if (( hue <= (_7YR80[x] + _55YR80[x]) / 2.0) && (hue > (_55YR80[x] + _4YR80[x]) / 2.0) && x < 45) { - correction = _55YR80[y] - _55YR80[x] ; - lbe = _55YR80[y]; - correctL = true; - } else if (( hue <= (_55YR80[x] + _4YR80[x]) / 2.0) && (hue > (_4YR80[x] - 0.035) && x < 45)) { - if(y > 49) { - y = 49; - } - - correction = _4YR80[y] - _4YR80[x] ; - lbe = _4YR80[y] ; - correctL = true; - } - } else if (lum < 95.0) { - if( (hue <= (_10YR90[x] + 0.035)) && (hue > (_10YR90[x] - 0.035) && x < 85)) { - if(y > 89) { - y = 89; - } - - correction = _10YR90[y] - _10YR90[x] ; - lbe = _10YR90[y]; - correctL = true; - } else if ( hue <= (_85YR90[x] + 0.035) && hue > (_85YR90[x] - 0.035) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _85YR90[y] - _85YR90[x] ; - lbe = _85YR90[y]; - correctL = true; - } else if (( hue <= (_55YR90[x] + 0.035) && (hue > (_55YR90[x] - 0.035) && x < 45))) { - if(y > 49) { - y = 49; - } - - correction = _55YR90[y] - _55YR90[x] ; - lbe = _55YR90[y]; - correctL = true; - } - } - } - } - //end red yellow - - //Green yellow correction - else if(zone == 3) { - if (lum >= 25.0) { - if (lum < 35.0) { - if( (hue <= (_7G30[x] + 0.035)) && (hue > (_7G30[x] + _5G30[x]) / 2.0) ) { - correction = _7G30[y] - _7G30[x] ; - lbe = _7G30[y]; - correctL = true; - } else if( (hue <= (_7G30[x] + _5G30[x]) / 2.0) && (hue > (_5G30[x] + _25G30[x]) / 2.0)) { - correction = _5G30[y] - _5G30[x] ; - lbe = _5G30[y]; - correctL = true; - } else if (( hue <= (_25G30[x] + _5G30[x]) / 2.0) && (hue > (_25G30[x] + _1G30[x]) / 2.0)) { - correction = _25G30[y] - _25G30[x] ; - lbe = _25G30[y]; - correctL = true; - } else if (( hue <= (_1G30[x] + _25G30[x]) / 2.0) && (hue > (_1G30[x] + _10GY30[x]) / 2.0)) { - correction = _1G30[y] - _1G30[x] ; - lbe = _1G30[y]; - correctL = true; - } else if (( hue <= (_1G30[x] + _10GY30[x]) / 2.0) && (hue > (_10GY30[x] + _75GY30[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _10GY30[y] - _10GY30[x] ; - lbe = _10GY30[y]; - correctL = true; - } else if (( hue <= (_10GY30[x] + _75GY30[x]) / 2.0) && (hue > (_75GY30[x] + _5GY30[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _75GY30[y] - _75GY30[x] ; - lbe = _75GY30[y]; - correctL = true; - } else if (( hue <= (_5GY30[x] + _75GY30[x]) / 2.0) && (hue > (_5GY30[x] - 0.035)) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _5GY30[y] - _5GY30[x] ; - lbe = _5GY30[y] ; - correctL = true; - } - } else if (lum < 45.0) { - if( (hue <= (_7G40[x] + 0.035)) && (hue > (_7G40[x] + _5G40[x]) / 2.0) ) { - correction = _7G40[y] - _7G40[x] ; - lbe = _7G40[y]; - correctL = true; - } else if( (hue <= (_7G40[x] + _5G40[x]) / 2.0) && (hue > (_5G40[x] + _25G40[x]) / 2.0)) { - correction = _5G40[y] - _5G40[x] ; - lbe = _5G40[y]; - correctL = true; - } else if (( hue <= (_25G40[x] + _5G40[x]) / 2.0) && (hue > (_25G40[x] + _1G40[x]) / 2.0)) { - correction = _25G40[y] - _25G40[x] ; - lbe = _25G40[y]; - correctL = true; - } else if (( hue <= (_1G40[x] + _25G40[x]) / 2.0) && (hue > (_1G40[x] + _10GY40[x]) / 2.0)) { - correction = _1G40[y] - _1G40[x] ; - lbe = _1G40[y]; - correctL = true; - } else if (( hue <= (_1G40[x] + _10GY40[x]) / 2.0) && (hue > (_10GY40[x] + _75GY40[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _10GY40[y] - _10GY40[x] ; - lbe = _10GY40[y]; - correctL = true; - } else if (( hue <= (_10GY40[x] + _75GY40[x]) / 2.0) && (hue > (_75GY40[x] + _5GY40[x]) / 2.0) && x < 85) { - if(y > 89) { - y = 89; - } - - correction = _75GY40[y] - _75GY40[x] ; - lbe = _75GY40[y]; - correctL = true; - } else if (( hue <= (_5GY40[x] + _75GY40[x]) / 2.0) && (hue > (_5GY40[x] - 0.035)) && x < 85) { - if(y > 89) { - y = 89; // - } - - correction = _5GY40[y] - _5GY40[x] ; - lbe = _5GY40[y]; - correctL = true; - } - } else if (lum < 55.0) { - if( (hue <= (_7G50[x] + 0.035)) && (hue > (_7G50[x] + _5G50[x]) / 2.0) ) { - correction = _7G50[y] - _7G50[x] ; - lbe = _7G50[y]; - correctL = true; - } else if( (hue <= (_7G50[x] + _5G50[x]) / 2.0) && (hue > (_5G50[x] + _25G50[x]) / 2.0)) { - correction = _5G50[y] - _5G50[x] ; - lbe = _5G50[y]; - correctL = true; - } else if (( hue <= (_25G50[x] + _5G50[x]) / 2.0) && (hue > (_25G50[x] + _1G50[x]) / 2.0)) { - correction = _25G50[y] - _25G50[x] ; - lbe = _25G50[y]; - correctL = true; - } else if (( hue <= (_1G50[x] + _25G50[x]) / 2.0) && (hue > (_1G50[x] + _10GY50[x]) / 2.0)) { - correction = _1G50[y] - _1G50[x] ; - lbe = _1G50[y]; - correctL = true; - } else if (( hue <= (_1G50[x] + _10GY50[x]) / 2.0) && (hue > (_10GY50[x] + _75GY50[x]) / 2.0)) { - correction = _10GY50[y] - _10GY50[x] ; - lbe = _10GY50[y]; - correctL = true; - } else if (( hue <= (_10GY50[x] + _75GY50[x]) / 2.0) && (hue > (_75GY50[x] + _5GY50[x]) / 2.0)) { - correction = _75GY50[y] - _75GY50[x] ; - lbe = _75GY50[y]; - correctL = true; - } else if (( hue <= (_5GY50[x] + _75GY50[x]) / 2.0) && (hue > (_5GY50[x] - 0.035))) { - correction = _5GY50[y] - _5GY50[x] ; - lbe = _5GY50[y]; - correctL = true; - } - } else if (lum < 65.0) { - if( (hue <= (_7G60[x] + 0.035)) && (hue > (_7G60[x] + _5G60[x]) / 2.0) ) { - correction = _7G60[y] - _7G60[x] ; - lbe = _7G60[y]; - correctL = true; - } else if( (hue <= (_7G60[x] + _5G60[x]) / 2.0) && (hue > (_5G60[x] + _25G60[x]) / 2.0)) { - correction = _5G60[y] - _5G60[x] ; - lbe = _5G60[y]; - correctL = true; - } else if (( hue <= (_25G60[x] + _5G60[x]) / 2.0) && (hue > (_25G60[x] + _1G60[x]) / 2.0)) { - correction = _25G60[y] - _25G60[x] ; - lbe = _25G60[y]; - correctL = true; - } else if (( hue <= (_1G60[x] + _25G60[x]) / 2.0) && (hue > (_1G60[x] + _10GY60[x]) / 2.0)) { - correction = _1G60[y] - _1G60[x] ; - lbe = _1G60[y]; - correctL = true; - } else if (( hue <= (_1G60[x] + _10GY60[x]) / 2.0) && (hue > (_10GY60[x] + _75GY60[x]) / 2.0)) { - correction = _10GY60[y] - _10GY60[x] ; - lbe = _10GY60[y]; - correctL = true; - } else if (( hue <= (_10GY60[x] + _75GY60[x]) / 2.0) && (hue > (_75GY60[x] + _5GY60[x]) / 2.0)) { - correction = _75GY60[y] - _75GY60[x] ; - lbe = _75GY60[y] ; - correctL = true; - } else if (( hue <= (_5GY60[x] + _75GY60[x]) / 2.0) && (hue > (_5GY60[x] - 0.035))) { - correction = _5GY60[y] - _5GY60[x] ; - lbe = _5GY60[y]; - correctL = true; - } - } else if (lum < 75.0) { - if( (hue <= (_7G70[x] + 0.035)) && (hue > (_7G70[x] + _5G70[x]) / 2.0) ) { - correction = _7G70[y] - _7G70[x] ; - lbe = _7G70[y]; - correctL = true; - } else if( (hue <= (_7G70[x] + _5G70[x]) / 2.0) && (hue > (_5G70[x] + _25G70[x]) / 2.0)) { - correction = _5G70[y] - _5G70[x] ; - lbe = _5G70[y]; - correctL = true; - } else if (( hue <= (_25G70[x] + _5G70[x]) / 2.0) && (hue > (_25G70[x] + _1G70[x]) / 2.0)) { - correction = _25G70[y] - _25G70[x] ; - lbe = _25G70[y]; - correctL = true; - } else if (( hue <= (_1G70[x] + _25G70[x]) / 2.0) && (hue > (_1G70[x] + _10GY70[x]) / 2.0)) { - correction = _1G70[y] - _1G70[x] ; - lbe = _1G70[y] ; - correctL = true; - } else if (( hue <= (_1G70[x] + _10GY70[x]) / 2.0) && (hue > (_10GY70[x] + _75GY70[x]) / 2.0)) { - correction = _10GY70[y] - _10GY70[x] ; - lbe = _10GY70[y]; - correctL = true; - } else if (( hue <= (_10GY70[x] + _75GY70[x]) / 2.0) && (hue > (_75GY70[x] + _5GY70[x]) / 2.0)) { - correction = _75GY70[y] - _75GY70[x] ; - lbe = _75GY70[y]; - correctL = true; - } else if (( hue <= (_5GY70[x] + _75GY70[x]) / 2.0) && (hue > (_5GY70[x] - 0.035))) { - correction = _5GY70[y] - _5GY70[x] ; - lbe = _5GY70[y]; - correctL = true; - } - } else if (lum < 85.0) { - if( (hue <= (_7G80[x] + 0.035)) && (hue > (_7G80[x] + _5G80[x]) / 2.0) ) { - correction = _7G80[y] - _7G80[x] ; - lbe = _7G80[y]; - correctL = true; - } else if( (hue <= (_7G80[x] + _5G80[x]) / 2.0) && (hue > (_5G80[x] + _25G80[x]) / 2.0)) { - correction = _5G80[y] - _5G80[x] ; - lbe = _5G80[y]; - correctL = true; - } else if (( hue <= (_25G80[x] + _5G80[x]) / 2.0) && (hue > (_25G80[x] + _1G80[x]) / 2.0)) { - correction = _25G80[y] - _25G80[x] ; - lbe = _25G80[y]; - correctL = true; - } else if (( hue <= (_1G80[x] + _25G80[x]) / 2.0) && (hue > (_1G80[x] + _10GY80[x]) / 2.0)) { - correction = _1G80[y] - _1G80[x] ; - lbe = _1G80[y]; - correctL = true; - } else if (( hue <= (_1G80[x] + _10GY80[x]) / 2.0) && (hue > (_10GY80[x] + _75GY80[x]) / 2.0)) { - correction = _10GY80[y] - _10GY80[x] ; - lbe = _10GY80[y]; - correctL = true; - } else if (( hue <= (_10GY80[x] + _75GY80[x]) / 2.0) && (hue > (_75GY80[x] + _5GY80[x]) / 2.0)) { - correction = _75GY80[y] - _75GY80[x] ; - lbe = _75GY80[y]; - correctL = true; - } else if (( hue <= (_5GY80[x] + _75GY80[x]) / 2.0) && (hue > (_5GY80[x] - 0.035))) { - correction = _5GY80[y] - _5GY80[x] ; - lbe = _5GY80[y]; - correctL = true; - } - } - } - } - //end green yellow - - //Red purple correction : only for L < 30 - else if(zone == 4) { - if (lum > 5.0) { - if (lum < 15.0) { - if( (hue <= (_5R10[x] + 0.035)) && (hue > (_5R10[x] - 0.043)) && x < 45) { - if(y > 44) { - y = 44; - } - - correction = _5R10[y] - _5R10[x] ; - lbe = _5R10[y]; - correctL = true; - } else if( (hue <= (_25R10[x] + 0.043)) && (hue > (_25R10[x] + _10RP10[x]) / 2.0) && x < 45 ) { - if(y > 44) { - y = 44; - } - - correction = _25R10[y] - _25R10[x] ; - lbe = _25R10[y]; - correctL = true; - } else if ( (hue <= (_25R10[x] + _10RP10[x]) / 2.0) && (hue > (_10RP10[x] - 0.035) ) && x < 45) { - if(y > 44) { - y = 44; - } - - correction = _10RP10[y] - _10RP10[x] ; - lbe = _10RP10[y]; - correctL = true; - } - } else if (lum < 25.0) { - if( (hue <= (_5R20[x] + 0.035)) && (hue > (_5R20[x] + _25R20[x]) / 2.0) && x < 70 ) { - if(y > 70) { - y = 70; - } - - correction = _5R20[y] - _5R20[x] ; - lbe = _5R20[y]; - correctL = true; - } else if( (hue <= (_5R20[x] + _25R20[x]) / 2.0) && (hue > (_10RP20[x] + _25R20[x]) / 2.0) && x < 70) { - if(y > 70) { - y = 70; - } - - correction = _25R20[y] - _25R20[x] ; - lbe = _25R20[y]; - correctL = true; - } else if (( hue <= (_10RP20[x] + _25R20[x]) / 2.0) && (hue > (_10RP20[x] - 0.035)) && x < 70) { - if(y > 70) { - y = 70; - } - - correction = _10RP20[y] - _10RP20[x] ; - lbe = _10RP20[y]; - correctL = true; - } - } else if (lum < 35.0) { - if( (hue <= (_5R30[x] + 0.035)) && (hue > (_5R30[x] + _25R30[x]) / 2.0) && x < 85 ) { - if(y > 85) { - y = 85; - } - - correction = _5R30[y] - _5R30[x] ; - lbe = _5R30[y]; - correctL = true; - } else if( (hue <= (_5R30[x] + _25R30[x]) / 2.0) && (hue > (_10RP30[x] + _25R30[x]) / 2.0) && x < 85) { - if(y > 85) { - y = 85; - } - - correction = _25R30[y] - _25R30[x] ; - lbe = _25R30[y]; - correctL = true; - } else if (( hue <= (_10RP30[x] + _25R30[x]) / 2.0) && (hue > (_10RP30[x] - 0.035)) && x < 85) { - if(y > 85) { - y = 85; - } - - correction = _10RP30[y] - _10RP30[x] ; - lbe = _10RP30[y]; - correctL = true; - } - } - } - } - - //end red purple -} - - /* * SkinSat * Copyright (c)2011 Jacques Desmis diff --git a/rtengine/color.h b/rtengine/color.h index 211615de1..045e062ad 100644 --- a/rtengine/color.h +++ b/rtengine/color.h @@ -20,15 +20,16 @@ #pragma once #include -#include #include "rt_math.h" #include "LUT.h" -#include "iccmatrices.h" #include "lcms2.h" #include "sleef.h" -#define SAT(a,b,c) ((float)max(a,b,c)-(float)min(a,b,c))/(float)max(a,b,c) +namespace Glib +{ +class ustring; +} namespace rtengine { @@ -100,7 +101,6 @@ private: #endif static float computeXYZ2Lab(float f); - static float computeXYZ2LabY(float f); public: @@ -132,7 +132,7 @@ public: constexpr static double sRGBGammaCurve = 2.4; constexpr static double eps = 216.0 / 24389.0; //0.008856 - constexpr static double eps_max = MAXVALF * eps; //580.40756; + constexpr static double eps_max = MAXVALD * eps; //580.40756; constexpr static double kappa = 24389.0 / 27.0; //903.29630; constexpr static double kappaInv = 27.0 / 24389.0; constexpr static double epsilonExpInv3 = 6.0 / 29.0; @@ -144,9 +144,10 @@ public: constexpr static float D50x = 0.9642f; //0.96422; constexpr static float D50z = 0.8249f; //0.82521; - constexpr static double u0 = 4.0 * D50x / (D50x + 15 + 3 * D50z); - constexpr static double v0 = 9.0 / (D50x + 15 + 3 * D50z); + constexpr static double u0 = 4.0 * static_cast(D50x) / (static_cast(D50x) + 15 + 3 * static_cast(D50z)); + constexpr static double v0 = 9.0 / (static_cast(D50x) + 15 + 3 * static_cast(D50z)); constexpr static double epskap = 8.0; + constexpr static float epskapf = epskap; constexpr static float c1By116 = 1.0 / 116.0; constexpr static float c16By116 = 16.0 / 116.0; @@ -183,6 +184,16 @@ public: static void init (); static void cleanup (); + static inline float computeXYZ2LabY(float f) + { + if (f < 0.f) { + return 327.68f * (kappa * f / MAXVALF); + } else if (f > 65535.f) { + return 327.68f * (116.f * xcbrtf(f / MAXVALF) - 16.f); + } else { + return cachefy[f]; + } + } /** * @brief Extract luminance "sRGB" from red/green/blue values @@ -206,7 +217,7 @@ public: static float rgbLuminance(float r, float g, float b, const double workingspace[3][3]) { - return r * workingspace[1][0] + g * workingspace[1][1] + b * workingspace[1][2]; + return static_cast(r) * workingspace[1][0] + static_cast(g) * workingspace[1][1] + static_cast(b) * workingspace[1][2]; } #ifdef __SSE2__ @@ -591,6 +602,7 @@ public: * @param xyz_rgb[3][3] transformation matrix to use for the conversion */ static void rgbxyz (float r, float g, float b, float &x, float &y, float &z, const double xyz_rgb[3][3]); + static void rgbxyY(float r, float g, float b, float &x, float &y, float &Y, const float xyz_rgb[3][3]); static void rgbxyz (float r, float g, float b, float &x, float &y, float &z, const float xyz_rgb[3][3]); #ifdef __SSE2__ static void rgbxyz (vfloat r, vfloat g, vfloat b, vfloat &x, vfloat &y, vfloat &z, const vfloat xyz_rgb[3][3]); @@ -607,6 +619,7 @@ public: */ static void Lab2XYZ(float L, float a, float b, float &x, float &y, float &z); static void L2XYZ(float L, float &x, float &y, float &z); + static float L2Y(float L); #ifdef __SSE2__ static void Lab2XYZ(vfloat L, vfloat a, vfloat b, vfloat &x, vfloat &y, vfloat &z); @@ -972,10 +985,10 @@ public: template static inline T interpolatePolarHue_PI (T h1, T h2, U balance) { - float d = h2 - h1; - float f; + T d = h2 - h1; + T f; f = T(balance); - double h; + T h; if (h1 > h2) { std::swap(h1, h2); @@ -986,7 +999,7 @@ public: if (d < T(0) || d < T(0.5) || d > T(1.)) { //there was an inversion here !! d > T(rtengine::RT_PI) h1 += T(1.); h = h1 + f * (h2 - h1); - h = std::fmod(h, 1.); + h = std::fmod(h, T(1.)); } else { h = h1 + f * d; } diff --git a/rtengine/colortemp.cc b/rtengine/colortemp.cc index 02d3e0e6d..2780fcc84 100644 --- a/rtengine/colortemp.cc +++ b/rtengine/colortemp.cc @@ -27,11 +27,13 @@ #include #include "sleef.h" #include "settings.h" +#include "iccstore.h" + namespace rtengine { -static const double cie_colour_match_jd[97][3] = {//350nm to 830nm 5 nm J.Desmis 2° Standard Observer. +static const double cie_colour_match_jd2[97][3] = {//350nm to 830nm 5 nm J.Desmis 2° Standard Observer. {0.0000000, 0.000000, 0.000000}, {0.0000000, 0.000000, 0.000000}, {0.0001299, 0.0003917, 0.0006061}, {0.0002321, 0.000006965, 0.001086}, {0.0004149, 0.00001239, 0.001946}, {0.0007416, 0.00002202, 0.003846}, {0.001368, 0.000039, 0.006450001}, {0.002236, 0.000064, 0.01054999}, {0.004243, 0.000120, 0.02005001}, @@ -67,6 +69,108 @@ static const double cie_colour_match_jd[97][3] = {//350nm to 830nm 5 nm J.Desm {0.000001251141, 0.00000045181, 0.000000} }; + +static double cie_colour_match_jd[97][3] = {//350nm to 830nm 5 nm J.Desmis 10° Standard Observer. +{0.000000000000, 0.000000000000, 0.000000000000}, +{0.000000000000, 0.000000000000, 0.000000000000}, +{0.000000122200, 0.000000013398, 0.000000535027}, +{0.000000919270, 0.000000100650, 0.000004028300}, +{0.000005958600, 0.000000651100, 0.000026143700}, +{0.000033266000, 0.000003625000, 0.000146220000}, +{0.000159952000, 0.000017364000, 0.000704776000}, +{0.000662440000, 0.000071560000, 0.002927800000}, +{0.002361600000, 0.000253400000, 0.010482200000}, +{0.007242300000, 0.000768500000, 0.032344000000}, +{0.019109700000, 0.002004400000, 0.086010900000}, +{0.043400000000, 0.004509000000, 0.197120000000}, +{0.084736000000, 0.008756000000, 0.389366000000}, +{0.140638000000, 0.014456000000, 0.656760000000}, +{0.204492000000, 0.021391000000, 0.972542000000}, +{0.264737000000, 0.029497000000, 1.282500000000}, +{0.314679000000, 0.038676000000, 1.553480000000}, +{0.357719000000, 0.049602000000, 1.798500000000}, +{0.383734000000, 0.062077000000, 1.967280000000}, +{0.386726000000, 0.074704000000, 2.027300000000}, +{0.370702000000, 0.089456000000, 1.994800000000}, +{0.342957000000, 0.106256000000, 1.900700000000}, +{0.302273000000, 0.128201000000, 1.745370000000}, +{0.254085000000, 0.152761000000, 1.554900000000}, +{0.195618000000, 0.185190000000, 1.317560000000}, +{0.132349000000, 0.219940000000, 1.030200000000}, +{0.080507000000, 0.253589000000, 0.772125000000}, +{0.041072000000, 0.297665000000, 0.570060000000}, +{0.016172000000, 0.339133000000, 0.415254000000}, +{0.005132000000, 0.395379000000, 0.302356000000}, +{0.003816000000, 0.460777000000, 0.218502000000}, +{0.015444000000, 0.531360000000, 0.159249000000}, +{0.037465000000, 0.606741000000, 0.112044000000}, +{0.071358000000, 0.685660000000, 0.082248000000}, +{0.117749000000, 0.761757000000, 0.060709000000}, +{0.172953000000, 0.823330000000, 0.043050000000}, +{0.236491000000, 0.875211000000, 0.030451000000}, +{0.304213000000, 0.923810000000, 0.020584000000}, +{0.376772000000, 0.961988000000, 0.013676000000}, +{0.451584000000, 0.982200000000, 0.007918000000}, +{0.529826000000, 0.991761000000, 0.003988000000}, +{0.616053000000, 0.999110000000, 0.001091000000}, +{0.793832000000, 0.982380000000, 0.000000000000}, +{0.878655000000, 0.955552000000, 0.000000000000}, +{0.951162000000, 0.915175000000, 0.000000000000}, +{1.014160000000, 0.868934000000, 0.000000000000}, +{1.074300000000, 0.825623000000, 0.000000000000}, +{1.118520000000, 0.777405000000, 0.000000000000}, +{1.134300000000, 0.720353000000, 0.000000000000}, +{1.123990000000, 0.658341000000, 0.000000000000}, +{1.089100000000, 0.593878000000, 0.000000000000}, +{1.030480000000, 0.527963000000, 0.000000000000}, +{0.950740000000, 0.461834000000, 0.000000000000}, +{0.856297000000, 0.398057000000, 0.000000000000}, +{0.754930000000, 0.339554000000, 0.000000000000}, +{0.647467000000, 0.283493000000, 0.000000000000}, +{0.535110000000, 0.228254000000, 0.000000000000}, +{0.431567000000, 0.179828000000, 0.000000000000}, +{0.343690000000, 0.140211000000, 0.000000000000}, +{0.268329000000, 0.107633000000, 0.000000000000}, +{0.204300000000, 0.081187000000, 0.000000000000}, +{0.152568000000, 0.060281000000, 0.000000000000}, +{0.112210000000, 0.044096000000, 0.000000000000}, +{0.081260600000, 0.031800400000, 0.000000000000}, +{0.057930000000, 0.022601700000, 0.000000000000}, +{0.040850800000, 0.015905100000, 0.000000000000}, +{0.028623000000, 0.011130300000, 0.000000000000}, +{0.019941300000, 0.007748800000, 0.000000000000}, +{0.013842000000, 0.005375100000, 0.000000000000}, +{0.009576880000, 0.003717740000, 0.000000000000}, +{0.006605200000, 0.002564560000, 0.000000000000}, +{0.004552630000, 0.001768470000, 0.000000000000}, +{0.003144700000, 0.001222390000, 0.000000000000}, +{0.002174960000, 0.000846190000, 0.000000000000}, +{0.001505700000, 0.000586440000, 0.000000000000}, +{0.001044760000, 0.000407410000, 0.000000000000}, +{0.000727450000, 0.000284041000, 0.000000000000}, +{0.000508258000, 0.000198730000, 0.000000000000}, +{0.000356380000, 0.000139550000, 0.000000000000}, +{0.000250969000, 0.000098428000, 0.000000000000}, +{0.000177730000, 0.000069819000, 0.000000000000}, +{0.000126390000, 0.000049737000, 0.000000000000}, +{0.000090151000, 0.000035540500, 0.000000000000}, +{0.000064525800, 0.000025486000, 0.000000000000}, +{0.000046339000, 0.000018338400, 0.000000000000}, +{0.000033411700, 0.000013249000, 0.000000000000}, +{0.000024209000, 0.000009619600, 0.000000000000}, +{0.000017611500, 0.000007012800, 0.000000000000}, +{0.000012855000, 0.000005129800, 0.000000000000}, +{0.000009413630, 0.000003764730, 0.000000000000}, +{0.000006913000, 0.000002770810, 0.000000000000}, +{0.000005093470, 0.000002046130, 0.000000000000}, +{0.000003767100, 0.000001516770, 0.000000000000}, +{0.000002795310, 0.000001128090, 0.000000000000}, +{0.000002082000, 0.000000842160, 0.000000000000}, +{0.000001553140, 0.000000629700, 0.000000000000} +}; + + + ColorTemp::ColorTemp (double t, double g, double e, const std::string &m) : temp(t), green(g), equal(e), method(m) { clip (temp, green, equal); @@ -395,6 +499,618 @@ const double ColorTemp::ColorchechGreE2_spect[97] = { 0.4297, 0.4837, 0.5142, 0.5446, 0.5541, 0.5636, 0.5608, 0.5579, 0.5480, 0.5381, 0.5258, 0.5135, 0.4959, 0.4783, 0.4570, 0.4356, 0.4124, 0.3891, 0.3710, 0.3529, 0.3425, 0.3320, 0.3266, 0.3211, 0.3180, 0.3149, 0.3129, 0.3108, 0.3123, 0.3137, 0.3193, 0.3248, 0.3335, 0.3422, 0.3518, 0.3613, 0.3693, 0.3772, 0.3810, 0.3847, 0.3838, 0.3829, 0.3838, 0.3847, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 }; +const double ColorTemp::ColorGreenM25_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0758, 0.0614, 0.0662, 0.0591, 0.0648, 0.0633, 0.0671, 0.0613, 0.0621, 0.0610, 0.0680, 0.0690, 0.0784, 0.0830, 0.0920, 0.1070, 0.1231, 0.1423, 0.1607, 0.1731, 0.1816, 0.1911, 0.1951, 0.1986, 0.1915, 0.1889, + 0.1758, 0.1673, 0.1606, 0.1505, 0.1384, 0.1317, 0.1230, 0.1149, 0.1081, 0.0992, 0.0882, 0.0785, 0.0709, 0.0629, 0.0550, 0.0502, 0.0486, 0.0474, 0.0445, 0.0434, 0.0429, 0.0423, 0.0411, 0.0405, 0.0397, 0.0387, 0.0399, 0.0398, 0.0398, 0.0407, 0.0408, 0.0426, 0.0445, 0.0443, 0.0468, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//0 658 45 0 0 131 98 84 123 104 131 112 121 121 139 128 148 199 296 389 476 689 945 1132 1326 1490 1674 1741 1775 1868 1914 1928 1961 1972 1992 2045 2064 2053 2048 2072 2086 2081 2069 2056 2073 2096 2114 2067 2089 2100 2061 2019 1983 1971 1961 2016 1956 1946 1922 1983 1991 +const double ColorTemp::ColorYellowkeltano_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0, 0.0658, 0.0045, 0.0, 0.0, 0.0131, 0.0098, 0.0084, 0.0123, 0.0104, 0.0131, 0.0112, 0.0121, 0.0121, 0.0139, + 0.0128, 0.0148, 0.0199, 0.0296, 0.0389, 0.0476, 0.0689, 0.0945, 0.1132, 0.1326, 0.1490, 0.1674, 0.1741, 0.1775, 0.1868, + 0.1914, 0.1928, 0.1961, 0.1972, 0.1992, 0.2045, 0.2064, 0.2053, 0.2048, 0.2072, 0.2086, 0.2081, 0.2069, 0.2056, 0.2073, + 0.2096, 0.2114, 0.2067, 0.2089, 0.2100, 0.2061, 0.2019, 0.1983, 0.1971, 0.1961, 0.2016, 0.1956, 0.1946, 0.1922, 0.1983, 0.1991, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::ColorGreenalsi_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1732, 0.0292, 0.0315, 0.0533, 0.0469, 0.0359, 0.0404, 0.0356, 0.0345, 0.0374, 0.0348, 0.0336, 0.0332, 0.0333, 0.0342, + 0.0330, 0.0350, 0.0343, 0.0354, 0.0371, 0.0399, 0.0426, 0.0497, 0.0541, 0.0616, 0.0701, 0.0750, 0.0764, 0.0783, 0.0794, + 0.0784, 0.0732, 0.0708, 0.0652, 0.0612, 0.0595, 0.0570, 0.0531, 0.0507, 0.0501, 0.0488, 0.0458, 0.0437, 0.0420, 0.0436, + 0.0424, 0.0417, 0.0389, 0.0380, 0.0378, 0.0371, 0.0350, 0.0333, 0.0350, 0.0394, 0.0379, 0.0446, 0.0491, 0.0575, 0.0734, 0.0953, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//1890 1097 855 899 987 881 807 804 787 691 643 549 465 404 385 302 244 195 165 159 123 129 108 111 114 126 126 134 162 170 213 248 279 351 412 566 752 909 1069 1270 1526 +//1707 1858 1999 2112 2293 2422 2471 2611 2718 2710 2778 2807 2825 2856 2909 2901 2974 3042 3044 3075 +const double ColorTemp::ColorRedpetunia_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1890, 0.1097, 0.0855, 0.0899, 0.0987, 0.0881, 0.0807, 0.0804, 0.0787, 0.0691, 0.0643, 0.0549, 0.0465, 0.0404, 0.0385, + 0.0302, 0.0244, 0.0195, 0.0165, 0.0159, 0.0123, 0.0129, 0.0108, 0.0111, 0.0114, 0.0126, 0.0126, 0.0134, 0.0162, 0.0170, + 0.0213, 0.0248, 0.0279, 0.0351, 0.0412, 0.0566, 0.0752, 0.0909, 0.1069, 0.1270, 0.1526, 0.1707, 0.1858, 0.1999, 0.2112, + 0.2293, 0.2422, 0.2471, 0.2611, 0.2718, 0.2710, 0.2778, 0.2807, 0.2825, 0.2856, 0.2909, 0.2901, 0.2974, 0.3042, 0.3044, 0.3075, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//0.1588 0.1980 0.2789 0.4585 0.6059 0.6609 0.6674 0.6599 0.6551 0.6472 0.6423 0.6485 0.6515 0.6379 0.6193 0.6121 0.6026 0.5678 0.5310 0.5245 0.5305 0.5324 0.5262 0.5219 0.5247 0.5312 0.5436 0.5634 0.5832 0.5943 0.5953 0.5902 0.5805 0.5754 0.5901 0.6262 + +const double ColorTemp::JDC468_B14_75Redspect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1588, 0.1780, 0.1980, 0.2310, 0.2789, 0.3213, 0.4585, 0.5324, 0.6059, 0.6334, 0.6609, 0.6630, 0.6674, 0.6640, 0.6599, 0.6600, 0.6551, 0.6532, 0.6472, 0.6450, + 0.6423, 0.6467, 0.6485, 0.6500, 0.6515, 0.6456, 0.6379, 0.6285, 0.6193, 0.6150, 0.6121, 0.6056, 0.6026, 0.5812, 0.5678, 0.5490, 0.5310, 0.5307, 0.5245, 0.5300, + 0.5305, 0.5310, 0.5324, 0.5298, 0.5262, 0.5230, 0.5219, 0.5231, 0.5247, 0.5280, 0.5312, 0.5364, 0.5436, 0.5550, 0.5634, 0.5731, 0.5832, 0.5901, 0.5943, 0.5950, + 0.5953, 0.5926, 0.5902, 0.5850, 0.5805, 0.5770, 0.5754, 0.6012, 0.6262, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +const double ColorTemp::ColorRedkurttu_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0979, 0.1536, 0.0745, 0.1145, 0.0937, 0.0996, 0.0972, 0.0924, 0.0875, 0.0878, 0.0826, 0.0766, 0.0658, 0.0599, 0.0545, + 0.0509, 0.0443, 0.0381, 0.0356, 0.0327, 0.0318, 0.0304, 0.0295, 0.0288, 0.0285, 0.0271, 0.0281, 0.0282, 0.0278, 0.0280, + 0.0296, 0.0309, 0.0324, 0.0342, 0.0343, 0.0376, 0.0419, 0.0464, 0.0520, 0.0634, 0.0747, 0.0905, 0.1093, 0.1167, 0.1264, + 0.1439, 0.1650, 0.1928, 0.2183, 0.2380, 0.2537, 0.2754, 0.2893, 0.3009, 0.3115, 0.3213, 0.3173, 0.3222, 0.3237, 0.3192, 0.3210, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#light red flower (lupiini) +//1792 1553 1684 1882 1909 1847 2053 2084 2045 2052 2039 2084 2041 2044 2007 1984 1906 1876 1886 1855 1859 1875 1816 1800 1811 1780 1802 1816 1838 1915 1973 2018 2083 2114 2133 2226 2304 2385 2458 2494 2571 2689 2738 2774 2734 2759 2781 2831 2844 2857 2878 2876 2884 2920 2932 2860 2894 2934 2925 2928 2921 +const double ColorTemp::ColorRedlupiini_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1792, 0.1553, 0.1684, 0.1882, 0.1909, 0.1847, 0.2053, 0.2084, 0.2045, 0.2052, 0.2039, 0.2084, 0.2041, 0.2044, 0.2007, 0.1984, 0.1906, 0.1876, + 0.1886, 0.1855, 0.1859, 0.1875, 0.1816, 0.1800, 0.1811, 0.1780, 0.1802, 0.1816, 0.1838, 0.1915, 0.1973, 0.2018, 0.2083, 0.2114, 0.2133, 0.2226, + 0.2304, 0.2385, 0.2458, 0.2494, 0.2571, 0.2689, 0.2738, 0.2774, 0.2734, 0.2759, 0.2781, 0.2831, 0.2844, 0.2857, 0.2878, 0.2876, 0.2884, 0.2920, + 0.2932, 0.2860, 0.2894, 0.2934, 0.2925, 0.2928, 0.2921, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//#red flower (hevosminttu) +//1280 706 612 462 391 339 253 285 261 264 239 208 201 186 185 161 156 149 146 148 161 144 143 151 147 146 139 148 173 185 185 197 222 238 283 322 384 439 519 633 792 922 1061 1186 1235 1342 1538 1691 1839 1974 2024 2098 2128 2187 2204 2217 2267 2299 2339 2331 2322 +const double ColorTemp::ColorRedhevosminttu_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1280, 0.0706, 0.0612, 0.0462, 0.0391, 0.0339, 0.0253, 0.0285, 0.0261, 0.0264, 0.0239, 0.0208, 0.0201, 0.0186, 0.0185, 0.0161, 0.0156, 0.0149, + 0.0146, 0.0148, 0.0161, 0.0144, 0.0143, 0.0151, 0.0147, 0.0146, 0.0139, 0.0148, 0.0173, 0.0185, 0.0185, 0.0197, 0.0222, 0.0238, 0.0283, 0.0322, + 0.0384, 0.0439, 0.0519, 0.0633, 0.0792, 0.0922, 0.1061, 0.1186, 0.1235, 0.1342, 0.1538, 0.1691, 0.1839, 0.1974, 0.2024, 0.2098, 0.2128, 0.2187, 0.2204, + 0.2217, 0.2267, 0.2299, 0.2339, 0.2331, 0.2322, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//#red flower (neilikka) +//0 0 394 0 245 95 174 149 194 171 181 175 172 167 147 137 107 108 100 87 93 87 83 77 80 67 72 64 83 84 88 90 91 94 114 133 178 241 309 419 612 823 992 1153 1222 1366 1503 1658 1767 1841 1884 1992 2035 2007 2009 2045 2065 2229 2290 2395 2449 +const double ColorTemp::ColorRedneilikka_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0, 0.0, 0.0394, 0.0, 0.0245, 0.0095, 0.0174, 0.0149, 0.0194, 0.0171, 0.0181, 0.0175, 0.0172, 0.0167, 0.0147, 0.0137, 0.0107, 0.0108, 0.0100, + 0.0087, 0.0093, 0.0087, 0.0083, 0.0077, 0.0080, 0.0067, 0.0072, 0.0064, 0.0083, 0.0084, 0.0088, 0.0090, 0.0091, 0.0094, 0.0114, 0.0133, + 0.0178, 0.0241, 0.0309, 0.0419, 0.0612, 0.0823, 0.0992, 0.1153, 0.1222, 0.1366, 0.1503, 0.1658, 0.1767, 0.1841, 0.1884, 0.1992, 0.2035, 0.2007, 0.2009, + 0.2045, 0.2065, 0.2229, 0.2290, 0.2395, 0.2449, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#red petal (pelargonia) +//2529 2048 2087 2698 2452 2372 2531 2475 2296 2294 2159 2111 1986 1898 1854 1729 1586 1501 1392 1332 1343 1255 1217 1182 1183 1203 1230 1277 1381 1474 1615 1762 1876 2028 2214 2464 2657 2919 3051 3172 3293 3421 3395 3494 3438 3495 3506 3490 3454 3487 3431 3452 3484 3438 3422 3368 3325 3441 3356 3432 3320 +const double ColorTemp::ColorRedpelagornia_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2529, 0.2048, 0.2087, 0.2698, 0.2452, 0.2372, 0.2531, 0.2475, 0.2296, 0.2294, 0.2159, 0.2111, 0.1986, 0.1898, 0.1854, 0.1729, 0.1586, 0.1501, 0.1392, 0.1332, 0.1343, + 0.1255, 0.1217, 0.1182, 0.1183, 0.1203, 0.1230, 0.1277, 0.1381, 0.1474, 0.1615, 0.1762, 0.1876, 0.2028, 0.2214, 0.2464, 0.2657, 0.2919, 0.3051, 0.3172, 0.3293, 0.3421, + 0.3395, 0.3494, 0.3438, 0.3495, 0.3506, 0.3490, 0.3454, 0.3487, 0.3431, 0.3452, 0.3484, 0.3438, 0.3422, 0.3368, 0.3325, 0.3441, 0.3356, 0.3432, 0.3320, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#red flower (talvio) +//3131 2199 2559 2540 2844 2530 2694 2765 2594 2673 2617 2629 2491 2384 2308 2256 2081 1973 1857 1752 1719 1652 1527 1477 1459 1386 1341 1283 1318 1334 1354 1424 1495 1543 1634 1773 1950 2129 2272 2431 2642 2827 2941 3045 3082 3158 3216 3307 3364 3388 3387 3517 3573 3501 3499 3523 3495 3606 3493 3518 3522 +const double ColorTemp::ColorRedtalvio_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.3131, 0.2199, 0.2559, 0.2540, 0.2844, 0.2530, 0.2694, 0.2765, 0.2594, 0.2673, 0.2617, 0.2629, 0.2491, 0.2384, 0.2308, 0.2256, 0.2081, 0.1973, 0.1857, 0.1752, 0.1719, + 0.1652, 0.1527, 0.1477, 0.1459, 0.1386, 0.1341, 0.1283, 0.1318, 0.1334, 0.1354, 0.1424, 0.1495, 0.1543, 0.1634, 0.1773, 0.1950, 0.2129, 0.2272, 0.2431, 0.2642, 0.2827, + 0.2941, 0.3045, 0.3082, 0.3158, 0.3216, 0.3307, 0.3364, 0.3388, 0.3387, 0.3517, 0.3573, 0.3501, 0.3499, 0.3523, 0.3495, 0.3606, 0.3493, 0.3518, 0.3522, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 + +}; + +//#brown dry leaf (poimulehti) +//964 520 223 244 261 247 196 199 200 207 202 198 209 204 207 222 205 218 213 212 224 218 230 235 251 250 245 250 263 273 271 275 281 264 274 288 287 307 303 307 323 304 335 335 346 345 347 348 370 364 380 393 384 407 419 421 419 433 431 461 465 +//RIs 67 +const double ColorTemp::ColorBrownpoimulehti_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0964, 0.0520, 0.0223, 0.0244, 0.0261, 0.0247, 0.0196, 0.0199, 0.0200, 0.0207, 0.0202, 0.0198, 0.0209, 0.0204, 0.0207, 0.0222, 0.0205, 0.0218, 0.0213, + 0.0212, 0.0224, 0.0218, 0.0230, 0.0235, 0.0251, 0.0250, 0.0245, 0.0250, 0.0263, 0.0273, 0.0271, 0.0275, 0.0281, 0.0264, 0.0274, 0.0288, 0.0287, 0.0307, + 0.0303, 0.0307, 0.0323, 0.0304, 0.0335, 0.0335, 0.0346, 0.0345, 0.0347, 0.0348, 0.0370, 0.0364, 0.0380, 0.0393, 0.0384, 0.0407, + 0.0419, 0.0421, 0.0419, 0.0433, 0.0431, 0.0461, 0.0465, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#orange leaf (koristepensas, tuntematon) +//241 195 223 489 574 565 634 605 574 613 645 636 644 628 621 603 614 654 676 719 776 795 862 879 918 918 955 980 1013 1055 1132 1225 1258 1362 1427 1579 1796 1936 2079 2258 2440 2597 2728 2790 2777 2857 2923 2991 3031 3040 3037 3094 3066 3023 3093 3044 3082 3085 3147 3226 3192 +const double ColorTemp::ColorOrangetuntematon_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0241, 0.0195, 0.0223, 0.0489, 0.0574, 0.0565, 0.0634, 0.0605, 0.0574, 0.0613, 0.0645, 0.0636, 0.0644, 0.0628, 0.0621, 0.0603, 0.0614, 0.0654, 0.0676, + 0.0719, 0.0776, 0.0795, 0.0862, 0.0879, 0.0918, 0.0918, 0.0955, 0.0980, 0.1013, 0.1055, 0.1132, 0.1225, 0.1258, 0.1362, 0.1427, 0.1579, 0.1796, 0.1936, 0.2079, + 0.2258, 0.2440, 0.2597, 0.2728, 0.2790, 0.2777, 0.2857, 0.2923, 0.2991, 0.3031, 0.3040, 0.3037, 0.3094, 0.3066, 0.3023, 0.3093, 0.3044, 0.3082, 0.3085, 0.3147, 0.3226, 0.3192, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//,#orange leaf (lehmus) +//1062 866 443 544 496 485 492 458 450 425 458 477 497 461 451 481 454 500 515 538 529 593 638 670 686 711 718 729 741 760 796 833 895 958 1016 1128 1246 1344 1450 1505 1596 1636 1621 1631 1627 1628 1658 1583 1486 1415 1322 1265 1159 1062 975 974 1063 1326 1736 2141 2568 +const double ColorTemp::ColorOrangetlehmus_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1062, 0.0866, 0.0443, 0.0544, 0.0496, 0.0485, 0.0492, 0.0458, 0.0450, 0.0425, 0.0458, 0.0477, 0.0497, 0.0461, 0.0451, 0.0481, 0.0454, 0.0500, 0.0515, + 0.0538, 0.0529, 0.0593, 0.0638, 0.0670, 0.0686, 0.0711, 0.0718, 0.0729, 0.0741, 0.0760, 0.0796, 0.0833, 0.0895, 0.0958, 0.1016, 0.1128, 0.1246, 0.1344, 0.1450, + 0.1505, 0.1596, 0.1636, 0.1621, 0.1631, 0.1627, 0.1628, 0.1658, 0.1583, 0.1486, 0.1415, 0.1322, 0.1265, 0.1159, 0.1062, 0.0975, 0.0974, 0.1063, 0.1326, 0.1736, 0.2141, 0.2568, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#orange leaf (vaahtera) +//1517 551 664 659 521 585 460 385 424 389 375 374 359 380 371 373 379 387 378 394 405 416 463 496 536 542 577 579 619 642 678 710 777 829 894 1035 1174 1334 1484 1611 1798 1941 2012 2065 2135 2229 2286 2317 2332 2357 2323 2330 2292 2236 2137 2093 2180 2240 2368 2487 2528 +const double ColorTemp::ColorOrangvaahtera_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1517, 0.0551, 0.0664, 0.0659, 0.0521, 0.0585, 0.0460, 0.0385, 0.0424, 0.0389, 0.0375, 0.0374, 0.0359, 0.0380, 0.0371, 0.0373, 0.0379, 0.0387, 0.0378, + 0.0394, 0.0405, 0.0416, 0.0463, 0.0496, 0.0536, 0.0542, 0.0577, 0.0579, 0.0619, 0.0642, 0.0678, 0.0710, 0.0777, 0.0829, 0.0894, 0.1035, 0.1174, 0.1334, 0.1484, + 0.1611, 0.1798, 0.1941, 0.2012, 0.2065, 0.2135, 0.2229, 0.2286, 0.2317, 0.2332, 0.2357, 0.2323, 0.2330, 0.2292, 0.2236, 0.2137, 0.2093, 0.2180, 0.2240, 0.2368, 0.2487, 0.2528, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#brown dry leaf (lehmus) +//758 236 148 430 347 435 438 495 439 454 472 471 461 459 458 479 492 482 499 513 520 545 567 594 623 647 698 717 744 792 803 834 864 876 916 932 963 1013 1025 1060 1099 1118 1153 1175 1207 1242 1268 1266 1284 1305 1305 1304 1353 1360 1330 1332 1413 1502 1610 1682 1737 +const double ColorTemp::ColorBrownlehmus_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0758, 0.0236, 0.0148, 0.0430, 0.0347, 0.0435, 0.0438, 0.0495, 0.0439, 0.0454, 0.0472, 0.0471, 0.0461, 0.0459, 0.0458, 0.0479, 0.0492, 0.0482, 0.0499, 0.0513, + 0.0520, 0.0545, 0.0567, 0.0594, 0.0623, 0.0647, 0.0698, 0.0717, 0.0744, 0.0792, 0.0803, 0.0834, 0.0864, 0.0876, 0.0916, 0.0932, 0.0963, 0.1013, 0.1025, 0.1060, + 0.1099, 0.1118, 0.1153, 0.1175, 0.1207, 0.1242, 0.1268, 0.1266, 0.1284, 0.1305, 0.1305, 0.1304, 0.1353, 0.1360, 0.1330, 0.1332, 0.1413, 0.1502, 0.1610, 0.1682, 0.1737, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#brown moss (nuotiosammal) +//482 260 178 92 104 88 92 40 43 52 58 64 70 63 67 67 62 76 82 82 91 96 104 116 135 141 142 155 168 179 198 199 193 201 212 218 226 240 242 238 255 265 277 266 265 283 289 275 289 277 291 288 277 252 262 260 264 299 375 411 446 +const double ColorTemp::ColorBrownuotiosammal_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0482, 0.0260, 0.0178, 0.0092, 0.0104, 0.0088, 0.0092, 0.0040, 0.0043, 0.0052, 0.0058, 0.0064, 0.0070, 0.0063, 0.0067, 0.0067, 0.0062, 0.0076, 0.0082, 0.0082, 0.0091, 0.0096, + 0.0104, 0.0116, 0.0135, 0.0141, 0.0142, 0.0155, 0.0168, 0.0179, 0.0198, 0.0199, 0.0193, 0.0201, 0.0212, 0.0218, 0.0226, 0.0240, 0.0242, 0.0238, 0.0255, 0.0265, + 0.0277, 0.0266, 0.0265, 0.0283, 0.0289, 0.0275, 0.0289, 0.0277, 0.0291, 0.0288, 0.0277, 0.0252, 0.0262, 0.0260, 0.0264, 0.0299, 0.0375, 0.0411, 0.0446, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#black soil +//0 0 89 122 52 53 104 127 130 134 137 137 134 136 138 139 134 140 142 148 154 153 152 150 151 156 153 166 154 171 163 163 166 166 169 169 166 174 174 170 170 168 176 177 176 174 179 180 180 183 177 193 178 187 194 193 182 196 184 195 195 +const double ColorTemp::ColorBlacksoil_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0, 0.0, 0.0089, 0.0122, 0.0052, 0.0053, 0.0104, 0.0127, 0.0130, 0.0134, 0.0137, 0.0137, 0.0134, 0.0136, 0.0138, 0.0139, 0.0134, 0.0140, 0.0142, 0.0148, 0.0154, 0.0153, + 0.0152, 0.0150, 0.0151, 0.0156, 0.0153, 0.0166, 0.0154, 0.0171, 0.0163, 0.0163, 0.0166, 0.0166, 0.0169, 0.0169, 0.0166, 0.0174, 0.0174, 0.0170, 0.0170, 0.0168, 0.0176, 0.0177, + 0.0176, 0.0174, 0.0179, 0.0180, 0.0180, 0.0183, 0.0177, 0.0193, 0.0178, 0.0187, 0.0194, 0.0193, 0.0182, 0.0196, 0.0184, 0.0195, 0.0195, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#black, dry leaf (pihlaja) +//0 79 111 172 174 201 214 211 207 207 191 200 196 206 196 194 203 207 204 208 210 212 211 208 209 219 222 224 231 241 232 244 249 250 267 264 262 269 282 277 289 284 279 302 289 308 313 315 310 325 313 319 356 340 331 347 356 352 364 373 352 +const double ColorTemp::ColorBlackpihlaja[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0, 0.0079, 0.0111, 0.0172, 0.0174, 0.0201, 0.0214, 0.0211, 0.0207, 0.0207, 0.0191, 0.0200, 0.0196, 0.0206, 0.0196, 0.0194, 0.0203, 0.0207, 0.0204, 0.0208, 0.0210, 0.0212, + 0.0211, 0.0208, 0.0209, 0.0219, 0.0222, 0.0224, 0.0231, 0.0241, 0.0232, 0.0244, 0.0249, 0.0250, 0.0267, 0.0264, 0.0262, 0.0269, 0.0282, 0.0277, 0.0289, 0.0284, 0.0279, 0.0302, + 0.0289, 0.0308, 0.0313, 0.0315, 0.0310, 0.0325, 0.0313, 0.0319, 0.0356, 0.0340, 0.0331, 0.0347, 0.0356, 0.0352, 0.0364, 0.0373, 0.0352, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + + +//#gray lichen (nahkajaekaelae) +//1204 585 1113 733 600 653 715 685 726 682 713 691 719 691 683 693 711 715 701 700 720 697 706 696 723 714 726 738 729 735 737 739 742 746 746 761 743 735 722 717 728 749 721 712 705 737 733 758 780 785 775 771 755 744 743 742 755 779 849 940 1042 +//RIS 74 +const double ColorTemp::ColorGraynahjajaekaelae_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1204, 0.0585, 0.1113, 0.0733, 0.0600, 0.0653, 0.0715, 0.0685, 0.0726, 0.0682, 0.0713, 0.0691, 0.0719, 0.0691, 0.0683, 0.0693, 0.0711, 0.0715, 0.0701, 0.0700, + 0.0720, 0.0697, 0.0706, 0.0696, 0.0723, 0.0714, 0.0726, 0.0738, 0.0729, 0.0735, 0.0737, 0.0739, 0.0742, 0.0746, 0.0746, 0.0761, 0.0743, 0.0735, 0.0722, 0.0717, + 0.0728, 0.0749, 0.0721, 0.0712, 0.0705, 0.0737, 0.0733, 0.0758, 0.0780, 0.0785, 0.0775, 0.0771, 0.0755, 0.0744, 0.0743, 0.0742, 0.0755, 0.0779, 0.0849, 0.0940, 0.1042, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#green moss (nuotiosammal) +//120 65 134 31 209 124 104 96 97 95 76 79 83 93 83 95 95 104 117 127 140 161 214 252 290 310 328 343 347 373 365 351 347 343 311 301 285 283 263 256 255 251 257 235 227 224 233 208 194 186 165 160 151 149 157 161 185 243 309 425 543 +const double ColorTemp::ColorGreennuotisammal_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0120, 0.0065, 0.0134, 0.0031, 0.0209, 0.0124, 0.0104, 0.0096, 0.0097, 0.0095, 0.0076, 0.0079, 0.0083, 0.0093, 0.0083, 0.0095, 0.0095, 0.0104, 0.0117, 0.0127, 0.0140, 0.0161, + 0.0214, 0.0252, 0.0290, 0.0310, 0.0328, 0.0343, 0.0347, 0.0373, 0.0365, 0.0351, 0.0347, 0.0343, 0.0311, 0.0301, 0.0285, 0.0283, 0.0263, 0.0256, 0.0255, 0.0251, + 0.0257, 0.0235, 0.0227, 0.0224, 0.0233, 0.0208, 0.0194, 0.0186, 0.0165, 0.0160, 0.0151, 0.0149, 0.0157, 0.0161, 0.0185, 0.0243, 0.0309, 0.0425, 0.0543, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#green leaf (leskenlehti) +//525 273 0 378 318 164 224 276 316 266 303 290 305 286 290 303 323 323 352 383 405 482 614 743 920 1015 1139 1192 1175 1216 1195 1145 1116 1009 947 867 802 754 741 709 675 625 574 579 561 565 557 511 471 419 399 372 365 395 375 382 458 555 716 1002 1407 +const double ColorTemp::ColorGreenleskenlehti_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0525, 0.0273, 0.0, 0.0378, 0.0318, 0.0164, 0.0224, 0.0276, 0.0316, 0.0266, 0.0303, 0.0290, 0.0305, 0.0286, 0.0290, 0.0303, 0.0323, 0.0323, 0.0352, 0.0383, 0.0405, 0.0482, + 0.0614, 0.0743, 0.0920, 0.1015, 0.1139, 0.1192, 0.1175, 0.1216, 0.1195, 0.1145, 0.1116, 0.1009, 0.0947, 0.0867, 0.0802, 0.0754, 0.0741, 0.0709, 0.0675, 0.0625, + 0.0574, 0.0579, 0.0561, 0.0565, 0.0557, 0.0511, 0.0471, 0.0419, 0.0399, 0.0372, 0.0365, 0.0395, 0.0375, 0.0382, 0.0458, 0.0555, 0.0716, 0.1002, 0.1407, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#green leaf (linnunkaali) +//602 0 267 306 339 335 300 247 292 289 295 298 292 318 312 289 299 307 310 320 350 375 446 499 574 634 698 725 736 754 736 702 668 633 590 551 514 499 467 460 445 424 415 409 399 412 393 380 370 362 366 343 342 350 333 350 364 418 494 670 914 +//RIS 77 +const double ColorTemp::ColorGreenlinnunkaali_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0602, 0.0, 0.0267, 0.0306, 0.0339, 0.0335, 0.0300, 0.0247, 0.0292, 0.0289, 0.0295, 0.0298, 0.0292, 0.0318, 0.0312, 0.0289, 0.0299, 0.0307, 0.0310, 0.0320, + 0.0350, 0.0375, 0.0446, 0.0499, 0.0574, 0.0634, 0.0698, 0.0725, 0.0736, 0.0754, 0.0736, 0.0702, 0.0668, 0.0633, 0.0590, 0.0551, 0.0514, 0.0499, 0.0467, 0.0460, + 0.0445, 0.0424, 0.0415, 0.0409, 0.0399, 0.0412, 0.0393, 0.0380, 0.0370, 0.0362, 0.0366, 0.0343, 0.0342, 0.0350, 0.0333, 0.0350, 0.0364, 0.0418, 0.0494, 0.0670, 0.0914, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//#green leaf (pelto-ohake) +//0 366 360 233 173 179 157 175 206 205 180 179 173 178 187 189 184 171 195 204 193 219 253 297 365 431 467 489 493 516 500 466 426 406 380 343 316 295 276 282 265 253 239 228 226 229 238 237 216 221 219 217 212 219 229 258 284 309 375 487 732 +const double ColorTemp::ColorGreenpelto_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0, 0.0366, 0.0360, 0.0233, 0.0173, 0.0179, 0.0157, 0.0175, 0.0206, 0.0205, 0.0180, 0.0179, 0.0173, 0.0178, 0.0187, 0.0189, 0.0184, 0.0171, 0.0195, 0.0204, 0.0193, 0.0219, + 0.0253, 0.0297, 0.0365, 0.0431, 0.0467, 0.0489, 0.0493, 0.0516, 0.0500, 0.0466, 0.0426, 0.0406, 0.0380, 0.0343, 0.0316, 0.0295, 0.0276, 0.0282, 0.0265, 0.0253, 0.0239, + 0.0228, 0.0226, 0.0229, 0.0238, 0.0237, 0.0216, 0.0221, 0.0219, 0.0217, 0.0212, 0.0219, 0.0229, 0.0258, 0.0284, 0.0309, 0.0375, 0.0487, 0.0732, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#green rod (voikukka), +//2205 1755 1710 1365 1159 1207 1024 1118 1127 1141 1134 1125 1149 1140 1120 1128 1139 1156 1212 1273 1262 1359 1461 1519 1568 1599 1660 1668 1680 1718 1697 1690 1672 1675 1663 1644 1642 1652 1626 1623 1653 1621 1614 1590 1625 1609 1615 1576 1509 1483 1418 1391 1324 1294 1267 1220 1315 1417 1650 1861 2006 +const double ColorTemp::ColorGreenrodvoikukka[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2205, 0.1755, 0.1710, 0.1365, 0.1159, 0.1207, 0.1024, 0.1118, 0.1127, 0.1141, 0.1134, 0.1125, 0.1149, 0.1140, 0.1120, 0.1128, 0.1139, 0.1156, 0.1212, 0.1273, 0.1262, 0.1359, + 0.1461, 0.1519, 0.1568, 0.1599, 0.1660, 0.1668, 0.1680, 0.1718, 0.1697, 0.1690, 0.1672, 0.1675, 0.1663, 0.1644, 0.1642, 0.1652, 0.1626, 0.1623, 0.1653, 0.1621, 0.1614, 0.1590, + 0.1625, 0.1609, 0.1615, 0.1576, 0.1509, 0.1483, 0.1418, 0.1391, 0.1324, 0.1294, 0.1267, 0.1220, 0.1315, 0.1417, 0.1650, 0.1861, 0.2006, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#green leaf (lehmus) +//2362 1024 945 666 617 604 591 580 648 631 656 607 616 653 643 626 643 656 710 753 801 929 1105 1277 1437 1601 1742 1774 1798 1848 1832 1820 1787 1730 1663 1593 1541 1461 1446 1419 1335 1298 1247 1192 1197 1199 1156 1072 1007 942 899 832 824 793 755 801 860 1031 1305 1809 2260 +const double ColorTemp::ColorGreenlehmus[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2362, 0.1024, 0.0945, 0.0666, 0.0617, 0.0604, 0.0591, 0.0580, 0.0648, 0.0631, 0.0656, 0.0607, 0.0616, 0.0653, 0.0643, 0.0626, 0.0643, 0.0656, 0.0710, 0.0753, + 0.0801, 0.0929, 0.1105, 0.1277, 0.1437, 0.1601, 0.1742, 0.1774, 0.1798, 0.1848, 0.1832, 0.1820, 0.1787, 0.1730, 0.1663, 0.1593, 0.1541, 0.1461, 0.1446, 0.1419, 0.1335, 0.1298, + 0.1247, 0.1192, 0.1197, 0.1199, 0.1156, 0.1072, 0.1007, 0.0942, 0.0899, 0.0832, 0.0824, 0.0793, 0.0755, 0.0801, 0.0860, 0.1031, 0.1305, 0.1809, 0.2260, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#green leaf (koristeherukka) +//945 292 315 433 321 294 295 321 278 261 282 272 270 278 285 274 277 268 269 283 275 309 325 389 450 493 551 557 587 585 567 554 515 487 460 424 409 387 353 349 353 333 309 309 312 315 321 298 304 304 281 273 293 311 314 333 355 392 439 595 811 +const double ColorTemp::ColorGreenkoriste[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0945, 0.0292, 0.0315, 0.0433, 0.0321, 0.0294, 0.0295, 0.0321, 0.0278, 0.0261, 0.0282, 0.0272, 0.0270, 0.0278, 0.0285, 0.0274, 0.0277, 0.0268, 0.0269, 0.0283, + 0.0275, 0.0309, 0.0325, 0.0389, 0.0450, 0.0493, 0.0551, 0.0557, 0.0587, 0.0585, 0.0567, 0.0554, 0.0515, 0.0487, 0.0460, 0.0424, 0.0409, 0.0387, 0.0353, 0.0349, + 0.0353, 0.0333, 0.0309, 0.0309, 0.0312, 0.0315, 0.0321, 0.0298, 0.0304, 0.0304, 0.0281, 0.0273, 0.0293, 0.0311, 0.0314, 0.0333, 0.0355, 0.0392, 0.0439, 0.0595, 0.0811, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#green leaf (poimulehti) +//1102 146 630 266 247 261 285 238 273 281 272 260 262 254 274 263 273 278 296 309 322 388 493 607 712 840 953 986 1006 1034 999 981 918 855 794 711 649 627 604 563 531 515 467 450 448 466 445 421 402 385 369 345 346 319 330 359 378 439 578 835 1177 +const double ColorTemp::ColorGreenpoimulehti[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1102, 0.0146, 0.0630, 0.0266, 0.0247, 0.0261, 0.0285, 0.0238, 0.0273, 0.0281, 0.0272, 0.0260, 0.0262, 0.0254, 0.0274, 0.0263, 0.0273, 0.0278, 0.0296, 0.0309, 0.0322, + 0.0388, 0.0493, 0.0607, 0.0712, 0.0840, 0.0953, 0.0986, 0.1006, 0.1034, 0.0999, 0.0981, 0.0918, 0.0855, 0.0794, 0.0711, 0.0649, 0.0627, 0.0604, 0.0563, 0.0531, 0.0515, + 0.0467, 0.0450, 0.0448, 0.0466, 0.0445, 0.0421, 0.0402, 0.0385, 0.0369, 0.0345, 0.0346, 0.0319, 0.0330, 0.0359, 0.0378, 0.0439, 0.0578, 0.0835, 0.1177, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#green leaf (hopeapaju) +//787 512 1260 1032 765 881 994 908 983 985 941 985 971 967 964 937 928 959 973 992 1004 1017 1053 1102 1180 1227 1281 1309 1317 1328 1318 1271 1238 1222 1179 1152 1131 1092 1086 1078 1083 1020 1015 1000 1027 1037 1028 970 962 977 952 963 955 935 980 979 963 1028 1059 1228 1401 +const double ColorTemp::ColorGreenhopeapaju[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0787, 0.0512, 0.1260, 0.1032, 0.0765, 0.0881, 0.0994, 0.0908, 0.0983, 0.0985, 0.0941, 0.0985, 0.0971, 0.0967, 0.0964, 0.0937, 0.0928, 0.0959, 0.0973, 0.0992, 0.1004, + 0.1017, 0.1053, 0.1102, 0.1180, 0.1227, 0.1281, 0.1309, 0.1317, 0.1328, 0.1318, 0.1271, 0.1238, 0.1222, 0.1179, 0.1152, 0.1131, 0.1092, 0.1086, 0.1078, 0.1083, 0.1020, + 0.1015, 0.1000, 0.1027, 0.1037, 0.1028, 0.0970, 0.0962, 0.0977, 0.0952, 0.0963, 0.0955, 0.0935, 0.0980, 0.0979, 0.0963, 0.1028, 0.1059, 0.1228, 0.1401, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#red flower (uuden guinean liisa) +//2288 1861 2364 2229 2783 2842 2842 2923 2902 2990 2828 2871 2772 2723 2639 2558 2424 2315 2169 2094 2064 1964 1865 1739 1680 1624 1548 1457 1424 1408 1434 1451 1492 1528 1597 1755 1951 2147 2367 2648 2986 3236 3393 3596 3665 3786 3879 3915 3926 3994 3987 4017 4026 4112 4067 4125 4139 4121 4050 4040 4095 +const double ColorTemp::ColorReduuden[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2288, 0.1861, 0.2364, 0.2229, 0.2783, 0.2842, 0.2842, 0.2923, 0.2902, 0.2990, 0.2828, 0.2871, 0.2772, 0.2723, 0.2639, 0.2558, 0.2424, 0.2315, 0.2169, 0.2094, 0.2064, + 0.1964, 0.1865, 0.1739, 0.1680, 0.1624, 0.1548, 0.1457, 0.1424, 0.1408, 0.1434, 0.1451, 0.1492, 0.1528, 0.1597, 0.1755, 0.1951, 0.2147, 0.2367, 0.2648, 0.2986, 0.3236, + 0.3393, 0.3596, 0.3665, 0.3786, 0.3879, 0.3915, 0.3926, 0.3994, 0.3987, 0.4017, 0.4026, 0.4112, 0.4067, 0.4125, 0.4139, 0.4121, 0.4050, 0.4040, 0.4095, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#red flower (pajuangervo) +//445 1024 605 833 937 959 1052 1028 1049 1029 1017 975 948 882 865 812 757 718 658 638 628 597 554 523 509 509 485 475 469 492 479 477 490 525 555 597 641 704 756 846 948 1055 1164 1221 1266 1339 1393 1491 1553 1604 1608 1650 1643 1652 1655 1658 1651 1739 1813 1818 1938 +const double ColorTemp::ColorRedpajuan[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0445, 0.1024, 0.0605, 0.0833, 0.0937, 0.0959, 0.1052, 0.1028, 0.1049, 0.1029, 0.1017, 0.0975, 0.0948, 0.0882, 0.0865, 0.0812, 0.0757, 0.0718, 0.0658, 0.0638, 0.0628, 0.0597, + 0.0554, 0.0523, 0.0509, 0.0509, 0.0485, 0.0475, 0.0469, 0.0492, 0.0479, 0.0477, 0.0490, 0.0525, 0.0555, 0.0597, 0.0641, 0.0704, 0.0756, 0.0846, 0.0948, 0.1055, 0.1164, 0.1221, + 0.1266, 0.1339, 0.1393, 0.1491, 0.1553, 0.1604, 0.1608, 0.1650, 0.1643, 0.1652, 0.1655, 0.1658, 0.1651, 0.1739, 0.1813, 0.1818, 0.1938, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#red flower (jaloangervo) +//120 152 512 635 662 538 749 713 743 792 777 785 733 726 728 749 709 674 661 657 645 635 598 570 553 544 545 538 546 514 540 567 585 577 602 651 690 765 836 907 980 1089 1147 1188 1212 1253 1318 1371 1412 1473 1459 1478 1548 1582 1564 1590 1595 1714 1728 1814 1837 +const double ColorTemp::ColorRedjaloan[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0120, 0.0152, 0.0512, 0.0635, 0.0662, 0.0538, 0.0749, 0.0713, 0.0743, 0.0792, 0.0777, 0.0785, 0.0733, 0.0726, 0.0728, 0.0749, 0.0709, 0.0674, 0.0661, 0.0657, 0.0645, 0.0635, + 0.0598, 0.0570, 0.0553, 0.0544, 0.0545, 0.0538, 0.0546, 0.0514, 0.0540, 0.0567, 0.0585, 0.0577, 0.0602, 0.0651, 0.0690, 0.0765, 0.0836, 0.0907, 0.0980, 0.1089, 0.1147, 0.1188, + 0.1212, 0.1253, 0.1318, 0.1371, 0.1412, 0.1473, 0.1459, 0.1478, 0.1548, 0.1582, 0.1564, 0.1590, 0.1595, 0.1714, 0.1728, 0.1814, 0.1837, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#blue flower (ukonhattu) +//801 682 1070 1319 1311 1420 1453 1394 1318 1292 1268 1179 1132 1054 1015 948 846 780 731 709 705 667 621 598 555 522 505 493 498 500 494 471 479 463 450 461 487 515 546 574 555 562 539 558 546 552 567 626 715 807 862 978 1086 1199 1313 1323 1350 1366 1358 1320 1365 +const double ColorTemp::ColorBlueukon[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0801, 0.0682, 0.1070, 0.1319, 0.1311, 0.1420, 0.1453, 0.1394, 0.1318, 0.1292, 0.1268, 0.1179, 0.1132, 0.1054, 0.1015, 0.0948, 0.0846, 0.0780, 0.0731, 0.0709, 0.0705, 0.0667, + 0.0621, 0.0598, 0.0555, 0.0522, 0.0505, 0.0493, 0.0498, 0.0500, 0.0494, 0.0471, 0.0479, 0.0463, 0.0450, 0.0461, 0.0487, 0.0515, 0.0546, 0.0574, 0.0555, 0.0562, 0.0539, 0.0558, + 0.0546, 0.0552, 0.0567, 0.0626, 0.0715, 0.0807, 0.0862, 0.0978, 0.1086, 0.1199, 0.1313, 0.1323, 0.1350, 0.1366, 0.1358, 0.1320, 0.1365, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#blue flower (orvokki) +//292 528 645 1000 932 1439 1752 1947 2077 2158 2169 2153 2164 2132 2091 1993 1916 1876 1803 1702 1659 1554 1503 1425 1330 1229 1186 1134 1065 1031 1014 993 989 980 939 936 945 995 1055 1104 1180 1247 1284 1343 1349 1403 1458 1538 1634 1790 1880 2006 2218 2396 2556 2612 2735 2811 2765 2840 2877 +const double ColorTemp::ColorBlueorvokki[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0292, 0.0528, 0.0645, 0.1000, 0.0932, 0.1439, 0.1752, 0.1947, 0.2077, 0.2158, 0.2169, 0.2153, 0.2164, 0.2132, 0.2091, 0.1993, 0.1916, 0.1876, 0.1803, 0.1702, 0.1659, 0.1554, + 0.1503, 0.1425, 0.1330, 0.1229, 0.1186, 0.1134, 0.1065, 0.1031, 0.1014, 0.0993, 0.0989, 0.0980, 0.0939, 0.0936, 0.0945, 0.0995, 0.1055, 0.1104, 0.1180, 0.1247, 0.1284, 0.1343, + 0.1349, 0.1403, 0.1458, 0.1538, 0.1634, 0.1790, 0.1880, 0.2006, 0.2218, 0.2396, 0.2556, 0.2612, 0.2735, 0.2811, 0.2765, 0.2840, 0.2877, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#blue flower (malvikki) +//1062 528 749 571 512 538 455 445 431 384 353 299 249 212 190 162 123 105 90 81 83 75 78 72 59 56 61 54 71 69 70 62 63 65 70 74 78 73 76 87 90 104 119 119 131 145 156 184 225 255 314 414 538 669 849 1068 1247 1467 1701 1885 2032 +const double ColorTemp::ColorBluemalvikki[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1062, 0.0528, 0.0749, 0.0571, 0.0512, 0.0538, 0.0455, 0.0445, 0.0431, 0.0384, 0.0353, 0.0299, 0.0249, 0.0212, 0.0190, 0.0162, 0.0123, 0.0105, 0.0090, 0.0081, 0.0083, 0.0075, + 0.0078, 0.0072, 0.0059, 0.0056, 0.0061, 0.0054, 0.0071, 0.0069, 0.0070, 0.0062, 0.0063, 0.0065, 0.0070, 0.0074, 0.0078, 0.0073, 0.0076, 0.0087, 0.0090, 0.0104, 0.0119, 0.0119, + 0.0131, 0.0145, 0.0156, 0.0184, 0.0225, 0.0255, 0.0314, 0.0414, 0.0538, 0.0669, 0.0849, 0.1068, 0.1247, 0.1467, 0.1701, 0.1885, 0.2032, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#black dry leaf (maitohorsma) +//256 0 172 356 213 270 203 203 195 208 202 201 210 210 203 204 209 203 209 201 205 201 194 210 206 197 203 198 207 201 204 202 198 200 198 197 186 203 202 198 200 208 206 231 235 223 244 254 278 289 297 309 338 335 338 368 412 524 686 926 1185 +const double ColorTemp::ColorBlackmaito[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0256, 0.0, 0.0172, 0.0356, 0.0213, 0.0270, 0.0203, 0.0203, 0.0195, 0.0208, 0.0202, 0.0201, 0.0210, 0.0210, 0.0203, 0.0204, 0.0209, 0.0203, 0.0209, 0.0201, 0.0205, 0.0201, + 0.0194, 0.0210, 0.0206, 0.0197, 0.0203, 0.0198, 0.0207, 0.0201, 0.0204, 0.0202, 0.0198, 0.0200, 0.0198, 0.0197, 0.0186, 0.0203, 0.0202, 0.0198, 0.0200, 0.0208, 0.0206, 0.0231, + 0.0235, 0.0223, 0.0244, 0.0254, 0.0278, 0.0289, 0.0297, 0.0309, 0.0338, 0.0335, 0.0338, 0.0368, 0.0412, 0.0524, 0.0686, 0.0926, 0.1185, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#orange berry (pihlaja) +//945 731 585 433 247 408 266 314 293 305 289 288 280 297 262 298 277 274 291 293 285 303 300 310 324 336 364 377 426 465 499 561 602 667 741 890 1028 1164 1275 1465 1602 1640 1695 1744 1812 1837 1859 1805 1791 1822 1796 1751 1715 1655 1575 1600 1560 1618 1666 1740 1838 +const double ColorTemp::ColorOrangpihlaja[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0945, 0.0731, 0.0585, 0.0433, 0.0247, 0.0408, 0.0266, 0.0314, 0.0293, 0.0305, 0.0289, 0.0288, 0.0280, 0.0297, 0.0262, 0.0298, 0.0277, 0.0274, 0.0291, 0.0293, 0.0285, 0.0303, + 0.0300, 0.0310, 0.0324, 0.0336, 0.0364, 0.0377, 0.0426, 0.0465, 0.0499, 0.0561, 0.0602, 0.0667, 0.0741, 0.0890, 0.1028, 0.1164, 0.1275, 0.1465, 0.1602, 0.1640, 0.1695, 0.1744, + 0.1812, 0.1837, 0.1859, 0.1805, 0.1791, 0.1822, 0.1796, 0.1751, 0.1715, 0.1655, 0.1575, 0.1600, 0.1560, 0.1618, 0.1666, 0.1740, 0.1838, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#green flower (lehmus=linden) +//2677 1682 1170 1032 1085 816 728 755 833 832 813 845 857 884 855 882 914 997 1084 1179 1231 1437 1661 1873 2048 2209 2378 2408 2442 2509 2503 2452 2457 2418 2383 2348 2277 2213 2221 2169 2146 2048 1977 1960 2000 1993 1961 1899 1784 1748 1625 1517 1389 1260 1165 1143 1244 1522 1870 2324 2586 +//RIS 81 +const double ColorTemp::ColorGreenlinden[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2677, 0.1682, 0.1170, 0.1032, 0.1085, 0.0816, 0.0728, 0.0755, 0.0833, 0.0832, 0.0813, 0.0845, 0.0857, 0.0884, 0.0855, 0.0882, 0.0914, 0.0997, 0.1084, 0.1179, 0.1231, 0.1437, + 0.1661, 0.1873, 0.2048, 0.2209, 0.2378, 0.2408, 0.2442, 0.2509, 0.2503, 0.2452, 0.2457, 0.2418, 0.2383, 0.2348, 0.2277, 0.2213, 0.2221, 0.2169, 0.2146, 0.2048, 0.1977, 0.1960, + 0.2000, 0.1993, 0.1961, 0.1899, 0.1784, 0.1748, 0.1625, 0.1517, 0.1389, 0.1260, 0.1165, 0.1143, 0.1244, 0.1522, 0.1870, 0.2324, 0.2586, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#yellow petal (lehmus) +//1890 1097 900 832 814 799 758 853 803 808 833 862 916 943 960 969 1039 1162 1283 1370 1427 1529 1689 1781 1894 1950 2105 2118 2140 2185 2191 2199 2234 2266 2263 2297 2328 2312 2298 2332 2344 2312 2288 2347 2384 2390 2358 2280 2306 2315 2310 2253 2274 2271 2242 2292 2254 2208 2319 2314 2264 +const double ColorTemp::ColorYellowlehmus[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1890, 0.1097, 0.0900, 0.0832, 0.0814, 0.0799, 0.0758, 0.0853, 0.0803, 0.0808, 0.0833, 0.0862, 0.0916, 0.0943, 0.0960, 0.0969, 0.1039, 0.1162, 0.1283, 0.1370, 0.1427, + 0.1529, 0.1689, 0.1781, 0.1894, 0.1950, 0.2105, 0.2118, 0.2140, 0.2185, 0.2191, 0.2199, 0.2234, 0.2266, 0.2263, 0.2297, 0.2328, 0.2312, 0.2298, 0.2332, 0.2344, 0.2312, 0.2288, + 0.2347, 0.2384, 0.2390, 0.2358, 0.2280, 0.2306, 0.2315, 0.2310, 0.2253, 0.2274, 0.2271, 0.2242, 0.2292, 0.2254, 0.2208, 0.2319, 0.2314, 0.2264, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#yellow flower (suikeroalpi) +//2048 1666 1140 1210 699 680 615 566 567 561 609 585 614 572 599 575 636 730 982 1194 1360 1766 2222 2558 2849 3048 3201 3395 3395 3484 3576 3623 3606 3672 3651 3634 3647 3669 3715 3660 3720 3692 3704 3784 3683 3731 3681 3697 3635 3694 3617 3610 3632 3663 3616 3595 3599 3584 3588 3613 3527 +const double ColorTemp::ColorYellowsuikeroalpi[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2048, 0.1666, 0.1140, 0.1210, 0.0699, 0.0680, 0.0615, 0.0566, 0.0567, 0.0561, 0.0609, 0.0585, 0.0614, 0.0572, 0.0599, 0.0575, 0.0636, 0.0730, 0.0982, 0.1194, 0.1360, 0.1766, + 0.2222, 0.2558, 0.2849, 0.3048, 0.3201, 0.3395, 0.3395, 0.3484, 0.3576, 0.3623, 0.3606, 0.3672, 0.3651, 0.3634, 0.3647, 0.3669, 0.3715, 0.3660, 0.3720, 0.3692, 0.3704, 0.3784, + 0.3683, 0.3731, 0.3681, 0.3697, 0.3635, 0.3694, 0.3617, 0.3610, 0.3632, 0.3663, 0.3616, 0.3595, 0.3599, 0.3584, 0.3588, 0.3613, 0.3527, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#yellow flower (pensashanhikki) +//356 1365 1024 902 535 387 355 247 365 307 321 330 319 332 317 336 408 487 709 963 1235 1631 2111 2436 2718 2950 3151 3262 3313 3420 3448 3475 3491 3534 3520 3565 3622 3631 3626 3657 3640 3607 3641 3627 3601 3591 3588 3667 3618 3601 3630 3613 3592 3609 3569 3590 3568 3563 3588 3480 3471 +const double ColorTemp::ColorYellowpensashanhikki1[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0356, 0.1365, 0.1024, 0.0902, 0.0535, 0.0387, 0.0355, 0.0247, 0.0365, 0.0307, 0.0321, 0.0330, 0.0319, 0.0332, 0.0317, 0.0336, 0.0408, 0.0487, 0.0709, 0.0963, 0.1235, + 0.1631, 0.2111, 0.2436, 0.2718, 0.2950, 0.3151, 0.3262, 0.3313, 0.3420, 0.3448, 0.3475, 0.3491, 0.3534, 0.3520, 0.3565, 0.3622, 0.3631, 0.3626, 0.3657, 0.3640, 0.3607, + 0.3641, 0.3627, 0.3601, 0.3591, 0.3588, 0.3667, 0.3618, 0.3601, 0.3630, 0.3613, 0.3592, 0.3609, 0.3569, 0.3590, 0.3568, 0.3563, 0.3588, 0.3480, 0.3471, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#yellow sepal (pensashanhikki) +//1068 427 326 416 428 590 503 470 539 526 546 540 539 526 497 546 555 603 753 903 1010 1268 1563 1868 2068 2226 2429 2495 2560 2625 2636 2610 2655 2667 2635 2630 2612 2560 2597 2588 2543 2478 2499 2472 2438 2431 2379 2406 2361 2319 2264 2174 2128 2010 1942 1912 1930 2148 2334 2585 2764 +const double ColorTemp::ColorYellowpensashanhikki2[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1068, 0.0427, 0.0326, 0.0416, 0.0428, 0.0590, 0.0503, 0.0470, 0.0539, 0.0526, 0.0546, 0.0540, 0.0539, 0.0526, 0.0497, 0.0546, 0.0555, 0.0603, 0.0753, 0.0903, 0.1010, 0.1268, + 0.1563, 0.1868, 0.2068, 0.2226, 0.2429, 0.2495, 0.2560, 0.2625, 0.2636, 0.2610, 0.2655, 0.2667, 0.2635, 0.2630, 0.2612, 0.2560, 0.2597, 0.2588, 0.2543, 0.2478, 0.2499, 0.2472, + 0.2438, 0.2431, 0.2379, 0.2406, 0.2361, 0.2319, 0.2264, 0.2174, 0.2128, 0.2010, 0.1942, 0.1912, 0.1930, 0.2148, 0.2334, 0.2585, 0.2764, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#blue flower (hiidenvirna) +//315 512 675 832 765 865 807 867 911 904 852 826 780 753 711 661 595 528 513 476 431 391 361 331 305 276 240 229 237 223 212 208 215 205 203 195 209 212 222 266 296 322 356 352 388 391 411 425 473 532 550 630 669 748 823 879 904 917 930 950 942 +const double ColorTemp::ColorBluehiidenvirna[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0315, 0.0512, 0.0675, 0.0832, 0.0765, 0.0865, 0.0807, 0.0867, 0.0911, 0.0904, 0.0852, 0.0826, 0.0780, 0.0753, 0.0711, 0.0661, 0.0595, 0.0528, 0.0513, 0.0476, 0.0431, 0.0391, + 0.0361, 0.0331, 0.0305, 0.0276, 0.0240, 0.0229, 0.0237, 0.0223, 0.0212, 0.0208, 0.0215, 0.0205, 0.0203, 0.0195, 0.0209, 0.0212, 0.0222, 0.0266, 0.0296, 0.0322, 0.0356, 0.0352, + 0.0388, 0.0391, 0.0411, 0.0425, 0.0473, 0.0532, 0.0550, 0.0630, 0.0669, 0.0748, 0.0823, 0.0879, 0.0904, 0.0917, 0.0930, 0.0950, 0.0942, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#blue flower (kurkkuyrtti) +//2687 1553 2181 2246 2209 2263 2442 2347 2261 2353 2292 2230 2095 2008 1896 1782 1569 1443 1333 1223 1177 1074 992 902 813 755 701 626 577 548 525 498 469 445 456 448 428 441 448 447 455 467 496 534 527 586 668 798 966 1126 1289 1469 1679 1870 2013 2040 2060 2077 2104 2155 2119 +//RIS 87 +const double ColorTemp::ColorBluekurkkuyrtti[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2687, 0.1553, 0.2181, 0.2246, 0.2209, 0.2263, 0.2442, 0.2347, 0.2261, 0.2353, 0.2292, 0.2230, 0.2095, 0.2008, 0.1896, 0.1782, 0.1569, 0.1443, 0.1333, 0.1223, 0.1177, 0.1074, + 0.0992, 0.0902, 0.0813, 0.0755, 0.0701, 0.0626, 0.0577, 0.0548, 0.0525, 0.0498, 0.0469, 0.0445, 0.0456, 0.0448, 0.0428, 0.0441, 0.0448, 0.0447, 0.0455, 0.0467, 0.0496, 0.0534, + 0.0527, 0.0586, 0.0668, 0.0798, 0.0966, 0.1126, 0.1289, 0.1469, 0.1679, 0.1870, 0.2013, 0.2040, 0.2060, 0.2077, 0.2104, 0.2155, 0.2119, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#pink (siankaersaemoe) +//585 859 758 1094 780 1012 987 1067 1059 1034 1098 1110 1097 1040 1058 1048 1028 1014 1068 1024 1023 1025 1032 1029 1011 1007 986 973 946 906 949 923 943 949 956 998 1051 1107 1166 1242 1284 1355 1394 1438 1451 1543 1589 1588 1612 1616 1562 1534 1562 1541 1494 1492 1518 1650 1749 1907 1991 +const double ColorTemp::ColorPinksiankaersaemoe[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0585, 0.0859, 0.0758, 0.1094, 0.0780, 0.1012, 0.0987, 0.1067, 0.1059, 0.1034, 0.1098, 0.1110, 0.1097, 0.1040, 0.1058, 0.1048, 0.1028, 0.1014, 0.1068, 0.1024, 0.1023, 0.1025, + 0.1032, 0.1029, 0.1011, 0.1007, 0.0986, 0.0973, 0.0946, 0.0906, 0.0949, 0.0923, 0.0943, 0.0949, 0.0956, 0.0998, 0.1051, 0.1107, 0.1166, 0.1242, 0.1284, 0.1355, 0.1394, 0.1438, + 0.1451, 0.1543, 0.1589, 0.1588, 0.1612, 0.1616, 0.1562, 0.1534, 0.1562, 0.1541, 0.1494, 0.1492, 0.1518, 0.1650, 0.1749, 0.1907, 0.1991, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#violet flower (harakankello) +//2520 1462 1890 1898 1751 1713 1555 1516 1471 1403 1282 1209 1144 1135 1069 976 895 823 782 762 713 685 661 635 603 559 551 550 541 567 562 574 580 589 586 620 670 690 718 801 786 769 773 739 800 806 837 845 971 1043 1102 1241 1359 1502 1611 1726 1793 1859 1909 1969 2014 +//RIS 89 +const double ColorTemp::ColorVioletharakankello[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2520, 0.1462, 0.1890, 0.1898, 0.1751, 0.1713, 0.1555, 0.1516, 0.1471, 0.1403, 0.1282, 0.1209, 0.1144, 0.1135, 0.1069, 0.0976, 0.0895, 0.0823, 0.0782, 0.0762, 0.0713, + 0.0685, 0.0661, 0.0635, 0.0603, 0.0559, 0.0551, 0.0550, 0.0541, 0.0567, 0.0562, 0.0574, 0.0580, 0.0589, 0.0586, 0.0620, 0.0670, 0.0690, 0.0718, 0.0801, 0.0786, 0.0769, + 0.0773, 0.0739, 0.0800, 0.0806, 0.0837, 0.0845, 0.0971, 0.1043, 0.1102, 0.1241, 0.1359, 0.1502, 0.1611, 0.1726, 0.1793, 0.1859, 0.1909, 0.1969, 0.2014, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#violet flower (alsikeapila) +//1260 585 765 1065 937 881 847 943 1075 1053 1020 994 1008 1026 1015 980 962 949 925 908 880 864 843 814 802 749 698 691 677 660 653 660 631 633 644 692 743 809 889 1005 1160 1325 1396 1450 1526 1583 1655 1674 1689 1707 1675 1674 1624 1576 1564 1591 1613 1717 1851 1962 2033 +const double ColorTemp::ColorVioletalsikeapila[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1260, 0.0585, 0.0765, 0.1065, 0.0937, 0.0881, 0.0847, 0.0943, 0.1075, 0.1053, 0.1020, 0.0994, 0.1008, 0.1026, 0.1015, 0.0980, 0.0962, 0.0949, 0.0925, 0.0908, 0.0880, 0.0864, + 0.0843, 0.0814, 0.0802, 0.0749, 0.0698, 0.0691, 0.0677, 0.0660, 0.0653, 0.0660, 0.0631, 0.0633, 0.0644, 0.0692, 0.0743, 0.0809, 0.0889, 0.1005, 0.1160, 0.1325, 0.1396, 0.1450, + 0.1526, 0.1583, 0.1655, 0.1674, 0.1689, 0.1707, 0.1675, 0.1674, 0.1624, 0.1576, 0.1564, 0.1591, 0.1613, 0.1717, 0.1851, 0.1962, 0.2033, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#violet flower (akilleija) +//843 1340 1393 1254 1290 1452 1508 1519 1454 1384 1301 1256 1178 1113 1056 985 884 827 743 720 691 664 605 578 540 507 499 475 485 494 492 479 487 493 471 495 559 595 645 689 720 732 716 723 734 750 804 849 948 1041 1169 1362 1525 1693 1761 1935 2071 2235 2376 2493 2604 +const double ColorTemp::ColorVioletakilleija[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0843, 0.1340, 0.1393, 0.1254, 0.1290, 0.1452, 0.1508, 0.1519, 0.1454, 0.1384, 0.1301, 0.1256, 0.1178, 0.1113, 0.1056, 0.0985, 0.0884, 0.0827, 0.0743, 0.0720, 0.0691, 0.0664, + 0.0605, 0.0578, 0.0540, 0.0507, 0.0499, 0.0475, 0.0485, 0.0494, 0.0492, 0.0479, 0.0487, 0.0493, 0.0471, 0.0495, 0.0559, 0.0595, 0.0645, 0.0689, 0.0720, 0.0732, 0.0716, 0.0723, + 0.0734, 0.0750, 0.0804, 0.0849, 0.0948, 0.1041, 0.1169, 0.1362, 0.1525, 0.1693, 0.1761, 0.1935, 0.2071, 0.2235, 0.2376, 0.2493, 0.2604, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#orange flower (kehaekukka) +//0 0 0 0 0 0 102 58 128 125 137 122 122 134 123 136 159 138 163 151 167 178 192 177 206 226 315 451 707 1045 1446 1707 1944 2131 2276 2524 2719 2841 2968 3052 3199 3264 3282 3429 3451 3454 3477 3556 3478 3565 3595 3569 3582 3582 3559 3610 3626 3668 3733 3692 3722 +const double ColorTemp::ColorOrangekehaekukka[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0102, 0.0058, 0.0128, 0.0125, 0.0137, 0.0122, 0.0122, 0.0134, 0.0123, 0.0136, 0.0159, 0.0138, 0.0163, 0.0151, 0.0167, 0.0178, 0.0192, + 0.0177, 0.0206, 0.0226, 0.0315, 0.0451, 0.0707, 0.1045, 0.1446, 0.1707, 0.1944, 0.2131, 0.2276, 0.2524, 0.2719, 0.2841, 0.2968, 0.3052, 0.3199, 0.3264, 0.3282, 0.3429, + 0.3451, 0.3454, 0.3477, 0.3556, 0.3478, 0.3565, 0.3595, 0.3569, 0.3582, 0.3582, 0.3559, 0.3610, 0.3626, 0.3668, 0.3733, 0.3692, 0.3722, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#red berry (pihlaja) +//0 0 0 0 25 84 128 87 165 130 167 147 155 146 148 165 158 159 164 160 158 158 157 157 173 173 179 195 210 234 264 302 349 386 461 572 735 886 1038 1216 1376 1521 1607 1691 1728 1769 1842 1843 1865 1910 1881 1920 1909 1909 1891 1879 1915 1879 1878 1843 1832 +const double ColorTemp::ColorRedpihlaja[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0, 0.0, 0.0, 0.0, 0.0025, 0.0084, 0.0128, 0.0087, 0.0165, 0.0130, 0.0167, 0.0147, 0.0155, 0.0146, 0.0148, 0.0165, 0.0158, 0.0159, 0.0164, 0.0160, 0.0158, 0.0158, + 0.0157, 0.0157, 0.0173, 0.0173, 0.0179, 0.0195, 0.0210, 0.0234, 0.0264, 0.0302, 0.0349, 0.0386, 0.0461, 0.0572, 0.0735, 0.0886, 0.1038, 0.1216, 0.1376, 0.1521, 0.1607, 0.1691, + 0.1728, 0.1769, 0.1842, 0.1843, 0.1865, 0.1910, 0.1881, 0.1920, 0.1909, 0.1909, 0.1891, 0.1879, 0.1915, 0.1879, 0.1878, 0.1843, 0.1832, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//#violet flower (petunia) +//292 66 227 313 325 332 310 319 300 268 229 193 164 137 127 104 67 50 49 37 34 34 44 32 33 31 38 41 33 34 45 44 37 42 44 49 49 67 80 89 110 130 137 145 153 171 194 223 275 321 391 464 580 720 907 1055 1230 1436 1548 1777 1933 +//RIS 94 +const double ColorTemp::ColorVioletpetunia[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0292, 0.0066, 0.0227, 0.0313, 0.0325, 0.0332, 0.0310, 0.0319, 0.0300, 0.0268, 0.0229, 0.0193, 0.0164, 0.0137, 0.0127, 0.0104, 0.0067, 0.0050, 0.0049, 0.0037, 0.0034, 0.0034, + 0.0044, 0.0032, 0.0033, 0.0031, 0.0038, 0.0041, 0.0033, 0.0034, 0.0045, 0.0044, 0.0037, 0.0042, 0.0044, 0.0049, 0.0049, 0.0067, 0.0080, 0.0089, 0.0110, 0.0130, 0.0137, 0.0145, + 0.0153, 0.0171, 0.0194, 0.0223, 0.0275, 0.0321, 0.0391, 0.0464, 0.0580, 0.0720, 0.0907, 0.1055, 0.1230, 0.1436, 0.1548, 0.1777, 0.1933, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#violet flower (orvokki) +//195 0 152 31 22 32 77 69 45 20 27 26 13 12 14 11 15 23 16 18 16 12 16 10 16 15 13 15 15 16 14 20 14 17 15 17 15 17 17 17 23 24 29 38 36 38 37 43 58 65 70 86 113 155 222 285 405 506 645 817 1035 +const double ColorTemp::ColorVioletorvokki[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0195, 0.0, 0.0152, 0.0031, 0.0022, 0.0032, 0.0077, 0.0069, 0.0045, 0.0020, 0.0027, 0.0026, 0.0013, 0.0012, 0.0014, 0.0011, 0.0015, 0.0023, 0.0016, 0.0018, 0.0016, 0.0012, 0.0016, + 0.0010, 0.0016, 0.0015, 0.0013, 0.0015, 0.0015, 0.0016, 0.0014, 0.0020, 0.0014, 0.0017, 0.0015, 0.0017, 0.0015, 0.0017, 0.0017, 0.0017, 0.0023, 0.0024, 0.0029, 0.0038, 0.0036, + 0.0038, 0.0037, 0.0043, 0.0058, 0.0065, 0.0070, 0.0086, 0.0113, 0.0155, 0.0222, 0.0285, 0.0405, 0.0506, 0.0645, 0.0817, 0.1035, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#blue flower (sinisievikki) +//801 1109 1861 2325 2329 2380 2562 2565 2558 2611 2517 2567 2475 2397 2337 2294 2195 2001 1881 1892 1854 1746 1668 1580 1491 1362 1229 1178 1110 1094 1072 1019 994 960 928 879 836 859 863 951 1046 1102 1154 1193 1174 1166 1153 1199 1275 1316 1376 1550 1739 1918 2104 2228 2364 2377 2423 2394 2334 +const double ColorTemp::ColorBluesinisievikki[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0801, 0.1109, 0.1861, 0.2325, 0.2329, 0.2380, 0.2562, 0.2565, 0.2558, 0.2611, 0.2517, 0.2567, 0.2475, 0.2397, 0.2337, 0.2294, 0.2195, 0.2001, 0.1881, 0.1892, 0.1854, 0.1746, + 0.1668, 0.1580, 0.1491, 0.1362, 0.1229, 0.1178, 0.1110, 0.1094, 0.1072, 0.1019, 0.0994, 0.0960, 0.0928, 0.0879, 0.0836, 0.0859, 0.0863, 0.0951, 0.1046, 0.1102, 0.1154, 0.1193, + 0.1174, 0.1166, 0.1153, 0.1199, 0.1275, 0.1316, 0.1376, 0.1550, 0.1739, 0.1918, 0.2104, 0.2228, 0.2364, 0.2377, 0.2423, 0.2394, 0.2334, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#blue flower (iisoppi) +//623 85 605 833 776 756 755 781 774 775 697 724 697 654 617 575 536 494 460 469 442 436 400 393 380 358 369 352 342 368 357 360 342 342 341 335 355 353 365 376 382 392 412 412 407 414 420 449 487 504 517 571 651 734 806 885 968 1088 1210 1296 1411 +const double ColorTemp::ColorBlueiisoppi[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0623, 0.0085, 0.0605, 0.0833, 0.0776, 0.0756, 0.0755, 0.0781, 0.0774, 0.0775, 0.0697, 0.0724, 0.0697, 0.0654, 0.0617, 0.0575, 0.0536, 0.0494, 0.0460, 0.0469, 0.0442, 0.0436, + 0.0400, 0.0393, 0.0380, 0.0358, 0.0369, 0.0352, 0.0342, 0.0368, 0.0357, 0.0360, 0.0342, 0.0342, 0.0341, 0.0335, 0.0355, 0.0353, 0.0365, 0.0376, 0.0382, 0.0392, 0.0412, 0.0412, + 0.0407, 0.0414, 0.0420, 0.0449, 0.0487, 0.0504, 0.0517, 0.0571, 0.0651, 0.0734, 0.0806, 0.0885, 0.0968, 0.1088, 0.1210, 0.1296, 0.1411, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//#white petal (ojakaersaemoe) +//1732 951 1800 1365 1801 1697 1762 2103 2243 2218 2200 2206 2255 2254 2269 2261 2272 2251 2254 2260 2256 2266 2247 2269 2310 2273 2345 2312 2301 2323 2302 2314 2362 2355 2348 2362 2396 2374 2362 2381 2396 2440 2383 2347 2422 2419 2472 2423 2406 2425 2377 2381 2380 2398 2390 2404 2370 2375 2364 2411 2417 +const double ColorTemp::ColorWhiteojaka[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1732, 0.0951, 0.1800, 0.1365, 0.1801, 0.1697, 0.1762, 0.2103, 0.2243, 0.2218, 0.2200, 0.2206, 0.2255, 0.2254, 0.2269, 0.2261, 0.2272, 0.2251, 0.2254, 0.2260, 0.2256, 0.2266, + 0.2247, 0.2269, 0.2310, 0.2273, 0.2345, 0.2312, 0.2301, 0.2323, 0.2302, 0.2314, 0.2362, 0.2355, 0.2348, 0.2362, 0.2396, 0.2374, 0.2362, 0.2381, 0.2396, 0.2440, 0.2383, 0.2347, + 0.2422, 0.2419, 0.2472, 0.2423, 0.2406, 0.2425, 0.2377, 0.2381, 0.2380, 0.2398, 0.2390, 0.2404, 0.2370, 0.2375, 0.2364, 0.2411, 0.2417, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//#white flower (petunia) +//4095 4022 4410 4095 4095 4095 4193 4207 4388 4328 4223 4168 4221 4304 4245 4210 4212 4192 4181 4233 4207 4224 4197 4262 4243 4241 4274 4257 4204 4285 4265 4241 4267 4275 4245 4276 4260 4217 4217 4244 4240 4186 4160 4156 4227 4286 4237 4137 4202 4187 4100 4112 4103 4090 4125 4115 4098 4036 4047 4105 4050 +const double ColorTemp::ColorWhitepetunia[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.4095, 0.4022, 0.4410, 0.4095, 0.4095, 0.4095, 0.4193, 0.4207, 0.4388, 0.4328, 0.4223, 0.4168, 0.4221, 0.4304, 0.4245, 0.4210, 0.4212, 0.4192, 0.4181, 0.4233, 0.4207, 0.4224, + 0.4197, 0.4262, 0.4243, 0.4241, 0.4274, 0.4257, 0.4204, 0.4285, 0.4265, 0.4241, 0.4267, 0.4275, 0.4245, 0.4276, 0.4260, 0.4217, 0.4217, 0.4244, 0.4240, 0.4186, 0.4160, 0.4156, + 0.4227, 0.4286, 0.4237, 0.4137, 0.4202, 0.4187, 0.4100, 0.4112, 0.4103, 0.4090, 0.4125, 0.4115, 0.4098, 0.4036, 0.4047, 0.4105, 0.4050, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + + +//#blue flower (lobelia dortmanna) +//0 660 1277 1544 1612 1961 1909 1950 1901 1907 1809 1785 1685 1622 1522 1377 1178 1054 931 898 850 732 610 508 434 370 343 329 303 265 232 199 183 169 172 177 200 233 214 214 199 186 199 228 249 321 435 684 1006 1345 1703 2082 2432 2661 2843 2936 3079 3015 3003 3045 3038 +//RIS 98 +const double ColorTemp::ColorBluelobelia[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0, 0.0660, 0.1277, 0.1544, 0.1612, 0.1961, 0.1909, 0.1950, 0.1901, 0.1907, 0.1809, 0.1785, 0.1685, 0.1622, 0.1522, 0.1377, 0.1178, 0.1054, 0.0931, 0.0898, 0.0850, 0.0732, + 0.0610, 0.0508, 0.0434, 0.0370, 0.0343, 0.0329, 0.0303, 0.0265, 0.0232, 0.0199, 0.0183, 0.0169, 0.0172, 0.0177, 0.0200, 0.0233, 0.0214, 0.0214, 0.0199, 0.0186, 0.0199, + 0.0228, 0.0249, 0.0321, 0.0435, 0.0684, 0.1006, 0.1345, 0.1703, 0.2082, 0.2432, 0.2661, 0.2843, 0.2936, 0.3079, 0.3015, 0.3003, 0.3045, 0.3038, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//#white petal (pelargonia) +//3493 2882 2284 2730 2869 2609 2781 2869 2861 2869 2795 2810 2740 2716 2650 2631 2539 2554 2450 2453 2447 2451 2343 2408 2404 2367 2343 2401 2474 2549 2668 2759 2843 2883 2989 3106 3209 3344 3383 3404 3453 3521 3495 3571 3521 3548 3582 3557 3581 3539 3563 3589 3597 3579 3502 3546 3507 3554 3490 3561 3518 +const double ColorTemp::ColorWhitepelargonia[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.3493, 0.2882, 0.2284, 0.2730, 0.2869, 0.2609, 0.2781, 0.2869, 0.2861, 0.2869, 0.2795, 0.2810, 0.2740, 0.2716, 0.2650, 0.2631, 0.2539, 0.2554, 0.2450, 0.2453, 0.2447, + 0.2451, 0.2343, 0.2408, 0.2404, 0.2367, 0.2343, 0.2401, 0.2474, 0.2549, 0.2668, 0.2759, 0.2843, 0.2883, 0.2989, 0.3106, 0.3209, 0.3344, 0.3383, 0.3404, 0.3453, 0.3521, + 0.3495, 0.3571, 0.3521, 0.3548, 0.3582, 0.3557, 0.3581, 0.3539, 0.3563, 0.3589, 0.3597, 0.3579, 0.3502, 0.3546, 0.3507, 0.3554, 0.3490, 0.3561, 0.3518, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +/* +#white petal (paeivaenkakkara) +2168 1365 1969 2095 2231 2530 2944 3092 3107 3148 3188 3207 3195 3216 3225 3261 3211 3228 3260 3237 3258 3276 3265 3316 3327 3291 3315 3324 3355 3255 3264 3308 3324 3328 3282 3253 3220 3257 3289 3265 3245 3297 3284 3292 3228 3312 3290 3277 3278 3284 3182 3244 3273 3291 3212 3256 3154 3243 3306 3234 3155 +*/ +const double ColorTemp::ColorWhitepaeivaen[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2168, 0.1365, 0.1969, 0.2095, 0.2231, 0.2530, 0.2944, 0.3092, 0.3107, 0.3148, 0.3188, 0.3207, 0.3195, 0.3216, 0.3225, 0.3261, 0.3211, 0.3228, 0.3260, 0.3237, 0.3258, + 0.3276, 0.3265, 0.3316, 0.3327, 0.3291, 0.3315, 0.3324, 0.3355, 0.3255, 0.3264, 0.3308, 0.3324, 0.3328, 0.3282, 0.3253, 0.3220, 0.3257, 0.3289, 0.3265, 0.3245, 0.3297, + 0.3284, 0.3292, 0.3228, 0.3312, 0.3290, 0.3277, 0.3278, 0.3284, 0.3182, 0.3244, 0.3273, 0.3291, 0.3212, 0.3256, 0.3154, 0.3243, 0.3306, 0.3234, 0.3155, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + //spectral data Colorchecker24 : Green B3 const double ColorTemp::ColorchechGreB3_spect[97] = { @@ -446,6 +1162,21 @@ const double ColorTemp::ColorchechGraC4_67_spect[97] = { 0.369, 0.3689, 0.368, 0.3673, 0.3678, 0.3684, 0.37, 0.3711, 0.3712, 0.3714, 0.3714, 0.3714, 0.371, 0.3707, 0.37, 0.3694, 0.3697, 0.3703, 0.3697, 0.3692, 0.3688, 0.3685, 0.3675, 0.3669, 0.3657, 0.3647, 0.3635, 0.3625, 0.361, 0.3596, 0.3585, 0.3579, 0.357, 0.3560, 0.3555, 0.3548, 0.3535, 0.3526, 0.3513, 0.3500, 0.349, 0.3475, 0.3467, 0.3460, 0.3452, 0.3444, 0.3431, 0.3421, 0.3411, 0.3403, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 }; +const double ColorTemp::Fictif_61greyspect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, + 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, + 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.1, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::JDC468_K15_87greyspect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1984, 0.2223, 0.2448, 0.2934, 0.3415, 0.4425, 0.5707, 0.6609, 0.7619, 0.7956, 0.8275, 0.8280, 0.8292, 0.8223, 0.8156, 0.8112, 0.8076, 0.8040, 0.7982, 0.7970, 0.7954, 0.8013, 0.8083, 0.8141, 0.8184, 0.8167, + 0.8137, 0.8080, 0.8026, 0.8013, 0.7988, 0.7963, 0.7942, 0.7855, 0.7765, 0.7680, 0.7603, 0.7640, 0.7681, 0.7750, 0.7827, 0.7876, 0.7923, 0.7935, 0.7945, 0.7955, 0.7964, 0.7975, 0.7982, 0.8000, 0.8017, 0.8051, + 0.8090, 0.8145, 0.8191, 0.8234, 0.8269, 0.8300, 0.8327, 0.8342, 0.8359, 0.8375, 0.8390, 0.8405, 0.8421, 0.8436, 0.8452, 0.8480, 0.8504, 0.8564, 0.8611, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 + +}; +//K15 275 275 0.1984 0.2448 0.3415 0.5707 0.7619 0.8275 0.8292 0.8156 0.8076 0.7982 0.7954 0.8083 0.8184 0.8137 0.8026 0.7988 0.7942 0.7765 0.7603 0.7681 0.7827 0.7923 0.7945 0.7964 0.7982 0.8017 0.8090 0.8191 0.8269 0.8327 0.8359 0.8390 0.8421 0.8452 0.8504 0.8611 //spectral data Colorchecker24 : Skin B1 //use also for palette WB @@ -478,7 +1209,7 @@ const double ColorTemp::ColorchechDCBluN881_m7_m14_spect[97] = { //spectral data ColorcheckerSG : Skin F7 //use also for palette WB const double ColorTemp::ColorchechSGSkiF763_14_26_spect[97] = { - 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0508, 0.64, 0.0776, 0.903, 0.1099, 0.1128, 0.1256, 0.128, 0.1307, 0.133, 0.1357, 0.139, 0.1425, 0.148, 0.1523, 0.159, 0.1669, 0.177, 0.1871, 0.20, 0.2118, 0.2235, 0.2355, 0.2445, 0.2537, 0.259, 0.2655, 0.268, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0508, 0.064, 0.0776, 0.903, 0.1099, 0.1128, 0.1256, 0.128, 0.1307, 0.133, 0.1357, 0.139, 0.1425, 0.148, 0.1523, 0.159, 0.1669, 0.177, 0.1871, 0.20, 0.2118, 0.2235, 0.2355, 0.2445, 0.2537, 0.259, 0.2655, 0.268, 0.2700, 0.2708, 0.2716, 0.2743, 0.2770, 0.2803, 0.2827, 0.283, 0.2832, 0.283, 0.2828, 0.295, 0.3079, 0.344, 0.3803, 0.4105, 0.4409, 0.455, 0.4694, 0.477, 0.4851, 0.4896, 0.4962, 0.501, 0.5066, 0.511, 0.5160, 0.521, 0.5256, 0.529, 0.5318, 0.535, 0.5383, 0.541, 0.5451, 0.549, 0.5524, 0.556, 0.5597, 0.562, 0.5650, 0.568, 0.5709, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 }; @@ -531,15 +1262,156 @@ const double ColorTemp::JDC468_GraK14_44_spect[97] = { 0.1408, 0.14330, 0.1475, 0.15170, 0.1583, 0.16500, 0.172, 0.17940, 0.1836, 0.18780, 0.188, 0.18820, 0.186, 0.18430, 0.1801, 0.17620, 0.1741, 0.17210, 0.179, 0.18420, 0.1991, 0.21430, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 }; +const double ColorTemp::JDC468_BluM5_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1510, 0.1802, 0.2069, 0.2550, 0.3047, 0.4055, 0.5069, 0.590, 0.6747, 0.701, 0.7351, 0.7345, 0.7338, 0.7195, 0.7063, 0.693, 0.6732, 0.6490, 0.6261, 0.5993, 0.5723, 0.5560, + 0.5401, 0.526, 0.5106, 0.4805, 0.4504, 0.42, 0.3907, 0.385, 0.3799, 0.3750, 0.3695, 0.3340, 0.3005, 0.2692, 0.2382, 0.2387, 0.2389, 0.2501, 0.2610, 0.2635, 0.2662, 0.2601, 0.2541, + 0.2450, 0.2426, 0.2430, 0.2434, 0.2490, 0.2523, 0.2612, 0.2692, 0.2694, 0.2996, 0.3145, 0.3329, 0.3413, 0.3498, 0.3467, 0.3442, 0.3355, 0.3266, 0.3131, 0.2996, 0.2911, 0.2831, 0.2950, 0.3070, 0.3430, 0.3799, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//m5 317 //0.1510 0.2069 0.3047 0.5069 0.6747 0.7351 0.7338 0.7063 0.6732 0.6261 0.5723 0.5401 +// 0.5106 0.4504 0.3907 0.3799 0.3695 0.3005 0.2382 0.2389 0.2610 0.2662 0.2541 +// 0.2426 0.2434 0.2523 0.2692 0.2996 0.3329 0.3498 0.3442 0.3266 0.2996 0.2831 0.3070 0.3799 + +const double ColorTemp::JDC468_RedG21va_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1207, 0.141, 0.1585, 0.1810, 0.2073, 0.2529, 0.2959, 0.3210, 0.3476, 0.3350, 0.3232, 0.2845, 0.2564, 0.2140, 0.1823, 0.1523, 0.1266, 0.1001, 0.0792, 0.061, 0.0439, 0.0349, 0.0295, 0.0260, 0.0222, + 0.0180, 0.0135, 0.0111, 0.0087, 0.0090, 0.0094, 0.0101, 0.0109, 0.0093, 0.0086, 0.0090, 0.0091, 0.0061, 0.0321, 0.0086, 0.1368, 0.2312, 0.3256, 0.4112, 0.4958, 0.5444, 0.5884, 0.6002, 0.6264, 0.6323, 0.6473, + 0.6546, 0.6659, 0.6775, 0.6881, 0.6982, 0.7081, 0.7150, 0.7201, 0.7217, 0.7232, 0.7222, 0.7215, 0.7187, 0.7157, 0.7144, 0.7131, 0.7196, 0.7269, 0.7303, 0.7599, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//g21 177 0.1207 0.1585 0.2073 0.2959 0.3476 0.3232 0.2564 0.1823 0.1266 0.0792 0.0439 0.0295 0.0222 0.0135 0.0087 0.0094 0.0109 0.0086 0.0091 0.0321 +// 0.1368 0.3256 0.4958 0.5884 0.6264 0.6473 0.6659 0.6881 0.7081 0.7201 0.7232 0.7215 0.7157 0.7131 0.7269 0.7599 +const double ColorTemp::JDC468_RedI9_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0258, 0.023, 0.0220, 0.0205, 0.0189, 0.0183, 0.0174, 0.0168, 0.0162, 0.0152, 0.0148, 0.0145, 0.0139, 0.0136, 0.0133, 0.0130, 0.0127, 0.0130, 0.0133, 0.0151, 0.0168, 0.0218, 0.0268, 0.0317, 0.0367, 0.0330, + 0.0313, 0.0270, 0.0227, 0.0240, 0.0255, 0.0280, 0.0302, 0.0280, 0.0225, 0.0215, 0.0209, 0.0424, 0.0639, 0.1401, 0.2131, 0.3250, 0.4369, 0.5210, 0.6265, 0.6795, 0.7336, 0.7551, 0.7784, 0.7890, 0.7994, 0.8070, + 0.8146, 0.8210, 0.8277, 0.8321, 0.8362, 0.8398, 0.8439, 0.8470, 0.8504, 0.8530, 0.8572, 0.8612, 0.8653, 0.8689, 0.8715, 0.8730, 0.8747, 0.8766, 0.8788, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//I9 RED 217 0.0258 0.0220 0.0189 0.0174 0.0162 0.0148 0.0139 0.0133 0.0127 0.0133 0.0168 0.0268 0.0367 0.0313 0.0227 0.0255 0.0302 0.0225 0.0209 0.0639 0.2131 0.4369 0.6265 0.7336 0.7784 0.7994 0.8146 0.8277 0.8362 0.8439 0.8504 0.8572 0.8653 0.8715 0.8747 0.8788 + +const double ColorTemp::JDC468_YelN10_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0531, 0.0520, 0.0504, 0.0510, 0.0518, 0.0608, 0.0628, 0.0669, 0.0699, 0.0705, 0.0716, 0.0720, 0.0735, 0.0755, 0.0775, 0.0800, 0.0825, 0.0896, 0.0969, 0.1260, 0.1563, 0.2312, 0.3096, 0.4132, 0.5177, 0.5905, 0.6637, + 0.7251, 0.7350, 0.7458, 0.7480, 0.7507, 0.7460, 0.7414, 0.7356, 0.7301, 0.7320, 0.7347, 0.7390, 0.7438, 0.7472, 0.7500, 0.7508, 0.7515, 0.7528, 0.7538, 0.7550, 0.7563, 0.7581, 0.7607, 0.7642, 0.7686, 0.7710, + 0.7791, 0.7840, 0.7872, 0.7902, 0.7935, 0.7955, 0.7979, 0.7995, 0.8021, 0.8035, 0.8058, 0.8072, 0.8090, 0.8110, 0.8143, 0.8198, 0.8259, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//n10 348 0.0531 0.0504 0.0518 0.0628 0.0699 0.0716 0.0735 0.0775 0.0825 0.0969 0.1563 0.3096 0.5177 0.6637 0.7251 0.7458 0.7507 0.7414 0.7301 0.7347 0.7438 0.7500 0.7515 0.7538 0.7563 0.7607 0.7686 0.7791 0.7872 0.7935 0.7979 0.8021 0.8058 0.8090 0.8143 0.8259 +const double ColorTemp::JDC468_GreN7_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0112, 0.0102, 0.0094, 0.0096, 0.0099, 0.0100, 0.0100, 0.0100, 0.0100, 0.0099, 0.0099, 0.0099, 0.0099, 0.0099, 0.0099, 0.0100, 0.0100, 0.0103, 0.0107, 0.0129, 0.0151, 0.0312, 0.0462, 0.1015, 0.1571, 0.2270, 0.2977, + 0.3558, 0.3441, 0.3321, 0.3020, 0.2710, 0.2312, 0.1954, 0.1602, 0.1251, 0.1003, 0.0794, 0.0672, 0.0563, 0.0513, 0.0452, 0.0418, 0.0378, 0.0356, 0.0337, 0.0336, 0.0335, 0.0345, 0.0358, 0.0383, 0.0405, 0.0445, 0.0497, + 0.0612, 0.0647, 0.0670, 0.0660, 0.0644, 0.0620, 0.0574, 0.0525, 0.0483, 0.0460, 0.0436, 0.0484, 0.0532, 0.0690, 0.0870, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//n7 345 0.0112 0.0094 0.0099 0.0100 0.0100 0.0099 0.0099 0.0099 0.0100 0.0107 0.0151 0.0462 0.1571 0.2977 0.3558 0.3321 0.2710 0.1954 0.1251 0.0794 0.0563 0.0452 0.0378 0.0337 0.0335 0.0358 0.0405 0.0497 0.0612 0.0670 0.0644 0.0574 0.0483 0.0436 0.0532 0.0870 + +const double ColorTemp::JDC468_GreA10_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0958, 0.1010, 0.1090, 0.1172, 0.1352, 0.1954, 0.1957, 0.2178, 0.2402, 0.2477, 0.2553, 0.2594, 0.2622, 0.2667, 0.2707, 0.2760, 0.2805, 0.2913, 0.3023, 0.3376, 0.3715, 0.4345, 0.5030, 0.5702, 0.6376, 0.6724, 0.7072, + 0.7216, 0.7160, 0.7110, 0.6990, 0.6865, 0.6667, 0.6446, 0.6174, 0.5921, 0.5727, 0.5511, 0.5386, 0.5238, 0.5134, 0.5070, 0.4980, 0.4918, 0.4867, 0.4830, 0.4834, 0.4838, 0.4889, 0.4906, 0.4976, 0.5046, 0.5162, 0.5279, + 0.5519, 0.5589, 0.5649, 0.5645, 0.5639, 0.5576, 0.5552, 0.5480, 0.5407, 0.5377, 0.5326, 0.5387, 0.5498, 0.5732, 0.5966, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::JDC468_GreQ7_spect[97] = { //468 Q7 + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0149, 0.0139, 0.0133, 0.0128, 0.0123, 0.01185, 0.0114, 0.011, 0.0106, 0.01045, 0.0103, 0.0104, 0.0105, 0.01065, 0.0108, 0.0109, 0.0110, 0.0117, 0.0124, 0.0205, 0.0283, 0.071, 0.1122, 0.2051, + 0.3017, 0.385, 0.4690, 0.4880, 0.5069, 0.4811, 0.4561, 0.411, 0.3687, 0.3185, 0.2673, 0.2190, 0.1703, 0.1371, 0.1042, 0.086, 0.0695, 0.598, 0.0527, 0.0475, 0.04210, 0.039, 0.03600, 0.0357, 0.0355, 0.037, + 0.0381, 0.0405, 0.0438, 0.0499, 0.0555, 0.0635, 0.0708, 0.074, 0.0789, 0.077, 0.0751, 0.071, 0.0658, 0.059, 0.0530, 0.049, 0.0458, 0.052, 0.0570, 0.077, 0.0982, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//a10 Green 10 0.0958 0.1090 0.1352 0.1957 0.2402 0.2553 0.2622 0.2707 0.2805 0.3023 0.3715 0.5030 0.6376 0.7072 0.7216 0.7110 0.6865 0.6446 0.5921 0.5511 0.5238 0.5070 0.4918 0.4830 0.4838 0.4906 0.5046 0.5279 0.5519 0.5649 0.5639 0.5552 0.5407 0.5326 0.5498 0.5966 +const double ColorTemp::JDC468_GreK7_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0114, 0.0111, 0.0109, 0.0107, 0.0105, 0.0106, 0.0108, 0.0107, 0.0106, 0.0105, 0.0104, 0.0103, 0.0103, 0.0106, 0.0109, 0.0112, 0.0118, 0.0135, 0.0153, 0.0244, 0.0334, 0.0666, 0.0984, 0.1534, 0.2082, 0.2412, 0.2835, + 0.2959, 0.2843, 0.2735, 0.2516, 0.2305, 0.2012, 0.1728, 0.1435, 0.1156, 0.0964, 0.0772, 0.0671, 0.0570, 0.0518, 0.0468, 0.0436, 0.0397, 0.0380, 0.0354, 0.0354, 0.0355, 0.0367, 0.0380, 0.0402, 0.0426, 0.0481, 0.0523, + 0.0643, 0.0678, 0.0704, 0.0693, 0.0676, 0.0639, 0.0609, 0.0567, 0.0514, 0.0487, 0.0468, 0.0518, 0.0567, 0.0730, 0.0902, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//k7 Green 267 0.0114 0.0109 0.0105 0.0108 0.0106 0.0104 0.0103 0.0109 0.0118 0.0153 0.0334 0.0984 0.2082 0.2835 0.2959 0.2735 0.2305 0.1728 0.1156 0.0772 0.0570 0.0468 0.0397 0.0354 0.0355 0.0380 0.0426 0.0523 0.0643 0.0704 0.0676 0.0609 0.0514 0.0468 0.0567 0.0902 + +const double ColorTemp::JDC468_PurE24_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0677, 0.901, 0.1043, 0.1298, 0.1534, 0.1913, 0.2297, 0.2553, 0.2756, 0.2789, 0.2620, 0.2380, 0.2135, 0.1837, 0.1536, 0.1312, 0.1068, 0.0867, 0.0663, 0.0517, 0.0368, 0.0309, 0.0247, 0.0214, 0.0186, 0.0151, 0.0116, + 0.0077, 0.0079, 0.0079, 0.0083, 0.0086, 0.0077, 0.0071, 0.0071, 0.0072, 0.0107, 0.0147, 0.0298, 0.0440, 0.0661, 0.0880, 0.1010, 0.1152, 0.1193, 0.1236, 0.1260, 0.1287, 0.1326, 0.1366, 0.1428, 0.1489, 0.1596, 0.1697, + 0.1936, 0.1996, 0.2057, 0.2036, 0.2015, 0.1954, 0.1890, 0.1798, 0.1706, 0.1651, 0.1603, 0.1692, 0.1788, 0.2075, 0.2363, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//E24 Pur 128 0.0677 0.1043 0.1534 0.2297 0.2756 0.2620 0.2135 0.1536 0.1068 0.0663 0.0368 0.0247 0.0186 0.0116 0.0077 0.0079 0.0086 0.0071 0.0072 0.0147 0.0440 0.0880 0.1152 0.1236 0.1287 0.1366 0.1489 0.1697 0.1936 0.2057 0.2015 0.1890 0.1706 0.1603 0.1788 0.2363 + //spectral data 468 color : Blue H10 - Gamut > WidegamutRGB const double ColorTemp::JDC468_BluH10_spect[97] = { 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, - 0.01590, 0.028, 0.03970, 0.0697, 0.09970, 0.1526, 0.20550, 0.253, 0.30110, 0.3412, 0.38180, 0.423, 0.46610, 0.4683, 0.51030, 0.4999, 0.49950, 0.4785, 0.45810, 0.429, 0.39950, 0.374, 0.35010, 0.3135, 0.29630, + 0.01590, 0.028, 0.03970, 0.0697, 0.09970, 0.1526, 0.20550, 0.253, 0.30110, 0.3412, 0.38180, 0.423, 0.46610, 0.4683, 0.51030, 0.5005, 0.49950, 0.4785, 0.45810, 0.429, 0.39950, 0.374, 0.35010, 0.3135, 0.29630, 0.2587, 0.22070, 0.182, 0.14450, 0.1125, 0.09060, 0.072, 0.04810, 0.033, 0.01740, 0.0113, 0.00520, 0.004, 0.00290, 0.0028, 0.00270, 0.0027, 0.00270, 0.0027, 0.00280, 0.0027, 0.00270, 0.0028, 0.00280, - 0.0029, 0.00300, 0.0029, 0.00290, 0.0029, 0.0029, 0.00290, 0.0029, 0.00290, 0.0029, 0.00290, 0.0029, 0.00290, 0.0029, 0.00290, 0.0029, 0.0031, 0.00320, 0.0035, 0.00380, 0.047, 0.00560, + 0.0029, 0.00300, 0.0029, 0.00290, 0.0029, 0.0029, 0.00290, 0.0029, 0.00290, 0.0029, 0.00290, 0.0029, 0.00290, 0.0029, 0.00290, 0.0029, 0.0031, 0.00320, 0.0035, 0.00380, 0.0047, 0.00560, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 }; +//0.0159, 0.028, 0.0397, 0.0697, 0.0997, 0.1526, 0.2055, 0.253, 0.3011, 0.3412, 0.3818, 0.423, 0.4661, 0.5103 0.4995 0.4581 0.3995 0.3501 0.2963 +//0.2207 0.1445 0.0906 0.0481 0.0174 0.0052 0.0029 0.0027 0.0027 0.0028 0.0027 0.0028 0.0030 0.0029 0.0029 0.0029 0.0029 0.0029 0.0029 +//0.0029 0.0032 0.0038 0.0056 + +const double ColorTemp::JDC468_BluD6_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1127, 0.143, 0.1773, 0.223, 0.2813, 0.3987, 0.4782, 0.5665, 0.6470, 0.6870, 0.7270, 0.7403, 0.7593, 0.7592, 0.7591, 0.7480, 0.7402, 0.7234, 0.7054, 0.6876, 0.6617, 0.6512, 0.6302, 0.6124, 0.5962, 0.5660, + 0.5352, 0.5009, 0.4655, 0.4356, 0.4191, 0.3923, 0.3619, 0.3145, 0.2653, 0.2245, 0.1744, 0.1499, 0.1255, 0.1124, 0.1014, 0.0972, 0.0855, 0.0786, 0.0715, 0.0659, 0.0626, 0.0625, 0.0624, 0.0645, 0.0670, 0.0714, + 0.0769, 0.0865, 0.0964, 0.1086, 0.1200, 0.123, 0.1327, 0.1309, 0.1281, 0.1214, 0.1146, 0.1023, 0.0950, 0.0901, 0.0839, 0.0918, 0.1009, 0.1260, 0.1597, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 + + +}; +//d6 blue 84 0.1127 0.1773 0.2813 0.4782 0.6470 0.7270 0.7593 0.7591 0.7402 0.7054 0.6617 0.6302 0.5962 0.5352 0.4655 0.4191 0.3619 0.2653 0.1744 0.1255 0.1014 0.0855 0.0715 0.0626 0.0624 0.0670 0.0769 0.0964 0.1200 0.1327 0.1281 0.1146 0.0950 0.0839 0.1009 0.1597 +const double ColorTemp::JDC468_BluF4_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0180, 0.0270, 0.0324, 0.0453, 0.0611, 0.0845, 0.1066, 0.1234, 0.1446, 0.1567, 0.1718, 0.1867, 0.1954, 0.2024, 0.2083, 0.2090, 0.2096, 0.2060, 0.2036, 0.1990, 0.1947, 0.1920, 0.1901, 0.1856, 0.1794, 0.1667, 0.1516, 0.1321, + 0.1167, 0.1032, 0.0876, 0.0730, 0.0584, 0.0445, 0.0296, 0.0212, 0.0125, 0.0099, 0.0069, 0.0060, 0.0053, 0.0050, 0.0049, 0.0047, 0.0046, 0.0045, 0.0044, 0.0043, 0.0043, 0.0043, 0.0043, 0.0046, 0.0049, 0.0050, 0.0052, 0.0057, + 0.0063, 0.0066, 0.0069, 0.0067, 0.0066, 0.0063, 0.0059, 0.0056, 0.0053, 0.0054, 0.0055, 0.0062, 0.0069, 0.0099, 0.0122, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 + +}; + +// f4 blue 134 0.0180 0.0324 0.0611 0.1066 0.1446 0.1718 0.1954 0.2083 0.2096 0.2036 0.1947 0.1901 0.1794 0.1516 0.1167 0.0876 0.0584 0.0296 0.0125 0.0069 0.0053 0.0049 0.0046 0.0044 0.0043 0.0043 0.0049 0.0052 0.0063 0.0069 0.0066 0.0059 0.0053 0.0055 0.0069 0.0122 +const double ColorTemp::JDC468_GreI8_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0230, 0.0232, 0.0234, 0.0254, 0.0263, 0.0298, 0.0329, 0.0367, 0.0377, 0.0388, 0.0399, 0.0410, 0.0421, 0.0440, 0.0460, 0.0481, 0.0496, 0.0523, 0.0559, 0.0645, 0.0727, 0.0878, 0.1020, 0.1156, 0.1288, 0.1334, 0.1394, 0.1398, + 0.1402, 0.1407, 0.1413, 0.1409, 0.1396, 0.1334, 0.1276, 0.1200, 0.1129, 0.1095, 0.1064, 0.1053, 0.1043, 0.1031, 0.1021, 0.1001, 0.0980, 0.0970, 0.0952, 0.0963, 0.0967, 0.0990, 0.1009, 0.1042, 0.1078, 0.1130, 0.1188, 0.1251, + 0.1307, 0.1335, 0.1374, 0.1376, 0.1378, 0.1362, 0.1345, 0.1312, 0.1278, 0.1257, 0.1240, 0.1290, 0.1345, 0.1476, 0.1615, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 + +}; + +// i8 green215 215 0.0230 0.0234 0.0263 0.0329 0.0377 0.0399 0.0421 0.0460 0.0496 0.0559 0.0727 0.1020 0.1288 0.1394 0.1402 0.1413 0.1396 0.1276 0.1129 0.1064 0.1043 0.1021 0.0980 0.0952 0.0967 0.1009 0.1078 0.1188 0.1307 0.1374 0.1378 0.1345 0.1278 0.1240 0.1345 0.1615 + +const double ColorTemp::JDC468_OraO18_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0826, 0.0830, 0.0832, 0.0861, 0.0892, 0.0993, 0.1108, 0.1180, 0.1248, 0.1253, 0.1263, 0.1261, 0.1259, 0.1267, 0.1289, 0.1304, 0.1319, 0.1370, 0.1419, 0.1631, 0.1851, 0.2311, 0.2743, 0.3131, 0.3536, 0.3551, 0.3585, 0.3488, 0.3322, + 0.3470, 0.3575, 0.3680, 0.3498, 0.3316, 0.3224, 0.3129, 0.3578, 0.4013, 0.4734, 0.5454, 0.5978, 0.6502, 0.6745, 0.6982, 0.7080, 0.7182, 0.7273, 0.7269, 0.7308, 0.7342, 0.7393, 0.7436, 0.7498, 0.7550, 0.7597, 0.7640, 0.7680, 0.7713, + 0.7766, 0.7786, 0.7816, 0.7841, 0.7863, 0.7889, 0.7902, 0.7931, 0.7957, 0.7997, 0.8068, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 + +}; +// o18 ora 382 382 0.0826 0.0832 0.0892 0.1108 0.1248 0.1263 0.1259 0.1289 0.1319 0.1419 0.1851 0.2743 0.3536 0.3585 0.3322 0.3470 0.3680 0.3316 0.3129 0.4013 0.5454 0.6502 0.6982 0.7182 0.7269 0.7342 0.7436 0.7550 0.7640 0.7713 0.7766 0.7816 0.7863 0.7902 0.7957 0.8068 +const double ColorTemp::JDC468_OraD17_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0462, 0.0442, 0.0422, 0.0401, 0.0383, 0.0390, 0.0396, 0.0396, 0.0395, 0.0388, 0.0380, 0.0378, 0.0376, 0.0381, 0.0384, 0.0391, 0.0399, 0.0421, 0.0451, 0.0561, 0.0676, 0.0934, 0.1189, 0.1432, 0.1671, 0.1650, 0.1632, 0.1512, 0.1402, 0.1456, + 0.1521, 0.1613, 0.1696, 0.1552, 0.1409, 0.1342, 0.1283, 0.1689, 0.2084, 0.2845, 0.3575, 0.4183, 0.4797, 0.5090, 0.5389, 0.5498, 0.5617, 0.5667, 0.5728, 0.5788, 0.5822, 0.5889, 0.5938, 0.6011, 0.6081, 0.6145, 0.6212, 0.6267, 0.6304, 0.6331, + 0.6352, 0.6361, 0.6373, 0.6372, 0.6370, 0.6376, 0.6384, 0.6413, 0.6483, 0.6523, 0.6668, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 + +}; + +// d17 ora 95 95 0.0462 0.0422 0.0383 0.0396 0.0395 0.0380 0.0376 0.0384 0.0399 0.0451 0.0676 0.1189 0.1671 0.1632 0.1402 0.1521 0.1696 0.1409 0.1283 0.2084 0.3575 0.4797 0.5389 0.5617 0.5728 0.5822 0.5938 0.6081 0.6212 0.6304 0.6352 0.6373 0.6370 0.6384 0.6483 0.6668 //spectral data ColorLab : Skin 35 15 17 const double ColorTemp::ColabSkin35_15_17_spect[97] = { @@ -827,7 +1699,877 @@ const double ColorTemp::ColabSky42_0_m24_spect[97] = { 0.0979, 0.112, 0.1269, 0.134, 0.1430, 0.147, 0.1497, 0.151, 0.1529, 0.1545, 0.1561, 0.158, 0.1603, 0.1616, 0.1627, 0.1625, 0.1623, 0.1614, 0.1605, 0.159, 0.1575, 0.1567, 0.1557, 0.1563, 0.1569, 0.159, 0.1627, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 }; +//spectral data ColorLab : blue 77 -44 -50 +const double ColorTemp::Colorblue_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0316, 0.0480, 0.0658, 0.0925, 0.1199, 0.1812, 0.2424, 0.2770, 0.3145, 0.3430, 0.3702, 0.4022, 0.4346, 0.4560, 0.4778, 0.4843, 0.4902, 0.4940, 0.4960, 0.4920, 0.4889, 0.4820, + 0.4764, 0.4685, 0.4606, 0.4486, 0.4379, 0.4160, 0.3955, 0.3640, 0.3330, 0.2990, 0.2660, 0.2291, 0.1991, 0.1705, 0.1403, 0.1220, 0.1067, 0.0967, 0.0907, 0.0846, 0.0785, 0.0698, + 0.0601, 0.0525, 0.0455, 0.0423, 0.0386, 0.0370, 0.0358, 0.0354, 0.0351, 0.0368, 0.0382, 0.0413, 0.0449, 0.0474, 0.0492, 0.0484, 0.0477, 0.0460, 0.0437, 0.0402, 0.0371, 0.0349, + 0.0329, 0.0341, 0.0356, 0.0410, 0.0462, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 + +}; +//0.1571 0.2150 0.3040 0.3684 0.3952 0.3965 0.3782 0.3418 0.2995 0.2543 0.2043 0.1686 0.1420 0.1070 0.0785 0.0725 0.0755 0.0695 0.0680 0.0914 0.1379 0.1833 0.2038 0.2065 0.2079 0.2110 0.2176 0.2319 0.2518 0.2632 0.2616 0.2522 0.2380 0.2290 0.2432 0.2901 + +const double ColorTemp::ColorViolA1_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1571, 0.185, 0.2150, 0.255, 0.3040, 0.332, 0.3684, 0.381, 0.3952, 0.3956, 0.3965, 0.387, 0.3782, 0.362, 0.3418, 0.322, 0.2995, 0.275, 0.2543, 0.229, 0.2043, 0.185, 0.1686, + 0.155, 0.1420, 0.131, 0.1070, 0.093, 0.0785, 0.075, 0.0725, 0.074, 0.0755, 0.072, 0.0695, 0.069, 0.0680, 0.083, 0.0914, 0.115, 0.1379, 0.162, 0.1833, 0.193, 0.2038, 0.205, + 0.2065, 0.207, 0.2079, 0.209, 0.2110, 0.214, 0.2176, 0.226, 0.2319, 0.242, 0.2518, 0.258, 0.2632, 0.263, 0.2616, 0.256, 0.2522, 0.246, 0.2380, 0.233, 0.2290, 0.235, 0.2432, 0.265, 0.2901, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//0.2270 0.2413 0.3287 0.4079 0.4469 0.4594 0.4535 0.4268 0.3886 0.3427 0.2866 0.2433 0.2087 0.1604 0.1181 0.1069 0.1098 0.0985 0.0916 0.1130 0.1496 0.1746 0.1783 0.1742 0.1738 0.1763 0.1831 0.1975 0.2169 0.2274 0.2247 0.2140 0.1990 0.1897 0.2039 0.2508 + +const double ColorTemp::ColorViolA4_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2270, 0231, 0.2413, 0.286, 0.3287, 0.367, 0.4079, 0.427, 0.4469, 0.452, 0.4594, 0.456, 0.4535, 0.432, 0.4268, 0.403, 0.3886, 0.368, 0.3427, 0.314, 0.2866, 0.265, 0.2433, 0.222, + 0.2087, 0.183, 0.1604, 0.130, 0.1181, 0.112, 0.1069, 0.108, 0.1098, 0.103, 0.0985, 0.094, 0.0916, 0.104, 0.1130, 0.131, 0.1496, 0.152, 0.1746, 0.176, 0.1783, 0.176, 0.1742, 0.174, + 0.1738, 0.175, 0.1763, 0.181, 0.1831, 0.192, 0.1975, 0.206, 0.2169, 0.222, 0.2274, 0.226, 0.2247, 0.219, 0.2140, 0.206, 0.1990, 0.195, 0.1897, 0.196, 0.2039, 0.221, 0.2508, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//0.1426 0.2660 0.3556 0.4259 0.4459 0.4317 0.3942 0.3425 0.2917 0.2413 0.1885 0.1524 0.1267 0.0948 0.0700 0.0661 0.0708 0.0671 0.0699 0.1092 0.2099 0.3582 0.4857 0.5583 0.5950 0.6146 0.6307 0.6495 0.6720 0.6825 0.6809 0.6718 0.6593 0.6517 0.6649 0.7066 +const double ColorTemp::ColorViolA6_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1426, 0.203, 0.2660, 0.315, 0.3556, 0.392, 0.4259, 0.435, 0.4459, 0.437, 0.4317, 0.417, 0.3942, 0.365, 0.3425, 0.317, 0.2917, 0.266, 0.2413, 0.218, 0.1885, 0.172, 0.1524, 0.141, + 0.1267, 0.112, 0.0948, 0.083, 0.0700, 0.068, 0.0661, 0.068, 0.0708, 0.069, 0.0671, 0.068, 0.0699, 0.900, 0.1092, 0.159, 0.2099, 0.284, 0.3582, 0.441, 0.4857, 0.525, 0.5583, 0.567, + 0.5950, 0.605, 0.6146, 0.623, 0.6307, 0.638, 0.6495, 0.661, 0.6720, 0.679, 0.6825, 0.681, 0.6809, 0.675, 0.6718, 0.667, 0.6593, 0.655, 0.6517, 0.658, 0.6649, 0.681, 0.7066, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//0.4939 0.3859 0.4198 0.4780 0.5328 0.5672 0.5880 0.5994 0.6029 0.5981 0.5808 0.5618 0.5369 0.4819 0.4190 0.3921 0.3815 0.3400 0.2991 0.2977 0.3090 0.3088 0.2930 0.2753 0.2660 0.2636 0.2678 0.2811 0.2995 0.3125 0.3153 0.3111 0.3006 0.2952 0.3116 0.3584 +const double ColorTemp::ColorBlueSkyK3_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.4939, 0.435, 0.3859, 0.403, 0.4198, 0.446, 0.4780, 0.505, 0.5328, 0.552, 0.5672, 0.578, 0.5880, 0.595, 0.5994, 0.602, 0.6029, 0.600, 0.5981, 0.588, 0.5808, 0.571, 0.5618, 0.551, + 0.5369, 0.503, 0.4819, 0.452, 0.4190, 0.404, 0.3921, 0.386, 0.3815, 0.364, 0.3400, 0.321, 0.2991, 0.298, 0.2977, 0.304, 0.3090, 0.309, 0.3088, 0.302, 0.2930, 0.284, 0.2753, 0.271, + 0.2660, 0.265, 0.2636, 0.266, 0.2678, 0.275, 0.2811, 0.290, 0.2995, 0.306, 0.3125, 0.314, 0.3153, 0.313, 0.3111, 0.307, 0.3006, 0.298, .2952, 0.306, 0.3116, 0.325, 0.3584, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//0.4058 0.4734 0.5372 0.6051 0.6698 0.6992 0.7118 0.7135 0.7071 0.6938 0.6702 0.6511 0.6282 0.5732 0.5103 0.4913 0.4926 0.4604 0.4341 0.4648 0.5111 0.5335 0.5283 0.5154 0.5098 0.5093 0.5151 0.5309 0.5520 0.5642 0.5657 0.5598 0.5489 0.5430 0.5601 0.6067 + +const double ColorTemp::ColorBlueSkyK9_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.4058, 0.441, 0.4734, 0.502, 0.5372, 0.585, 0.6051, 0.643, 0.6698, 0.685, 0.6992, 0.705, 0.7118, 0.712, 0.7135, 0.711, 0.7071, 0.702, 0.6938, 0.681, 0.6702, 0.663, 0.6511, 0.642, + 0.6282, 0.604, 0.5732, 0.542, 0.5103, 0.499, 0.4913, 0.492, 0.4926, 0.475, 0.4604, 0.452, 0.4341, 0.453, 0.4648, 0.496, 0.5111, 0.525, 0.5335, 0.531, 0.5283, 0.522, 0.5154, 0.512, + 0.5098, 0.509, 0.5093, 0.513, 0.5151, 0.523, 0.5309, 0.544, 0.5520, 0.562, 0.5642, 0.565, 0.5657, 0.562, 0.5598, 0.554, 0.5489, 0.546, 0.5430, 0.553, 0.5601, 0.576, 0.6067, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//42 C4 0.3280 0.2611 0.3781 0.4646 0.5292 0.5732 0.6112 0.6307 0.6310 0.6181 0.5847 0.5488 0.5066 0.4358 0.3585 0.3151 0.2855 0.2309 0.1786 0.1546 0.1443 0.1359 0.1245 0.1151 0.1120 0.1127 0.1169 0.1275 0.1421 0.1504 0.1488 0.1416 0.1303 0.1241 0.1355 0.1739 +const double ColorTemp::ColorBlueSkyC4_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.3280, 0.2950, 0.2611, 0.304, 0.3781, 0.423, 0.4646, 0.498, 0.5292, 0.555, 0.5732, 0.591, 0.6112, 0.6221, 0.6307, 0.631, 0.6310, 0.625, 0.6181, 0.607, 0.5847, 0.563, 0.5488, 0.524, + 0.5066, 0.465, 0.4358, 0.398, 0.3585, 0.336, 0.3151, 0.302, 0.2855, 0.254, 0.2309, 0.203, 0.1786, 0.166, 0.1546, 0.149, 0.1443, 0.143, 0.1359, 0.131, 0.1245, 0.123, 0.115, 0.114, + 0.1120, 0.112, 0.1127, 0.114, 0.1169, 0.122, 0.1275, 0.133, 0.1421, 0.147, 0.1504, 0.149, 0.1488, 0.145, 0.1416, 0.136, 0.1303, 0.127, 0.1241, 0.132, 0.1355, 0.155, 0.1739, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//52 C14 0.5697 0.4660 0.5000 0.5560 0.6072 0.6402 0.6632 0.6850 0.7069 0.7292 0.7488 0.7678 0.7786 0.7721 0.7544 0.7394 0.7232 0.6889 0.6446 0.6171 0.5966 0.5743 0.5425 0.5093 0.4884 0.4784 0.4774 0.4822 0.4944 0.5076 0.5186 0.5268 0.5303 0.5332 0.5454 0.5760 +const double ColorTemp::ColorBlueSkyC14_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.5697, 0.511, 0.4660, 0.481, 0.5000, 0.528, 0.5560, 0.583, 0.6072, 0.622, 0.6402, 0.653, 0.6632, 0.674, 0.6850, 0.699, 0.7069, 0.717, 0.7292, 0.735, 0.7488, 0.757, 0.7678, 0.773, + 0.7786, 0.776, 0.7721, 0.765, 0.7544, 0.746, 0.7394, 0.731, 0.7232, 0.704, 0.6889, 0.674, 0.6446, 0.631, 0.6171, 0.606, 0.5966, 0.585, 0.5743, 0.5570, 0.5425, 0.529, 0.5093, 0.498, + 0.4884, 0.482, 0.4784, 0.478, 0.4774, 0.481, 0.4822, 0.487, 0.4944, 0.503, 0.5076, 0.512, 0.5186, 0.522, 0.5268, 0.529, 0.5303, 0.532, 0.5332, 0.539, 0.5454, 0.565, 0.5760, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//80 E4 0.1483 0.1756 0.2536 0.3084 0.3665 0.4189 0.4746 0.5127 0.5239 0.5193 0.4917 0.4569 0.4123 0.3422 0.2672 0.2179 0.1820 0.1356 0.0972 0.0784 0.0698 0.0646 0.0592 0.0556 0.0546 0.0551 0.0571 0.0611 0.0670 0.0701 0.0692 0.0661 0.0620 0.0606 0.0663 0.0834 +const double ColorTemp::ColorBlueSkyE4_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1483, 0.161, 0.1756, 0.213, 0.2536, 0.283, 0.3084, 0.331, 0.3665, 0.387, 0.4189, 0.445, 0.4746, 0.496, 0.5127, 0.519, 0.5239, 0.522, 0.5193, 0.508, 0.4917, 0.476, 0.4569, 0.431, + 0.4123, 0.375, 0.3422, 0.309, 0.2672, 0.242, 0.2179, 0.208, 0.1820, 0.162, 0.1356, 0.113, 0.0972, 0.091, 0.0784, 0.073, 0.0698, 0.066, 0.0646, 0.062, 0.0592, 0.057, 0.0556, 0.055, + 0.0546, 0.055, 0.0551, 0.056, 0.0571, 0.059, 0.0611, 0.064, 0.0670, 0.069, 0.0701, 0.070, 0.0692, 0.067, 0.0661, 0.065, 0.0620, 0.061, 0.0606, 0.063, 0.0663, 0.072, 0.0834, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//229 M1 0.3100 0.2922 0.3514 0.4042 0.4443 0.4769 0.5002 0.5133 0.5187 0.5179 0.5057 0.4928 0.4729 0.4235 0.3643 0.3371 0.3234 0.2827 0.2418 0.2338 0.2370 0.2329 0.2184 0.2028 0.1958 0.1937 0.1973 0.2084 0.2244 0.2351 0.2372 0.2331 0.2239 0.2178 0.2319 0.2731 +const double ColorTemp::ColorBlueSkyM1_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.3100, 0.303, 0.2922, 0.322, 0.3514, 0.376, 0.4042, 0.424, 0.4443, 0.457, 0.4769, 0.497, 0.5002, 0.507, 0.5133, 0.516, 0.5187, 0.518, 0.5179, 0.511, 0.5057, 0.497, 0.4928, 0.483, + 0.4729, 0.454, 0.4235, 0.398, 0.3643, 0.346, 0.3371, 0.329, 0.3234, 0.301, 0.2827, 0.263, 0.2418, 0.235, 0.2338, 0.235, 0.2370, 0.236, 0.2329, 0.226, 0.2184, 0.213, 0.2028, 0.198, + 0.1958, 0.194, 0.1937, 0.196, 0.1973, 0.203, 0.2084, 0.212, 0.2244, 0.233, 0.2351, 0.236, 0.2372, 0.234, 0.2331, 0.229, 0.2239, 0.222, 0.2178, 0.224, 0.2319, 0.251, 0.2731, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//514 2B1 0.5277 0.4431 0.4972 0.5820 0.6387 0.6750 0.7001 0.7140 0.7202 0.7193 0.7053 0.6891 0.6657 0.6181 0.5614 0.5312 0.5101 0.4589 0.4045 0.3857 0.3826 0.3751 0.3574 0.3393 0.3314 0.3304 0.3368 0.3523 0.3742 0.3874 0.3883 0.3818 0.3693 0.3616 0.3800 0.4324 +const double ColorTemp::ColorBlueSky2B1_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.5277, 0.485, 0.4431, 0.476, 0.4972, 0.539, 0.5820, 0.607, 0.6387, 0.653, 0.6750, 0.691, 0.7001, 0.707, 0.7140, 0.718, 0.7202, 0.720, 0.7193, 0.713, 0.7053, 0.695, 0.6891, 0.674, + 0.6657, 0.632, 0.6181, 0.587, 0.5614, 0.543, 0.5312, 0.521, 0.5101, 0.483, 0.4589, 0.431, 0.4045, 0.398, 0.3857, 0.385, 0.3826, 0.376, 0.3751, 0.364, 0.3574, 0.346, 0.3393, 0.335, + 0.3314, 0.331, 0.3304, 0.333, 0.3368, 0.346, 0.3523, 0.363, 0.3742, 0.382, 0.3874, 0.385, 0.3883, 0.384, 0.3818, 0.375, 0.3693, 0.364, 0.3616, 0.374, 0.3800, 0.396, 0.4324, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//368 T7 0.1943 0.3199 0.4536 0.5443 0.6043 0.6499 0.6839 0.7125 0.7329 0.7482 0.7527 0.7514 0.7383 0.7028 0.6526 0.6034 0.5500 0.4708 0.3848 0.3268 0.2929 0.2712 0.2493 0.2316 0.2243 0.2234 0.2288 0.2436 0.2640 0.2762 0.2767 0.2693 0.2566 0.2489 0.2665 0.3165 +const double ColorTemp::ColorBlueSkyT7_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1943, 0.256, 0.3199, 0.376, 0.4536, 0.494, 0.5443, 0.572, 0.6043, 0.631, 0.6499, 0.664, 0.6839, 0.698, 0.7125, 0.726, 0.7329, 0.741, 0.7482, 0.751, 0.7527, 0.752, 0.7514, 0.745, + 0.7383, 0.721, 0.7028, 0.675, 0.6526, 0.631, 0.6034, 0.589, 0.5500, 0.512, 0.4708, 0.432, 0.3848, 0.342, 0.3268, 0.311, 0.2929, 0.282, 0.2712, 0.261, 0.2493, 0.236, 0.2316, 0.227, + 0.2243, 0.223, 0.2234, 0.229, 0.2288, 0.235, 0.2436, 0.255, 0.2640, 0.268, 0.2762, 0.277, 0.2767, 0.272, 0.2693, 0.263, 0.2566, 0.254, 0.2489, 0.255, 0.2665, 0.275, 0.3165, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + + +//399 U19 0.5829 0.4865 0.4927 0.5690 0.6221 0.6532 0.6728 0.6832 0.6889 0.6884 0.6771 0.6648 0.6465 0.6038 0.5524 0.5297 0.5194 0.4797 0.4387 0.4356 0.4455 0.4444 0.4282 0.4094 0.4009 0.3992 0.4046 0.4185 0.4385 0.4515 0.4545 0.4505 0.4411 0.4368 0.4539 0.5013 +const double ColorTemp::ColorBlueSkyU19_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.5829, 0.534, 0.4865, 0.489, 0.4927, 0.532, 0.5690, 0.593, 0.6221, 0.641, 0.6532, 0.662, 0.6728, 0.674, 0.6832, 0.687, 0.6889, 0.688, 0.6884, 0.683, 0.6771, 0.671, 0.6648, 0.665, + 0.6465, 0.622, 0.6038, 0.583, 0.5524, 0.542, 0.5297, 0.523, 0.5194, 0.492, 0.4797, 0.451, 0.4387, 0.436, 0.4356, 0.442, 0.4455, 0.445, 0.4444, 0.432, 0.4282, 0.413, 0.4094, 0.404, + 0.4009, 0.400, 0.3992, 0.402, 0.4046, 0.411, 0.4185, 0.426, 0.4385, 0.446, 0.4515, 0.452, 0.4545, 0.452, 0.4505, 0.446, 0.4411, 0.438, 0.4368, 0.443, 0.4539, 0.467, 0.5013, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//382 U2 0.3594 0.3425 0.3214 0.3654 0.4097 0.4360 0.4590 0.4793 0.5002 0.5234 0.5476 0.5745 0.5940 0.5901 0.5703 0.5545 0.5384 0.5029 0.4592 0.4334 0.4149 0.3947 0.3657 0.3363 0.3177 0.3087 0.3077 0.3123 0.3231 0.3351 0.3454 0.3520 0.3545 0.3562 0.3674 0.3976 +const double ColorTemp::ColorBlueSkyU2_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.3594, 0.345, 0.3425, 0.333, 0.3214, 0.346, 0.3654, 0.387, 0.4097, 0.424, 0.4360, 0.446, 0.4590, 0.467, 0.4793, 0.494, 0.5002, 0.517, 0.5234, 0.538, 0.5476, 0.564, 0.5745, 0.583, + 0.5940, 0.593, 0.5901, 0.580, 0.5703, 0.563, 0.5545, 0.546, 0.5384, 0.521, 0.5029, 0.478, 0.4592, 0.444, 0.4334, 0.421, 0.4149, 0.408, 0.3947, 0.378, 0.3657, 0.352, 0.3363, 0.324, + 0.3177, 0.313, 0.3087, 0.308, 0.3077, 0.310, 0.3123, 0.317, 0.3231, 0.329, 0.3351, 0.339, 0.3454, 0.348, 0.3520, 0.353, 0.3545, 0.355, 0.3562, 0.359, 0.3674, 0.375, 0.3976, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + + +//378 T17 0.4213 0.3332 0.4205 0.5078 0.5650 0.6025 0.6223 0.6279 0.6195 0.5981 0.5578 0.5197 0.4785 0.4074 0.3325 0.3030 0.2918 0.2511 0.2125 0.2105 0.2198 0.2199 0.2083 0.1945 0.1895 0.1898 0.1954 0.2094 0.2288 0.2406 0.2399 0.2317 0.2189 0.2108 0.2261 0.2755 +const double ColorTemp::ColorBlueSkyT17_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.4213, 0.376, 0.3332, 0.387, 0.4205, 0.467, 0.5078, 0.532, 0.5650, 0.587, 0.6025, 0.611, 0.6223, 0.624, 0.6279, 0.623, 0.6195, 0.607, 0.5981, 0.576, 0.5578, 0.534, 0.5197, 0.499, + 0.4785, 0.435, 0.4074, 0.376, 0.3325, 0.317, 0.3030, 0.295, 0.2918, 0.272, 0.2511, 0.235, 0.2125, 0.212, 0.2105, 0.214, 0.2198, 0.219, 0.2199, 0.215, 0.2083, 0.202, 0.1945, 0.191, + 0.1895, 0.189, 0.1898, 0.193, 0.1954, 0.202, 0.2094, 0.215, 0.2288, 0.236, 0.2406, 0.240, 0.2399, 0.236, 0.2317, 0.225, 0.2189, 0.214, 0.2108, 0.218, 0.2261, 0.245, 0.2755, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//236 M8 -0.0593 0.0128 0.0031 0.0149 0.0197 0.0221 0.0223 0.0230 0.0232 0.0237 0.0243 0.0247 0.0249 0.0249 0.0248 0.0247 0.0244 0.0240 0.0240 0.0242 0.0244 0.0247 0.0252 0.0254 0.0262 0.0269 0.0271 0.0273 0.0278 0.0280 0.0276 0.0275 0.0282 0.0288 0.0295 0.0303 +const double ColorTemp::ColorBlackM8_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0593, 0.040, 0.0128, 0.023, 0.0031, 0.024, 0.0149, 0.017, 0.0197, 0.021, 0.0221, 0.022, 0.0223, 0.023, 0.0230, 0.023, 0.0232, 0.023, 0.0237, 0.024, 0.0243, 0.024, 0.0247, 0.024, + 0.0249, 0.025, 0.0249, 0.025, 0.0248, 0.025, 0.0247, 0.024, 0.0244, 0.024, 0.0240, 0.024, 0.0240, 0.024, 0.0242, 0.024, 0.0244, 0.024, 0.0247, 0.025, 0.0252, 0.025, 0.0254, 0.026, + 0.0262, 0.027, 0.0269, 0.027, 0.0271, 0.027, 0.0273, 0.027, 0.0278, 0.028, 0.0280, 0.028, 0.0276, 0.028, 0.0275, 0.028, 0.0282, 0.028, 0.0288, 0.029, 0.0295, 0.030, 0.0303, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//240 M12 -0.0377 0.0146 0.0167 0.0222 0.0257 0.0261 0.0270 0.0271 0.0274 0.0281 0.0287 0.0299 0.0306 0.0304 0.0297 0.0285 0.0277 0.0267 0.0257 0.0257 0.0258 0.0259 0.0263 0.0276 0.0279 0.0288 0.0297 0.0302 0.0304 0.0303 0.0302 0.0303 0.0310 0.0321 0.0337 0.0356 +const double ColorTemp::ColorBlackM12_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0377, 0.022, 0.0146, 0.015, 0.0167, 0.020, 0.0222, 0.023, 0.0257, 0.026, 0.0261, 0.027, 0.0270, 0.027, 0.0271, 0.027, 0.0274, 0.028, 0.0281, 0.028, 0.0287, 0.029, 0.0299, 0.030, + 0.0306, 0.030, 0.0304, 0.030, 0.0297, 0.029, 0.0285, 0.028, 0.0277, 0.027, 0.0267, 0.026, 0.0257, 0.026, 0.0257, 0.026, 0.0258, 0.026, 0.0259, 0.026, 0.0263, 0.027, 0.0276, 0.028, + 0.0279, 0.028, 0.0288, 0.029, 0.0297, 0.030, 0.0302, 0.030, 0.0304, 0.030, 0.0303, 0.030, 0.0302, 0.030, 0.0303, 0.031, 0.0310, 0.031, 0.0321, 0.033, 0.0337, 0.035, 0.0356, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//241 M13 0.2961 0.0487 0.0261 0.0330 0.0296 0.0305 0.0305 0.0314 0.0320 0.0322 0.0335 0.0348 0.0352 0.0347 0.0336 0.0325 0.0314 0.0299 0.0284 0.0284 0.0286 0.0288 0.0290 0.0299 0.0306 0.0314 0.0320 0.0328 0.0332 0.0331 0.0330 0.0328 0.0337 0.0350 0.0366 0.0385 +const double ColorTemp::ColorBlackM13_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2961, 0.100, 0.0487, 0.035, 0.0261, 0.030, 0.0330, 0.031, 0.0296, 0.030, 0.0305, 0.030, 0.0305, 0.031, 0.0314, 0.032, 0.0320, 0.032, 0.0322, 0.033, 0.0335, 0.034, 0.0348, 0.035, + 0.0352, 0.035, 0.0347, 0.034, 0.0336, 0.033, 0.0325, 0.032, 0.0314, 0.030, 0.0299, 0.029, 0.0284, 0.028, 0.0284, 0.029, 0.0286, 0.029, 0.0288, 0.029, 0.0290, 0.030, 0.0299, 0.030, + 0.0306, 0.031, 0.0314, 0.032, 0.0320, 0.032, 0.0328, 0.033, 0.0332, 0.033, 0.0331, 0.033, 0.0330, 0.033, 0.0328, 0.033, 0.0337, 0.034, 0.0350, 0.036, 0.0366, 0.037, 0.0385, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//525 2B12 0.3848 0.4127 0.4780 0.5375 0.5917 0.6194 0.6353 0.6485 0.6625 0.6784 0.7010 0.7367 0.7706 0.7847 0.7843 0.7826 0.7799 0.7689 0.7521 0.7463 0.7401 0.7314 0.7168 0.7008 0.6904 0.6860 0.6861 0.6896 0.6986 0.7064 0.7138 0.7185 0.7233 0.7281 0.7338 0.7498 +const double ColorTemp::ColorWhite2B12_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.3848, 0.405, 0.4127, 0.435, 0.4780, 0.501, 0.5375, 0.572, 0.5917, 0.606, 0.6194, 0.627, 0.6353, 0.642, 0.6485, 0.653, 0.6625, 0.669, 0.6784, 0.692, 0.7010, 0.072, 0.7367, 0.0760, + 0.7706, 0.775, 0.7847, 0.784, 0.7843, 0.784, 0.7826, 0.781, 0.7799, 0.775, 0.7689, 0.762, 0.7521, 0.748, 0.7463, 0.743, 0.7401, 0.731, 0.7314, 0.723, 0.7168, 0.705, 0.7008, 0.701, + 0.6904, 0.689, 0.6860, 0.686, 0.6861, 0.687, 0.6896, 0.691, 0.6986, 0.701, 0.7064, 0.711, 0.7138, 0.715, 0.7185, 0.721, 0.7233, 0.725, 0.7281, 0.731, 0.7338, 0.741, 0.7498, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//527 2B14 0.6608 0.5900 0.6114 0.6747 0.7329 0.7599 0.7706 0.7776 0.7831 0.7890 0.7952 0.8074 0.8185 0.8214 0.8201 0.8218 0.8244 0.8229 0.8192 0.8281 0.8344 0.8388 0.8415 0.8445 0.8495 0.8521 0.8556 0.8604 0.8666 0.8687 0.8687 0.8672 0.8682 0.8703 0.8720 0.8803 +const double ColorTemp::ColorWhite2B14_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.6608, 0.631, 0.5900, 0.605, 0.6114, 0.634, 0.6747, 0.698, 0.7329, 0.745, 0.7599, 0.765, 0.7706, 0.775, 0.7776, 0.781, 0.7831, 0.786, 0.7890, 0.792, 0.7952, 0.797, 0.8074, 0.810, + 0.8185, 0.821, 0.8214, 0.821, 0.8201, 0.821, 0.8218, 0.822, 0.8244, 0.823, 0.8229, 0.822, 0.8192, 0.824, 0.8281, 0.831, 0.8344, 0.836, 0.8388, 0.840, 0.8415, 0.843, 0.8445, 0.847, + 0.8495, 0.851, 0.8521, 0.853, 0.8556, 0.858, 0.8604, 0.863, 0.8666, 0.867, 0.8687, 0.869, 0.8687, 0.867, 0.8672, 0.868, 0.8682, 0.870, 0.8703, 0.871, 0.8720, 0.874, 0.8803, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//97 97 0.0031 0.0047 0.0056 0.0064 0.0070 0.0070 0.0071 0.0066 0.0065 0.0065 0.0064 0.0063 0.0063 0.0058 0.0052 0.0052 0.0053 0.0047 0.0044 0.0052 0.0066 0.0077 0.0081 0.0082 0.0084 0.0089 0.0096 0.0106 0.0121 0.0127 0.0128 0.0124 0.0115 0.0117 0.0133 0.0169 +const double ColorTemp::JDC468_Blackred97_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0031, 0.0035, 0.0047, 0.0050, 0.0056, 0.0060, 0.0064, 0.0065, 0.0070, 0.007, 0.0070, 0.007, 0.0071, 0.007, 0.0066, 0.007, 0.0065, 0.006, 0.0065, 0.006, 0.0064, 0.006, 0.0063, + 0.006, 0.0063, 0.006, 0.0058, 0.005, 0.0052, 0.005, 0.0052, 0.005, 0.0053, 0.005, 0.0047, 0.005, 0.0044, 0.005, 0.0052, 0.006, 0.0066, 0.007, 0.0077, 0.008, 0.0081, 0.008, 0.008, + 0.008, 0.0084, 0.009, 0.0089, 0.009, 0.0096, 0.01, 0.0106, 0.011, 0.0121, 0.012, 0.0127, 0.012, 0.0128, 0.012, 0.0124, 0.012, 0.0115, 0.012, 0.0117, 0.013, 0.0133, 0.015, 0.0169, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//443 443 0.0067 0.0068 0.0067 0.0074 0.0083 0.0088 0.0092 0.0093 0.0098 0.0099 0.0101 0.0106 0.0109 0.0104 0.0094 0.0086 0.0075 0.0058 0.0044 0.0039 0.0037 0.0038 0.0036 0.0035 0.0036 0.0033 0.0033 0.0036 0.0038 0.0042 0.0041 0.0036 0.0033 0.0035 0.0042 0.0062 +const double ColorTemp::JDC468_Blackredbl443_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0067, 0.0067, 0.0068, 0.0068, 0.0067, 0.0070, 0.0074, 0.008, 0.0083, 0.0085, 0.0088, 0.009, 0.0092, 0.0092, 0.0093, 0.0096, 0.0098, 0.0098, 0.0099, 0.01, 0.0101, 0.0104, 0.0106, + 0.0106, 0.0109, 0.0105, 0.0104, 0.01, 0.0094, 0.09, 0.0086, 0.08, 0.0075, 0.06, 0.0058, 0.05, 0.0044, 0.04, 0.0039, 0.0038, 0.0037, 0.0037, 0.0038, 0.0037, 0.0036, 0.0036, + 0.0035, 0.0036, 0.0036, 0.0034, 0.0033, 0.0033, 0.0033, 0.0035, 0.0036, 0.0037, 0.0038, 0.004, 0.0042, 0.004, 0.0041, 0.004, 0.0036, 0.0034, 0.0033, 0.0034, 0.0035, 0.004, 0.0042, 0.005, 0.0062, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//27 27 0.0060 0.0064 0.0070 0.0076 0.0086 0.0086 0.0088 0.0089 0.0089 0.0083 0.0079 0.0078 0.0077 0.0067 0.0059 0.0057 0.0056 0.0046 0.0041 0.0045 0.0050 0.0056 0.0054 0.0053 0.0054 0.0055 0.0057 0.0065 0.0073 0.0079 0.0080 0.0075 0.0067 0.0068 0.0081 0.0114 +const double ColorTemp::JDC468_Blackbl27_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0060, 0.0062, 0.0064, 0.0066, 0.0070, 0.0073, 0.0076, 0.008, 0.0086, 0.0086, 0.0086, 0.0087, 0.0088, 0.0088, 0.0089, 0.0089, 0.0089, 0.0085, 0.0083, 0.008, 0.0079, 0.0078, 0.0078, + 0.0078, 0.0077, 0.007, 0.0067, 0.006, 0.0059, 0.0057, 0.0057, 0.0057, 0.0056, 0.005, 0.0046, 0.0045, 0.0041, 0.0043, 0.0045, 0.0047, 0.0050, 0.0053, 0.0056, 0.0055, 0.0054, 0.0055, + 0.0053, 0.0053, 0.0054, 0.0054, 0.0055, 0.0056, 0.0057, 0.006, 0.0065, 0.007, 0.0073, 0.0075, 0.0079, 0.008, 0.0080, 0.008, 0.0075, 0.007, 0.0067, 0.0067, 0.0068, 0.007, 0.0081, 0.01, 0.0114, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//28 28 0.0092 0.0118 0.0155 0.0218 0.0267 0.0296 0.0312 0.0306 0.0282 0.0244 0.0205 0.0186 0.0167 0.0126 0.0091 0.0080 0.0071 0.0050 0.0042 0.0042 0.0044 0.0045 0.0045 0.0042 0.0041 0.0039 0.0040 0.0043 0.0048 0.0050 0.0047 0.0042 0.0041 0.0042 0.0049 0.0074 +const double ColorTemp::JDC468_Blackbl28_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0092, 0.01, 0.0118, 0.012, 0.0155, 0.016, 0.0218, 0.025, 0.0267, 0.028, 0.0296, 0.03, 0.0312, 0.031, 0.0306, 0.03, 0.0282, 0.026, 0.0244, 0.022, 0.0205, 0.02, 0.0186, 0.017, 0.0167, + 0.015, 0.0126, 0.01, 0.0091, 0.0085, 0.0080, 0.0075, 0.0071, 0.006, 0.0050, 0.05, 0.0042, 0.0042, 0.0042, 0.0043, 0.0044, 0.0044, 0.0045, 0.0045, 0.0045, 0.0043, 0.0042, 0.0042, + 0.0041, 0.004, 0.0039, 0.004, 0.0040, 0.004, 0.0043, 0.0044, 0.0048, 0.005, 0.0050, 0.0048, 0.0047, 0.0045, 0.0042, 0.0041, 0.0041, 0.0041, 0.0042, 0.0045, 0.0049, 0.006, 0.0074, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//214 214 0.0072 0.0062 0.0061 0.0064 0.0069 0.0071 0.0075 0.0081 0.0082 0.0088 0.0103 0.0126 0.0145 0.0146 0.0140 0.0133 0.0118 0.0094 0.0070 0.0059 0.0051 0.0046 0.0045 0.0043 0.0045 0.0045 0.0048 0.0056 0.0065 0.0072 0.0067 0.0065 0.0057 0.0058 0.0068 0.0103 +const double ColorTemp::JDC468_Blackgr214_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0072, 0.007, 0.0062, 0.0062, 0.0061, 0.0063, 0.0064, 0.0067, 0.0069, 0.007, 0.0071, 0.0072, 0.0075, 0.008, 0.0081, 0.008, 0.0082, 0.0085, 0.0088, 0.009, 0.0103, 0.011, 0.0126, + 0.012, 0.0145, 0.0145, 0.0146, 0.014, 0.0140, 0.014, 0.0133, 0.012, 0.0118, 0.01, 0.0094, 0.008, 0.0070, 0.006, 0.0059, 0.0055, 0.0051, 0.005, 0.0046, 0.0045, 0.0045, 0.0044, + 0.0043, 0.0044, 0.0045, 0.0045, 0.0045, 0.0046, 0.0048, 0.005, 0.0056, 0.006, 0.0065, 0.007, 0.0072, 0.007, 0.0067, 0.0066, 0.0065, 0.006, 0.0057, 0.0056, 0.0058, 0.006, 0.0068, 0.008, 0.0103, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + + +//436 436 0.0095 0.0123 0.0173 0.0242 0.0293 0.0317 0.0310 0.0283 0.0246 0.0197 0.0152 0.0129 0.0112 0.0083 0.0063 0.0059 0.0056 0.0045 0.0043 0.0050 0.0059 0.0064 0.0062 0.0060 0.0060 0.0062 0.0066 0.0075 0.0086 0.0093 0.0089 0.0082 0.0073 0.0072 0.0088 0.0139 +const double ColorTemp::JDC468_Blackbl436_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0095, 0.01, 0.0123, 0.013, 0.0173, 0.02, 0.0242, 0.026, 0.0293, 0.03, 0.0317, 0.031, 0.0310, 0.03, 0.0283, 0.025, 0.0246, 0.02, 0.0197, 0.018, 0.0152, 0.014, 0.0129, 0.012, + 0.0112, 0.01, 0.0083, 0.007, 0.0063, 0.006, 0.0059, 0.0058, 0.0056, 0.005, 0.0045, 0.0045, 0.0043, 0.005, 0.0050, 0.0055, 0.0059, 0.006, 0.0064, 0.0063, 0.0062, 0.006, 0.0060, + 0.006, 0.0060, 0.006, 0.0062, 0.0064, 0.0066, 0.007, 0.0075, 0.008, 0.0086, 0.009, 0.0093, 0.009, 0.0089, 0.0086, 0.0082, 0.008, 0.0073, 0.0072, 0.0072, 0.008, 0.0088, 0.01, 0.0139, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + + +//455 455 0.1560 0.1943 0.2724 0.4469 0.5896 0.6393 0.6390 0.6239 0.6096 0.5895 0.5698 0.5662 0.5603 0.5304 0.4977 0.4975 0.4998 0.4601 0.4261 0.4520 0.4986 0.5237 0.5270 0.5260 0.5297 0.5375 0.5504 0.5711 0.5910 0.6023 0.6029 0.5977 0.5880 0.5830 0.5978 0.6345 +const double ColorTemp::JDC468_Whitebl455_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1560, 0.18, 0.1943, 0.25, 0.2724, 0.40, 0.4469, 0.50, 0.5896, 0.60, 0.6393, 0.639, 0.6390, 0.625, 0.6239, 0.61, 0.6096, 0.60, 0.5895, 0.57, 0.5698, 0.567, 0.5662, 0.56, + 0.5603, 0.55, 0.5304, 0.51, 0.4977, 0.498, 0.4975, 0.498, 0.4998, 0.47, 0.4601, 0.44, 0.4261, 0.43, 0.4520, 0.47, 0.4986, 0.51, 0.5237, 0.525, 0.5270, 0.526, 0.5260, 0.528, + 0.5297, 0.53, 0.5375, 0.54, 0.5504, 0.56, 0.5711, 0.58, 0.5910, 0.595, 0.6023, 0.602, 0.6029, 0.600, 0.5977, 0.59, 0.5880, 0.585, 0.5830, 0.59, 0.5978, 0.61, 0.6345, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//101 101 0.0076 0.0094 0.0116 0.0139 0.0158 0.0158 0.0152 0.0142 0.0130 0.0111 0.0094 0.0090 0.0085 0.0069 0.0058 0.0057 0.0058 0.0048 0.0044 0.0060 0.0094 0.0126 0.0141 0.0141 0.0148 0.0157 0.0172 0.0197 0.0227 0.0245 0.0242 0.0233 0.0215 0.0205 0.0240 0.0321 +const double ColorTemp::JDC468_Blackvio101_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0076, 0.008, 0.0094, 0.01, 0.0116, 0.012, 0.0139, 0.015, 0.0158, 0.0158, 0.0158, 0.0156, 0.0152, 0.015, 0.0142, 0.014, 0.0130, 0.012, 0.0111, 0.01, 0.0094, 0.009, 0.0090, 0.009, + 0.0085, 0.008, 0.0069, 0.006, 0.0058, 0.0057, 0.0057, 0.0058, 0.0058, 0.005, 0.0048, 0.0045, 0.0044, 0.005, 0.0060, 0.008, 0.0094, 0.011, 0.0126, 0.013, 0.0141, 0.014, 0.0141, 0.0145, 0.0148, 0.015, 0.0157, 0.016, 0.0172, 0.018, 0.0197, 0.021, 0.0227, 0.023, 0.0245, 0.0241, + 0.0242, 0.0235, 0.0233, 0.022, 0.0215, 0.021, 0.0205, 0.022, 0.0240, 0.026, 0.0321, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//92 92 0.1652 0.2036 0.2848 0.4708 0.6230 0.6758 0.6761 0.6619 0.6502 0.6343 0.6195 0.6194 0.6169 0.5939 0.5677 0.5678 0.5695 0.5373 0.5105 0.5356 0.5778 0.6020 0.6073 0.6090 0.6124 0.6187 0.6295 0.6456 0.6603 0.6693 0.6716 0.6704 0.6660 0.6640 0.6749 0.7003 +const double ColorTemp::JDC468_Whitebl92_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1652, 0.19, 0.2036, 0.24, 0.2848, 0.35, 0.4708, 0.55, 0.6230, 0.65, 0.6758, 0.6759, 0.6761, 0.665, 0.6619, 0.655, 0.6502, 0.64, 0.6343, 0.62, 0.6195, 0.6194, 0.6194, 0.618, + 0.6169, 0.605, 0.5939, 0.58, 0.5677, 0.5677, 0.5678, 0.568, 0.5695, 0.555, 0.5373, 0.52, 0.5105, 0.52, 0.5356, 0.55, 0.5778, 0.60, 0.6020, 0.605, 0.6073, 0.608, 0.6090, 0.61, + 0.6124, 0.615, 0.6187, 0.62, 0.6295, 0.64, 0.6456, 0.65, 0.6603, 0.665, 0.6693, 0.67, 0.6716, 0.671, 0.6704, 0.669, 0.6660, 0.665, 0.6640, 0.67, 0.6749, 0.69, 0.7003, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//94 94 0.0506 0.0569 0.0678 0.0906 0.1088 0.1160 0.1184 0.1195 0.1203 0.1215 0.1293 0.1474 0.1609 0.1538 0.1415 0.1466 0.1535 0.1364 0.1248 0.1494 0.1871 0.2098 0.2163 0.2179 0.2217 0.2282 0.2372 0.2500 0.2631 0.2713 0.2739 0.2725 0.2678 0.2660 0.2770 0.3025 +const double ColorTemp::JDC468_Greyredbl94_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0506, 0.053, 0.0569, 0.06, 0.0678, 0.08, 0.0906, 0.1, 0.1088, 0.11, 0.1160, 0.117, 0.1184, 0.119, 0.1195, 0.12, 0.1203, 0.1205, 0.1215, 0.125, 0.1293, 0.133, 0.1474, 0.15, + 0.1609, 0.155, 0.1538, 0.145, 0.1415, 0.143, 0.1466, 0.15, 0.1535, 0.14, 0.1364, 0.13, 0.1248, 0.14, 0.1494, 0.17, 0.1871, 0.200, 0.2098, 0.21, 0.2163, 0.217, 0.2179, 0.22, + 0.2217, 0.222, 0.2282, 0.23, 0.2372, 0.24, 0.2500, 0.256, 0.2631, 0.27, 0.2713, 0.272, 0.2739, 0.273, 0.2725, 0.27, 0.2678, 0.267, 0.2660, 0.272, 0.2770, 0.28, 0.3025, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + + + +//32 32 0.0933 0.1333 0.1967 0.3132 0.4096 0.4556 0.4763 0.4845 0.4870 0.4852 0.4868 0.4959 0.4971 0.4755 0.4407 0.4085 0.3643 0.2922 0.2161 0.1658 0.1370 0.1190 0.1040 0.0947 0.0949 0.1001 0.1106 0.1306 0.1536 0.1652 0.1609 0.1480 0.1291 0.1188 0.1370 0.1933 +const double ColorTemp::JDC468_Blue32_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0933, 0.11, 0.1333, 0.17, 0.1967, 0.265, 0.3132, 0.35, 0.4096, 0.43, 0.4556, 0.465, 0.4763, 0.48, 0.4845, 0.486, .4870, 0.486, 0.4852, 0.486, 0.4868, 0.49, 0.4959, 0.496, + 0.4971, 0.48, 0.4755, 0.46, 0.4407, 0.42, 0.4085, 0.38, 0.3643, 0.32, 0.2922, 0.25, 0.2161, 0.19, 0.1658, 0.15, 0.1370, 0.12, 0.1190, 0.11, 0.1040, 0.10, 0.0947, 0.0948, + 0.0949, 0.097, 0.1001, 0.105, 0.1106, 0.12, 0.1306, 0.14, 0.1536, 0.16, 0.1652, 0.162, 0.1609, 0.154, 0.1480, 0.135, 0.1291, 0.12, 0.1188, 0.125, 0.1370, 0.16, 0.1933, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + + +//236 236 0.0165 0.0259 0.0432 0.0684 0.0858 0.0895 0.0828 0.0683 0.0527 0.0365 0.0235 0.0177 0.0143 0.0096 0.0067 0.0063 0.0060 0.0052 0.0053 0.0061 0.0074 0.0083 0.0085 0.0080 0.0078 0.0076 0.0081 0.0095 0.0112 0.0121 0.0114 0.0100 0.0086 0.0083 0.0102 0.0180 +const double ColorTemp::JDC468_Blue236_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0165, 0.021, 0.0259, 0.035, 0.0432, 0.05, 0.0684, 0.075, 0.0858, 0.087, 0.0895, 0.085, 0.0828, 0.075, 0.0683, 0.058, 0.0527, 0.045, 0.0365, 0.031, 0.0235, 0.021, 0.0177, 0.016, + 0.0143, 0.012, 0.0096, 0.0085, 0.0067, 0.0065, 0.0063, 0.0062, 0.0060, 0.006, 0.0052, 0.0052, 0.0053, 0.006, 0.0061, 0.007, 0.0074, 0.008, 0.0083, 0.0084, 0.0085, 0.0083, + 0.0080, 0.008, 0.0078, 0.0077, 0.0076, 0.008, 0.0081, 0.009, 0.0095, 0.01, 0.0112, 0.012, 0.0121, 0.012, 0.0114, 0.011, 0.0100, 0.009, 0.0086, 0.0085, 0.0083, 0.009, 0.0102, 0.0015, 0.0180, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//300 300 0.0079 0.0085 0.0087 0.0092 0.0094 0.0093 0.0093 0.0095 0.0097 0.0110 0.0158 0.0544 0.1907 0.3753 0.4883 0.5181 0.5044 0.4631 0.4070 0.3594 0.3262 0.3054 0.2873 0.2772 0.2790 0.2875 0.3029 0.3292 0.3571 0.3719 0.3693 0.3573 0.3371 0.3253 0.3471 0.4087 +const double ColorTemp::JDC468_Gre300_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0079, 0.008, 0.0085, 0.0086, 0.0087, 0.009, 0.0092, 0.0093, 0.0094, 0.0094, 0.0093, 0.0093, 0.0093, 0.0094, 0.0095, 0.0096, 0.0097, 0.01, 0.0110, 0.012, 0.0158, 0.045, + 0.0544, 0.134, 0.1907, 0.25, 0.3753, 0.435, 0.4883, 0.505, 0.5181, 0.512, 0.5044, 0.485, 0.4631, 0.433, 0.4070, 0.387, 0.3594, 0.334, 0.3262, 0.31, 0.3054, 0.295, 0.2873, 0.292, + 0.2772, 0.278, 0.2790, 0.281, 0.2875, 0.291, 0.3029, 0.3121, 0.3292, 0.333, 0.3571, 0.365, 0.3719, 0.365, 0.3693, 0.362, 0.3573, 0.342, 0.3371, 0.325, 0.3253, 0.336, 0.3471, 0.367, 0.4087, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//340 340 0.0175 0.0320 0.0587 0.0989 0.1267 0.1322 0.1210 0.0978 0.0732 0.0487 0.0297 0.0212 0.0167 0.0106 0.0069 0.0064 0.0062 0.0051 0.0052 0.0061 0.0073 0.0081 0.0080 0.0076 0.0075 0.0072 0.0077 0.0088 0.0105 0.0112 0.0104 0.0092 0.0079 0.0075 0.0092 0.0167 +const double ColorTemp::JDC468_Blue340_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0175, 0.02, 0.0320, 0.04, 0.0587, 0.08, 0.0989, 0.11, 0.1267, 0.13, 0.1322, 0.125, 0.1210, 0.111, 0.0978, 0.08, 0.0732, 0.06, 0.0487, 0.04, 0.0297, 0.025, 0.0212, 0.02, + 0.0167, 0.012, 0.0106, 0.008, 0.0069, 0.0065, 0.0064, 0.0063, 0.0062, 0.0055, 0.0051, 0.0051, 0.0052, 0.006, 0.0061, 0.007, 0.0073, 0.008, 0.0081, 0.008, 0.0080, 0.0078, + 0.0076, 0.0076, 0.0075, 0.0074, 0.0072, 0.0075, 0.0077, 0.008, 0.0088, 0.0092, 0.0105, 0.011, 0.0112, 0.0108, 0.0104, 0.01, 0.0092, 0.008, 0.0079, 0.0075, 0.0075, 0.008, + 0.0092, 0.01, 0.0167, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//110 110 0.0954 0.1234 0.1702 0.2631 0.3363 0.3664 0.3799 0.3905 0.4002 0.4160 0.4582 0.5262 0.5798 0.5915 0.5742 0.5465 0.5035 0.4364 0.3581 0.2977 0.2589 0.2349 0.2152 0.2030 0.2032 0.2106 0.2249 0.2511 0.2799 0.2951 0.2915 0.2776 0.2552 0.2419 0.2638 0.3287 +const double ColorTemp::JDC468_Gree110_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0954, 0.11, 0.1234, 0.15, 0.1702, 0.22, 0.2631, 0.312, 0.3363, 0.352, 0.3664, 0.372, 0.3799, 0.385, 0.3905, 0.395, 0.4002, 0.41, 0.4160, 0.43, 0.4582, 0.511, 0.5262, 0.544, + 0.5798, 0.585, 0.5915, 0.585, 0.5742, 0.563, 0.5465, 0.523, 0.5035, 0.465, 0.4364, 0.389, 0.3581, 0.3334, 0.2977, 0.275, 0.2589, 0.245, 0.2349, 0.223, 0.2152, 0.211, 0.2030, 0.204, + 0.2032, 0.206, 0.2106, 0.221, 0.2249, 0.243, 0.2511, 0.271, 0.2799, 0.286, 0.2951, 0.294, 0.2915, 0.2876, 0.2776, 0.2657, 0.2552, 0.2456, 0.2419, 0.253, 0.2638, 0.275, 0.3287, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//457 457 0.0127 0.0126 0.0112 0.0110 0.0109 0.0106 0.0105 0.0104 0.0110 0.0136 0.0318 0.1246 0.3262 0.5051 0.5566 0.5181 0.4406 0.3429 0.2411 0.1647 0.1202 0.0968 0.0804 0.0709 0.0703 0.0747 0.0840 0.1023 0.1243 0.1355 0.1311 0.1179 0.0993 0.0884 0.1043 0.1590 +const double ColorTemp::JDC468_Gree457_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0127, 0.0126, 0.0126, 0.012, 0.0112, 0.011, 0.0110, 0.011, 0.0109, 0.0107, 0.0106, 0.0105, 0.0105, 0.0105, 0.0104, 0.0107, 0.0110, 0.0124, 0.0136, 0.0234, 0.0318, 0.09, + 0.1246, 0.22, 0.3262, 0.43, 0.5051, 0.52, 0.5566, 0.54, 0.5181, 0.476, 0.4406, 0.398, 0.3429, 0.296, 0.2411, 0.203, 0.1647, 0.142, 0.1202, 0.1, 0.0968, 0.09, 0.0804, 0.08, + 0.0709, 0.0708, 0.0703, 0.0723, 0.0747, 0.08, 0.0840, 0.09, 0.1023, 0.11, 0.1243, 0.13, 0.1355, 0.132, 0.1311, 0.12, 0.1179, 0.10, 0.0993, 0.09, 0.0884, 0.09, 0.1043, 0.12, 0.1590, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//241 241 0.0134 0.0106 0.0110 0.0108 0.0111 0.0114 0.0114 0.0115 0.0114 0.0122 0.0192 0.0731 0.2455 0.4689 0.6183 0.6852 0.7107 0.7112 0.7059 0.7177 0.7335 0.7445 0.7487 0.7523 0.7555 0.7606 0.7683 0.7779 0.7855 0.7915 0.7964 0.8011 0.8056 0.8097 0.8144 0.8239 +const double ColorTemp::JDC468_Yel241_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0134, 0.012, 0.0106, 0.011, 0.0110, 0.011, 0.0108, 0.011, 0.0111, 0.0112, 0.0114, 0.0114, 0.0114, 0.0114, 0.0115, 0.0114, 0.0114, 0.012, 0.0122, 0.017, 0.0192, 0.05, 0.0731, 0.12, + 0.2455, 0.355, 0.4689, 0.556, 0.6183, 0.645, 0.6852, 0.698, 0.7107, 0.711, 0.7112, 0.708, 0.7059, 0.712, 0.7177, 0.724, 0.7335, 0.742, 0.7445, 0.746, 0.7487, 0.751, 0.7523, 0.753, + 0.7555, 0.758, 0.760, 0.7626, 0.7683, 0.771, 0.7779, 0.782, 0.7855, 0.791, 0.7915, 0.794, 0.7964, 0.799, 0.8011, 0.804, 0.8056, 0.807, 0.8097, 0.811, 0.8144, 0.820, 0.8239, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//321 321 0.0247 0.0203 0.0182 0.0183 0.0182 0.0179 0.0182 0.0188 0.0199 0.0249 0.0529 0.1519 0.3116 0.4138 0.4410 0.4679 0.4906 0.4655 0.4517 0.5203 0.6238 0.6952 0.7270 0.7406 0.7469 0.7527 0.7607 0.7708 0.7786 0.7849 0.7897 0.7940 0.7984 0.8025 0.8069 0.8160 +const double ColorTemp::JDC468_Ora321_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0247, 0.022, 0.0203, 0.019, 0.0182, 0.0182, 0.0183, 0.0182, 0.0182, 0.018, 0.0179, 0.018, 0.0182, 0.0185, 0.0188, 0.019, 0.0199, 0.022, 0.0249, 0.035, 0.0529, 0.112, + 0.1519, 0.231, 0.3116, 0.365, 0.4138, 0.421, 0.4410, 0.451, 0.4679, 0.485, 0.4906, 0.473, 0.4655, 0.455, 0.4517, 0.487, 0.5203, 0.578, 0.6238, 0.667, 0.6952, 0.711, 0.7270, 0.735, + 0.7406, 0.743, 0.7469, .751, 0.7527, 0.756, 0.7607, 0.765, 0.7708, 0.774, 0.7786, 0.782, 0.7849, 0.786, 0.7897, 0.79, 0.7940, 0.794, 0.7984, 0.799, 0.8025, 0.805, 0.8069, 0.811, 0.8160, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//353 353 0.0260 0.0294 0.0331 0.0420 0.0490 0.0517 0.0541 0.0572 0.0608 0.0664 0.0813 0.1070 0.1291 0.1344 0.1317 0.1356 0.1390 0.1289 0.1195 0.1278 0.1420 0.1493 0.1500 0.1500 0.1527 0.1576 0.1651 0.1759 0.1870 0.1942 0.1963 0.1952 0.1910 0.1898 0.1995 0.2209 +const double ColorTemp::JDC468_Yellow353_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0260, 0.027, 0.0294, 0.031, 0.0331, 0.037, 0.0420, 0.045, 0.0490, 0.051, 0.0517, 0.053, 0.0541, 0.056, 0.0572, 0.059, 0.0608, 0.063, 0.0664, 0.072, 0.0813, 0.096, 0.1070, 0.112, + 0.1291, 0.132, 0.1344, 0.133, 0.1317, 0.134, 0.1356, 0.137, 0.1390, 0.134, 0.1289, 0.123, 0.1195, 0.122, 0.1278, 0.134, 0.1420, 0.145, 0.1493, 0.15, 0.1500, 0.15, 0.1500, 0.153, + 0.1527, 0.154, 0.1576, 0.162, 0.1651, 0.172, 0.1759, 0.182, 0.1870, 0.191, 0.1942, 0.195, 0.1963, 0.196, 0.1952, 0.193, 0.1910, 0.19, 0.1898, 0.195, 0.1995, 0.21, 0.2209, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//465 465 0.0388 0.0654 0.1020 0.1557 0.1880 0.1783 0.1434 0.1013 0.0684 0.0410 0.0219 0.0149 0.0117 0.0080 0.0062 0.0062 0.0062 0.0056 0.0063 0.0098 0.0230 0.0440 0.0577 0.0617 0.0645 0.0690 0.0766 0.0903 0.1064 0.1144 0.1113 0.1022 0.0898 0.0833 0.0962 0.1377 +const double ColorTemp::JDC468_Mag465_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0388, 0.05, 0.0654, 0.09, 0.1020, 0.12, 0.1557, 0.17, 0.1880, 0.182, 0.1783, 0.162, 0.1434, 0.12, 0.1013, 0.09, 0.0684, 0.05, 0.0410, 0.03, 0.0219, 0.02, 0.0149, 0.012, + 0.0117, 0.009, 0.0080, 0.007, 0.0062, 0.0062, 0.0062, 0.0062, 0.0062, 0.006, 0.0056, 0.006, 0.0063, 0.008, 0.0098, 0.018, 0.0230, 0.03, 0.0440, 0.05, 0.0577, 0.06, 0.0617, 0.062, + 0.0645, 0.065, 0.0690, 0.07, 0.0766, 0.08, 0.0903, 0.1, 0.1064, 0.111, 0.1144, 0.112, 0.1113, 0.104, 0.1022, 0.09, 0.0898, 0.088, 0.0833, 0.09, 0.0962, 0.111, 0.1377, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//333 333 0.1030 0.1508 0.2133 0.3191 0.3910 0.3895 0.3424 0.2770 0.2184 0.1593 0.1074 0.0825 0.0669 0.0430 0.0265 0.0278 0.0315 0.0212 0.0163 0.0355 0.0861 0.1365 0.1565 0.1589 0.1629 0.1713 0.1852 0.2099 0.2378 0.2517 0.2469 0.2322 0.2102 0.1973 0.2191 0.2855 +const double ColorTemp::JDC468_Mag333_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1030, 0.12, 0.1508, 0.18, 0.2133, 0.26, 0.3191, 0.364, 0.3910, 0.39, 0.3895, 0.375, 0.3424, 0.312, 0.2770, 0.251, 0.2184, 0.183, 0.1593, 0.122, 0.1074, 0.1, 0.0825, 0.07, + 0.0669, 0.05, 0.0430, 0.03, 0.0265, 0.027, 0.0278, 0.03, 0.0315, 0.025, 0.0212, 0.02, 0.0163, 0.03, 0.0355, 0.05, 0.0861, 0.112, 0.1365, 0.143, 0.1565, 0.157, 0.1589, 0.16, + 0.1629, 0.165, 0.1713, 0.175, 0.1852, 0.19, 0.2099, 0.221, 0.2378, 0.245, 0.2517, 0.25, 0.2469, 0.238, 0.2322, 0.224, 0.2102, 0.206, 0.1973, 0.209, 0.2191, 0.231, 0.2855, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + + +//203 203 0.0833 0.1329 0.2005 0.3099 0.3855 0.3916 0.3530 0.2926 0.2346 0.1741 0.1201 0.0934 0.0759 0.0495 0.0306 0.0308 0.0330 0.0214 0.0150 0.0256 0.0510 0.0723 0.0769 0.0748 0.0761 0.0813 0.0911 0.1087 0.1295 0.1399 0.1353 0.1232 0.1064 0.0971 0.1137 0.1677 +const double ColorTemp::JDC468_Mag203_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0833, 0.11, 0.1329, 0.16, 0.2005, 0.25, 0.3099, 0.342, 0.3855, 0.39, 0.3916, 0.374, 0.3530, 0.321, 0.2926, 0.267, 0.2346, 0.21, 0.1741, 0.153, 0.1201, 0.1, 0.0934, 0.08, + 0.0759, 0.06, 0.0495, 0.04, 0.0306, 0.0307, 0.0308, 0.032, 0.0330, 0.025, 0.0214, 0.018, 0.0150, 0.02, 0.0256, 0.04, 0.0510, 0.06, 0.0723, 0.074, 0.0769, 0.075, 0.0748, 0.076, + 0.0761, 0.08, 0.0813, 0.09, 0.0911, 0.1, 0.1087, 0.115, 0.1295, 0.134, 0.1399, 0.136, 0.1353, 0.131, 0.1232, 0.114, 0.1064, 0.1, 0.0971, 0.105, 0.1137, 0.123, 0.1677, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//blue cyan +const double ColorTemp::J570_BlueB6_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1611, 0.18, 0.1947, 0.23, 0.2639, 0.31, 0.3488, 0.37, 0.4022, 0.43, 0.4517, 0.49, 0.501, 0.52, 0.5317, 0.534, 0.5367, 0.53, 0.5246, 0.51, 0.4905, 0.47, 0.4510, 0.43, 0.4059, + 0.37, 0.3351, 0.31, 0.2612, 0.24, 0.2177, 0.205, 0.1883, 0.16, 0.1444, 0.123, 0.1065, 0.1, 0.0889, 0.085, 0.0811, 0.08, 0.0757, 0.071, 0.0695, 0.067, 0.0648, 0.064, 0.0634, + 0.063, 0.0637, 0.065, 0.0662, 0.068, 0.0714, 0.075, 0.0787, 0.08, 0.0828, 0.082, 0.0822, 0.08, 0.0781, 0.075, 0.0726, 0.071, 0.0698, 0.075, 0.0770, 0.08, 0.0973, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueB15_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2207, 0.2, 0.1897, 0.21, 0.2274, 0.25, 0.2805, 0.30, 0.3216, 0.34, 0.3596, 0.38, 0.4003, 0.42, 0.4438, 0.47, 0.4909, 0.52, 0.5469, 0.57, 0.6009, 0.62, 0.6414, 0.65, 0.6557, + 0.64, 0.6275, 0.59, 0.5675, 0.53, 0.5022, 0.48, 0.4348, 0.39, 0.3473, 0.31, 0.2613, 0.24, 0.2039, 0.18, 0.1696, 0.15, 0.1465, 0.13, 0.1243, 0.11, 0.1055, 0.10, 0.0952, 0.094, + 0.0911, 0.091, 0.0906, 0.092, 0.0940, 0.1, 0.1006, 0.104, 0.1075, 0.11, 0.1125, 0.113, 0.1146, 0.113, 0.1129, 0.112, 0.1120, 0.115, 0.1198, 0.13, 0.1431, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueC2_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2534, 0.25, 0.2454, 0.28, 0.3101, 0.33, 0.3567, 0.37, 0.3981, 0.41, 0.4258, 0.43, 0.4472, 0.45, 0.4574, 0.455, 0.4571, 0.45, 0.4468, 0.43, 0.4205, 0.41, 0.3947, 0.38, + 0.3647, 0.33, 0.3074, 0.27, 0.2471, 0.23, 0.2221, 0.22, 0.2128, 0.20, 0.1810, 0.17, 0.1510, 0.15, 0.1486, 0.15, 0.1546, 0.154, 0.1532, 0.15, 0.1426, 0.135, 0.1310, 0.125, + 0.1257, 0.125, 0.1246, 0.126, 0.1276, 0.13, 0.1360, 0.14, 0.1483, 0.15, 0.1566, 0.157, 0.1575, 0.155, 0.1535, 0.15, 0.1453, 0.143, 0.1403, 0.146, 0.1510, 0.16, 0.1855, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueC14_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.5697, 0.51, 0.4660, 0.49, 0.5000, 0.53, 0.5560, 0.58, 0.6072, 0.62, 0.6402, 0.65, 0.6632, 0.67, 0.6850, 0.69, 0.7069, 0.71, 0.7292, 0.74, 0.7488, 0.75, 0.7678, 0.77, 0.7786, + 0.775, 0.7721, 0.76, 0.7544, 0.75, 0.7394, 0.73, 0.7232, 0.70, 0.6889, 0.66, 0.6446, 0.63, 0.6171, 0.61, 0.5966, 0.58, 0.5743, 0.56, 0.5425, 0.53, 0.5093, 0.50, 0.4884, 0.48, + 0.4784, 0.475, 0.4774, 0.48, 0.4822, 0.49, 0.4944, 0.50, 0.5076, 0.51, 0.5186, 0.52, 0.5268, 0.53, 0.5303, 0.532, 0.5332, 0.54, 0.5454, 0.56, 0.5760, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueC16_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1909, 0.10, 0.0635, 0.06, 0.0554, 0.056, 0.0571, 0.057, 0.0580, 0.06, 0.0608, 0.063, 0.0662, 0.07, 0.0712, 0.072, 0.0742, 0.08, 0.0811, 0.09, 0.0985, 0.11, 0.1363, 0.15, + 0.1743, 0.173, 0.1720, 0.15, 0.1372, 0.12, 0.1005, 0.09, 0.0731, 0.06, 0.0509, 0.04, 0.0374, 0.036, 0.0322, 0.032, 0.0308, 0.031, 0.0309, 0.031, 0.0319, 0.033, + 0.0333, 0.034, 0.0349, 0.035, 0.0364, 0.037, 0.0377, 0.038, 0.0386, 0.0386, 0.0386, 0.0384, 0.0383, 0.038, 0.0377, 0.0377, 0.0378, 0.038, 0.0386, 0.04, 0.0417, 0.043, + 0.0461, 0.049, 0.0514, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueF1_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + -0.0060, 0.04, 0.0975, 0.11, 0.1297, 0.13, 0.1426, 0.15, 0.1538, 0.16, 0.1624, 0.165, 0.1684, 0.17, 0.1727, 0.175, 0.1761, 0.178, 0.1798, 0.18, 0.1863, 0.19, 0.1993, 0.20, + 0.2091, 0.205, 0.2041, 0.20, 0.1902, 0.19, 0.1836, 0.182, 0.1809, 0.17, 0.1675, 0.16, 0.1527, 0.151, 0.1511, 0.153, 0.1541, 0.154, 0.1545, 0.153, 0.1516, 0.15, + 0.1484, 0.149, 0.1489, 0.15, 0.1516, 0.153, 0.1563, 0.16, 0.1654, 0.17, 0.1766, 0.18, 0.1827, 0.182, 0.1817, 0.18, 0.1766, 0.17, 0.1693, 0.166, 0.1643, 0.17, 0.1726, 0.18, 0.1978, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueF2_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1613, 0.20, 0.2384, 0.30, 0.3288, 0.35, 0.4026, 0.43, 0.4630, 0.48, 0.4992, 0.51, 0.5294, 0.53, 0.5377, 0.53, 0.5261, 0.51, 0.4995, 0.48, 0.4513, 0.43, 0.4064, 0.38, + 0.3620, 0.31, 0.2935, 0.25, 0.2263, 0.21, 0.1977, 0.19, 0.1851, 0.17, 0.1519, 0.14, 0.1213, 0.12, 0.1149, 0.113, 0.1162, 0.114, 0.1133, 0.11, 0.1053, 0.10, 0.0976, 0.095, + 0.0947, 0.095, 0.0953, 0.097, 0.0985, 0.1, 0.1070, 0.11, 0.1188, 0.12, 0.1256, 0.124, 0.1246, 0.12, 0.1187, 0.11, 0.1099, 0.105, 0.1048, 0.11, 0.1145, 0.12, 0.145, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueF10_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.3003, 0.20, 0.1512, 0.20, 0.2149, 0.25, 0.2709, 0.30, 0.3127, 0.32, 0.3534, 0.37, 0.4001, 0.42, 0.4456, 0.46, 0.4882, 0.51, 0.5343, 0.55, 0.5728, 0.58, 0.5968, 0.595, + 0.5932, 0.56, 0.5490, 0.51, 0.4756, 0.43, 0.3989, 0.37, 0.3256, 0.28, 0.2424, 0.21, 0.1691, 0.15, 0.1239, 0.10, 0.0998, 0.09, 0.0866, 0.08, 0.0752, 0.07, 0.0664, 0.065, + 0.0623, 0.062, 0.0616, 0.062, 0.0626, 0.064, 0.0662, 0.07, 0.0720, 0.075, 0.0767, 0.077, 0.0784, 0.078, 0.0770, 0.075, 0.0734, 0.073, 0.0716, 0.075, 0.0779, 0.08, 0.0968, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueF13_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.3075, 0.22, 0.1514, 0.13, 0.1216, 0.125, 0.1264, 0.13, 0.1312, 0.14, 0.1448, 0.15, 0.1665, 0.17, 0.1850, 0.19, 0.1922, 0.195, 0.1970, 0.20, 0.2036, 0.21, + 0.2136, 0.213, 0.2122, 0.19, 0.1832, 0.16, 0.1412, 0.12, 0.1066, 0.09, 0.0810, 0.07, 0.0579, 0.05, 0.0422, 0.04, 0.0358, 0.035, 0.0336, 0.033, 0.0335, 0.0335, + 0.0339, 0.034, 0.0348, 0.035, 0.0358, 0.036, 0.0371, 0.038, 0.0384, 0.039, 0.0394, 0.04, 0.0405, 0.0404, 0.0405, 0.04, 0.0399, 0.039, 0.0387, 0.039, + 0.0396, 0.04, 0.0422, 0.045, 0.0467, 0.05, 0.0527, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueG9_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0937, 0.09, 0.0891, 0.07, 0.0621, 0.07, 0.0735, 0.08, 0.0842, 0.09, 0.0918, 0.1, 0.1009, 0.105, 0.1091, 0.11, 0.1158, 0.12, 0.1254, 0.13, 0.1452, 0.16, + 0.1805, 0.20, 0.2126, 0.213, 0.2128, 0.20, 0.1863, 0.17, 0.1550, 0.14, 0.1270, 0.1, 0.0973, 0.08, 0.0725, 0.06, 0.0585, 0.055, 0.0521, 0.05, 0.0486, 0.047, + 0.0458, 0.045, 0.0441, 0.044, 0.0439, 0.044, 0.0443, 0.045, 0.0455, 0.046, 0.0478, 0.049, 0.0500, 0.051, 0.0512, 0.051, 0.0511, 0.05, 0.0498, 0.049, + 0.0487, 0.049, 0.0495, 0.05, 0.0531, 0.055, 0.0620, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueG19_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1198, 0.12, 0.1376, 0.15, 0.1735, 0.18, 0.1903, 0.20, 0.2116, 0.22, 0.2322, 0.24, 0.2555, 0.27, 0.2802, 0.29, 0.3077, 0.32, 0.3420, 0.36, 0.3822, 0.41, + 0.4261, 0.43, 0.4565, 0.45, 0.4481, 0.43, 0.4109, 0.39, 0.3736, 0.35, 0.3368, 0.30, 0.2811, 0.25, 0.2228, 0.19, 0.1839, 0.17, 0.1592, 0.15, 0.1394, 0.12, + 0.1183, 0.1, 0.0998, 0.09, 0.0897, 0.085, 0.0851, 0.085, 0.0844, 0.085, 0.0863, 0.09, 0.0912, 0.095, 0.0977, 0.1, 0.1027, 0.105, 0.1064, 0.106, 0.1064, 0.106, + 0.1067, 0.11, 0.1135, 0.12, 0.1319, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueI5_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1096, 012, 0.1546, 0.16, 0.1855, 0.2, 0.2350, 0.25, 0.2720, 0.29, 0.3065, 0.32, 0.3404, 0.36, 0.3782, 0.4, 0.4229, 0.45, 0.4801, 0.51, 0.5416, 0.57, + 0.5962, 0.61, 0.6281, 0.62, 0.6144, 0.58, 0.5680, 0.55, 0.5211, 0.5, 0.4726, 0.43, 0.3991, 0.37, 0.3209, 0.29, 0.2674, 0.25, 0.2311, 0.22, 0.2000, 0.18, + 0.1656, 0.15, 0.1349, 0.12, 0.1161, 0.11, 0.1078, 0.105, 0.1046, 0.105, 0.1049, 0.107, 0.1097, 0.11, 0.1179, 0.12, 0.1264, 0.13, 0.1337, 0.135, 0.1378, 0.14, 0.1402, 0.145, 0.1474, 0.15, 0.1662, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueH15_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1047, 0.105, 0.1078, 0.12, 0.1550, 0.20, 0.2110, 0.23, 0.2487, 0.27, 0.2893, 0.31, 0.3386, 0.35, 0.3723, 0.375, 0.3773, 0.37, 0.3665, 0.35, 0.3373, 0.32, + 0.3037, 0.28, 0.2663, 0.24, 0.2106, 0.17, 0.1540, 0.13, 0.1200, 0.11, 0.0980, 0.08, 0.0721, 0.06, 0.0527, 0.05, 0.0448, 0.043, 0.0418, 0.041, 0.0403, 0.04, + 0.0390, 0.039, 0.0386, 0.039, 0.0392, 0.04, 0.0401, 0.041, 0.0413, 0.042, 0.0435, 0.044, 0.0456, 0.046, 0.0465, 0.046, 0.0457, 0.045, 0.0447, 0.044, 0.0435, 0.044, + 0.0442, 0.046, 0.0485, 0.05, 0.0576, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueI3_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1759, 0.21, 0.2647, 0.31, 0.3209, 0.36, 0.4249, 0.45, 0.4957, 0.52, 0.5536, 0.57, 0.6073, 0.62, 0.6431, 0.65, 0.6538, 0.653, 0.6506, 0.64, 0.6282, 0.61, + 0.5973, 0.57, 0.5559, 0.52, 0.4856, 0.43, 0.4033, 0.37, 0.3417, 0.32, 0.2901, 0.26, 0.2211, 0.19, 0.1585, 0.14, 0.1236, 0.11, 0.1062, 0.1, 0.0959, 0.09, + 0.0865, 0.085, 0.0801, 0.08, 0.0780, 0.079, 0.0788, 0.08, 0.0819, 0.09, 0.0903, 0.1, 0.1009, 0.105, 0.1073, 0.106, 0.1055, 0.1, 0.0998, 0.095, 0.0914, 0.09, 0.0863, 0.09, 0.0961, 0.11, 0.1250, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueI19_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.3031, 0.28, 0.2588, 0.25, 0.2472, 0.26, 0.2738, 0.29, 0.3035, 0.31, 0.3271, 0.33, 0.3496, 0.36, 0.3724, 0.38, 0.3968, 0.41, 0.4252, 0.44, 0.4562, 0.47, + 0.4899, 0.5, 0.5147, 0.512, 0.5100, 0.49, 0.4841, 0.47, 0.4608, 0.45, 0.4373, 0.42, 0.3934, 0.37, 0.3420, 0.32, 0.3086, 0.30, 0.2850, 0.27, 0.2622, 0.25, + 0.2334, 0.22, 0.2054, 0.19, 0.1887, 0.185, 0.1806, 0.18, 0.1791, 0.18, 0.1825, 0.185, 0.1909, 0.2, 0.2018, 0.21, 0.2108, 0.213, 0.2164, 0.217, 0.2180, 0.219, + 0.2198, 0.22, 0.2295, 0.24, 0.2562, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueJ4_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + -0.0290, 0.02, 0.0598, 0.1, 0.1278, 0.15, 0.1764, 0.19, 0.2052, 0.21, 0.2331, 0.25, 0.2642, 0.28, 0.2906, 0.3, 0.3093, 0.31, 0.3263, 0.33, 0.3413, 0.35, + 0.3550, 0.354, 0.3532, 0.33, 0.3206, 0.3, 0.2685, 0.24, 0.2212, 0.2, 0.1802, 0.16, 0.1346, 0.1, 0.0965, 0.08, 0.0751, 0.07, 0.0646, 0.06, 0.0586, 0.055, + 0.0535, 0.052, 0.0504, 0.05, 0.0491, 0.0495, 0.0493, 0.05, 0.0504, 0.051, 0.0529, 0.053, 0.0565, 0.057, 0.0591, 0.059, 0.0593, 0.058, 0.0576, 0.056, 0.0556, 0.055, + 0.0553, 0.06, 0.0602, 0.065, 0.0727, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueJ6_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.3039, 0.3, 0.2571, 0.27, 0.2960, 0.31, 0.3446, 0.37, 0.3937, 0.41, 0.4405, 0.47, 0.4884, 0.51, 0.5337, 0.56, 0.5771, 0.59, 0.6221, 0.64, 0.6589, 0.67, + 0.6808, 0.68, 0.6770, 0.65, 0.6375, 0.59, 0.5693, 0.53, 0.4933, 0.45, 0.4160, 0.39, 0.3223, 0.26, 0.2338, 0.21, 0.1761, 0.16, 0.1447, 0.13, 0.1258, 0.12, + 0.1090, 0.1, 0.0961, 0.09, 0.0899, 0.089, 0.0877, 0.088, 0.0892, 0.09, 0.0949, 0.1, 0.1045, 0.11, 0.1115, 0.112, 0.1131, 0.112, 0.1115, 0.11, 0.1065, 0.105, + 0.1033, 0.11, 0.1122, 0.12, 0.1400, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_BlueJ11_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1274, 0.1, 0.091, 0.08, 0.0656, 0.064, 0.0604, 0.06, 0.0570, 0.06, 0.0604, 0.061, 0.0644, 0.065, 0.0668, 0.07, 0.0700, 0.072, 0.0754, 0.08, 0.0874, 0.1, + 0.1111, 0.12, 0.1327, 0.132, 0.1313, 0.12, 0.1127, 0.1, 0.0931, 0.08, 0.0758, 0.06, 0.0580, 0.05, 0.0449, 0.04, 0.0385, 0.036, 0.0360, 0.035, 0.0351, 0.035, + 0.0351, 0.035, 0.0355, 0.036, 0.0371, 0.0375, 0.0379, 0.038, 0.0388, 0.04, 0.0406, 0.041, 0.0414, 0.0415, 0.0416, 0.041, 0.0409, 0.04, + 0.0398, 0.04, 0.0397, 0.04, 0.0424, 0.043, 0.0458, 0.05, 0.0522, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_BlueJ13_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2802, 0.28, 0.2820, 0.3, 0.3461, 0.4, 0.4357, 0.45, 0.5027, 0.53, 0.5528, 0.58, 0.6001, 0.62, 0.6402, 0.66, 0.6730, 0.69, 0.7019, 0.71, 0.7216, 0.725, + 0.7288, 0.72, 0.7172, 0.7, 0.6779, 0.65, 0.6160, 0.58, 0.5478, 0.52, 0.4751, 0.43, 0.3816, 0.35, 0.2882, 0.25, 0.2260, 0.2, 0.1905, 0.18, 0.1699, 0.16, + 0.1514, 0.14, 0.1361, 0.13, 0.1295, 0.129, 0.1281, 0.13, 0.1309, 0.135, 0.1408, 0.145, 0.1546, 0.16, 0.1644, 0.165, 0.1656, 0.162, + 0.1606, 0.155, 0.1516, 0.15, 0.1461, 0.15, 0.1585, 0.16, 0.1975, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_BlueK5_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1727, 0.18, 0.1814, 0.19, 0.1931, 0.21, 0.2379, 0.25, 0.2728, 0.29, 0.3054, 0.31, 0.3396, 0.36, 0.3780, 0.4, 0.4243, 0.45, 0.4829, 0.51, 0.5464, 0.57, + 0.6024, 0.62, 0.6348, 0.63, 0.6209, 0.59, 0.5741, 0.55, 0.5258, 0.49, 0.4755, 0.43, 0.4003, 0.37, 0.3204, 0.3, 0.2656, 0.25, 0.2282, 0.21, 0.1966, 0.17, + 0.1624, 0.15, 0.1322, 0.12, 0.1137, 0.11, 0.1052, 0.105, 0.1025, 0.102, 0.1028, 0.105, 0.1075, 0.11, 0.1155, 0.12, 0.1237, 0.13, 0.1310, 0.133, + 0.1352, 0.136, 0.1370, 0.14, 0.1444, 0.15, 0.1632, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_BlueN1_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1936, 0.194, 0.1942, 0.22, 0.2692, 0.29, 0.3102, 0.33, 0.3535, 0.37, 0.3885, 0.4, 0.4230, 0.44, 0.4594, 0.48, 0.5011, 0.52, 0.5510, 0.58, 0.6022, 0.62, 0.6479, 0.66, + 0.6748, 0.67, 0.6640, 0.65, 0.6268, 0.61, 0.5919, 0.58, 0.5549, 0.53, 0.4921, 0.46, 0.4209, 0.39, 0.3723, 0.35, 0.3364, 0.32, 0.3005, 0.28, 0.2569, 0.23, 0.2154, 0.19, + 0.1897, 0.18, 0.1768, 0.175, 0.1723, 0.173, 0.1722, 0.175, 0.1785, 0.18, 0.1892, 0.19, 0.2017, 0.21, 0.2134, 0.22, 0.2202, 0.222, 0.2247, 0.23, 0.2333, 0.24, 0.2566, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_BlueN4_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.3138, 0.25, 0.2038, 0.19, 0.1787, 0.18, 0.1840, 0.2, 0.2109, 0.23, 0.2400, 0.26, 0.2715, 0.29, 0.3075, 0.33, 0.3534, 0.39, 0.4149, 0.45, 0.4863, 0.52, + 0.5520, 0.57, 0.5904, 0.58, 0.5750, 0.55, 0.5198, 0.48, 0.4602, 0.43, 0.3997, 0.36, 0.3199, 0.27, 0.2411, 0.2, 0.1883, 0.17, 0.1553, 0.14, 0.1307, 0.12, + 0.1062, 0.1, 0.0859, 0.08, 0.0746, 0.07, 0.0697, 0.069, 0.0678, 0.068, 0.0683, 0.07, 0.0715, 0.075, 0.0765, 0.08, 0.0818, 0.085, 0.0862, 0.087, 0.0885, 0.089, + 0.0899, 0.09, 0.0951, 0.1, 0.1090, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_BlueO19_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1231, 0.13, 0.1348, 0.12, 0.1152, 0.12, 0.1368, 0.15, 0.1627, 0.17, 0.1860, 0.2, 0.2130, 0.23, 0.2462, 0.26, 0.2859, 0.31, 0.3425, 0.38, 0.4152, 0.45, 0.4902, 0.51, + 0.5386, 0.53, 0.5259, 0.49, 0.4652, 0.43, 0.3950, 0.35, 0.3266, 0.28, 0.2469, 0.21, 0.1750, 0.15, 0.1293, 0.12, 0.1033, 0.09, 0.0859, 0.08, 0.0703, 0.06, 0.0578, 0.055, + 0.0521, 0.05, 0.0494, 0.049, 0.0492, 0.049, 0.0498, 0.05, 0.0522, 0.053, 0.0558, 0.058, 0.0590, 0.06, 0.0615, 0.062, 0.0625, 0.063, 0.0634, 0.065, 0.0670, 0.07, 0.0776, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_BlueU8_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0776, 0.1, 0.1703, 0.23, 0.2942, 0.35, 0.4022, 0.45, 0.4795, 0.51, 0.5389, 0.56, 0.5968, 0.6, 0.6362, 0.64, 0.6512, 0.652, 0.6523, 0.64, 0.6340, 0.62, 0.6052, 0.58, + 0.5645, 0.53, 0.4952, 0.45, 0.4124, 0.38, 0.3457, 0.32, 0.2883, 0.25, 0.2164, 0.19, 0.1529, 0.14, 0.1168, 0.1, 0.0983, 0.09, 0.0883, 0.08, 0.0798, 0.075, 0.0735, 0.073, + 0.0720, 0.072, 0.0726, 0.074, 0.0757, 0.08, 0.0830, 0.09, 0.0930, 0.095, 0.0989, 0.097, 0.0971, 0.095, 0.0911, 0.085, 0.0832, 0.08, 0.0795, 0.082, 0.0877, 0.09, 0.1140, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//N8 +const double ColorTemp::J570_NeuN8_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + -0.0632, -0.04, -0.0244, 0.01, 0.0125, 0.02, 0.0294, 0.03, 0.0326, 0.033, 0.0352, 0.036, 0.0361, 0.037, 0.0374, 0.0374, 0.0373, 0.038, 0.0378, 0.039, 0.0397, 0.04, + 0.0421, 0.043, 0.0431, 0.042, 0.0417, 0.04, 0.0391, 0.038, 0.0378, 0.037, 0.0368, 0.035, 0.0347, 0.034, 0.0335, 0.034, 0.0341, 0.035, 0.0350, 0.035, 0.0355, 0.036, + 0.0357, 0.0357, 0.0358, 0.036, 0.0369, 0.037, 0.0372, 0.0376, 0.0378, 0.038, 0.0388, 0.039, 0.0397, 0.04, 0.0400, 0.0395, 0.0394, 0.039, 0.0386, 0.0385, 0.0384, 0.039, + 0.0395, 0.04, 0.0415, 0.043, 0.0448, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuN9_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0573, 0.054, 0.0516, 0.053, 0.0548, 0.05, 0.0401, 0.041, 0.0424, 0.043, 0.0449, 0.046, 0.0467, 0.047, 0.0473, 0.0473, 0.0474, 0.048, 0.0483, 0.05, 0.0508, 0.053, + 0.0558, 0.057, 0.0584, 0.058, 0.0550, 0.05, 0.0495, 0.048, 0.0468, 0.0465, 0.0460, 0.044, 0.0430, 0.042, 0.0411, 0.042, 0.0425, 0.044, 0.0457, 0.046, 0.0473, 0.0474, + 0.0475, 0.0475, 0.0474, 0.0475, 0.0476, 0.048, 0.0487, 0.049, 0.0499, 0.05, 0.0515, 0.052, 0.0533, 0.054, 0.0544, 0.054, 0.0539, 0.053, 0.0526, 0.052, 0.0512, 0.0515, + 0.0515, 0.053, 0.0538, 0.056, 0.0597, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuO8_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + -0.0014, 0.02, 0.0806, 0.07, 0.0673, 0.07, 0.0854, 0.09, 0.0901, 0.095, 0.0960, 0.098, 0.0992, 0.1, 0.1017, 0.102, 0.1030, 0.104, 0.1052, 0.107, 0.1098, 0.11, + 0.1176, 0.12, 0.1230, 0.12, 0.1176, 0.11, 0.1071, 0.105, 0.1032, 0.103, 0.1032, 0.1, 0.0963, 0.09, 0.0899, 0.09, 0.0939, 0.095, 0.1007, 0.102, 0.1037, 0.104, + 0.1029, 0.102, 0.1014, 0.102, 0.1020, 0.103, 0.1039, 0.105, 0.1072, 0.11, 0.1134, 0.12, 0.1207, 0.122, 0.1245, 0.123, 0.1236, 0.121, 0.1205, 0.12, 0.1158, 0.115, + 0.1132, 0.115, 0.1185, 0.12, 0.1345, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuO11_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2926, 0.2, 0.1863, 0.16, 0.1428, 0.14, 0.1322, 0.134, 0.1396, 0.14, 0.1450, 0.146, 0.1498, 0.15, 0.1527, 0.155, 0.1554, 0.157, 0.1583, 0.16, 0.1631, 0.17, + 0.1754, 0.18, 0.1841, 0.18, 0.1761, 0.17, 0.1600, 0.155, 0.1549, 0.155, 0.1555, 0.15, 0.1449, 0.14, 0.1352, 0.14, 0.1414, 0.15, 0.1519, 0.153, 0.1568, 0.156, + 0.1556, 0.154, 0.1534, 0.154, 0.1547, 0.156, 0.1573, 0.16, 0.1622, 0.17, 0.1713, 0.18, 0.1823, 0.185, 0.1886, 0.188, 0.1873, 0.183, 0.1829, 0.18, 0.1753, 0.174, + 0.1716, 0.175, 0.1800, 0.2, 0.2039, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuD5_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0840, 0.1, 0.1627, 0.18, 0.1934, 0.2, 0.2234, 0.23, 0.2430, 0.25, 0.2547, 0.26, 0.2618, 0.264, 0.2651, 0.265, 0.2655, 0.2655, 0.2659, 0.266, 0.2674, 0.27, + 0.2776, 0.28, 0.2841, 0.27, 0.2654, 0.25, 0.2351, 0.23, 0.2246, 0.225, 0.2247, 0.22, 0.2074, 0.20, 0.1913, 0.20, 0.2029, 0.21, 0.2231, 0.23, 0.2337, 0.233, + 0.2327, 0.23, 0.2291, 0.23, 0.2305, 0.232, 0.2344, 0.24, 0.2417, 0.25, 0.2553, 0.26, 0.2724, 0.28, 0.2816, 0.28, 0.2797, 0.276, 0.2720, 0.27, + 0.2603, 0.26, 0.2536, 0.26, 0.2660, 0.28, 0.3027, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_NeuE11_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1699, 0.18, 0.1971, 0.21, 0.2276, 0.23, 0.2483, 0.25, 0.2690, 0.28, 0.2820, 0.29, 0.2916, 0.295, 0.2992, 0.3, 0.3064, 0.31, 0.3151, 0.32, 0.3301, 0.34, 0.3593, 0.37, + 0.3873, 0.39, 0.3913, 0.38, 0.3793, 0.375, 0.3723, 0.37, 0.3678, 0.35, 0.3482, 0.33, 0.3249, 0.32, 0.3188, 0.319, 0.3188, 0.318, 0.3179, 0.315, 0.3128, 0.31, + 0.3086, 0.31, 0.3105, 0.312, 0.3148, 0.313, 0.3222, 0.33, 0.3364, 0.34, 0.3535, 0.36, 0.3629, 0.362, 0.3621, 0.36, 0.3549, 0.35, 0.3444, 0.34, 0.3394, 0.35, 0.3511, 0.36, 0.3862, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_NeuK16_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.5837, 0.45, 0.4117, 0.43, 0.4427, 0.47, 0.5098, 0.52, 0.5451, 0.55, 0.5698, 0.57, 0.5828, 0.59, 0.5939, 0.6, 0.6045, 0.607, 0.6140, 0.62, 0.6219, 0.63, 0.6330, 0.64, + 0.6419, 0.643, 0.6440, 0.642, 0.6417, 0.64, 0.6379, 0.631, 0.6309, 0.62, 0.6154, 0.6, 0.5911, 0.58, 0.5736, 0.57, 0.5612, 0.56, 0.5539, 0.55, 0.5462, 0.543, + 0.5406, 0.542, 0.5418, 0.543, 0.5452, 0.55, 0.5529, 0.56, 0.5654, 0.57, 0.5806, 0.584, 0.5888, 0.589, 0.5898, 0.586, 0.5858, 0.58, 0.5796, 0.577, 0.5770, 0.58, 0.5883, 0.59, 0.6190, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuM3_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2659, 0.255, 0.2526, 0.26, 0.2616, 0.27, 0.2854, 0.29, 0.3088, 0.31, 0.3231, 0.33, 0.3336, 0.34, 0.3421, 0.345, 0.347, 0.35, 0.3542, 0.36, 0.3647, 0.37, + 0.3854, 0.4, 0.4041, 0.402, 0.4012, 0.39, 0.3856, 0.38, 0.3769, 0.375, 0.3725, 0.36, 0.3525, 0.34, 0.3286, 0.325, 0.3247, 0.326, 0.3279, 0.328, 0.3285, 0.325, + 0.3240, 0.322, 0.3202, 0.321, 0.3220, 0.323, 0.3267, 0.33, 0.3342, 0.34, 0.3487, 0.35, 0.3667, 0.37, 0.3761, 0.375, 0.3746, 0.37, 0.3670, 0.36, 0.3559, 0.35, 0.3498, 0.35, 0.3630, 0.37, 0.3998, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuN18_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1284, 0.11, 0.1090, 0.13, 0.1573, 0.17, 0.1837, 0.19, 0.1971, 0.2, 0.2059, 0.21, 0.2143, 0.22, 0.2213, 0.225, 0.2271, 0.23, 0.2341, 0.24, 0.2487, 0.26, 0.2764, 0.29, + 0.3025, 0.303, 0.3052, 0.3, 0.2919, 0.29, 0.2843, 0.283, 0.2800, 0.27, 0.2612, 0.24, 0.2394, 0.235, 0.2339, 0.234, 0.2340, 0.233, 0.2326, 0.23, 0.2277, 0.225, + 0.2235, 0.224, 0.2246, 0.226, 0.2282, 0.23, 0.2349, 0.24, 0.2477, 0.25, 0.2632, 0.27, 0.2714, 0.271, 0.2702, 0.27, 0.2637, 0.26, 0.2538, 0.25, 0.2479, 0.25, 0.2589, 0.26, 0.2918, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuQ1_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0610, 0.06, 0.0592, 0.04, 0.0339, 0.04, 0.0338, 0.034, 0.0350, 0.036, 0.0363, 0.037, 0.0380, 0.038, 0.0383, 0.0383, 0.0385, 0.04, 0.0408, 0.042, 0.0451, 0.05, + 0.0524, 0.055, 0.0589, 0.058, 0.0585, 0.055, 0.0529, 0.05, 0.0456, 0.04, 0.0390, 0.035, 0.0330, 0.03, 0.0286, 0.028, 0.0275, 0.0276, 0.0275, 0.0278, 0.0279, 0.028, + 0.0289, 0.03, 0.0304, 0.031, 0.0320, 0.032, 0.0328, 0.033, 0.0341, 0.0345, 0.0346, 0.0346, 0.0347, 0.034, 0.0341, 0.034, 0.0336, 0.034, 0.0340, 0.035, + 0.0351, 0.036, 0.0373, 0.038, 0.0411, 0.042, 0.0446, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuS7_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1447, 0.06, 0.0448, 0.042, 0.0411, 0.03, 0.0282, 0.028, 0.0270, 0.029, 0.0298, 0.03, 0.0319, 0.032, 0.0331, 0.0333, 0.0335, 0.036, 0.0361, 0.038, 0.0403, 0.045, + 0.0493, 0.05, 0.0599, 0.06, 0.0636, 0.062, 0.0606, 0.06, 0.0547, 0.05, 0.0488, 0.045, 0.0421, 0.04, 0.0366, 0.035, 0.0335, 0.033, 0.0323, 0.032, 0.0320, 0.032, + 0.0321, 0.0322, 0.0324, 0.033, 0.0333, 0.034, 0.0345, 0.035, 0.0356, 0.036, 0.0364, 0.037, 0.0372, 0.037, 0.0367, 0.0365, 0.0363, 0.0364, + 0.0361, 0.0362, 0.0363, 0.037, 0.0376, 0.04, 0.0412, 0.042, 0.0450, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuV10_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1439, 0.07, 0.0583, 0.04, 0.0372, 0.037, 0.0362, 0.035, 0.0344, 0.034, 0.0340, 0.035, 0.0351, 0.036, 0.0361, 0.0361, 0.0361, 0.037, 0.0377, 0.039, 0.0404, 0.042, + 0.0450, 0.047, 0.0483, 0.048, 0.0475, 0.045, 0.0436, 0.04, 0.0387, 0.036, 0.0343, 0.03, 0.0299, 0.028, 0.0271, 0.027, 0.0262, 0.0262, 0.0262, 0.0267, 0.0269, 0.027, + 0.0283, 0.029, 0.0299, 0.03, 0.0308, 0.031, 0.0319, 0.032, 0.0331, 0.0333, 0.0337, 0.0337, 0.0337, 0.0333, 0.0332, 0.0332, 0.0331, 0.0331, 0.0331, 0.034, + 0.0341, 0.035, 0.0371, 0.038, 0.0399, 0.041, 0.0432, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuW18_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.4685, 0.45, 0.4262, 0.5, 0.5061, 0.55, 0.5898, 0.6, 0.6487, 0.66, 0.6781, 0.68, 0.6947, 0.7, 0.7070, 0.71, 0.7185, 0.72, 0.7294, 0.73, 0.7383, 0.74, 0.7499, 0.75, + 0.7582, 0.758, 0.7582, 0.755, 0.7531, 0.75, 0.7484, 0.745, 0.7422, 0.73, 0.7263, 0.72, 0.7033, 0.7, 0.6913, 0.69, 0.6820, 0.68, 0.6738, 0.67, 0.6628, 0.66, + 0.6512, 0.65, 0.6462, 0.645, 0.6448, 0.645, 0.6485, 0.65, 0.6569, 0.66, 0.6698, 0.67, 0.6781, 0.68, 0.6822, 0.682, 0.6820, 0.682, 0.6815, 0.682, 0.6820, 0.69, 0.6907, 0.7, 0.7152, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuZ14_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.2765, 0.2, 0.1352, 0.13, 0.1222, 0.121, 0.1206, 0.13, 0.1300, 0.134, 0.1357, 0.14, 0.1407, 0.142, 0.1455, 0.147, 0.1485, 0.15, 0.1539, 0.16, 0.1648, 0.17, + 0.1844, 0.2, 0.2015, 0.202, 0.2024, 0.2, 0.1922, 0.19, 0.1868, 0.185, 0.1841, 0.18, 0.1715, 0.16, 0.1566, 0.155, 0.1536, 0.154, 0.1545, 0.154, 0.1536, 0.151, + 0.1500, 0.148, 0.1471, 0.1472, 0.1478, 0.15, 0.1505, 0.153, 0.1552, 0.16, 0.1641, 0.17, 0.1751, 0.18, 0.1813, 0.181, 0.1801, 0.18, + 0.1757, 0.17, 0.1683, 0.165, 0.1642, 0.17, 0.1728, 0.18, 0.1970, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::J570_NeuC18_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0555, 0.055, 0.0545, 0.055, 0.0585, 0.058, 0.0577, 0.056, 0.0554, 0.056, 0.0564, 0.058, 0.0590, 0.06, 0.0611, 0.062, 0.0638, 0.065, 0.0685, 0.07, 0.0797, 0.09, + 0.1009, 0.11, 0.1222, 0.124, 0.1298, 0.127, 0.1257, 0.123, 0.1208, 0.12, 0.1164, 0.11, 0.1067, 0.1, 0.0954, 0.09, 0.0895, 0.088, 0.0862, 0.085, 0.0834, 0.082, + 0.0806, 0.08, 0.0782, 0.078, 0.0780, 0.078, 0.0789, 0.08, 0.0813, 0.084, 0.0858, 0.09, 0.0911, 0.092, 0.0944, 0.093, 0.0938, 0.092, 0.0914, 0.09, 0.0878, 0.086, + 0.0858, 0.09, 0.0903, 0.1, 0.1037, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuD17_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1980, 0.1, 0.0793, 0.06, 0.0578, 0.05, 0.0476, 0.046, 0.0454, 0.046, 0.0471, 0.048, 0.0499, 0.05, 0.0518, 0.052, 0.0533, 0.055, 0.0574, 0.06, 0.0676, 0.07, + 0.0897, 0.1, 0.1129, 0.113, 0.1140, 0.1, 0.0958, 0.08, 0.0743, 0.06, 0.0566, 0.05, 0.0422, 0.04, 0.0332, 0.03, 0.0297, 0.0295, 0.0292, 0.0293, 0.0294, 0.03, + 0.0306, 0.031, 0.0319, 0.032, 0.0339, 0.034, 0.0353, 0.036, 0.0363, 0.037, 0.0370, 0.037, 0.0372, 0.037, 0.0368, 0.0365, 0.0363, 0.036, + 0.0360, 0.037, 0.0376, 0.039, 0.0406, 0.042, 0.0448, 0.046, 0.0499, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuJ11_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1274, 0.1, 0.0916, 0.08, 0.0656, 0.061, 0.0604, 0.06, 0.0570, 0.06, 0.0604, 0.062, 0.0644, 0.065, 0.0668, 0.069, 0.0700, 0.072, 0.0754, 0.08, 0.0874, 0.1, + 0.1111, 0.12, 0.1327, 0.132, 0.1313, 0.12, 0.1127, 0.1, 0.0931, 0.08, 0.0758, 0.06, 0.0580, 0.05, 0.0449, 0.04, 0.0385, 0.037, 0.0360, 0.036, 0.0351, 0.035, + 0.0351, 0.0354, 0.0355, 0.036, 0.0371, 0.0375, 0.0379, 0.038, 0.0388, 0.04, 0.0406, 0.041, 0.0414, 0.0415, 0.0416, 0.041, 0.0409, 0.04, 0.0398, 0.0397, 0.0397, 0.04, + 0.0424, 0.043, 0.0458, 0.048, 0.0522, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::J570_NeuL4_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0348, 0.05, 0.0700, 0.09, 0.1043, 0.11, 0.1320, 0.14, 0.1505, 0.16, 0.1622, 0.17, 0.1721, 0.18, 0.1805, 0.185, 0.1877, 0.19, 0.1955, 0.2, 0.2068, 0.21, + 0.2226, 0.23, 0.2350, 0.235, 0.2352, 0.23, 0.2251, 0.22, 0.2128, 0.2, 0.1990, 0.18, 0.1761, 0.16, 0.1494, 0.13, 0.1296, 0.12, 0.1171, 0.11, 0.1089, 0.105, + 0.1010, 0.1, 0.0949, 0.093, 0.0926, 0.093, 0.0937, 0.095, 0.0961, 0.1, 0.1020, 0.11, 0.1104, 0.112, 0.1150, 0.115, 0.1155, 0.113, 0.1123, 0.11, + 0.1070, 0.105, 0.1040, 0.11, 0.1110, 0.12, 0.1323, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +const double ColorTemp::Colorlab_n72_n2_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + -0.0116, 0.01, 0.0171, 0.05, 0.0625, 0.08, 0.1486, 0.16, 0.1963, 0.2, 0.2409, 0.26, 0.2974, 0.31, 0.3468, 0.36, 0.3790, 0.39, 0.4075, 0.41, 0.4216, 0.43, + 0.4399, 0.47, 0.4878, 0.50, 0.5589, 0.57, 0.5882, 0.57, 0.5566, 0.52, 0.5030, 0.46, 0.4451, 0.42, 0.3928, 0.37, 0.3625, 0.35, 0.3396, 0.29, 0.2670, 0.15, + 0.1028, 0.05, -0.0397, -0.08, -0.1151, -0.12, -0.1464, -0.15, -0.1582, -0.16, -0.1609, -0.16, -0.1581, -0.155, -0.1556, -0.156, + -0.1582, -0.16, -0.1621, -0.165, -0.1683, -0.17, -0.1719, -0.17, -0.1696, -0.165, -0.1623, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::Colorlab_10_n70_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0964, 0.1, 0.1534, 0.2, 0.2437, 0.33, 0.4663, 0.5, 0.6005, 0.65, 0.6958, 0.75, 0.8010, 0.83, 0.8598, 0.858, 0.8579, 0.85, 0.8432, 0.83, 0.8102, 0.79, + 0.7607, 0.7, 0.6760, 0.6, 0.5530, 0.5, 0.4212, 0.3, 0.2974, 0.2, 0.1839, 0.1, 0.0743, 0.03, -0.0208, -0.05, -0.0747, -0.08, -0.0913, -0.05, -0.0458, 0.03, + 0.0806, 0.1, 0.1936, 0.2, 0.2556, 0.27, 0.2816, 0.29, 0.2925, 0.3, 0.3033, 0.31, 0.3175, 0.32, 0.3257, 0.325, 0.3246, 0.32, + 0.3187, 0.31, 0.3082, 0.305, 0.3014, 0.304, 0.3059, 0.31, 0.3253, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::Colorlab_n33_n70_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0615, 0.1, 0.1219, 0.2, 0.2179, 0.3, 0.4397, 0.5, 0.5722, 0.6, 0.6714, 0.7, 0.7834, 0.8, 0.8535, 0.86, 0.8647, 0.864, 0.8642, 0.864, 0.8429, 0.82, + 0.8035, 0.75, 0.7316, 0.7, 0.6238, 0.55, 0.4996, 0.45, 0.3717, 0.3, 0.2487, 0.2, 0.1299, 0.06, 0.0272, 0.01, -0.0315, -0.04, -0.0557, -0.051, + -0.0519, -0.03, -0.0234, 0.001, 0.0041, 0.01, 0.0201, 0.021, 0.0269, 0.028, 0.0298, 0.03, 0.0371, 0.04, 0.0497, 0.05, 0.0578, 0.056, + 0.0557, 0.05, 0.0490, 0.04, 0.0374, 0.03, 0.0299, 0.03, 0.0348, 0.04, 0.0537, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::Colorlab_n8_n74_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0603, 0.08, 0.1069, 0.15, 0.1810, 0.25, 0.3573, 0.4, 0.4634, 0.5, 0.5406, 0.6, 0.6266, 0.65, 0.6772, 0.679, 0.6800, 0.68, 0.6732, 0.66, 0.6511, 0.63, + 0.6136, 0.6, 0.5444, 0.5, 0.4415, 0.4, 0.3317, 0.3, 0.2286, 0.2, 0.1336, 0.1, 0.0425, 0.01, -0.0360, -0.05, -0.0807, -0.09, -0.0967, -0.08, + -0.0761, -0.05, -0.0119, 0.02, 0.0462, 0.05, 0.0784, 0.08, 0.0919, 0.095, 0.0974, 0.1, 0.1046, 0.11, 0.1152, 0.12, 0.1217, 0.121, + 0.1205, 0.12, 0.1155, 0.11, 0.1067, 0.104, 0.1010, 0.103, 0.1047, 0.11, 0.1199, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::Colorlab_19_n69_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1281, 0.16, 0.1941, 0.24, 0.2982, 0.4, 0.5607, 0.65, 0.7192, 0.8, 0.8299, 0.9, 0.9517, 1.0, 1.0174, 1.014, 1.0115, 1.0, 0.9899, 0.96, 0.9475, 0.91, + 0.8877, 0.82, 0.7902, 0.7, 0.6508, 0.57, 0.5008, 0.45, 0.3595, 0.3, 0.2302, 0.15, 0.1049, 0.02, -0.0045, -0.03, -0.0662, -0.07, -0.0832, -0.05, -0.0161, 0.05, + 0.1648, 0.2, 0.3257, 0.37, 0.4137, 0.43, 0.4506, 0.46, 0.4661, 0.47, 0.4801, 0.49, 0.4974, 0.5, 0.5072, 0.505, 0.5062, 0.5, 0.4995, 0.49, 0.4876, 0.48, + 0.4799, 0.48, 0.4849, 0.49, 0.5081, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::Colorlab_n80_10_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + -0.0247, -0.01, -0.0057, 0.01, 0.0242, 0.05, 0.0736, 0.08, 0.0996, 0.1, 0.1281, 0.14, 0.1660, 0.19, 0.2037, 0.21, 0.2337, 0.25, 0.2618, 0.27, 0.2793, 0.29, + 0.3024, 0.32, 0.3564, 0.4, 0.4360, 0.44, 0.4788, 0.47, 0.4655, 0.45, 0.4308, 0.42, 0.3920, 0.37, 0.3564, 0.34, 0.3357, 0.32, 0.3167, 0.28, 0.2434, 0.1, + 0.0745, 0.01, -0.0725, -0.09, -0.1506, -0.18, -0.1831, -0.19, -0.1955, -0.195, -0.1995, -0.199, -0.1989, -0.198, + -0.1976, -0.198, -0.1999, -0.2, -0.2027, -0.208, -0.2070, -0.208, -0.2094, -0.208, -0.2080, -0.207, -0.2038, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +const double ColorTemp::Colorlab_n80_26_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + -0.0325, -0.03, -0.0203, -0.01, -0.0012, 0.01, 0.0228, 0.03, 0.0332, 0.04, 0.0506, 0.06, 0.0762, 0.09, 0.1069, 0.12, 0.1370, 0.15, 0.1666, 0.17, 0.1877, 0.2, + 0.2174, 0.25, 0.2849, 0.33, 0.3849, 0.4, 0.4477, 0.45, 0.4509, 0.44, 0.4305, 0.42, 0.4049, 0.39, 0.3806, 0.37, 0.3664, 0.35, 0.3495, 0.29, 0.2724, 0.1, + 0.0921, 0.01, -0.0651, -0.09, -0.1489, -0.15, -0.1837, -0.19, -0.1970, -0.2, -0.2020, -0.202, -0.2029, -0.203, -0.2026, -0.204, + -0.2047, -0.205, -0.2069, -0.208, -0.2099, -0.21, -0.2115, -0.21, -0.2106, -0.209, -0.2086, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +/* +//0,1767000 0,2207000 0,3142000 0,5269000 0,7018000 0,7605000 0,7580000 0,7366000 0,7182000 0,6929000 0,6661000 0,6542000 +//0,6420000 0,6085000 0,5752000 0,5728000 0,5723000 0,5318000 0,4982000 0,5226000 0,5670000 0,5929000 0,5977000 0,5975000 +//0,6002000 0,6065000 0,6177000 0,6352000 0,6526000 0,6623000 0,6633000 0,6593000 0,6517000 0,6479000 0,6607000 0,6908000 + +const double ColorTemp::JDC468_greyc14_66_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1767, 0.19, 0.2207, 0.25, 0.3142, 0.40, 0.5269, 0.63, 0.7018, 0.73, 0.7605, 0.76, 0.7580, 0.74, 0.7366, 0.725, 0.7182, 0.705, 0.6929, 0.68, 0.6661, 0.66, 0.6542, 0.65, + 0.642, 0.62, 0.6085, 0.585, 0.5752, 0.573, 0.5728, 0.573, 0.5723, 0.555, 0.5318, 0.51, 0.4982, 0.51, 0.5226, 0.54, 0.5670, 0.58, 0.5929, 0.594, 0.5977, 0.597, 0.5975, 0.6, + 0.6002, 0.602, 0.6065, 0.61, 0.6177, 0.62, 0.6352, 0.64, 0.6526, 0.66, 0.6623, 0.662, 0.6633, 0.66, 0.6593, 0.653, 0.6517, 0.65, 0.6479, 0.65, 0.6607, 0.69, 0.6908, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +//0,1325000 0,1637000 0,2222000 0,3492000 0,4523000 0,4897000 0,4918000 0,4840000 0,4761000 0,4638000 0,4538000 0,4582000 +// 0,4588000 0,4360000 0,4091000 0,4101000 0,4128000 0,3785000 0,3494000 0,3720000 0,4122000 0,4339000 0,4362000 0,4355000 +// 0,4395000 0,4475000 0,4606000 0,4807000 0,5006000 0,5125000 0,5145000 0,5112000 0,5029000 0,4992000 0,5150000 0,5526000 + +const double ColorTemp::JDC468_greym13_325_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.1325, 0.15, 0.1637, 0.2, 0.2222, 0.28, 0.3492, 0.40, 0.4523, 0.47, 0.4897, 0.49, 0.4918, 0.49, 0.4840, 0.48, 0.4761, 0.47, 0.4638, 0.46, 0.4538, 0.455, 0.4582, 0.458, + 0.4588, 0.45, 0.4360, 0.42, 0.4091, 0.41, 0.4101, 0.411, 0.4128, 0.405, 0.3785, 0.36, 0.3494, 0.36, 0.3720, 0.41, 0.4122, 0.425, 0.4339, 0.435, 0.4362, 0.597, 0.4355, 0.437, + 0.4395, 0.44, 0.4475, 0.45, 0.4606, 0.47, 0.4807, 0.49, 0.5006, 0.51, 0.5125, 0.513, 0.5145, 0.512, 0.5112, 0.51, 0.5029, 0.5, 0.4992, 0.51, 0.5150, 0.53, 0.5526, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; + +//0,0823000 0,1036000 0,1337000 0,1966000 0,2468000 0,2679000 0,2728000 0,2726000 0,2724000 0,2698000 0,2705000 0,2810000 +// 0,2879000 0,2756000 0,2586000 0,2601000 0,2617000 0,2357000 0,2124000 0,2241000 0,2471000 0,2581000 0,2569000 0,2548000 +// 0,2579000 0,2653000 0,2765000 0,2941000 0,3126000 0,3230000 0,3238000 0,3189000 0,3091000 0,3043000 0,3200000 0,3579000 + +const double ColorTemp::JDC468_greyf26_156_spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0823, 0.1, 0.1036, 0.11, 0.1337, 0.16, 0.1966, 0.22, 0.2468, 0.255, 0.2679, 0.27, 0.2728, 0.273, 0.2726, 0.273, 0.2724, 0.271, 0.2698, 0.27, 0.2705, 0.275, 0.2810, 0.285, + 0.2879, 0.28, 0.2756, 0.26, 0.2586, 0.26, 0.2601, 0.261, 0.2617, 0.25, 0.2357, 0.22, 0.2124, 0.22, 0.2241, 0.23, 0.2471, 0.25, 0.2581, 0.278, 0.2569, 0.255, 0.2548, 0.255, + 0.2579, 0.26, 0.2653, 0.27, 0.2765, 0.28, 0.2941, 0.30, 0.3126, 0.32, 0.3230, 0.323, 0.3238, 0.32, 0.3189, 0.31, 0.3091, 0.302, 0.3043, 0.31, 0.3200, 0.34, 0.3579, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +*/ +//A1 0.0912 0.1228 0.1712 0.2978 0.3713 0.4241 0.4861 0.5255 0.5355 0.5363 0.5237 0.5251 +// 0.5722 0.6554 0.6936 0.6675 0.6203 0.5651 0.5116 0.4825 0.4714 0.4866 0.5320 0.5729 +// 0.5968 0.6069 0.6131 0.6198 0.6285 0.6325 0.6316 0.6282 0.6227 0.6196 0.6215 0.6337 + +const double ColorTemp::Colorlab_n80_5_9_5_9spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0912, 0.1, 0.1228, 0.15, 0.1712, 0.2, 0.2978, 0.32, 0.3713, 0.41, 0.4241, 0.44, 0.4861, 0.51, 0.5255, 0.53, 0.5355, 0.534, 0.5363, 0.53, 0.5237, 0.524, 0.5251, 0.56, + 0.5722, 0.6, 0.6554, 0.67, 0.6936, 0.67, 0.6675, 0.65, 0.6203, 0.6, 0.5651, 0.54, 0.5116, 0.5, 0.4825, 0.48, 0.4714, 0.48, 0.4866, 0.5, 0.5320, 0.55, 0.5729, 0.58, + 0.5968, 0.6, 0.6069, 0.61, 0.6131, 0.615, 0.6198, 0.62, 0.6285, 0.63, 0.6325, 0.632, 0.6316, 0.63, 0.6282, 0.625, 0.6227, 0.62, 0.6196, 0.62, 0.6215, 0.63, 0.6337, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +/* +//A2 0.0385 0.0514 0.0711 0.1229 0.1528 0.1744 0.1999 0.2163 0.2209 0.2216 0.2167 0.2185 +//0.2414 0.2813 0.3012 0.2922 0.2734 0.2511 0.2292 0.2173 0.2127 0.2183 0.2354 0.2508 +//0.2599 0.2637 0.2662 0.2689 0.2725 0.2742 0.2738 0.2724 0.2701 0.2689 0.2697 0.2747 + +const double ColorTemp::Colorlab_n57_5_6_9spect[97] = { + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, + 0.0385, 0.04, 0.0514, 0.06, 0.0711, 0.1, 0.1229, 0.14, 0.1528, 0.16, 0.1744, 0.18, 0.1999, 0.2, 0.2163, 0.22, 0.2209, 0.221, 0.2216, 0.22, 0.2167, 0.216, 0.2185, 0.23, + 0.2414, 0.26, 0.2813, 0.3, 0.3012, 0.3, 0.2922, 0.28, 0.2734, 0.26, 0.2511, 0.24, 0.2292, 0.22, 0.2173, 0.215, 0.2127, 0.215, 0.2183, 0.22, 0.2354, 0.24, 0.2508, 0.255, + 0.2599, 0.26, 0.2637, 0.263, 0.2662, 0.267, 0.2689, 0.27, 0.2725, 0.273, 0.2742, 0.274, 0.2738, 0.273, 0.2724, 0.271, 0.2701, 0.27, 0.2689, 0.269, 0.2697, 0.27, 0.2747, + 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0 +}; +*/ /* * Name: XYZtoCorColorTemp.c * @@ -1024,6 +2766,197 @@ void ColorTemp::cieCAT02(double Xw, double Yw, double Zw, double &CAM02BB00, dou } +void ColorTemp::cieCAT02float(float Xw, float Yw, float Zw, float &CAM02BB00, float &CAM02BB01, float &CAM02BB02, float &CAM02BB10, float &CAM02BB11, float &CAM02BB12, float &CAM02BB20, float &CAM02BB21, float &CAM02BB22, float adap) +{ + +// CIECAT02 - J.Desmis January 2012 review September 2012 + const float whiteD50p[3] = {0.9646019585, 1.0, 0.8244507152}; //calculate with these tools + + float cam_dest[3] = {0., 0., 0.}; + float cam_orig[3] = {0., 0., 0.}; + const float CAT02[3][3] = {{0.7328, 0.4296, -0.1624},//CAT02 2002 + { -0.7036, 1.6975, 0.0061}, + {0.0030, 0.0136, 0.9834} + }; + const float INVCAT02[3][3] = {{1.09612382083551, -0.278869000218287, 0.182745179382773}, //Inverse CAT02 + {0.454369041975359, 0.4735331543070412, 0.0720978037172291}, + { -0.009627608738442936, -0.00569803121611342, 1.01532563995454} + }; + + float inv_white_orig[3][3] = {{0., 0., 0.}, + {0., 0., 0.}, + {0., 0., 0.} + }; + float intermed[3][3] = {{0., 0., 0.}, + {0., 0., 0.}, + {0., 0., 0.} + }; + + float intermed_2[3][3] = {{0., 0., 0.}, + {0., 0., 0.}, + {0., 0., 0.} + }; + float CAM02[3][3] = {{0., 0., 0.}, + {0., 0., 0.}, + {0., 0., 0.} + }; + float D = adap; + + //white destination Wd : RT use always D50 + cam_dest[0] = CAT02[0][0] * whiteD50p[0] + CAT02[0][1] * whiteD50p[1] + CAT02[0][2] * whiteD50p[2]; //Cone response RoD + cam_dest[1] = CAT02[1][0] * whiteD50p[0] + CAT02[1][1] * whiteD50p[1] + CAT02[1][2] * whiteD50p[2]; //GaD + cam_dest[2] = CAT02[2][0] * whiteD50p[0] + CAT02[2][1] * whiteD50p[1] + CAT02[2][2] * whiteD50p[2]; //BeD + + //origin white Ws : A, D65, custom, etc. + cam_orig[0] = CAT02[0][0] * Xw + CAT02[0][1] * Yw + CAT02[0][2] * Zw; //Cone response RoS + cam_orig[1] = CAT02[1][0] * Xw + CAT02[1][1] * Yw + CAT02[1][2] * Zw; + cam_orig[2] = CAT02[2][0] * Xw + CAT02[2][1] * Yw + CAT02[2][2] * Zw; + + //inverse white + inv_white_orig[0][0] = 1. / cam_orig[0]; // 1/RoS + inv_white_orig[1][1] = 1. / cam_orig[1]; // 1/GaS + inv_white_orig[2][2] = 1. / cam_orig[2]; // 1/BeS + + //intermediates computation + for (int i = 0; i < 3; i++) + for (int j = 0; j < 3 ; j++) { + intermed[i][j] = inv_white_orig[i][i] * CAT02[i][j]; + } + + for (int i = 0; i < 3; i++) + for (int j = 0; j < 3 ; j++) { + intermed_2[i][j] = cam_dest[i] * intermed[i][j]; + } + + //and CAM02 + for (int i = 0; i < 3; i++) + for (int j = 0; j < 3; j++) + for (int k = 0; k < 3; k++) { + CAM02[i][j] += INVCAT02[i][k] * intermed_2[k][j]; + } + + //adaptation jdc : slightly different from CIECAM02 : Rc=(Yw(D/Rw)+(1-D))*R , but it's work ! true at 0 and 1 + CAM02[1][1] = (CAM02[1][1] - 1.0) * D + 1.0; + CAM02[0][0] = (CAM02[0][0] - 1.0) * D + 1.0; + CAM02[2][2] = (CAM02[2][2] - 1.0) * D + 1.0; +// CAM02[1][1] *= D; +// CAM02[0][0] *= D; +// CAM02[2][2] *= D; + CAM02[0][1] *= D; + CAM02[0][2] *= D; + CAM02[1][0] *= D; + CAM02[1][2] *= D; + CAM02[2][0] *= D; + CAM02[2][1] *= D; + //CAT02 matrix with D adaptation + CAM02BB00 = CAM02[0][0]; + CAM02BB01 = CAM02[0][1]; + CAM02BB02 = CAM02[0][2]; + CAM02BB10 = CAM02[1][0]; + CAM02BB11 = CAM02[1][1]; + CAM02BB12 = CAM02[1][2]; + CAM02BB20 = CAM02[2][0]; + CAM02BB21 = CAM02[2][1]; + CAM02BB22 = CAM02[2][2]; + +} + +void ColorTemp::icieCAT02float(float Xw, float Yw, float Zw, float &iCAM02BB00, float &iCAM02BB01, float &iCAM02BB02, float &iCAM02BB10, float &iCAM02BB11, float &iCAM02BB12, float &iCAM02BB20, float &iCAM02BB21, float &iCAM02BB22, float adap) +{ + +// CIECAT02 - J.Desmis January 2012 review September 2017 + const float whiteD50p[3] = {0.9646019585, 1.0, 0.8244507152}; //calculate with these tools + + float cam_dest[3] = {0., 0., 0.}; + float cam_orig[3] = {0., 0., 0.}; + const float CAT02[3][3] = {{0.7328, 0.4296, -0.1624},//CAT02 2002 + { -0.7036, 1.6975, 0.0061}, + {0.0030, 0.0136, 0.9834} + }; + const float INVCAT02[3][3] = {{1.09612382083551, -0.278869000218287, 0.182745179382773}, //Inverse CAT02 + {0.454369041975359, 0.4735331543070412, 0.0720978037172291}, + { -0.009627608738442936, -0.00569803121611342, 1.01532563995454} + }; + + float inv_white_orig[3][3] = {{0., 0., 0.}, + {0., 0., 0.}, + {0., 0., 0.} + }; + float intermed[3][3] = {{0., 0., 0.}, + {0., 0., 0.}, + {0., 0., 0.} + }; + + float intermed_2[3][3] = {{0., 0., 0.}, + {0., 0., 0.}, + {0., 0., 0.} + }; + float INVCAM02[3][3] = {{0., 0., 0.}, + {0., 0., 0.}, + {0., 0., 0.} + }; + float D = adap / 2.; + + //white destination Wd : RT use always D50 + cam_dest[0] = INVCAT02[0][0] * whiteD50p[0] + INVCAT02[0][1] * whiteD50p[1] + INVCAT02[0][2] * whiteD50p[2]; //Cone reponse RoD + cam_dest[1] = INVCAT02[1][0] * whiteD50p[0] + INVCAT02[1][1] * whiteD50p[1] + INVCAT02[1][2] * whiteD50p[2]; //GaD + cam_dest[2] = INVCAT02[2][0] * whiteD50p[0] + INVCAT02[2][1] * whiteD50p[1] + INVCAT02[2][2] * whiteD50p[2]; //BeD + + //origin white Ws : A, D65, custom, etc. + cam_orig[0] = INVCAT02[0][0] * Xw + INVCAT02[0][1] * Yw + INVCAT02[0][2] * Zw; //Cone reponse RoS + cam_orig[1] = INVCAT02[1][0] * Xw + INVCAT02[1][1] * Yw + INVCAT02[1][2] * Zw; + cam_orig[2] = INVCAT02[2][0] * Xw + INVCAT02[2][1] * Yw + INVCAT02[2][2] * Zw; +// cam_orig[0] = CAT02[0][0] * Xw + CAT02[0][1] * Yw + CAT02[0][2] * Zw; //Cone reponse RoS +// cam_orig[1] = CAT02[1][0] * Xw + CAT02[1][1] * Yw + CAT02[1][2] * Zw; + // cam_orig[2] = CAT02[2][0] * Xw + CAT02[2][1] * Yw + CAT02[2][2] * Zw; + + //inverse white + inv_white_orig[0][0] = 1. / cam_orig[0]; // 1/RoS + inv_white_orig[1][1] = 1. / cam_orig[1]; // 1/GaS + inv_white_orig[2][2] = 1. / cam_orig[2]; // 1/BeS + + //intermediates computation + for (int i = 0; i < 3; i++) + for (int j = 0; j < 3 ; j++) { + // intermed[i][j] = inv_white_orig[i][i] * INVCAT02[i][j]; + intermed[i][j] = inv_white_orig[i][i] * CAT02[i][j]; + } + + for (int i = 0; i < 3; i++) + for (int j = 0; j < 3 ; j++) { + intermed_2[i][j] = cam_dest[i] * intermed[i][j]; + } + + //and CAM02 + for (int i = 0; i < 3; i++) + for (int j = 0; j < 3; j++) + for (int k = 0; k < 3; k++) { + INVCAM02[i][j] += INVCAT02[i][k] * intermed_2[k][j]; + } + + //adaptation jdc : slightly different from CIECAM02 : Rc=(Yw(D/Rw)+(1-D))*R , but it's work ! true at 0 and 1 + INVCAM02[0][0] = (INVCAM02[0][0] - 1.0) * D + 1.0; + INVCAM02[2][2] = (INVCAM02[2][2] - 1.0) * D + 1.0; + INVCAM02[0][1] *= D; + INVCAM02[0][2] *= D; + INVCAM02[1][0] *= D; + INVCAM02[1][2] *= D; + INVCAM02[2][0] *= D; + INVCAM02[2][1] *= D; + //CAT02 matrix with D adaptation + iCAM02BB00 = INVCAM02[0][0]; + iCAM02BB01 = INVCAM02[0][1]; + iCAM02BB02 = INVCAM02[0][2]; + iCAM02BB10 = INVCAM02[1][0]; + iCAM02BB11 = INVCAM02[1][1]; + iCAM02BB12 = INVCAM02[1][2]; + iCAM02BB20 = INVCAM02[2][0]; + iCAM02BB21 = INVCAM02[2][1]; + iCAM02BB22 = INVCAM02[2][2]; + +} + + void ColorTemp::temp2mulxyz (double temp, const std::string &method, double &Xxyz, double &Zxyz) { double x, y, z; @@ -1071,10 +3004,10 @@ void ColorTemp::temp2mul (double temp, double green, double equal, double& rmul, double Xwb, Zwb; temp2mulxyz(temp, method, Xwb, Zwb); - float adj = 1.f; + double adj = 1.0; if(equal < 0.9999 || equal > 1.0001 ) { - adj = (100.f + ( 1000.f - (1000.f * (float)equal) ) / 20.f) / 100.f; + adj = (100.0 + ( 1000.0 - (1000.0 * equal) ) / 20.0) / 100.0; } @@ -1389,7 +3322,7 @@ void ColorTemp::temp2mul (double temp, double green, double equal, double& rmul, } for(int i = 0; i < 8; i++) { - CRIs[i] = 100 - 3.0 * DeltaEs[i]; //3.0 coef to adapt ==> same results than CRI "official" + CRIs[i] = 100 - 3.f * DeltaEs[i]; //3.0 coef to adapt ==> same results than CRI "official" } for(int i = 0; i < 8; i++) { @@ -1409,7 +3342,7 @@ void ColorTemp::temp2mul (double temp, double green, double equal, double& rmul, } for(int i = 0; i < N_c; i++) { - CRI[i] = 100 - 3.0 * DeltaE[i]; //3.0 coef to adapt ==> same results than CRI "official" + CRI[i] = 100 - 3.f * DeltaE[i]; //3.0 coef to adapt ==> same results than CRI "official" } for(int i = 0; i < N_c; i++) { @@ -1425,8 +3358,8 @@ void ColorTemp::temp2mul (double temp, double green, double equal, double& rmul, quadCRI /= N_c; if(settings->CRI_color != 0) { - printf("CRI_standard=%i CRI:1->8=%i %i %i %i %i %i %i %i Sigma=%2.1f\n", (int) CRI_RTs, (int) CRIs[0], (int) CRIs[1], (int) CRIs[2], (int) CRIs[3], (int) CRIs[4], (int) CRIs[5], (int) CRIs[6], (int) CRIs[7], sqrt(quadCRIs)); - printf("CRI_RT_exten=%i CRI:9->20=%i %i %i %i %i %i %i %i %i %i %i %i Sigma=%2.1f\n", (int) CRI_RT, (int) CRI[8], (int) CRI[9], (int) CRI[10], (int) CRI[11], (int) CRI[12], (int) CRI[13], (int) CRI[14], (int) CRI[15], (int) CRI[16], (int) CRI[17], (int) CRI[18], (int) CRI[19], sqrt(quadCRI)); + printf("CRI_standard=%i CRI:1->8=%i %i %i %i %i %i %i %i Sigma=%2.1f\n", (int) CRI_RTs, (int) CRIs[0], (int) CRIs[1], (int) CRIs[2], (int) CRIs[3], (int) CRIs[4], (int) CRIs[5], (int) CRIs[6], (int) CRIs[7], sqrt(static_cast(quadCRIs))); + printf("CRI_RT_exten=%i CRI:9->20=%i %i %i %i %i %i %i %i %i %i %i %i Sigma=%2.1f\n", (int) CRI_RT, (int) CRI[8], (int) CRI[9], (int) CRI[10], (int) CRI[11], (int) CRI[12], (int) CRI[13], (int) CRI[14], (int) CRI[15], (int) CRI[16], (int) CRI[17], (int) CRI[18], (int) CRI[19], static_cast(sqrt(quadCRI))); } } } @@ -1438,8 +3371,8 @@ void ColorTemp::temp2mul (double temp, double green, double equal, double& rmul, //calculate spectral data for blackbody at temp! double ColorTemp::blackbody_spect(double wavelength, double temperature) { - double wlm = wavelength * 1e-9; /* Wavelength in meters */ - return (3.7417715247e-16 / pow(wlm, 5)) / //3.7417..= c1 = 2*Pi*h*c2 where h=Planck constant, c=velocity of light + const double wlm = wavelength * 1e-9; /* Wavelength in meters */ + return (3.7417715247e-16 / rtengine::pow5(wlm)) / //3.7417..= c1 = 2*Pi*h*c2 where h=Planck constant, c=velocity of light (xexp(1.438786e-2 / (wlm * temperature)) - 1.0); //1.4387..= c2 = h*c/k where k=Boltzmann constant } @@ -1458,6 +3391,7 @@ this values are often called xBar yBar zBar and are characteristics of a color / values cie_colour_match[][3] = 2° Standard Observer x2, y2, z2 E.g. for 380nm: x2=0.001368 y2=0.000039 z2=0.006451 round in J.Walker to 0.0014 0.0000 0.0065 above I have increase precision used by J.Walker and pass to 350nm to 830nm +And also add 10° standard observer */ void ColorTemp::spectrum_to_xyz_daylight(double _m1, double _m2, double &x, double &y, double &z) @@ -1516,6 +3450,7 @@ void ColorTemp::spectrum_to_xyz_preset(const double* spec_intens, double &x, dou values cie_colour_match[][3] = 2° Standard Observer x2, y2, z2 E.g. for 380nm: x2=0.001368 y2=0.000039 z2=0.006451 round in J.Walker to 0.0014 0.0000 0.0065 above I have increased the precision used by J.Walker and pass from 350nm to 830nm + And also add standard observer 10° */ for (i = 0, lambda = 350.; lambda < 830.1; i++, lambda += 5.) { double Me = get_spectral_color(lambda, spec_intens); @@ -1565,62 +3500,38 @@ void ColorTemp::spectrum_to_color_xyz_preset(const double* spec_color, const dou void ColorTemp::spectrum_to_color_xyz_daylight(const double* spec_color, double _m1, double _m2, double &xx, double &yy, double &zz) { int i; - double lambda, X = 0, Y = 0, Z = 0, Yo = 0; + double lambda, X = 0, Y = 0, Z = 0; for (i = 0, lambda = 350; lambda < 830.1; i++, lambda += 5) { - - double Me; - double Mc; - - Me = get_spectral_color(lambda, spec_color); - Mc = daylight_spect(lambda, _m1, _m2); + const double Me = spec_color[i]; + const double Mc = daylight_spect(lambda, _m1, _m2); X += Mc * cie_colour_match_jd[i][0] * Me; Y += Mc * cie_colour_match_jd[i][1] * Me; Z += Mc * cie_colour_match_jd[i][2] * Me; } - for (i = 0, lambda = 350; lambda < 830.1; i++, lambda += 5) { - - double Ms; - - Ms = daylight_spect(lambda, _m1, _m2); - Yo += cie_colour_match_jd[i][1] * Ms; - } - - xx = X / Yo; - yy = Y / Yo; - zz = Z / Yo; + xx = X / Y; + yy = 1.0; + zz = Z / Y; } //calculate XYZ from spectrum data (color) and illuminant : J.Desmis december 2011 void ColorTemp::spectrum_to_color_xyz_blackbody(const double* spec_color, double _temp, double &xx, double &yy, double &zz) { int i; - double lambda, X = 0, Y = 0, Z = 0, Yo = 0; + double lambda, X = 0, Y = 0, Z = 0; for (i = 0, lambda = 350; lambda < 830.1; i++, lambda += 5) { - - double Me; - double Mc; - - Me = get_spectral_color(lambda, spec_color); - Mc = blackbody_spect(lambda, _temp); + const double Me = spec_color[i]; + const double Mc = blackbody_spect(lambda, _temp); X += Mc * cie_colour_match_jd[i][0] * Me; Y += Mc * cie_colour_match_jd[i][1] * Me; Z += Mc * cie_colour_match_jd[i][2] * Me; } - for (i = 0, lambda = 350; lambda < 830.1; i++, lambda += 5) { - - double Ms; - - Ms = blackbody_spect(lambda, _temp); - Yo += cie_colour_match_jd[i][1] * Ms; - } - - xx = X / Yo; - yy = Y / Yo; - zz = Z / Yo; + xx = X / Y; + yy = 1.0; + zz = Z / Y; } double ColorTemp::daylight_spect(double wavelength, double m1, double m2) @@ -1648,6 +3559,289 @@ double ColorTemp::daylight_spect(double wavelength, double m1, double m2) return (s0[wlm] + m1 * s1[wlm] + m2 * s2[wlm]); } +//tempxy : return x and y of xyY for 200 or more refreence color, and for T temperature from 2000K to 12000K +// we can change step for temperature and increase number for T > 7500K if necessary +//these values Temp, x, y are references for all calculations and very precise. +//copyright J.Desmis august 2017 and june 2018 +void ColorTemp::tempxy(bool separated, int repref, float **Tx, float **Ty, float **Tz, float **Ta, float **Tb, float **TL, double *TX, double *TY, double *TZ, const procparams::WBParams & wbpar) +{ + const double* spec_colorforxcyc[] = {//color references + JDC468_BluH10_spect, JDC468_BluD6_spect, ColorchechCyaF3_spect, JDC468_BluM5_spect, // 0 3 + ColorGreenM25_spect, JDC468_GreK7_spect, ColabSky42_0_m24_spect, ColabSky60_0_m31_spect, ColorchechBluC150_m5_m22_spect,//8 + JDC468_GreQ7_spect, ColorchechDCBluN881_m7_m14_spect, ColorchechGreB3_spect, ColorchechPurD2_spect, //12 + ColorchechSGBlaN3_6_spect, ColorchechGraC4_67_spect, JDC468_K15_87greyspect,//15 + JDC468_GraK14_44_spect, ColorGreenalsi_spect, Fictif_61greyspect, ColorchechGreD1_spect,//19 + ColorchechWhiA496_spect, JDC468_GreA10_spect, JDC468_GreI8_spect,//22 + ColabSkin91_4_14_spect, JDC468_PurE24_spect, //24 + ColorchechSGSkiK285_11_17_spect, ColorchechGreE2_spect, ColorchechMagE3_spect, //27 + ColorchechSkiB166_18_18_spect, ColabSkin70_7_32_spect, ColorchechSGSkiF763_14_26_spect,//30 + ColorchechSkiA138_13_14_spect, ColabSkin57_22_18_spect, JDC468_YelN10_spect,//33 + ColabSkin35_15_17_spect, ColabSkin40_17_17_spect, ColorRedkurttu_spect, ColorYellowkeltano_spect, ColorchechYelD3_spect, JDC468_OraO18_spect,//39 + JDC468_GreN7_spect, JDC468_RedG21va_spect, JDC468_OraD17_spect,//42 + ColorchechredC3_spect, JDC468_RedI9_spect, ColorRedpetunia_spect, ColorchechOraA2_spect,//46 + ColabSkin87_8_8_spect, ColabSkin89_8_21_spect, ColabSkin75_8_4_spect, ColabSkin75_10_33_spect,//50 + ColabSkin65_33_11_spect, ColabSkin65_7_24_spect, ColabSkin57_19_6_spect, ColabSkin57_4_19_spect, ColabSkin57_10_28_spect, ColabSkin40_17_6_spect,//56 + ColabSkin26_18_18_spect, ColabSkin90_m1_20_spect, ColorRedlupiini_spect, ColorRedhevosminttu_spect, //60 + ColorRedneilikka_spect, ColorRedpelagornia_spect, ColorRedtalvio_spect, ColorBrownpoimulehti_spect, ColorOrangetuntematon_spect,//65 + ColorOrangetlehmus_spect, ColorOrangvaahtera_spect, ColorBrownlehmus_spect, ColorBrownuotiosammal_spect,//69 + ColorBlacksoil_spect, ColorGraynahjajaekaelae_spect, //71 + ColorGreennuotisammal_spect, ColorGreenleskenlehti_spect, ColorGreenlinnunkaali_spect, //74 + ColorGreenpelto_spect, ColorGreenrodvoikukka, ColorGreenlehmus, ColorGreenlinden, ColorYellowlehmus, ColorYellowsuikeroalpi, //80 + ColorYellowpensashanhikki1, ColorYellowpensashanhikki2, ColorBluehiidenvirna, ColorBluekurkkuyrtti, //84 + ColorPinksiankaersaemoe, ColorVioletharakankello, ColorVioletalsikeapila, ColorVioletakilleija, ColorOrangekehaekukka,//89 + ColorRedpihlaja, ColorVioletpetunia, ColorVioletorvokki, ColorBluesinisievikki, ColorBlueiisoppi, ColorBluelobelia, //95 + ColorWhiteojaka, ColorWhitepetunia, ColorWhitepelargonia, ColorWhitepaeivaen, JDC468_B14_75Redspect,//100 + ColorGreenkoriste, ColorGreenpoimulehti, ColorGreenhopeapaju, //103 + ColorReduuden, ColorRedpajuan, ColorRedjaloan, ColorBlueukon, ColorBlueorvokki, ColorBluemalvikki, //109 + ColorBlackmaito, ColorOrangpihlaja, ColorBlackpihlaja, //112 + ColorViolA1_spect, ColorViolA4_spect, ColorViolA6_spect, ColorBlueSkyK3_spect, ColorBlueSkyK9_spect, //117 + ColorBlueSkyC4_spect, ColorBlueSkyC14_spect, ColorBlueSkyE4_spect, //120 + ColorBlueSkyM1_spect, ColorBlueSky2B1_spect, ColorBlueSkyT7_spect, //123 + ColorBlueSkyU19_spect, ColorBlueSkyU2_spect, ColorBlueSkyT17_spect, //126 + ColorBlackM8_spect, ColorBlackM12_spect, ColorBlackM13_spect, ColorWhite2B12_spect, ColorWhite2B14_spect, //131 + JDC468_Blackred97_spect, JDC468_Blackredbl443_spect, JDC468_Blackbl27_spect, JDC468_Blackbl28_spect, //135 + JDC468_Blackgr214_spect, JDC468_Blackbl436_spect, JDC468_Whitebl455_spect, JDC468_Blackvio101_spect, JDC468_Whitebl92_spect, JDC468_Greyredbl94_spect, //141 + JDC468_Blue32_spect, JDC468_Blue236_spect, JDC468_Gre300_spect, //144 + JDC468_Blue340_spect, JDC468_Gree110_spect, JDC468_Gree457_spect, JDC468_Yel241_spect, JDC468_Ora321_spect, JDC468_Yellow353_spect, JDC468_Mag465_spect, //151 + JDC468_Mag333_spect, JDC468_Mag203_spect, J570_BlueB6_spect, J570_BlueB15_spect, J570_BlueC2_spect, J570_BlueC14_spect, J570_BlueC16_spect,//158 + J570_BlueF1_spect, J570_BlueF2_spect, J570_BlueF10_spect, J570_BlueF13_spect, J570_BlueG9_spect, J570_BlueG19_spect, J570_BlueI5_spect,//165 + J570_BlueI3_spect, J570_BlueI19_spect, J570_BlueJ4_spect, J570_BlueJ6_spect, J570_BlueJ11_spect, J570_BlueK5_spect, //171 + J570_BlueN1_spect, J570_BlueN4_spect, J570_BlueO19_spect, J570_BlueU8_spect, J570_NeuN8_spect,//176 + J570_NeuN9_spect, J570_NeuO8_spect, J570_NeuO11_spect, J570_NeuD5_spect,//180 + J570_NeuE11_spect, J570_NeuK16_spect, J570_NeuM3_spect, J570_NeuN18_spect, + J570_NeuQ1_spect, J570_NeuS7_spect, + J570_NeuV10_spect, J570_NeuW18_spect, J570_NeuZ14_spect, //189 + J570_NeuC18_spect, J570_NeuD17_spect, J570_NeuJ11_spect, J570_NeuL4_spect, Colorlab_n72_n2_spect, + Colorlab_10_n70_spect, Colorlab_n33_n70_spect, Colorlab_n8_n74_spect, Colorlab_19_n69_spect, Colorlab_n80_10_spect, Colorlab_n80_26_spect, + Colorlab_n80_5_9_5_9spect //, Colorlab_n57_5_6_9spect + + /*JDC468_greyc14_66_spect, JDC468_greym13_325_spect, JDC468_greyf26_156_spect*/ + }; + + + typedef struct WbTxyz { + double Tem; + double XX; + double ZZ; + } WbTxyz; + //probbaly can be "passed" with rawimagesource.cc but I don't know how to do. + constexpr WbTxyz Txyz[118] = {//temperature Xwb Zwb 118 values - same table as in Rawimagesource.cc x wb and y wb are calculated after + {2001., 1.273842, 0.145295}, + {2101., 1.244008, 0.167533}, + {2201., 1.217338, 0.190697}, + {2301., 1.193444, 0.214632}, + {2401., 1.171996, 0.239195}, + {2501., 1.152883, 0.264539}, + {2605., 1.134667, 0.290722}, + {2655., 1.126659, 0.303556}, + {2705., 1.119049, 0.316446}, + {2755., 1.111814, 0.329381}, + {2803., 1.105381, 0.342193}, + {2856., 1.098258, 0.355599}, + {2910., 1.091550, 0.369645}, + {2960., 1.085649, 0.382655}, + {3003., 1.080982, 0.394258}, + {3050., 1.075727, 0.406057}, + {3103., 1.070277, 0.419815}, + {3153., 1.065384, 0.432769}, + {3203., 1.060906, 0.446161}, + {3250., 1.056535, 0.457806}, + {3303., 1.052034, 0.471422}, + {3353., 1.047990, 0.484218}, + {3400., 1.044547, 0.496719}, + {3450., 1.040667, 0.508891}, + {3500., 1.037145, 0.521523}, + {3550., 1.033783, 0.534090}, + {3600., 1.030574, 0.546590}, + {3650., 1.027510, 0.559020}, + {3699., 1.024834, 0.571722}, + {3801., 1.019072, 0.596102}, + {3851., 1.016527, 0.608221}, + {3902., 1.014244, 0.621136}, + {3952., 1.011729, 0.632447}, + {4002., 0.996153, 0.609518}, + {4052., 0.993720, 0.620805}, + {4102., 0.993908, 0.631520}, + {4152., 0.989179, 0.643262}, + {4202., 0.989283, 0.653999}, + {4252., 0.985039, 0.665536}, + {4302., 0.985067, 0.676288}, + {4352., 0.981271, 0.687599}, + {4402., 0.981228, 0.698349}, + {4452., 0.977843, 0.709425}, + {4502., 0.977736, 0.720159}, + {4552., 0.974728, 0.730993}, + {4602., 0.974562, 0.741698}, + {4652., 0.971899, 0.752284}, + {4702., 0.971681, 0.762949}, + {4752., 0.969335, 0.773285}, + {4802., 0.969069, 0.783899}, + {4827., 0.967570, 0.788836}, + {4852., 0.967011, 0.793982}, + {4877., 0.966465, 0.799108}, + {4902., 0.965933, 0.804214}, + {4927., 0.965414, 0.809229}, + {4952., 0.964908, 0.814366}, + {4977., 0.964415, 0.819412}, + {5002., 0.963934, 0.824438}, + {5027., 0.963465, 0.829444}, + {5052., 0.963008, 0.834429}, + {5077., 0.962563, 0.839395}, + {5102., 0.962129, 0.844339}, + {5127., 0.961706, 0.849263}, + {5152., 0.961294, 0.854166}, + {5177., 0.960893, 0.859049}, + {5202., 0.960501, 0.863911}, + {5252., 0.959749, 0.873572}, + {5302., 0.959313, 0.883815}, + {5352., 0.958361, 0.892644}, + {5402., 0.957903, 0.902793}, + {5452., 0.957116, 0.911379}, + {5502., 0.956639, 0.921431}, + {5552., 0.956002, 0.929779}, + {5602., 0.955509, 0.939728}, + {5652., 0.955008, 0.947842}, + {5702., 0.954502, 0.957685}, + {5752., 0.954124, 0.965569}, + {5802., 0.953608, 0.975303}, + {5852., 0.953342, 0.982963}, + {5902., 0.952818, 0.992584}, + {5952., 0.952652, 1.000025}, + {6002., 0.952122, 1.009532}, + {6052., 0.952047, 1.016759}, + {6102., 0.951514, 1.026149}, + {6152., 0.951520, 1.033168}, + {6202., 0.950985, 1.042439}, + {6252., 0.951064, 1.049256}, + {6302., 0.950530, 1.058406}, + {6352., 0.950674, 1.065027}, + {6402., 0.950143, 1.074055}, + {6452., 0.950345, 1.080484}, + {6502., 0.950201, 1.088097}, + {6552., 0.950070, 1.095633}, + {6602., 0.949952, 1.103094}, + {6652., 0.949846, 1.110479}, + {6702., 0.949752, 1.119138}, + {6752., 0.949668, 1.125027}, + {6802., 0.949596, 1.132190}, + {6902., 0.949033, 1.147691}, + {7002., 0.949402, 1.160129}, + {7152., 0.949348, 1.180429}, + {7301., 0.948896, 1.201432}, + {7451., 0.949434, 1.219076}, + {7601., 0.949099, 1.239061}, + {7751., 0.949729, 1.255559}, + {7901., 0.949498, 1.274460}, + {8151., 0.950361, 1.300912}, + {8301., 0.950253, 1.318464}, + {8451., 0.950966, 1.332651}, + {8601., 0.950941, 1.349261}, + {8801., 0.951772, 1.367421}, + {9001., 0.951969, 1.387639}, + {9201., 0.952784, 1.404422}, + {9401., 0.953081, 1.423213}, + {9901., 0.954537, 1.464134}, + {10501., 0.956321, 1.508623}, + {11001., 0.957747, 1.541281}, + {12001., 0.960440, 1.601019} + }; + + int N_c = sizeof(spec_colorforxcyc) / sizeof(spec_colorforxcyc[0]); //number of color + int N_t = sizeof(Txyz) / sizeof(Txyz[0]); //number of temperature White point + typedef struct XYZref { + double Xref; + double Yref; + double Zref; + } XYZref; + XYZref Refxyz[N_c + 1]; + + for (int i = 0; i < N_c; i++) { + Refxyz[i].Xref = 0.f; + Refxyz[i].Yref = 0.f; + Refxyz[i].Zref = 0.f; + } + + if (settings->verbose) { + if (settings->itcwb_stdobserver10 == false) { + printf("Use standard observer 2°\n"); + } else { + printf("Use standard observer 10°\n"); + } + } + + if (settings->itcwb_stdobserver10 == false) { + for (int i = 0; i < 97; i++) { + cie_colour_match_jd[i][0] = cie_colour_match_jd2[i][0]; + cie_colour_match_jd[i][1] = cie_colour_match_jd2[i][1];; + cie_colour_match_jd[i][2] = cie_colour_match_jd2[i][2]; + } + } + + if (separated) { + const double tempw = Txyz[repref].Tem; + + if (tempw <= INITIALBLACKBODY) { + for (int i = 0; i < N_c; i++) { + spectrum_to_color_xyz_blackbody(spec_colorforxcyc[i], tempw, TX[i], TY[i], TZ[i]); + } + } else { + double m11, m22, x_DD, y_DD, interm2; + + if (tempw <= 7000) { + x_DD = -4.6070e9 / (tempw * tempw * tempw) + 2.9678e6 / (tempw * tempw) + 0.09911e3 / tempw + 0.244063; + } else { + x_DD = -2.0064e9 / (tempw * tempw * tempw) + 1.9018e6 / (tempw * tempw) + 0.24748e3 / tempw + 0.237040; + } + + y_DD = -3.0 * x_DD * x_DD + 2.87 * x_DD - 0.275; + //calculate D -daylight in function of s0, s1, s2 and temp ==> x_D y_D + //S(lamda)=So(lambda)+m1*s1(lambda)+m2*s2(lambda) + interm2 = (0.0241 + 0.2562 * x_DD - 0.734 * y_DD); + m11 = (-1.3515 - 1.7703 * x_DD + 5.9114 * y_DD) / interm2; + m22 = (0.03 - 31.4424 * x_DD + 30.0717 * y_DD) / interm2; + + for (int i = 0; i < N_c; i++) { + spectrum_to_color_xyz_daylight(spec_colorforxcyc[i], m11, m22, TX[i], TY[i], TZ[i]); + } + } + } else { + for (int tt = 0; tt < N_t; tt++) { + const double tempw = Txyz[tt].Tem; + + if (tempw <= INITIALBLACKBODY) { + for (int i = 0; i < N_c; i++) { + spectrum_to_color_xyz_blackbody(spec_colorforxcyc[i], tempw, Refxyz[i].Xref, Refxyz[i].Yref, Refxyz[i].Zref); + } + } else { + double x_DD; + + if (tempw <= 7000) { + x_DD = -4.6070e9 / (tempw * tempw * tempw) + 2.9678e6 / (tempw * tempw) + 0.09911e3 / tempw + 0.244063; + } else { + x_DD = -2.0064e9 / (tempw * tempw * tempw) + 1.9018e6 / (tempw * tempw) + 0.24748e3 / tempw + 0.237040; + } + + const double y_DD = -3.0 * x_DD * x_DD + 2.87 * x_DD - 0.275; + //calculate D -daylight in function of s0, s1, s2 and temp ==> x_D y_D + //S(lamda)=So(lambda)+m1*s1(lambda)+m2*s2(lambda) + const double interm2 = (0.0241 + 0.2562 * x_DD - 0.734 * y_DD); + const double m11 = (-1.3515 - 1.7703 * x_DD + 5.9114 * y_DD) / interm2; + const double m22 = (0.03 - 31.4424 * x_DD + 30.0717 * y_DD) / interm2; + + for (int i = 0; i < N_c; i++) { + spectrum_to_color_xyz_daylight(spec_colorforxcyc[i], m11, m22, Refxyz[i].Xref, Refxyz[i].Yref, Refxyz[i].Zref); + } + } + + for (int i = 0; i < N_c; i++) { + Tx[i][tt] = Refxyz[i].Xref; + Ty[i][tt] = Refxyz[i].Yref; + Tz[i][tt] = Refxyz[i].Zref; + } + } + } +} + } diff --git a/rtengine/colortemp.h b/rtengine/colortemp.h index a38e01072..89c324490 100644 --- a/rtengine/colortemp.h +++ b/rtengine/colortemp.h @@ -21,6 +21,7 @@ #include #include #include +#include "procparams.h" namespace rtengine { @@ -53,6 +54,7 @@ public: explicit ColorTemp (double e) : temp(-1.), green(-1.), equal (e), method("Custom") {} ColorTemp (double t, double g, double e, const std::string &m); ColorTemp (double mulr, double mulg, double mulb, double e); + static void tempxy(bool separated, int repref, float **Tx, float **Ty, float **Tz, float **Ta, float **Tb, float **TL, double *TX, double *TY, double *TZ, const procparams::WBParams & wbpar); void update (const double rmul, const double gmul, const double bmul, const double equal, const double tempBias=0.0) { @@ -95,6 +97,8 @@ public: static void temp2mulxyz (double tem, const std::string &method, double &Xxyz, double &Zxyz); static void cieCAT02(double Xw, double Yw, double Zw, double &CAM02BB00, double &CAM02BB01, double &CAM02BB02, double &CAM02BB10, double &CAM02BB11, double &CAM02BB12, double &CAM02BB20, double &CAM02BB21, double &CAM02BB22, double adap ); + static void cieCAT02float(float Xw, float Yw, float Zw, float &CAM02BB00, float &CAM02BB01, float &CAM02BB02, float &CAM02BB10, float &CAM02BB11, float &CAM02BB12, float &CAM02BB20, float &CAM02BB21, float &CAM02BB22, float adap); + static void icieCAT02float(float Xw, float Yw, float Zw, float &iCAM02BB00, float &iCAM02BB01, float &iCAM02BB02, float &iCAM02BB10, float &iCAM02BB11, float &iCAM02BB12, float &iCAM02BB20, float &iCAM02BB21, float &iCAM02BB22, float adap); bool operator== (const ColorTemp& other) const { @@ -162,6 +166,125 @@ public: static const double ColorchechGreD1_spect[97]; static const double ColorchechSGBlaN3_6_spect[97];//ColorChecker SG N3 static const double JDC468_GraK14_44_spect[97];//468 K14 + static const double JDC468_BluM5_spect[97]; //468 M5 + static const double JDC468_BluD6_spect[97]; //468 D6 + static const double JDC468_BluF4_spect[97]; //468 F4 + static const double JDC468_RedG21va_spect[97]; //468 G21 modifié + static const double JDC468_RedI9_spect[97]; //468 I9 + static const double JDC468_GreI8_spect[97]; //468 I8 + static const double JDC468_GreQ7_spect[97]; //468 Q7 + static const double ColorGreenM25_spect[97]; + static const double ColorYellowkeltano_spect[97]; + static const double ColorGreenalsi_spect[97]; + static const double ColorRedpetunia_spect[97]; + static const double ColorRedkurttu_spect[97]; + static const double ColorRedlupiini_spect[97]; + static const double ColorRedhevosminttu_spect[97]; + static const double ColorRedneilikka_spect[97]; + static const double ColorRedpelagornia_spect[97]; + static const double ColorRedtalvio_spect[97]; + static const double ColorBrownpoimulehti_spect[97]; + static const double ColorOrangetuntematon_spect[97]; + static const double ColorOrangetlehmus_spect[97]; + static const double ColorOrangvaahtera_spect[97]; + static const double ColorBrownlehmus_spect[97]; + static const double ColorBrownuotiosammal_spect[97]; + static const double ColorBlacksoil_spect[97]; + static const double ColorGraynahjajaekaelae_spect[97]; + static const double ColorGreennuotisammal_spect[97]; + static const double ColorGreenleskenlehti_spect[97]; + static const double ColorGreenlinnunkaali_spect[97]; + static const double ColorGreenpelto_spect[97]; + static const double ColorGreenrodvoikukka[97]; + static const double ColorGreenlehmus[97]; + static const double ColorGreenlinden[97]; + static const double ColorYellowlehmus[97]; + static const double ColorYellowsuikeroalpi[97]; + static const double ColorYellowpensashanhikki1[97]; + static const double ColorYellowpensashanhikki2[97]; + static const double ColorBluehiidenvirna[97]; + static const double ColorBluekurkkuyrtti[97]; + static const double ColorPinksiankaersaemoe[97]; + static const double ColorVioletharakankello[97]; + static const double ColorVioletalsikeapila[97]; + static const double ColorVioletakilleija[97]; + static const double ColorOrangekehaekukka[97]; + static const double ColorRedpihlaja[97]; + static const double ColorVioletpetunia[97]; + static const double ColorVioletorvokki[97]; + static const double ColorBluesinisievikki[97]; + static const double ColorBlueiisoppi[97]; + static const double ColorBluelobelia[97]; + static const double ColorWhiteojaka[97]; + static const double ColorWhitepetunia[97]; + static const double ColorWhitepelargonia[97]; + static const double ColorWhitepaeivaen[97]; + static const double JDC468_B14_75Redspect[97]; + static const double Colorblue_spect[97]; + static const double ColorGreenkoriste[97]; + static const double ColorGreenpoimulehti[97]; + static const double ColorGreenhopeapaju[97]; + static const double ColorReduuden[97]; + static const double ColorRedpajuan[97]; + static const double ColorRedjaloan[97]; + static const double ColorBlueukon[97]; + static const double ColorBlueorvokki[97]; + static const double ColorBluemalvikki[97]; + static const double ColorBlackmaito[97]; + static const double ColorOrangpihlaja[97]; + static const double ColorBlackpihlaja[97]; + static const double ColorViolA1_spect[97]; + static const double ColorViolA4_spect[97]; + static const double ColorViolA6_spect[97]; + static const double ColorBlueSkyK3_spect[97]; + static const double ColorBlueSkyK9_spect[97]; + static const double ColorBlueSkyC4_spect[97]; + static const double ColorBlueSkyC14_spect[97]; + static const double ColorBlueSkyE4_spect[97]; + static const double ColorBlueSkyM1_spect[97]; + static const double ColorBlueSky2B1_spect[97]; + static const double ColorBlueSkyT7_spect[97]; + static const double ColorBlueSkyU19_spect[97]; + static const double ColorBlueSkyU2_spect[97]; + static const double ColorBlueSkyT17_spect[97]; + static const double ColorBlackM8_spect[97]; + static const double ColorBlackM12_spect[97]; + static const double ColorBlackM13_spect[97]; + static const double ColorWhite2B12_spect[97]; + static const double ColorWhite2B14_spect[97]; + static const double JDC468_Blackred97_spect[97]; + static const double JDC468_Blackredbl443_spect[97]; + static const double JDC468_Blackbl27_spect[97]; + static const double JDC468_Blackbl28_spect[97]; + static const double JDC468_Blackgr214_spect[97]; + static const double JDC468_Blackbl436_spect[97]; + static const double JDC468_Whitebl455_spect[97]; + static const double JDC468_Blackvio101_spect[97]; + static const double JDC468_Whitebl92_spect[97]; + static const double JDC468_Greyredbl94_spect[97]; + static const double JDC468_Blue32_spect[97]; + static const double JDC468_Blue236_spect[97]; + static const double JDC468_Gre300_spect[97]; + static const double JDC468_Blue340_spect[97]; + static const double JDC468_Gree110_spect[97]; + static const double JDC468_Gree457_spect[97]; + static const double JDC468_Yel241_spect[97]; + static const double JDC468_Ora321_spect[97]; + static const double JDC468_Yellow353_spect[97]; + static const double JDC468_Mag465_spect[97]; + static const double JDC468_Mag333_spect[97]; + static const double JDC468_Mag203_spect[97]; + + + static const double JDC468_OraO18_spect[97]; //468 O18 + static const double JDC468_OraD17_spect[97]; //468 D17 + static const double Fictif_61greyspect[97];//468 K15 + static const double JDC468_K15_87greyspect[97]; + static const double JDC468_YelN10_spect[97]; //468 N10 + static const double JDC468_GreN7_spect[97]; //468 N7 + static const double JDC468_GreA10_spect[97]; //468 A10 + static const double JDC468_GreK7_spect[97]; //468 K7 + static const double JDC468_PurE24_spect[97]; //468 E24 static const double JDC468_BluH10_spect[97];//468 H10 static const double ColabSkin35_15_17_spect[97];//Skin L 35 static const double ColabSkin57_22_18_spect[97];//Skin L 57 @@ -195,7 +318,63 @@ public: static const double ColabSkin70_7_32_spect[97];//Skin L 77 static const double ColabSky60_0_m31_spect[97];//Sky L=60 static const double ColabSky42_0_m24_spect[97];//Sky L=42 - + static const double J570_BlueB6_spect[97];//blue Cyan + static const double J570_BlueB15_spect[97];//blue Cyan + static const double J570_BlueC2_spect[97];//blue Cyan + static const double J570_BlueC14_spect[97];//blue Cyan + static const double J570_BlueC16_spect[97];//blue Cyan + static const double J570_BlueF1_spect[97];//blue Cyan + static const double J570_BlueF2_spect[97];//blue Cyan + static const double J570_BlueF10_spect[97];//blue Cyan + static const double J570_BlueF13_spect[97];//blue Cyan + static const double J570_BlueG9_spect[97];//blue Cyan + static const double J570_BlueG19_spect[97];//blue Cyan + static const double J570_BlueI5_spect[97];//blue Cyan + static const double J570_BlueH15_spect[97];//blue Cyan + static const double J570_BlueI3_spect[97];//blue Cyan + static const double J570_BlueI19_spect[97];//blue Cyan + static const double J570_BlueJ4_spect[97];//blue Cyan + static const double J570_BlueJ6_spect[97];//blue Cyan + static const double J570_BlueJ11_spect[97];//blue Cyan + static const double J570_BlueJ13_spect[97];//blue Cyan + static const double J570_BlueK5_spect[97];//blue Cyan + static const double J570_BlueN1_spect[97];//blue Cyan + static const double J570_BlueN4_spect[97];//blue Cyan + static const double J570_BlueO19_spect[97];//blue Cyan + static const double J570_BlueU8_spect[97];//blue Cyan + static const double J570_NeuN8_spect[97];//neutral + static const double J570_NeuN9_spect[97];//neutral + static const double J570_NeuO8_spect[97];//neutral + static const double J570_NeuO11_spect[97];//neutral + static const double J570_NeuD5_spect[97];//neutral + static const double J570_NeuE11_spect[97];//neutral + static const double J570_NeuK16_spect[97];//neutral + static const double J570_NeuM3_spect[97];//neutral + static const double J570_NeuN18_spect[97];//neutral + static const double J570_NeuQ1_spect[97];//neutral + static const double J570_NeuS7_spect[97];//neutral + static const double J570_NeuV10_spect[97];//neutral + static const double J570_NeuW18_spect[97];//neutral + static const double J570_NeuZ14_spect[97];//neutral + static const double J570_NeuC18_spect[97];//neutral + static const double J570_NeuD17_spect[97];//neutral + static const double J570_NeuJ11_spect[97];//neutral + static const double J570_NeuL4_spect[97];//neutral + static const double Colorlab_n72_n2_spect[97]; + static const double Colorlab_10_n70_spect[97]; + static const double Colorlab_n33_n70_spect[97]; + static const double Colorlab_n8_n74_spect[97]; + static const double Colorlab_19_n69_spect[97]; + static const double Colorlab_n80_10_spect[97]; + static const double Colorlab_n80_26_spect[97]; + static const double Colorlab_n80_5_9_5_9spect[97]; +// static const double Colorlab_n57_5_6_9spect[97]; + + /* + static const double JDC468_greyc14_66_spect[97]; + static const double JDC468_greym13_325_spect[97]; + static const double JDC468_greyf26_156_spect[97]; + */ static void spectrum_to_xyz_daylight (double _m1, double _m2, double &x, double &y, double &z); static void spectrum_to_xyz_blackbody (double _temp, double &x, double &y, double &z); static void spectrum_to_xyz_preset (const double* spec_intens, double &x, double &y, double &z); diff --git a/rtengine/cplx_wavelet_filter_coeffs.h b/rtengine/cplx_wavelet_filter_coeffs.h index 6287fc03b..5d191e50c 100644 --- a/rtengine/cplx_wavelet_filter_coeffs.h +++ b/rtengine/cplx_wavelet_filter_coeffs.h @@ -48,7 +48,11 @@ const float Daub4_anal16[2][16] ALIGNED16 = {//Daub 14 {0.f, 0.f, 0.055049715f, 0.28039564f, 0.515574245f, 0.33218624f, -0.10175691f, -0.158417505f, 0.05042335f, 0.057001725f, -0.026891225f, -0.01171997f, 0.008874895f, 0.0003037575f, -0.0012739524f, 0.0002501134f}, { -0.0002501134f, -0.0012739524f, -0.0003037575f, 0.008874895f, 0.01171997f , -0.026891225f, -0.057001725f, 0.05042335f, 0.158417505f, -0.10175691f, -0.33218624f, 0.515574245f, -0.28039564f, 0.055049715f, 0.f, 0.f} }; - -// if necessary ?? we can add D20 !! +/* +const double Daub4_anal22[2][22] ALIGNED16 = {//Daub 20 + {0., 0., 0.01885858, 0.13306109, 0.37278754, 0.48681406, 0.19881887, -0.1766681, -0.13855494, 0.09006372, 0.0658015, -0.05048328, -0.02082962, 0.0234849, 0.0025502185, -0.0075895, 0.0009866625, 0.0014088433, -0.00048497392, -0.0000823545, 0.00006617718, -0.000009379205}, + {0.000009379205, -0.00006617718, 0.0000823545, 0.00048497392, -0.0014088433, -0.0009866627, 0.0075895, -0.0025502185, -0.0234849, 0.02082962, 0.05048328, -0.0658015, -0.09006372, 0.13855494, 0.1766681, -0.19881887, -0.48681406, -0.37278754, -0.13306109, -0.01885858, 0., 0.} +}; +*/ } diff --git a/rtengine/curves.cc b/rtengine/curves.cc index b2105a091..14711c730 100644 --- a/rtengine/curves.cc +++ b/rtengine/curves.cc @@ -21,8 +21,7 @@ #include #include #include -#include -#include +#include #include "rt_math.h" @@ -33,6 +32,7 @@ #include "opthelper.h" #include "ciecam02.h" #include "color.h" +#include "iccmatrices.h" #include "iccstore.h" using namespace std; @@ -1209,6 +1209,41 @@ void WavCurve::Set(const std::vector &curvePoints) } } +Wavblcurve::Wavblcurve() {} + +void Wavblcurve::Reset() +{ + lutblcurve.reset(); +} + +void Wavblcurve::Set(const Curve &pCurve) +{ + if (pCurve.isIdentity()) { + Reset(); // raise this value if the quality suffers from this number of samples + return; + } + + lutblcurve(501); // raise this value if the quality suffers from this number of samples + + for (int i = 0; i < 501; i++) { + lutblcurve[i] = pCurve.getVal(double(i) / 500.); + } +} + +void Wavblcurve::Set(const std::vector &curvePoints) +{ + if (!curvePoints.empty() && curvePoints[0] > FCT_Linear && curvePoints[0] < FCT_Unchanged) { + FlatCurve tcurve(curvePoints, false, CURVES_MIN_POLY_POINTS / 2); + tcurve.setIdentityValue(0.); + Set(tcurve); + } else { + Reset(); + } + +} + + + WavOpacityCurveRG::WavOpacityCurveRG() {} @@ -2186,7 +2221,7 @@ void PerceptualToneCurve::init() } } -void PerceptualToneCurve::initApplyState(PerceptualToneCurveState & state, Glib::ustring workingSpace) const +void PerceptualToneCurve::initApplyState(PerceptualToneCurveState & state, const Glib::ustring &workingSpace) const { // Get the curve's contrast value, and convert to a chroma scaling diff --git a/rtengine/curves.h b/rtengine/curves.h index bc8193b76..03fa3e812 100644 --- a/rtengine/curves.h +++ b/rtengine/curves.h @@ -22,21 +22,23 @@ #include #include -#include - #include "rt_math.h" #include "flatcurvetypes.h" #include "diagonalcurvetypes.h" -#include "pipettebuffer.h" #include "noncopyable.h" #include "LUT.h" #include "sleef.h" #define CURVES_MIN_POLY_POINTS 1000 -#include "rt_math.h" - #define CLIPI(a) ((a)>0?((a)<65534?(a):65534):0) +namespace Glib +{ + +class ustring; + +} + using namespace std; namespace rtengine @@ -292,11 +294,11 @@ public: } static inline float gamma2 (float x) { - return x <= 0.00304 ? x * 12.92310 : 1.055 * expf(logf(x) / sRGBGammaCurve) - 0.055; + return x <= 0.00304f ? x * 12.92310f : 1.055f * expf(logf(x) / static_cast(sRGBGammaCurve)) - 0.055f; } static inline float igamma2 (float x) { - return x <= 0.03928 ? x / 12.92310 : expf(logf((x + 0.055) / 1.055) * sRGBGammaCurve); + return x <= 0.03928f ? x / 12.92310f : expf(logf((x + 0.055f) / 1.055f) * static_cast(sRGBGammaCurve)); } // gamma function with adjustable parameters static inline double gamma (double x, double gamma, double start, double slope, double mul, double add) @@ -327,8 +329,8 @@ public: #endif static inline float hlcurve (const float exp_scale, const float comp, const float hlrange, float level) { - if (comp > 0.0) { - float val = level + (hlrange - 65536.0); + if (comp > 0.f) { + float val = level + (hlrange - 65536.f); if(val == 0.0f) { // to avoid division by zero val = 0.000001f; @@ -337,7 +339,7 @@ public: float Y = val * exp_scale / hlrange; Y *= comp; - if(Y <= -1.0) { // to avoid log(<=0) + if(Y <= -1.f) { // to avoid log(<=0) Y = -.999999f; } @@ -454,7 +456,7 @@ public: virtual bool isIdentity () const = 0; }; -class DiagonalCurve : public Curve +class DiagonalCurve final : public Curve { protected: @@ -476,7 +478,7 @@ public: }; }; -class FlatCurve : public Curve, public rtengine::NonCopyable +class FlatCurve final : public Curve, public rtengine::NonCopyable { private: @@ -625,6 +627,30 @@ public: } }; +class Wavblcurve +{ +private: + LUTf lutblcurve; // 0xffff range + void Set(const Curve &pCurve); +public: + virtual ~Wavblcurve() {}; + Wavblcurve(); + + void Reset(); + // void Set(const std::vector &curvePoints, bool &opautili); + void Set(const std::vector &curvePoints); + float operator[](float index) const + { + return lutblcurve[index]; + } + + operator bool (void) const + { + return lutblcurve; + } +}; + + class WavOpacityCurveRG { private: @@ -940,7 +966,7 @@ private: float calculateToneCurveContrastValue() const; public: static void init(); - void initApplyState(PerceptualToneCurveState & state, Glib::ustring workingSpace) const; + void initApplyState(PerceptualToneCurveState & state, const Glib::ustring& workingSpace) const; void BatchApply(const size_t start, const size_t end, float *r, float *g, float *b, const PerceptualToneCurveState &state) const; }; diff --git a/rtengine/dcp.cc b/rtengine/dcp.cc index 11fe306b8..89256bba4 100644 --- a/rtengine/dcp.cc +++ b/rtengine/dcp.cc @@ -1064,9 +1064,11 @@ void DCPProfile::apply( for (int i = 0; i < 3; ++i) { for (int j = 0; j < 3; ++j) { + double temp = 0.0; for (int k = 0; k < 3; ++k) { - mat[i][j] += work_matrix[i][k] * xyz_cam[k][j]; + temp += work_matrix[i][k] * xyz_cam[k][j]; } + mat[i][j] = temp; } } @@ -1092,9 +1094,11 @@ void DCPProfile::apply( for (int i = 0; i < 3; ++i) { for (int j = 0; j < 3; ++j) { + double temp = 0.0; for (int k = 0; k < 3; ++k) { - pro_photo[i][j] += prophoto_xyz[i][k] * xyz_cam[k][j]; + temp += prophoto_xyz[i][k] * xyz_cam[k][j]; } + pro_photo[i][j] = temp; } } @@ -1102,9 +1106,11 @@ void DCPProfile::apply( for (int i = 0; i < 3; ++i) { for (int j = 0; j < 3; ++j) { + double temp = 0.0; for (int k = 0; k < 3; ++k) { - work[i][j] += work_matrix[i][k] * xyz_prophoto[k][j]; + temp += work_matrix[i][k] * xyz_prophoto[k][j]; } + work[i][j] = temp; } } @@ -1173,27 +1179,35 @@ void DCPProfile::setStep2ApplyState(const Glib::ustring& working_space, bool use mWork = ICCStore::getInstance()->workingSpaceMatrix (working_space); memset(as_out.data->pro_photo, 0, sizeof(as_out.data->pro_photo)); - for (int i = 0; i < 3; i++) - for (int j = 0; j < 3; j++) + for (int i = 0; i < 3; i++) { + for (int j = 0; j < 3; j++) { + double temp = 0.0; for (int k = 0; k < 3; k++) { - as_out.data->pro_photo[i][j] += prophoto_xyz[i][k] * mWork[k][j]; + temp += prophoto_xyz[i][k] * mWork[k][j]; } + as_out.data->pro_photo[i][j] = temp; + } + } mWork = ICCStore::getInstance()->workingSpaceInverseMatrix (working_space); memset(as_out.data->work, 0, sizeof(as_out.data->work)); - for (int i = 0; i < 3; i++) - for (int j = 0; j < 3; j++) + for (int i = 0; i < 3; i++) { + for (int j = 0; j < 3; j++) { + double temp = 0.0; for (int k = 0; k < 3; k++) { - as_out.data->work[i][j] += mWork[i][k] * xyz_prophoto[k][j]; + temp += mWork[i][k] * xyz_prophoto[k][j]; } + as_out.data->work[i][j] = temp; + } + } } } void DCPProfile::step2ApplyTile(float* rc, float* gc, float* bc, int width, int height, int tile_width, const DCPProfileApplyState& as_in) const { -#define FCLIP(a) ((a)>0.0?((a)<65535.5?(a):65535.5):0.0) +#define FCLIP(a) ((a)>0.f?((a)<65535.5f?(a):65535.5f):0.f) #define CLIP01(a) ((a)>0?((a)<1?(a):1):0) float exp_scale = as_in.data->bl_scale; diff --git a/rtengine/dcraw.cc b/rtengine/dcraw.cc index 812f122b3..edb7dc317 100644 --- a/rtengine/dcraw.cc +++ b/rtengine/dcraw.cc @@ -62,12 +62,8 @@ $Date: 2018/06/01 20:36:25 $ */ -#define DCRAW_VERSION "9.28" +//#define DCRAW_VERSION "9.28" -#ifndef _GNU_SOURCE -#define _GNU_SOURCE -#endif -#define _USE_MATH_DEFINES #include #include #include @@ -94,9 +90,12 @@ #ifdef WIN32 #include #include -#define snprintf _snprintf +#ifndef strcasecmp #define strcasecmp stricmp +#endif +#ifndef strncasecmp #define strncasecmp strnicmp +#endif typedef __int64 INT64; typedef unsigned __int64 UINT64; #else @@ -158,7 +157,6 @@ const float d65_white[3] = { 0.950456, 1, 1.088754 }; #define MIN(a,b) rtengine::min(a,static_cast<__typeof__(a)>(b)) #define MAX(a,b) rtengine::max(a,static_cast<__typeof__(a)>(b)) #define LIM(x,min,max) rtengine::LIM(x,static_cast<__typeof__(x)>(min),static_cast<__typeof__(x)>(max)) -#define ULIM(x,y,z) rtengine::median(x,static_cast<__typeof__(x)>(y),static_cast<__typeof__(x)>(z)) #define CLIP(x) rtengine::CLIP(x) #define SWAP(a,b) { a=a+b; b=a-b; a=a-b; } @@ -6900,7 +6898,7 @@ it under the terms of the one of two licenses as you choose: break; case 50778: case 50779: - if( get2() == 21 ) + if( get2() != 17 ) // 17 is Standard light A cm_D65 = (tag-50778); break; case 50829: /* ActiveArea */ @@ -9098,6 +9096,8 @@ void CLASS adobe_coeff (const char *make, const char *model) if (load_raw == &CLASS sony_arw2_load_raw) { // RT: arw2 scale fix black <<= 2; tiff_bps += 2; + } else if (load_raw == &CLASS panasonic_load_raw) { + tiff_bps = RT_pana_info.bpp; } { /* Check for RawTherapee table overrides and extensions */ int black_level, white_level; @@ -9868,6 +9868,7 @@ void CLASS identify() filters = 0; tiff_samples = colors = 3; load_raw = &CLASS canon_sraw_load_raw; + FORC4 cblack[c] = 0; // ALB } else if (!strcmp(model,"PowerShot 600")) { height = 613; width = 854; @@ -10047,6 +10048,9 @@ canon_a5: } else if (!strncmp(model, "X-A3", 4) || !strncmp(model, "X-A5", 4)) { width = raw_width = 6016; height = raw_height = 4014; + } else if (!strcmp(model, "X-Pro3") || !strcmp(model, "X-T3") || !strcmp(model, "X-T30")) { + width = raw_width = 6384; + height = raw_height = 4182; } top_margin = (raw_height - height) >> 2 << 1; left_margin = (raw_width - width ) >> 2 << 1; @@ -11021,7 +11025,6 @@ void CLASS nikon_14bit_load_raw() /*RT*/#undef MIN /*RT*/#undef ABS /*RT*/#undef LIM -/*RT*/#undef ULIM /*RT*/#undef CLIP #ifdef __GNUC__ #pragma GCC diagnostic pop diff --git a/rtengine/dcrop.cc b/rtengine/dcrop.cc index 890003ee0..11bf19edf 100644 --- a/rtengine/dcrop.cc +++ b/rtengine/dcrop.cc @@ -24,13 +24,15 @@ #include "dcrop.h" #include "image8.h" #include "imagefloat.h" +#include "improccoordinator.h" #include "labimage.h" #include "mytime.h" #include "procparams.h" #include "refreshmap.h" #include "rt_math.h" - +#include "color.h" #include "../rtgui/editcallbacks.h" +#include "guidedfilter.h" namespace { @@ -49,7 +51,7 @@ namespace rtengine Crop::Crop(ImProcCoordinator* parent, EditDataProvider *editDataProvider, bool isDetailWindow) : PipetteBuffer(editDataProvider), origCrop(nullptr), laboCrop(nullptr), labnCrop(nullptr), - cropImg (nullptr), transCrop (nullptr), cieCrop (nullptr), + cropImg(nullptr), transCrop(nullptr), cieCrop(nullptr), updating(false), newUpdatePending(false), skip(10), cropx(0), cropy(0), cropw(-1), croph(-1), trafx(0), trafy(0), trafw(-1), trafh(-1), @@ -814,6 +816,7 @@ void Crop::update(int todo) parent->ipf.workingtrc(workingCrop, workingCrop, cw, ch, 5, params.icm.workingProfile, params.icm.workingTRCGamma, params.icm.workingTRCSlope, parent->getCustomTransformOut(), false, true, true); } } + double rrm, ggm, bbm; DCPProfileApplyState as; DCPProfile *dcpProf = parent->imgsrc->getDCP(params.icm, as); @@ -823,6 +826,7 @@ void Crop::update(int todo) params.toneCurve.saturation, parent->rCurve, parent->gCurve, parent->bCurve, parent->colourToningSatLimit, parent->colourToningSatLimitOpacity, parent->ctColorCurve, parent->ctOpacityCurve, parent->opautili, parent->clToningcurve, parent->cl2Toningcurve, parent->customToneCurve1, parent->customToneCurve2, parent->beforeToneCurveBW, parent->afterToneCurveBW, rrm, ggm, bbm, parent->bwAutoR, parent->bwAutoG, parent->bwAutoB, dcpProf, as, histToneCurve); + if (workingCrop != baseCrop) { delete workingCrop; } @@ -879,8 +883,8 @@ void Crop::update(int todo) parent->ipf.MLsharpen(labnCrop); if ((params.colorappearance.enabled && !settings->autocielab) || (!params.colorappearance.enabled)) { - parent->ipf.MLmicrocontrast (labnCrop); - parent->ipf.sharpening (labnCrop, params.sharpening, parent->sharpMask); + parent->ipf.MLmicrocontrast(labnCrop); + parent->ipf.sharpening(labnCrop, params.sharpening, parent->sharpMask); } } @@ -963,22 +967,183 @@ void Crop::update(int todo) } WavCurve wavCLVCurve; + Wavblcurve wavblcurve; WavOpacityCurveRG waOpacityCurveRG; WavOpacityCurveBY waOpacityCurveBY; WavOpacityCurveW waOpacityCurveW; WavOpacityCurveWL waOpacityCurveWL; LUTf wavclCurve; - params.wavelet.getCurves(wavCLVCurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL); + params.wavelet.getCurves(wavCLVCurve, wavblcurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL); + LabImage *unshar = nullptr; + Glib::ustring provis; + LabImage *provradius = nullptr; + bool procont = WaveParams.expcontrast; + bool prochro = WaveParams.expchroma; + bool proedge = WaveParams.expedge; + bool profin = WaveParams.expfinal; + bool proton = WaveParams.exptoning; + bool pronois = WaveParams.expnoise; + + if(WaveParams.showmask) { + // WaveParams.showmask = false; + // WaveParams.expclari = true; + } + + + if (WaveParams.softrad > 0.f) { + provradius = new LabImage(labnCrop->W, labnCrop->H); + provradius->CopyFrom(labnCrop); + } + + + + if ((WaveParams.ushamethod == "sharp" || WaveParams.ushamethod == "clari") && WaveParams.expclari && WaveParams.CLmethod != "all") { + + unshar = new LabImage(labnCrop->W, labnCrop->H); + provis = params.wavelet.CLmethod; + params.wavelet.CLmethod = "all"; + parent->ipf.ip_wavelet(labnCrop, labnCrop, kall, WaveParams, wavCLVCurve, wavblcurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL, parent->wavclCurve, skip); + unshar->CopyFrom(labnCrop); + + params.wavelet.CLmethod = provis; + + WaveParams.expcontrast = false; + WaveParams.expchroma = false; + WaveParams.expedge = false; + WaveParams.expfinal = false; + WaveParams.exptoning = false; + WaveParams.expnoise = false; + } + + parent->ipf.ip_wavelet(labnCrop, labnCrop, kall, WaveParams, wavCLVCurve, wavblcurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL, parent->wavclCurve, skip); + + if ((WaveParams.ushamethod == "sharp" || WaveParams.ushamethod == "clari") && WaveParams.expclari && WaveParams.CLmethod != "all") { + WaveParams.expcontrast = procont; + WaveParams.expchroma = prochro; + WaveParams.expedge = proedge; + WaveParams.expfinal = profin; + WaveParams.exptoning = proton; + WaveParams.expnoise = pronois; + if (WaveParams.softrad > 0.f) { + array2D ble(labnCrop->W, labnCrop->H); + array2D guid(labnCrop->W, labnCrop->H); + Imagefloat *tmpImage = nullptr; + tmpImage = new Imagefloat(labnCrop->W, labnCrop->H); + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < labnCrop->H ; ir++) + for (int jr = 0; jr < labnCrop->W; jr++) { + float X, Y, Z; + float L = provradius->L[ir][jr]; + float a = provradius->a[ir][jr]; + float b = provradius->b[ir][jr]; + Color::Lab2XYZ(L, a, b, X, Y, Z); + + guid[ir][jr] = Y / 32768.f; + float La = labnCrop->L[ir][jr]; + float aa = labnCrop->a[ir][jr]; + float ba = labnCrop->b[ir][jr]; + Color::Lab2XYZ(La, aa, ba, X, Y, Z); + tmpImage->r(ir, jr) = X; + tmpImage->g(ir, jr) = Y; + tmpImage->b(ir, jr) = Z; + ble[ir][jr] = Y / 32768.f; + } + double epsilmax = 0.0001; + double epsilmin = 0.00001; + double aepsil = (epsilmax - epsilmin) / 90.f; + double bepsil = epsilmax - 100.f * aepsil; + double epsil = aepsil * WaveParams.softrad + bepsil; + + float blur = 10.f / skip * (0.0001f + 0.8f * WaveParams.softrad); + rtengine::guidedFilter(guid, ble, ble, blur, epsil, false); + + + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < labnCrop->H; ir++) + for (int jr = 0; jr < labnCrop->W; jr++) { + float X = tmpImage->r(ir, jr); + float Y = 32768.f * ble[ir][jr]; + float Z = tmpImage->b(ir, jr); + float L, a, b; + Color::XYZ2Lab(X, Y, Z, L, a, b); + labnCrop->L[ir][jr] = L; + } + delete tmpImage; + } + + } + + + if ((WaveParams.ushamethod == "sharp" || WaveParams.ushamethod == "clari") && WaveParams.expclari && WaveParams.CLmethod != "all") { + + float mL = (float)(WaveParams.mergeL / 100.f); + float mC = (float)(WaveParams.mergeC / 100.f); + float mL0; + float mC0; + float background = 0.f; + int show = 0; + + if ((WaveParams.CLmethod == "one" || WaveParams.CLmethod == "inf") && WaveParams.Backmethod == "black") { + mL0 = mC0 = 0.f; + mL = -1.5f * mL; + mC = -mC; + background = 12000.f; + show = 0; + } else if (WaveParams.CLmethod == "sup" && WaveParams.Backmethod == "resid") { + mL0 = mL; + mC0 = mC; + background = 0.f; + show = 0; + } else { + mL0 = mL = mC0 = mC = 0.f; + background = 0.f; + show = 0; + } + + float indic = 1.f; + if(WaveParams.showmask){ + mL0 = mC0 = -1.f; + indic = -1.f; + mL = fabs(mL); + mC = fabs(mC); + show = 1; + } + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int x = 0; x < labnCrop->H; x++) + for (int y = 0; y < labnCrop->W; y++) { + labnCrop->L[x][y] = LIM((1.f + mL0) * (unshar->L[x][y]) + show * background - mL * indic * labnCrop->L[x][y], 0.f, 32768.f); + labnCrop->a[x][y] = (1.f + mC0) * (unshar->a[x][y]) - mC * indic * labnCrop->a[x][y]; + labnCrop->b[x][y] = (1.f + mC0) * (unshar->b[x][y]) - mC * indic * labnCrop->b[x][y]; + } + + delete unshar; + unshar = NULL; + if (WaveParams.softrad > 0.f) { + delete provradius; + provradius = NULL; + } + + + } + - parent->ipf.ip_wavelet(labnCrop, labnCrop, kall, WaveParams, wavCLVCurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL, parent->wavclCurve, skip); } parent->ipf.softLight(labnCrop); - // } - - // } if (params.colorappearance.enabled) { float fnum = parent->imgsrc->getMetaData()->getFNumber(); // F number float fiso = parent->imgsrc->getMetaData()->getISOSpeed() ; // ISO diff --git a/rtengine/dcrop.h b/rtengine/dcrop.h index c65c1e72f..0b33854c5 100644 --- a/rtengine/dcrop.h +++ b/rtengine/dcrop.h @@ -18,11 +18,7 @@ */ #pragma once -#include "improccoordinator.h" #include "rtengine.h" -#include "improcfun.h" -#include "imagesource.h" -#include "procevents.h" #include "pipettebuffer.h" #include "../rtgui/threadutils.h" @@ -30,12 +26,13 @@ namespace rtengine { class Image8; +class CieImage; using namespace procparams; class ImProcCoordinator; -class Crop : public DetailedCrop, public PipetteBuffer +class Crop final : public DetailedCrop, public PipetteBuffer { protected: diff --git a/rtengine/demosaic_algos.cc b/rtengine/demosaic_algos.cc index 538858a9a..a31415968 100644 --- a/rtengine/demosaic_algos.cc +++ b/rtengine/demosaic_algos.cc @@ -1069,7 +1069,7 @@ void RawImageSource::dcb_hid(float (*image)[3], int x0, int y0) for (int col = colMin + (FC(y0 - TILEBORDER + row, x0 - TILEBORDER + colMin) & 1), indx = row * CACHESIZE + col; col < colMax; col += 2, indx += 2) { assert(indx - u - 1 >= 0 && indx + u + 1 < u * u); - image[indx][1] = 0.25*(image[indx-1][1]+image[indx+1][1]+image[indx-u][1]+image[indx+u][1]); + image[indx][1] = 0.25f * (image[indx-1][1]+image[indx+1][1]+image[indx-u][1]+image[indx+u][1]); } } diff --git a/rtengine/dfmanager.cc b/rtengine/dfmanager.cc index 1fb1d2e1b..6961a4b54 100644 --- a/rtengine/dfmanager.cc +++ b/rtengine/dfmanager.cc @@ -476,7 +476,7 @@ dfInfo* DFManager::find( const std::string &mak, const std::string &mod, int iso } } - return bestD != INFINITY ? &(bestMatch->second) : nullptr ; + return bestD != RT_INFINITY ? &(bestMatch->second) : nullptr ; } } diff --git a/rtengine/dfmanager.h b/rtengine/dfmanager.h index 216dcfc53..b23981ffb 100644 --- a/rtengine/dfmanager.h +++ b/rtengine/dfmanager.h @@ -31,7 +31,7 @@ namespace rtengine { class RawImage; -class dfInfo +class dfInfo final { public: @@ -74,7 +74,7 @@ protected: void updateRawImage(); }; -class DFManager +class DFManager final { public: void init(const Glib::ustring &pathname); diff --git a/rtengine/diagonalcurves.cc b/rtengine/diagonalcurves.cc index bb20b7cc1..622683ea2 100644 --- a/rtengine/diagonalcurves.cc +++ b/rtengine/diagonalcurves.cc @@ -16,8 +16,6 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . */ -#include -#include #include "curves.h" #include #include @@ -65,23 +63,23 @@ DiagonalCurve::DiagonalCurve (const std::vector& p, int poly_pn) } } - if (x[0] != 0.0f || x[N - 1] != 1.0f) + if (x[0] != 0.0 || x[N - 1] != 1.0) // Special (and very rare) case where all points are on the identity line but // not reaching the limits { identity = false; } - if(x[0] == 0.f && x[1] == 0.f) + if(x[0] == 0.0 && x[1] == 0.0) // Avoid crash when first two points are at x = 0 (git Issue 2888) { - x[1] = 0.01f; + x[1] = 0.01; } - if(x[0] == 1.f && x[1] == 1.f) + if(x[0] == 1.0 && x[1] == 1.0) // Avoid crash when first two points are at x = 1 (100 in gui) (git Issue 2923) { - x[0] = 0.99f; + x[0] = 0.99; } if (!identity) { @@ -97,7 +95,7 @@ DiagonalCurve::DiagonalCurve (const std::vector& p, int poly_pn) } } } else if (kind == DCT_Parametric) { - if ((p.size() == 8 || p.size() == 9) && (p.at(4) != 0.0f || p.at(5) != 0.0f || p.at(6) != 0.0f || p.at(7) != 0.0f)) { + if ((p.size() == 8 || p.size() == 9) && (p.at(4) != 0.0 || p.at(5) != 0.0 || p.at(6) != 0.0 || p.at(7) != 0.0)) { identity = false; x = new double[9]; diff --git a/rtengine/dirpyr_equalizer.cc b/rtengine/dirpyr_equalizer.cc index 1f62badcb..0624f4443 100644 --- a/rtengine/dirpyr_equalizer.cc +++ b/rtengine/dirpyr_equalizer.cc @@ -228,11 +228,11 @@ void fillLut(LUTf &irangefn, int level, double dirpyrThreshold, float mult, floa } const float offs = skinprot == 0.f ? 0.f : -1.f; - constexpr float noise = 2000.f; - const float noisehi = 1.33f * noise * dirpyrThreshold / expf(level * log(3.0)), noiselo = 0.66f * noise * dirpyrThreshold / expf(level * log(3.0)); + constexpr double noise = 2000.0; + const float noisehi = 1.33 * noise * dirpyrThreshold / exp(level * log(3.0)), noiselo = 0.66 * noise * dirpyrThreshold / exp(level * log(3.0)); for (int i = 0; i < 0x20000; i++) { - if (abs(i - 0x10000) > noisehi || multbis < 1.0) { + if (abs(i - 0x10000) > noisehi || multbis < 1.f) { irangefn[i] = multbis + offs; } else { if (abs(i - 0x10000) < noiselo) { @@ -262,7 +262,7 @@ void idirpyr_eq_channel(const float * const * data_coarse, const float * const * buffer[i][j] += irangefn[hipass + 0x10000] * hipass; } } - } else if (skinprot > 0.f) { + } else if (skinprot > 0.0) { #ifdef _OPENMP #pragma omp parallel for schedule(dynamic,16) #endif @@ -314,7 +314,7 @@ void idirpyr_eq_channelcam(const float * const * data_coarse, const float * cons buffer[i][j] += irangefn[hipass + 0x10000] * hipass; } } - } else if (skinprot > 0.f) { + } else if (skinprot > 0.0) { #ifdef _OPENMP #pragma omp parallel for schedule(dynamic,16) #endif diff --git a/rtengine/dual_demosaic_RT.cc b/rtengine/dual_demosaic_RT.cc index 93508808c..253468a76 100644 --- a/rtengine/dual_demosaic_RT.cc +++ b/rtengine/dual_demosaic_RT.cc @@ -45,7 +45,7 @@ void RawImageSource::dual_demosaic_RT(bool isBayer, const procparams::RAWParams { BENCHFUN - if (contrast == 0.f && !autoContrast) { + if (contrast == 0.0 && !autoContrast) { // contrast == 0.0 means only first demosaicer will be used if(isBayer) { if (raw.bayersensor.method == procparams::RAWParams::BayerSensor::getMethodString(procparams::RAWParams::BayerSensor::Method::AMAZEVNG4) ) { @@ -103,7 +103,7 @@ void RawImageSource::dual_demosaic_RT(bool isBayer, const procparams::RAWParams } // calculate contrast based blend factors to use vng4 in regions with low contrast JaggedArray blend(winw, winh); - float contrastf = contrast / 100.f; + float contrastf = contrast / 100.0; buildBlendMask(L, blend, winw, winh, contrastf, autoContrast); contrast = contrastf * 100.f; diff --git a/rtengine/eahd_demosaic.cc b/rtengine/eahd_demosaic.cc index ad4bda3cd..009be0714 100644 --- a/rtengine/eahd_demosaic.cc +++ b/rtengine/eahd_demosaic.cc @@ -360,8 +360,8 @@ void RawImageSource::eahd_demosaic () int wh = 0; - for (int dmi = 0; dmi < 9; dmi++) { - wh += (dLmaph[dmi] <= eL) * (dCamaph[dmi] <= eCa) * (dCbmaph[dmi] <= eCb); + for (int d = 0; d < 9; ++d) { + wh += (dLmaph[d] <= eL) * (dCamaph[d] <= eCa) * (dCbmaph[d] <= eCb); } homh[imx][j - 1] += wh; @@ -376,8 +376,8 @@ void RawImageSource::eahd_demosaic () int wv = 0; - for (int dmi = 0; dmi < 9; dmi++) { - wv += (dLmapv[dmi] <= eL) * (dCamapv[dmi] <= eCa) * (dCbmapv[dmi] <= eCb); + for (int d = 0; d < 9; ++d) { + wv += (dLmapv[d] <= eL) * (dCamapv[d] <= eCa) * (dCbmapv[d] <= eCb); } homv[imx][j - 1] += wv; diff --git a/rtengine/ffmanager.cc b/rtengine/ffmanager.cc index ce60277e1..c55bc5108 100644 --- a/rtengine/ffmanager.cc +++ b/rtengine/ffmanager.cc @@ -428,7 +428,7 @@ ffInfo* FFManager::find( const std::string &mak, const std::string &mod, const s } } - return bestD != INFINITY ? &(bestMatch->second) : nullptr ; + return bestD != RT_INFINITY ? &(bestMatch->second) : nullptr ; } } diff --git a/rtengine/ffmanager.h b/rtengine/ffmanager.h index 80ef5fa1c..f3303f12b 100644 --- a/rtengine/ffmanager.h +++ b/rtengine/ffmanager.h @@ -29,7 +29,7 @@ namespace rtengine { class RawImage; -class ffInfo +class ffInfo final { public: @@ -71,7 +71,7 @@ protected: void updateRawImage(); }; -class FFManager +class FFManager final { public: void init(const Glib::ustring &pathname); diff --git a/rtengine/filmnegativeproc.cc b/rtengine/filmnegativeproc.cc index 1f27983ed..6d4fe1ad6 100644 --- a/rtengine/filmnegativeproc.cc +++ b/rtengine/filmnegativeproc.cc @@ -35,6 +35,9 @@ namespace { +using rtengine::ST_BAYER; +using rtengine::ST_FUJI_XTRANS; +using rtengine::settings; bool channelsAvg( const rtengine::RawImage* ri, @@ -43,17 +46,16 @@ bool channelsAvg( const float* cblacksom, rtengine::Coord spotPos, int spotSize, - const rtengine::procparams::FilmNegativeParams& params, std::array& avgs ) { avgs = {}; // Channel averages - if (ri->getSensorType() != rtengine::ST_BAYER && ri->getSensorType() != rtengine::ST_FUJI_XTRANS) { + if (ri->getSensorType() != ST_BAYER && ri->getSensorType() != ST_FUJI_XTRANS) { return false; } - if (rtengine::settings->verbose) { + if (settings->verbose) { printf("Spot coord: x=%d y=%d\n", spotPos.x, spotPos.y); } @@ -69,9 +71,10 @@ bool channelsAvg( } std::array pxCount = {}; // Per-channel sample counts + for (int c = x1; c < x2; ++c) { for (int r = y1; r < y2; ++r) { - const int ch = ri->getSensorType() == rtengine::ST_BAYER ? ri->FC(r,c) : ri->XTRANSFC(r,c); + const int ch = ri->getSensorType() == ST_BAYER ? ri->FC(r, c) : ri->XTRANSFC(r, c); ++pxCount[ch]; @@ -88,6 +91,112 @@ bool channelsAvg( return true; } +void calcMedians( + const rtengine::RawImage* ri, + float** data, + int x1, int y1, int x2, int y2, + std::array& meds +) +{ + + MyTime t1, t2, t3; + t1.set(); + + // Channel vectors to calculate medians + std::array, 3> cvs; + + // Sample one every 5 pixels, and push the value in the appropriate channel vector. + // Choose an odd step, not a multiple of the CFA size, to get a chance to visit each channel. + if (ri->getSensorType() == ST_BAYER) { + for (int row = y1; row < y2; row += 5) { + const int c0 = ri->FC(row, x1 + 0); + const int c1 = ri->FC(row, x1 + 5); + int col = x1; + + for (; col < x2 - 5; col += 10) { + cvs[c0].push_back(data[row][col]); + cvs[c1].push_back(data[row][col + 5]); + } + + if (col < x2) { + cvs[c0].push_back(data[row][col]); + } + } + } else if (ri->getSensorType() == ST_FUJI_XTRANS) { + for (int row = y1; row < y2; row += 5) { + const std::array cs = { + ri->XTRANSFC(row, x1 + 0), + ri->XTRANSFC(row, x1 + 5), + ri->XTRANSFC(row, x1 + 10), + ri->XTRANSFC(row, x1 + 15), + ri->XTRANSFC(row, x1 + 20), + ri->XTRANSFC(row, x1 + 25) + }; + int col = x1; + + for (; col < x2 - 25; col += 30) { + for (int c = 0; c < 6; ++c) { + cvs[cs[c]].push_back(data[row][col + c * 5]); + } + } + + for (int c = 0; col < x2; col += 5, ++c) { + cvs[cs[c]].push_back(data[row][col]); + } + } + } + + t2.set(); + + if (settings->verbose) { + printf("Median vector fill loop time us: %d\n", t2.etime(t1)); + } + + t2.set(); + + for (int c = 0; c < 3; ++c) { + // Find median values for each channel + if (!cvs[c].empty()) { + rtengine::findMinMaxPercentile(cvs[c].data(), cvs[c].size(), 0.5f, meds[c], 0.5f, meds[c], true); + } + } + + t3.set(); + + if (settings->verbose) { + printf("Sample count: R=%zu, G=%zu, B=%zu\n", cvs[0].size(), cvs[1].size(), cvs[2].size()); + printf("Median calc time us: %d\n", t3.etime(t2)); + } + +} + +std::array calcWBMults( + const rtengine::ColorTemp& wb, + const rtengine::ImageMatrices& imatrices, + const rtengine::RawImage *ri, + const float ref_pre_mul[4]) +{ + std::array wb_mul; + double r, g, b; + wb.getMultipliers(r, g, b); + wb_mul[0] = imatrices.cam_rgb[0][0] * r + imatrices.cam_rgb[0][1] * g + imatrices.cam_rgb[0][2] * b; + wb_mul[1] = imatrices.cam_rgb[1][0] * r + imatrices.cam_rgb[1][1] * g + imatrices.cam_rgb[1][2] * b; + wb_mul[2] = imatrices.cam_rgb[2][0] * r + imatrices.cam_rgb[2][1] * g + imatrices.cam_rgb[2][2] * b; + + for (int c = 0; c < 3; ++c) { + wb_mul[c] = ri->get_pre_mul(c) / wb_mul[c] / ref_pre_mul[c]; + } + + // Normalize max channel gain to 1.0 + float mg = rtengine::max(wb_mul[0], wb_mul[1], wb_mul[2]); + + for (int c = 0; c < 3; ++c) { + wb_mul[c] /= mg; + } + + return wb_mul; +} + } bool rtengine::RawImageSource::getFilmNegativeExponents(Coord2D spotA, Coord2D spotB, int tran, const procparams::FilmNegativeParams ¤tParams, std::array& newExps) @@ -104,26 +213,34 @@ bool rtengine::RawImageSource::getFilmNegativeExponents(Coord2D spotA, Coord2D s std::array clearVals; std::array denseVals; + // Get channel averages in the two spots, sampling from the original ri->data buffer. + // NOTE: rawData values might be affected by CA corection, FlatField, etc, so: + // rawData[y][x] == (ri->data[y][x] - cblacksom[c]) * scale_mul[c] + // is not always true. To calculate exponents on the exact values, we should keep + // a copy of the rawData buffer after preprocessing. Worth the memory waste? + // Sample first spot transformPosition(spotA.x, spotA.y, tran, spot.x, spot.y); - if (!channelsAvg(ri, W, H, cblacksom, spot, spotSize, currentParams, clearVals)) { + + if (!channelsAvg(ri, W, H, cblacksom, spot, spotSize, clearVals)) { return false; } // Sample second spot transformPosition(spotB.x, spotB.y, tran, spot.x, spot.y); - if (!channelsAvg(ri, W, H, cblacksom, spot, spotSize, currentParams, denseVals)) { + + if (!channelsAvg(ri, W, H, cblacksom, spot, spotSize, denseVals)) { return false; } // Detect which one is the dense spot, based on green channel if (clearVals[1] < denseVals[1]) { - std::swap(clearVals, denseVals); + std::swap(clearVals, denseVals); } if (settings->verbose) { - printf("Clear film values: R=%g G=%g B=%g\n", clearVals[0], clearVals[1], clearVals[2]); - printf("Dense film values: R=%g G=%g B=%g\n", denseVals[0], denseVals[1], denseVals[2]); + printf("Clear film values: R=%g G=%g B=%g\n", static_cast(clearVals[0]), static_cast(clearVals[1]), static_cast(clearVals[2])); + printf("Dense film values: R=%g G=%g B=%g\n", static_cast(denseVals[0]), static_cast(denseVals[1]), static_cast(denseVals[2])); } const float denseGreenRatio = clearVals[1] / denseVals[1]; @@ -141,18 +258,43 @@ bool rtengine::RawImageSource::getFilmNegativeExponents(Coord2D spotA, Coord2D s if (ch == 1) { newExps[ch] = 1.f; // Green is the reference channel } else { - newExps[ch] = CLAMP(logBase(clearVals[ch] / denseVals[ch], denseGreenRatio), 0.3f, 4.f); + newExps[ch] = rtengine::LIM(logBase(clearVals[ch] / denseVals[ch], denseGreenRatio), 0.3f, 4.f); } } if (settings->verbose) { - printf("New exponents: R=%g G=%g B=%g\n", newExps[0], newExps[1], newExps[2]); + printf("New exponents: R=%g G=%g B=%g\n", static_cast(newExps[0]), static_cast(newExps[1]), static_cast(newExps[2])); } return true; } -void rtengine::RawImageSource::filmNegativeProcess(const procparams::FilmNegativeParams ¶ms) +bool rtengine::RawImageSource::getRawSpotValues(Coord2D spotCoord, int spotSize, int tran, const procparams::FilmNegativeParams ¶ms, std::array& rawValues) +{ + Coord spot; + transformPosition(spotCoord.x, spotCoord.y, tran, spot.x, spot.y); + + if (settings->verbose) { + printf("Transformed coords: %d,%d\n", spot.x, spot.y); + } + + if (spotSize < 4) { + return false; + } + + // Calculate averages of raw unscaled channels + if (!channelsAvg(ri, W, H, cblacksom, spot, spotSize, rawValues)) { + return false; + } + + if (settings->verbose) { + printf("Raw spot values: R=%g, G=%g, B=%g\n", rawValues[0], rawValues[1], rawValues[2]); + } + + return true; +} + +void rtengine::RawImageSource::filmNegativeProcess(const procparams::FilmNegativeParams ¶ms, std::array& filmBaseValues) { // BENCHFUNMICRO @@ -168,92 +310,114 @@ void rtengine::RawImageSource::filmNegativeProcess(const procparams::FilmNegativ static_cast(-params.blueRatio * params.greenExp) }; - MyTime t1, t2, t3,t4, t5; - - t1.set(); - - // Channel vectors to calculate medians - std::array, 3> cvs; - - // Sample one every 5 pixels, and push the value in the appropriate channel vector. - // Choose an odd step, not a multiple of the CFA size, to get a chance to visit each channel. - if (ri->getSensorType() == ST_BAYER) { - for (int row = 0; row < H; row += 5) { - const int c0 = ri->FC(row, 0); - const int c1 = ri->FC(row, 5); - int col = 0; - for (; col < W - 5; col += 10) { - cvs[c0].push_back(rawData[row][col]); - cvs[c1].push_back(rawData[row][col + 5]); - } - if (col < W) { - cvs[c0].push_back(rawData[row][col]); - } - } - } - else if (ri->getSensorType() == ST_FUJI_XTRANS) { - for (int row = 0; row < H; row += 5) { - const std::array cs = { - ri->XTRANSFC(row, 0), - ri->XTRANSFC(row, 5), - ri->XTRANSFC(row, 10), - ri->XTRANSFC(row, 15), - ri->XTRANSFC(row, 20), - ri->XTRANSFC(row, 25) - }; - int col = 0; - for (; col < W - 25; col += 30) { - for (int c = 0; c < 6; ++c) { - cvs[cs[c]].push_back(rawData[row][col + c * 5]); - } - } - for (int c = 0; col < W; col += 5, ++c) { - cvs[cs[c]].push_back(rawData[row][col]); - } - } - } - constexpr float MAX_OUT_VALUE = 65000.f; - t2.set(); + // Get multipliers for a known, fixed WB setting, that will be the starting point + // for balancing the converted image. + const std::array wb_mul = calcWBMults( + ColorTemp(3500., 1., 1., "Custom"), imatrices, ri, ref_pre_mul); - if (settings->verbose) { - printf("Median vector fill loop time us: %d\n", t2.etime(t1)); + + if (rtengine::settings->verbose) { + printf("Fixed WB mults: %g %g %g\n", wb_mul[0], wb_mul[1], wb_mul[2]); } - t2.set(); + // Compensation factor to restore the non-autoWB initialGain (see RawImageSource::load) + const float autoGainComp = camInitialGain / initialGain; - std::array medians; // Channel median values - std::array mults = { - 1.f, - 1.f, - 1.f - }; // Channel normalization multipliers + std::array mults; // Channel normalization multipliers + + // If film base values are set in params, use those + if (filmBaseValues[0] <= 0.f) { + // ...otherwise, the film negative tool might have just been enabled on this image, + // whithout any previous setting. So, estimate film base values from channel medians + + std::array medians; + + // Special value for backwards compatibility with profiles saved by RT 5.7 + const bool oldChannelScaling = filmBaseValues[0] == -1.f; + + // If using the old channel scaling method, get medians from the whole current image, + // reading values from the already-scaled rawData buffer. + if (oldChannelScaling) { + calcMedians(ri, rawData, 0, 0, W, H, medians); + } else { + // Cut 20% border from medians calculation. It will probably contain outlier values + // from the film holder, which will bias the median result. + const int bW = W * 20 / 100; + const int bH = H * 20 / 100; + calcMedians(ri, rawData, bW, bH, W - bW, H - bH, medians); + } + + // Un-scale rawData medians + for (int c = 0; c < 3; ++c) { + medians[c] /= scale_mul[c]; + } + + if (settings->verbose) { + printf("Channel medians: R=%g, G=%g, B=%g\n", medians[0], medians[1], medians[2]); + } + + for (int c = 0; c < 3; ++c) { + + // Estimate film base values, so that in the output data, each channel + // median will correspond to 1/24th of MAX. + filmBaseValues[c] = pow_F(24.f / 512.f, 1.f / exps[c]) * medians[c]; + + if (oldChannelScaling) { + // If using the old channel scaling method, apply WB multipliers here to undo their + // effect later, since fixed wb compensation was not used in previous version. + // Also, undo the effect of the autoGainComp factor (see below). + filmBaseValues[c] /= pow_F((wb_mul[c] / autoGainComp), 1.f / exps[c]);// / autoGainComp; + } - for (int c = 0; c < 3; ++c) { - // Find median values for each channel - if (!cvs[c].empty()) { - findMinMaxPercentile(cvs[c].data(), cvs[c].size(), 0.5f, medians[c], 0.5f, medians[c], true); - medians[c] = pow_F(rtengine::max(medians[c], 1.f), exps[c]); - // Determine the channel multiplier so that N times the median becomes 65k. This clips away - // the values in the dark border surrounding the negative (due to the film holder, for example), - // the reciprocal of which have blown up to stellar values. - mults[c] = MAX_OUT_VALUE / (medians[c] * 24.f); } } - t3.set(); + + // Calculate multipliers based on previously obtained film base input values. + + // Apply current scaling coefficients to raw, unscaled base values. + std::array fb = { + filmBaseValues[0] * scale_mul[0], + filmBaseValues[1] * scale_mul[1], + filmBaseValues[2] * scale_mul[2] + }; if (settings->verbose) { - printf("Sample count: %zu, %zu, %zu\n", cvs[0].size(), cvs[1].size(), cvs[2].size()); - printf("Medians: %g %g %g\n", medians[0], medians[1], medians[2] ); - printf("Computed multipliers: %g %g %g\n", mults[0], mults[1], mults[2] ); - printf("Median calc time us: %d\n", t3.etime(t2)); + printf("Input film base values: %g %g %g\n", fb[0], fb[1], fb[2]); } + for (int c = 0; c < 3; ++c) { + // Apply channel exponents, to obtain the corresponding base values in the output data + fb[c] = pow_F(rtengine::max(fb[c], 1.f), exps[c]); + + // Determine the channel multiplier so that the film base value is 1/512th of max. + mults[c] = (MAX_OUT_VALUE / 512.f) / fb[c]; + + // Un-apply the fixed WB multipliers, to reverse their effect later in the WB tool. + // This way, the output image will be adapted to this fixed WB setting + mults[c] /= wb_mul[c]; + + // Also compensate for the initialGain difference between the default scaling (forceAutoWB=true) + // and the non-autoWB scaling (see camInitialGain). + // This effectively restores camera scaling multipliers, and gives us stable multipliers + // (not depending on image content). + mults[c] *= autoGainComp; + + } + + if (settings->verbose) { + printf("Output film base values: %g %g %g\n", static_cast(fb[0]), static_cast(fb[1]), static_cast(fb[2])); + printf("Computed multipliers: %g %g %g\n", static_cast(mults[0]), static_cast(mults[1]), static_cast(mults[2])); + } + + constexpr float CLIP_VAL = 65535.f; - t3.set(); + MyTime t1, t2, t3; + + t1.set(); if (ri->getSensorType() == ST_BAYER) { #ifdef __SSE2__ @@ -264,6 +428,7 @@ void rtengine::RawImageSource::filmNegativeProcess(const procparams::FilmNegativ #ifdef _OPENMP #pragma omp parallel for schedule(dynamic, 16) #endif + for (int row = 0; row < H; ++row) { int col = 0; // Avoid trouble with zeroes, minimum pixel value is 1. @@ -274,14 +439,18 @@ void rtengine::RawImageSource::filmNegativeProcess(const procparams::FilmNegativ #ifdef __SSE2__ const vfloat expsv = _mm_setr_ps(exps0, exps1, exps0, exps1); const vfloat multsv = _mm_setr_ps(mult0, mult1, mult0, mult1); + for (; col < W - 3; col += 4) { STVFU(rawData[row][col], vminf(multsv * pow_F(vmaxf(LVFU(rawData[row][col]), onev), expsv), clipv)); } + #endif // __SSE2__ + for (; col < W - 1; col += 2) { rawData[row][col] = rtengine::min(mult0 * pow_F(rtengine::max(rawData[row][col], 1.f), exps0), CLIP_VAL); rawData[row][col + 1] = rtengine::min(mult1 * pow_F(rtengine::max(rawData[row][col + 1], 1.f), exps1), CLIP_VAL); } + if (col < W) { rawData[row][col] = rtengine::min(mult0 * pow_F(rtengine::max(rawData[row][col], 1.f), exps0), CLIP_VAL); } @@ -295,6 +464,7 @@ void rtengine::RawImageSource::filmNegativeProcess(const procparams::FilmNegativ #ifdef _OPENMP #pragma omp parallel for schedule(dynamic, 16) #endif + for (int row = 0; row < H; row ++) { int col = 0; // Avoid trouble with zeroes, minimum pixel value is 1. @@ -321,30 +491,34 @@ void rtengine::RawImageSource::filmNegativeProcess(const procparams::FilmNegativ const vfloat multsv0 = _mm_setr_ps(multsc[0], multsc[1], multsc[2], multsc[3]); const vfloat multsv1 = _mm_setr_ps(multsc[4], multsc[5], multsc[0], multsc[1]); const vfloat multsv2 = _mm_setr_ps(multsc[2], multsc[3], multsc[4], multsc[5]); + for (; col < W - 11; col += 12) { STVFU(rawData[row][col], vminf(multsv0 * pow_F(vmaxf(LVFU(rawData[row][col]), onev), expsv0), clipv)); STVFU(rawData[row][col + 4], vminf(multsv1 * pow_F(vmaxf(LVFU(rawData[row][col + 4]), onev), expsv1), clipv)); STVFU(rawData[row][col + 8], vminf(multsv2 * pow_F(vmaxf(LVFU(rawData[row][col + 8]), onev), expsv2), clipv)); } + #endif // __SSE2__ + for (; col < W - 5; col += 6) { for (int c = 0; c < 6; ++c) { rawData[row][col + c] = rtengine::min(multsc[c] * pow_F(rtengine::max(rawData[row][col + c], 1.f), expsc[c]), CLIP_VAL); } } + for (int c = 0; col < W; col++, c++) { rawData[row][col + c] = rtengine::min(multsc[c] * pow_F(rtengine::max(rawData[row][col + c], 1.f), expsc[c]), CLIP_VAL); } } } - t4.set(); + t2.set(); if (settings->verbose) { - printf("Pow loop time us: %d\n", t4.etime(t3)); + printf("Pow loop time us: %d\n", t2.etime(t1)); } - t4.set(); + t2.set(); PixelsMap bitmapBads(W, H); @@ -354,6 +528,7 @@ void rtengine::RawImageSource::filmNegativeProcess(const procparams::FilmNegativ #ifdef _OPENMP #pragma omp parallel for reduction(+:totBP) schedule(dynamic,16) #endif + for (int i = 0; i < H; ++i) { for (int j = 0; j < W; ++j) { if (rawData[i][j] >= MAX_OUT_VALUE) { @@ -367,11 +542,11 @@ void rtengine::RawImageSource::filmNegativeProcess(const procparams::FilmNegativ interpolateBadPixelsBayer(bitmapBads, rawData); } - } - else if (ri->getSensorType() == ST_FUJI_XTRANS) { + } else if (ri->getSensorType() == ST_FUJI_XTRANS) { #ifdef _OPENMP #pragma omp parallel for reduction(+:totBP) schedule(dynamic,16) #endif + for (int i = 0; i < H; ++i) { for (int j = 0; j < W; ++j) { if (rawData[i][j] >= MAX_OUT_VALUE) { @@ -386,10 +561,10 @@ void rtengine::RawImageSource::filmNegativeProcess(const procparams::FilmNegativ } } - t5.set(); + t3.set(); if (settings->verbose) { printf("Bad pixels count: %d\n", totBP); - printf("Bad pixels interpolation time us: %d\n", t5.etime(t4)); + printf("Bad pixels interpolation time us: %d\n", t3.etime(t2)); } } diff --git a/rtengine/filmnegativethumb.cc b/rtengine/filmnegativethumb.cc index b31432a55..57f2601f9 100644 --- a/rtengine/filmnegativethumb.cc +++ b/rtengine/filmnegativethumb.cc @@ -18,6 +18,7 @@ */ #include +#include "colortemp.h" #include "LUT.h" #include "rtengine.h" #include "rtthumbnail.h" @@ -29,70 +30,179 @@ #define BENCHMARK #include "StopWatch.h" +namespace +{ + +using rtengine::Imagefloat; +using rtengine::findMinMaxPercentile; + + +void calcMedians( + const Imagefloat* baseImg, + const int x1, const int y1, + const int x2, const int y2, + float &rmed, float &gmed, float &bmed +) +{ + // Channel vectors to calculate medians + std::vector rv, gv, bv; + + const int sz = std::max(0, (y2 - y1) * (x2 - x1)); + rv.reserve(sz); + gv.reserve(sz); + bv.reserve(sz); + + for (int i = y1; i < y2; i++) { + for (int j = x1; j < x2; j++) { + rv.push_back(baseImg->r(i, j)); + gv.push_back(baseImg->g(i, j)); + bv.push_back(baseImg->b(i, j)); + } + } + + // Calculate channel medians from whole image + findMinMaxPercentile(rv.data(), rv.size(), 0.5f, rmed, 0.5f, rmed, true); + findMinMaxPercentile(gv.data(), gv.size(), 0.5f, gmed, 0.5f, gmed, true); + findMinMaxPercentile(bv.data(), bv.size(), 0.5f, bmed, 0.5f, bmed, true); +} + +} + void rtengine::Thumbnail::processFilmNegative( const procparams::ProcParams ¶ms, const Imagefloat* baseImg, - const int rwidth, const int rheight, - float &rmi, float &gmi, float &bmi -) { + const int rwidth, const int rheight +) +{ // Channel exponents const float rexp = -params.filmNegative.redRatio * params.filmNegative.greenExp; const float gexp = -params.filmNegative.greenExp; const float bexp = -params.filmNegative.blueRatio * params.filmNegative.greenExp; - // Need to calculate channel averages, to fake the same conditions - // found in rawimagesource, where get_ColorsCoeff is called with - // forceAutoWB=true. - float rsum = 0.f, gsum = 0.f, bsum = 0.f; - - // Channel vectors to calculate medians - std::vector rv, gv, bv; - - for (int i = 0; i < rheight; i++) { - for (int j = 0; j < rwidth; j++) { - const float r = baseImg->r(i, j); - const float g = baseImg->g(i, j); - const float b = baseImg->b(i, j); - - rsum += r; - gsum += g; - bsum += b; - - rv.push_back(r); - gv.push_back(g); - bv.push_back(b); - } - } - - const float ravg = rsum / (rheight*rwidth); - const float gavg = gsum / (rheight*rwidth); - const float bavg = bsum / (rheight*rwidth); - - // Shifting current WB multipliers, based on channel averages. - rmi /= (gavg/ravg); - // gmi /= (gAvg/gAvg); green chosen as reference channel - bmi /= (gavg/bavg); - - float rmed, gmed, bmed; - findMinMaxPercentile(rv.data(), rv.size(), 0.5f, rmed, 0.5f, rmed, true); - findMinMaxPercentile(gv.data(), gv.size(), 0.5f, gmed, 0.5f, gmed, true); - findMinMaxPercentile(bv.data(), bv.size(), 0.5f, bmed, 0.5f, bmed, true); - - rmed = powf(rmed, rexp); - gmed = powf(gmed, gexp); - bmed = powf(bmed, bexp); + // Calculate output multipliers + float rmult, gmult, bmult; const float MAX_OUT_VALUE = 65000.f; - const float rmult = (MAX_OUT_VALUE / (rmed * 24)) ; - const float gmult = (MAX_OUT_VALUE / (gmed * 24)) ; - const float bmult = (MAX_OUT_VALUE / (bmed * 24)) ; + + // For backwards compatibility with profiles saved by RT 5.7 + const bool oldChannelScaling = params.filmNegative.redBase == -1.f; + + // If the film base values are not set in params, estimate multipliers from each channel's median value. + if (params.filmNegative.redBase <= 0.f) { + + // Channel medians + float rmed, gmed, bmed; + + if (oldChannelScaling) { + // If using the old method, calculate nedians on the whole image + calcMedians(baseImg, 0, 0, rwidth, rheight, rmed, gmed, bmed); + } else { + // The new method cuts out a 20% border from medians calculation. + const int bW = rwidth * 20 / 100; + const int bH = rheight * 20 / 100; + calcMedians(baseImg, bW, bH, rwidth - bW, rheight - bH, rmed, gmed, bmed); + } + + if (settings->verbose) { + printf("Thumbnail input channel medians: %g %g %g\n", rmed, gmed, bmed); + } + + // Calculate output medians + rmed = powf(rmed, rexp); + gmed = powf(gmed, gexp); + bmed = powf(bmed, bexp); + + // Calculate output multipliers so that the median value is 1/24 of the output range. + rmult = (MAX_OUT_VALUE / 24.f) / rmed; + gmult = (MAX_OUT_VALUE / 24.f) / gmed; + bmult = (MAX_OUT_VALUE / 24.f) / bmed; + + } else { + + // Read film-base values from params + float rbase = params.filmNegative.redBase; + float gbase = params.filmNegative.greenBase; + float bbase = params.filmNegative.blueBase; + + // Reconstruct scale_mul coefficients from thumbnail metadata: + // redMultiplier / camwbRed is pre_mul[0] + // pre_mul[0] * scaleGain is scale_mul[0] + // Apply channel scaling to raw (unscaled) input base values, to + // match with actual (scaled) data in baseImg + rbase *= (redMultiplier / camwbRed) * scaleGain; + gbase *= (greenMultiplier / camwbGreen) * scaleGain; + bbase *= (blueMultiplier / camwbBlue) * scaleGain; + + if (settings->verbose) { + printf("Thumbnail input film base values: %g %g %g\n", rbase, gbase, bbase); + } + + // Apply exponents to get output film base values + rbase = powf(rbase, rexp); + gbase = powf(gbase, gexp); + bbase = powf(bbase, bexp); + + if (settings->verbose) { + printf("Thumbnail output film base values: %g %g %g\n", rbase, gbase, bbase); + } + + // Calculate multipliers so that film base value is 1/512th of the output range. + rmult = (MAX_OUT_VALUE / 512.f) / rbase; + gmult = (MAX_OUT_VALUE / 512.f) / gbase; + bmult = (MAX_OUT_VALUE / 512.f) / bbase; + + } + + + if (oldChannelScaling) { + // Need to calculate channel averages, to fake the same conditions + // found in rawimagesource, where get_ColorsCoeff is called with + // forceAutoWB=true. + float rsum = 0.f, gsum = 0.f, bsum = 0.f; + + for (int i = 0; i < rheight; i++) { + for (int j = 0; j < rwidth; j++) { + rsum += baseImg->r(i, j); + gsum += baseImg->g(i, j); + bsum += baseImg->b(i, j); + } + } + + const float ravg = rsum / (rheight * rwidth); + const float gavg = gsum / (rheight * rwidth); + const float bavg = bsum / (rheight * rwidth); + + // Shifting current WB multipliers, based on channel averages. + rmult /= gavg / ravg; + // gmult /= gAvg / gAvg; green chosen as reference channel + bmult /= gavg / bavg; + + } else { + + // Get and un-apply multipliers to adapt the thumbnail to a known fixed WB setting, + // as in the main image processing. + + double r, g, b; + ColorTemp(3500., 1., 1., "Custom").getMultipliers(r, g, b); + //iColorMatrix is cam_rgb + const double rm = camwbRed / (iColorMatrix[0][0] * r + iColorMatrix[0][1] * g + iColorMatrix[0][2] * b); + const double gm = camwbGreen / (iColorMatrix[1][0] * r + iColorMatrix[1][1] * g + iColorMatrix[1][2] * b); + const double bm = camwbBlue / (iColorMatrix[2][0] * r + iColorMatrix[2][1] * g + iColorMatrix[2][2] * b); + + // Normalize max WB multiplier to 1.f + const double m = max(rm, gm, bm); + rmult /= rm / m; + gmult /= gm / m; + bmult /= bm / m; + } + if (settings->verbose) { - printf("Thumbnail channel medians: %g %g %g\n", rmed, gmed, bmed); - printf("Thumbnail computed multipliers: %g %g %g\n", rmult, gmult, bmult); + printf("Thumbnail computed multipliers: %g %g %g\n", static_cast(rmult), static_cast(gmult), static_cast(bmult)); } + #ifdef __SSE2__ const vfloat clipv = F2V(MAXVALF); const vfloat rexpv = F2V(rexp); @@ -109,12 +219,15 @@ void rtengine::Thumbnail::processFilmNegative( float *bline = baseImg->b(i); int j = 0; #ifdef __SSE2__ - for (; j < rwidth - 3; j +=4) { + + for (; j < rwidth - 3; j += 4) { STVFU(rline[j], vminf(rmultv * pow_F(LVFU(rline[j]), rexpv), clipv)); STVFU(gline[j], vminf(gmultv * pow_F(LVFU(gline[j]), gexpv), clipv)); STVFU(bline[j], vminf(bmultv * pow_F(LVFU(bline[j]), bexpv), clipv)); } + #endif + for (; j < rwidth; ++j) { rline[j] = CLIP(rmult * pow_F(rline[j], rexp)); gline[j] = CLIP(gmult * pow_F(gline[j], gexp)); diff --git a/rtengine/green_equil_RT.cc b/rtengine/green_equil_RT.cc index fc4f18548..a66bca160 100644 --- a/rtengine/green_equil_RT.cc +++ b/rtengine/green_equil_RT.cc @@ -47,7 +47,7 @@ void RawImageSource::green_equilibrate_global(array2D &rawData) for (int i = border; i < H - border; i++) { double avgg = 0.; for (int j = border + ((FC(i, border) & 1) ^ 1); j < W - border; j += 2) { - avgg += rawData[i][j]; + avgg += static_cast(rawData[i][j]); } int ng = (W - 2 * border + (FC(i, border) & 1)) / 2; @@ -71,15 +71,15 @@ void RawImageSource::green_equilibrate_global(array2D &rawData) avgg2 = 1.0; } - double corrg1 = (avgg1 / ng1 + avgg2 / ng2) / 2.0 / (avgg1 / ng1); - double corrg2 = (avgg1 / ng1 + avgg2 / ng2) / 2.0 / (avgg2 / ng2); + const float corrg1 = (avgg1 / ng1 + avgg2 / ng2) / 2.0 / (avgg1 / ng1); + const float corrg2 = (avgg1 / ng1 + avgg2 / ng2) / 2.0 / (avgg2 / ng2); #ifdef _OPENMP #pragma omp parallel for schedule(dynamic,16) #endif for (int i = border; i < H - border; i++) { - double corrg = (i & 1) ? corrg2 : corrg1; + const float corrg = (i & 1) ? corrg2 : corrg1; for (int j = border + ((FC(i, border) & 1) ^ 1); j < W - border; j += 2) { rawData[i][j] *= corrg; @@ -220,7 +220,7 @@ void RawImageSource::green_equilibrate(const GreenEqulibrateThreshold &thresh, a float tf = thresh(rr, cc); - if (c1 + c2 < 6 * tf * fabs(d1 - d2)) { + if (c1 + c2 < 6 * tf * std::fabs(d1 - d2)) { //pixel interpolation float gin = cfa[rr][cc >> 1]; diff --git a/rtengine/guidedfilter.cc b/rtengine/guidedfilter.cc index ad3beec51..f83560cfc 100644 --- a/rtengine/guidedfilter.cc +++ b/rtengine/guidedfilter.cc @@ -29,6 +29,7 @@ * available at https://arxiv.org/abs/1505.00996 */ +#include "array2D.h" #include "boxblur.h" #include "guidedfilter.h" #include "imagefloat.h" diff --git a/rtengine/hilite_recon.cc b/rtengine/hilite_recon.cc index 697a5e3d3..1ba42a68b 100644 --- a/rtengine/hilite_recon.cc +++ b/rtengine/hilite_recon.cc @@ -323,7 +323,7 @@ void RawImageSource::HLRecovery_inpaint(float** red, float** green, float** blue if (settings->verbose) { for (int c = 0; c < 3; ++c) { - printf("chmax[%d] : %f\tclmax[%d] : %f\tratio[%d] : %f\n", c, chmax[c], c, clmax[c], c, chmax[c] / clmax[c]); + printf("chmax[%d] : %f\tclmax[%d] : %f\tratio[%d] : %f\n", c, static_cast(chmax[c]), c, static_cast(clmax[c]), c, static_cast(chmax[c] / clmax[c])); } } @@ -366,7 +366,7 @@ void RawImageSource::HLRecovery_inpaint(float** red, float** green, float** blue if (settings->verbose) { for (int c = 0; c < 3; ++c) { - printf("correction factor[%d] : %f\n", c, factor[c]); + printf("correction factor[%d] : %f\n", c, static_cast(factor[c])); } } @@ -496,7 +496,7 @@ void RawImageSource::HLRecovery_inpaint(float** red, float** green, float** blue && blue[i + miny][j + minx] < max_f[2] ) { // if one or more channels is highlight but none are blown, add to highlight accumulator - hipass_sum += channelblur[0][i][j]; + hipass_sum += static_cast(channelblur[0][i][j]); ++hipass_norm; hilite_full[0][i][j] = red[i + miny][j + minx]; @@ -507,7 +507,7 @@ void RawImageSource::HLRecovery_inpaint(float** red, float** green, float** blue } } - const float hipass_ave = 2.f * hipass_sum / (hipass_norm + epsilon); + const float hipass_ave = 2.0 * hipass_sum / (hipass_norm + static_cast(epsilon)); if (plistener) { progress += 0.05; diff --git a/rtengine/histmatching.cc b/rtengine/histmatching.cc index f5d16866e..0053cb0d4 100644 --- a/rtengine/histmatching.cc +++ b/rtengine/histmatching.cc @@ -179,7 +179,7 @@ void mappingToCurve(const std::vector &mapping, std::vector &curve) }; idx = -1; for (ssize_t i = curve.size()-1; i > 0; i -= 2) { - if (curve[i] <= 0.f) { + if (curve[i] <= 0.0) { idx = i+1; break; } @@ -328,7 +328,7 @@ void RawImageSource::getAutoMatchedToneCurve(const ColorManagementParams &cp, st int tw = target->getWidth(), th = target->getHeight(); float thumb_ratio = float(std::max(sw, sh)) / float(std::min(sw, sh)); float target_ratio = float(std::max(tw, th)) / float(std::min(tw, th)); - if (std::abs(thumb_ratio - target_ratio) > 0.01) { + if (std::abs(thumb_ratio - target_ratio) > 0.01f) { int cx = 0, cy = 0; if (thumb_ratio > target_ratio) { // crop the height @@ -342,7 +342,7 @@ void RawImageSource::getAutoMatchedToneCurve(const ColorManagementParams &cp, st tw -= cw; } if (settings->verbose) { - std::cout << "histogram matching: cropping target to get an aspect ratio of " << round(thumb_ratio * 100)/100.0 << ":1, new size is " << tw << "x" << th << std::endl; + std::cout << "histogram matching: cropping target to get an aspect ratio of " << round(thumb_ratio * 100)/100.f << ":1, new size is " << tw << "x" << th << std::endl; } if (cx || cy) { diff --git a/rtengine/iccstore.cc b/rtengine/iccstore.cc index aea03664e..6b2be1713 100644 --- a/rtengine/iccstore.cc +++ b/rtengine/iccstore.cc @@ -43,7 +43,6 @@ #include "color.h" #include "cJSON.h" -#define inkc_constant 0x696E6B43 namespace { @@ -636,7 +635,7 @@ public: MyMutex::MyLock lock(mutex); - for (const auto profile : fileProfiles) { + for (const auto& profile : fileProfiles) { if ( ( type == ICCStore::ProfileType::MONITOR diff --git a/rtengine/iccstore.h b/rtengine/iccstore.h index 731a155bb..117124122 100644 --- a/rtengine/iccstore.h +++ b/rtengine/iccstore.h @@ -39,7 +39,7 @@ namespace procparams typedef const double(*TMatrix)[3]; -class ProfileContent +class ProfileContent final { public: ProfileContent(); @@ -54,7 +54,7 @@ private: std::string data; }; -class ICCStore +class ICCStore final { public: enum class ProfileType { diff --git a/rtengine/iimage.h b/rtengine/iimage.h index 7309dd91f..cd8aa9a9e 100644 --- a/rtengine/iimage.h +++ b/rtengine/iimage.h @@ -20,7 +20,6 @@ #include -#include #include #include "alignedbuffer.h" @@ -28,7 +27,7 @@ #include "imagedimensions.h" #include "LUT.h" #include "rt_math.h" - +#include "procparams.h" #include "../rtgui/threadutils.h" #define TR_NONE 0 @@ -41,6 +40,13 @@ #define CHECK_BOUNDS 0 +namespace Glib +{ + +class ustring; + +} + namespace rtengine { @@ -105,6 +111,10 @@ public: { rm = gm = bm = 1.0; } + virtual void getAutoWBMultipliersitc(double &tempref, double &greenref, double &tempitc, double &greenitc, float &studgood, int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, double &rm, double &gm, double &bm, const procparams::WBParams & wbpar, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw) + { + rm = gm = bm = 1.0; + } }; @@ -658,7 +668,7 @@ public: /* If any of the required allocation fails, "width" and "height" are set to -1, and all remaining buffer are freed * Can be safely used to reallocate an existing image */ - void allocate (int W, int H) override + void allocate (int W, int H) final { if (W == width && H == height) { @@ -746,7 +756,7 @@ public: } } - void rotate (int deg) override + void rotate (int deg) final { if (deg == 90) { @@ -873,7 +883,7 @@ public: } } - void hflip () override + void hflip () final { int width2 = width / 2; @@ -905,7 +915,7 @@ public: #endif } - void vflip () override + void vflip () final { int height2 = height / 2; @@ -989,7 +999,7 @@ public: } } - void computeHistogramAutoWB (double &avg_r, double &avg_g, double &avg_b, int &n, LUTu &histogram, const int compression) const override + void computeHistogramAutoWB (double &avg_r, double &avg_g, double &avg_b, int &n, LUTu &histogram, const int compression) const final { histogram.clear(); avg_r = avg_g = avg_b = 0.; @@ -1328,7 +1338,7 @@ public: * If any of the required allocation fails, "width" and "height" are set to -1, and all remaining buffer are freed * Can be safely used to reallocate an existing image or to free up it's memory with "allocate (0,0);" */ - void allocate (int W, int H) override + void allocate (int W, int H) final { if (W == width && H == height) { @@ -1382,7 +1392,7 @@ public: memcpy (dest->data, data, 3 * width * height * sizeof(T)); } - void rotate (int deg) override + void rotate (int deg) final { if (deg == 90) { @@ -1516,7 +1526,7 @@ public: } } - void hflip () override + void hflip () final { int width2 = width / 2; @@ -1552,7 +1562,7 @@ public: } } - void vflip () override + void vflip () final { AlignedBuffer lBuffer(3 * width); @@ -1619,7 +1629,7 @@ public: } } - void computeHistogramAutoWB (double &avg_r, double &avg_g, double &avg_b, int &n, LUTu &histogram, const int compression) const override + void computeHistogramAutoWB (double &avg_r, double &avg_g, double &avg_b, int &n, LUTu &histogram, const int compression) const final { histogram.clear(); avg_r = avg_g = avg_b = 0.; diff --git a/rtengine/image16.cc b/rtengine/image16.cc index a98d64d51..07fc66fad 100644 --- a/rtengine/image16.cc +++ b/rtengine/image16.cc @@ -147,10 +147,10 @@ void Image16::getStdImage(const ColorTemp &ctemp, int tran, Imagefloat* image, P gm = dgm; bm = dbm; - rm = 1.0 / rm; - gm = 1.0 / gm; - bm = 1.0 / bm; - float mul_lum = 0.299 * rm + 0.587 * gm + 0.114 * bm; + rm = 1.f / rm; + gm = 1.f / gm; + bm = 1.f / bm; + float mul_lum = 0.299f * rm + 0.587f * gm + 0.114f * bm; rm /= mul_lum; gm /= mul_lum; bm /= mul_lum; @@ -187,8 +187,6 @@ void Image16::getStdImage(const ColorTemp &ctemp, int tran, Imagefloat* image, P gm /= area; bm /= area; -#define GCLIP( x ) Color::gamma_srgb(CLIP(x)) - #ifdef _OPENMP #pragma omp parallel { diff --git a/rtengine/image16.h b/rtengine/image16.h index d0053cbfc..de9288f2d 100644 --- a/rtengine/image16.h +++ b/rtengine/image16.h @@ -29,7 +29,7 @@ namespace rtengine class Image8; class Imagefloat; -class Image16 : public IImage16, public ImageIO +class Image16 final : public IImage16, public ImageIO { public: diff --git a/rtengine/image8.cc b/rtengine/image8.cc index 66ad8b60f..67b38d0c1 100644 --- a/rtengine/image8.cc +++ b/rtengine/image8.cc @@ -111,10 +111,10 @@ void Image8::getStdImage (const ColorTemp &ctemp, int tran, Imagefloat* image, P gm = dgm; bm = dbm; - rm = 1.0 / rm; - gm = 1.0 / gm; - bm = 1.0 / bm; - float mul_lum = 0.299 * rm + 0.587 * gm + 0.114 * bm; + rm = 1.f / rm; + gm = 1.f / gm; + bm = 1.f / bm; + float mul_lum = 0.299f * rm + 0.587f * gm + 0.114f * bm; rm /= mul_lum; gm /= mul_lum; bm /= mul_lum; @@ -151,8 +151,6 @@ void Image8::getStdImage (const ColorTemp &ctemp, int tran, Imagefloat* image, P gm /= area; bm /= area; -#define GCLIP( x ) Color::gamma_srgb(CLIP(x)) - #ifdef _OPENMP #pragma omp parallel { diff --git a/rtengine/image8.h b/rtengine/image8.h index f125dccf8..c11d9d7fc 100644 --- a/rtengine/image8.h +++ b/rtengine/image8.h @@ -27,7 +27,7 @@ namespace rtengine { class Imagefloat; -class Image8 : public IImage8, public ImageIO +class Image8 final : public IImage8, public ImageIO { public: diff --git a/rtengine/imagedata.cc b/rtengine/imagedata.cc index 24cfefde9..a631a6c8d 100644 --- a/rtengine/imagedata.cc +++ b/rtengine/imagedata.cc @@ -502,11 +502,11 @@ FrameData::FrameData(rtexif::TagDirectory* frameRootDir_, rtexif::TagDirectory* } else if (!make.compare (0, 6, "PENTAX") || (!make.compare (0, 5, "RICOH") && !model.compare (0, 6, "PENTAX"))) { // ISO at max value supported, check manufacturer specific if (iso_speed == 65535 || iso_speed == 0) { - rtexif::Tag* baseIsoTag = mnote->getTag("ISO"); + const rtexif::Tag* const baseIsoTag = mnote->getTag("ISO"); if (baseIsoTag) { - std::string isoData = baseIsoTag->valueToString(); + const std::string isoData = baseIsoTag->valueToString(); if (isoData.size() > 1) { - iso_speed = stoi(isoData); + iso_speed = std::stoi(isoData); } } } diff --git a/rtengine/imagedata.h b/rtengine/imagedata.h index ff8ed4b86..4bf9bdf5b 100644 --- a/rtengine/imagedata.h +++ b/rtengine/imagedata.h @@ -23,12 +23,18 @@ #include #include -#include #include #include "imageio.h" +namespace Glib +{ + +class ustring; + +} + namespace rtexif { @@ -38,7 +44,7 @@ class TagDirectory; namespace rtengine { -class FrameData +class FrameData final { protected: @@ -95,7 +101,7 @@ public: int getRating () const; }; -class FramesData : public FramesMetaData { +class FramesData final : public FramesMetaData { private: // frame's root IFD, can be a file root IFD or a SUB-IFD std::vector> frames; diff --git a/rtengine/imagefloat.cc b/rtengine/imagefloat.cc index 1da91a4b4..f905134a0 100644 --- a/rtengine/imagefloat.cc +++ b/rtengine/imagefloat.cc @@ -178,10 +178,10 @@ void Imagefloat::getStdImage (const ColorTemp &ctemp, int tran, Imagefloat* imag gm = dgm; bm = dbm; - rm = 1.0 / rm; - gm = 1.0 / gm; - bm = 1.0 / bm; - float mul_lum = 0.299 * rm + 0.587 * gm + 0.114 * bm; + rm = 1.f / rm; + gm = 1.f / gm; + bm = 1.f / bm; + float mul_lum = 0.299f * rm + 0.587f * gm + 0.114f * bm; rm /= mul_lum; gm /= mul_lum; bm /= mul_lum; @@ -368,7 +368,7 @@ Imagefloat::to16() const void Imagefloat::normalizeFloat(float srcMinVal, float srcMaxVal) { - float scale = MAXVALD / (srcMaxVal - srcMinVal); + float scale = MAXVALF / (srcMaxVal - srcMinVal); int w = width; int h = height; diff --git a/rtengine/imagefloat.h b/rtengine/imagefloat.h index 4a2b2f7e1..cd08daf70 100644 --- a/rtengine/imagefloat.h +++ b/rtengine/imagefloat.h @@ -34,7 +34,7 @@ class LabImage; /* * Image type used by most tools; expected range: [0.0 ; 65535.0] */ -class Imagefloat : public IImagefloat, public ImageIO +class Imagefloat final : public IImagefloat, public ImageIO { public: diff --git a/rtengine/imagesource.h b/rtengine/imagesource.h index e0c26aa9f..ea049d37c 100644 --- a/rtengine/imagesource.h +++ b/rtengine/imagesource.h @@ -25,8 +25,9 @@ #include "coord2d.h" #include "imagedata.h" -#include "LUT.h" #include "rtengine.h" +#include "colortemp.h" +#include "array2D.h" template class LUT; @@ -86,19 +87,19 @@ protected: public: ImageSource () : references (1), redAWBMul(-1.), greenAWBMul(-1.), blueAWBMul(-1.), - embProfile(nullptr), idata(nullptr), dirpyrdenoiseExpComp(INFINITY) {} + embProfile(nullptr), idata(nullptr), dirpyrdenoiseExpComp(RT_INFINITY) {} ~ImageSource () override {} virtual int load (const Glib::ustring &fname) = 0; virtual void preprocess (const procparams::RAWParams &raw, const procparams::LensProfParams &lensProf, const procparams::CoarseTransformParams& coarse, bool prepareDenoise = true) {}; - virtual void filmNegativeProcess (const procparams::FilmNegativeParams ¶ms) {}; + virtual void filmNegativeProcess (const procparams::FilmNegativeParams ¶ms, std::array& filmBaseValues) {}; virtual bool getFilmNegativeExponents (Coord2D spotA, Coord2D spotB, int tran, const procparams::FilmNegativeParams& currentParams, std::array& newExps) { return false; }; + virtual bool getRawSpotValues (Coord2D spot, int spotSize, int tran, const procparams::FilmNegativeParams ¶ms, std::array& rawValues) { return false; }; virtual void demosaic (const procparams::RAWParams &raw, bool autoContrast, double &contrastThreshold, bool cache = false) {}; virtual void retinex (const procparams::ColorManagementParams& cmp, const procparams::RetinexParams &deh, const procparams::ToneCurveParams& Tc, LUTf & cdcurve, LUTf & mapcurve, const RetinextransmissionCurve & dehatransmissionCurve, const RetinexgaintransmissionCurve & dehagaintransmissionCurve, multi_array2D &conversionBuffer, bool dehacontlutili, bool mapcontlutili, bool useHsl, float &minCD, float &maxCD, float &mini, float &maxi, float &Tmean, float &Tsigma, float &Tmin, float &Tmax, LUTu &histLRETI) {}; virtual void retinexPrepareCurves (const procparams::RetinexParams &retinexParams, LUTf &cdcurve, LUTf &mapcurve, RetinextransmissionCurve &retinextransmissionCurve, RetinexgaintransmissionCurve &retinexgaintransmissionCurve, bool &retinexcontlutili, bool &mapcontlutili, bool &useHsl, LUTu & lhist16RETI, LUTu & histLRETI) {}; virtual void retinexPrepareBuffers (const procparams::ColorManagementParams& cmp, const procparams::RetinexParams &retinexParams, multi_array2D &conversionBuffer, LUTu &lhist16RETI) {}; - virtual void flushRawData () {}; - virtual void flushRGB () {}; + virtual void flush () = 0; virtual void HLRecovery_Global (const procparams::ToneCurveParams &hrp) {}; virtual void HLRecovery_inpaint (float** red, float** green, float** blue) {}; @@ -119,8 +120,11 @@ public: virtual void convertColorSpace (Imagefloat* image, const procparams::ColorManagementParams &cmp, const ColorTemp &wb) = 0; // DIRTY HACK: this method is derived in rawimagesource and strimagesource, but (...,RAWParams raw) will be used ONLY for raw images virtual void getAutoWBMultipliers (double &rm, double &gm, double &bm) = 0; + virtual void getAutoWBMultipliersitc(double &tempref, double &greenref, double &tempitc, double & greenitc, float &studgood, int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, double &rm, double &gm, double &bm, const procparams::WBParams & wbpar, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw) = 0; virtual ColorTemp getWB () const = 0; virtual ColorTemp getSpotWB (std::vector &red, std::vector &green, std::vector &blue, int tran, double equal) = 0; + virtual void WBauto(double &tempref, double &greenref, array2D &redloc, array2D &greenloc, array2D &blueloc, int bfw, int bfh, double &avg_rm, double &avg_gm, double &avg_bm, double &tempitc, double &greenitc, float &studgood, bool &twotimes, const procparams::WBParams & wbpar, int begx, int begy, int yEn, int xEn, int cx, int cy, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw) = 0; + virtual void getrgbloc(int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w) = 0; virtual double getDefGain () const { @@ -143,11 +147,11 @@ public: virtual void setProgressListener (ProgressListener* pl) {} - void increaseRef () override + void increaseRef () final { references++; } - void decreaseRef () override + void decreaseRef () final { references--; @@ -175,15 +179,15 @@ public: return dirpyrdenoiseExpComp; } // functions inherited from the InitialImage interface - Glib::ustring getFileName () override + Glib::ustring getFileName () final { return fileName; } - cmsHPROFILE getEmbeddedProfile () override + cmsHPROFILE getEmbeddedProfile () final { return embProfile; } - const FramesMetaData* getMetaData () override + const FramesMetaData* getMetaData () final { return idata; } diff --git a/rtengine/improccoordinator.cc b/rtengine/improccoordinator.cc index e915a11b0..f68616b96 100644 --- a/rtengine/improccoordinator.cc +++ b/rtengine/improccoordinator.cc @@ -36,6 +36,7 @@ #include "lcp.h" #include "procparams.h" #include "refreshmap.h" +#include "guidedfilter.h" #include "../rtgui/options.h" @@ -43,6 +44,22 @@ #include #endif +namespace +{ +using rtengine::Coord2D; +Coord2D translateCoord(const rtengine::ImProcFunctions& ipf, int fw, int fh, int x, int y) { + + const std::vector points = {Coord2D(x, y)}; + + std::vector red; + std::vector green; + std::vector blue; + ipf.transCoord(fw, fh, points, red, green, blue); + + return green[0]; +} + +} namespace rtengine { @@ -55,11 +72,12 @@ ImProcCoordinator::ImProcCoordinator() : fattal_11_dcrop_cache(nullptr), previmg(nullptr), workimg(nullptr), - ncie (nullptr), - imgsrc (nullptr), - lastAwbEqual (0.), - lastAwbTempBias (0.0), - monitorIntent (RI_RELATIVE), + ncie(nullptr), + imgsrc(nullptr), + lastAwbEqual(0.), + lastAwbTempBias(0.0), + lastAwbauto(""), + monitorIntent(RI_RELATIVE), softProof(false), gamutCheck(false), sharpMask(false), @@ -194,12 +212,12 @@ ImProcCoordinator::~ImProcCoordinator() imgsrc->decreaseRef(); - if(customTransformIn) { + if (customTransformIn) { cmsDeleteTransform(customTransformIn); customTransformIn = nullptr; } - if(customTransformOut) { + if (customTransformOut) { cmsDeleteTransform(customTransformOut); customTransformOut = nullptr; } @@ -231,11 +249,12 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) MyMutex::MyLock processingLock(mProcessing); bool highDetailNeeded = options.prevdemo == PD_Sidecar ? true : (todo & M_HIGHQUAL); + // printf("metwb=%s \n", params->wb.method.c_str()); // Check if any detail crops need high detail. If not, take a fast path short cut if (!highDetailNeeded) { for (size_t i = 0; i < crops.size(); i++) { - if (crops[i]->get_skip() == 1) { // skip=1 -> full resolution + if (crops[i]->get_skip() == 1) { // skip=1 -> full resolution highDetailNeeded = true; break; } @@ -252,7 +271,7 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) RAWParams rp = params->raw; ColorManagementParams cmp = params->icm; LCurveParams lcur = params->labCurve; - + if (!highDetailNeeded) { // if below 100% magnification, take a fast path if (rp.bayersensor.method != RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::NONE) && rp.bayersensor.method != RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::MONO)) { @@ -279,9 +298,11 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) imgsrc->setCurrentFrame(params->raw.bayersensor.imageNum); imgsrc->preprocess(rp, params->lensProf, params->coarse); + if (flatFieldAutoClipListener && rp.ff_AutoClipControl) { flatFieldAutoClipListener->flatFieldAutoClipValueChanged(imgsrc->getFlatFieldAutoClipValue()); } + imgsrc->getRAWHistogram(histRedRaw, histGreenRaw, histBlueRaw); highDetailPreprocessComputed = highDetailNeeded; @@ -295,7 +316,15 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) ) && params->filmNegative.enabled ) { - imgsrc->filmNegativeProcess(params->filmNegative); + std::array filmBaseValues = { + static_cast(params->filmNegative.redBase), + static_cast(params->filmNegative.greenBase), + static_cast(params->filmNegative.blueBase) + }; + imgsrc->filmNegativeProcess(params->filmNegative, filmBaseValues); + if (filmNegListener && params->filmNegative.redBase <= 0.f) { + filmNegListener->filmBaseValuesChanged(filmBaseValues); + } } } @@ -327,8 +356,9 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) printf("Demosaic X-Trans image with using method: %s\n", rp.xtranssensor.method.c_str()); } } - if(imgsrc->getSensorType() == ST_BAYER) { - if(params->raw.bayersensor.method != RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::PIXELSHIFT)) { + + if (imgsrc->getSensorType() == ST_BAYER) { + if (params->raw.bayersensor.method != RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::PIXELSHIFT)) { imgsrc->setBorder(params->raw.bayersensor.border); } else { imgsrc->setBorder(std::max(params->raw.bayersensor.border, 2)); @@ -336,6 +366,7 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) } else if (imgsrc->getSensorType() == ST_FUJI_XTRANS) { imgsrc->setBorder(params->raw.xtranssensor.border); } + bool autoContrast = imgsrc->getSensorType() == ST_BAYER ? params->raw.bayersensor.dualDemosaicAutoContrast : params->raw.xtranssensor.dualDemosaicAutoContrast; double contrastThreshold = imgsrc->getSensorType() == ST_BAYER ? params->raw.bayersensor.dualDemosaicContrast : params->raw.xtranssensor.dualDemosaicContrast; imgsrc->demosaic(rp, autoContrast, contrastThreshold, params->pdsharpening.enabled); @@ -343,7 +374,8 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) if (imgsrc->getSensorType() == ST_BAYER && bayerAutoContrastListener && autoContrast) { bayerAutoContrastListener->autoContrastChanged(contrastThreshold); } else if (imgsrc->getSensorType() == ST_FUJI_XTRANS && xtransAutoContrastListener && autoContrast) { - xtransAutoContrastListener->autoContrastChanged(autoContrast ? contrastThreshold : -1.0); + + xtransAutoContrastListener->autoContrastChanged(contrastThreshold); } // if a demosaic happened we should also call getimage later, so we need to set the M_INIT flag todo |= (M_INIT | M_CSHARP); @@ -381,6 +413,12 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) } } + if (todo & (M_INIT | M_LINDENOISE | M_HDR)) { + if (params->wb.method == "autitcgreen") { + imgsrc->getrgbloc(0, 0, fh, fw, 0, 0, fh, fw); + } + } + if ((todo & (M_RETINEX | M_INIT)) && params->retinex.enabled) { bool dehacontlutili = false; bool mapcontlutili = false; @@ -397,6 +435,10 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) } } + const bool autowb = (params->wb.method == "autold" || params->wb.method == "autitcgreen"); + if (settings->verbose) { + printf("automethod=%s \n", params->wb.method.c_str()); + } if (todo & (M_INIT | M_LINDENOISE | M_HDR)) { MyMutex::MyLock initLock(minit); // Also used in crop window @@ -408,28 +450,53 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) } currWB = ColorTemp(params->wb.temperature, params->wb.green, params->wb.equal, params->wb.method); + float studgood = 1000.f; if (!params->wb.enabled) { currWB = ColorTemp(); } else if (params->wb.method == "Camera") { currWB = imgsrc->getWB(); - } else if (params->wb.method == "Auto") { - if (lastAwbEqual != params->wb.equal || lastAwbTempBias != params->wb.tempBias) { + lastAwbauto = ""; //reinitialize auto + } else if (autowb) { + if (params->wb.method == "autitcgreen" || lastAwbEqual != params->wb.equal || lastAwbTempBias != params->wb.tempBias || lastAwbauto != params->wb.method) { double rm, gm, bm; - imgsrc->getAutoWBMultipliers(rm, gm, bm); + double tempitc = 5000.f; + double greenitc = 1.; + currWBitc = imgsrc->getWB(); + double tempref = currWBitc.getTemp() * (1. + params->wb.tempBias); + double greenref = currWBitc.getGreen(); + if (settings->verbose && params->wb.method == "autitcgreen") { + printf("tempref=%f greref=%f\n", tempref, greenref); + } + + imgsrc->getAutoWBMultipliersitc(tempref, greenref, tempitc, greenitc, studgood, 0, 0, fh, fw, 0, 0, fh, fw, rm, gm, bm, params->wb, params->icm, params->raw); + + if (params->wb.method == "autitcgreen") { + params->wb.temperature = tempitc; + params->wb.green = greenitc; + currWB = ColorTemp(params->wb.temperature, params->wb.green, 1., params->wb.method); + currWB.getMultipliers(rm, gm, bm); + } if (rm != -1.) { - autoWB.update(rm, gm, bm, params->wb.equal, params->wb.tempBias); + double bias = params->wb.tempBias; + + if (params->wb.method == "autitcgreen") { + bias = 0.; + } + + autoWB.update(rm, gm, bm, params->wb.equal, bias); lastAwbEqual = params->wb.equal; lastAwbTempBias = params->wb.tempBias; + lastAwbauto = params->wb.method; } else { lastAwbEqual = -1.; lastAwbTempBias = 0.0; + lastAwbauto = ""; autoWB.useDefaults(params->wb.equal); } - - //double rr,gg,bb; - //autoWB.getMultipliers(rr,gg,bb); + + } currWB = autoWB; @@ -440,9 +507,13 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) params->wb.green = currWB.getGreen(); } - if (params->wb.method == "Auto" && awbListener && params->wb.enabled) { - awbListener->WBChanged(params->wb.temperature, params->wb.green); - } + if (autowb && awbListener && params->wb.method == "autitcgreen") { + awbListener->WBChanged(params->wb.temperature, params->wb.green, studgood); + } + + if (autowb && awbListener && params->wb.method == "autold") { + awbListener->WBChanged(params->wb.temperature, params->wb.green, -1.f); + } /* GammaValues g_a; @@ -605,7 +676,7 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) } } - if (todo & (M_AUTOEXP | M_RGBCURVE)) { + if (todo & (M_AUTOEXP | M_RGBCURVE)) { if (params->icm.workingTRC == "Custom") { //exec TRC IN free if (oprevi == orig_prev) { oprevi = new Imagefloat(pW, pH); @@ -617,17 +688,21 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) if (profile == "sRGB" || profile == "Adobe RGB" || profile == "ProPhoto" || profile == "WideGamut" || profile == "BruceRGB" || profile == "Beta RGB" || profile == "BestRGB" || profile == "Rec2020" || profile == "ACESp0" || profile == "ACESp1") { const int cw = oprevi->getWidth(); const int ch = oprevi->getHeight(); + // put gamma TRC to 1 - if(customTransformIn) { + if (customTransformIn) { cmsDeleteTransform(customTransformIn); customTransformIn = nullptr; } + ipf.workingtrc(oprevi, oprevi, cw, ch, -5, params->icm.workingProfile, 2.4, 12.92310, customTransformIn, true, false, true); + //adjust TRC - if(customTransformOut) { + if (customTransformOut) { cmsDeleteTransform(customTransformOut); customTransformOut = nullptr; } + ipf.workingtrc(oprevi, oprevi, cw, ch, 5, params->icm.workingProfile, params->icm.workingTRCGamma, params->icm.workingTRCSlope, customTransformOut, false, true, true); } } @@ -635,7 +710,7 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) if ((todo & M_RGBCURVE) || (todo & M_CROP)) { - // if (hListener) oprevi->calcCroppedHistogram(params, scale, histCropped); + // if (hListener) oprevi->calcCroppedHistogram(params, scale, histCropped); //complexCurve also calculated pre-curves histogram depending on crop CurveFactory::complexCurve(params->toneCurve.expcomp, params->toneCurve.black / 65535.0, @@ -729,12 +804,12 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) DCPProfileApplyState as; DCPProfile *dcpProf = imgsrc->getDCP(params->icm, as); - ipf.rgbProc (oprevi, oprevl, nullptr, hltonecurve, shtonecurve, tonecurve, params->toneCurve.saturation, + ipf.rgbProc(oprevi, oprevl, nullptr, hltonecurve, shtonecurve, tonecurve, params->toneCurve.saturation, rCurve, gCurve, bCurve, colourToningSatLimit, colourToningSatLimitOpacity, ctColorCurve, ctOpacityCurve, opautili, clToningcurve, cl2Toningcurve, customToneCurve1, customToneCurve2, beforeToneCurveBW, afterToneCurveBW, rrm, ggm, bbm, bwAutoR, bwAutoG, bwAutoB, params->toneCurve.expcomp, params->toneCurve.hlcompr, params->toneCurve.hlcomprthresh, dcpProf, as, histToneCurve); if (params->blackwhite.enabled && params->blackwhite.autoc && abwListener) { if (settings->verbose) { - printf("ImProcCoordinator / Auto B&W coefs: R=%.2f G=%.2f B=%.2f\n", bwAutoR, bwAutoG, bwAutoB); + printf("ImProcCoordinator / Auto B&W coefs: R=%.2f G=%.2f B=%.2f\n", static_cast(bwAutoR), static_cast(bwAutoG), static_cast(bwAutoB)); } abwListener->BWChanged((float) rrm, (float) ggm, (float) bbm); @@ -814,17 +889,220 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) wavcontlutili = false; CurveFactory::curveWavContL(wavcontlutili, params->wavelet.wavclCurve, wavclCurve, scale == 1 ? 1 : 16); - if ((params->wavelet.enabled)) { WaveletParams WaveParams = params->wavelet; - WaveParams.getCurves(wavCLVCurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL); - + WaveParams.getCurves(wavCLVCurve, wavblcurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL); int kall = 0; - ipf.ip_wavelet(nprevl, nprevl, kall, WaveParams, wavCLVCurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL, wavclCurve, scale); + LabImage *unshar = nullptr; + Glib::ustring provis; + LabImage *provradius = nullptr; + bool procont = WaveParams.expcontrast; + bool prochro = WaveParams.expchroma; + bool proedge = WaveParams.expedge; + bool profin = WaveParams.expfinal; + bool proton = WaveParams.exptoning; + bool pronois = WaveParams.expnoise; + if(WaveParams.showmask) { + // WaveParams.showmask = false; + // WaveParams.expclari = true; + } + + if (WaveParams.softrad > 0.f) { + provradius = new LabImage(pW, pH); + provradius->CopyFrom(nprevl); + } + + + + + if ((WaveParams.ushamethod == "sharp" || WaveParams.ushamethod == "clari") && WaveParams.expclari && WaveParams.CLmethod != "all") { + unshar = new LabImage(pW, pH); + provis = params->wavelet.CLmethod; + params->wavelet.CLmethod = "all"; + ipf.ip_wavelet(nprevl, nprevl, kall, WaveParams, wavCLVCurve, wavblcurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL, wavclCurve, scale); + + unshar->CopyFrom(nprevl); + + params->wavelet.CLmethod = provis; + + WaveParams.expcontrast = false; + WaveParams.expchroma = false; + WaveParams.expedge = false; + WaveParams.expfinal = false; + WaveParams.exptoning = false; + WaveParams.expnoise = false; + } + + ipf.ip_wavelet(nprevl, nprevl, kall, WaveParams, wavCLVCurve, wavblcurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL, wavclCurve, scale); + + + if ((WaveParams.ushamethod == "sharp" || WaveParams.ushamethod == "clari") && WaveParams.expclari && WaveParams.CLmethod != "all") { + WaveParams.expcontrast = procont; + WaveParams.expchroma = prochro; + WaveParams.expedge = proedge; + WaveParams.expfinal = profin; + WaveParams.exptoning = proton; + WaveParams.expnoise = pronois; + + if (WaveParams.softrad > 0.f) { + + array2D ble(pW, pH); + array2D guid(pW, pH); + Imagefloat *tmpImage = nullptr; + tmpImage = new Imagefloat(pW, pH); + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < pH; ir++) + for (int jr = 0; jr < pW; jr++) { + float X, Y, Z; + float L = provradius->L[ir][jr]; + float a = provradius->a[ir][jr]; + float b = provradius->b[ir][jr]; + Color::Lab2XYZ(L, a, b, X, Y, Z); + + guid[ir][jr] = Y / 32768.f; + float La = nprevl->L[ir][jr]; + float aa = nprevl->a[ir][jr]; + float ba = nprevl->b[ir][jr]; + Color::Lab2XYZ(La, aa, ba, X, Y, Z); + tmpImage->r(ir, jr) = X; + tmpImage->g(ir, jr) = Y; + tmpImage->b(ir, jr) = Z; + ble[ir][jr] = Y / 32768.f; + } + + double epsilmax = 0.0001; + double epsilmin = 0.00001; + double aepsil = (epsilmax - epsilmin) / 90.f; + double bepsil = epsilmax - 100.f * aepsil; + double epsil = aepsil * WaveParams.softrad + bepsil; + + float blur = 10.f / scale * (0.0001f + 0.8f * WaveParams.softrad); + // rtengine::guidedFilter(guid, ble, ble, blur, 0.001, multiTh); + rtengine::guidedFilter(guid, ble, ble, blur, epsil, false); + + + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < pH; ir++) + for (int jr = 0; jr < pW; jr++) { + float X = tmpImage->r(ir, jr); + float Y = 32768.f * ble[ir][jr]; + float Z = tmpImage->b(ir, jr); + float L, a, b; + Color::XYZ2Lab(X, Y, Z, L, a, b); + nprevl->L[ir][jr] = L; + } + + delete tmpImage; + + } + + } + + if ((WaveParams.ushamethod == "sharp" || WaveParams.ushamethod == "clari") && WaveParams.expclari && WaveParams.CLmethod != "all") { + float mL = (float)(WaveParams.mergeL / 100.f); + float mC = (float)(WaveParams.mergeC / 100.f); + float mL0; + float mC0; + float background = 0.f; + int show = 0; + + + + if ((WaveParams.CLmethod == "one" || WaveParams.CLmethod == "inf") && WaveParams.Backmethod == "black") { + mL0 = mC0 = 0.f; + mL = - 1.5f * mL; + mC = -mC; + background = 12000.f; + show = 0; + } else if (WaveParams.CLmethod == "sup" && WaveParams.Backmethod == "resid") { + mL0 = mL; + mC0 = mC; + background = 0.f; + show = 0; + } else { + mL0 = mL = mC0 = mC = 0.f; + background = 0.f; + show = 0; + } + float indic = 1.f; + + if(WaveParams.showmask){ + mL0 = mC0 = -1.f; + indic = -1.f; + mL = fabs(mL); + mC = fabs(mC); + show = 1; + } +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int x = 0; x < pH; x++) + for (int y = 0; y < pW; y++) { + nprevl->L[x][y] = LIM((1.f + mL0) * (unshar->L[x][y]) + show * background - mL * indic * nprevl->L[x][y], 0.f, 32768.f); + nprevl->a[x][y] = (1.f + mC0) * (unshar->a[x][y]) - mC * indic * nprevl->a[x][y]; + nprevl->b[x][y] = (1.f + mC0) * (unshar->b[x][y]) - mC * indic * nprevl->b[x][y]; + } + + delete unshar; + unshar = NULL; +/* + if (WaveParams.softrad > 0.f) { + array2D ble(pW, pH); + array2D guid(pW, pH); +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < pH; ir++) + for (int jr = 0; jr < pW; jr++) { + ble[ir][jr] = (nprevl->L[ir][jr] - provradius->L[ir][jr]) / 32768.f; + guid[ir][jr] = provradius->L[ir][jr] / 32768.f; + } + double epsilmax = 0.001; + double epsilmin = 0.0001; + double aepsil = (epsilmax - epsilmin) / 90.f; + double bepsil = epsilmax - 100.f * aepsil; + double epsil = aepsil * WaveParams.softrad + bepsil; + + float blur = 10.f / scale * (0.001f + 0.8f * WaveParams.softrad); + // rtengine::guidedFilter(guid, ble, ble, blur, 0.001, multiTh); + rtengine::guidedFilter(guid, ble, ble, blur, epsil, false); + + + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < pH; ir++) + for (int jr = 0; jr < pW; jr++) { + nprevl->L[ir][jr] = provradius->L[ir][jr] + 32768.f * ble[ir][jr]; + } + } +*/ + if (WaveParams.softrad > 0.f) { + + delete provradius; + provradius = NULL; + + } + + + } + } - ipf.softLight(nprevl); + ipf.softLight(nprevl); if (params->colorappearance.enabled) { // L histo and Chroma histo for ciecam @@ -871,7 +1149,7 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) double E_V = fcomp + log2(double ((fnum * fnum) / fspeed / (fiso / 100.f))); E_V += params->toneCurve.expcomp;// exposure compensation in tonecurve ==> direct EV E_V += log2(params->raw.expos); // exposure raw white point ; log2 ==> linear to EV - adap = powf(2.f, E_V - 3.f); // cd / m2 + adap = pow(2.0, E_V - 3.0); // cd / m2 // end calculation adaptation scene luminosity } @@ -897,17 +1175,23 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) ipf.ciecam_02float(ncie, float (adap), pW, 2, nprevl, params.get(), customColCurve1, customColCurve2, customColCurve3, histLCAM, histCCAM, CAMBrightCurveJ, CAMBrightCurveQ, CAMMean, 0 , scale, execsharp, d, dj, yb, 1); - if ((params->colorappearance.autodegree || params->colorappearance.autodegreeout) && acListener && params->colorappearance.enabled) { + if ((params->colorappearance.autodegree || params->colorappearance.autodegreeout) && acListener && params->colorappearance.enabled && !params->colorappearance.presetcat02) { acListener->autoCamChanged(100.* (double)d, 100.* (double)dj); } - if (params->colorappearance.autoadapscen && acListener && params->colorappearance.enabled) { + if (params->colorappearance.autoadapscen && acListener && params->colorappearance.enabled && !params->colorappearance.presetcat02) { acListener->adapCamChanged(adap); //real value of adapt scene } - if (params->colorappearance.autoybscen && acListener && params->colorappearance.enabled) { + if (params->colorappearance.autoybscen && acListener && params->colorappearance.enabled && !params->colorappearance.presetcat02) { acListener->ybCamChanged((int) yb); //real value Yb scene } + + if (params->colorappearance.enabled && params->colorappearance.presetcat02 && params->colorappearance.autotempout) { + // acListener->wbCamChanged(params->wb.temperature, params->wb.green); //real temp and tint + acListener->wbCamChanged(params->wb.temperature, 1.f); //real temp and tint = 1. + } + } else { // CIECAM is disabled, we free up its image buffer to save some space if (ncie) { @@ -976,6 +1260,7 @@ void ImProcCoordinator::updatePreviewImage(int todo, bool panningRelatedChange) hListener->histogramChanged(histRed, histGreen, histBlue, histLuma, histToneCurve, histLCurve, histCCurve, /*histCLurve, histLLCurve,*/ histLCAM, histCCAM, histRedRaw, histGreenRaw, histBlueRaw, histChroma, histLRETI); } } + if (orig_prev != oprevi) { delete oprevi; oprevi = nullptr; @@ -1137,18 +1422,27 @@ bool ImProcCoordinator::getAutoWB(double& temp, double& green, double equal, dou { if (imgsrc) { - if (lastAwbEqual != equal || lastAwbTempBias != tempBias) { + if (lastAwbEqual != equal || lastAwbTempBias != tempBias || lastAwbauto != params->wb.method) { // Issue 2500 MyMutex::MyLock lock(minit); // Also used in crop window double rm, gm, bm; - imgsrc->getAutoWBMultipliers(rm, gm, bm); + params->wb.method = "autold";//same result as before muliple Auto WB + + // imgsrc->getAutoWBMultipliers(rm, gm, bm); + double tempitc = 5000.; + double greenitc = 1.; + float studgood = 1000.f; + double tempref, greenref; + imgsrc->getAutoWBMultipliersitc(tempref, greenref, tempitc, greenitc, studgood, 0, 0, fh, fw, 0, 0, fh, fw, rm, gm, bm, params->wb, params->icm, params->raw); if (rm != -1) { autoWB.update(rm, gm, bm, equal, tempBias); lastAwbEqual = equal; lastAwbTempBias = tempBias; + lastAwbauto = params->wb.method; } else { lastAwbEqual = -1.; autoWB.useDefaults(equal); + lastAwbauto = ""; lastAwbTempBias = 0.0; } } @@ -1211,27 +1505,22 @@ bool ImProcCoordinator::getFilmNegativeExponents(int xA, int yA, int xB, int yB, { MyMutex::MyLock lock(mProcessing); - const auto xlate = - [this](int x, int y) -> Coord2D - { - const std::vector points = {Coord2D(x, y)}; - - std::vector red; - std::vector green; - std::vector blue; - ipf.transCoord(fw, fh, points, red, green, blue); - - return green[0]; - }; - const int tr = getCoarseBitMask(params->coarse); - const Coord2D p1 = xlate(xA, yA); - const Coord2D p2 = xlate(xB, yB); + const Coord2D p1 = translateCoord(ipf, fw, fh, xA, yA); + const Coord2D p2 = translateCoord(ipf, fw, fh, xB, yB); return imgsrc->getFilmNegativeExponents(p1, p2, tr, params->filmNegative, newExps); } +bool ImProcCoordinator::getRawSpotValues(int x, int y, int spotSize, std::array& rawValues) +{ + MyMutex::MyLock lock(mProcessing); + + return imgsrc->getRawSpotValues(translateCoord(ipf, fw, fh, x, y), spotSize, + getCoarseBitMask(params->coarse), params->filmNegative, rawValues); +} + void ImProcCoordinator::getAutoCrop(double ratio, int &x, int &y, int &w, int &h) { @@ -1323,7 +1612,7 @@ void ImProcCoordinator::saveInputICCReference(const Glib::ustring& fname, bool a if (params->wb.method == "Camera") { currWB = imgsrc->getWB(); - } else if (params->wb.method == "Auto") { + } else if (params->wb.method == "autold") { if (lastAwbEqual != params->wb.equal || lastAwbTempBias != params->wb.tempBias) { double rm, gm, bm; imgsrc->getAutoWBMultipliers(rm, gm, bm); diff --git a/rtengine/improccoordinator.h b/rtengine/improccoordinator.h index 96d1f80ce..e17d88183 100644 --- a/rtengine/improccoordinator.h +++ b/rtengine/improccoordinator.h @@ -27,7 +27,6 @@ #include "imagesource.h" #include "improcfun.h" #include "LUT.h" -#include "procevents.h" #include "rtengine.h" #include "../rtgui/threadutils.h" @@ -55,7 +54,7 @@ class Crop; * but using this class' LUT and other precomputed parameters. The main preview area is displaying a non framed Crop object, * while detail windows are framed Crop objects. */ -class ImProcCoordinator : public StagedImageProcessor +class ImProcCoordinator final : public StagedImageProcessor { friend class Crop; @@ -74,9 +73,13 @@ protected: ColorTemp currWB; ColorTemp autoWB; + ColorTemp currWBloc; + ColorTemp autoWBloc; + ColorTemp currWBitc; double lastAwbEqual; double lastAwbTempBias; + Glib::ustring lastAwbauto; Glib::ustring monitorProfile; RenderingIntent monitorIntent; @@ -136,6 +139,7 @@ protected: NoiseCurve noiseLCurve; NoiseCurve noiseCCurve; WavCurve wavCLVCurve; + Wavblcurve wavblcurve; WavOpacityCurveRG waOpacityCurveRG; WavOpacityCurveBY waOpacityCurveBY; WavOpacityCurveW waOpacityCurveW; @@ -171,6 +175,7 @@ protected: AutoRadiusListener *pdSharpenAutoRadiusListener; FrameCountListener *frameCountListener; ImageTypeListener *imageTypeListener; + FilmNegListener *filmNegListener; AutoColorTonListener* actListener; AutoChromaListener* adnListener; @@ -277,6 +282,7 @@ public: void getCamWB (double& temp, double& green) override; void getSpotWB (int x, int y, int rectSize, double& temp, double& green) override; bool getFilmNegativeExponents(int xA, int yA, int xB, int yB, std::array& newExps) override; + bool getRawSpotValues(int x, int y, int spotSize, std::array& rawValues) override; void getAutoCrop (double ratio, int &x, int &y, int &w, int &h) override; bool getHighQualComputed() override; void setHighQualComputed() override; @@ -385,6 +391,11 @@ public: imageTypeListener = itl; } + void setFilmNegListener (FilmNegListener* fnl) override + { + filmNegListener = fnl; + } + void saveInputICCReference (const Glib::ustring& fname, bool apply_wb) override; InitialImage* getInitialImage () override diff --git a/rtengine/improcfun.cc b/rtengine/improcfun.cc index d5c69773e..aa5515e79 100644 --- a/rtengine/improcfun.cc +++ b/rtengine/improcfun.cc @@ -31,15 +31,16 @@ #include "cieimage.h" #include "clutstore.h" #include "color.h" +#include "colortemp.h" #include "curves.h" #include "dcp.h" #include "EdgePreservingDecomposition.h" #include "iccmatrices.h" #include "iccstore.h" #include "imagesource.h" -#include "improccoordinator.h" #include "improcfun.h" #include "labimage.h" +#include "pipettebuffer.h" #include "procparams.h" #include "rt_math.h" #include "rtengine.h" @@ -54,9 +55,6 @@ #include "mytime.h" #endif -#undef CLIPD -#define CLIPD(a) ((a)>0.0f?((a)<1.0f?(a):1.0f):0.0f) - namespace { using namespace rtengine; @@ -137,7 +135,7 @@ void highlightToneCurve(const LUTf &hltonecurve, float *rtemp, float *gtemp, flo float b = btemp[ti * tileSize + tj + k]; float tonefactor = ((r < MAXVALF ? hltonecurve[r] : CurveFactory::hlcurve(exp_scale, comp, hlrange, r)) + (g < MAXVALF ? hltonecurve[g] : CurveFactory::hlcurve(exp_scale, comp, hlrange, g)) + - (b < MAXVALF ? hltonecurve[b] : CurveFactory::hlcurve(exp_scale, comp, hlrange, b))) / 3.0; + (b < MAXVALF ? hltonecurve[b] : CurveFactory::hlcurve(exp_scale, comp, hlrange, b))) / 3.f; // note: tonefactor includes exposure scaling, that is here exposure slider and highlight compression takes place rtemp[ti * tileSize + tj + k] = r * tonefactor; @@ -165,7 +163,7 @@ void highlightToneCurve(const LUTf &hltonecurve, float *rtemp, float *gtemp, flo //float tonefactor = hltonecurve[(0.299f*r+0.587f*g+0.114f*b)]; float tonefactor = ((r < MAXVALF ? hltonecurve[r] : CurveFactory::hlcurve(exp_scale, comp, hlrange, r)) + (g < MAXVALF ? hltonecurve[g] : CurveFactory::hlcurve(exp_scale, comp, hlrange, g)) + - (b < MAXVALF ? hltonecurve[b] : CurveFactory::hlcurve(exp_scale, comp, hlrange, b))) / 3.0; + (b < MAXVALF ? hltonecurve[b] : CurveFactory::hlcurve(exp_scale, comp, hlrange, b))) / 3.f; // note: tonefactor includes exposure scaling, that is here exposure slider and highlight compression takes place rtemp[ti * tileSize + tj] = r * tonefactor; @@ -518,8 +516,7 @@ void ImProcFunctions::ciecam_02float (CieImage* ncie, float adap, int pW, int pw int width = lab->W, height = lab->H; float minQ = 10000.f; float maxQ = -1000.f; - float Yw; - Yw = 1.0; + double Yw = 1.0; double Xw, Zw; float f = 0.f, nc = 0.f, la, c = 0.f, xw, yw, zw, f2 = 1.f, c2 = 1.f, nc2 = 1.f, yb2; float fl, n, nbb, ncb, aw; //d @@ -596,13 +593,13 @@ void ImProcFunctions::ciecam_02float (CieImage* ncie, float adap, int pW, int pw algepd = true; } - xwd = 100.f * Xwout; - zwd = 100.f * Zwout; - ywd = 100.f / params->colorappearance.greenout;//approximation to simplify + xwd = 100.0 * Xwout; + zwd = 100.0 * Zwout; + ywd = 100.0 / params->colorappearance.greenout;//approximation to simplify - xws = 100.f * Xwsc; - zws = 100.f * Zwsc; - yws = 100.f / params->colorappearance.greensc;//approximation to simplify + xws = 100.0 * Xwsc; + zws = 100.0 * Zwsc; + yws = 100.0 / params->colorappearance.greensc;//approximation to simplify /* @@ -699,20 +696,20 @@ void ImProcFunctions::ciecam_02float (CieImage* ncie, float adap, int pW, int pw if (alg == 3 || alg == 1) { schr = params->colorappearance.schroma; - if (schr > 0.0) { - schr = schr / 2.0f; //divide sensibility for saturation + if (schr > 0.f) { + schr = schr / 2.f; //divide sensibility for saturation } if (alg == 3) { - if (schr == -100.0f) { + if (schr == -100.f) { schr = -99.f; } - if (schr == 100.0f) { + if (schr == 100.f) { schr = 98.f; } } else { - if (schr == -100.0f) { + if (schr == -100.f) { schr = -99.8f; } } @@ -751,7 +748,7 @@ void ImProcFunctions::ciecam_02float (CieImage* ncie, float adap, int pW, int pw LUTu hist16J; LUTu hist16Q; - if ((needJ && CAMBrightCurveJ.dirty) || (needQ && CAMBrightCurveQ.dirty) || (std::isnan (mean) && settings->viewinggreySc != 0)) { + if ((needJ && CAMBrightCurveJ.dirty) || (needQ && CAMBrightCurveQ.dirty) || (std::isnan(mean) && settings->viewinggreySc != 0)) { if (needJ) { hist16J (32768); @@ -788,7 +785,7 @@ void ImProcFunctions::ciecam_02float (CieImage* ncie, float adap, int pW, int pw #endif - for (int i = 0; i < height; i++) + for (int i = 0; i < height; i++) { for (int j = 0; j < width; j++) { //rough correspondence between L and J float currL = lab->L[i][j] / 327.68f; float koef; //rough correspondence between L and J @@ -849,10 +846,11 @@ void ImProcFunctions::ciecam_02float (CieImage* ncie, float adap, int pW, int pw //hist16Qthr[ (int) (sqrtf ((koef * (lab->L[i][j])) * 32768.f))]++; //for brightness Q : approximation for Q=wh*sqrt(J/100) J not equal L } - sum += koef * lab->L[i][j]; //evaluate mean J to calculate Yb + sum += static_cast(koef) * static_cast(lab->L[i][j]); //evaluate mean J to calculate Yb //sumQ += whestim * sqrt ((koef * (lab->L[i][j])) / 32768.f); //can be used in case of... } + } #ifdef _OPENMP #pragma omp critical @@ -868,8 +866,8 @@ void ImProcFunctions::ciecam_02float (CieImage* ncie, float adap, int pW, int pw } - if (std::isnan (mean)) { - mean = (sum / ((height) * width)) / 327.68f; //for Yb for all image...if one day "pipette" we can adapt Yb for each zone + if (std::isnan(mean)) { + mean = (sum / ((height) * width)) / 327.68; //for Yb for all image...if one day "pipette" we can adapt Yb for each zone } } #ifdef _OPENMP @@ -916,9 +914,9 @@ void ImProcFunctions::ciecam_02float (CieImage* ncie, float adap, int pW, int pw const bool highlight = params->toneCurve.hrenabled; //Get the value if "highlight reconstruction" is activated const int gamu = (params->colorappearance.gamut) ? 1 : 0; - xw = 100.0f * Xw; - yw = 100.0f * Yw; - zw = 100.0f * Zw; + xw = 100.0 * Xw; + yw = 100.0 * Yw; + zw = 100.0 * Zw; float xw1 = 0.f, yw1 = 0.f, zw1 = 0.f, xw2 = 0.f, yw2 = 0.f, zw2 = 0.f; // settings of WB: scene and viewing @@ -1991,8 +1989,8 @@ void ImProcFunctions::moyeqt (Imagefloat* working, float &moyS, float &eqty) { BENCHFUN - int tHh = working->getHeight(); - int tWw = working->getWidth(); + const int height = working->getHeight(); + const int width = working->getWidth(); double moy = 0.0; double sqrs = 0.0; @@ -2000,17 +1998,17 @@ void ImProcFunctions::moyeqt (Imagefloat* working, float &moyS, float &eqty) #pragma omp parallel for reduction(+:moy,sqrs) schedule(dynamic,16) #endif - for (int i = 0; i < tHh; i++) { - for (int j = 0; j < tWw; j++) { - float s = Color::rgb2s (CLIP (working->r (i, j)), CLIP (working->g (i, j)), CLIP (working->b (i, j))); + for (int i = 0; i < height; i++) { + for (int j = 0; j < width; j++) { + const double s = Color::rgb2s(CLIP(working->r (i, j)), CLIP(working->g (i, j)), CLIP(working->b (i, j))); moy += s; - sqrs += SQR (s); + sqrs += SQR(s); } } - moy /= (tHh * tWw); - sqrs /= (tHh * tWw); - eqty = sqrt (sqrs - SQR (moy)); + moy /= (height * width); + sqrs /= (height * width); + eqty = std::sqrt(std::max(sqrs - SQR(moy), 0.0)); moyS = moy; } @@ -2108,17 +2106,17 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer float toxyz[3][3] = { { - static_cast ( wprof[0][0] / Color::D50x), - static_cast ( wprof[0][1] / Color::D50x), - static_cast ( wprof[0][2] / Color::D50x) + static_cast(wprof[0][0] / static_cast(Color::D50x)), + static_cast(wprof[0][1] / static_cast(Color::D50x)), + static_cast(wprof[0][2] / static_cast(Color::D50x)) }, { - static_cast ( wprof[1][0]), - static_cast ( wprof[1][1]), - static_cast ( wprof[1][2]) + static_cast(wprof[1][0]), + static_cast(wprof[1][1]), + static_cast(wprof[1][2]) }, { - static_cast ( wprof[2][0] / Color::D50z), - static_cast ( wprof[2][1] / Color::D50z), - static_cast ( wprof[2][2] / Color::D50z) + static_cast(wprof[2][0] / static_cast(Color::D50z)), + static_cast(wprof[2][1] / static_cast(Color::D50z)), + static_cast(wprof[2][2] / static_cast(Color::D50z)) } }; float maxFactorToxyz = max (toxyz[1][0], toxyz[1][1], toxyz[1][2]); @@ -2238,10 +2236,10 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer const float film_simulation_strength = static_cast (params->filmSimulation.strength) / 100.0f; - const float exp_scale = pow (2.0, expcomp); - const float comp = (max (0.0, expcomp) + 1.0) * hlcompr / 100.0; - const float shoulder = ((65536.0 / max (1.0f, exp_scale)) * (hlcomprthresh / 200.0)) + 0.1; - const float hlrange = 65536.0 - shoulder; + const float exp_scale = pow(2.0, expcomp); + const float comp = (max(0.0, expcomp) + 1.0) * hlcompr / 100.0; + const float shoulder = ((65536.f / max(1.0f, exp_scale)) * (hlcomprthresh / 200.f)) + 0.1f; + const float hlrange = 65536.f - shoulder; const bool isProPhoto = (params->icm.workingProfile == "ProPhoto"); // extracting data from 'params' to avoid cache flush (to be confirmed) ToneCurveMode curveMode = params->toneCurve.curveMode; @@ -2303,43 +2301,43 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer } */ - float RedLow = params->colorToning.redlow / 100.f; - float GreenLow = params->colorToning.greenlow / 100.f; - float BlueLow = params->colorToning.bluelow / 100.f; - float RedMed = params->colorToning.redmed / 100.f; - float GreenMed = params->colorToning.greenmed / 100.f; - float BlueMed = params->colorToning.bluemed / 100.f; - float RedHigh = params->colorToning.redhigh / 100.f; - float GreenHigh = params->colorToning.greenhigh / 100.f; - float BlueHigh = params->colorToning.bluehigh / 100.f; - float SatLow = float (params->colorToning.shadowsColSat.getBottom()) / 100.f; - float SatHigh = float (params->colorToning.hlColSat.getBottom()) / 100.f; + float RedLow = params->colorToning.redlow / 100.0; + float GreenLow = params->colorToning.greenlow / 100.0; + float BlueLow = params->colorToning.bluelow / 100.0; + float RedMed = params->colorToning.redmed / 100.0; + float GreenMed = params->colorToning.greenmed / 100.0; + float BlueMed = params->colorToning.bluemed / 100.0; + float RedHigh = params->colorToning.redhigh / 100.0; + float GreenHigh = params->colorToning.greenhigh / 100.0; + float BlueHigh = params->colorToning.bluehigh / 100.0; + float SatLow = params->colorToning.shadowsColSat.getBottom() / 100.f; + float SatHigh = params->colorToning.hlColSat.getBottom() / 100.f; - float Balan = float (params->colorToning.balance); + float Balan = params->colorToning.balance; - float chMixRR = float (params->chmixer.red[0])/10.f; - float chMixRG = float (params->chmixer.red[1])/10.f; - float chMixRB = float (params->chmixer.red[2])/10.f; - float chMixGR = float (params->chmixer.green[0])/10.f; - float chMixGG = float (params->chmixer.green[1])/10.f; - float chMixGB = float (params->chmixer.green[2])/10.f; - float chMixBR = float (params->chmixer.blue[0])/10.f; - float chMixBG = float (params->chmixer.blue[1])/10.f; - float chMixBB = float (params->chmixer.blue[2])/10.f; + float chMixRR = params->chmixer.red[0] / 10.f; + float chMixRG = params->chmixer.red[1] / 10.f; + float chMixRB = params->chmixer.red[2] / 10.f; + float chMixGR = params->chmixer.green[0] / 10.f; + float chMixGG = params->chmixer.green[1] / 10.f; + float chMixGB = params->chmixer.green[2] / 10.f; + float chMixBR = params->chmixer.blue[0] / 10.f; + float chMixBG = params->chmixer.blue[1] / 10.f; + float chMixBB = params->chmixer.blue[2] / 10.f; bool blackwhite = params->blackwhite.enabled; bool complem = params->blackwhite.enabledcc; - float bwr = float (params->blackwhite.mixerRed); - float bwg = float (params->blackwhite.mixerGreen); - float bwb = float (params->blackwhite.mixerBlue); - float bwrgam = float (params->blackwhite.gammaRed); - float bwggam = float (params->blackwhite.gammaGreen); - float bwbgam = float (params->blackwhite.gammaBlue); - float mixerOrange = float (params->blackwhite.mixerOrange); - float mixerYellow = float (params->blackwhite.mixerYellow); - float mixerCyan = float (params->blackwhite.mixerCyan); - float mixerMagenta = float (params->blackwhite.mixerMagenta); - float mixerPurple = float (params->blackwhite.mixerPurple); + float bwr = params->blackwhite.mixerRed; + float bwg = params->blackwhite.mixerGreen; + float bwb = params->blackwhite.mixerBlue; + float bwrgam = params->blackwhite.gammaRed; + float bwggam = params->blackwhite.gammaGreen; + float bwbgam = params->blackwhite.gammaBlue; + float mixerOrange = params->blackwhite.mixerOrange; + float mixerYellow = params->blackwhite.mixerYellow; + float mixerCyan = params->blackwhite.mixerCyan; + float mixerMagenta = params->blackwhite.mixerMagenta; + float mixerPurple = params->blackwhite.mixerPurple; int algm = 0; if (params->blackwhite.method == "Desaturation") { @@ -2720,7 +2718,7 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer //HSV equalizer if (hCurveEnabled) { - h = (hCurve->getVal (double (h)) - 0.5) * 2.f + h; + h = (hCurve->getVal(h) - 0.5) * 2.0 + static_cast(h); if (h > 1.0f) { h -= 1.0f; @@ -2751,7 +2749,7 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer } //shift value - float valparam = vCurve->getVal ((double)h) - 0.5f; + float valparam = vCurve->getVal(h) - 0.5; valparam *= (1.f - SQR (SQR (1.f - min (s, 1.0f)))); if (valparam > 0.00001f) { @@ -3063,7 +3061,7 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer if (bwlCurveEnabled) { L /= 32768.f; double hr = Color::huelab_to_huehsv2 (HH); - float valparam = float ((bwlCurve->getVal (hr) - 0.5f) * 2.0f); //get l_r=f(H) + float valparam = (bwlCurve->getVal(hr) - 0.5) * 2.0; //get l_r=f(H) float kcc = (CC / 70.f); //take Chroma into account...70 "middle" of chromaticity (arbitrary and simple), one can imagine other algorithme //reduct action for low chroma and increase action for high chroma valparam *= kcc; @@ -3317,9 +3315,9 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer for (int i = 0; i < tH; i++) { for (int j = 0; j < tW; j++) { - nr += tmpImage->r (i, j); - ng += tmpImage->g (i, j); - nb += tmpImage->b (i, j); + nr += static_cast(tmpImage->r(i, j)); + ng += static_cast(tmpImage->g(i, j)); + nb += static_cast(tmpImage->b(i, j)); } } @@ -3660,7 +3658,8 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer delete vCurve; } - shadowsHighlights(lab); + // shadowsHighlights(lab); + shadowsHighlights(lab, params->sh.enabled, params->sh.lab,params->sh.highlights ,params->sh.shadows, params->sh.radius, scale, params->sh.htonalwidth, params->sh.stonalwidth); if (params->localContrast.enabled) { // Alberto's local contrast @@ -4385,8 +4384,7 @@ void ImProcFunctions::chromiLuminanceCurve (PipetteBuffer *pipetteBuffer, int pW float factnoise = 1.f; if (params->dirpyrDenoise.enabled) { - factnoise = (1.f + params->dirpyrDenoise.chroma / 500.f); //levels=5 -// if(yyyy) factnoise=(1.f+params->dirpyrDenoise.chroma/100.f);//levels=7 + factnoise = 1.0 + params->dirpyrDenoise.chroma / 500.0; //levels=5 } const float scaleConst = 100.0f / 100.1f; @@ -4564,7 +4562,7 @@ void ImProcFunctions::chromiLuminanceCurve (PipetteBuffer *pipetteBuffer, int pW float l_r;//Luminance Lab in 0..1 l_r = Lprov1 / 100.f; { - float valparam = float ((lhCurve->getVal (Color::huelab_to_huehsv2 (HH)) - 0.5f)); //get l_r=f(H) + float valparam = lhCurve->getVal(Color::huelab_to_huehsv2(HH)) - 0.5; //get l_r=f(H) float valparamneg; valparamneg = valparam; float kcc = (CC / amountchroma); //take Chroma into account...40 "middle low" of chromaticity (arbitrary and simple), one can imagine other algorithme @@ -4597,9 +4595,9 @@ void ImProcFunctions::chromiLuminanceCurve (PipetteBuffer *pipetteBuffer, int pW float fx = (0.002f * aprov1) + fy; float fz = fy - (0.005f * bprov1); - float x_ = 65535.0f * Color::f2xyz (fx) * Color::D50x; - float z_ = 65535.0f * Color::f2xyz (fz) * Color::D50z; - float y_ = (Lprov1 > Color::epskap) ? 65535.0 * fy * fy * fy : 65535.0 * Lprov1 / Color::kappa; + float x_ = 65535.f * Color::f2xyz (fx) * Color::D50x; + float z_ = 65535.f * Color::f2xyz (fz) * Color::D50z; + float y_ = Lprov1 > Color::epskapf ? 65535.f * fy * fy * fy : 65535.f * Lprov1 / Color::kappaf; float R, G, B; Color::xyz2rgb (x_, y_, z_, R, G, B, wip); @@ -4627,7 +4625,7 @@ void ImProcFunctions::chromiLuminanceCurve (PipetteBuffer *pipetteBuffer, int pW // calculate C=f(H) if (chutili) { double hr = Color::huelab_to_huehsv2 (HH); - float chparam = float ((chCurve->getVal (hr) - 0.5f) * 2.0f); //get C=f(H) + float chparam = (chCurve->getVal(hr) - 0.5) * 2.0; //get C=f(H) float chromaChfactor = 1.0f + chparam; atmp *= chromaChfactor;//apply C=f(H) btmp *= chromaChfactor; @@ -4635,9 +4633,9 @@ void ImProcFunctions::chromiLuminanceCurve (PipetteBuffer *pipetteBuffer, int pW if (hhutili) { // H=f(H) //hue Lab in -PI +PI - float valparam = float ((hhCurve->getVal (Color::huelab_to_huehsv2 (HH)) - 0.5f) * 1.7f) + HH; //get H=f(H) 1.7 optimisation ! + float valparam = (hhCurve->getVal(Color::huelab_to_huehsv2(HH)) - 0.5) * 1.7 + static_cast(HH); //get H=f(H) 1.7 optimisation ! HH = valparam; - sincosval = xsincosf (HH); + sincosval = xsincosf(HH); } if (!bwToning) { @@ -4713,11 +4711,11 @@ void ImProcFunctions::chromiLuminanceCurve (PipetteBuffer *pipetteBuffer, int pW deltaHH = protect_redhcur; //transition hue - if (chromaCfactor > 0.0) { + if (chromaCfactor > 0.f) { Color::scalered ( rstprotection, chromaCfactor, 0.0, HH, deltaHH, scale, scaleext); //1.0 } - if (chromaCfactor > 1.0) { + if (chromaCfactor > 1.f) { float interm = (chromaCfactor - 1.0f) * 100.0f; factorskin = 1.0f + (interm * scale) / 100.0f; factorskinext = 1.0f + (interm * scaleext) / 100.0f; @@ -4774,11 +4772,11 @@ void ImProcFunctions::chromiLuminanceCurve (PipetteBuffer *pipetteBuffer, int pW deltaHH = protect_redhcur; //transition hue - if (chromaCfactor > 0.0) { + if (chromaCfactor > 0.f) { Color::scalered ( rstprotection, chromaCfactor, 0.0, HH, deltaHH, scale, scaleext); //1.0 } - if (chromaCfactor > 1.0) { + if (chromaCfactor > 1.f) { float interm = (chromaCfactor - 1.0f) * 100.0f; factorskin = 1.0f + (interm * scale) / 100.0f; factorskinext = 1.0f + (interm * scaleext) / 100.0f; @@ -5061,7 +5059,7 @@ void ImProcFunctions::impulsedenoise (LabImage* lab) if (params->impulseDenoise.enabled && lab->W >= 8 && lab->H >= 8) { - impulse_nr (lab, (float)params->impulseDenoise.thresh / 20.0 ); + impulse_nr(lab, params->impulseDenoise.thresh / 20.0); } } @@ -5071,7 +5069,7 @@ void ImProcFunctions::impulsedenoisecam (CieImage* ncie, float **buffers[3]) if (params->impulseDenoise.enabled && ncie->W >= 8 && ncie->H >= 8) { - impulse_nrcam (ncie, (float)params->impulseDenoise.thresh / 20.0, buffers ); + impulse_nrcam(ncie, params->impulseDenoise.thresh / 20.0, buffers); } } @@ -5141,11 +5139,11 @@ void ImProcFunctions::EPDToneMapCIE (CieImage *ncie, float a_w, float c_, int Wi float sca = params->epd.scale; float gamm = params->epd.gamma; float rew = params->epd.reweightingIterates; - float Qpro = ( 4.0 / c_) * ( a_w + 4.0 ) ; //estimate Q max if J=100.0 + float Qpro = (4.f / c_) * (a_w + 4.f) ; //estimate Q max if J=100.0 float *Qpr = ncie->Q_p[0]; if (settings->verbose) { - printf ("minQ=%f maxQ=%f Qpro=%f\n", minQ, maxQ, Qpro); + printf ("minQ=%f maxQ=%f Qpro=%f\n", static_cast(minQ), static_cast(maxQ), static_cast(Qpro)); } if (maxQ > Qpro) { @@ -5172,7 +5170,7 @@ void ImProcFunctions::EPDToneMapCIE (CieImage *ncie, float a_w, float c_, int Wi //Auto select number of iterates. Note that p->EdgeStopping = 0 makes a Gaussian blur. if (Iterates == 0) { - Iterates = (unsigned int) (edgest * 15.0); + Iterates = edgest * 15.f; } //Jacques Desmis : always Iterates=5 for compatibility images between preview and output @@ -5399,7 +5397,7 @@ void ImProcFunctions::getAutoExp (const LUTu &histogram, int histcompr, double octile[count] += histogram[j]; if (octile[count] > sum / 8.f || (count == 7 && octile[count] > sum / 16.f)) { - octile[count] = xlog (1. + j) / log (2.f); + octile[count] = xlog(1. + j) / log(2.0); count++;// = min(count+1,7); } } @@ -5412,7 +5410,7 @@ void ImProcFunctions::getAutoExp (const LUTu &histogram, int histcompr, double octile[count] += histogram[j]; if (octile[count] > sum / 8.f || (count == 7 && octile[count] > sum / 16.f)) { - octile[count] = xlog (1. + j) / log (2.f); + octile[count] = xlog(1. + j) / log(2.0); count++;// = min(count+1,7); } } @@ -5487,7 +5485,7 @@ void ImProcFunctions::getAutoExp (const LUTu &histogram, int histcompr, double } //compute clipped white point - unsigned int clippable = (int) (sum * clip / 100.f ); + unsigned int clippable = (int) (static_cast(sum) * clip / 100.0 ); clipped = 0; int whiteclip = (imax) - 1; @@ -5546,8 +5544,8 @@ void ImProcFunctions::getAutoExp (const LUTu &histogram, int histcompr, double hlcomprthresh = 0; //this is a series approximation of the actual formula for comp, //which is a transcendental equation - float comp = (gain * ((float)whiteclip) / scale - 1.f) * 2.3f; // 2.3 instead of 2 to increase slightly comp - hlcompr = (int) (100.*comp / (max (0.0, expcomp) + 1.0)); + double comp = (gain * whiteclip / scale - 1.f) * 2.3f; // 2.3 instead of 2 to increase slightly comp + hlcompr = 100.0 * comp / (max(0.0, expcomp) + 1.0); hlcompr = max (0, min (100, hlcompr)); //now find brightness if gain didn't bring ave to midgray using @@ -5555,9 +5553,9 @@ void ImProcFunctions::getAutoExp (const LUTu &histogram, int histcompr, double float midtmp = gain * sqrt (median * ave) / scale; if (midtmp < 0.1f) { - bright = (midgray - midtmp) * 15.0 / (midtmp); + bright = (midgray - midtmp) * 15.f / (midtmp); } else { - bright = (midgray - midtmp) * 15.0 / (0.10833 - 0.0833 * midtmp); + bright = (midgray - midtmp) * 15.f / (0.10833f - 0.0833f * midtmp); } bright = 0.25 */*(median/ave)*(hidev/lodev)*/max (0, bright); @@ -5566,7 +5564,7 @@ void ImProcFunctions::getAutoExp (const LUTu &histogram, int histcompr, double contr = (int) 50.0f * (1.1f - ospread); contr = max (0, min (100, contr)); //take gamma into account - double whiteclipg = (int) (CurveFactory::gamma2 (whiteclip * corr / 65536.0) * 65536.0); + double whiteclipg = (int) (CurveFactory::gamma2(whiteclip * static_cast(corr) / 65536.0) * 65536.0); float gavg = 0.; @@ -5588,7 +5586,7 @@ void ImProcFunctions::getAutoExp (const LUTu &histogram, int histcompr, double } } - whiteclipg = CurveFactory::igamma2 ((float) (whiteclipg / 65535.0)) * 65535.0; //need to inverse gamma transform to get correct exposure compensation parameter + whiteclipg = CurveFactory::igamma2(whiteclipg / 65535.0) * 65535.0; //need to inverse gamma transform to get correct exposure compensation parameter //correction with gamma black = (int) ((65535 * black) / whiteclipg); @@ -5823,8 +5821,8 @@ void ImProcFunctions::lab2rgb (const LabImage &src, Imagefloat &dst, const Glib: */ void ImProcFunctions::colorToningLabGrid(LabImage *lab, int xstart, int xend, int ystart, int yend, bool MultiThread) { - const float factor = ColorToningParams::LABGRID_CORR_MAX * 3.f; - const float scaling = ColorToningParams::LABGRID_CORR_SCALE; + const double factor = ColorToningParams::LABGRID_CORR_MAX * 3.0; + const double scaling = ColorToningParams::LABGRID_CORR_SCALE; float a_scale = (params->colorToning.labgridAHigh - params->colorToning.labgridALow) / factor / scaling; float a_base = params->colorToning.labgridALow / scaling; float b_scale = (params->colorToning.labgridBHigh - params->colorToning.labgridBLow) / factor / scaling; diff --git a/rtengine/improcfun.h b/rtengine/improcfun.h index 8f4ae7771..d003df644 100644 --- a/rtengine/improcfun.h +++ b/rtengine/improcfun.h @@ -19,11 +19,17 @@ #pragma once #include +#include #include "coord2d.h" #include "gamutwarning.h" -#include "pipettebuffer.h" +namespace Glib +{ + +class ustring; + +} template class LUT; @@ -44,8 +50,10 @@ class FramesMetaData; class LensCorrection; class NoiseCurve; class OpacityCurve; +class PipetteBuffer; class ToneCurve; class WavCurve; +class Wavblcurve; class WavOpacityCurveBY; class WavOpacityCurveRG; class WavOpacityCurveW; @@ -180,6 +188,7 @@ public: void EPDToneMapResid(float * WavCoeffs_L0, unsigned int Iterates, int skip, struct cont_params& cp, int W_L, int H_L, float max0, float min0); void CompressDR(float *Source, int W_L, int H_L, float Compression, float DetailBoost); + void Compresslevels2(float **Source, int W_L, int H_L, float compression, float detailattenuator, float thres, float mean, float maxp, float meanN, float maxN, float madL); void ContrastResid(float * WavCoeffs_L0, struct cont_params &cp, int W_L, int H_L, float max0, float min0); void EPDToneMap(LabImage *lab, unsigned int Iterates = 0, int skip = 1); @@ -193,30 +202,33 @@ public: int pitch, int scale, const int luma, const int chroma/*, LUTf & Lcurve, LUTf & abcurve*/); void Tile_calc(int tilesize, int overlap, int kall, int imwidth, int imheight, int &numtiles_W, int &numtiles_H, int &tilewidth, int &tileheight, int &tileWskip, int &tileHskip); - void ip_wavelet(LabImage * lab, LabImage * dst, int kall, const procparams::WaveletParams & waparams, const WavCurve & wavCLVCcurve, const WavOpacityCurveRG & waOpacityCurveRG, const WavOpacityCurveBY & waOpacityCurveBY, const WavOpacityCurveW & waOpacityCurveW, const WavOpacityCurveWL & waOpacityCurveWL, LUTf &wavclCurve, int skip); + void ip_wavelet(LabImage * lab, LabImage * dst, int kall, const procparams::WaveletParams & waparams, const WavCurve & wavCLVCcurve, const Wavblcurve & wavblcurve, const WavOpacityCurveRG & waOpacityCurveRG, const WavOpacityCurveBY & waOpacityCurveBY, const WavOpacityCurveW & waOpacityCurveW, const WavOpacityCurveWL & waOpacityCurveWL, const LUTf &wavclCurve, int skip); - void WaveletcontAllL(LabImage * lab, float **varhue, float **varchrom, wavelet_decomposition &WaveletCoeffs_L, + void WaveletcontAllL(LabImage * lab, float **varhue, float **varchrom, const wavelet_decomposition &WaveletCoeffs_L, const Wavblcurve & wavblcurve, struct cont_params &cp, int skip, float *mean, float *sigma, float *MaxP, float *MaxN, const WavCurve & wavCLVCcurve, const WavOpacityCurveW & waOpacityCurveW, FlatCurve* ChCurve, bool Chutili); - void WaveletcontAllLfinal(wavelet_decomposition &WaveletCoeffs_L, struct cont_params &cp, float *mean, float *sigma, float *MaxP, const WavOpacityCurveWL & waOpacityCurveWL); - void WaveletcontAllAB(LabImage * lab, float **varhue, float **varchrom, wavelet_decomposition &WaveletCoeffs_a, const WavOpacityCurveW & waOpacityCurveW, - struct cont_params &cp, const bool useChannelA); - void WaveletAandBAllAB(wavelet_decomposition &WaveletCoeffs_a, wavelet_decomposition &WaveletCoeffs_b, - struct cont_params &cp, FlatCurve* hhcurve, bool hhutili); + void WaveletcontAllLfinal(const wavelet_decomposition &WaveletCoeffs_L, const cont_params &cp, float *mean, float *sigma, float *MaxP, const WavOpacityCurveWL & waOpacityCurveWL); + void WaveletcontAllAB(LabImage * lab, float **varhue, float **varchrom, const wavelet_decomposition &WaveletCoeffs_a, const Wavblcurve & wavblcurve, const WavOpacityCurveW & waOpacityCurveW, + struct cont_params &cp, const bool useChannelA, int skip, float *meanab, float *sigmaab); + void WaveletAandBAllAB(const wavelet_decomposition &WaveletCoeffs_a, const wavelet_decomposition &WaveletCoeffs_b, + const cont_params &cp, FlatCurve* hhcurve, bool hhutili); void ContAllL(float **koeLi, float *maxkoeLi, bool lipschitz, int maxlvl, LabImage * lab, float **varhue, float **varchrom, float ** WavCoeffs_L, float * WavCoeffs_L0, int level, int dir, struct cont_params &cp, int W_L, int H_L, int skip, float *mean, float *sigma, float *MaxP, float *MaxN, const WavCurve & wavCLVCcurve, const WavOpacityCurveW & waOpacityCurveW, FlatCurve* ChCurve, bool Chutili); - void finalContAllL(float ** WavCoeffs_L, float * WavCoeffs_L0, int level, int dir, struct cont_params &cp, + void finalContAllL(float ** WavCoeffs_L, float * WavCoeffs_L0, int level, int dir, const cont_params &cp, int W_L, int H_L, float *mean, float *sigma, float *MaxP, const WavOpacityCurveWL & waOpacityCurveWL); void ContAllAB(LabImage * lab, int maxlvl, float **varhue, float **varchrom, float ** WavCoeffs_a, float * WavCoeffs_a0, int level, int dir, const WavOpacityCurveW & waOpacityCurveW, struct cont_params &cp, int W_ab, int H_ab, const bool useChannelA); - void Evaluate2(wavelet_decomposition &WaveletCoeffs_L, + void Evaluate2(const wavelet_decomposition &WaveletCoeffs_L, float *mean, float *meanN, float *sigma, float *sigmaN, float *MaxP, float *MaxN); void Eval2(float ** WavCoeffs_L, int level, int W_L, int H_L, float *mean, float *meanN, float *sigma, float *sigmaN, float *MaxP, float *MaxN); + void calceffect(int level, float *mean, float *sigma, float *mea, float effect, float offs); + void Aver(float * HH_Coeffs, int datalen, float &averagePlus, float &averageNeg, float &max, float &min); void Sigma(float * HH_Coeffs, int datalen, float averagePlus, float averageNeg, float &sigmaPlus, float &sigmaNeg); - void calckoe(float ** WavCoeffs_LL, const struct cont_params& cp, float ** koeLi, int level, int dir, int W_L, int H_L, float edd, float *maxkoeLi, float **tmC = nullptr); + void calckoe(float ** WavCoeffs_LL, const cont_params& cp, float ** koeLi, int level, int dir, int W_L, int H_L, float edd, float *maxkoeLi, float **tmC = nullptr); + void softproc2(const LabImage* bufcolorig, const LabImage* bufcolfin, float rad, int bfh, int bfw, double epsilmax, double epsilmin, float thres, int sk, bool multiThread, int flag); void Median_Denoise(float **src, float **dst, int width, int height, Median medianType, int iterations, int numThreads, float **buffer = nullptr); @@ -226,18 +238,22 @@ public: void RGB_denoise_info(Imagefloat * src, Imagefloat * provicalc, bool isRAW, const LUTf &gamcurve, float gam, float gamthresh, float gamslope, const procparams::DirPyrDenoiseParams & dnparams, const double expcomp, float &chaut, int &Nb, float &redaut, float &blueaut, float &maxredaut, float & maxblueaut, float &minredaut, float & minblueaut, float &chromina, float &sigma, float &lumema, float &sigma_L, float &redyel, float &skinc, float &nsknc, bool multiThread = false); void RGBtile_denoise(float * fLblox, int hblproc, float noisevar_Ldetail); //for DCT void RGBoutput_tile_row(float *bloxrow_L, float ** Ldetail, float ** tilemask_out, int height, int width, int top); - bool WaveletDenoiseAllL(const wavelet_decomposition &WaveletCoeffs_L, float *noisevarlum, float madL[8][3], float * vari, int edge); - bool WaveletDenoiseAllAB(const wavelet_decomposition &WaveletCoeffs_L, const wavelet_decomposition &WaveletCoeffs_ab, float *noisevarchrom, float madL[8][3], float noisevar_ab, const bool useNoiseCCurve, bool autoch, bool denoiseMethodRgb); + void WaveletDenoiseAll_info(int levwav, const wavelet_decomposition &WaveletCoeffs_a, const wavelet_decomposition &WaveletCoeffs_b, float **noisevarlum, float **noisevarchrom, float **noisevarhue, float &chaut, int &Nb, float &redaut, float &blueaut, float &maxredaut, float &maxblueaut, float &minredaut, float & minblueaut, int schoice, float &chromina, float &sigma, float &lumema, float &sigma_L, float &redyel, float &skinc, float &nsknc, float &maxchred, float &maxchblue, float &minchred, float &minchblue, int &nb, float &chau, float &chred, float &chblue, bool denoiseMethodRgb); - bool WaveletDenoiseAll_BiShrinkL(const wavelet_decomposition &WaveletCoeffs_L, float *noisevarlum, float madL[8][3]); - bool WaveletDenoiseAll_BiShrinkAB(const wavelet_decomposition &WaveletCoeffs_L, const wavelet_decomposition &WaveletCoeffs_ab, float *noisevarchrom, float madL[8][3], float noisevar_ab, - const bool useNoiseCCurve, bool autoch, bool denoiseMethodRgb); + bool WaveletDenoiseAllL(const wavelet_decomposition &WaveletCoeffs_L, float *noisevarlum, float madL[8][3], float * vari, int edge, int denoiseNestedLevels); + bool WaveletDenoiseAllAB(const wavelet_decomposition &WaveletCoeffs_L, const wavelet_decomposition &WaveletCoeffs_ab, float *noisevarchrom, float madL[8][3], float *variC, int local, float noisevar_ab, const bool useNoiseCCurve, bool autoch, bool denoiseMethodRgb, int denoiseNestedLevels); + + bool WaveletDenoiseAll_BiShrinkL(const wavelet_decomposition &WaveletCoeffs_L, float *noisevarlum, float madL[8][3], float * vari, int edge, int denoiseNestedLevels); + bool WaveletDenoiseAll_BiShrinkAB(const wavelet_decomposition &WaveletCoeffs_L, const wavelet_decomposition &WaveletCoeffs_ab, float *noisevarchrom, float madL[8][3], float *variC, int local, float noisevar_ab, const bool useNoiseCCurve, bool autoch, bool denoiseMethodRgb, int denoiseNestedLevels); + void ShrinkAllL(const wavelet_decomposition &WaveletCoeffs_L, float **buffer, int level, int dir, float *noisevarlum, float * madL, float * vari, int edge); void ShrinkAllAB(const wavelet_decomposition &WaveletCoeffs_L, const wavelet_decomposition &WaveletCoeffs_ab, float **buffer, int level, int dir, - float *noisevarchrom, float noisevar_ab, const bool useNoiseCCurve, bool autoch, bool denoiseMethodRgb, float * madL, float * madaab = nullptr, bool madCalculated = false); + float *noisevarchrom, float noisevar_ab, const bool useNoiseCCurve, bool autoch, bool denoiseMethodRgb, float * madL, float * variC, int local, float * madaab = nullptr, bool madCalculated = false); + + void ShrinkAll_info(float ** WavCoeffs_a, float ** WavCoeffs_b, int W_ab, int H_ab, float **noisevarlum, float **noisevarchrom, float **noisevarhue, float &chaut, int &Nb, float &redaut, float &blueaut, float &maxredaut, float &maxblueaut, float &minredaut, float &minblueaut, int schoice, int lvl, float &chromina, float &sigma, float &lumema, float &sigma_L, float &redyel, float &skinc, float &nsknc, float &maxchred, float &maxchblue, float &minchred, float &minchblue, int &nb, float &chau, float &chred, float &chblue, bool denoiseMethodRgb); @@ -263,7 +279,8 @@ public: void ToneMapFattal02(Imagefloat *rgb); void localContrast(LabImage *lab); void colorToningLabGrid(LabImage *lab, int xstart, int xend, int ystart, int yend, bool MultiThread); - void shadowsHighlights(LabImage *lab); + //void shadowsHighlights(LabImage *lab); + void shadowsHighlights(LabImage *lab, bool ena, int labmode, int hightli, int shado, int rad, int scal, int hltonal, int shtonal); void softLight(LabImage *lab); void labColorCorrectionRegions(LabImage *lab); diff --git a/rtengine/ipdehaze.cc b/rtengine/ipdehaze.cc index 28a0f2d57..53939b5c0 100644 --- a/rtengine/ipdehaze.cc +++ b/rtengine/ipdehaze.cc @@ -32,6 +32,7 @@ #include #include +#include "array2D.h" #include "color.h" #include "guidedfilter.h" #include "iccstore.h" @@ -240,9 +241,9 @@ float estimate_ambient_light(const array2D &R, const array2D &G, c float g = G[y][x]; float b = B[y][x]; if (r + g + b >= bright_lim) { - rr += r; - gg += g; - bb += b; + rr += static_cast(r); + gg += static_cast(g); + bb += static_cast(b); ++n; } } diff --git a/rtengine/iplabregions.cc b/rtengine/iplabregions.cc index 6526419f5..786d42e56 100644 --- a/rtengine/iplabregions.cc +++ b/rtengine/iplabregions.cc @@ -139,7 +139,7 @@ BENCHFUN auto &hm = hmask[i]; auto &cm = cmask[i]; auto &lm = lmask[i]; - float blend = LIM01((hm ? hm->getVal(h) : 1.f) * (cm ? cm->getVal(c) : 1.f) * (lm ? lm->getVal(l) : 1.f)); + float blend = LIM01((hm ? hm->getVal(h) : 1.0) * (cm ? cm->getVal(c) : 1.0) * (lm ? lm->getVal(l) : 1.0)); Lmask[i][y][x] = abmask[i][y][x] = blend; } } @@ -147,8 +147,8 @@ BENCHFUN } for (int i = begin_idx; i < end_idx; ++i) { - float blur = params->colorToning.labregions[i].maskBlur; - blur = blur < 0.f ? -1.f/blur : 1.f + blur; + double blur = params->colorToning.labregions[i].maskBlur; + blur = blur < 0.0 ? -1.0 / blur : 1.0 + blur; int r1 = max(int(4 / scale * blur + 0.5), 1); int r2 = max(int(25 / scale * blur + 0.5), 1); rtengine::guidedFilter(guide, abmask[i], abmask[i], r1, 0.001, multiThread); @@ -188,7 +188,7 @@ BENCHFUN auto &r = params->colorToning.labregions[i]; abca[i] = abcoord(r.a); abcb[i] = abcoord(r.b); - rs[i] = 1.f + r.saturation / (SGN(r.saturation) > 0 ? 50.f : 100.f); + rs[i] = 1.0 + r.saturation / (SGN(r.saturation) > 0 ? 50.0 : 100.0); slope[i] = r.slope; offset[i] = r.offset; power[i] = r.power; diff --git a/rtengine/ipretinex.cc b/rtengine/ipretinex.cc index 84f33482f..6768eca93 100644 --- a/rtengine/ipretinex.cc +++ b/rtengine/ipretinex.cc @@ -110,8 +110,8 @@ void mean_stddv2( float **dst, float &mean, float &stddv, int W_L, int H_L, floa for (int i = 0; i < H_L; i++ ) for (int j = 0; j < W_L; j++) { - sum += dst[i][j]; - vsquared += (dst[i][j] * dst[i][j]); + sum += static_cast(dst[i][j]); + vsquared += rtengine::SQR(dst[i][j]); lmax = dst[i][j] > lmax ? dst[i][j] : lmax; lmin = dst[i][j] < lmin ? dst[i][j] : lmin; @@ -128,8 +128,8 @@ void mean_stddv2( float **dst, float &mean, float &stddv, int W_L, int H_L, floa } mean = sum / (double) (W_L * H_L); vsquared /= (double) W_L * H_L; - stddv = ( vsquared - (mean * mean) ); - stddv = (float)sqrt(stddv); + stddv = vsquared - rtengine::SQR(mean); + stddv = std::sqrt(stddv); } } @@ -678,9 +678,9 @@ BENCHFUN float valparam; if(useHsl || useHslLin) { - valparam = shcurve->getVal(HH) - 0.5f; + valparam = shcurve->getVal(HH) - 0.5; } else { - valparam = shcurve->getVal(Color::huelab_to_huehsv2(HH)) - 0.5f; + valparam = shcurve->getVal(Color::huelab_to_huehsv2(HH)) - 0.5; } str *= (1.f + 2.f * valparam); diff --git a/rtengine/ipshadowshighlights.cc b/rtengine/ipshadowshighlights.cc index 5c5b6b324..0eb3df9c5 100644 --- a/rtengine/ipshadowshighlights.cc +++ b/rtengine/ipshadowshighlights.cc @@ -31,22 +31,22 @@ #include "procparams.h" #include "sleef.h" -namespace rtengine +namespace rtengine { +//modifications to pass parameters needs by locallab, to avoid 2 functions - no change in process - J.Desmis march 2019 +void ImProcFunctions::shadowsHighlights(LabImage *lab, bool ena, int labmode, int hightli, int shado, int rad, int scal, int hltonal, int shtonal) { - -void ImProcFunctions::shadowsHighlights(LabImage *lab) -{ - if (!params->sh.enabled || (!params->sh.highlights && !params->sh.shadows)){ + if (!ena || (!hightli && !shado)){ return; } const int width = lab->W; const int height = lab->H; - const bool lab_mode = params->sh.lab; + const bool lab_mode = labmode; array2D mask(width, height); array2D L(width, height); - const float radius = float(params->sh.radius) * 10 / scale; +// const float radius = params->sh.radius * 10 / scale; + const float radius = float(rad) * 10 / scal; LUTf f(lab_mode ? 32768 : 65536); TMatrix ws = ICCStore::getInstance()->workingSpaceMatrix(params->icm.workingProfile); @@ -193,12 +193,12 @@ void ImProcFunctions::shadowsHighlights(LabImage *lab) } }; - if (params->sh.highlights > 0) { - apply(params->sh.highlights * 0.7, params->sh.htonalwidth, true); + if (hightli > 0) { + apply(hightli * 0.7, hltonal, true); } - if (params->sh.shadows > 0) { - apply(params->sh.shadows * 0.6, params->sh.stonalwidth, false); + if (shado > 0) { + apply(shado * 0.6, shtonal, false); } } diff --git a/rtengine/ipsharpen.cc b/rtengine/ipsharpen.cc index 7198b76c5..0e46cd596 100644 --- a/rtengine/ipsharpen.cc +++ b/rtengine/ipsharpen.cc @@ -103,7 +103,7 @@ void sharpenHaloCtrl (float** luminance, float** blurmap, float** base, float** void dcdamping (float** aI, float** aO, float damping, int W, int H) { - const float dampingFac = -2.0 / (damping * damping); + const float dampingFac = -2.f / (damping * damping); #ifdef __SSE2__ vfloat Iv, Ov, Uv, zerov, onev, fourv, fivev, dampingFacv, Tv, Wv, Lv; @@ -163,7 +163,7 @@ namespace rtengine void ImProcFunctions::deconvsharpening (float** luminance, float** tmp, const float * const * blend, int W, int H, const procparams::SharpeningParams &sharpenParam, double Scale) { - if (sharpenParam.deconvamount == 0 && sharpenParam.blurradius < 0.25f) { + if (sharpenParam.deconvamount == 0 && sharpenParam.blurradius < 0.25) { return; } BENCHFUN @@ -180,7 +180,7 @@ BENCHFUN JaggedArray* blurbuffer = nullptr; - if (sharpenParam.blurradius >= 0.25f) { + if (sharpenParam.blurradius >= 0.25) { blurbuffer = new JaggedArray(W, H); JaggedArray &blur = *blurbuffer; #ifdef _OPENMP @@ -229,7 +229,7 @@ BENCHFUN } } - if (sharpenParam.blurradius >= 0.25f) { + if (sharpenParam.blurradius >= 0.25) { JaggedArray &blur = *blurbuffer; #ifdef _OPENMP #pragma omp for @@ -255,7 +255,7 @@ void ImProcFunctions::sharpening (LabImage* lab, const procparams::SharpeningPar // calculate contrast based blend factors to reduce sharpening in regions with low contrast JaggedArray blend(W, H); - float contrast = sharpenParam.contrast / 100.f; + float contrast = sharpenParam.contrast / 100.0; buildBlendMask(lab->L, blend, W, H, contrast); if(showMask) { @@ -292,7 +292,7 @@ BENCHFUN JaggedArray blur(W, H); - if (sharpenParam.blurradius >= 0.25f) { + if (sharpenParam.blurradius >= 0.25) { #ifdef _OPENMP #pragma omp parallel #endif @@ -372,7 +372,7 @@ BENCHFUN delete [] b3; } - if (sharpenParam.blurradius >= 0.25f) { + if (sharpenParam.blurradius >= 0.25) { #ifdef _OPENMP #pragma omp parallel for #endif @@ -385,241 +385,6 @@ BENCHFUN } -// To the extent possible under law, Manuel Llorens -// has waived all copyright and related or neighboring rights to this work. -// This work is published from: Spain. - -// Thanks to Manuel for this excellent job (Jacques Desmis JDC or frej83) -void ImProcFunctions::MLsharpen (LabImage* lab) -{ - // JD: this algorithm maximize clarity of images; it does not play on accutance. It can remove (partially) the effects of the AA filter) - // I think we can use this algorithm alone in most cases, or first to clarify image and if you want a very little USM (unsharp mask sharpening) after... - if (!params->sharpenEdge.enabled) { - return; - } - - MyTime t1e, t2e; - t1e.set(); - - int offset, c, i, j, p, width2; - int width = lab->W, height = lab->H; - float *L, lumH, lumV, lumD1, lumD2, v, contrast, s; - float difL, difR, difT, difB, difLT, difRB, difLB, difRT, wH, wV, wD1, wD2, chmax[3]; - float f1, f2, f3, f4; - float templab; - int iii, kkk; - width2 = 2 * width; - const float epsil = 0.01f; //prevent divide by zero - const float eps2 = 0.001f; //prevent divide by zero - float amount; - amount = params->sharpenEdge.amount / 100.0f; - - if (amount < 0.00001f) { - return; - } - - if (settings->verbose) { - printf ("SharpenEdge amount %f\n", amount); - } - - L = new float[width * height]; - - chmax[0] = 8.0f; - chmax[1] = 3.0f; - chmax[2] = 3.0f; - - int channels; - - if (params->sharpenEdge.threechannels) { - channels = 0; - } else { - channels = 2; - } - - if (settings->verbose) { - printf ("SharpenEdge channels %d\n", channels); - } - - int passes = params->sharpenEdge.passes; - - if (settings->verbose) { - printf ("SharpenEdge passes %d\n", passes); - } - - for (p = 0; p < passes; p++) - for (c = 0; c <= channels; c++) { // c=0 Luminance only - -#ifdef _OPENMP - #pragma omp parallel for private(offset) shared(L) -#endif - - for (offset = 0; offset < width * height; offset++) { - int ii = offset / width; - int kk = offset - ii * width; - - if (c == 0) { - L[offset] = lab->L[ii][kk] / 327.68f; // adjust to RT and to 0..100 - } else if (c == 1) { - L[offset] = lab->a[ii][kk] / 327.68f; - } else { /*if (c==2) */ - L[offset] = lab->b[ii][kk] / 327.68f; - } - } - -#ifdef _OPENMP - #pragma omp parallel for private(j,i,iii,kkk, templab,offset,wH,wV,wD1,wD2,s,lumH,lumV,lumD1,lumD2,v,contrast,f1,f2,f3,f4,difT,difB,difL,difR,difLT,difLB,difRT,difRB) shared(lab,L,amount) -#endif - - for(j = 2; j < height - 2; j++) - for(i = 2, offset = j * width + i; i < width - 2; i++, offset++) { - // weight functions - wH = eps2 + fabs(L[offset + 1] - L[offset - 1]); - wV = eps2 + fabs(L[offset + width] - L[offset - width]); - - s = 1.0f + fabs(wH - wV) / 2.0f; - wD1 = eps2 + fabs(L[offset + width + 1] - L[offset - width - 1]) / s; - wD2 = eps2 + fabs(L[offset + width - 1] - L[offset - width + 1]) / s; - s = wD1; - wD1 /= wD2; - wD2 /= s; - - // initial values - int ii = offset / width; - int kk = offset - ii * width; - - if (c == 0) { - lumH = lumV = lumD1 = lumD2 = v = lab->L[ii][kk] / 327.68f; - } else if (c == 1) { - lumH = lumV = lumD1 = lumD2 = v = lab->a[ii][kk] / 327.68f; - } else { /* if (c==2) */ - lumH = lumV = lumD1 = lumD2 = v = lab->b[ii][kk] / 327.68f; - } - - - // contrast detection - contrast = sqrt(fabs(L[offset + 1] - L[offset - 1]) * fabs(L[offset + 1] - L[offset - 1]) + fabs(L[offset + width] - L[offset - width]) * fabs(L[offset + width] - L[offset - width])) / chmax[c]; - - if (contrast > 1.0f) { - contrast = 1.0f; - } - - // new possible values - if (((L[offset] < L[offset - 1]) && (L[offset] > L[offset + 1])) || ((L[offset] > L[offset - 1]) && (L[offset] < L[offset + 1]))) { - f1 = fabs(L[offset - 2] - L[offset - 1]); - f2 = fabs(L[offset - 1] - L[offset]); - f3 = fabs(L[offset - 1] - L[offset - width]) * fabs(L[offset - 1] - L[offset + width]); - f4 = sqrt(fabs(L[offset - 1] - L[offset - width2]) * fabs(L[offset - 1] - L[offset + width2])); - difL = f1 * f2 * f2 * f3 * f3 * f4; - f1 = fabs(L[offset + 2] - L[offset + 1]); - f2 = fabs(L[offset + 1] - L[offset]); - f3 = fabs(L[offset + 1] - L[offset - width]) * fabs(L[offset + 1] - L[offset + width]); - f4 = sqrt(fabs(L[offset + 1] - L[offset - width2]) * fabs(L[offset + 1] - L[offset + width2])); - difR = f1 * f2 * f2 * f3 * f3 * f4; - - if ((difR > epsil) && (difL > epsil)) { - lumH = (L[offset - 1] * difR + L[offset + 1] * difL) / (difL + difR); - lumH = v * (1.f - contrast) + lumH * contrast; - } - } - - if (((L[offset] < L[offset - width]) && (L[offset] > L[offset + width])) || ((L[offset] > L[offset - width]) && (L[offset] < L[offset + width]))) { - f1 = fabs(L[offset - width2] - L[offset - width]); - f2 = fabs(L[offset - width] - L[offset]); - f3 = fabs(L[offset - width] - L[offset - 1]) * fabs(L[offset - width] - L[offset + 1]); - f4 = sqrt(fabs(L[offset - width] - L[offset - 2]) * fabs(L[offset - width] - L[offset + 2])); - difT = f1 * f2 * f2 * f3 * f3 * f4; - f1 = fabs(L[offset + width2] - L[offset + width]); - f2 = fabs(L[offset + width] - L[offset]); - f3 = fabs(L[offset + width] - L[offset - 1]) * fabs(L[offset + width] - L[offset + 1]); - f4 = sqrt(fabs(L[offset + width] - L[offset - 2]) * fabs(L[offset + width] - L[offset + 2])); - difB = f1 * f2 * f2 * f3 * f3 * f4; - - if ((difB > epsil) && (difT > epsil)) { - lumV = (L[offset - width] * difB + L[offset + width] * difT) / (difT + difB); - lumV = v * (1.f - contrast) + lumV * contrast; - } - } - - if (((L[offset] < L[offset - 1 - width]) && (L[offset] > L[offset + 1 + width])) || ((L[offset] > L[offset - 1 - width]) && (L[offset] < L[offset + 1 + width]))) { - f1 = fabs(L[offset - 2 - width2] - L[offset - 1 - width]); - f2 = fabs(L[offset - 1 - width] - L[offset]); - f3 = fabs(L[offset - 1 - width] - L[offset - width + 1]) * fabs(L[offset - 1 - width] - L[offset + width - 1]); - f4 = sqrt(fabs(L[offset - 1 - width] - L[offset - width2 + 2]) * fabs(L[offset - 1 - width] - L[offset + width2 - 2])); - difLT = f1 * f2 * f2 * f3 * f3 * f4; - f1 = fabs(L[offset + 2 + width2] - L[offset + 1 + width]); - f2 = fabs(L[offset + 1 + width] - L[offset]); - f3 = fabs(L[offset + 1 + width] - L[offset - width + 1]) * fabs(L[offset + 1 + width] - L[offset + width - 1]); - f4 = sqrt(fabs(L[offset + 1 + width] - L[offset - width2 + 2]) * fabs(L[offset + 1 + width] - L[offset + width2 - 2])); - difRB = f1 * f2 * f2 * f3 * f3 * f4; - - if ((difLT > epsil) && (difRB > epsil)) { - lumD1 = (L[offset - 1 - width] * difRB + L[offset + 1 + width] * difLT) / (difLT + difRB); - lumD1 = v * (1.f - contrast) + lumD1 * contrast; - } - } - - if (((L[offset] < L[offset + 1 - width]) && (L[offset] > L[offset - 1 + width])) || ((L[offset] > L[offset + 1 - width]) && (L[offset] < L[offset - 1 + width]))) { - f1 = fabs(L[offset - 2 + width2] - L[offset - 1 + width]); - f2 = fabs(L[offset - 1 + width] - L[offset]); - f3 = fabs(L[offset - 1 + width] - L[offset - width - 1]) * fabs(L[offset - 1 + width] - L[offset + width + 1]); - f4 = sqrt(fabs(L[offset - 1 + width] - L[offset - width2 - 2]) * fabs(L[offset - 1 + width] - L[offset + width2 + 2])); - difLB = f1 * f2 * f2 * f3 * f3 * f4; - f1 = fabs(L[offset + 2 - width2] - L[offset + 1 - width]); - f2 = fabs(L[offset + 1 - width] - L[offset]) * fabs(L[offset + 1 - width] - L[offset]); - f3 = fabs(L[offset + 1 - width] - L[offset + width + 1]) * fabs(L[offset + 1 - width] - L[offset - width - 1]); - f4 = sqrt(fabs(L[offset + 1 - width] - L[offset + width2 + 2]) * fabs(L[offset + 1 - width] - L[offset - width2 - 2])); - difRT = f1 * f2 * f2 * f3 * f3 * f4; - - if ((difLB > epsil) && (difRT > epsil)) { - lumD2 = (L[offset + 1 - width] * difLB + L[offset - 1 + width] * difRT) / (difLB + difRT); - lumD2 = v * (1.f - contrast) + lumD2 * contrast; - } - } - - s = amount; - - // avoid sharpening diagonals too much - if (((fabs(wH / wV) < 0.45f) && (fabs(wH / wV) > 0.05f)) || ((fabs(wV / wH) < 0.45f) && (fabs(wV / wH) > 0.05f))) { - s = amount / 3.0f; - } - - // final mix - if ((wH != 0.0f) && (wV != 0.0f) && (wD1 != 0.0f) && (wD2 != 0.0f)) { - iii = offset / width; - kkk = offset - iii * width; - float provL = lab->L[iii][kkk] / 327.68f; - - if(c == 0) { - if(provL < 92.f) { - templab = v * (1.f - s) + (lumH * wH + lumV * wV + lumD1 * wD1 + lumD2 * wD2) / (wH + wV + wD1 + wD2) * s; - } else { - templab = provL; - } - } else { - templab = v * (1.f - s) + (lumH * wH + lumV * wV + lumD1 * wD1 + lumD2 * wD2) / (wH + wV + wD1 + wD2) * s; - } - - if (c == 0) { - lab->L[iii][kkk] = fabs(327.68f * templab); // fabs because lab->L always >0 - } else if (c == 1) { - lab->a[iii][kkk] = 327.68f * templab ; - } else if (c == 2) { - lab->b[iii][kkk] = 327.68f * templab ; - } - } - - } - } - - delete [] L; - - t2e.set(); - - if (settings->verbose) { - printf("SharpenEdge gradient %d usec\n", t2e.etime(t1e)); - } -} - // To the extent possible under law, Manuel Llorens // has waived all copyright and related or neighboring rights to this work. // This code is licensed under CC0 v1.0, see license information at @@ -640,10 +405,10 @@ BENCHFUN // k=2 matrix 5x5 k=1 matrix 3x3 const int width = W, height = H; const int unif = params->sharpenMicro.uniformity; - const float amount = (k == 1 ? 2.7f : 1.f) * params->sharpenMicro.amount / 1500.0f; //amount 2000.0 quasi no artifacts ==> 1500 = maximum, after artifacts, 25/9 if 3x3 + const float amount = (k == 1 ? 2.7 : 1.) * params->sharpenMicro.amount / 1500.0; //amount 2000.0 quasi no artifacts ==> 1500 = maximum, after artifacts, 25/9 if 3x3 if (settings->verbose) { - printf ("Micro-contrast amount %f\n", amount); + printf ("Micro-contrast amount %f\n", static_cast(amount)); printf ("Micro-contrast uniformity %i\n", unif); } @@ -674,7 +439,7 @@ BENCHFUN // calculate contrast based blend factors to reduce sharpening in regions with low contrast JaggedArray blend(W, H); - float contrast = params->sharpenMicro.contrast / 100.f; + float contrast = params->sharpenMicro.contrast / 100.0; buildBlendMask(luminance, blend, W, H, contrast); #ifdef _OPENMP @@ -883,7 +648,7 @@ void ImProcFunctions::sharpeningcam (CieImage* ncie, float** b2, bool showMask) // calculate contrast based blend factors to reduce sharpening in regions with low contrast JaggedArray blend(W, H); - float contrast = params->sharpening.contrast / 100.f; + float contrast = params->sharpening.contrast / 100.0; buildBlendMask(ncie->sh_p, blend, W, H, contrast); if(showMask) { #ifdef _OPENMP diff --git a/rtengine/ipsharpenedges.cc b/rtengine/ipsharpenedges.cc new file mode 100644 index 000000000..6a44ee40a --- /dev/null +++ b/rtengine/ipsharpenedges.cc @@ -0,0 +1,217 @@ +/* + * This file is part of RawTherapee. + * + * Copyright (c) 2004-2020 Gabor Horvath + * + * RawTherapee is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * RawTherapee is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with RawTherapee. If not, see . +*/ + +#include +#include "improcfun.h" +#include "labimage.h" +#include "procparams.h" +#include "rt_math.h" + +namespace { +#ifdef __SSE2__ +bool inintervalLoRo(float a, float b, float c) +{ + return a < std::max(b, c) && a > std::min(b, c); +} + +float selectweight(float a, float b, float low, float high) +{ + const float minVal = std::min(a,b); + const float maxVal = std::max(a,b); + const float res = (minVal < 0.45f * maxVal) ? low : high; + return (minVal > 0.05f * maxVal) ? res : high; +} + +#else +bool inintervalLoRo(float a, float b, float c) +{ + return (a < b && a > c) || (a < c && a > b); +} + +float selectweight(float a, float b, float low, float high) +{ + if ((a < 0.45f * b && a > 0.05f * b) || (b < 0.45f * a && b > 0.05f * a)) { + return low; + } else { + return high; + } +} + +#endif +} +namespace rtengine +{ + +// To the extent possible under law, Manuel Llorens +// has waived all copyright and related or neighboring rights to this work. +// This work is published from: Spain. + +// Thanks to Manuel for this excellent job (Jacques Desmis JDC or frej83) +void ImProcFunctions::MLsharpen (LabImage* lab) +{ + // JD: this algorithm maximize clarity of images; it does not play on accutance. It can remove (partially) the effects of the AA filter) + // I think we can use this algorithm alone in most cases, or first to clarify image and if you want a very little USM (unsharp mask sharpening) after... + if (!params->sharpenEdge.enabled || params->sharpenEdge.amount == 0) { + return; + } + + const int width = lab->W, height = lab->H; + constexpr float chmax[3] = {1.f / 8.f, 1.f / 3.f, 1.f / 3.f}; + const int width2 = 2 * width; + constexpr float eps2 = 0.001f; //prevent divide by zero + const float amount = params->sharpenEdge.amount / 100.0; + const float amountby3 = params->sharpenEdge.amount / 300.0; + + std::unique_ptr L(new float[width * height]); + + const int channels = params->sharpenEdge.threechannels ? 1 : 3; + const int passes = params->sharpenEdge.passes; + + for (int c = 0; c < channels; ++c) { // c=0 Luminance only + float** channel = c == 0 ? lab->L : c == 1 ? lab->a : lab->b; + for (int p = 0; p < passes; ++p) { +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int i = 0; i < height; ++i) { + for (int j = 0; j < width; ++j) { + L[i * width + j] = channel[i][j] / 327.68f; + } + } + +#ifdef _OPENMP + #pragma omp parallel for schedule(dynamic,16) +#endif + + for (int j = 2; j < height - 2; j++) { + for (int i = 2, offset = j * width + i; i < width - 2; i++, offset++) { + // weight functions + const float wH = eps2 + std::fabs(L[offset + 1] - L[offset - 1]); + const float wV = eps2 + std::fabs(L[offset + width] - L[offset - width]); + + float s = 2.f / (2.f + std::fabs(wH - wV)); + float wD1 = eps2 + std::fabs(L[offset + width + 1] - L[offset - width - 1]) * s; + float wD2 = eps2 + std::fabs(L[offset + width - 1] - L[offset - width + 1]) * s; + s = wD1; + wD1 /= wD2; + wD2 /= s; + + const float v = L[offset]; + float lumH, lumV, lumD1, lumD2; + lumH = lumV = lumD1 = lumD2 = v; + + // contrast detection + const float contrast = std::min(std::sqrt(SQR(L[offset + 1] - L[offset - 1]) + SQR(L[offset + width] - L[offset - width])) * chmax[c], 1.f); + + // new possible values + if (inintervalLoRo(v, L[offset - 1], L[offset + 1])) { + float f1 = std::fabs(L[offset - 2] - L[offset - 1]); + float f2 = L[offset - 1] - v; + float f3 = (L[offset - 1] - L[offset - width]) * (L[offset - 1] - L[offset + width]); + float f4 = std::sqrt(std::fabs((L[offset - 1] - L[offset - width2]) * (L[offset - 1] - L[offset + width2]))); + const float difL = f1 * SQR(f2 * f3) * f4; + if (difL > 0.f) { + f1 = std::fabs(L[offset + 2] - L[offset + 1]); + f2 = L[offset + 1] - v; + f3 = (L[offset + 1] - L[offset - width]) * (L[offset + 1] - L[offset + width]); + f4 = std::sqrt(std::fabs((L[offset + 1] - L[offset - width2]) * (L[offset + 1] - L[offset + width2]))); + const float difR = f1 * SQR(f2 * f3) * f4; + if (difR > 0.f) { + lumH = (L[offset - 1] * difR + L[offset + 1] * difL) / (difL + difR); + lumH = intp(contrast, lumH, v); + } + } + } + + if (inintervalLoRo(v, L[offset - width], L[offset + width])) { + float f1 = std::fabs(L[offset - width2] - L[offset - width]); + float f2 = L[offset - width] - v; + float f3 = (L[offset - width] - L[offset - 1]) * (L[offset - width] - L[offset + 1]); + float f4 = std::sqrt(std::fabs((L[offset - width] - L[offset - 2]) * (L[offset - width] - L[offset + 2]))); + const float difT = f1 * SQR(f2 * f3) * f4; + if (difT > 0.f) { + f1 = std::fabs(L[offset + width2] - L[offset + width]); + f2 = L[offset + width] - v; + f3 = (L[offset + width] - L[offset - 1]) * (L[offset + width] - L[offset + 1]); + f4 = std::sqrt(std::fabs((L[offset + width] - L[offset - 2]) * (L[offset + width] - L[offset + 2]))); + const float difB = f1 * SQR(f2 * f3) * f4; + if (difB > 0.f) { + lumV = (L[offset - width] * difB + L[offset + width] * difT) / (difT + difB); + lumV = intp(contrast, lumV, v); + } + } + } + + if (inintervalLoRo(v, L[offset - 1 - width], L[offset + 1 + width])) { + float f1 = std::fabs(L[offset - 2 - width2] - L[offset - 1 - width]); + float f2 = L[offset - 1 - width] - v; + float f3 = (L[offset - 1 - width] - L[offset - width + 1]) * (L[offset - 1 - width] - L[offset + width - 1]); + float f4 = std::sqrt(std::fabs((L[offset - 1 - width] - L[offset - width2 + 2]) * (L[offset - 1 - width] - L[offset + width2 - 2]))); + const float difLT = f1 * SQR(f2 * f3) * f4; + if (difLT > 0.f) { + f1 = std::fabs(L[offset + 2 + width2] - L[offset + 1 + width]); + f2 = L[offset + 1 + width] - v; + f3 = (L[offset + 1 + width] - L[offset - width + 1]) * (L[offset + 1 + width] - L[offset + width - 1]); + f4 = std::sqrt(std::fabs((L[offset + 1 + width] - L[offset - width2 + 2]) * (L[offset + 1 + width] - L[offset + width2 - 2]))); + const float difRB = f1 * SQR(f2 * f3) * f4; + if (difRB > 0.f) { + lumD1 = (L[offset - 1 - width] * difRB + L[offset + 1 + width] * difLT) / (difLT + difRB); + lumD1 = intp(contrast, lumD1, v); + } + } + } + + if (inintervalLoRo(v, L[offset + 1 - width], L[offset - 1 + width])) { + float f1 = std::fabs(L[offset - 2 + width2] - L[offset - 1 + width]); + float f2 = L[offset - 1 + width] - v; + float f3 = (L[offset - 1 + width] - L[offset - width - 1]) * (L[offset - 1 + width] - L[offset + width + 1]); + float f4 = std::sqrt(std::fabs((L[offset - 1 + width] - L[offset - width2 - 2]) * (L[offset - 1 + width] - L[offset + width2 + 2]))); + const float difLB = f1 * SQR(f2 * f3) * f4; + if (difLB > 0.f) { + f1 = std::fabs(L[offset + 2 - width2] - L[offset + 1 - width]); + f2 = L[offset + 1 - width] - v; + f3 = (L[offset + 1 - width] - L[offset + width + 1]) * (L[offset + 1 - width] - L[offset - width - 1]); + f4 = std::sqrt(std::fabs((L[offset + 1 - width] - L[offset + width2 + 2]) * (L[offset + 1 - width] - L[offset - width2 - 2]))); + const float difRT = f1 * SQR(f2 * f3) * f4; + if (difRT > 0.f) { + lumD2 = (L[offset + 1 - width] * difLB + L[offset - 1 + width] * difRT) / (difLB + difRT); + lumD2 = intp(contrast, lumD2, v); + } + } + } + + // final mix + // avoid sharpening diagonals too much + const float weight = selectweight(wH, wV, amountby3, amount); + + if (c == 0) { + if (v < 92.f) { + channel[j][i] = std::fabs(327.68f * intp(weight, (lumH * wH + lumV * wV + lumD1 * wD1 + lumD2 * wD2) / (wH + wV + wD1 + wD2), v)); // fabs because lab->L always > 0 + } + } else { + channel[j][i] = 327.68f * intp(weight, (lumH * wH + lumV * wV + lumD1 * wD1 + lumD2 * wD2) / (wH + wV + wD1 + wD2), v); + } + } + } + } + } +} + +} diff --git a/rtengine/iptransform.cc b/rtengine/iptransform.cc index dc095735f..eb823d711 100644 --- a/rtengine/iptransform.cc +++ b/rtengine/iptransform.cc @@ -807,11 +807,11 @@ static void calcGradientParams (int oW, int oH, const GradientParams& gradient, gp.ta = tan (gradient_angle); gp.xc = w * gradient_center_x; gp.yc = h * gradient_center_y; - gp.ys = sqrt ((float)h * h + (float)w * w) * (gradient_span / cos (gradient_angle)); - gp.ys_inv = 1.0 / gp.ys; - gp.top_edge_0 = gp.yc - gp.ys / 2.0; + gp.ys = rtengine::norm2(static_cast(h), static_cast(w)) * (gradient_span / cos(gradient_angle)); + gp.ys_inv = 1.f / gp.ys; + gp.top_edge_0 = gp.yc - gp.ys / 2.f; - if (gp.ys < 1.0 / h) { + if (h * gp.ys < 1.f) { gp.ys_inv = 0; gp.ys = 0; } @@ -841,7 +841,7 @@ static float calcGradientFactor (const struct grad_params& gp, int x, int y) val = 1.f - pow3 (xcosf (val)); } - return gp.scale + val * (1.0 - gp.scale); + return gp.scale + val * (1.f - gp.scale); } } else { int gy = gp.transpose ? x : y; @@ -865,7 +865,7 @@ static float calcGradientFactor (const struct grad_params& gp, int x, int y) val = 1.f - pow3 (xcosf (val)); } - return gp.scale + val * (1.0 - gp.scale); + return gp.scale + val * (1.f - gp.scale); } } } @@ -884,7 +884,7 @@ static void calcPCVignetteParams (int fW, int fH, int oW, int oH, const PCVignet { // ellipse formula: (x/a)^2 + (y/b)^2 = 1 - double roundness = pcvignette.roundness / 100.0; + float roundness = pcvignette.roundness / 100.f; pcv.feather = pcvignette.feather / 100.0; if (crop.enabled) { @@ -901,42 +901,40 @@ static void calcPCVignetteParams (int fW, int fH, int oW, int oH, const PCVignet pcv.h = oH; } - pcv.fadeout_mul = 1.0 / (0.05 * sqrtf (oW * oW + oH * oH)); + pcv.fadeout_mul = 20.0 / rtengine::norm2(static_cast(oW), static_cast(oW)); float short_side = (pcv.w < pcv.h) ? pcv.w : pcv.h; float long_side = (pcv.w > pcv.h) ? pcv.w : pcv.h; pcv.sep = 2; pcv.sepmix = 0; - pcv.oe_a = sqrt (2.0) * long_side * 0.5; + pcv.oe_a = std::sqrt(2.f) * long_side * 0.5f; pcv.oe_b = pcv.oe_a * short_side / long_side; - pcv.ie_mul = (1.0 / sqrt (2.0)) * (1.0 - pcv.feather); + pcv.ie_mul = (1.f - pcv.feather) / std::sqrt(2.f); pcv.is_super_ellipse_mode = false; pcv.is_portrait = (pcv.w < pcv.h); - if (roundness < 0.5) { + if (roundness < 0.5f) { // make super-ellipse of higher and higher degree pcv.is_super_ellipse_mode = true; - float sepf = 2 + 4 * powf (1.0 - 2 * roundness, 1.3); // gamma 1.3 used to balance the effect in the 0.0...0.5 roundness range + float sepf = 2 + 4 * std::pow(1.f - 2 * roundness, 1.3f); // gamma 1.3 used to balance the effect in the 0.0...0.5 roundness range pcv.sep = ((int)sepf) & ~0x1; - pcv.sepmix = (sepf - pcv.sep) * 0.5; // 0.0 to 1.0 - pcv.oe1_a = powf (2.0, 1.0 / pcv.sep) * long_side * 0.5; + pcv.sepmix = (sepf - pcv.sep) * 0.5f; // 0.0 to 1.0 + pcv.oe1_a = std::pow(2.f, 1.f / pcv.sep) * long_side * 0.5f; pcv.oe1_b = pcv.oe1_a * short_side / long_side; - pcv.ie1_mul = (1.0 / powf (2.0, 1.0 / pcv.sep)) * (1.0 - pcv.feather); - pcv.oe2_a = powf (2.0, 1.0 / (pcv.sep + 2)) * long_side * 0.5; + pcv.ie1_mul = (1.f - pcv.feather) / std::pow(2.f, 1.f / pcv.sep); + pcv.oe2_a = std::pow(2.f, 1.f / (pcv.sep + 2)) * long_side * 0.5f; pcv.oe2_b = pcv.oe2_a * short_side / long_side; - pcv.ie2_mul = (1.0 / powf (2.0, 1.0 / (pcv.sep + 2))) * (1.0 - pcv.feather); - } - - if (roundness > 0.5) { + pcv.ie2_mul = (1.f - pcv.feather) / std::pow(2.f, 1.f / (pcv.sep + 2)); + } else if (roundness > 0.5f) { // scale from fitted ellipse towards circle - float rad = sqrtf (pcv.w * pcv.w + pcv.h * pcv.h) / 2.0; + float rad = rtengine::norm2(static_cast(pcv.w), static_cast(pcv.h)) / 2.f; float diff_a = rad - pcv.oe_a; float diff_b = rad - pcv.oe_b; - pcv.oe_a = pcv.oe_a + diff_a * 2 * (roundness - 0.5); - pcv.oe_b = pcv.oe_b + diff_b * 2 * (roundness - 0.5); + pcv.oe_a = pcv.oe_a + diff_a * 2 * (roundness - 0.5f); + pcv.oe_b = pcv.oe_b + diff_b * 2 * (roundness - 0.5f); } - pcv.scale = powf (2, -pcvignette.strength); + pcv.scale = std::pow(2, -pcvignette.strength); if (pcvignette.strength >= 6.0) { pcv.scale = 0.0; @@ -1072,23 +1070,23 @@ void ImProcFunctions::transformLuminanceOnly (Imagefloat* original, Imagefloat* double r = sqrt (vig_x_d * vig_x_d + vig_y_d * vig_y_d); if (darkening) { - factor /= std::max (v + mul * tanh (b * (maxRadius - r) / maxRadius), 0.001); + factor /= std::max (v + mul * tanh(b * (maxRadius - r) / maxRadius), 0.001); } else { - factor = v + mul * tanh (b * (maxRadius - r) / maxRadius); + factor = v + mul * tanh(b * (maxRadius - r) / maxRadius); } } if (applyGradient) { - factor *= calcGradientFactor (gp, cx + x, cy + y); + factor *= static_cast(calcGradientFactor(gp, cx + x, cy + y)); } if (applyPCVignetting) { - factor *= calcPCVignetteFactor (pcv, cx + x, cy + y); + factor *= static_cast(calcPCVignetteFactor(pcv, cx + x, cy + y)); } - transformed->r (y, x) = original->r (y, x) * factor; - transformed->g (y, x) = original->g (y, x) * factor; - transformed->b (y, x) = original->b (y, x) * factor; + transformed->r(y, x) = static_cast(original->r(y, x)) * factor; + transformed->g(y, x) = static_cast(original->g(y, x)) * factor; + transformed->b(y, x) = static_cast(original->b(y, x)) * factor; } } } @@ -1299,11 +1297,11 @@ void ImProcFunctions::transformGeneral(bool highQuality, Imagefloat *original, I } if (enableGradient) { - vignmul *= calcGradientFactor(gp, cx + x, cy + y); + vignmul *= static_cast(calcGradientFactor(gp, cx + x, cy + y)); } if (enablePCVignetting) { - vignmul *= calcPCVignetteFactor(pcv, cx + x, cy + y); + vignmul *= static_cast(calcPCVignetteFactor(pcv, cx + x, cy + y)); } if (yc > 0 && yc < original->getHeight() - 2 && xc > 0 && xc < original->getWidth() - 2) { diff --git a/rtengine/ipvibrance.cc b/rtengine/ipvibrance.cc index 14e5f3c44..8636ecb95 100644 --- a/rtengine/ipvibrance.cc +++ b/rtengine/ipvibrance.cc @@ -48,7 +48,7 @@ void fillCurveArrayVib (DiagonalCurve* diagCurve, LUTf &outCurve) // change to [0,1] range // apply custom/parametric/NURBS curve, if any // and store result in a temporary array - outCurve[i] = 65535.f * diagCurve->getVal ( double (i) / 65535.0 ); + outCurve[i] = 65535.0 * diagCurve->getVal(i / 65535.0); } } else { outCurve.makeIdentity(); @@ -606,7 +606,7 @@ void ImProcFunctions::vibrance (LabImage* lab) bool inGamut; const float fyy = Color::c1By116 * Lprov + Color::c16By116; - const float yy_ = (Lprov > Color::epskap) ? fyy * fyy*fyy : Lprov / Color::kappaf; + const float yy_ = (Lprov > static_cast(Color::epskap)) ? fyy * fyy*fyy : Lprov / Color::kappaf; float ChprovOld = std::numeric_limits::min(); do { inGamut = true; diff --git a/rtengine/ipwavelet.cc b/rtengine/ipwavelet.cc index 7c0dc368b..f415c9c8e 100644 --- a/rtengine/ipwavelet.cc +++ b/rtengine/ipwavelet.cc @@ -3,7 +3,7 @@ // // // -// code dated: December , 2014 +// code dated: 9 , 2019 // // Ipwaveletcc is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -17,7 +17,7 @@ // // You should have received a copy of the GNU General Public License // along with this program. If not, see . -// * 2014 Jacques Desmis +// * 2014 - 2019 2020 - Jacques Desmis // * 2014 Ingo Weyrich // @@ -26,15 +26,16 @@ #include #include -#include "../rtgui/threadutils.h" - #include "array2D.h" #include "color.h" #include "curves.h" #include "EdgePreservingDecomposition.h" #include "iccstore.h" #include "improcfun.h" +#include "imagefloat.h" #include "labimage.h" +#include "gauss.h" +#include "boxblur.h" #include "LUT.h" #include "median.h" #include "opthelper.h" @@ -43,33 +44,33 @@ #include "rtengine.h" #include "sleef.h" #include "../rtgui/options.h" - +#include "guidedfilter.h" #ifdef _OPENMP #include #endif #include "cplx_wavelet_dec.h" -#define TS 64 // Tile size -#define offset 25 // shift between tiles -#define fTS ((TS/2+1)) // second dimension of Fourier tiles -#define blkrad 1 // radius of block averaging - -#define epsilon 0.001f/(TS*TS) //tolerance - namespace rtengine { struct cont_params { float mul[10]; + float sigm; int chrom; int chro; + float chrwav; int contrast; float th; float thH; float conres; float conresH; + float blurres; + float blurcres; + float bluwav; + float radius; float chrores; + bool oldsh; float hueres; float sky; float b_l, t_l, b_r, t_r; @@ -81,6 +82,7 @@ struct cont_params { float b_lpast, t_lpast, b_rpast, t_rpast; float b_lsat, t_lsat, b_rsat, t_rsat; int rad; + float eff; int val; int til; int numlevH, numlevS; @@ -130,17 +132,22 @@ struct cont_params { bool finena; bool toningena; bool noiseena; + bool blena; int maxilev; float edgsens; float edgampl; int neigh; bool lipp; + float ballum; + float balchrom; + float chromfi; + float chromco; }; int wavNestedLevels = 1; -void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const procparams::WaveletParams & waparams, const WavCurve & wavCLVCcurve, const WavOpacityCurveRG & waOpacityCurveRG, const WavOpacityCurveBY & waOpacityCurveBY, const WavOpacityCurveW & waOpacityCurveW, const WavOpacityCurveWL & waOpacityCurveWL, LUTf &wavclCurve, int skip) +void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const procparams::WaveletParams & waparams, const WavCurve & wavCLVCcurve, const Wavblcurve & wavblcurve, const WavOpacityCurveRG & waOpacityCurveRG, const WavOpacityCurveBY & waOpacityCurveBY, const WavOpacityCurveW & waOpacityCurveW, const WavOpacityCurveWL & waOpacityCurveWL, const LUTf &wavclCurve, int skip) { @@ -148,38 +155,32 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const // init variables to display Munsell corrections MunsellDebugInfo* MunsDebugInfo = new MunsellDebugInfo(); #endif - TMatrix wiprof = ICCStore::getInstance()->workingSpaceInverseMatrix (params->icm.workingProfile); + TMatrix wiprof = ICCStore::getInstance()->workingSpaceInverseMatrix(params->icm.workingProfile); const double wip[3][3] = { {wiprof[0][0], wiprof[0][1], wiprof[0][2]}, {wiprof[1][0], wiprof[1][1], wiprof[1][2]}, {wiprof[2][0], wiprof[2][1], wiprof[2][2]} }; - const short int imheight = lab->H, imwidth = lab->W; + const int imheight = lab->H, imwidth = lab->W; + struct cont_params cp; + cp.avoi = params->wavelet.avoid; - if(params->wavelet.Medgreinf == "more") { + if (params->wavelet.Medgreinf == "more") { cp.reinforce = 1; - } - - if(params->wavelet.Medgreinf == "none") { + } else if (params->wavelet.Medgreinf == "none") { cp.reinforce = 2; - } - - if(params->wavelet.Medgreinf == "less") { + } else if (params->wavelet.Medgreinf == "less") { cp.reinforce = 3; } - if(params->wavelet.NPmethod == "none") { + if (params->wavelet.NPmethod == "none") { cp.lip3 = false; - } - - if(params->wavelet.NPmethod == "low") { + } else if (params->wavelet.NPmethod == "low") { cp.lip3 = true; cp.neigh = 0; - } - - if(params->wavelet.NPmethod == "high") { + } else if (params->wavelet.NPmethod == "high") { cp.lip3 = true; cp.neigh = 1; } @@ -188,35 +189,28 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const cp.diag = params->wavelet.tmr; cp.balan = (float)params->wavelet.balance; cp.ite = params->wavelet.iter; - cp.tonemap = false; + cp.tonemap = params->wavelet.tmrs != 0; cp.bam = false; - if(params->wavelet.tmrs == 0) { - cp.tonemap = false; - } else { - cp.tonemap = true; - } - - if(params->wavelet.TMmethod == "cont") { + if (params->wavelet.TMmethod == "cont") { cp.contmet = 1; - } else if(params->wavelet.TMmethod == "tm") { + } else if (params->wavelet.TMmethod == "tm") { cp.contmet = 2; } - if(params->wavelet.BAmethod != "none") { + if (params->wavelet.BAmethod != "none") { cp.bam = true; + + if (params->wavelet.BAmethod == "sli") { + cp.BAmet = 1; + } else if (params->wavelet.BAmethod == "cur") { + cp.BAmet = 2; + } } - if(params->wavelet.BAmethod == "sli") { - cp.BAmet = 1; - } - - if(params->wavelet.BAmethod == "cur") { - cp.BAmet = 2; - } + cp.sigm = params->wavelet.sigma; cp.tmstrength = params->wavelet.tmrs; - //cp.tonemap = params->wavelet.tmr; cp.contena = params->wavelet.expcontrast; cp.chromena = params->wavelet.expchroma; cp.edgeena = params->wavelet.expedge; @@ -224,16 +218,14 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const cp.finena = params->wavelet.expfinal; cp.toningena = params->wavelet.exptoning; cp.noiseena = params->wavelet.expnoise; + cp.blena = params->wavelet.expbl; + cp.chrwav = 0.01f * params->wavelet.chrwav; - if(params->wavelet.Backmethod == "black") { + if (params->wavelet.Backmethod == "black") { cp.backm = 0; - } - - if(params->wavelet.Backmethod == "grey") { + } else if (params->wavelet.Backmethod == "grey") { cp.backm = 1; - } - - if(params->wavelet.Backmethod == "resid") { + } else if (params->wavelet.Backmethod == "resid") { cp.backm = 2; } @@ -245,57 +237,44 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const cp.edgsens = 60.f; cp.edgampl = 10.f; - if(cp.lipp) { + if (cp.lipp) { cp.edgsens = (float) params->wavelet.edgesensi; cp.edgampl = (float) params->wavelet.edgeampli; } - //int N = imheight * imwidth; - int maxmul = params->wavelet.thres; + const int maxmul = params->wavelet.thres; cp.maxilev = maxmul; static const float scales[10] = {1.f, 2.f, 4.f, 8.f, 16.f, 32.f, 64.f, 128.f, 256.f, 512.f}; float scaleskip[10]; - for(int sc = 0; sc < 10; sc++) { + for (int sc = 0; sc < 10; sc++) { scaleskip[sc] = scales[sc] / skip; } - float atten0 = 0.40f; - float atten123 = 0.90f; + constexpr float atten0 = 0.40f; + constexpr float atten123 = 0.90f; //int DaubLen = settings->daubech ? 8 : 6; int DaubLen; - if(params->wavelet.daubcoeffmethod == "2_") { + if (params->wavelet.daubcoeffmethod == "2_") { DaubLen = 4; - } - - if(params->wavelet.daubcoeffmethod == "4_") { + } else if (params->wavelet.daubcoeffmethod == "4_") { DaubLen = 6; - } - - if(params->wavelet.daubcoeffmethod == "6_") { + } else if (params->wavelet.daubcoeffmethod == "6_") { DaubLen = 8; - } - - if(params->wavelet.daubcoeffmethod == "10_") { + } else if (params->wavelet.daubcoeffmethod == "10_") { DaubLen = 12; - } - - if(params->wavelet.daubcoeffmethod == "14_") { + } else { /* if (params->wavelet.daubcoeffmethod == "14_") */ DaubLen = 16; } cp.CHSLmet = 1; -// if(params->wavelet.CHSLmethod=="SL") cp.CHSLmet=1; -// if(params->wavelet.CHSLmethod=="CU") cp.CHSLmet=2; cp.EDmet = 1; - if(params->wavelet.EDmethod == "SL") { + if (params->wavelet.EDmethod == "SL") { cp.EDmet = 1; - } - - if(params->wavelet.EDmethod == "CU") { + } else if (params->wavelet.EDmethod == "CU") { cp.EDmet = 2; } @@ -315,29 +294,27 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const cp.CHmet = 0; cp.HSmet = false; - if(params->wavelet.CHmethod == "with") { + if (params->wavelet.CHmethod == "with") { cp.CHmet = 1; - } - - if(params->wavelet.CHmethod == "link") { + } else if (params->wavelet.CHmethod == "link") { cp.CHmet = 2; } - if(params->wavelet.HSmethod == "with") { + if (params->wavelet.HSmethod == "with") { cp.HSmet = true; } - cp.strength = min(1.f, max(0.f, ((float)params->wavelet.strength / 100.f))); + cp.strength = rtengine::min(1.f, rtengine::max(0.f, ((float)params->wavelet.strength / 100.f))); - for(int m = 0; m < maxmul; m++) { + for (int m = 0; m < maxmul; m++) { cp.mulC[m] = waparams.ch[m]; } - if(waOpacityCurveRG) { + if (waOpacityCurveRG) { cp.opaRG = true; } - if(cp.opaRG) { + if (cp.opaRG) { cp.mulopaRG[0] = 200.f * (waOpacityCurveRG[0] - 0.5f); cp.mulopaRG[1] = 200.f * (waOpacityCurveRG[62] - 0.5f); cp.mulopaRG[2] = 200.f * (waOpacityCurveRG[125] - 0.5f); @@ -348,16 +325,16 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const cp.mulopaRG[7] = 200.f * (waOpacityCurveRG[438] - 0.5f); cp.mulopaRG[8] = 200.f * (waOpacityCurveRG[500] - 0.5f); } else { - for(int level = 0; level < 9; level++) { + for (int level = 0; level < 9; level++) { cp.mulopaRG[level] = 0.f; } } - if(waOpacityCurveBY) { + if (waOpacityCurveBY) { cp.opaBY = true; } - if(cp.opaBY) { + if (cp.opaBY) { cp.mulopaBY[0] = 200.f * (waOpacityCurveBY[0] - 0.5f); cp.mulopaBY[1] = 200.f * (waOpacityCurveBY[62] - 0.5f); cp.mulopaBY[2] = 200.f * (waOpacityCurveBY[125] - 0.5f); @@ -368,47 +345,46 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const cp.mulopaBY[7] = 200.f * (waOpacityCurveBY[438] - 0.5f); cp.mulopaBY[8] = 200.f * (waOpacityCurveBY[500] - 0.5f); } else { - for(int level = 0; level < 9; level++) { + for (int level = 0; level < 9; level++) { cp.mulopaBY[level] = 0.f; } } - if(wavCLVCcurve) { + if (wavCLVCcurve) { cp.edgcurv = true; } - if(waOpacityCurveWL) { + if (waOpacityCurveWL) { cp.diagcurv = true; } - for(int m = 0; m < maxmul; m++) { + for (int m = 0; m < maxmul; m++) { cp.mul[m] = waparams.c[m]; } cp.mul[9] = (float) waparams.sup; - for(int sc = 0; sc < 10; sc++) { //reduce strength if zoom < 100% for contrast - if(sc == 0) { - if(scaleskip[sc] < 1.f) { + for (int sc = 0; sc < 10; sc++) { //reduce strength if zoom < 100% for contrast + if (sc == 0) { + if (scaleskip[sc] < 1.f) { cp.mul[sc] *= (atten0 * scaleskip[sc]); } } else { - if(scaleskip[sc] < 1.f) { + if (scaleskip[sc] < 1.f) { cp.mul[sc] *= (atten123 * scaleskip[sc]); } } } -// if(settings->verbose) printf("Wav mul 0=%f 1=%f 2=%f 3=%f 4=%f 5=%f 6=%f 7=%f 8=%f 9=%f\n",cp.mul[0],cp.mul[1],cp.mul[2],cp.mul[3],cp.mul[4],cp.mul[5],cp.mul[6],cp.mul[7],cp.mul[8],cp.mul[9]); - for(int sc = 0; sc < 9; sc++) { //reduce strength if zoom < 100% for chroma and tuning - if(sc == 0) { - if(scaleskip[sc] < 1.f) { + for (int sc = 0; sc < 9; sc++) { //reduce strength if zoom < 100% for chroma and tuning + if (sc == 0) { + if (scaleskip[sc] < 1.f) { cp.mulC[sc] *= (atten0 * scaleskip[sc]); cp.mulopaRG[sc] *= (atten0 * scaleskip[sc]); cp.mulopaBY[sc] *= (atten0 * scaleskip[sc]); } } else { - if(scaleskip[sc] < 1.f) { + if (scaleskip[sc] < 1.f) { cp.mulC[sc] *= (atten123 * scaleskip[sc]); cp.mulopaRG[sc] *= (atten123 * scaleskip[sc]); cp.mulopaBY[sc] *= (atten123 * scaleskip[sc]); @@ -422,10 +398,20 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const cp.rad = waparams.edgrad; cp.val = waparams.edgval; cp.til = waparams.edgthresh; + cp.eff = waparams.edgeffect; + cp.balchrom = waparams.balchrom; + cp.chromfi = 0.1f * waparams.chromfi; + cp.chromco = 0.1f * waparams.chromco; + cp.ballum = waparams.ballum; cp.conres = waparams.rescon; cp.conresH = waparams.resconH; + cp.radius = waparams.radius; cp.chrores = waparams.reschro; + cp.oldsh = waparams.oldsh; + cp.blurres = waparams.resblur; + cp.blurcres = waparams.resblurc; + cp.bluwav = waparams.bluwav; //cp.hueres=waparams.reshue; cp.hueres = 2.f; cp.th = float(waparams.thr); @@ -450,14 +436,12 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const cp.t_rsl = static_cast(params->wavelet.bllev.getTopRight()); cp.numlevS = params->wavelet.threshold2; int maxlevS = 9 - cp.numlevH; - cp.numlevS = MIN(cp.numlevS, maxlevS); - //printf("levHigh=%d levShad=%d\n",cp.numlevH,cp.numlevS); + cp.numlevS = rtengine::min(cp.numlevS, maxlevS); //highlight cp.b_lhl = static_cast(params->wavelet.hllev.getBottomLeft()); cp.t_lhl = static_cast(params->wavelet.hllev.getTopLeft()); cp.b_rhl = static_cast(params->wavelet.hllev.getBottomRight()); cp.t_rhl = static_cast(params->wavelet.hllev.getTopRight()); - //printf("BL=%f TL=%f BR=%f TR=%f\n",cp.b_lhl,cp.t_lhl,cp.b_rhl,cp.t_rhl); //pastel cp.b_lpast = static_cast(params->wavelet.pastlev.getBottomLeft()); cp.t_lpast = static_cast(params->wavelet.pastlev.getTopLeft()); @@ -484,52 +468,50 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const cp.lev3n = static_cast(params->wavelet.level3noise.getTop()); cp.detectedge = params->wavelet.medianlev; - //printf("low=%f mean=%f sd=%f max=%f\n",cp.edg_low,cp.edg_mean,cp.edg_sd,cp.edg_max); - int minwin = min(imwidth, imheight); + int minwin = rtengine::min(imwidth, imheight); int maxlevelcrop = 9; - if(cp.mul[9] != 0) { + if (cp.mul[9] != 0) { maxlevelcrop = 10; } // adap maximum level wavelet to size of crop - if(minwin * skip < 1024) { + if (minwin * skip < 1024) { maxlevelcrop = 9; //sampling wavelet 512 } - if(minwin * skip < 512) { + if (minwin * skip < 512) { maxlevelcrop = 8; //sampling wavelet 256 } - if(minwin * skip < 256) { + if (minwin * skip < 256) { maxlevelcrop = 7; //sampling 128 } - if(minwin * skip < 128) { + if (minwin * skip < 128) { maxlevelcrop = 6; } - if(minwin < 64) { + if (minwin < 64) { maxlevelcrop = 5; } - // printf("minwin=%d maxcrop=%d\n",minwin, maxlevelcrop); int levwav = params->wavelet.thres; - if(levwav == 9 && cp.mul[9] != 0) { + if (levwav == 9 && cp.mul[9] != 0) { levwav = 10; } - levwav = min(maxlevelcrop, levwav); + levwav = rtengine::min(maxlevelcrop, levwav); // determine number of levels to process. - // for(levwav=min(maxlevelcrop,levwav);levwav>0;levwav--) + // for(levwav=rtengine::min(maxlevelcrop,levwav);levwav>0;levwav--) // if(cp.mul[levwav-1]!=0.f || cp.curv) // if(cp.mul[levwav-1]!=0.f) // break; // I suppress this fonctionality ==> crash for level < 3 - if(levwav < 1) { + if (levwav < 1) { return; // nothing to do } @@ -539,28 +521,29 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const //output buffer int realtile = 0; - if(params->wavelet.Tilesmethod == "big") { + if (params->wavelet.Tilesmethod == "big") { realtile = 22; } - if(params->wavelet.Tilesmethod == "lit") { - realtile = 12; - } - + /* + if (params->wavelet.Tilesmethod == "lit") { + realtile = 12; + } + */ int tilesize = 128 * realtile; int overlap = (int) tilesize * 0.125f; int numtiles_W, numtiles_H, tilewidth, tileheight, tileWskip, tileHskip; - if(params->wavelet.Tilesmethod == "full") { + if (params->wavelet.Tilesmethod == "full") { kall = 0; } - Tile_calc (tilesize, overlap, kall, imwidth, imheight, numtiles_W, numtiles_H, tilewidth, tileheight, tileWskip, tileHskip); + Tile_calc(tilesize, overlap, kall, imwidth, imheight, numtiles_W, numtiles_H, tilewidth, tileheight, tileWskip, tileHskip); const int numtiles = numtiles_W * numtiles_H; LabImage * dsttmp; - if(numtiles == 1) { + if (numtiles == 1) { dsttmp = dst; } else { dsttmp = new LabImage(imwidth, imheight); @@ -572,97 +555,93 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const //now we have tile dimensions, overlaps //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% - int minsizetile = min(tilewidth, tileheight); + int minsizetile = rtengine::min(tilewidth, tileheight); int maxlev2 = 10; - if(minsizetile < 1024 && levwav == 10) { + if (minsizetile < 1024 && levwav == 10) { maxlev2 = 9; } - if(minsizetile < 512) { + if (minsizetile < 512) { maxlev2 = 8; } - if(minsizetile < 256) { + if (minsizetile < 256) { maxlev2 = 7; } - if(minsizetile < 128) { + if (minsizetile < 128) { maxlev2 = 6; } - levwav = min(maxlev2, levwav); - - //printf("levwav = %d\n",levwav); + levwav = rtengine::min(maxlev2, levwav); #ifdef _OPENMP int numthreads = 1; int maxnumberofthreadsforwavelet = 0; //reduce memory for big tile size - if(kall != 0) { - if(realtile <= 22) { + if (kall != 0) { + if (realtile <= 22) { maxnumberofthreadsforwavelet = 2; } - if(realtile <= 20) { + if (realtile <= 20) { maxnumberofthreadsforwavelet = 3; } - if(realtile <= 18) { + if (realtile <= 18) { maxnumberofthreadsforwavelet = 4; } - if(realtile <= 16) { + if (realtile <= 16) { maxnumberofthreadsforwavelet = 6; } - if(realtile <= 14) { + if (realtile <= 14) { maxnumberofthreadsforwavelet = 8; } - //printf("maxNRT=%d\n",maxnumberofthreadsforwavelet); - if((maxnumberofthreadsforwavelet == 6 || maxnumberofthreadsforwavelet == 8) && levwav == 10) { + if ((maxnumberofthreadsforwavelet == 6 || maxnumberofthreadsforwavelet == 8) && levwav == 10) { maxnumberofthreadsforwavelet -= 2; } - if(levwav <= 7 && maxnumberofthreadsforwavelet == 8) { + if (levwav <= 7 && maxnumberofthreadsforwavelet == 8) { maxnumberofthreadsforwavelet = 0; } } - //printf("maxthre=%d\n",maxnumberofthreadsforwavelet); // Calculate number of tiles. If less than omp_get_max_threads(), then limit num_threads to number of tiles - if( options.rgbDenoiseThreadLimit > 0) { - maxnumberofthreadsforwavelet = min(max(options.rgbDenoiseThreadLimit / 2, 1), maxnumberofthreadsforwavelet); + if (options.rgbDenoiseThreadLimit > 0) { + maxnumberofthreadsforwavelet = rtengine::LIM(options.rgbDenoiseThreadLimit / 2, 1, maxnumberofthreadsforwavelet); } - numthreads = MIN(numtiles, omp_get_max_threads()); + numthreads = rtengine::min(numtiles, omp_get_max_threads()); - if(maxnumberofthreadsforwavelet > 0) { - numthreads = MIN(numthreads, maxnumberofthreadsforwavelet); + if (maxnumberofthreadsforwavelet > 0) { + numthreads = rtengine::min(numthreads, maxnumberofthreadsforwavelet); } #ifdef _OPENMP wavNestedLevels = omp_get_max_threads() / numthreads; bool oldNested = omp_get_nested(); - if(wavNestedLevels < 2) { + if (wavNestedLevels < 2) { wavNestedLevels = 1; } else { omp_set_nested(true); } - if(maxnumberofthreadsforwavelet > 0) - while(wavNestedLevels * numthreads > maxnumberofthreadsforwavelet) { + if (maxnumberofthreadsforwavelet > 0) + while (wavNestedLevels * numthreads > maxnumberofthreadsforwavelet) { wavNestedLevels--; } #endif - if(settings->verbose) { + if (settings->verbose) { printf("Ip Wavelet uses %d main thread(s) and up to %d nested thread(s) for each main thread\n", numthreads, wavNestedLevels); } @@ -676,17 +655,22 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const float MaxP[10]; float MaxN[10]; + float meanab[10]; + float meanNab[10]; + float sigmaab[10]; + float sigmaNab[10]; + float MaxPab[10]; + float MaxNab[10]; + + array2D varchro(tilewidth, tileheight); + float** varhue = new float*[tileheight]; for (int i = 0; i < tileheight; i++) { varhue[i] = new float[tilewidth]; } - float** varchro = new float*[tileheight]; - for (int i = 0; i < tileheight; i++) { - varchro[i] = new float[tilewidth]; - } #ifdef _OPENMP #pragma omp for schedule(dynamic) collapse(2) @@ -694,18 +678,18 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const for (int tiletop = 0; tiletop < imheight; tiletop += tileHskip) { for (int tileleft = 0; tileleft < imwidth ; tileleft += tileWskip) { - int tileright = MIN(imwidth, tileleft + tilewidth); - int tilebottom = MIN(imheight, tiletop + tileheight); + int tileright = rtengine::min(imwidth, tileleft + tilewidth); + int tilebottom = rtengine::min(imheight, tiletop + tileheight); int width = tileright - tileleft; int height = tilebottom - tiletop; LabImage * labco; float **Lold = nullptr; float *LoldBuffer = nullptr; - if(numtiles == 1) { // untiled processing => we can use output buffer for labco + if (numtiles == 1) { // untiled processing => we can use output buffer for labco labco = dst; - if(cp.avoi) { // we need a buffer to hold a copy of the L channel + if (cp.avoi) { // we need a buffer to hold a copy of the L channel Lold = new float*[tileheight]; LoldBuffer = new float[tilewidth * tileheight]; memcpy(LoldBuffer, lab->L[0], tilewidth * tileheight * sizeof(float)); @@ -725,40 +709,35 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const #endif for (int i = tiletop; i < tilebottom; i++) { - int i1 = i - tiletop; - int j; + const int i1 = i - tiletop; + int j = tileleft; #ifdef __SSE2__ - __m128 c327d68v = _mm_set1_ps(327.68f); - __m128 av, bv, huev, chrov; + const vfloat c327d68v = F2V(327.68f); - for (j = tileleft; j < tileright - 3; j += 4) { - int j1 = j - tileleft; - av = LVFU(lab->a[i][j]); - bv = LVFU(lab->b[i][j]); - huev = xatan2f(bv, av); - chrov = vsqrtf(SQRV(av) + SQRV(bv)) / c327d68v; - _mm_storeu_ps(&varhue[i1][j1], huev); - _mm_storeu_ps(&varchro[i1][j1], chrov); + for (; j < tileright - 3; j += 4) { + const int j1 = j - tileleft; + const vfloat av = LVFU(lab->a[i][j]); + const vfloat bv = LVFU(lab->b[i][j]); + STVFU(varhue[i1][j1], xatan2f(bv, av)); + STVFU(varchro[i1][j1], vsqrtf(SQRV(av) + SQRV(bv)) / c327d68v); - if(labco != lab) { - _mm_storeu_ps(&(labco->L[i1][j1]), LVFU(lab->L[i][j])); - _mm_storeu_ps(&(labco->a[i1][j1]), av); - _mm_storeu_ps(&(labco->b[i1][j1]), bv); + if (labco != lab) { + STVFU((labco->L[i1][j1]), LVFU(lab->L[i][j])); + STVFU((labco->a[i1][j1]), av); + STVFU((labco->b[i1][j1]), bv); } } -#else - j = tileleft; #endif for (; j < tileright; j++) { - int j1 = j - tileleft; - float a = lab->a[i][j]; - float b = lab->b[i][j]; + const int j1 = j - tileleft; + const float a = lab->a[i][j]; + const float b = lab->b[i][j]; varhue[i1][j1] = xatan2f(b, a); varchro[i1][j1] = (sqrtf(a * a + b * b)) / 327.68f; - if(labco != lab) { + if (labco != lab) { labco->L[i1][j1] = lab->L[i][j]; labco->a[i1][j1] = a; labco->b[i1][j1] = b; @@ -767,7 +746,7 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const } //to avoid artifacts in blue sky - if(params->wavelet.median) { + if (params->wavelet.median) { float** tmL; int wid = labco->W; int hei = labco->H; @@ -778,8 +757,8 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const tmL[i] = new float[wid]; } - for(int i = borderL; i < hei - borderL; i++ ) { - for(int j = borderL; j < wid - borderL; j++) { + for (int i = borderL; i < hei - borderL; i++) { + for (int j = borderL; j < wid - borderL; j++) { tmL[i][j] = labco->L[i][j]; } } @@ -790,14 +769,14 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const for (int i = 1; i < hei - 1; i++) { for (int j = 1; j < wid - 1; j++) { - if((varhue[i][j] < -1.3f && varhue[i][j] > - 2.5f) && (varchro[i][j] > 15.f && varchro[i][j] < 55.f) && labco->L[i][j] > 6000.f) { //blue sky + med3x3 ==> after for more effect use denoise - tmL[i][j] = median(labco->L[i][j] , labco->L[i - 1][j], labco->L[i + 1][j] , labco->L[i][j + 1], labco->L[i][j - 1], labco->L[i - 1][j - 1], labco->L[i - 1][j + 1], labco->L[i + 1][j - 1], labco->L[i + 1][j + 1]); //3x3 + if ((varhue[i][j] < -1.3f && varhue[i][j] > - 2.5f) && (varchro[i][j] > 15.f && varchro[i][j] < 55.f) && labco->L[i][j] > 6000.f) { //blue sky + med3x3 ==> after for more effect use denoise + tmL[i][j] = median(labco->L[i][j], labco->L[i - 1][j], labco->L[i + 1][j], labco->L[i][j + 1], labco->L[i][j - 1], labco->L[i - 1][j - 1], labco->L[i - 1][j + 1], labco->L[i + 1][j - 1], labco->L[i + 1][j + 1]); //3x3 } } } - for(int i = borderL; i < hei - borderL; i++ ) { - for(int j = borderL; j < wid - borderL; j++) { + for (int i = borderL; i < hei - borderL; i++) { + for (int j = borderL; j < wid - borderL; j++) { labco->L[i][j] = tmL[i][j]; } } @@ -810,7 +789,7 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const // end blue sky } - if(numtiles == 1) { + if (numtiles == 1) { // reduce the varhue array to get faster access in following processing and reduce peak memory usage float temphue[(tilewidth + 1) / 2] ALIGNED64; @@ -824,7 +803,7 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const memcpy(varhue[i], temphue, ((tilewidth + 1) / 2) * sizeof(float)); } - for(int i = (tileheight + 1) / 2; i < tileheight; i++) { + for (int i = (tileheight + 1) / 2; i < tileheight; i++) { delete [] varhue[i]; varhue[i] = nullptr; } @@ -841,38 +820,62 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const int levwavL = levwav; bool ref0 = false; - if((cp.lev0s > 0.f || cp.lev1s > 0.f || cp.lev2s > 0.f || cp.lev3s > 0.f) && cp.noiseena) { + if ((cp.lev0s > 0.f || cp.lev1s > 0.f || cp.lev2s > 0.f || cp.lev3s > 0.f) && cp.noiseena) { ref0 = true; } - // printf("LevwavL before: %d\n",levwavL); - if(cp.contrast == 0.f && !cp.tonemap && cp.conres == 0.f && cp.conresH == 0.f && cp.val == 0 && !ref0 && params->wavelet.CLmethod == "all") { // no processing of residual L or edge=> we probably can reduce the number of levels - while(levwavL > 0 && cp.mul[levwavL - 1] == 0.f) { // cp.mul[level] == 0.f means no changes to level + bool wavcurvecomp = false;//not enable if 0.75 + + if (wavblcurve) { + for (int i = 0; i < 500; i++) { + if (wavblcurve[i] != 0.) { + wavcurvecomp = true; + } + } + } + + bool exblurL = cp.blena && wavcurvecomp; + + if (exblurL) { + if (cp.mul[0] == 0.f) { + cp.mul[0] = 0.01f;//to always enable WaveletcontAllL if no contrast is nead + } + } + + if (!exblurL && cp.contrast == 0.f && cp.blurres == 0.f && !cp.tonemap && cp.conres == 0.f && cp.conresH == 0.f && cp.val == 0 && !ref0 && params->wavelet.CLmethod == "all") { // no processing of residual L or edge=> we probably can reduce the number of levels + while (levwavL > 0 && cp.mul[levwavL - 1] == 0.f) { // cp.mul[level] == 0.f means no changes to level levwavL--; } } - // printf("LevwavL after: %d\n",levwavL); - // if(cp.noiseena){ - if(levwavL < 4 ) { + if (cp.chromfi > 0.f || cp.chromco > 0.f) { + if (levwavL < 7) { + levwavL = 7; + } + } + + if (levwavL < 4) { levwavL = 4; //to allow edge => I always allocate 3 (4) levels..because if user select wavelet it is to do something !! } - // } - // else { - // if(levwavL < 3) levwavL=3;//to allow edge => I always allocate 3 (4) levels..because if user select wavelet it is to do something !! - // } - if(levwavL > 0) { - wavelet_decomposition* Ldecomp = new wavelet_decomposition (labco->data, labco->W, labco->H, levwavL, 1, skip, max(1, wavNestedLevels), DaubLen ); + if (settings->verbose) { + printf("Level decomp L=%i\n", levwavL); + } - if(!Ldecomp->memoryAllocationFailed) { + bool usechrom = cp.chromfi > 0.f || cp.chromco > 0.f; - float madL[8][3]; + if (levwavL > 0) { + const std::unique_ptr Ldecomp(new wavelet_decomposition(labco->data, labco->W, labco->H, levwavL, 1, skip, rtengine::max(1, wavNestedLevels), DaubLen)); + float madL[8][3]; + + if (!Ldecomp->memoryAllocationFailed) { + + // float madL[8][3]; #ifdef _OPENMP #pragma omp parallel for schedule(dynamic) collapse(2) num_threads(wavNestedLevels) if(wavNestedLevels>1) #endif - for (int lvl = 0; lvl < 4; lvl++) { + for (int lvl = 0; lvl < levwavL; lvl++) { for (int dir = 1; dir < 4; dir++) { int Wlvl_L = Ldecomp->level_W(lvl); int Hlvl_L = Ldecomp->level_H(lvl); @@ -885,39 +888,87 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const bool ref = false; - if((cp.lev0s > 0.f || cp.lev1s > 0.f || cp.lev2s > 0.f || cp.lev3s > 0.f) && cp.noiseena) { + if ((cp.lev0s > 0.f || cp.lev1s > 0.f || cp.lev2s > 0.f || cp.lev3s > 0.f) && cp.noiseena) { ref = true; } bool contr = false; - for(int f = 0; f < levwavL; f++) { - if(cp.mul[f] != 0.f) { + for (int f = 0; f < levwavL; f++) { + if (cp.mul[f] != 0.f) { contr = true; } } - if(cp.val > 0 || ref || contr) {//edge + if (cp.val > 0 || ref || contr) { //edge Evaluate2(*Ldecomp, mean, meanN, sigma, sigmaN, MaxP, MaxN); } //init for edge and denoise float vari[4]; - vari[0] = 8.f * SQR((cp.lev0n / 125.0) * (1.0 + cp.lev0n / 25.0)); - vari[1] = 8.f * SQR((cp.lev1n / 125.0) * (1.0 + cp.lev1n / 25.0)); - vari[2] = 8.f * SQR((cp.lev2n / 125.0) * (1.0 + cp.lev2n / 25.0)); - vari[3] = 8.f * SQR((cp.lev3n / 125.0) * (1.0 + cp.lev3n / 25.0)); + vari[0] = 8.f * SQR((cp.lev0n / 125.f) * (1.f + cp.lev0n / 25.f)); + vari[1] = 8.f * SQR((cp.lev1n / 125.f) * (1.f + cp.lev1n / 25.f)); + vari[2] = 8.f * SQR((cp.lev2n / 125.f) * (1.f + cp.lev2n / 25.f)); + vari[3] = 8.f * SQR((cp.lev3n / 125.f) * (1.f + cp.lev3n / 25.f)); + float kr3 = 1.f; - if((cp.lev0n > 0.1f || cp.lev1n > 0.1f || cp.lev2n > 0.1f || cp.lev3n > 0.1f) && cp.noiseena) { - int edge = 1; - vari[0] = max(0.0001f, vari[0]); - vari[1] = max(0.0001f, vari[1]); - vari[2] = max(0.0001f, vari[2]); - vari[3] = max(0.0001f, vari[3]); - float* noisevarlum = nullptr; // we need a dummy to pass it to WaveletDenoiseAllL + if (cp.lev3n < 10.f) { + kr3 = 0.f; + } else if (cp.lev3n < 30.f) { + kr3 = 0.5f; + } else if (cp.lev3n < 70.f) { + kr3 = 0.7f; + } else { + kr3 = 1.f; + } - WaveletDenoiseAllL(*Ldecomp, noisevarlum, madL, vari, edge); + if ((cp.lev0n > 0.1f || cp.lev1n > 0.1f || cp.lev2n > 0.1f || cp.lev3n > 0.1f) && cp.noiseena) { + int edge = 4; + vari[0] = rtengine::max(0.0001f, vari[0]); + vari[1] = rtengine::max(0.0001f, vari[1]); + vari[2] = rtengine::max(0.0001f, vari[2]); + vari[3] = rtengine::max(0.0001f, kr3 * vari[3]); + // float* noisevarlum = nullptr; // we need a dummy to pass it to WaveletDenoiseAllL + int GWL = labco->W; + int GHL = labco->H; + float* noisevarlum = new float[GHL * GWL]; + int GW2L = (GWL + 1) / 2; + + float nvlh[13] = {1.f, 1.f, 1.f, 1.f, 1.f, 1.f, 1.f, 1.f, 1.f, 1.f, 1.f, 0.7f, 0.5f}; //high value + float nvll[13] = {0.1f, 0.15f, 0.2f, 0.25f, 0.3f, 0.35f, 0.4f, 0.45f, 0.7f, 0.8f, 1.f, 1.f, 1.f}; //low value + + float seuillow = 3000.f;//low + float seuilhigh = 18000.f;//high + int i = 10 - cp.ballum; + float ac = (nvlh[i] - nvll[i]) / (seuillow - seuilhigh); + float bc = nvlh[i] - seuillow * ac; + +#ifdef _OPENMP + #pragma omp parallel for + +#endif + + for (int ir = 0; ir < GHL; ir++) + for (int jr = 0; jr < GWL; jr++) { + float lN = labco->L[ir][jr]; + + if (lN < seuillow) { + noisevarlum[(ir >> 1)*GW2L + (jr >> 1)] = nvlh[i]; + } else if (lN < seuilhigh) { + noisevarlum[(ir >> 1)*GW2L + (jr >> 1)] = ac * lN + bc; + } else { + noisevarlum[(ir >> 1)*GW2L + (jr >> 1)] = nvll[i]; + } + } + + if (cp.lev3n < 0.5f) { + WaveletDenoiseAllL(*Ldecomp, noisevarlum, madL, vari, edge, 1); + } else { + WaveletDenoiseAll_BiShrinkL(*Ldecomp, noisevarlum, madL, vari, edge, 1); + + WaveletDenoiseAllL(*Ldecomp, noisevarlum, madL, vari, edge, 1); + } } //Flat curve for Contrast=f(H) in levels @@ -933,118 +984,378 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const Chutili = true; } + WaveletcontAllL(labco, varhue, varchro, *Ldecomp, wavblcurve, cp, skip, mean, sigma, MaxP, MaxN, wavCLVCcurve, waOpacityCurveW, ChCurve, Chutili); - WaveletcontAllL(labco, varhue, varchro, *Ldecomp, cp, skip, mean, sigma, MaxP, MaxN, wavCLVCcurve, waOpacityCurveW, ChCurve, Chutili); - - if(cp.val > 0 || ref || contr || cp.diagcurv) {//edge + if (cp.val > 0 || ref || contr || cp.diagcurv) { //edge Evaluate2(*Ldecomp, mean, meanN, sigma, sigmaN, MaxP, MaxN); } WaveletcontAllLfinal(*Ldecomp, cp, mean, sigma, MaxP, waOpacityCurveWL); + //Evaluate2(*Ldecomp, cp, ind, mean, meanN, sigma, sigmaN, MaxP, MaxN, madL); - - Ldecomp->reconstruct(labco->data, cp.strength); - } - - delete Ldecomp; - } - - //Flat curve for H=f(H) in residual image - FlatCurve* hhCurve = new FlatCurve(params->wavelet.hhcurve); //curve H=f(H) - bool hhutili = false; - - if (!hhCurve || hhCurve->isIdentity()) { - if (hhCurve) { - delete hhCurve; - hhCurve = nullptr; - } - } else { - hhutili = true; - } - - - if(!hhutili) {//always a or b - int levwava = levwav; - - // printf("Levwava before: %d\n",levwava); - if(cp.chrores == 0.f && params->wavelet.CLmethod == "all" && !cp.cbena) { // no processing of residual ab => we probably can reduce the number of levels - while(levwava > 0 && !cp.diag && (((cp.CHmet == 2 && (cp.chro == 0.f || cp.mul[levwava - 1] == 0.f )) || (cp.CHmet != 2 && (levwava == 10 || (!cp.curv || cp.mulC[levwava - 1] == 0.f))))) && (!cp.opaRG || levwava == 10 || (cp.opaRG && cp.mulopaRG[levwava - 1] == 0.f)) && ((levwava == 10 || (cp.CHSLmet == 1 && cp.mulC[levwava - 1] == 0.f)))) { - levwava--; - } - } - - //printf("Levwava after: %d\n",levwava); - if(levwava > 0) { - wavelet_decomposition* adecomp = new wavelet_decomposition (labco->data + datalen, labco->W, labco->H, levwava, 1, skip, max(1, wavNestedLevels), DaubLen ); - - if(!adecomp->memoryAllocationFailed) { - WaveletcontAllAB(labco, varhue, varchro, *adecomp, waOpacityCurveW, cp, true); - adecomp->reconstruct(labco->data + datalen, cp.strength); + /* + Ldecomp->reconstruct(labco->data, cp.strength); + } + } + */ + if (!usechrom) { + Ldecomp->reconstruct(labco->data, cp.strength); } - delete adecomp; - } + float variC[7]; + float variCb[7]; - int levwavb = levwav; + float noisecfr = cp.chromfi; + float noiseccr = cp.chromco; - //printf("Levwavb before: %d\n",levwavb); - if(cp.chrores == 0.f && params->wavelet.CLmethod == "all" && !cp.cbena) { // no processing of residual ab => we probably can reduce the number of levels - while(levwavb > 0 && !cp.diag && (((cp.CHmet == 2 && (cp.chro == 0.f || cp.mul[levwavb - 1] == 0.f )) || (cp.CHmet != 2 && (levwavb == 10 || (!cp.curv || cp.mulC[levwavb - 1] == 0.f))))) && (!cp.opaBY || levwavb == 10 || (cp.opaBY && cp.mulopaBY[levwavb - 1] == 0.f)) && ((levwavb == 10 || (cp.CHSLmet == 1 && cp.mulC[levwavb - 1] == 0.f)))) { - levwavb--; - } - } - - // printf("Levwavb after: %d\n",levwavb); - if(levwavb > 0) { - wavelet_decomposition* bdecomp = new wavelet_decomposition (labco->data + 2 * datalen, labco->W, labco->H, levwavb, 1, skip, max(1, wavNestedLevels), DaubLen ); - - if(!bdecomp->memoryAllocationFailed) { - WaveletcontAllAB(labco, varhue, varchro, *bdecomp, waOpacityCurveW, cp, false); - bdecomp->reconstruct(labco->data + 2 * datalen, cp.strength); + if (cp.balchrom > 0.f) { + noisecfr = cp.chromfi * ((100.f + cp.balchrom) / 10.f); + noiseccr = cp.chromco + ((100.f + cp.balchrom) / 10.f); } - delete bdecomp; - } - } else {// a and b - int levwavab = levwav; - - // printf("Levwavab before: %d\n",levwavab); - if(cp.chrores == 0.f && !hhutili && params->wavelet.CLmethod == "all") { // no processing of residual ab => we probably can reduce the number of levels - while(levwavab > 0 && (((cp.CHmet == 2 && (cp.chro == 0.f || cp.mul[levwavab - 1] == 0.f )) || (cp.CHmet != 2 && (levwavab == 10 || (!cp.curv || cp.mulC[levwavab - 1] == 0.f))))) && (!cp.opaRG || levwavab == 10 || (cp.opaRG && cp.mulopaRG[levwavab - 1] == 0.f)) && ((levwavab == 10 || (cp.CHSLmet == 1 && cp.mulC[levwavab - 1] == 0.f)))) { - levwavab--; - } - } - - // printf("Levwavab after: %d\n",levwavab); - if(levwavab > 0) { - wavelet_decomposition* adecomp = new wavelet_decomposition (labco->data + datalen, labco->W, labco->H, levwavab, 1, skip, max(1, wavNestedLevels), DaubLen ); - wavelet_decomposition* bdecomp = new wavelet_decomposition (labco->data + 2 * datalen, labco->W, labco->H, levwavab, 1, skip, max(1, wavNestedLevels), DaubLen ); - - if(!adecomp->memoryAllocationFailed && !bdecomp->memoryAllocationFailed) { - WaveletcontAllAB(labco, varhue, varchro, *adecomp, waOpacityCurveW, cp, true); - WaveletcontAllAB(labco, varhue, varchro, *bdecomp, waOpacityCurveW, cp, false); - WaveletAandBAllAB(*adecomp, *bdecomp, cp, hhCurve, hhutili ); - - adecomp->reconstruct(labco->data + datalen, cp.strength); - bdecomp->reconstruct(labco->data + 2 * datalen, cp.strength); + float noisecfb = cp.chromfi; + float noiseccb = cp.chromco; + if (cp.balchrom < 0.f) { + noisecfb = cp.chromfi * ((100.f - cp.balchrom) / 10.f); + noiseccb = cp.chromco * ((100.f - cp.balchrom) / 10.f); } - delete adecomp; - delete bdecomp; + + if (noisecfr < 0.f) { + noisecfr = 0.0001f; + } + + if (noiseccr < 0.f) { + noiseccr = 0.0001f; + } + + if (noisecfb < 0.f) { + noisecfb = 0.0001f; + } + + if (noiseccb < 0.f) { + noiseccb = 0.0001f; + } + + int edge = 2; + variC[0] = SQR(noisecfr); + variC[1] = SQR(noisecfr); + variC[2] = SQR(noisecfr); + + variC[3] = SQR(noisecfr); + variC[4] = SQR(noisecfr); + variC[5] = SQR(noiseccr); + variC[6] = SQR(noiseccr); + + variCb[0] = SQR(noisecfb); + variCb[1] = SQR(noisecfb); + variCb[2] = SQR(noisecfb); + + variCb[3] = SQR(noisecfb); + variCb[4] = SQR(noisecfb); + variCb[5] = SQR(noiseccb); + variCb[6] = SQR(noiseccb); + + float k1 = 0.f; + float k2 = 0.f; + float k3 = 0.f; + + if (cp.chromfi < 0.2f) { + k1 = 0.f; + k2 = 0.f; + k3 = 0.f; + } else if (cp.chromfi < 0.3f) { + k1 = 0.1f; + k2 = 0.0f; + k3 = 0.f; + } else if (cp.chromfi < 0.5f) { + k1 = 0.2f; + k2 = 0.1f; + k3 = 0.f; + } else if (cp.chromfi < 0.8f) { + k1 = 0.3f; + k2 = 0.25f; + k3 = 0.f; + } else if (cp.chromfi < 1.f) { + k1 = 0.4f; + k2 = 0.25f; + k3 = 0.1f; + } else if (cp.chromfi < 2.f) { + k1 = 0.5f; + k2 = 0.3f; + k3 = 0.15f; + } else if (cp.chromfi < 3.f) { + k1 = 0.6f; + k2 = 0.45f; + k3 = 0.3f; + } else if (cp.chromfi < 4.f) { + k1 = 0.7f; + k2 = 0.5f; + k3 = 0.4f; + } else if (cp.chromfi < 5.f) { + k1 = 0.8f; + k2 = 0.6f; + k3 = 0.5f; + } else if (cp.chromfi < 6.f) { + k1 = 0.85f; + k2 = 0.7f; + k3 = 0.6f; + } else if (cp.chromfi < 8.f) { + k1 = 0.9f; + k2 = 0.8f; + k3 = 0.7f; + } else if (cp.chromfi < 10.f) { + k1 = 1.f; + k2 = 1.f; + k3 = 0.9f; + + } else { + k1 = 1.f; + k2 = 1.f; + k3 = 1.f; + } + + float minic = 0.0001f; + variC[0] = max(minic, variC[0]); + variC[1] = max(minic, k1 * variC[1]); + variC[2] = max(minic, k2 * variC[2]); + variC[3] = max(minic, k3 * variC[3]); + + variCb[0] = max(minic, variCb[0]); + variCb[1] = max(minic, k1 * variCb[1]); + variCb[2] = max(minic, k2 * variCb[2]); + variCb[3] = max(minic, k3 * variCb[3]); + + float k4 = 0.f; + float k5 = 0.f; + float k6 = 0.f; + + if (cp.chromco == 0.01f) { + k4 = 0.f; + k5 = 0.0f; + } else if (cp.chromco < 0.2f) { + k4 = 0.1f; + k5 = 0.0f; + } else if (cp.chromco < 0.5f) { + k4 = 0.15f; + k5 = 0.0f; + } else if (cp.chromco < 1.f) { + k4 = 0.15f; + k5 = 0.1f; + } else if (cp.chromco < 3.f) { + k4 = 0.3f; + k5 = 0.15f; + } else if (cp.chromco < 4.f) { + k4 = 0.6f; + k5 = 0.4f; + } else if (cp.chromco < 6.f) { + k4 = 0.8f; + k5 = 0.6f; + } else { + k4 = 1.f; + k5 = 1.f; + } + + variC[4] = max(0.0001f, k4 * variC[4]); + variC[5] = max(0.0001f, k5 * variC[5]); + variCb[4] = max(0.0001f, k4 * variCb[4]); + variCb[5] = max(0.0001f, k5 * variCb[5]); + + if (cp.chromco < 4.f) { + k6 = 0.f; + } else if (cp.chromco < 5.f) { + k6 = 0.4f; + } else if (cp.chromco < 6.f) { + k6 = 0.7f; + } else { + k6 = 1.f; + } + + variC[6] = max(0.0001f, k6 * variC[6]); + variCb[6] = max(0.0001f, k6 * variCb[6]); + /* + for (int y = 0; y < 7; y++) { + printf("y=%i madL=%f varia=%f variab=%f\n", y, madL[y][1], variC[y], variCb[y]); + } + */ + float nvch = 0.6f;//high value + float nvcl = 0.1f;//low value + + if (cp.chromco > 30.f) { + nvch = 0.8f; + nvcl = 0.4f; + } + + float seuil = 4000.f;//low + float seuil2 = 15000.f;//high + //ac and bc for transition + float ac = (nvch - nvcl) / (seuil - seuil2); + float bc = nvch - seuil * ac; + int GW = labco->W; + int GH = labco->H; + float* noisevarchrom = new float[GH * GW]; + //noisevarchrom in function chroma + int GW2 = (GW + 1) / 2; + float noisevarab_r = 100.f; + + for (int ir = 0; ir < GH; ir++) + for (int jr = 0; jr < GW; jr++) { + float cN = sqrt(SQR(labco->a[ir][jr]) + SQR(labco->b[ir][jr])); + + if (cN < seuil) { + noisevarchrom[(ir >> 1)*GW2 + (jr >> 1)] = nvch; + } else if (cN < seuil2) { + noisevarchrom[(ir >> 1)*GW2 + (jr >> 1)] = ac * cN + bc; + } else { + noisevarchrom[(ir >> 1)*GW2 + (jr >> 1)] = nvcl; + } + } + + + //Flat curve for H=f(H) in residual image + FlatCurve* hhCurve = new FlatCurve(params->wavelet.hhcurve); //curve H=f(H) + bool hhutili = false; + + if (!hhCurve || hhCurve->isIdentity()) { + if (hhCurve) { + delete hhCurve; + hhCurve = nullptr; + } + } else { + hhutili = true; + } + + bool exblurab = cp.chrwav > 0.f && exblurL; + + if (!hhutili) { //always a or b + int levwava = levwav; + + if (!exblurab && cp.chrores == 0.f && cp.blurcres == 0.f && params->wavelet.CLmethod == "all" && !cp.cbena) { // no processing of residual ab => we probably can reduce the number of levels + while (levwava > 0 && !cp.diag && (((cp.CHmet == 2 && (cp.chro == 0.f || cp.mul[levwava - 1] == 0.f)) || (cp.CHmet != 2 && (levwava == 10 || (!cp.curv || cp.mulC[levwava - 1] == 0.f))))) && (!cp.opaRG || levwava == 10 || (cp.opaRG && cp.mulopaRG[levwava - 1] == 0.f)) && ((levwava == 10 || (cp.CHSLmet == 1 && cp.mulC[levwava - 1] == 0.f)))) { + levwava--; + } + } + + if (cp.chromfi > 0.f || cp.chromco > 0.f) { + if (levwava < 7) { + levwava = 7; + } + } + + if (settings->verbose) { + printf("Leval decomp a=%i\n", levwava); + } + + if (levwava > 0) { + const std::unique_ptr adecomp(new wavelet_decomposition(labco->data + datalen, labco->W, labco->H, levwava, 1, skip, rtengine::max(1, wavNestedLevels), DaubLen)); + + if (!adecomp->memoryAllocationFailed) { + if (cp.noiseena && (cp.chromfi > 0.f || cp.chromfi > 0.f)) { + WaveletDenoiseAll_BiShrinkAB(*Ldecomp, *adecomp, noisevarchrom, madL, variC, edge, noisevarab_r, true, false, false, 1); + WaveletDenoiseAllAB(*Ldecomp, *adecomp, noisevarchrom, madL, variC, edge, noisevarab_r, true, false, false, 1); + } + + Evaluate2(*adecomp, meanab, meanNab, sigmaab, sigmaNab, MaxPab, MaxNab); + WaveletcontAllAB(labco, varhue, varchro, *adecomp, wavblcurve, waOpacityCurveW, cp, true, skip, meanab, sigmaab); + adecomp->reconstruct(labco->data + datalen, cp.strength); + } + } + + int levwavb = levwav; + + if (!exblurab && cp.chrores == 0.f && cp.blurcres == 0.f && params->wavelet.CLmethod == "all" && !cp.cbena) { // no processing of residual ab => we probably can reduce the number of levels + while (levwavb > 0 && !cp.diag && (((cp.CHmet == 2 && (cp.chro == 0.f || cp.mul[levwavb - 1] == 0.f)) || (cp.CHmet != 2 && (levwavb == 10 || (!cp.curv || cp.mulC[levwavb - 1] == 0.f))))) && (!cp.opaBY || levwavb == 10 || (cp.opaBY && cp.mulopaBY[levwavb - 1] == 0.f)) && ((levwavb == 10 || (cp.CHSLmet == 1 && cp.mulC[levwavb - 1] == 0.f)))) { + levwavb--; + } + } + + if (cp.chromfi > 0.f || cp.chromco > 0.f) { + if (levwavb < 7) { + levwavb = 7; + } + } + + if (settings->verbose) { + printf("Leval decomp b=%i\n", levwavb); + } + + + if (levwavb > 0) { + const std::unique_ptr bdecomp(new wavelet_decomposition(labco->data + 2 * datalen, labco->W, labco->H, levwavb, 1, skip, rtengine::max(1, wavNestedLevels), DaubLen)); + + if (!bdecomp->memoryAllocationFailed) { + if (cp.noiseena && (cp.chromfi > 0.f || cp.chromfi > 0.f)) { + WaveletDenoiseAll_BiShrinkAB(*Ldecomp, *bdecomp, noisevarchrom, madL, variCb, edge, noisevarab_r, true, false, false, 1); + WaveletDenoiseAllAB(*Ldecomp, *bdecomp, noisevarchrom, madL, variCb, edge, noisevarab_r, true, false, false, 1); + } + + Evaluate2(*bdecomp, meanab, meanNab, sigmaab, sigmaNab, MaxPab, MaxNab); + WaveletcontAllAB(labco, varhue, varchro, *bdecomp, wavblcurve, waOpacityCurveW, cp, false, skip, meanab, sigmaab); + bdecomp->reconstruct(labco->data + 2 * datalen, cp.strength); + } + } + } else {// a and b + int levwavab = levwav; + + if (!exblurab && cp.chrores == 0.f && cp.blurcres == 0.f && !hhutili && params->wavelet.CLmethod == "all") { // no processing of residual ab => we probably can reduce the number of levels + while (levwavab > 0 && (((cp.CHmet == 2 && (cp.chro == 0.f || cp.mul[levwavab - 1] == 0.f)) || (cp.CHmet != 2 && (levwavab == 10 || (!cp.curv || cp.mulC[levwavab - 1] == 0.f))))) && (!cp.opaRG || levwavab == 10 || (cp.opaRG && cp.mulopaRG[levwavab - 1] == 0.f)) && ((levwavab == 10 || (cp.CHSLmet == 1 && cp.mulC[levwavab - 1] == 0.f)))) { + levwavab--; + } + } + + if (cp.chromfi > 0.f || cp.chromco > 0.f) { + if (levwavab < 7) { + levwavab = 7; + } + } + + if (levwavab > 0) { + const std::unique_ptr adecomp(new wavelet_decomposition(labco->data + datalen, labco->W, labco->H, levwavab, 1, skip, rtengine::max(1, wavNestedLevels), DaubLen)); + const std::unique_ptr bdecomp(new wavelet_decomposition(labco->data + 2 * datalen, labco->W, labco->H, levwavab, 1, skip, rtengine::max(1, wavNestedLevels), DaubLen)); + + if (!adecomp->memoryAllocationFailed && !bdecomp->memoryAllocationFailed) { + if (cp.noiseena && (cp.chromfi > 0.f || cp.chromfi > 0.f)) { + WaveletDenoiseAll_BiShrinkAB(*Ldecomp, *adecomp, noisevarchrom, madL, variC, edge, noisevarab_r, true, false, false, 1); + WaveletDenoiseAllAB(*Ldecomp, *adecomp, noisevarchrom, madL, variC, edge, noisevarab_r, true, false, false, 1); + } + + Evaluate2(*adecomp, meanab, meanNab, sigmaab, sigmaNab, MaxPab, MaxNab); + WaveletcontAllAB(labco, varhue, varchro, *adecomp, wavblcurve, waOpacityCurveW, cp, true, skip, meanab, sigmaab); + WaveletDenoiseAll_BiShrinkAB(*Ldecomp, *bdecomp, noisevarchrom, madL, variCb, edge, noisevarab_r, true, false, false, 1); + WaveletDenoiseAllAB(*Ldecomp, *bdecomp, noisevarchrom, madL, variCb, edge, noisevarab_r, true, false, false, 1); + Evaluate2(*bdecomp, meanab, meanNab, sigmaab, sigmaNab, MaxPab, MaxNab); + + if (cp.noiseena && (cp.chromfi > 0.f || cp.chromfi > 0.f)) { + WaveletcontAllAB(labco, varhue, varchro, *bdecomp, wavblcurve, waOpacityCurveW, cp, false, skip, meanab, sigmaab); + WaveletAandBAllAB(*adecomp, *bdecomp, cp, hhCurve, hhutili); + } + + adecomp->reconstruct(labco->data + datalen, cp.strength); + bdecomp->reconstruct(labco->data + 2 * datalen, cp.strength); + + } + } + } + + delete[] noisevarchrom; + + if (hhCurve) { + delete hhCurve; + } + + if (usechrom) { + Ldecomp->reconstruct(labco->data, cp.strength); + } } } - if (hhCurve) { - delete hhCurve; - } - - if(numtiles > 1 || (numtiles == 1 /*&& cp.avoi*/)) {//in all case since I add contrast curve + if (numtiles > 1 || (numtiles == 1 /*&& cp.avoi*/)) { //in all case since I add contrast curve //calculate mask for feathering output tile overlaps float Vmask[height + overlap] ALIGNED16; float Hmask[width + overlap] ALIGNED16; - if(numtiles > 1) { + if (numtiles > 1) { for (int i = 0; i < height; i++) { Vmask[i] = 1; } @@ -1081,58 +1392,54 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const #endif for (int i = tiletop; i < tilebottom; i++) { - int i1 = i - tiletop; + const int i1 = i - tiletop; float L, a, b; #ifdef __SSE2__ - int rowWidth = tileright - tileleft; + const int rowWidth = tileright - tileleft; float atan2Buffer[rowWidth] ALIGNED64; float chprovBuffer[rowWidth] ALIGNED64; float xBuffer[rowWidth] ALIGNED64; float yBuffer[rowWidth] ALIGNED64; - if(cp.avoi) { - int col; - __m128 av, bv; - __m128 cv, yv, xv; - __m128 zerov = _mm_setzero_ps(); - __m128 onev = _mm_set1_ps(1.f); - __m128 c327d68v = _mm_set1_ps(327.68f); - vmask xyMask; + if (cp.avoi) { + int col = 0; + const vfloat onev = F2V(1.f); + const vfloat c327d68v = F2V(327.68f); - for(col = 0; col < rowWidth - 3; col += 4) { - av = LVFU(labco->a[i1][col]); - bv = LVFU(labco->b[i1][col]); + for (; col < rowWidth - 3; col += 4) { + const vfloat av = LVFU(labco->a[i1][col]); + const vfloat bv = LVFU(labco->b[i1][col]); STVF(atan2Buffer[col], xatan2f(bv, av)); - cv = vsqrtf(SQRV(av) + SQRV(bv)); - yv = av / cv; - xv = bv / cv; - xyMask = vmaskf_eq(zerov, cv); + const vfloat cv = vsqrtf(SQRV(av) + SQRV(bv)); + vfloat yv = av / cv; + vfloat xv = bv / cv; + const vmask xyMask = vmaskf_eq(ZEROV, cv); yv = vself(xyMask, onev, yv); - xv = vself(xyMask, zerov, xv); + xv = vselfnotzero(xyMask, xv); STVF(yBuffer[col], yv); STVF(xBuffer[col], xv); STVF(chprovBuffer[col], cv / c327d68v); } - for(; col < rowWidth; col++) { - float a = labco->a[i1][col]; - float b = labco->b[i1][col]; - atan2Buffer[col] = xatan2f(b, a); - float Chprov1 = sqrtf(SQR(a) + SQR(b)); - yBuffer[col] = (Chprov1 == 0.f) ? 1.f : a / Chprov1; - xBuffer[col] = (Chprov1 == 0.f) ? 0.f : b / Chprov1; - chprovBuffer[col] = Chprov1 / 327.68; + for (; col < rowWidth; col++) { + const float la = labco->a[i1][col]; + const float lb = labco->b[i1][col]; + atan2Buffer[col] = xatan2f(lb, la); + const float Chprov1 = sqrtf(SQR(la) + SQR(lb)); + yBuffer[col] = (Chprov1 == 0.f) ? 1.f : la / Chprov1; + xBuffer[col] = (Chprov1 == 0.f) ? 0.f : lb / Chprov1; + chprovBuffer[col] = Chprov1 / 327.68f; } } #endif for (int j = tileleft; j < tileright; j++) { - int j1 = j - tileleft; + const int j1 = j - tileleft; - if(cp.avoi) { //Gamut and Munsell + if (cp.avoi) { //Gamut and Munsell #ifdef __SSE2__ float HH = atan2Buffer[j1]; float Chprov1 = chprovBuffer[j1]; @@ -1149,10 +1456,9 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const sincosv.x = (Chprov1 == 0.0f) ? 0.f : b / (Chprov1); Chprov1 /= 327.68f; #endif - L = labco->L[i1][j1]; const float Lin = labco->L[i1][j1]; - if(wavclCurve && cp.finena) { + if (wavclCurve && cp.finena) { labco->L[i1][j1] = (0.5f * Lin + 1.5f * wavclCurve[Lin]) / 2.f; //apply contrast curve } @@ -1176,15 +1482,15 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const float correctionHue = 0.0f; // Munsell's correction float correctlum = 0.0f; Lprov1 = L / 327.68f; - float Chprov = sqrtf(SQR(a) + SQR(b)) / 327.68f; + const float Chprov = sqrtf(SQR(a) + SQR(b)) / 327.68f; #ifdef _DEBUG Color::AllMunsellLch(true, Lprov1, Lprov2, HH, Chprov, memChprov, correctionHue, correctlum, MunsDebugInfo); #else Color::AllMunsellLch(true, Lprov1, Lprov2, HH, Chprov, memChprov, correctionHue, correctlum); #endif - if(correctionHue != 0.f || correctlum != 0.f) { // only calculate sin and cos if HH changed - if(fabs(correctionHue) < 0.015f) { + if (correctionHue != 0.f || correctlum != 0.f) { // only calculate sin and cos if HH changed + if (std::fabs(correctionHue) < 0.015f) { HH += correctlum; // correct only if correct Munsell chroma very little. } @@ -1197,7 +1503,7 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const L = labco->L[i1][j1]; const float Lin = std::max(0.f, L); - if(wavclCurve && cp.finena) { + if (wavclCurve && cp.finena) { labco->L[i1][j1] = (0.5f * Lin + 1.5f * wavclCurve[Lin]) / 2.f; //apply contrast curve } @@ -1206,7 +1512,7 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const b = labco->b[i1][j1]; } - if(numtiles > 1) { + if (numtiles > 1) { float factor = Vmask[i1] * Hmask[j1]; dsttmp->L[i][j] += factor * L; dsttmp->a[i][j] += factor * a; @@ -1221,61 +1527,93 @@ void ImProcFunctions::ip_wavelet(LabImage * lab, LabImage * dst, int kall, const } } - if(LoldBuffer != nullptr) { + if (LoldBuffer != nullptr) { delete [] LoldBuffer; delete [] Lold; } - if(numtiles > 1) { + if (numtiles > 1) { delete labco; } } } for (int i = 0; i < tileheight; i++) - if(varhue[i] != nullptr) { + if (varhue[i] != nullptr) { delete [] varhue[i]; } delete [] varhue; - - for (int i = 0; i < tileheight; i++) { - delete [] varchro[i]; - } - - delete [] varchro; - } #ifdef _OPENMP omp_set_nested(oldNested); #endif - if(numtiles != 1) { + if (numtiles != 1) { dst->CopyFrom(dsttmp); delete dsttmp; } + if (waparams.softradend > 0.f && cp.finena) { + array2D ble(lab->W, lab->H); + array2D guid(lab->W, lab->H); + + bool multiTh = false; + +#ifdef _OPENMP + + if (numthreads > 1) { + multiTh = true; + } + + #pragma omp parallel for +#endif + + for (int ir = 0; ir < lab->H; ir++) { + for (int jr = 0; jr < lab->W; jr++) { + guid[ir][jr] = Color::L2Y(lab->L[ir][jr]) / 32768.f; + ble[ir][jr] = Color::L2Y(dst->L[ir][jr]) / 32768.f; + } + } + + constexpr double epsilmax = 0.002; + constexpr double epsilmin = 0.0005; + constexpr double aepsil = 0.01f * (epsilmax - epsilmin); + constexpr double bepsil = epsilmin; + const double epsil = aepsil * waparams.softradend + bepsil; + + const float blur = 10.f / scale * (0.001f + 0.8f * waparams.softradend); + + rtengine::guidedFilter(guid, ble, ble, blur, epsil, multiTh); + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < lab->H; ir++) { + for (int jr = 0; jr < lab->W; jr++) { + dst->L[ir][jr] = Color::computeXYZ2LabY(32768.f * ble[ir][jr]); + } + } + } + #ifdef _DEBUG delete MunsDebugInfo; #endif } -#undef TS -#undef fTS -#undef offset -#undef epsilon -void ImProcFunctions::Aver( float * RESTRICT DataList, int datalen, float &averagePlus, float &averageNeg, float &max, float &min) +void ImProcFunctions::Aver(float * RESTRICT DataList, int datalen, float &averagePlus, float &averageNeg, float &max, float &min) { //find absolute mean int countP = 0, countN = 0; double averaP = 0.0, averaN = 0.0; // use double precision for large summations - float thres = 5.f;//different fom zero to take into account only data large enough + constexpr float thres = 32.7f;//different fom zero to take into account only data large enough 32.7 = 0.1 in range 0..100 very low value max = 0.f; - min = 0.f; + min = RT_INFINITY_F; #ifdef _OPENMP #pragma omp parallel num_threads(wavNestedLevels) if(wavNestedLevels>1) #endif @@ -1285,22 +1623,14 @@ void ImProcFunctions::Aver( float * RESTRICT DataList, int datalen, float &aver #pragma omp for reduction(+:averaP,averaN,countP,countN) nowait #endif - for(int i = 0; i < datalen; i++) { - if(DataList[i] >= thres) { - averaP += DataList[i]; - - if(DataList[i] > lmax) { - lmax = DataList[i]; - } - + for (int i = 0; i < datalen; i++) { + if (DataList[i] >= thres) { + averaP += static_cast(DataList[i]); + lmax = rtengine::max(lmax, DataList[i]); countP++; - } else if(DataList[i] < -thres) { - averaN += DataList[i]; - - if(DataList[i] < lmin) { - lmin = DataList[i]; - } - + } else if (DataList[i] < -thres) { + averaN += static_cast(DataList[i]); + lmin = rtengine::min(lmin, DataList[i]); countN++; } } @@ -1309,18 +1639,18 @@ void ImProcFunctions::Aver( float * RESTRICT DataList, int datalen, float &aver #pragma omp critical #endif { - max = max > lmax ? max : lmax; - min = min < lmin ? min : lmin; + max = rtengine::max(max, lmax); + min = rtengine::min(min, lmin); } } - if(countP > 0) { + if (countP > 0) { averagePlus = averaP / countP; } else { averagePlus = 0; } - if(countN > 0) { + if (countN > 0) { averageNeg = averaN / countN; } else { averageNeg = 0; @@ -1329,33 +1659,33 @@ void ImProcFunctions::Aver( float * RESTRICT DataList, int datalen, float &aver } -void ImProcFunctions::Sigma( float * RESTRICT DataList, int datalen, float averagePlus, float averageNeg, float &sigmaPlus, float &sigmaNeg) +void ImProcFunctions::Sigma(float * RESTRICT DataList, int datalen, float averagePlus, float averageNeg, float &sigmaPlus, float &sigmaNeg) { int countP = 0, countN = 0; double variP = 0.0, variN = 0.0; // use double precision for large summations - float thres = 5.f;//different fom zero to take into account only data large enough + float thres = 32.7f;//different fom zero to take into account only data large enough 32.7 = 0.1 in range 0..100 #ifdef _OPENMP #pragma omp parallel for reduction(+:variP,variN,countP,countN) num_threads(wavNestedLevels) if(wavNestedLevels>1) #endif - for(int i = 0; i < datalen; i++) { - if(DataList[i] >= thres) { - variP += SQR(DataList[i] - averagePlus); + for (int i = 0; i < datalen; i++) { + if (DataList[i] >= thres) { + variP += static_cast(SQR(DataList[i] - averagePlus)); countP++; - } else if(DataList[i] <= -thres) { - variN += SQR(DataList[i] - averageNeg); + } else if (DataList[i] <= -thres) { + variN += static_cast(SQR(DataList[i] - averageNeg)); countN++; } } - if(countP > 0) { + if (countP > 0) { sigmaPlus = sqrt(variP / countP); } else { sigmaPlus = 0; } - if(countN > 0) { + if (countN > 0) { sigmaNeg = sqrt(variN / countN); } else { sigmaNeg = 0; @@ -1363,7 +1693,7 @@ void ImProcFunctions::Sigma( float * RESTRICT DataList, int datalen, float aver } -void ImProcFunctions::Evaluate2(wavelet_decomposition &WaveletCoeffs_L, +void ImProcFunctions::Evaluate2(const wavelet_decomposition &WaveletCoeffs_L, float *mean, float *meanN, float *sigma, float *sigmaN, float *MaxP, float *MaxN) { //StopWatch Stop1("Evaluate2"); @@ -1376,12 +1706,65 @@ void ImProcFunctions::Evaluate2(wavelet_decomposition &WaveletCoeffs_L, float ** WavCoeffs_L = WaveletCoeffs_L.level_coeffs(lvl); - Eval2 (WavCoeffs_L, lvl, Wlvl_L, Hlvl_L, mean, meanN, sigma, sigmaN, MaxP, MaxN); + Eval2(WavCoeffs_L, lvl, Wlvl_L, Hlvl_L, mean, meanN, sigma, sigmaN, MaxP, MaxN); } } -void ImProcFunctions::Eval2 (float ** WavCoeffs_L, int level, - int W_L, int H_L, float *mean, float *meanN, float *sigma, float *sigmaN, float *MaxP, float *MaxN) + +void ImProcFunctions::calceffect(int level, float *mean, float *sigma, float *mea, float effect, float offs) +{ + float rap = 0.f; + float sig = 1.f; + + if (effect < 1.f) { + sig = effect; + } + + if (effect <= 1.f) { + rap = offs * mean[level] - sig * sigma[level]; + } + + if (rap > 0.f) { + mea[0] = rap; + } else { + mea[0] = mean[level] / 6.f; + } + + rap = 0.f; + + if (effect <= 1.f) { + rap = offs * mean[level] - 0.5f * sig * sigma[level]; + } + + if (rap > 0.f) { + mea[1] = rap; + } else { + mea[1] = mean[level] / 4.f; + } + + rap = 0.f; + + if (effect <= 1.f) { + rap = offs * mean[level] - 0.2f * sig * sigma[level]; + } + + if (rap > 0.f) { + mea[2] = rap; + } else { + mea[2] = mean[level] / 2.f; + } + + mea[3] = offs * mean[level]; // 50% data + mea[4] = offs * mean[level] + effect * sigma[level] / 2.f; + mea[5] = offs * mean[level] + effect * sigma[level]; //66% + mea[6] = offs * mean[level] + effect * 1.2f * sigma[level]; + mea[7] = offs * mean[level] + effect * 1.5f * sigma[level]; // + mea[8] = offs * mean[level] + effect * 2.f * sigma[level]; //95% + mea[9] = offs * mean[level] + effect * 2.5f * sigma[level]; //99% +} + +void ImProcFunctions::Eval2(float ** WavCoeffs_L, int level, + int W_L, int H_L, float *mean, float *meanN, float *sigma, float *sigmaN, float *MaxP, float *MaxN) { float avLP[4], avLN[4]; @@ -1431,17 +1814,17 @@ void ImProcFunctions::CompressDR(float *Source, int W_L, int H_L, float Compress float exponent; - if(DetailBoost > 0.f && DetailBoost < 0.05f ) { + if (DetailBoost > 0.f && DetailBoost < 0.05f) { float betemp = expf(-(2.f - DetailBoost + 0.694f)) - 1.f; //0.694 = log(2) - exponent = 1.2f * xlogf( -betemp); + exponent = 1.2f * xlogf(-betemp); exponent /= 20.f; - } else if(DetailBoost >= 0.05f && DetailBoost < 0.25f ) { + } else if (DetailBoost >= 0.05f && DetailBoost < 0.25f) { float betemp = expf(-(2.f - DetailBoost + 0.694f)) - 1.f; //0.694 = log(2) - exponent = 1.2f * xlogf( -betemp); + exponent = 1.2f * xlogf(-betemp); exponent /= (-75.f * DetailBoost + 23.75f); - } else if(DetailBoost >= 0.25f) { + } else if (DetailBoost >= 0.25f) { float betemp = expf(-(2.f - DetailBoost + 0.694f)) - 1.f; //0.694 = log(2) - exponent = 1.2f * xlogf( -betemp); + exponent = 1.2f * xlogf(-betemp); exponent /= (-2.f * DetailBoost + 5.5f); } else { exponent = (Compression - 1.0f) / 20.f; @@ -1455,17 +1838,17 @@ void ImProcFunctions::CompressDR(float *Source, int W_L, int H_L, float Compress #pragma omp parallel #endif { - vfloat exponentv = F2V(exponent); + const vfloat exponentv = F2V(exponent); #ifdef _OPENMP #pragma omp for #endif - for(int i = 0; i < n - 3; i += 4) { + for (int i = 0; i < n - 3; i += 4) { STVFU(Source[i], xexpf(xlogf(LVFU(Source[i])) * exponentv)); } } - for(int i = n - (n % 4); i < n; i++) { + for (int i = n - (n % 4); i < n; i++) { Source[i] = xexpf(xlogf(Source[i]) * exponent); } @@ -1474,7 +1857,7 @@ void ImProcFunctions::CompressDR(float *Source, int W_L, int H_L, float Compress #pragma omp parallel for #endif - for(int i = 0; i < n; i++) { + for (int i = 0; i < n; i++) { Source[i] = xexpf(xlogf(Source[i]) * exponent); } @@ -1488,7 +1871,7 @@ void ImProcFunctions::ContrastResid(float * WavCoeffs_L0, struct cont_params &cp float gamm = params->wavelet.gamma; cp.TMmeth = 2; //default after testing - if(cp.TMmeth == 1) { + if (cp.TMmeth == 1) { min0 = 0.0f; max0 = 32768.f; } else if (cp.TMmeth == 2) { @@ -1499,7 +1882,7 @@ void ImProcFunctions::ContrastResid(float * WavCoeffs_L0, struct cont_params &cp #pragma omp parallel for #endif - for(int i = 0; i < W_L * H_L; i++) { + for (int i = 0; i < W_L * H_L; i++) { WavCoeffs_L0[i] = (WavCoeffs_L0[i] - min0) / max0; WavCoeffs_L0[i] *= gamm; } @@ -1507,7 +1890,7 @@ void ImProcFunctions::ContrastResid(float * WavCoeffs_L0, struct cont_params &cp float Compression = expf(-stren); //This modification turns numbers symmetric around 0 into exponents. float DetailBoost = stren; - if(stren < 0.0f) { + if (stren < 0.0f) { DetailBoost = 0.0f; //Go with effect of exponent only if uncompressing. } @@ -1519,7 +1902,7 @@ void ImProcFunctions::ContrastResid(float * WavCoeffs_L0, struct cont_params &cp #pragma omp parallel for // removed schedule(dynamic,10) #endif - for(int ii = 0; ii < W_L * H_L; ii++) { + for (int ii = 0; ii < W_L * H_L; ii++) { WavCoeffs_L0[ii] = WavCoeffs_L0[ii] * max0 * (1.f / gamm) + min0; } } @@ -1532,14 +1915,14 @@ void ImProcFunctions::EPDToneMapResid(float * WavCoeffs_L0, unsigned int Iterat float stren = cp.tmstrength; - float edgest = params->epd.edgeStopping; - float sca = params->epd.scale; + float edgest = params->wavelet.edgs; + float sca = params->wavelet.scale; float gamm = params->wavelet.gamma; - float rew = params->epd.reweightingIterates; + int rew = 0; //params->epd.reweightingIterates; EdgePreservingDecomposition epd2(W_L, H_L); cp.TMmeth = 2; //default after testing - if(cp.TMmeth == 1) { + if (cp.TMmeth == 1) { min0 = 0.0f; max0 = 32768.f; } else if (cp.TMmeth == 2) { @@ -1551,7 +1934,7 @@ void ImProcFunctions::EPDToneMapResid(float * WavCoeffs_L0, unsigned int Iterat #pragma omp parallel for #endif - for(int i = 0; i < W_L * H_L; i++) { + for (int i = 0; i < W_L * H_L; i++) { WavCoeffs_L0[i] = (WavCoeffs_L0[i] - min0) / max0; WavCoeffs_L0[i] *= gamm; } @@ -1559,12 +1942,12 @@ void ImProcFunctions::EPDToneMapResid(float * WavCoeffs_L0, unsigned int Iterat float Compression = expf(-stren); //This modification turns numbers symmetric around 0 into exponents. float DetailBoost = stren; - if(stren < 0.0f) { + if (stren < 0.0f) { DetailBoost = 0.0f; //Go with effect of exponent only if uncompressing. } //Auto select number of iterates. Note that p->EdgeStopping = 0 makes a Gaussian blur. - if(Iterates == 0) { + if (Iterates == 0) { Iterates = (unsigned int)(edgest * 15.0f); } @@ -1576,12 +1959,12 @@ void ImProcFunctions::EPDToneMapResid(float * WavCoeffs_L0, unsigned int Iterat #pragma omp parallel for // removed schedule(dynamic,10) #endif - for(int ii = 0; ii < W_L * H_L; ii++) { + for (int ii = 0; ii < W_L * H_L; ii++) { WavCoeffs_L0[ii] = WavCoeffs_L0[ii] * max0 * (1.f / gamm) + min0; } } -void ImProcFunctions::WaveletcontAllLfinal(wavelet_decomposition &WaveletCoeffs_L, struct cont_params &cp, float *mean, float *sigma, float *MaxP, const WavOpacityCurveWL & waOpacityCurveWL) +void ImProcFunctions::WaveletcontAllLfinal(const wavelet_decomposition &WaveletCoeffs_L, const cont_params &cp, float *mean, float *sigma, float *MaxP, const WavOpacityCurveWL & waOpacityCurveWL) { int maxlvl = WaveletCoeffs_L.maxlevel(); float * WavCoeffs_L0 = WaveletCoeffs_L.coeff0; @@ -1591,36 +1974,32 @@ void ImProcFunctions::WaveletcontAllLfinal(wavelet_decomposition &WaveletCoeffs_ int Wlvl_L = WaveletCoeffs_L.level_W(lvl); int Hlvl_L = WaveletCoeffs_L.level_H(lvl); float ** WavCoeffs_L = WaveletCoeffs_L.level_coeffs(lvl); - finalContAllL (WavCoeffs_L, WavCoeffs_L0, lvl, dir, cp, Wlvl_L, Hlvl_L, mean, sigma, MaxP, waOpacityCurveWL); + finalContAllL(WavCoeffs_L, WavCoeffs_L0, lvl, dir, cp, Wlvl_L, Hlvl_L, mean, sigma, MaxP, waOpacityCurveWL); } } } -void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float **varchrom, wavelet_decomposition &WaveletCoeffs_L, +void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float **varchrom, const wavelet_decomposition &WaveletCoeffs_L, const Wavblcurve & wavblcurve, struct cont_params &cp, int skip, float *mean, float *sigma, float *MaxP, float *MaxN, const WavCurve & wavCLVCcurve, const WavOpacityCurveW & waOpacityCurveW, FlatCurve* ChCurve, bool Chutili) { - int maxlvl = WaveletCoeffs_L.maxlevel(); - int W_L = WaveletCoeffs_L.level_W(0); - int H_L = WaveletCoeffs_L.level_H(0); + const int maxlvl = WaveletCoeffs_L.maxlevel(); + const int W_L = WaveletCoeffs_L.level_W(0); + const int H_L = WaveletCoeffs_L.level_H(0); float * WavCoeffs_L0 = WaveletCoeffs_L.coeff0; - float maxh = 2.5f; //amplification contrast above mean - float maxl = 2.5f; //reduction contrast under mean float contrast = cp.contrast; - float multL = (float)contrast * (maxl - 1.f) / 100.f + 1.f; - float multH = (float) contrast * (maxh - 1.f) / 100.f + 1.f; double avedbl = 0.0; // use double precision for large summations float max0 = 0.f; float min0 = FLT_MAX; - if(contrast != 0.f || (cp.tonemap && cp.resena)) { // contrast = 0.f means that all will be multiplied by 1.f, so we can skip this step + if (contrast != 0.f || (cp.tonemap && cp.resena)) { // contrast = 0.f means that all will be multiplied by 1.f, so we can skip this step #ifdef _OPENMP #pragma omp parallel for reduction(+:avedbl) num_threads(wavNestedLevels) if(wavNestedLevels>1) #endif for (int i = 0; i < W_L * H_L; i++) { - avedbl += WavCoeffs_L0[i]; + avedbl += static_cast(WavCoeffs_L0[i]); } #ifdef _OPENMP @@ -1634,12 +2013,12 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * #pragma omp for #endif - for(int i = 0; i < W_L * H_L; i++) { - if(WavCoeffs_L0[i] < lminL) { + for (int i = 0; i < W_L * H_L; i++) { + if (WavCoeffs_L0[i] < lminL) { lminL = WavCoeffs_L0[i]; } - if(WavCoeffs_L0[i] > lmaxL) { + if (WavCoeffs_L0[i] > lmaxL) { lmaxL = WavCoeffs_L0[i]; } @@ -1649,11 +2028,11 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * #pragma omp critical #endif { - if(lminL < min0) { + if (lminL < min0) { min0 = lminL; } - if(lmaxL > max0) { + if (lmaxL > max0) { max0 = lmaxL; } } @@ -1662,10 +2041,9 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * } - // printf("MAXmax0=%f MINmin0=%f\n",max0,min0); //tone mapping - if(cp.tonemap && cp.contmet == 2 && cp.resena) { + if (cp.tonemap && cp.contmet == 2 && cp.resena) { //iterate = 5 EPDToneMapResid(WavCoeffs_L0, 0, skip, cp, W_L, H_L, max0, min0); @@ -1677,20 +2055,13 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * max0 /= 327.68f; min0 /= 327.68f; float ave = avedbl / (double)(W_L * H_L); - float av = ave / 327.68f; - float ah = (multH - 1.f) / (av - max0); // - float bh = 1.f - max0 * ah; - float al = (multL - 1.f) / (av - min0); - float bl = 1.f - min0 * al; - float factorx = 1.f; -// float *koeLi[9]; -// float maxkoeLi[9]; + float avg = ave / 32768.f; float *koeLi[12]; float maxkoeLi[12]; float *koeLibuffer = nullptr; - for(int y = 0; y < 12; y++) { + for (int y = 0; y < 12; y++) { maxkoeLi[y] = 0.f; //9 } @@ -1700,44 +2071,44 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * koeLi[i] = &koeLibuffer[i * W_L * H_L]; } - for(int j = 0; j < 12; j++) //9 + for (int j = 0; j < 12; j++) //9 for (int i = 0; i < W_L * H_L; i++) { koeLi[j][i] = 0.f; } + avg = LIM01(avg); + double contreal = 0.6 * contrast; + DiagonalCurve resid_contrast({ + DCT_NURBS, + 0, 0, + avg - avg * (0.6 - contreal / 250.0), avg - avg * (0.6 + contreal / 250.0), + avg + (1. - avg) * (0.6 - contreal / 250.0), avg + (1. - avg) * (0.6 + contreal / 250.0), + 1, 1 + }); + + #ifdef _OPENMP #pragma omp parallel num_threads(wavNestedLevels) if(wavNestedLevels>1) #endif { - if(contrast != 0.f && cp.resena && max0 > 0.0) { // contrast = 0.f means that all will be multiplied by 1.f, so we can skip this step + if (contrast != 0.f && cp.resena && max0 > 0.f) { // contrast = 0.f means that all will be multiplied by 1.f, so we can skip this step { + #ifdef _OPENMP #pragma omp for #endif - for (int i = 0; i < W_L * H_L; i++) { //contrast - if(WavCoeffs_L0[i] < 32768.f) { - float prov; - - if( WavCoeffs_L0[i] > ave) { - float kh = ah * (WavCoeffs_L0[i] / 327.68f) + bh; - prov = WavCoeffs_L0[i]; - WavCoeffs_L0[i] = ave + kh * (WavCoeffs_L0[i] - ave); - } else { - float kl = al * (WavCoeffs_L0[i] / 327.68f) + bl; - prov = WavCoeffs_L0[i]; - WavCoeffs_L0[i] = ave - kl * (ave - WavCoeffs_L0[i]); - } - - float diflc = WavCoeffs_L0[i] - prov; - diflc *= factorx; - WavCoeffs_L0[i] = prov + diflc; - } + for (int i = 0; i < W_L * H_L; i++) { + float buf = LIM01(WavCoeffs_L0[i] / 32768.f); + buf = resid_contrast.getVal(buf); + buf *= 32768.f; + WavCoeffs_L0[i] = buf; } } } - if(cp.tonemap && cp.contmet == 1 && cp.resena) { + + if (cp.tonemap && cp.contmet == 1 && cp.resena) { float maxp = max0 * 256.f; float minp = min0 * 256.f; #ifdef _OPENMP @@ -1745,67 +2116,127 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * #endif ContrastResid(WavCoeffs_L0, cp, W_L, H_L, maxp, minp); } + } + if ((cp.conres >= 0.f || cp.conresH >= 0.f) && cp.resena && !cp.oldsh) { // cp.conres = 0.f and cp.comresH = 0.f means that all will be multiplied by 1.f, so we can skip this step + LabImage *temp = nullptr; + temp = new LabImage(W_L, H_L); #ifdef _OPENMP - #pragma omp barrier + #pragma omp for #endif - if((cp.conres != 0.f || cp.conresH != 0.f) && cp.resena) { // cp.conres = 0.f and cp.comresH = 0.f means that all will be multiplied by 1.f, so we can skip this step -#ifdef _OPENMP - #pragma omp for nowait -#endif - - for (int i = 0; i < W_L * H_L; i++) { - float LL = WavCoeffs_L0[i]; - float LL100 = LL / 327.68f; - float tran = 5.f;//transition - //shadow - float alp = 3.f; //increase contrast sahdow in lowlights between 1 and ?? - - if(cp.th > (100.f - tran)) { - tran = 100.f - cp.th; - } - - if(LL100 < cp.th) { - float aalp = (1.f - alp) / cp.th; //no changes for LL100 = cp.th - float kk = aalp * LL100 + alp; - WavCoeffs_L0[i] *= (1.f + kk * cp.conres / 200.f); - } else if(LL100 < cp.th + tran) { - float ath = -cp.conres / tran; - float bth = cp.conres - ath * cp.th; - WavCoeffs_L0[i] *= (1.f + (LL100 * ath + bth) / 200.f); - } - - //highlight - tran = 5.f; - - if(cp.thH < (tran)) { - tran = cp.thH; - } - - if(LL100 > cp.thH) { - WavCoeffs_L0[i] *= (1.f + cp.conresH / 200.f); - } else if(LL100 > (cp.thH - tran)) { - float athH = cp.conresH / tran; - float bthH = cp.conresH - athH * cp.thH; - WavCoeffs_L0[i] *= (1.f + (LL100 * athH + bthH) / 200.f); - } + for (int i = 0; i < H_L; i++) { + for (int j = 0; j < W_L; j++) { + temp->L[i][j] = WavCoeffs_L0[i * W_L + j]; } } + { + ImProcFunctions::shadowsHighlights(temp, true, 1, cp.conresH, cp.conres, cp.radius, skip, cp.thH, cp.th); + } + +#ifdef _OPENMP + #pragma omp for +#endif + + for (int i = 0; i < H_L; i++) { + for (int j = 0; j < W_L; j++) { + WavCoeffs_L0[i * W_L + j] = temp->L[i][j]; + } + } + + delete temp; + + } + +#ifdef _OPENMP + #pragma omp barrier +#endif + + if ((cp.conres != 0.f || cp.conresH != 0.f) && cp.resena && cp.oldsh) { // cp.conres = 0.f and cp.comresH = 0.f means that all will be multiplied by 1.f, so we can skip this step +#ifdef _OPENMP + #pragma omp for nowait +#endif + + for (int i = 0; i < W_L * H_L; i++) { + float LL = WavCoeffs_L0[i]; + float LL100 = LL / 327.68f; + float tran = 5.f;//transition + //shadow + float alp = 3.f; //increase contrast sahdow in lowlights between 1 and ?? + + if (cp.th > (100.f - tran)) { + tran = 100.f - cp.th; + } + + if (LL100 < cp.th) { + float aalp = (1.f - alp) / cp.th; //no changes for LL100 = cp.th + float kk = aalp * LL100 + alp; + WavCoeffs_L0[i] *= (1.f + kk * cp.conres / 200.f); + } else if (LL100 < cp.th + tran) { + float ath = -cp.conres / tran; + float bth = cp.conres - ath * cp.th; + WavCoeffs_L0[i] *= (1.f + (LL100 * ath + bth) / 200.f); + } + + //highlight + tran = 5.f; + + if (cp.thH < (tran)) { + tran = cp.thH; + } + + if (LL100 > cp.thH) { + WavCoeffs_L0[i] *= (1.f + cp.conresH / 200.f); + } else if (LL100 > (cp.thH - tran)) { + float athH = cp.conresH / tran; + float bthH = cp.conresH - athH * cp.thH; + WavCoeffs_L0[i] *= (1.f + (LL100 * athH + bthH) / 200.f); + } + } + } + +//Blur luma + if (cp.blurres != 0.f && cp.resena) { + float rad = 0.7f * cp.blurres / skip; + float * bef = new float[W_L * H_L]; + float * aft = new float[W_L * H_L]; + + for (int i = 0; i < H_L * W_L; i++) { + bef[i] = WavCoeffs_L0[i]; + } + + boxblur(bef, aft, rad, W_L, H_L, false); + + for (int i = 0; i < H_L * W_L; i++) { + WavCoeffs_L0[i] = aft[i]; + } + + delete[] bef; + delete[] aft; + } + +// + int n0, n1, n2, n3, n4, n5, n6, n7, n8, n9, n10, n32; + n0 = n1 = n2 = n3 = n4 = n5 = n6 = n7 = n8 = n9 = n10 = n32 = 0; + +#ifdef _OPENMP + #pragma omp parallel num_threads(wavNestedLevels) if(wavNestedLevels>1) +#endif + { //enabled Lipschitz..replace simple by complex edge detection // I found this concept on the web (doctoral thesis on medical Imaging) // I was inspired by the principle of Canny and Lipschitz (continuity and derivability) // I adapted the principle but have profoundly changed the algorithm // One can 1) change all parameters and found good parameters; //one can also change in calckoe - float edd = 3.f; - float eddlow = 15.f; + constexpr float edd = 3.f; + constexpr float eddlow = 15.f; float eddlipinfl = 0.005f * cp.edgsens + 0.4f; float eddlipampl = 1.f + cp.edgampl / 50.f; - if(cp.detectedge) { //enabled Lipschitz control...more memory..more time... + if (cp.detectedge) { //enabled Lipschitz control...more memory..more time... float *tmCBuffer = new float[H_L * W_L]; float *tmC[H_L]; @@ -1819,11 +2250,8 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * for (int lvl = 0; lvl < 4; lvl++) { for (int dir = 1; dir < 4; dir++) { - int W_L = WaveletCoeffs_L.level_W(lvl); - int H_L = WaveletCoeffs_L.level_H(lvl); - float ** WavCoeffs_LL = WaveletCoeffs_L.level_coeffs(lvl); - calckoe(WavCoeffs_LL, cp, koeLi, lvl , dir, W_L, H_L, edd, maxkoeLi, tmC); + calckoe(WavCoeffs_LL, cp, koeLi, lvl, dir, WaveletCoeffs_L.level_W(lvl), WaveletCoeffs_L.level_H(lvl), edd, maxkoeLi, tmC); // return convolution KoeLi and maxkoeLi of level 0 1 2 3 and Dir Horiz, Vert, Diag } } @@ -1842,7 +2270,7 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * //treatment of koeLi and maxkoeLi float interm = 0.f; - if(cp.lip3 && cp.lipp) { + if (cp.lip3 && cp.lipp) { // comparison between pixel and neighbours const auto neigh = cp.neigh == 1; const auto kneigh = neigh ? 28.f : 38.f; @@ -1881,11 +2309,11 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * //Liamp=1 for eddlipinfl //liamp > 1 for alp >eddlipinfl and alph < 1 //Liamp < 1 for alp < eddlipinfl and alph > 0 - if(alph > 1.f) { + if (alph > 1.f) { alph = 1.f / alph; } - if(beta > 1.f) { + if (beta > 1.f) { beta = 1.f / beta; } @@ -1895,14 +2323,14 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * float bet = 1.f; //if(cp.lip3) {//enhance algorithm - if(alph > eddlipinfl && beta < 0.85f * eddlipinfl) { //0.85 arbitrary value ==> eliminate from edge if H V D too different + if (alph > eddlipinfl && beta < 0.85f * eddlipinfl) { //0.85 arbitrary value ==> eliminate from edge if H V D too different bet = beta; } //} float AmpLip = 1.f; - if(alph > eddlipinfl) { + if (alph > eddlipinfl) { AmpLip = alipinfl * alph + blipinfl; //If beta low reduce kampli kampli = SQR(bet) * AmpLip * aamp; } else { @@ -1922,7 +2350,7 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * interm *= kampli; - if(interm < cp.eddetthr / eddlow) { + if (interm < cp.eddetthr / eddlow) { interm = 0.01f; //eliminate too low values } @@ -1936,8 +2364,19 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * // end } + bool wavcurvecomp = false;//not enable if 0.75 + + if (wavblcurve) { + for (int i = 0; i < 500; i++) { + if (wavblcurve[i] != 0.) { + wavcurvecomp = true; + } + } + } + #ifdef _OPENMP - #pragma omp for schedule(dynamic) collapse(2) + // #pragma omp for schedule(dynamic) collapse(2) + #pragma omp for reduction(+:n0, n1, n2, n3, n4, n5, n6, n7, n8, n9, n10, n32) schedule(dynamic) collapse(2) #endif for (int dir = 1; dir < 4; dir++) { @@ -1948,21 +2387,96 @@ void ImProcFunctions::WaveletcontAllL(LabImage * labco, float ** varhue, float * float ** WavCoeffs_L = WaveletCoeffs_L.level_coeffs(lvl); - ContAllL (koeLi, maxkoeLi, true, maxlvl, labco, varhue, varchrom, WavCoeffs_L, WavCoeffs_L0, lvl, dir, cp, Wlvl_L, Hlvl_L, skip, mean, sigma, MaxP, MaxN, wavCLVCcurve, waOpacityCurveW, ChCurve, Chutili); + ContAllL(koeLi, maxkoeLi, true, maxlvl, labco, varhue, varchrom, WavCoeffs_L, WavCoeffs_L0, lvl, dir, cp, Wlvl_L, Hlvl_L, skip, mean, sigma, MaxP, MaxN, wavCLVCcurve, waOpacityCurveW, ChCurve, Chutili); + //blur level + float klev = 1.f; + + if (wavblcurve && wavcurvecomp && cp.blena) { + // printf("Blur level L\n"); + float mea[10]; + float effect = cp.bluwav; + float beta = 0.f; + float offs = 1.f; + + calceffect(lvl, mean, sigma, mea, effect, offs); + + float * bef = new float[Wlvl_L * Hlvl_L]; + float * aft = new float[Wlvl_L * Hlvl_L]; + + for (int co = 0; co < Hlvl_L * Wlvl_L; co++) { + bef[co] = WavCoeffs_L[dir][co]; + float WavCL = std::fabs(WavCoeffs_L[dir][co]); + + if (WavCL < mea[0]) { + beta = 0.05f; + n0++; + + if (WavCL < 32.7) { + n32++; + } + } else if (WavCL < mea[1]) { + beta = 0.2f; + n1++; + } else if (WavCL < mea[2]) { + beta = 0.7f; + n2++; + } else if (WavCL < mea[3]) { + beta = 1.f; //standard + n3++; + } else if (WavCL < mea[4]) { + beta = 1.f; + n4++; + } else if (WavCL < mea[5]) { + beta = 0.8f; //+sigma + n5++; + } else if (WavCL < mea[6]) { + beta = 0.6f; + n6++; + } else if (WavCL < mea[7]) { + beta = 0.4f; + n7++; + } else if (WavCL < mea[8]) { + beta = 0.2f; // + 2 sigma + n8++; + } else if (WavCL < mea[9]) { + beta = 0.1f; + n9++; + } else { + beta = 0.01f; + n10++; + } + } + + if (settings->verbose) { + printf("lvl=%i n0=%i n32=%i n1=%i n2=%i n3=%i n4=%i n5=%i n6=%i n7=%i n8=%i n9=%i n10=%i\n", lvl, n0, n0 - n32, n1, n2, n3, n4, n5, n6, n7, n8, n9, n10); + } + + klev = (wavblcurve[lvl * 55.5f]); + + klev *= beta * 100.f / skip; + boxblur(bef, aft, klev, Wlvl_L, Hlvl_L, false); + + for (int co = 0; co < Hlvl_L * Wlvl_L; co++) { + WavCoeffs_L[dir][co] = aft[co]; + } + + delete[] bef; + delete[] aft; + } } } } //delete edge detection - if(koeLibuffer) { + if (koeLibuffer) { delete [] koeLibuffer; } } -void ImProcFunctions::WaveletAandBAllAB(wavelet_decomposition &WaveletCoeffs_a, wavelet_decomposition &WaveletCoeffs_b, - struct cont_params &cp, FlatCurve* hhCurve, bool hhutili) +void ImProcFunctions::WaveletAandBAllAB(const wavelet_decomposition &WaveletCoeffs_a, const wavelet_decomposition &WaveletCoeffs_b, + const cont_params &cp, FlatCurve* hhCurve, bool hhutili) { // StopWatch Stop1("WaveletAandBAllAB"); if (hhutili && cp.resena) { // H=f(H) @@ -1989,15 +2503,13 @@ void ImProcFunctions::WaveletAandBAllAB(wavelet_decomposition &WaveletCoeffs_a, int k; for (k = 0; k < W_L - 3; k += 4) { - __m128 av = LVFU(WavCoeffs_a0[i * W_L + k]); - __m128 bv = LVFU(WavCoeffs_b0[i * W_L + k]); - __m128 huev = xatan2f(bv, av); - __m128 chrv = vsqrtf(SQRV(av) + SQRV(bv)); - STVF(huebuffer[k], huev); - STVF(chrbuffer[k], chrv); + const vfloat av = LVFU(WavCoeffs_a0[i * W_L + k]); + const vfloat bv = LVFU(WavCoeffs_b0[i * W_L + k]); + STVF(huebuffer[k], xatan2f(bv, av)); + STVF(chrbuffer[k], vsqrtf(SQRV(av) + SQRV(bv))); } - for(; k < W_L; k++) { + for (; k < W_L; k++) { huebuffer[k] = xatan2f(WavCoeffs_b0[i * W_L + k], WavCoeffs_a0[i * W_L + k]); chrbuffer[k] = sqrtf(SQR(WavCoeffs_b0[i * W_L + k]) + SQR(WavCoeffs_a0[i * W_L + k])) / 327.68f; } @@ -2018,7 +2530,7 @@ void ImProcFunctions::WaveletAandBAllAB(wavelet_decomposition &WaveletCoeffs_a, editWhatever->v(i,j) = valpar; } */ - float valparam = float((hhCurve->getVal(Color::huelab_to_huehsv2(hueR)) - 0.5f) * 1.7f) + hueR; //get H=f(H) 1.7 optimisation ! + float valparam = (static_cast(hhCurve->getVal(Color::huelab_to_huehsv2(hueR))) - 0.5f) * 1.7f + hueR; //get H=f(H) 1.7 optimisation ! float2 sincosval = xsincosf(valparam); WavCoeffs_a0[i * W_L + j] = chR * sincosval.y; WavCoeffs_b0[i * W_L + j] = chR * sincosval.x; @@ -2029,8 +2541,8 @@ void ImProcFunctions::WaveletAandBAllAB(wavelet_decomposition &WaveletCoeffs_a, } -void ImProcFunctions::WaveletcontAllAB(LabImage * labco, float ** varhue, float **varchrom, wavelet_decomposition &WaveletCoeffs_ab, const WavOpacityCurveW & waOpacityCurveW, - struct cont_params &cp, const bool useChannelA) +void ImProcFunctions::WaveletcontAllAB(LabImage * labco, float ** varhue, float **varchrom, const wavelet_decomposition &WaveletCoeffs_ab, const Wavblcurve & wavblcurve, const WavOpacityCurveW & waOpacityCurveW, + struct cont_params &cp, const bool useChannelA, int skip, float *meanab, float *sigmaab) { int maxlvl = WaveletCoeffs_ab.maxlevel(); @@ -2043,7 +2555,7 @@ void ImProcFunctions::WaveletcontAllAB(LabImage * labco, float ** varhue, float #pragma omp parallel num_threads(wavNestedLevels) if(wavNestedLevels>1) #endif { - if(cp.chrores != 0.f && cp.resena) { // cp.chrores == 0.f means all will be multiplied by 1.f, so we can skip the processing of residual + if (cp.chrores != 0.f && cp.resena) { // cp.chrores == 0.f means all will be multiplied by 1.f, so we can skip the processing of residual #ifdef _OPENMP #pragma omp for nowait @@ -2057,22 +2569,22 @@ void ImProcFunctions::WaveletcontAllAB(LabImage * labco, float ** varhue, float float modhue = varhue[ii][jj]; float scale = 1.f; - if(skyprot > 0.f) { - if((modhue < cp.t_ry && modhue > cp.t_ly)) { + if (skyprot > 0.f) { + if ((modhue < cp.t_ry && modhue > cp.t_ly)) { scale = (100.f - cp.sky) / 100.1f; - } else if((modhue >= cp.t_ry && modhue < cp.b_ry)) { + } else if ((modhue >= cp.t_ry && modhue < cp.b_ry)) { scale = (100.f - cp.sky) / 100.1f; float ar = (scale - 1.f) / (cp.t_ry - cp.b_ry); float br = scale - cp.t_ry * ar; scale = ar * modhue + br; - } else if((modhue > cp.b_ly && modhue < cp.t_ly)) { + } else if ((modhue > cp.b_ly && modhue < cp.t_ly)) { scale = (100.f - cp.sky) / 100.1f; float al = (scale - 1.f) / (-cp.b_ly + cp.t_ly); float bl = scale - cp.t_ly * al; scale = al * modhue + bl; } - } else if(skyprot < 0.f) { - if((modhue > cp.t_ry || modhue < cp.t_ly)) { + } else if (skyprot < 0.f) { + if ((modhue > cp.t_ry || modhue < cp.t_ly)) { scale = (100.f + cp.sky) / 100.1f; } @@ -2096,7 +2608,7 @@ void ImProcFunctions::WaveletcontAllAB(LabImage * labco, float ** varhue, float } } - if(cp.cbena && cp.resena) {//if user select Toning and color balance + if (cp.cbena && cp.resena) { //if user select Toning and color balance #ifdef _OPENMP #pragma omp for nowait @@ -2109,24 +2621,24 @@ void ImProcFunctions::WaveletcontAllAB(LabImage * labco, float ** varhue, float float sca = 1.f; //amplifer - reducter...about 1, but perhaps 0.6 or 1.3 - if(useChannelA) {//green red (little magenta) + if (useChannelA) { //green red (little magenta) //transition to avoid artifacts with 6 between 30 to 36 and 63 to 69 float aa = (cp.grmed - cp.grlow) / 6.f; float bb = cp.grlow - 30.f * aa; float aaa = (cp.grhigh - cp.grmed) / 6.f; float bbb = cp.grmed - 63.f * aaa; - if(LL < 30.f) { //shadows + if (LL < 30.f) { //shadows WavCoeffs_ab0[i] += cp.grlow * (sca) * 300.f; - } else if(LL >= 30.f && LL < 36.f) { //transition + } else if (LL >= 30.f && LL < 36.f) { //transition float tr = aa * LL + bb; WavCoeffs_ab0[i] += tr * (sca) * 300.f; - } else if(LL >= 36.f && LL < 63.f) { //midtones + } else if (LL >= 36.f && LL < 63.f) { //midtones WavCoeffs_ab0[i] += cp.grmed * (sca) * 300.f; - } else if(LL >= 63.f && LL < 69.f) { //transition + } else if (LL >= 63.f && LL < 69.f) { //transition float trh = aaa * LL + bbb; WavCoeffs_ab0[i] += trh * (sca) * 300.f; - } else if(LL >= 69.f) { //highlights + } else if (LL >= 69.f) { //highlights WavCoeffs_ab0[i] += cp.grhigh * (sca) * 300.f; } } else { //blue yellow @@ -2136,23 +2648,54 @@ void ImProcFunctions::WaveletcontAllAB(LabImage * labco, float ** varhue, float float aaa1 = (cp.blhigh - cp.blmed) / 6.f; float bbb1 = cp.blmed - 63.f * aaa1; - if(LL < 30.f) { + if (LL < 30.f) { WavCoeffs_ab0[i] += cp.bllow * (sca) * 300.f; - } else if(LL >= 30.f && LL < 36.f) { + } else if (LL >= 30.f && LL < 36.f) { float tr1 = aa1 * LL + bb1; WavCoeffs_ab0[i] += tr1 * (sca) * 300.f; - } else if(LL >= 36.f && LL < 63.f) { + } else if (LL >= 36.f && LL < 63.f) { WavCoeffs_ab0[i] += cp.blmed * (sca) * 300.f; - } else if(LL >= 63.f && LL < 69.f) { + } else if (LL >= 63.f && LL < 69.f) { float trh1 = aaa1 * LL + bbb1; WavCoeffs_ab0[i] += trh1 * (sca) * 300.f; - } else if(LL >= 69.f) { + } else if (LL >= 69.f) { WavCoeffs_ab0[i] += cp.blhigh * (sca) * 300.f; } } } } +//Blur chroma + if (cp.blurcres != 0.f && cp.resena) { + float rad = 0.7f * cp.blurcres / skip; + float * bef = new float[W_L * H_L]; + float * aft = new float[W_L * H_L]; + + for (int i = 0; i < H_L * W_L; i++) { + bef[i] = WavCoeffs_ab0[i]; + } + + boxblur(bef, aft, rad, W_L, H_L, false); + + for (int i = 0; i < H_L * W_L; i++) { + WavCoeffs_ab0[i] = aft[i]; + } + + delete[] bef; + delete[] aft; + } + + + bool wavcurvecomp = false;//not enable if 0.75 + + if (wavblcurve) { + for (int i = 0; i < 500; i++) { + if (wavblcurve[i] != 0.) { + wavcurvecomp = true; + } + } + } + #ifdef _OPENMP #pragma omp for schedule(dynamic) collapse(2) #endif @@ -2164,7 +2707,67 @@ void ImProcFunctions::WaveletcontAllAB(LabImage * labco, float ** varhue, float int Hlvl_ab = WaveletCoeffs_ab.level_H(lvl); float ** WavCoeffs_ab = WaveletCoeffs_ab.level_coeffs(lvl); - ContAllAB (labco, maxlvl, varhue, varchrom, WavCoeffs_ab, WavCoeffs_ab0, lvl, dir, waOpacityCurveW, cp, Wlvl_ab, Hlvl_ab, useChannelA); + ContAllAB(labco, maxlvl, varhue, varchrom, WavCoeffs_ab, WavCoeffs_ab0, lvl, dir, waOpacityCurveW, cp, Wlvl_ab, Hlvl_ab, useChannelA); + + if (wavblcurve && wavcurvecomp && cp.blena && cp.chrwav > 0.f) { + + float mea[10]; + float effect = cp.bluwav; + float beta = 0.f; + float offs = 1.f; + + calceffect(lvl, meanab, sigmaab, mea, effect, offs); + + float * bef = new float[Wlvl_ab * Hlvl_ab]; + float * aft = new float[Wlvl_ab * Hlvl_ab]; + float klev; + + for (int co = 0; co < Hlvl_ab * Wlvl_ab; co++) { + bef[co] = WavCoeffs_ab[dir][co]; + float WavCab = std::fabs(WavCoeffs_ab[dir][co]); + + if (WavCab < mea[0]) { + beta = 0.05f; + } else if (WavCab < mea[1]) { + beta = 0.2f; + } else if (WavCab < mea[2]) { + beta = 0.7f; + } else if (WavCab < mea[3]) { + beta = 1.f; //standard + } else if (WavCab < mea[4]) { + beta = 1.f; + } else if (WavCab < mea[5]) { + beta = 0.8f; //+sigma + } else if (WavCab < mea[6]) { + beta = 0.6f; + } else if (WavCab < mea[7]) { + beta = 0.4f; + } else if (WavCab < mea[8]) { + beta = 0.2f; // + 2 sigma + } else if (WavCab < mea[9]) { + beta = 0.1f; + } else { + beta = 0.0f; + } + + + } + + klev = (wavblcurve[lvl * 55.5f]); + + klev *= beta * cp.chrwav * 100.f / skip; + + boxblur(bef, aft, klev, Wlvl_ab, Hlvl_ab, false); + + for (int co = 0; co < Hlvl_ab * Wlvl_ab; co++) { + WavCoeffs_ab[dir][co] = aft[co]; + } + + delete[] bef; + delete[] aft; + } + + } } @@ -2175,12 +2778,11 @@ void ImProcFunctions::WaveletcontAllAB(LabImage * labco, float ** varhue, float //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -void ImProcFunctions::calckoe(float ** WavCoeffs_LL, const struct cont_params& cp, float *koeLi[12], int level, int dir, int W_L, int H_L, float edd, float *maxkoeLi, float **tmC) +void ImProcFunctions::calckoe(float ** WavCoeffs_LL, const cont_params& cp, float *koeLi[12], int level, int dir, int W_L, int H_L, float edd, float *maxkoeLi, float **tmC) { int borderL = 2; -// printf("cpedth=%f\n",cp.eddetthr); - if(cp.eddetthr < 30.f) { + if (cp.eddetthr < 30.f) { borderL = 1; // I calculate coefficients with r size matrix 3x3 r=1 ; 5x5 r=2; 7x7 r=3 @@ -2204,7 +2806,7 @@ void ImProcFunctions::calckoe(float ** WavCoeffs_LL, const struct cont_params& c } } - } else if(cp.eddetthr >= 30.f && cp.eddetthr < 50.f) { + } else if (cp.eddetthr >= 30.f && cp.eddetthr < 50.f) { borderL = 1; for (int i = 1; i < H_L - 1; i++) { //sigma=0.85 @@ -2220,7 +2822,7 @@ void ImProcFunctions::calckoe(float ** WavCoeffs_LL, const struct cont_params& c } - else if(cp.eddetthr >= 50.f && cp.eddetthr < 75.f) { + else if (cp.eddetthr >= 50.f && cp.eddetthr < 75.f) { borderL = 1; for (int i = 1; i < H_L - 1; i++) { @@ -2232,11 +2834,11 @@ void ImProcFunctions::calckoe(float ** WavCoeffs_LL, const struct cont_params& c } } - else if(cp.eddetthr >= 75.f) { + else if (cp.eddetthr >= 75.f) { borderL = 2; //if(cp.lip3 && level > 1) { - if(level > 1) {// do not activate 5x5 if level 0 or 1 + if (level > 1) { // do not activate 5x5 if level 0 or 1 for (int i = 2; i < H_L - 2; i++) { for (int j = 2; j < W_L - 2; j++) { @@ -2254,7 +2856,7 @@ void ImProcFunctions::calckoe(float ** WavCoeffs_LL, const struct cont_params& c // 4 9 12 9 4 // 2 4 5 4 2 // divi 159 - if(cp.eddetthr < 85.f) { //sigma=1.1 + if (cp.eddetthr < 85.f) { //sigma=1.1 tmC[i][j] = (15.f * WavCoeffs_LL[dir][i * W_L + j] + 10.f * WavCoeffs_LL[dir][(i - 1) * W_L + j] + 10.f * WavCoeffs_LL[dir][(i + 1) * W_L + j] + 10.f * WavCoeffs_LL[dir][i * W_L + j + 1] + 10.f * WavCoeffs_LL[dir][i * W_L + j - 1] + 7.f * WavCoeffs_LL[dir][(i - 1) * W_L + j - 1] + 7.f * WavCoeffs_LL[dir][(i - 1) * W_L + j + 1] + 7.f * WavCoeffs_LL[dir][(i + 1) * W_L + j - 1] + 7.f * WavCoeffs_LL[dir][(i + 1) * W_L + j + 1] @@ -2305,24 +2907,24 @@ void ImProcFunctions::calckoe(float ** WavCoeffs_LL, const struct cont_params& c thr2 += cp.eddet / 30.f; //to test float diffFactor = (cp.eddet / 100.f); - for(int i = 0; i < H_L; i++ ) { - for(int j = 0; j < W_L; j++) { + for (int i = 0; i < H_L; i++) { + for (int j = 0; j < W_L; j++) { koeLi[level * 3 + dir - 1][i * W_L + j] = 1.f; } } - for(int i = borderL; i < H_L - borderL; i++ ) { - for(int j = borderL; j < W_L - borderL; j++) { + for (int i = borderL; i < H_L - borderL; i++) { + for (int j = borderL; j < W_L - borderL; j++) { // my own algo : probably a little false, but simpler as Lipschitz ! // Thr2 = maximum of the function ==> Lipsitch says = probably edge // float temp = WavCoeffs_LL[dir][i*W_L + j]; // if(temp>=0.f && temp < thr) temp = thr; // if(temp < 0.f && temp > -thr) temp = -thr; - float temp = max(fabsf(WavCoeffs_LL[dir][i * W_L + j]), thr ); - koeLi[level * 3 + dir - 1][i * W_L + j] = min(thr2, fabs(tmC[i][j] / temp)); // limit maxi + float temp = rtengine::max(std::fabs(WavCoeffs_LL[dir][i * W_L + j]), thr); + koeLi[level * 3 + dir - 1][i * W_L + j] = rtengine::min(thr2, std::fabs(tmC[i][j] / temp)); // limit maxi //it will be more complicated to calculate both Wh and Wv, but we have also Wd==> pseudo Lipschitz - if(koeLi[level * 3 + dir - 1][i * W_L + j] > maxkoeLi[level * 3 + dir - 1]) { + if (koeLi[level * 3 + dir - 1][i * W_L + j] > maxkoeLi[level * 3 + dir - 1]) { maxkoeLi[level * 3 + dir - 1] = koeLi[level * 3 + dir - 1][i * W_L + j]; } @@ -2334,10 +2936,10 @@ void ImProcFunctions::calckoe(float ** WavCoeffs_LL, const struct cont_params& c } -void ImProcFunctions::finalContAllL (float ** WavCoeffs_L, float * WavCoeffs_L0, int level, int dir, struct cont_params &cp, - int W_L, int H_L, float *mean, float *sigma, float *MaxP, const WavOpacityCurveWL & waOpacityCurveWL) +void ImProcFunctions::finalContAllL(float ** WavCoeffs_L, float * WavCoeffs_L0, int level, int dir, const cont_params &cp, + int W_L, int H_L, float *mean, float *sigma, float *MaxP, const WavOpacityCurveWL & waOpacityCurveWL) { - if(cp.diagcurv && cp.finena && MaxP[level] > 0.f && mean[level] != 0.f && sigma[level] != 0.f ) { //curve + if (cp.diagcurv && cp.finena && MaxP[level] > 0.f && mean[level] != 0.f && sigma[level] != 0.f) { //curve float insigma = 0.666f; //SD float logmax = log(MaxP[level]); //log Max float rapX = (mean[level] + sigma[level]) / MaxP[level]; //rapport between sD / max @@ -2355,15 +2957,15 @@ void ImProcFunctions::finalContAllL (float ** WavCoeffs_L, float * WavCoeffs_L0, for (int i = 0; i < W_L * H_L; i++) { float absciss; - if(fabsf(WavCoeffs_L[dir][i]) >= (mean[level] + sigma[level])) { //for max - float valcour = xlogf(fabsf(WavCoeffs_L[dir][i])); + if (std::fabs(WavCoeffs_L[dir][i]) >= (mean[level] + sigma[level])) { //for max + float valcour = xlogf(std::fabs(WavCoeffs_L[dir][i])); float valc = valcour - logmax; float vald = valc * rap; absciss = xexpf(vald); - } else if(fabsf(WavCoeffs_L[dir][i]) >= mean[level]) { - absciss = asig * fabsf(WavCoeffs_L[dir][i]) + bsig; + } else if (std::fabs(WavCoeffs_L[dir][i]) >= mean[level]) { + absciss = asig * std::fabs(WavCoeffs_L[dir][i]) + bsig; } else { - absciss = amean * fabsf(WavCoeffs_L[dir][i]); + absciss = amean * std::fabs(WavCoeffs_L[dir][i]); } float kc = waOpacityCurveWL[absciss * 500.f] - 0.5f; @@ -2381,34 +2983,34 @@ void ImProcFunctions::finalContAllL (float ** WavCoeffs_L, float * WavCoeffs_L0, int choiceClevel = 0; - if(params->wavelet.CLmethod == "one") { + if (params->wavelet.CLmethod == "one") { choiceClevel = 0; - } else if(params->wavelet.CLmethod == "inf") { + } else if (params->wavelet.CLmethod == "inf") { choiceClevel = 1; - } else if(params->wavelet.CLmethod == "sup") { + } else if (params->wavelet.CLmethod == "sup") { choiceClevel = 2; - } else if(params->wavelet.CLmethod == "all") { + } else if (params->wavelet.CLmethod == "all") { choiceClevel = 3; } int choiceDir = 0; - if(params->wavelet.Dirmethod == "one") { + if (params->wavelet.Dirmethod == "one") { choiceDir = 1; - } else if(params->wavelet.Dirmethod == "two") { + } else if (params->wavelet.Dirmethod == "two") { choiceDir = 2; - } else if(params->wavelet.Dirmethod == "thr") { + } else if (params->wavelet.Dirmethod == "thr") { choiceDir = 3; - } else if(params->wavelet.Dirmethod == "all") { + } else if (params->wavelet.Dirmethod == "all") { choiceDir = 0; } int dir1 = (choiceDir == 2) ? 1 : 2; int dir2 = (choiceDir == 3) ? 1 : 3; - if(choiceClevel < 3) { // not all levels visible, paint residual - if(level == 0) { - if(cp.backm != 2) { // nothing to change when residual is used as background + if (choiceClevel < 3) { // not all levels visible, paint residual + if (level == 0) { + if (cp.backm != 2) { // nothing to change when residual is used as background float backGroundColor = (cp.backm == 1) ? 12000.f : 0.f; for (int i = 0; i < W_L * H_L; i++) { @@ -2418,66 +3020,66 @@ void ImProcFunctions::finalContAllL (float ** WavCoeffs_L, float * WavCoeffs_L0, } } - if(choiceClevel == 0) { // Only one level + if (choiceClevel == 0) { // Only one level - if(choiceDir == 0) { // All directions - if(level != choicelevel) { // zero all for the levels != choicelevel - for (int dir = 1; dir < 4; dir++) { + if (choiceDir == 0) { // All directions + if (level != choicelevel) { // zero all for the levels != choicelevel + for (int d = 1; d < 4; d++) { for (int i = 0; i < W_L * H_L; i++) { - WavCoeffs_L[dir][i] = 0.f; + WavCoeffs_L[d][i] = 0.f; } } } } else { // zero the unwanted directions for level == choicelevel - if(choicelevel >= cp.maxilev) { - for (int dir = 1; dir < 4; dir++) { + if (choicelevel >= cp.maxilev) { + for (int d = 1; d < 4; d++) { for (int i = 0; i < W_L * H_L; i++) { - WavCoeffs_L[dir][i] = 0.f; + WavCoeffs_L[d][i] = 0.f; } } - } else if(level != choicelevel) { // zero all for the levels != choicelevel + } else if (level != choicelevel) { // zero all for the levels != choicelevel for (int i = 0; i < W_L * H_L; i++) { WavCoeffs_L[dir1][i] = WavCoeffs_L[dir2][i] = 0.f; } } } - } else if(choiceClevel == 1) { // Only below level - if(choiceDir == 0) { // All directions - if(level > choicelevel) { - for (int dir = 1; dir < 4; dir++) { + } else if (choiceClevel == 1) { // Only below level + if (choiceDir == 0) { // All directions + if (level > choicelevel) { + for (int d = 1; d < 4; d++) { for (int i = 0; i < W_L * H_L; i++) { - WavCoeffs_L[dir][i] = 0.f; + WavCoeffs_L[d][i] = 0.f; } } } } else { // zero the unwanted directions for level >= choicelevel - if(level > choicelevel) { + if (level > choicelevel) { for (int i = 0; i < W_L * H_L; i++) { WavCoeffs_L[dir1][i] = WavCoeffs_L[dir2][i] = 0.f; } } } - } else if(choiceClevel == 2) { // Only above level - if(choiceDir == 0) { // All directions - if(level <= choicelevel) { - for (int dir = 1; dir < 4; dir++) { + } else if (choiceClevel == 2) { // Only above level + if (choiceDir == 0) { // All directions + if (level <= choicelevel) { + for (int d = 1; d < 4; d++) { for (int i = 0; i < W_L * H_L; i++) { - WavCoeffs_L[dir][i] = 0.f; + WavCoeffs_L[d][i] = 0.f; } } } } else { // zero the unwanted directions for level >= choicelevel - if(choicelevel >= cp.maxilev) { - for (int dir = 1; dir < 4; dir++) { + if (choicelevel >= cp.maxilev) { + for (int d = 1; d < 4; d++) { for (int i = 0; i < W_L * H_L; i++) { - WavCoeffs_L[dir][i] = 0.f; + WavCoeffs_L[d][i] = 0.f; } } } - else if(level <= choicelevel) { + else if (level <= choicelevel) { for (int i = 0; i < W_L * H_L; i++) { WavCoeffs_L[dir1][i] = WavCoeffs_L[dir2][i] = 0.f; } @@ -2488,32 +3090,78 @@ void ImProcFunctions::finalContAllL (float ** WavCoeffs_L, float * WavCoeffs_L0, } -void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschitz, int maxlvl, LabImage * labco, float ** varhue, float **varchrom, float ** WavCoeffs_L, float * WavCoeffs_L0, int level, int dir, struct cont_params &cp, - int W_L, int H_L, int skip, float *mean, float *sigma, float *MaxP, float *MaxN, const WavCurve & wavCLVCcurve, const WavOpacityCurveW & waOpacityCurveW, FlatCurve* ChCurve, bool Chutili) +void ImProcFunctions::ContAllL(float *koeLi[12], float *maxkoeLi, bool lipschitz, int maxlvl, LabImage * labco, float ** varhue, float **varchrom, float ** WavCoeffs_L, float * WavCoeffs_L0, int level, int dir, struct cont_params &cp, + int W_L, int H_L, int skip, float *mean, float *sigma, float *MaxP, float *MaxN, const WavCurve & wavCLVCcurve, const WavOpacityCurveW & waOpacityCurveW, FlatCurve* ChCurve, bool Chutili) { - assert (level >= 0); - assert (maxlvl > level); + assert(level >= 0); + assert(maxlvl > level); static const float scales[10] = {1.f, 2.f, 4.f, 8.f, 16.f, 32.f, 64.f, 128.f, 256.f, 512.f}; float scaleskip[10]; - for(int sc = 0; sc < 10; sc++) { + for (int sc = 0; sc < 10; sc++) { scaleskip[sc] = scales[sc] / skip; } - float t_r = 40.f; - float t_l = 10.f; - float b_r = 75.f; - float edd = 3.f; - float eddstrength = 1.3f; - float aedstr = (eddstrength - 1.f) / 90.f; - float bedstr = 1.f - 10.f * aedstr; + if (settings->verbose) { + printf("level=%i mean=%f sigma=%f maxp=%f\n", level, mean[level], sigma[level], MaxP[level]); + } + + constexpr float t_r = 40.f; + constexpr float t_l = 10.f; + constexpr float b_r = 75.f; + constexpr float edd = 3.f; + constexpr float eddstrength = 1.3f; + constexpr float aedstr = (eddstrength - 1.f) / 90.f; + constexpr float bedstr = 1.f - 10.f * aedstr; + + float mea[10]; + float beta = 1.f; + + if (cp.eff < 2.5f) { + float effect = cp.eff; + float offs = 1.f; + + calceffect(level, mean, sigma, mea, effect, offs); + + for (int co = 0; co < H_L * W_L; co++) { + float WavCL = std::fabs(WavCoeffs_L[dir][co]); + + if (WavCL < mea[0]) { + beta = 0.05f; + } else if (WavCL < mea[1]) { + beta = 0.2f; + } else if (WavCL < mea[2]) { + beta = 0.7f; + } else if (WavCL < mea[3]) { + beta = 1.f; //standard + } else if (WavCL < mea[4]) { + beta = 1.f; + } else if (WavCL < mea[5]) { + beta = 0.8f; //+sigma + } else if (WavCL < mea[6]) { + beta = 0.6f; + } else if (WavCL < mea[7]) { + beta = 0.4f; + } else if (WavCL < mea[8]) { + beta = 0.2f; // + 2 sigma + } else if (WavCL < mea[9]) { + beta = 0.1f; + } else { + beta = 0.0f; + } + + } + } + + + if (cp.val > 0 && cp.edgeena) { + - if(cp.val > 0 && cp.edgeena) { float * koe = nullptr; float maxkoe = 0.f; - if(!lipschitz) { + if (!lipschitz) { koe = new float [H_L * W_L]; for (int i = 0; i < W_L * H_L; i++) { @@ -2522,7 +3170,7 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit maxkoe = 0.f; - if(cp.detectedge) { + if (cp.detectedge) { float** tmC; int borderL = 1; tmC = new float*[H_L]; @@ -2548,33 +3196,31 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit - for(int i = borderL; i < H_L - borderL; i++ ) { - for(int j = borderL; j < W_L - borderL; j++) { + for (int i = borderL; i < H_L - borderL; i++) { + for (int j = borderL; j < W_L - borderL; j++) { // my own algo : probably a little false, but simpler as Lipschitz ! float thr = 40.f; //avoid artifact eg. noise...to test float thr2 = edd; //edd can be modified in option ed_detect thr2 += cp.eddet / 30.f; //to test float temp = WavCoeffs_L[dir][i * W_L + j]; - if(temp >= 0.f && temp < thr) { + if (temp >= 0.f && temp < thr) { temp = thr; } - if(temp < 0.f && temp > -thr) { + if (temp < 0.f && temp > -thr) { temp = -thr; } - koe[i * W_L + j] = min(thr2, fabs(tmC[i][j] / temp)); + koe[i * W_L + j] = rtengine::min(thr2, std::fabs(tmC[i][j] / temp)); - if(koe[i * W_L + j] > maxkoe) { - maxkoe = koe[i * W_L + j]; - } + maxkoe = rtengine::max(maxkoe, koe[i * W_L + j]); float diff = maxkoe - koe[i * W_L + j]; diff *= (cp.eddet / 100.f); float interm = maxkoe - diff; - if(interm < cp.eddetthr / 30.f) { + if (interm < cp.eddetthr / 30.f) { interm = 0.01f; } @@ -2601,24 +3247,21 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit value *= (atten01234 * scaleskip[1]); //for zoom < 100% reduce strength...I choose level 1...but!! } + value *= beta; float edge = 1.f; float lim0 = 20.f; //arbitrary limit for low radius and level between 2 or 3 to 30 maxi float lev = float (level); float repart = (float)cp.til; - float brepart; - if(cp.reinforce == 1) { - brepart = 3.f; - } - - if(cp.reinforce == 3) { - brepart = 0.5f; //arbitrary value to increase / decrease repart, between 1 and 0 - } - - float arepart = -(brepart - 1.f) / (lim0 / 60.f); if (cp.reinforce != 2) { - if(rad < lim0 / 60.f) { + const float brepart = + cp.reinforce == 1 + ? 3.f + : 0.5f; + const float arepart = -(brepart - 1.f) / (lim0 / 60.f); + + if (rad < lim0 / 60.f) { repart *= (arepart * rad + brepart); //linear repartition of repart } } @@ -2629,38 +3272,38 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit float ak = -(al0 - al10) / 10.f; //10 = maximum levels float bk = al0; float koef = ak * level + bk; //modulate for levels : more levels high, more koef low ==> concentrated action on low levels, without or near for high levels - float expkoef = -pow(fabs(rad - lev), koef); //reduce effect for high levels + float expkoef = -std::pow(std::fabs(rad - lev), koef); //reduce effect for high levels if (cp.reinforce == 3) { - if(rad < lim0 / 60.f && level == 0) { + if (rad < lim0 / 60.f && level == 0) { expkoef *= abs(repart); //reduce effect for low values of rad and level=0==> quasi only level 1 is effective } } if (cp.reinforce == 1) { - if(rad < lim0 / 60.f && level == 1) { + if (rad < lim0 / 60.f && level == 1) { expkoef /= repart; //increase effect for low values of rad and level=1==> quasi only level 0 is effective } } //take into account local contrast - float refin = value * exp (expkoef); + float refin = value * exp(expkoef); - if(cp.link && cp.noiseena) { //combi + if (cp.link && cp.noiseena) { //combi { - if(level == 0) { + if (level == 0) { refin *= (1.f + cp.lev0s / 50.f); // we can change this sensibility! } - if(level == 1) { + if (level == 1) { refin *= (1.f + cp.lev1s / 50.f); } - if(level == 2) { + if (level == 2) { refin *= (1.f + cp.lev2s / 50.f); } - if(level == 3) { + if (level == 3) { refin *= (1.f + cp.lev3s / 50.f); } } @@ -2668,7 +3311,7 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit float edgePrecalc = 1.f + refin; //estimate edge "pseudo variance" - if(cp.EDmet == 2 && MaxP[level] > 0.f) { //curve + if (cp.EDmet == 2 && MaxP[level] > 0.f) { //curve // if(exa) {//curve float insigma = 0.666f; //SD float logmax = log(MaxP[level]); //log Max @@ -2684,21 +3327,21 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit float kmul; int borderL = 1; - for(int i = borderL; i < H_L - borderL; i++ ) { - for(int j = borderL; j < W_L - borderL; j++) { + for (int i = borderL; i < H_L - borderL; i++) { + for (int j = borderL; j < W_L - borderL; j++) { int k = i * W_L + j; - if(cp.detectedge) { - if(!lipschitz) { - if(cp.eddet > 10.f) { + if (cp.detectedge) { + if (!lipschitz) { + if (cp.eddet > 10.f) { edge = (aedstr * cp.eddet + bedstr) * (edgePrecalc * (1.f + koe[k])) / (1.f + 0.9f * maxkoe); } else { edge = (edgePrecalc * (1.f + koe[k])) / (1.f + 0.9f * maxkoe); } } - if(lipschitz) { - if(level < 4) { + if (lipschitz) { + if (level < 4) { edge = 1.f + (edgePrecalc - 1.f) * (koeLi[level * 3][k]) / (1.f + 0.9f * maxkoeLi[level * 3 + dir - 1]); } else { edge = edgePrecalc; @@ -2708,17 +3351,17 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit edge = edgePrecalc; } - if(cp.edgcurv) { - if(fabs(WavCoeffs_L[dir][k]) >= (mean[level] + sigma[level])) { //for max - float valcour = log(fabs(WavCoeffs_L[dir][k])); + if (cp.edgcurv) { + if (std::fabs(WavCoeffs_L[dir][k]) >= (mean[level] + sigma[level])) { //for max + float valcour = xlogf(std::fabs(WavCoeffs_L[dir][k])); float valc = valcour - logmax; float vald = valc * rap; absciss = exp(vald); - } else if(fabs(WavCoeffs_L[dir][k]) >= mean[level] && fabs(WavCoeffs_L[dir][k]) < (mean[level] + sigma[level])) { - absciss = asig * fabs(WavCoeffs_L[dir][k]) + bsig; - } else if(fabs(WavCoeffs_L[dir][k]) < mean[level]) { - absciss = amean * fabs(WavCoeffs_L[dir][k]); + } else if (std::fabs(WavCoeffs_L[dir][k]) >= mean[level] && std::fabs(WavCoeffs_L[dir][k]) < (mean[level] + sigma[level])) { + absciss = asig * std::fabs(WavCoeffs_L[dir][k]) + bsig; + } else if (std::fabs(WavCoeffs_L[dir][k]) < mean[level]) { + absciss = amean * std::fabs(WavCoeffs_L[dir][k]); } // Threshold adjuster settings==> approximative for curve @@ -2728,50 +3371,46 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit // kmul about max ==> 9 // we can change these values // result is different not best or bad than threshold slider...but similar - float abssd = 4.f; //amplification reference - float bbssd = 2.f; //mini ampli - float maxamp = 2.5f; //maxi ampli at end - float maxampd = 10.f; //maxi ampli at end - float a_abssd = (maxamp - abssd) / 0.333f; - float b_abssd = maxamp - a_abssd; - float da_abssd = (maxampd - abssd) / 0.333f; - float db_abssd = maxampd - da_abssd; - float am = (abssd - bbssd) / 0.666f; + constexpr float abssd = 4.f; //amplification reference + constexpr float bbssd = 2.f; //mini ampli float kmuld = 0.f; - if(absciss > 0.666f && absciss < 1.f) { + if (absciss > 0.666f && absciss < 1.f) { + constexpr float maxamp = 2.5f; //maxi ampli at end + constexpr float maxampd = 10.f; //maxi ampli at end + constexpr float a_abssd = (maxamp - abssd) / 0.333f; + constexpr float b_abssd = maxamp - a_abssd; + constexpr float da_abssd = (maxampd - abssd) / 0.333f; + constexpr float db_abssd = maxampd - da_abssd; kmul = a_abssd * absciss + b_abssd; //about max ==> kinterm kmuld = da_abssd * absciss + db_abssd; } else { + constexpr float am = (abssd - bbssd) / 0.666f; kmul = kmuld = absciss * am + bbssd; } - kinterm = 1.f; - float kc = kmul * (wavCLVCcurve[absciss * 500.f] - 0.5f); - float kcd = kmuld * (wavCLVCcurve[absciss * 500.f] - 0.5f); + const float kc = kmul * (wavCLVCcurve[absciss * 500.f] - 0.5f); - if(kc >= 0.f) { + if (kc >= 0.f) { float reduceeffect = 0.6f; kinterm = 1.f + reduceeffect * kmul * (wavCLVCcurve[absciss * 500.f] - 0.5f); //about 1 to 3 general and big amplification for max (under 0) } else { + const float kcd = kmuld * (wavCLVCcurve[absciss * 500.f] - 0.5f); kinterm = 1.f - (SQR(kcd)) / 10.f; } - if(kinterm < 0.f) { + if (kinterm < 0.f) { kinterm = 0.01f; } edge *= kinterm; - - if(edge < 1.f) { - edge = 1.f; - } + edge = rtengine::max(edge, 1.f); } WavCoeffs_L[dir][k] *= edge; } } - } else if(cp.EDmet == 1) { //threshold adjuster + } else if (cp.EDmet == 1) { //threshold adjuster float MaxPCompare = MaxP[level] * SQR(cp.edg_max / 100.f); //100 instead of b_r...case if b_r < 100 float MaxNCompare = MaxN[level] * SQR(cp.edg_max / 100.f); //always reduce a little edge for near max values float edgeSdCompare = (mean[level] + 1.5f * sigma[level]) * SQR(cp.edg_sd / t_r); // 1.5 standard deviation #80% range between mean 50% and 80% @@ -2780,7 +3419,7 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit float edgeMeanFactor = cbrt(cp.edg_mean / t_l); float interm; - if(cp.edg_low < 10.f) { + if (cp.edg_low < 10.f) { interm = cbrt((5.f + cp.edg_low) / 5.f); } else { interm = 1.437f; //cbrt(3); @@ -2794,21 +3433,21 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit //for (int i=0; i 10.f) { + if (cp.detectedge) { + if (!lipschitz) { + if (cp.eddet > 10.f) { edge = (aedstr * cp.eddet + bedstr) * (edgePrecalc * (1.f + koe[k])) / (1.f + 0.9f * maxkoe); } else { edge = (edgePrecalc * (1.f + koe[k])) / (1.f + 0.9f * maxkoe); } } - if(lipschitz) { - if(level < 4) { + if (lipschitz) { + if (level < 4) { edge = 1.f + (edgePrecalc - 1.f) * (koeLi[level * 3][k]) / (1.f + 0.9f * maxkoeLi[level * 3 + dir - 1]); } else { edge = edgePrecalc; @@ -2828,17 +3467,18 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit // If we move sliders to the left, local contrast is reduced // if we move sliders to the right local contrast is increased // MaxP, MaxN, mean, sigma are calculated if necessary (val > 0) by evaluate2(), eval2(), aver() , sigma() - if(b_r < 100.f && cp.edg_max / b_r > 1.f) { //in case of b_r < 100 and slider move to right +// if (b_r < 100.f && cp.edg_max / b_r > 1.f) { //in case of b_r < 100 and slider move to right + if (cp.edg_max / b_r > 1.f) { //in case of b_r < 100 and slider move to right if (WavCoeffs_L[dir][k] > MaxPCompare * cp.edg_max / b_r) { edge *= edgMaxFsup; - if(edge < 1.f) { + if (edge < 1.f) { edge = 1.f; } } else if (WavCoeffs_L[dir][k] < MaxNCompare * cp.edg_max / b_r) { edge *= edgMaxFsup; - if(edge < 1.f) { + if (edge < 1.f) { edge = 1.f; } } @@ -2847,39 +3487,39 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit if (WavCoeffs_L[dir][k] > MaxPCompare) { edge *= edgeMaxFactor; - if(edge < 1.f) { + if (edge < 1.f) { edge = 1.f; } }//reduce edge if > new max else if (WavCoeffs_L[dir][k] < MaxNCompare) { edge *= edgeMaxFactor; - if(edge < 1.f) { + if (edge < 1.f) { edge = 1.f; } } - if (fabs(WavCoeffs_L[dir][k]) >= edgeMeanCompare && fabs(WavCoeffs_L[dir][k]) < edgeSdCompare) { - //if (fabs(WavCoeffs_L[dir][i]) > edgeSdCompare) { + if (std::fabs(WavCoeffs_L[dir][k]) >= edgeMeanCompare && std::fabs(WavCoeffs_L[dir][k]) < edgeSdCompare) { + //if (std::fabs(WavCoeffs_L[dir][i]) > edgeSdCompare) { edge *= edgeSdFactor; - if(edge < 1.f) { + if (edge < 1.f) { edge = 1.f; } }//modify effect if sd change - if (fabs(WavCoeffs_L[dir][k]) < edgeMeanCompare) { + if (std::fabs(WavCoeffs_L[dir][k]) < edgeMeanCompare) { edge *= edgeMeanFactor; - if(edge < 1.f) { + if (edge < 1.f) { edge = 1.f; } } // modify effect if mean change - if (fabs(WavCoeffs_L[dir][k]) < edgeLowCompare) { + if (std::fabs(WavCoeffs_L[dir][k]) < edgeLowCompare) { edge *= edgeLowFactor; - if(edge < 1.f) { + if (edge < 1.f) { edge = 1.f; } } @@ -2889,29 +3529,29 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit } } - if(!lipschitz) { + if (!lipschitz) { delete [] koe; } } - if(!cp.link && cp.noiseena) { //used both with denoise 1 2 3 + if (!cp.link && cp.noiseena) { //used both with denoise 1 2 3 float refine = 0.f; for (int i = 0; i < W_L * H_L; i++) { - if(level == 0) { + if (level == 0) { refine = cp.lev0s / 40.f; } - if(level == 1) { + if (level == 1) { refine = cp.lev1s / 40.f; } - if(level == 2) { + if (level == 2) { refine = cp.lev2s / 40.f; } - if(level == 3) { + if (level == 3) { refine = cp.lev3s / 40.f; } @@ -2922,57 +3562,55 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit float cpMul = cp.mul[level]; - if(cpMul != 0.f && cp.contena) { // cpMul == 0.f means all will be multiplied by 1.f, so we can skip this + if (cpMul != 0.f && cp.contena) { // cpMul == 0.f means all will be multiplied by 1.f, so we can skip this const float skinprot = params->wavelet.skinprotect; const float skinprotneg = -skinprot; const float factorHard = (1.f - skinprotneg / 100.f); - - //to adjust increase contrast with local contrast - - //for each pixel and each level + const float offs = params->wavelet.offset; + const float lowthr = params->wavelet.lowthr; + float mea[10]; + float effect = cp.sigm; float beta; - float mea[9]; - mea[0] = mean[level] / 6.f; - mea[1] = mean[level] / 2.f; - mea[2] = mean[level]; // 50% data - mea[3] = mean[level] + sigma[level] / 2.f; - mea[4] = mean[level] + sigma[level]; //66% - mea[5] = mean[level] + 1.2f * sigma[level]; - mea[6] = mean[level] + 1.5f * sigma[level]; // - mea[7] = mean[level] + 2.f * sigma[level]; //95% - mea[8] = mean[level] + 2.5f * sigma[level]; //99% + + calceffect(level, mean, sigma, mea, effect, offs); bool useChromAndHue = (skinprot != 0.f || cp.HSmet); float modchro; + float red0 = 0.005f * (110.f - lowthr); + float red1 = 0.008f * (110.f - lowthr); + float red2 = 0.011f * (110.f - lowthr); + for (int i = 0; i < W_L * H_L; i++) { float kLlev = 1.f; - if(cpMul < 0.f) { + if (cpMul < 0.f) { beta = 1.f; // disabled for negatives values "less contrast" } else { - float WavCL = fabsf(WavCoeffs_L[dir][i]); + float WavCL = std::fabs(WavCoeffs_L[dir][i]); //reduction amplification: max action between mean / 2 and mean + sigma // arbitrary coefficient, we can add a slider !! - if(WavCL < mea[0]) { - beta = 0.6f; //preserve very low contrast (sky...) - } else if(WavCL < mea[1]) { - beta = 0.8f; - } else if(WavCL < mea[2]) { + if (WavCL < mea[0]) { + beta = 0.4f * red0;//preserve very low contrast (sky...) + } else if (WavCL < mea[1]) { + beta = 0.5f * red1; + } else if (WavCL < mea[2]) { + beta = 0.7f * red2; + } else if (WavCL < mea[3]) { beta = 1.f; //standard - } else if(WavCL < mea[3]) { + } else if (WavCL < mea[4]) { beta = 1.f; - } else if(WavCL < mea[4]) { + } else if (WavCL < mea[5]) { beta = 0.8f; //+sigma - } else if(WavCL < mea[5]) { + } else if (WavCL < mea[6]) { beta = 0.6f; - } else if(WavCL < mea[6]) { + } else if (WavCL < mea[7]) { beta = 0.4f; - } else if(WavCL < mea[7]) { + } else if (WavCL < mea[8]) { beta = 0.2f; // + 2 sigma - } else if(WavCL < mea[8]) { + } else if (WavCL < mea[9]) { beta = 0.1f; } else { beta = 0.0f; @@ -2989,10 +3627,10 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit float LL = labco->L[ii * 2][jj * 2]; LL100 = LL100init = LL / 327.68f; LL100res = WavCoeffs_L0[i] / 327.68f; - float delta = fabs(LL100init - LL100res) / (maxlvl / 2); + float delta = std::fabs(LL100init - LL100res) / (maxlvl / 2); - for(int ml = 0; ml < maxlvl; ml++) { - if(ml < maxlvl / 2) { + for (int ml = 0; ml < maxlvl; ml++) { + if (ml < maxlvl / 2) { kH[ml] = (LL100res + ml * delta) / LL100res; // fixed a priori max to level middle } else { kH[ml] = (LL100init - ml * delta) / LL100res; @@ -3000,16 +3638,16 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit } - if(useChromAndHue) { + if (useChromAndHue) { float modhue = varhue[ii][jj]; modchro = varchrom[ii * 2][jj * 2]; // hue chroma skin with initial lab data scale = 1.f; - if(skinprot > 0.f) { - Color::SkinSatCbdl2 (LL100, modhue, modchro, skinprot, scale, true, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 0); //0 for skin and extand - } else if(skinprot < 0.f) { - Color::SkinSatCbdl2 (LL100, modhue, modchro, skinprotneg, scale, false, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 0); + if (skinprot > 0.f) { + Color::SkinSatCbdl2(LL100, modhue, modchro, skinprot, scale, true, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 0); //0 for skin and extand + } else if (skinprot < 0.f) { + Color::SkinSatCbdl2(LL100, modhue, modchro, skinprotneg, scale, false, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 0); if (scale == 1.f) { scale = factorHard; @@ -3020,14 +3658,13 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit } - if(Chutili) { + if (Chutili) { int i_i = i / W_L; int j_j = i - i_i * W_L; - double lr; float modhue2 = varhue[i_i][j_j]; - float valparam = float((ChCurve->getVal(lr = Color::huelab_to_huehsv2(modhue2)) - 0.5f)); //get valparam=f(H) + float valparam = static_cast(ChCurve->getVal(Color::huelab_to_huehsv2(modhue2))) - 0.5f; //get valparam=f(H) - if(valparam > 0.f) { + if (valparam > 0.f) { scale2 = 1.f + 3.f * valparam; //arbitrary value } else { scale2 = 1.f + 1.9f * valparam; //near 0 but not zero if curve # 0 @@ -3038,7 +3675,7 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit float diagacc = 1.f; float alpha = (1024.f + 15.f * (float) cpMul * scale * scale2 * beta * diagacc) / 1024.f ; - if(cp.HSmet && cp.contena) { + if (cp.HSmet && cp.contena) { float aaal = (1.f - alpha) / ((cp.b_lhl - cp.t_lhl) * kH[level]); float bbal = 1.f - aaal * cp.b_lhl * kH[level]; float aaar = (alpha - 1.f) / (cp.t_rhl - cp.b_rhl) * kH[level]; @@ -3049,24 +3686,24 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit float aaarS = (alpha - 1.f) / (cp.t_rsl - cp.b_rsl); float bbbrS = 1.f - cp.b_rsl * aaarS; - if(level <= cp.numlevH) { //in function of levels - if((LL100 > cp.t_lhl * kH[level] && LL100 < cp.t_rhl * kH[level])) { + if (level <= cp.numlevH) { //in function of levels + if ((LL100 > cp.t_lhl * kH[level] && LL100 < cp.t_rhl * kH[level])) { kLlev = alpha; - } else if((LL100 > cp.b_lhl * kH[level] && LL100 <= cp.t_lhl * kH[level])) { + } else if ((LL100 > cp.b_lhl * kH[level] && LL100 <= cp.t_lhl * kH[level])) { kLlev = aaal * LL100 + bbal; - } else if((LL100 > cp.t_rhl * kH[level] && LL100 <= cp.b_rhl * kH[level])) { + } else if ((LL100 > cp.t_rhl * kH[level] && LL100 <= cp.b_rhl * kH[level])) { kLlev = aaar * LL100 + bbbr; } else { kLlev = 1.f; } } - if(level >= (9 - cp.numlevS)) { - if((LL100 > cp.t_lsl && LL100 < cp.t_rsl)) { + if (level >= (9 - cp.numlevS)) { + if ((LL100 > cp.t_lsl && LL100 < cp.t_rsl)) { kLlev = alpha; - } else if((LL100 > cp.b_lsl && LL100 <= cp.t_lsl)) { + } else if ((LL100 > cp.b_lsl && LL100 <= cp.t_lsl)) { kLlev = aaalS * LL100 + bbalS; - } else if((LL100 > cp.t_rsl && LL100 <= cp.b_rsl)) { + } else if ((LL100 > cp.t_rsl && LL100 <= cp.b_rsl)) { kLlev = aaarS * LL100 + bbbrS; } else { kLlev = 1.f; @@ -3081,27 +3718,27 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit } } - if(waOpacityCurveW) { + if (waOpacityCurveW) { cp.opaW = true; } - if(cp.bam && cp.finena) { - if(cp.opaW && cp.BAmet == 2) { + if (cp.bam && cp.finena) { + if (cp.opaW && cp.BAmet == 2) { int iteration = cp.ite; int itplus = 7 + iteration; int itmoins = 7 - iteration; int med = maxlvl / 2; int it; - if(level < med) { + if (level < med) { it = itmoins; - } else if(level == med) { + } else if (level == med) { it = 7; - } else /*if(level > med)*/ { + } else { /*if(level > med)*/ it = itplus; } - for(int j = 0; j < it; j++) { + for (int j = 0; j < it; j++) { //float bal = cp.balan;//-100 +100 float kba = 1.f; @@ -3114,11 +3751,11 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit float k1 = 0.3f * (waOpacityCurveW[6.f * LL100] - 0.5f); //k1 between 0 and 0.5 0.5==> 1/6=0.16 float k2 = k1 * 2.f; - if(dir < 3) { + if (dir < 3) { kba = 1.f + k1; } - if(dir == 3) { + if (dir == 3) { kba = 1.f - k2; } @@ -3127,22 +3764,22 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit } } - if(cp.BAmet == 1) { + if (cp.BAmet == 1) { int iteration = cp.ite; int itplus = 7 + iteration; int itmoins = 7 - iteration; int med = maxlvl / 2; int it; - if(level < med) { + if (level < med) { it = itmoins; - } else if(level == med) { + } else if (level == med) { it = 7; - } else /*if(level > med)*/ { + } else { /*if(level > med)*/ it = itplus; } - for(int j = 0; j < it; j++) { + for (int j = 0; j < it; j++) { float bal = cp.balan;//-100 +100 float kba = 1.f; @@ -3154,17 +3791,17 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit float k1 = 600.f; float k2 = 300.f; float LL100 = labco->L[ii * 2][jj * 2] / 327.68f; - float aa = 4970.f; - float bb = -397000.f; - float b0 = 100000.f; - float a0 = -4970.f; + constexpr float aa = 4970.f; + constexpr float bb = -397000.f; + constexpr float b0 = 100000.f; + constexpr float a0 = -4970.f; - if(LL100 > 80.f) { + if (LL100 > 80.f) { k1 = aa * LL100 + bb; k2 = 0.5f * k1; } - if(LL100 < 20.f) { + if (LL100 < 20.f) { k1 = a0 * LL100 + b0; k2 = 0.5f * k1; } @@ -3173,11 +3810,11 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit //k2=300.f; //k1=0.3f*(waOpacityCurveW[6.f*LL100]-0.5f);//k1 between 0 and 0.5 0.5==> 1/6=0.16 //k2=k1*2.f; - if(dir < 3) { + if (dir < 3) { kba = 1.f + bal / k1; } - if(dir == 3) { + if (dir == 3) { kba = 1.f - bal / k2; } @@ -3189,16 +3826,16 @@ void ImProcFunctions::ContAllL (float *koeLi[12], float *maxkoeLi, bool lipschit } // to see each level of wavelet ...level from 0 to 8 - int choicelevel = params->wavelet.Lmethod - 1; - choicelevel = choicelevel == -1 ? 4 : choicelevel; +// int choicelevel = params->wavelet.Lmethod - 1; +// choicelevel = choicelevel == -1 ? 4 : choicelevel; } -void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, float **varchrom, float ** WavCoeffs_ab, float * WavCoeffs_ab0, int level, int dir, const WavOpacityCurveW & waOpacityCurveW, struct cont_params &cp, - int W_ab, int H_ab, const bool useChannelA) +void ImProcFunctions::ContAllAB(LabImage * labco, int maxlvl, float ** varhue, float **varchrom, float ** WavCoeffs_ab, float * WavCoeffs_ab0, int level, int dir, const WavOpacityCurveW & waOpacityCurveW, struct cont_params &cp, + int W_ab, int H_ab, const bool useChannelA) { float cpMul = cp.mul[level]; - if(cpMul != 0.f && cp.CHmet == 2 && cp.chro != 0.f && cp.chromena) { // cpMul == 0.f or cp.chro = 0.f means all will be multiplied by 1.f, so we can skip this + if (cpMul != 0.f && cp.CHmet == 2 && cp.chro != 0.f && cp.chromena) { // cpMul == 0.f or cp.chro = 0.f means all will be multiplied by 1.f, so we can skip this const float skinprot = params->wavelet.skinprotect; const float skinprotneg = -skinprot; const float factorHard = (1.f - skinprotneg / 100.f); @@ -3209,7 +3846,7 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, float alphaC = (1024.f + 15.f * cpMul * cpChrom / 50.f) / 1024.f ; for (int i = 0; i < W_ab * H_ab; i++) { - if(useSkinControl) { + if (useSkinControl) { int ii = i / W_ab; int jj = i - ii * W_ab; float LL100 = labco->L[ii * 2][jj * 2] / 327.68f; @@ -3218,10 +3855,10 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, // hue chroma skin with initial lab data float scale = 1.f; - if(skinprot > 0.f) { - Color::SkinSatCbdl2 (LL100, modhue, modchro, skinprot, scale, true, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 0); //0 for skin and extand - } else if(skinprot < 0.f) { - Color::SkinSatCbdl2 (LL100, modhue, modchro, skinprotneg, scale, false, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 0); + if (skinprot > 0.f) { + Color::SkinSatCbdl2(LL100, modhue, modchro, skinprot, scale, true, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 0); //0 for skin and extand + } else if (skinprot < 0.f) { + Color::SkinSatCbdl2(LL100, modhue, modchro, skinprotneg, scale, false, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 0); scale = (scale == 1.f) ? factorHard : 1.f; } @@ -3237,7 +3874,7 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, float cpMulC = cp.mulC[level]; // if( (cp.curv || cp.CHSLmet==1) && cp.CHmet!=2 && level < 9 && cpMulC != 0.f) { // cpMulC == 0.f means all will be multiplied by 1.f, so we can skip - if( cp.CHmet != 2 && level < 9 && cpMulC != 0.f && cp.chromena) { // cpMulC == 0.f means all will be multiplied by 1.f, so we can skip + if (cp.CHmet != 2 && level < 9 && cpMulC != 0.f && cp.chromena) { // cpMulC == 0.f means all will be multiplied by 1.f, so we can skip const float skinprot = params->wavelet.skinprotect; const float skinprotneg = -skinprot; const float factorHard = (1.f - skinprotneg / 100.f); @@ -3250,37 +3887,37 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, float scale = 1.f; float modchro = varchrom[ii * 2][jj * 2]; - if(useSkinControl) { + if (useSkinControl) { // hue chroma skin with initial lab data float LL100 = labco->L[ii * 2][jj * 2] / 327.68f; float modhue = varhue[ii][jj]; - if(skinprot > 0.f) { - Color::SkinSatCbdl2 (LL100, modhue, modchro, skinprot, scale, true, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 1); //1 for curve - } else if(skinprot < 0.f) { - Color::SkinSatCbdl2 (LL100, modhue, modchro, skinprotneg, scale, false, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 1); + if (skinprot > 0.f) { + Color::SkinSatCbdl2(LL100, modhue, modchro, skinprot, scale, true, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 1); //1 for curve + } else if (skinprot < 0.f) { + Color::SkinSatCbdl2(LL100, modhue, modchro, skinprotneg, scale, false, cp.b_l, cp.t_l, cp.t_r, cp.b_r, 1); scale = (scale == 1.f) ? factorHard : 1.f; } } float beta = (1024.f + 20.f * cpMulC * scale) / 1024.f ; - if(beta < 0.02f) { + if (beta < 0.02f) { beta = 0.02f; } float kClev = beta; - if(cp.CHmet == 1) { - if(level < cp.chrom) { + if (cp.CHmet == 1) { + if (level < cp.chrom) { //linear for saturated - if((modchro > cp.t_lsat && modchro < cp.t_rsat)) { + if ((modchro > cp.t_lsat && modchro < cp.t_rsat)) { kClev = beta; - } else if((modchro > cp.b_lsat && modchro <= cp.t_lsat)) { + } else if ((modchro > cp.b_lsat && modchro <= cp.t_lsat)) { float aaal = (1.f - beta) / (cp.b_lsat - cp.t_lsat); float bbal = 1.f - aaal * cp.b_lsat; kClev = aaal * modchro + bbal; - } else if((modchro > cp.t_rsat && modchro <= cp.b_rsat)) { + } else if ((modchro > cp.t_rsat && modchro <= cp.b_rsat)) { float aaar = (beta - 1.f) / (cp.t_rsat - cp.b_rsat); float bbbr = 1.f - cp.b_rsat * aaar; kClev = aaar * modchro + bbbr; @@ -3289,13 +3926,13 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, } } else { //linear for pastel - if((modchro > cp.t_lpast && modchro < cp.t_rpast)) { + if ((modchro > cp.t_lpast && modchro < cp.t_rpast)) { kClev = beta; - } else if((modchro > cp.b_lpast && modchro <= cp.t_lpast)) { + } else if ((modchro > cp.b_lpast && modchro <= cp.t_lpast)) { float aaalS = (1.f - beta) / (cp.b_lpast - cp.t_lpast); float bbalS = 1.f - aaalS * cp.b_lpast; kClev = aaalS * modchro + bbalS; - } else if((modchro > cp.t_rpast && modchro <= cp.b_rpast)) { + } else if ((modchro > cp.t_rpast && modchro <= cp.b_rpast)) { float aaarS = (beta - 1.f) / (cp.t_rpast - cp.b_rpast); float bbbrS = 1.f - cp.b_rpast * aaarS; kClev = aaarS * modchro + bbbrS; @@ -3303,7 +3940,7 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, kClev = 1.f; } } - } else if(cp.CHmet == 0) { + } else if (cp.CHmet == 0) { kClev = beta; } @@ -3314,19 +3951,21 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, bool useOpacity; float mulOpacity = 0.f; - if(useChannelA) { + if (useChannelA) { useOpacity = cp.opaRG; - if(level < 9) { + + if (level < 9) { mulOpacity = cp.mulopaRG[level]; } } else { useOpacity = cp.opaBY; - if(level < 9) { + + if (level < 9) { mulOpacity = cp.mulopaBY[level]; } } - if((useOpacity && level < 9 && mulOpacity != 0.f) && cp.toningena) { //toning + if ((useOpacity && level < 9 && mulOpacity != 0.f) && cp.toningena) { //toning float beta = (1024.f + 20.f * mulOpacity) / 1024.f ; @@ -3338,28 +3977,27 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, // WavCoeffs_ab[dir][i] += beta; } - if(waOpacityCurveW) { + if (waOpacityCurveW) { cp.opaW = true; } - if(cp.bam && cp.diag) { -//printf("OK Chroma\n"); - if(cp.opaW && cp.BAmet == 2) { + if (cp.bam && cp.diag) { + if (cp.opaW && cp.BAmet == 2) { int iteration = cp.ite; int itplus = 7 + iteration; int itmoins = 7 - iteration; int med = maxlvl / 2; int it; - if(level < med) { + if (level < med) { it = itmoins; - } else if(level == med) { + } else if (level == med) { it = 7; - } else /*if(level > med)*/ { + } else { /*if(level > med)*/ it = itplus; } - for(int j = 0; j < it; j++) { + for (int j = 0; j < it; j++) { //float bal = cp.balan;//-100 +100 float kba = 1.f; @@ -3372,11 +4010,11 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, float k1 = 0.3f * (waOpacityCurveW[6.f * LL100] - 0.5f); //k1 between 0 and 0.5 0.5==> 1/6=0.16 float k2 = k1 * 2.f; - if(dir < 3) { + if (dir < 3) { kba = 1.f + k1; } - if(dir == 3) { + if (dir == 3) { kba = 1.f - k2; } @@ -3385,22 +4023,22 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, } } - if(cp.BAmet == 1) { + if (cp.BAmet == 1) { int iteration = cp.ite; int itplus = 7 + iteration; int itmoins = 7 - iteration; int med = maxlvl / 2; int it; - if(level < med) { + if (level < med) { it = itmoins; - } else if(level == med) { + } else if (level == med) { it = 7; - } else /*if(level > med)*/ { + } else { /*if(level > med)*/ it = itplus; } - for(int j = 0; j < it; j++) { + for (int j = 0; j < it; j++) { float bal = cp.balan;//-100 +100 float kba = 1.f; @@ -3412,17 +4050,17 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, float k1 = 600.f; float k2 = 300.f; float LL100 = labco->L[ii * 2][jj * 2] / 327.68f; - float aa = 4970.f; - float bb = -397000.f; - float b0 = 100000.f; - float a0 = -4970.f; + constexpr float aa = 4970.f; + constexpr float bb = -397000.f; + constexpr float b0 = 100000.f; + constexpr float a0 = -4970.f; - if(LL100 > 80.f) { + if (LL100 > 80.f) { k1 = aa * LL100 + bb; k2 = 0.5f * k1; } - if(LL100 < 20.f) { + if (LL100 < 20.f) { k1 = a0 * LL100 + b0; k2 = 0.5f * k1; } @@ -3431,11 +4069,11 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, //k2=300.f; //k1=0.3f*(waOpacityCurveW[6.f*LL100]-0.5f);//k1 between 0 and 0.5 0.5==> 1/6=0.16 //k2=k1*2.f; - if(dir < 3) { + if (dir < 3) { kba = 1.f + bal / k1; } - if(dir == 3) { + if (dir == 3) { kba = 1.f - bal / k2; } @@ -3451,34 +4089,34 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, choicelevel = choicelevel == -1 ? 4 : choicelevel; int choiceClevel = 0; - if(params->wavelet.CLmethod == "one") { + if (params->wavelet.CLmethod == "one") { choiceClevel = 0; - } else if(params->wavelet.CLmethod == "inf") { + } else if (params->wavelet.CLmethod == "inf") { choiceClevel = 1; - } else if(params->wavelet.CLmethod == "sup") { + } else if (params->wavelet.CLmethod == "sup") { choiceClevel = 2; - } else if(params->wavelet.CLmethod == "all") { + } else if (params->wavelet.CLmethod == "all") { choiceClevel = 3; } int choiceDir = 0; - if(params->wavelet.Dirmethod == "one") { + if (params->wavelet.Dirmethod == "one") { choiceDir = 1; - } else if(params->wavelet.Dirmethod == "two") { + } else if (params->wavelet.Dirmethod == "two") { choiceDir = 2; - } else if(params->wavelet.Dirmethod == "thr") { + } else if (params->wavelet.Dirmethod == "thr") { choiceDir = 3; - } else if(params->wavelet.Dirmethod == "all") { + } else if (params->wavelet.Dirmethod == "all") { choiceDir = 0; } int dir1 = (choiceDir == 2) ? 1 : 2; int dir2 = (choiceDir == 3) ? 1 : 3; - if(choiceClevel < 3) { // not all levels visible, paint residual - if(level == 0) { - if(cp.backm != 2) { // nothing to change when residual is used as background + if (choiceClevel < 3) { // not all levels visible, paint residual + if (level == 0) { + if (cp.backm != 2) { // nothing to change when residual is used as background for (int i = 0; i < W_ab * H_ab; i++) { WavCoeffs_ab0[i] = 0.f; } @@ -3486,61 +4124,61 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, } } - if(choiceClevel == 0) { // Only one level - if(choiceDir == 0) { // All directions - if(level != choicelevel) { // zero all for the levels != choicelevel - for (int dir = 1; dir < 4; dir++) { + if (choiceClevel == 0) { // Only one level + if (choiceDir == 0) { // All directions + if (level != choicelevel) { // zero all for the levels != choicelevel + for (int d = 1; d < 4; d++) { for (int i = 0; i < W_ab * H_ab; i++) { - WavCoeffs_ab[dir][i] = 0.f; + WavCoeffs_ab[d][i] = 0.f; } } } } else { // zero the unwanted directions for level == choicelevel - if(choicelevel >= cp.maxilev) { - for (int dir = 1; dir < 4; dir++) { + if (choicelevel >= cp.maxilev) { + for (int d = 1; d < 4; d++) { for (int i = 0; i < W_ab * H_ab; i++) { - WavCoeffs_ab[dir][i] = 0.f; + WavCoeffs_ab[d][i] = 0.f; } } - } else if(level != choicelevel) { // zero all for the levels != choicelevel + } else if (level != choicelevel) { // zero all for the levels != choicelevel for (int i = 0; i < W_ab * H_ab; i++) { WavCoeffs_ab[dir1][i] = WavCoeffs_ab[dir2][i] = 0.f; } } } - } else if(choiceClevel == 1) { // Only below level - if(choiceDir == 0) { // All directions - if(level > choicelevel) { - for (int dir = 1; dir < 4; dir++) { + } else if (choiceClevel == 1) { // Only below level + if (choiceDir == 0) { // All directions + if (level > choicelevel) { + for (int d = 1; d < 4; d++) { for (int i = 0; i < W_ab * H_ab; i++) { - WavCoeffs_ab[dir][i] = 0.f; + WavCoeffs_ab[d][i] = 0.f; } } } } else { // zero the unwanted directions for level >= choicelevel - if(level > choicelevel) { + if (level > choicelevel) { for (int i = 0; i < W_ab * H_ab; i++) { WavCoeffs_ab[dir1][i] = WavCoeffs_ab[dir2][i] = 0.f; } } } - } else if(choiceClevel == 2) { // Only above level - if(choiceDir == 0) { // All directions - if(level <= choicelevel) { - for (int dir = 1; dir < 4; dir++) { + } else if (choiceClevel == 2) { // Only above level + if (choiceDir == 0) { // All directions + if (level <= choicelevel) { + for (int d = 1; d < 4; d++) { for (int i = 0; i < W_ab * H_ab; i++) { - WavCoeffs_ab[dir][i] = 0.f; + WavCoeffs_ab[d][i] = 0.f; } } } } else { // zero the unwanted directions for level >= choicelevel - if(choicelevel >= cp.maxilev) { - for (int dir = 1; dir < 4; dir++) { + if (choicelevel >= cp.maxilev) { + for (int d = 1; d < 4; d++) { for (int i = 0; i < W_ab * H_ab; i++) { - WavCoeffs_ab[dir][i] = 0.f; + WavCoeffs_ab[d][i] = 0.f; } } - } else if(level <= choicelevel) { + } else if (level <= choicelevel) { for (int i = 0; i < W_ab * H_ab; i++) { WavCoeffs_ab[dir1][i] = WavCoeffs_ab[dir2][i] = 0.f; } @@ -3548,4 +4186,192 @@ void ImProcFunctions::ContAllAB (LabImage * labco, int maxlvl, float ** varhue, } } } + +void ImProcFunctions::softproc2(const LabImage* bufcolorig, const LabImage* bufcolfin, float rad, int bfh, int bfw, double epsilmax, double epsilmin, float thres, int sk, bool multiThread, int flag) +{ + if (flag == 0) { + if (rad > 0.f) { + array2D ble(bfw, bfh); + array2D guid(bfw, bfh); + Imagefloat *tmpImage = nullptr; + tmpImage = new Imagefloat(bfw, bfh); + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < bfh; ir++) + for (int jr = 0; jr < bfw; jr++) { + + float X, Y, Z; + float L = bufcolorig->L[ir][jr]; + float a = bufcolorig->a[ir][jr]; + float b = bufcolorig->b[ir][jr]; + Color::Lab2XYZ(L, a, b, X, Y, Z); + + guid[ir][jr] = Y / 32768.f; + float La = bufcolfin->L[ir][jr]; + float aa = bufcolfin->a[ir][jr]; + float ba = bufcolfin->b[ir][jr]; + Color::Lab2XYZ(La, aa, ba, X, Y, Z); + tmpImage->r(ir, jr) = X; + tmpImage->g(ir, jr) = Y; + tmpImage->b(ir, jr) = Z; + + ble[ir][jr] = Y / 32768.f; + } + + double aepsil = (epsilmax - epsilmin) / 90.f; + double bepsil = epsilmax - 100.f * aepsil; + double epsil = aepsil * 0.1 * rad + bepsil; + + float blur = 10.f / sk * (thres + 0.8f * rad); + rtengine::guidedFilter(guid, ble, ble, blur, epsil, multiThread, 4); + + + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < bfh; ir++) + for (int jr = 0; jr < bfw; jr++) { + float X = tmpImage->r(ir, jr); + float Y = 32768.f * ble[ir][jr]; + float Z = tmpImage->b(ir, jr); + float L, a, b; + Color::XYZ2Lab(X, Y, Z, L, a, b); + bufcolfin->L[ir][jr] = L; + } + + delete tmpImage; + } + } else if (flag == 1) { + if (rad > 0.f) { + array2D ble(bfw, bfh); + array2D blechro(bfw, bfh); + array2D hue(bfw, bfh); + array2D guid(bfw, bfh); + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < bfh; ir++) + for (int jr = 0; jr < bfw; jr++) { +// hue[ir][jr] = xatan2f(bufcolfin->b[ir][jr], bufcolfin->a[ir][jr]); +// float chromah = sqrt(SQR(bufcolfin->b[ir][jr]) + SQR(bufcolfin->a[ir][jr])); + + ble[ir][jr] = (bufcolfin->L[ir][jr]) / 32768.f; +// blechro[ir][jr] = chromah / 32768.f; + guid[ir][jr] = bufcolorig->L[ir][jr] / 32768.f; + } + + double aepsil = (epsilmax - epsilmin) / 90.f; + double bepsil = epsilmax - 100.f * aepsil; + double epsil = aepsil * 0.1 * rad + bepsil; + + if (rad != 0.f) { + float blur = rad; + blur = blur < 0.f ? -1.f / blur : 1.f + blur; + // int r1 = max(int(4 / sk * blur + 0.5), 1); + int r2 = max(int(25 / sk * blur + 0.5), 1); + + if (rad < 0.f) { + epsil = 0.0001; + } + + rtengine::guidedFilter(guid, ble, ble, r2, epsil, multiThread); +// rtengine::guidedFilter(guid, blechro, blechro, r1, 0.5 * epsil, multiThread); + } + + + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < bfh; ir++) + for (int jr = 0; jr < bfw; jr++) { + // float2 sincosval = xsincosf(hue[ir][jr]); + + bufcolfin->L[ir][jr] = 32768.f * ble[ir][jr]; + // bufcolfin->a[ir][jr] = 32768.f * sincosval.y * blechro[ir][jr]; + // bufcolfin->b[ir][jr] = 32768.f * sincosval.x * blechro[ir][jr]; + } + } + + } +} + + +void ImProcFunctions::Compresslevels2(float **Source, int W_L, int H_L, float compression, float detailattenuator, float thres, float mean, float maxp, float meanN, float maxN, float madL) +{ + //J.Desmis 12-2019 + + float exponent; + + if (detailattenuator > 0.f && detailattenuator < 0.05f) { + float betemp = expf(-(2.f - detailattenuator + 0.693147f)) - 1.f; //0.69315 = log(2) + exponent = 1.2f * xlogf(-betemp); + exponent /= 20.f; + } else if (detailattenuator >= 0.05f && detailattenuator < 0.25f) { + float betemp = expf(-(2.f - detailattenuator + 0.693147f)) - 1.f; + exponent = 1.2f * xlogf(-betemp); + exponent /= (-75.f * detailattenuator + 23.75f); + } else if (detailattenuator >= 0.25f) { + float betemp = expf(-(2.f - detailattenuator + 0.693147f)) - 1.f; + exponent = 1.2f * xlogf(-betemp); + exponent /= (-2.f * detailattenuator + 5.5f); + } else { + exponent = (compression - 1.0f) / 20.f; + } + + exponent += 1.f; + + + float ap = (thres - 1.f) / (maxp - mean); + float bp = 1.f - ap * mean; + + float a0 = (1.33f * thres - 1.f) / (1.f - mean); + float b0 = 1.f - a0 * mean; + + float apn = (thres - 1.f) / (maxN - meanN); + float bpn = 1.f - apn * meanN; + + float a0n = (1.33f * thres - 1.f) / (1.f - meanN); + float b0n = 1.f - a0n * meanN; + + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int y = 0; y < H_L; y++) { + for (int x = 0; x < W_L; x++) { + float expone = 1.f; + + if (Source[y][x] >= 0.f) { + + if (Source[y][x] > mean) { + expone = 1.f + (exponent - 1.f) * (ap * Source[y][x] + bp); + } else { + expone = 1.f + (exponent - 1.f) * (a0 * Source[y][x] + b0); + } + + Source[y][x] = xexpf(xlogf(Source[y][x] + 0.05f * madL) * expone); + } else if (Source[y][x] < 0.f) { + if (-Source[y][x] > mean) { + expone = 1.f + (exponent - 1.f) * (apn * -Source[y][x] + bpn); + } else { + expone = 1.f + (exponent - 1.f) * (a0n * -Source[y][x] + b0n); + } + + Source[y][x] = -xexpf(xlogf(-Source[y][x] + 0.05f * madL) * expone); + } + } + } + +} + } diff --git a/rtengine/jdatasrc.cc b/rtengine/jdatasrc.cc index 8c04a14a2..e461b60f5 100644 --- a/rtengine/jdatasrc.cc +++ b/rtengine/jdatasrc.cc @@ -25,11 +25,6 @@ #define JFREAD(file,buf,sizeofbuf) \ ((size_t) fread((void *) (buf), (size_t) 1, (size_t) (sizeofbuf), (file))) -#define JFWRITE(file,buf,sizeofbuf) \ - ((size_t) fwrite((const void *) (buf), (size_t) 1, (size_t) (sizeofbuf), (file))) - - - /* Expanded data source object for stdio input */ namespace diff --git a/rtengine/klt/selectGoodFeatures.cc b/rtengine/klt/selectGoodFeatures.cc index 20e67fb2e..ccd7681db 100644 --- a/rtengine/klt/selectGoodFeatures.cc +++ b/rtengine/klt/selectGoodFeatures.cc @@ -9,7 +9,6 @@ #include /* fflush() */ #include /* memset() */ #include /* fsqrt() */ -#define fsqrt(X) sqrt(X) /* Our includes */ #include "base.h" diff --git a/rtengine/labimage.h b/rtengine/labimage.h index 79f003b07..7140d9de0 100644 --- a/rtengine/labimage.h +++ b/rtengine/labimage.h @@ -23,7 +23,7 @@ namespace rtengine { -class LabImage +class LabImage final { private: void allocLab(size_t w, size_t h); diff --git a/rtengine/lcp.cc b/rtengine/lcp.cc index c80a126f5..1826101e7 100644 --- a/rtengine/lcp.cc +++ b/rtengine/lcp.cc @@ -42,7 +42,6 @@ class rtengine::LCPProfile::LCPPersModel public: LCPPersModel(); bool hasModeData(LCPCorrectionMode mode) const; - void print() const; float focLen; float focDist; @@ -82,27 +81,18 @@ bool rtengine::LCPModelCommon::empty() const && param[2] == 0.0f; } -void rtengine::LCPModelCommon::print() const -{ - std::printf("focLen %g/%g; imgCenter %g/%g; scale %g; err %g\n", foc_len_x, foc_len_y, img_center_x, img_center_y, scale_factor, mean_error); - std::printf("xy0 %g/%g fxy %g/%g\n", x0, y0, fx, fy); - std::printf("param: %g/%g/%g/%g/%g\n", param[0], param[1], param[2], param[3], param[4]); -} - // weighted merge two parameters void rtengine::LCPModelCommon::merge(const LCPModelCommon& a, const LCPModelCommon& b, float facA) { - const float facB = 1.0f - facA; - - foc_len_x = facA * a.foc_len_x + facB * b.foc_len_x; - foc_len_y = facA * a.foc_len_y + facB * b.foc_len_y; - img_center_x = facA * a.img_center_x + facB * b.img_center_x; - img_center_y = facA * a.img_center_y + facB * b.img_center_y; - scale_factor = facA * a.scale_factor + facB * b.scale_factor; - mean_error = facA * a.mean_error + facB * b.mean_error; + foc_len_x = rtengine::intp(facA, a.foc_len_x, b.foc_len_x); + foc_len_y = rtengine::intp(facA, a.foc_len_y, b.foc_len_y); + img_center_x = rtengine::intp(facA, a.img_center_x, b.img_center_x); + img_center_y = rtengine::intp(facA, a.img_center_y, b.img_center_y); + scale_factor = rtengine::intp(facA, a.scale_factor, b.scale_factor); + mean_error = rtengine::intp(facA, a.mean_error, b.mean_error); for (int i = 0; i < 5; ++i) { - param[i] = facA * a.param[i] + facB * b.param[i]; + param[i] = rtengine::intp(facA, a.param[i], b.param[i]); } const float param0Sqr = param[0] * param[0]; @@ -152,7 +142,6 @@ void rtengine::LCPModelCommon::prepareParams( rfx = 1.0f / fx; rfy = 1.0f / fy; - //std::printf("FW %i /X0 %g FH %i /Y0 %g %g\n",fullWidth,x0,fullHeight,y0, imgYCenter); } rtengine::LCPProfile::LCPPersModel::LCPPersModel() : @@ -188,35 +177,6 @@ bool rtengine::LCPProfile::LCPPersModel::hasModeData(LCPCorrectionMode mode) con return false; } -void rtengine::LCPProfile::LCPPersModel::print() const -{ - std::printf("--- PersModel focLen %g; focDist %g; aperture %g\n", focLen, focDist, aperture); - std::printf("Base:\n"); - base.print(); - - if (!chromRG.empty()) { - std::printf("ChromRG:\n"); - chromRG.print(); - } - - if (!chromG.empty()) { - std::printf("ChromG:\n"); - chromG.print(); - } - - if (!chromBG.empty()) { - std::printf("ChromBG:\n"); - chromBG.print(); - } - - if (!vignette.empty()) { - std::printf("Vignette:\n"); - vignette.print(); - } - - std::printf("\n"); -} - rtengine::LCPProfile::LCPProfile(const Glib::ustring& fname) : isFisheye(false), sensorFormatFactor(1.f), @@ -522,7 +482,7 @@ void rtengine::LCPProfile::calcParams( ) { // Mix in aperture const float facAperLow = (pHigh->aperture - aperture) / (pHigh->aperture - pLow->aperture); - facLow = focLenOnSpot ? facAperLow : (0.5 * facLow + 0.5 * facAperLow); + facLow = focLenOnSpot ? facAperLow : (0.5f * (facLow + facAperLow)); } else if ( mode != LCPCorrectionMode::VIGNETTE @@ -532,7 +492,7 @@ void rtengine::LCPProfile::calcParams( ) { // focus distance for all else (if focus distance is given) const float facDistLow = (std::log(pHigh->focDist) + euler - focusDistLog) / (std::log(pHigh->focDist) - std::log(pLow->focDist)); - facLow = focLenOnSpot ? facDistLow : (0.8 * facLow + 0.2 * facDistLow); + facLow = focLenOnSpot ? facDistLow : (0.8f * facLow + 0.2f * facDistLow); } switch (mode) { @@ -555,7 +515,16 @@ void rtengine::LCPProfile::calcParams( } if (settings->verbose) { - std::printf("LCP mode=%i, dist: %g found frames: Fno %g-%g; FocLen %g-%g; Dist %g-%g with weight %g\n", toUnderlying(mode), focusDist, pLow->aperture, pHigh->aperture, pLow->focLen, pHigh->focLen, pLow->focDist, pHigh->focDist, facLow); + std::printf("LCP mode=%i, dist: %g found frames: Fno %g-%g; FocLen %g-%g; Dist %g-%g with weight %g\n", + toUnderlying(mode), + static_cast(focusDist), + static_cast(pLow->aperture), + static_cast(pHigh->aperture), + static_cast(pLow->focLen), + static_cast(pHigh->focLen), + static_cast(pLow->focDist), + static_cast(pHigh->focDist), + static_cast(facLow)); } } else { if (settings->verbose) { @@ -564,15 +533,6 @@ void rtengine::LCPProfile::calcParams( } } -void rtengine::LCPProfile::print() const -{ - std::printf("=== Profile %s\n", profileName.c_str()); - std::printf("Frames: %i, RAW: %i; Fisheye: %i; Sensorformat: %f\n", persModelCount, isRaw, isFisheye, sensorFormatFactor); - - for (int pm = 0; pm < persModelCount; ++pm) { - aPersModel[pm]->print(); - } -} // from all frames not marked as bad already, take average and filter out frames with higher deviation than this if there are enough values int rtengine::LCPProfile::filterBadFrames(LCPCorrectionMode mode, double maxAvgDevFac, int minFramesLeft) @@ -649,7 +609,7 @@ int rtengine::LCPProfile::filterBadFrames(LCPCorrectionMode mode, double maxAvgD } if (settings->verbose && count) { - std::printf("Filtered %.1f%% frames for maxAvgDevFac %g leaving %i\n", filtered * 100.f / count, maxAvgDevFac, count - filtered); + std::printf("Filtered %.1f%% frames for maxAvgDevFac %g leaving %i\n", filtered * 100.0 / count, maxAvgDevFac, count - filtered); } } @@ -1007,7 +967,7 @@ rtengine::LCPMapper::LCPMapper( const bool mirrorX = (rot == 90 || rot == 180); const bool mirrorY = (rot == 180 || rot == 270); if (settings->verbose) { - std::printf("Vign: %i, fullWidth: %i/%i, focLen %g SwapXY: %i / MirX/Y %i / %i on rot:%i from %i\n",vignette, fullWidth, fullHeight, focalLength, swapXY, mirrorX, mirrorY, rot, rawRotationDeg); + std::printf("Vign: %i, fullWidth: %i/%i, focLen %g SwapXY: %i / MirX/Y %i / %i on rot:%i from %i\n",vignette, fullWidth, fullHeight, static_cast(focalLength), swapXY, mirrorX, mirrorY, rot, rawRotationDeg); } pProf->calcParams(vignette ? LCPCorrectionMode::VIGNETTE : LCPCorrectionMode::DISTORTION, focalLength, focusDist, aperture, &mc, nullptr, nullptr); @@ -1038,8 +998,8 @@ void rtengine::LCPMapper::correctDistortion(double &x, double &y, int cx, int cy if (isFisheye) { const double u = x * scale; const double v = y * scale; - const double u0 = mc.x0 * scale; - const double v0 = mc.y0 * scale; + const double u0 = static_cast(mc.x0) * scale; + const double v0 = static_cast(mc.y0) * scale; const double du = (u - u0); const double dv = (v - v0); const double fx = mc.fx; @@ -1059,22 +1019,22 @@ void rtengine::LCPMapper::correctDistortion(double &x, double &y, int cx, int cy } else { x *= scale; y *= scale; - const double x0 = mc.x0 * scale; - const double y0 = mc.y0 * scale; - const double xd = (x - x0) / mc.fx, yd = (y - y0) / mc.fy; + const double x0 = static_cast(mc.x0) * scale; + const double y0 = static_cast(mc.y0) * scale; + const double xd = (x - x0) / static_cast(mc.fx), yd = (y - y0) / static_cast(mc.fy); - const LCPModelCommon::Param aDist = mc.param; + const auto& aDist = mc.param; const double rsqr = xd * xd + yd * yd; - const double xfac = aDist[swapXY ? 3 : 4], yfac = aDist[swapXY ? 4 : 3]; + const double xfac = static_cast(aDist[swapXY ? 3 : 4]), yfac = static_cast(aDist[swapXY ? 4 : 3]); - const double commonFac = (((aDist[2] * rsqr + aDist[1]) * rsqr + aDist[0]) * rsqr + 1.) + const double commonFac = (((static_cast(aDist[2]) * rsqr + static_cast(aDist[1])) * rsqr + static_cast(aDist[0])) * rsqr + 1.) + 2. * (yfac * yd + xfac * xd); const double xnew = xd * commonFac + xfac * rsqr; const double ynew = yd * commonFac + yfac * rsqr; - x = xnew * mc.fx + x0; - y = ynew * mc.fy + y0; + x = xnew * static_cast(mc.fx) + x0; + y = ynew * static_cast(mc.fy) + y0; } x -= cx * scale; @@ -1094,20 +1054,20 @@ void rtengine::LCPMapper::correctCA(double& x, double& y, int cx, int cy, int ch // First calc the green channel like normal distortion // the other are just deviations from it - double xd = (x - chrom[1].x0) / chrom[1].fx; - double yd = (y - chrom[1].y0) / chrom[1].fy; + double xd = (x - static_cast(chrom[1].x0)) / static_cast(chrom[1].fx); + double yd = (y - static_cast(chrom[1].y0)) / static_cast(chrom[1].fy); // Green contains main distortion, just like base if (useCADist) { - const LCPModelCommon::Param aDist = chrom[1].param; - double rsqr = xd * xd + yd * yd; - double xfac = aDist[swapXY ? 3 : 4], yfac = aDist[swapXY ? 4 : 3]; + const auto& aDist = chrom[1].param; + double rsqr = xd * xd + yd * yd; + double xfac = static_cast(aDist[swapXY ? 3 : 4]), yfac = static_cast(aDist[swapXY ? 4 : 3]); - double commonFac = (((aDist[2] * rsqr + aDist[1]) * rsqr + aDist[0]) * rsqr + 1.) + double commonFac = (((static_cast(aDist[2]) * rsqr + static_cast(aDist[1])) * rsqr + static_cast(aDist[0])) * rsqr + 1.) + 2. * (yfac * yd + xfac * xd); - xgreen = xd * commonFac + aDist[4] * rsqr; - ygreen = yd * commonFac + aDist[3] * rsqr; + xgreen = xd * commonFac + static_cast(aDist[4]) * rsqr; + ygreen = yd * commonFac + static_cast(aDist[3]) * rsqr; } else { xgreen = xd; ygreen = yd; @@ -1115,20 +1075,20 @@ void rtengine::LCPMapper::correctCA(double& x, double& y, int cx, int cy, int ch if (channel == 1) { // green goes directly - x = xgreen * chrom[1].fx + chrom[1].x0; - y = ygreen * chrom[1].fy + chrom[1].y0; + x = xgreen * static_cast(chrom[1].fx) + static_cast(chrom[1].x0); + y = ygreen * static_cast(chrom[1].fy) + static_cast(chrom[1].y0); } else { // others are diffs from green xd = xgreen; yd = ygreen; const double rsqr = xd * xd + yd * yd; - const LCPModelCommon::Param aCA = chrom[channel].param; - const double xfac = aCA[swapXY ? 3 : 4], yfac = aCA[swapXY ? 4 : 3]; - const double commonSum = 1. + rsqr * (aCA[0] + rsqr * (aCA[1] + aCA[2] * rsqr)) + 2. * (yfac * yd + xfac * xd); + const auto& aCA = chrom[channel].param; + const double xfac = static_cast(aCA[swapXY ? 3 : 4]), yfac = static_cast(aCA[swapXY ? 4 : 3]); + const double commonSum = 1. + rsqr * (static_cast(aCA[0]) + rsqr * (static_cast(aCA[1]) + static_cast(aCA[2] )* rsqr)) + 2. * (yfac * yd + xfac * xd); - x = (chrom[channel].scale_factor * ( xd * commonSum + xfac * rsqr )) * chrom[channel].fx + chrom[channel].x0; - y = (chrom[channel].scale_factor * ( yd * commonSum + yfac * rsqr )) * chrom[channel].fy + chrom[channel].y0; + x = (static_cast(chrom[channel].scale_factor) * ( xd * commonSum + xfac * rsqr )) * static_cast(chrom[channel].fx) + static_cast(chrom[channel].x0); + y = (static_cast(chrom[channel].scale_factor) * ( yd * commonSum + yfac * rsqr )) * static_cast(chrom[channel].fy) + static_cast(chrom[channel].y0); } x -= cx; diff --git a/rtengine/lcp.h b/rtengine/lcp.h index 2e36fe113..4c1e09865 100644 --- a/rtengine/lcp.h +++ b/rtengine/lcp.h @@ -54,7 +54,6 @@ public: LCPModelCommon(); bool empty() const; // is it empty - void print() const; // printf all values void merge(const LCPModelCommon& a, const LCPModelCommon& b, float facA); void prepareParams( int fullWidth, @@ -106,7 +105,6 @@ public: LCPModelCommon *pCorr3 ) const; // Interpolates between the persModels frames - void print() const; //private: // Common data diff --git a/rtengine/lmmse_demosaic.cc b/rtengine/lmmse_demosaic.cc index f4af1b801..5c4ddffed 100644 --- a/rtengine/lmmse_demosaic.cc +++ b/rtengine/lmmse_demosaic.cc @@ -334,7 +334,7 @@ void RawImageSource::lmmse_interpolate_omp(int winw, int winh, const array2D +* +* RawTherapee is free software: you can redistribute it and/or modify +* it under the terms of the GNU General Public License as published by +* the Free Software Foundation, either version 3 of the License, or +* (at your option) any later version. +* +* RawTherapee is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with RawTherapee. If not, see . +*/ + +#include "color.h" + +using namespace std; + +namespace rtengine +{ + +/* + * MunsellLch correction + * Copyright (c) 2012 Jacques Desmis + * Copyright (c) 2020 Ingo Weyrich + * + * Find the right LUT and calculate the correction + */ +void Color::MunsellLch (float lum, float hue, float chrom, float memChprov, float &correction, int zone, float &lbe, bool &correctL) +{ + + const int x = memChprov; + int y = chrom; + + //begin PB correction + sky + if (zone == 1) { + if (lum > 5.f) { + if (lum < 15.f) { + if (x <= 45 && (hue >= (_15PB10[x] - 0.035f)) && (hue < (_15PB10[x] + 0.052f))) { + if (y > 49) { + y = 49; + } + correction = _15PB10[y] - _15PB10[x] ; + lbe = _15PB10[y]; + correctL = true; + } else if (x <= 85 && (hue >= ( _3PB10[x] - 0.052f)) && (hue < (_45PB10[x] + _3PB10[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _3PB10[y] - _3PB10[x]; + lbe = _3PB10[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_45PB10[x] + _3PB10[x]) * 0.5f) && (hue < (_45PB10[x] + 0.052f))) { + if (y > 89) { + y = 89; + } + correction = _45PB10[y] - _45PB10[x] ; + lbe = _45PB10[y]; + correctL = true; + } else if ((hue >= (_6PB10[x] - 0.052f) && (hue < (_6PB10[x] + _75PB10[x]) * 0.5f))) { + correction = _6PB10[y] - _6PB10[x] ; + lbe = _6PB10[y]; + correctL = true; + } else if ((hue >= (_6PB10[x] + _75PB10[x]) * 0.5f) && (hue < (_9PB10[x] + _75PB10[x]) * 0.5f)) { + correction = _75PB10[y] - _75PB10[x] ; + lbe = _75PB10[y]; + correctL = true; + } else if ((hue >= (_9PB10[x] + _75PB10[x]) * 0.5f) && (hue < (_9PB10[x] + _10PB10[x]) * 0.5f)) { + correction = _9PB10[y] - _9PB10[x] ; + lbe = _9PB10[y]; + correctL = true; + } else if ((hue >= (_10PB10[x] + _9PB10[x]) * 0.5f) && (hue < (_1P10[x] + _10PB10[x]) * 0.5f)) { + correction = _10PB10[y] - _10PB10[x] ; + lbe = _10PB10[y]; + correctL = true; + } else if ((hue >= (_10PB10[x] + _1P10[x]) * 0.5f) && (hue < (_1P10[x] + _4P10[x]) * 0.5f)) { + correction = _1P10[y] - _1P10[x]; + lbe = _1P10[y]; + correctL = true; + } else if ((hue >= (_1P10[x] + _4P10[x]) * 0.5f) && (hue < (0.035f + _4P10[x]) * 0.5f)) { + correction = _4P10[y] - _4P10[x] ; + lbe = _4P10[y]; + correctL = true; + } + } else if (lum < 25.f) { + if (x <= 85 && (hue >= (_15PB20[x] - 0.035f)) && (hue < (_15PB20[x] + _3PB20[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _15PB20[y] - _15PB20[x] ; + lbe = _15PB20[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_15PB20[x] + _3PB20[x]) * 0.5f) && (hue < (_45PB20[x] + _3PB20[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _3PB20[y] - _3PB20[x] ; + lbe = _3PB20[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_45PB20[x] + _3PB20[x]) * 0.5f) && (hue < ( _45PB20[x] + 0.052f))) { + if (y > 89) { + y = 89; + } + correction = _45PB20[y] - _45PB20[x] ; + lbe = _45PB20[y]; + correctL = true; + } else if ((hue >= (_45PB20[x] + 0.052f)) && (hue < (_6PB20[x] + _75PB20[x]) * 0.5f)) { + correction = _6PB20[y] - _6PB20[x]; + lbe = _6PB20[y]; + correctL = true; + } else if ((hue >= (_6PB20[x] + _75PB20[x]) * 0.5f) && (hue < (_9PB20[x] + _75PB20[x]) * 0.5f)) { + correction = _75PB20[y] - _75PB20[x] ; + lbe = _75PB20[y]; + correctL = true; + } else if ((hue >= (_9PB20[x] + _75PB20[x]) * 0.5f) && (hue < (_9PB20[x] + _10PB20[x]) * 0.5f)) { + correction = _9PB20[y] - _9PB20[x] ; + lbe = _9PB20[y]; + correctL = true; + } else if ((hue >= (_10PB20[x] + _9PB20[x]) * 0.5f) && (hue < (_1P20[x] + _10PB20[x]) * 0.5f)) { + correction = _10PB20[y] - _10PB20[x] ; + lbe = _10PB20[y]; + correctL = true; + } else if ((hue >= (_10PB20[x] + _1P20[x]) * 0.5f) && (hue < (_1P20[x] + _4P20[x]) * 0.5f)) { + correction = _1P20[y] - _1P20[x] ; + lbe = _1P20[y]; + correctL = true; + } else if ((hue >= (_1P20[x] + _4P20[x]) * 0.5f) && (hue < (0.035f + _4P20[x]) * 0.5f)) { + correction = _4P20[y] - _4P20[x] ; + lbe = _4P20[y]; + correctL = true; + } + } else if (lum < 35.f) { + if (x <= 85 && (hue >= (_15PB30[x] - 0.035f)) && (hue < (_15PB30[x] + _3PB30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _15PB30[y] - _15PB30[x] ; + lbe = _15PB30[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_15PB30[x] + _3PB30[x]) * 0.5f) && (hue < (_45PB30[x] + _3PB30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _3PB30[y] - _3PB30[x] ; + lbe = _3PB30[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_45PB30[x] + _3PB30[x]) * 0.5f) && (hue < (_45PB30[x] + 0.052f))) { + if (y > 89) { + y = 89; + } + correction = _45PB30[y] - _45PB30[x] ; + lbe = _45PB30[y]; + correctL = true; + } else if ((hue >= ( _45PB30[x] + 0.052f)) && (hue < (_6PB30[x] + _75PB30[x]) * 0.5f)) { + correction = _6PB30[y] - _6PB30[x] ; + lbe = _6PB30[y]; + correctL = true; + } else if ((hue >= (_6PB30[x] + _75PB30[x]) * 0.5f) && (hue < (_9PB30[x] + _75PB30[x]) * 0.5f)) { + correction = _75PB30[y] - _75PB30[x] ; + lbe = _75PB30[y] ; + correctL = true; + } else if ((hue >= (_9PB30[x] + _75PB30[x]) * 0.5f) && (hue < (_9PB30[x] + _10PB30[x]) * 0.5f)) { + correction = _9PB30[y] - _9PB30[x] ; + lbe = _9PB30[y]; + correctL = true; + } else if ((hue >= (_10PB30[x] + _9PB30[x]) * 0.5f) && (hue < (_1P30[x] + _10PB30[x]) * 0.5f)) { + correction = _10PB30[y] - _10PB30[x] ; + lbe = _10PB30[y]; + correctL = true; + } else if ((hue >= (_10PB30[x] + _1P30[x]) * 0.5f) && (hue < (_1P30[x] + _4P30[x]) * 0.5f)) { + correction = _1P30[y] - _1P30[x] ; + lbe = _1P30[y]; + correctL = true; + } else if ((hue >= (_1P30[x] + _4P30[x]) * 0.5f) && (hue < (0.035f + _4P30[x]) * 0.5f)) { + correction = _4P30[y] - _4P30[x] ; + lbe = _4P30[y]; + correctL = true; + } + } else if (lum < 45.f) { + if (x < 75 && (hue <= (_05PB40[x] + _15PB40[x]) * 0.5f) && (hue > (_05PB40[x] + _10B40[x]) * 0.5f)) { + if (y > 75) { + y = 75; + } + correction = _05PB40[y] - _05PB40[x] ; + lbe = _05PB40[y]; + correctL = true; + } else if (x < 70 && (hue <= (_05PB40[x] + _10B40[x]) * 0.5f) && (hue > (_10B40[x] + _9B40[x]) * 0.5f)) { + if (y > 70) { + y = 70; + } + correction = _10B40[y] - _10B40[x] ; + lbe = _10B40[y]; + correctL = true; + } else if (x < 70 && (hue <= (_10B40[x] + _9B40[x]) * 0.5f) && (hue > (_9B40[x] + _7B40[x]) * 0.5f)) { + if (y > 70) { + y = 70; + } + correction = _9B40[y] - _9B40[x] ; + lbe = _9B40[y]; + correctL = true; + } else if (x < 70 && (hue <= (_9B40[x] + _7B40[x]) * 0.5f) && (hue > (_5B40[x] + _7B40[x]) * 0.5f)) { + if (y > 70) { + y = 70; + } + correction = _7B40[y] - _7B40[x] ; + lbe = _7B40[y]; + correctL = true; + } else if (x < 70 && (hue <= (_5B40[x] + _7B40[x]) * 0.5f) && (hue > (_5B40[x] - 0.035f))) { + if (y > 70) { + y = 70; // + } + correction = _5B40[y] - _5B40[x] ; + lbe = _5B40[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_15PB40[x] - 0.035f)) && (hue < (_15PB40[x] + _3PB40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _15PB40[y] - _15PB40[x] ; + lbe = _15PB40[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_15PB40[x] + _3PB40[x]) * 0.5f) && (hue < (_45PB40[x] + _3PB40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _3PB40[y] - _3PB40[x] ; + lbe = _3PB40[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_45PB40[x] + _3PB40[x]) * 0.5f) && (hue < (_45PB40[x] + 0.052f))) { + if (y > 89) { + y = 89; + } + correction = _45PB40[y] - _45PB40[x] ; + lbe = _45PB40[y] ; + correctL = true; + } else if ((hue >= (_45PB40[x] + 0.052f)) && (hue < (_6PB40[x] + _75PB40[x]) * 0.5f)) { + correction = _6PB40[y] - _6PB40[x] ; + lbe = _6PB40[y]; + correctL = true; + } else if ((hue >= (_6PB40[x] + _75PB40[x]) * 0.5f) && (hue < (_9PB40[x] + _75PB40[x]) * 0.5f)) { + correction = _75PB40[y] - _75PB40[x] ; + lbe = _75PB40[y]; + correctL = true; + } else if ((hue >= (_9PB40[x] + _75PB40[x]) * 0.5f) && (hue < (_9PB40[x] + _10PB40[x]) * 0.5f)) { + correction = _9PB40[y] - _9PB40[x] ; + lbe = _9PB40[y]; + correctL = true; + } else if ((hue >= (_10PB40[x] + _9PB40[x]) * 0.5f) && (hue < (_1P40[x] + _10PB40[x]) * 0.5f)) { + correction = _10PB40[y] - _10PB40[x] ; + lbe = _10PB40[y]; + correctL = true; + } else if ((hue >= (_10PB40[x] + _1P40[x]) * 0.5f) && (hue < (_1P40[x] + _4P40[x]) * 0.5f)) { + correction = _1P40[y] - _1P40[x] ; + lbe = _1P40[y]; + correctL = true; + } else if ((hue >= (_1P40[x] + _4P40[x]) * 0.5f) && (hue < (0.035f + _4P40[x]) * 0.5f)) { + correction = _4P40[y] - _4P40[x] ; + lbe = _4P40[y]; + correctL = true; + } + } else if (lum < 55.f) { + if (x < 79 && (hue <= (_05PB50[x] + _15PB50[x]) * 0.5f) && (hue > (_05PB50[x] + _10B50[x]) * 0.5f)) { + if (y > 79) { + y = 79; + } + correction = _05PB50[y] - _05PB50[x] ; + lbe = _05PB50[y]; + correctL = true; + } else if (x < 79 && (hue <= (_05PB50[x] + _10B50[x]) * 0.5f) && (hue > (_10B50[x] + _9B50[x]) * 0.5f)) { + if (y > 79) { + y = 79; + } + correction = _10B50[y] - _10B50[x] ; + lbe = _10B50[y]; + correctL = true; + } else if (x < 79 && (hue <= (_10B50[x] + _9B50[x]) * 0.5f) && (hue > (_9B50[x] + _7B50[x]) * 0.5f)) { + if (y > 79) { + y = 79; + } + correction = _9B50[y] - _9B50[x] ; + lbe = _9B50[y]; + correctL = true; + } else if (x < 79 && (hue <= (_9B50[x] + _7B50[x]) * 0.5f) && (hue > (_5B50[x] + _7B50[x]) * 0.5f)) { + if (y > 79) { + y = 79; + } + correction = _7B50[y] - _7B50[x] ; + lbe = _7B50[y]; + correctL = true; + } else if (x < 79 && (hue <= (_5B50[x] + _7B50[x]) * 0.5f) && (hue > (_5B50[x] - 0.035f))) { + if (y > 79) { + y = 79; // + } + correction = _5B50[y] - _5B50[x] ; + lbe = _5B50[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_15PB50[x] - 0.035f)) && (hue < (_15PB50[x] + _3PB50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _15PB50[y] - _15PB50[x] ; + lbe = _15PB50[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_15PB50[x] + _3PB50[x]) * 0.5f) && (hue < (_45PB50[x] + _3PB50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _3PB50[y] - _3PB50[x] ; + lbe = _3PB50[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_45PB50[x] + _3PB50[x]) * 0.5f) && (hue < (_6PB50[x] + _45PB50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _45PB50[y] - _45PB50[x] ; + lbe = _45PB50[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_6PB50[x] + _45PB50[x]) * 0.5f) && (hue < (_6PB50[x] + _75PB50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _6PB50[y] - _6PB50[x] ; + lbe = _6PB50[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_6PB50[x] + _75PB50[x]) * 0.5f) && (hue < (_9PB50[x] + _75PB50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _75PB50[y] - _75PB50[x] ; + lbe = _75PB50[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_9PB50[x] + _75PB50[x]) * 0.5f) && (hue < (_9PB50[x] + _10PB50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _9PB50[y] - _9PB50[x] ; + lbe = _9PB50[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_10PB50[x] + _9PB50[x]) * 0.5f) && (hue < (_1P50[x] + _10PB50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10PB50[y] - _10PB50[x] ; + lbe = _10PB50[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_10PB50[x] + _1P50[x]) * 0.5f) && (hue < (_1P50[x] + _4P50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _1P50[y] - _1P50[x] ; + lbe = _1P50[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_1P50[x] + _4P50[x]) * 0.5f) && (hue < (0.035f + _4P50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _4P50[y] - _4P50[x] ; + lbe = _4P50[y]; + correctL = true; + } + } else if (lum < 65.f) { + if (x < 79 && (hue <= (_05PB60[x] + _15PB60[x]) * 0.5f) && (hue > (_05PB60[x] + _10B60[x]) * 0.5f)) { + if (y > 79) { + y = 79; + } + correction = _05PB60[y] - _05PB60[x] ; + lbe = _05PB60[y]; + correctL = true; + } else if (x < 79 && (hue <= (_05PB60[x] + _10B60[x]) * 0.5f) && (hue > (_10B60[x] + _9B60[x]) * 0.5f)) { + if (y > 79) { + y = 79; + } + correction = _10B60[y] - _10B60[x] ; + lbe = _10B60[y]; + correctL = true; + } else if (x < 79 && (hue <= (_10B60[x] + _9B60[x]) * 0.5f) && (hue > (_9B60[x] + _7B60[x]) * 0.5f)) { + if (y > 79) { + y = 79; + } + correction = _9B60[y] - _9B60[x] ; + lbe = _9B60[y]; + correctL = true; + } else if (x < 79 && (hue <= (_9B60[x] + _7B60[x]) * 0.5f) && (hue > (_5B60[x] + _7B60[x]) * 0.5f)) { + if (y > 79) { + y = 79; + } + correction = _7B60[y] - _7B60[x] ; + lbe = _7B60[y]; + correctL = true; + } else if (x < 79 && (hue <= (_5B60[x] + _7B60[x]) * 0.5f) && (hue > (_5B60[x] - 0.035f))) { + if (y > 79) { + y = 79; // + } + correction = _5B60[y] - _5B60[x] ; + lbe = _5B60[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_15PB60[x] - 0.035f)) && (hue < (_15PB60[x] + _3PB60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _15PB60[y] - _15PB60[x] ; + lbe = _15PB60[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_15PB60[x] + _3PB60[x]) * 0.5f) && (hue < (_45PB60[x] + _3PB60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _3PB60[y] - _3PB60[x] ; + lbe = _3PB60[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_45PB60[x] + _3PB60[x]) * 0.5f) && (hue < (_6PB60[x] + _45PB60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _45PB60[y] - _45PB60[x] ; + lbe = _45PB60[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_6PB60[x] + _45PB60[x]) * 0.5f) && (hue < (_6PB60[x] + _75PB60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _6PB60[y] - _6PB60[x] ; + lbe = _6PB60[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_6PB60[x] + _75PB60[x]) * 0.5f) && (hue < (_9PB60[x] + _75PB60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _75PB60[y] - _75PB60[x] ; + lbe = _75PB60[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_9PB60[x] + _75PB60[x]) * 0.5f) && (hue < (_9PB60[x] + _10PB60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _9PB60[y] - _9PB60[x] ; + lbe = _9PB60[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_10PB60[x] + _9PB60[x]) * 0.5f) && (hue < (_1P60[x] + _10PB60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10PB60[y] - _10PB60[x] ; + lbe = _10PB60[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_10PB60[x] + _1P60[x]) * 0.5f) && (hue < (_1P60[x] + _4P60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _1P60[y] - _1P60[x] ; + lbe = _1P60[y]; + correctL = true; + } else if (x <= 85 && (hue >= (_1P60[x] + _4P60[x]) * 0.5f) && (hue < (0.035f + _4P60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _4P60[y] - _4P60[x] ; + lbe = _4P60[y]; + correctL = true; + } + } else if (lum < 75.f) { + if (x < 50 && (hue <= (_05PB70[x] + _15PB70[x]) * 0.5f) && (hue > (_05PB70[x] + _10B70[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _05PB70[y] - _05PB70[x] ; + lbe = _05PB70[y]; + correctL = true; + } else if (x < 50 && (hue <= (_05PB70[x] + _10B70[x]) * 0.5f) && (hue > (_10B70[x] + _9B70[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _10B70[y] - _10B70[x] ; + lbe = _10B70[y]; + correctL = true; + } else if (x < 50 && (hue <= (_10B70[x] + _9B70[x]) * 0.5f) && (hue > (_9B70[x] + _7B70[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _9B70[y] - _9B70[x] ; + lbe = _9B70[y]; + correctL = true; + } else if (x < 50 && (hue <= (_9B70[x] + _7B70[x]) * 0.5f) && (hue > (_5B70[x] + _7B70[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _7B70[y] - _7B70[x] ; + lbe = _7B70[y]; + correctL = true; + } else if (x < 50 && (hue <= (_5B70[x] + _7B70[x]) * 0.5f) && (hue > (_5B70[x] - 0.035f))) { + if (y > 49) { + y = 49; // + } + correction = _5B70[y] - _5B70[x] ; + lbe = _5B70[y]; + correctL = true; + } else if (x < 50 && (hue >= (_15PB70[x] - 0.035f)) && (hue < (_15PB70[x] + _3PB70[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _15PB70[y] - _15PB70[x] ; + lbe = _15PB70[y]; + correctL = true; + } else if (x < 50 && (hue >= (_45PB70[x] + _3PB70[x]) * 0.5f) && (hue < (_6PB70[x] + _45PB70[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _45PB70[y] - _45PB70[x] ; + lbe = _45PB70[y]; + correctL = true; + } else if (x < 50 && (hue >= (_6PB70[x] + _45PB70[x]) * 0.5f) && (hue < (_6PB70[x] + _75PB70[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _6PB70[y] - _6PB70[x] ; + lbe = _6PB70[y]; + correctL = true; + } else if (x < 50 && (hue >= (_6PB70[x] + _75PB70[x]) * 0.5f) && (hue < (_9PB70[x] + _75PB70[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _75PB70[y] - _75PB70[x] ; + lbe = _75PB70[y]; + correctL = true; + } else if (x < 50 && (hue >= (_9PB70[x] + _75PB70[x]) * 0.5f) && (hue < (_9PB70[x] + 0.035f))) { + if (y > 49) { + y = 49; + } + correction = _9PB70[y] - _9PB70[x] ; + lbe = _9PB70[y]; + correctL = true; + } + } else if (lum < 85.f) { + if (x < 40 && (hue <= (_05PB80[x] + _15PB80[x]) * 0.5f) && (hue > (_05PB80[x] + _10B80[x]) * 0.5f)) { + if (y > 39) { + y = 39; + } + correction = _05PB80[y] - _05PB80[x] ; + lbe = _05PB80[y] ; + correctL = true; + } else if (x < 40 && (hue <= (_05PB80[x] + _10B80[x]) * 0.5f) && (hue > (_10B80[x] + _9B80[x]) * 0.5f)) { + if (y > 39) { + y = 39; + } + correction = _10B80[y] - _10B80[x] ; + lbe = _10B80[y]; + correctL = true; + } else if (x < 40 && (hue <= (_10B80[x] + _9B80[x]) * 0.5f) && (hue > (_9B80[x] + _7B80[x]) * 0.5f)) { + if (y > 39) { + y = 39; + } + correction = _9B80[y] - _9B80[x] ; + lbe = _9B80[y]; + correctL = true; + } else if (x < 50 &&(hue <= (_9B80[x] + _7B80[x]) * 0.5f) && (hue > (_5B80[x] + _7B80[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _7B80[y] - _7B80[x] ; + lbe = _7B80[y]; + correctL = true; + } else if (x < 50 && (hue <= (_5B80[x] + _7B80[x]) * 0.5f) && (hue > (_5B80[x] - 0.035f))) { + if (y > 49) { + y = 49; // + } + correction = _5B80[y] - _5B80[x] ; + lbe = _5B80[y]; + correctL = true; + } else if (x < 50 && (hue >= (_15PB80[x] - 0.035f)) && (hue < (_15PB80[x] + _3PB80[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _15PB80[y] - _15PB80[x] ; + lbe = _15PB80[y]; + correctL = true; + } else if (x < 50 && (hue >= (_45PB80[x] + _3PB80[x]) * 0.5f) && (hue < (_6PB80[x] + _45PB80[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _45PB80[y] - _45PB80[x] ; + lbe = _45PB80[y]; + correctL = true; + } else if (x < 50 && (hue >= (_6PB80[x] + _45PB80[x]) * 0.5f) && (hue < (_6PB80[x] + _75PB80[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _6PB80[y] - _6PB80[x] ; + lbe = _6PB80[y]; + correctL = true; + } else if (x < 50 && (hue >= (_6PB80[x] + _75PB80[x]) * 0.5f) && (hue < (_9PB80[x] + _75PB80[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _75PB80[y] - _75PB80[x] ; + lbe = _75PB80[y]; + correctL = true; + } else if (x < 50 && (hue >= (_9PB80[x] + _75PB80[x]) * 0.5f) && (hue < (_9PB80[x] + 0.035f))) { + if (y > 49) { + y = 49; + } + correction = _9PB80[y] - _9PB80[x] ; + lbe = _9PB80[y]; + correctL = true; + } + } + } + } else if (zone == 2) { //red yellow correction + if (lum > 15.f) { + if (lum < 25.f) { + if (x <= 45 && (hue <= (_10YR20[x] + 0.035f)) && (hue > (_10YR20[x] + _85YR20[x]) * 0.5f)) { + if (y > 49) { + y = 49; + } + correction = _10YR20[y] - _10YR20[x] ; + lbe = _10YR20[y]; + correctL = true; + } else if (x <= 45 && (hue <= (_85YR20[x] + _10YR20[x]) * 0.5f) && (hue > (_85YR20[x] + 0.035f))) { + if (y > 49) { + y = 49; + } + correction = _85YR20[y] - _85YR20[x] ; + lbe = _85YR20[y]; + correctL = true; + } + } else if (lum < 35.f) { + if (x < 85 && (hue <= (_10YR30[x] + 0.035f)) && (hue > (_10YR30[x] + _85YR30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10YR30[y] - _10YR30[x] ; + lbe = _10YR30[y]; + correctL = true; + } else if (x < 85 && (hue <= (_10YR30[x] + _85YR30[x]) * 0.5f) && (hue > (_85YR30[x] + _7YR30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _85YR30[y] - _85YR30[x] ; + lbe = _85YR30[y]; + correctL = true; + } else if (x < 85 && (hue <= (_85YR30[x] + _7YR30[x]) * 0.5f) && (hue > (_7YR30[x] + _55YR30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _7YR30[y] - _7YR30[x] ; + lbe = _7YR30[y]; + correctL = true; + } else if (x < 85 && (hue <= (_7YR30[x] + _55YR30[x]) * 0.5f) && (hue > (_55YR30[x] + _4YR30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _55YR30[y] - _55YR30[x] ; + lbe = _55YR30[y]; + correctL = true; + } else if (x < 85 && (hue <= (_55YR30[x] + _4YR30[x]) * 0.5f) && (hue > (_4YR30[x] + _25YR30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _4YR30[y] - _4YR30[x] ; + lbe = _4YR30[y]; + correctL = true; + } else if (x < 85 && (hue <= (_4YR30[x] + _25YR30[x]) * 0.5f) && (hue > (_25YR30[x] + _10R30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _25YR30[y] - _25YR30[x] ; + lbe = _25YR30[y]; + correctL = true; + } else if (x < 85 && (hue <= (_25YR30[x] + _10R30[x]) * 0.5f) && (hue > (_10R30[x] + _9R30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10R30[y] - _10R30[x] ; + lbe = _10R30[y]; + correctL = true; + } else if (x < 85 && (hue <= (_10R30[x] + _9R30[x]) * 0.5f) && (hue > (_9R30[x] + _7R30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _9R30[y] - _9R30[x] ; + lbe = _9R30[y]; + correctL = true; + } else if (x < 85 && (hue <= (_9R30[x] + _7R30[x]) * 0.5f) && (hue > (_7R30[x] - 0.035f))) { + if (y > 89) { + y = 89; + } + + correction = _7R30[y] - _7R30[x] ; + lbe = _7R30[y] ; + correctL = true; + } + } else if (lum < 45.f) { + if (x < 85 && (hue <= (_10YR40[x] + 0.035f)) && (hue > (_10YR40[x] + _85YR40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10YR40[y] - _10YR40[x] ; + lbe = _10YR40[y]; + correctL = true; + } else if (x < 85 && (hue <= (_10YR40[x] + _85YR40[x]) * 0.5f) && (hue > (_85YR40[x] + _7YR40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _85YR40[y] - _85YR40[x] ; + lbe = _85YR40[y]; + correctL = true; + } else if (x < 85 && (hue <= (_85YR40[x] + _7YR40[x]) * 0.5f) && (hue > (_7YR40[x] + _55YR40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _7YR40[y] - _7YR40[x] ; + lbe = _7YR40[y]; + correctL = true; + } else if (x < 85 && (hue <= (_7YR40[x] + _55YR40[x]) * 0.5f) && (hue > (_55YR40[x] + _4YR40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _55YR40[y] - _55YR40[x] ; + lbe = _55YR40[y]; + correctL = true; + } else if (x < 85 && (hue <= (_55YR40[x] + _4YR40[x]) * 0.5f) && (hue > (_4YR40[x] + _25YR40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _4YR40[y] - _4YR40[x] ; + lbe = _4YR40[y]; + correctL = true; + } else if (x < 85 && (hue <= (_4YR40[x] + _25YR40[x]) * 0.5f) && (hue > (_25YR40[x] + _10R40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _25YR40[y] - _25YR40[x] ; + lbe = _25YR40[y] ; + correctL = true; + } else if (x < 85 && (hue <= (_25YR40[x] + _10R40[x]) * 0.5f) && (hue > (_10R40[x] + _9R40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10R40[y] - _10R40[x] ; + lbe = _10R40[y]; + correctL = true; + } else if (x < 85 && (hue <= (_10R40[x] + _9R40[x]) * 0.5f) && (hue > (_9R40[x] + _7R40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _9R40[y] - _9R40[x] ; + lbe = _9R40[y]; + correctL = true; + } else if (x < 85 && (hue <= (_9R40[x] + _7R40[x]) * 0.5f) && (hue > (_7R40[x] - 0.035f))) { + if (y > 89) { + y = 89; + } + correction = _7R40[y] - _7R40[x] ; + lbe = _7R40[y]; + correctL = true; + } + } else if (lum < 55.f) { + if (x < 85 && (hue <= (_10YR50[x] + 0.035f)) && (hue > (_10YR50[x] + _85YR50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10YR50[y] - _10YR50[x] ; + lbe = _10YR50[y]; + correctL = true; + } else if (x < 85 && (hue <= (_10YR50[x] + _85YR50[x]) * 0.5f) && (hue > (_85YR50[x] + _7YR50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _85YR50[y] - _85YR50[x] ; + lbe = _85YR50[y]; + correctL = true; + } else if (x < 85 && (hue <= (_85YR50[x] + _7YR50[x]) * 0.5f) && (hue > (_7YR50[x] + _55YR50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _7YR50[y] - _7YR50[x] ; + lbe = _7YR50[y]; + correctL = true; + } else if (x < 85 && (hue <= (_7YR50[x] + _55YR50[x]) * 0.5f) && (hue > (_55YR50[x] + _4YR50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _55YR50[y] - _55YR50[x] ; + lbe = _55YR50[y]; + correctL = true; + } else if (x < 85 && (hue <= (_55YR50[x] + _4YR50[x]) * 0.5f) && (hue > (_4YR50[x] + _25YR50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _4YR50[y] - _4YR50[x] ; + lbe = _4YR50[y]; + correctL = true; + } else if (x < 85 && (hue <= (_4YR50[x] + _25YR50[x]) * 0.5f) && (hue > (_25YR50[x] + _10R50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _25YR50[y] - _25YR50[x] ; + lbe = _25YR50[y]; + correctL = true; + } else if (x < 85 && (hue <= (_25YR50[x] + _10R50[x]) * 0.5f) && (hue > (_10R50[x] + _9R50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10R50[y] - _10R50[x] ; + lbe = _10R50[y]; + correctL = true; + } else if (x < 85 && (hue <= (_10R50[x] + _9R50[x]) * 0.5f) && (hue > (_9R50[x] + _7R50[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _9R50[y] - _9R50[x] ; + lbe = _9R50[y]; + correctL = true; + } else if (x < 85 && (hue <= (_9R50[x] + _7R50[x]) * 0.5f) && (hue > (_7R50[x] - 0.035f))) { + if (y > 89) { + y = 89; + } + correction = _7R50[y] - _7R50[x] ; + lbe = _7R50[y]; + correctL = true; + } + } else if (lum < 65.f) { + if ((hue <= (_10YR60[x] + 0.035f)) && (hue > (_10YR60[x] + _85YR60[x]) * 0.5f)) { + correction = _10YR60[y] - _10YR60[x] ; + lbe = _10YR60[y]; + correctL = true; + } else if ((hue <= (_10YR60[x] + _85YR60[x]) * 0.5f) && (hue > (_85YR60[x] + _7YR60[x]) * 0.5f)) { + correction = _85YR60[y] - _85YR60[x] ; + lbe = _85YR60[y]; + correctL = true; + } else if ((hue <= (_85YR60[x] + _7YR60[x]) * 0.5f) && (hue > (_7YR60[x] + _55YR60[x]) * 0.5f)) { + correction = _7YR60[y] - _7YR60[x] ; + lbe = _7YR60[y]; + correctL = true; + } else if ((hue <= (_7YR60[x] + _55YR60[x]) * 0.5f) && (hue > (_55YR60[x] + _4YR60[x]) * 0.5f)) { + correction = _55YR60[y] - _55YR60[x] ; + lbe = _55YR60[y]; + correctL = true; + } else if ((hue <= (_55YR60[x] + _4YR60[x]) * 0.5f) && (hue > (_4YR60[x] + _25YR60[x]) * 0.5f)) { + correction = _4YR60[y] - _4YR60[x] ; + lbe = _4YR60[y]; + correctL = true; + } else if (x < 85 && (hue <= (_4YR60[x] + _25YR60[x]) * 0.5f) && (hue > (_25YR60[x] + _10R60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _25YR60[y] - _25YR60[x] ; + lbe = _25YR60[y]; + correctL = true; + } else if (x < 85 && (hue <= (_25YR60[x] + _10R60[x]) * 0.5f) && (hue > (_10R60[x] + _9R60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10R60[y] - _10R60[x] ; + lbe = _10R60[y]; + correctL = true; + } else if (x < 85 && (hue <= (_10R60[x] + _9R60[x]) * 0.5f) && (hue > (_9R60[x] + _7R60[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _9R60[y] - _9R60[x] ; + lbe = _9R60[y]; + correctL = true; + } else if (x < 85 && (hue <= (_9R60[x] + _7R60[x]) * 0.5f) && (hue > (_7R60[x] - 0.035f))) { + if (y > 89) { + y = 89; + } + correction = _7R60[y] - _7R60[x] ; + lbe = _7R60[y]; + correctL = true; + } + } else if (lum < 75.f) { + if ((hue <= (_10YR70[x] + 0.035f)) && (hue > (_10YR70[x] + _85YR70[x]) * 0.5f)) { + correction = _10YR70[y] - _10YR70[x] ; + lbe = _10YR70[y]; + correctL = true; + } else if ((hue <= (_10YR70[x] + _85YR70[x]) * 0.5f) && (hue > (_85YR70[x] + _7YR70[x]) * 0.5f)) { + correction = _85YR70[y] - _85YR70[x] ; + lbe = _85YR70[y]; + correctL = true; + } else if ((hue <= (_85YR70[x] + _7YR70[x]) * 0.5f) && (hue > (_7YR70[x] + _55YR70[x]) * 0.5f)) { + correction = _7YR70[y] - _7YR70[x] ; + lbe = _7YR70[y]; + correctL = true; + } else if ((hue <= (_7YR70[x] + _55YR70[x]) * 0.5f) && (hue > (_55YR70[x] + _4YR70[x]) * 0.5f)) { + correction = _55YR70[y] - _55YR70[x] ; + lbe = _55YR70[y]; + correctL = true; + } else if ((hue <= (_55YR70[x] + _4YR70[x]) * 0.5f) && (hue > (_4YR70[x] + _25YR70[x]) * 0.5f)) { + correction = _4YR70[y] - _4YR70[x] ; + lbe = _4YR70[y]; + correctL = true; + } else if (x < 85 && (hue <= (_4YR70[x] + _25YR70[x]) * 0.5f) && (hue > (_25YR70[x] + _10R70[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _25YR70[y] - _25YR70[x] ; + lbe = _25YR70[y]; + correctL = true; + } else if (x < 85 && (hue <= (_25YR70[x] + _10R70[x]) * 0.5f) && (hue > (_10R70[x] + _9R70[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10R70[y] - _10R70[x] ; + lbe = _10R70[y]; + correctL = true; + } else if (x < 85 && (hue <= (_10R70[x] + _9R70[x]) * 0.5f) && (hue > (_9R70[x] + _7R70[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _9R70[y] - _9R70[x] ; + lbe = _9R70[y] ; + correctL = true; + } else if (x < 85 && (hue <= (_9R70[x] + _7R70[x]) * 0.5f) && (hue > (_7R70[x] - 0.035f))) { + if (y > 89) { + y = 89; + } + correction = _7R70[y] - _7R70[x] ; + lbe = _7R70[y]; + correctL = true; + } + } else if (lum < 85.f) { + if ((hue <= (_10YR80[x] + 0.035f)) && (hue > (_10YR80[x] + _85YR80[x]) * 0.5f)) { + correction = _10YR80[y] - _10YR80[x] ; + lbe = _10YR80[y]; + correctL = true; + } else if ((hue <= (_10YR80[x] + _85YR80[x]) * 0.5f) && (hue > (_85YR80[x] + _7YR80[x]) * 0.5f)) { + correction = _85YR80[y] - _85YR80[x] ; + lbe = _85YR80[y]; + } else if (x < 85 && (hue <= (_85YR80[x] + _7YR80[x]) * 0.5f) && (hue > (_7YR80[x] + _55YR80[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _7YR80[y] - _7YR80[x] ; + lbe = _7YR80[y]; + correctL = true; + } else if (x < 45 && (hue <= (_7YR80[x] + _55YR80[x]) * 0.5f) && (hue > (_55YR80[x] + _4YR80[x]) * 0.5f)) { + correction = _55YR80[y] - _55YR80[x] ; + lbe = _55YR80[y]; + correctL = true; + } else if (x < 45 && (hue <= (_55YR80[x] + _4YR80[x]) * 0.5f) && (hue > (_4YR80[x] - 0.035f))) { + if (y > 49) { + y = 49; + } + correction = _4YR80[y] - _4YR80[x] ; + lbe = _4YR80[y] ; + correctL = true; + } + } else if (lum < 95.f) { + if (x < 85 && (hue <= (_10YR90[x] + 0.035f)) && (hue > (_10YR90[x] - 0.035f))) { + if (y > 89) { + y = 89; + } + correction = _10YR90[y] - _10YR90[x] ; + lbe = _10YR90[y]; + correctL = true; + } else if (x < 85 && hue <= (_85YR90[x] + 0.035f) && hue > (_85YR90[x] - 0.035f)) { + if (y > 89) { + y = 89; + } + correction = _85YR90[y] - _85YR90[x] ; + lbe = _85YR90[y]; + correctL = true; + } else if (x < 45 && (hue <= (_55YR90[x] + 0.035f) && (hue > (_55YR90[x] - 0.035f)))) { + if (y > 49) { + y = 49; + } + correction = _55YR90[y] - _55YR90[x] ; + lbe = _55YR90[y]; + correctL = true; + } + } + } + } else if (zone == 3) { // //Green yellow correction + if (lum >= 25.f) { + if (lum < 35.f) { + if ((hue <= (_7G30[x] + 0.035f)) && (hue > (_7G30[x] + _5G30[x]) * 0.5f)) { + correction = _7G30[y] - _7G30[x] ; + lbe = _7G30[y]; + correctL = true; + } else if ((hue <= (_7G30[x] + _5G30[x]) * 0.5f) && (hue > (_5G30[x] + _25G30[x]) * 0.5f)) { + correction = _5G30[y] - _5G30[x] ; + lbe = _5G30[y]; + correctL = true; + } else if ((hue <= (_25G30[x] + _5G30[x]) * 0.5f) && (hue > (_25G30[x] + _1G30[x]) * 0.5f)) { + correction = _25G30[y] - _25G30[x] ; + lbe = _25G30[y]; + correctL = true; + } else if ((hue <= (_1G30[x] + _25G30[x]) * 0.5f) && (hue > (_1G30[x] + _10GY30[x]) * 0.5f)) { + correction = _1G30[y] - _1G30[x] ; + lbe = _1G30[y]; + correctL = true; + } else if (x < 85 && (hue <= (_1G30[x] + _10GY30[x]) * 0.5f) && (hue > (_10GY30[x] + _75GY30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10GY30[y] - _10GY30[x] ; + lbe = _10GY30[y]; + correctL = true; + } else if (x < 85 && (hue <= (_10GY30[x] + _75GY30[x]) * 0.5f) && (hue > (_75GY30[x] + _5GY30[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _75GY30[y] - _75GY30[x] ; + lbe = _75GY30[y]; + correctL = true; + } else if (x < 85 && (hue <= (_5GY30[x] + _75GY30[x]) * 0.5f) && (hue > (_5GY30[x] - 0.035f))) { + if (y > 89) { + y = 89; + } + correction = _5GY30[y] - _5GY30[x] ; + lbe = _5GY30[y] ; + correctL = true; + } + } else if (lum < 45.f) { + if ((hue <= (_7G40[x] + 0.035f)) && (hue > (_7G40[x] + _5G40[x]) * 0.5f)) { + correction = _7G40[y] - _7G40[x] ; + lbe = _7G40[y]; + correctL = true; + } else if ((hue <= (_7G40[x] + _5G40[x]) * 0.5f) && (hue > (_5G40[x] + _25G40[x]) * 0.5f)) { + correction = _5G40[y] - _5G40[x] ; + lbe = _5G40[y]; + correctL = true; + } else if ((hue <= (_25G40[x] + _5G40[x]) * 0.5f) && (hue > (_25G40[x] + _1G40[x]) * 0.5f)) { + correction = _25G40[y] - _25G40[x] ; + lbe = _25G40[y]; + correctL = true; + } else if ((hue <= (_1G40[x] + _25G40[x]) * 0.5f) && (hue > (_1G40[x] + _10GY40[x]) * 0.5f)) { + correction = _1G40[y] - _1G40[x] ; + lbe = _1G40[y]; + correctL = true; + } else if (x < 85 && (hue <= (_1G40[x] + _10GY40[x]) * 0.5f) && (hue > (_10GY40[x] + _75GY40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _10GY40[y] - _10GY40[x] ; + lbe = _10GY40[y]; + correctL = true; + } else if (x < 85 && (hue <= (_10GY40[x] + _75GY40[x]) * 0.5f) && (hue > (_75GY40[x] + _5GY40[x]) * 0.5f)) { + if (y > 89) { + y = 89; + } + correction = _75GY40[y] - _75GY40[x] ; + lbe = _75GY40[y]; + correctL = true; + } else if (x < 85 && (hue <= (_5GY40[x] + _75GY40[x]) * 0.5f) && (hue > (_5GY40[x] - 0.035f))) { + if (y > 89) { + y = 89; // + } + correction = _5GY40[y] - _5GY40[x] ; + lbe = _5GY40[y]; + correctL = true; + } + } else if (lum < 55.f) { + if ((hue <= (_7G50[x] + 0.035f)) && (hue > (_7G50[x] + _5G50[x]) * 0.5f)) { + correction = _7G50[y] - _7G50[x] ; + lbe = _7G50[y]; + correctL = true; + } else if ((hue <= (_7G50[x] + _5G50[x]) * 0.5f) && (hue > (_5G50[x] + _25G50[x]) * 0.5f)) { + correction = _5G50[y] - _5G50[x] ; + lbe = _5G50[y]; + correctL = true; + } else if ((hue <= (_25G50[x] + _5G50[x]) * 0.5f) && (hue > (_25G50[x] + _1G50[x]) * 0.5f)) { + correction = _25G50[y] - _25G50[x] ; + lbe = _25G50[y]; + correctL = true; + } else if ((hue <= (_1G50[x] + _25G50[x]) * 0.5f) && (hue > (_1G50[x] + _10GY50[x]) * 0.5f)) { + correction = _1G50[y] - _1G50[x] ; + lbe = _1G50[y]; + correctL = true; + } else if ((hue <= (_1G50[x] + _10GY50[x]) * 0.5f) && (hue > (_10GY50[x] + _75GY50[x]) * 0.5f)) { + correction = _10GY50[y] - _10GY50[x] ; + lbe = _10GY50[y]; + correctL = true; + } else if ((hue <= (_10GY50[x] + _75GY50[x]) * 0.5f) && (hue > (_75GY50[x] + _5GY50[x]) * 0.5f)) { + correction = _75GY50[y] - _75GY50[x] ; + lbe = _75GY50[y]; + correctL = true; + } else if ((hue <= (_5GY50[x] + _75GY50[x]) * 0.5f) && (hue > (_5GY50[x] - 0.035f))) { + correction = _5GY50[y] - _5GY50[x] ; + lbe = _5GY50[y]; + correctL = true; + } + } else if (lum < 65.f) { + if ((hue <= (_7G60[x] + 0.035f)) && (hue > (_7G60[x] + _5G60[x]) * 0.5f)) { + correction = _7G60[y] - _7G60[x] ; + lbe = _7G60[y]; + correctL = true; + } else if ((hue <= (_7G60[x] + _5G60[x]) * 0.5f) && (hue > (_5G60[x] + _25G60[x]) * 0.5f)) { + correction = _5G60[y] - _5G60[x] ; + lbe = _5G60[y]; + correctL = true; + } else if ((hue <= (_25G60[x] + _5G60[x]) * 0.5f) && (hue > (_25G60[x] + _1G60[x]) * 0.5f)) { + correction = _25G60[y] - _25G60[x] ; + lbe = _25G60[y]; + correctL = true; + } else if ((hue <= (_1G60[x] + _25G60[x]) * 0.5f) && (hue > (_1G60[x] + _10GY60[x]) * 0.5f)) { + correction = _1G60[y] - _1G60[x] ; + lbe = _1G60[y]; + correctL = true; + } else if ((hue <= (_1G60[x] + _10GY60[x]) * 0.5f) && (hue > (_10GY60[x] + _75GY60[x]) * 0.5f)) { + correction = _10GY60[y] - _10GY60[x] ; + lbe = _10GY60[y]; + correctL = true; + } else if ((hue <= (_10GY60[x] + _75GY60[x]) * 0.5f) && (hue > (_75GY60[x] + _5GY60[x]) * 0.5f)) { + correction = _75GY60[y] - _75GY60[x] ; + lbe = _75GY60[y] ; + correctL = true; + } else if ((hue <= (_5GY60[x] + _75GY60[x]) * 0.5f) && (hue > (_5GY60[x] - 0.035f))) { + correction = _5GY60[y] - _5GY60[x] ; + lbe = _5GY60[y]; + correctL = true; + } + } else if (lum < 75.f) { + if ((hue <= (_7G70[x] + 0.035f)) && (hue > (_7G70[x] + _5G70[x]) * 0.5f)) { + correction = _7G70[y] - _7G70[x] ; + lbe = _7G70[y]; + correctL = true; + } else if ((hue <= (_7G70[x] + _5G70[x]) * 0.5f) && (hue > (_5G70[x] + _25G70[x]) * 0.5f)) { + correction = _5G70[y] - _5G70[x] ; + lbe = _5G70[y]; + correctL = true; + } else if ((hue <= (_25G70[x] + _5G70[x]) * 0.5f) && (hue > (_25G70[x] + _1G70[x]) * 0.5f)) { + correction = _25G70[y] - _25G70[x] ; + lbe = _25G70[y]; + correctL = true; + } else if ((hue <= (_1G70[x] + _25G70[x]) * 0.5f) && (hue > (_1G70[x] + _10GY70[x]) * 0.5f)) { + correction = _1G70[y] - _1G70[x] ; + lbe = _1G70[y] ; + correctL = true; + } else if ((hue <= (_1G70[x] + _10GY70[x]) * 0.5f) && (hue > (_10GY70[x] + _75GY70[x]) * 0.5f)) { + correction = _10GY70[y] - _10GY70[x] ; + lbe = _10GY70[y]; + correctL = true; + } else if ((hue <= (_10GY70[x] + _75GY70[x]) * 0.5f) && (hue > (_75GY70[x] + _5GY70[x]) * 0.5f)) { + correction = _75GY70[y] - _75GY70[x] ; + lbe = _75GY70[y]; + correctL = true; + } else if ((hue <= (_5GY70[x] + _75GY70[x]) * 0.5f) && (hue > (_5GY70[x] - 0.035f))) { + correction = _5GY70[y] - _5GY70[x] ; + lbe = _5GY70[y]; + correctL = true; + } + } else if (lum < 85.f) { + if ((hue <= (_7G80[x] + 0.035f)) && (hue > (_7G80[x] + _5G80[x]) * 0.5f)) { + correction = _7G80[y] - _7G80[x] ; + lbe = _7G80[y]; + correctL = true; + } else if ((hue <= (_7G80[x] + _5G80[x]) * 0.5f) && (hue > (_5G80[x] + _25G80[x]) * 0.5f)) { + correction = _5G80[y] - _5G80[x] ; + lbe = _5G80[y]; + correctL = true; + } else if ((hue <= (_25G80[x] + _5G80[x]) * 0.5f) && (hue > (_25G80[x] + _1G80[x]) * 0.5f)) { + correction = _25G80[y] - _25G80[x] ; + lbe = _25G80[y]; + correctL = true; + } else if ((hue <= (_1G80[x] + _25G80[x]) * 0.5f) && (hue > (_1G80[x] + _10GY80[x]) * 0.5f)) { + correction = _1G80[y] - _1G80[x] ; + lbe = _1G80[y]; + correctL = true; + } else if ((hue <= (_1G80[x] + _10GY80[x]) * 0.5f) && (hue > (_10GY80[x] + _75GY80[x]) * 0.5f)) { + correction = _10GY80[y] - _10GY80[x] ; + lbe = _10GY80[y]; + correctL = true; + } else if ((hue <= (_10GY80[x] + _75GY80[x]) * 0.5f) && (hue > (_75GY80[x] + _5GY80[x]) * 0.5f)) { + correction = _75GY80[y] - _75GY80[x] ; + lbe = _75GY80[y]; + correctL = true; + } else if ((hue <= (_5GY80[x] + _75GY80[x]) * 0.5f) && (hue > (_5GY80[x] - 0.035f))) { + correction = _5GY80[y] - _5GY80[x] ; + lbe = _5GY80[y]; + correctL = true; + } + } + } + } else if (zone == 4) { //Red purple correction : only for L < 30 + if (lum > 5.f) { + if (lum < 15.f && x < 45) { + y = std::min(y, 44); + if ((hue <= (_5R10[x] + 0.035f)) && (hue > (_5R10[x] - 0.043f))) { + correction = _5R10[y] - _5R10[x] ; + lbe = _5R10[y]; + correctL = true; + } else if ((hue <= (_25R10[x] + 0.043f)) && (hue > (_25R10[x] + _10RP10[x]) * 0.5f)) { + correction = _25R10[y] - _25R10[x] ; + lbe = _25R10[y]; + correctL = true; + } else if ((hue <= (_25R10[x] + _10RP10[x]) * 0.5f) && (hue > (_10RP10[x] - 0.035f))) { + correction = _10RP10[y] - _10RP10[x] ; + lbe = _10RP10[y]; + correctL = true; + } + } else if (lum < 25.f && x < 70) { + y = std::min(y, 70); + if ((hue <= (_5R20[x] + 0.035f)) && (hue > (_5R20[x] + _25R20[x]) * 0.5f)) { + correction = _5R20[y] - _5R20[x] ; + lbe = _5R20[y]; + correctL = true; + } else if ((hue <= (_5R20[x] + _25R20[x]) * 0.5f) && (hue > (_10RP20[x] + _25R20[x]) * 0.5f)) { + correction = _25R20[y] - _25R20[x] ; + lbe = _25R20[y]; + correctL = true; + } else if ( (hue <= (_10RP20[x] + _25R20[x]) * 0.5f) && (hue > (_10RP20[x] - 0.035f))) { + correction = _10RP20[y] - _10RP20[x] ; + lbe = _10RP20[y]; + correctL = true; + } + } else if (lum < 35.f && x < 85) { + y = rtengine::min(y, 85); + if ((hue <= (_5R30[x] + 0.035f)) && (hue > (_5R30[x] + _25R30[x]) * 0.5f)) { + correction = _5R30[y] - _5R30[x] ; + lbe = _5R30[y]; + correctL = true; + } else if ((hue <= (_5R30[x] + _25R30[x]) * 0.5f) && (hue > (_10RP30[x] + _25R30[x]) * 0.5f)) { + correction = _25R30[y] - _25R30[x] ; + lbe = _25R30[y]; + correctL = true; + } else if ((hue <= (_10RP30[x] + _25R30[x]) * 0.5f) && (hue > (_10RP30[x] - 0.035f))) { + correction = _10RP30[y] - _10RP30[x] ; + lbe = _10RP30[y]; + correctL = true; + } + } + } + } + //end red purple +} +} diff --git a/rtengine/opthelper.h b/rtengine/opthelper.h index b65ede227..f431c0ec9 100644 --- a/rtengine/opthelper.h +++ b/rtengine/opthelper.h @@ -18,27 +18,24 @@ // along with this program. If not, see . // //////////////////////////////////////////////////////////////// +#pragma once -#ifndef OPTHELPER_H - #define OPTHELPER_H +#define pow_F(a,b) (xexpf(b*xlogf(a))) - #define pow_F(a,b) (xexpf(b*xlogf(a))) - - #ifdef __SSE2__ - #include "sleefsseavx.c" - #endif - - #ifdef __GNUC__ - #define RESTRICT __restrict__ - #define LIKELY(x) __builtin_expect (!!(x), 1) - #define UNLIKELY(x) __builtin_expect (!!(x), 0) - #define ALIGNED64 __attribute__ ((aligned (64))) - #define ALIGNED16 __attribute__ ((aligned (16))) - #else - #define RESTRICT - #define LIKELY(x) (x) - #define UNLIKELY(x) (x) - #define ALIGNED64 - #define ALIGNED16 - #endif +#ifdef __SSE2__ + #include "sleefsseavx.h" +#endif + +#ifdef __GNUC__ + #define RESTRICT __restrict__ + #define LIKELY(x) __builtin_expect (!!(x), 1) + #define UNLIKELY(x) __builtin_expect (!!(x), 0) + #define ALIGNED64 __attribute__ ((aligned (64))) + #define ALIGNED16 __attribute__ ((aligned (16))) +#else + #define RESTRICT + #define LIKELY(x) (x) + #define UNLIKELY(x) (x) + #define ALIGNED64 + #define ALIGNED16 #endif diff --git a/rtengine/pdaflinesfilter.cc b/rtengine/pdaflinesfilter.cc index 1eddbc1ea..b5c72f7f4 100644 --- a/rtengine/pdaflinesfilter.cc +++ b/rtengine/pdaflinesfilter.cc @@ -177,7 +177,7 @@ PDAFLinesFilter::PDAFLinesFilter(RawImage *ri): gthresh_ = new PDAFGreenEqulibrateThreshold(W_, H_); CameraConstantsStore* ccs = CameraConstantsStore::getInstance(); - CameraConst *cc = ccs->get(ri_->get_maker().c_str(), ri_->get_model().c_str()); + const CameraConst *cc = ccs->get(ri_->get_maker().c_str(), ri_->get_model().c_str()); if (cc) { pattern_ = cc->get_pdafPattern(); diff --git a/rtengine/previewimage.h b/rtengine/previewimage.h index e6c3ea070..2143509a3 100644 --- a/rtengine/previewimage.h +++ b/rtengine/previewimage.h @@ -18,10 +18,16 @@ */ #pragma once -#include #include +namespace Glib +{ + +class ustring; + +} + namespace rtengine { diff --git a/rtengine/processingjob.h b/rtengine/processingjob.h index 6cdc6bd7c..9c3846958 100644 --- a/rtengine/processingjob.h +++ b/rtengine/processingjob.h @@ -24,7 +24,7 @@ namespace rtengine { -class ProcessingJobImpl : public ProcessingJob +class ProcessingJobImpl final : public ProcessingJob { public: diff --git a/rtengine/procparams.cc b/rtengine/procparams.cc index bb55cf41d..af48d027a 100644 --- a/rtengine/procparams.cc +++ b/rtengine/procparams.cc @@ -1305,9 +1305,12 @@ bool WBParams::operator !=(const WBParams& other) const const std::vector& WBParams::getWbEntries() { + + static const std::vector wb_entries = { {"Camera", WBEntry::Type::CAMERA, M("TP_WBALANCE_CAMERA"), 0, 1.f, 1.f, 0.f}, - {"Auto", WBEntry::Type::AUTO, M("TP_WBALANCE_AUTO"), 0, 1.f, 1.f, 0.f}, + {"autitcgreen", WBEntry::Type::AUTO, M("TP_WBALANCE_AUTOITCGREEN"), 0, 1.f, 1.f, 0.f}, + {"autold", WBEntry::Type::AUTO, M("TP_WBALANCE_AUTOOLD"), 0, 1.f, 1.f, 0.f}, {"Daylight", WBEntry::Type::DAYLIGHT, M("TP_WBALANCE_DAYLIGHT"), 5300, 1.f, 1.f, 0.f}, {"Cloudy", WBEntry::Type::CLOUDY, M("TP_WBALANCE_CLOUDY"), 6200, 1.f, 1.f, 0.f}, {"Shade", WBEntry::Type::SHADE, M("TP_WBALANCE_SHADE"), 7600, 1.f, 1.f, 0.f}, @@ -1341,7 +1344,6 @@ const std::vector& WBParams::getWbEntries() // Should remain the last one {"Custom", WBEntry::Type::CUSTOM, M("TP_WBALANCE_CUSTOM"), 0, 1.f, 1.f, 0.f} }; - return wb_entries; } @@ -1372,6 +1374,7 @@ ColorAppearanceParams::ColorAppearanceParams() : adaplum(16), badpixsl(0), wbmodel("RawT"), + illum("i50"), algo("No"), contrast(0.0), qcontrast(0.0), @@ -1387,10 +1390,12 @@ ColorAppearanceParams::ColorAppearanceParams() : datacie(false), tonecie(false), tempout(5000), + autotempout(true), ybout(18), greenout(1.0), - tempsc(5000), - greensc(1.0) + tempsc(5003), + greensc(1.0), + presetcat02(false) { } @@ -1417,6 +1422,7 @@ bool ColorAppearanceParams::operator ==(const ColorAppearanceParams& other) cons && adaplum == other.adaplum && badpixsl == other.badpixsl && wbmodel == other.wbmodel + && illum == other.illum && algo == other.algo && contrast == other.contrast && qcontrast == other.qcontrast @@ -1432,10 +1438,12 @@ bool ColorAppearanceParams::operator ==(const ColorAppearanceParams& other) cons && datacie == other.datacie && tonecie == other.tonecie && tempout == other.tempout + && autotempout == other.autotempout && ybout == other.ybout && greenout == other.greenout && tempsc == other.tempsc - && greensc == other.greensc; + && greensc == other.greensc + && presetcat02 == other.presetcat02; } bool ColorAppearanceParams::operator !=(const ColorAppearanceParams& other) const @@ -2182,6 +2190,18 @@ WaveletParams::WaveletParams() : 0.35, 0.35 }, + blcurve{ + static_cast(FCT_MinMaxCPoints), +0.0, 0.0, 0.0, 0.35, 0.5, 0., 0.35, 0.35, 1.0, 0.0, 0.35, 0.35 +/* 0.0, + 0.75, + 0.35, + 0.35, + 1.0, + 0.75, + 0.35, + 0.35*/ + }, opacityCurveRG{ static_cast(FCT_MinMaxCPoints), 0.0, @@ -2254,8 +2274,18 @@ WaveletParams::WaveletParams() : bluemed(0), greenhigh(0), bluehigh(0), + ballum(7.), + balchrom(0.), + chromfi(0.), + chromco(0.), + mergeL(40.), + mergeC(20.), + softrad(0.), + softradend(0.), lipst(false), avoid(false), + showmask(false), + oldsh(true), tmr(false), strength(100), balance(0), @@ -2265,10 +2295,12 @@ WaveletParams::WaveletParams() : c{}, ch{}, expedge(false), + expbl(false), expresid(false), expfinal(false), exptoning(false), expnoise(false), + expclari(false), Lmethod(4), CLmethod("all"), Backmethod("grey"), @@ -2276,6 +2308,7 @@ WaveletParams::WaveletParams() : daubcoeffmethod("4_"), CHmethod("without"), Medgreinf("less"), + ushamethod("clari"), CHSLmethod("SL"), EDmethod("CU"), NPmethod("none"), @@ -2283,10 +2316,17 @@ WaveletParams::WaveletParams() : TMmethod("cont"), Dirmethod("all"), HSmethod("with"), + sigma(1.0), + offset(1.0), + lowthr(40.0), rescon(0), resconH(0), reschro(0), + resblur(0), + resblurc(0), tmrs(0), + edgs(1.4), + scale(1.), gamma(1), sup(0), sky(0.0), @@ -2302,11 +2342,15 @@ WaveletParams::WaveletParams() : edgeampli(10), contrast(0), edgrad(15), + edgeffect(1.0), edgval(0), edgthresh(10), - thr(35), - thrH(65), + thr(30), + thrH(70), + radius(40), skinprotect(0.0), + chrwav(0.), + bluwav(1.0), hueskin(-5, 25, 170, 120, false), hueskin2(-260, -250, -130, -140, false), hllev(50, 75, 100, 98, false), @@ -2325,6 +2369,7 @@ bool WaveletParams::operator ==(const WaveletParams& other) const { return ccwcurve == other.ccwcurve + && blcurve == other.blcurve && opacityCurveRG == other.opacityCurveRG && opacityCurveBY == other.opacityCurveBY && opacityCurveW == other.opacityCurveW @@ -2343,8 +2388,18 @@ bool WaveletParams::operator ==(const WaveletParams& other) const && bluemed == other.bluemed && greenhigh == other.greenhigh && bluehigh == other.bluehigh + && ballum == other.ballum + && balchrom == other.balchrom + && chromfi == other.chromfi + && chromco == other.chromco + && mergeL == other.mergeL + && mergeC == other.mergeC + && softrad == other.softrad + && softradend == other.softradend && lipst == other.lipst && avoid == other.avoid + && showmask == other.showmask + && oldsh == other.oldsh && tmr == other.tmr && strength == other.strength && balance == other.balance @@ -2361,8 +2416,10 @@ bool WaveletParams::operator ==(const WaveletParams& other) const return true; }() && expedge == other.expedge + && expbl == other.expbl && expresid == other.expresid && expfinal == other.expfinal + && expclari == other.expclari && exptoning == other.exptoning && expnoise == other.expnoise && Lmethod == other.Lmethod @@ -2372,6 +2429,7 @@ bool WaveletParams::operator ==(const WaveletParams& other) const && daubcoeffmethod == other.daubcoeffmethod && CHmethod == other.CHmethod && Medgreinf == other.Medgreinf + && ushamethod == other.ushamethod && CHSLmethod == other.CHSLmethod && EDmethod == other.EDmethod && NPmethod == other.NPmethod @@ -2379,10 +2437,17 @@ bool WaveletParams::operator ==(const WaveletParams& other) const && TMmethod == other.TMmethod && Dirmethod == other.Dirmethod && HSmethod == other.HSmethod + && sigma == other.sigma + && offset == other.offset + && lowthr == other.lowthr && rescon == other.rescon && resconH == other.resconH && reschro == other.reschro + && resblur == other.resblur + && resblurc == other.resblurc && tmrs == other.tmrs + && edgs == other.edgs + && scale == other.scale && gamma == other.gamma && sup == other.sup && sky == other.sky @@ -2398,11 +2463,15 @@ bool WaveletParams::operator ==(const WaveletParams& other) const && edgeampli == other.edgeampli && contrast == other.contrast && edgrad == other.edgrad + && edgeffect == other.edgeffect && edgval == other.edgval && edgthresh == other.edgthresh && thr == other.thr && thrH == other.thrH + && radius == other.radius && skinprotect == other.skinprotect + && chrwav == other.chrwav + && bluwav == other.bluwav && hueskin == other.hueskin && hueskin2 == other.hueskin2 && hllev == other.hllev @@ -2423,6 +2492,7 @@ bool WaveletParams::operator !=(const WaveletParams& other) const void WaveletParams::getCurves( WavCurve& cCurve, + Wavblcurve& tCurve, WavOpacityCurveRG& opacityCurveLUTRG, WavOpacityCurveBY& opacityCurveLUTBY, WavOpacityCurveW& opacityCurveLUTW, @@ -2430,6 +2500,7 @@ void WaveletParams::getCurves( ) const { cCurve.Set(this->ccwcurve); + tCurve.Set(this->blcurve); opacityCurveLUTRG.Set(this->opacityCurveRG); opacityCurveLUTBY.Set(this->opacityCurveBY); opacityCurveLUTW.Set(this->opacityCurveW); @@ -2845,7 +2916,10 @@ FilmNegativeParams::FilmNegativeParams() : enabled(false), redRatio(1.36), greenExp(1.5), - blueRatio(0.86) + blueRatio(0.86), + redBase(0), + greenBase(0), + blueBase(0) { } @@ -2853,9 +2927,12 @@ bool FilmNegativeParams::operator ==(const FilmNegativeParams& other) const { return enabled == other.enabled - && redRatio == other.redRatio + && redRatio == other.redRatio && greenExp == other.greenExp - && blueRatio == other.blueRatio; + && blueRatio == other.blueRatio + && redBase == other.redBase + && greenBase == other.greenBase + && blueBase == other.blueBase; } bool FilmNegativeParams::operator !=(const FilmNegativeParams& other) const @@ -3212,6 +3289,7 @@ int ProcParams::save(const Glib::ustring& fname, const Glib::ustring& fname2, bo saveToKeyfile(!pedited || pedited->colorappearance.adaplum, "Color appearance", "AdaptLum", colorappearance.adaplum, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.badpixsl, "Color appearance", "Badpixsl", colorappearance.badpixsl, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.wbmodel, "Color appearance", "Model", colorappearance.wbmodel, keyFile); + saveToKeyfile(!pedited || pedited->colorappearance.illum, "Color appearance", "Illum", colorappearance.illum, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.algo, "Color appearance", "Algorithm", colorappearance.algo, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.jlight, "Color appearance", "J-Light", colorappearance.jlight, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.qbright, "Color appearance", "Q-Bright", colorappearance.qbright, keyFile); @@ -3229,12 +3307,14 @@ int ProcParams::save(const Glib::ustring& fname, const Glib::ustring& fname2, bo saveToKeyfile(!pedited || pedited->colorappearance.surrsource, "Color appearance", "SurrSource", colorappearance.surrsource, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.gamut, "Color appearance", "Gamut", colorappearance.gamut, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.tempout, "Color appearance", "Tempout", colorappearance.tempout, keyFile); + saveToKeyfile(!pedited || pedited->colorappearance.autotempout, "Color appearance", "Autotempout", colorappearance.autotempout, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.greenout, "Color appearance", "Greenout", colorappearance.greenout, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.tempsc, "Color appearance", "Tempsc", colorappearance.tempsc, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.greensc, "Color appearance", "Greensc", colorappearance.greensc, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.ybout, "Color appearance", "Ybout", colorappearance.ybout, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.datacie, "Color appearance", "Datacie", colorappearance.datacie, keyFile); saveToKeyfile(!pedited || pedited->colorappearance.tonecie, "Color appearance", "Tonecie", colorappearance.tonecie, keyFile); + saveToKeyfile(!pedited || pedited->colorappearance.presetcat02, "Color appearance", "Presetcat02", colorappearance.presetcat02, keyFile); const std::map ca_mapping = { {ColorAppearanceParams::TcMode::LIGHT, "Lightness"}, @@ -3494,13 +3574,23 @@ int ProcParams::save(const Glib::ustring& fname, const Glib::ustring& fname2, bo saveToKeyfile(!pedited || pedited->wavelet.bluehigh, "Wavelet", "CBbluehigh", wavelet.bluehigh, keyFile); saveToKeyfile(!pedited || pedited->wavelet.bluemed, "Wavelet", "CBbluemed", wavelet.bluemed, keyFile); saveToKeyfile(!pedited || pedited->wavelet.bluelow, "Wavelet", "CBbluelow", wavelet.bluelow, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.ballum, "Wavelet", "Ballum", wavelet.ballum, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.balchrom, "Wavelet", "Balchrom", wavelet.balchrom, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.chromfi, "Wavelet", "Chromfine", wavelet.chromfi, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.chromco, "Wavelet", "Chromcoarse", wavelet.chromco, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.mergeL, "Wavelet", "MergeL", wavelet.mergeL, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.mergeC, "Wavelet", "MergeC", wavelet.mergeC, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.softrad, "Wavelet", "Softrad", wavelet.softrad, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.softradend, "Wavelet", "Softradend", wavelet.softradend, keyFile); saveToKeyfile(!pedited || pedited->wavelet.expcontrast, "Wavelet", "Expcontrast", wavelet.expcontrast, keyFile); saveToKeyfile(!pedited || pedited->wavelet.expchroma, "Wavelet", "Expchroma", wavelet.expchroma, keyFile); saveToKeyfile(!pedited || pedited->wavelet.expedge, "Wavelet", "Expedge", wavelet.expedge, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.expbl, "Wavelet", "expbl", wavelet.expbl, keyFile); saveToKeyfile(!pedited || pedited->wavelet.expresid, "Wavelet", "Expresid", wavelet.expresid, keyFile); saveToKeyfile(!pedited || pedited->wavelet.expfinal, "Wavelet", "Expfinal", wavelet.expfinal, keyFile); saveToKeyfile(!pedited || pedited->wavelet.exptoning, "Wavelet", "Exptoning", wavelet.exptoning, keyFile); saveToKeyfile(!pedited || pedited->wavelet.expnoise, "Wavelet", "Expnoise", wavelet.expnoise, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.expclari, "Wavelet", "Expclari", wavelet.expclari, keyFile); for (int i = 0; i < 9; i++) { std::stringstream ss; @@ -3535,6 +3625,7 @@ int ProcParams::save(const Glib::ustring& fname, const Glib::ustring& fname2, bo saveToKeyfile(!pedited || pedited->wavelet.chroma, "Wavelet", "ThresholdChroma", wavelet.chroma, keyFile); saveToKeyfile(!pedited || pedited->wavelet.CHmethod, "Wavelet", "CHromaMethod", wavelet.CHmethod, keyFile); saveToKeyfile(!pedited || pedited->wavelet.Medgreinf, "Wavelet", "Medgreinf", wavelet.Medgreinf, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.ushamethod, "Wavelet", "Ushamethod", wavelet.ushamethod, keyFile); saveToKeyfile(!pedited || pedited->wavelet.CHSLmethod, "Wavelet", "CHSLromaMethod", wavelet.CHSLmethod, keyFile); saveToKeyfile(!pedited || pedited->wavelet.EDmethod, "Wavelet", "EDMethod", wavelet.EDmethod, keyFile); saveToKeyfile(!pedited || pedited->wavelet.NPmethod, "Wavelet", "NPMethod", wavelet.NPmethod, keyFile); @@ -3542,6 +3633,7 @@ int ProcParams::save(const Glib::ustring& fname, const Glib::ustring& fname2, bo saveToKeyfile(!pedited || pedited->wavelet.TMmethod, "Wavelet", "TMMethod", wavelet.TMmethod, keyFile); saveToKeyfile(!pedited || pedited->wavelet.chro, "Wavelet", "ChromaLink", wavelet.chro, keyFile); saveToKeyfile(!pedited || pedited->wavelet.ccwcurve, "Wavelet", "ContrastCurve", wavelet.ccwcurve, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.blcurve, "Wavelet", "blcurve", wavelet.blcurve, keyFile); saveToKeyfile(!pedited || pedited->wavelet.pastlev, "Wavelet", "Pastlev", wavelet.pastlev.toVector(), keyFile); saveToKeyfile(!pedited || pedited->wavelet.satlev, "Wavelet", "Satlev", wavelet.satlev.toVector(), keyFile); saveToKeyfile(!pedited || pedited->wavelet.opacityCurveRG, "Wavelet", "OpacityCurveRG", wavelet.opacityCurveRG, keyFile); @@ -3557,18 +3649,31 @@ int ProcParams::save(const Glib::ustring& fname, const Glib::ustring& fname2, bo saveToKeyfile(!pedited || pedited->wavelet.cbenab, "Wavelet", "CBenab", wavelet.cbenab, keyFile); saveToKeyfile(!pedited || pedited->wavelet.lipst, "Wavelet", "Lipst", wavelet.lipst, keyFile); saveToKeyfile(!pedited || pedited->wavelet.skinprotect, "Wavelet", "Skinprotect", wavelet.skinprotect, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.chrwav, "Wavelet", "chrwav", wavelet.chrwav, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.bluwav, "Wavelet", "bluwav", wavelet.bluwav, keyFile); saveToKeyfile(!pedited || pedited->wavelet.hueskin, "Wavelet", "Hueskin", wavelet.hueskin.toVector(), keyFile); saveToKeyfile(!pedited || pedited->wavelet.edgrad, "Wavelet", "Edgrad", wavelet.edgrad, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.edgeffect, "Wavelet", "Edgeffect", wavelet.edgeffect, keyFile); saveToKeyfile(!pedited || pedited->wavelet.edgval, "Wavelet", "Edgval", wavelet.edgval, keyFile); saveToKeyfile(!pedited || pedited->wavelet.edgthresh, "Wavelet", "ThrEdg", wavelet.edgthresh, keyFile); saveToKeyfile(!pedited || pedited->wavelet.avoid, "Wavelet", "AvoidColorShift", wavelet.avoid, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.showmask, "Wavelet", "Showmask", wavelet.showmask, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.oldsh, "Wavelet", "Oldsh", wavelet.oldsh, keyFile); saveToKeyfile(!pedited || pedited->wavelet.tmr, "Wavelet", "TMr", wavelet.tmr, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.sigma, "Wavelet", "Sigma", wavelet.sigma, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.offset, "Wavelet", "Offset", wavelet.offset, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.lowthr, "Wavelet", "Lowthr", wavelet.lowthr, keyFile); saveToKeyfile(!pedited || pedited->wavelet.rescon, "Wavelet", "ResidualcontShadow", wavelet.rescon, keyFile); saveToKeyfile(!pedited || pedited->wavelet.resconH, "Wavelet", "ResidualcontHighlight", wavelet.resconH, keyFile); saveToKeyfile(!pedited || pedited->wavelet.thr, "Wavelet", "ThresholdResidShadow", wavelet.thr, keyFile); saveToKeyfile(!pedited || pedited->wavelet.thrH, "Wavelet", "ThresholdResidHighLight", wavelet.thrH, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.radius, "Wavelet", "Residualradius", wavelet.radius, keyFile); saveToKeyfile(!pedited || pedited->wavelet.reschro, "Wavelet", "Residualchroma", wavelet.reschro, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.resblur, "Wavelet", "Residualblur", wavelet.resblur, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.resblurc, "Wavelet", "Residualblurc", wavelet.resblurc, keyFile); saveToKeyfile(!pedited || pedited->wavelet.tmrs, "Wavelet", "ResidualTM", wavelet.tmrs, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.edgs, "Wavelet", "ResidualEDGS", wavelet.edgs, keyFile); + saveToKeyfile(!pedited || pedited->wavelet.scale, "Wavelet", "ResidualSCALE", wavelet.scale, keyFile); saveToKeyfile(!pedited || pedited->wavelet.gamma, "Wavelet", "Residualgamma", wavelet.gamma, keyFile); saveToKeyfile(!pedited || pedited->wavelet.sky, "Wavelet", "HueRangeResidual", wavelet.sky, keyFile); saveToKeyfile(!pedited || pedited->wavelet.hueskin2, "Wavelet", "HueRange", wavelet.hueskin2.toVector(), keyFile); @@ -3730,6 +3835,9 @@ int ProcParams::save(const Glib::ustring& fname, const Glib::ustring& fname2, bo saveToKeyfile(!pedited || pedited->filmNegative.redRatio, "Film Negative", "RedRatio", filmNegative.redRatio, keyFile); saveToKeyfile(!pedited || pedited->filmNegative.greenExp, "Film Negative", "GreenExponent", filmNegative.greenExp, keyFile); saveToKeyfile(!pedited || pedited->filmNegative.blueRatio, "Film Negative", "BlueRatio", filmNegative.blueRatio, keyFile); + saveToKeyfile(!pedited || pedited->filmNegative.baseValues, "Film Negative", "RedBase", filmNegative.redBase, keyFile); + saveToKeyfile(!pedited || pedited->filmNegative.baseValues, "Film Negative", "GreenBase", filmNegative.greenBase, keyFile); + saveToKeyfile(!pedited || pedited->filmNegative.baseValues, "Film Negative", "BlueBase", filmNegative.blueBase, keyFile); // EXIF change list if (!pedited || pedited->exif) { @@ -4163,10 +4271,12 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited) assignFromKeyfile(keyFile, "Vibrance", "PastSatTog", pedited, vibrance.pastsattog, pedited->vibrance.pastsattog); assignFromKeyfile(keyFile, "Vibrance", "SkinTonesCurve", pedited, vibrance.skintonescurve, pedited->vibrance.skintonescurve); } - if (keyFile.has_group("White Balance")) { assignFromKeyfile(keyFile, "White Balance", "Enabled", pedited, wb.enabled, pedited->wb.enabled); assignFromKeyfile(keyFile, "White Balance", "Setting", pedited, wb.method, pedited->wb.method); + if (wb.method == "Auto") { + wb.method = "autold"; + } assignFromKeyfile(keyFile, "White Balance", "Temperature", pedited, wb.temperature, pedited->wb.temperature); assignFromKeyfile(keyFile, "White Balance", "Green", pedited, wb.green, pedited->wb.green); assignFromKeyfile(keyFile, "White Balance", "Equal", pedited, wb.equal, pedited->wb.equal); @@ -4205,6 +4315,7 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited) assignFromKeyfile(keyFile, "Color appearance", "AdaptLum", pedited, colorappearance.adaplum, pedited->colorappearance.adaplum); assignFromKeyfile(keyFile, "Color appearance", "Badpixsl", pedited, colorappearance.badpixsl, pedited->colorappearance.badpixsl); assignFromKeyfile(keyFile, "Color appearance", "Model", pedited, colorappearance.wbmodel, pedited->colorappearance.wbmodel); + assignFromKeyfile(keyFile, "Color appearance", "Illum", pedited, colorappearance.illum, pedited->colorappearance.illum); assignFromKeyfile(keyFile, "Color appearance", "Algorithm", pedited, colorappearance.algo, pedited->colorappearance.algo); assignFromKeyfile(keyFile, "Color appearance", "J-Light", pedited, colorappearance.jlight, pedited->colorappearance.jlight); assignFromKeyfile(keyFile, "Color appearance", "Q-Bright", pedited, colorappearance.qbright, pedited->colorappearance.qbright); @@ -4222,12 +4333,14 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited) assignFromKeyfile(keyFile, "Color appearance", "SurrSource", pedited, colorappearance.surrsource, pedited->colorappearance.surrsource); assignFromKeyfile(keyFile, "Color appearance", "Gamut", pedited, colorappearance.gamut, pedited->colorappearance.gamut); assignFromKeyfile(keyFile, "Color appearance", "Tempout", pedited, colorappearance.tempout, pedited->colorappearance.tempout); + assignFromKeyfile(keyFile, "Color appearance", "Autotempout", pedited, colorappearance.autotempout, pedited->colorappearance.autotempout); assignFromKeyfile(keyFile, "Color appearance", "Greenout", pedited, colorappearance.greenout, pedited->colorappearance.greenout); assignFromKeyfile(keyFile, "Color appearance", "Tempsc", pedited, colorappearance.tempsc, pedited->colorappearance.tempsc); assignFromKeyfile(keyFile, "Color appearance", "Greensc", pedited, colorappearance.greensc, pedited->colorappearance.greensc); assignFromKeyfile(keyFile, "Color appearance", "Ybout", pedited, colorappearance.ybout, pedited->colorappearance.ybout); assignFromKeyfile(keyFile, "Color appearance", "Datacie", pedited, colorappearance.datacie, pedited->colorappearance.datacie); assignFromKeyfile(keyFile, "Color appearance", "Tonecie", pedited, colorappearance.tonecie, pedited->colorappearance.tonecie); + assignFromKeyfile(keyFile, "Color appearance", "Presetcat02", pedited, colorappearance.presetcat02, pedited->colorappearance.presetcat02); const std::map tc_mapping = { {"Lightness", ColorAppearanceParams::TcMode::LIGHT}, @@ -4329,7 +4442,7 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited) if (keyFile.has_key("Shadows & Highlights", "LocalContrast") && ppVersion < 329) { int lc = keyFile.get_integer("Shadows & Highlights", "LocalContrast"); - localContrast.amount = float(lc) / 30.; + localContrast.amount = float(lc) / 30.f; if (pedited) { pedited->localContrast.amount = true; @@ -4651,16 +4764,27 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited) assignFromKeyfile(keyFile, "Wavelet", "CBbluehigh", pedited, wavelet.bluehigh, pedited->wavelet.bluehigh); assignFromKeyfile(keyFile, "Wavelet", "CBbluemed", pedited, wavelet.bluemed, pedited->wavelet.bluemed); assignFromKeyfile(keyFile, "Wavelet", "CBbluelow", pedited, wavelet.bluelow, pedited->wavelet.bluelow); + assignFromKeyfile(keyFile, "Wavelet", "Ballum", pedited, wavelet.ballum, pedited->wavelet.ballum); + assignFromKeyfile(keyFile, "Wavelet", "Balchrom", pedited, wavelet.balchrom, pedited->wavelet.balchrom); + assignFromKeyfile(keyFile, "Wavelet", "Chromfine", pedited, wavelet.chromfi, pedited->wavelet.chromfi); + assignFromKeyfile(keyFile, "Wavelet", "Chromcoarse", pedited, wavelet.chromco, pedited->wavelet.chromco); + assignFromKeyfile(keyFile, "Wavelet", "MergeL", pedited, wavelet.mergeL, pedited->wavelet.mergeL); + assignFromKeyfile(keyFile, "Wavelet", "MergeC", pedited, wavelet.mergeC, pedited->wavelet.mergeC); + assignFromKeyfile(keyFile, "Wavelet", "Softrad", pedited, wavelet.softrad, pedited->wavelet.softrad); + assignFromKeyfile(keyFile, "Wavelet", "Softradend", pedited, wavelet.softradend, pedited->wavelet.softradend); assignFromKeyfile(keyFile, "Wavelet", "Lipst", pedited, wavelet.lipst, pedited->wavelet.lipst); assignFromKeyfile(keyFile, "Wavelet", "AvoidColorShift", pedited, wavelet.avoid, pedited->wavelet.avoid); + assignFromKeyfile(keyFile, "Wavelet", "Showmask", pedited, wavelet.showmask, pedited->wavelet.showmask); + assignFromKeyfile(keyFile, "Wavelet", "Oldsh", pedited, wavelet.oldsh, pedited->wavelet.oldsh); assignFromKeyfile(keyFile, "Wavelet", "TMr", pedited, wavelet.tmr, pedited->wavelet.tmr); if (ppVersion < 331) { // wavelet.Lmethod was a string before version 331 Glib::ustring temp; assignFromKeyfile(keyFile, "Wavelet", "LevMethod", pedited, temp, pedited->wavelet.Lmethod); - if (!temp.empty()) { + try { wavelet.Lmethod = std::stoi(temp); + } catch (...) { } } else { assignFromKeyfile(keyFile, "Wavelet", "LevMethod", pedited, wavelet.Lmethod, pedited->wavelet.Lmethod); @@ -4672,6 +4796,7 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited) assignFromKeyfile(keyFile, "Wavelet", "DaubMethod", pedited, wavelet.daubcoeffmethod, pedited->wavelet.daubcoeffmethod); assignFromKeyfile(keyFile, "Wavelet", "CHromaMethod", pedited, wavelet.CHmethod, pedited->wavelet.CHmethod); assignFromKeyfile(keyFile, "Wavelet", "Medgreinf", pedited, wavelet.Medgreinf, pedited->wavelet.Medgreinf); + assignFromKeyfile(keyFile, "Wavelet", "Ushamethod", pedited, wavelet.ushamethod, pedited->wavelet.ushamethod); assignFromKeyfile(keyFile, "Wavelet", "CHSLromaMethod", pedited, wavelet.CHSLmethod, pedited->wavelet.CHSLmethod); assignFromKeyfile(keyFile, "Wavelet", "EDMethod", pedited, wavelet.EDmethod, pedited->wavelet.EDmethod); assignFromKeyfile(keyFile, "Wavelet", "NPMethod", pedited, wavelet.NPmethod, pedited->wavelet.NPmethod); @@ -4679,10 +4804,17 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited) assignFromKeyfile(keyFile, "Wavelet", "TMMethod", pedited, wavelet.TMmethod, pedited->wavelet.TMmethod); assignFromKeyfile(keyFile, "Wavelet", "HSMethod", pedited, wavelet.HSmethod, pedited->wavelet.HSmethod); assignFromKeyfile(keyFile, "Wavelet", "DirMethod", pedited, wavelet.Dirmethod, pedited->wavelet.Dirmethod); + assignFromKeyfile(keyFile, "Wavelet", "Sigma", pedited, wavelet.sigma, pedited->wavelet.sigma); + assignFromKeyfile(keyFile, "Wavelet", "Offset", pedited, wavelet.offset, pedited->wavelet.offset); + assignFromKeyfile(keyFile, "Wavelet", "Lowthr", pedited, wavelet.lowthr, pedited->wavelet.lowthr); assignFromKeyfile(keyFile, "Wavelet", "ResidualcontShadow", pedited, wavelet.rescon, pedited->wavelet.rescon); assignFromKeyfile(keyFile, "Wavelet", "ResidualcontHighlight", pedited, wavelet.resconH, pedited->wavelet.resconH); assignFromKeyfile(keyFile, "Wavelet", "Residualchroma", pedited, wavelet.reschro, pedited->wavelet.reschro); + assignFromKeyfile(keyFile, "Wavelet", "Residualblur", pedited, wavelet.resblur, pedited->wavelet.resblur); + assignFromKeyfile(keyFile, "Wavelet", "Residualblurc", pedited, wavelet.resblurc, pedited->wavelet.resblurc); assignFromKeyfile(keyFile, "Wavelet", "ResidualTM", pedited, wavelet.tmrs, pedited->wavelet.tmrs); + assignFromKeyfile(keyFile, "Wavelet", "ResidualEDGS", pedited, wavelet.edgs, pedited->wavelet.edgs); + assignFromKeyfile(keyFile, "Wavelet", "ResidualSCALE", pedited, wavelet.scale, pedited->wavelet.scale); assignFromKeyfile(keyFile, "Wavelet", "Residualgamma", pedited, wavelet.gamma, pedited->wavelet.gamma); assignFromKeyfile(keyFile, "Wavelet", "ContExtra", pedited, wavelet.sup, pedited->wavelet.sup); assignFromKeyfile(keyFile, "Wavelet", "HueRangeResidual", pedited, wavelet.sky, pedited->wavelet.sky); @@ -4698,11 +4830,14 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited) assignFromKeyfile(keyFile, "Wavelet", "ChromaLink", pedited, wavelet.chro, pedited->wavelet.chro); assignFromKeyfile(keyFile, "Wavelet", "Contrast", pedited, wavelet.contrast, pedited->wavelet.contrast); assignFromKeyfile(keyFile, "Wavelet", "Edgrad", pedited, wavelet.edgrad, pedited->wavelet.edgrad); + assignFromKeyfile(keyFile, "Wavelet", "Edgeffect", pedited, wavelet.edgeffect, pedited->wavelet.edgeffect); assignFromKeyfile(keyFile, "Wavelet", "Edgval", pedited, wavelet.edgval, pedited->wavelet.edgval); assignFromKeyfile(keyFile, "Wavelet", "ThrEdg", pedited, wavelet.edgthresh, pedited->wavelet.edgthresh); assignFromKeyfile(keyFile, "Wavelet", "ThresholdResidShadow", pedited, wavelet.thr, pedited->wavelet.thr); assignFromKeyfile(keyFile, "Wavelet", "ThresholdResidHighLight", pedited, wavelet.thrH, pedited->wavelet.thrH); + assignFromKeyfile(keyFile, "Wavelet", "Residualradius", pedited, wavelet.radius, pedited->wavelet.radius); assignFromKeyfile(keyFile, "Wavelet", "ContrastCurve", pedited, wavelet.ccwcurve, pedited->wavelet.ccwcurve); + assignFromKeyfile(keyFile, "Wavelet", "blcurve", pedited, wavelet.blcurve, pedited->wavelet.blcurve); assignFromKeyfile(keyFile, "Wavelet", "OpacityCurveRG", pedited, wavelet.opacityCurveRG, pedited->wavelet.opacityCurveRG); assignFromKeyfile(keyFile, "Wavelet", "OpacityCurveBY", pedited, wavelet.opacityCurveBY, pedited->wavelet.opacityCurveBY); assignFromKeyfile(keyFile, "Wavelet", "OpacityCurveW", pedited, wavelet.opacityCurveW, pedited->wavelet.opacityCurveW); @@ -4844,6 +4979,8 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited) } assignFromKeyfile(keyFile, "Wavelet", "Skinprotect", pedited, wavelet.skinprotect, pedited->wavelet.skinprotect); + assignFromKeyfile(keyFile, "Wavelet", "chrwav", pedited, wavelet.chrwav, pedited->wavelet.chrwav); + assignFromKeyfile(keyFile, "Wavelet", "bluwav", pedited, wavelet.bluwav, pedited->wavelet.bluwav); assignFromKeyfile(keyFile, "Wavelet", "Expcontrast", pedited, wavelet.expcontrast, pedited->wavelet.expcontrast); assignFromKeyfile(keyFile, "Wavelet", "Expchroma", pedited, wavelet.expchroma, pedited->wavelet.expchroma); @@ -4874,10 +5011,12 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited) } assignFromKeyfile(keyFile, "Wavelet", "Expedge", pedited, wavelet.expedge, pedited->wavelet.expedge); + assignFromKeyfile(keyFile, "Wavelet", "expbl", pedited, wavelet.expbl, pedited->wavelet.expbl); assignFromKeyfile(keyFile, "Wavelet", "Expresid", pedited, wavelet.expresid, pedited->wavelet.expresid); assignFromKeyfile(keyFile, "Wavelet", "Expfinal", pedited, wavelet.expfinal, pedited->wavelet.expfinal); assignFromKeyfile(keyFile, "Wavelet", "Exptoning", pedited, wavelet.exptoning, pedited->wavelet.exptoning); assignFromKeyfile(keyFile, "Wavelet", "Expnoise", pedited, wavelet.expnoise, pedited->wavelet.expnoise); + assignFromKeyfile(keyFile, "Wavelet", "Expclari", pedited, wavelet.expclari, pedited->wavelet.expclari); } if (keyFile.has_group("Directional Pyramid Equalizer")) { @@ -5309,6 +5448,24 @@ int ProcParams::load(const Glib::ustring& fname, ParamsEdited* pedited) assignFromKeyfile(keyFile, "Film Negative", "RedRatio", pedited, filmNegative.redRatio, pedited->filmNegative.redRatio); assignFromKeyfile(keyFile, "Film Negative", "GreenExponent", pedited, filmNegative.greenExp, pedited->filmNegative.greenExp); assignFromKeyfile(keyFile, "Film Negative", "BlueRatio", pedited, filmNegative.blueRatio, pedited->filmNegative.blueRatio); + if (ppVersion >= 347) { + bool r, g, b; + assignFromKeyfile(keyFile, "Film Negative", "RedBase", pedited, filmNegative.redBase, r); + assignFromKeyfile(keyFile, "Film Negative", "GreenBase", pedited, filmNegative.greenBase, g); + assignFromKeyfile(keyFile, "Film Negative", "BlueBase", pedited, filmNegative.blueBase, b); + if (pedited) { + pedited->filmNegative.baseValues = r || g || b; + } + } else { + // Backwards compatibility with film negative in RT 5.7: use special film base value -1, + // to signal that the old channel scaling method should be used. + filmNegative.redBase = -1.f; + filmNegative.greenBase = -1.f; + filmNegative.blueBase = -1.f; + if (pedited) { + pedited->filmNegative.baseValues = true; + } + } } if (keyFile.has_group("MetaData")) { diff --git a/rtengine/procparams.h b/rtengine/procparams.h index 1472a5059..8a95032e8 100644 --- a/rtengine/procparams.h +++ b/rtengine/procparams.h @@ -40,6 +40,7 @@ class OpacityCurve; class RetinexgaintransmissionCurve; class RetinextransmissionCurve; class WavCurve; +class Wavblcurve; class WavOpacityCurveBY; class WavOpacityCurveRG; class WavOpacityCurveW; @@ -661,6 +662,7 @@ struct ColorAppearanceParams { double adaplum; int badpixsl; Glib::ustring wbmodel; + Glib::ustring illum; Glib::ustring algo; double contrast; double qcontrast; @@ -676,10 +678,12 @@ struct ColorAppearanceParams { bool datacie; bool tonecie; int tempout; + bool autotempout; int ybout; double greenout; int tempsc; double greensc; + bool presetcat02; ColorAppearanceParams(); @@ -1195,6 +1199,7 @@ private: struct WaveletParams { std::vector ccwcurve; + std::vector blcurve; std::vector opacityCurveRG; std::vector opacityCurveBY; std::vector opacityCurveW; @@ -1213,9 +1218,19 @@ struct WaveletParams { int bluemed; int greenhigh; int bluehigh; + double ballum; + double balchrom; + double chromfi; + double chromco; + double mergeL; + double mergeC; + double softrad; + double softradend; bool lipst; bool avoid; + bool showmask; + bool oldsh; bool tmr; int strength; int balance; @@ -1225,10 +1240,12 @@ struct WaveletParams { int c[9]; int ch[9]; bool expedge; + bool expbl; bool expresid; bool expfinal; bool exptoning; bool expnoise; + bool expclari; int Lmethod; Glib::ustring CLmethod; @@ -1237,6 +1254,7 @@ struct WaveletParams { Glib::ustring daubcoeffmethod; Glib::ustring CHmethod; Glib::ustring Medgreinf; + Glib::ustring ushamethod; Glib::ustring CHSLmethod; Glib::ustring EDmethod; Glib::ustring NPmethod; @@ -1244,10 +1262,17 @@ struct WaveletParams { Glib::ustring TMmethod; Glib::ustring Dirmethod; Glib::ustring HSmethod; + double sigma; + double offset; + double lowthr; int rescon; int resconH; int reschro; + int resblur; + int resblurc; double tmrs; + double edgs; + double scale; double gamma; int sup; double sky; @@ -1263,11 +1288,15 @@ struct WaveletParams { int edgeampli; int contrast; int edgrad; + double edgeffect; int edgval; int edgthresh; int thr; int thrH; + int radius; double skinprotect; + double chrwav; + double bluwav; Threshold hueskin; Threshold hueskin2; Threshold hllev; @@ -1287,6 +1316,7 @@ struct WaveletParams { void getCurves( WavCurve& cCurve, + Wavblcurve& tCurve, WavOpacityCurveRG& opacityCurveLUTRG, WavOpacityCurveBY& opacityCurveLUTBY, @@ -1542,6 +1572,10 @@ struct FilmNegativeParams { double greenExp; double blueRatio; + double redBase; + double greenBase; + double blueBase; + FilmNegativeParams(); bool operator ==(const FilmNegativeParams& other) const; diff --git a/rtengine/rawimage.cc b/rtengine/rawimage.cc index 4421e4af4..c2df70468 100644 --- a/rtengine/rawimage.cc +++ b/rtengine/rawimage.cc @@ -171,7 +171,7 @@ void RawImage::get_colorsCoeff( float *pre_mul_, float *scale_mul_, float *cblac } for (int c = 0; c < 4; c++) { - dsumthr[c] += sum[c]; + dsumthr[c] += static_cast(sum[c]); } skip_block2: @@ -195,7 +195,7 @@ skip_block2: } for(int c = 0; c < 4; c++) { - dsum[c] -= cblack_[c] * dsum[c + 4]; + dsum[c] -= static_cast(cblack_[c]) * dsum[c + 4]; } } else if(isXtrans()) { @@ -241,7 +241,7 @@ skip_block2: } for (int c = 0; c < 8; c++) { - dsumthr[c] += sum[c]; + dsumthr[c] += static_cast(sum[c]); } skip_block3: @@ -365,18 +365,14 @@ skip_block: } for (dmin = DBL_MAX, dmax = c = 0; c < 4; c++) { - if (dmin > pre_mul_[c]) { - dmin = pre_mul_[c]; - } - - if (dmax < pre_mul_[c]) { - dmax = pre_mul_[c]; - } + dmin = rtengine::min(dmin, pre_mul_[c]); + dmax = rtengine::max(dmax, pre_mul_[c]); } for (c = 0; c < 4; c++) { int sat = this->get_white(c) - cblack_[c]; - scale_mul_[c] = (pre_mul_[c] /= dmax) * 65535.0 / sat; + pre_mul_[c] /= static_cast(dmax); + scale_mul_[c] = pre_mul_[c] * 65535.f / sat; } if (settings->verbose) { @@ -387,25 +383,30 @@ skip_block: asn[c] = 0; } - if (asn[c] > dmax) { + if (asn[c] > static_cast(dmax)) { dmax = asn[c]; } } for (c = 0; c < 4; c++) { - asn[c] /= dmax; + asn[c] /= static_cast(dmax); } printf("cam_mul:[%f %f %f %f], AsShotNeutral:[%f %f %f %f]\n", - cam_mul[0], cam_mul[1], cam_mul[2], cam_mul[3], asn[0], asn[1], asn[2], asn[3]); + static_cast(cam_mul[0]), static_cast(cam_mul[1]), + static_cast(cam_mul[2]), static_cast(cam_mul[3]), + static_cast(asn[0]), static_cast(asn[1]), static_cast(asn[2]), static_cast(asn[3])); printf("pre_mul:[%f %f %f %f], scale_mul:[%f %f %f %f], cblack:[%f %f %f %f]\n", - pre_mul_[0], pre_mul_[1], pre_mul_[2], pre_mul_[3], - scale_mul_[0], scale_mul_[1], scale_mul_[2], scale_mul_[3], - cblack_[0], cblack_[1], cblack_[2], cblack_[3]); + static_cast(pre_mul_[0]), static_cast(pre_mul_[1]), + static_cast(pre_mul_[2]), static_cast(pre_mul_[3]), + static_cast(scale_mul_[0]), static_cast(scale_mul_[1]), + static_cast(scale_mul_[2]), static_cast(scale_mul_[3]), + static_cast(cblack_[0]), static_cast(cblack_[1]), + static_cast(cblack_[2]), static_cast(cblack_[3])); printf("rgb_cam:[ [ %f %f %f], [%f %f %f], [%f %f %f] ]%s\n", - rgb_cam[0][0], rgb_cam[1][0], rgb_cam[2][0], - rgb_cam[0][1], rgb_cam[1][1], rgb_cam[2][1], - rgb_cam[0][2], rgb_cam[1][2], rgb_cam[2][2], + static_cast(rgb_cam[0][0]), static_cast(rgb_cam[1][0]), static_cast(rgb_cam[2][0]), + static_cast(rgb_cam[0][1]), static_cast(rgb_cam[1][1]), static_cast(rgb_cam[2][1]), + static_cast(rgb_cam[0][2]), static_cast(rgb_cam[1][2]), static_cast(rgb_cam[2][2]), (!this->isBayer()) ? " (not bayer)" : ""); } @@ -523,7 +524,7 @@ int RawImage::loadRaw (bool loadData, unsigned int imageNum, bool closeFile, Pro } CameraConstantsStore* ccs = CameraConstantsStore::getInstance(); - CameraConst *cc = ccs->get(make, model); + const CameraConst *cc = ccs->get(make, model); if (raw_image) { if (cc && cc->has_rawCrop()) { @@ -849,42 +850,18 @@ DCraw::dcraw_coeff_overrides(const char make[], const char model[], const int is short trans[12]; // set first value to 0 for no change } table[] = { - { - "Canon EOS 5D Mark III", -1, 0x3a98, /* RT */ - { 6722, -635, -963, -4287, 12460, 2028, -908, 2162, 5668 } - }, { "Canon EOS 5D", -1, 0xe6c, /* RT */ { 6319, -793, -614, -5809, 13342, 2738, -1132, 1559, 7971 } }, - { - "Canon EOS 6D", -1, 0x3c82, - { 7034, -804, -1014, -4420, 12564, 2058, -851, 1994, 5758 } - }, - { - "Canon EOS 7D", -1, 0x3510, /* RT - Colin Walker */ - { 5962, -171, -732, -4189, 12307, 2099, -911, 1981, 6304 } - }, { "Canon EOS 20D", -1, 0xfff, /* RT */ { 7590, -1646, -673, -4697, 12411, 2568, -627, 1118, 7295 } }, - { - "Canon EOS 40D", -1, 0x3f60, /* RT */ - { 6070, -531, -883, -5763, 13647, 2315, -1533, 2582, 6801 } - }, - { - "Canon EOS 60D", -1, 0x2ff7, /* RT - Colin Walker */ - { 5678, -179, -718, -4389, 12381, 2243, -869, 1819, 6380 } - }, { "Canon EOS 450D", -1, 0x390d, /* RT */ { 6246, -1272, -523, -5075, 12357, 3075, -1035, 1825, 7333 } }, - { - "Canon EOS 550D", -1, 0x3dd7, /* RT - Lebedev*/ - { 6519, -772, -703, -4994, 12737, 2519, -1387, 2492, 6175 } - }, { "Canon EOS-1D Mark III", 0, 0x3bb0, /* RT */ { 7406, -1592, -646, -4856, 12457, 2698, -432, 726, 7921 } @@ -893,18 +870,10 @@ DCraw::dcraw_coeff_overrides(const char make[], const char model[], const int is "Canon PowerShot G10", -1, -1, /* RT */ { 12535, -5030, -796, -2711, 10134, 3006, -413, 1605, 5264 } }, - { - "Canon PowerShot G12", -1, -1, /* RT */ - { 12222, -4097, -1380, -2876, 11016, 2130, -888, 1630, 4434 } - }, - - { "Fujifilm X100", -1, -1, /* RT - Colin Walker */ { 10841, -3288, -807, -4652, 12552, 2344, -642, 1355, 7206 } }, - - { "Nikon D200", -1, 0xfbc, /* RT */ { 8498, -2633, -295, -5423, 12869, 2860, -777, 1077, 8124 } @@ -917,32 +886,14 @@ DCraw::dcraw_coeff_overrides(const char make[], const char model[], const int is "Nikon D3100", -1, -1, /* RT */ { 7729, -2212, -481, -5709, 13148, 2858, -1295, 1908, 8936 } }, - { - "Nikon D3S", -1, -1, /* RT */ - { 8792, -2663, -344, -5221, 12764, 2752, -1491, 2165, 8121 } - }, { "Nikon D5200", -1, -1, // color matrix copied from D5200 DNG D65 matrix { 8322, -3112, -1047, -6367, 14342, 2179, -988, 1638, 6394 } }, - { - "Nikon D7000", -1, -1, /* RT - Tanveer(tsk1979) */ - { 7530, -1942, -255, -4318, 11390, 3362, -926, 1694, 7649 } - }, { "Nikon D7100", -1, -1, // color matrix and WP copied from D7100 DNG D65 matrix { 8322, -3112, -1047, -6367, 14342, 2179, -988, 1638, 6394 } }, - { - "Nikon D700", -1, -1, /* RT */ - { 8364, -2503, -352, -6307, 14026, 2492, -1134, 1512, 8156 } - }, - { - "Nikon COOLPIX A", -1, 0x3e00, // color matrix and WP copied from "COOLPIX A" DNG D65 matrix - { 8198, -2239, -724, -4871, 12389, 2798, -1043, 205, 7181 } - }, - - { "Olympus E-30", -1, 0xfbc, /* RT - Colin Walker */ { 8510, -2355, -693, -4819, 12520, 2578, -1029, 2067, 7752 } @@ -983,69 +934,14 @@ DCraw::dcraw_coeff_overrides(const char make[], const char model[], const int is "Olympus XZ-1", -1, -1, /* RT - Colin Walker */ { 8665, -2247, -762, -2424, 10372, 2382, -1011, 2286, 5189 } }, - - - /* since Dcraw_v9.21 Panasonic BlackLevel is read from exif (tags 0x001c BlackLevelRed, 0x001d BlackLevelGreen, 0x001e BlackLevelBlue - and we define here the needed offset of around 15. The total BL is BL + BLoffset (cblack + black) */ - - { - "Panasonic DMC-FZ150", 15, 0xfd2, /* RT */ - { 10435, -3208, -72, -2293, 10506, 2067, -486, 1725, 4682 } - }, - { - "Panasonic DMC-G10", 15, 0xf50, /* RT - Colin Walker - variable WL 3920 - 4080 */ - { 8310, -1811, -960, -4941, 12990, 2151, -1378, 2468, 6860 } - }, - { - "Panasonic DMC-G1", 15, 0xf50, /* RT - Colin Walker - variable WL 3920 - 4080 */ - { 7477, -1615, -651, -5016, 12769, 2506, -1380, 2475, 7240 } - }, - { - "Panasonic DMC-G2", 15, 0xf50, /* RT - Colin Walker - variable WL 3920 - 4080 */ - { 8310, -1811, -960, -4941, 12990, 2151, -1378, 2468, 6860 } - }, - { - "Panasonic DMC-G3", 15, 0xfdc, /* RT - Colin Walker - WL 4060 */ - { 6051, -1406, -671, -4015, 11505, 2868, -1654, 2667, 6219 } - }, - { - "Panasonic DMC-G5", 15, 0xfdc, /* RT - WL 4060 */ - { 7122, -2092, -419, -4643, 11769, 3283, -1363, 2413, 5944 } - }, - { - "Panasonic DMC-GF1", 15, 0xf50, /* RT - Colin Walker - Variable WL 3920 - 4080 */ - { 7863, -2080, -668, -4623, 12331, 2578, -1020, 2066, 7266 } - }, - { - "Panasonic DMC-GF2", 15, 0xfd2, /* RT - Colin Walker - WL 4050 */ - { 7694, -1791, -745, -4917, 12818, 2332, -1221, 2322, 7197 } - }, - { - "Panasonic DMC-GF3", 15, 0xfd2, /* RT - Colin Walker - WL 4050 */ - { 8074, -1846, -861, -5026, 12999, 2239, -1320, 2375, 7422 } - }, - { - "Panasonic DMC-GH1", 15, 0xf5a, /* RT - Colin Walker - variable WL 3930 - 4080 */ - { 6360, -1557, -375, -4201, 11504, 3086, -1378, 2518, 5843 } - }, - { - "Panasonic DMC-GH2", 15, 0xf5a, /* RT - Colin Walker - variable WL 3930 - 4080 */ -// { 6855,-1765,-456,-4223,11600,2996,-1450,2602,5761 } }, disabled due to problems with underwater WB - { 7780, -2410, -806, -3913, 11724, 2484, -1018, 2390, 5298 } - }, // dcraw original - { "Pentax K200D", -1, -1, /* RT */ { 10962, -4428, -542, -5486, 13023, 2748, -569, 842, 8390 } }, - - { "Leica Camera AG M9 Digital Camera", -1, -1, /* RT */ { 7181, -1706, -55, -3557, 11409, 2450, -621, 2072, 7533 } }, - - { "SONY NEX-3", 128 << dcraw_arw2_scaling_bugfix_shift, -1, /* RT - Colin Walker */ { 5145, -741, -123, -4915, 12310, 2945, -794, 1489, 6906 } @@ -1103,7 +999,7 @@ DCraw::dcraw_coeff_overrides(const char make[], const char model[], const int is { // test if we have any information in the camera constants store, if so we take that. rtengine::CameraConstantsStore* ccs = rtengine::CameraConstantsStore::getInstance(); - rtengine::CameraConst *cc = ccs->get(make, model); + const rtengine::CameraConst *cc = ccs->get(make, model); if (cc) { if (RT_blacklevel_from_constant == ThreeValBool::T) { diff --git a/rtengine/rawimagesource.cc b/rtengine/rawimagesource.cc index 18fc18f58..75088a07c 100644 --- a/rtengine/rawimagesource.cc +++ b/rtengine/rawimagesource.cc @@ -17,6 +17,7 @@ * along with RawTherapee. If not, see . */ #include +#include #include #include "camconst.h" @@ -25,6 +26,7 @@ #include "dcp.h" #include "dfmanager.h" #include "ffmanager.h" +#include "iccmatrices.h" #include "iccstore.h" #include "imagefloat.h" #include "improcfun.h" @@ -41,7 +43,7 @@ #include "rtlensfun.h" #include "../rtgui/options.h" -//#define BENCHMARK +#define BENCHMARK #include "StopWatch.h" #ifdef _OPENMP @@ -49,10 +51,6 @@ #endif #include "opthelper.h" -#define clipretinex( val, minv, maxv ) (( val = (val < minv ? minv : val ) ) > maxv ? maxv : val ) - -#undef CLIPD -#define CLIPD(a) ((a)>0.0f?((a)<1.0f?(a):1.0f):0.0f) namespace { @@ -101,7 +99,7 @@ void transLineFuji (const float* const red, const float* const green, const floa { // Fuji SuperCCD rotation + coarse rotation - int start = ABS(fw - i); + int start = std::abs(fw - i); int w = fw * 2 + 1; int h = (imheight - fw) * 2 + 1; int end = min(h + fw - i, w - fw + i); @@ -197,8 +195,8 @@ void transLineD1x (const float* const red, const float* const green, const float image->b(row, col) = (blue[j] + image->b(row + 1, col)) / 2; } - if(i == 2 && oddHeight) { - int row = 2 * imheight; + if (i == 2 && oddHeight) { + row = 2 * imheight; for (int j = 0; j < imwidth; j++) { int col = imwidth - 1 - j; @@ -234,7 +232,7 @@ void transLineD1x (const float* const red, const float* const green, const float image->g(row, col) = MAX(0.f, -0.0625f * (green[j] + image->g(row + 3, col)) + 0.5625f * (image->g(row - 1, col) + image->g(row + 1, col))); image->b(row, col) = MAX(0.f, -0.0625f * (blue[j] + image->b(row + 3, col)) + 0.5625f * (image->b(row - 1, col) + image->b(row + 1, col))); - if(clip) { + if (clip) { image->r(row, col) = MIN(image->r(row, col), rtengine::MAXVALF); image->g(row, col) = MIN(image->g(row, col), rtengine::MAXVALF); image->b(row, col) = MIN(image->b(row, col), rtengine::MAXVALF); @@ -245,7 +243,7 @@ void transLineD1x (const float* const red, const float* const green, const float break; case TR_R90: // rotate right - if( i == 0) { + if (i == 0) { for (int j = 0; j < imwidth; j++) { image->r(j, 2 * imheight - 1) = red[j]; image->g(j, 2 * imheight - 1) = green[j]; @@ -267,7 +265,7 @@ void transLineD1x (const float* const red, const float* const green, const float image->g(j, col) = (green[j] + image->g(j, col + 1)) / 2; image->b(j, col) = (blue[j] + image->b(j, col + 1)) / 2; - if(oddHeight && i == 2) { + if (oddHeight && i == 2) { image->r(j, 2 * imheight) = (red[j] + image->r(j, 2 * imheight - 2)) / 2; image->g(j, 2 * imheight) = (green[j] + image->g(j, 2 * imheight - 2)) / 2; image->b(j, 2 * imheight) = (blue[j] + image->b(j, 2 * imheight - 2)) / 2; @@ -297,7 +295,7 @@ void transLineD1x (const float* const red, const float* const green, const float image->g(j, col) = MAX(0.f, -0.0625f * (green[j] + image->g(j, col + 3)) + 0.5625f * (image->g(j, col - 1) + image->g(j, col + 1))); image->b(j, col) = MAX(0.f, -0.0625f * (blue[j] + image->b(j, col + 3)) + 0.5625f * (image->b(j, col - 1) + image->b(j, col + 1))); - if(clip) { + if (clip) { image->r(j, col) = MIN(image->r(j, col), rtengine::MAXVALF); image->g(j, col) = MIN(image->g(j, col), rtengine::MAXVALF); image->b(j, col) = MIN(image->b(j, col), rtengine::MAXVALF); @@ -329,7 +327,7 @@ void transLineD1x (const float* const red, const float* const green, const float image->g(row, 2 * i - 3) = MAX(0.f, -0.0625f * (green[j] + image->g(row, 2 * i - 6)) + 0.5625f * (image->g(row, 2 * i - 2) + image->g(row, 2 * i - 4))); image->b(row, 2 * i - 3) = MAX(0.f, -0.0625f * (blue[j] + image->b(row, 2 * i - 6)) + 0.5625f * (image->b(row, 2 * i - 2) + image->b(row, 2 * i - 4))); - if(clip) { + if (clip) { image->r(row, 2 * i - 3) = MIN(image->r(row, 2 * i - 3), rtengine::MAXVALF); image->g(row, 2 * i - 3) = MIN(image->g(row, 2 * i - 3), rtengine::MAXVALF); image->b(row, 2 * i - 3) = MIN(image->b(row, 2 * i - 3), rtengine::MAXVALF); @@ -347,7 +345,7 @@ void transLineD1x (const float* const red, const float* const green, const float image->g(row, 2 * i - 1) = MAX(0.f, -0.0625f * (green[j] + image->g(row, 2 * i - 4)) + 0.5625f * (image->g(row, 2 * i) + image->g(row, 2 * i - 2))); image->b(row, 2 * i - 1) = MAX(0.f, -0.0625f * (blue[j] + image->b(row, 2 * i - 4)) + 0.5625f * (image->b(row, 2 * i) + image->b(row, 2 * i - 2))); - if(clip) { + if (clip) { image->r(j, 2 * i - 1) = MIN(image->r(j, 2 * i - 1), rtengine::MAXVALF); image->g(j, 2 * i - 1) = MIN(image->g(j, 2 * i - 1), rtengine::MAXVALF); image->b(j, 2 * i - 1) = MIN(image->b(j, 2 * i - 1), rtengine::MAXVALF); @@ -385,7 +383,7 @@ void transLineD1x (const float* const red, const float* const green, const float image->g(2 * i - 3, j) = MAX(0.f, -0.0625f * (green[j] + image->g(2 * i - 6, j)) + 0.5625f * (image->g(2 * i - 2, j) + image->g(2 * i - 4, j))); image->b(2 * i - 3, j) = MAX(0.f, -0.0625f * (blue[j] + image->b(2 * i - 6, j)) + 0.5625f * (image->b(2 * i - 2, j) + image->b(2 * i - 4, j))); - if(clip) { + if (clip) { image->r(2 * i - 3, j) = MIN(image->r(2 * i - 3, j), rtengine::MAXVALF); image->g(2 * i - 3, j) = MIN(image->g(2 * i - 3, j), rtengine::MAXVALF); image->b(2 * i - 3, j) = MIN(image->b(2 * i - 3, j), rtengine::MAXVALF); @@ -399,7 +397,7 @@ void transLineD1x (const float* const red, const float* const green, const float image->g(2 * i - 1, j) = MAX(0.f, -0.0625f * (green[j] + image->g(2 * i - 4, j)) + 0.5625f * (image->g(2 * i, j) + image->g(2 * i - 2, j))); image->b(2 * i - 1, j) = MAX(0.f, -0.0625f * (blue[j] + image->b(2 * i - 4, j)) + 0.5625f * (image->b(2 * i, j) + image->b(2 * i - 2, j))); - if(clip) { + if (clip) { image->r(2 * i - 1, j) = MIN(image->r(2 * i - 1, j), rtengine::MAXVALF); image->g(2 * i - 1, j) = MIN(image->g(2 * i - 1, j), rtengine::MAXVALF); image->b(2 * i - 1, j) = MIN(image->b(2 * i - 1, j), rtengine::MAXVALF); @@ -425,12 +423,6 @@ void transLineD1x (const float* const red, const float* const green, const float namespace rtengine { -#undef ABS -#undef DIST - -#define ABS(a) ((a)<0?-(a):(a)) -#define DIST(a,b) (ABS(a-b)) - RawImageSource::RawImageSource () : ImageSource() , W(0), H(0) @@ -456,21 +448,24 @@ RawImageSource::RawImageSource () , initialGain(0.0) , camInitialGain(0.0) , defGain(0.0) + , camProfile(nullptr) , ri(nullptr) , rawData(0, 0) , green(0, 0) + , greenloc(0, 0) , red(0, 0) + , redloc(0, 0) , blue(0, 0) + , blueloc(0, 0) , greenCache(nullptr) , redCache(nullptr) , blueCache(nullptr) , rawDirty(true) , histMatchingParams(new procparams::ColorManagementParams) { - camProfile = nullptr; embProfile = nullptr; rgbSourceModified = false; - for(int i = 0; i < 4; ++i) { + for (int i = 0; i < 4; ++i) { psRedBrightness[i] = psGreenBrightness[i] = psBlueBrightness[i] = 1.f; } } @@ -485,17 +480,14 @@ RawImageSource::~RawImageSource () delete greenCache; delete blueCache; - for(size_t i = 0; i < numFrames; ++i) { + for (size_t i = 0; i < numFrames; ++i) { delete riFrames[i]; } - for(size_t i = 0; i + 1 < numFrames; ++i) { + for (size_t i = 0; i + 1 < numFrames; ++i) { delete rawDataBuffer[i]; } - flushRGB(); - flushRawData(); - if (camProfile) { cmsCloseProfile (camProfile); } @@ -558,11 +550,11 @@ void RawImageSource::transformRect (const PreviewProps &pp, int tran, int &ssx1, sh = w; } - if( pp_width > sw - 2 * border) { + if (pp_width > sw - 2 * border) { pp_width = sw - 2 * border; } - if( pp_height > sh - 2 * border) { + if (pp_height > sh - 2 * border) { pp_height = sh - 2 * border; } @@ -602,16 +594,16 @@ void RawImageSource::transformRect (const PreviewProps &pp, int tran, int &ssx1, // atszamoljuk a koordinatakat fuji-ra: // recalculate the coordinates fuji-ra: ssx1 = (sx1 + sy1) / 2; - ssy1 = (sy1 - sx2 ) / 2 + ri->get_FujiWidth(); + ssy1 = (sy1 - sx2) / 2 + ri->get_FujiWidth(); int ssx2 = (sx2 + sy2) / 2 + 1; int ssy2 = (sy2 - sx1) / 2 + ri->get_FujiWidth(); - fw = (sx2 - sx1) / 2 / pp.getSkip(); - width = (ssx2 - ssx1) / pp.getSkip() + ((ssx2 - ssx1) % pp.getSkip() > 0); + fw = (sx2 - sx1) / 2 / pp.getSkip(); + width = (ssx2 - ssx1) / pp.getSkip() + ((ssx2 - ssx1) % pp.getSkip() > 0); height = (ssy2 - ssy1) / pp.getSkip() + ((ssy2 - ssy1) % pp.getSkip() > 0); } else { ssx1 = sx1; ssy1 = sy1; - width = (sx2 + 1 - sx1) / pp.getSkip() + ((sx2 + 1 - sx1) % pp.getSkip() > 0); + width = (sx2 + 1 - sx1) / pp.getSkip() + ((sx2 + 1 - sx1) % pp.getSkip() > 0); height = (sy2 + 1 - sy1) / pp.getSkip() + ((sy2 + 1 - sy1) % pp.getSkip() > 0); } } @@ -620,7 +612,7 @@ float calculate_scale_mul(float scale_mul[4], const float pre_mul_[4], const flo { if (isMono || colors == 1) { for (int c = 0; c < 4; c++) { - scale_mul[c] = 65535.0 / (c_white[c] - c_black[c]); + scale_mul[c] = 65535.f / (c_white[c] - c_black[c]); } } else { float pre_mul[4]; @@ -636,7 +628,7 @@ float calculate_scale_mul(float scale_mul[4], const float pre_mul_[4], const flo float maxpremul = max(pre_mul[0], pre_mul[1], pre_mul[2], pre_mul[3]); for (int c = 0; c < 4; c++) { - scale_mul[c] = (pre_mul[c] / maxpremul) * 65535.0 / (c_white[c] - c_black[c]); + scale_mul[c] = (pre_mul[c] / maxpremul) * 65535.f / (c_white[c] - c_black[c]); } } @@ -644,7 +636,7 @@ float calculate_scale_mul(float scale_mul[4], const float pre_mul_[4], const flo return gain; } -void RawImageSource::getImage (const ColorTemp &ctemp, int tran, Imagefloat* image, const PreviewProps &pp, const ToneCurveParams &hrp, const RAWParams &raw ) +void RawImageSource::getImage (const ColorTemp &ctemp, int tran, Imagefloat* image, const PreviewProps &pp, const ToneCurveParams &hrp, const RAWParams &raw) { MyMutex::MyLock lock(getImageMutex); @@ -675,7 +667,7 @@ void RawImageSource::getImage (const ColorTemp &ctemp, int tran, Imagefloat* ima || (ri->getSensorType() == ST_BAYER && raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::MONO)); for (int i = 0; i < 4; ++i) { - c_white[i] = (ri->get_white(i) - cblacksom[i]) / raw.expos + cblacksom[i]; + c_white[i] = (ri->get_white(i) - cblacksom[i]) / static_cast(raw.expos) + cblacksom[i]; } float gain = calculate_scale_mul(new_scale_mul, new_pre_mul, c_white, cblacksom, isMono, ri->get_colors()); @@ -684,21 +676,21 @@ void RawImageSource::getImage (const ColorTemp &ctemp, int tran, Imagefloat* ima bm = new_scale_mul[2] / scale_mul[2] * gain; //fprintf(stderr, "camera gain: %f, current wb gain: %f, diff in stops %f\n", camInitialGain, gain, log2(camInitialGain) - log2(gain)); } else { - // old scaling: used a fixed reference gain based on camera (as-shot) white balance - - // how much we need to scale each channel to get our new white balance - rm = refwb_red / rm; - gm = refwb_green / gm; - bm = refwb_blue / bm; - // normalize so larger multiplier becomes 1.0 - float minval = min(rm, gm, bm); - rm /= minval; - gm /= minval; - bm /= minval; - // multiply with reference gain, ie as-shot WB - rm *= camInitialGain; - gm *= camInitialGain; - bm *= camInitialGain; +// // old scaling: used a fixed reference gain based on camera (as-shot) white balance +// +// // how much we need to scale each channel to get our new white balance +// rm = refwb_red / rm; +// gm = refwb_green / gm; +// bm = refwb_blue / bm; +// // normalize so larger multiplier becomes 1.0 +// float minval = min(rm, gm, bm); +// rm /= minval; +// gm /= minval; +// bm /= minval; +// // multiply with reference gain, ie as-shot WB +// rm *= camInitialGain; +// gm *= camInitialGain; +// bm *= camInitialGain; } defGain = 0.0; @@ -849,9 +841,9 @@ void RawImageSource::getImage (const ColorTemp &ctemp, int tran, Imagefloat* ima hlRecovery (hrp.method, line_red, line_grn, line_blue, imwidth, hlmax); } - if(d1x) { + if (d1x) { transLineD1x (line_red, line_grn, line_blue, ix, image, tran, imwidth, imheight, d1xHeightOdd, doClip); - } else if(fuji) { + } else if (fuji) { transLineFuji (line_red, line_grn, line_blue, ix, image, tran, imheight, fw); } else { transLineStandard (line_red, line_grn, line_blue, ix, image, tran, imwidth, imheight); @@ -877,13 +869,13 @@ void RawImageSource::getImage (const ColorTemp &ctemp, int tran, Imagefloat* ima for (int i = 1; i < image->getHeight() - 1; i++) { for (int j = 2 - (a + i + 1) % 2; j < image->getWidth() - 1; j += 2) { // edge-adaptive interpolation - double dh = (ABS(image->r(i, j + 1) - image->r(i, j - 1)) + ABS(image->g(i, j + 1) - image->g(i, j - 1)) + ABS(image->b(i, j + 1) - image->b(i, j - 1))) / 1.0; - double dv = (ABS(image->r(i + 1, j) - image->r(i - 1, j)) + ABS(image->g(i + 1, j) - image->g(i - 1, j)) + ABS(image->b(i + 1, j) - image->b(i - 1, j))) / 1.0; - double eh = 1.0 / (1.0 + dh); - double ev = 1.0 / (1.0 + dv); - image->r(i, j) = (eh * (image->r(i, j + 1) + image->r(i, j - 1)) + ev * (image->r(i + 1, j) + image->r(i - 1, j))) / (2.0 * (eh + ev)); - image->g(i, j) = (eh * (image->g(i, j + 1) + image->g(i, j - 1)) + ev * (image->g(i + 1, j) + image->g(i - 1, j))) / (2.0 * (eh + ev)); - image->b(i, j) = (eh * (image->b(i, j + 1) + image->b(i, j - 1)) + ev * (image->b(i + 1, j) + image->b(i - 1, j))) / (2.0 * (eh + ev)); + float dh = (std::fabs(image->r(i, j + 1) - image->r(i, j - 1)) + std::fabs(image->g(i, j + 1) - image->g(i, j - 1)) + std::fabs(image->b(i, j + 1) - image->b(i, j - 1))); + float dv = (std::fabs(image->r(i + 1, j) - image->r(i - 1, j)) + std::fabs(image->g(i + 1, j) - image->g(i - 1, j)) + std::fabs(image->b(i + 1, j) - image->b(i - 1, j))); + float eh = 1.f / (1.f + dh); + float ev = 1.f / (1.f + dv); + image->r(i, j) = (eh * (image->r(i, j + 1) + image->r(i, j - 1)) + ev * (image->r(i + 1, j) + image->r(i - 1, j))) / (2.f * (eh + ev)); + image->g(i, j) = (eh * (image->g(i, j + 1) + image->g(i, j - 1)) + ev * (image->g(i + 1, j) + image->g(i - 1, j))) / (2.f * (eh + ev)); + image->b(i, j) = (eh * (image->b(i, j + 1) + image->b(i, j - 1)) + ev * (image->b(i + 1, j) + image->b(i - 1, j))) / (2.f * (eh + ev)); } // first pixel @@ -902,9 +894,9 @@ void RawImageSource::getImage (const ColorTemp &ctemp, int tran, Imagefloat* ima } // last row - int b = (a == 1 && image->getHeight() % 2) || (a == 0 && image->getHeight() % 2 == 0); + int offset = (a == 1 && image->getHeight() % 2) || (a == 0 && image->getHeight() % 2 == 0); - for (int j = 1 + b; j < image->getWidth() - 1; j += 2) { + for (int j = 1 + offset; j < image->getWidth() - 1; j += 2) { image->r(image->getHeight() - 1, j) = (image->r(image->getHeight() - 2, j) + image->r(image->getHeight() - 1, j + 1) + image->r(image->getHeight() - 1, j - 1)) / 3; image->g(image->getHeight() - 1, j) = (image->g(image->getHeight() - 2, j) + image->g(image->getHeight() - 1, j + 1) + image->g(image->getHeight() - 1, j - 1)) / 3; image->b(image->getHeight() - 1, j) = (image->b(image->getHeight() - 2, j) + image->b(image->getHeight() - 1, j + 1) + image->b(image->getHeight() - 1, j - 1)) / 3; @@ -921,7 +913,7 @@ void RawImageSource::getImage (const ColorTemp &ctemp, int tran, Imagefloat* ima } // Colour correction (only when running on full resolution) - if(pp.getSkip() == 1) { + if (pp.getSkip() == 1) { switch(ri->getSensorType()) { case ST_BAYER: processFalseColorCorrection (image, raw.bayersensor.ccSteps); @@ -1037,7 +1029,7 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly) errCode = 0; - if(numFrames >= 7) { + if (numFrames >= 7) { // special case to avoid crash when loading Hasselblad H6D-100cMS pixelshift files // limit to 6 frames and skip first frame, as first frame is not bayer if (firstFrameOnly) { @@ -1053,8 +1045,8 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly) #ifdef _OPENMP #pragma omp for nowait #endif - for(unsigned int i = 0; i < numFrames; ++i) { - if(i == 0) { + for (unsigned int i = 0; i < numFrames; ++i) { + if (i == 0) { riFrames[i] = ri; errCodeThr = riFrames[i]->loadRaw (true, i + 1, true, plistener, 0.8); } else { @@ -1069,7 +1061,7 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly) errCode = errCodeThr ? errCodeThr : errCode; } } - } else if(numFrames > 1) { + } else if (numFrames > 1) { #ifdef _OPENMP #pragma omp parallel #endif @@ -1078,8 +1070,8 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly) #ifdef _OPENMP #pragma omp for nowait #endif - for(unsigned int i = 0; i < numFrames; ++i) { - if(i == 0) { + for (unsigned int i = 0; i < numFrames; ++i) { + if (i == 0) { riFrames[i] = ri; errCodeThr = riFrames[i]->loadRaw (true, i, true, plistener, 0.8); } else { @@ -1099,16 +1091,16 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly) errCode = riFrames[0]->loadRaw (true, 0, true, plistener, 0.8); } - if(!errCode) { - for(unsigned int i = 0; i < numFrames; ++i) { + if (!errCode) { + for (unsigned int i = 0; i < numFrames; ++i) { riFrames[i]->compress_image(i); } } else { return errCode; } - if(numFrames > 1 ) { // this disables multi frame support for Fuji S5 until I found a solution to handle different dimensions - if(riFrames[0]->get_width() != riFrames[1]->get_width() || riFrames[0]->get_height() != riFrames[1]->get_height()) { + if (numFrames > 1) { // this disables multi frame support for Fuji S5 until I found a solution to handle different dimensions + if (riFrames[0]->get_width() != riFrames[1]->get_width() || riFrames[0]->get_height() != riFrames[1]->get_height()) { numFrames = 1; } } @@ -1131,15 +1123,15 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly) // first arg is matrix, second arg is inverse inverse33 (imatrices.rgb_cam, imatrices.cam_rgb); - d1x = ! ri->get_model().compare("D1X"); + d1x = ! ri->get_model().compare("D1X"); - if(ri->getSensorType() == ST_FUJI_XTRANS) { + if (ri->getSensorType() == ST_FUJI_XTRANS) { border = 7; - } else if(ri->getSensorType() == ST_FOVEON) { + } else if (ri->getSensorType() == ST_FOVEON) { border = 0; } - if ( ri->get_profile() ) { + if (ri->get_profile()) { embProfile = cmsOpenProfileFromMem (ri->get_profile(), ri->get_profileLen()); } @@ -1158,7 +1150,7 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly) // First we get the "as shot" ("Camera") white balance and store it float pre_mul[4]; // FIXME: get_colorsCoeff not so much used nowadays, when we have calculate_scale_mul() function here - ri->get_colorsCoeff( pre_mul, scale_mul, c_black, false);//modify for black level + ri->get_colorsCoeff(pre_mul, scale_mul, c_black, false);//modify for black level camInitialGain = max(scale_mul[0], scale_mul[1], scale_mul[2], scale_mul[3]) / min(scale_mul[0], scale_mul[1], scale_mul[2], scale_mul[3]); double camwb_red = ri->get_pre_mul(0) / pre_mul[0]; @@ -1174,7 +1166,7 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly) { // ...then we re-get the constants but now with auto which gives us better demosaicing and CA auto-correct // performance for strange white balance settings (such as UniWB) - ri->get_colorsCoeff( ref_pre_mul, scale_mul, c_black, true); + ri->get_colorsCoeff(ref_pre_mul, scale_mul, c_black, true); refwb_red = ri->get_pre_mul(0) / ref_pre_mul[0]; refwb_green = ri->get_pre_mul(1) / ref_pre_mul[1]; refwb_blue = ri->get_pre_mul(2) / ref_pre_mul[2]; @@ -1195,9 +1187,9 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly) ColorTemp d50wb = ColorTemp(5000.0, 1.0, 1.0, "Custom"); double rm,gm,bm,r,g,b; d50wb.getMultipliers(r, g, b); - camwb_red = imatrices.cam_rgb[0][0]*r + imatrices.cam_rgb[0][1]*g + imatrices.cam_rgb[0][2]*b; + camwb_red = imatrices.cam_rgb[0][0]*r + imatrices.cam_rgb[0][1]*g + imatrices.cam_rgb[0][2]*b; camwb_green = imatrices.cam_rgb[1][0]*r + imatrices.cam_rgb[1][1]*g + imatrices.cam_rgb[1][2]*b; - camwb_blue = imatrices.cam_rgb[2][0]*r + imatrices.cam_rgb[2][1]*g + imatrices.cam_rgb[2][2]*b; + camwb_blue = imatrices.cam_rgb[2][0]*r + imatrices.cam_rgb[2][1]*g + imatrices.cam_rgb[2][2]*b; double pre_mul[3], dmax = 0; pre_mul[0] = ri->get_pre_mul(0) / camwb_red; pre_mul[1] = ri->get_pre_mul(1) / camwb_green; @@ -1220,7 +1212,7 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly) initialGain = 1.0 / min(pre_mul[0], pre_mul[1], pre_mul[2]); }*/ - for(unsigned int i = 0;i < numFrames; ++i) { + for (unsigned int i = 0;i < numFrames; ++i) { riFrames[i]->set_prefilters(); } @@ -1242,7 +1234,7 @@ int RawImageSource::load (const Glib::ustring &fname, bool firstFrameOnly) plistener = nullptr; // This must be reset, because only load() is called through progressConnector t2.set(); - if( settings->verbose ) { + if (settings->verbose) { printf("Load %s: %d usec\n", fname.c_str(), t2.etime(t1)); } @@ -1261,27 +1253,27 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le RawImage *rid = nullptr; if (!raw.df_autoselect) { - if( !raw.dark_frame.empty()) { - rid = dfm.searchDarkFrame( raw.dark_frame ); + if (!raw.dark_frame.empty()) { + rid = dfm.searchDarkFrame(raw.dark_frame); } } else { rid = dfm.searchDarkFrame(idata->getMake(), idata->getModel(), idata->getISOSpeed(), idata->getShutterSpeed(), idata->getDateTimeAsTS()); } - if( rid && settings->verbose) { - printf( "Subtracting Darkframe:%s\n", rid->get_filename().c_str()); + if (rid && settings->verbose) { + printf("Subtracting Darkframe:%s\n", rid->get_filename().c_str()); } std::unique_ptr bitmapBads; int totBP = 0; // Hold count of bad pixels to correct - if(ri->zeroIsBad()) { // mark all pixels with value zero as bad, has to be called before FF and DF. dcraw sets this flag only for some cameras (mainly Panasonic and Leica) + if (ri->zeroIsBad()) { // mark all pixels with value zero as bad, has to be called before FF and DF. dcraw sets this flag only for some cameras (mainly Panasonic and Leica) bitmapBads.reset(new PixelsMap(W, H)); totBP = findZeroPixels(*(bitmapBads.get())); - if( settings->verbose) { - printf( "%d pixels with value zero marked as bad pixels\n", totBP); + if (settings->verbose) { + printf("%d pixels with value zero marked as bad pixels\n", totBP); } } @@ -1289,28 +1281,28 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le RawImage *rif = nullptr; if (!raw.ff_AutoSelect) { - if( !raw.ff_file.empty()) { - rif = ffm.searchFlatField( raw.ff_file ); + if (!raw.ff_file.empty()) { + rif = ffm.searchFlatField(raw.ff_file); } } else { - rif = ffm.searchFlatField( idata->getMake(), idata->getModel(), idata->getLens(), idata->getFocalLen(), idata->getFNumber(), idata->getDateTimeAsTS()); + rif = ffm.searchFlatField(idata->getMake(), idata->getModel(), idata->getLens(), idata->getFocalLen(), idata->getFNumber(), idata->getDateTimeAsTS()); } bool hasFlatField = (rif != nullptr); - if( hasFlatField && settings->verbose) { - printf( "Flat Field Correction:%s\n", rif->get_filename().c_str()); + if (hasFlatField && settings->verbose) { + printf("Flat Field Correction:%s\n", rif->get_filename().c_str()); } - if(numFrames == 4) { + if (numFrames == 4) { int bufferNumber = 0; - for(unsigned int i=0; i<4; ++i) { - if(i==currFrame) { + for (unsigned int i=0; i<4; ++i) { + if (i==currFrame) { copyOriginalPixels(raw, ri, rid, rif, rawData); rawDataFrames[i] = &rawData; } else { - if(!rawDataBuffer[bufferNumber]) { + if (!rawDataBuffer[bufferNumber]) { rawDataBuffer[bufferNumber] = new array2D; } rawDataFrames[i] = rawDataBuffer[bufferNumber]; @@ -1319,7 +1311,7 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le } } } else if (numFrames == 2 && currFrame == 2) { // average the frames - if(!rawDataBuffer[0]) { + if (!rawDataBuffer[0]) { rawDataBuffer[0] = new array2D; } rawDataFrames[1] = rawDataBuffer[0]; @@ -1338,16 +1330,16 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le // Always correct camera badpixels from .badpixels file - std::vector *bp = dfm.getBadPixels( ri->get_maker(), ri->get_model(), idata->getSerialNumber() ); + std::vector *bp = dfm.getBadPixels(ri->get_maker(), ri->get_model(), idata->getSerialNumber()); - if( bp ) { - if(!bitmapBads) { + if (bp) { + if (!bitmapBads) { bitmapBads.reset(new PixelsMap(W, H)); } totBP += bitmapBads->set(*bp); - if( settings->verbose ) { + if (settings->verbose) { std::cout << "Correcting " << bp->size() << " pixels from .badpixels" << std::endl; } } @@ -1355,30 +1347,30 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le // If darkframe selected, correct hotpixels found on darkframe bp = nullptr; - if( raw.df_autoselect ) { + if (raw.df_autoselect) { bp = dfm.getHotPixels(idata->getMake(), idata->getModel(), idata->getISOSpeed(), idata->getShutterSpeed(), idata->getDateTimeAsTS()); - } else if( !raw.dark_frame.empty() ) { - bp = dfm.getHotPixels( raw.dark_frame ); + } else if (!raw.dark_frame.empty()) { + bp = dfm.getHotPixels(raw.dark_frame); } - if(bp) { - if(!bitmapBads) { + if (bp) { + if (!bitmapBads) { bitmapBads.reset(new PixelsMap(W, H)); } totBP += bitmapBads->set(*bp); - if( settings->verbose && !bp->empty()) { + if (settings->verbose && !bp->empty()) { std::cout << "Correcting " << bp->size() << " hotpixels from darkframe" << std::endl; } } - if(numFrames == 4) { - for(int i=0; i<4; ++i) { - scaleColors( 0, 0, W, H, raw, *rawDataFrames[i]); + if (numFrames == 4) { + for (int i=0; i<4; ++i) { + scaleColors(0, 0, W, H, raw, *rawDataFrames[i]); } } else { - scaleColors( 0, 0, W, H, raw, rawData); //+ + raw parameters for black level(raw.blackxx) + scaleColors(0, 0, W, H, raw, rawData); //+ + raw parameters for black level(raw.blackxx) } // Correct vignetting of lens profile @@ -1397,14 +1389,14 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le if (pmap) { LensCorrection &map = *pmap; if (ri->getSensorType() == ST_BAYER || ri->getSensorType() == ST_FUJI_XTRANS || ri->get_colors() == 1) { - if(numFrames == 4) { - for(int i = 0; i < 4; ++i) { + if (numFrames == 4) { + for (int i = 0; i < 4; ++i) { map.processVignette(W, H, *rawDataFrames[i]); } } else { map.processVignette(W, H, rawData); } - } else if(ri->get_colors() == 3) { + } else if (ri->get_colors() == 3) { map.processVignette3Channels(W, H, rawData); } } @@ -1412,21 +1404,21 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le defGain = 0.0;//log(initialGain) / log(2.0); - if ( ri->getSensorType() == ST_BAYER && (raw.hotPixelFilter > 0 || raw.deadPixelFilter > 0)) { + if (ri->getSensorType() == ST_BAYER && (raw.hotPixelFilter > 0 || raw.deadPixelFilter > 0)) { if (plistener) { plistener->setProgressStr ("PROGRESSBAR_HOTDEADPIXELFILTER"); plistener->setProgress (0.0); } - if(!bitmapBads) { + if (!bitmapBads) { bitmapBads.reset(new PixelsMap(W, H)); } - int nFound = findHotDeadPixels(*(bitmapBads.get()), raw.hotdeadpix_thresh, raw.hotPixelFilter, raw.deadPixelFilter ); + int nFound = findHotDeadPixels(*(bitmapBads.get()), raw.hotdeadpix_thresh, raw.hotPixelFilter, raw.deadPixelFilter); totBP += nFound; - if( settings->verbose && nFound > 0) { - printf( "Correcting %d hot/dead pixels found inside image\n", nFound ); + if (settings->verbose && nFound > 0) { + printf("Correcting %d hot/dead pixels found inside image\n", nFound); } } @@ -1461,17 +1453,17 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le [&]() -> bool { CameraConstantsStore *ccs = CameraConstantsStore::getInstance(); - CameraConst *cc = ccs->get(ri->get_maker().c_str(), ri->get_model().c_str()); + const CameraConst *cc = ccs->get(ri->get_maker().c_str(), ri->get_model().c_str()); return cc && cc->get_globalGreenEquilibration(); }; - if ( ri->getSensorType() == ST_BAYER && (raw.bayersensor.greenthresh || (globalGreenEq() && raw.bayersensor.method != RAWParams::BayerSensor::getMethodString( RAWParams::BayerSensor::Method::VNG4))) ) { + if (ri->getSensorType() == ST_BAYER && (raw.bayersensor.greenthresh || (globalGreenEq() && raw.bayersensor.method != RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::VNG4)))) { if (settings->verbose) { printf("Performing global green equilibration...\n"); } // global correction - if(numFrames == 4) { - for(int i = 0; i < 4; ++i) { + if (numFrames == 4) { + for (int i = 0; i < 4; ++i) { green_equilibrate_global(*rawDataFrames[i]); } } else { @@ -1479,7 +1471,7 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le } } - if ( ri->getSensorType() == ST_BAYER && raw.bayersensor.greenthresh > 0) { + if (ri->getSensorType() == ST_BAYER && raw.bayersensor.greenthresh > 0) { if (plistener) { plistener->setProgressStr ("PROGRESSBAR_GREENEQUIL"); plistener->setProgress (0.0); @@ -1487,8 +1479,8 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le GreenEqulibrateThreshold thresh(0.01 * raw.bayersensor.greenthresh); - if(numFrames == 4) { - for(int i = 0; i < 4; ++i) { + if (numFrames == 4) { + for (int i = 0; i < 4; ++i) { green_equilibrate(thresh, *rawDataFrames[i]); } } else { @@ -1497,23 +1489,23 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le } - if( totBP ) { - if ( ri->getSensorType() == ST_BAYER ) { - if(numFrames == 4) { - for(int i = 0; i < 4; ++i) { + if (totBP) { + if (ri->getSensorType() == ST_BAYER) { + if (numFrames == 4) { + for (int i = 0; i < 4; ++i) { interpolateBadPixelsBayer(*(bitmapBads.get()), *rawDataFrames[i]); } } else { interpolateBadPixelsBayer(*(bitmapBads.get()), rawData); } - } else if ( ri->getSensorType() == ST_FUJI_XTRANS ) { + } else if (ri->getSensorType() == ST_FUJI_XTRANS) { interpolateBadPixelsXtrans(*(bitmapBads.get())); } else { interpolateBadPixelsNColours(*(bitmapBads.get()), ri->get_colors()); } } - if ( ri->getSensorType() == ST_BAYER && raw.bayersensor.linenoise > 0 ) { + if (ri->getSensorType() == ST_BAYER && raw.bayersensor.linenoise > 0) { if (plistener) { plistener->setProgressStr ("PROGRESSBAR_LINEDENOISE"); plistener->setProgress (0.0); @@ -1530,15 +1522,15 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le cfa_linedn(0.00002 * (raw.bayersensor.linenoise), int(raw.bayersensor.linenoiseDirection) & int(RAWParams::BayerSensor::LineNoiseDirection::VERTICAL), int(raw.bayersensor.linenoiseDirection) & int(RAWParams::BayerSensor::LineNoiseDirection::HORIZONTAL), *line_denoise_rowblender); } - if ( (raw.ca_autocorrect || fabs(raw.cared) > 0.001 || fabs(raw.cablue) > 0.001) && ri->getSensorType() == ST_BAYER ) { // Auto CA correction disabled for X-Trans, for now... + if ((raw.ca_autocorrect || std::fabs(raw.cared) > 0.001 || std::fabs(raw.cablue) > 0.001) && ri->getSensorType() == ST_BAYER) { // Auto CA correction disabled for X-Trans, for now... if (plistener) { plistener->setProgressStr ("PROGRESSBAR_RAWCACORR"); plistener->setProgress (0.0); } - if(numFrames == 4) { + if (numFrames == 4) { double fitParams[64]; float *buffer = CA_correct_RT(raw.ca_autocorrect, raw.caautoiterations, raw.cared, raw.cablue, raw.ca_avoidcolourshift, *rawDataFrames[0], fitParams, false, true, nullptr, false, options.chunkSizeCA, options.measure); - for(int i = 1; i < 3; ++i) { + for (int i = 1; i < 3; ++i) { CA_correct_RT(raw.ca_autocorrect, raw.caautoiterations, raw.cared, raw.cablue, raw.ca_avoidcolourshift, *rawDataFrames[i], fitParams, true, false, buffer, false, options.chunkSizeCA, options.measure); } CA_correct_RT(raw.ca_autocorrect, raw.caautoiterations, raw.cared, raw.cablue, raw.ca_avoidcolourshift, *rawDataFrames[3], fitParams, true, false, buffer, true, options.chunkSizeCA, options.measure); @@ -1547,7 +1539,7 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le } } - if(prepareDenoise && dirpyrdenoiseExpComp == INFINITY) { + if (prepareDenoise && dirpyrdenoiseExpComp == RT_INFINITY) { LUTu aehist; int aehistcompr; double clip = 0; @@ -1558,7 +1550,7 @@ void RawImageSource::preprocess (const RAWParams &raw, const LensProfParams &le t2.set(); - if( settings->verbose ) { + if (settings->verbose) { printf("Preprocessing: %d usec\n", t2.etime(t1)); } @@ -1573,13 +1565,13 @@ void RawImageSource::demosaic(const RAWParams &raw, bool autoContrast, double &c t1.set(); if (ri->getSensorType() == ST_BAYER) { - if ( raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::HPHD) ) { + if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::HPHD)) { hphd_demosaic (); - } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::VNG4) ) { + } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::VNG4)) { vng4_demosaic (rawData, red, green, blue); - } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::AHD) ) { + } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::AHD)) { ahd_demosaic (); - } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::AMAZE) ) { + } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::AMAZE)) { amaze_demosaic_RT (0, 0, W, H, rawData, red, green, blue, options.chunkSizeAMAZE, options.measure); } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::AMAZEVNG4) || raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::DCBVNG4) @@ -1590,9 +1582,9 @@ void RawImageSource::demosaic(const RAWParams &raw, bool autoContrast, double &c } else { dual_demosaic_RT (true, raw, W, H, rawData, red, green, blue, contrastThreshold, true); } - } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::PIXELSHIFT) ) { + } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::PIXELSHIFT)) { pixelshift(0, 0, W, H, raw, currFrame, ri->get_maker(), ri->get_model(), raw.expos); - } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::DCB) ) { + } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::DCB)) { dcb_demosaic(raw.bayersensor.dcb_iterations, raw.bayersensor.dcb_enhance); } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::EAHD)) { eahd_demosaic (); @@ -1600,21 +1592,21 @@ void RawImageSource::demosaic(const RAWParams &raw, bool autoContrast, double &c igv_interpolate(W, H); } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::LMMSE)) { lmmse_interpolate_omp(W, H, rawData, red, green, blue, raw.bayersensor.lmmse_iterations); - } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::FAST) ) { + } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::FAST)) { fast_demosaic(); - } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::MONO) ) { + } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::MONO)) { nodemosaic(true); - } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::RCD) ) { + } else if (raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::RCD)) { rcd_demosaic(options.chunkSizeRCD, options.measure); } else { nodemosaic(false); } } else if (ri->getSensorType() == ST_FUJI_XTRANS) { - if (raw.xtranssensor.method == RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::FAST) ) { + if (raw.xtranssensor.method == RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::FAST)) { fast_xtrans_interpolate(rawData, red, green, blue); } else if (raw.xtranssensor.method == RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::ONE_PASS)) { xtrans_interpolate(1, false, options.chunkSizeXT, options.measure); - } else if (raw.xtranssensor.method == RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::THREE_PASS) ) { + } else if (raw.xtranssensor.method == RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::THREE_PASS)) { xtrans_interpolate(3, true, options.chunkSizeXT, options.measure); } else if (raw.xtranssensor.method == RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::FOUR_PASS) || raw.xtranssensor.method == RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::TWO_PASS)) { if (!autoContrast) { @@ -1623,7 +1615,7 @@ void RawImageSource::demosaic(const RAWParams &raw, bool autoContrast, double &c } else { dual_demosaic_RT (false, raw, W, H, rawData, red, green, blue, contrastThreshold, true); } - } else if(raw.xtranssensor.method == RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::MONO) ) { + } else if (raw.xtranssensor.method == RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::MONO)) { nodemosaic(true); } else { nodemosaic(false); @@ -1681,7 +1673,7 @@ void RawImageSource::demosaic(const RAWParams &raw, bool autoContrast, double &c delete blueCache; blueCache = nullptr; } - if( settings->verbose ) { + if (settings->verbose) { if (getSensorType() == ST_BAYER) { printf("Demosaicing Bayer data: %s - %d usec\n", raw.bayersensor.method.c_str(), t2.etime(t1)); } else if (getSensorType() == ST_FUJI_XTRANS) { @@ -1703,20 +1695,20 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con LUTf *retinexgamtab = nullptr;//gamma before and after Retinex to restore tones LUTf lutTonereti; - if(retinexParams.gammaretinex == "low") { + if (retinexParams.gammaretinex == "low") { retinexgamtab = &(Color::gammatab_115_2); - } else if(retinexParams.gammaretinex == "mid") { + } else if (retinexParams.gammaretinex == "mid") { retinexgamtab = &(Color::gammatab_13_2); - } else if(retinexParams.gammaretinex == "hig") { + } else if (retinexParams.gammaretinex == "hig") { retinexgamtab = &(Color::gammatab_145_3); - } else if(retinexParams.gammaretinex == "fre") { + } else if (retinexParams.gammaretinex == "fre") { GammaValues g_a; double pwr = 1.0 / retinexParams.gam; double gamm = retinexParams.gam; double ts = retinexParams.slope; double gamm2 = retinexParams.gam; - if(gamm2 < 1.) { + if (gamm2 < 1.) { std::swap(pwr, gamm); } @@ -1727,7 +1719,7 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con double start; double add; - if(gamm2 < 1.) { + if (gamm2 < 1.) { start = g_a[2]; add = g_a[4]; } else { @@ -1743,7 +1735,7 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con double val = (i) / 65535.; double x; - if(gamm2 < 1.) { + if (gamm2 < 1.) { x = Color::igammareti (val, gamm, start, ts, mul , add); } else { x = Color::gammareti (val, gamm, start, ts, mul , add); @@ -1772,15 +1764,15 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con printf("rr2=%f gg2=%f bb2=%f \n",rr,gg,bb); */ /* - if(retinexParams.highlig < 100 && retinexParams.retinexMethod == "highliplus") {//try to recover magenta...very difficult ! + if (retinexParams.highlig < 100 && retinexParams.retinexMethod == "highliplus") {//try to recover magenta...very difficult ! float hig = ((float)retinexParams.highlig)/100.f; float higgb = ((float)retinexParams.grbl)/100.f; #ifdef _OPENMP #pragma omp parallel for #endif - for (int i = border; i < H - border; i++ ) { - for (int j = border; j < W - border; j++ ) { + for (int i = border; i < H - border; i++) { + for (int j = border; j < W - border; j++) { float R_,G_,B_; R_=red[i][j]; G_=green[i][j]; @@ -1788,20 +1780,20 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con //empirical method to find highlight magenta with no conversion RGB and no white balance //red = master Gr and Bl default higgb=0.5 - // if(R_>65535.f*hig && G_ > 65535.f*higgb && B_ > 65535.f*higgb) conversionBuffer[3][i - border][j - border] = R_; + // if (R_>65535.f*hig && G_ > 65535.f*higgb && B_ > 65535.f*higgb) conversionBuffer[3][i - border][j - border] = R_; // else conversionBuffer[3][i - border][j - border] = 0.f; } } } */ - if(retinexParams.gammaretinex != "none" && retinexParams.str != 0 && retinexgamtab) {//gamma + if (retinexParams.gammaretinex != "none" && retinexParams.str != 0 && retinexgamtab) {//gamma #ifdef _OPENMP #pragma omp parallel for #endif - for (int i = border; i < H - border; i++ ) { - for (int j = border; j < W - border; j++ ) { + for (int i = border; i < H - border; i++) { + for (int j = border; j < W - border; j++) { float R_, G_, B_; R_ = red[i][j]; G_ = green[i][j]; @@ -1814,7 +1806,7 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con } } - if(useHsl) { + if (useHsl) { #ifdef _OPENMP #pragma omp parallel #endif @@ -1822,7 +1814,7 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con // one LUT per thread LUTu lhist16RETIThr; - if(lhist16RETI) + if (lhist16RETI) { lhist16RETIThr(lhist16RETI.getSize()); lhist16RETIThr.clear(); @@ -1835,7 +1827,7 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con #pragma omp for #endif - for (int i = border; i < H - border; i++ ) + for (int i = border; i < H - border; i++) { int j = border; #ifdef __SSE2__ @@ -1849,9 +1841,9 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con STVFU(conversionBuffer[2][i - border][j - border], L); STVFU(conversionBuffer[3][i - border][j - border], H); - if(lhist16RETI) { - for(int p = 0; p < 4; p++) { - int pos = ( conversionBuffer[2][i - border][j - border + p]);//histogram in curve HSL + if (lhist16RETI) { + for (int p = 0; p < 4; p++) { + int pos = (conversionBuffer[2][i - border][j - border + p]);//histogram in curve HSL lhist16RETIThr[pos]++; } } @@ -1866,7 +1858,7 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con L *= 32768.f; conversionBuffer[2][i - border][j - border] = L; - if(lhist16RETI) { + if (lhist16RETI) { int pos = L; lhist16RETIThr[pos]++; } @@ -1876,7 +1868,7 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con #ifdef _OPENMP #pragma omp critical { - if(lhist16RETI) + if (lhist16RETI) { lhist16RETI += lhist16RETIThr; // Add per Thread LUT to global LUT } @@ -1901,7 +1893,7 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con // one LUT per thread LUTu lhist16RETIThr; - if(lhist16RETI) { + if (lhist16RETI) { lhist16RETIThr(lhist16RETI.getSize()); lhist16RETIThr.clear(); } @@ -1910,7 +1902,7 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con #pragma omp for schedule(dynamic,16) #endif - for (int i = border; i < H - border; i++ ) + for (int i = border; i < H - border; i++) for (int j = border; j < W - border; j++) { float X, Y, Z, L, aa, bb; //rgb=>lab @@ -1922,9 +1914,9 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con conversionBuffer[2][i - border][j - border] = L; conversionBuffer[3][i - border][j - border] = xatan2f(bb, aa); -// if(R_>40000.f && G_ > 30000.f && B_ > 30000.f) conversionBuffer[3][i - border][j - border] = R_; +// if (R_>40000.f && G_ > 30000.f && B_ > 30000.f) conversionBuffer[3][i - border][j - border] = R_; // else conversionBuffer[3][i - border][j - border] = 0.f; - if(lhist16RETI) { + if (lhist16RETI) { int pos = L; lhist16RETIThr[pos]++;//histogram in Curve Lab } @@ -1933,7 +1925,7 @@ void RawImageSource::retinexPrepareBuffers(const ColorManagementParams& cmp, con #ifdef _OPENMP #pragma omp critical { - if(lhist16RETI) { + if (lhist16RETI) { lhist16RETI += lhist16RETIThr; // Add per Thread LUT to global LUT } } @@ -1950,7 +1942,7 @@ void RawImageSource::retinexPrepareCurves(const RetinexParams &retinexParams, LU { useHsl = (retinexParams.retinexcolorspace == "HSLLOG" || retinexParams.retinexcolorspace == "HSLLIN"); - if(useHsl) { + if (useHsl) { CurveFactory::curveDehaContL (retinexcontlutili, retinexParams.cdHcurve, cdcurve, 1, lhist16RETI, histLRETI); } else { CurveFactory::curveDehaContL (retinexcontlutili, retinexParams.cdcurve, cdcurve, 1, lhist16RETI, histLRETI); @@ -1975,13 +1967,13 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara LUTf *retinexigamtab = nullptr;//gamma before and after Retinex to restore tones - if(deh.gammaretinex == "low") { + if (deh.gammaretinex == "low") { retinexigamtab = &(Color::igammatab_115_2); - } else if(deh.gammaretinex == "mid") { + } else if (deh.gammaretinex == "mid") { retinexigamtab = &(Color::igammatab_13_2); - } else if(deh.gammaretinex == "hig") { + } else if (deh.gammaretinex == "hig") { retinexigamtab = &(Color::igammatab_145_3); - } else if(deh.gammaretinex == "fre") { + } else if (deh.gammaretinex == "fre") { GammaValues g_a; double pwr = 1.0 / deh.gam; double gamm = deh.gam; @@ -1989,7 +1981,7 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara double ts = deh.slope; int mode = 0; - if(gamm2 < 1.) { + if (gamm2 < 1.) { std::swap(pwr, gamm); } @@ -1999,7 +1991,7 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara double add; double start; - if(gamm2 < 1.) { + if (gamm2 < 1.) { start = g_a[3]; add = g_a[3]; } else { @@ -2012,7 +2004,7 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara double val = (i) / 65535.; double x; - if(gamm2 < 1.) { + if (gamm2 < 1.) { x = Color::gammareti (val, gamm, start, ts, mul , add); } else { x = Color::igammareti (val, gamm, start, ts, mul , add); @@ -2034,7 +2026,7 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara LUTf dLcurve; LUTu hist16RET; - if(dehacontlutili && histLRETI) { + if (dehacontlutili && histLRETI) { hist16RET(32768); hist16RET.clear(); histLRETI.clear(); @@ -2066,7 +2058,7 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara // one LUT per thread LUTu hist16RETThr; - if(hist16RET) { + if (hist16RET) { hist16RETThr(hist16RET.getSize()); hist16RETThr.clear(); } @@ -2075,12 +2067,12 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara #pragma omp for #endif - for (int i = 0; i < H - 2 * border; i++ ) - if(dehacontlutili) + for (int i = 0; i < H - 2 * border; i++) + if (dehacontlutili) for (int j = 0; j < W - 2 * border; j++) { LBuffer[i][j] = cdcurve[2.f * temp[i][j]] / 2.f; - if(histLRETI) { + if (histLRETI) { int pos = LBuffer[i][j]; hist16RETThr[pos]++; //histogram in Curve } @@ -2094,13 +2086,13 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara #pragma omp critical #endif { - if(hist16RET) { + if (hist16RET) { hist16RET += hist16RETThr; // Add per Thread LUT to global LUT } } } - if(hist16RET) {//update histogram + if (hist16RET) {//update histogram // TODO : When rgbcurvesspeedup branch is merged into master, replace this by the following 1-liner // hist16RET.compressTo(histLRETI); // also remove declaration and init of dLcurve some lines above then and finally remove this comment :) @@ -2118,13 +2110,13 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara MSR(LBuffer, conversionBuffer[2], conversionBuffer[3], mapcurve, mapcontlutili, WNew, HNew, deh, dehatransmissionCurve, dehagaintransmissionCurve, minCD, maxCD, mini, maxi, Tmean, Tsigma, Tmin, Tmax); - if(useHsl) { - if(chutili) { + if (useHsl) { + if (chutili) { #ifdef _OPENMP #pragma omp parallel for #endif - for (int i = border; i < H - border; i++ ) { + for (int i = border; i < H - border; i++) { int j = border; for (; j < W - border; j++) { @@ -2140,7 +2132,7 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara #pragma omp parallel for #endif - for (int i = border; i < H - border; i++ ) { + for (int i = border; i < H - border; i++) { int j = border; #ifdef __SSE2__ vfloat c32768 = F2V(32768.f); @@ -2188,7 +2180,7 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara #pragma omp for #endif - for (int i = border; i < H - border; i++ ) { + for (int i = border; i < H - border; i++) { #ifdef __SSE2__ // vectorized precalculation { @@ -2213,12 +2205,12 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara { float aa = conversionBuffer[0][i - border][j - border]; float bb = conversionBuffer[1][i - border][j - border]; - float Chprov1 = sqrt(SQR(aa) + SQR(bb)) / 327.68f; + float Chprov1 = std::sqrt(SQR(aa) + SQR(bb)) / 327.68f; sqrtBuffer[j - border] = Chprov1; float HH = xatan2f(bb, aa); atan2Buffer[j - border] = HH; - if(Chprov1 == 0.0f) { + if (Chprov1 == 0.0f) { sincosyBuffer[j - border] = 1.f; sincosxBuffer[j - border] = 0.0f; } else { @@ -2241,11 +2233,11 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara #else float aa = conversionBuffer[0][i - border][j - border]; float bb = conversionBuffer[1][i - border][j - border]; - float Chprov1 = sqrt(SQR(aa) + SQR(bb)) / 327.68f; + float Chprov1 = std::sqrt(SQR(aa) + SQR(bb)) / 327.68f; float HH = xatan2f(bb, aa); float2 sincosval;// = xsincosf(HH); - if(Chprov1 == 0.0f) { + if (Chprov1 == 0.0f) { sincosval.y = 1.f; sincosval.x = 0.0f; } else { @@ -2255,7 +2247,7 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara #endif - if(chutili) { // c=f(H) + if (chutili) { // c=f(H) float valp = float((chcurve->getVal(Color::huelab_to_huehsv2(HH)) - 0.5f)); Chprov1 *= (1.f + 2.f * valp); } @@ -2283,8 +2275,8 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara #ifdef __SSE2__ vfloat wipv[3][3]; - for(int i = 0; i < 3; i++) - for(int j = 0; j < 3; j++) { + for (int i = 0; i < 3; i++) + for (int j = 0; j < 3; j++) { wipv[i][j] = F2V(wiprof[i][j]); } @@ -2293,7 +2285,7 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara #pragma omp parallel for #endif - for (int i = border; i < H - border; i++ ) { + for (int i = border; i < H - border; i++) { int j = border; #ifdef __SSE2__ @@ -2327,13 +2319,13 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara delete chcurve; } - if(deh.gammaretinex != "none" && deh.str != 0) { //inverse gamma + if (deh.gammaretinex != "none" && deh.str != 0) { //inverse gamma #ifdef _OPENMP #pragma omp parallel for #endif - for (int i = border; i < H - border; i++ ) { - for (int j = border; j < W - border; j++ ) { + for (int i = border; i < H - border; i++) { + for (int j = border; j < W - border; j++) { float R_, G_, B_; R_ = red[i][j]; G_ = green[i][j]; @@ -2349,21 +2341,22 @@ void RawImageSource::retinex(const ColorManagementParams& cmp, const RetinexPara t5.set(); - if( settings->verbose ) { + if (settings->verbose) { printf("Retinex=%d usec\n", t5.etime(t4)); } } -void RawImageSource::flushRawData() +void RawImageSource::flush() { + for (size_t i = 0; i + 1 < numFrames; ++i) { + delete rawDataBuffer[i]; + rawDataBuffer[i] = nullptr; + } + if (rawData) { rawData(0, 0); } -} - -void RawImageSource::flushRGB() -{ if (green) { green(0, 0); } @@ -2375,12 +2368,24 @@ void RawImageSource::flushRGB() if (blue) { blue(0, 0); } + + if (greenloc) { + greenloc(0, 0); + } + + if (redloc) { + redloc(0, 0); + } + + if (blueloc) { + blueloc(0, 0); + } } void RawImageSource::HLRecovery_Global(const ToneCurveParams &hrp) { if (hrp.hrenabled && hrp.method == "Color") { - if(!rgbSourceModified) { + if (!rgbSourceModified) { if (settings->verbose) { printf ("Applying Highlight Recovery: Color propagation...\n"); } @@ -2395,7 +2400,7 @@ void RawImageSource::HLRecovery_Global(const ToneCurveParams &hrp) /* Copy original pixel data and * subtract dark frame (if present) from current image and apply flat field correction (if present) */ -void RawImageSource::copyOriginalPixels(const RAWParams &raw, RawImage *src, RawImage *riDark, RawImage *riFlatFile, array2D &rawData ) +void RawImageSource::copyOriginalPixels(const RAWParams &raw, RawImage *src, RawImage *riDark, RawImage *riFlatFile, array2D &rawData) { const float black[4] = { static_cast(ri->get_cblack(0)), static_cast(ri->get_cblack(1)), @@ -2414,9 +2419,9 @@ void RawImageSource::copyOriginalPixels(const RAWParams &raw, RawImage *src, Raw #endif for (int row = 0; row < H; row++) { const int c0 = FC(row, 0); - const float black0 = black[(c0 == 1 && !(row & 1) ) ? 3 : c0]; + const float black0 = black[(c0 == 1 && !(row & 1)) ? 3 : c0]; const int c1 = FC(row, 1); - const float black1 = black[(c1 == 1 && !(row & 1) ) ? 3 : c1]; + const float black1 = black[(c1 == 1 && !(row & 1)) ? 3 : c1]; int col; for (col = 0; col < W - 1; col += 2) { rawData[row][col] = max(src->data[row][col] + black0 - riDark->data[row][col], 0.0f); @@ -2427,6 +2432,7 @@ void RawImageSource::copyOriginalPixels(const RAWParams &raw, RawImage *src, Raw } } } else { + #ifdef _OPENMP #pragma omp parallel for #endif @@ -2474,8 +2480,8 @@ void RawImageSource::copyOriginalPixels(const RAWParams &raw, RawImage *src, Raw if (riDark && W == riDark->get_width() && H == riDark->get_height()) { for (int row = 0; row < H; row++) { for (int col = 0; col < W; col++) { - int c = FC(row, col); - int c4 = ( c == 1 && !(row & 1) ) ? 3 : c; + int c = FC(row, col); + int c4 = (c == 1 && !(row & 1)) ? 3 : c; rawData[row][3 * col + 0] = max(src->data[row][3 * col + 0] + black[c4] - riDark->data[row][3 * col + 0], 0.0f); rawData[row][3 * col + 1] = max(src->data[row][3 * col + 1] + black[c4] - riDark->data[row][3 * col + 1], 0.0f); rawData[row][3 * col + 2] = max(src->data[row][3 * col + 2] + black[c4] - riDark->data[row][3 * col + 2], 0.0f); @@ -2502,7 +2508,7 @@ void RawImageSource::scaleColors(int winx, int winy, int winw, int winh, const R //adjust black level (eg Canon) bool isMono = false; - if (getSensorType() == ST_BAYER || getSensorType() == ST_FOVEON ) { + if (getSensorType() == ST_BAYER || getSensorType() == ST_FOVEON) { black_lev[0] = raw.bayersensor.black1; //R black_lev[1] = raw.bayersensor.black0; //G1 @@ -2520,8 +2526,8 @@ void RawImageSource::scaleColors(int winx, int winy, int winw, int winh, const R isMono = RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::MONO) == raw.xtranssensor.method; } - for(int i = 0; i < 4 ; i++) { - cblacksom[i] = max( c_black[i] + black_lev[i], 0.0f ); // adjust black level + for (int i = 0; i < 4 ; i++) { + cblacksom[i] = max(c_black[i] + black_lev[i], 0.0f); // adjust black level } for (int i = 0; i < 4; ++i) { @@ -2531,7 +2537,7 @@ void RawImageSource::scaleColors(int winx, int winy, int winw, int winh, const R initialGain = calculate_scale_mul(scale_mul, ref_pre_mul, c_white, cblacksom, isMono, ri->get_colors()); // recalculate scale colors with adjusted levels //fprintf(stderr, "recalc: %f [%f %f %f %f]\n", initialGain, scale_mul[0], scale_mul[1], scale_mul[2], scale_mul[3]); - for(int i = 0; i < 4 ; i++) { + for (int i = 0; i < 4 ; i++) { clmax[i] = (c_white[i] - cblacksom[i]) * scale_mul[i]; // raw clip level } @@ -2539,7 +2545,7 @@ void RawImageSource::scaleColors(int winx, int winy, int winw, int winh, const R // scale image colors - if( ri->getSensorType() == ST_BAYER) { + if (ri->getSensorType() == ST_BAYER) { #ifdef _OPENMP #pragma omp parallel #endif @@ -2553,8 +2559,8 @@ void RawImageSource::scaleColors(int winx, int winy, int winw, int winh, const R for (int row = winy; row < winy + winh; row ++) { for (int col = winx; col < winx + winw; col++) { - const int c = FC(row, col); // three colors, 0=R, 1=G, 2=B - const int c4 = ( c == 1 && !(row & 1) ) ? 3 : c; // four colors, 0=R, 1=G1, 2=B, 3=G2 + const int c = FC(row, col); // three colors, 0=R, 1=G, 2=B + const int c4 = (c == 1 && !(row & 1)) ? 3 : c; // four colors, 0=R, 1=G1, 2=B, 3=G2 const float val = max(0.f, rawData[row][col] - cblacksom[c4]) * scale_mul[c4]; rawData[row][col] = val; tmpchmax[c] = max(tmpchmax[c], val); @@ -2570,7 +2576,7 @@ void RawImageSource::scaleColors(int winx, int winy, int winw, int winh, const R chmax[2] = max(tmpchmax[2], chmax[2]); } } - } else if ( ri->get_colors() == 1 ) { + } else if (ri->get_colors() == 1) { #ifdef _OPENMP #pragma omp parallel #endif @@ -2596,7 +2602,7 @@ void RawImageSource::scaleColors(int winx, int winy, int winw, int winh, const R chmax[0] = chmax[1] = chmax[2] = chmax[3] = max(tmpchmax, chmax[0]); } } - } else if(ri->getSensorType() == ST_FUJI_XTRANS) { + } else if (ri->getSensorType() == ST_FUJI_XTRANS) { #ifdef _OPENMP #pragma omp parallel #endif @@ -2916,7 +2922,7 @@ lab2ProphotoRgbD50(float L, float A, float B, float& r, float& g, float& b) float X; float Y; float Z; -#define CLIP01(a) ((a)>0?((a)<1?(a):1):0) + { // convert from Lab to XYZ float x, y, z, fx, fy, fz; @@ -2951,9 +2957,6 @@ lab2ProphotoRgbD50(float L, float A, float B, float& r, float& g, float& b) r = prophoto_xyz[0][0] * X + prophoto_xyz[0][1] * Y + prophoto_xyz[0][2] * Z; g = prophoto_xyz[1][0] * X + prophoto_xyz[1][1] * Y + prophoto_xyz[1][2] * Z; b = prophoto_xyz[2][0] * X + prophoto_xyz[2][1] * Y + prophoto_xyz[2][2] * Z; - // r = CLIP01(r); - // g = CLIP01(g); - // b = CLIP01(b); } // Converts raw image including ICC input profile to working space - floating point version @@ -3122,7 +3125,7 @@ void RawImageSource::colorSpaceConversion_ (Imagefloat* im, const ColorManagemen transform_via_pcs_lab = true; separate_pcs_lab_highlights = true; // We transform to Lab because we can and that we avoid getting an unnecessary unmatched gamma conversion which we would need to revert. - hTransform = cmsCreateTransform (in, TYPE_RGB_FLT, nullptr, TYPE_Lab_FLT, INTENT_RELATIVE_COLORIMETRIC, cmsFLAGS_NOOPTIMIZE | cmsFLAGS_NOCACHE ); + hTransform = cmsCreateTransform (in, TYPE_RGB_FLT, nullptr, TYPE_Lab_FLT, INTENT_RELATIVE_COLORIMETRIC, cmsFLAGS_NOOPTIMIZE | cmsFLAGS_NOCACHE); for (int i = 0; i < 3; i++) { for (int j = 0; j < 3; j++) { @@ -3140,7 +3143,7 @@ void RawImageSource::colorSpaceConversion_ (Imagefloat* im, const ColorManagemen case CAMERA_ICC_TYPE_NIKON: case CAMERA_ICC_TYPE_GENERIC: default: - hTransform = cmsCreateTransform (in, TYPE_RGB_FLT, prophoto, TYPE_RGB_FLT, INTENT_RELATIVE_COLORIMETRIC, cmsFLAGS_NOOPTIMIZE | cmsFLAGS_NOCACHE ); // NOCACHE is important for thread safety + hTransform = cmsCreateTransform (in, TYPE_RGB_FLT, prophoto, TYPE_RGB_FLT, INTENT_RELATIVE_COLORIMETRIC, cmsFLAGS_NOOPTIMIZE | cmsFLAGS_NOCACHE); // NOCACHE is important for thread safety break; } @@ -3149,7 +3152,7 @@ void RawImageSource::colorSpaceConversion_ (Imagefloat* im, const ColorManagemen if (hTransform == nullptr) { // Fallback: create transform from camera profile. Should not happen normally. lcmsMutex->lock (); - hTransform = cmsCreateTransform (camprofile, TYPE_RGB_FLT, prophoto, TYPE_RGB_FLT, INTENT_RELATIVE_COLORIMETRIC, cmsFLAGS_NOOPTIMIZE | cmsFLAGS_NOCACHE ); + hTransform = cmsCreateTransform (camprofile, TYPE_RGB_FLT, prophoto, TYPE_RGB_FLT, INTENT_RELATIVE_COLORIMETRIC, cmsFLAGS_NOOPTIMIZE | cmsFLAGS_NOCACHE); lcmsMutex->unlock (); } @@ -3171,11 +3174,11 @@ void RawImageSource::colorSpaceConversion_ (Imagefloat* im, const ColorManagemen #pragma omp for schedule(static) #endif - for ( int h = 0; h < im->getHeight(); ++h ) { + for (int h = 0; h < im->getHeight(); ++h) { float *p = buffer.data, *pR = im->r(h), *pG = im->g(h), *pB = im->b(h); // Apply pre-processing - for ( int w = 0; w < im->getWidth(); ++w ) { + for (int w = 0; w < im->getWidth(); ++w) { float r = *(pR++); float g = *(pG++); float b = *(pB++); @@ -3258,7 +3261,7 @@ void RawImageSource::colorSpaceConversion_ (Imagefloat* im, const ColorManagemen pG = im->g(h); pB = im->b(h); - for ( int w = 0; w < im->getWidth(); ++w ) { + for (int w = 0; w < im->getWidth(); ++w) { float r, g, b, hr = 0.f, hg = 0.f, hb = 0.f; @@ -3325,9 +3328,9 @@ void RawImageSource::colorSpaceConversion_ (Imagefloat* im, const ColorManagemen // to a small space such as sRGB we may end up with negative values and values larger than max. if (!working_space_is_prophoto) { //convert from Prophoto to XYZ - float x = (toxyz[0][0] * r + toxyz[0][1] * g + toxyz[0][2] * b ) ; - float y = (toxyz[1][0] * r + toxyz[1][1] * g + toxyz[1][2] * b ) ; - float z = (toxyz[2][0] * r + toxyz[2][1] * g + toxyz[2][2] * b ) ; + float x = (toxyz[0][0] * r + toxyz[0][1] * g + toxyz[0][2] * b) ; + float y = (toxyz[1][0] * r + toxyz[1][1] * g + toxyz[1][2] * b) ; + float z = (toxyz[2][0] * r + toxyz[2][1] * g + toxyz[2][2] * b) ; //convert from XYZ to cmp.working (sRGB...Adobe...Wide..) r = ((torgb[0][0] * x + torgb[0][1] * y + torgb[0][2] * z)) ; g = ((torgb[1][0] * x + torgb[1][1] * y + torgb[1][2] * z)) ; @@ -3404,9 +3407,7 @@ void RawImageSource::HLRecovery_blend(float* rin, float* gin, float* bin, int wi constexpr float trans[ColorCount][ColorCount] = { { 1, 1, 1 }, { 1.7320508, -1.7320508, 0 }, { -1, -1, 2 } }; constexpr float itrans[ColorCount][ColorCount] = { { 1, 0.8660254, -0.5 }, { 1, -0.8660254, -0.5 }, { 1, 0, 1 } }; -#define FOREACHCOLOR for (int c=0; c < ColorCount; c++) - - float minpt = min(hlmax[0], hlmax[1], hlmax[2]); //min of the raw clip points + float minpt = rtengine::min(hlmax[0], hlmax[1], hlmax[2]); //min of the raw clip points //float maxpt=max(hlmax[0],hlmax[1],hlmax[2]);//max of the raw clip points //float medpt=hlmax[0]+hlmax[1]+hlmax[2]-minpt-maxpt;//median of the raw clip points float maxave = (hlmax[0] + hlmax[1] + hlmax[2]) / 3; //ave of the raw clip points @@ -3416,7 +3417,9 @@ void RawImageSource::HLRecovery_blend(float* rin, float* gin, float* bin, int wi const float satthresh = 0.5; float clip[3]; - FOREACHCOLOR clip[c] = min(maxave, hlmax[c]); + for (int c = 0; c < ColorCount; ++c) { + clip[c] = rtengine::min(maxave, hlmax[c]); + } // Determine the maximum level (clip) of all channels const float clippt = clipthresh * maxval; @@ -3433,20 +3436,20 @@ void RawImageSource::HLRecovery_blend(float* rin, float* gin, float* bin, int wi rgb[2] = bin[col]; // If no channel is clipped, do nothing on pixel - int c; + int cc; - for (c = 0; c < ColorCount; c++) { - if (rgb[c] > clippt) { + for (cc = 0; cc < ColorCount; ++cc) { + if (rgb[cc] > clippt) { break; } } - if (c == ColorCount) { + if (cc == ColorCount) { continue; } // Initialize cam with raw input [0] and potentially clipped input [1] - FOREACHCOLOR { + for (int c = 0; c < ColorCount; ++c) { lratio += min(rgb[c], clip[c]); cam[0][c] = rgb[c]; cam[1][c] = min(cam[0][c], maxval); @@ -3454,7 +3457,7 @@ void RawImageSource::HLRecovery_blend(float* rin, float* gin, float* bin, int wi // Calculate the lightness correction ratio (chratio) for (int i = 0; i < 2; i++) { - FOREACHCOLOR { + for (int c = 0; c < ColorCount; ++c) { lab[i][c] = 0; for (int j = 0; j < ColorCount; j++) @@ -3470,7 +3473,7 @@ void RawImageSource::HLRecovery_blend(float* rin, float* gin, float* bin, int wi } } - chratio = (sqrt(sum[1] / sum[0])); + chratio = std::sqrt(sum[1] / sum[0]); // Apply ratio to lightness in LCH space for (int c = 1; c < ColorCount; c++) { @@ -3478,7 +3481,7 @@ void RawImageSource::HLRecovery_blend(float* rin, float* gin, float* bin, int wi } // Transform back from LCH to RGB - FOREACHCOLOR { + for (int c = 0; c < ColorCount; ++c) { cam[0][c] = 0; for (int j = 0; j < ColorCount; j++) @@ -3486,7 +3489,9 @@ void RawImageSource::HLRecovery_blend(float* rin, float* gin, float* bin, int wi cam[0][c] += itrans[c][j] * lab[0][j]; } } - FOREACHCOLOR rgb[c] = cam[0][c] / ColorCount; + for (int c = 0; c < ColorCount; ++c) { + rgb[c] = cam[0][c] / ColorCount; + } // Copy converted pixel back if (rin[col] > fixpt) { @@ -3540,7 +3545,7 @@ void RawImageSource::HLRecovery_Luminance (float* rin, float* gin, float* bin, f double Ho = 2 * bo - ro - go; if (r != g && g != b) { - double ratio = sqrt ((Co * Co + Ho * Ho) / (C * C + H * H)); + double ratio = std::sqrt ((Co * Co + Ho * Ho) / (C * C + H * H)); C *= ratio; H *= ratio; } @@ -3618,7 +3623,7 @@ void RawImageSource::HLRecovery_CIELab (float* rin, float* gin, float* bin, floa //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -void RawImageSource::hlRecovery (const std::string &method, float* red, float* green, float* blue, int width, float* hlmax ) +void RawImageSource::hlRecovery (const std::string &method, float* red, float* green, float* blue, int width, float* hlmax) { if (method == "Luminance") { @@ -3659,8 +3664,8 @@ void RawImageSource::getAutoExpHistogram (LUTu & histogram, int& histcompr) if (ri->getSensorType() == ST_BAYER) { // precalculate factors to avoid expensive per pixel calculations - float refwb0 = refwb[ri->FC(i, start)]; - float refwb1 = refwb[ri->FC(i, start + 1)]; + float refwb0 = refwb[ri->FC(i, start)]; + float refwb1 = refwb[ri->FC(i, start + 1)]; int j; for (j = start; j < end - 1; j += 2) { @@ -3668,17 +3673,17 @@ void RawImageSource::getAutoExpHistogram (LUTu & histogram, int& histcompr) tmphistogram[(int)(refwb1 * rawData[i][j + 1])] += 4; } - if(j < end) { + if (j < end) { tmphistogram[(int)(refwb0 * rawData[i][j])] += 4; } } else if (ri->getSensorType() == ST_FUJI_XTRANS) { // precalculate factors to avoid expensive per pixel calculations - float refwb0 = refwb[ri->XTRANSFC(i, start)]; - float refwb1 = refwb[ri->XTRANSFC(i, start + 1)]; - float refwb2 = refwb[ri->XTRANSFC(i, start + 2)]; - float refwb3 = refwb[ri->XTRANSFC(i, start + 3)]; - float refwb4 = refwb[ri->XTRANSFC(i, start + 4)]; - float refwb5 = refwb[ri->XTRANSFC(i, start + 5)]; + float refwb0 = refwb[ri->XTRANSFC(i, start)]; + float refwb1 = refwb[ri->XTRANSFC(i, start + 1)]; + float refwb2 = refwb[ri->XTRANSFC(i, start + 2)]; + float refwb3 = refwb[ri->XTRANSFC(i, start + 3)]; + float refwb4 = refwb[ri->XTRANSFC(i, start + 4)]; + float refwb5 = refwb[ri->XTRANSFC(i, start + 5)]; int j; for (j = start; j < end - 5; j += 6) { @@ -3754,7 +3759,7 @@ void RawImageSource::getRAWHistogram (LUTu & histRedRaw, LUTu & histGreenRaw, LU #ifdef _OPENMP int numThreads; // reduce the number of threads under certain conditions to avoid overhead of too many critical regions - numThreads = sqrt((((H - 2 * border) * (W - 2 * border)) / 262144.f)); + numThreads = std::sqrt((((H - 2 * border) * (W - 2 * border)) / 262144.f)); numThreads = std::min(std::max(numThreads, 1), omp_get_max_threads()); #pragma omp parallel num_threads(numThreads) @@ -3788,23 +3793,23 @@ void RawImageSource::getRAWHistogram (LUTu & histRedRaw, LUTu & histGreenRaw, LU if (ri->getSensorType() == ST_BAYER) { int j; int c1 = FC(i, start); - c1 = ( fourColours && c1 == 1 && !(i & 1) ) ? 3 : c1; + c1 = (fourColours && c1 == 1 && !(i & 1)) ? 3 : c1; int c2 = FC(i, start + 1); - c2 = ( fourColours && c2 == 1 && !(i & 1) ) ? 3 : c2; + c2 = (fourColours && c2 == 1 && !(i & 1)) ? 3 : c2; for (j = start; j < end - 1; j += 2) { tmphist[c1][(int)(ri->data[i][j] * scale)]++; tmphist[c2][(int)(ri->data[i][j + 1] * scale)]++; } - if(j < end) { // last pixel of row if width is odd + if (j < end) { // last pixel of row if width is odd tmphist[c1][(int)(ri->data[i][j] * scale)]++; } } else if (ri->get_colors() == 1) { for (int j = start; j < end; j++) { tmphist[0][(int)(ri->data[i][j] * scale)]++; } - } else if(ri->getSensorType() == ST_FUJI_XTRANS) { + } else if (ri->getSensorType() == ST_FUJI_XTRANS) { for (int j = start; j < end - 1; j += 2) { int c = ri->XTRANSFC(i, j); tmphist[c][(int)(ri->data[i][j] * scale)]++; @@ -3842,7 +3847,7 @@ void RawImageSource::getRAWHistogram (LUTu & histRedRaw, LUTu & histGreenRaw, LU return f > 0.f ? (f < 1.f ? 1 : std::min(int(f), 255)) : 0; }; - for(int i = 0; i < histoSize; i++) { + for (int i = 0; i < histoSize; i++) { int idx = getidx(0, i); histRedRaw[idx] += hist[0][i]; @@ -3864,11 +3869,11 @@ void RawImageSource::getRAWHistogram (LUTu & histRedRaw, LUTu & histGreenRaw, LU for (int i = 0; i < 256; i++) { histGreenRaw[i] >>= 1; } - else if(ri->getSensorType() == ST_FUJI_XTRANS) // since Xtrans has 2.5 as many greens, correct for it + else if (ri->getSensorType() == ST_FUJI_XTRANS) // since Xtrans has 2.5 as many greens, correct for it for (int i = 0; i < 256; i++) { histGreenRaw[i] = (histGreenRaw[i] * 2) / 5; } - else if(ri->get_colors() == 1) { // monochrome sensor => set all histograms equal + else if (ri->get_colors() == 1) { // monochrome sensor => set all histograms equal histGreenRaw += histRedRaw; histBlueRaw += histRedRaw; } @@ -3881,7 +3886,7 @@ void RawImageSource::getRowStartEnd (int x, int &start, int &end) { if (fuji) { int fw = ri->get_FujiWidth(); - start = ABS(fw - x) + border; + start = std::abs(fw - x) + border; end = min(H + W - fw - x, fw + x) - border; } else { start = border; @@ -3889,7 +3894,1726 @@ void RawImageSource::getRowStartEnd (int x, int &start, int &end) } } -//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + +static void histoxyY(int bfhitc, int bfwitc, const array2D & xc, const array2D & yc, const array2D & Yc, LUTf &xxx, LUTf &yyy, LUTf &YYY, LUTu &histxy) +{ + //calculate histogram x y in a range of 190 colors + //this "choice" are guided by generally colors who are in nature skin, sky, etc. in those cases "steps" are small + // of course we can change to be more precise +#ifdef _OPENMP + #pragma omp parallel +#endif + { + LUTu histxythr(histxy.getSize()); + histxythr.clear(); + LUTf xxxthr(xxx.getSize()); + xxxthr.clear(); + LUTf yyythr(yyy.getSize()); + yyythr.clear(); + LUTf YYYthr(YYY.getSize()); + YYYthr.clear(); +#ifdef _OPENMP + #pragma omp for schedule(dynamic, 4) nowait +#endif + for (int y = 0; y < bfhitc ; y++) { + for (int x = 0; x < bfwitc ; x++) { + int nh = -1; + if (xc[y][x] < 0.12f && xc[y][x] > 0.03f && yc[y][x] > 0.1f) { // near Prophoto + if (yc[y][x] < 0.2f) { + nh = 0; + //blue hard + } else if (yc[y][x] < 0.3f) { + nh = 1; + //blue + } else if (yc[y][x] < 0.4f) { + nh = 2; + + } else if (yc[y][x] < 0.5f) { + //blue green + nh = 3; + } else if (yc[y][x] < 0.6f) { + nh = 4; + } else if (yc[y][x] < 0.82f) { + //green + nh = 5; + } + } else if (xc[y][x] < 0.24f && yc[y][x] > 0.05f) { + if (yc[y][x] < 0.2f) { + nh = 6; + } else if (yc[y][x] < 0.3f) { + nh = 7; + } else if (yc[y][x] < 0.4f) { + nh = 8; + } else if (yc[y][x] < 0.5f) { + nh = 9; + } else if (yc[y][x] < 0.6f) { + nh = 10; + } else if (yc[y][x] < 0.75f) { + nh = 11; + } + } else if (xc[y][x] < 0.28f && yc[y][x] > 0.1f) {//blue sky and other + if (yc[y][x] < 0.2f) { + nh = 12; + } else if (yc[y][x] < 0.25f) { + nh = 13; + } else if (yc[y][x] < 0.29f) { + nh = 14; + } else if (yc[y][x] < 0.33f) { + nh = 15; + } else if (yc[y][x] < 0.37f) { + nh = 16; + } else if (yc[y][x] < 0.4f) { + nh = 17; + } else if (yc[y][x] < 0.45f) { + nh = 18; + } else if (yc[y][x] < 0.5f) { + nh = 19; + } else if (yc[y][x] < 0.6f) { + nh = 20; + } else if (yc[y][x] < 0.75f) { + nh = 21; + } + } else if (xc[y][x] < 0.31f && yc[y][x] > 0.1f) {//near neutral others + if (yc[y][x] < 0.2f) { + nh = 22; + } else if (yc[y][x] < 0.24f) { + nh = 23; + } else if (yc[y][x] < 0.29f) { + nh = 24; + } else if (yc[y][x] < 0.32f) { + nh = 25; + } else if (yc[y][x] < 0.36f) { + nh = 26; + } else if (yc[y][x] < 0.4f) { + nh = 27; + } else if (yc[y][x] < 0.5f) { + nh = 28; + } else if (yc[y][x] < 0.7f) { + nh = 29; + } + } else if (xc[y][x] < 0.325f && yc[y][x] > 0.1f) {//neutral 34 + if (yc[y][x] < 0.2f) { + nh = 30; + } else if (yc[y][x] < 0.24f) { + nh = 31; + } else if (yc[y][x] < 0.29f) { + nh = 32; + } else if (yc[y][x] < 0.32f) { + nh = 33; + } else if (yc[y][x] < 0.33f) { + nh = 34; + } else if (yc[y][x] < 0.335f) { + nh = 35; + } else if (yc[y][x] < 0.34f) { + nh = 36; + } else if (yc[y][x] < 0.35f) { + nh = 37; + } else if (yc[y][x] < 0.37f) { + nh = 38; + } else if (yc[y][x] < 0.4f) { + nh = 39; + } else if (yc[y][x] < 0.45f) { + nh = 40; + } else if (yc[y][x] < 0.5f) { + nh = 41; + } else if (yc[y][x] < 0.55f) { + nh = 42; + } else if (yc[y][x] < 0.7f) { + nh = 43; + } + } else if (xc[y][x] < 0.335f && yc[y][x] > 0.1f) {//neutral + if (yc[y][x] < 0.2f) { + nh = 44; + } else if (yc[y][x] < 0.24f) { + nh = 45; + } else if (yc[y][x] < 0.29f) { + nh = 46; + } else if (yc[y][x] < 0.32f) { + nh = 47; + } else if (yc[y][x] < 0.33f) { + nh = 48; + } else if (yc[y][x] < 0.335f) { + nh = 49; + } else if (yc[y][x] < 0.34f) { + nh = 50; + } else if (yc[y][x] < 0.345f) { + nh = 51; + } else if (yc[y][x] < 0.35f) { + nh = 52; + } else if (yc[y][x] < 0.355f) { + nh = 53; + } else if (yc[y][x] < 0.36f) { + nh = 54; + } else if (yc[y][x] < 0.37f) { + nh = 55; + } else if (yc[y][x] < 0.38f) { + nh = 56; + } else if (yc[y][x] < 0.4f) { + nh = 57; + } else if (yc[y][x] < 0.45f) { + nh = 58; + } else if (yc[y][x] < 0.5f) { + nh = 59; + } else if (yc[y][x] < 0.55f) { + nh = 60; + } else if (yc[y][x] < 0.7f) { + nh = 61; + } + } else if (xc[y][x] < 0.340f && yc[y][x] > 0.1f) {//neutral + if (yc[y][x] < 0.2f) { + nh = 62; + } else if (yc[y][x] < 0.24f) { + nh = 63; + } else if (yc[y][x] < 0.29f) { + nh = 64; + } else if (yc[y][x] < 0.32f) { + nh = 65; + } else if (yc[y][x] < 0.325f) { + nh = 66; + } else if (yc[y][x] < 0.33f) { + nh = 67; + } else if (yc[y][x] < 0.335f) { + nh = 68; + } else if (yc[y][x] < 0.34f) { + nh = 69; + } else if (yc[y][x] < 0.345f) { + nh = 70; + } else if (yc[y][x] < 0.35f) { + nh = 71; + } else if (yc[y][x] < 0.355f) { + nh = 72; + } else if (yc[y][x] < 0.36f) { + nh = 73; + } else if (yc[y][x] < 0.37f) { + nh = 74; + } else if (yc[y][x] < 0.38f) { + nh = 75; + } else if (yc[y][x] < 0.4f) { + nh = 76; + } else if (yc[y][x] < 0.45f) { + nh = 77; + } else if (yc[y][x] < 0.5f) { + nh = 78; + } else if (yc[y][x] < 0.55f) { + nh = 79; + } else if (yc[y][x] < 0.7f) { + nh = 80; + } + } else if (xc[y][x] < 0.345f && yc[y][x] > 0.1f) {//neutral 37 + if (yc[y][x] < 0.2f) { + nh = 81; + } else if (yc[y][x] < 0.24f) { + nh = 82; + } else if (yc[y][x] < 0.29f) { + nh = 83; + } else if (yc[y][x] < 0.32f) { + nh = 84; + } else if (yc[y][x] < 0.33f) { + nh = 85; + } else if (yc[y][x] < 0.335f) { + nh = 86; + } else if (yc[y][x] < 0.34f) { + nh = 87; + } else if (yc[y][x] < 0.345f) { + nh = 88; + } else if (yc[y][x] < 0.35f) { + nh = 89; + } else if (yc[y][x] < 0.355f) { + nh = 90; + } else if (yc[y][x] < 0.36f) { + nh = 91; + } else if (yc[y][x] < 0.37f) { + nh = 92; + } else if (yc[y][x] < 0.38f) { + nh = 93; + } else if (yc[y][x] < 0.39f) { + nh = 94; + } else if (yc[y][x] < 0.4f) { + nh = 95; + } else if (yc[y][x] < 0.42f) { + nh = 96; + } else if (yc[y][x] < 0.45f) { + nh = 97; + } else if (yc[y][x] < 0.48f) { + nh = 98; + } else if (yc[y][x] < 0.5f) { + nh = 99; + } else if (yc[y][x] < 0.55f) { + nh = 100; + } else if (yc[y][x] < 0.65f) { + nh = 101; + } + } else if (xc[y][x] < 0.355f && yc[y][x] > 0.1f) {//neutral 37 + if (yc[y][x] < 0.2f) { + nh = 102; + } else if (yc[y][x] < 0.24f) { + nh = 103; + } else if (yc[y][x] < 0.29f) { + nh = 104; + } else if (yc[y][x] < 0.32f) { + nh = 105; + } else if (yc[y][x] < 0.33f) { + nh = 106; + } else if (yc[y][x] < 0.335f) { + nh = 107; + } else if (yc[y][x] < 0.34f) { + nh = 108; + } else if (yc[y][x] < 0.345f) { + nh = 109; + } else if (yc[y][x] < 0.35f) { + nh = 110; + } else if (yc[y][x] < 0.355f) { + nh = 111; + } else if (yc[y][x] < 0.36f) { + nh = 112; + } else if (yc[y][x] < 0.37f) { + nh = 113; + } else if (yc[y][x] < 0.38f) { + nh = 114; + } else if (yc[y][x] < 0.39f) { + nh = 115; + } else if (yc[y][x] < 0.4f) { + nh = 116; + } else if (yc[y][x] < 0.42f) { + nh = 117; + } else if (yc[y][x] < 0.45f) { + nh = 118; + } else if (yc[y][x] < 0.48f) { + nh = 119; + } else if (yc[y][x] < 0.5f) { + nh = 120; + } else if (yc[y][x] < 0.55f) { + nh = 121; + } else if (yc[y][x] < 0.65f) { + nh = 122; + } + } else if (xc[y][x] < 0.365f && yc[y][x] > 0.15f) { //0.4 + if (yc[y][x] < 0.2f) { + nh = 123; + } else if (yc[y][x] < 0.24f) { + nh = 124; + } else if (yc[y][x] < 0.29f) { + nh = 125; + } else if (yc[y][x] < 0.32f) { + nh = 126; + } else if (yc[y][x] < 0.33f) { + nh = 127; + } else if (yc[y][x] < 0.34f) { + nh = 128; + } else if (yc[y][x] < 0.35f) { + nh = 129; + } else if (yc[y][x] < 0.36f) { + nh = 130; + } else if (yc[y][x] < 0.37f) { + nh = 131; + } else if (yc[y][x] < 0.38f) { + nh = 132; + } else if (yc[y][x] < 0.39f) { + nh = 133; + } else if (yc[y][x] < 0.4f) { + nh = 134; + } else if (yc[y][x] < 0.42f) { + nh = 135; + } else if (yc[y][x] < 0.45f) { + nh = 136; + } else if (yc[y][x] < 0.5f) { + nh = 137; + } else if (yc[y][x] < 0.55f) { + nh = 138; + } else if (yc[y][x] < 0.63f) { + nh = 139; + } + } else if (xc[y][x] < 0.405f && yc[y][x] > 0.15f) {//45 + if (yc[y][x] < 0.2f) { + nh = 140; + } else if (yc[y][x] < 0.24f) { + nh = 141; + } else if (yc[y][x] < 0.29f) { + nh = 142; + } else if (yc[y][x] < 0.32f) { + nh = 143; + } else if (yc[y][x] < 0.34f) { + nh = 144; + } else if (yc[y][x] < 0.37f) { + nh = 145; + } else if (yc[y][x] < 0.4f) { + nh = 146; + } else if (yc[y][x] < 0.45f) { + nh = 147; + } else if (yc[y][x] < 0.5f) { + nh = 148; + } else if (yc[y][x] < 0.55f) { + nh = 149; + } else if (yc[y][x] < 0.6f) { + nh = 150; + } + } else if (xc[y][x] < 0.445f && yc[y][x] > 0.15f) {//45 + if (yc[y][x] < 0.2f) { + nh = 151; + } else if (yc[y][x] < 0.24f) { + nh = 152; + } else if (yc[y][x] < 0.29f) { + nh = 153; + } else if (yc[y][x] < 0.32f) { + nh = 154; + } else if (yc[y][x] < 0.34f) { + nh = 155; + } else if (yc[y][x] < 0.37f) { + nh = 156; + } else if (yc[y][x] < 0.4f) { + nh = 157; + } else if (yc[y][x] < 0.45f) { + nh = 158; + } else if (yc[y][x] < 0.5f) { + nh = 159; + } else if (yc[y][x] < 0.55f) { + nh = 160; + } else if (yc[y][x] < 0.58f) { + nh = 161; + } + } else if (xc[y][x] < 0.495f && yc[y][x] > 0.15f) { + if (yc[y][x] < 0.2f) { + nh = 162; + } else if (yc[y][x] < 0.24f) { + nh = 163; + } else if (yc[y][x] < 0.29f) { + nh = 164; + } else if (yc[y][x] < 0.32f) { + nh = 165; + } else if (yc[y][x] < 0.34f) { + nh = 166; + } else if (yc[y][x] < 0.37f) { + nh = 167; + } else if (yc[y][x] < 0.4f) { + nh = 168; + } else if (yc[y][x] < 0.45f) { + nh = 169; + } else if (yc[y][x] < 0.5f) { + nh = 170; + } else if (yc[y][x] < 0.55f) { + nh = 171; + } + } else if (xc[y][x] < 0.545f && yc[y][x] > 0.15f) { + if (yc[y][x] < 0.2f) { + nh = 172; + } else if (yc[y][x] < 0.24f) { + nh = 173; + } else if (yc[y][x] < 0.29f) { + nh = 174; + } else if (yc[y][x] < 0.32f) { + nh = 175; + } else if (yc[y][x] < 0.34f) { + nh = 176; + } else if (yc[y][x] < 0.37f) { + nh = 177; + } else if (yc[y][x] < 0.4f) { + nh = 178; + } else if (yc[y][x] < 0.45f) { + nh = 179; + } else if (yc[y][x] < 0.5f) { + nh = 180; + } + } else if (xc[y][x] < 0.595f && yc[y][x] > 0.15f) { + if (yc[y][x] < 0.22f) { + nh = 181; + } else if (yc[y][x] < 0.25f) { + nh = 182; + } else if (yc[y][x] < 0.3f) { + nh = 183; + } else if (yc[y][x] < 0.35f) { + nh = 184; + } else if (yc[y][x] < 0.4f) { + nh = 185; + } else if (yc[y][x] < 0.45f) { + nh = 186; + } + } else if (xc[y][x] < 0.65f && yc[y][x] > 0.12f) { + if (yc[y][x] < 0.25f) { + nh = 187; + } else if (yc[y][x] < 0.3f) { + nh = 188; + } else if (yc[y][x] < 0.35f) { + nh = 189; + } else if (yc[y][x] < 0.45f) { + nh = 190; + } + } else if (xc[y][x] < 0.75f && yc[y][x] > 0.1f) { + nh = 191; + } + if (nh >= 0) { + histxythr[nh]++; + xxxthr[nh] += xc[y][x]; + yyythr[nh] += yc[y][x]; + YYYthr[nh] += Yc[y][x]; + } + } + } +#ifdef _OPENMP + #pragma omp critical +#endif + { + histxy += histxythr; + xxx += xxxthr; + yyy += yyythr; + YYY += YYYthr; + } + } +} + +float static studentXY(const array2D & YYcurr, const array2D & reffYY, int sizcurr, int Nc, int tt) +{ + //calculate Student coeff YY + float somcurrY = 0.f; + float somreffY = 0.f; + float somcurr2Y = 0.f; + float somreff2Y = 0.f; + + for (int i = 0; i < sizcurr; i++) { + somcurrY += YYcurr[i][tt]; + //sum observations first group + } + somcurrY *= 100.f; + + for (int i = 0; i < Nc; i++) { + somreffY += reffYY[i][tt]; + //sum observations second group + } + somreffY *= 100.f; + + for (int i = 0; i < sizcurr; i++) { + somcurr2Y += SQR(YYcurr[i][tt]); + //sum sqr observations first group + } + somcurr2Y *= SQR(100.f); + + for (int i = 0; i < Nc; i++) { + somreff2Y += SQR(reffYY[i][tt]); + //sum sqr observations second group + } + somreff2Y *= SQR(100.f); + + const float somsqueccurrY = somcurr2Y - SQR(somcurrY) / sizcurr; + //sum sqr differences first + const float somsquecreffY = somreff2Y - SQR(somreffY) / Nc; + //sum sqr differences second + + const float diviY = std::sqrt(((somsqueccurrY + somsquecreffY) * (1.f / sizcurr + 1.f / Nc)) / (sizcurr + Nc - 2)); + //divisor student + const float numerY = somcurrY / sizcurr - somreffY / Nc; + //numerator student + + return numerY / diviY ; + //student coeeficient +} + +void RawImageSource::ItcWB(bool extra, double &tempref, double &greenref, double &tempitc, double &greenitc, float &studgood, array2D &redloc, array2D &greenloc, array2D &blueloc, int bfw, int bfh, double &avg_rm, double &avg_gm, double &avg_bm, const ColorManagementParams &cmp, const RAWParams &raw, const WBParams & wbpar) +{ + /* + Copyright (c) Jacques Desmis 6 - 2018 jdesmis@gmail.com + Copyright (c) Ingo Weyrich 3 - 2020 (heckflosse67@gmx.de) + + This algorithm try to find temperature correlation between 20 to 201 color between 201 spectral color and about 20 to 55 color found in the image between 192, I just found the idea in the web "correlate with chroma" instead of RGB grey point,but I don't use any algo found on the web. + + I have test many many algorithms to find the first one that work :) + Probably (sure) there are improvement to do... + + I have create a table temperature with temp and white point with 118 values between 2000K and 12000K we can obviously change these values, more...with different steps + I have create a table for tint (green)with 134 values between 0.4 to 4. + I have create or recuparate and transformed 201 spectral colors from Colorchecker24, others color and my 468 colors target, or from web flowers, etc. with a step of 5nm, I think it is large enough. + I think this value of 201 is now complete: I tested correlation with 60, 90, 100, 120, 155...better student increase with number of color, but now it seems stabilized + Of course we can increase this number :) + + 1) for the current raw file we create a table for each temp of RGB multipliers + 2) then, I choose the "camera temp" to initialize calculation (why not) + 3) for this temp, I calculated XYZ values for the 201 spectral datas + 4) then I create for the image an "histogram", but for xyY (CIE 1931 color space or CIE 1964 (default)) + 5) for each pixel (in fact to accelerate only 1/5 for and 1/5 for y), I determine for each couple xy, the number of occurences, can be change by Itcwb_precis to 3 or 9 + 6) I sort this result in ascending order + 7) in option we can sort in another manner to take into account chroma : chromax = x - white point x, chromay = y - white point y + 8) then I compare this result, with spectral datas found above in 3) with deltaE (limited to chroma) + 9) at this point we have xyY values that match Camera temp, and spectral datas associated + 10) then I recalculate RGB values from xyY histogram + 11) after, I vary temp, between 2000K to 12000K + 12) RGB values are recalculated from 10) with RGB multipliers, and then xyY are calculated for each temp + 13) spectral datas choose are recalculated with temp between 2000K to 12000K with matrix spectral calculation, that leads to xyY values + 14) I calculated for each couple xy, Student correlation (without Snedecor test) + 15) the good result, is the best correlation + 16) we have found the best temperature where color image and color references are correlate + 17) after we pass this value to improccoordinator + + 18) in a second part if camera green is out, I used an "extra" algorithm + 19) we make vary green between 2 limits (settings in option) + 20) between these green limits, we make slightly vary temp (settings in options) and recalculated RGB multipliers + 21) with this multipliers for the RGB color find in histogram we recalculate xyY + 22) we re-adjust references color for these xyY from 20) + 23) then find all Student correlation for each couple green / temp + 24) sort these Student values, and choose the minimum + 25) then for the 3 better couple "temp / green" choose the one where green is nearest from 1. + + Some variables or function are not used, keep in case of + I have test with cat02 but result are not stable enough ! why ??, therefore cat02 neutralized + This operation is done (actually) 100 times and compare Student coefficient, and keep the absolute minimum, We can probably optimize.... + But actually the goal is to find the good algorithm ! + + I think, this algo is very good in most cases :) ...to verify of course. + You can used it in images :flowers, landscape, portrait, skin, where illuminants are "normal" (daylight, blackbody) + You must avoid when illuminant is non standard (fluorescent, LED...) and also, when the subject is lost in the image (some target to generate profiles). + + You can change parameters in option.cc + Itcwb_thres : 34 by default ==> number of color used in final algorithm - between 10 and max 55 + Itcwb_sort : false by default, can improve algorithm if true, ==> sort value in something near chroma order, instead of histogram number + Itcwb_greenrange : 0 amplitude of green variation - between 0 to 2 + Itcwb_greendeltatemp : 1 - delta temp in green iterate loop for "extra" - between 0 to 4 + Itcwb_forceextra : false - if true force algorithm "extra" ("extra" is used when camera wbsettings are wrong) to all images + Itcwb_sizereference : 3 by default, can be set to 5 ==> size of reference color compare to size of histogram real color + itcwb_delta : 1 by default can be set between 0 to 5 ==> delta temp to build histogram xy - if camera temp is not probably good + itcwb_stdobserver10 : true by default - use standard observer 10°, false = standard observer 2° + itcwb_precis : 5 by default - can be set to 3 or 9 - 3 best sampling but more time...9 "old" settings - but low differences in times with 3 instead of 9 about twice time 160ms instead of 80ms for a big raw file + */ +// BENCHFUN + + TMatrix wprof = ICCStore::getInstance()->workingSpaceMatrix("sRGB"); + const float wp[3][3] = { + {static_cast(wprof[0][0]), static_cast(wprof[0][1]), static_cast(wprof[0][2])}, + {static_cast(wprof[1][0]), static_cast(wprof[1][1]), static_cast(wprof[1][2])}, + {static_cast(wprof[2][0]), static_cast(wprof[2][1]), static_cast(wprof[2][2])} + }; + + TMatrix wiprof = ICCStore::getInstance()->workingSpaceInverseMatrix("sRGB"); + //inverse matrix user select + const float wip[3][3] = { + {static_cast(wiprof[0][0]), static_cast(wiprof[0][1]), static_cast(wiprof[0][2])}, + {static_cast(wiprof[1][0]), static_cast(wiprof[1][1]), static_cast(wiprof[1][2])}, + {static_cast(wiprof[2][0]), static_cast(wiprof[2][1]), static_cast(wiprof[2][2])} + }; + + const int bfwitc = bfw; + const int bfhitc = bfh; + + typedef struct WbGreen { + double green; + float snedecor;//1. actually but put in case of confiance interval + } WbGreen; + //green (tint) values between 0.4 to 4.0 + constexpr WbGreen gree[134] = {//symmetric coefficient between 0.717 and 1.40 + {0.400, 1.f}, + {0.420, 1.f}, + {0.440, 1.f}, + {0.460, 1.f}, + {0.480, 1.f}, + {0.500, 1.f}, + {0.520, 1.f}, + {0.540, 1.f}, + {0.550, 1.f}, + {0.560, 1.f}, + {0.570, 1.f}, + {0.580, 1.f}, + {0.590, 1.f}, + {0.600, 1.f}, + {0.610, 1.f}, + {0.620, 1.f}, + {0.630, 1.f}, + {0.640, 1.f}, + {0.650, 1.f}, + {0.660, 1.f}, + {0.670, 1.f}, + {0.680, 1.f}, + {0.690, 1.f}, + {0.700, 1.f}, + {0.714, 1.f}, + {0.727, 1.f}, + {0.741, 1.f}, + {0.755, 1.f}, + {0.769, 1.f}, + {0.784, 1.f}, + {0.800, 1.f}, + {0.806, 1.f}, + {0.813, 1.f}, + {0.820, 1.f}, + {0.826, 1.f}, + {0.833, 1.f}, + {0.840, 1.f}, + {0.847, 1.f}, + {0.855, 1.f}, + {0.862, 1.f}, + {0.870, 1.f}, + {0.877, 1.f}, + {0.885, 1.f}, + {0.893, 1.f}, + {0.901, 1.f}, + {0.909, 1.f}, + {0.917, 1.f}, + {0.926, 1.f}, + {0.935, 1.f}, + {0.943, 1.f}, + {0.952, 1.f}, + {0.962, 1.f}, + {0.971, 1.f}, + {0.980, 1.f}, + {0.990, 1.f}, + {1.000, 1.f},//55 + {1.010, 1.f}, + {1.020, 1.f}, + {1.030, 1.f}, + {1.040, 1.f}, + {1.050, 1.f}, + {1.060, 1.f}, + {1.070, 1.f}, + {1.080, 1.f}, + {1.090, 1.f}, + {1.100, 1.f}, + {1.110, 1.f}, + {1.120, 1.f}, + {1.130, 1.f}, + {1.140, 1.f}, + {1.150, 1.f}, + {1.160, 1.f}, + {1.170, 1.f}, + {1.180, 1.f}, + {1.190, 1.f}, + {1.200, 1.f}, + {1.210, 1.f}, + {1.220, 1.f}, + {1.230, 1.f}, + {1.240, 1.f}, + {1.250, 1.f}, + {1.275, 1.f}, + {1.300, 1.f}, + {1.325, 1.f}, + {1.350, 1.f}, + {1.375, 1.f}, + {1.400, 1.f}, + {1.425, 1.f}, + {1.450, 1.f}, + {1.475, 1.f}, + {1.500, 1.f}, + {1.525, 1.f}, + {1.550, 1.f}, + {1.575, 1.f}, + {1.600, 1.f}, + {1.633, 1.f}, + {1.666, 1.f}, + {1.700, 1.f}, + {1.733, 1.f}, + {1.766, 1.f}, + {1.800, 1.f}, + {1.833, 1.f}, + {1.866, 1.f}, + {1.900, 1.f}, + {1.933, 1.f}, + {1.966, 1.f}, + {2.000, 1.f}, + {2.033, 1.f}, + {2.066, 1.f}, + {2.100, 1.f}, + {2.133, 1.f}, + {2.166, 1.f}, + {2.200, 1.f}, + {2.250, 1.f}, + {2.300, 1.f}, + {2.350, 1.f}, + {2.400, 1.f}, + {2.450, 1.f}, + {2.500, 1.f}, + {2.550, 1.f}, + {2.600, 1.f}, + {2.650, 1.f}, + {2.700, 1.f}, + {2.750, 1.f}, + {2.800, 1.f}, + {2.850, 1.f}, + {2.900, 1.f}, + {2.950, 1.f}, + {3.000, 1.f}, + {3.200, 1.f}, + {3.400, 1.f}, + {3.600, 1.f}, + {3.800, 1.f}, + {4.000, 1.f} + }; + const int N_g = sizeof(gree) / sizeof(gree[0]); //number of green + + typedef struct RangeGreen { + int begin; + int end; + } RangeGreen; + + constexpr RangeGreen Rangestandard = {24, 86}; + constexpr RangeGreen Rangeextended = {15, 93}; + const RangeGreen Rangemax = {0, N_g}; + + RangeGreen Rangegreenused; + + if (settings->itcwb_greenrange == 0) { + Rangegreenused = Rangestandard; + } else if (settings->itcwb_greenrange == 1) { + Rangegreenused = Rangeextended; + } else { + Rangegreenused = Rangemax; + } + + typedef struct WbTxyz { + double Tem; + double XX; + double ZZ; + } WbTxyz; + //we can change step to increase precision if need - also in Colortemp.cc with same changes + //I don't know how to pass this structure to Colortemp ! + // X and Z values calculate for each temp between 2000K to 12000K, so no result after 12000K ! + //of course we can change the step between each temp if need + constexpr WbTxyz Txyz[118] = {//temperature Xwb Zwb 118 values x wb and y wb are calculated after, Xwb and Ywb calculated with a spreadsheet + {2001., 1.273842, 0.145295}, + {2101., 1.244008, 0.167533}, + {2201., 1.217338, 0.190697}, + {2301., 1.193444, 0.214632}, + {2401., 1.171996, 0.239195}, + {2501., 1.152883, 0.264539}, + {2605., 1.134667, 0.290722}, + {2655., 1.126659, 0.303556}, + {2705., 1.119049, 0.316446}, + {2755., 1.111814, 0.329381}, + {2803., 1.105381, 0.342193}, + {2856., 1.098258, 0.355599}, + {2910., 1.091550, 0.369645}, + {2960., 1.085649, 0.382655}, + {3003., 1.080982, 0.394258}, + {3050., 1.075727, 0.406057}, + {3103., 1.070277, 0.419815}, + {3153., 1.065384, 0.432769}, + {3203., 1.060906, 0.446161}, + {3250., 1.056535, 0.457806}, + {3303., 1.052034, 0.471422}, + {3353., 1.047990, 0.484218}, + {3400., 1.044547, 0.496719}, + {3450., 1.040667, 0.508891}, + {3500., 1.037145, 0.521523}, + {3550., 1.033783, 0.534090}, + {3600., 1.030574, 0.546590}, + {3650., 1.027510, 0.559020}, + {3699., 1.024834, 0.571722}, + {3801., 1.019072, 0.596102}, + {3851., 1.016527, 0.608221}, + {3902., 1.014244, 0.621136}, + {3952., 1.011729, 0.632447}, + {4002., 0.996153, 0.609518}, + {4052., 0.993720, 0.620805}, + {4102., 0.993908, 0.631520}, + {4152., 0.989179, 0.643262}, + {4202., 0.989283, 0.653999}, + {4252., 0.985039, 0.665536}, + {4302., 0.985067, 0.676288}, + {4352., 0.981271, 0.687599}, + {4402., 0.981228, 0.698349}, + {4452., 0.977843, 0.709425}, + {4502., 0.977736, 0.720159}, + {4552., 0.974728, 0.730993}, + {4602., 0.974562, 0.741698}, + {4652., 0.971899, 0.752284}, + {4702., 0.971681, 0.762949}, + {4752., 0.969335, 0.773285}, + {4802., 0.969069, 0.783899}, + {4827., 0.967570, 0.788836}, + {4852., 0.967011, 0.793982}, + {4877., 0.966465, 0.799108}, + {4902., 0.965933, 0.804214}, + {4927., 0.965414, 0.809229}, + {4952., 0.964908, 0.814366}, + {4977., 0.964415, 0.819412}, + {5002., 0.963934, 0.824438}, + {5027., 0.963465, 0.829444}, + {5052., 0.963008, 0.834429}, + {5077., 0.962563, 0.839395}, + {5102., 0.962129, 0.844339}, + {5127., 0.961706, 0.849263}, + {5152., 0.961294, 0.854166}, + {5177., 0.960893, 0.859049}, + {5202., 0.960501, 0.863911}, + {5252., 0.959749, 0.873572}, + {5302., 0.959313, 0.883815}, + {5352., 0.958361, 0.892644}, + {5402., 0.957903, 0.902793}, + {5452., 0.957116, 0.911379}, + {5502., 0.956639, 0.921431}, + {5552., 0.956002, 0.929779}, + {5602., 0.955509, 0.939728}, + {5652., 0.955008, 0.947842}, + {5702., 0.954502, 0.957685}, + {5752., 0.954124, 0.965569}, + {5802., 0.953608, 0.975303}, + {5852., 0.953342, 0.982963}, + {5902., 0.952818, 0.992584}, + {5952., 0.952652, 1.000025}, + {6002., 0.952122, 1.009532}, + {6052., 0.952047, 1.016759}, + {6102., 0.951514, 1.026149}, + {6152., 0.951520, 1.033168}, + {6202., 0.950985, 1.042439}, + {6252., 0.951064, 1.049256}, + {6302., 0.950530, 1.058406}, + {6352., 0.950674, 1.065027}, + {6402., 0.950143, 1.074055}, + {6452., 0.950345, 1.080484}, + {6502., 0.950201, 1.088097}, + {6552., 0.950070, 1.095633}, + {6602., 0.949952, 1.103094}, + {6652., 0.949846, 1.110479}, + {6702., 0.949752, 1.119138}, + {6752., 0.949668, 1.125027}, + {6802., 0.949596, 1.132190}, + {6902., 0.949033, 1.147691}, + {7002., 0.949402, 1.160129}, + {7152., 0.949348, 1.180429}, + {7301., 0.948896, 1.201432}, + {7451., 0.949434, 1.219076}, + {7601., 0.949099, 1.239061}, + {7751., 0.949729, 1.255559}, + {7901., 0.949498, 1.274460}, + {8151., 0.950361, 1.300912}, + {8301., 0.950253, 1.318464}, + {8451., 0.950966, 1.332651}, + {8601., 0.950941, 1.349261}, + {8801., 0.951772, 1.367421}, + {9001., 0.951969, 1.387639}, + {9201., 0.952784, 1.404422}, + {9401., 0.953081, 1.423213}, + {9901., 0.954537, 1.464134}, + {10501., 0.956321, 1.508623}, + {11001., 0.957747, 1.541281}, + {12001., 0.960440, 1.601019} + }; + const int N_t = sizeof(Txyz) / sizeof(Txyz[0]); //number of temperature White point + constexpr int Nc = 201 + 1;//201 number of reference spectral colors, I think it is enough to retrieve good values + array2D Tx(N_t, Nc); + array2D Ty(N_t, Nc); + array2D Tz(N_t, Nc); + array2D Ta(N_t, Nc); + array2D Tb(N_t, Nc); + array2D TL(N_t, Nc); + double TX[Nc]; + double TY[Nc]; + double TZ[Nc]; + std::vector good_spectral(Nc, false); + + float rmm[N_t]; + float gmm[N_t]; + float bmm[N_t]; + + constexpr int siza = 192;//size of histogram + + //tempref and greenref are camera wb values. + // I used them by default to select good spectral values !! + tempref = rtengine::min(tempref, 12000.0); + + int repref = 0; + + for (int tt = 0; tt < N_t; tt++) { + if (Txyz[tt].Tem > tempref) { + repref = tt;//show the select temp + break; + } + } + + //calculate R G B multiplier in function illuminant and temperature + const bool isMono = (ri->getSensorType() == ST_FUJI_XTRANS && raw.xtranssensor.method == RAWParams::XTransSensor::getMethodString(RAWParams::XTransSensor::Method::MONO)) + || (ri->getSensorType() == ST_BAYER && raw.bayersensor.method == RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::MONO)); + for (int tt = 0; tt < N_t; ++tt) { + double r, g, b; + float rm, gm, bm; + ColorTemp WBiter = ColorTemp(Txyz[tt].Tem, greenitc, 1.f, "Custom"); + WBiter.getMultipliers(r, g, b); + rm = imatrices.cam_rgb[0][0] * r + imatrices.cam_rgb[0][1] * g + imatrices.cam_rgb[0][2] * b; + gm = imatrices.cam_rgb[1][0] * r + imatrices.cam_rgb[1][1] * g + imatrices.cam_rgb[1][2] * b; + bm = imatrices.cam_rgb[2][0] * r + imatrices.cam_rgb[2][1] * g + imatrices.cam_rgb[2][2] * b; + + const float new_pre_mul[4] = { ri->get_pre_mul(0) / rm, ri->get_pre_mul(1) / gm, ri->get_pre_mul(2) / bm, ri->get_pre_mul(3) / gm }; + float new_scale_mul[4]; + const float gain = calculate_scale_mul(new_scale_mul, new_pre_mul, c_white, cblacksom, isMono, ri->get_colors()); + + rm = new_scale_mul[0] / scale_mul[0] * gain; + gm = new_scale_mul[1] / scale_mul[1] * gain; + bm = new_scale_mul[2] / scale_mul[2] * gain; + rmm[tt] = rm / gm; + gmm[tt] = 1.f; + bmm[tt] = bm / gm; + //return rmm, gmm, bmm in function of temp + } + + struct hiss { + int histnum; + int index; + bool operator()(const hiss& lhis, const hiss& rhis) + { + return lhis.histnum < rhis.histnum; + } + + } ; + + //intermediate structure + struct chrom { + float chroxy_number; + float chroxy; + float chrox; + float chroy; + float Y; + int index; + int interest; + bool operator()(const chrom& lchro, const chrom& rchro) + { + return lchro.chroxy_number < rchro.chroxy_number; + } + + } ; + + LUTu histxy(siza); //number of values for each pair xy + histxy.clear(); + + LUTf xxx(siza);//for color references calculated ==> max in images "like histogram" + xxx.clear(); + LUTf yyy(siza); + yyy.clear(); + LUTf YYY(siza);//not used directly, but necessary to keep good range + YYY.clear(); + + bool separated = true; + int w = -1; + + array2D reff_spect_yy_camera(N_t, 2 * Nc + 2); + array2D reff_spect_xx_camera(N_t, 2 * Nc + 2); + + //here we select the good spectral color inside the 113 values + //call tempxy to calculate for 201 color references Temp and XYZ with cat02 + + ColorTemp::tempxy(separated, repref, Tx, Ty, Tz, Ta, Tb, TL, TX, TY, TZ, wbpar); //calculate chroma xy (xyY) for Z known colors on under 200 illuminants + + //find the good spectral values + //calculate xy reference spectral for tempref + for (int j = 0; j < Nc ; j++) { + reff_spect_xx_camera[j][repref] = TX[j] / (TX[j] + TY[j] + TZ[j]); // x from xyY + reff_spect_yy_camera[j][repref] = TY[j] / (TX[j] + TY[j] + TZ[j]); // y from xyY + } + + array2D xc(bfwitc, bfhitc); + array2D yc(bfwitc, bfhitc); + array2D Yc(bfwitc, bfhitc); + + const int deltarepref = settings->itcwb_delta; + + for (int nn = 0, drep = -deltarepref; nn <= 2; ++nn, drep += deltarepref) { + //three loop to refine color if temp camera is probably not very good + const int rep = rtengine::LIM(repref + drep, 0, N_t); + + //initialize calculation of xy current for tempref +#ifdef _OPENMP + #pragma omp parallel for +#endif + for (int y = 0; y < bfh ; ++y) { + for (int x = 0; x < bfw ; ++x) { + const float RR = rmm[rep] * redloc[y][x]; + const float GG = gmm[rep] * greenloc[y][x]; + const float BB = bmm[rep] * blueloc[y][x]; + Color::rgbxyY(RR, GG, BB, xc[y][x], yc[y][x], Yc[y][x], wp); + } + } + //histogram xy depend of temp...but in most cases D45 ..D65.. + //calculate for this image the mean values for each family of color, near histogram x y (number) + //xy vary from x 0..0.77 y 0..0.82 + //neutral values are near x=0.34 0.33 0.315 0.37 y =0.35 0.36 0.34 + //skin are about x 0.45 0.49 y 0.4 0.47 + //blue sky x=0.25 y=0.28 and x=0.29 y=0.32 + // step about 0.02 x 0.32 0.34 y= 0.34 0.36 skin -- sky x 0.24 0.30 y 0.28 0.32 + //big step about 0.2 + + histoxyY(bfhitc, bfwitc, xc, yc, Yc, xxx, yyy, YYY, histxy); + //return histogram x and y for each temp and in a range of 158 colors (siza) + } + + // free some memory + xc.free(); + yc.free(); + Yc.free(); + //calculate x y Y + const int sizcurrref = siza;//choice of number of correlate colors in image + array2D histcurrref(N_t, sizcurrref); + array2D xx_curref(N_t, sizcurrref); + array2D yy_curref(N_t, sizcurrref); + array2D YY_curref(N_t, sizcurrref); + array2D xx_curref_reduc(N_t, sizcurrref); + array2D yy_curref_reduc(N_t, sizcurrref); + array2D YY_curref_reduc(N_t, sizcurrref); + + hiss Wbhis[siza]; + + for (int nh = 0; nh < siza; nh++) { + Wbhis[nh].histnum = histxy[nh]; + Wbhis[nh].index = nh; + } + + //sort in ascending order + std::sort(Wbhis, Wbhis + siza, Wbhis[0]); + + int n1 = 0; + int n4 = 0; + int n15 = 0; + int n30 = 0; + //part to improve + //determined the number of colors who be used after + for (int nh = 0; nh < siza; nh++) { + if (Wbhis[nh].histnum < 30) { + n30++; //keep only existing color but avoid to small + if (Wbhis[nh].histnum < 15) { + n15++; //keep only existing color but avoid to small + if (Wbhis[nh].histnum < 4) { + n4++; //keep only existing color but avoid to small + if (Wbhis[nh].histnum < 1) { + n1++; //keep only existing color but avoid to small + } + } + } + } + } + + int ntr = n30; + + if (ntr > (siza - 25)) { + ntr = n15; //if to less elements 25 elements mini + } + + if (ntr > (siza - 23)) { + ntr = n4; //if to less elements 25 elements mini + } + + if (ntr > (siza - 20)) { + ntr = n1; //if to less elements 20 elements mini - normally never be used ! + } + + int sizcurr2ref = sizcurrref - ntr; + const int sizcu30 = sizcurrref - n30; + const int sizcu4 = rtengine::min(sizcu30, 55); + + chrom wbchro[sizcu4]; + const float swpr = Txyz[repref].XX + Txyz[repref].ZZ + 1.f; + const float xwpr = Txyz[repref].XX / swpr;//white point for tt in xy coordiantes + const float ywpr = 1.f / swpr; + + for (int i = 0; i < sizcu4; ++i) { //take the max values + histcurrref[i][repref] = Wbhis[siza - (i + 1)].histnum; + xx_curref[i][repref] = xxx[Wbhis[siza - (i + 1)].index] / histcurrref[i][repref]; + yy_curref[i][repref] = yyy[Wbhis[siza - (i + 1)].index] / histcurrref[i][repref]; + YY_curref[i][repref] = YYY[Wbhis[siza - (i + 1)].index] / histcurrref[i][repref]; + } + + float estimchrom = 0.f; + //estimate chromaticity for references + for (int nh = 0; nh < sizcu4; ++nh) { + const float chxy = std::sqrt(SQR(xx_curref[nh][repref] - xwpr) + SQR(yy_curref[nh][repref] - ywpr)); + wbchro[nh].chroxy_number = chxy * std::sqrt(histcurrref[nh][repref]); + wbchro[nh].chroxy = std::sqrt(chxy); + wbchro[nh].chrox = xx_curref[nh][repref]; + wbchro[nh].chroy = yy_curref[nh][repref]; + wbchro[nh].Y = YY_curref[nh][repref]; + wbchro[nh].index = nh; + estimchrom += chxy; + } + + estimchrom /= sizcu4; + if (settings->verbose) { + printf("estimchrom=%f\n", estimchrom); + } + if (settings->itcwb_sort) { //sort in ascending with chroma values + std::sort(wbchro, wbchro + sizcu4, wbchro[0]); + } + + const int maxval = rtengine::LIM(settings->itcwb_thres, 10, 55);//max values of color to find correllation + + sizcurr2ref = rtengine::min(sizcurr2ref, maxval); //keep about the biggest values, + + for (int i = 0; i < sizcurr2ref; ++i) { + //is condition chroxy necessary ? + if (wbchro[sizcu4 - (i + 1)].chrox > 0.1f && wbchro[sizcu4 - (i + 1)].chroy > 0.1f && wbchro[sizcu4 - (i + 1)].chroxy > 0.0f) { //suppress value too far from reference spectral + w++; + xx_curref_reduc[w][repref] = wbchro[sizcu4 - (i + 1)].chrox; + yy_curref_reduc[w][repref] = wbchro[sizcu4 - (i + 1)].chroy; + YY_curref_reduc[w][repref] = wbchro[sizcu4 - (i + 1)].Y; + } + } + + //calculate deltaE xx to find best values of spectrals datas - limited to chroma values + int maxnb = rtengine::LIM(settings->itcwb_sizereference, 1, 5); + + if (settings->itcwb_thres > 55) { + maxnb = 201 / settings->itcwb_thres; + } + + for (int nb = 1; nb <= maxnb; ++nb) { //max 5 iterations for Itcwb_thres=33, after trial 3 is good in most cases but in some cases 5 + for (int i = 0; i < w; ++i) { + float mindeltaE = 100000.f; + int kN = 0; + + for (int j = 0; j < Nc ; j++) { + if (!good_spectral[j]) { + const float deltaE = SQR(xx_curref_reduc[i][repref] - reff_spect_xx_camera[j][repref]) + SQR(yy_curref_reduc[i][repref] - reff_spect_yy_camera[j][repref]); + + if (deltaE < mindeltaE) { + mindeltaE = deltaE; + kN = j; + } + } + } + + good_spectral[kN] = true;//good spectral are spectral color that match color histogram xy + } + } + + // reuse some buffers + array2D& R_curref_reduc = xx_curref_reduc; + array2D& G_curref_reduc = yy_curref_reduc; + array2D& B_curref_reduc = YY_curref_reduc; + + //reconvert to RGB for "reduction" + for (int i = 0; i < w; i++) { + const float X = 65535.f * xx_curref_reduc[i][repref] * YY_curref_reduc[i][repref] / yy_curref_reduc[i][repref]; + const float Y = 65535.f * YY_curref_reduc[i][repref]; + const float Z = 65535.f * (1.f - xx_curref_reduc[i][repref] - yy_curref_reduc[i][repref]) * YY_curref_reduc[i][repref] / yy_curref_reduc[i][repref]; + float r, g, b; + Color::xyz2rgb(X, Y, Z, r, g, b, wip); + R_curref_reduc[i][repref] = r / rmm[repref]; + G_curref_reduc[i][repref] = g / gmm[repref]; + B_curref_reduc[i][repref] = b / bmm[repref]; + + } + +//end first part + + //Now begin real calculations + separated = false; + //recalculate histogram with good values and not estimated + ColorTemp::tempxy(separated, repref, Tx, Ty, Tz, Ta, Tb, TL, TX, TY, TZ, wbpar); //calculate chroma xy (xyY) for Z known colors on under 90 illuminants + //calculate x y Y + int sizcurr = siza;//choice of number of correlate colors in image + array2D xxyycurr_reduc(N_t, 2 * sizcurr); + array2D reff_spect_xxyy(N_t, 2 * Nc + 2); + array2D reff_spect_xxyy_prov(N_t, 2 * Nc + 2); + + float minstud = 100000.f; + int goodref = 1; + +//calculate x y z for each pixel with multiplier rmm gmm bmm + + for (int tt = 0; tt < N_t; ++tt) {//N_t + for (int i = 0; i < w; ++i) { + float unused; + + const float RR = rmm[tt] * R_curref_reduc[i][repref]; + const float GG = gmm[tt] * G_curref_reduc[i][repref]; + const float BB = bmm[tt] * B_curref_reduc[i][repref]; + Color::rgbxyY(RR, GG, BB, xxyycurr_reduc[2 * i][tt], xxyycurr_reduc[2 * i + 1][tt], unused, wp); + } + + for (int j = 0; j < Nc ; ++j) { + reff_spect_xxyy_prov[2 * j][tt] = Tx[j][tt] / (Tx[j][tt] + Ty[j][tt] + Tz[j][tt]); // x from xyY + reff_spect_xxyy_prov[2 * j + 1][tt] = Ty[j][tt] / (Tx[j][tt] + Ty[j][tt] + Tz[j][tt]); // y from xyY + } + + int kk = -1; + + for (int i = 0; i < Nc ; ++i) { + if (good_spectral[i]) { + kk++; + //we calculate now absolute chroma for each spectral color + reff_spect_xxyy[2 * kk][tt] = reff_spect_xxyy_prov[2 * i][tt]; + reff_spect_xxyy[2 * kk + 1][tt] = reff_spect_xxyy_prov[2 * i + 1][tt]; + } + } + + const float abstud = std::fabs(studentXY(xxyycurr_reduc, reff_spect_xxyy, 2 * w, 2 * kk, tt)); + + if (abstud < minstud) { // find the minimum Student + minstud = abstud; + goodref = tt; + } + } + + if (extra) {//always used because I made this choice, brings better results + struct Tempgreen { + float student; + int tempref; + int greenref; + bool operator()(const Tempgreen& ltg, const Tempgreen& rtg) + { + return ltg.student < rtg.student; + } + }; + Tempgreen Tgstud[N_g]; + + for (int i = 0; i < N_g; ++i) {//init variables with + Tgstud[i].student = 1000.f;//max value to initialize + Tgstud[i].tempref = 57;//5002K + Tgstud[i].greenref = 55;// 1.f + + } + + const int dgoodref = rtengine::min(settings->itcwb_greendeltatemp, 4); + const int scantempbeg = rtengine::max(goodref - (dgoodref + 1), 1); + const int scantempend = rtengine::min(goodref + dgoodref, N_t - 1); + for (int gr = Rangegreenused.begin; gr < Rangegreenused.end; ++gr) { + float minstudgr = 100000.f; + int goodrefgr = 1; + + for (int tt = scantempbeg; tt < scantempend; ++tt) { + double r, g, b; + ColorTemp WBiter(Txyz[tt].Tem, gree[gr].green, 1.f, "Custom"); + WBiter.getMultipliers(r, g, b); + float rm = imatrices.cam_rgb[0][0] * r + imatrices.cam_rgb[0][1] * g + imatrices.cam_rgb[0][2] * b; + float gm = imatrices.cam_rgb[1][0] * r + imatrices.cam_rgb[1][1] * g + imatrices.cam_rgb[1][2] * b; + float bm = imatrices.cam_rgb[2][0] * r + imatrices.cam_rgb[2][1] * g + imatrices.cam_rgb[2][2] * b; + //recalculate Multipliers now with good range of temp and green + + const float new_pre_mul[4] = { ri->get_pre_mul(0) / rm, ri->get_pre_mul(1) / gm, ri->get_pre_mul(2) / bm, ri->get_pre_mul(3) / gm }; + float new_scale_mul[4]; + const float gain = calculate_scale_mul(new_scale_mul, new_pre_mul, c_white, cblacksom, isMono, ri->get_colors()); + + rm = new_scale_mul[0] / scale_mul[0] * gain; + gm = new_scale_mul[1] / scale_mul[1] * gain; + bm = new_scale_mul[2] / scale_mul[2] * gain; + rmm[tt] = rm / gm; + gmm[tt] = 1.f; + bmm[tt] = bm / gm; + } + + + for (int tt = scantempbeg; tt < scantempend; ++tt) {//N_t + for (int i = 0; i < w; ++i) { + float unused; + + const float RR = rmm[tt] * R_curref_reduc[i][repref]; + const float GG = gmm[tt] * G_curref_reduc[i][repref]; + const float BB = bmm[tt] * B_curref_reduc[i][repref]; + Color::rgbxyY(RR, GG, BB, xxyycurr_reduc[2 * i][tt], xxyycurr_reduc[2 * i + 1][tt], unused, wp); + } + //recalculate xy spectral now with good range of temp and green + + for (int j = 0; j < Nc ; ++j) { + reff_spect_xxyy_prov[2 * j][tt] = Tx[j][tt] / (Tx[j][tt] + Ty[j][tt] + Tz[j][tt]); // x from xyY + reff_spect_xxyy_prov[2 * j + 1][tt] = Ty[j][tt] / (Tx[j][tt] + Ty[j][tt] + Tz[j][tt]); // y from xyY + } + + int kkg = -1; + for (int i = 0; i < Nc ; ++i) { + if (good_spectral[i]) { + kkg++; + reff_spect_xxyy[2 * kkg][tt] = reff_spect_xxyy_prov[2 * i][tt]; + reff_spect_xxyy[2 * kkg + 1][tt] = reff_spect_xxyy_prov[2 * i + 1][tt]; + } + } + //now we have good spectral datas + //claculate student correlation + const float abstudgr = std::fabs(studentXY(xxyycurr_reduc, reff_spect_xxyy, 2 * w, 2 * kkg, tt)); + + if (abstudgr < minstudgr) { // find the minimum Student + minstudgr = abstudgr; + goodrefgr = tt; + } + //found the values + Tgstud[gr].tempref = goodrefgr; + Tgstud[gr].greenref = gr; + Tgstud[gr].student = minstudgr; + + } + } + + std::sort(Tgstud, Tgstud + N_g, Tgstud[0]); + + //now search the value of green the nearest of 1 with a good student value + // I take the 3 first values + //I admit a symetrie in green coefiicient for rgb multiplier...probably not exactly true + //perhaps we can used a Snedecor test ? but why...at least we have confidence interval > 90% + int greengood; + int greengoodprov; + int goodrefprov; + float studprov; + const int goodref0 = Tgstud[0].tempref; + const int greengood0 = Tgstud[0].greenref - 55;//55 green = 1 + const float stud0 = Tgstud[0].student; + const int goodref1 = Tgstud[1].tempref; + const float stud1 = Tgstud[1].student; + const int greengood1 = Tgstud[1].greenref - 55; + const int goodref2 = Tgstud[2].tempref; + const int greengood2 = Tgstud[2].greenref - 55; + const float stud2 = Tgstud[2].student; + + if (std::fabs(greengood2) < std::fabs(greengood1)) { + greengoodprov = greengood2; + goodrefprov = goodref2; + studprov = stud2; + } else { + greengoodprov = greengood1; + goodrefprov = goodref1; + studprov = stud1; + + } + + if (std::fabs(greengoodprov) < std::fabs(greengood0)) { + goodref = goodrefprov; + greengood = greengoodprov + 55; + studgood = studprov; + + } else { + goodref = goodref0; + greengood = greengood0 + 55; + studgood = stud0; + } + + tempitc = Txyz[goodref].Tem; + greenitc = gree[greengood].green; + if (estimchrom < 0.025f) { + float ac = -2.40f * estimchrom + 0.06f;//small empirical correction, maximum 0.06 if chroma=0 for all image, currently for very low chroma +0.02 + greenitc += ac; + } + } + + avg_rm = 10000.f * rmm[goodref]; + avg_gm = 10000.f * gmm[goodref]; + avg_bm = 10000.f * bmm[goodref]; + + if (!extra) { + tempitc = Txyz[goodref].Tem; + } + //now we have temp green and student + if (settings->verbose) { + printf("ITCWB tempitc=%f gritc=%f stud=%f \n", tempitc, greenitc, studgood); + } +} + +void RawImageSource::WBauto(double & tempref, double & greenref, array2D &redloc, array2D &greenloc, array2D &blueloc, int bfw, int bfh, double & avg_rm, double & avg_gm, double & avg_bm, double & tempitc, double & greenitc, float & studgood, bool & twotimes, const WBParams & wbpar, int begx, int begy, int yEn, int xEn, int cx, int cy, const ColorManagementParams & cmp, const RAWParams & raw) +{ +// BENCHFUN + //auto white balance + //put green (tint) in reasonable limits for an Daylight illuminant + // avoid too bi or too low values + if (wbpar.method == "autitcgreen") { + bool extra = false; + + if (greenref > 0.5 && greenref < 1.3) {// 0.5 and 1.3 arbitraties values + greenitc = greenref; + + if (settings->itcwb_forceextra) { + extra = true; + } + } else { + greenitc = 1.; + extra = true; + } + + tempitc = 5000.; + + ItcWB(extra, tempref, greenref, tempitc, greenitc, studgood, redloc, greenloc, blueloc, bfw, bfh, avg_rm, avg_gm, avg_bm, cmp, raw, wbpar); + } +} + +void RawImageSource::getrgbloc(int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w) +{ +// BENCHFUN + //used by auto WB local to calculate red, green, blue in local region + int precision = 5; + if (settings->itcwb_precis == 5) { + precision = 5; + } else if (settings->itcwb_precis < 5) { + precision = 3; + } else if (settings->itcwb_precis > 5) { + precision = 9; + } + + const int bfw = W / precision + ((W % precision) > 0 ? 1 : 0);// 5 arbitrary value can be change to 3 or 9 ; + const int bfh = H / precision + ((H % precision) > 0 ? 1 : 0); + + if (! greenloc) { + greenloc(bfw, bfh); + } + + if (! redloc) { + redloc(bfw, bfh); + } + + if (! blueloc) { + blueloc(bfw, bfh); + } + + double avgL = 0.0; + //center data on normal values + int nn = 0; + +#ifdef _OPENMP + #pragma omp parallel for reduction(+:avgL, nn) +#endif + for (int i = 0; i < H; i ++) { + for (int j = 0; j < W; j++) { + const float LL = 0.299f * red[i][j] + 0.587f * green[i][j] + 0.114f * blue[i][j]; + avgL += static_cast(LL); + nn++; + } + } + avgL /= nn; + + double vari = 0.f; + int mm = 0; + +#ifdef _OPENMP + #pragma omp parallel for reduction(+:vari, mm) +#endif + for (int i = 0; i < H; i++) + for (int j = 0; j < W; j++) { + const float LL = 0.299f * red[i][j] + 0.587f * green[i][j] + 0.114f * blue[i][j]; + vari += SQR(LL - avgL); + mm++; + } + + const float sig = std::sqrt(vari / mm); + const float multip = 60000.f / (avgL + 2.f * sig); + //multip to put red, blue, green in a good range +#ifdef _OPENMP + #pragma omp parallel for +#endif + for (int i = 0; i < bfh; ++i) { + const int ii = i * precision; + if (ii < H) { + for (int j = 0, jj = 0; j < bfw; ++j, jj += precision) { + redloc[i][j] = red[ii][jj] * multip; + greenloc[i][j] = green[ii][jj] * multip; + blueloc[i][j] = blue[ii][jj] * multip; + } + } + } +} + +void RawImageSource::getAutoWBMultipliersitc(double & tempref, double & greenref, double & tempitc, double & greenitc, float &studgood, int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, double & rm, double & gm, double & bm, const WBParams & wbpar, const ColorManagementParams & cmp, const RAWParams & raw) +{ +// BENCHFUN + constexpr double clipHigh = 64000.0; + + if (ri->get_colors() == 1) { + rm = gm = bm = 1; + return; + } + + double avg_r = 0; + double avg_g = 0; + double avg_b = 0; + int rn = 0, gn = 0, bn = 0; + double avg_rm, avg_gm, avg_bm; + if (wbpar.method == "autold") { + if (fuji) { + for (int i = 32; i < H - 32; i++) { + int fw = ri->get_FujiWidth(); + int start = ABS(fw - i) + 32; + int end = min(H + W - fw - i, fw + i) - 32; + + for (int j = start; j < end; j++) { + if (ri->getSensorType() != ST_BAYER) { + double dr = CLIP(initialGain * (rawData[i][3 * j] )); + double dg = CLIP(initialGain * (rawData[i][3 * j + 1])); + double db = CLIP(initialGain * (rawData[i][3 * j + 2])); + + if (dr > clipHigh || dg > clipHigh || db > clipHigh) { + continue; + } + + avg_r += dr; + avg_g += dg; + avg_b += db; + rn = gn = ++bn; + } else { + int c = FC(i, j); + double d = CLIP(initialGain * (rawData[i][j])); + + if (d > clipHigh) { + continue; + } + + // Let's test green first, because they are more numerous + if (c == 1) { + avg_g += d; + gn++; + } else if (c == 0) { + avg_r += d; + rn++; + } else { /*if (c==2)*/ + avg_b += d; + bn++; + } + } + } + } + } else { + if (ri->getSensorType() != ST_BAYER) { + if (ri->getSensorType() == ST_FUJI_XTRANS) { + const double compval = clipHigh / initialGain; +#ifdef _OPENMP + #pragma omp parallel +#endif + { + double avg_c[3] = {0.0}; + int cn[3] = {0}; +#ifdef _OPENMP + #pragma omp for schedule(dynamic,16) nowait +#endif + + for (int i = 32; i < H - 32; i++) { + for (int j = 32; j < W - 32; j++) { + // each loop read 1 rgb triplet value + double d = rawData[i][j]; + + if (d > compval) { + continue; + } + + int c = ri->XTRANSFC(i, j); + avg_c[c] += d; + cn[c]++; + } + } + +#ifdef _OPENMP + #pragma omp critical +#endif + { + avg_r += avg_c[0]; + avg_g += avg_c[1]; + avg_b += avg_c[2]; + rn += cn[0]; + gn += cn[1]; + bn += cn[2]; + } + } + avg_r *= initialGain; + avg_g *= initialGain; + avg_b *= initialGain; + } else { + for (int i = 32; i < H - 32; i++) + for (int j = 32; j < W - 32; j++) { + // each loop read 1 rgb triplet value + + double dr = CLIP(initialGain * (rawData[i][3 * j] )); + double dg = CLIP(initialGain * (rawData[i][3 * j + 1])); + double db = CLIP(initialGain * (rawData[i][3 * j + 2])); + + if (dr > clipHigh || dg > clipHigh || db > clipHigh) { + continue; + } + + avg_r += dr; + rn++; + avg_g += dg; + avg_b += db; + } + + gn = rn; + bn = rn; + } + } else { + //determine GRBG coset; (ey,ex) is the offset of the R subarray + int ey, ex; + + if (ri->ISGREEN(0, 0)) { //first pixel is G + if (ri->ISRED(0, 1)) { + ey = 0; + ex = 1; + } else { + ey = 1; + ex = 0; + } + } else {//first pixel is R or B + if (ri->ISRED(0, 0)) { + ey = 0; + ex = 0; + } else { + ey = 1; + ex = 1; + } + } + + const double compval = clipHigh / initialGain; +#ifdef _OPENMP + #pragma omp parallel for reduction(+:avg_r,avg_g,avg_b,rn,gn,bn) schedule(dynamic,8) +#endif + + for (int i = 32; i < H - 32; i += 2) + for (int j = 32; j < W - 32; j += 2) { + //average each Bayer quartet component individually if non-clipped + double d[2][2]; + d[0][0] = rawData[i][j]; + d[0][1] = rawData[i][j + 1]; + d[1][0] = rawData[i + 1][j]; + d[1][1] = rawData[i + 1][j + 1]; + + if (d[ey][ex] <= compval) { + avg_r += d[ey][ex]; + rn++; + } + + if (d[1 - ey][ex] <= compval) { + avg_g += d[1 - ey][ex]; + gn++; + } + + if (d[ey][1 - ex] <= compval) { + avg_g += d[ey][1 - ex]; + gn++; + } + + if (d[1 - ey][1 - ex] <= compval) { + avg_b += d[1 - ey][1 - ex]; + bn++; + } + } + + avg_r *= initialGain; + avg_g *= initialGain; + avg_b *= initialGain; + + } + } + } + + if (wbpar.method == "autitcgreen") { + bool twotimes = false; + int precision = 5; + if (settings->itcwb_precis == 5) { + precision = 5; + } else if (settings->itcwb_precis < 5) { + precision = 3; + } else if (settings->itcwb_precis > 5) { + precision = 9; + } + + const int bfw = W / precision + ((W % precision) > 0 ? 1 : 0);// 5 arbitrary value can be change to 3 or 9 ; + const int bfh = H / precision + ((H % precision) > 0 ? 1 : 0); + WBauto(tempref, greenref, redloc, greenloc, blueloc, bfw, bfh, avg_rm, avg_gm, avg_bm, tempitc, greenitc, studgood, twotimes, wbpar, begx, begy, yEn, xEn, cx, cy, cmp, raw); + } + + redloc(0, 0); + greenloc(0, 0); + blueloc(0, 0); + + if (settings->verbose) { + printf ("AVG: %g %g %g\n", avg_r / std::max(1, rn), avg_g / std::max(1, gn), avg_b / std::max(1, bn)); + } + + if (wbpar.method == "autitcgreen") { + //not used + redAWBMul = rm = avg_rm * refwb_red; + greenAWBMul = gm = avg_gm * refwb_green; + blueAWBMul = bm = avg_bm * refwb_blue; + } else { + const double reds = avg_r / std::max(1, rn) * refwb_red; + const double greens = avg_g / std::max(1, gn) * refwb_green; + const double blues = avg_b / std::max(1, bn) * refwb_blue; + redAWBMul = rm = imatrices.rgb_cam[0][0] * reds + imatrices.rgb_cam[0][1] * greens + imatrices.rgb_cam[0][2] * blues; + greenAWBMul = gm = imatrices.rgb_cam[1][0] * reds + imatrices.rgb_cam[1][1] * greens + imatrices.rgb_cam[1][2] * blues; + blueAWBMul = bm = imatrices.rgb_cam[2][0] * reds + imatrices.rgb_cam[2][1] * greens + imatrices.rgb_cam[2][2] * blues; + } + +} + void RawImageSource::getAutoWBMultipliers (double &rm, double &gm, double &bm) { // BENCHFUN @@ -3922,12 +5646,12 @@ void RawImageSource::getAutoWBMultipliers (double &rm, double &gm, double &bm) if (fuji) { for (int i = 32; i < H - 32; i++) { int fw = ri->get_FujiWidth(); - int start = ABS(fw - i) + 32; + int start = std::abs(fw - i) + 32; int end = min(H + W - fw - i, fw + i) - 32; for (int j = start; j < end; j++) { if (ri->getSensorType() != ST_BAYER) { - double dr = CLIP(initialGain * (rawData[i][3 * j] )); + double dr = CLIP(initialGain * (rawData[i][3 * j] )); double dg = CLIP(initialGain * (rawData[i][3 * j + 1])); double db = CLIP(initialGain * (rawData[i][3 * j + 2])); @@ -3940,7 +5664,7 @@ void RawImageSource::getAutoWBMultipliers (double &rm, double &gm, double &bm) avg_b += db; rn = gn = ++bn; } else { - int c = FC( i, j); + int c = FC(i, j); double d = CLIP(initialGain * (rawData[i][j])); if (d > clipHigh) { @@ -3963,7 +5687,7 @@ void RawImageSource::getAutoWBMultipliers (double &rm, double &gm, double &bm) } } else { if (ri->getSensorType() != ST_BAYER) { - if(ri->getSensorType() == ST_FUJI_XTRANS) { + if (ri->getSensorType() == ST_FUJI_XTRANS) { const double compval = clipHigh / initialGain; #ifdef _OPENMP #pragma omp parallel @@ -4010,7 +5734,7 @@ void RawImageSource::getAutoWBMultipliers (double &rm, double &gm, double &bm) for (int j = 32; j < W - 32; j++) { // each loop read 1 rgb triplet value - double dr = CLIP(initialGain * (rawData[i][3 * j] )); + double dr = CLIP(initialGain * (rawData[i][3 * j] )); double dg = CLIP(initialGain * (rawData[i][3 * j + 1])); double db = CLIP(initialGain * (rawData[i][3 * j + 2])); @@ -4091,24 +5815,21 @@ void RawImageSource::getAutoWBMultipliers (double &rm, double &gm, double &bm) } } - if( settings->verbose ) { + if (settings->verbose) { printf ("AVG: %g %g %g\n", avg_r / std::max(1, rn), avg_g / std::max(1, gn), avg_b / std::max(1, bn)); } // return ColorTemp (pow(avg_r/rn, 1.0/6.0)*img_r, pow(avg_g/gn, 1.0/6.0)*img_g, pow(avg_b/bn, 1.0/6.0)*img_b); - double reds = avg_r / std::max(1, rn) * refwb_red; + double reds = avg_r / std::max(1, rn) * refwb_red; double greens = avg_g / std::max(1, gn) * refwb_green; - double blues = avg_b / std::max(1, bn) * refwb_blue; + double blues = avg_b / std::max(1, bn) * refwb_blue; - redAWBMul = rm = imatrices.rgb_cam[0][0] * reds + imatrices.rgb_cam[0][1] * greens + imatrices.rgb_cam[0][2] * blues; + redAWBMul = rm = imatrices.rgb_cam[0][0] * reds + imatrices.rgb_cam[0][1] * greens + imatrices.rgb_cam[0][2] * blues; greenAWBMul = gm = imatrices.rgb_cam[1][0] * reds + imatrices.rgb_cam[1][1] * greens + imatrices.rgb_cam[1][2] * blues; - blueAWBMul = bm = imatrices.rgb_cam[2][0] * reds + imatrices.rgb_cam[2][1] * greens + imatrices.rgb_cam[2][2] * blues; + blueAWBMul = bm = imatrices.rgb_cam[2][0] * reds + imatrices.rgb_cam[2][1] * greens + imatrices.rgb_cam[2][2] * blues; } -//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% - - ColorTemp RawImageSource::getSpotWB (std::vector &red, std::vector &green, std::vector &blue, int tran, double equal) { @@ -4118,7 +5839,7 @@ ColorTemp RawImageSource::getSpotWB (std::vector &red, std::vectorgetSensorType() != ST_BAYER) { - if(ri->getSensorType() == ST_FUJI_XTRANS) { + if (ri->getSensorType() == ST_FUJI_XTRANS) { int d[9][2] = {{0, 0}, { -1, -1}, { -1, 0}, { -1, 1}, {0, -1}, {0, 1}, {1, -1}, {1, 0}, {1, 1}}; for (size_t i = 0; i < red.size(); i++) { @@ -4131,7 +5852,7 @@ ColorTemp RawImageSource::getSpotWB (std::vector &red, std::vector= 0 && yv >= 0 && xv < W && yv < H) { + if (xv >= 0 && yv >= 0 && xv < W && yv < H) { if (ri->ISXTRANSRED(yv, xv)) { //RED rloc += (rawData[yv][xv]); rnbrs++; @@ -4169,7 +5890,7 @@ ColorTemp RawImageSource::getSpotWB (std::vector &red, std::vector 52500 || + if (initialGain * (rawData[yr][3 * xr] ) > 52500 || initialGain * (rawData[yg][3 * xg + 1]) > 52500 || initialGain * (rawData[yb][3 * xb + 2]) > 52500) { continue; @@ -4181,7 +5902,7 @@ ColorTemp RawImageSource::getSpotWB (std::vector &red, std::vector= 0 && ymin >= 0 && xmax < W && ymax < H) { - reds += (rawData[yr][3 * xr] ); + reds += (rawData[yr][3 * xr] ); greens += (rawData[yg][3 * xg + 1]); blues += (rawData[yb][3 * xb + 2]); rn++; @@ -4204,7 +5925,7 @@ ColorTemp RawImageSource::getSpotWB (std::vector &red, std::vector= 0 && yv >= 0 && xv < W && yv < H) { + if (xv >= 0 && yv >= 0 && xv < W && yv < H) { if (c == 0) { //RED rloc += (rawData[yv][xv]); rnbrs++; @@ -4240,7 +5961,7 @@ ColorTemp RawImageSource::getSpotWB (std::vector &red, std::vector= 0 && yv >= 0 && xv < W && yv < H) { + if (xv >= 0 && yv >= 0 && xv < W && yv < H) { if (c == 0) { //RED rloc += (rawData[yv][xv]); rnbrs++; @@ -4276,7 +5997,7 @@ ColorTemp RawImageSource::getSpotWB (std::vector &red, std::vector= 0 && yv >= 0 && xv < W && yv < H) { + if (xv >= 0 && yv >= 0 && xv < W && yv < H) { if (c == 0) { //RED rloc += (rawData[yv][xv]); rnbrs++; @@ -4321,9 +6042,6 @@ ColorTemp RawImageSource::getSpotWB (std::vector &red, std::vectorgetSensorType() == ST_FUJI_XTRANS ? ri->XTRANSFC(ynew,xnew) : ri->FC(ynew,xnew); int val = round(rawData[ynew][xnew] / scale_mul[c]); - if(c == 0) { + if (c == 0) { R = val; G = 0; B = 0; - } else if(c == 2) { + } else if (c == 2) { R = 0; G = 0; B = val; } else { R = 0; G = val; B = 0; diff --git a/rtengine/rawimagesource.h b/rtengine/rawimagesource.h index bd460c61b..770c18ae3 100644 --- a/rtengine/rawimagesource.h +++ b/rtengine/rawimagesource.h @@ -26,6 +26,7 @@ #include "colortemp.h" #include "iimage.h" #include "imagesource.h" +#include "procparams.h" #define HR_SCALE 2 @@ -37,7 +38,7 @@ class DiagonalCurve; class RetinextransmissionCurve; class RetinexgaintransmissionCurve; -class RawImageSource : public ImageSource +class RawImageSource final : public ImageSource { private: static DiagonalCurve *phaseOneIccCurve; @@ -86,11 +87,13 @@ protected: // the interpolated green plane: array2D green; + array2D greenloc; // the interpolated red plane: array2D red; + array2D redloc; // the interpolated blue plane: array2D blue; - // the interpolated green plane: + array2D blueloc; array2D* greenCache; // the interpolated red plane: array2D* redCache; @@ -108,6 +111,7 @@ protected: void hlRecovery (const std::string &method, float* red, float* green, float* blue, int width, float* hlmax); void transformRect (const PreviewProps &pp, int tran, int &sx1, int &sy1, int &width, int &height, int &fw); void transformPosition (int x, int y, int tran, int& tx, int& ty); + void ItcWB(bool extra, double &tempref, double &greenref, double &tempitc, double &greenitc, float &studgood, array2D &redloc, array2D &greenloc, array2D &blueloc, int bfw, int bfh, double &avg_rm, double &avg_gm, double &avg_bm, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw, const procparams::WBParams & wbpar); unsigned FC(int row, int col) const; inline void getRowStartEnd (int x, int &start, int &end); @@ -120,14 +124,14 @@ public: int load(const Glib::ustring &fname) override { return load(fname, false); } int load(const Glib::ustring &fname, bool firstFrameOnly); void preprocess (const procparams::RAWParams &raw, const procparams::LensProfParams &lensProf, const procparams::CoarseTransformParams& coarse, bool prepareDenoise = true) override; - void filmNegativeProcess (const procparams::FilmNegativeParams ¶ms) override; + void filmNegativeProcess (const procparams::FilmNegativeParams ¶ms, std::array& filmBaseValues) override; bool getFilmNegativeExponents (Coord2D spotA, Coord2D spotB, int tran, const procparams::FilmNegativeParams ¤tParams, std::array& newExps) override; + bool getRawSpotValues(Coord2D spot, int spotSize, int tran, const procparams::FilmNegativeParams ¶ms, std::array& rawValues) override; void demosaic (const procparams::RAWParams &raw, bool autoContrast, double &contrastThreshold, bool cache = false) override; void retinex (const procparams::ColorManagementParams& cmp, const procparams::RetinexParams &deh, const procparams::ToneCurveParams& Tc, LUTf & cdcurve, LUTf & mapcurve, const RetinextransmissionCurve & dehatransmissionCurve, const RetinexgaintransmissionCurve & dehagaintransmissionCurve, multi_array2D &conversionBuffer, bool dehacontlutili, bool mapcontlutili, bool useHsl, float &minCD, float &maxCD, float &mini, float &maxi, float &Tmean, float &Tsigma, float &Tmin, float &Tmax, LUTu &histLRETI) override; void retinexPrepareCurves (const procparams::RetinexParams &retinexParams, LUTf &cdcurve, LUTf &mapcurve, RetinextransmissionCurve &retinextransmissionCurve, RetinexgaintransmissionCurve &retinexgaintransmissionCurve, bool &retinexcontlutili, bool &mapcontlutili, bool &useHsl, LUTu & lhist16RETI, LUTu & histLRETI) override; void retinexPrepareBuffers (const procparams::ColorManagementParams& cmp, const procparams::RetinexParams &retinexParams, multi_array2D &conversionBuffer, LUTu &lhist16RETI) override; - void flushRawData () override; - void flushRGB () override; + void flush () override; void HLRecovery_Global (const procparams::ToneCurveParams &hrp) override; void refinement(int PassCount); void setBorder(unsigned int rawBorder) override {border = rawBorder;} @@ -139,6 +143,9 @@ public: void processFlatField(const procparams::RAWParams &raw, const RawImage *riFlatFile, const float black[4]); void copyOriginalPixels(const procparams::RAWParams &raw, RawImage *ri, RawImage *riDark, RawImage *riFlatFile, array2D &rawData ); void scaleColors (int winx, int winy, int winw, int winh, const procparams::RAWParams &raw, array2D &rawData); // raw for cblack + void WBauto(double &tempref, double &greenref, array2D &redloc, array2D &greenloc, array2D &blueloc, int bfw, int bfh, double &avg_rm, double &avg_gm, double &avg_bm, double &tempitc, double &greenitc, float &studgood, bool &twotimes, const procparams::WBParams & wbpar, int begx, int begy, int yEn, int xEn, int cx, int cy, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw) override; + void getAutoWBMultipliersitc(double &tempref, double &greenref, double &tempitc, double &greenitc, float &studgood, int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, double &rm, double &gm, double &bm, const procparams::WBParams & wbpar, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw) override; + void getrgbloc(int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w) override; void getImage (const ColorTemp &ctemp, int tran, Imagefloat* image, const PreviewProps &pp, const procparams::ToneCurveParams &hrp, const procparams::RAWParams &raw) override; eSensorType getSensorType () const override; diff --git a/rtengine/rescale.h b/rtengine/rescale.h index 70974aa48..2138cd8e8 100644 --- a/rtengine/rescale.h +++ b/rtengine/rescale.h @@ -20,9 +20,12 @@ #pragma once -#include "array2D.h" #include "rt_math.h" +template +class array2D; + + namespace rtengine { diff --git a/rtengine/rt_math.h b/rtengine/rt_math.h index 9342f5430..6d4799254 100644 --- a/rtengine/rt_math.h +++ b/rtengine/rt_math.h @@ -44,6 +44,12 @@ constexpr T pow4(T x) return SQR(SQR(x)); } +template +constexpr T pow5(T x) +{ + return x * pow4(x); +} + template constexpr const T& min(const T& a) { diff --git a/rtengine/rtengine.h b/rtengine/rtengine.h index 0473622c4..028cedec9 100644 --- a/rtengine/rtengine.h +++ b/rtengine/rtengine.h @@ -31,7 +31,6 @@ #include "imageformat.h" #include "procevents.h" #include "rawmetadatalocation.h" -#include "rt_math.h" #include "settings.h" #include "../rtgui/threadutils.h" @@ -356,6 +355,8 @@ public : virtual void autoCamChanged(double ccam, double ccamout) = 0; virtual void adapCamChanged(double cadap) = 0; virtual void ybCamChanged(int yb) = 0; + virtual void wbCamChanged(double tem, double tin) = 0; + }; class AutoChromaListener @@ -392,7 +393,7 @@ class AutoWBListener { public: virtual ~AutoWBListener() = default; - virtual void WBChanged(double temp, double green) = 0; + virtual void WBChanged(double temp, double green, float studgood) = 0; }; class FrameCountListener @@ -438,6 +439,13 @@ public: }; +class FilmNegListener +{ +public: + virtual ~FilmNegListener() = default; + virtual void filmBaseValuesChanged(std::array rgb) = 0; +}; + /** This class represents a detailed part of the image (looking through a kind of window). * It can be created and destroyed with the appropriate members of StagedImageProcessor. * Several crops can be assigned to the same image. */ @@ -523,6 +531,8 @@ public: virtual void getCamWB (double& temp, double& green) = 0; virtual void getSpotWB (int x, int y, int rectSize, double& temp, double& green) = 0; virtual bool getFilmNegativeExponents(int xA, int yA, int xB, int yB, std::array& newExps) = 0; + virtual bool getRawSpotValues (int x, int y, int spotSize, std::array& rawValues) = 0; + virtual void getAutoCrop (double ratio, int &x, int &y, int &w, int &h) = 0; virtual void saveInputICCReference (const Glib::ustring& fname, bool apply_wb) = 0; @@ -547,6 +557,7 @@ public: virtual void setRetinexListener (RetinexListener* l) = 0; virtual void setWaveletListener (WaveletListener* l) = 0; virtual void setImageTypeListener (ImageTypeListener* l) = 0; + virtual void setFilmNegListener (FilmNegListener* l) = 0; virtual void setMonitorProfile (const Glib::ustring& monitorProfile, RenderingIntent intent) = 0; virtual void getMonitorProfile (Glib::ustring& monitorProfile, RenderingIntent& intent) const = 0; diff --git a/rtengine/rtthumbnail.cc b/rtengine/rtthumbnail.cc index 9da601e2a..e8126be36 100644 --- a/rtengine/rtthumbnail.cc +++ b/rtengine/rtthumbnail.cc @@ -31,6 +31,7 @@ #include "colortemp.h" #include "curves.h" #include "dcp.h" +#include "iccmatrices.h" #include "iccstore.h" #include "image8.h" #include "improcfun.h" @@ -511,8 +512,6 @@ Thumbnail* Thumbnail::loadQuickFromRaw (const Glib::ustring& fname, RawMetaDataL ((filter >> ((((row) << 1 & 14) + ((col) & 1)) << 1) & 3)==0 || !filter) #define FISGREEN(filter,row,col) \ ((filter >> ((((row) << 1 & 14) + ((col) & 1)) << 1) & 3)==1 || !filter) -#define FISBLUE(filter,row,col) \ - ((filter >> ((((row) << 1 & 14) + ((col) & 1)) << 1) & 3)==2 || !filter) RawMetaDataLocation Thumbnail::loadMetaDataFromRaw (const Glib::ustring& fname) { @@ -595,6 +594,8 @@ Thumbnail* Thumbnail::loadFromRaw (const Glib::ustring& fname, RawMetaDataLocati tpp->defGain = max (scale_mul[0], scale_mul[1], scale_mul[2], scale_mul[3]) / min (scale_mul[0], scale_mul[1], scale_mul[2], scale_mul[3]); tpp->defGain *= std::pow(2, ri->getBaselineExposure()); + tpp->scaleGain = scale_mul[0] / pre_mul[0]; // used to reconstruct scale_mul from filmnegativethumb.cc + tpp->gammaCorrected = true; unsigned filter = ri->get_filters(); @@ -1043,6 +1044,7 @@ Thumbnail::Thumbnail () : scaleForSave (8192), gammaCorrected (false), colorMatrix{}, + scaleGain (1.0), isRaw (true) { } @@ -1131,7 +1133,7 @@ IImage8* Thumbnail::processImage (const procparams::ProcParams& params, eSensorT double cam_g = colorMatrix[1][0] * camwbRed + colorMatrix[1][1] * camwbGreen + colorMatrix[1][2] * camwbBlue; double cam_b = colorMatrix[2][0] * camwbRed + colorMatrix[2][1] * camwbGreen + colorMatrix[2][2] * camwbBlue; currWB = ColorTemp (cam_r, cam_g, cam_b, params.wb.equal); - } else if (params.wb.method == "Auto") { + } else if (params.wb.method == "autold") { currWB = ColorTemp (autoWBTemp, autoWBGreen, wbEqual, "Custom"); } @@ -1180,7 +1182,7 @@ IImage8* Thumbnail::processImage (const procparams::ProcParams& params, eSensorT Imagefloat* baseImg = resizeTo (rwidth, rheight, interp, thumbImg); if (isRaw && params.filmNegative.enabled) { - processFilmNegative(params, baseImg, rwidth, rheight, rmi, gmi, bmi); + processFilmNegative(params, baseImg, rwidth, rheight); } if (params.coarse.rotate) { @@ -2123,6 +2125,10 @@ bool Thumbnail::readData (const Glib::ustring& fname) colorMatrix[i][j] = cm[ix++]; } } + + if (keyFile.has_key ("LiveThumbData", "ScaleGain")) { + scaleGain = keyFile.get_double ("LiveThumbData", "ScaleGain"); + } } return true; @@ -2174,6 +2180,7 @@ bool Thumbnail::writeData (const Glib::ustring& fname) keyFile.set_boolean ("LiveThumbData", "GammaCorrected", gammaCorrected); Glib::ArrayHandle cm ((double*)colorMatrix, 9, Glib::OWNERSHIP_NONE); keyFile.set_double_list ("LiveThumbData", "ColorMatrix", cm); + keyFile.set_double ("LiveThumbData", "ScaleGain", scaleGain); keyData = keyFile.to_data (); @@ -2254,44 +2261,6 @@ bool Thumbnail::writeEmbProfile (const Glib::ustring& fname) return false; } -bool Thumbnail::readAEHistogram (const Glib::ustring& fname) -{ - - FILE* f = g_fopen(fname.c_str(), "rb"); - - if (!f) { - aeHistogram.reset(); - } else { - aeHistogram(65536 >> aeHistCompression); - const size_t histoBytes = (65536 >> aeHistCompression) * sizeof(aeHistogram[0]); - const size_t bytesRead = fread(&aeHistogram[0], 1, histoBytes, f); - fclose (f); - if (bytesRead != histoBytes) { - aeHistogram.reset(); - return false; - } - return true; - } - - return false; -} - -bool Thumbnail::writeAEHistogram (const Glib::ustring& fname) -{ - - if (aeHistogram) { - FILE* f = g_fopen (fname.c_str (), "wb"); - - if (f) { - fwrite (&aeHistogram[0], 1, (65536 >> aeHistCompression)*sizeof (aeHistogram[0]), f); - fclose (f); - return true; - } - } - - return false; -} - unsigned char* Thumbnail::getImage8Data() { if (thumbImg && thumbImg->getType() == rtengine::sImage8) { diff --git a/rtengine/rtthumbnail.h b/rtengine/rtthumbnail.h index dcc9596f6..a0033d35f 100644 --- a/rtengine/rtthumbnail.h +++ b/rtengine/rtthumbnail.h @@ -18,8 +18,6 @@ */ #pragma once -#include - #include #include "image16.h" @@ -30,6 +28,13 @@ #include "../rtgui/threadutils.h" +namespace Glib +{ + +class ustring; + +} + namespace rtengine { @@ -70,8 +75,9 @@ class Thumbnail int scaleForSave; bool gammaCorrected; double colorMatrix[3][3]; + double scaleGain; - void processFilmNegative(const procparams::ProcParams& params, const Imagefloat* baseImg, int rwidth, int rheight, float &rmi, float &gmi, float &bmi); + void processFilmNegative(const procparams::ProcParams& params, const Imagefloat* baseImg, int rwidth, int rheight); public: @@ -108,10 +114,6 @@ public: bool readEmbProfile (const Glib::ustring& fname); bool writeEmbProfile (const Glib::ustring& fname); - bool readAEHistogram (const Glib::ustring& fname); - bool writeAEHistogram (const Glib::ustring& fname); - - bool isAeValid() { return aeValid; }; unsigned char* getImage8Data(); // accessor to the 8bit image if it is one, which should be the case for the "Inspector" mode. // Hombre: ... let's hope that proper template can make this cleaner diff --git a/rtengine/settings.h b/rtengine/settings.h index f261444c8..529336cbc 100644 --- a/rtengine/settings.h +++ b/rtengine/settings.h @@ -7,8 +7,8 @@ * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. - * * RawTherapee is distributed in the hope that it will be useful, +itcw * * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. @@ -80,7 +80,17 @@ public: // bool bw_complementary; double level0_cbdl; double level123_cbdl; - Glib::ustring lensfunDbDirectory; ///< The directory containing the lensfun database. If empty, the system defaults will be used (as described in http://lensfun.sourceforge.net/manual/dbsearch.html) + Glib::ustring lensfunDbDirectory; // The directory containing the lensfun database. If empty, the system defaults will be used, as described in https://lensfun.github.io/manual/latest/dbsearch.html + int itcwb_thres; + bool itcwb_sort; + int itcwb_greenrange; + int itcwb_greendeltatemp; + bool itcwb_forceextra; + int itcwb_sizereference; + int itcwb_delta; + bool itcwb_stdobserver10; + int itcwb_precis; + enum class ThumbnailInspectorMode { JPEG, diff --git a/rtengine/shmap.cc b/rtengine/shmap.cc index abdcc42a4..306e30bdd 100644 --- a/rtengine/shmap.cc +++ b/rtengine/shmap.cc @@ -27,6 +27,37 @@ #undef THREAD_PRIORITY_NORMAL #include "opthelper.h" +namespace { + +void fillLuminance(rtengine::Imagefloat* img, float** luminance, const float lumi[3], int W, int H) // fill with luminance +{ + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int i = 0; i < H; i++) + for (int j = 0; j < W; j++) { + luminance[i][j] = lumi[0] * std::max(img->r(i, j), 0.f) + lumi[1] * std::max(img->g(i, j), 0.f) + lumi[2] * std::max(img->b(i, j), 0.f); + } + +} + +void fillLuminanceL(float** L, float** luminance, int W, int H) // fill with luminance +{ + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int i = 0; i < H; i++) + for (int j = 0; j < W; j++) { + luminance[i][j] = std::max(L[i][j], 0.f) ;//we can put here some enhancements Gamma, compression data,... + } + +} + +} namespace rtengine { @@ -51,39 +82,13 @@ SHMap::~SHMap () delete [] map; } -void SHMap::fillLuminance( Imagefloat * img, float **luminance, double lumi[3] ) // fill with luminance -{ - -#ifdef _OPENMP - #pragma omp parallel for -#endif - - for (int i = 0; i < H; i++) - for (int j = 0; j < W; j++) { - luminance[i][j] = lumi[0] * std::max(img->r(i, j), 0.f) + lumi[1] * std::max(img->g(i, j), 0.f) + lumi[2] * std::max(img->b(i, j), 0.f); - } - -} - -void SHMap::fillLuminanceL( float ** L, float **luminance) // fill with luminance -{ - -#ifdef _OPENMP - #pragma omp parallel for -#endif - - for (int i = 0; i < H; i++) - for (int j = 0; j < W; j++) { - luminance[i][j] = std::max(L[i][j], 0.f) ;//we can put here some enhancements Gamma, compression data,... - } - -} - void SHMap::update (Imagefloat* img, double radius, double lumi[3], bool hq, int skip) { + const float lumif[3] = { static_cast(lumi[0]), static_cast(lumi[1]), static_cast(lumi[2]) }; + if (!hq) { - fillLuminance( img, map, lumi); + fillLuminance(img, map, lumif, W, H); const bool useBoxBlur = radius > 40.0; // boxblur is less prone to artifacts for large radi @@ -91,7 +96,7 @@ void SHMap::update (Imagefloat* img, double radius, double lumi[3], bool hq, int #pragma omp parallel if (!useBoxBlur) #endif { - gaussianBlur (map, map, W, H, radius, useBoxBlur); + gaussianBlur(map, map, W, H, radius, useBoxBlur); } } @@ -99,7 +104,7 @@ void SHMap::update (Imagefloat* img, double radius, double lumi[3], bool hq, int //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% //experimental dirpyr shmap - float thresh = (100.f * radius); //1000; + float thresh = 100.0 * radius; //1000; // set up range function // calculate size of Lookup table. That's possible because from a value k for all i>=k rangefn[i] will be exp(-10) @@ -142,7 +147,7 @@ void SHMap::update (Imagefloat* img, double radius, double lumi[3], bool hq, int dirpyrlo[1] = buffer; } - fillLuminance( img, dirpyrlo[0], lumi); + fillLuminance(img, dirpyrlo[0], lumif, W, H); scale = 1; int level = 0; @@ -181,28 +186,18 @@ void SHMap::update (Imagefloat* img, double radius, double lumi[3], bool hq, int for (int j = 0; j < W; j++) { _val = map[i][j]; - if (_val < _min_f) { - _min_f = _val; - } + _min_f = std::min(_min_f, _val); + _max_f = std::max(_max_f, _val); - if (_val > _max_f) { - _max_f = _val; - } - - _avg += _val; + _avg += static_cast(_val); } #ifdef _OPENMP #pragma omp critical #endif { - if(_min_f < min_f ) { - min_f = _min_f; - } - - if(_max_f > max_f ) { - max_f = _max_f; - } + min_f = std::min(min_f, _min_f); + max_f = std::max(max_f, _max_f); } } _avg /= ((H) * (W)); @@ -214,7 +209,7 @@ void SHMap::updateL (float** L, double radius, bool hq, int skip) { if (!hq) { - fillLuminanceL( L, map); + fillLuminanceL(L, map, W, H); #ifdef _OPENMP #pragma omp parallel #endif @@ -228,7 +223,7 @@ void SHMap::updateL (float** L, double radius, bool hq, int skip) { //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% //experimental dirpyr shmap - float thresh = (100.f * radius); //1000; + float thresh = 100.0 * radius; //1000; int levrad; // = 16; levrad = 2; //for retinex - otherwise levrad = 16 // set up range function @@ -274,7 +269,7 @@ void SHMap::updateL (float** L, double radius, bool hq, int skip) dirpyrlo[1] = buffer; } - fillLuminanceL( L, dirpyrlo[0]); + fillLuminanceL(L, dirpyrlo[0], W, H); scale = 1; int level = 0; @@ -313,28 +308,18 @@ void SHMap::updateL (float** L, double radius, bool hq, int skip) for (int j = 0; j < W; j++) { _val = map[i][j]; - if (_val < _min_f) { - _min_f = _val; - } + _min_f = std::min(_min_f, _val); + _max_f = std::max(_max_f, _val); - if (_val > _max_f) { - _max_f = _val; - } - - _avg += _val; + _avg += static_cast(_val); } #ifdef _OPENMP #pragma omp critical #endif { - if(_min_f < min_f ) { - min_f = _min_f; - } - - if(_max_f > max_f ) { - max_f = _max_f; - } + min_f = std::min(min_f, _min_f); + max_f = std::max(max_f, _max_f); } } _avg /= ((H) * (W)); diff --git a/rtengine/shmap.h b/rtengine/shmap.h index 68e352b23..b1b1e5eff 100644 --- a/rtengine/shmap.h +++ b/rtengine/shmap.h @@ -48,8 +48,6 @@ public: private: int W, H; - void fillLuminance( Imagefloat * img, float **luminance, double lumi[3] ); - void fillLuminanceL( float ** L, float **luminance ); void dirpyr_shmap(float ** data_fine, float ** data_coarse, int width, int height, const LUTf& rangefn, int level, int scale); }; diff --git a/rtengine/simpleprocess.cc b/rtengine/simpleprocess.cc index 1c1e46a65..14a594ac2 100644 --- a/rtengine/simpleprocess.cc +++ b/rtengine/simpleprocess.cc @@ -35,6 +35,9 @@ #include "rawimagesource.h" #include "../rtgui/multilangmgr.h" #include "mytime.h" +#include "guidedfilter.h" +#include "color.h" + #undef THREAD_PRIORITY_NORMAL namespace rtengine @@ -44,7 +47,7 @@ namespace { template -void adjust_radius (const T &default_param, double scale_factor, T ¶m) +void adjust_radius(const T &default_param, double scale_factor, T ¶m) { const double delta = (param - default_param) * scale_factor; param = default_param + delta; @@ -60,12 +63,12 @@ public: ProgressListener* pl, bool flush ) : - job (static_cast (pjob)), - errorCode (errorCode), - pl (pl), - flush (flush), + job(static_cast(pjob)), + errorCode(errorCode), + pl(pl), + flush(flush), // internal state - ii(nullptr), + initialImage(nullptr), imgsrc(nullptr), fw(0), fh(0), @@ -94,6 +97,7 @@ public: hlcomprthresh(0), baseImg(nullptr), labView(nullptr), + ctColorCurve(), autili(false), butili(false) { @@ -143,14 +147,14 @@ private: errorCode = 0; if (pl) { - pl->setProgressStr ("PROGRESSBAR_PROCESSING"); - pl->setProgress (0.0); + pl->setProgressStr("PROGRESSBAR_PROCESSING"); + pl->setProgress(0.0); } - ii = job->initialImage; + initialImage = job->initialImage; - if (!ii) { - ii = InitialImage::load (job->fname, job->isRaw, &errorCode); + if (!initialImage) { + initialImage = InitialImage::load(job->fname, job->isRaw, &errorCode); if (errorCode) { delete job; @@ -161,11 +165,12 @@ private: procparams::ProcParams& params = job->pparams; // acquire image from imagesource - imgsrc = ii->getImageSource (); + imgsrc = initialImage->getImageSource(); - tr = getCoarseBitMask (params.coarse); - if(imgsrc->getSensorType() == ST_BAYER) { - if(params.raw.bayersensor.method!= RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::PIXELSHIFT)) { + tr = getCoarseBitMask(params.coarse); + + if (imgsrc->getSensorType() == ST_BAYER) { + if (params.raw.bayersensor.method != RAWParams::BayerSensor::getMethodString(RAWParams::BayerSensor::Method::PIXELSHIFT)) { imgsrc->setBorder(params.raw.bayersensor.border); } else { imgsrc->setBorder(std::max(params.raw.bayersensor.border, 2)); @@ -173,7 +178,8 @@ private: } else if (imgsrc->getSensorType() == ST_FUJI_XTRANS) { imgsrc->setBorder(params.raw.xtranssensor.border); } - imgsrc->getFullSize (fw, fh, tr); + + imgsrc->getFullSize(fw, fh, tr); // check the crop params if (params.crop.x > fw || params.crop.y > fh) { @@ -207,20 +213,26 @@ private: // MyTime t1,t2; // t1.set(); - ipf_p.reset (new ImProcFunctions (¶ms, true)); + ipf_p.reset(new ImProcFunctions(¶ms, true)); ImProcFunctions &ipf = * (ipf_p.get()); - imgsrc->setCurrentFrame (params.raw.bayersensor.imageNum); - imgsrc->preprocess ( params.raw, params.lensProf, params.coarse, params.dirpyrDenoise.enabled); + imgsrc->setCurrentFrame(params.raw.bayersensor.imageNum); + imgsrc->preprocess(params.raw, params.lensProf, params.coarse, params.dirpyrDenoise.enabled); // After preprocess, run film negative processing if enabled if ((imgsrc->getSensorType() == ST_BAYER || (imgsrc->getSensorType() == ST_FUJI_XTRANS)) && params.filmNegative.enabled) { - imgsrc->filmNegativeProcess (params.filmNegative); + std::array filmBaseValues = { + static_cast(params.filmNegative.redBase), + static_cast(params.filmNegative.greenBase), + static_cast(params.filmNegative.blueBase) + }; + imgsrc->filmNegativeProcess (params.filmNegative, filmBaseValues); } if (pl) { - pl->setProgress (0.20); + pl->setProgress(0.20); } + bool autoContrast = imgsrc->getSensorType() == ST_BAYER ? params.raw.bayersensor.dualDemosaicAutoContrast : params.raw.xtranssensor.dualDemosaicAutoContrast; double contrastThreshold = imgsrc->getSensorType() == ST_BAYER ? params.raw.bayersensor.dualDemosaicContrast : params.raw.xtranssensor.dualDemosaicContrast; @@ -231,52 +243,52 @@ private: if (pl) { - pl->setProgress (0.30); + pl->setProgress(0.30); } - pp = PreviewProps (0, 0, fw, fh, 1); + + pp = PreviewProps(0, 0, fw, fh, 1); if (params.retinex.enabled) { //enabled Retinex - LUTf cdcurve (65536, 0); - LUTf mapcurve (65536, 0); - LUTu dummy; + LUTf cdcurve(65536, 0); + LUTf mapcurve(65536, 0); RetinextransmissionCurve dehatransmissionCurve; RetinexgaintransmissionCurve dehagaintransmissionCurve; bool dehacontlutili = false; bool mapcontlutili = false; bool useHsl = false; - multi_array2D conversionBuffer (1, 1); - imgsrc->retinexPrepareBuffers (params.icm, params.retinex, conversionBuffer, dummy); - imgsrc->retinexPrepareCurves (params.retinex, cdcurve, mapcurve, dehatransmissionCurve, dehagaintransmissionCurve, dehacontlutili, mapcontlutili, useHsl, dummy, dummy ); + multi_array2D conversionBuffer(1, 1); + imgsrc->retinexPrepareBuffers(params.icm, params.retinex, conversionBuffer, dummy); + imgsrc->retinexPrepareCurves(params.retinex, cdcurve, mapcurve, dehatransmissionCurve, dehagaintransmissionCurve, dehacontlutili, mapcontlutili, useHsl, dummy, dummy); float minCD, maxCD, mini, maxi, Tmean, Tsigma, Tmin, Tmax; - imgsrc->retinex ( params.icm, params.retinex, params.toneCurve, cdcurve, mapcurve, dehatransmissionCurve, dehagaintransmissionCurve, conversionBuffer, dehacontlutili, mapcontlutili, useHsl, minCD, maxCD, mini, maxi, Tmean, Tsigma, Tmin, Tmax, dummy); + imgsrc->retinex(params.icm, params.retinex, params.toneCurve, cdcurve, mapcurve, dehatransmissionCurve, dehagaintransmissionCurve, conversionBuffer, dehacontlutili, mapcontlutili, useHsl, minCD, maxCD, mini, maxi, Tmean, Tsigma, Tmin, Tmax, dummy); } if (pl) { - pl->setProgress (0.40); + pl->setProgress(0.40); } - imgsrc->HLRecovery_Global ( params.toneCurve ); + imgsrc->HLRecovery_Global(params.toneCurve); if (pl) { - pl->setProgress (0.45); + pl->setProgress(0.45); } // set the color temperature - currWB = ColorTemp (params.wb.temperature, params.wb.green, params.wb.equal, params.wb.method); + currWB = ColorTemp(params.wb.temperature, params.wb.green, params.wb.equal, params.wb.method); if (!params.wb.enabled) { currWB = ColorTemp(); } else if (params.wb.method == "Camera") { - currWB = imgsrc->getWB (); - } else if (params.wb.method == "Auto") { + currWB = imgsrc->getWB(); + } else if (params.wb.method == "autold") { double rm, gm, bm; - imgsrc->getAutoWBMultipliers (rm, gm, bm); - currWB.update (rm, gm, bm, params.wb.equal, params.wb.tempBias); + imgsrc->getAutoWBMultipliers(rm, gm, bm); + currWB.update(rm, gm, bm, params.wb.equal, params.wb.tempBias); } calclum = nullptr ; - params.dirpyrDenoise.getCurves (noiseLCurve, noiseCCurve); + params.dirpyrDenoise.getCurves(noiseLCurve, noiseCCurve); autoNR = (float) settings->nrauto;// autoNRmax = (float) settings->nrautomax;// @@ -293,7 +305,7 @@ private: // const int tilesize = 768; // const int overlap = 96; int numtiles_W, numtiles_H, tilewidth, tileheight, tileWskip, tileHskip; - ipf.Tile_calc (tilesize, overlap, 2, fw, fh, numtiles_W, numtiles_H, tilewidth, tileheight, tileWskip, tileHskip); + ipf.Tile_calc(tilesize, overlap, 2, fw, fh, numtiles_W, numtiles_H, tilewidth, tileheight, tileWskip, tileHskip); int nbtl = numtiles_W * numtiles_H; if ((settings->leveldnautsimpl == 1 && params.dirpyrDenoise.Cmethod == "AUT") || (settings->leveldnautsimpl == 0 && params.dirpyrDenoise.C2method == "AUTO")) { @@ -346,16 +358,16 @@ private: // Imagefloat *origCropPart;//init auto noise // origCropPart = new Imagefloat (crW, crH);//allocate memory if (params.dirpyrDenoise.enabled) {//evaluate Noise - LUTf gamcurve (65536, 0); + LUTf gamcurve(65536, 0); float gam, gamthresh, gamslope; - ipf.RGB_denoise_infoGamCurve (params.dirpyrDenoise, imgsrc->isRAW(), gamcurve, gam, gamthresh, gamslope); + ipf.RGB_denoise_infoGamCurve(params.dirpyrDenoise, imgsrc->isRAW(), gamcurve, gam, gamthresh, gamslope); #ifdef _OPENMP #pragma omp parallel #endif { Imagefloat *origCropPart;//init auto noise - origCropPart = new Imagefloat (crW, crH);//allocate memory - Imagefloat *provicalc = new Imagefloat ((crW + 1) / 2, (crH + 1) / 2); //for denoise curves + origCropPart = new Imagefloat(crW, crH); //allocate memory + Imagefloat *provicalc = new Imagefloat((crW + 1) / 2, (crH + 1) / 2); //for denoise curves int skipP = 1; #ifdef _OPENMP #pragma omp for schedule(dynamic) collapse(2) nowait @@ -365,20 +377,20 @@ private: for (int hcr = 0; hcr < numtiles_H; hcr++) { int beg_tileW = wcr * tileWskip + tileWskip / 2.f - crW / 2.f; int beg_tileH = hcr * tileHskip + tileHskip / 2.f - crH / 2.f; - PreviewProps ppP (beg_tileW, beg_tileH, crW, crH, skipP); - imgsrc->getImage (currWB, tr, origCropPart, ppP, params.toneCurve, params.raw ); + PreviewProps ppP(beg_tileW, beg_tileH, crW, crH, skipP); + imgsrc->getImage(currWB, tr, origCropPart, ppP, params.toneCurve, params.raw); //baseImg->getStdImage(currWB, tr, origCropPart, ppP, true, params.toneCurve); // we only need image reduced to 1/4 here for (int ii = 0; ii < crH; ii += 2) { for (int jj = 0; jj < crW; jj += 2) { - provicalc->r (ii >> 1, jj >> 1) = origCropPart->r (ii, jj); - provicalc->g (ii >> 1, jj >> 1) = origCropPart->g (ii, jj); - provicalc->b (ii >> 1, jj >> 1) = origCropPart->b (ii, jj); + provicalc->r(ii >> 1, jj >> 1) = origCropPart->r(ii, jj); + provicalc->g(ii >> 1, jj >> 1) = origCropPart->g(ii, jj); + provicalc->b(ii >> 1, jj >> 1) = origCropPart->b(ii, jj); } } - imgsrc->convertColorSpace (provicalc, params.icm, currWB); //for denoise luminance curve + imgsrc->convertColorSpace(provicalc, params.icm, currWB); //for denoise luminance curve float maxr = 0.f; float maxb = 0.f; float pondcorrec = 1.0f; @@ -391,11 +403,11 @@ private: maxblueaut = 0.f; chromina = 0.f; sigma = 0.f; - ipf.RGB_denoise_info (origCropPart, provicalc, imgsrc->isRAW(), gamcurve, gam, gamthresh, gamslope, params.dirpyrDenoise, imgsrc->getDirPyrDenoiseExpComp(), chaut, Nb, redaut, blueaut, maxredaut, maxblueaut, minredaut, minblueaut, chromina, sigma, lumema, sigma_L, redyel, skinc, nsknc); + ipf.RGB_denoise_info(origCropPart, provicalc, imgsrc->isRAW(), gamcurve, gam, gamthresh, gamslope, params.dirpyrDenoise, imgsrc->getDirPyrDenoiseExpComp(), chaut, Nb, redaut, blueaut, maxredaut, maxblueaut, minredaut, minblueaut, chromina, sigma, lumema, sigma_L, redyel, skinc, nsknc); float multip = 1.f; float adjustr = 1.f; - if (params.icm.workingProfile == "ProPhoto") { + if (params.icm.workingProfile == "ProPhoto") { adjustr = 1.f; // } else if (params.icm.workingProfile == "Adobe RGB") { adjustr = 1.f / 1.3f; @@ -417,11 +429,11 @@ private: multip = 2.f; //take into account gamma for TIF / JPG approximate value...not good for gamma=1 } - float maxmax = max (maxredaut, maxblueaut); + float maxmax = max(maxredaut, maxblueaut); float delta; int mode = 2; int lissage = settings->leveldnliss; - ipf.calcautodn_info (chaut, delta, Nb, levaut, maxmax, lumema, chromina, mode, lissage, redyel, skinc, nsknc); + ipf.calcautodn_info(chaut, delta, Nb, levaut, maxmax, lumema, chromina, mode, lissage, redyel, skinc, nsknc); // printf("PROCESS cha=%f red=%f bl=%f redM=%f bluM=%f chrom=%f sigm=%f lum=%f sigL=%f\n",chaut,redaut,blueaut, maxredaut, maxblueaut, chromina, sigma, lumema, sigma_L); if (maxredaut > maxblueaut) { @@ -520,7 +532,7 @@ private: if (settings->verbose) { t2pone.set(); - printf ("Info denoise ponderated performed in %d usec:\n", t2pone.etime (t1pone)); + printf("Info denoise ponderated performed in %d usec:\n", t2pone.etime(t1pone)); } } @@ -561,9 +573,9 @@ private: } if (params.dirpyrDenoise.enabled) {//evaluate Noise - LUTf gamcurve (65536, 0); + LUTf gamcurve(65536, 0); float gam, gamthresh, gamslope; - ipf.RGB_denoise_infoGamCurve (params.dirpyrDenoise, imgsrc->isRAW(), gamcurve, gam, gamthresh, gamslope); + ipf.RGB_denoise_infoGamCurve(params.dirpyrDenoise, imgsrc->isRAW(), gamcurve, gam, gamthresh, gamslope); int Nb[9]; int coordW[3];//coordinate of part of image to measure noise int coordH[3]; @@ -580,8 +592,8 @@ private: #endif { Imagefloat *origCropPart;//init auto noise - origCropPart = new Imagefloat (crW, crH);//allocate memory - Imagefloat *provicalc = new Imagefloat ((crW + 1) / 2, (crH + 1) / 2); //for denoise curves + origCropPart = new Imagefloat(crW, crH); //allocate memory + Imagefloat *provicalc = new Imagefloat((crW + 1) / 2, (crH + 1) / 2); //for denoise curves #ifdef _OPENMP #pragma omp for schedule(dynamic) collapse(2) nowait @@ -589,24 +601,24 @@ private: for (int wcr = 0; wcr <= 2; wcr++) { for (int hcr = 0; hcr <= 2; hcr++) { - PreviewProps ppP (coordW[wcr], coordH[hcr], crW, crH, 1); - imgsrc->getImage (currWB, tr, origCropPart, ppP, params.toneCurve, params.raw); + PreviewProps ppP(coordW[wcr], coordH[hcr], crW, crH, 1); + imgsrc->getImage(currWB, tr, origCropPart, ppP, params.toneCurve, params.raw); //baseImg->getStdImage(currWB, tr, origCropPart, ppP, true, params.toneCurve); // we only need image reduced to 1/4 here for (int ii = 0; ii < crH; ii += 2) { for (int jj = 0; jj < crW; jj += 2) { - provicalc->r (ii >> 1, jj >> 1) = origCropPart->r (ii, jj); - provicalc->g (ii >> 1, jj >> 1) = origCropPart->g (ii, jj); - provicalc->b (ii >> 1, jj >> 1) = origCropPart->b (ii, jj); + provicalc->r(ii >> 1, jj >> 1) = origCropPart->r(ii, jj); + provicalc->g(ii >> 1, jj >> 1) = origCropPart->g(ii, jj); + provicalc->b(ii >> 1, jj >> 1) = origCropPart->b(ii, jj); } } - imgsrc->convertColorSpace (provicalc, params.icm, currWB); //for denoise luminance curve + imgsrc->convertColorSpace(provicalc, params.icm, currWB); //for denoise luminance curve int nb = 0; float chaut = 0.f, redaut = 0.f, blueaut = 0.f, maxredaut = 0.f, maxblueaut = 0.f, minredaut = 0.f, minblueaut = 0.f, chromina = 0.f, sigma = 0.f, lumema = 0.f, sigma_L = 0.f, redyel = 0.f, skinc = 0.f, nsknc = 0.f; - ipf.RGB_denoise_info (origCropPart, provicalc, imgsrc->isRAW(), gamcurve, gam, gamthresh, gamslope, params.dirpyrDenoise, imgsrc->getDirPyrDenoiseExpComp(), chaut, nb, redaut, blueaut, maxredaut, maxblueaut, minredaut, minblueaut, chromina, sigma, lumema, sigma_L, redyel, skinc, nsknc); + ipf.RGB_denoise_info(origCropPart, provicalc, imgsrc->isRAW(), gamcurve, gam, gamthresh, gamslope, params.dirpyrDenoise, imgsrc->getDirPyrDenoiseExpComp(), chaut, nb, redaut, blueaut, maxredaut, maxblueaut, minredaut, minblueaut, chromina, sigma, lumema, sigma_L, redyel, skinc, nsknc); Nb[hcr * 3 + wcr] = nb; ch_M[hcr * 3 + wcr] = chaut; max_r[hcr * 3 + wcr] = maxredaut; @@ -642,7 +654,7 @@ private: float MinRMoy = 0.f; float MinBMoy = 0.f; - if (params.icm.workingProfile == "ProPhoto") { + if (params.icm.workingProfile == "ProPhoto") { adjustr = 1.f; } else if (params.icm.workingProfile == "Adobe RGB") { adjustr = 1.f / 1.3f; @@ -669,8 +681,8 @@ private: int lissage = settings->leveldnliss; for (int k = 0; k < 9; k++) { - float maxmax = max (max_r[k], max_b[k]); - ipf.calcautodn_info (ch_M[k], delta[k], Nb[k], levaut, maxmax, lumL[k], chromC[k], mode, lissage, ry[k], sk[k], pcsk[k] ); + float maxmax = max(max_r[k], max_b[k]); + ipf.calcautodn_info(ch_M[k], delta[k], Nb[k], levaut, maxmax, lumL[k], chromC[k], mode, lissage, ry[k], sk[k], pcsk[k]); // printf("ch_M=%f delta=%f\n",ch_M[k], delta[k]); } @@ -743,17 +755,17 @@ private: if (settings->verbose) { t2aue.set(); - printf ("Info denoise auto performed in %d usec:\n", t2aue.etime (t1aue)); + printf("Info denoise auto performed in %d usec:\n", t2aue.etime(t1aue)); } //end evaluate noise } - baseImg = new Imagefloat (fw, fh); - imgsrc->getImage (currWB, tr, baseImg, pp, params.toneCurve, params.raw); + baseImg = new Imagefloat(fw, fh); + imgsrc->getImage(currWB, tr, baseImg, pp, params.toneCurve, params.raw); if (pl) { - pl->setProgress (0.50); + pl->setProgress(0.50); } // LUTf Noisecurve (65536,0); @@ -769,9 +781,10 @@ private: if (params.toneCurve.autoexp) { LUTu aehist; int aehistcompr; - imgsrc->getAutoExpHistogram (aehist, aehistcompr); - ipf.getAutoExp (aehist, aehistcompr, params.toneCurve.clip, expcomp, bright, contr, black, hlcompr, hlcomprthresh); + imgsrc->getAutoExpHistogram(aehist, aehistcompr); + ipf.getAutoExp(aehist, aehistcompr, params.toneCurve.clip, expcomp, bright, contr, black, hlcompr, hlcomprthresh); } + if (params.toneCurve.histmatching) { if (!params.toneCurve.fromHistMatching) { imgsrc->getAutoMatchedToneCurve(params.icm, params.toneCurve.curve); @@ -787,14 +800,13 @@ private: params.toneCurve.brightness = 0; params.toneCurve.contrast = 0; params.toneCurve.black = 0; - } + } // at this stage, we can flush the raw data to free up quite an important amount of memory // commented out because it makes the application crash when batch processing... // TODO: find a better place to flush rawData and rawRGB if (flush) { - imgsrc->flushRawData(); - imgsrc->flushRGB(); + imgsrc->flush(); } return true; @@ -816,29 +828,29 @@ private: noiseLCurve.Reset(); } - if (denoiseParams.enabled && (noiseLCurve || noiseCCurve )) { + if (denoiseParams.enabled && (noiseLCurve || noiseCCurve)) { // we only need image reduced to 1/4 here - calclum = new Imagefloat ((fw + 1) / 2, (fh + 1) / 2); //for luminance denoise curve + calclum = new Imagefloat((fw + 1) / 2, (fh + 1) / 2); //for luminance denoise curve #ifdef _OPENMP #pragma omp parallel for #endif for (int ii = 0; ii < fh; ii += 2) { for (int jj = 0; jj < fw; jj += 2) { - calclum->r (ii >> 1, jj >> 1) = baseImg->r (ii, jj); - calclum->g (ii >> 1, jj >> 1) = baseImg->g (ii, jj); - calclum->b (ii >> 1, jj >> 1) = baseImg->b (ii, jj); + calclum->r(ii >> 1, jj >> 1) = baseImg->r(ii, jj); + calclum->g(ii >> 1, jj >> 1) = baseImg->g(ii, jj); + calclum->b(ii >> 1, jj >> 1) = baseImg->b(ii, jj); } } - imgsrc->convertColorSpace (calclum, params.icm, currWB); + imgsrc->convertColorSpace(calclum, params.icm, currWB); } if (denoiseParams.enabled) { ImProcFunctions &ipf = * (ipf_p.get()); float nresi, highresi; int kall = 2; - ipf.RGB_denoise (kall, baseImg, baseImg, calclum, ch_M, max_r, max_b, imgsrc->isRAW(), denoiseParams, imgsrc->getDirPyrDenoiseExpComp(), noiseLCurve, noiseCCurve, nresi, highresi); + ipf.RGB_denoise(kall, baseImg, baseImg, calclum, ch_M, max_r, max_b, imgsrc->isRAW(), denoiseParams, imgsrc->getDirPyrDenoiseExpComp(), noiseLCurve, noiseCCurve, nresi, highresi); } @@ -861,12 +873,12 @@ private: //ImProcFunctions ipf (¶ms, true); ImProcFunctions &ipf = * (ipf_p.get()); - imgsrc->convertColorSpace (baseImg, params.icm, currWB); + imgsrc->convertColorSpace(baseImg, params.icm, currWB); // perform first analysis - hist16 (65536); + hist16(65536); - ipf.firstAnalysis (baseImg, params, hist16); + ipf.firstAnalysis(baseImg, params, hist16); ipf.dehaze(baseImg); ipf.ToneMapFattal02(baseImg); @@ -874,14 +886,17 @@ private: // perform transform (excepted resizing) if (ipf.needsTransform(fw, fh, imgsrc->getRotateDegree(), imgsrc->getMetaData())) { Imagefloat* trImg = nullptr; + if (ipf.needsLuminanceOnly()) { trImg = baseImg; } else { - trImg = new Imagefloat (fw, fh); + trImg = new Imagefloat(fw, fh); } - ipf.transform (baseImg, trImg, 0, 0, 0, 0, fw, fh, fw, fh, + + ipf.transform(baseImg, trImg, 0, 0, 0, 0, fw, fh, fw, fh, imgsrc->getMetaData(), imgsrc->getRotateDegree(), true, true); - if(trImg != baseImg) { + + if (trImg != baseImg) { delete baseImg; baseImg = trImg; } @@ -897,10 +912,10 @@ private: if (params.dirpyrequalizer.cbdlMethod == "bef" && params.dirpyrequalizer.enabled && !params.colorappearance.enabled) { const int W = baseImg->getWidth(); const int H = baseImg->getHeight(); - LabImage labcbdl (W, H); - ipf.rgb2lab (*baseImg, labcbdl, params.icm.workingProfile); - ipf.dirpyrequalizer (&labcbdl, 1); - ipf.lab2rgb (labcbdl, *baseImg, params.icm.workingProfile); + LabImage labcbdl(W, H); + ipf.rgb2lab(*baseImg, labcbdl, params.icm.workingProfile); + ipf.dirpyrequalizer(&labcbdl, 1); + ipf.lab2rgb(labcbdl, *baseImg, params.icm.workingProfile); } //gamma TRC working @@ -910,55 +925,55 @@ private: if (profile == "sRGB" || profile == "Adobe RGB" || profile == "ProPhoto" || profile == "WideGamut" || profile == "BruceRGB" || profile == "Beta RGB" || profile == "BestRGB" || profile == "Rec2020" || profile == "ACESp0" || profile == "ACESp1") { const int cw = baseImg->getWidth(); const int ch = baseImg->getHeight(); - cmsHTRANSFORM dummy = nullptr; + cmsHTRANSFORM dummyTransForm = nullptr; // put gamma TRC to 1 - ipf.workingtrc(baseImg, baseImg, cw, ch, -5, params.icm.workingProfile, 2.4, 12.92310, dummy, true, false, false); + ipf.workingtrc(baseImg, baseImg, cw, ch, -5, params.icm.workingProfile, 2.4, 12.92310, dummyTransForm, true, false, false); //adjust TRC - ipf.workingtrc(baseImg, baseImg, cw, ch, 5, params.icm.workingProfile, params.icm.workingTRCGamma, params.icm.workingTRCSlope, dummy, false, true, false); + ipf.workingtrc(baseImg, baseImg, cw, ch, 5, params.icm.workingProfile, params.icm.workingTRCGamma, params.icm.workingTRCSlope, dummyTransForm, false, true, false); } } // RGB processing - curve1 (65536); - curve2 (65536); - curve (65536, 0); - satcurve (65536, 0); - lhskcurve (65536, 0); - lumacurve (32770, 0); // lumacurve[32768] and lumacurve[32769] will be set to 32768 and 32769 later to allow linear interpolation - clcurve (65536, 0); - wavclCurve (65536, 0); + curve1(65536); + curve2(65536); + curve(65536, 0); + satcurve(65536, 0); + lhskcurve(65536, 0); + lumacurve(32770, 0); // lumacurve[32768] and lumacurve[32769] will be set to 32768 and 32769 later to allow linear interpolation + clcurve(65536, 0); + wavclCurve(65536, 0); //if(params.blackwhite.enabled) params.toneCurve.hrenabled=false; - CurveFactory::complexCurve (expcomp, black / 65535.0, hlcompr, hlcomprthresh, params.toneCurve.shcompr, bright, contr, - params.toneCurve.curve, params.toneCurve.curve2, - hist16, curve1, curve2, curve, dummy, customToneCurve1, customToneCurve2 ); + CurveFactory::complexCurve(expcomp, black / 65535.0, hlcompr, hlcomprthresh, params.toneCurve.shcompr, bright, contr, + params.toneCurve.curve, params.toneCurve.curve2, + hist16, curve1, curve2, curve, dummy, customToneCurve1, customToneCurve2); - CurveFactory::RGBCurve (params.rgbCurves.rcurve, rCurve, 1); - CurveFactory::RGBCurve (params.rgbCurves.gcurve, gCurve, 1); - CurveFactory::RGBCurve (params.rgbCurves.bcurve, bCurve, 1); + CurveFactory::RGBCurve(params.rgbCurves.rcurve, rCurve, 1); + CurveFactory::RGBCurve(params.rgbCurves.gcurve, gCurve, 1); + CurveFactory::RGBCurve(params.rgbCurves.bcurve, bCurve, 1); bool opautili = false; if (params.colorToning.enabled) { - TMatrix wprof = ICCStore::getInstance()->workingSpaceMatrix (params.icm.workingProfile); + TMatrix wprof = ICCStore::getInstance()->workingSpaceMatrix(params.icm.workingProfile); double wp[3][3] = { {wprof[0][0], wprof[0][1], wprof[0][2]}, {wprof[1][0], wprof[1][1], wprof[1][2]}, {wprof[2][0], wprof[2][1], wprof[2][2]} }; - params.colorToning.getCurves (ctColorCurve, ctOpacityCurve, wp, opautili); - clToningcurve (65536, 0); - CurveFactory::curveToning (params.colorToning.clcurve, clToningcurve, 1); - cl2Toningcurve (65536, 0); - CurveFactory::curveToning (params.colorToning.cl2curve, cl2Toningcurve, 1); + params.colorToning.getCurves(ctColorCurve, ctOpacityCurve, wp, opautili); + clToningcurve(65536, 0); + CurveFactory::curveToning(params.colorToning.clcurve, clToningcurve, 1); + cl2Toningcurve(65536, 0); + CurveFactory::curveToning(params.colorToning.cl2curve, cl2Toningcurve, 1); } - labView = new LabImage (fw, fh); + labView = new LabImage(fw, fh); if (params.blackwhite.enabled) { - CurveFactory::curveBW (params.blackwhite.beforeCurve, params.blackwhite.afterCurve, hist16, dummy, customToneCurvebw1, customToneCurvebw2, 1); + CurveFactory::curveBW(params.blackwhite.beforeCurve, params.blackwhite.afterCurve, hist16, dummy, customToneCurvebw1, customToneCurvebw2, 1); } double rrm, ggm, bbm; @@ -969,7 +984,7 @@ private: if (params.colorToning.enabled && params.colorToning.autosat && params.colorToning.method != "LabGrid") { //for colortoning evaluation of saturation settings float moyS = 0.f; float eqty = 0.f; - ipf.moyeqt (baseImg, moyS, eqty);//return image : mean saturation and standard dev of saturation + ipf.moyeqt(baseImg, moyS, eqty); //return image : mean saturation and standard dev of saturation float satp = ((moyS + 1.5f * eqty) - 0.3f) / 0.7f; //1.5 sigma ==> 93% pixels with high saturation -0.3 / 0.7 convert to Hombre scale if (satp >= 0.92f) { @@ -987,18 +1002,18 @@ private: autor = -9000.f; // This will ask to compute the "auto" values for the B&W tool (have to be inferior to -5000) DCPProfileApplyState as; - DCPProfile *dcpProf = imgsrc->getDCP (params.icm, as); + DCPProfile *dcpProf = imgsrc->getDCP(params.icm, as); LUTu histToneCurve; - ipf.rgbProc (baseImg, labView, nullptr, curve1, curve2, curve, params.toneCurve.saturation, rCurve, gCurve, bCurve, satLimit, satLimitOpacity, ctColorCurve, ctOpacityCurve, opautili, clToningcurve, cl2Toningcurve, customToneCurve1, customToneCurve2, customToneCurvebw1, customToneCurvebw2, rrm, ggm, bbm, autor, autog, autob, expcomp, hlcompr, hlcomprthresh, dcpProf, as, histToneCurve, options.chunkSizeRGB, options.measure); + ipf.rgbProc(baseImg, labView, nullptr, curve1, curve2, curve, params.toneCurve.saturation, rCurve, gCurve, bCurve, satLimit, satLimitOpacity, ctColorCurve, ctOpacityCurve, opautili, clToningcurve, cl2Toningcurve, customToneCurve1, customToneCurve2, customToneCurvebw1, customToneCurvebw2, rrm, ggm, bbm, autor, autog, autob, expcomp, hlcompr, hlcomprthresh, dcpProf, as, histToneCurve, options.chunkSizeRGB, options.measure); if (settings->verbose) { - printf ("Output image / Auto B&W coefs: R=%.2f G=%.2f B=%.2f\n", autor, autog, autob); + printf ("Output image / Auto B&W coefs: R=%.2f G=%.2f B=%.2f\n", static_cast(autor), static_cast(autog), static_cast(autob)); } // if clut was used and size of clut cache == 1 we free the memory used by the clutstore (default clut cache size = 1 for 32 bit OS) - if ( params.filmSimulation.enabled && !params.filmSimulation.clutFilename.empty() && options.clutCacheSize == 1) { + if (params.filmSimulation.enabled && !params.filmSimulation.clutFilename.empty() && options.clutCacheSize == 1) { CLUTStore::getInstance().clearCache(); } @@ -1017,7 +1032,7 @@ private: baseImg = nullptr; if (pl) { - pl->setProgress (0.55); + pl->setProgress(0.55); } //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% @@ -1032,7 +1047,7 @@ private: #pragma omp parallel #endif { - LUTu hist16thr (hist16.getSize()); // one temporary lookup table per thread + LUTu hist16thr(hist16.getSize()); // one temporary lookup table per thread hist16thr.clear(); #ifdef _OPENMP #pragma omp for schedule(static) nowait @@ -1040,7 +1055,7 @@ private: for (int i = 0; i < fh; i++) for (int j = 0; j < fw; j++) { - hist16thr[ (int) ((labView->L[i][j]))]++; + hist16thr[(int)((labView->L[i][j]))]++; } #ifdef _OPENMP @@ -1053,74 +1068,216 @@ private: } bool utili; - CurveFactory::complexLCurve (params.labCurve.brightness, params.labCurve.contrast, params.labCurve.lcurve, hist16, lumacurve, dummy, 1, utili); + CurveFactory::complexLCurve(params.labCurve.brightness, params.labCurve.contrast, params.labCurve.lcurve, hist16, lumacurve, dummy, 1, utili); bool clcutili; - CurveFactory::curveCL (clcutili, params.labCurve.clcurve, clcurve, 1); + CurveFactory::curveCL(clcutili, params.labCurve.clcurve, clcurve, 1); bool ccutili, cclutili; - CurveFactory::complexsgnCurve (autili, butili, ccutili, cclutili, params.labCurve.acurve, params.labCurve.bcurve, params.labCurve.cccurve, - params.labCurve.lccurve, curve1, curve2, satcurve, lhskcurve, 1); + CurveFactory::complexsgnCurve(autili, butili, ccutili, cclutili, params.labCurve.acurve, params.labCurve.bcurve, params.labCurve.cccurve, + params.labCurve.lccurve, curve1, curve2, satcurve, lhskcurve, 1); - ipf.chromiLuminanceCurve (nullptr, 1, labView, labView, curve1, curve2, satcurve, lhskcurve, clcurve, lumacurve, utili, autili, butili, ccutili, cclutili, clcutili, dummy, dummy); + ipf.chromiLuminanceCurve(nullptr, 1, labView, labView, curve1, curve2, satcurve, lhskcurve, clcurve, lumacurve, utili, autili, butili, ccutili, cclutili, clcutili, dummy, dummy); if ((params.colorappearance.enabled && !params.colorappearance.tonecie) || (!params.colorappearance.enabled)) { ipf.EPDToneMap (labView, 0, 1); } - ipf.vibrance (labView); + ipf.vibrance(labView); ipf.labColorCorrectionRegions(labView); // for all treatments Defringe, Sharpening, Contrast detail ,Microcontrast they are activated if "CIECAM" function are disabled if ((params.colorappearance.enabled && !settings->autocielab) || (!params.colorappearance.enabled)) { ipf.impulsedenoise (labView); - ipf.defringe (labView); + ipf.defringe(labView); } if (params.sharpenEdge.enabled) { - ipf.MLsharpen (labView); + ipf.MLsharpen(labView); } if (params.sharpenMicro.enabled) { - if ((params.colorappearance.enabled && !settings->autocielab) || (!params.colorappearance.enabled)) { - ipf.MLmicrocontrast (labView); //!params.colorappearance.sharpcie + if ((params.colorappearance.enabled && !settings->autocielab) || (!params.colorappearance.enabled)) { + ipf.MLmicrocontrast(labView); //!params.colorappearance.sharpcie } } if (((params.colorappearance.enabled && !settings->autocielab) || (!params.colorappearance.enabled)) && params.sharpening.enabled) { - ipf.sharpening (labView, params.sharpening); + ipf.sharpening(labView, params.sharpening); } - WaveletParams WaveParams = params.wavelet; - WavCurve wavCLVCurve; - WavOpacityCurveRG waOpacityCurveRG; - WavOpacityCurveBY waOpacityCurveBY; - WavOpacityCurveW waOpacityCurveW; - WavOpacityCurveWL waOpacityCurveWL; - - params.wavelet.getCurves (wavCLVCurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL ); // directional pyramid wavelet if (params.dirpyrequalizer.cbdlMethod == "aft") { if ((params.colorappearance.enabled && !settings->autocielab) || !params.colorappearance.enabled) { - ipf.dirpyrequalizer (labView, 1); //TODO: this is the luminance tonecurve, not the RGB one + ipf.dirpyrequalizer(labView, 1); //TODO: this is the luminance tonecurve, not the RGB one } } - bool wavcontlutili = false; + if ((params.wavelet.enabled)) { + LabImage *unshar = nullptr; + Glib::ustring provis; - CurveFactory::curveWavContL (wavcontlutili, params.wavelet.wavclCurve, wavclCurve,/* hist16C, dummy,*/ 1); + bool wavcontlutili = false; + WaveletParams WaveParams = params.wavelet; + WavCurve wavCLVCurve; + Wavblcurve wavblcurve; + WavOpacityCurveRG waOpacityCurveRG; + WavOpacityCurveBY waOpacityCurveBY; + WavOpacityCurveW waOpacityCurveW; + WavOpacityCurveWL waOpacityCurveWL; + LabImage *provradius = nullptr; + bool procont = WaveParams.expcontrast; + bool prochro = WaveParams.expchroma; + bool proedge = WaveParams.expedge; + bool profin = WaveParams.expfinal; + bool proton = WaveParams.exptoning; + bool pronois = WaveParams.expnoise; + +/* + if(WaveParams.showmask) { + WaveParams.showmask = false; + WaveParams.expclari = true; + } +*/ + if (WaveParams.softrad > 0.f) { + provradius = new LabImage(fw, fh); + provradius->CopyFrom(labView); + } - if (params.wavelet.enabled) { - ipf.ip_wavelet (labView, labView, 2, WaveParams, wavCLVCurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL, wavclCurve, 1); + params.wavelet.getCurves(wavCLVCurve, wavblcurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL); + + CurveFactory::curveWavContL(wavcontlutili, params.wavelet.wavclCurve, wavclCurve,/* hist16C, dummy,*/ 1); + + if ((WaveParams.ushamethod == "sharp" || WaveParams.ushamethod == "clari") && WaveParams.expclari && WaveParams.CLmethod != "all") { + unshar = new LabImage(fw, fh); + provis = params.wavelet.CLmethod; + params.wavelet.CLmethod = "all"; + ipf.ip_wavelet(labView, labView, 2, WaveParams, wavCLVCurve, wavblcurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL, wavclCurve, 1); + unshar->CopyFrom(labView); + params.wavelet.CLmethod = provis; + + WaveParams.expcontrast = false; + WaveParams.expchroma = false; + WaveParams.expedge = false; + WaveParams.expfinal = false; + WaveParams.exptoning = false; + WaveParams.expnoise = false; + } + + ipf.ip_wavelet(labView, labView, 2, WaveParams, wavCLVCurve, wavblcurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL, wavclCurve, 1); + + if ((WaveParams.ushamethod == "sharp" || WaveParams.ushamethod == "clari") && WaveParams.expclari && WaveParams.CLmethod != "all") { + WaveParams.expcontrast = procont; + WaveParams.expchroma = prochro; + WaveParams.expedge = proedge; + WaveParams.expfinal = profin; + WaveParams.exptoning = proton; + WaveParams.expnoise = pronois; + + if (WaveParams.softrad > 0.f) { + array2D ble(fw, fh); + array2D guid(fw, fh); + Imagefloat *tmpImage = nullptr; + tmpImage = new Imagefloat(fw, fh); +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < fh; ir++) + for (int jr = 0; jr < fw; jr++) { + float X, Y, Z; + float L = provradius->L[ir][jr]; + float a = provradius->a[ir][jr]; + float b = provradius->b[ir][jr]; + Color::Lab2XYZ(L, a, b, X, Y, Z); + + guid[ir][jr] = Y / 32768.f; + float La = labView->L[ir][jr]; + float aa = labView->a[ir][jr]; + float ba = labView->b[ir][jr]; + Color::Lab2XYZ(La, aa, ba, X, Y, Z); + tmpImage->r(ir, jr) = X; + tmpImage->g(ir, jr) = Y; + tmpImage->b(ir, jr) = Z; + ble[ir][jr] = Y / 32768.f; + } + double epsilmax = 0.0001; + double epsilmin = 0.00001; + double aepsil = (epsilmax - epsilmin) / 90.f; + double bepsil = epsilmax - 100.f * aepsil; + double epsil = aepsil * WaveParams.softrad + bepsil; + + float blur = 10.f / 1 * (0.0001f + 0.8f * WaveParams.softrad); + // rtengine::guidedFilter(guid, ble, ble, blur, 0.001, multiTh); + rtengine::guidedFilter(guid, ble, ble, blur, epsil, false); + + + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int ir = 0; ir < fh; ir++) + for (int jr = 0; jr < fw; jr++) { + float X = tmpImage->r(ir, jr); + float Y = 32768.f * ble[ir][jr]; + float Z = tmpImage->b(ir, jr); + float L, a, b; + Color::XYZ2Lab(X, Y, Z, L, a, b); + labView->L[ir][jr] = L; + } + delete tmpImage; + } + + } + + if ((WaveParams.ushamethod == "sharp" || WaveParams.ushamethod == "clari") && WaveParams.expclari && WaveParams.CLmethod != "all") { + float mL = (float)(WaveParams.mergeL / 100.f); + float mC = (float)(WaveParams.mergeC / 100.f); + float mL0; + float mC0; + + if ((WaveParams.CLmethod == "one" || WaveParams.CLmethod == "inf") && WaveParams.Backmethod == "black") { + mL0 = mC0 = 0.f; + mL = -1.5f * mL; + mC = -mC; + } else if (WaveParams.CLmethod == "sup" && WaveParams.Backmethod == "resid") { + mL0 = mL; + mC0 = mC; + } else { + mL0 = mL = mC0 = mC = 0.f; + } + + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int x = 0; x < fh; x++) + for (int y = 0; y < fw; y++) { + labView->L[x][y] = LIM((1.f + mL0) * (unshar->L[x][y]) - mL * labView->L[x][y], 0.f, 32768.f); + labView->a[x][y] = (1.f + mC0) * (unshar->a[x][y]) - mC * labView->a[x][y]; + labView->b[x][y] = (1.f + mC0) * (unshar->b[x][y]) - mC * labView->b[x][y]; + } + + delete unshar; + unshar = NULL; + + if (WaveParams.softrad > 0.f) { + delete provradius; + provradius = NULL; + } + + } + + wavCLVCurve.Reset(); } - wavCLVCurve.Reset(); - ipf.softLight(labView); //Colorappearance and tone-mapping associated @@ -1132,9 +1289,9 @@ private: f_h = fh; } - CieImage *cieView = new CieImage (f_w, (f_h)); + CieImage *cieView = new CieImage(f_w, (f_h)); - CurveFactory::curveLightBrightColor ( + CurveFactory::curveLightBrightColor( params.colorappearance.curve, params.colorappearance.curve2, params.colorappearance.curve3, @@ -1148,24 +1305,26 @@ private: if (params.colorappearance.enabled) { double adap; int imgNum = 0; + if (imgsrc->getSensorType() == ST_BAYER) { imgNum = params.raw.bayersensor.imageNum; } else if (imgsrc->getSensorType() == ST_FUJI_XTRANS) { //imgNum = params.raw.xtranssensor.imageNum; } - float fnum = imgsrc->getMetaData()->getFNumber (imgNum); // F number - float fiso = imgsrc->getMetaData()->getISOSpeed (imgNum) ; // ISO - float fspeed = imgsrc->getMetaData()->getShutterSpeed (imgNum) ; //speed - float fcomp = imgsrc->getMetaData()->getExpComp (imgNum); //compensation + - + + float fnum = imgsrc->getMetaData()->getFNumber(imgNum); // F number + float fiso = imgsrc->getMetaData()->getISOSpeed(imgNum) ; // ISO + float fspeed = imgsrc->getMetaData()->getShutterSpeed(imgNum) ; //speed + float fcomp = imgsrc->getMetaData()->getExpComp(imgNum); //compensation + - if (fnum < 0.3f || fiso < 5.f || fspeed < 0.00001f) { adap = 2000.; }//if no exif data or wrong else { - float E_V = fcomp + log2 ((fnum * fnum) / fspeed / (fiso / 100.f)); + double E_V = fcomp + log2 ((fnum * fnum) / fspeed / (fiso / 100.f)); E_V += params.toneCurve.expcomp;// exposure compensation in tonecurve ==> direct EV - E_V += log2 (params.raw.expos); // exposure raw white point ; log2 ==> linear to EV - adap = powf (2.f, E_V - 3.f); //cd / m2 + E_V += log2(params.raw.expos); // exposure raw white point ; log2 ==> linear to EV + adap = std::pow(2.0, E_V - 3.0); //cd / m2 } LUTf CAMBrightCurveJ; @@ -1187,11 +1346,11 @@ private: //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% if (pl) { - pl->setProgress (0.60); + pl->setProgress(0.60); } int imw, imh; - double tmpScale = ipf.resizeScale (¶ms, fw, fh, imw, imh); + double tmpScale = ipf.resizeScale(¶ms, fw, fh, imw, imh); bool labResize = params.resize.enabled && params.resize.method != "Nearest" && (tmpScale != 1.0 || params.prsharpening.enabled); LabImage *tmplab; @@ -1205,7 +1364,7 @@ private: ch = params.crop.h; if (labResize) { // crop lab data - tmplab = new LabImage (cw, ch); + tmplab = new LabImage(cw, ch); for (int row = 0; row < ch; row++) { for (int col = 0; col < cw; col++) { @@ -1224,13 +1383,14 @@ private: if (labResize) { // resize lab data if ((labView->W != imw || labView->H != imh) && - (params.resize.allowUpscaling || (labView->W >= imw && labView->H >= imh))) { + (params.resize.allowUpscaling || (labView->W >= imw && labView->H >= imh))) { // resize image - tmplab = new LabImage (imw, imh); - ipf.Lanczos (labView, tmplab, tmpScale); + tmplab = new LabImage(imw, imh); + ipf.Lanczos(labView, tmplab, tmpScale); delete labView; labView = tmplab; } + cw = labView->W; ch = labView->H; @@ -1240,13 +1400,11 @@ private: labView->L[i][j] = labView->L[i][j] < 0.f ? 0.f : labView->L[i][j]; } } - ipf.sharpening (labView, params.prsharpening); + + ipf.sharpening(labView, params.prsharpening); } } - cmsHPROFILE jprof = nullptr; - constexpr bool customGamma = false; - constexpr bool useLCMS = false; bool bwonly = params.blackwhite.enabled && !params.colorToning.enabled && !autili && !butili && !params.colorappearance.enabled; ///////////// Custom output gamma has been removed, the user now has to create @@ -1255,10 +1413,10 @@ private: // if Default gamma mode: we use the profile selected in the "Output profile" combobox; // gamma come from the selected profile, otherwise it comes from "Free gamma" tool - Imagefloat* readyImg = ipf.lab2rgbOut (labView, cx, cy, cw, ch, params.icm); + Imagefloat* readyImg = ipf.lab2rgbOut(labView, cx, cy, cw, ch, params.icm); if (settings->verbose) { - printf ("Output profile_: \"%s\"\n", params.icm.outputProfile.c_str()); + printf("Output profile_: \"%s\"\n", params.icm.outputProfile.c_str()); } delete labView; @@ -1268,76 +1426,70 @@ private: if (bwonly) { //force BW r=g=b if (settings->verbose) { - printf ("Force BW\n"); + printf("Force BW\n"); } for (int ccw = 0; ccw < cw; ccw++) { for (int cch = 0; cch < ch; cch++) { - readyImg->r (cch, ccw) = readyImg->g (cch, ccw); - readyImg->b (cch, ccw) = readyImg->g (cch, ccw); + readyImg->r(cch, ccw) = readyImg->g(cch, ccw); + readyImg->b(cch, ccw) = readyImg->g(cch, ccw); } } } if (pl) { - pl->setProgress (0.70); + pl->setProgress(0.70); } if (tmpScale != 1.0 && params.resize.method == "Nearest" && - (params.resize.allowUpscaling || (readyImg->getWidth() >= imw && readyImg->getHeight() >= imh))) { // resize rgb data (gamma applied) - Imagefloat* tempImage = new Imagefloat (imw, imh); - ipf.resize (readyImg, tempImage, tmpScale); + (params.resize.allowUpscaling || (readyImg->getWidth() >= imw && readyImg->getHeight() >= imh))) { // resize rgb data (gamma applied) + Imagefloat* tempImage = new Imagefloat(imw, imh); + ipf.resize(readyImg, tempImage, tmpScale); delete readyImg; readyImg = tempImage; } switch (params.metadata.mode) { - case MetaDataParams::TUNNEL: - // Sending back the whole first root, which won't necessarily be the selected frame number - // and may contain subframe depending on initial raw's hierarchy - readyImg->setMetadata (ii->getMetaData()->getRootExifData ()); - break; - case MetaDataParams::EDIT: - // ask for the correct frame number, but may contain subframe depending on initial raw's hierarchy - readyImg->setMetadata (ii->getMetaData()->getBestExifData(imgsrc, ¶ms.raw), params.exif, params.iptc); - break; - default: // case MetaDataParams::STRIP - // nothing to do - break; + case MetaDataParams::TUNNEL: + // Sending back the whole first root, which won't necessarily be the selected frame number + // and may contain subframe depending on initial raw's hierarchy + readyImg->setMetadata(initialImage->getMetaData()->getRootExifData()); + break; + + case MetaDataParams::EDIT: + // ask for the correct frame number, but may contain subframe depending on initial raw's hierarchy + readyImg->setMetadata(initialImage->getMetaData()->getBestExifData(imgsrc, ¶ms.raw), params.exif, params.iptc); + break; + + default: // case MetaDataParams::STRIP + // nothing to do + break; } // Setting the output curve to readyImg - if (customGamma) { - if (!useLCMS) { - // use corrected sRGB profile in order to apply a good TRC if present, otherwise use LCMS2 profile generated by lab2rgb16 w/ gamma - ProfileContent pc (jprof); - readyImg->setOutputProfile (pc.getData().c_str(), pc.getData().size()); - } - } else { - // use the selected output profile if present, otherwise use LCMS2 profile generate by lab2rgb16 w/ gamma + // use the selected output profile if present, otherwise use LCMS2 profile generate by lab2rgb16 w/ gamma - if (!params.icm.outputProfile.empty() && params.icm.outputProfile != ColorManagementParams::NoICMString) { + if (!params.icm.outputProfile.empty() && params.icm.outputProfile != ColorManagementParams::NoICMString) { - // if ICCStore::getInstance()->getProfile send back an object, then ICCStore::getInstance()->getContent will do too - cmsHPROFILE jprof = ICCStore::getInstance()->getProfile (params.icm.outputProfile); //get outProfile + // if ICCStore::getInstance()->getProfile send back an object, then ICCStore::getInstance()->getContent will do too + cmsHPROFILE jprof = ICCStore::getInstance()->getProfile(params.icm.outputProfile); //get outProfile - if (jprof == nullptr) { - if (settings->verbose) { - printf ("\"%s\" ICC output profile not found!\n - use LCMS2 substitution\n", params.icm.outputProfile.c_str()); - } - } else { - if (settings->verbose) { - printf ("Using \"%s\" output profile\n", params.icm.outputProfile.c_str()); - } - - ProfileContent pc = ICCStore::getInstance()->getContent (params.icm.outputProfile); - readyImg->setOutputProfile (pc.getData().c_str(), pc.getData().size()); + if (jprof == nullptr) { + if (settings->verbose) { + printf("\"%s\" ICC output profile not found!\n - use LCMS2 substitution\n", params.icm.outputProfile.c_str()); } } else { - // No ICM - readyImg->setOutputProfile (nullptr, 0); + if (settings->verbose) { + printf("Using \"%s\" output profile\n", params.icm.outputProfile.c_str()); + } + + ProfileContent pc = ICCStore::getInstance()->getContent(params.icm.outputProfile); + readyImg->setOutputProfile(pc.getData().c_str(), pc.getData().size()); } + } else { + // No ICM + readyImg->setOutputProfile(nullptr, 0); } // t2.set(); @@ -1345,13 +1497,13 @@ private: // printf("Total:- %d usec\n", t2.etime(t1)); if (!job->initialImage) { - ii->decreaseRef (); + initialImage->decreaseRef(); } delete job; if (pl) { - pl->setProgress (0.75); + pl->setProgress(0.75); } /* curve1.reset();curve2.reset(); @@ -1375,10 +1527,10 @@ private: ImProcFunctions &ipf = * (ipf_p.get()); int imw, imh; - double scale_factor = ipf.resizeScale (¶ms, fw, fh, imw, imh); + double scale_factor = ipf.resizeScale(¶ms, fw, fh, imw, imh); - std::unique_ptr tmplab (new LabImage (fw, fh)); - ipf.rgb2lab (*baseImg, *tmplab, params.icm.workingProfile); + std::unique_ptr tmplab(new LabImage(fw, fh)); + ipf.rgb2lab(*baseImg, *tmplab, params.icm.workingProfile); if (params.crop.enabled) { int cx = params.crop.x; @@ -1386,7 +1538,7 @@ private: int cw = params.crop.w; int ch = params.crop.h; - std::unique_ptr cropped (new LabImage (cw, ch)); + std::unique_ptr cropped(new LabImage(cw, ch)); for (int row = 0; row < ch; row++) { for (int col = 0; col < cw; col++) { @@ -1396,29 +1548,29 @@ private: } } - tmplab = std::move (cropped); + tmplab = std::move(cropped); } - assert (params.resize.enabled); + assert(params.resize.enabled); // resize image if (params.resize.allowUpscaling || (imw <= fw && imh <= fh)) { - std::unique_ptr resized (new LabImage (imw, imh)); - ipf.Lanczos (tmplab.get(), resized.get(), scale_factor); - tmplab = std::move (resized); + std::unique_ptr resized(new LabImage(imw, imh)); + ipf.Lanczos(tmplab.get(), resized.get(), scale_factor); + tmplab = std::move(resized); } - adjust_procparams (scale_factor); + adjust_procparams(scale_factor); fw = imw; fh = imh; delete baseImg; - baseImg = new Imagefloat (fw, fh); - ipf.lab2rgb (*tmplab, *baseImg, params.icm.workingProfile); + baseImg = new Imagefloat(fw, fh); + ipf.lab2rgb(*tmplab, *baseImg, params.icm.workingProfile); } - void adjust_procparams (double scale_factor) + void adjust_procparams(double scale_factor) { procparams::ProcParams ¶ms = job->pparams; procparams::ProcParams defaultparams; @@ -1449,13 +1601,13 @@ private: lcurve[i] *= min(noise_factor /* * scale_factor*/, 1.0); } - noiseLCurve.Set (lcurve); + noiseLCurve.Set(lcurve); const char *medmethods[] = { "soft", "33", "55soft", "55", "77", "99" }; if (params.dirpyrDenoise.median) { auto &key = params.dirpyrDenoise.methodmed == "RGB" ? params.dirpyrDenoise.rgbmethod : params.dirpyrDenoise.medmethod; - for (int i = 1; i < int (sizeof (medmethods) / sizeof (const char *)); ++i) { + for (int i = 1; i < int (sizeof(medmethods) / sizeof(const char *)); ++i) { if (key == medmethods[i]) { int j = i - int (1.0 / scale_factor); @@ -1473,17 +1625,17 @@ private: params.epd.scale *= scale_factor; //params.epd.edgeStopping *= scale_factor; - const double dirpyreq_scale = min (scale_factor * 1.5, 1.0); + const double dirpyreq_scale = min(scale_factor * 1.5, 1.0); for (int i = 0; i < 6; ++i) { - adjust_radius (defaultparams.dirpyrequalizer.mult[i], dirpyreq_scale, - params.dirpyrequalizer.mult[i]); + adjust_radius(defaultparams.dirpyrequalizer.mult[i], dirpyreq_scale, + params.dirpyrequalizer.mult[i]); } params.dirpyrequalizer.threshold *= scale_factor; - adjust_radius (defaultparams.defringe.radius, scale_factor, - params.defringe.radius); + adjust_radius(defaultparams.defringe.radius, scale_factor, + params.defringe.radius); params.sh.radius *= scale_factor; params.localContrast.radius *= scale_factor; @@ -1509,7 +1661,7 @@ private: // internal state std::unique_ptr ipf_p; - InitialImage *ii; + InitialImage *initialImage; ImageSource *imgsrc; int fw; int fh; @@ -1578,40 +1730,40 @@ private: } // namespace -IImagefloat* processImage (ProcessingJob* pjob, int& errorCode, ProgressListener* pl, bool flush) +IImagefloat* processImage(ProcessingJob* pjob, int& errorCode, ProgressListener* pl, bool flush) { - ImageProcessor proc (pjob, errorCode, pl, flush); + ImageProcessor proc(pjob, errorCode, pl, flush); return proc(); } -void batchProcessingThread (ProcessingJob* job, BatchProcessingListener* bpl) +void batchProcessingThread(ProcessingJob* job, BatchProcessingListener* bpl) { ProcessingJob* currentJob = job; while (currentJob) { int errorCode; - IImagefloat* img = processImage (currentJob, errorCode, bpl, true); + IImagefloat* img = processImage(currentJob, errorCode, bpl, true); if (errorCode) { - bpl->error (M ("MAIN_MSG_CANNOTLOAD")); + bpl->error(M("MAIN_MSG_CANNOTLOAD")); currentJob = nullptr; } else { try { - currentJob = bpl->imageReady (img); + currentJob = bpl->imageReady(img); } catch (Glib::Exception& ex) { - bpl->error (ex.what()); + bpl->error(ex.what()); currentJob = nullptr; } } } } -void startBatchProcessing (ProcessingJob* job, BatchProcessingListener* bpl) +void startBatchProcessing(ProcessingJob* job, BatchProcessingListener* bpl) { if (bpl) { - Glib::Thread::create (sigc::bind (sigc::ptr_fun (batchProcessingThread), job, bpl), 0, true, true, Glib::THREAD_PRIORITY_LOW); + Glib::Thread::create(sigc::bind(sigc::ptr_fun(batchProcessingThread), job, bpl), 0, true, true, Glib::THREAD_PRIORITY_LOW); } } diff --git a/rtengine/sleef.h b/rtengine/sleef.h index b7655258b..fc23cbad9 100644 --- a/rtengine/sleef.h +++ b/rtengine/sleef.h @@ -929,7 +929,7 @@ __inline float mulsignf(float x, float y) { return intBitsToFloat(floatToRawIntBits(x) ^ (floatToRawIntBits(y) & (1 << 31))); } -__inline float signf(float d) { return copysign(1, d); } +__inline float signf(float d) { return std::copysign(1.f, d); } __inline float mlaf(float x, float y, float z) { return x * y + z; } __inline int xisnanf(float x) { return x != x; } diff --git a/rtengine/sleefsseavx.c b/rtengine/sleefsseavx.c deleted file mode 100644 index 0af516f9b..000000000 --- a/rtengine/sleefsseavx.c +++ /dev/null @@ -1,1483 +0,0 @@ -//////////////////////////////////////////////////////////////// -// -// this code was taken from http://shibatch.sourceforge.net/ -// Many thanks to the author of original version: Naoki Shibata -// -// This version contains modifications made by Ingo Weyrich -// -//////////////////////////////////////////////////////////////// - - -#ifndef SLEEFSSEAVX -#define SLEEFSSEAVX - -#include -#include "rt_math.h" -#ifdef __SSE2__ -#include "helpersse2.h" - -#ifdef ENABLE_AVX -#include "helperavx.h" -#endif - -#ifdef __GNUC__ -#define INLINE __inline -#else -#define INLINE inline -#endif - -#define PI4_A .7853981554508209228515625 -#define PI4_B .794662735614792836713604629039764404296875e-8 -#define PI4_C .306161699786838294306516483068750264552437361480769e-16 -#define M_4_PI 1.273239544735162542821171882678754627704620361328125 - -#define L2U .69314718055966295651160180568695068359375 -#define L2L .28235290563031577122588448175013436025525412068e-12 -#define R_LN2 1.442695040888963407359924681001892137426645954152985934135449406931 - -#define PI4_Af 0.78515625f -#define PI4_Bf 0.00024127960205078125f -#define PI4_Cf 6.3329935073852539062e-07f -#define PI4_Df 4.9604681473525147339e-10f - -#define L2Uf 0.693145751953125f -#define L2Lf 1.428606765330187045e-06f -#define R_LN2f 1.442695040888963407359924681001892137426645954152985934135449406931f - -#define INFINITYf ((float)rtengine::RT_INFINITY) -#define NANf ((float)rtengine::RT_NAN) - -static INLINE vdouble vadd3(vdouble v0, vdouble v1, vdouble v2) { - return vadd(vadd(v0, v1), v2); -} - -static INLINE vdouble vadd4(vdouble v0, vdouble v1, vdouble v2, vdouble v3) { - return vadd3(vadd(v0, v1), v2, v3); -} - -static INLINE vdouble vadd5(vdouble v0, vdouble v1, vdouble v2, vdouble v3, vdouble v4) { - return vadd4(vadd(v0, v1), v2, v3, v4); -} - -static INLINE vdouble vadd6(vdouble v0, vdouble v1, vdouble v2, vdouble v3, vdouble v4, vdouble v5) { - return vadd5(vadd(v0, v1), v2, v3, v4, v5); -} - -static INLINE vdouble vadd7(vdouble v0, vdouble v1, vdouble v2, vdouble v3, vdouble v4, vdouble v5, vdouble v6) { - return vadd6(vadd(v0, v1), v2, v3, v4, v5, v6); -} - -static INLINE vdouble vsub3(vdouble v0, vdouble v1, vdouble v2) { - return vsub(vsub(v0, v1), v2); -} - -static INLINE vdouble vsub4(vdouble v0, vdouble v1, vdouble v2, vdouble v3) { - return vsub3(vsub(v0, v1), v2, v3); -} - -static INLINE vdouble vsub5(vdouble v0, vdouble v1, vdouble v2, vdouble v3, vdouble v4) { - return vsub4(vsub(v0, v1), v2, v3, v4); -} - -// - -static INLINE vdouble2 normalize_d(vdouble2 t) { - vdouble2 s; - - s.x = vadd(t.x, t.y); - s.y = vadd(vsub(t.x, s.x), t.y); - - return s; -} - -static INLINE vdouble2 scale_d(vdouble2 d, vdouble s) { - vdouble2 r = {vmul(d.x, s), vmul(d.y, s)}; - return r; -} - -static INLINE vdouble2 add_ss(vdouble x, vdouble y) { - vdouble2 r; - - r.x = vadd(x, y); - r.y = vadd(vsub(x, r.x), y); - - return r; -} - -static INLINE vdouble2 add2_ss(vdouble x, vdouble y) { - vdouble2 r; - - r.x = vadd(x, y); - vdouble v = vsub(r.x, x); - r.y = vadd(vsub(x, vsub(r.x, v)), vsub(y, v)); - - return r; -} - -static INLINE vdouble2 add_ds(vdouble2 x, vdouble y) { - vdouble2 r; - - r.x = vadd(x.x, y); - r.y = vadd3(vsub(x.x, r.x), y, x.y); - - return r; -} - -static INLINE vdouble2 add2_ds(vdouble2 x, vdouble y) { - vdouble2 r; - - r.x = vadd(x.x, y); - vdouble v = vsub(r.x, x.x); - r.y = vadd(vsub(x.x, vsub(r.x, v)), vsub(y, v)); - r.y = vadd(r.y, x.y); - - return r; -} - -static INLINE vdouble2 add_sd(vdouble x, vdouble2 y) { - vdouble2 r; - - r.x = vadd(x, y.x); - r.y = vadd3(vsub(x, r.x), y.x, y.y); - - return r; -} - -static INLINE vdouble2 add_dd(vdouble2 x, vdouble2 y) { - // |x| >= |y| - - vdouble2 r; - - r.x = vadd(x.x, y.x); - r.y = vadd4(vsub(x.x, r.x), y.x, x.y, y.y); - - return r; -} - -static INLINE vdouble2 add2_dd(vdouble2 x, vdouble2 y) { - vdouble2 r; - - r.x = vadd(x.x, y.x); - vdouble v = vsub(r.x, x.x); - r.y = vadd(vsub(x.x, vsub(r.x, v)), vsub(y.x, v)); - r.y = vadd(r.y, vadd(x.y, y.y)); - - return r; -} - -static INLINE vdouble2 div_dd(vdouble2 n, vdouble2 d) { - vdouble t = vrec(d.x); - vdouble dh = vupper(d.x), dl = vsub(d.x, dh); - vdouble th = vupper(t ), tl = vsub(t , th); - vdouble nhh = vupper(n.x), nhl = vsub(n.x, nhh); - - vdouble2 q; - - q.x = vmul(n.x, t); - - vdouble u = vadd5(vsub(vmul(nhh, th), q.x), vmul(nhh, tl), vmul(nhl, th), vmul(nhl, tl), - vmul(q.x, vsub5(vcast_vd_d(1), vmul(dh, th), vmul(dh, tl), vmul(dl, th), vmul(dl, tl)))); - - q.y = vadd(vmul(t, vsub(n.y, vmul(q.x, d.y))), u); - - return q; -} - -static INLINE vdouble2 mul_ss(vdouble x, vdouble y) { - vdouble xh = vupper(x), xl = vsub(x, xh); - vdouble yh = vupper(y), yl = vsub(y, yh); - vdouble2 r; - - r.x = vmul(x, y); - r.y = vadd5(vmul(xh, yh), vneg(r.x), vmul(xl, yh), vmul(xh, yl), vmul(xl, yl)); - - return r; -} - -static INLINE vdouble2 mul_ds(vdouble2 x, vdouble y) { - vdouble xh = vupper(x.x), xl = vsub(x.x, xh); - vdouble yh = vupper(y ), yl = vsub(y , yh); - vdouble2 r; - - r.x = vmul(x.x, y); - r.y = vadd6(vmul(xh, yh), vneg(r.x), vmul(xl, yh), vmul(xh, yl), vmul(xl, yl), vmul(x.y, y)); - - return r; -} - -static INLINE vdouble2 mul_dd(vdouble2 x, vdouble2 y) { - vdouble xh = vupper(x.x), xl = vsub(x.x, xh); - vdouble yh = vupper(y.x), yl = vsub(y.x, yh); - vdouble2 r; - - r.x = vmul(x.x, y.x); - r.y = vadd7(vmul(xh, yh), vneg(r.x), vmul(xl, yh), vmul(xh, yl), vmul(xl, yl), vmul(x.x, y.y), vmul(x.y, y.x)); - - return r; -} - -static INLINE vdouble2 squ_d(vdouble2 x) { - vdouble xh = vupper(x.x), xl = vsub(x.x, xh); - vdouble2 r; - - r.x = vmul(x.x, x.x); - r.y = vadd5(vmul(xh, xh), vneg(r.x), vmul(vadd(xh, xh), xl), vmul(xl, xl), vmul(x.x, vadd(x.y, x.y))); - - return r; -} - -static INLINE vdouble2 rec_s(vdouble d) { - vdouble t = vrec(d); - vdouble dh = vupper(d), dl = vsub(d, dh); - vdouble th = vupper(t), tl = vsub(t, th); - vdouble2 q; - - q.x = t; - q.y = vmul(t, vsub5(vcast_vd_d(1), vmul(dh, th), vmul(dh, tl), vmul(dl, th), vmul(dl, tl))); - - return q; -} - -static INLINE vdouble2 sqrt_d(vdouble2 d) { - vdouble t = vsqrt(vadd(d.x, d.y)); - return scale_d(mul_dd(add2_dd(d, mul_ss(t, t)), rec_s(t)), vcast_vd_d(0.5)); -} - -// - -static INLINE vdouble xldexp(vdouble x, vint q) { return vldexp(x, q); } - -static INLINE vint xilogb(vdouble d) { - vdouble e = vcast_vd_vi(vsubi(vilogbp1(vabs(d)), vcast_vi_i(1))); - e = vsel(vmask_eq(d, vcast_vd_d(0)), vcast_vd_d(-2147483648.0), e); - e = vsel(vmask_eq(vabs(d), vcast_vd_d(rtengine::RT_INFINITY)), vcast_vd_d(2147483647), e); - return vrint_vi_vd(e); -} - -static INLINE vdouble xsin(vdouble d) { - vint q; - vdouble u, s; - - q = vrint_vi_vd(vmul(d, vcast_vd_d(rtengine::RT_1_PI))); - - u = vcast_vd_vi(q); - d = vadd(d, vmul(u, vcast_vd_d(-PI4_A*4))); - d = vadd(d, vmul(u, vcast_vd_d(-PI4_B*4))); - d = vadd(d, vmul(u, vcast_vd_d(-PI4_C*4))); - - s = vmul(d, d); - - d = vsel(vmaski_eq(vandi(q, vcast_vi_i(1)), vcast_vi_i(1)), vneg(d), d); - - u = vcast_vd_d(-7.97255955009037868891952e-18); - u = vmla(u, s, vcast_vd_d(2.81009972710863200091251e-15)); - u = vmla(u, s, vcast_vd_d(-7.64712219118158833288484e-13)); - u = vmla(u, s, vcast_vd_d(1.60590430605664501629054e-10)); - u = vmla(u, s, vcast_vd_d(-2.50521083763502045810755e-08)); - u = vmla(u, s, vcast_vd_d(2.75573192239198747630416e-06)); - u = vmla(u, s, vcast_vd_d(-0.000198412698412696162806809)); - u = vmla(u, s, vcast_vd_d(0.00833333333333332974823815)); - u = vmla(u, s, vcast_vd_d(-0.166666666666666657414808)); - - u = vmla(s, vmul(u, d), d); - - return u; -} - -static INLINE vdouble xcos(vdouble d) { - vint q; - vdouble u, s; - - q = vrint_vi_vd(vsub(vmul(d, vcast_vd_d(rtengine::RT_1_PI)), vcast_vd_d(0.5))); - q = vaddi(vaddi(q, q), vcast_vi_i(1)); - - u = vcast_vd_vi(q); - d = vadd(d, vmul(u, vcast_vd_d(-PI4_A*2))); - d = vadd(d, vmul(u, vcast_vd_d(-PI4_B*2))); - d = vadd(d, vmul(u, vcast_vd_d(-PI4_C*2))); - - s = vmul(d, d); - - d = vsel(vmaski_eq(vandi(q, vcast_vi_i(2)), vcast_vi_i(0)), vneg(d), d); - - u = vcast_vd_d(-7.97255955009037868891952e-18); - u = vmla(u, s, vcast_vd_d(2.81009972710863200091251e-15)); - u = vmla(u, s, vcast_vd_d(-7.64712219118158833288484e-13)); - u = vmla(u, s, vcast_vd_d(1.60590430605664501629054e-10)); - u = vmla(u, s, vcast_vd_d(-2.50521083763502045810755e-08)); - u = vmla(u, s, vcast_vd_d(2.75573192239198747630416e-06)); - u = vmla(u, s, vcast_vd_d(-0.000198412698412696162806809)); - u = vmla(u, s, vcast_vd_d(0.00833333333333332974823815)); - u = vmla(u, s, vcast_vd_d(-0.166666666666666657414808)); - - u = vmla(s, vmul(u, d), d); - - return u; -} - -static INLINE vdouble2 xsincos(vdouble d) { - vint q; - vmask m; - vdouble u, s, t, rx, ry; - vdouble2 r; - - q = vrint_vi_vd(vmul(d, vcast_vd_d(rtengine::RT_2_PI))); - - s = d; - - u = vcast_vd_vi(q); - s = vmla(u, vcast_vd_d(-PI4_A*2), s); - s = vmla(u, vcast_vd_d(-PI4_B*2), s); - s = vmla(u, vcast_vd_d(-PI4_C*2), s); - - t = s; - - s = vmul(s, s); - - u = vcast_vd_d(1.58938307283228937328511e-10); - u = vmla(u, s, vcast_vd_d(-2.50506943502539773349318e-08)); - u = vmla(u, s, vcast_vd_d(2.75573131776846360512547e-06)); - u = vmla(u, s, vcast_vd_d(-0.000198412698278911770864914)); - u = vmla(u, s, vcast_vd_d(0.0083333333333191845961746)); - u = vmla(u, s, vcast_vd_d(-0.166666666666666130709393)); - u = vmul(vmul(u, s), t); - - rx = vadd(t, u); - - u = vcast_vd_d(-1.13615350239097429531523e-11); - u = vmla(u, s, vcast_vd_d(2.08757471207040055479366e-09)); - u = vmla(u, s, vcast_vd_d(-2.75573144028847567498567e-07)); - u = vmla(u, s, vcast_vd_d(2.48015872890001867311915e-05)); - u = vmla(u, s, vcast_vd_d(-0.00138888888888714019282329)); - u = vmla(u, s, vcast_vd_d(0.0416666666666665519592062)); - u = vmla(u, s, vcast_vd_d(-0.5)); - - ry = vadd(vcast_vd_d(1), vmul(s, u)); - - m = vmaski_eq(vandi(q, vcast_vi_i(1)), vcast_vi_i(0)); - r.x = vsel(m, rx, ry); - r.y = vsel(m, ry, rx); - - m = vmaski_eq(vandi(q, vcast_vi_i(2)), vcast_vi_i(2)); - r.x = vreinterpret_vd_vm(vxorm(vandm(m, vreinterpret_vm_vd(vcast_vd_d(-0.0))), vreinterpret_vm_vd(r.x))); - - m = vmaski_eq(vandi(vaddi(q, vcast_vi_i(1)), vcast_vi_i(2)), vcast_vi_i(2)); - r.y = vreinterpret_vd_vm(vxorm(vandm(m, vreinterpret_vm_vd(vcast_vd_d(-0.0))), vreinterpret_vm_vd(r.y))); - - m = vmask_isinf(d); - r.x = vsel(m, vcast_vd_d(rtengine::RT_NAN), r.x); - r.y = vsel(m, vcast_vd_d(rtengine::RT_NAN), r.y); - - return r; -} - -static INLINE vdouble xtan(vdouble d) { - vint q; - vdouble u, s, x; - vmask m; - - q = vrint_vi_vd(vmul(d, vcast_vd_d(rtengine::RT_2_PI))); - - u = vcast_vd_vi(q); - x = vadd(d, vmul(u, vcast_vd_d(-PI4_A*2))); - x = vadd(x, vmul(u, vcast_vd_d(-PI4_B*2))); - x = vadd(x, vmul(u, vcast_vd_d(-PI4_C*2))); - - s = vmul(x, x); - - m = vmaski_eq(vandi(q, vcast_vi_i(1)), vcast_vi_i(1)); - x = vsel(m, vneg(x), x); - - u = vcast_vd_d(1.01419718511083373224408e-05); - u = vmla(u, s, vcast_vd_d(-2.59519791585924697698614e-05)); - u = vmla(u, s, vcast_vd_d(5.23388081915899855325186e-05)); - u = vmla(u, s, vcast_vd_d(-3.05033014433946488225616e-05)); - u = vmla(u, s, vcast_vd_d(7.14707504084242744267497e-05)); - u = vmla(u, s, vcast_vd_d(8.09674518280159187045078e-05)); - u = vmla(u, s, vcast_vd_d(0.000244884931879331847054404)); - u = vmla(u, s, vcast_vd_d(0.000588505168743587154904506)); - u = vmla(u, s, vcast_vd_d(0.00145612788922812427978848)); - u = vmla(u, s, vcast_vd_d(0.00359208743836906619142924)); - u = vmla(u, s, vcast_vd_d(0.00886323944362401618113356)); - u = vmla(u, s, vcast_vd_d(0.0218694882853846389592078)); - u = vmla(u, s, vcast_vd_d(0.0539682539781298417636002)); - u = vmla(u, s, vcast_vd_d(0.133333333333125941821962)); - u = vmla(u, s, vcast_vd_d(0.333333333333334980164153)); - - u = vmla(s, vmul(u, x), x); - - u = vsel(m, vrec(u), u); - - u = vsel(vmask_isinf(d), vcast_vd_d(rtengine::RT_NAN), u); - - return u; -} - -static INLINE vdouble atan2k(vdouble y, vdouble x) { - vdouble s, t, u; - vint q; - vmask p; - - q = vseli_lt(x, vcast_vd_d(0), vcast_vi_i(-2), vcast_vi_i(0)); - x = vabs(x); - - q = vseli_lt(x, y, vaddi(q, vcast_vi_i(1)), q); - p = vmask_lt(x, y); - s = vsel (p, vneg(x), y); - t = vmax (x, y); - - s = vdiv(s, t); - t = vmul(s, s); - - u = vcast_vd_d(-1.88796008463073496563746e-05); - u = vmla(u, t, vcast_vd_d(0.000209850076645816976906797)); - u = vmla(u, t, vcast_vd_d(-0.00110611831486672482563471)); - u = vmla(u, t, vcast_vd_d(0.00370026744188713119232403)); - u = vmla(u, t, vcast_vd_d(-0.00889896195887655491740809)); - u = vmla(u, t, vcast_vd_d(0.016599329773529201970117)); - u = vmla(u, t, vcast_vd_d(-0.0254517624932312641616861)); - u = vmla(u, t, vcast_vd_d(0.0337852580001353069993897)); - u = vmla(u, t, vcast_vd_d(-0.0407629191276836500001934)); - u = vmla(u, t, vcast_vd_d(0.0466667150077840625632675)); - u = vmla(u, t, vcast_vd_d(-0.0523674852303482457616113)); - u = vmla(u, t, vcast_vd_d(0.0587666392926673580854313)); - u = vmla(u, t, vcast_vd_d(-0.0666573579361080525984562)); - u = vmla(u, t, vcast_vd_d(0.0769219538311769618355029)); - u = vmla(u, t, vcast_vd_d(-0.090908995008245008229153)); - u = vmla(u, t, vcast_vd_d(0.111111105648261418443745)); - u = vmla(u, t, vcast_vd_d(-0.14285714266771329383765)); - u = vmla(u, t, vcast_vd_d(0.199999999996591265594148)); - u = vmla(u, t, vcast_vd_d(-0.333333333333311110369124)); - - t = vadd(s, vmul(s, vmul(t, u))); - t = vadd(t, vmul(vcast_vd_vi(q), vcast_vd_d(rtengine::RT_PI/2))); - - return t; -} - -static INLINE vdouble xatan2(vdouble y, vdouble x) { - vdouble r = atan2k(vabs(y), x); - - r = vmulsign(r, x); - r = vsel(vorm(vmask_isinf(x), vmask_eq(x, vcast_vd_d(0))), vsub(vcast_vd_d(rtengine::RT_PI/2), visinf2(x, vmulsign(vcast_vd_d(rtengine::RT_PI/2), x))), r); - r = vsel(vmask_isinf(y), vsub(vcast_vd_d(rtengine::RT_PI/2), visinf2(x, vmulsign(vcast_vd_d(rtengine::RT_PI/4), x))), r); - r = vsel(vmask_eq(y, vcast_vd_d(0)), vsel(vmask_eq(vsign(x), vcast_vd_d(-1.0)), vcast_vd_d(rtengine::RT_PI), vcast_vd_d(0)), r); - - return vsel(vorm(vmask_isnan(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_NAN), vmulsign(r, y)); -} - -static INLINE vdouble xasin(vdouble d) { - vdouble x, y; - x = vadd(vcast_vd_d(1), d); - y = vsub(vcast_vd_d(1), d); - x = vmul(x, y); - x = vsqrt(x); - x = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), atan2k(vabs(d), x)); - return vmulsign(x, d); -} - -static INLINE vdouble xacos(vdouble d) { - vdouble x, y; - x = vadd(vcast_vd_d(1), d); - y = vsub(vcast_vd_d(1), d); - x = vmul(x, y); - x = vsqrt(x); - x = vmulsign(atan2k(x, vabs(d)), d); - y = (vdouble)vandm(vmask_lt(d, vcast_vd_d(0)), (vmask)vcast_vd_d(rtengine::RT_PI)); - x = vadd(x, y); - return x; -} - -static INLINE vdouble xatan(vdouble s) { - vdouble t, u; - vint q; - - q = vseli_lt(s, vcast_vd_d(0), vcast_vi_i(2), vcast_vi_i(0)); - s = vabs(s); - - q = vseli_lt(vcast_vd_d(1), s, vaddi(q, vcast_vi_i(1)), q); - s = vsel(vmask_lt(vcast_vd_d(1), s), vdiv(vcast_vd_d(1), s), s); - - t = vmul(s, s); - - u = vcast_vd_d(-1.88796008463073496563746e-05); - u = vmla(u, t, vcast_vd_d(0.000209850076645816976906797)); - u = vmla(u, t, vcast_vd_d(-0.00110611831486672482563471)); - u = vmla(u, t, vcast_vd_d(0.00370026744188713119232403)); - u = vmla(u, t, vcast_vd_d(-0.00889896195887655491740809)); - u = vmla(u, t, vcast_vd_d(0.016599329773529201970117)); - u = vmla(u, t, vcast_vd_d(-0.0254517624932312641616861)); - u = vmla(u, t, vcast_vd_d(0.0337852580001353069993897)); - u = vmla(u, t, vcast_vd_d(-0.0407629191276836500001934)); - u = vmla(u, t, vcast_vd_d(0.0466667150077840625632675)); - u = vmla(u, t, vcast_vd_d(-0.0523674852303482457616113)); - u = vmla(u, t, vcast_vd_d(0.0587666392926673580854313)); - u = vmla(u, t, vcast_vd_d(-0.0666573579361080525984562)); - u = vmla(u, t, vcast_vd_d(0.0769219538311769618355029)); - u = vmla(u, t, vcast_vd_d(-0.090908995008245008229153)); - u = vmla(u, t, vcast_vd_d(0.111111105648261418443745)); - u = vmla(u, t, vcast_vd_d(-0.14285714266771329383765)); - u = vmla(u, t, vcast_vd_d(0.199999999996591265594148)); - u = vmla(u, t, vcast_vd_d(-0.333333333333311110369124)); - - t = vadd(s, vmul(s, vmul(t, u))); - - t = vsel(vmaski_eq(vandi(q, vcast_vi_i(1)), vcast_vi_i(1)), vsub(vcast_vd_d(rtengine::RT_PI/2), t), t); - t = vsel(vmaski_eq(vandi(q, vcast_vi_i(2)), vcast_vi_i(2)), vneg(t), t); - - return t; -} - -static INLINE vdouble xlog(vdouble d) { - vdouble x, x2; - vdouble t, m; - vint e; - - e = vilogbp1(vmul(d, vcast_vd_d(0.7071))); - m = vldexp(d, vsubi(vcast_vi_i(0), e)); - - x = vdiv(vadd(vcast_vd_d(-1), m), vadd(vcast_vd_d(1), m)); - x2 = vmul(x, x); - - t = vcast_vd_d(0.148197055177935105296783); - t = vmla(t, x2, vcast_vd_d(0.153108178020442575739679)); - t = vmla(t, x2, vcast_vd_d(0.181837339521549679055568)); - t = vmla(t, x2, vcast_vd_d(0.22222194152736701733275)); - t = vmla(t, x2, vcast_vd_d(0.285714288030134544449368)); - t = vmla(t, x2, vcast_vd_d(0.399999999989941956712869)); - t = vmla(t, x2, vcast_vd_d(0.666666666666685503450651)); - t = vmla(t, x2, vcast_vd_d(2)); - - x = vadd(vmul(x, t), vmul(vcast_vd_d(0.693147180559945286226764), vcast_vd_vi(e))); - - x = vsel(vmask_ispinf(d), vcast_vd_d(rtengine::RT_INFINITY), x); - x = vsel(vmask_gt(vcast_vd_d(0), d), vcast_vd_d(rtengine::RT_NAN), x); - x = vsel(vmask_eq(d, vcast_vd_d(0)), vcast_vd_d(-rtengine::RT_INFINITY), x); - - return x; -} - -static INLINE vdouble xexp(vdouble d) { - vint q = vrint_vi_vd(vmul(d, vcast_vd_d(R_LN2))); - vdouble s, u; - - s = vadd(d, vmul(vcast_vd_vi(q), vcast_vd_d(-L2U))); - s = vadd(s, vmul(vcast_vd_vi(q), vcast_vd_d(-L2L))); - - u = vcast_vd_d(2.08860621107283687536341e-09); - u = vmla(u, s, vcast_vd_d(2.51112930892876518610661e-08)); - u = vmla(u, s, vcast_vd_d(2.75573911234900471893338e-07)); - u = vmla(u, s, vcast_vd_d(2.75572362911928827629423e-06)); - u = vmla(u, s, vcast_vd_d(2.4801587159235472998791e-05)); - u = vmla(u, s, vcast_vd_d(0.000198412698960509205564975)); - u = vmla(u, s, vcast_vd_d(0.00138888888889774492207962)); - u = vmla(u, s, vcast_vd_d(0.00833333333331652721664984)); - u = vmla(u, s, vcast_vd_d(0.0416666666666665047591422)); - u = vmla(u, s, vcast_vd_d(0.166666666666666851703837)); - u = vmla(u, s, vcast_vd_d(0.5)); - - u = vadd(vcast_vd_d(1), vadd(s, vmul(vmul(s, s), u))); - - u = vldexp(u, q); - - u = vsel(vmask_isminf(d), vcast_vd_d(0), u); - - return u; -} - -static INLINE vdouble2 logk(vdouble d) { - vdouble2 x, x2; - vdouble t, m; - vint e; - - e = vilogbp1(vmul(d, vcast_vd_d(0.7071))); - m = vldexp(d, vsubi(vcast_vi_i(0), e)); - - x = div_dd(add2_ss(vcast_vd_d(-1), m), add2_ss(vcast_vd_d(1), m)); - x2 = squ_d(x); - x2 = normalize_d(x2); - - t = vcast_vd_d(0.134601987501262130076155); - t = vmla(t, x2.x, vcast_vd_d(0.132248509032032670243288)); - t = vmla(t, x2.x, vcast_vd_d(0.153883458318096079652524)); - t = vmla(t, x2.x, vcast_vd_d(0.181817427573705403298686)); - t = vmla(t, x2.x, vcast_vd_d(0.222222231326187414840781)); - t = vmla(t, x2.x, vcast_vd_d(0.285714285651261412873718)); - t = vmla(t, x2.x, vcast_vd_d(0.400000000000222439910458)); - t = vmla(t, x2.x, vcast_vd_d(0.666666666666666371239645)); - - return add2_dd(mul_ds(dd(vcast_vd_d(0.693147180559945286226764), vcast_vd_d(2.319046813846299558417771e-17)), - vcast_vd_vi(e)), - add2_dd(scale_d(x, vcast_vd_d(2)), mul_ds(mul_dd(x2, x), t))); -} - -static INLINE vdouble expk(vdouble2 d) { - vdouble u = vmul(vadd(d.x, d.y), vcast_vd_d(R_LN2)); - vint q = vrint_vi_vd(u); - vdouble2 s, t; - - s = add2_ds(d, vmul(vcast_vd_vi(q), vcast_vd_d(-L2U))); - s = add2_ds(s, vmul(vcast_vd_vi(q), vcast_vd_d(-L2L))); - - q = vrint_vi_vd(vmin(vmax(vcast_vd_d(-2047.49), u), vcast_vd_d(2047.49))); - - s = normalize_d(s); - - u = vcast_vd_d(2.51069683420950419527139e-08); - u = vmla(u, s.x, vcast_vd_d(2.76286166770270649116855e-07)); - u = vmla(u, s.x, vcast_vd_d(2.75572496725023574143864e-06)); - u = vmla(u, s.x, vcast_vd_d(2.48014973989819794114153e-05)); - u = vmla(u, s.x, vcast_vd_d(0.000198412698809069797676111)); - u = vmla(u, s.x, vcast_vd_d(0.0013888888939977128960529)); - u = vmla(u, s.x, vcast_vd_d(0.00833333333332371417601081)); - u = vmla(u, s.x, vcast_vd_d(0.0416666666665409524128449)); - u = vmla(u, s.x, vcast_vd_d(0.166666666666666740681535)); - u = vmla(u, s.x, vcast_vd_d(0.500000000000000999200722)); - - t = add_dd(s, mul_ds(squ_d(s), u)); - - t = add_sd(vcast_vd_d(1), t); - u = vadd(t.x, t.y); - u = vldexp(u, q); - - return u; -} - -static INLINE vdouble xpow(vdouble x, vdouble y) { -#if 1 - vmask yisint = vmask_eq(vcast_vd_vi(vrint_vi_vd(y)), y); - vmask yisodd = vandm(vmaski_eq(vandi(vrint_vi_vd(y), vcast_vi_i(1)), vcast_vi_i(1)), yisint); - - vdouble result = expk(mul_ds(logk(vabs(x)), y)); - - //result = vsel(vmask_isnan(result), vcast_vd_d(rtengine::RT_INFINITY), result); - - result = vmul(result, - vsel(vmask_gt(x, vcast_vd_d(0)), - vcast_vd_d(1), - vsel(yisint, - vsel(yisodd, - vcast_vd_d(-1), - vcast_vd_d(1)), - vcast_vd_d(rtengine::RT_NAN)))); - - vdouble efx = vreinterpret_vd_vm(vxorm(vreinterpret_vm_vd(vsub(vabs(x), vcast_vd_d(1))), vsignbit(y))); - - result = vsel(vmask_isinf(y), - vsel(vmask_lt(efx, vcast_vd_d(0)), - vcast_vd_d(0), - vsel(vmask_eq(efx, vcast_vd_d(0)), - vcast_vd_d(1.0), - vcast_vd_d(rtengine::RT_INFINITY))), - result); - - result = vsel(vorm(vmask_isinf(x), vmask_eq(x, vcast_vd_d(0))), - vmul(vsel(yisodd, vsign(x), vcast_vd_d(1)), - vsel(vmask_lt(vsel(vmask_eq(x, vcast_vd_d(0)), vneg(y), y), vcast_vd_d(0)), - vcast_vd_d(0), - vcast_vd_d(rtengine::RT_INFINITY))), - result); - - result = vsel(vorm(vmask_isnan(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_NAN), result); - - result = vsel(vorm(vmask_eq(y, vcast_vd_d(0)), vmask_eq(x, vcast_vd_d(1))), vcast_vd_d(1), result); - - return result; -#else - return expk(mul_ds(logk(x), y)); -#endif -} - -static INLINE vdouble2 expk2(vdouble2 d) { - vdouble u = vmul(vadd(d.x, d.y), vcast_vd_d(R_LN2)); - vint q = vrint_vi_vd(u); - vdouble2 s, t; - - s = add2_ds(d, vmul(vcast_vd_vi(q), vcast_vd_d(-L2U))); - s = add2_ds(s, vmul(vcast_vd_vi(q), vcast_vd_d(-L2L))); - - q = vrint_vi_vd(vmin(vmax(vcast_vd_d(-2047.49), u), vcast_vd_d(2047.49))); - - s = normalize_d(s); - - u = vcast_vd_d(2.51069683420950419527139e-08); - u = vmla(u, s.x, vcast_vd_d(2.76286166770270649116855e-07)); - u = vmla(u, s.x, vcast_vd_d(2.75572496725023574143864e-06)); - u = vmla(u, s.x, vcast_vd_d(2.48014973989819794114153e-05)); - u = vmla(u, s.x, vcast_vd_d(0.000198412698809069797676111)); - u = vmla(u, s.x, vcast_vd_d(0.0013888888939977128960529)); - u = vmla(u, s.x, vcast_vd_d(0.00833333333332371417601081)); - u = vmla(u, s.x, vcast_vd_d(0.0416666666665409524128449)); - u = vmla(u, s.x, vcast_vd_d(0.166666666666666740681535)); - u = vmla(u, s.x, vcast_vd_d(0.500000000000000999200722)); - - t = add_dd(s, mul_ds(squ_d(s), u)); - - t = add_sd(vcast_vd_d(1), t); - - return dd(vldexp(t.x, q), vldexp(t.y, q)); -} - -static INLINE vdouble xsinh(vdouble x) { - vdouble y = vabs(x); - vdouble2 d = expk2(dd(y, vcast_vd_d(0))); - d = add2_dd(d, div_dd(dd(vcast_vd_d(-1), vcast_vd_d(0)), d)); - y = vmul(vadd(d.x, d.y), vcast_vd_d(0.5)); - - y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_INFINITY), y); - y = vmulsign(y, x); - y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); - - return y; -} - -static INLINE vdouble xcosh(vdouble x) { - vdouble2 d = expk2(dd(x, vcast_vd_d(0))); - d = add2_dd(d, div_dd(dd(vcast_vd_d(1), vcast_vd_d(0)), d)); - vdouble y = vmul(vadd(d.x, d.y), vcast_vd_d(0.5)); - - y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_INFINITY), y); - y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); - - return y; -} - -static INLINE vdouble xtanh(vdouble x) { - vdouble y = vabs(x); - vdouble2 d = expk2(dd(y, vcast_vd_d(0))); - vdouble2 e = div_dd(dd(vcast_vd_d(1), vcast_vd_d(0)), d); - d = div_dd(add2_dd(d, scale_d(e, vcast_vd_d(-1))), add2_dd(d, e)); - y = d.x + d.y; - - y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(1.0), y); - y = vmulsign(y, x); - y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); - - return y; -} - -static INLINE vdouble2 logk2(vdouble2 d) { - vdouble2 x, x2, m; - vdouble t; - vint e; - - d = normalize_d(d); - e = vilogbp1(vmul(d.x, vcast_vd_d(0.7071))); - m = scale_d(d, vldexp(vcast_vd_d(1), vsubi(vcast_vi_i(0), e))); - - x = div_dd(add2_ds(m, vcast_vd_d(-1)), add2_ds(m, vcast_vd_d(1))); - x2 = squ_d(x); - x2 = normalize_d(x2); - - t = vcast_vd_d(0.134601987501262130076155); - t = vmla(t, x2.x, vcast_vd_d(0.132248509032032670243288)); - t = vmla(t, x2.x, vcast_vd_d(0.153883458318096079652524)); - t = vmla(t, x2.x, vcast_vd_d(0.181817427573705403298686)); - t = vmla(t, x2.x, vcast_vd_d(0.222222231326187414840781)); - t = vmla(t, x2.x, vcast_vd_d(0.285714285651261412873718)); - t = vmla(t, x2.x, vcast_vd_d(0.400000000000222439910458)); - t = vmla(t, x2.x, vcast_vd_d(0.666666666666666371239645)); - - return add2_dd(mul_ds(dd(vcast_vd_d(0.693147180559945286226764), vcast_vd_d(2.319046813846299558417771e-17)), - vcast_vd_vi(e)), - add2_dd(scale_d(x, vcast_vd_d(2)), mul_ds(mul_dd(x2, x), t))); -} - -static INLINE vdouble xasinh(vdouble x) { - vdouble y = vabs(x); - vdouble2 d = logk2(add2_ds(sqrt_d(add2_ds(mul_ss(y, y), vcast_vd_d(1))), y)); - y = vadd(d.x, d.y); - - y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_INFINITY), y); - y = vmulsign(y, x); - y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); - - return y; -} - -static INLINE vdouble xacosh(vdouble x) { - vdouble2 d = logk2(add2_ds(sqrt_d(add2_ds(mul_ss(x, x), vcast_vd_d(-1))), x)); - vdouble y = vadd(d.x, d.y); - - y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_INFINITY), y); - y = vsel(vmask_eq(x, vcast_vd_d(1.0)), vcast_vd_d(0.0), y); - y = vsel(vmask_lt(x, vcast_vd_d(1.0)), vcast_vd_d(rtengine::RT_NAN), y); - y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); - - return y; -} - -static INLINE vdouble xatanh(vdouble x) { - vdouble y = vabs(x); - vdouble2 d = logk2(div_dd(add2_ss(vcast_vd_d(1), y), add2_ss(vcast_vd_d(1), -y))); - y = vsel(vmask_gt(y, vcast_vd_d(1.0)), vcast_vd_d(rtengine::RT_NAN), vsel(vmask_eq(y, vcast_vd_d(1.0)), vcast_vd_d(rtengine::RT_INFINITY), vmul(vadd(d.x, d.y), vcast_vd_d(0.5)))); - - y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_NAN), y); - y = vmulsign(y, x); - y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); - - return y; -} - -static INLINE vdouble xcbrt(vdouble d) { - vdouble x, y, q = vcast_vd_d(1.0); - vint e, qu, re; - vdouble t; - - e = vilogbp1(vabs(d)); - d = vldexp(d, vsubi(vcast_vi_i(0), e)); - - t = vadd(vcast_vd_vi(e), vcast_vd_d(6144)); - qu = vtruncate_vi_vd(vdiv(t, vcast_vd_d(3))); - re = vtruncate_vi_vd(vsub(t, vmul(vcast_vd_vi(qu), vcast_vd_d(3)))); - - q = vsel(vmaski_eq(re, vcast_vi_i(1)), vcast_vd_d(1.2599210498948731647672106), q); - q = vsel(vmaski_eq(re, vcast_vi_i(2)), vcast_vd_d(1.5874010519681994747517056), q); - q = vldexp(q, vsubi(qu, vcast_vi_i(2048))); - - q = vmulsign(q, d); - - d = vabs(d); - - x = vcast_vd_d(-0.640245898480692909870982); - x = vmla(x, d, vcast_vd_d(2.96155103020039511818595)); - x = vmla(x, d, vcast_vd_d(-5.73353060922947843636166)); - x = vmla(x, d, vcast_vd_d(6.03990368989458747961407)); - x = vmla(x, d, vcast_vd_d(-3.85841935510444988821632)); - x = vmla(x, d, vcast_vd_d(2.2307275302496609725722)); - - y = vmul(x, x); y = vmul(y, y); x = vsub(x, vmul(vmla(d, y, vneg(x)), vcast_vd_d(1.0 / 3.0))); - y = vmul(vmul(d, x), x); - y = vmul(vsub(y, vmul(vmul(vcast_vd_d(2.0 / 3.0), y), vmla(y, x, vcast_vd_d(-1.0)))), q); - - return y; -} - -static INLINE vdouble xexp2(vdouble a) { - vdouble u = expk(mul_ds(dd(vcast_vd_d(0.69314718055994528623), vcast_vd_d(2.3190468138462995584e-17)), a)); - u = vsel(vmask_ispinf(a), vcast_vd_d(rtengine::RT_INFINITY), u); - u = vsel(vmask_isminf(a), vcast_vd_d(0), u); - return u; -} - -static INLINE vdouble xexp10(vdouble a) { - vdouble u = expk(mul_ds(dd(vcast_vd_d(2.3025850929940459011), vcast_vd_d(-2.1707562233822493508e-16)), a)); - u = vsel(vmask_ispinf(a), vcast_vd_d(rtengine::RT_INFINITY), u); - u = vsel(vmask_isminf(a), vcast_vd_d(0), u); - return u; -} - -static INLINE vdouble xexpm1(vdouble a) { - vdouble2 d = add2_ds(expk2(dd(a, vcast_vd_d(0))), vcast_vd_d(-1.0)); - vdouble x = d.x + d.y; - x = vsel(vmask_ispinf(a), vcast_vd_d(rtengine::RT_INFINITY), x); - x = vsel(vmask_isminf(a), vcast_vd_d(-1), x); - return x; -} - -static INLINE vdouble xlog10(vdouble a) { - vdouble2 d = mul_dd(logk(a), dd(vcast_vd_d(0.43429448190325176116), vcast_vd_d(6.6494347733425473126e-17))); - vdouble x = d.x + d.y; - - x = vsel(vmask_ispinf(a), vcast_vd_d(rtengine::RT_INFINITY), x); - x = vsel(vmask_gt(vcast_vd_d(0), a), vcast_vd_d(rtengine::RT_NAN), x); - x = vsel(vmask_eq(a, vcast_vd_d(0)), vcast_vd_d(-rtengine::RT_INFINITY), x); - - return x; -} - -static INLINE vdouble xlog1p(vdouble a) { - vdouble2 d = logk2(add2_ss(a, vcast_vd_d(1))); - vdouble x = d.x + d.y; - - x = vsel(vmask_ispinf(a), vcast_vd_d(rtengine::RT_INFINITY), x); - x = vsel(vmask_gt(vcast_vd_d(-1), a), vcast_vd_d(rtengine::RT_NAN), x); - x = vsel(vmask_eq(a, vcast_vd_d(-1)), vcast_vd_d(-rtengine::RT_INFINITY), x); - - return x; -} - -// - -typedef struct { - vfloat x, y; -} vfloat2; - -static INLINE vfloat vabsf(vfloat f) { return (vfloat)vandnotm((vmask)vcast_vf_f(-0.0f), (vmask)f); } -static INLINE vfloat vnegf(vfloat f) { return (vfloat)vxorm((vmask)f, (vmask)vcast_vf_f(-0.0f)); } - -#ifdef __SSE4_1__ -// only one instruction when using SSE4.1 -static INLINE vfloat vself(vmask mask, vfloat x, vfloat y) { - return _mm_blendv_ps(y,x,(vfloat)mask); -} - -static INLINE vint vselc(vmask mask, vint x, vint y) { - return _mm_blendv_epi8(y,x,mask); -} - -#else -// three instructions when using SSE2 -static INLINE vfloat vself(vmask mask, vfloat x, vfloat y) { - return (vfloat)vorm(vandm(mask, (vmask)x), vandnotm(mask, (vmask)y)); -} - -static INLINE vint vselc(vmask mask, vint x, vint y) { - return vorm(vandm(mask, (vmask)x), vandnotm(mask, (vmask)y)); -} -#endif - -static INLINE vfloat vselfzero(vmask mask, vfloat x) { - // returns value of x if corresponding mask bits are 1, else returns 0 - // faster than vself(mask, x, ZEROV) - return _mm_and_ps((vfloat)mask, x); -} -static INLINE vfloat vselfnotzero(vmask mask, vfloat x) { - // returns value of x if corresponding mask bits are 0, else returns 0 - // faster than vself(mask, ZEROV, x) - return _mm_andnot_ps((vfloat)mask, x); -} - -static INLINE vint vselizero(vmask mask, vint x) { - // returns value of x if corresponding mask bits are 1, else returns 0 - // faster than vselc(mask, x, ZEROV) - return _mm_and_si128(mask, x); -} -static INLINE vint vselinotzero(vmask mask, vint x) { - // returns value of x if corresponding mask bits are 0, else returns 0 - // faster than vselc(mask, ZEROV, x) - return _mm_andnot_si128(mask, x); -} - -static INLINE vint2 vseli2_lt(vfloat f0, vfloat f1, vint2 x, vint2 y) { - vint2 m2 = vcast_vi2_vm(vmaskf_lt(f0, f1)); - return vori2(vandi2(m2, x), vandnoti2(m2, y)); -} - -static INLINE vmask vsignbitf(vfloat f) { - return vandm((vmask)f, (vmask)vcast_vf_f(-0.0f)); -} - -static INLINE vfloat vmulsignf(vfloat x, vfloat y) { - return (vfloat)vxorm((vmask)x, vsignbitf(y)); -} - -static INLINE vfloat vsignf(vfloat f) { - return (vfloat)vorm((vmask)vcast_vf_f(1.0f), vandm((vmask)vcast_vf_f(-0.0f), (vmask)f)); -} - -static INLINE vmask vmaskf_isinf(vfloat d) { return vmaskf_eq(vabsf(d), vcast_vf_f(INFINITYf)); } -static INLINE vmask vmaskf_ispinf(vfloat d) { return vmaskf_eq(d, vcast_vf_f(INFINITYf)); } -static INLINE vmask vmaskf_isminf(vfloat d) { return vmaskf_eq(d, vcast_vf_f(-INFINITYf)); } -static INLINE vmask vmaskf_isnan(vfloat d) { return vmaskf_neq(d, d); } -// the following is equivalent to vorm(vmaskf_isnan(a), vmaskf_isnan(b)), but faster -static INLINE vmask vmaskf_isnan(vfloat a, vfloat b) { return (vmask)_mm_cmpunord_ps(a, b); } -static INLINE vfloat visinf2f(vfloat d, vfloat m) { return (vfloat)vandm(vmaskf_isinf(d), vorm(vsignbitf(d), (vmask)m)); } -static INLINE vfloat visinff(vfloat d) { return visinf2f(d, vcast_vf_f(1.0f)); } - -static INLINE vint2 vilogbp1f(vfloat d) { - vmask m = vmaskf_lt(d, vcast_vf_f(5.421010862427522E-20f)); - d = vself(m, vmulf(vcast_vf_f(1.8446744073709552E19f), d), d); - vint2 q = vandi2(vsrli2(vcast_vi2_vm(vreinterpret_vm_vf(d)), 23), vcast_vi2_i(0xff)); - q = vsubi2(q, vseli2(m, vcast_vi2_i(64 + 0x7e), vcast_vi2_i(0x7e))); - return q; -} - -static INLINE vfloat vldexpf(vfloat x, vint2 q) { - vfloat u; - vint2 m = vsrai2(q, 31); - m = vslli2(vsubi2(vsrai2(vaddi2(m, q), 6), m), 4); - q = vsubi2(q, vslli2(m, 2)); - u = vreinterpret_vf_vm(vcast_vm_vi2(vslli2(vaddi2(m, vcast_vi2_i(0x7f)), 23))); - x = vmulf(vmulf(vmulf(vmulf(x, u), u), u), u); - u = vreinterpret_vf_vm(vcast_vm_vi2(vslli2(vaddi2(q, vcast_vi2_i(0x7f)), 23))); - return vmulf(x, u); -} - -static INLINE vfloat xsinf(vfloat d) { - vint2 q; - vfloat u, s; - - q = vrint_vi2_vf(vmulf(d, vcast_vf_f((float)rtengine::RT_1_PI))); - - u = vcast_vf_vi2(q); - d = vmlaf(u, vcast_vf_f(-PI4_Af*4), d); - d = vmlaf(u, vcast_vf_f(-PI4_Bf*4), d); - d = vmlaf(u, vcast_vf_f(-PI4_Cf*4), d); - d = vmlaf(u, vcast_vf_f(-PI4_Df*4), d); - - s = vmulf(d, d); - - d = vself(vmaski2_eq(vandi2(q, vcast_vi2_i(1)), vcast_vi2_i(1)), vnegf(d), d); - - u = vcast_vf_f(2.6083159809786593541503e-06f); - u = vmlaf(u, s, vcast_vf_f(-0.0001981069071916863322258f)); - u = vmlaf(u, s, vcast_vf_f(0.00833307858556509017944336f)); - u = vmlaf(u, s, vcast_vf_f(-0.166666597127914428710938f)); - - u = vmlaf(s, vmulf(u, d), d); - - return u; -} - -static INLINE vfloat xcosf(vfloat d) { - vint2 q; - vfloat u, s; - - q = vrint_vi2_vf(vsubf(vmulf(d, vcast_vf_f((float)rtengine::RT_1_PI)), vcast_vf_f(0.5f))); - q = vaddi2(vaddi2(q, q), vcast_vi2_i(1)); - - u = vcast_vf_vi2(q); - d = vmlaf(u, vcast_vf_f(-PI4_Af*2), d); - d = vmlaf(u, vcast_vf_f(-PI4_Bf*2), d); - d = vmlaf(u, vcast_vf_f(-PI4_Cf*2), d); - d = vmlaf(u, vcast_vf_f(-PI4_Df*2), d); - - s = vmulf(d, d); - - d = vself(vmaski2_eq(vandi2(q, vcast_vi2_i(2)), vcast_vi2_i(2)), d, vnegf(d)); - - u = vcast_vf_f(2.6083159809786593541503e-06f); - u = vmlaf(u, s, vcast_vf_f(-0.0001981069071916863322258f)); - u = vmlaf(u, s, vcast_vf_f(0.00833307858556509017944336f)); - u = vmlaf(u, s, vcast_vf_f(-0.166666597127914428710938f)); - - u = vmlaf(s, vmulf(u, d), d); - - return u; -} - -static INLINE vfloat2 xsincosf(vfloat d) { - vint2 q; - vmask m; - vfloat u, s, t, rx, ry; - vfloat2 r; - - q = vrint_vi2_vf(vmulf(d, vcast_vf_f((float)rtengine::RT_2_PI))); - - s = d; - - u = vcast_vf_vi2(q); - s = vmlaf(u, vcast_vf_f(-PI4_Af*2), s); - s = vmlaf(u, vcast_vf_f(-PI4_Bf*2), s); - s = vmlaf(u, vcast_vf_f(-PI4_Cf*2), s); - s = vmlaf(u, vcast_vf_f(-PI4_Df*2), s); - - t = s; - - s = vmulf(s, s); - - u = vcast_vf_f(-0.000195169282960705459117889f); - u = vmlaf(u, s, vcast_vf_f(0.00833215750753879547119141f)); - u = vmlaf(u, s, vcast_vf_f(-0.166666537523269653320312f)); - u = vmulf(vmulf(u, s), t); - - rx = vaddf(t, u); - - u = vcast_vf_f(-2.71811842367242206819355e-07f); - u = vmlaf(u, s, vcast_vf_f(2.47990446951007470488548e-05f)); - u = vmlaf(u, s, vcast_vf_f(-0.00138888787478208541870117f)); - u = vmlaf(u, s, vcast_vf_f(0.0416666641831398010253906f)); - u = vmlaf(u, s, vcast_vf_f(-0.5)); - - ry = vaddf(vcast_vf_f(1), vmulf(s, u)); - - m = vmaski2_eq(vandi2(q, vcast_vi2_i(1)), vcast_vi2_i(0)); - r.x = vself(m, rx, ry); - r.y = vself(m, ry, rx); - - m = vmaski2_eq(vandi2(q, vcast_vi2_i(2)), vcast_vi2_i(2)); - r.x = vreinterpret_vf_vm(vxorm(vandm(m, vreinterpret_vm_vf(vcast_vf_f(-0.0))), vreinterpret_vm_vf(r.x))); - - m = vmaski2_eq(vandi2(vaddi2(q, vcast_vi2_i(1)), vcast_vi2_i(2)), vcast_vi2_i(2)); - r.y = vreinterpret_vf_vm(vxorm(vandm(m, vreinterpret_vm_vf(vcast_vf_f(-0.0))), vreinterpret_vm_vf(r.y))); - - m = vmaskf_isinf(d); - r.x = vself(m, vcast_vf_f(rtengine::RT_NAN), r.x); - r.y = vself(m, vcast_vf_f(rtengine::RT_NAN), r.y); - - return r; -} - -static INLINE vfloat xtanf(vfloat d) { - vint2 q; - vmask m; - vfloat u, s, x; - - q = vrint_vi2_vf(vmulf(d, vcast_vf_f((float)(2 * rtengine::RT_1_PI)))); - - x = d; - - u = vcast_vf_vi2(q); - x = vmlaf(u, vcast_vf_f(-PI4_Af*2), x); - x = vmlaf(u, vcast_vf_f(-PI4_Bf*2), x); - x = vmlaf(u, vcast_vf_f(-PI4_Cf*2), x); - x = vmlaf(u, vcast_vf_f(-PI4_Df*2), x); - - s = vmulf(x, x); - - m = vmaski2_eq(vandi2(q, vcast_vi2_i(1)), vcast_vi2_i(1)); - x = vself(m, vnegf(x), x); - - u = vcast_vf_f(0.00927245803177356719970703f); - u = vmlaf(u, s, vcast_vf_f(0.00331984995864331722259521f)); - u = vmlaf(u, s, vcast_vf_f(0.0242998078465461730957031f)); - u = vmlaf(u, s, vcast_vf_f(0.0534495301544666290283203f)); - u = vmlaf(u, s, vcast_vf_f(0.133383005857467651367188f)); - u = vmlaf(u, s, vcast_vf_f(0.333331853151321411132812f)); - - u = vmlaf(s, vmulf(u, x), x); - - u = vself(m, vrecf(u), u); - - u = vself(vmaskf_isinf(d), vcast_vf_f(NANf), u); - - return u; -} - -static INLINE vfloat xatanf(vfloat s) { - vfloat t, u; - vint2 q; - - q = vseli2_lt(s, vcast_vf_f(0.0f), vcast_vi2_i(2), vcast_vi2_i(0)); - s = vabsf(s); - - q = vseli2_lt(vcast_vf_f(1.0f), s, vaddi2(q, vcast_vi2_i(1)), q); - s = vself(vmaskf_lt(vcast_vf_f(1.0f), s), vdivf(vcast_vf_f(1.0f), s), s); - - t = vmulf(s, s); - - u = vcast_vf_f(0.00282363896258175373077393f); - u = vmlaf(u, t, vcast_vf_f(-0.0159569028764963150024414f)); - u = vmlaf(u, t, vcast_vf_f(0.0425049886107444763183594f)); - u = vmlaf(u, t, vcast_vf_f(-0.0748900920152664184570312f)); - u = vmlaf(u, t, vcast_vf_f(0.106347933411598205566406f)); - u = vmlaf(u, t, vcast_vf_f(-0.142027363181114196777344f)); - u = vmlaf(u, t, vcast_vf_f(0.199926957488059997558594f)); - u = vmlaf(u, t, vcast_vf_f(-0.333331018686294555664062f)); - - t = vaddf(s, vmulf(s, vmulf(t, u))); - - t = vself(vmaski2_eq(vandi2(q, vcast_vi2_i(1)), vcast_vi2_i(1)), vsubf(vcast_vf_f((float)(rtengine::RT_PI/2)), t), t); - t = vself(vmaski2_eq(vandi2(q, vcast_vi2_i(2)), vcast_vi2_i(2)), vnegf(t), t); - - return t; -} - -static INLINE vfloat atan2kf(vfloat y, vfloat x) { - vfloat s, t, u; - vint2 q; - vmask p; - - q = vseli2_lt(x, vcast_vf_f(0.0f), vcast_vi2_i(-2), vcast_vi2_i(0)); - x = vabsf(x); - - q = vseli2_lt(x, y, vaddi2(q, vcast_vi2_i(1)), q); - p = vmaskf_lt(x, y); - s = vself(p, vnegf(x), y); - t = vmaxf(x, y); - - s = vdivf(s, t); - t = vmulf(s, s); - - u = vcast_vf_f(0.00282363896258175373077393f); - u = vmlaf(u, t, vcast_vf_f(-0.0159569028764963150024414f)); - u = vmlaf(u, t, vcast_vf_f(0.0425049886107444763183594f)); - u = vmlaf(u, t, vcast_vf_f(-0.0748900920152664184570312f)); - u = vmlaf(u, t, vcast_vf_f(0.106347933411598205566406f)); - u = vmlaf(u, t, vcast_vf_f(-0.142027363181114196777344f)); - u = vmlaf(u, t, vcast_vf_f(0.199926957488059997558594f)); - u = vmlaf(u, t, vcast_vf_f(-0.333331018686294555664062f)); - - t = vaddf(s, vmulf(s, vmulf(t, u))); - t = vaddf(t, vmulf(vcast_vf_vi2(q), vcast_vf_f((float)(rtengine::RT_PI/2)))); - - return t; -} - -static INLINE vfloat xatan2f(vfloat y, vfloat x) { - vfloat r = atan2kf(vabsf(y), x); - - r = vmulsignf(r, x); - r = vself(vorm(vmaskf_isinf(x), vmaskf_eq(x, vcast_vf_f(0.0f))), vsubf(vcast_vf_f((float)(rtengine::RT_PI/2)), visinf2f(x, vmulsignf(vcast_vf_f((float)(rtengine::RT_PI/2)), x))), r); - r = vself(vmaskf_isinf(y), vsubf(vcast_vf_f((float)(rtengine::RT_PI/2)), visinf2f(x, vmulsignf(vcast_vf_f((float)(rtengine::RT_PI/4)), x))), r); - r = vself(vmaskf_eq(y, vcast_vf_f(0.0f)), vselfzero(vmaskf_eq(vsignf(x), vcast_vf_f(-1.0f)), vcast_vf_f((float)rtengine::RT_PI)), r); - - return vself(vmaskf_isnan(x, y), vcast_vf_f(NANf), vmulsignf(r, y)); -} - -static INLINE vfloat xasinf(vfloat d) { - vfloat x, y; - x = vaddf(vcast_vf_f(1.0f), d); - y = vsubf(vcast_vf_f(1.0f), d); - x = vmulf(x, y); - x = vsqrtf(x); - x = vself(vmaskf_isnan(x), vcast_vf_f(NANf), atan2kf(vabsf(d), x)); - return vmulsignf(x, d); -} - -static INLINE vfloat xacosf(vfloat d) { - vfloat x, y; - x = vaddf(vcast_vf_f(1.0f), d); - y = vsubf(vcast_vf_f(1.0f), d); - x = vmulf(x, y); - x = vsqrtf(x); - x = vmulsignf(atan2kf(x, vabsf(d)), d); - y = (vfloat)vandm(vmaskf_lt(d, vcast_vf_f(0.0f)), (vmask)vcast_vf_f((float)rtengine::RT_PI)); - x = vaddf(x, y); - return x; -} - -static INLINE vfloat xlogf(vfloat d) { - vfloat x, x2, t, m; - vint2 e; - - e = vilogbp1f(vmulf(d, vcast_vf_f(0.7071f))); - m = vldexpf(d, vsubi2(vcast_vi2_i(0), e)); - - x = vdivf(vaddf(vcast_vf_f(-1.0f), m), vaddf(vcast_vf_f(1.0f), m)); - x2 = vmulf(x, x); - - t = vcast_vf_f(0.2371599674224853515625f); - t = vmlaf(t, x2, vcast_vf_f(0.285279005765914916992188f)); - t = vmlaf(t, x2, vcast_vf_f(0.400005519390106201171875f)); - t = vmlaf(t, x2, vcast_vf_f(0.666666567325592041015625f)); - t = vmlaf(t, x2, vcast_vf_f(2.0f)); - - x = vaddf(vmulf(x, t), vmulf(vcast_vf_f(0.693147180559945286226764f), vcast_vf_vi2(e))); - - x = vself(vmaskf_ispinf(d), vcast_vf_f(INFINITYf), x); - x = vself(vmaskf_gt(vcast_vf_f(0), d), vcast_vf_f(NANf), x); - x = vself(vmaskf_eq(d, vcast_vf_f(0)), vcast_vf_f(-INFINITYf), x); - - return x; -} - -static INLINE vfloat xlogf1(vfloat d) { // does xlogf(vmaxf(d, 1.f)) but faster - vfloat x, x2, t, m; - vint2 e; - - e = vilogbp1f(vmulf(d, vcast_vf_f(0.7071f))); - m = vldexpf(d, vsubi2(vcast_vi2_i(0), e)); - - x = vdivf(vaddf(vcast_vf_f(-1.0f), m), vaddf(vcast_vf_f(1.0f), m)); - x2 = vmulf(x, x); - - t = vcast_vf_f(0.2371599674224853515625f); - t = vmlaf(t, x2, vcast_vf_f(0.285279005765914916992188f)); - t = vmlaf(t, x2, vcast_vf_f(0.400005519390106201171875f)); - t = vmlaf(t, x2, vcast_vf_f(0.666666567325592041015625f)); - t = vmlaf(t, x2, vcast_vf_f(2.0f)); - - x = vaddf(vmulf(x, t), vmulf(vcast_vf_f(0.693147180559945286226764f), vcast_vf_vi2(e))); - - x = vself(vmaskf_ispinf(d), vcast_vf_f(INFINITYf), x); - x = vselfnotzero(vmaskf_le(d, vcast_vf_f(1.f)), x); - - return x; -} - -static INLINE vfloat xlogf0(vfloat d) { - vfloat x, x2, t, m; - vint2 e; - - e = vilogbp1f(vmulf(d, vcast_vf_f(0.7071f))); - m = vldexpf(d, vsubi2(vcast_vi2_i(0), e)); - - x = vdivf(vaddf(vcast_vf_f(-1.0f), m), vaddf(vcast_vf_f(1.0f), m)); - x2 = vmulf(x, x); - - t = vcast_vf_f(0.2371599674224853515625f); - t = vmlaf(t, x2, vcast_vf_f(0.285279005765914916992188f)); - t = vmlaf(t, x2, vcast_vf_f(0.400005519390106201171875f)); - t = vmlaf(t, x2, vcast_vf_f(0.666666567325592041015625f)); - t = vmlaf(t, x2, vcast_vf_f(2.0f)); - - x = vaddf(vmulf(x, t), vmulf(vcast_vf_f(0.693147180559945286226764f), vcast_vf_vi2(e))); - - x = vself(vmaskf_ispinf(d), vcast_vf_f(0), x); - x = vself(vmaskf_gt(vcast_vf_f(0), d), vcast_vf_f(0), x); - x = vself(vmaskf_eq(d, vcast_vf_f(0)), vcast_vf_f(0), x); - - return x; -} - -static INLINE vfloat xlogfNoCheck(vfloat d) { // this version does not check input values. Use it only when you know the input values are > 0 e.g. when filling a lookup table - vfloat x, x2, t, m; - vint2 e; - - e = vilogbp1f(vmulf(d, vcast_vf_f(0.7071f))); - m = vldexpf(d, vsubi2(vcast_vi2_i(0), e)); - - x = vdivf(vaddf(vcast_vf_f(-1.0f), m), vaddf(vcast_vf_f(1.0f), m)); - x2 = vmulf(x, x); - - t = vcast_vf_f(0.2371599674224853515625f); - t = vmlaf(t, x2, vcast_vf_f(0.285279005765914916992188f)); - t = vmlaf(t, x2, vcast_vf_f(0.400005519390106201171875f)); - t = vmlaf(t, x2, vcast_vf_f(0.666666567325592041015625f)); - t = vmlaf(t, x2, vcast_vf_f(2.0f)); - - return vaddf(vmulf(x, t), vmulf(vcast_vf_f(0.693147180559945286226764f), vcast_vf_vi2(e))); - -} - -static INLINE vfloat xexpf(vfloat d) { - vint2 q = vrint_vi2_vf(vmulf(d, vcast_vf_f(R_LN2f))); - vfloat s, u; - - s = vmlaf(vcast_vf_vi2(q), vcast_vf_f(-L2Uf),d); - s = vmlaf(vcast_vf_vi2(q), vcast_vf_f(-L2Lf),s); - - u = vcast_vf_f(0.00136324646882712841033936f); - u = vmlaf(u, s, vcast_vf_f(0.00836596917361021041870117f)); - u = vmlaf(u, s, vcast_vf_f(0.0416710823774337768554688f)); - u = vmlaf(u, s, vcast_vf_f(0.166665524244308471679688f)); - u = vmlaf(u, s, vcast_vf_f(0.499999850988388061523438f)); - - u = vaddf(vcast_vf_f(1.0f), vmlaf(vmulf(s, s), u, s)); - - u = vldexpf(u, q); - - // -104.0 - return vselfnotzero(vmaskf_gt(vcast_vf_f(-104.f), d), u); -} - -static INLINE vfloat xexpfNoCheck(vfloat d) { // this version does not check input values. Use it only when you know the input values are > -104.f e.g. when filling a lookup table - vint2 q = vrint_vi2_vf(vmulf(d, vcast_vf_f(R_LN2f))); - vfloat s, u; - - s = vmlaf(vcast_vf_vi2(q), vcast_vf_f(-L2Uf),d); - s = vmlaf(vcast_vf_vi2(q), vcast_vf_f(-L2Lf),s); - - u = vcast_vf_f(0.00136324646882712841033936f); - u = vmlaf(u, s, vcast_vf_f(0.00836596917361021041870117f)); - u = vmlaf(u, s, vcast_vf_f(0.0416710823774337768554688f)); - u = vmlaf(u, s, vcast_vf_f(0.166665524244308471679688f)); - u = vmlaf(u, s, vcast_vf_f(0.499999850988388061523438f)); - - u = vaddf(vcast_vf_f(1.0f), vmlaf(vmulf(s, s), u, s)); - - return vldexpf(u, q); -} - -static INLINE vfloat xcbrtf(vfloat d) { - vfloat x, y, q = vcast_vf_f(1.0), t; - vint2 e, qu, re; - - e = vilogbp1f(vabsf(d)); - d = vldexpf(d, vsubi2(vcast_vi2_i(0), e)); - - t = vaddf(vcast_vf_vi2(e), vcast_vf_f(6144)); - qu = vtruncate_vi2_vf(vdivf(t, vcast_vf_f(3))); - re = vtruncate_vi2_vf(vsubf(t, vmulf(vcast_vf_vi2(qu), vcast_vf_f(3)))); - - q = vself(vmaski2_eq(re, vcast_vi2_i(1)), vcast_vf_f(1.2599210498948731647672106f), q); - q = vself(vmaski2_eq(re, vcast_vi2_i(2)), vcast_vf_f(1.5874010519681994747517056f), q); - q = vldexpf(q, vsubi2(qu, vcast_vi2_i(2048))); - - q = vmulsignf(q, d); - d = vabsf(d); - - x = vcast_vf_f(-0.601564466953277587890625f); - x = vmlaf(x, d, vcast_vf_f(2.8208892345428466796875f)); - x = vmlaf(x, d, vcast_vf_f(-5.532182216644287109375f)); - x = vmlaf(x, d, vcast_vf_f(5.898262500762939453125f)); - x = vmlaf(x, d, vcast_vf_f(-3.8095417022705078125f)); - x = vmlaf(x, d, vcast_vf_f(2.2241256237030029296875f)); - - y = vmulf(vmulf(d, x), x); - y = vmulf(vsubf(y, vmulf(vmulf(vcast_vf_f(2.0f / 3.0f), y), vmlaf(y, x, vcast_vf_f(-1.0f)))), q); - - return y; -} - -static INLINE vfloat vclampf(vfloat value, vfloat low, vfloat high) { - // clamps value in [low;high], returns low if value is NaN - return vmaxf(vminf(high, value), low); -} - -static INLINE vfloat SQRV(vfloat a){ - return a * a; -} - -static inline void vswap( vmask condition, vfloat &a, vfloat &b) { - // conditional swap the elements of two vfloats - vfloat temp = vself(condition, a, b); // the values which fit to condition - a = vself(condition, b, a); // the values which fit to inverted condition - b = temp; -} - -static inline float vhadd( vfloat a ) { - // returns a[0] + a[1] + a[2] + a[3] - a += _mm_movehl_ps(a, a); - return _mm_cvtss_f32(_mm_add_ss(a, _mm_shuffle_ps(a, a, 1))); -} - -static inline float vhmin(vfloat a) { - // returns min(a[0], a[1], a[2], a[3]) - a = vminf(a, _mm_movehl_ps(a, a)); - return _mm_cvtss_f32(vminf(a, _mm_shuffle_ps(a, a, 1))); -} - -static inline float vhmax(vfloat a) { - // returns max(a[0], a[1], a[2], a[3]) - a = vmaxf(a, _mm_movehl_ps(a, a)); - return _mm_cvtss_f32(vmaxf(a, _mm_shuffle_ps(a, a, 1))); -} - -static INLINE vfloat vmul2f(vfloat a){ - // fastest way to multiply by 2 - return a + a; -} - -static INLINE vfloat vintpf(vfloat a, vfloat b, vfloat c) { - // calculate a * b + (1 - a) * c (interpolate two values) - // following is valid: - // vintpf(a, b+x, c+x) = vintpf(a, b, c) + x - // vintpf(a, b*x, c*x) = vintpf(a, b, c) * x - return a * (b-c) + c; -} - -static INLINE vfloat vdup(vfloat a){ - // returns { a[0],a[0],a[1],a[1] } - return _mm_unpacklo_ps( a, a ); -} - -static INLINE vfloat vaddc2vfu(float &a) -{ - // loads a[0]..a[7] and returns { a[0]+a[1], a[2]+a[3], a[4]+a[5], a[6]+a[7] } - vfloat a1 = _mm_loadu_ps( &a ); - vfloat a2 = _mm_loadu_ps( (&a) + 4 ); - return _mm_shuffle_ps(a1,a2,_MM_SHUFFLE( 2,0,2,0 )) + _mm_shuffle_ps(a1,a2,_MM_SHUFFLE( 3,1,3,1 )); -} - -static INLINE vfloat vadivapb (vfloat a, vfloat b) { - return a / (a+b); -} - -static INLINE void vconvertrgbrgbrgbrgb2rrrrggggbbbb (const float * src, vfloat &rv, vfloat &gv, vfloat &bv) { // cool function name, isn't it ? :P - // converts a sequence of 4 float RGB triplets to 3 red, green and blue quadruples - rv = _mm_setr_ps(src[0],src[3],src[6],src[9]); - gv = _mm_setr_ps(src[1],src[4],src[7],src[10]); - bv = _mm_setr_ps(src[2],src[5],src[8],src[11]); -} - -#if defined( __SSE4_1__ ) && defined( __x86_64__ ) -static INLINE vfloat vceilf(vfloat x) { - return _mm_round_ps(x, _MM_FROUND_TO_POS_INF |_MM_FROUND_NO_EXC); -} - -#else - -static INLINE vfloat vceilf(vfloat x) { - __m128i zerov = _mm_setzero_si128(); - zerov = _mm_cmpeq_epi32(zerov, zerov); - const vfloat onev = (vfloat)_mm_slli_epi32(_mm_srli_epi32(zerov, 25), 23); //create vector 1.0f - const vfloat xi = _mm_cvtepi32_ps(_mm_cvttps_epi32(x)); - return xi + _mm_and_ps(_mm_cmplt_ps(xi, x), onev); -} -#endif - -#endif // __SSE2__ -#endif // SLEEFSSEAVX diff --git a/rtengine/sleefsseavx.h b/rtengine/sleefsseavx.h index 8fe20c54b..c10f4a0c2 100644 --- a/rtengine/sleefsseavx.h +++ b/rtengine/sleefsseavx.h @@ -1,124 +1,897 @@ -#include -#include +//////////////////////////////////////////////////////////////// +// +// this code was taken from http://shibatch.sourceforge.net/ +// Many thanks to the author of original version: Naoki Shibata +// +// This version contains modifications made by Ingo Weyrich +// +//////////////////////////////////////////////////////////////// +#pragma once +#include "rt_math.h" #ifdef __SSE2__ -#define VECTLENDP 2 -#define VECTLENSP 4 - -typedef __m128d vdouble; -typedef __m128i vint; - -typedef __m128 vfloat; -typedef __m128i vint2; -typedef __m128i vmask; - -static vdouble vloadu(double *p) -{ - return _mm_loadu_pd(p); -} -static void vstoreu(double *p, vdouble v) -{ - _mm_storeu_pd(p, v); -} - -static vfloat vloaduf(float *p) -{ - return _mm_loadu_ps(p); -} -static void vstoreuf(float *p, vfloat v) -{ - _mm_storeu_ps(p, v); -} - -static vint2 vloadui2(int32_t *p) -{ - return (vint2)_mm_loadu_si128((__m128i *)p); -} -static void vstoreui2(int32_t *p, vint2 v) -{ - _mm_storeu_si128((__m128i *)p, (__m128i)v); -} -#endif +#include "helpersse2.h" #ifdef ENABLE_AVX -#define VECTLENDP 4 -#define VECTLENSP 8 +#include "helperavx.h" +#endif -typedef __m256d vdouble; -typedef __m128i vint; +#ifdef __GNUC__ +#define INLINE __inline +#else +#define INLINE inline +#endif +#define PI4_A .7853981554508209228515625 +#define PI4_B .794662735614792836713604629039764404296875e-8 +#define PI4_C .306161699786838294306516483068750264552437361480769e-16 +#define M_4_PI 1.273239544735162542821171882678754627704620361328125 -typedef __m256 vfloat; -typedef struct { - vint x, y; -} vint2; +#define L2U .69314718055966295651160180568695068359375 +#define L2L .28235290563031577122588448175013436025525412068e-12 +#define R_LN2 1.442695040888963407359924681001892137426645954152985934135449406931 -static vdouble vloadu(double *p) -{ - return _mm256_loadu_pd(p); -} -static void vstoreu(double *p, vdouble v) -{ - return _mm256_storeu_pd(p, v); +#define PI4_Af 0.78515625f +#define PI4_Bf 0.00024127960205078125f +#define PI4_Cf 6.3329935073852539062e-07f +#define PI4_Df 4.9604681473525147339e-10f + +#define L2Uf 0.693145751953125f +#define L2Lf 1.428606765330187045e-06f +#define R_LN2f 1.442695040888963407359924681001892137426645954152985934135449406931f + +#define INFINITYf ((float)rtengine::RT_INFINITY) +#define NANf ((float)rtengine::RT_NAN) + +static INLINE vdouble vadd3(vdouble v0, vdouble v1, vdouble v2) { + return vadd(vadd(v0, v1), v2); } -static vfloat vloaduf(float *p) -{ - return _mm256_loadu_ps(p); -} -static void vstoreuf(float *p, vfloat v) -{ - return _mm256_storeu_ps(p, v); +static INLINE vdouble vadd4(vdouble v0, vdouble v1, vdouble v2, vdouble v3) { + return vadd3(vadd(v0, v1), v2, v3); } -static vint2 vloadui2(int32_t *p) -{ - vint2 r; - r.x = _mm_loadu_si128((__m128i *) p ); - r.y = _mm_loadu_si128((__m128i *)(p + 4)); +static INLINE vdouble vadd5(vdouble v0, vdouble v1, vdouble v2, vdouble v3, vdouble v4) { + return vadd4(vadd(v0, v1), v2, v3, v4); +} + +static INLINE vdouble vadd6(vdouble v0, vdouble v1, vdouble v2, vdouble v3, vdouble v4, vdouble v5) { + return vadd5(vadd(v0, v1), v2, v3, v4, v5); +} + +static INLINE vdouble vadd7(vdouble v0, vdouble v1, vdouble v2, vdouble v3, vdouble v4, vdouble v5, vdouble v6) { + return vadd6(vadd(v0, v1), v2, v3, v4, v5, v6); +} + +static INLINE vdouble vsub3(vdouble v0, vdouble v1, vdouble v2) { + return vsub(vsub(v0, v1), v2); +} + +static INLINE vdouble vsub4(vdouble v0, vdouble v1, vdouble v2, vdouble v3) { + return vsub3(vsub(v0, v1), v2, v3); +} + +static INLINE vdouble vsub5(vdouble v0, vdouble v1, vdouble v2, vdouble v3, vdouble v4) { + return vsub4(vsub(v0, v1), v2, v3, v4); +} + +// + +static INLINE vdouble2 normalize_d(vdouble2 t) { + vdouble2 s; + + s.x = vadd(t.x, t.y); + s.y = vadd(vsub(t.x, s.x), t.y); + + return s; +} + +static INLINE vdouble2 scale_d(vdouble2 d, vdouble s) { + vdouble2 r = {vmul(d.x, s), vmul(d.y, s)}; return r; } -static void vstoreui2(int32_t *p, vint2 v) -{ - _mm_storeu_si128((__m128i *) p , v.x); - _mm_storeu_si128((__m128i *)(p + 4), v.y); +static INLINE vdouble2 add_ss(vdouble x, vdouble y) { + vdouble2 r; + + r.x = vadd(x, y); + r.y = vadd(vsub(x, r.x), y); + + return r; } -#endif -typedef struct { +static INLINE vdouble2 add2_ss(vdouble x, vdouble y) { + vdouble2 r; + + r.x = vadd(x, y); + vdouble v = vsub(r.x, x); + r.y = vadd(vsub(x, vsub(r.x, v)), vsub(y, v)); + + return r; +} + +static INLINE vdouble2 add_ds(vdouble2 x, vdouble y) { + vdouble2 r; + + r.x = vadd(x.x, y); + r.y = vadd3(vsub(x.x, r.x), y, x.y); + + return r; +} + +static INLINE vdouble2 add2_ds(vdouble2 x, vdouble y) { + vdouble2 r; + + r.x = vadd(x.x, y); + vdouble v = vsub(r.x, x.x); + r.y = vadd(vsub(x.x, vsub(r.x, v)), vsub(y, v)); + r.y = vadd(r.y, x.y); + + return r; +} + +static INLINE vdouble2 add_sd(vdouble x, vdouble2 y) { + vdouble2 r; + + r.x = vadd(x, y.x); + r.y = vadd3(vsub(x, r.x), y.x, y.y); + + return r; +} + +static INLINE vdouble2 add_dd(vdouble2 x, vdouble2 y) { + // |x| >= |y| + + vdouble2 r; + + r.x = vadd(x.x, y.x); + r.y = vadd4(vsub(x.x, r.x), y.x, x.y, y.y); + + return r; +} + +static INLINE vdouble2 add2_dd(vdouble2 x, vdouble2 y) { + vdouble2 r; + + r.x = vadd(x.x, y.x); + vdouble v = vsub(r.x, x.x); + r.y = vadd(vsub(x.x, vsub(r.x, v)), vsub(y.x, v)); + r.y = vadd(r.y, vadd(x.y, y.y)); + + return r; +} + +static INLINE vdouble2 div_dd(vdouble2 n, vdouble2 d) { + vdouble t = vrec(d.x); + vdouble dh = vupper(d.x), dl = vsub(d.x, dh); + vdouble th = vupper(t ), tl = vsub(t , th); + vdouble nhh = vupper(n.x), nhl = vsub(n.x, nhh); + + vdouble2 q; + + q.x = vmul(n.x, t); + + vdouble u = vadd5(vsub(vmul(nhh, th), q.x), vmul(nhh, tl), vmul(nhl, th), vmul(nhl, tl), + vmul(q.x, vsub5(vcast_vd_d(1), vmul(dh, th), vmul(dh, tl), vmul(dl, th), vmul(dl, tl)))); + + q.y = vadd(vmul(t, vsub(n.y, vmul(q.x, d.y))), u); + + return q; +} + +static INLINE vdouble2 mul_ss(vdouble x, vdouble y) { + vdouble xh = vupper(x), xl = vsub(x, xh); + vdouble yh = vupper(y), yl = vsub(y, yh); + vdouble2 r; + + r.x = vmul(x, y); + r.y = vadd5(vmul(xh, yh), vneg(r.x), vmul(xl, yh), vmul(xh, yl), vmul(xl, yl)); + + return r; +} + +static INLINE vdouble2 mul_ds(vdouble2 x, vdouble y) { + vdouble xh = vupper(x.x), xl = vsub(x.x, xh); + vdouble yh = vupper(y ), yl = vsub(y , yh); + vdouble2 r; + + r.x = vmul(x.x, y); + r.y = vadd6(vmul(xh, yh), vneg(r.x), vmul(xl, yh), vmul(xh, yl), vmul(xl, yl), vmul(x.y, y)); + + return r; +} + +static INLINE vdouble2 mul_dd(vdouble2 x, vdouble2 y) { + vdouble xh = vupper(x.x), xl = vsub(x.x, xh); + vdouble yh = vupper(y.x), yl = vsub(y.x, yh); + vdouble2 r; + + r.x = vmul(x.x, y.x); + r.y = vadd7(vmul(xh, yh), vneg(r.x), vmul(xl, yh), vmul(xh, yl), vmul(xl, yl), vmul(x.x, y.y), vmul(x.y, y.x)); + + return r; +} + +static INLINE vdouble2 squ_d(vdouble2 x) { + vdouble xh = vupper(x.x), xl = vsub(x.x, xh); + vdouble2 r; + + r.x = vmul(x.x, x.x); + r.y = vadd5(vmul(xh, xh), vneg(r.x), vmul(vadd(xh, xh), xl), vmul(xl, xl), vmul(x.x, vadd(x.y, x.y))); + + return r; +} + +static INLINE vdouble2 rec_s(vdouble d) { + vdouble t = vrec(d); + vdouble dh = vupper(d), dl = vsub(d, dh); + vdouble th = vupper(t), tl = vsub(t, th); + vdouble2 q; + + q.x = t; + q.y = vmul(t, vsub5(vcast_vd_d(1), vmul(dh, th), vmul(dh, tl), vmul(dl, th), vmul(dl, tl))); + + return q; +} + +static INLINE vdouble2 sqrt_d(vdouble2 d) { + vdouble t = vsqrt(vadd(d.x, d.y)); + return scale_d(mul_dd(add2_dd(d, mul_ss(t, t)), rec_s(t)), vcast_vd_d(0.5)); +} + +// + +static INLINE vdouble xldexp(vdouble x, vint q) { return vldexp(x, q); } + +static INLINE vint xilogb(vdouble d) { + vdouble e = vcast_vd_vi(vsubi(vilogbp1(vabs(d)), vcast_vi_i(1))); + e = vsel(vmask_eq(d, vcast_vd_d(0)), vcast_vd_d(-2147483648.0), e); + e = vsel(vmask_eq(vabs(d), vcast_vd_d(rtengine::RT_INFINITY)), vcast_vd_d(2147483647), e); + return vrint_vi_vd(e); +} + +static INLINE vdouble xsin(vdouble d) { + vint q; + vdouble u, s; + + q = vrint_vi_vd(vmul(d, vcast_vd_d(rtengine::RT_1_PI))); + + u = vcast_vd_vi(q); + d = vadd(d, vmul(u, vcast_vd_d(-PI4_A*4))); + d = vadd(d, vmul(u, vcast_vd_d(-PI4_B*4))); + d = vadd(d, vmul(u, vcast_vd_d(-PI4_C*4))); + + s = vmul(d, d); + + d = vsel(vmaski_eq(vandi(q, vcast_vi_i(1)), vcast_vi_i(1)), vneg(d), d); + + u = vcast_vd_d(-7.97255955009037868891952e-18); + u = vmla(u, s, vcast_vd_d(2.81009972710863200091251e-15)); + u = vmla(u, s, vcast_vd_d(-7.64712219118158833288484e-13)); + u = vmla(u, s, vcast_vd_d(1.60590430605664501629054e-10)); + u = vmla(u, s, vcast_vd_d(-2.50521083763502045810755e-08)); + u = vmla(u, s, vcast_vd_d(2.75573192239198747630416e-06)); + u = vmla(u, s, vcast_vd_d(-0.000198412698412696162806809)); + u = vmla(u, s, vcast_vd_d(0.00833333333333332974823815)); + u = vmla(u, s, vcast_vd_d(-0.166666666666666657414808)); + + u = vmla(s, vmul(u, d), d); + + return u; +} + +static INLINE vdouble xcos(vdouble d) { + vint q; + vdouble u, s; + + q = vrint_vi_vd(vsub(vmul(d, vcast_vd_d(rtengine::RT_1_PI)), vcast_vd_d(0.5))); + q = vaddi(vaddi(q, q), vcast_vi_i(1)); + + u = vcast_vd_vi(q); + d = vadd(d, vmul(u, vcast_vd_d(-PI4_A*2))); + d = vadd(d, vmul(u, vcast_vd_d(-PI4_B*2))); + d = vadd(d, vmul(u, vcast_vd_d(-PI4_C*2))); + + s = vmul(d, d); + + d = vsel(vmaski_eq(vandi(q, vcast_vi_i(2)), vcast_vi_i(0)), vneg(d), d); + + u = vcast_vd_d(-7.97255955009037868891952e-18); + u = vmla(u, s, vcast_vd_d(2.81009972710863200091251e-15)); + u = vmla(u, s, vcast_vd_d(-7.64712219118158833288484e-13)); + u = vmla(u, s, vcast_vd_d(1.60590430605664501629054e-10)); + u = vmla(u, s, vcast_vd_d(-2.50521083763502045810755e-08)); + u = vmla(u, s, vcast_vd_d(2.75573192239198747630416e-06)); + u = vmla(u, s, vcast_vd_d(-0.000198412698412696162806809)); + u = vmla(u, s, vcast_vd_d(0.00833333333333332974823815)); + u = vmla(u, s, vcast_vd_d(-0.166666666666666657414808)); + + u = vmla(s, vmul(u, d), d); + + return u; +} + +static INLINE vdouble2 xsincos(vdouble d) { + vint q; + vmask m; + vdouble u, s, t, rx, ry; + vdouble2 r; + + q = vrint_vi_vd(vmul(d, vcast_vd_d(rtengine::RT_2_PI))); + + s = d; + + u = vcast_vd_vi(q); + s = vmla(u, vcast_vd_d(-PI4_A*2), s); + s = vmla(u, vcast_vd_d(-PI4_B*2), s); + s = vmla(u, vcast_vd_d(-PI4_C*2), s); + + t = s; + + s = vmul(s, s); + + u = vcast_vd_d(1.58938307283228937328511e-10); + u = vmla(u, s, vcast_vd_d(-2.50506943502539773349318e-08)); + u = vmla(u, s, vcast_vd_d(2.75573131776846360512547e-06)); + u = vmla(u, s, vcast_vd_d(-0.000198412698278911770864914)); + u = vmla(u, s, vcast_vd_d(0.0083333333333191845961746)); + u = vmla(u, s, vcast_vd_d(-0.166666666666666130709393)); + u = vmul(vmul(u, s), t); + + rx = vadd(t, u); + + u = vcast_vd_d(-1.13615350239097429531523e-11); + u = vmla(u, s, vcast_vd_d(2.08757471207040055479366e-09)); + u = vmla(u, s, vcast_vd_d(-2.75573144028847567498567e-07)); + u = vmla(u, s, vcast_vd_d(2.48015872890001867311915e-05)); + u = vmla(u, s, vcast_vd_d(-0.00138888888888714019282329)); + u = vmla(u, s, vcast_vd_d(0.0416666666666665519592062)); + u = vmla(u, s, vcast_vd_d(-0.5)); + + ry = vadd(vcast_vd_d(1), vmul(s, u)); + + m = vmaski_eq(vandi(q, vcast_vi_i(1)), vcast_vi_i(0)); + r.x = vsel(m, rx, ry); + r.y = vsel(m, ry, rx); + + m = vmaski_eq(vandi(q, vcast_vi_i(2)), vcast_vi_i(2)); + r.x = vreinterpret_vd_vm(vxorm(vandm(m, vreinterpret_vm_vd(vcast_vd_d(-0.0))), vreinterpret_vm_vd(r.x))); + + m = vmaski_eq(vandi(vaddi(q, vcast_vi_i(1)), vcast_vi_i(2)), vcast_vi_i(2)); + r.y = vreinterpret_vd_vm(vxorm(vandm(m, vreinterpret_vm_vd(vcast_vd_d(-0.0))), vreinterpret_vm_vd(r.y))); + + m = vmask_isinf(d); + r.x = vsel(m, vcast_vd_d(rtengine::RT_NAN), r.x); + r.y = vsel(m, vcast_vd_d(rtengine::RT_NAN), r.y); + + return r; +} + +static INLINE vdouble xtan(vdouble d) { + vint q; + vdouble u, s, x; + vmask m; + + q = vrint_vi_vd(vmul(d, vcast_vd_d(rtengine::RT_2_PI))); + + u = vcast_vd_vi(q); + x = vadd(d, vmul(u, vcast_vd_d(-PI4_A*2))); + x = vadd(x, vmul(u, vcast_vd_d(-PI4_B*2))); + x = vadd(x, vmul(u, vcast_vd_d(-PI4_C*2))); + + s = vmul(x, x); + + m = vmaski_eq(vandi(q, vcast_vi_i(1)), vcast_vi_i(1)); + x = vsel(m, vneg(x), x); + + u = vcast_vd_d(1.01419718511083373224408e-05); + u = vmla(u, s, vcast_vd_d(-2.59519791585924697698614e-05)); + u = vmla(u, s, vcast_vd_d(5.23388081915899855325186e-05)); + u = vmla(u, s, vcast_vd_d(-3.05033014433946488225616e-05)); + u = vmla(u, s, vcast_vd_d(7.14707504084242744267497e-05)); + u = vmla(u, s, vcast_vd_d(8.09674518280159187045078e-05)); + u = vmla(u, s, vcast_vd_d(0.000244884931879331847054404)); + u = vmla(u, s, vcast_vd_d(0.000588505168743587154904506)); + u = vmla(u, s, vcast_vd_d(0.00145612788922812427978848)); + u = vmla(u, s, vcast_vd_d(0.00359208743836906619142924)); + u = vmla(u, s, vcast_vd_d(0.00886323944362401618113356)); + u = vmla(u, s, vcast_vd_d(0.0218694882853846389592078)); + u = vmla(u, s, vcast_vd_d(0.0539682539781298417636002)); + u = vmla(u, s, vcast_vd_d(0.133333333333125941821962)); + u = vmla(u, s, vcast_vd_d(0.333333333333334980164153)); + + u = vmla(s, vmul(u, x), x); + + u = vsel(m, vrec(u), u); + + u = vsel(vmask_isinf(d), vcast_vd_d(rtengine::RT_NAN), u); + + return u; +} + +static INLINE vdouble atan2k(vdouble y, vdouble x) { + vdouble s, t, u; + vint q; + vmask p; + + q = vseli_lt(x, vcast_vd_d(0), vcast_vi_i(-2), vcast_vi_i(0)); + x = vabs(x); + + q = vseli_lt(x, y, vaddi(q, vcast_vi_i(1)), q); + p = vmask_lt(x, y); + s = vsel (p, vneg(x), y); + t = vmax (x, y); + + s = vdiv(s, t); + t = vmul(s, s); + + u = vcast_vd_d(-1.88796008463073496563746e-05); + u = vmla(u, t, vcast_vd_d(0.000209850076645816976906797)); + u = vmla(u, t, vcast_vd_d(-0.00110611831486672482563471)); + u = vmla(u, t, vcast_vd_d(0.00370026744188713119232403)); + u = vmla(u, t, vcast_vd_d(-0.00889896195887655491740809)); + u = vmla(u, t, vcast_vd_d(0.016599329773529201970117)); + u = vmla(u, t, vcast_vd_d(-0.0254517624932312641616861)); + u = vmla(u, t, vcast_vd_d(0.0337852580001353069993897)); + u = vmla(u, t, vcast_vd_d(-0.0407629191276836500001934)); + u = vmla(u, t, vcast_vd_d(0.0466667150077840625632675)); + u = vmla(u, t, vcast_vd_d(-0.0523674852303482457616113)); + u = vmla(u, t, vcast_vd_d(0.0587666392926673580854313)); + u = vmla(u, t, vcast_vd_d(-0.0666573579361080525984562)); + u = vmla(u, t, vcast_vd_d(0.0769219538311769618355029)); + u = vmla(u, t, vcast_vd_d(-0.090908995008245008229153)); + u = vmla(u, t, vcast_vd_d(0.111111105648261418443745)); + u = vmla(u, t, vcast_vd_d(-0.14285714266771329383765)); + u = vmla(u, t, vcast_vd_d(0.199999999996591265594148)); + u = vmla(u, t, vcast_vd_d(-0.333333333333311110369124)); + + t = vadd(s, vmul(s, vmul(t, u))); + t = vadd(t, vmul(vcast_vd_vi(q), vcast_vd_d(rtengine::RT_PI/2))); + + return t; +} + +static INLINE vdouble xatan2(vdouble y, vdouble x) { + vdouble r = atan2k(vabs(y), x); + + r = vmulsign(r, x); + r = vsel(vorm(vmask_isinf(x), vmask_eq(x, vcast_vd_d(0))), vsub(vcast_vd_d(rtengine::RT_PI/2), visinf2(x, vmulsign(vcast_vd_d(rtengine::RT_PI/2), x))), r); + r = vsel(vmask_isinf(y), vsub(vcast_vd_d(rtengine::RT_PI/2), visinf2(x, vmulsign(vcast_vd_d(rtengine::RT_PI/4), x))), r); + r = vsel(vmask_eq(y, vcast_vd_d(0)), vsel(vmask_eq(vsign(x), vcast_vd_d(-1.0)), vcast_vd_d(rtengine::RT_PI), vcast_vd_d(0)), r); + + return vsel(vorm(vmask_isnan(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_NAN), vmulsign(r, y)); +} + +static INLINE vdouble xasin(vdouble d) { vdouble x, y; -} vdouble2; + x = vadd(vcast_vd_d(1), d); + y = vsub(vcast_vd_d(1), d); + x = vmul(x, y); + x = vsqrt(x); + x = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), atan2k(vabs(d), x)); + return vmulsign(x, d); +} -vdouble xldexp(vdouble x, vint q); -vint xilogb(vdouble d); +static INLINE vdouble xacos(vdouble d) { + vdouble x, y; + x = vadd(vcast_vd_d(1), d); + y = vsub(vcast_vd_d(1), d); + x = vmul(x, y); + x = vsqrt(x); + x = vmulsign(atan2k(x, vabs(d)), d); + y = (vdouble)vandm(vmask_lt(d, vcast_vd_d(0)), (vmask)vcast_vd_d(rtengine::RT_PI)); + x = vadd(x, y); + return x; +} -vdouble xsin(vdouble d); -vdouble xcos(vdouble d); -vdouble2 xsincos(vdouble d); -vdouble xtan(vdouble d); -vdouble xasin(vdouble s); -vdouble xacos(vdouble s); -vdouble xatan(vdouble s); -vdouble xatan2(vdouble y, vdouble x); -vdouble xlog(vdouble d); -vdouble xexp(vdouble d); -vdouble xpow(vdouble x, vdouble y); +static INLINE vdouble xatan(vdouble s) { + vdouble t, u; + vint q; -vdouble xsinh(vdouble d); -vdouble xcosh(vdouble d); -vdouble xtanh(vdouble d); -vdouble xasinh(vdouble s); -vdouble xacosh(vdouble s); -vdouble xatanh(vdouble s); + q = vseli_lt(s, vcast_vd_d(0), vcast_vi_i(2), vcast_vi_i(0)); + s = vabs(s); -vdouble xcbrt(vdouble d); + q = vseli_lt(vcast_vd_d(1), s, vaddi(q, vcast_vi_i(1)), q); + s = vsel(vmask_lt(vcast_vd_d(1), s), vdiv(vcast_vd_d(1), s), s); -vdouble xexp2(vdouble a); -vdouble xexp10(vdouble a); -vdouble xexpm1(vdouble a); -vdouble xlog10(vdouble a); -vdouble xlog1p(vdouble a); + t = vmul(s, s); + + u = vcast_vd_d(-1.88796008463073496563746e-05); + u = vmla(u, t, vcast_vd_d(0.000209850076645816976906797)); + u = vmla(u, t, vcast_vd_d(-0.00110611831486672482563471)); + u = vmla(u, t, vcast_vd_d(0.00370026744188713119232403)); + u = vmla(u, t, vcast_vd_d(-0.00889896195887655491740809)); + u = vmla(u, t, vcast_vd_d(0.016599329773529201970117)); + u = vmla(u, t, vcast_vd_d(-0.0254517624932312641616861)); + u = vmla(u, t, vcast_vd_d(0.0337852580001353069993897)); + u = vmla(u, t, vcast_vd_d(-0.0407629191276836500001934)); + u = vmla(u, t, vcast_vd_d(0.0466667150077840625632675)); + u = vmla(u, t, vcast_vd_d(-0.0523674852303482457616113)); + u = vmla(u, t, vcast_vd_d(0.0587666392926673580854313)); + u = vmla(u, t, vcast_vd_d(-0.0666573579361080525984562)); + u = vmla(u, t, vcast_vd_d(0.0769219538311769618355029)); + u = vmla(u, t, vcast_vd_d(-0.090908995008245008229153)); + u = vmla(u, t, vcast_vd_d(0.111111105648261418443745)); + u = vmla(u, t, vcast_vd_d(-0.14285714266771329383765)); + u = vmla(u, t, vcast_vd_d(0.199999999996591265594148)); + u = vmla(u, t, vcast_vd_d(-0.333333333333311110369124)); + + t = vadd(s, vmul(s, vmul(t, u))); + + t = vsel(vmaski_eq(vandi(q, vcast_vi_i(1)), vcast_vi_i(1)), vsub(vcast_vd_d(rtengine::RT_PI/2), t), t); + t = vsel(vmaski_eq(vandi(q, vcast_vi_i(2)), vcast_vi_i(2)), vneg(t), t); + + return t; +} + +static INLINE vdouble xlog(vdouble d) { + vdouble x, x2; + vdouble t, m; + vint e; + + e = vilogbp1(vmul(d, vcast_vd_d(0.7071))); + m = vldexp(d, vsubi(vcast_vi_i(0), e)); + + x = vdiv(vadd(vcast_vd_d(-1), m), vadd(vcast_vd_d(1), m)); + x2 = vmul(x, x); + + t = vcast_vd_d(0.148197055177935105296783); + t = vmla(t, x2, vcast_vd_d(0.153108178020442575739679)); + t = vmla(t, x2, vcast_vd_d(0.181837339521549679055568)); + t = vmla(t, x2, vcast_vd_d(0.22222194152736701733275)); + t = vmla(t, x2, vcast_vd_d(0.285714288030134544449368)); + t = vmla(t, x2, vcast_vd_d(0.399999999989941956712869)); + t = vmla(t, x2, vcast_vd_d(0.666666666666685503450651)); + t = vmla(t, x2, vcast_vd_d(2)); + + x = vadd(vmul(x, t), vmul(vcast_vd_d(0.693147180559945286226764), vcast_vd_vi(e))); + + x = vsel(vmask_ispinf(d), vcast_vd_d(rtengine::RT_INFINITY), x); + x = vsel(vmask_gt(vcast_vd_d(0), d), vcast_vd_d(rtengine::RT_NAN), x); + x = vsel(vmask_eq(d, vcast_vd_d(0)), vcast_vd_d(-rtengine::RT_INFINITY), x); + + return x; +} + +static INLINE vdouble xexp(vdouble d) { + vint q = vrint_vi_vd(vmul(d, vcast_vd_d(R_LN2))); + vdouble s, u; + + s = vadd(d, vmul(vcast_vd_vi(q), vcast_vd_d(-L2U))); + s = vadd(s, vmul(vcast_vd_vi(q), vcast_vd_d(-L2L))); + + u = vcast_vd_d(2.08860621107283687536341e-09); + u = vmla(u, s, vcast_vd_d(2.51112930892876518610661e-08)); + u = vmla(u, s, vcast_vd_d(2.75573911234900471893338e-07)); + u = vmla(u, s, vcast_vd_d(2.75572362911928827629423e-06)); + u = vmla(u, s, vcast_vd_d(2.4801587159235472998791e-05)); + u = vmla(u, s, vcast_vd_d(0.000198412698960509205564975)); + u = vmla(u, s, vcast_vd_d(0.00138888888889774492207962)); + u = vmla(u, s, vcast_vd_d(0.00833333333331652721664984)); + u = vmla(u, s, vcast_vd_d(0.0416666666666665047591422)); + u = vmla(u, s, vcast_vd_d(0.166666666666666851703837)); + u = vmla(u, s, vcast_vd_d(0.5)); + + u = vadd(vcast_vd_d(1), vadd(s, vmul(vmul(s, s), u))); + + u = vldexp(u, q); + + u = vsel(vmask_isminf(d), vcast_vd_d(0), u); + + return u; +} + +static INLINE vdouble2 logk(vdouble d) { + vdouble2 x, x2; + vdouble t, m; + vint e; + + e = vilogbp1(vmul(d, vcast_vd_d(0.7071))); + m = vldexp(d, vsubi(vcast_vi_i(0), e)); + + x = div_dd(add2_ss(vcast_vd_d(-1), m), add2_ss(vcast_vd_d(1), m)); + x2 = squ_d(x); + x2 = normalize_d(x2); + + t = vcast_vd_d(0.134601987501262130076155); + t = vmla(t, x2.x, vcast_vd_d(0.132248509032032670243288)); + t = vmla(t, x2.x, vcast_vd_d(0.153883458318096079652524)); + t = vmla(t, x2.x, vcast_vd_d(0.181817427573705403298686)); + t = vmla(t, x2.x, vcast_vd_d(0.222222231326187414840781)); + t = vmla(t, x2.x, vcast_vd_d(0.285714285651261412873718)); + t = vmla(t, x2.x, vcast_vd_d(0.400000000000222439910458)); + t = vmla(t, x2.x, vcast_vd_d(0.666666666666666371239645)); + + return add2_dd(mul_ds(dd(vcast_vd_d(0.693147180559945286226764), vcast_vd_d(2.319046813846299558417771e-17)), + vcast_vd_vi(e)), + add2_dd(scale_d(x, vcast_vd_d(2)), mul_ds(mul_dd(x2, x), t))); +} + +static INLINE vdouble expk(vdouble2 d) { + vdouble u = vmul(vadd(d.x, d.y), vcast_vd_d(R_LN2)); + vint q = vrint_vi_vd(u); + vdouble2 s, t; + + s = add2_ds(d, vmul(vcast_vd_vi(q), vcast_vd_d(-L2U))); + s = add2_ds(s, vmul(vcast_vd_vi(q), vcast_vd_d(-L2L))); + + q = vrint_vi_vd(vmin(vmax(vcast_vd_d(-2047.49), u), vcast_vd_d(2047.49))); + + s = normalize_d(s); + + u = vcast_vd_d(2.51069683420950419527139e-08); + u = vmla(u, s.x, vcast_vd_d(2.76286166770270649116855e-07)); + u = vmla(u, s.x, vcast_vd_d(2.75572496725023574143864e-06)); + u = vmla(u, s.x, vcast_vd_d(2.48014973989819794114153e-05)); + u = vmla(u, s.x, vcast_vd_d(0.000198412698809069797676111)); + u = vmla(u, s.x, vcast_vd_d(0.0013888888939977128960529)); + u = vmla(u, s.x, vcast_vd_d(0.00833333333332371417601081)); + u = vmla(u, s.x, vcast_vd_d(0.0416666666665409524128449)); + u = vmla(u, s.x, vcast_vd_d(0.166666666666666740681535)); + u = vmla(u, s.x, vcast_vd_d(0.500000000000000999200722)); + + t = add_dd(s, mul_ds(squ_d(s), u)); + + t = add_sd(vcast_vd_d(1), t); + u = vadd(t.x, t.y); + u = vldexp(u, q); + + return u; +} + +static INLINE vdouble xpow(vdouble x, vdouble y) { +#if 1 + vmask yisint = vmask_eq(vcast_vd_vi(vrint_vi_vd(y)), y); + vmask yisodd = vandm(vmaski_eq(vandi(vrint_vi_vd(y), vcast_vi_i(1)), vcast_vi_i(1)), yisint); + + vdouble result = expk(mul_ds(logk(vabs(x)), y)); + + //result = vsel(vmask_isnan(result), vcast_vd_d(rtengine::RT_INFINITY), result); + + result = vmul(result, + vsel(vmask_gt(x, vcast_vd_d(0)), + vcast_vd_d(1), + vsel(yisint, + vsel(yisodd, + vcast_vd_d(-1), + vcast_vd_d(1)), + vcast_vd_d(rtengine::RT_NAN)))); + + vdouble efx = vreinterpret_vd_vm(vxorm(vreinterpret_vm_vd(vsub(vabs(x), vcast_vd_d(1))), vsignbit(y))); + + result = vsel(vmask_isinf(y), + vsel(vmask_lt(efx, vcast_vd_d(0)), + vcast_vd_d(0), + vsel(vmask_eq(efx, vcast_vd_d(0)), + vcast_vd_d(1.0), + vcast_vd_d(rtengine::RT_INFINITY))), + result); + + result = vsel(vorm(vmask_isinf(x), vmask_eq(x, vcast_vd_d(0))), + vmul(vsel(yisodd, vsign(x), vcast_vd_d(1)), + vsel(vmask_lt(vsel(vmask_eq(x, vcast_vd_d(0)), vneg(y), y), vcast_vd_d(0)), + vcast_vd_d(0), + vcast_vd_d(rtengine::RT_INFINITY))), + result); + + result = vsel(vorm(vmask_isnan(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_NAN), result); + + result = vsel(vorm(vmask_eq(y, vcast_vd_d(0)), vmask_eq(x, vcast_vd_d(1))), vcast_vd_d(1), result); + + return result; +#else + return expk(mul_ds(logk(x), y)); +#endif +} + +static INLINE vdouble2 expk2(vdouble2 d) { + vdouble u = vmul(vadd(d.x, d.y), vcast_vd_d(R_LN2)); + vint q = vrint_vi_vd(u); + vdouble2 s, t; + + s = add2_ds(d, vmul(vcast_vd_vi(q), vcast_vd_d(-L2U))); + s = add2_ds(s, vmul(vcast_vd_vi(q), vcast_vd_d(-L2L))); + + q = vrint_vi_vd(vmin(vmax(vcast_vd_d(-2047.49), u), vcast_vd_d(2047.49))); + + s = normalize_d(s); + + u = vcast_vd_d(2.51069683420950419527139e-08); + u = vmla(u, s.x, vcast_vd_d(2.76286166770270649116855e-07)); + u = vmla(u, s.x, vcast_vd_d(2.75572496725023574143864e-06)); + u = vmla(u, s.x, vcast_vd_d(2.48014973989819794114153e-05)); + u = vmla(u, s.x, vcast_vd_d(0.000198412698809069797676111)); + u = vmla(u, s.x, vcast_vd_d(0.0013888888939977128960529)); + u = vmla(u, s.x, vcast_vd_d(0.00833333333332371417601081)); + u = vmla(u, s.x, vcast_vd_d(0.0416666666665409524128449)); + u = vmla(u, s.x, vcast_vd_d(0.166666666666666740681535)); + u = vmla(u, s.x, vcast_vd_d(0.500000000000000999200722)); + + t = add_dd(s, mul_ds(squ_d(s), u)); + + t = add_sd(vcast_vd_d(1), t); + + return dd(vldexp(t.x, q), vldexp(t.y, q)); +} + +static INLINE vdouble xsinh(vdouble x) { + vdouble y = vabs(x); + vdouble2 d = expk2(dd(y, vcast_vd_d(0))); + d = add2_dd(d, div_dd(dd(vcast_vd_d(-1), vcast_vd_d(0)), d)); + y = vmul(vadd(d.x, d.y), vcast_vd_d(0.5)); + + y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_INFINITY), y); + y = vmulsign(y, x); + y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); + + return y; +} + +static INLINE vdouble xcosh(vdouble x) { + vdouble2 d = expk2(dd(x, vcast_vd_d(0))); + d = add2_dd(d, div_dd(dd(vcast_vd_d(1), vcast_vd_d(0)), d)); + vdouble y = vmul(vadd(d.x, d.y), vcast_vd_d(0.5)); + + y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_INFINITY), y); + y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); + + return y; +} + +static INLINE vdouble xtanh(vdouble x) { + vdouble y = vabs(x); + vdouble2 d = expk2(dd(y, vcast_vd_d(0))); + vdouble2 e = div_dd(dd(vcast_vd_d(1), vcast_vd_d(0)), d); + d = div_dd(add2_dd(d, scale_d(e, vcast_vd_d(-1))), add2_dd(d, e)); + y = d.x + d.y; + + y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(1.0), y); + y = vmulsign(y, x); + y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); + + return y; +} + +static INLINE vdouble2 logk2(vdouble2 d) { + vdouble2 x, x2, m; + vdouble t; + vint e; + + d = normalize_d(d); + e = vilogbp1(vmul(d.x, vcast_vd_d(0.7071))); + m = scale_d(d, vldexp(vcast_vd_d(1), vsubi(vcast_vi_i(0), e))); + + x = div_dd(add2_ds(m, vcast_vd_d(-1)), add2_ds(m, vcast_vd_d(1))); + x2 = squ_d(x); + x2 = normalize_d(x2); + + t = vcast_vd_d(0.134601987501262130076155); + t = vmla(t, x2.x, vcast_vd_d(0.132248509032032670243288)); + t = vmla(t, x2.x, vcast_vd_d(0.153883458318096079652524)); + t = vmla(t, x2.x, vcast_vd_d(0.181817427573705403298686)); + t = vmla(t, x2.x, vcast_vd_d(0.222222231326187414840781)); + t = vmla(t, x2.x, vcast_vd_d(0.285714285651261412873718)); + t = vmla(t, x2.x, vcast_vd_d(0.400000000000222439910458)); + t = vmla(t, x2.x, vcast_vd_d(0.666666666666666371239645)); + + return add2_dd(mul_ds(dd(vcast_vd_d(0.693147180559945286226764), vcast_vd_d(2.319046813846299558417771e-17)), + vcast_vd_vi(e)), + add2_dd(scale_d(x, vcast_vd_d(2)), mul_ds(mul_dd(x2, x), t))); +} + +static INLINE vdouble xasinh(vdouble x) { + vdouble y = vabs(x); + vdouble2 d = logk2(add2_ds(sqrt_d(add2_ds(mul_ss(y, y), vcast_vd_d(1))), y)); + y = vadd(d.x, d.y); + + y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_INFINITY), y); + y = vmulsign(y, x); + y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); + + return y; +} + +static INLINE vdouble xacosh(vdouble x) { + vdouble2 d = logk2(add2_ds(sqrt_d(add2_ds(mul_ss(x, x), vcast_vd_d(-1))), x)); + vdouble y = vadd(d.x, d.y); + + y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_INFINITY), y); + y = vsel(vmask_eq(x, vcast_vd_d(1.0)), vcast_vd_d(0.0), y); + y = vsel(vmask_lt(x, vcast_vd_d(1.0)), vcast_vd_d(rtengine::RT_NAN), y); + y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); + + return y; +} + +static INLINE vdouble xatanh(vdouble x) { + vdouble y = vabs(x); + vdouble2 d = logk2(div_dd(add2_ss(vcast_vd_d(1), y), add2_ss(vcast_vd_d(1), -y))); + y = vsel(vmask_gt(y, vcast_vd_d(1.0)), vcast_vd_d(rtengine::RT_NAN), vsel(vmask_eq(y, vcast_vd_d(1.0)), vcast_vd_d(rtengine::RT_INFINITY), vmul(vadd(d.x, d.y), vcast_vd_d(0.5)))); + + y = vsel(vorm(vmask_isinf(x), vmask_isnan(y)), vcast_vd_d(rtengine::RT_NAN), y); + y = vmulsign(y, x); + y = vsel(vmask_isnan(x), vcast_vd_d(rtengine::RT_NAN), y); + + return y; +} + +static INLINE vdouble xcbrt(vdouble d) { + vdouble x, y, q = vcast_vd_d(1.0); + vint e, qu, re; + vdouble t; + + e = vilogbp1(vabs(d)); + d = vldexp(d, vsubi(vcast_vi_i(0), e)); + + t = vadd(vcast_vd_vi(e), vcast_vd_d(6144)); + qu = vtruncate_vi_vd(vdiv(t, vcast_vd_d(3))); + re = vtruncate_vi_vd(vsub(t, vmul(vcast_vd_vi(qu), vcast_vd_d(3)))); + + q = vsel(vmaski_eq(re, vcast_vi_i(1)), vcast_vd_d(1.2599210498948731647672106), q); + q = vsel(vmaski_eq(re, vcast_vi_i(2)), vcast_vd_d(1.5874010519681994747517056), q); + q = vldexp(q, vsubi(qu, vcast_vi_i(2048))); + + q = vmulsign(q, d); + + d = vabs(d); + + x = vcast_vd_d(-0.640245898480692909870982); + x = vmla(x, d, vcast_vd_d(2.96155103020039511818595)); + x = vmla(x, d, vcast_vd_d(-5.73353060922947843636166)); + x = vmla(x, d, vcast_vd_d(6.03990368989458747961407)); + x = vmla(x, d, vcast_vd_d(-3.85841935510444988821632)); + x = vmla(x, d, vcast_vd_d(2.2307275302496609725722)); + + y = vmul(x, x); y = vmul(y, y); x = vsub(x, vmul(vmla(d, y, vneg(x)), vcast_vd_d(1.0 / 3.0))); + y = vmul(vmul(d, x), x); + y = vmul(vsub(y, vmul(vmul(vcast_vd_d(2.0 / 3.0), y), vmla(y, x, vcast_vd_d(-1.0)))), q); + + return y; +} + +static INLINE vdouble xexp2(vdouble a) { + vdouble u = expk(mul_ds(dd(vcast_vd_d(0.69314718055994528623), vcast_vd_d(2.3190468138462995584e-17)), a)); + u = vsel(vmask_ispinf(a), vcast_vd_d(rtengine::RT_INFINITY), u); + u = vsel(vmask_isminf(a), vcast_vd_d(0), u); + return u; +} + +static INLINE vdouble xexp10(vdouble a) { + vdouble u = expk(mul_ds(dd(vcast_vd_d(2.3025850929940459011), vcast_vd_d(-2.1707562233822493508e-16)), a)); + u = vsel(vmask_ispinf(a), vcast_vd_d(rtengine::RT_INFINITY), u); + u = vsel(vmask_isminf(a), vcast_vd_d(0), u); + return u; +} + +static INLINE vdouble xexpm1(vdouble a) { + vdouble2 d = add2_ds(expk2(dd(a, vcast_vd_d(0))), vcast_vd_d(-1.0)); + vdouble x = d.x + d.y; + x = vsel(vmask_ispinf(a), vcast_vd_d(rtengine::RT_INFINITY), x); + x = vsel(vmask_isminf(a), vcast_vd_d(-1), x); + return x; +} + +static INLINE vdouble xlog10(vdouble a) { + vdouble2 d = mul_dd(logk(a), dd(vcast_vd_d(0.43429448190325176116), vcast_vd_d(6.6494347733425473126e-17))); + vdouble x = d.x + d.y; + + x = vsel(vmask_ispinf(a), vcast_vd_d(rtengine::RT_INFINITY), x); + x = vsel(vmask_gt(vcast_vd_d(0), a), vcast_vd_d(rtengine::RT_NAN), x); + x = vsel(vmask_eq(a, vcast_vd_d(0)), vcast_vd_d(-rtengine::RT_INFINITY), x); + + return x; +} + +static INLINE vdouble xlog1p(vdouble a) { + vdouble2 d = logk2(add2_ss(a, vcast_vd_d(1))); + vdouble x = d.x + d.y; + + x = vsel(vmask_ispinf(a), vcast_vd_d(rtengine::RT_INFINITY), x); + x = vsel(vmask_gt(vcast_vd_d(-1), a), vcast_vd_d(rtengine::RT_NAN), x); + x = vsel(vmask_eq(a, vcast_vd_d(-1)), vcast_vd_d(-rtengine::RT_INFINITY), x); + + return x; +} // @@ -126,15 +899,580 @@ typedef struct { vfloat x, y; } vfloat2; -vfloat xsinf(vfloat d); -vfloat xcosf(vfloat d); -vfloat2 xsincosf(vfloat d); -vfloat xtanf(vfloat d); -vfloat xasinf(vfloat s); -vfloat xacosf(vfloat s); -vfloat xatanf(vfloat s); -vfloat xatan2f(vfloat y, vfloat x); -vfloat xlogf(vfloat d); -vfloat xlogf0(vfloat d); -vfloat xexpf(vfloat d); -vfloat xcbrtf(vfloat s); +static INLINE vfloat vabsf(vfloat f) { return (vfloat)vandnotm((vmask)vcast_vf_f(-0.0f), (vmask)f); } +static INLINE vfloat vnegf(vfloat f) { return (vfloat)vxorm((vmask)f, (vmask)vcast_vf_f(-0.0f)); } + +#ifdef __SSE4_1__ +// only one instruction when using SSE4.1 +static INLINE vfloat vself(vmask mask, vfloat x, vfloat y) { + return _mm_blendv_ps(y,x,(vfloat)mask); +} + +static INLINE vint vselc(vmask mask, vint x, vint y) { + return _mm_blendv_epi8(y,x,mask); +} + +#else +// three instructions when using SSE2 +static INLINE vfloat vself(vmask mask, vfloat x, vfloat y) { + return (vfloat)vorm(vandm(mask, (vmask)x), vandnotm(mask, (vmask)y)); +} + +static INLINE vint vselc(vmask mask, vint x, vint y) { + return vorm(vandm(mask, (vmask)x), vandnotm(mask, (vmask)y)); +} +#endif + +static INLINE vfloat vselfzero(vmask mask, vfloat x) { + // returns value of x if corresponding mask bits are 1, else returns 0 + // faster than vself(mask, x, ZEROV) + return _mm_and_ps((vfloat)mask, x); +} +static INLINE vfloat vselfnotzero(vmask mask, vfloat x) { + // returns value of x if corresponding mask bits are 0, else returns 0 + // faster than vself(mask, ZEROV, x) + return _mm_andnot_ps((vfloat)mask, x); +} + +static INLINE vint vselizero(vmask mask, vint x) { + // returns value of x if corresponding mask bits are 1, else returns 0 + // faster than vselc(mask, x, ZEROV) + return _mm_and_si128(mask, x); +} +static INLINE vint vselinotzero(vmask mask, vint x) { + // returns value of x if corresponding mask bits are 0, else returns 0 + // faster than vselc(mask, ZEROV, x) + return _mm_andnot_si128(mask, x); +} + +static INLINE vint2 vseli2_lt(vfloat f0, vfloat f1, vint2 x, vint2 y) { + vint2 m2 = vcast_vi2_vm(vmaskf_lt(f0, f1)); + return vori2(vandi2(m2, x), vandnoti2(m2, y)); +} + +static INLINE vmask vsignbitf(vfloat f) { + return vandm((vmask)f, (vmask)vcast_vf_f(-0.0f)); +} + +static INLINE vfloat vmulsignf(vfloat x, vfloat y) { + return (vfloat)vxorm((vmask)x, vsignbitf(y)); +} + +static INLINE vfloat vsignf(vfloat f) { + return (vfloat)vorm((vmask)vcast_vf_f(1.0f), vandm((vmask)vcast_vf_f(-0.0f), (vmask)f)); +} + +static INLINE vmask vmaskf_isinf(vfloat d) { return vmaskf_eq(vabsf(d), vcast_vf_f(INFINITYf)); } +static INLINE vmask vmaskf_ispinf(vfloat d) { return vmaskf_eq(d, vcast_vf_f(INFINITYf)); } +static INLINE vmask vmaskf_isminf(vfloat d) { return vmaskf_eq(d, vcast_vf_f(-INFINITYf)); } +static INLINE vmask vmaskf_isnan(vfloat d) { return vmaskf_neq(d, d); } +// the following is equivalent to vorm(vmaskf_isnan(a), vmaskf_isnan(b)), but faster +static INLINE vmask vmaskf_isnan(vfloat a, vfloat b) { return (vmask)_mm_cmpunord_ps(a, b); } +static INLINE vfloat visinf2f(vfloat d, vfloat m) { return (vfloat)vandm(vmaskf_isinf(d), vorm(vsignbitf(d), (vmask)m)); } +static INLINE vfloat visinff(vfloat d) { return visinf2f(d, vcast_vf_f(1.0f)); } + +static INLINE vint2 vilogbp1f(vfloat d) { + vmask m = vmaskf_lt(d, vcast_vf_f(5.421010862427522E-20f)); + d = vself(m, vmulf(vcast_vf_f(1.8446744073709552E19f), d), d); + vint2 q = vandi2(vsrli2(vcast_vi2_vm(vreinterpret_vm_vf(d)), 23), vcast_vi2_i(0xff)); + q = vsubi2(q, vseli2(m, vcast_vi2_i(64 + 0x7e), vcast_vi2_i(0x7e))); + return q; +} + +static INLINE vfloat vldexpf(vfloat x, vint2 q) { + vfloat u; + vint2 m = vsrai2(q, 31); + m = vslli2(vsubi2(vsrai2(vaddi2(m, q), 6), m), 4); + q = vsubi2(q, vslli2(m, 2)); + u = vreinterpret_vf_vm(vcast_vm_vi2(vslli2(vaddi2(m, vcast_vi2_i(0x7f)), 23))); + x = vmulf(vmulf(vmulf(vmulf(x, u), u), u), u); + u = vreinterpret_vf_vm(vcast_vm_vi2(vslli2(vaddi2(q, vcast_vi2_i(0x7f)), 23))); + return vmulf(x, u); +} + +static INLINE vfloat xsinf(vfloat d) { + vint2 q; + vfloat u, s; + + q = vrint_vi2_vf(vmulf(d, vcast_vf_f((float)rtengine::RT_1_PI))); + + u = vcast_vf_vi2(q); + d = vmlaf(u, vcast_vf_f(-PI4_Af*4), d); + d = vmlaf(u, vcast_vf_f(-PI4_Bf*4), d); + d = vmlaf(u, vcast_vf_f(-PI4_Cf*4), d); + d = vmlaf(u, vcast_vf_f(-PI4_Df*4), d); + + s = vmulf(d, d); + + d = vself(vmaski2_eq(vandi2(q, vcast_vi2_i(1)), vcast_vi2_i(1)), vnegf(d), d); + + u = vcast_vf_f(2.6083159809786593541503e-06f); + u = vmlaf(u, s, vcast_vf_f(-0.0001981069071916863322258f)); + u = vmlaf(u, s, vcast_vf_f(0.00833307858556509017944336f)); + u = vmlaf(u, s, vcast_vf_f(-0.166666597127914428710938f)); + + u = vmlaf(s, vmulf(u, d), d); + + return u; +} + +static INLINE vfloat xcosf(vfloat d) { + vint2 q; + vfloat u, s; + + q = vrint_vi2_vf(vsubf(vmulf(d, vcast_vf_f((float)rtengine::RT_1_PI)), vcast_vf_f(0.5f))); + q = vaddi2(vaddi2(q, q), vcast_vi2_i(1)); + + u = vcast_vf_vi2(q); + d = vmlaf(u, vcast_vf_f(-PI4_Af*2), d); + d = vmlaf(u, vcast_vf_f(-PI4_Bf*2), d); + d = vmlaf(u, vcast_vf_f(-PI4_Cf*2), d); + d = vmlaf(u, vcast_vf_f(-PI4_Df*2), d); + + s = vmulf(d, d); + + d = vself(vmaski2_eq(vandi2(q, vcast_vi2_i(2)), vcast_vi2_i(2)), d, vnegf(d)); + + u = vcast_vf_f(2.6083159809786593541503e-06f); + u = vmlaf(u, s, vcast_vf_f(-0.0001981069071916863322258f)); + u = vmlaf(u, s, vcast_vf_f(0.00833307858556509017944336f)); + u = vmlaf(u, s, vcast_vf_f(-0.166666597127914428710938f)); + + u = vmlaf(s, vmulf(u, d), d); + + return u; +} + +static INLINE vfloat2 xsincosf(vfloat d) { + vint2 q; + vmask m; + vfloat u, s, t, rx, ry; + vfloat2 r; + + q = vrint_vi2_vf(vmulf(d, vcast_vf_f((float)rtengine::RT_2_PI))); + + s = d; + + u = vcast_vf_vi2(q); + s = vmlaf(u, vcast_vf_f(-PI4_Af*2), s); + s = vmlaf(u, vcast_vf_f(-PI4_Bf*2), s); + s = vmlaf(u, vcast_vf_f(-PI4_Cf*2), s); + s = vmlaf(u, vcast_vf_f(-PI4_Df*2), s); + + t = s; + + s = vmulf(s, s); + + u = vcast_vf_f(-0.000195169282960705459117889f); + u = vmlaf(u, s, vcast_vf_f(0.00833215750753879547119141f)); + u = vmlaf(u, s, vcast_vf_f(-0.166666537523269653320312f)); + u = vmulf(vmulf(u, s), t); + + rx = vaddf(t, u); + + u = vcast_vf_f(-2.71811842367242206819355e-07f); + u = vmlaf(u, s, vcast_vf_f(2.47990446951007470488548e-05f)); + u = vmlaf(u, s, vcast_vf_f(-0.00138888787478208541870117f)); + u = vmlaf(u, s, vcast_vf_f(0.0416666641831398010253906f)); + u = vmlaf(u, s, vcast_vf_f(-0.5)); + + ry = vaddf(vcast_vf_f(1), vmulf(s, u)); + + m = vmaski2_eq(vandi2(q, vcast_vi2_i(1)), vcast_vi2_i(0)); + r.x = vself(m, rx, ry); + r.y = vself(m, ry, rx); + + m = vmaski2_eq(vandi2(q, vcast_vi2_i(2)), vcast_vi2_i(2)); + r.x = vreinterpret_vf_vm(vxorm(vandm(m, vreinterpret_vm_vf(vcast_vf_f(-0.0))), vreinterpret_vm_vf(r.x))); + + m = vmaski2_eq(vandi2(vaddi2(q, vcast_vi2_i(1)), vcast_vi2_i(2)), vcast_vi2_i(2)); + r.y = vreinterpret_vf_vm(vxorm(vandm(m, vreinterpret_vm_vf(vcast_vf_f(-0.0))), vreinterpret_vm_vf(r.y))); + + m = vmaskf_isinf(d); + r.x = vself(m, vcast_vf_f(rtengine::RT_NAN), r.x); + r.y = vself(m, vcast_vf_f(rtengine::RT_NAN), r.y); + + return r; +} + +static INLINE vfloat xtanf(vfloat d) { + vint2 q; + vmask m; + vfloat u, s, x; + + q = vrint_vi2_vf(vmulf(d, vcast_vf_f((float)(2 * rtengine::RT_1_PI)))); + + x = d; + + u = vcast_vf_vi2(q); + x = vmlaf(u, vcast_vf_f(-PI4_Af*2), x); + x = vmlaf(u, vcast_vf_f(-PI4_Bf*2), x); + x = vmlaf(u, vcast_vf_f(-PI4_Cf*2), x); + x = vmlaf(u, vcast_vf_f(-PI4_Df*2), x); + + s = vmulf(x, x); + + m = vmaski2_eq(vandi2(q, vcast_vi2_i(1)), vcast_vi2_i(1)); + x = vself(m, vnegf(x), x); + + u = vcast_vf_f(0.00927245803177356719970703f); + u = vmlaf(u, s, vcast_vf_f(0.00331984995864331722259521f)); + u = vmlaf(u, s, vcast_vf_f(0.0242998078465461730957031f)); + u = vmlaf(u, s, vcast_vf_f(0.0534495301544666290283203f)); + u = vmlaf(u, s, vcast_vf_f(0.133383005857467651367188f)); + u = vmlaf(u, s, vcast_vf_f(0.333331853151321411132812f)); + + u = vmlaf(s, vmulf(u, x), x); + + u = vself(m, vrecf(u), u); + + u = vself(vmaskf_isinf(d), vcast_vf_f(NANf), u); + + return u; +} + +static INLINE vfloat xatanf(vfloat s) { + vfloat t, u; + vint2 q; + + q = vseli2_lt(s, vcast_vf_f(0.0f), vcast_vi2_i(2), vcast_vi2_i(0)); + s = vabsf(s); + + q = vseli2_lt(vcast_vf_f(1.0f), s, vaddi2(q, vcast_vi2_i(1)), q); + s = vself(vmaskf_lt(vcast_vf_f(1.0f), s), vdivf(vcast_vf_f(1.0f), s), s); + + t = vmulf(s, s); + + u = vcast_vf_f(0.00282363896258175373077393f); + u = vmlaf(u, t, vcast_vf_f(-0.0159569028764963150024414f)); + u = vmlaf(u, t, vcast_vf_f(0.0425049886107444763183594f)); + u = vmlaf(u, t, vcast_vf_f(-0.0748900920152664184570312f)); + u = vmlaf(u, t, vcast_vf_f(0.106347933411598205566406f)); + u = vmlaf(u, t, vcast_vf_f(-0.142027363181114196777344f)); + u = vmlaf(u, t, vcast_vf_f(0.199926957488059997558594f)); + u = vmlaf(u, t, vcast_vf_f(-0.333331018686294555664062f)); + + t = vaddf(s, vmulf(s, vmulf(t, u))); + + t = vself(vmaski2_eq(vandi2(q, vcast_vi2_i(1)), vcast_vi2_i(1)), vsubf(vcast_vf_f((float)(rtengine::RT_PI/2)), t), t); + t = vself(vmaski2_eq(vandi2(q, vcast_vi2_i(2)), vcast_vi2_i(2)), vnegf(t), t); + + return t; +} + +static INLINE vfloat atan2kf(vfloat y, vfloat x) { + vfloat s, t, u; + vint2 q; + vmask p; + + q = vseli2_lt(x, vcast_vf_f(0.0f), vcast_vi2_i(-2), vcast_vi2_i(0)); + x = vabsf(x); + + q = vseli2_lt(x, y, vaddi2(q, vcast_vi2_i(1)), q); + p = vmaskf_lt(x, y); + s = vself(p, vnegf(x), y); + t = vmaxf(x, y); + + s = vdivf(s, t); + t = vmulf(s, s); + + u = vcast_vf_f(0.00282363896258175373077393f); + u = vmlaf(u, t, vcast_vf_f(-0.0159569028764963150024414f)); + u = vmlaf(u, t, vcast_vf_f(0.0425049886107444763183594f)); + u = vmlaf(u, t, vcast_vf_f(-0.0748900920152664184570312f)); + u = vmlaf(u, t, vcast_vf_f(0.106347933411598205566406f)); + u = vmlaf(u, t, vcast_vf_f(-0.142027363181114196777344f)); + u = vmlaf(u, t, vcast_vf_f(0.199926957488059997558594f)); + u = vmlaf(u, t, vcast_vf_f(-0.333331018686294555664062f)); + + t = vaddf(s, vmulf(s, vmulf(t, u))); + t = vaddf(t, vmulf(vcast_vf_vi2(q), vcast_vf_f((float)(rtengine::RT_PI/2)))); + + return t; +} + +static INLINE vfloat xatan2f(vfloat y, vfloat x) { + vfloat r = atan2kf(vabsf(y), x); + + r = vmulsignf(r, x); + r = vself(vorm(vmaskf_isinf(x), vmaskf_eq(x, vcast_vf_f(0.0f))), vsubf(vcast_vf_f((float)(rtengine::RT_PI/2)), visinf2f(x, vmulsignf(vcast_vf_f((float)(rtengine::RT_PI/2)), x))), r); + r = vself(vmaskf_isinf(y), vsubf(vcast_vf_f((float)(rtengine::RT_PI/2)), visinf2f(x, vmulsignf(vcast_vf_f((float)(rtengine::RT_PI/4)), x))), r); + r = vself(vmaskf_eq(y, vcast_vf_f(0.0f)), vselfzero(vmaskf_eq(vsignf(x), vcast_vf_f(-1.0f)), vcast_vf_f((float)rtengine::RT_PI)), r); + + return vself(vmaskf_isnan(x, y), vcast_vf_f(NANf), vmulsignf(r, y)); +} + +static INLINE vfloat xasinf(vfloat d) { + vfloat x, y; + x = vaddf(vcast_vf_f(1.0f), d); + y = vsubf(vcast_vf_f(1.0f), d); + x = vmulf(x, y); + x = vsqrtf(x); + x = vself(vmaskf_isnan(x), vcast_vf_f(NANf), atan2kf(vabsf(d), x)); + return vmulsignf(x, d); +} + +static INLINE vfloat xacosf(vfloat d) { + vfloat x, y; + x = vaddf(vcast_vf_f(1.0f), d); + y = vsubf(vcast_vf_f(1.0f), d); + x = vmulf(x, y); + x = vsqrtf(x); + x = vmulsignf(atan2kf(x, vabsf(d)), d); + y = (vfloat)vandm(vmaskf_lt(d, vcast_vf_f(0.0f)), (vmask)vcast_vf_f((float)rtengine::RT_PI)); + x = vaddf(x, y); + return x; +} + +static INLINE vfloat xlogf(vfloat d) { + vfloat x, x2, t, m; + vint2 e; + + e = vilogbp1f(vmulf(d, vcast_vf_f(0.7071f))); + m = vldexpf(d, vsubi2(vcast_vi2_i(0), e)); + + x = vdivf(vaddf(vcast_vf_f(-1.0f), m), vaddf(vcast_vf_f(1.0f), m)); + x2 = vmulf(x, x); + + t = vcast_vf_f(0.2371599674224853515625f); + t = vmlaf(t, x2, vcast_vf_f(0.285279005765914916992188f)); + t = vmlaf(t, x2, vcast_vf_f(0.400005519390106201171875f)); + t = vmlaf(t, x2, vcast_vf_f(0.666666567325592041015625f)); + t = vmlaf(t, x2, vcast_vf_f(2.0f)); + + x = vaddf(vmulf(x, t), vmulf(vcast_vf_f(0.693147180559945286226764f), vcast_vf_vi2(e))); + + x = vself(vmaskf_ispinf(d), vcast_vf_f(INFINITYf), x); + x = vself(vmaskf_gt(vcast_vf_f(0), d), vcast_vf_f(NANf), x); + x = vself(vmaskf_eq(d, vcast_vf_f(0)), vcast_vf_f(-INFINITYf), x); + + return x; +} + +static INLINE vfloat xlogf1(vfloat d) { // does xlogf(vmaxf(d, 1.f)) but faster + vfloat x, x2, t, m; + vint2 e; + + e = vilogbp1f(vmulf(d, vcast_vf_f(0.7071f))); + m = vldexpf(d, vsubi2(vcast_vi2_i(0), e)); + + x = vdivf(vaddf(vcast_vf_f(-1.0f), m), vaddf(vcast_vf_f(1.0f), m)); + x2 = vmulf(x, x); + + t = vcast_vf_f(0.2371599674224853515625f); + t = vmlaf(t, x2, vcast_vf_f(0.285279005765914916992188f)); + t = vmlaf(t, x2, vcast_vf_f(0.400005519390106201171875f)); + t = vmlaf(t, x2, vcast_vf_f(0.666666567325592041015625f)); + t = vmlaf(t, x2, vcast_vf_f(2.0f)); + + x = vaddf(vmulf(x, t), vmulf(vcast_vf_f(0.693147180559945286226764f), vcast_vf_vi2(e))); + + x = vself(vmaskf_ispinf(d), vcast_vf_f(INFINITYf), x); + x = vselfnotzero(vmaskf_le(d, vcast_vf_f(1.f)), x); + + return x; +} + +static INLINE vfloat xlogf0(vfloat d) { + vfloat x, x2, t, m; + vint2 e; + + e = vilogbp1f(vmulf(d, vcast_vf_f(0.7071f))); + m = vldexpf(d, vsubi2(vcast_vi2_i(0), e)); + + x = vdivf(vaddf(vcast_vf_f(-1.0f), m), vaddf(vcast_vf_f(1.0f), m)); + x2 = vmulf(x, x); + + t = vcast_vf_f(0.2371599674224853515625f); + t = vmlaf(t, x2, vcast_vf_f(0.285279005765914916992188f)); + t = vmlaf(t, x2, vcast_vf_f(0.400005519390106201171875f)); + t = vmlaf(t, x2, vcast_vf_f(0.666666567325592041015625f)); + t = vmlaf(t, x2, vcast_vf_f(2.0f)); + + x = vaddf(vmulf(x, t), vmulf(vcast_vf_f(0.693147180559945286226764f), vcast_vf_vi2(e))); + + x = vself(vmaskf_ispinf(d), vcast_vf_f(0), x); + x = vself(vmaskf_gt(vcast_vf_f(0), d), vcast_vf_f(0), x); + x = vself(vmaskf_eq(d, vcast_vf_f(0)), vcast_vf_f(0), x); + + return x; +} + +static INLINE vfloat xlogfNoCheck(vfloat d) { // this version does not check input values. Use it only when you know the input values are > 0 e.g. when filling a lookup table + vfloat x, x2, t, m; + vint2 e; + + e = vilogbp1f(vmulf(d, vcast_vf_f(0.7071f))); + m = vldexpf(d, vsubi2(vcast_vi2_i(0), e)); + + x = vdivf(vaddf(vcast_vf_f(-1.0f), m), vaddf(vcast_vf_f(1.0f), m)); + x2 = vmulf(x, x); + + t = vcast_vf_f(0.2371599674224853515625f); + t = vmlaf(t, x2, vcast_vf_f(0.285279005765914916992188f)); + t = vmlaf(t, x2, vcast_vf_f(0.400005519390106201171875f)); + t = vmlaf(t, x2, vcast_vf_f(0.666666567325592041015625f)); + t = vmlaf(t, x2, vcast_vf_f(2.0f)); + + return vaddf(vmulf(x, t), vmulf(vcast_vf_f(0.693147180559945286226764f), vcast_vf_vi2(e))); + +} + +static INLINE vfloat xexpf(vfloat d) { + vint2 q = vrint_vi2_vf(vmulf(d, vcast_vf_f(R_LN2f))); + vfloat s, u; + + s = vmlaf(vcast_vf_vi2(q), vcast_vf_f(-L2Uf),d); + s = vmlaf(vcast_vf_vi2(q), vcast_vf_f(-L2Lf),s); + + u = vcast_vf_f(0.00136324646882712841033936f); + u = vmlaf(u, s, vcast_vf_f(0.00836596917361021041870117f)); + u = vmlaf(u, s, vcast_vf_f(0.0416710823774337768554688f)); + u = vmlaf(u, s, vcast_vf_f(0.166665524244308471679688f)); + u = vmlaf(u, s, vcast_vf_f(0.499999850988388061523438f)); + + u = vaddf(vcast_vf_f(1.0f), vmlaf(vmulf(s, s), u, s)); + + u = vldexpf(u, q); + + // -104.0 + return vselfnotzero(vmaskf_gt(vcast_vf_f(-104.f), d), u); +} + +static INLINE vfloat xexpfNoCheck(vfloat d) { // this version does not check input values. Use it only when you know the input values are > -104.f e.g. when filling a lookup table + vint2 q = vrint_vi2_vf(vmulf(d, vcast_vf_f(R_LN2f))); + vfloat s, u; + + s = vmlaf(vcast_vf_vi2(q), vcast_vf_f(-L2Uf),d); + s = vmlaf(vcast_vf_vi2(q), vcast_vf_f(-L2Lf),s); + + u = vcast_vf_f(0.00136324646882712841033936f); + u = vmlaf(u, s, vcast_vf_f(0.00836596917361021041870117f)); + u = vmlaf(u, s, vcast_vf_f(0.0416710823774337768554688f)); + u = vmlaf(u, s, vcast_vf_f(0.166665524244308471679688f)); + u = vmlaf(u, s, vcast_vf_f(0.499999850988388061523438f)); + + u = vaddf(vcast_vf_f(1.0f), vmlaf(vmulf(s, s), u, s)); + + return vldexpf(u, q); +} + +static INLINE vfloat xcbrtf(vfloat d) { + vfloat x, y, q = vcast_vf_f(1.0), t; + vint2 e, qu, re; + + e = vilogbp1f(vabsf(d)); + d = vldexpf(d, vsubi2(vcast_vi2_i(0), e)); + + t = vaddf(vcast_vf_vi2(e), vcast_vf_f(6144)); + qu = vtruncate_vi2_vf(vdivf(t, vcast_vf_f(3))); + re = vtruncate_vi2_vf(vsubf(t, vmulf(vcast_vf_vi2(qu), vcast_vf_f(3)))); + + q = vself(vmaski2_eq(re, vcast_vi2_i(1)), vcast_vf_f(1.2599210498948731647672106f), q); + q = vself(vmaski2_eq(re, vcast_vi2_i(2)), vcast_vf_f(1.5874010519681994747517056f), q); + q = vldexpf(q, vsubi2(qu, vcast_vi2_i(2048))); + + q = vmulsignf(q, d); + d = vabsf(d); + + x = vcast_vf_f(-0.601564466953277587890625f); + x = vmlaf(x, d, vcast_vf_f(2.8208892345428466796875f)); + x = vmlaf(x, d, vcast_vf_f(-5.532182216644287109375f)); + x = vmlaf(x, d, vcast_vf_f(5.898262500762939453125f)); + x = vmlaf(x, d, vcast_vf_f(-3.8095417022705078125f)); + x = vmlaf(x, d, vcast_vf_f(2.2241256237030029296875f)); + + y = vmulf(vmulf(d, x), x); + y = vmulf(vsubf(y, vmulf(vmulf(vcast_vf_f(2.0f / 3.0f), y), vmlaf(y, x, vcast_vf_f(-1.0f)))), q); + + return y; +} + +static INLINE vfloat vclampf(vfloat value, vfloat low, vfloat high) { + // clamps value in [low;high], returns low if value is NaN + return vmaxf(vminf(high, value), low); +} + +static INLINE vfloat SQRV(vfloat a){ + return a * a; +} + +static inline void vswap( vmask condition, vfloat &a, vfloat &b) { + // conditional swap the elements of two vfloats + vfloat temp = vself(condition, a, b); // the values which fit to condition + a = vself(condition, b, a); // the values which fit to inverted condition + b = temp; +} + +static inline float vhadd( vfloat a ) { + // returns a[0] + a[1] + a[2] + a[3] + a += _mm_movehl_ps(a, a); + return _mm_cvtss_f32(_mm_add_ss(a, _mm_shuffle_ps(a, a, 1))); +} + +static inline float vhmin(vfloat a) { + // returns min(a[0], a[1], a[2], a[3]) + a = vminf(a, _mm_movehl_ps(a, a)); + return _mm_cvtss_f32(vminf(a, _mm_shuffle_ps(a, a, 1))); +} + +static inline float vhmax(vfloat a) { + // returns max(a[0], a[1], a[2], a[3]) + a = vmaxf(a, _mm_movehl_ps(a, a)); + return _mm_cvtss_f32(vmaxf(a, _mm_shuffle_ps(a, a, 1))); +} + +static INLINE vfloat vmul2f(vfloat a){ + // fastest way to multiply by 2 + return a + a; +} + +static INLINE vfloat vintpf(vfloat a, vfloat b, vfloat c) { + // calculate a * b + (1 - a) * c (interpolate two values) + // following is valid: + // vintpf(a, b+x, c+x) = vintpf(a, b, c) + x + // vintpf(a, b*x, c*x) = vintpf(a, b, c) * x + return a * (b-c) + c; +} + +static INLINE vfloat vdup(vfloat a){ + // returns { a[0],a[0],a[1],a[1] } + return _mm_unpacklo_ps( a, a ); +} + +static INLINE vfloat vaddc2vfu(float &a) +{ + // loads a[0]..a[7] and returns { a[0]+a[1], a[2]+a[3], a[4]+a[5], a[6]+a[7] } + vfloat a1 = _mm_loadu_ps( &a ); + vfloat a2 = _mm_loadu_ps( (&a) + 4 ); + return _mm_shuffle_ps(a1,a2,_MM_SHUFFLE( 2,0,2,0 )) + _mm_shuffle_ps(a1,a2,_MM_SHUFFLE( 3,1,3,1 )); +} + +static INLINE vfloat vadivapb (vfloat a, vfloat b) { + return a / (a+b); +} + +static INLINE void vconvertrgbrgbrgbrgb2rrrrggggbbbb (const float * src, vfloat &rv, vfloat &gv, vfloat &bv) { // cool function name, isn't it ? :P + // converts a sequence of 4 float RGB triplets to 3 red, green and blue quadruples + rv = _mm_setr_ps(src[0],src[3],src[6],src[9]); + gv = _mm_setr_ps(src[1],src[4],src[7],src[10]); + bv = _mm_setr_ps(src[2],src[5],src[8],src[11]); +} + +#if defined( __SSE4_1__ ) && defined( __x86_64__ ) +static INLINE vfloat vceilf(vfloat x) { + return _mm_round_ps(x, _MM_FROUND_TO_POS_INF |_MM_FROUND_NO_EXC); +} + +#else + +static INLINE vfloat vceilf(vfloat x) { + __m128i zerov = _mm_setzero_si128(); + zerov = _mm_cmpeq_epi32(zerov, zerov); + const vfloat onev = (vfloat)_mm_slli_epi32(_mm_srli_epi32(zerov, 25), 23); //create vector 1.0f + const vfloat xi = _mm_cvtepi32_ps(_mm_cvttps_epi32(x)); + return xi + _mm_and_ps(_mm_cmplt_ps(xi, x), onev); +} +#endif + +#endif // __SSE2__ diff --git a/rtengine/stdimagesource.cc b/rtengine/stdimagesource.cc index 1cb11e94d..8cb8fa792 100644 --- a/rtengine/stdimagesource.cc +++ b/rtengine/stdimagesource.cc @@ -32,6 +32,8 @@ namespace rtengine { +using namespace procparams; +ProcParams* params; template void freeArray (T** a, int H) { @@ -53,7 +55,6 @@ template T** allocArray (int W, int H) return t; } -#define HR_SCALE 2 StdImageSource::StdImageSource () : ImageSource(), img(nullptr), plistener(nullptr), full(false), max{}, rgbSourceModified(false) { @@ -310,6 +311,27 @@ void StdImageSource::getAutoExpHistogram (LUTu & histogram, int& histcompr) } } +void StdImageSource::WBauto(double &tempref, double &greenref, array2D &redloc, array2D &greenloc, array2D &blueloc, int bfw, int bfh, double &avg_rm, double &avg_gm, double &avg_bm, double &tempitc, double &greenitc, float &studgood, bool &twotimes, const WBParams & wbpar, int begx, int begy, int yEn, int xEn, int cx, int cy, const ColorManagementParams &cmp, const RAWParams &raw) +{ +} + +void StdImageSource::getAutoWBMultipliersitc(double &tempref, double &greenref, double &tempitc, double &greenitc, float &studgood, int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, double &rm, double &gm, double &bm, const WBParams & wbpar, const ColorManagementParams &cmp, const RAWParams &raw) +{ + if (redAWBMul != -1.) { + rm = redAWBMul; + gm = greenAWBMul; + bm = blueAWBMul; + return; + } + + img->getAutoWBMultipliersitc(tempref, greenref, tempitc, greenitc,studgood, begx, begy, yEn, xEn, cx, cy, bf_h, bf_w, rm, gm, bm, params->wb, params->icm, params->raw); + + redAWBMul = rm; + greenAWBMul = gm; + blueAWBMul = bm; +} + + void StdImageSource::getAutoWBMultipliers (double &rm, double &gm, double &bm) { if (redAWBMul != -1.) { @@ -341,7 +363,7 @@ ColorTemp StdImageSource::getSpotWB (std::vector &red, std::vectorallocate(0, 0); }; diff --git a/rtengine/stdimagesource.h b/rtengine/stdimagesource.h index b95328c80..f937188b4 100644 --- a/rtengine/stdimagesource.h +++ b/rtengine/stdimagesource.h @@ -20,6 +20,7 @@ #include "colortemp.h" #include "imagesource.h" +#include "procparams.h" namespace rtengine { @@ -57,12 +58,15 @@ public: int load (const Glib::ustring &fname) override; void getImage (const ColorTemp &ctemp, int tran, Imagefloat* image, const PreviewProps &pp, const procparams::ToneCurveParams &hrp, const procparams::RAWParams &raw) override; + void getrgbloc (int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w) override {}; ColorTemp getWB () const override { return wb; } void getAutoWBMultipliers (double &rm, double &gm, double &bm) override; ColorTemp getSpotWB (std::vector &red, std::vector &green, std::vector &blue, int tran, double equal) override; + void WBauto(double &tempref, double &greenref, array2D &redloc, array2D &greenloc, array2D &blueloc, int bfw, int bfh, double &avg_rm, double &avg_gm, double &avg_bm, double &tempitc, double &greenitc, float &studgood, bool &twotimes, const procparams::WBParams & wbpar, int begx, int begy, int yEn, int xEn, int cx, int cy, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw) override; + void getAutoWBMultipliersitc(double &tempref, double &greenref, double &tempitc, double &greenitc, float &studgood, int begx, int begy, int yEn, int xEn, int cx, int cy, int bf_h, int bf_w, double &rm, double &gm, double &bm, const procparams::WBParams & wbpar, const procparams::ColorManagementParams &cmp, const procparams::RAWParams &raw) override; eSensorType getSensorType() const override {return ST_NONE;} bool isMono() const override {return false;} @@ -114,7 +118,7 @@ public: void getRawValues(int x, int y, int rotate, int &R, int &G, int &B) override { R = G = B = 0;} - void flushRGB () override; + void flush () override; void captureSharpening(const procparams::CaptureSharpeningParams &sharpeningParams, bool showMask, double &conrastThreshold, double &radius) override {}; }; diff --git a/rtengine/tmo_fattal02.cc b/rtengine/tmo_fattal02.cc index feba5c95f..cee57c851 100644 --- a/rtengine/tmo_fattal02.cc +++ b/rtengine/tmo_fattal02.cc @@ -308,7 +308,7 @@ float calculateGradients (Array2Df* H, Array2Df* G, int k, bool multithread) // however, the impact is not visible so we ignore this here (*G) (x, y) = sqrt (gx * gx + gy * gy) / divider; - avgGrad += (*G) (x, y); + avgGrad += static_cast((*G) (x, y)); } } @@ -381,7 +381,7 @@ void calculateFiMatrix (Array2Df* FI, Array2Df* gradients[], #endif for ( int y = 0; y < height; y++ ) { for ( int x = 0; x < width; x++ ) { - float grad = ((*gradients[k]) (x, y) < 1e-4f) ? 1e-4 : (*gradients[k]) (x, y); + float grad = ((*gradients[k]) (x, y) < 1e-4f) ? 1e-4f : (*gradients[k]) (x, y); float a = alfa * avgGrad[k]; float value = pow ((grad + noise) / a, beta - 1.0f); @@ -603,8 +603,8 @@ void tmo_fattal02 (size_t width, // sets index+1 based on the boundary assumption H(N+1)=H(N-1) unsigned int xp1 = (x + 1 >= width ? width - 2 : x + 1); // forward differences in H, so need to use between-points approx of FI - (*Gx) (x, y) = ((*H) (xp1, y) - (*H) (x, y)) * 0.5 * ((*FI) (xp1, y) + (*FI) (x, y)); - (*Gy) (x, y) = ((*H) (x, yp1) - (*H) (x, y)) * 0.5 * ((*FI) (x, yp1) + (*FI) (x, y)); + (*Gx) (x, y) = ((*H) (xp1, y) - (*H) (x, y)) * 0.5f * ((*FI) (xp1, y) + (*FI) (x, y)); + (*Gy) (x, y) = ((*H) (x, yp1) - (*H) (x, y)) * 0.5f * ((*FI) (x, yp1) + (*FI) (x, y)); } } @@ -747,7 +747,7 @@ void transform_ev2normal (Array2Df *A, Array2Df *T, bool multithread) } for (int y = 1 ; y < height - 1 ; y++ ) { - (*A) (0, y) *= 0.5; + (*A) (0, y) *= 0.5f; (*A) (width - 1, y) *= 0.5f; } @@ -912,7 +912,7 @@ void solve_pde_fft (Array2Df *F, Array2Df *U, Array2Df *buf, bool multithread)/* for (int y = 0 ; y < height ; y++ ) { for (int x = 0 ; x < width ; x++ ) { - (*F_tr) (x, y) = (*F_tr) (x, y) / (l1[y] + l2[x]); + (*F_tr) (x, y) = static_cast((*F_tr) (x, y)) / (l1[y] + l2[x]); } } diff --git a/rtengine/utils.cc b/rtengine/utils.cc index a07a1235f..0674c9806 100644 --- a/rtengine/utils.cc +++ b/rtengine/utils.cc @@ -22,7 +22,6 @@ #include "rt_math.h" #include "utils.h" -#include "rt_math.h" using namespace std; diff --git a/rtengine/xtrans_demosaic.cc b/rtengine/xtrans_demosaic.cc index cb1315ed0..b01b0ac1c 100644 --- a/rtengine/xtrans_demosaic.cc +++ b/rtengine/xtrans_demosaic.cc @@ -31,7 +31,7 @@ namespace rtengine { -const double xyz_rgb[3][3] = { // XYZ from RGB +const float xyz_rgb[3][3] = { // XYZ from RGB { 0.412453, 0.357580, 0.180423 }, { 0.212671, 0.715160, 0.072169 }, { 0.019334, 0.119193, 0.950227 } diff --git a/rtexif/CMakeLists.txt b/rtexif/CMakeLists.txt index 5a3831455..836f832e2 100644 --- a/rtexif/CMakeLists.txt +++ b/rtexif/CMakeLists.txt @@ -18,12 +18,12 @@ if(WIN32) link_directories(. "${PROJECT_SOURCE_DIR}/rtexif" ${EXTRA_LIBDIR} ${GLIB2_LIBRARY_DIRS} ${GLIBMM_LIBRARY_DIRS} ${GTK_LIBRARY_DIRS} ${GTKMM_LIBRARY_DIRS} ${LENSFUN_LIBRARY_DIRS}) else() set_target_properties(rtexif PROPERTIES COMPILE_FLAGS " -fPIC") - include_directories(${EXTRA_INCDIR} ${GLIB2_INCLUDE_DIRS} ${GLIBMM_INCLUDE_DIRS} ${GTK_INCLUDE_DIRS} ${GTKMM_INCLUDE_DIRS}) - link_directories(${EXTRA_LIBDIR} ${GLIB2_LIBRARY_DIRS} ${GLIBMM_LIBRARY_DIRS} ${GTK_LIBRARY_DIRS} ${GTKMM_LIBRARY_DIRS} ${LENSFUN_LIBRARY_DIRS}) + include_directories("${EXTRA_INCDIR} ${GLIB2_INCLUDE_DIRS} ${GLIBMM_INCLUDE_DIRS} ${GTK_INCLUDE_DIRS} ${GTKMM_INCLUDE_DIRS}") + link_directories("${EXTRA_LIBDIR} ${GLIB2_LIBRARY_DIRS} ${GLIBMM_LIBRARY_DIRS} ${GTK_LIBRARY_DIRS} ${GTKMM_LIBRARY_DIRS} ${LENSFUN_LIBRARY_DIRS}") endif() include_directories(BEFORE "${CMAKE_CURRENT_BINARY_DIR}") if(BUILD_SHARED_LIBS) - install(TARGETS rtexif DESTINATION ${LIBDIR}) + install(TARGETS rtexif DESTINATION "${LIBDIR}") endif() diff --git a/rtexif/canonattribs.cc b/rtexif/canonattribs.cc index 0e6f7eb2f..a91b7266c 100644 --- a/rtexif/canonattribs.cc +++ b/rtexif/canonattribs.cc @@ -16,8 +16,6 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . */ -#ifndef _CANONATTRIBS_ -#define _CANONATTRIBS_ #include #include @@ -557,7 +555,8 @@ public: { choices = { {1, "Canon EF 50mm f/1.8"}, - {2, "Canon EF 28mm f/2.8"}, + {2, "Canon EF 28mm f/2.8 or Sigma Lens"}, + {2, "Sigma 24mm f/2.8 Super Wide II"}, {3, "Canon EF 135mm f/2.8 Soft"}, {4, "Canon EF 35-105mm f/3.5-4.5 or Sigma Lens"}, {4, "Sigma UC Zoom 35-135mm f/4-5.6"}, @@ -598,6 +597,8 @@ public: {26, "Tamron SP AF 90mm f/2.8 Di Macro"}, {26, "Tamron SP AF 180mm f/3.5 Di Macro"}, {26, "Carl Zeiss Planar T* 50mm f/1.4"}, + {26, "Voigtlander APO Lanthar 125mm F2.5 SL Macro"}, + {26, "Carl Zeiss Planar T 85mm f/1.4 ZE"}, {27, "Canon EF 35-80mm f/4-5.6"}, {28, "Canon EF 80-200mm f/4.5-5.6 or Tamron Lens"}, {28, "Tamron SP AF 28-105mm f/2.8 LD Aspherical IF"}, @@ -629,7 +630,7 @@ public: {36, "Canon EF 38-76mm f/4.5-5.6"}, {37, "Canon EF 35-80mm f/4-5.6 or Tamron Lens"}, {37, "Tamron 70-200mm f/2.8 Di LD IF Macro"}, - {37, "Tamron AF 28-300mm f/3.5-6.3 XR Di VC LD Aspherical [IF] Macro Model A20"}, + {37, "Tamron AF 28-300mm f/3.5-6.3 XR Di VC LD Aspherical [IF] Macro (A20)"}, {37, "Tamron SP AF 17-50mm f/2.8 XR Di II VC LD Aspherical [IF]"}, {37, "Tamron AF 18-270mm f/3.5-6.3 Di II VC LD Aspherical [IF] Macro"}, {38, "Canon EF 80-200mm f/4.5-5.6"}, @@ -637,13 +638,14 @@ public: {40, "Canon EF 28-80mm f/3.5-5.6"}, {41, "Canon EF 28-90mm f/4-5.6"}, {42, "Canon EF 28-200mm f/3.5-5.6 or Tamron Lens"}, - {42, "Tamron AF 28-300mm f/3.5-6.3 XR Di VC LD Aspherical [IF] Macro Model A20"}, + {42, "Tamron AF 28-300mm f/3.5-6.3 XR Di VC LD Aspherical [IF] Macro (A20)"}, {43, "Canon EF 28-105mm f/4-5.6"}, {44, "Canon EF 90-300mm f/4.5-5.6"}, {45, "Canon EF-S 18-55mm f/3.5-5.6 [II]"}, {46, "Canon EF 28-90mm f/4-5.6"}, {47, "Zeiss Milvus 35mm f/2 or 50mm f/2"}, {47, "Zeiss Milvus 50mm f/2 Makro"}, + {47, "Zeiss Milvus 135mm f/2 ZE"}, {48, "Canon EF-S 18-55mm f/3.5-5.6 IS"}, {49, "Canon EF-S 55-250mm f/4-5.6 IS"}, {50, "Canon EF-S 18-200mm f/3.5-5.6 IS"}, @@ -660,10 +662,17 @@ public: {103, "Samyang AF 14mm f/2.8 EF or Rokinon Lens"}, {103, "Rokinon SP 14mm f/2.4"}, {103, "Rokinon AF 14mm f/2.8 EF"}, + {106, "Rokinon SP / Samyang XP 35mm f/1.2"}, + {112, "Sigma 28mm f/1.5 FF High-speed Prime or other Sigma Lens"}, + {112, "Sigma 40mm f/1.5 FF High-speed Prime"}, + {112, "Sigma 105mm f/1.5 FF High-speed Prime"}, + {117, "Tamron 35-150mm f/2.8-4.0 Di VC OSD (A043) or other Tamron Lens"}, + {117, "Tamron SP 35mm f/1.4 Di USD (F045)"}, {124, "Canon MP-E 65mm f/2.8 1-5x Macro Photo"}, {125, "Canon TS-E 24mm f/3.5L"}, {126, "Canon TS-E 45mm f/2.8"}, - {127, "Canon TS-E 90mm f/2.8"}, + {127, "Canon TS-E 90mm f/2.8 or Tamron Lens"}, + {127, "Tamron 18-200mm f/3.5-6.3 Di II VC (B018)"}, {129, "Canon EF 300mm f/2.8L USM"}, {130, "Canon EF 50mm f/1.0L USM"}, {131, "Canon EF 28-80mm f/2.8-4L USM or Sigma Lens"}, @@ -674,10 +683,12 @@ public: {131, "Sigma APO 120-300mm f/2.8 EX DG HSM"}, {131, "Sigma 4.5mm f/2.8 EX DC HSM Circular Fisheye"}, {131, "Sigma 70-200mm f/2.8 APO EX HSM"}, + {131, "Sigma 28-70mm f/2.8-4 DG"}, {132, "Canon EF 1200mm f/5.6L USM"}, {134, "Canon EF 600mm f/4L IS USM"}, {135, "Canon EF 200mm f/1.8L USM"}, {136, "Canon EF 300mm f/2.8L USM"}, + {136, "Tamron SP 15-30mm f/2.8 Di VC USD (A012)"}, {137, "Canon EF 85mm f/1.2L USM or Sigma or Tamron Lens"}, {137, "Sigma 18-50mm f/2.8-4.5 DC OS HSM"}, {137, "Sigma 50-200mm f/4-5.6 DC OS HSM"}, @@ -687,14 +698,15 @@ public: {137, "Sigma 17-70mm f/2.8-4 DC Macro OS HSM | C"}, {137, "Sigma 17-50mm f/2.8 OS HSM"}, {137, "Sigma 18-200mm f/3.5-6.3 DC OS HSM [II]"}, - {137, "Tamron AF 18-270mm f/3.5-6.3 Di II VC PZD"}, + {137, "Tamron AF 18-270mm f/3.5-6.3 Di II VC PZD (B008)"}, {137, "Sigma 8-16mm f/4.5-5.6 DC HSM"}, - {137, "Tamron SP 17-50mm f/2.8 XR Di II VC"}, - {137, "Tamron SP 60mm f/2 Macro Di II"}, + {137, "Tamron SP 17-50mm f/2.8 XR Di II VC (B005)"}, + {137, "Tamron SP 60mm f/2 Macro Di II (G005)"}, {137, "Sigma 10-20mm f/3.5 EX DC HSM"}, {137, "Tamron SP 24-70mm f/2.8 Di VC USD"}, {137, "Sigma 18-35mm f/1.8 DC HSM"}, {137, "Sigma 12-24mm f/4.5-5.6 DG HSM II"}, + {137, "Sigma 70-300mm f/4-5.6 DG OS"}, {138, "Canon EF 28-80mm f/2.8-4L"}, {139, "Canon EF 400mm f/2.8L USM"}, {140, "Canon EF 500mm f/4.5L USM"}, @@ -713,23 +725,28 @@ public: {150, "Sigma 30mm f/1.4 DC HSM"}, {150, "Sigma 24mm f/1.8 DG Macro EX"}, {150, "Sigma 28mm f/1.8 DG Macro EX"}, + {150, "Sigma 18-35mm f/1.8 DC HSM | A"}, {151, "Canon EF 200mm f/2.8L USM"}, {152, "Canon EF 300mm f/4L IS USM or Sigma Lens"}, {152, "Sigma 12-24mm f/4.5-5.6 EX DG ASPHERICAL HSM"}, {152, "Sigma 14mm f/2.8 EX Aspherical HSM"}, {152, "Sigma 10-20mm f/4-5.6"}, {152, "Sigma 100-300mm f/4"}, + {152, "Sigma 300-800mm f/5.6 APO EX DG HSM"}, {153, "Canon EF 35-350mm f/3.5-5.6L USM or Sigma or Tamron Lens"}, {153, "Sigma 50-500mm f/4-6.3 APO HSM EX"}, {153, "Tamron AF 28-300mm f/3.5-6.3 XR LD Aspherical [IF] Macro"}, - {153, "Tamron AF 18-200mm f/3.5-6.3 XR Di II LD Aspherical [IF] Macro Model A14"}, + {153, "Tamron AF 18-200mm f/3.5-6.3 XR Di II LD Aspherical [IF] Macro (A14)"}, {153, "Tamron 18-250mm f/3.5-6.3 Di II LD Aspherical [IF] Macro"}, {154, "Canon EF 20mm f/2.8 USM or Zeiss Lens"}, {154, "Zeiss Milvus 21mm f/2.8"}, - {155, "Canon EF 85mm f/1.8 USM"}, + {154, "Zeiss Milvus 15mm f/2.8 ZE"}, + {154, "Zeiss Milvus 18mm f/2.8 ZE"}, + {155, "Canon EF 85mm f/1.8 USM or Sigma Lens"}, + {155, "Sigma 14mm f/1.8 DG HSM | A"}, {156, "Canon EF 28-105mm f/3.5-4.5 USM or Tamron Lens"}, - {156, "Tamron SP 70-300mm f/4-5.6 Di VC USD"}, - {156, "Tamron SP AF 28-105mm f/2.8 LD Aspherical IF"}, + {156, "Tamron SP 70-300mm f/4-5.6 Di VC USD (A005)"}, + {156, "Tamron SP AF 28-105mm f/2.8 LD Aspherical IF (176D)"}, {160, "Canon EF 20-35mm f/3.5-4.5 USM or Tamron or Tokina Lens"}, {160, "Tamron AF 19-35mm f/3.5-4.5"}, {160, "Tokina AT-X 124 AF Pro DX 12-24mm f/4"}, @@ -742,7 +759,7 @@ public: {161, "Sigma 24-60mm f/2.8 EX DG"}, {161, "Tamron AF 17-50mm f/2.8 Di-II LD Aspherical"}, {161, "Tamron 90mm f/2.8"}, - {161, "Tamron SP AF 17-35mm f/2.8-4 Di LD Aspherical IF"}, + {161, "Tamron SP AF 17-35mm f/2.8-4 Di LD Aspherical IF (A05)"}, {161, "Tamron SP AF 28-75mm f/2.8 XR Di LD Aspherical [IF] Macro"}, {161, "Tokina AT-X 24-70mm f/2.8 PRO FX (IF)"}, {162, "Canon EF 200mm f/2.8L USM"}, @@ -762,18 +779,30 @@ public: {169, "Sigma 30mm f/1.4 EX DC HSM"}, {169, "Sigma 35mm f/1.4 DG HSM"}, {169, "Sigma 35mm f/1.5 FF High-Speed Prime | 017"}, - {170, "Canon EF 200mm f/2.8L II USM"}, + {169, "Sigma 70mm f/2.8 Macro EX DG"}, + {170, "Canon EF 200mm f/2.8L II USM or Sigma Lens"}, + {170, "Sigma 300mm f/2.8 APO EX DG HSM"}, + {170, "Sigma 800mm f/5.6 APO EX DG HSM"}, {171, "Canon EF 300mm f/4L USM"}, {172, "Canon EF 400mm f/5.6L USM or Sigma Lens"}, {172, "Sigma 150-600mm f/5-6.3 DG OS HSM | S"}, + {172, "Sigma 500mm f/4.5 APO EX DG HSM"}, {173, "Canon EF 180mm Macro f/3.5L USM or Sigma Lens"}, {173, "Sigma 180mm EX HSM Macro f/3.5"}, {173, "Sigma APO Macro 150mm f/2.8 EX DG HSM"}, + {173, "Sigma 10mm f/2.8 EX DC Fisheye"}, + {173, "Sigma 15mm f/2.8 EX DG Diagonal Fisheye"}, + {173, "Venus Laowa 100mm F2.8 2X Ultra Macro APO"}, {174, "Canon EF 135mm f/2L USM or Other Lens"}, {174, "Sigma 70-200mm f/2.8 EX DG APO OS HSM"}, {174, "Sigma 50-500mm f/4.5-6.3 APO DG OS HSM"}, {174, "Sigma 150-500mm f/5-6.3 APO DG OS HSM"}, {174, "Zeiss Milvus 100mm f/2 Makro"}, + {174, "Sigma APO 50-150mm f/2.8 EX DC OS HSM"}, + {174, "Sigma APO 120-300mm f/2.8 EX DG OS HSM"}, + {174, "Sigma 120-300mm f/2.8 DG OS HSM S013"}, + {174, "Sigma 120-400mm f/4.5-5.6 APO DG OS HSM"}, + {174, "Sigma 200-500mm f/2.8 APO EX DG"}, {175, "Canon EF 400mm f/2.8L USM"}, {176, "Canon EF 24-85mm f/3.5-4.5 USM"}, {177, "Canon EF 300mm f/4L IS USM"}, @@ -788,6 +817,8 @@ public: {180, "Sigma 24mm f/1.5 FF High-Speed Prime | 017"}, {180, "Sigma 50mm f/1.5 FF High-Speed Prime | 017"}, {180, "Sigma 85mm f/1.5 FF High-Speed Prime | 017"}, + {180, "Tokina Opera 50mm f/1.4 FF"}, + {180, "Sigma 20mm f/1.4 DG HSM | A"}, {181, "Canon EF 100-400mm f/4.5-5.6L IS USM + 1.4x or Sigma Lens"}, {181, "Sigma 150-600mm f/5-6.3 DG OS HSM | S + 1.4x"}, {182, "Canon EF 100-400mm f/4.5-5.6L IS USM + 2x or Sigma Lens"}, @@ -814,11 +845,14 @@ public: {195, "Canon EF 35-105mm f/4.5-5.6 USM"}, {196, "Canon EF 75-300mm f/4-5.6 USM"}, {197, "Canon EF 75-300mm f/4-5.6 IS USM or Sigma Lens"}, - {197, "Sigma 18-300mm f/3.5-6.3 DC Macro OS HS"}, - {198, "Canon EF 50mm f/1.4 USM or Zeiss Lens"}, + {197, "Sigma 18-300mm f/3.5-6.3 DC Macro OS HSM"}, + {198, "Canon EF 50mm f/1.4 USM or Other Lens"}, {198, "Zeiss Otus 55mm f/1.4 ZE"}, {198, "Zeiss Otus 85mm f/1.4 ZE"}, {198, "Zeiss Milvus 25mm f/1.4"}, + {198, "Zeiss Otus 100mm f/1.4"}, + {198, "Zeiss Milvus 35mm f/1.4 ZE"}, + {198, "Yongnuo YN 35mm f/2"}, {199, "Canon EF 28-80mm f/3.5-5.6 USM"}, {200, "Canon EF 75-300mm f/4-5.6 USM"}, {201, "Canon EF 28-80mm f/3.5-5.6 USM"}, @@ -829,13 +863,14 @@ public: {211, "Canon EF 28-200mm f/3.5-5.6 USM"}, {212, "Canon EF 28-105mm f/4-5.6 USM"}, {213, "Canon EF 90-300mm f/4.5-5.6 USM or Tamron Lens"}, - {213, "Tamron SP 150-600mm f/5-6.3 Di VC USD"}, - {213, "Tamron 16-300mm f/3.5-6.3 Di II VC PZD Macro"}, - {213, "Tamron SP 35mm f/1.8 Di VC USD"}, - {213, "Tamron SP 45mm f/1.8 Di VC USD"}, + {213, "Tamron SP 150-600mm f/5-6.3 Di VC USD (A011)"}, + {213, "Tamron 16-300mm f/3.5-6.3 Di II VC PZD Macro (B016)"}, + {213, "Tamron SP 35mm f/1.8 Di VC USD (F012)"}, + {213, "Tamron SP 45mm f/1.8 Di VC USD (F013)"}, {214, "Canon EF-S 18-55mm f/3.5-5.6 USM"}, {215, "Canon EF 55-200mm f/4.5-5.6 II USM"}, {217, "Tamron AF 18-270mm f/3.5-6.3 Di II VC PZD"}, + {220, "Yongnuo YN 50mm f/1.8"}, {224, "Canon EF 70-200mm f/2.8L IS USM"}, {225, "Canon EF 70-200mm f/2.8L IS USM + 1.4x"}, {226, "Canon EF 70-200mm f/2.8L IS USM + 2x"}, @@ -843,7 +878,8 @@ public: {228, "Canon EF 28-105mm f/3.5-4.5 USM"}, {229, "Canon EF 16-35mm f/2.8L USM"}, {230, "Canon EF 24-70mm f/2.8L USM"}, - {231, "Canon EF 17-40mm f/4L USM"}, + {231, "Canon EF 17-40mm f/4L USM or Sigma Lens"}, + {231, "Sigma 12-24mm f/4 DG HSM A016"}, {232, "Canon EF 70-300mm f/4.5-5.6 DO IS USM"}, {233, "Canon EF 28-300mm f/3.5-5.6L IS USM"}, {234, "Canon EF-S 17-85mm f/4-5.6 IS USM or Tokina Lens"}, @@ -867,13 +903,19 @@ public: {248, "Sigma 24-35mm f/2 DG HSM | A"}, {248, "Sigma 135mm f/2 FF High-Speed Prime | 017"}, {248, "Sigma 24-35mm f/2.2 FF Zoom | 017"}, + {248, "Sigma 135mm f/1.8 DG HSM A017"}, {249, "Canon EF 800mm f/5.6L IS USM"}, {250, "Canon EF 24mm f/1.4L II USM or Sigma Lens"}, {250, "Sigma 20mm f/1.4 DG HSM | A"}, {250, "Sigma 20mm f/1.5 FF High-Speed Prime | 017"}, + {250, "Tokina Opera 16-28mm f/2.8 FF"}, + {250, "Sigma 85mm f/1.4 DG HSM A016"}, {251, "Canon EF 70-200mm f/2.8L IS II USM"}, + {251, "Canon EF 70-200mm f/2.8L IS III USM"}, {252, "Canon EF 70-200mm f/2.8L IS II USM + 1.4x"}, + {252, "Canon EF 70-200mm f/2.8L IS III USM + 1.4x"}, {253, "Canon EF 70-200mm f/2.8L IS II USM + 2x"}, + {253, "Canon EF 70-200mm f/2.8L IS III USM + 2x"}, {254, "Canon EF 100mm f/2.8L Macro IS USM"}, {255, "Sigma 24-105mm f/4 DG OS HSM | A or Other Sigma Lens"}, {255, "Sigma 180mm f/2.8 EX DG OS HSM APO Macro"}, @@ -882,6 +924,12 @@ public: {368, "Sigma 50mm f/1.4 DG HSM | A"}, {368, "Sigma 40mm f/1.4 DG HSM | A"}, {368, "Sigma 60-600mm f/4.5-6.3 DG OS HSM | S"}, + {368, "Sigma 28mm f/1.4 DG HSM | A"}, + {368, "Sigma 150-600mm f/5-6.3 DG OS HSM | S"}, + {368, "Sigma 85mm f/1.4 DG HSM | A"}, + {368, "Sigma 105mm f/1.4 DG HSM"}, + {368, "Sigma 14-24mm f/2.8 DG HSM"}, + {368, "Sigma 70mm f/2.8 DG Macro"}, {488, "Canon EF-S 15-85mm f/3.5-5.6 IS USM"}, {489, "Canon EF 70-300mm f/4-5.6L IS USM"}, {490, "Canon EF 8-15mm f/4L Fisheye USM"}, @@ -897,7 +945,7 @@ public: {493, "Canon EF 24-105mm f/4L IS USM"}, {494, "Canon EF 600mm f/4L IS II USM"}, {495, "Canon EF 24-70mm f/2.8L II USM or Sigma Lens"}, - {495, "Sigma 24-70mm F2.8 DG OS HSM | A"}, + {495, "Sigma 24-70mm f/2.8 DG OS HSM | A"}, {496, "Canon EF 200-400mm f/4L IS USM"}, {499, "Canon EF 200-400mm f/4L IS USM + 1.4x"}, {502, "Canon EF 28mm f/2.8 IS USM or Tamron Lens"}, @@ -908,14 +956,16 @@ public: {506, "Canon EF 400mm f/4 DO IS II USM"}, {507, "Canon EF 16-35mm f/4L IS USM"}, {508, "Canon EF 11-24mm f/4L USM or Tamron Lens"}, - {508, "Tamron 10-24mm f/3.5-4.5 Di II VC HLD"}, + {508, "Tamron 10-24mm f/3.5-4.5 Di II VC HLD (B023)"}, + {624, "Sigma 70-200mm f/2.8 DG OS HSM | S"}, {747, "Canon EF 100-400mm f/4.5-5.6L IS II USM or Tamron Lens"}, {747, "Tamron SP 150-600mm f/5-6.3 Di VC USD G2"}, {748, "Canon EF 100-400mm f/4.5-5.6L IS II USM + 1.4x or Tamron Lens"}, {748, "Tamron 100-400mm f/4.5-6.3 Di VC USD A035E + 1.4x"}, {748, "Tamron 70-210mm f/4 Di VC USD (A034) + 2x"}, {749, "Tamron 100-400mm f/4.5-6.3 Di VC USD A035E + 2x"}, - {750, "Canon EF 35mm f/1.4L II USM"}, + {750, "Canon EF 35mm f/1.4L II USM or Tamron Lens"}, + {750, "Tamron SP 85mm f/1.8 Di VC USD (F016)"}, {751, "Canon EF 16-35mm f/2.8L III USM"}, {752, "Canon EF 24-105mm f/4L IS II USM"}, {753, "Canon EF 85mm f/1.4L IS USM"}, @@ -938,16 +988,21 @@ public: {4154, "Canon EF-S 24mm f/2.8 STM"}, {4155, "Canon EF-M 28mm f/3.5 Macro IS STM"}, {4156, "Canon EF 50mm f/1.8 STM"}, - {4157, "Canon EF-M 18-150mm 1:3.5-6.3 IS STM"}, + {4157, "Canon EF-M 18-150mm f/3.5-6.3 IS STM"}, {4158, "Canon EF-S 18-55mm f/4-5.6 IS STM"}, {4159, "Canon EF-M 32mm f/1.4 STM"}, {4160, "Canon EF-S 35mm f/2.8 Macro IS STM"}, + {4208, "Sigma 56mm f/1.4 DC DN | C"}, {36910, "Canon EF 70-300mm f/4-5.6 IS II USM"}, {36912, "Canon EF-S 18-135mm f/3.5-5.6 IS USM"}, {61182, "Canon RF 35mm F1.8 Macro IS STM or other Canon RF Lens"}, {61182, "Canon RF 50mm F1.2 L USM"}, {61182, "Canon RF 24-105mm F4 L IS USM"}, {61182, "Canon RF 28-70mm F2 L USM"}, + {61182, "Canon RF 85mm F1.2L USM"}, + {61182, "Canon RF 24-240mm F4-6.3 IS USM"}, + {61182, "Canon RF 24-70mm F2.8 L IS USM"}, + {61182, "Canon RF 15-35mm F2.8 L IS USM"}, {61491, "Canon CN-E 14mm T3.1 L F"}, {61492, "Canon CN-E 24mm T1.5 L F"}, {61494, "Canon CN-E 85mm T1.3 L F"}, @@ -1174,7 +1229,7 @@ public: int a = Interpreter::toInt (t, ofs, astype); if (a > 1) { - int i = int (double (powf (2.f, float (a) / 32.f - 4.f)) * 50.f + 0.5f); + int i = static_cast(powf (2.f, static_cast(a) / 32.f - 4.f)) * 50.0 + 0.5; return i; } else { return 0; @@ -1514,7 +1569,11 @@ public: { choices[1042] = "EOS M50 / Kiss M"; choices[2049] = "PowerShot SX740 HS"; + choices[2052] = "PowerShot G5 X Mark II"; choices[2053] = "PowerShot SX70 HS"; + choices[2056] = "PowerShot G7 X Mark III"; + choices[2065] = "EOS M6 Mark II"; + choices[2066] = "EOS M200"; choices[16842752] = "PowerShot A30"; choices[17039360] = "PowerShot S300 / Digital IXUS 300 / IXY Digital 300"; choices[17170432] = "PowerShot A20"; @@ -1679,6 +1738,7 @@ public: choices[52822016] = "PowerShot A3400 IS"; choices[52887552] = "PowerShot A2400 IS"; choices[52953088] = "PowerShot A2300"; + choices[53608448] = "PowerShot S100V"; choices[53673984] = "PowerShot G15"; choices[53739520] = "PowerShot SX50 HS"; choices[53805056] = "PowerShot SX160 IS"; @@ -1737,7 +1797,7 @@ public: choices[67239936] = "PowerShot SX420 IS"; choices[67305472] = "PowerShot ELPH 190 IS / IXUS 180 / IXY 190"; choices[67371008] = "PowerShot G1"; - choices[67371009] = "IXY 180"; + choices[67371009] = "PowerShot ELPH 180 IS / IXUS 175 / IXY 180"; choices[67436544] = "PowerShot SX720 HS"; choices[67502080] = "PowerShot SX620 HS"; choices[67567616] = "EOS M6"; @@ -1821,7 +1881,7 @@ public: choices[2147484453] = "EOS 70D"; choices[2147484454] = "EOS Rebel T5i / 700D / Kiss X7i"; choices[2147484455] = "EOS Rebel T5 / 1200D / Kiss X70 / Hi"; - choices[2147484456] = "EOS-1D X MARK II"; + choices[2147484456] = "EOS-1D X Mark II"; choices[2147484465] = "EOS M"; choices[2147484486] = "EOS Rebel SL1 / 100D / Kiss X7"; choices[2147484487] = "EOS Rebel T6s / 760D / 8000D"; @@ -1837,8 +1897,14 @@ public: choices[2147484680] = "EOS 77D / 9000D"; choices[2147484695] = "EOS Rebel SL2 / 200D / Kiss X9"; choices[2147484706] = "EOS Rebel T100 / 4000D / 3000D"; - choices[2147484708] = "EOR R"; + choices[2147484708] = "EOS R"; + choices[2147484712] = "EOS-1D X Mark III"; choices[2147484722] = "EOS Rebel T7 / 2000D / 1500D / Kiss X90"; + choices[2147484723] = "EOS RP"; + choices[2147484726] = "EOS SL3 / 250D / Kiss X10"; + choices[2147484727] = "EOS 90D"; + choices[2147484960] = "EOS D2000C"; + choices[2147485024] = "EOS D6000C"; } }; CAModelIDInterpreter caModelIDInterpreter; @@ -2074,5 +2140,4 @@ const TagAttrib canonAttribs[] = { { -1, AC_DONTWRITE, 0, nullptr, 0, AUTO, "", nullptr} }; } -#endif diff --git a/rtexif/fujiattribs.cc b/rtexif/fujiattribs.cc index 0eaa505f6..ffbf3a0be 100644 --- a/rtexif/fujiattribs.cc +++ b/rtexif/fujiattribs.cc @@ -16,8 +16,6 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . */ -#ifndef _FUJIATTRIBS_ -#define _FUJIATTRIBS_ #include "rtexif.h" @@ -312,5 +310,4 @@ const TagAttrib fujiAttribs[] = { { -1, AC_DONTWRITE, 0, nullptr, 0, AUTO, "", nullptr} }; } -#endif diff --git a/rtexif/kodakattribs.cc b/rtexif/kodakattribs.cc index a9c168a70..c89ca2298 100644 --- a/rtexif/kodakattribs.cc +++ b/rtexif/kodakattribs.cc @@ -1,8 +1,6 @@ /* * This file is part of RawTherapee. */ -#ifndef _KODAKATTRIBS_ -#define _KODAKATTRIBS_ #include #include "rtexif.h" @@ -58,7 +56,7 @@ void parseKodakIfdTextualInfo (Tag *textualInfo, Tag* exif_) // Proback645 may have "Lens" but not "Focal Length" float flen = atof (val.c_str()); - if (flen != 0.0) { + if (flen != 0.f) { t = new Tag (exif, lookupAttrib (exifAttribs, "FocalLength")); t->initRational (flen * 32, 32); exif->replaceTag (t); @@ -66,7 +64,7 @@ void parseKodakIfdTextualInfo (Tag *textualInfo, Tag* exif_) } else if (key == "Focal Length") { float flen = atof (val.c_str()); - if (flen != 0.0) { + if (flen != 0.f) { t = new Tag (exif, lookupAttrib (exifAttribs, "FocalLength")); t->initRational (flen * 32, 32); exif->replaceTag (t); @@ -74,7 +72,7 @@ void parseKodakIfdTextualInfo (Tag *textualInfo, Tag* exif_) } else if (key == "Aperture") { float aperture = atof (&val.c_str()[1]); - if (aperture != 0.0) { + if (aperture != 0.f) { t = new Tag (exif, lookupAttrib (exifAttribs, "FNumber")); t->initRational ((int) (aperture * 10), 10); exif->replaceTag (t); @@ -161,5 +159,4 @@ const TagAttrib kodakIfdAttribs[] = { }; } -#endif diff --git a/rtexif/nikonattribs.cc b/rtexif/nikonattribs.cc index 77720dde0..0bc9ce730 100644 --- a/rtexif/nikonattribs.cc +++ b/rtexif/nikonattribs.cc @@ -16,8 +16,6 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . */ -#ifndef _NIKONATTRIBS_ -#define _NIKONATTRIBS_ #include #include @@ -70,7 +68,7 @@ public: int a = t->getValue()[ofs]; if (a > 1) { - int i = int (double (powf (2.f, float (a) / 12.f - 5.f)) * 100.f + 0.5f); + int i = static_cast(powf(2.f, float (a) / 12.f - 5.f)) * 100.0 + 0.5; return i; } else { return 0; @@ -627,6 +625,7 @@ const std::map NALensDataInterpreter::lenses = { {"02 48 65 65 24 24 02 00", "Sigma Macro 90mm f/2.8"}, {"03 43 5C 81 35 35 02 00", "Soligor AF C/D Zoom UMCS 70-210mm 1:4.5"}, {"03 48 5C 81 30 30 02 00", "AF Zoom-Nikkor 70-210mm f/4"}, + {"03 54 68 68 0C 0C 00 00", "Zeiss Otus 1.4/100"}, {"04 48 3C 3C 24 24 03 00", "AF Nikkor 28mm f/2.8"}, {"05 54 50 50 0C 0C 04 00", "AF Nikkor 50mm f/1.4"}, {"06 3F 68 68 2C 2C 06 00", "Cosina AF 100mm f/3.5 Macro"}, @@ -906,12 +905,14 @@ const std::map NALensDataInterpreter::lenses = { {"7F 48 2B 5C 24 34 1C 06", "Sigma 17-70mm f/2.8-4.5 DC Macro Asp. IF"}, {"7F 48 2D 50 24 24 1C 06", "Sigma 18-50mm f/2.8 EX DC Macro"}, {"80 48 1A 1A 24 24 85 06", "AF DX Fisheye-Nikkor 10.5mm f/2.8G ED"}, + {"80 48 1C 29 24 24 7A 06", "Tokina atx-i 11-16mm f/2.8 CF"}, {"81 34 76 A6 38 40 4B 0E", "Sigma 150-600mm f/5-6.3 DG OS HSM | S"}, {"81 54 80 80 18 18 86 0E", "AF-S VR Nikkor 200mm f/2G IF-ED"}, {"82 34 76 A6 38 40 4B 0E", "Sigma 150-600mm f/5-6.3 DG OS HSM | C"}, {"82 48 8E 8E 24 24 87 0E", "AF-S VR Nikkor 300mm f/2.8G IF-ED"}, {"83 00 B0 B0 5A 5A 88 04", "FSA-L2, EDG 65, 800mm f/13 G"}, {"88 54 50 50 0C 0C 4B 06", "Sigma 50mm f/1.4 DG HSM | A"}, + {"89 30 2D 80 2C 40 4B 0E", "Sigma 18-200mm f/3.5-6.3 DC Macro OS HS | C"}, {"89 3C 53 80 30 3C 8B 06", "AF-S DX Zoom-Nikkor 55-200mm f/4-5.6G ED"}, {"8A 3C 37 6A 30 30 4B 0E", "Sigma 24-105mm f/4 DG OS HSM"}, {"8A 54 6A 6A 24 24 8C 0E", "AF-S VR Micro-Nikkor 105mm f/2.8G IF-ED"}, @@ -955,6 +956,7 @@ const std::map NALensDataInterpreter::lenses = { {"9E 38 11 29 34 3C 4B 06", "Sigma 8-16mm f/4.5-5.6 DC HSM"}, {"9E 40 2D 6A 2C 3C A0 0E", "AF-S DX VR Zoom-Nikkor 18-105mm f/3.5-5.6G ED"}, {"9F 37 50 A0 34 40 4B 0E", "Sigma 50-500mm f/4.5-6.3 DG OS HSM"}, + {"9F 48 48 48 24 24 A1 06", "Yongnuo YN40mm f/2.8N"}, {"9F 58 44 44 14 14 A1 06", "AF-S DX Nikkor 35mm f/1.8G"}, {"A0 40 2D 53 2C 3C CA 0E", "AF-P DX Nikkor 18-55mm f/3.5-5.6G VR"}, {"A0 40 2D 53 2C 3C CA 8E", "AF-P DX Nikkor 18-55mm f/3.5-5.6G"}, @@ -1007,6 +1009,7 @@ const std::map NALensDataInterpreter::lenses = { {"AA 48 88 A4 3C 3C D5 4E", "AF-S Nikkor 180-400mm f/4E TC1.4 FL ED VR + 1.4x TC"}, {"AB 3C A0 A0 30 30 C6 4E", "AF-S Nikkor 500mm f/4E FL ED VR"}, {"AB 44 5C 8E 34 3C D6 0E", "AF-P Nikkor 70-300mm f/4.5-5.6E ED VR"}, + {"AB 44 5C 8E 34 3C D6 4E", "AF-P Nikkor 70-300mm f/4.5-5.6E ED VR"}, {"AB 44 5C 8E 34 3C D6 CE", "AF-P Nikkor 70-300mm f/4.5-5.6E ED VR"}, {"AC 38 53 8E 34 3C AE 0E", "AF-S DX Nikkor 55-300mm f/4.5-5.6G ED VR"}, {"AC 3C A6 A6 30 30 C7 4E", "AF-S Nikkor 600mm f/4E FL ED VR"}, @@ -1038,6 +1041,8 @@ const std::map NALensDataInterpreter::lenses = { {"C1 48 24 37 24 24 4B 46", "Sigma 14-24mm f/2.8 DG HSM | A"}, {"C2 4C 24 24 14 14 4B 06", "Sigma 14mm f/1.8 DG HSM | A"}, {"C3 34 68 98 38 40 4B 4E", "Sigma 100-400mm f/5-6.3 DG OS HSM | C"}, + {"C8 54 44 44 0D 0D DF 46", "Tamron SP 35mm f/1.4 Di USD (F045)"}, + {"C8 54 62 62 0C 0C 4B 06", "Sigma 85mm f/1.4 DG HSM | A"}, {"C8 54 62 62 0C 0C 4B 46", "Sigma 85mm f/1.4 DG HSM | A"}, {"C9 48 37 5C 24 24 4B 4E", "Sigma 24-70mm f/2.8 DG OS HSM | A"}, {"CA 48 27 3E 24 24 DF 4E", "Tamron SP 15-30mm f/2.8 Di VC USD G2 (A041)"}, @@ -1051,21 +1056,22 @@ const std::map NALensDataInterpreter::lenses = { {"DC 48 19 19 24 24 4B 06", "Sigma 10mm f/2.8 EX DC HSM Fisheye"}, {"DE 54 50 50 0C 0C 4B 06", "Sigma 50mm f/1.4 EX DG HSM"}, {"E0 3C 5C 8E 30 3C 4B 06", "Sigma 70-300mm f/4-5.6 APO DG Macro HSM"}, - {"E0 40 2D 98 2C 41 DF 4E", "Tamron AF 18-400mm f/3.5-6.3 Di II VC HLD (B028)"}, + {"E0 40 2D 98 2C 41 DF 4E", "Tamron 18-400mm f/3.5-6.3 Di II VC HLD (B028)"}, {"E1 40 19 36 2C 35 DF 4E", "Tamron 10-24mm f/3.5-4.5 Di II VC HLD (B023)"}, {"E1 58 37 37 14 14 1C 02", "Sigma 24mm f/1.8 EX DG Aspherical Macro"}, {"E2 47 5C 80 24 24 DF 4E", "Tamron SP 70-200mm f/2.8 Di VC USD G2 (A025)"}, {"E3 40 76 A6 38 40 DF 4E", "Tamron SP 150-600mm f/5-6.3 Di VC USD G2"}, {"E3 54 50 50 24 24 35 02", "Sigma Macro 50mm f/2.8 EX DG"}, {"E4 54 64 64 24 24 DF 0E", "Tamron SP 90mm f/2.8 Di VC USD Macro 1:1 (F017)"}, + {"E5 4C 62 62 14 14 C9 4E", "Tamron SP 85mm f/1.8 Di VC USD (F016)"}, {"E5 54 6A 6A 24 24 35 02", "Sigma Macro 105mm f/2.8 EX DG"}, - {"E6 40 2D 80 2C 40 DF 0E", "Tamron AF 18-200mm f/3.5-6.3 Di II VC (B018)"}, + {"E6 40 2D 80 2C 40 DF 0E", "Tamron 18-200mm f/3.5-6.3 Di II VC (B018)"}, {"E6 41 3C 8E 2C 40 1C 02", "Sigma 28-300mm f/3.5-6.3 DG Macro"}, {"E7 4C 4C 4C 14 14 DF 0E", "Tamron SP 45mm f/1.8 Di VC USD (F013)"}, {"E8 4C 44 44 14 14 DF 0E", "Tamron SP 35mm f/1.8 Di VC USD (F012)"}, {"E9 48 27 3E 24 24 DF 0E", "Tamron SP 15-30mm f/2.8 Di VC USD (A012)"}, {"E9 54 37 5C 24 24 1C 02", "Sigma 24-70mm f/2.8 EX DG Macro"}, - {"EA 40 29 8E 2C 40 DF 0E", "Tamron AF 16-300mm f/3.5-6.3 Di II VC PZD (B016)"}, + {"EA 40 29 8E 2C 40 DF 0E", "Tamron 16-300mm f/3.5-6.3 Di II VC PZD (B016)"}, {"EA 48 27 27 24 24 1C 02", "Sigma 15mm f/2.8 EX Diagonal Fisheye"}, {"EB 40 76 A6 38 40 DF 0E", "Tamron SP AF 150-600mm f/5-6.3 VC USD (A011)"}, {"ED 40 2D 80 2C 40 4B 0E", "Sigma 18-200mm f/3.5-6.3 DC OS HSM"}, @@ -1076,6 +1082,7 @@ const std::map NALensDataInterpreter::lenses = { {"F1 47 5C 8E 30 3C DF 0E", "Tamron SP 70-300mm f/4-5.6 Di VC USD (A005)"}, {"F3 48 68 8E 30 30 4B 02", "Sigma APO 100-300mm f/4 EX IF HSM"}, {"F3 54 2B 50 24 24 84 0E", "Tamron SP AF 17-50mm f/2.8 XR Di II VC LD Aspherical (IF) (B005)"}, + {"F4 4C 7C 7C 2C 2C 4B 02", "Sigma APO Macro 180mm f/3.5 EX DG HSM"}, {"F4 54 56 56 18 18 84 06", "Tamron SP AF 60mm f/2.0 Di II Macro 1:1 (G005)"}, {"F5 40 2C 8A 2C 40 40 0E", "Tamron AF 18-270mm f/3.5-6.3 Di II VC LD Aspherical (IF) Macro (B003)"}, {"F5 48 76 76 24 24 4B 06", "Sigma APO Macro 150mm f/2.8 EX DG HSM"}, @@ -1220,5 +1227,3 @@ const TagAttrib nikon3Attribs[] = { }; } -#endif - diff --git a/rtexif/olympusattribs.cc b/rtexif/olympusattribs.cc index f9869f13e..52fbec55d 100644 --- a/rtexif/olympusattribs.cc +++ b/rtexif/olympusattribs.cc @@ -16,8 +16,6 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . */ -#ifndef _OLYMPUSATTRIBS_ -#define _OLYMPUSATTRIBS_ #include #include @@ -130,8 +128,10 @@ public: lenses["00 30 10"] = "Olympus M.Zuiko Digital ED 45mm f/1.2 Pro"; lenses["00 31 00"] = "Olympus Zuiko Digital ED 12-60mm f/2.8-4.0 SWD"; lenses["00 32 00"] = "Olympus Zuiko Digital ED 14-35mm f/2.0 SWD"; + lenses["00 32 10"] = "Olympus M.Zuiko Digital ED 12-200mm f/3.5-6.3"; lenses["00 33 00"] = "Olympus Zuiko Digital 25mm f/2.8"; lenses["00 34 00"] = "Olympus Zuiko Digital ED 9-18mm f/4.0-5.6"; + lenses["00 34 10"] = "Olympus M.Zuiko Digital ED 12-45mm f/4.0 Pro"; lenses["00 35 00"] = "Olympus Zuiko Digital 14-54mm f/2.8-3.5 II"; lenses["01 01 00"] = "Sigma 18-50mm f/3.5-5.6 DC"; lenses["01 01 10"] = "Sigma 30mm f/2.8 EX DN"; @@ -190,6 +190,13 @@ public: lenses["02 26 10"] = "Lumix G 25mm f/1.7 Asph."; lenses["02 27 10"] = "Leica DG Vario-Elmar 100-400mm f/4.0-6.3 Asph. Power OIS"; lenses["02 28 10"] = "Lumix G Vario 12-60mm f/3.5-5.6 Asph. Power OIS"; + lenses["02 29 10"] = "Leica DG Summilux 12mm f/1.4 Asph."; + lenses["02 30 10"] = "Leica DG Vario-Elmarit 12-60mm f/2.8-4 Asph. Power OIS"; + lenses["02 33 10"] = "Lumix G X Vario 12-35mm f/2.8 II Asph. Power OIS"; + lenses["02 35 10"] = "Leica DG Vario-Elmarit 8-18mm f/2.8-4 Asph."; + lenses["02 36 10"] = "Leica DG Elmarit 200mm f/2.8 Power OIS"; + lenses["02 37 10"] = "Leica DG Vario-Elmarit 50-200mm f/2.8-4 Asph. Power OIS"; + lenses["02 38 10"] = "Leica DG Vario-Summilux 10-25mm f/1.7 Asph."; lenses["03 01 00"] = "Leica D Vario Elmarit 14-50mm f/2.8-3.5 Asph."; lenses["03 02 00"] = "Leica D Summilux 25mm f/1.4 Asph."; lenses["05 01 10"] = "Tamron 14-150mm f/3.5-5.8 Di III"; @@ -842,5 +849,3 @@ const TagAttrib olympusAttribs[] = { { -1, AC_DONTWRITE, 0, nullptr, 0, AUTO, "", nullptr} }; } -#endif - diff --git a/rtexif/panasonicattribs.cc b/rtexif/panasonicattribs.cc index 3062824cf..4ebcf2447 100644 --- a/rtexif/panasonicattribs.cc +++ b/rtexif/panasonicattribs.cc @@ -1,8 +1,6 @@ /* * This file is part of RawTherapee. */ -#ifndef _PANASONICATTRIBS_ -#define _PANASONICATTRIBS_ #include #include "rtexif.h" @@ -138,5 +136,3 @@ const TagAttrib panasonicRawAttribs[] = { }; } -#endif - diff --git a/rtexif/pentaxattribs.cc b/rtexif/pentaxattribs.cc index 898150696..d6b9a9c84 100644 --- a/rtexif/pentaxattribs.cc +++ b/rtexif/pentaxattribs.cc @@ -16,8 +16,6 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . */ -#ifndef _PENTAXATTRIBS_ -#define _PENTAXATTRIBS_ #include #include @@ -696,7 +694,7 @@ public: }; PAColorSpaceInterpreter paColorSpaceInterpreter; -class PALensTypeInterpreter : public IntLensInterpreter< int > +class PALensTypeInterpreter final: public IntLensInterpreter< int > { public: PALensTypeInterpreter () @@ -752,7 +750,7 @@ public: choices.insert (p_t (256 * 3 + 44, "Sigma 17-70mm f/2.8-4.5 DC Macro")); choices.insert (p_t (256 * 3 + 44, "Sigma 18-50mm f/3.5-5.6 DC")); choices.insert (p_t (256 * 3 + 44, "Sigma 17-35mm f/2.8-4 EX DG")); - choices.insert (p_t (256 * 3 + 44, "Tamron 35-90mm f/4 AF")); + choices.insert (p_t (256 * 3 + 44, "Tamron 35-90mm f/4-5.6 AF")); choices.insert (p_t (256 * 3 + 44, "Sigma AF 18-35mm f/3.5-4.5 Aspherical")); choices.insert (p_t (256 * 3 + 46, "Sigma or Samsung Lens (3 46)")); choices.insert (p_t (256 * 3 + 46, "Sigma APO 70-200mm f/2.8 EX")); @@ -784,6 +782,7 @@ public: choices.insert (p_t (256 * 4 + 2, "smc PENTAX-FA 80-320mm f/4.5-5.6")); choices.insert (p_t (256 * 4 + 3, "smc PENTAX-FA 43mm f/1.9 Limited")); choices.insert (p_t (256 * 4 + 6, "smc PENTAX-FA 35-80mm f/4-5.6")); + choices.insert (p_t (256 * 4 + 8, "Irix 150mm f/2.8 Macro")); choices.insert (p_t (256 * 4 + 9, "Irix 11mm f/4 Firefly")); choices.insert (p_t (256 * 4 + 10, "Irix 15mm f/2.4")); choices.insert (p_t (256 * 4 + 12, "smc PENTAX-FA 50mm f/1.4")); @@ -908,8 +907,9 @@ public: choices.insert (p_t (256 * 7 + 243, "smc PENTAX-DA 70mm f/2.4 Limited")); choices.insert (p_t (256 * 7 + 244, "smc PENTAX-DA 21mm f/3.2 AL Limited")); choices.insert (p_t (256 * 8 + 0, "Sigma 50-150mm f/2.8 II APO EX DC HSM")); - choices.insert (p_t (256 * 8 + 3, "Sigma AF 18-125mm f/3.5-5.6 DC")); + choices.insert (p_t (256 * 8 + 3, "Sigma 18-125mm f/3.8-5.6 DC HSM")); choices.insert (p_t (256 * 8 + 4, "Sigma 50mm f/1.4 EX DG HSM")); + choices.insert (p_t (256 * 8 + 6, "Sigma 4.5mm f/2.8 EX DC Fisheye")); choices.insert (p_t (256 * 8 + 7, "Sigma 24-70mm f/2.8 IF EX DG HSM")); choices.insert (p_t (256 * 8 + 8, "Sigma 18-250mm f/3.5-6.3 DC OS HSM")); choices.insert (p_t (256 * 8 + 11, "Sigma 10-20mm f/3.5 EX DC HSM")); @@ -920,6 +920,7 @@ public: choices.insert (p_t (256 * 8 + 16, "Sigma 70-200mm f/2.8 EX DG Macro HSM II")); choices.insert (p_t (256 * 8 + 17, "Sigma 50-500mm f/4.5-6.3 DG OS HSM")); choices.insert (p_t (256 * 8 + 18, "Sigma 8-16mm f/4.5-5.6 DC HSM")); + choices.insert (p_t (256 * 8 + 20, "Sigma 18-50mm f/2.8-4.5 DC HSM")); choices.insert (p_t (256 * 8 + 21, "Sigma 17-50mm f/2.8 EX DC OS HSM")); choices.insert (p_t (256 * 8 + 22, "Sigma 85mm f/1.4 EX DG HSM")); choices.insert (p_t (256 * 8 + 23, "Sigma 70-200mm f/2.8 APO EX DG OS HSM")); @@ -938,6 +939,8 @@ public: choices.insert (p_t (256 * 8 + 62, "HD PENTAX-D FA 24-70mm f/2.8 ED SDM WR")); choices.insert (p_t (256 * 8 + 63, "HD PENTAX-D FA 15-30mm f/2.8 ED SDM WR")); choices.insert (p_t (256 * 8 + 64, "HD PENTAX-D FA* 50mm f/1.4 SDM AW")); + choices.insert (p_t (256 * 8 + 65, "HD PENTAX-D FA 70-210mm f/4 ED SDM WR")); + choices.insert (p_t (256 * 8 + 196, "HD PENTAX-DA* 11-18mm f/2.8 ED DC AW")); choices.insert (p_t (256 * 8 + 197, "HD PENTAX-DA 55-300mm f/4.5-6.3 ED PLM WR RE")); choices.insert (p_t (256 * 8 + 198, "smc PENTAX-DA L 18-50mm f/4-5.6 DC WR RE")); choices.insert (p_t (256 * 8 + 199, "HD PENTAX-DA 18-50mm f/4-5.6 DC WR RE")); @@ -992,6 +995,7 @@ public: choices.insert (p_t (256 * 22 + 3, "03 Fish-eye 3.2mm f/5.6")); choices.insert (p_t (256 * 22 + 4, "04 Toy Lens Wide 6.3mm f/7.1")); choices.insert (p_t (256 * 22 + 5, "05 Toy Lens Telephoto 18mm f/8")); + choices.insert (p_t (256 * 31 + 1, "GR Lens")); } std::string toString (const Tag* t) const override { @@ -1391,9 +1395,9 @@ public: std::string toString (const Tag* t) const override { int a = t->toInt (0, BYTE); - float b = float (10 * int (a >> 2)) * pow (4.f, float (int (a & 0x03) - 2)); + double b = static_cast(10 * (a >> 2)) * std::pow(4.0, static_cast((a & 0x03) - 2)); - if (b > 1.f) { + if (b > 1.0) { char buffer[32]; sprintf (buffer, "%.2f", b ); return buffer; @@ -1404,9 +1408,9 @@ public: double toDouble (const Tag* t, int ofs) override { int a = t->toInt (ofs, BYTE); - float b = float (10 * int (a >> 2)) * pow (4.f, float (int (a & 0x03) - 2)); + double b = static_cast(10 * (a >> 2)) * std::pow(4.0, static_cast((a & 0x03) - 2)); - if (b > 1.f) { + if (b > 1.0) { return b; } else { return 0.; @@ -2212,7 +2216,6 @@ const TagAttrib pentaxCameraInfoAttribs[] = { }; } -#endif diff --git a/rtexif/rtexif.cc b/rtexif/rtexif.cc index 89ff6cd33..06604ade5 100644 --- a/rtexif/rtexif.cc +++ b/rtexif/rtexif.cc @@ -2344,7 +2344,7 @@ void ExifManager::parseCIFF (int length, TagDirectory* root) ev = ((short)get2 (f, INTEL)) / 32.0f; fseek (f, 34, SEEK_CUR); - if (shutter > 1e6) { + if (shutter > 1e6f) { shutter = get2 (f, INTEL) / 10.0f; } diff --git a/rtexif/rtexif.h b/rtexif/rtexif.h index c37533352..1a956a4a5 100644 --- a/rtexif/rtexif.h +++ b/rtexif/rtexif.h @@ -163,14 +163,14 @@ public: // Try to get the Tag in the current directory and in subdirectories // if lookUpward = true, it will scan the parents TagDirectory up to the root one, // but w/o looking into their subdirs - virtual Tag* findTag (const char* name, bool lookUpward = false) const; + Tag* findTag (const char* name, bool lookUpward = false) const; // Find a all Tags with the given name by scanning the whole tag tree std::vector findTags (const char* name); // Find a all Tags with the given ID by scanning the whole tag tree std::vector findTags (int ID); // Try to get the Tag in the current directory and in parent directories // (won't look into subdirs) - virtual Tag* findTagUpward (const char* name) const; + Tag* findTagUpward (const char* name) const; bool getXMPTagValue (const char* name, char* value) const; void keepTag (int ID); @@ -191,10 +191,10 @@ public: virtual TagDirectory* clone (TagDirectory* parent) const; void applyChange (const std::string &field, const Glib::ustring &value); - virtual void printAll (unsigned int level = 0) const; // reentrant debug function, keep level=0 on first call ! - virtual bool CPBDump (const Glib::ustring &commFName, const Glib::ustring &imageFName, const Glib::ustring &profileFName, const Glib::ustring &defaultPParams, + void printAll (unsigned int level = 0) const; // reentrant debug function, keep level=0 on first call ! + bool CPBDump (const Glib::ustring &commFName, const Glib::ustring &imageFName, const Glib::ustring &profileFName, const Glib::ustring &defaultPParams, const CacheImageData* cfs, const bool flagMode, Glib::KeyFile *keyFile = nullptr, Glib::ustring tagDirName = "") const; - virtual void sort (); + void sort (); }; // a table of tags: id are offset from beginning and not identifiers diff --git a/rtexif/sonyminoltaattribs.cc b/rtexif/sonyminoltaattribs.cc index 4410a4051..4c901b8c0 100644 --- a/rtexif/sonyminoltaattribs.cc +++ b/rtexif/sonyminoltaattribs.cc @@ -15,8 +15,6 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . */ -#ifndef _SONYMINOLTAATTRIBS_ -#define _SONYMINOLTAATTRIBS_ #include @@ -541,7 +539,7 @@ public: }; SAAntiBlurInterpreter saAntiBlurInterpreter; -class SALensIDInterpreter : public IntLensInterpreter +class SALensIDInterpreter final : public IntLensInterpreter { public: SALensIDInterpreter () @@ -574,11 +572,12 @@ public: {23, "Minolta AF 200mm f/4 Macro APO G"}, {24, "Minolta/Sony AF 24-105mm f/3.5-4.5 (D) or Sigma or Tamron Lens"}, {24, "Sigma 18-50mm f/2.8"}, - {24, "Sigma 17-70mm f/2.8-4.5 (D)"}, + {24, "Sigma 17-70mm f/2.8-4.5 DC Macro"}, {24, "Sigma 20-40mm f/2.8 EX DG Aspherical IF"}, {24, "Sigma 18-200mm f/3.5-6.3 DC"}, {24, "Sigma DC 18-125mm f/4-5,6 D"}, {24, "Tamron SP AF 28-75mm f/2.8 XR Di LD Aspherical [IF] Macro"}, + {24, "Sigma 15-30mm f/3.5-4.5 EX DG Aspherical"}, {25, "Minolta AF 100-300mm f/4.5-5.6 APO (D) or Sigma Lens"}, {25, "Sigma 100-300mm f/4 EX (APO (D) or D IF)"}, {25, "Sigma 70mm f/2.8 EX DG Macro"}, @@ -612,8 +611,9 @@ public: {45, "Carl Zeiss Planar T* 85mm f/1.4 ZA (SAL85F14Z)"}, {46, "Carl Zeiss Vario-Sonnar T* DT 16-80mm f/3.5-4.5 ZA (SAL1680Z)"}, {47, "Carl Zeiss Sonnar T* 135mm f/1.8 ZA (SAL135F18Z)"}, - {48, "Carl Zeiss Vario-Sonnar T* 24-70mm f/2.8 ZA SSM (SAL2470Z) or ZA SSM II"}, + {48, "Carl Zeiss Vario-Sonnar T* 24-70mm f/2.8 ZA SSM (SAL2470Z) or Other Lens"}, {48, "Carl Zeiss Vario-Sonnar T* 24-70mm f/2.8 ZA SSM II (SAL2470Z2)"}, + {48, "Tamron SP 24-70mm f/2.8 Di USD"}, {49, "Sony DT 55-200mm f/4-5.6 (SAL55200)"}, {50, "Sony DT 18-250mm f/3.5-6.3 (SAL18250)"}, {51, "Sony DT 16-105mm f/3.5-5.6 (SAL16105)"}, @@ -645,7 +645,6 @@ public: {128, "Tamron or Sigma Lens (128)"}, {128, "Tamron AF 18-200mm f/3.5-6.3 XR Di II LD Aspherical [IF] Macro"}, {128, "Tamron AF 28-300mm f/3.5-6.3 XR Di LD Aspherical [IF] Macro"}, - {128, "Tamron 80-300mm f/3.5-6.3"}, {128, "Tamron AF 28-200mm f/3.8-5.6 XR Di Aspherical [IF] Macro"}, {128, "Tamron SP AF 17-35mm f/2.8-4 Di LD Aspherical IF"}, {128, "Sigma AF 50-150mm f/2.8 EX DC APO HSM II"}, @@ -680,7 +679,7 @@ public: {137, "Cosina 70-210mm f/2.8-4 AF"}, {138, "Soligor 19-35mm f/3.5-4.5"}, {139, "Tokina AF 28-300mm f/4-6.3"}, - {142, "Voigtlander 70-300mm f/4.5-5.6"}, + {142, "Cosina AF 70-300mm f/4.5-5.6 MC"}, {146, "Voigtlander Macro APO-Lanthar 125mm f/2.5 SL"}, {194, "Tamron SP AF 17-50mm f/2.8 XR Di II LD Aspherical [IF]"}, {202, "Tamron SP AF 70-200mm f/2.8 Di LD [IF] Macro"}, @@ -723,10 +722,11 @@ public: {2552, "Angenieux AF 28-70mm f/2.6"}, {2552, "Tokina AT-X 17 AF 17mm f/3.5"}, {2552, "Tokina 20-35mm f/3.5-4.5 II AF"}, - {2553, "Minolta AF 28-135mm f/4-4.5 or Sigma Lens"}, + {2553, "Minolta AF 28-135mm f/4-4.5 or Other Lens"}, {2553, "Sigma ZOOM-alpha 35-135mm f/3.5-4.5"}, {2553, "Sigma 28-105mm f/2.8-4 Aspherical"}, {2553, "Sigma 28-105mm f/4-5.6 UC"}, + {2553, "Tokina AT-X 242 AF 24-200mm f/3.5-5.6"}, {2554, "Minolta AF 35-105mm f/3.5-4.5"}, {2555, "Minolta AF 70-210mm f/4 Macro or Sigma Lens"}, {2555, "Sigma 70-210mm f/4-5.6 APO"}, @@ -805,7 +805,7 @@ public: {2624, "Minolta AF 35-80mm f/4-5.6 Power Zoom"}, {2628, "Minolta AF 80-200mm f/2.8 HS-APO G"}, {2629, "Minolta AF 85mm f/1.4 New"}, - {2631, "Minolta/Sony AF 100-300mm f/4.5-5.6 APO"}, + {2631, "Minolta AF 100-300mm f/4.5-5.6 APO"}, {2632, "Minolta AF 24-50mm f/4 New"}, {2638, "Minolta AF 50mm f/2.8 Macro New"}, {2639, "Minolta AF 100mm f/2.8 Macro"}, @@ -818,6 +818,7 @@ public: {2672, "Minolta AF 24-105mm f/3.5-4.5 (D)"}, {3046, "Metabones Canon EF Speed Booster"}, {4567, "Tokina 70-210mm f/4-5.6"}, + {4568, "Tokina AF 35-200mm f/4-5.6 Zoom SD"}, {4570, "Tamron AF 35-135mm f/3.5-4.5"}, {4571, "Vivitar 70-210mm f/4.5-5.6"}, {4574, "2x Teleconverter or Tamron or Tokina Lens"}, @@ -832,97 +833,6 @@ public: {6118, "Canon EF Adapter"}, {6528, "Sigma 16mm f/2.8 Filtermatic Fisheye"}, {6553, "E-Mount, T-Mount, Other Lens or no lens"}, - {6553, "Sony E 16mm f/2.8"}, - {6553, "Sony E 18-55mm f/3.5-5.6 OSS"}, - {6553, "Sony E 55-210mm f/4.5-6.3 OSS"}, - {6553, "Sony E 18-200mm f/3.5-6.3 OSS"}, - {6553, "Sony E 30mm f/3.5 Macro"}, - {6553, "Sony E 24mm f/1.8 ZA"}, - {6553, "Sony E 50mm f/1.8 OSS"}, - {6553, "Sony E 16-70mm f/4 ZA OSS"}, - {6553, "Sony E 10-18mm f/4 OSS"}, - {6553, "Sony E PZ 16-50mm f/3.5-5.6 OSS"}, - {6553, "Sony FE 35mm f/2.8 ZA"}, - {6553, "Sony FE 24-70mm f/4 ZA OSS"}, - {6553, "Sony FE 85mm f/1.8"}, - {6553, "Sony E 18-200mm f/3.5-6.3 OSS LE"}, - {6553, "Sony E 20mm f/2.8"}, - {6553, "Sony E 35mm f/1.8 OSS"}, - {6553, "Sony E PZ 18-105mm f/4 G OSS"}, - {6553, "Sony FE 12-24mm f/4 G"}, - {6553, "Sony FE 90mm f/2.8 Macro G OSS"}, - {6553, "Sony E 18-50mm f/4-5.6"}, - {6553, "Sony FE 24mm f/1.4 GM"}, - {6553, "Sony FE 24-105mm f/4 G OSS"}, - {6553, "Sony E PZ 18-200mm f/3.5-6.3 OSS"}, - {6553, "Sony FE 55mm f/1.8 ZA"}, - {6553, "Sony FE 70-200mm f/4 G OSS"}, - {6553, "Sony FE 16-35mm f/4 ZA OSS"}, - {6553, "Sony FE 50mm f/2.8 Macro"}, - {6553, "Sony FE 28-70mm f/3.5-5.6 OSS"}, - {6553, "Sony FE 35mm f/1.4 ZA"}, - {6553, "Sony FE 24-240mm f/3.5-6.3 OSS"}, - {6553, "Sony FE 28mm f/2"}, - {6553, "Sony FE PZ 28-135mm f/4 G OSS"}, - {6553, "Sony FE 100mm f/2.8 STF GM OSS"}, - {6553, "Sony E PZ 18-110mm f/4 G OSS"}, - {6553, "Sony FE 24-70mm f/2.8 GM"}, - {6553, "Sony FE 50mm f/1.4 ZA"}, - {6553, "Sony FE 85mm f/1.4 GM"}, - {6553, "Sony FE 50mm f/1.8"}, - {6553, "Sony FE 21mm f/2.8 (SEL28F20 + SEL075UWC)"}, - {6553, "Sony FE 16mm f/3.5 Fisheye (SEL28F20 + SEL057FEC)"}, - {6553, "Sony FE 70-300mm f/4.5-5.6 G OSS"}, - {6553, "Sony FE 100-400mm f/4.5-5.6 GM OSS"}, - {6553, "Sony FE 70-200mm f/2.8 GM OSS"}, - {6553, "Sony FE 16-35mm f/2.8 GM"}, - {6553, "Sony FE 400mm f/2.8 GM OSS"}, - {6553, "Sony E 18-135mm f/3.5-5.6 OSS"}, - {6553, "Sony FE 70-200mm f/2.8 GM OSS + 1.4X Teleconverter"}, - {6553, "Sony FE 70-200mm f/2.8 GM OSS + 2X Teleconverter"}, - {6553, "Sony FE 100-400mm f/4.5-5.6 GM OSS + 1.4X Teleconverter"}, - {6553, "Sony FE 100-400mm f/4.5-5.6 GM OSS + 2X Teleconverter"}, - {6553, "Sony FE 400mm f/2.8 GM OSS + 1.4X Teleconverter"}, - {6553, "Sony FE 400mm f/2.8 GM OSS + 2X Teleconverter"}, - {6553, "Samyang AF 50mm f/1.4 FE"}, - {6553, "Samyang AF 14mm f/2.8 FE"}, - {6553, "Samyang AF 24mm f/2.8"}, - {6553, "Samyang AF 35mm f/2.8 FE"}, - {6553, "Samyang AF 35mm f/1.4"}, - {6553, "Sigma 19mm f/2.8 [EX] DN"}, - {6553, "Sigma 30mm f/2.8 [EX] DN"}, - {6553, "Sigma 60mm f/2.8 DN"}, - {6553, "Sigma 30mm f/1.4 DC DN | C"}, - {6553, "Sigma 85mm f/1.4 DG HSM | A"}, - {6553, "Sigma 16mm f/1.4 DC DN | C"}, - {6553, "Sigma 105mm f/1.4 DG HSM | A"}, - {6553, "Sigma 56mm f/1.4 DC DN | C"}, - {6553, "Sigma 70-200mm f/2.8 DG OS HSM | S"}, - {6553, "Sigma 70mm f/2.8 DG MACRO | A"}, - {6553, "Tamron 18-200mm f/3.5-6.3 Di III VC"}, - {6553, "Tamron 28-75mm f/2.8 Di III RXD"}, - {6553, "Tokina Firin 20mm f/2 FE MF"}, - {6553, "Voigtlander SUPER WIDE-HELIAR 15mm f/4.5 III"}, - {6553, "Voigtlander HELIAR-HYPER WIDE 10mm f/5.6"}, - {6553, "Voigtlander ULTRA WIDE-HELIAR 12mm f/5.6 III"}, - {6553, "Voigtlander MACRO APO-LANTHAR 65mm f/2 Aspherical"}, - {6553, "Voigtlander NOKTON 40mm f/1.2 Aspherical"}, - {6553, "Voigtlander NOKTON classic 35mm f/1.4"}, - {6553, "Voigtlander MACRO APO-LANTHAR 110mm f/2.5"}, - {6553, "Voigtlander COLOR-SKOPAR 21mm f/3.5 Aspherical"}, - {6553, "Zeiss Touit 12mm f/2.8"}, - {6553, "Zeiss Touit 32mm f/1.8"}, - {6553, "Zeiss Touit 50mm f/2.8 Macro"}, - {6553, "Zeiss Batis 25mm f/2"}, - {6553, "Zeiss Batis 85mm f/1.8"}, - {6553, "Zeiss Batis 18mm f/2.8"}, - {6553, "Zeiss Batis 135mm f/2.8"}, - {6553, "Zeiss Batis 40mm f/2 CF"}, - {6553, "Zeiss Loxia 50mm f/2"}, - {6553, "Zeiss Loxia 35mm f/2"}, - {6553, "Zeiss Loxia 21mm f/2.8"}, - {6553, "Zeiss Loxia 85mm f/2.4"}, - {6553, "Zeiss Loxia 25mm f/2.4"}, {6553, "Arax MC 35mm f/2.8 Tilt+Shift"}, {6553, "Arax MC 80mm f/2.8 Tilt+Shift"}, {6553, "Zenitar MF 16mm f/2.8 Fisheye M42"}, @@ -948,10 +858,11 @@ public: {25521, "Angenieux AF 28-70mm f/2.6"}, {25521, "Tokina AT-X 17 AF 17mm f/3.5"}, {25521, "Tokina 20-35mm f/3.5-4.5 II AF"}, - {25531, "Minolta AF 28-135mm f/4-4.5 or Sigma Lens"}, + {25531, "Minolta AF 28-135mm f/4-4.5 or Other Lens"}, {25531, "Sigma ZOOM-alpha 35-135mm f/3.5-4.5"}, {25531, "Sigma 28-105mm f/2.8-4 Aspherical"}, {25531, "Sigma 28-105mm f/4-5.6 UC"}, + {25531, "Tokina AT-X 242 AF 24-200mm f/3.5-5.6"}, {25541, "Minolta AF 35-105mm f/3.5-4.5"}, {25551, "Minolta AF 70-210mm f/4 Macro or Sigma Lens"}, {25551, "Sigma 70-210mm f/4-5.6 APO"}, @@ -1030,7 +941,7 @@ public: {26241, "Minolta AF 35-80mm f/4-5.6 Power Zoom"}, {26281, "Minolta AF 80-200mm f/2.8 HS-APO G"}, {26291, "Minolta AF 85mm f/1.4 New"}, - {26311, "Minolta/Sony AF 100-300mm f/4.5-5.6 APO"}, + {26311, "Minolta AF 100-300mm f/4.5-5.6 APO"}, {26321, "Minolta AF 24-50mm f/4 New"}, {26381, "Minolta AF 50mm f/2.8 Macro New"}, {26391, "Minolta AF 100mm f/2.8 Macro"}, @@ -1043,6 +954,7 @@ public: {26721, "Minolta AF 24-105mm f/3.5-4.5 (D)"}, {30464, "Metabones Canon EF Speed Booster"}, {45671, "Tokina 70-210mm f/4-5.6"}, + {45681, "Tokina AF 35-200mm f/4-5.6 Zoom SD"}, {45701, "Tamron AF 35-135mm f/3.5-4.5"}, {45711, "Vivitar 70-210mm f/4.5-5.6"}, {45741, "2x Teleconverter or Tamron or Tokina Lens"}, @@ -1057,104 +969,13 @@ public: {61184, "Canon EF Adapter"}, {65280, "Sigma 16mm f/2.8 Filtermatic Fisheye"}, {65535, "E-Mount, T-Mount, Other Lens or no lens"}, - {65535, "Sony E 16mm f/2.8"}, - {65535, "Sony E 18-55mm f/3.5-5.6 OSS"}, - {65535, "Sony E 55-210mm f/4.5-6.3 OSS"}, - {65535, "Sony E 18-200mm f/3.5-6.3 OSS"}, - {65535, "Sony E 30mm f/3.5 Macro"}, - {65535, "Sony E 24mm f/1.8 ZA"}, - {65535, "Sony E 50mm f/1.8 OSS"}, - {65535, "Sony E 16-70mm f/4 ZA OSS"}, - {65535, "Sony E 10-18mm f/4 OSS"}, - {65535, "Sony E PZ 16-50mm f/3.5-5.6 OSS"}, - {65535, "Sony FE 35mm f/2.8 ZA"}, - {65535, "Sony FE 24-70mm f/4 ZA OSS"}, - {65535, "Sony FE 85mm f/1.8"}, - {65535, "Sony E 18-200mm f/3.5-6.3 OSS LE"}, - {65535, "Sony E 20mm f/2.8"}, - {65535, "Sony E 35mm f/1.8 OSS"}, - {65535, "Sony E PZ 18-105mm f/4 G OSS"}, - {65535, "Sony FE 12-24mm f/4 G"}, - {65535, "Sony FE 90mm f/2.8 Macro G OSS"}, - {65535, "Sony E 18-50mm f/4-5.6"}, - {65535, "Sony FE 24mm f/1.4 GM"}, - {65535, "Sony FE 24-105mm f/4 G OSS"}, - {65535, "Sony E PZ 18-200mm f/3.5-6.3 OSS"}, - {65535, "Sony FE 55mm f/1.8 ZA"}, - {65535, "Sony FE 70-200mm f/4 G OSS"}, - {65535, "Sony FE 16-35mm f/4 ZA OSS"}, - {65535, "Sony FE 50mm f/2.8 Macro"}, - {65535, "Sony FE 28-70mm f/3.5-5.6 OSS"}, - {65535, "Sony FE 35mm f/1.4 ZA"}, - {65535, "Sony FE 24-240mm f/3.5-6.3 OSS"}, - {65535, "Sony FE 28mm f/2"}, - {65535, "Sony FE PZ 28-135mm f/4 G OSS"}, - {65535, "Sony FE 100mm f/2.8 STF GM OSS"}, - {65535, "Sony E PZ 18-110mm f/4 G OSS"}, - {65535, "Sony FE 24-70mm f/2.8 GM"}, - {65535, "Sony FE 50mm f/1.4 ZA"}, - {65535, "Sony FE 85mm f/1.4 GM"}, - {65535, "Sony FE 50mm f/1.8"}, - {65535, "Sony FE 21mm f/2.8 (SEL28F20 + SEL075UWC)"}, - {65535, "Sony FE 16mm f/3.5 Fisheye (SEL28F20 + SEL057FEC)"}, - {65535, "Sony FE 70-300mm f/4.5-5.6 G OSS"}, - {65535, "Sony FE 100-400mm f/4.5-5.6 GM OSS"}, - {65535, "Sony FE 70-200mm f/2.8 GM OSS"}, - {65535, "Sony FE 16-35mm f/2.8 GM"}, - {65535, "Sony FE 400mm f/2.8 GM OSS"}, - {65535, "Sony E 18-135mm f/3.5-5.6 OSS"}, - {65535, "Sony FE 70-200mm f/2.8 GM OSS + 1.4X Teleconverter"}, - {65535, "Sony FE 70-200mm f/2.8 GM OSS + 2X Teleconverter"}, - {65535, "Sony FE 100-400mm f/4.5-5.6 GM OSS + 1.4X Teleconverter"}, - {65535, "Sony FE 100-400mm f/4.5-5.6 GM OSS + 2X Teleconverter"}, - {65535, "Sony FE 400mm f/2.8 GM OSS + 1.4X Teleconverter"}, - {65535, "Sony FE 400mm f/2.8 GM OSS + 2X Teleconverter"}, - {65535, "Samyang AF 50mm f/1.4 FE"}, - {65535, "Samyang AF 14mm f/2.8 FE"}, - {65535, "Samyang AF 24mm f/2.8"}, - {65535, "Samyang AF 35mm f/2.8 FE"}, - {65535, "Samyang AF 35mm f/1.4"}, - {65535, "Sigma 19mm f/2.8 [EX] DN"}, - {65535, "Sigma 30mm f/2.8 [EX] DN"}, - {65535, "Sigma 60mm f/2.8 DN"}, - {65535, "Sigma 30mm f/1.4 DC DN | C"}, - {65535, "Sigma 85mm f/1.4 DG HSM | A"}, - {65535, "Sigma 16mm f/1.4 DC DN | C"}, - {65535, "Sigma 105mm f/1.4 DG HSM | A"}, - {65535, "Sigma 56mm f/1.4 DC DN | C"}, - {65535, "Sigma 70-200mm f/2.8 DG OS HSM | S"}, - {65535, "Sigma 70mm f/2.8 DG MACRO | A"}, - {65535, "Tamron 18-200mm f/3.5-6.3 Di III VC"}, - {65535, "Tamron 28-75mm f/2.8 Di III RXD"}, - {65535, "Tokina Firin 20mm f/2 FE MF"}, - {65535, "Voigtlander SUPER WIDE-HELIAR 15mm f/4.5 III"}, - {65535, "Voigtlander HELIAR-HYPER WIDE 10mm f/5.6"}, - {65535, "Voigtlander ULTRA WIDE-HELIAR 12mm f/5.6 III"}, - {65535, "Voigtlander MACRO APO-LANTHAR 65mm f/2 Aspherical"}, - {65535, "Voigtlander NOKTON 40mm f/1.2 Aspherical"}, - {65535, "Voigtlander NOKTON classic 35mm f/1.4"}, - {65535, "Voigtlander MACRO APO-LANTHAR 110mm f/2.5"}, - {65535, "Voigtlander COLOR-SKOPAR 21mm f/3.5 Aspherical"}, - {65535, "Zeiss Touit 12mm f/2.8"}, - {65535, "Zeiss Touit 32mm f/1.8"}, - {65535, "Zeiss Touit 50mm f/2.8 Macro"}, - {65535, "Zeiss Batis 25mm f/2"}, - {65535, "Zeiss Batis 85mm f/1.8"}, - {65535, "Zeiss Batis 18mm f/2.8"}, - {65535, "Zeiss Batis 135mm f/2.8"}, - {65535, "Zeiss Batis 40mm f/2 CF"}, - {65535, "Zeiss Loxia 50mm f/2"}, - {65535, "Zeiss Loxia 35mm f/2"}, - {65535, "Zeiss Loxia 21mm f/2.8"}, - {65535, "Zeiss Loxia 85mm f/2.4"}, - {65535, "Zeiss Loxia 25mm f/2.4"}, {65535, "Arax MC 35mm f/2.8 Tilt+Shift"}, {65535, "Arax MC 80mm f/2.8 Tilt+Shift"}, {65535, "Zenitar MF 16mm f/2.8 Fisheye M42"}, {65535, "Samyang 500mm Mirror f/8.0"}, {65535, "Pentacon Auto 135mm f/2.8"}, {65535, "Pentacon Auto 29mm f/2.8"}, - {65535, "Helios 44-2 58mm f/2.0"}, + {65535, "Helios 44-2 58mm f/2.0"} }; } @@ -1192,18 +1013,31 @@ public: }; SALensIDInterpreter saLensIDInterpreter; -class SALensID2Interpreter : public IntLensInterpreter< int > +class SALensID2Interpreter final : public IntLensInterpreter< int > { public: SALensID2Interpreter () { choices.insert (p_t (0, "Unknown E-mount lens or other lens")); + choices.insert (p_t (0, "Sigma 19mm f/2.8 [EX] DN")); + choices.insert (p_t (0, "Sigma 30mm f/2.8 [EX] DN")); + choices.insert (p_t (0, "Sigma 60mm f/2.8 DN")); + choices.insert (p_t (0, "Sony E 18-200mm f/3.5-6.3 OSS LE")); + choices.insert (p_t (0, "Tamron 18-200mm f/3.5-6.3 Di III VC")); + choices.insert (p_t (0, "Tokina FiRIN 20mm f/2 FE AF")); + choices.insert (p_t (0, "Tokina FiRIN 20mm f/2 FE MF")); + choices.insert (p_t (0, "Zeiss Touit 12mm f/2.8")); + choices.insert (p_t (0, "Zeiss Touit 32mm f/1.8")); + choices.insert (p_t (0, "Zeiss Touit 50mm f/2.8 Macro")); + choices.insert (p_t (0, "Zeiss Loxia 50mm f/2")); + choices.insert (p_t (0, "Zeiss Loxia 35mm f/2")); choices.insert (p_t (1, "Sony LA-EA1 or Sigma MC-11 Adapter")); choices.insert (p_t (2, "Sony LA-EA2 Adapter")); choices.insert (p_t (3, "Sony LA-EA3 Adapter")); choices.insert (p_t (6, "Sony LA-EA4 Adapter")); choices.insert (p_t (44, "Metabones Canon EF Smart Adapter")); choices.insert (p_t (78, "Metabones Canon EF Smart Adapter Mark III or Other Adapter")); + choices.insert (p_t (184, "Metabones Canon EF Speed Booster Ultra")); choices.insert (p_t (234, "Metabones Canon EF Smart Adapter Mark IV")); choices.insert (p_t (239, "Metabones Canon EF Speed Booster")); choices.insert (p_t (32784, "Sony E 16mm f/2.8")); @@ -1211,17 +1045,19 @@ public: choices.insert (p_t (32786, "Sony E 55-210mm f/4.5-6.3 OSS")); choices.insert (p_t (32787, "Sony E 18-200mm f/3.5-6.3 OSS")); choices.insert (p_t (32788, "Sony E 30mm f/3.5 Macro")); - choices.insert (p_t (32789, "Sony E 24mm f/1.8 ZA or Samyang AF 50mm f/1.4 FE")); - choices.insert (p_t (32789, "Samyang AF 50mm f/1.4 FE")); - choices.insert (p_t (32790, "Sony E 50mm f/1.8 OSS or Samyang AF 14mm f/2.8 FE")); - choices.insert (p_t (32790, "Samyang AF 14mm f/2.8 FE")); + choices.insert (p_t (32789, "Sony E 24mm f/1.8 ZA or Samyang AF 50mm f/1.4")); + choices.insert (p_t (32789, "Samyang AF 50mm f/1.4")); + choices.insert (p_t (32790, "Sony E 50mm f/1.8 OSS or Samyang AF 14mm f/2.8")); + choices.insert (p_t (32790, "Samyang AF 14mm f/2.8")); choices.insert (p_t (32791, "Sony E 16-70mm f/4 ZA OSS")); choices.insert (p_t (32792, "Sony E 10-18mm f/4 OSS")); choices.insert (p_t (32793, "Sony E PZ 16-50mm f/3.5-5.6 OSS")); - choices.insert (p_t (32794, "Sony FE 35mm f/2.8 ZA or Samyang AF 24mm f/2.8 FE")); - choices.insert (p_t (32794, "Samyang AF 24mm f/2.8 FE")); + choices.insert (p_t (32794, "Sony FE 35mm f/2.8 ZA or Samyang Lens")); + choices.insert (p_t (32794, "Samyang AF 24mm f/2.8")); + choices.insert (p_t (32794, "Samyang AF 35mm f/2.8")); choices.insert (p_t (32795, "Sony FE 24-70mm f/4 ZA OSS")); - choices.insert (p_t (32796, "Sony FE 85mm f/1.8")); + choices.insert (p_t (32796, "Sony FE 85mm f/1.8 or Viltrox PFU RBMH 85mm f/1.8")); + choices.insert (p_t (32796, "Viltrox PFU RBMH 85mm f/1.8")); choices.insert (p_t (32797, "Sony E 18-200mm f/3.5-6.3 OSS LE")); choices.insert (p_t (32798, "Sony E 20mm f/2.8")); choices.insert (p_t (32799, "Sony E 35mm f/1.8 OSS")); @@ -1245,7 +1081,8 @@ public: choices.insert (p_t (32820, "Sony E PZ 18-110mm f/4 G OSS")); choices.insert (p_t (32821, "Sony FE 24-70mm f/2.8 GM")); choices.insert (p_t (32822, "Sony FE 50mm f/1.4 ZA")); - choices.insert (p_t (32823, "Sony FE 85mm f/1.4 GM")); + choices.insert (p_t (32823, "Sony FE 85mm f/1.4 GM or Samyang AF 85mm f/1.4")); + choices.insert (p_t (32823, "Samyang AF 85mm f/1.4")); choices.insert (p_t (32824, "Sony FE 50mm f/1.8")); choices.insert (p_t (32826, "Sony FE 21mm f/2.8 (SEL28F20 + SEL075UWC)")); choices.insert (p_t (32827, "Sony FE 16mm f/3.5 Fisheye (SEL28F20 + SEL057FEC)")); @@ -1255,6 +1092,12 @@ public: choices.insert (p_t (32831, "Sony FE 16-35mm f/2.8 GM")); choices.insert (p_t (32848, "Sony FE 400mm f/2.8 GM OSS")); choices.insert (p_t (32849, "Sony E 18-135mm f/3.5-5.6 OSS")); + choices.insert (p_t (32850, "Sony FE 135mm f/1.8 GM")); + choices.insert (p_t (32851, "Sony FE 200-600mm f/5.6-6.3 G OSS")); + choices.insert (p_t (32852, "Sony FE 600mm f/4 GM OSS")); + choices.insert (p_t (32853, "Sony E 16-55mm f/2.8 G")); + choices.insert (p_t (32854, "Sony E 70-350mm f/4.5-6.3 G OSS")); + choices.insert (p_t (32858, "Sony FE 35mm f/1.8")); choices.insert (p_t (33072, "Sony FE 70-200mm f/2.8 GM OSS + 1.4X Teleconverter")); choices.insert (p_t (33073, "Sony FE 70-200mm f/2.8 GM OSS + 2X Teleconverter")); choices.insert (p_t (33076, "Sony FE 100mm f/2.8 STF GM OSS (macro mode)")); @@ -1262,6 +1105,10 @@ public: choices.insert (p_t (33078, "Sony FE 100-400mm f/4.5-5.6 GM OSS + 2X Teleconverter")); choices.insert (p_t (33079, "Sony FE 400mm f/2.8 GM OSS + 1.4X Teleconverter")); choices.insert (p_t (33080, "Sony FE 400mm f/2.8 GM OSS + 2X Teleconverter")); + choices.insert (p_t (33081, "Sony FE 200-600mm f/5.6-6.3 G OSS + 1.4X Teleconverter")); + choices.insert (p_t (33082, "Sony FE 200-600mm f/5.6-6.3 G OSS + 2X Teleconverter")); + choices.insert (p_t (33083, "Sony FE 600mm f/4 GM OSS + 1.4X Teleconverter")); + choices.insert (p_t (33084, "Sony FE 600mm f/4 GM OSS + 2X Teleconverter")); choices.insert (p_t (49201, "Zeiss Touit 12mm f/2.8")); choices.insert (p_t (49202, "Zeiss Touit 32mm f/1.8")); choices.insert (p_t (49203, "Zeiss Touit 50mm f/2.8 Macro")); @@ -1276,11 +1123,18 @@ public: choices.insert (p_t (49235, "Zeiss Loxia 85mm f/2.4")); choices.insert (p_t (49236, "Zeiss Loxia 25mm f/2.4")); choices.insert (p_t (49457, "Tamron 28-75mm f/2.8 Di III RXD")); + choices.insert (p_t (49458, "Tamron 17-28mm f/2.8 Di III RXD")); + choices.insert (p_t (49459, "Tamron 35mm f/2.8 Di III OSD M1:2")); + choices.insert (p_t (49460, "Tamron 24mm f/2.8 Di III OSD M1:2")); + choices.insert (p_t (49461, "Tamron 20mm f/2.8 Di III OSD M1:2")); + choices.insert (p_t (49712, "Tokina FiRIN 20mm f/2 FE AF")); + choices.insert (p_t (49713, "Tokina FiRIN 100mm f/2.8 FE MACRO")); choices.insert (p_t (50480, "Sigma 30mm f/1.4 DC DN | C")); choices.insert (p_t (50481, "Sigma 50mm f/1.4 DG HSM | A")); choices.insert (p_t (50482, "Sigma 18-300mm f/3.5-6.3 DC MACRO OS HSM | C + MC-11")); choices.insert (p_t (50483, "Sigma 18-35mm f/1.8 DC HSM | A + MC-11")); choices.insert (p_t (50484, "Sigma 24-35mm f/2 DG HSM | A + MC-11")); + choices.insert (p_t (50485, "Sigma 24mm f/1.4 DG HSM | A + MC-11")); choices.insert (p_t (50486, "Sigma 150-600mm f/5-6.3 DG OS HSM | C + MC-11")); choices.insert (p_t (50487, "Sigma 20mm f/1.4 DG HSM | A + MC-11")); choices.insert (p_t (50488, "Sigma 35mm f/1.4 DG HSM | A")); @@ -1294,8 +1148,12 @@ public: choices.insert (p_t (50503, "Sigma 16mm f/1.4 DC DN | C")); choices.insert (p_t (50507, "Sigma 105mm f/1.4 DG HSM | A")); choices.insert (p_t (50508, "Sigma 56mm f/1.4 DC DN | C")); - choices.insert (p_t (50512, "Sigma 70-200mm f/2.8 DG OS HSM | S")); + choices.insert (p_t (50512, "Sigma 70-200mm f/2.8 DG OS HSM | S + MC-11")); choices.insert (p_t (50513, "Sigma 70mm f/2.8 DG MACRO | A")); + choices.insert (p_t (50514, "Sigma 45mm f/2.8 DG DN | C")); + choices.insert (p_t (50515, "Sigma 35mm f/1.2 DG DN | A")); + choices.insert (p_t (50516, "Sigma 14-24mm f/2.8 DG DN | A")); + choices.insert (p_t (50517, "Sigma 24-70mm f/2.8 DG DN | A")); choices.insert (p_t (50992, "Voigtlander SUPER WIDE-HELIAR 15mm f/4.5 III")); choices.insert (p_t (50993, "Voigtlander HELIAR-HYPER WIDE 10mm f/5.6")); choices.insert (p_t (50994, "Voigtlander ULTRA WIDE-HELIAR 12mm f/5.6 III")); @@ -1304,9 +1162,15 @@ public: choices.insert (p_t (50997, "Voigtlander NOKTON classic 35mm f/1.4")); choices.insert (p_t (50998, "Voigtlander MACRO APO-LANTHAR 110mm f/2.5")); choices.insert (p_t (50999, "Voigtlander COLOR-SKOPAR 21mm f/3.5 Aspherical")); - choices.insert (p_t (51505, "Samyang AF 14mm f/2.8 FE or Samyang AF 35mm f/2.8 FE")); - choices.insert (p_t (51505, "Samyang AF 35mm f/2.8 FE")); + choices.insert (p_t (51000, "Voigtlander NOKTON 50mm f/1.2 Aspherical")); + choices.insert (p_t (51001, "Voigtlander NOKTON 21mm f/1.4 Aspherical")); + choices.insert (p_t (51002, "Voigtlander APO-LANTHAR 50mm f/2 Aspherical")); + choices.insert (p_t (51504, "Samyang AF 50mm f/1.4")); + choices.insert (p_t (51505, "Samyang AF 14mm f/2.8 or Samyang AF 35mm f/2.8")); + choices.insert (p_t (51505, "Samyang AF 35mm f/2.8")); choices.insert (p_t (51507, "Samyang AF 35mm f/1.4")); + choices.insert (p_t (51508, "Samyang AF 45mm f/1.8")); + choices.insert (p_t (51510, "Samyang AF 18mm f/2.8")); } std::string toString (const Tag* t) const override @@ -2252,7 +2116,7 @@ public: // Decode the value if (a && a != 254) { // 254 = 'Auto' for CameraSettings3, but we might say the same for CameraSettings & CameraSettings2 (?) - return int (expf ((double (a) / 8.f - 6.f) * logf (2.f)) * 100.f + 0.5f); + return std::exp((a / 8.f - 6.f) * std::log(2.f)) * 100.f + 0.5f; } else { return 0; } @@ -2635,6 +2499,4 @@ const TagAttrib sonyCameraSettingsAttribs3[] = { {-1, AC_DONTWRITE, 0, 0, 0, AUTO, "", NULL}};*/ } -#endif - diff --git a/rtexif/stdattribs.cc b/rtexif/stdattribs.cc index 8e076152d..be7a28a5c 100644 --- a/rtexif/stdattribs.cc +++ b/rtexif/stdattribs.cc @@ -17,8 +17,6 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . */ -#ifndef _STDATTRIBS_ -#define _STDATTRIBS_ #include #include @@ -927,5 +925,3 @@ const TagAttrib ifdAttribs[] = { { -1, AC_DONTWRITE, 0, nullptr, 0, AUTO, "", nullptr} }; } - -#endif diff --git a/rtgui/CMakeLists.txt b/rtgui/CMakeLists.txt index 4b21ce421..828151338 100644 --- a/rtgui/CMakeLists.txt +++ b/rtgui/CMakeLists.txt @@ -164,13 +164,13 @@ set(NONCLISOURCEFILES zoompanel.cc ) -include_directories(BEFORE "${CMAKE_CURRENT_BINARY_DIR}") +include_directories(BEFORE ${CMAKE_CURRENT_BINARY_DIR}) if(APPLE) find_package(MacIntegration REQUIRED) # At the time of writing CMake has no module finder for gtkmacintegration so here we have it hard-coded, if installed via macports it should be in /opt/local/... - set(EXTRA_LIB_RTGUI ${MacIntegration_LIBRARIES}) - set(EXTRA_INCDIR ${EXTRA_INCDIR} ${MacIntegration_INCLUDE_DIRS}) + set(EXTRA_LIB_RTGUI "${MacIntegration_LIBRARIES}") + set(EXTRA_INCDIR "${EXTRA_INCDIR}" "${MacIntegration_INCLUDE_DIRS}") endif() if(WIN32) @@ -236,16 +236,16 @@ else() endif() # Excluding libatomic needed by Clang/FreeBSD, #3636 -if(OPENMP_FOUND AND NOT APPLE AND NOT "${CMAKE_SYSTEM_NAME}" STREQUAL "FreeBSD") - set(EXTRA_LIB_RTGUI ${EXTRA_LIB_RTGUI} "atomic") +if(OPENMP_FOUND AND NOT APPLE AND NOT ${CMAKE_SYSTEM_NAME} STREQUAL "FreeBSD") + set(EXTRA_LIB_RTGUI "${EXTRA_LIB_RTGUI}" "atomic") endif() # Create config.h which defines where data are stored configure_file("${CMAKE_CURRENT_SOURCE_DIR}/config.h.in" "${CMAKE_CURRENT_BINARY_DIR}/config.h") # Create new executables targets -add_executable(rth ${EXTRA_SRC_NONCLI} ${NONCLISOURCEFILES}) -add_executable(rth-cli ${EXTRA_SRC_CLI} ${CLISOURCEFILES}) +add_executable(rth "${EXTRA_SRC_NONCLI}" "${NONCLISOURCEFILES}") +add_executable(rth-cli "${EXTRA_SRC_CLI}" "${CLISOURCEFILES}") # Add dependencies to executables targets add_dependencies(rth UpdateInfo) @@ -311,5 +311,5 @@ target_link_libraries(rth-cli rtengine ) # Install executables -install(TARGETS rth DESTINATION ${BINDIR}) -install(TARGETS rth-cli DESTINATION ${BINDIR}) +install(TARGETS rth DESTINATION "${BINDIR}") +install(TARGETS rth-cli DESTINATION "${BINDIR}") diff --git a/rtgui/addsetids.h b/rtgui/addsetids.h index 8e7833a33..6f68c6ae7 100644 --- a/rtgui/addsetids.h +++ b/rtgui/addsetids.h @@ -90,6 +90,7 @@ enum { ADDSET_WA_SKINPROTECT, ADDSET_WA_THRR, ADDSET_WA_THRRH, + ADDSET_WA_RADIUS, ADDSET_WA_THRES, ADDSET_WA_THRESHOLD, ADDSET_WA_THRESHOLD2, @@ -107,6 +108,8 @@ enum { ADDSET_WA_EDGEDETECTTHR, ADDSET_WA_EDGEDETECTTHR2, ADDSET_WA_TMRS, + ADDSET_WA_EDGS, + ADDSET_WA_SCALE, ADDSET_WA_GAMMA, ADDSET_RETI_STR, ADDSET_RETI_NEIGH, diff --git a/rtgui/adjuster.h b/rtgui/adjuster.h index 59250bc81..143268786 100644 --- a/rtgui/adjuster.h +++ b/rtgui/adjuster.h @@ -33,7 +33,7 @@ public: typedef double(*double2double_fun)(double val); -class Adjuster : public Gtk::Grid +class Adjuster final : public Gtk::Grid { protected: diff --git a/rtgui/batchqueueentry.h b/rtgui/batchqueueentry.h index c4cd48615..f06b65046 100644 --- a/rtgui/batchqueueentry.h +++ b/rtgui/batchqueueentry.h @@ -50,7 +50,7 @@ struct BatchQueueEntryIdleHelper { int pending; }; -class BatchQueueEntry : public ThumbBrowserEntryBase, public BQEntryUpdateListener, public rtengine::NonCopyable +class BatchQueueEntry final : public ThumbBrowserEntryBase, public BQEntryUpdateListener, public rtengine::NonCopyable { guint8* opreview; diff --git a/rtgui/batchtoolpanelcoord.cc b/rtgui/batchtoolpanelcoord.cc index f21d82f25..4462401be 100644 --- a/rtgui/batchtoolpanelcoord.cc +++ b/rtgui/batchtoolpanelcoord.cc @@ -171,7 +171,7 @@ void BatchToolPanelCoordinator::initSession () shadowshighlights->setAdjusterBehavior (false, false); dirpyrequalizer->setAdjusterBehavior (false, false, false); - wavelet->setAdjusterBehavior (false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false); + wavelet->setAdjusterBehavior (false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false); dirpyrdenoise->setAdjusterBehavior (false, false, false, false, false, false, false); bayerprocess->setAdjusterBehavior(false, false, false, false, false, false); xtransprocess->setAdjusterBehavior(false, false); @@ -219,7 +219,7 @@ void BatchToolPanelCoordinator::initSession () blackwhite->setAdjusterBehavior (options.baBehav[ADDSET_BLACKWHITE_HUES], options.baBehav[ADDSET_BLACKWHITE_GAMMA]); shadowshighlights->setAdjusterBehavior (options.baBehav[ADDSET_SH_HIGHLIGHTS], options.baBehav[ADDSET_SH_SHADOWS]); dirpyrequalizer->setAdjusterBehavior (options.baBehav[ADDSET_DIRPYREQ], options.baBehav[ADDSET_DIRPYREQ_THRESHOLD], options.baBehav[ADDSET_DIRPYREQ_SKINPROTECT]); - wavelet->setAdjusterBehavior (options.baBehav[ADDSET_WA], options.baBehav[ADDSET_WA_THRESHOLD], options.baBehav[ADDSET_WA_THRESHOLD2], options.baBehav[ADDSET_WA_THRES], options.baBehav[ADDSET_WA_CHRO], options.baBehav[ADDSET_WA_CHROMA], options.baBehav[ADDSET_WA_CONTRAST], options.baBehav[ADDSET_WA_SKINPROTECT], options.baBehav[ADDSET_WA_RESCHRO], options.baBehav[ADDSET_WA_TMRS], options.baBehav[ADDSET_WA_RESCON], options.baBehav[ADDSET_WA_RESCONH], options.baBehav[ADDSET_WA_THRR], options.baBehav[ADDSET_WA_THRRH], options.baBehav[ADDSET_WA_SKYPROTECT], options.baBehav[ADDSET_WA_EDGRAD], options.baBehav[ADDSET_WA_EDGVAL], options.baBehav[ADDSET_WA_STRENGTH], options.baBehav[ADDSET_WA_GAMMA], options.baBehav[ADDSET_WA_EDGEDETECT], options.baBehav[ADDSET_WA_EDGEDETECTTHR], options.baBehav[ADDSET_WA_EDGEDETECTTHR2]); + wavelet->setAdjusterBehavior (options.baBehav[ADDSET_WA], options.baBehav[ADDSET_WA_THRESHOLD], options.baBehav[ADDSET_WA_THRESHOLD2], options.baBehav[ADDSET_WA_THRES], options.baBehav[ADDSET_WA_CHRO], options.baBehav[ADDSET_WA_CHROMA], options.baBehav[ADDSET_WA_CONTRAST], options.baBehav[ADDSET_WA_SKINPROTECT], options.baBehav[ADDSET_WA_RESCHRO], options.baBehav[ADDSET_WA_TMRS], options.baBehav[ADDSET_WA_EDGS], options.baBehav[ADDSET_WA_SCALE], options.baBehav[ADDSET_WA_RESCON], options.baBehav[ADDSET_WA_RESCONH], options.baBehav[ADDSET_WA_THRR], options.baBehav[ADDSET_WA_THRRH], options.baBehav[ADDSET_WA_RADIUS], options.baBehav[ADDSET_WA_SKYPROTECT], options.baBehav[ADDSET_WA_EDGRAD], options.baBehav[ADDSET_WA_EDGVAL], options.baBehav[ADDSET_WA_STRENGTH], options.baBehav[ADDSET_WA_GAMMA], options.baBehav[ADDSET_WA_EDGEDETECT], options.baBehav[ADDSET_WA_EDGEDETECTTHR], options.baBehav[ADDSET_WA_EDGEDETECTTHR2]); dirpyrdenoise->setAdjusterBehavior (options.baBehav[ADDSET_DIRPYRDN_LUMA], options.baBehav[ADDSET_DIRPYRDN_LUMDET], options.baBehav[ADDSET_DIRPYRDN_CHROMA], options.baBehav[ADDSET_DIRPYRDN_CHROMARED], options.baBehav[ADDSET_DIRPYRDN_CHROMABLUE], options.baBehav[ADDSET_DIRPYRDN_GAMMA], options.baBehav[ADDSET_DIRPYRDN_PASSES]); bayerprocess->setAdjusterBehavior(options.baBehav[ADDSET_BAYER_FALSE_COLOR_SUPPRESSION], options.baBehav[ADDSET_BAYER_ITER], options.baBehav[ADDSET_BAYER_DUALDEMOZCONTRAST], options.baBehav[ADDSET_BAYER_PS_SIGMA], options.baBehav[ADDSET_BAYER_PS_SMOOTH], options.baBehav[ADDSET_BAYER_PS_EPERISO]); xtransprocess->setAdjusterBehavior(options.baBehav[ADDSET_BAYER_FALSE_COLOR_SUPPRESSION], options.baBehav[ADDSET_BAYER_DUALDEMOZCONTRAST]); @@ -341,8 +341,11 @@ void BatchToolPanelCoordinator::initSession () if (options.baBehav[ADDSET_WA_RESCONH]) { pparams.wavelet.resconH = 0; } if (options.baBehav[ADDSET_WA_RESCHRO]) { pparams.wavelet.reschro = 0; } if (options.baBehav[ADDSET_WA_TMRS]) { pparams.wavelet.tmrs = 0; } + if (options.baBehav[ADDSET_WA_EDGS]) { pparams.wavelet.edgs = 0; } + if (options.baBehav[ADDSET_WA_SCALE]) { pparams.wavelet.scale = 0; } if (options.baBehav[ADDSET_WA_THRR]) { pparams.wavelet.thr = 0; } if (options.baBehav[ADDSET_WA_THRRH]) { pparams.wavelet.thrH = 0; } + if (options.baBehav[ADDSET_WA_RADIUS]) { pparams.wavelet.radius = 0; } if (options.baBehav[ADDSET_WA_SKYPROTECT]) { pparams.wavelet.sky = 0; } if (options.baBehav[ADDSET_WA_EDGRAD]) { pparams.wavelet.edgrad = 0; } if (options.baBehav[ADDSET_WA_EDGVAL]) { pparams.wavelet.edgval = 0; } diff --git a/rtgui/batchtoolpanelcoord.h b/rtgui/batchtoolpanelcoord.h index 7a5fe77ed..ea11f97c8 100644 --- a/rtgui/batchtoolpanelcoord.h +++ b/rtgui/batchtoolpanelcoord.h @@ -28,7 +28,7 @@ class FilePanel; class Thumbnail; -class BatchToolPanelCoordinator : +class BatchToolPanelCoordinator final : public ToolPanelCoordinator, public FileSelectionChangeListener, public BatchPParamsChangeListener, diff --git a/rtgui/blackwhite.cc b/rtgui/blackwhite.cc index 596d99607..ea493d6e1 100644 --- a/rtgui/blackwhite.cc +++ b/rtgui/blackwhite.cc @@ -70,7 +70,7 @@ BlackWhite::BlackWhite (): FoldableToolPanel(this, "blackwhite", M("TP_BWMIX_LAB // -0.1 rad < Hue < 1.6 rad for (int i = 0; i < 7; i++) { - float x = float(i) * (1.0f / 6.0); + float x = float(i) * (1.0f / 6.f); Color::hsv2rgb01(x, 0.5f, 0.5f, R, G, B); bottomMilestones.push_back( GradientMilestone(double(x), double(R), double(G), double(B)) ); } @@ -1185,10 +1185,10 @@ void BlackWhite::updateRGBLabel () RGBLabels->set_text( Glib::ustring::compose(M("TP_BWMIX_RGBLABEL"), - Glib::ustring::format(std::fixed, std::setprecision(1), r * 100.), - Glib::ustring::format(std::fixed, std::setprecision(1), g * 100.), - Glib::ustring::format(std::fixed, std::setprecision(1), b * 100.), - Glib::ustring::format(std::fixed, std::setprecision(0), ceil(kcorrec * 100./*(r+g+b)*100.)*/))) + Glib::ustring::format(std::fixed, std::setprecision(1), r * 100.f), + Glib::ustring::format(std::fixed, std::setprecision(1), g * 100.f), + Glib::ustring::format(std::fixed, std::setprecision(1), b * 100.f), + Glib::ustring::format(std::fixed, std::setprecision(0), ceil(kcorrec * 100.f/*(r+g+b)*100.)*/))) ); // We have to update the RGB sliders too if preset values has been chosen diff --git a/rtgui/cachemanager.cc b/rtgui/cachemanager.cc index c37964e23..93dafc1ba 100644 --- a/rtgui/cachemanager.cc +++ b/rtgui/cachemanager.cc @@ -39,7 +39,7 @@ namespace { constexpr int cacheDirMode = 0777; -constexpr const char* cacheDirs[] = { "profiles", "images", "aehistograms", "embprofiles", "data" }; +constexpr const char* cacheDirs[] = { "profiles", "images", "embprofiles", "data" }; } @@ -59,9 +59,7 @@ void CacheManager::init () auto error = g_mkdir_with_parents (baseDir.c_str(), cacheDirMode); for (const auto& cacheDir : cacheDirs) { - if (strncmp(cacheDir, "aehistograms", 12)) { // don't create aehistograms folder. - error |= g_mkdir_with_parents (Glib::build_filename (baseDir, cacheDir).c_str(), cacheDirMode); - } + error |= g_mkdir_with_parents (Glib::build_filename (baseDir, cacheDir).c_str(), cacheDirMode); } if (error != 0 && rtengine::settings->verbose) { @@ -187,7 +185,6 @@ void CacheManager::renameEntry (const std::string& oldfilename, const std::strin auto error = g_rename (getCacheFileName ("profiles", oldfilename, paramFileExtension, oldmd5).c_str (), getCacheFileName ("profiles", newfilename, paramFileExtension, newmd5).c_str ()); error |= g_rename (getCacheFileName ("images", oldfilename, ".rtti", oldmd5).c_str (), getCacheFileName ("images", newfilename, ".rtti", newmd5).c_str ()); - error |= g_rename (getCacheFileName ("aehistograms", oldfilename, "", oldmd5).c_str (), getCacheFileName ("aehistograms", newfilename, "", newmd5).c_str ()); error |= g_rename (getCacheFileName ("embprofiles", oldfilename, ".icc", oldmd5).c_str (), getCacheFileName ("embprofiles", newfilename, ".icc", newmd5).c_str ()); error |= g_rename (getCacheFileName ("data", oldfilename, ".txt", oldmd5).c_str (), getCacheFileName ("data", newfilename, ".txt", newmd5).c_str ()); @@ -241,7 +238,6 @@ void CacheManager::clearImages () const deleteDir ("data"); deleteDir ("images"); - deleteDir ("aehistograms"); deleteDir ("embprofiles"); } @@ -277,7 +273,6 @@ void CacheManager::deleteFiles (const Glib::ustring& fname, const std::string& m } auto error = g_remove (getCacheFileName ("images", fname, ".rtti", md5).c_str ()); - error |= g_remove (getCacheFileName ("aehistograms", fname, "", md5).c_str ()); error |= g_remove (getCacheFileName ("embprofiles", fname, ".icc", md5).c_str ()); if (purgeData) { diff --git a/rtgui/colorappearance.cc b/rtgui/colorappearance.cc index 62f6eee2c..bdbe3de3a 100644 --- a/rtgui/colorappearance.cc +++ b/rtgui/colorappearance.cc @@ -25,6 +25,7 @@ #include "guiutils.h" #include "options.h" #include "rtimage.h" +#include "eventmapper.h" #include "../rtengine/color.h" #include "../rtengine/procparams.h" @@ -32,7 +33,7 @@ #define MINTEMP0 2000 //1200 #define MAXTEMP0 12000 //12000 -#define CENTERTEMP0 5000 +#define CENTERTEMP0 5003 #define MINGREEN0 0.8 #define MAXGREEN0 1.2 @@ -217,8 +218,17 @@ ColorAppearance::ColorAppearance () : FoldableToolPanel (this, "colorappearance" milestones.push_back ( GradientMilestone (0., 0., 0., 0.) ); milestones.push_back ( GradientMilestone (1., 1., 1., 1.) ); + auto m = ProcEventMapper::getInstance(); + Evcatpreset = m->newEvent(LUMINANCECURVE, "HISTORY_MSG_CAT02PRESET"); + EvCATAutotempout = m->newEvent(LUMINANCECURVE, "HISTORY_MSG_TEMPOUT"); + EvCATillum = m->newEvent(LUMINANCECURVE, "HISTORY_MSG_ILLUM"); + //preset button cat02 + presetcat02 = Gtk::manage (new Gtk::CheckButton (M ("TP_COLORAPP_PRESETCAT02"))); + presetcat02->set_tooltip_markup (M("TP_COLORAPP_PRESETCAT02_TIP")); + presetcat02conn = presetcat02->signal_toggled().connect( sigc::mem_fun(*this, &ColorAppearance::presetcat02pressed)); + pack_start (*presetcat02, Gtk::PACK_SHRINK); - // ------------------------ Process #1: Converting to CIECAM + // ----------------------- Process #1: Converting to CIECAM // Process 1 frame @@ -232,7 +242,7 @@ ColorAppearance::ColorAppearance () : FoldableToolPanel (this, "colorappearance" p1VBox = Gtk::manage ( new Gtk::VBox()); p1VBox->set_spacing (2); - degree = Gtk::manage (new Adjuster (M ("TP_COLORAPP_CIECAT_DEGREE"), 0., 100., 1., 100.)); + degree = Gtk::manage (new Adjuster (M ("TP_COLORAPP_CIECAT_DEGREE"), 0., 100., 1., 90.)); if (degree->delay < options.adjusterMaxDelay) { degree->delay = options.adjusterMaxDelay; @@ -276,6 +286,26 @@ ColorAppearance::ColorAppearance () : FoldableToolPanel (this, "colorappearance" wbmHBox->pack_start (*wbmodel); p1VBox->pack_start (*wbmHBox); + + Gtk::HBox* illumHBox = Gtk::manage (new Gtk::HBox ()); + illumHBox->set_spacing (2); + illumHBox->set_tooltip_markup (M ("TP_COLORAPP_ILLUM_TOOLTIP")); + Gtk::Label* illumLab = Gtk::manage (new Gtk::Label (M ("TP_COLORAPP_ILLUM") + ":")); + illumHBox->pack_start (*illumLab, Gtk::PACK_SHRINK); + illum = Gtk::manage (new MyComboBoxText ()); + illum->append (M ("TP_COLORAPP_ILA")); + illum->append (M ("TP_COLORAPP_IL41")); + illum->append (M ("TP_COLORAPP_IL50")); + illum->append (M ("TP_COLORAPP_IL55")); + illum->append (M ("TP_COLORAPP_IL60")); + illum->append (M ("TP_COLORAPP_IL65")); + illum->append (M ("TP_COLORAPP_IL75")); + illum->append (M ("TP_COLORAPP_ILFREE")); + + illum->set_active (0); + illumHBox->pack_start (*illum); + p1VBox->pack_start (*illumHBox); + Gtk::Image* itempL = Gtk::manage (new RTImage ("circle-blue-small.png")); Gtk::Image* itempR = Gtk::manage (new RTImage ("circle-yellow-small.png")); Gtk::Image* igreenL = Gtk::manage (new RTImage ("circle-magenta-small.png")); @@ -523,7 +553,7 @@ ColorAppearance::ColorAppearance () : FoldableToolPanel (this, "colorappearance" float R, G, B; for (int i = 0; i < 7; i++) { - float x = float (i) * (1.0f / 6.0); + float x = float (i) * (1.0f / 6.f); Color::hsv2rgb01 (x, 0.5f, 0.5f, R, G, B); shape3Milestones.push_back ( GradientMilestone (double (x), double (R), double (G), double (B)) ); } @@ -599,7 +629,7 @@ ColorAppearance::ColorAppearance () : FoldableToolPanel (this, "colorappearance" // Gtk::Image* iblueredL = Gtk::manage (new RTImage ("circle-blue-small.png")); // Gtk::Image* iblueredR = Gtk::manage (new RTImage ("circle-red-small.png")); - degreeout = Gtk::manage (new Adjuster (M ("TP_COLORAPP_CIECAT_DEGREE"), 0., 100., 1., 100.)); + degreeout = Gtk::manage (new Adjuster (M ("TP_COLORAPP_CIECAT_DEGREE"), 0., 100., 1., 90.)); if (degreeout->delay < options.adjusterMaxDelay) { degreeout->delay = options.adjusterMaxDelay; @@ -617,7 +647,9 @@ ColorAppearance::ColorAppearance () : FoldableToolPanel (this, "colorappearance" tempout = Gtk::manage (new Adjuster (M ("TP_WBALANCE_TEMPERATURE"), MINTEMP0, MAXTEMP0, 5, CENTERTEMP0, itempR1, itempL1, &wbSlider2Temp, &wbTemp2Slider)); greenout = Gtk::manage (new Adjuster (M ("TP_WBALANCE_GREEN"), MINGREEN0, MAXGREEN0, 0.001, 1.0, igreenR1, igreenL1)); ybout = Gtk::manage (new Adjuster (M ("TP_COLORAPP_MEANLUMINANCE"), 5, 90, 1, 18)); - tempout->set_tooltip_markup (M ("TP_COLORAPP_TEMP_TOOLTIP")); + tempout->set_tooltip_markup (M ("TP_COLORAPP_TEMP2_TOOLTIP")); + tempout->throwOnButtonRelease(); + tempout->addAutoButton (M ("TP_COLORAPP_TEMPOUT_TOOLTIP")); tempout->show(); greenout->show(); @@ -690,6 +722,7 @@ ColorAppearance::ColorAppearance () : FoldableToolPanel (this, "colorappearance" // surrconn = surrsource->signal_toggled().connect ( sigc::mem_fun (*this, &ColorAppearance::surrsource_toggled) ); wbmodelconn = wbmodel->signal_changed().connect ( sigc::mem_fun (*this, &ColorAppearance::wbmodelChanged) ); + illumconn = illum->signal_changed().connect ( sigc::mem_fun (*this, &ColorAppearance::illumChanged) ); algoconn = algo->signal_changed().connect ( sigc::mem_fun (*this, &ColorAppearance::algoChanged) ); surroundconn = surround->signal_changed().connect ( sigc::mem_fun (*this, &ColorAppearance::surroundChanged) ); surrsrcconn = surrsrc->signal_changed().connect ( sigc::mem_fun (*this, &ColorAppearance::surrsrcChanged) ); @@ -759,12 +792,14 @@ void ColorAppearance::neutral_pressed () qcontrast->resetValue (false); colorh->resetValue (false); tempout->resetValue (false); + tempout->setAutoValue (true); greenout->resetValue (false); ybout->resetValue (false); tempsc->resetValue (false); greensc->resetValue (false); badpixsl->resetValue (false); wbmodel->set_active (0); + illum->set_active (2); toneCurveMode->set_active (0); toneCurveMode2->set_active (0); toneCurveMode3->set_active (0); @@ -801,6 +836,7 @@ void ColorAppearance::read (const ProcParams* pp, const ParamsEdited* pedited) tcmodeconn.block (true); tcmode2conn.block (true); tcmode3conn.block (true); + presetcat02conn.block (true); shape->setCurve (pp->colorappearance.curve); shape2->setCurve (pp->colorappearance.curve2); shape3->setCurve (pp->colorappearance.curve3); @@ -808,7 +844,11 @@ void ColorAppearance::read (const ProcParams* pp, const ParamsEdited* pedited) toneCurveMode2->set_active (toUnderlying(pp->colorappearance.curveMode2)); toneCurveMode3->set_active (toUnderlying(pp->colorappearance.curveMode3)); curveMode3Changed(); // This will set the correct sensitive state of depending Adjusters + presetcat02->set_active(pp->colorappearance.presetcat02); + nexttemp = pp->wb.temperature; + nextgreen = 1.; //pp->wb.green; + if (pedited) { degree->setEditedState (pedited->colorappearance.degree ? Edited : UnEdited); degreeout->setEditedState (pedited->colorappearance.degreeout ? Edited : UnEdited); @@ -842,6 +882,7 @@ void ColorAppearance::read (const ProcParams* pp, const ParamsEdited* pedited) adapscen->setAutoInconsistent (multiImage && !pedited->colorappearance.autoadapscen); ybscen->setAutoInconsistent (multiImage && !pedited->colorappearance.autoybscen); set_inconsistent (multiImage && !pedited->colorappearance.enabled); + tempout->setAutoInconsistent (multiImage && !pedited->colorappearance.autotempout); shape->setUnChanged (!pedited->colorappearance.curve); shape2->setUnChanged (!pedited->colorappearance.curve2); @@ -858,6 +899,7 @@ void ColorAppearance::read (const ProcParams* pp, const ParamsEdited* pedited) if (!pedited->colorappearance.curveMode3) { toneCurveMode3->set_active (3); } + presetcat02->set_inconsistent(!pedited->colorappearance.presetcat02); } @@ -919,6 +961,32 @@ void ColorAppearance::read (const ProcParams* pp, const ParamsEdited* pedited) // Have to be manually called to handle initial state update wbmodelChanged(); + illumconn.block (true); + + if (pedited && !pedited->colorappearance.illum) { + illum->set_active (8); + } else if (pp->colorappearance.illum == "iA") { + illum->set_active (0); + } else if (pp->colorappearance.illum == "i41") { + illum->set_active (1); + } else if (pp->colorappearance.illum == "i50") { + illum->set_active (2); + } else if (pp->colorappearance.illum == "i55") { + illum->set_active (3); + } else if (pp->colorappearance.illum == "i60") { + illum->set_active (4); + } else if (pp->colorappearance.illum == "i65") { + illum->set_active (5); + } else if (pp->colorappearance.illum == "i75") { + illum->set_active (6); + } else if (pp->colorappearance.illum == "ifree") { + illum->set_active (7); + } + + illumconn.block (false); + // Have to be manually called to handle initial state update + illumChanged(); + algoconn.block (true); if (pedited && !pedited->colorappearance.algo) { @@ -967,6 +1035,7 @@ void ColorAppearance::read (const ProcParams* pp, const ParamsEdited* pedited) lastAutoAdapscen = pp->colorappearance.autoadapscen; lastAutoDegreeout = pp->colorappearance.autodegreeout; lastAutoybscen = pp->colorappearance.autoybscen; + lastAutotempout = pp->colorappearance.autotempout; degree->setValue (pp->colorappearance.degree); degree->setAutoValue (pp->colorappearance.autodegree); @@ -989,10 +1058,15 @@ void ColorAppearance::read (const ProcParams* pp, const ParamsEdited* pedited) qcontrast->setValue (pp->colorappearance.qcontrast); colorh->setValue (pp->colorappearance.colorh); tempout->setValue (pp->colorappearance.tempout); + tempout->setAutoValue (pp->colorappearance.autotempout); greenout->setValue (pp->colorappearance.greenout); ybout->setValue (pp->colorappearance.ybout); tempsc->setValue (pp->colorappearance.tempsc); greensc->setValue (pp->colorappearance.greensc); + presetcat02conn.block (true); + presetcat02->set_active (pp->colorappearance.presetcat02); + presetcat02conn.block (false); + lastpresetcat02 = pp->colorappearance.presetcat02; tcmode3conn.block (false); tcmode2conn.block (false); @@ -1041,10 +1115,12 @@ void ColorAppearance::write (ProcParams* pp, ParamsEdited* pedited) pp->colorappearance.curve2 = shape2->getCurve (); pp->colorappearance.curve3 = shape3->getCurve (); pp->colorappearance.tempout = tempout->getValue (); + pp->colorappearance.autotempout = tempout->getAutoValue (); pp->colorappearance.greenout = greenout->getValue (); pp->colorappearance.ybout = ybout->getValue (); pp->colorappearance.tempsc = tempsc->getValue (); pp->colorappearance.greensc = greensc->getValue (); + pp->colorappearance.presetcat02 = presetcat02->get_active(); int tcMode = toneCurveMode->get_active_row_number(); @@ -1096,6 +1172,7 @@ void ColorAppearance::write (ProcParams* pp, ParamsEdited* pedited) pedited->colorappearance.surround = surround->get_active_text() != M ("GENERAL_UNCHANGED"); pedited->colorappearance.surrsrc = surrsrc->get_active_text() != M ("GENERAL_UNCHANGED"); pedited->colorappearance.wbmodel = wbmodel->get_active_text() != M ("GENERAL_UNCHANGED"); + pedited->colorappearance.illum = illum->get_active_text() != M ("GENERAL_UNCHANGED"); pedited->colorappearance.algo = algo->get_active_text() != M ("GENERAL_UNCHANGED"); // pedited->colorappearance.surrsource = !surrsource->get_inconsistent(); pedited->colorappearance.gamut = !gamut->get_inconsistent(); @@ -1114,6 +1191,8 @@ void ColorAppearance::write (ProcParams* pp, ParamsEdited* pedited) pedited->colorappearance.ybout = ybout->getEditedState (); pedited->colorappearance.tempsc = tempsc->getEditedState (); pedited->colorappearance.greensc = greensc->getEditedState (); + pedited->colorappearance.presetcat02 = presetcat02->get_inconsistent (); + pedited->colorappearance.autotempout = !tempout->getAutoInconsistent(); } @@ -1144,7 +1223,24 @@ void ColorAppearance::write (ProcParams* pp, ParamsEdited* pedited) pp->colorappearance.wbmodel = "RawTCAT02"; } else if (wbmodel->get_active_row_number() == 2) { pp->colorappearance.wbmodel = "free"; + } + if (illum->get_active_row_number() == 0) { + pp->colorappearance.illum = "iA"; + } else if (illum->get_active_row_number() == 1) { + pp->colorappearance.illum = "i41"; + } else if (illum->get_active_row_number() == 2) { + pp->colorappearance.illum = "i50"; + } else if (illum->get_active_row_number() == 3) { + pp->colorappearance.illum = "i55"; + } else if (illum->get_active_row_number() == 4) { + pp->colorappearance.illum = "i60"; + } else if (illum->get_active_row_number() == 5) { + pp->colorappearance.illum = "i65"; + } else if (illum->get_active_row_number() == 6) { + pp->colorappearance.illum = "i75"; + } else if (illum->get_active_row_number() == 7) { + pp->colorappearance.illum = "ifree"; } if (algo->get_active_row_number() == 0) { @@ -1309,6 +1405,133 @@ void ColorAppearance::badpix_toggled () { } */ +void ColorAppearance::presetcat02pressed () +{ + if (presetcat02->get_active ()) { + disableListener(); + jlight->resetValue (false); + qbright->resetValue (false); + chroma->resetValue (false); + schroma->resetValue (false); + mchroma->resetValue (false); + rstprotection->resetValue (false); + contrast->resetValue (false); + qcontrast->resetValue (false); + colorh->resetValue (false); + tempout->resetValue (false); + greenout->resetValue (false); + ybout->resetValue (false); + tempsc->resetValue (false); + greensc->resetValue (false); + badpixsl->resetValue (false); + wbmodel->set_active (0); + illum->set_active (2); + toneCurveMode->set_active (0); + toneCurveMode2->set_active (0); + toneCurveMode3->set_active (0); + shape->reset(); + shape2->reset(); + shape3->reset(); + gamutconn.block (true); + gamut->set_active (true); + gamutconn.block (false); + degree->setAutoValue (true); + degree->resetValue (false); + degree->setValue(90); + adapscen->resetValue (false); + adapscen->setAutoValue (true); + degreeout->resetValue (false); + degreeout->setAutoValue (true); + ybscen->resetValue (false); + ybscen->setAutoValue (true); + surrsrc->set_active (0); + wbmodel->set_active (2); + tempsc->resetValue (false); + greensc->resetValue (false); + adapscen->setValue(400.); + ybscen->setValue(18); + surround->set_active (0); + adaplum->setValue(400.); + degreeout->setValue(90); + ybout->setValue(18); + tempout->setValue (nexttemp); + greenout->setValue (nextgreen); + enableListener(); + } else { + disableListener(); +/* jlight->resetValue (false); + qbright->resetValue (false); + chroma->resetValue (false); + schroma->resetValue (false); + mchroma->resetValue (false); + rstprotection->resetValue (false); + contrast->resetValue (false); + qcontrast->resetValue (false); + colorh->resetValue (false); + tempout->resetValue (false); + greenout->resetValue (false); + ybout->resetValue (false); + tempsc->resetValue (false); + greensc->resetValue (false); + badpixsl->resetValue (false); + wbmodel->set_active (0); + toneCurveMode->set_active (0); + toneCurveMode2->set_active (0); + toneCurveMode3->set_active (0); + shape->reset(); + shape2->reset(); + shape3->reset(); + gamutconn.block (true); + gamut->set_active (true); + gamutconn.block (false); +*/ + degree->setAutoValue (true); + degree->resetValue (false); + adapscen->resetValue (false); + adapscen->setAutoValue (true); + degreeout->resetValue (false); + degreeout->setAutoValue (true); + ybscen->resetValue (false); + ybscen->setAutoValue (true); + surrsrc->set_active (0); + wbmodel->set_active (0); + illum->set_active (2); + tempsc->resetValue (false); + greensc->resetValue (false); + adapscen->resetValue (false); + ybscen->resetValue (false); + surround->set_active (0); + adaplum->resetValue (false); + degreeout->resetValue (false); + ybout->resetValue (false); + tempout->resetValue (false); + greenout->resetValue (false); + enableListener(); + + } + if (batchMode) { + if (presetcat02->get_inconsistent()) { + presetcat02->set_inconsistent (false); + presetcat02conn.block (true); + presetcat02->set_active (false); + presetcat02conn.block (false); + } else if (lastpresetcat02) { + presetcat02->set_inconsistent (true); + } + + lastpresetcat02 = presetcat02->get_active (); + } + + if (listener) { + if (presetcat02->get_active ()) { + listener->panelChanged (Evcatpreset, M ("GENERAL_ENABLED")); + } else { + listener->panelChanged (Evcatpreset, M ("GENERAL_DISABLED")); + } + } + +} + void ColorAppearance::datacie_toggled () { @@ -1470,6 +1693,10 @@ void ColorAppearance::autoCamChanged (double ccam, double ccamout) void ColorAppearance::adapCamChanged (double cadap) { + if(presetcat02->get_active()){ + return; + } + idle_register.add( [this, cadap]() -> bool { @@ -1481,8 +1708,28 @@ void ColorAppearance::adapCamChanged (double cadap) ); } + +void ColorAppearance::wbCamChanged (double temp, double tin) +{ + + idle_register.add( + [this, temp, tin]() -> bool + { + disableListener(); + tempout->setValue(temp); + greenout->setValue(tin); + enableListener(); + return false; + } + ); +} + void ColorAppearance::ybCamChanged (int ybsc) { + if(presetcat02->get_active()){ + return; + } + idle_register.add( [this, ybsc]() -> bool { @@ -1602,7 +1849,16 @@ void ColorAppearance::adjusterAutoToggled(Adjuster* a) ybscen->setAutoInconsistent (true); } - lastAutoybscen = ybscen->getAutoValue(); + lastAutotempout = tempout->getAutoValue(); + + if (tempout->getAutoInconsistent()) { + tempout->setAutoInconsistent (false); + tempout->setAutoValue (false); + } else if (lastAutotempout) { + tempout->setAutoInconsistent (true); + } + + lastAutotempout = tempout->getAutoValue(); } @@ -1649,6 +1905,15 @@ void ColorAppearance::adjusterAutoToggled(Adjuster* a) } } + if (a == tempout) { + if (tempout->getAutoInconsistent()) { + listener->panelChanged (EvCATAutotempout, M ("GENERAL_UNCHANGED")); + } else if (tempout->getAutoValue()) { + listener->panelChanged (EvCATAutotempout, M ("GENERAL_ENABLED")); + } else { + listener->panelChanged (EvCATAutotempout, M ("GENERAL_DISABLED")); + } + } } } @@ -1688,13 +1953,17 @@ void ColorAppearance::surroundChanged () void ColorAppearance::wbmodelChanged () { if (wbmodel->get_active_row_number() == 0 || wbmodel->get_active_row_number() == 1) { + illum->hide(); tempsc->hide(); greensc->hide(); + tempsc->setValue (5003); + greensc->setValue (1); } if (wbmodel->get_active_row_number() == 2) { tempsc->show(); greensc->show(); + illum->show(); } if (listener && (multiImage || getEnabled()) ) { @@ -1702,6 +1971,47 @@ void ColorAppearance::wbmodelChanged () } } +void ColorAppearance::illumChanged () +{ + if (illum->get_active_row_number() == 0) { + tempsc->setValue (2856); + tempsc->set_sensitive(false); + greensc->set_sensitive(false); + } else if (illum->get_active_row_number() == 1) { + tempsc->setValue (4100); + tempsc->set_sensitive(false); + greensc->set_sensitive(false); + } else if (illum->get_active_row_number() == 2) { + tempsc->setValue (5003); + tempsc->set_sensitive(false); + greensc->set_sensitive(false); + } else if (illum->get_active_row_number() == 3) { + tempsc->setValue (5503); + tempsc->set_sensitive(false); + greensc->set_sensitive(false); + } else if (illum->get_active_row_number() == 4) { + tempsc->setValue (6000); + tempsc->set_sensitive(false); + greensc->set_sensitive(false); + } else if (illum->get_active_row_number() == 5) { + tempsc->setValue (6504); + tempsc->set_sensitive(false); + greensc->set_sensitive(false); + } else if (illum->get_active_row_number() == 6) { + tempsc->setValue (7504); + tempsc->set_sensitive(false); + greensc->set_sensitive(false); + } else if (illum->get_active_row_number() == 7) { + tempsc->set_sensitive(true); + greensc->set_sensitive(true); + } + + if (listener && (multiImage || getEnabled()) ) { + listener->panelChanged (EvCATillum, illum->get_active_text ()); + } +} + + void ColorAppearance::algoChanged () { @@ -1804,6 +2114,7 @@ void ColorAppearance::setBatchMode (bool batchMode) surround->append (M ("GENERAL_UNCHANGED")); surrsrc->append (M ("GENERAL_UNCHANGED")); wbmodel->append (M ("GENERAL_UNCHANGED")); + illum->append (M ("GENERAL_UNCHANGED")); algo->append (M ("GENERAL_UNCHANGED")); toneCurveMode->append (M ("GENERAL_UNCHANGED")); toneCurveMode2->append (M ("GENERAL_UNCHANGED")); diff --git a/rtgui/colorappearance.h b/rtgui/colorappearance.h index c42bca774..c326b06f9 100644 --- a/rtgui/colorappearance.h +++ b/rtgui/colorappearance.h @@ -53,6 +53,7 @@ public: void surroundChanged (); void surrsrcChanged (); void wbmodelChanged (); + void illumChanged (); void algoChanged (); void surrsource_toggled (); void gamut_toggled (); @@ -63,10 +64,11 @@ public: void autoCamChanged (double ccam, double ccamout) override; bool autoCamComputed_ (); void adapCamChanged (double cadap) override; + void wbCamChanged(double tem, double tin) override; bool adapCamComputed_ (); void ybCamChanged (int yb) override; bool ybCamComputed_ (); - + void presetcat02pressed (); void curveChanged (CurveEditor* ce) override; void curveMode1Changed (); bool curveMode1Changed_ (); @@ -99,6 +101,9 @@ public: void writeOptions (std::vector &tpOpen); private: + rtengine::ProcEvent Evcatpreset; + rtengine::ProcEvent EvCATAutotempout; + rtengine::ProcEvent EvCATillum; bool bgTTipQuery (int x, int y, bool keyboard_tooltip, const Glib::RefPtr& tooltip); bool srTTipQuery (int x, int y, bool keyboard_tooltip, const Glib::RefPtr& tooltip); void foldAllButMe (GdkEventButton* event, MyExpander *expander); @@ -143,6 +148,9 @@ private: Gtk::CheckButton* tonecie; // Gtk::CheckButton* sharpcie; Gtk::Button* neutral; + Gtk::CheckButton* presetcat02; + sigc::connection presetcat02conn; + MyComboBoxText* surrsrc; sigc::connection surrsrcconn; @@ -150,6 +158,8 @@ private: sigc::connection surroundconn; MyComboBoxText* wbmodel; sigc::connection wbmodelconn; + MyComboBoxText* illum; + sigc::connection illumconn; MyComboBoxText* algo; sigc::connection algoconn; sigc::connection surrconn; @@ -168,10 +178,14 @@ private: bool lastAutoAdapscen; bool lastAutoDegreeout; bool lastAutoybscen; + bool lastAutotempout; bool lastsurr; bool lastgamut; bool lastdatacie; bool lasttonecie; + bool lastpresetcat02; + double nexttemp; + double nextgreen; IdleRegister idle_register; }; diff --git a/rtgui/coloredbar.h b/rtgui/coloredbar.h index 6cc121cd5..69cfa47d1 100644 --- a/rtgui/coloredbar.h +++ b/rtgui/coloredbar.h @@ -30,7 +30,7 @@ * the bar itself, i.e. use render_background (depending on its Gtk::Style) * */ -class ColoredBar : private BackBuffer, public ColorCaller +class ColoredBar final : private BackBuffer, public ColorCaller { private: diff --git a/rtgui/colortoning.cc b/rtgui/colortoning.cc index 59768a6ce..ddf917149 100644 --- a/rtgui/colortoning.cc +++ b/rtgui/colortoning.cc @@ -74,7 +74,7 @@ ColorToning::ColorToning () : FoldableToolPanel(this, "colortoning", M("TP_COLOR // whole hue range for (int i = 0; i < 7; i++) { float R, G, B; - float x = float(i) * (1.0f / 6.0); + float x = float(i) * (1.0f / 6.f); Color::hsv2rgb01(x, 0.5f, 0.5f, R, G, B); milestones.push_back( GradientMilestone(double(x), double(R), double(G), double(B)) ); } @@ -1203,11 +1203,11 @@ void ColorToning::colorForValue (double valX, double valY, enum ColorCaller::Ele // the strength applied to the current hue double strength, hue; hlColSat->getValue(strength, hue); - Color::hsv2rgb01(hue / 360.f, 1.f, 1.f, R, G, B); + Color::hsv2rgb01(hue / 360.0, 1.f, 1.f, R, G, B); const double gray = 0.46; - R = (gray * (1.0 - valX)) + R * valX; - G = (gray * (1.0 - valX)) + G * valX; - B = (gray * (1.0 - valX)) + B * valX; + R = (gray * (1.0 - valX)) + static_cast(R) * valX; + G = (gray * (1.0 - valX)) + static_cast(G) * valX; + B = (gray * (1.0 - valX)) + static_cast(B) * valX; } } else if (callerId == 3) { // Slider 2 background if (valY <= 0.5) @@ -1218,17 +1218,17 @@ void ColorToning::colorForValue (double valX, double valY, enum ColorCaller::Ele // the strength applied to the current hue double strength, hue; shadowsColSat->getValue(strength, hue); - Color::hsv2rgb01(hue / 360.f, 1.f, 1.f, R, G, B); + Color::hsv2rgb01(hue / 360.0, 1.f, 1.f, R, G, B); const double gray = 0.46; - R = (gray * (1.0 - valX)) + R * valX; - G = (gray * (1.0 - valX)) + G * valX; - B = (gray * (1.0 - valX)) + B * valX; + R = (gray * (1.0 - valX)) + static_cast(R) * valX; + G = (gray * (1.0 - valX)) + static_cast(G) * valX; + B = (gray * (1.0 - valX)) + static_cast(B) * valX; } } else if (callerId == 4) { // color curve vertical and horizontal crosshair Color::hsv2rgb01(float(valY), 1.0f, 0.5f, R, G, B); } else if (callerId == ID_LABREGION_HUE) { // TODO - float x = valX - 1.f/6.f; + float x = valX - 1.0/6.0; if (x < 0.f) { x += 1.f; } diff --git a/rtgui/config.h.in b/rtgui/config.h.in index 95217b689..558c25f76 100644 --- a/rtgui/config.h.in +++ b/rtgui/config.h.in @@ -22,10 +22,19 @@ #cmakedefine BUILD_BUNDLE #cmakedefine HAVE_UNALIGNED_MALLOC + +#ifdef __APPLE__ +#define DATA_SEARCH_PATH "/Applications/RawTherapee.app/Contents/Resources/share" +#define DOC_SEARCH_PATH "/Applications/RawTherapee.app/Contents/Resources" +#define CREDITS_SEARCH_PATH "/Applications/RawTherapee.app/Contents/Resources" +#define LICENCE_SEARCH_PATH "/Applications/RawTherapee.app/Contents/Resources" +#define LENSFUN_DB_PATH "${LENSFUNDBDIR}" +#else #define DATA_SEARCH_PATH "${DATADIR}" #define DOC_SEARCH_PATH "${DOCDIR}" #define CREDITS_SEARCH_PATH "${CREDITSDIR}" #define LICENCE_SEARCH_PATH "${LICENCEDIR}" #define LENSFUN_DB_PATH "${LENSFUNDBDIR}" +#endif #endif diff --git a/rtgui/coordinateadjuster.cc b/rtgui/coordinateadjuster.cc index ebf36b7e7..57190cf63 100644 --- a/rtgui/coordinateadjuster.cc +++ b/rtgui/coordinateadjuster.cc @@ -69,14 +69,14 @@ void CoordinateAdjuster::AxisAdjuster::setValue(double newValue) { float range = rangeUpperBound - rangeLowerBound; spinButtonConn.block(true); - spinButton->set_value(newValue * range + rangeLowerBound); + spinButton->set_value(static_cast(newValue) * range + rangeLowerBound); spinButtonConn.block(false); } void CoordinateAdjuster::AxisAdjuster::valueChanged() { float range = rangeUpperBound - rangeLowerBound; - parent->updatePos(idx, (spinButton->get_value() - rangeLowerBound) / range); + parent->updatePos(idx, (static_cast(spinButton->get_value()) - rangeLowerBound) / range); } CoordinateAdjuster::CoordinateAdjuster(CoordinateProvider *provider, CurveEditorSubGroup *parent, const std::vector &axis) @@ -171,7 +171,7 @@ void CoordinateAdjuster::startNumericalAdjustment(const std::vector Gtk::SpinButton *currSpinButton = axisAdjusters.at(i)->spinButton; currSpinButton->set_sensitive(true); float range = axisAdjusters.at(i)->rangeUpperBound - axisAdjusters.at(i)->rangeLowerBound; - currSpinButton->set_range(newBoundaries.at(i).minVal * range + axisAdjusters.at(i)->rangeLowerBound, newBoundaries.at(i).maxVal * range + axisAdjusters.at(i)->rangeLowerBound); + currSpinButton->set_range(newBoundaries.at(i).minVal * static_cast(range) + static_cast(axisAdjusters.at(i)->rangeLowerBound), newBoundaries.at(i).maxVal * static_cast(range) + static_cast(axisAdjusters.at(i)->rangeLowerBound)); } axisAdjusters.at(0)->spinButton->grab_focus(); @@ -200,7 +200,7 @@ void CoordinateAdjuster::switchAdjustedPoint(std::vector &pos, const std // ...narrow the range to the new interval float range = axisAdjusters.at(i)->rangeUpperBound - axisAdjusters.at(i)->rangeLowerBound; - currAxis->spinButton->set_range(newBoundaries.at(i).minVal * range + axisAdjusters.at(i)->rangeLowerBound, newBoundaries.at(i).maxVal * range + axisAdjusters.at(i)->rangeLowerBound); + currAxis->spinButton->set_range(newBoundaries.at(i).minVal * static_cast(range) + static_cast(axisAdjusters.at(i)->rangeLowerBound), newBoundaries.at(i).maxVal * static_cast(range) + static_cast(axisAdjusters.at(i)->rangeLowerBound)); // enable events currAxis->spinButtonConn.block(false); diff --git a/rtgui/coordinateadjuster.h b/rtgui/coordinateadjuster.h index 70fe42233..24edc707a 100644 --- a/rtgui/coordinateadjuster.h +++ b/rtgui/coordinateadjuster.h @@ -69,7 +69,7 @@ public: * * The position of the Axis in the vector will be used in the communication between the Adjuster and the Provider to identify the Axis */ -class CoordinateAdjuster : public Gtk::FlowBox +class CoordinateAdjuster final : public Gtk::FlowBox { public: diff --git a/rtgui/crop.cc b/rtgui/crop.cc index 3bdcf14cf..48d1e09af 100644 --- a/rtgui/crop.cc +++ b/rtgui/crop.cc @@ -16,6 +16,8 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . */ +#include + #include "crop.h" #include "options.h" @@ -46,39 +48,82 @@ inline void get_custom_ratio(int w, int h, double &rw, double &rh) } // namespace +class Crop::CropRatios final +{ +public: + CropRatios() : + ratios{ + {M("GENERAL_ASIMAGE"), 0.0}, + {M("GENERAL_CURRENT"), -1.0}, + {"3:2", 3.0 / 2.0}, // L1.5, P0.666... + {"4:3", 4.0 / 3.0}, // L1.333..., P0.75 + {"16:9", 16.0 / 9.0}, // L1.777..., P0.5625 + {"16:10", 16.0 / 10.0}, // L1.6, P0.625 + {"1:1", 1.0 / 1.0}, // L1, P1 + {"2:1", 2.0 / 1.0}, // L2, P0.5 + {"3:1", 3.0 / 1.0}, // L3, P0.333... + {"4:1", 4.0 / 1.0}, // L4, P0.25 + {"5:1", 5.0 / 1.0}, // L5, P0.2 + {"6:1", 6.0 / 1.0}, // L6, P0.1666... + {"7:1", 7.0 / 1.0}, // L7, P0.142... + {"4:5", 4.0 / 5.0}, // L1.25, P0.8 + {"5:7", 5.0 / 7.0}, // L1.4, P0.714... + {"6:7", 6.0 / 7.0}, // L1.166..., P0.857... + {"6:17", 6.0 / 17.0}, // L2.833..., P0.352... + {"24:65 - XPAN", 24.0 / 65.0}, // L2.708..., P0.369... + {"1.414 - DIN EN ISO 216", 1.414}, // L1.414, P0.707... + {"3.5:5", 3.5 / 5.0}, // L1.428..., P0.7 + {"8.5:11 - US Letter", 8.5 / 11.0}, // L1.294..., P0.772... + {"9.5:12", 9.5 / 12.0}, // L1.263..., P0.791... + {"10:12", 10.0 / 12.0}, // L1.2, P0.833... + {"11:14", 11.0 / 14.0}, // L1.272..., P0.785... + {"11:17 - Tabloid", 11.0 / 17.0}, // L1.545..., P0.647... + {"13:19", 13.0 / 19.0}, // L1.461..., P0.684... + {"17:22", 17.0 / 22.0}, // L1.294..., P0.772... + {"45:35 - ePassport", 45.0 / 35.0}, // L1.285,... P0.777... + {"64:27", 64.0 / 27.0}, // L2.370..., P0.421... + } + { + } + + std::vector getLabels() const + { + std::vector res; + + res.reserve(ratios.size()); + + for (const auto& ratio : ratios) { + res.push_back(ratio.label); + } + + return res; + } + + double getValue(std::size_t index) const + { + return + index < ratios.size() + ? ratios[index].value + : ratios[0].value; + } + + void updateCurrentRatio(double value) + { + ratios[1].value = value; + } + +private: + struct CropRatio { + Glib::ustring label; + double value; + }; + + std::vector ratios; +}; + Crop::Crop(): FoldableToolPanel(this, "crop", M("TP_CROP_LABEL"), false, true), - crop_ratios{ - {M("GENERAL_ASIMAGE"), 0.0}, - {M("GENERAL_CURRENT"), -1.0}, - {"3:2", 3.0 / 2.0}, // L1.5, P0.666... - {"4:3", 4.0 / 3.0}, // L1.333..., P0.75 - {"16:9", 16.0 / 9.0}, // L1.777..., P0.5625 - {"16:10", 16.0 / 10.0}, // L1.6, P0.625 - {"1:1", 1.0 / 1.0}, // L1, P1 - {"2:1", 2.0 / 1.0}, // L2, P0.5 - {"3:1", 3.0 / 1.0}, // L3, P0.333... - {"4:1", 4.0 / 1.0}, // L4, P0.25 - {"5:1", 5.0 / 1.0}, // L5, P0.2 - {"6:1", 6.0 / 1.0}, // L6, P0.1666... - {"7:1", 7.0 / 1.0}, // L7, P0.142... - {"4:5", 4.0 / 5.0}, // L1.25, P0.8 - {"5:7", 5.0 / 7.0}, // L1.4, P0.714... - {"6:7", 6.0 / 7.0}, // L1.166..., P0.857... - {"6:17", 6.0 / 17.0}, // L2.833..., P0.352... - {"24:65 - XPAN", 24.0 / 65.0}, // L2.708..., P0.369... - {"1.414 - DIN EN ISO 216", 1.414}, // L1.414, P0.707... - {"3.5:5", 3.5 / 5.0}, // L1.428..., P0.7 - {"8.5:11 - US Letter", 8.5 / 11.0}, // L1.294..., P0.772... - {"9.5:12", 9.5 / 12.0}, // L1.263..., P0.791... - {"10:12", 10.0 / 12.0}, // L1.2, P0.833... - {"11:14", 11.0 / 14.0}, // L1.272..., P0.785... - {"11:17 - Tabloid", 11.0 / 17.0}, // L1.545..., P0.647... - {"13:19", 13.0 / 19.0}, // L1.461..., P0.684... - {"17:22", 17.0 / 22.0}, // L1.294..., P0.772... - {"45:35 - ePassport", 45.0 / 35.0}, // L1.285,... P0.777... - {"64:27", 64.0 / 27.0}, // L2.370..., P0.421... - }, + crop_ratios(new CropRatios), opt(0), wDirty(true), hDirty(true), @@ -229,8 +274,8 @@ Crop::Crop(): // ppigrid END // Populate the combobox - for (const auto& crop_ratio : crop_ratios) { - ratio->append (crop_ratio.label); + for (const auto& label : crop_ratios->getLabels()) { + ratio->append (label); } ratio->set_active (0); @@ -354,7 +399,10 @@ void Crop::read (const ProcParams* pp, const ParamsEdited* pedited) setDimensions (pp->crop.x + pp->crop.w, pp->crop.y + pp->crop.h); } - const bool flip_orientation = pp->crop.fixratio && crop_ratios[ratio->get_active_row_number()].value > 0 && crop_ratios[ratio->get_active_row_number()].value < 1.0; + const bool flip_orientation = + pp->crop.fixratio + && crop_ratios->getValue(ratio->get_active_row_number()) > 0 + && crop_ratios->getValue(ratio->get_active_row_number()) < 1.0; if (pp->crop.orientation == "Landscape") { orientation->set_active (flip_orientation ? 1 : 0); @@ -469,7 +517,10 @@ void Crop::write (ProcParams* pp, ParamsEdited* pedited) } // for historical reasons we store orientation different if ratio is written as 2:3 instead of 3:2, but in GUI 'landscape' is always long side horizontal regardless of the ratio is written short or long side first. - const bool flip_orientation = fixr->get_active() && crop_ratios[ratio->get_active_row_number()].value > 0 && crop_ratios[ratio->get_active_row_number()].value < 1.0; + const bool flip_orientation = + fixr->get_active() + && crop_ratios->getValue(ratio->get_active_row_number()) > 0 + && crop_ratios->getValue(ratio->get_active_row_number()) < 1.0; if (orientation->get_active_row_number() == 0) { pp->crop.orientation = flip_orientation ? "Portrait" : "Landscape"; @@ -561,6 +612,11 @@ void Crop::doresetCrop () yDirty = true; wDirty = true; hDirty = true; + + // Reset ratio, ratio lock and orientation as well + ratio->set_active(0); + orientation->set_active(2); + fixr->set_active(true); int X = 0; int Y = 0; @@ -1006,7 +1062,7 @@ void Crop::cropWidth1Resized (int &X, int &Y, int &W, int &H, float custom_ratio } if (fixr->get_active() || custom_ratio > 0) { - double r = custom_ratio > 0 ? custom_ratio : getRatio(); + double r = custom_ratio > 0.f ? custom_ratio : static_cast(getRatio()); H = (int)round(W / r); int Hmax = min(ny + nh, maxh - ny); @@ -1053,7 +1109,7 @@ void Crop::cropWidth2Resized (int &X, int &Y, int &W, int &H, float custom_ratio } if (fixr->get_active() || custom_ratio > 0) { - double r = custom_ratio > 0 ? custom_ratio : getRatio(); + double r = custom_ratio > 0 ? custom_ratio : static_cast(getRatio()); H = (int)round(W / r); int Hmax = min(ny + nh, maxh - ny); @@ -1101,7 +1157,7 @@ void Crop::cropHeight1Resized (int &X, int &Y, int &W, int &H, float custom_rati } if (fixr->get_active() || custom_ratio > 0) { - double r = custom_ratio > 0 ? custom_ratio : getRatio(); + double r = custom_ratio > 0 ? custom_ratio : static_cast(getRatio()); W = (int)round(H * r); int Wmax = min(nx + nw, maxw - nx); @@ -1148,7 +1204,7 @@ void Crop::cropHeight2Resized (int &X, int &Y, int &W, int &H, float custom_rati } if (fixr->get_active() || custom_ratio > 0) { - double r = custom_ratio > 0 ? custom_ratio : getRatio(); + double r = custom_ratio > 0 ? custom_ratio : static_cast(getRatio()); W = (int)round(H * r); int Wmax = min(nx + nw, maxw - nx); @@ -1205,7 +1261,7 @@ void Crop::cropTopLeftResized (int &X, int &Y, int &W, int &H, float custom_rati } if (fixr->get_active() || custom_ratio > 0) { - double r = custom_ratio > 0 ? custom_ratio : getRatio(); + double r = custom_ratio > 0 ? custom_ratio : static_cast(getRatio()); W = (int)round(H * r); if (W > oldXR) { @@ -1252,7 +1308,7 @@ void Crop::cropTopRightResized (int &X, int &Y, int &W, int &H, float custom_rat } if (fixr->get_active() || custom_ratio > 0) { - double r = custom_ratio > 0 ? custom_ratio : getRatio(); + double r = custom_ratio > 0 ? custom_ratio : static_cast(getRatio()); W = (int)round(H * r); if (W > maxw - nx) { @@ -1298,7 +1354,7 @@ void Crop::cropBottomLeftResized (int &X, int &Y, int &W, int &H, float custom_r } if (fixr->get_active() || custom_ratio > 0) { - double r = custom_ratio > 0 ? custom_ratio : getRatio(); + double r = custom_ratio > 0 ? custom_ratio : static_cast(getRatio()); W = (int)round(H * r); if (W > oldXR) { @@ -1342,7 +1398,7 @@ void Crop::cropBottomRightResized (int &X, int &Y, int &W, int &H, float custom_ } if (fixr->get_active() || custom_ratio > 0) { - double r = custom_ratio > 0 ? custom_ratio : getRatio(); + double r = custom_ratio > 0 ? custom_ratio : static_cast(getRatio()); W = (int)round(H * r); if (W > maxw - nx) { @@ -1501,7 +1557,7 @@ double Crop::getRatio () const return r; } - r = crop_ratios[ratio->get_active_row_number()].value; + r = crop_ratios->getValue(ratio->get_active_row_number()); if (!r) { r = maxh <= maxw ? float(maxh)/float(maxw) : float(maxw)/float(maxh); } @@ -1539,5 +1595,5 @@ void Crop::updateCurrentRatio() double rw, rh; get_custom_ratio(w->get_value(), h->get_value(), rw, rh); customRatioLabel->set_text(Glib::ustring::compose("%1:%2", rw, rh)); - crop_ratios[1].value = double(w->get_value())/double(h->get_value()); + crop_ratios->updateCurrentRatio(static_cast(w->get_value()) / static_cast(h->get_value())); } diff --git a/rtgui/crop.h b/rtgui/crop.h index b9221a803..c6636b917 100644 --- a/rtgui/crop.h +++ b/rtgui/crop.h @@ -18,7 +18,7 @@ */ #pragma once -#include +#include #include @@ -91,16 +91,13 @@ public: void rotateCrop (int deg, bool hflip, bool vflip); private: - struct CropRatio { - Glib::ustring label; - double value; - }; - - std::vector crop_ratios; + class CropRatios; void adjustCropToRatio(); void updateCurrentRatio(); + const std::unique_ptr crop_ratios; + Gtk::CheckButton* fixr; MyComboBoxText* ratio; MyComboBoxText* orientation; diff --git a/rtgui/cropwindow.cc b/rtgui/cropwindow.cc index 0a9b81112..d87876cec 100644 --- a/rtgui/cropwindow.cc +++ b/rtgui/cropwindow.cc @@ -37,6 +37,7 @@ #include "rtsurface.h" #include "../rtengine/dcrop.h" +#include "../rtengine/imagesource.h" #include "../rtengine/procparams.h" #include "../rtengine/rt_math.h" @@ -123,7 +124,7 @@ void CropWindow::initZoomSteps() zoomSteps.push_back(ZoomStep(" 8%", 1.0/12.0, 120, true)); char lbl[64]; for (int s = 100; s >= 11; --s) { - float z = 10./float(s); + float z = 10.f / s; sprintf(lbl, "% 2d%%", int(z * 100)); bool is_major = (s == s/10 * 10); zoomSteps.push_back(ZoomStep(lbl, z, s, is_major)); @@ -294,7 +295,7 @@ void CropWindow::flawnOver (bool isFlawnOver) void CropWindow::scroll (int state, GdkScrollDirection direction, int x, int y, double deltaX, double deltaY) { double delta = 0.0; - if (abs(deltaX) > abs(deltaY)) { + if (std::fabs(deltaX) > std::fabs(deltaY)) { delta = deltaX; } else { delta = deltaY; @@ -303,7 +304,7 @@ void CropWindow::scroll (int state, GdkScrollDirection direction, int x, int y, if (direction == GDK_SCROLL_SMOOTH) { scrollAccum += delta; //Only change zoom level if we've accumulated +/- 1.0 of deltas. This conditional handles the previous delta=0.0 case - if (abs(scrollAccum) < 1.0) { + if (std::fabs(scrollAccum) < 1.0) { return; } } diff --git a/rtgui/cropwindow.h b/rtgui/cropwindow.h index 491124ad5..623653d2d 100644 --- a/rtgui/cropwindow.h +++ b/rtgui/cropwindow.h @@ -54,7 +54,7 @@ public: }; class ImageArea; -class CropWindow : public LWButtonListener, public CropDisplayHandler, public EditCoordSystem, public ObjectMOBuffer, public rtengine::NonCopyable +class CropWindow final : public LWButtonListener, public CropDisplayHandler, public EditCoordSystem, public ObjectMOBuffer, public rtengine::NonCopyable { static bool initialized; diff --git a/rtgui/curveeditor.h b/rtgui/curveeditor.h index baae8f492..abc0cc10a 100644 --- a/rtgui/curveeditor.h +++ b/rtgui/curveeditor.h @@ -18,8 +18,8 @@ */ #pragma once -#include "coloredbar.h" #include "editcallbacks.h" +#include "guiutils.h" #include "../rtengine/diagonalcurvetypes.h" #include "../rtengine/flatcurvetypes.h" @@ -28,6 +28,7 @@ class CurveEditorGroup; class CurveEditorSubGroup; +class ColorProvider; class PopUpToggleButton; /* diff --git a/rtgui/defringe.cc b/rtgui/defringe.cc index cdec88edc..7aae8377a 100644 --- a/rtgui/defringe.cc +++ b/rtgui/defringe.cc @@ -37,7 +37,7 @@ Defringe::Defringe () : FoldableToolPanel(this, "defringe", M("TP_DEFRINGE_LABEL float R, G, B; for (int i = 0; i < 7; i++) { - float x = float(i) * (1.0f / 6.0); + float x = i / 6.f; Color::hsv2rgb01(x, 0.5f, 0.5f, R, G, B); bottomMilestones.push_back( GradientMilestone(double(x), double(R), double(G), double(B)) ); } diff --git a/rtgui/diagonalcurveeditorsubgroup.cc b/rtgui/diagonalcurveeditorsubgroup.cc index eed6c63d3..079a083ea 100644 --- a/rtgui/diagonalcurveeditorsubgroup.cc +++ b/rtgui/diagonalcurveeditorsubgroup.cc @@ -477,13 +477,13 @@ void DiagonalCurveEditorSubGroup::pipetteMouseOver(EditDataProvider *provider, i double pos[3]; shcSelector->getPositions(pos[0], pos[1], pos[2]); - if (pipetteVal >= pos[2]) { + if (static_cast(pipetteVal) >= pos[2]) { editedAdjuster = highlights; paramCurve->setActiveParam(4); - } else if(pipetteVal >= pos[1]) { + } else if(static_cast(pipetteVal) >= pos[1]) { editedAdjuster = lights; paramCurve->setActiveParam(5); - } else if(pipetteVal >= pos[0]) { + } else if(static_cast(pipetteVal) >= pos[0]) { editedAdjuster = darks; paramCurve->setActiveParam(6); } else { diff --git a/rtgui/diagonalcurveeditorsubgroup.h b/rtgui/diagonalcurveeditorsubgroup.h index a077da807..9b1f67462 100644 --- a/rtgui/diagonalcurveeditorsubgroup.h +++ b/rtgui/diagonalcurveeditorsubgroup.h @@ -27,7 +27,7 @@ class DiagonalCurveEditor; class MyDiagonalCurve; -class DiagonalCurveEditorSubGroup : +class DiagonalCurveEditorSubGroup final : public CurveEditorSubGroup, public SHCListener, public AdjusterListener, diff --git a/rtgui/dirbrowser.cc b/rtgui/dirbrowser.cc index 669528ac1..10ef61566 100644 --- a/rtgui/dirbrowser.cc +++ b/rtgui/dirbrowser.cc @@ -293,36 +293,32 @@ void DirBrowser::row_expanded (const Gtk::TreeModel::iterator& iter, const Gtk:: auto dir = Gio::File::create_for_path (iter->get_value (dtColumns.dirname)); auto subDirs = listSubDirs (dir, options.fbShowHidden); - if (subDirs.empty()) { - dirtree->collapse_row(path); - } else { - Gtk::TreeNodeChildren children = iter->children(); - std::list forErase(children.begin(), children.end()); + Gtk::TreeNodeChildren children = iter->children(); + std::list forErase(children.begin(), children.end()); - std::sort (subDirs.begin (), subDirs.end (), [] (const Glib::ustring& firstDir, const Glib::ustring& secondDir) - { - switch (options.dirBrowserSortType) { - default: - case Gtk::SORT_ASCENDING: - return firstDir < secondDir; - case Gtk::SORT_DESCENDING: - return firstDir > secondDir; - } - }); - - for (auto it = subDirs.begin(), end = subDirs.end(); it != end; ++it) { - addDir(iter, *it); + std::sort (subDirs.begin (), subDirs.end (), [] (const Glib::ustring& firstDir, const Glib::ustring& secondDir) + { + switch (options.dirBrowserSortType) { + default: + case Gtk::SORT_ASCENDING: + return firstDir < secondDir; + case Gtk::SORT_DESCENDING: + return firstDir > secondDir; } + }); - for (auto it = forErase.begin(), end = forErase.end(); it != end; ++it) { - dirTreeModel->erase(*it); - } - - dirTreeModel->set_sort_column(prevSortColumn, prevSortType); - - expandSuccess = true; + for (auto it = subDirs.begin(), end = subDirs.end(); it != end; ++it) { + addDir(iter, *it); } + for (auto it = forErase.begin(), end = forErase.end(); it != end; ++it) { + dirTreeModel->erase(*it); + } + + dirTreeModel->set_sort_column(prevSortColumn, prevSortType); + + expandSuccess = true; + Glib::RefPtr monitor = dir->monitor_directory (); iter->set_value (dtColumns.monitor, monitor); monitor->signal_changed().connect (sigc::bind(sigc::mem_fun(*this, &DirBrowser::file_changed), iter, dir->get_parse_name())); @@ -383,8 +379,10 @@ void DirBrowser::row_activated (const Gtk::TreeModel::Path& path, Gtk::TreeViewC Glib::ustring dname = dirTreeModel->get_iter (path)->get_value (dtColumns.dirname); - if (Glib::file_test (dname, Glib::FILE_TEST_IS_DIR)) + if (Glib::file_test (dname, Glib::FILE_TEST_IS_DIR)) { dirSelectionSignal (dname, Glib::ustring()); + dirtree->expand_row(path, false); + } } Gtk::TreePath DirBrowser::expandToDir (const Glib::ustring& absDirPath) diff --git a/rtgui/dirpyrequalizer.cc b/rtgui/dirpyrequalizer.cc index fd0268efa..34aecf095 100644 --- a/rtgui/dirpyrequalizer.cc +++ b/rtgui/dirpyrequalizer.cc @@ -428,7 +428,7 @@ void DirPyrEqualizer::lumacontrastPlusPressed () { for (int i = 0; i < 6; i++) { - float inc = 0.05 * (6 - i); + double inc = 0.05 * (6 - i); multiplier[i]->setValue(multiplier[i]->getValue() + inc); adjusterChanged(multiplier[i], multiplier[i]->getValue()); } @@ -439,7 +439,7 @@ void DirPyrEqualizer::lumacontrastMinusPressed () { for (int i = 0; i < 6; i++) { - float inc = -0.05 * (6 - i); + double inc = -0.05 * (6 - i); multiplier[i]->setValue(multiplier[i]->getValue() + inc); adjusterChanged(multiplier[i], multiplier[i]->getValue()); } diff --git a/rtgui/editcallbacks.h b/rtgui/editcallbacks.h index c2efcf53e..ee357c2f7 100644 --- a/rtgui/editcallbacks.h +++ b/rtgui/editcallbacks.h @@ -129,19 +129,19 @@ public: @param picked True if the cursor is still above the the same object than on button pressed and with the same modifier keys. If false, the user moved the cursor away or the modifier key is different, so the element is considered as NOT selected. @return true if the preview has to be redrawn, false otherwise */ - virtual bool pick1 (bool picked); + bool pick1 (bool picked); /** @brief Triggered when the user is releasing mouse button 2 while in action==ES_ACTION_PICKING mode @param picked True if the cursor is still above the the same object than on button pressed and with the same modifier keys. If false, the user moved the cursor away or the modifier key is different, so the element is considered as NOT selected. @return true if the preview has to be redrawn, false otherwise */ - virtual bool pick2 (bool picked); + bool pick2 (bool picked); /** @brief Triggered when the user is releasing mouse button 3 while in action==ES_ACTION_PICKING mode @param picked True if the cursor is still above the the same object than on button pressed and with the same modifier keys. If false, the user moved the cursor away or the modifier key is different, so the element is considered as NOT selected. @return true if the preview has to be redrawn, false otherwise */ - virtual bool pick3 (bool picked); + bool pick3 (bool picked); /** @brief Get the geometry to be shown to the user */ const std::vector& getVisibleGeometry (); diff --git a/rtgui/editorpanel.cc b/rtgui/editorpanel.cc index 806af8b2e..1a82c4a94 100644 --- a/rtgui/editorpanel.cc +++ b/rtgui/editorpanel.cc @@ -61,7 +61,7 @@ void setprogressStrUI(double val, const Glib::ustring str, MyProgressBar* pProgr } } - +#if !defined(__APPLE__) // monitor profile not supported on apple bool find_default_monitor_profile (GdkWindow *rootwin, Glib::ustring &defprof, Glib::ustring &defprofname) { #ifdef WIN32 @@ -91,7 +91,7 @@ bool find_default_monitor_profile (GdkWindow *rootwin, Glib::ustring &defprof, G ReleaseDC (NULL, hDC); } -#elif !defined(__APPLE__) +#else // taken from geeqie (image.c) and adapted // Originally licensed as GPL v2+, with the following copyright: // * Copyright (C) 2006 John Ellis @@ -129,7 +129,7 @@ bool find_default_monitor_profile (GdkWindow *rootwin, Glib::ustring &defprof, G #endif return false; } - +#endif } @@ -172,7 +172,7 @@ private: const std::vector profiles = rtengine::ICCStore::getInstance()->getProfiles (rtengine::ICCStore::ProfileType::MONITOR); - for (const auto profile : profiles) { + for (const auto& profile : profiles) { profileBox.append (profile); } diff --git a/rtgui/editwidgets.cc b/rtgui/editwidgets.cc index f7c748744..e67b664db 100644 --- a/rtgui/editwidgets.cc +++ b/rtgui/editwidgets.cc @@ -126,13 +126,13 @@ void Circle::drawInnerGeometry(Cairo::RefPtr &cr, ObjectMOBuffer if (filled && state != INSENSITIVE) { cr->arc(center_.x + 0.5, center_.y + 0.5, radius_, 0., 2.*rtengine::RT_PI); - if (innerLineWidth > 0.) { + if (innerLineWidth > 0.f) { cr->fill_preserve(); cr->stroke(); } else { cr->fill(); } - } else if (innerLineWidth > 0.) { + } else if (innerLineWidth > 0.f) { cr->arc(center_.x + 0.5, center_.y + 0.5, radius_, 0., 2.*rtengine::RT_PI); if (state == INSENSITIVE) { @@ -176,7 +176,7 @@ void Circle::drawToMOChannel (Cairo::RefPtr &cr, unsigned short cr->arc(center_.x + 0.5, center_.y + 0.5, radius_, 0, 2.*rtengine::RT_PI); if (filled) { - if (innerLineWidth > 0.) { + if (innerLineWidth > 0.f) { cr->fill_preserve(); cr->stroke(); } else { @@ -224,7 +224,7 @@ void Line::drawOuterGeometry(Cairo::RefPtr &cr, ObjectMOBuffer * void Line::drawInnerGeometry(Cairo::RefPtr &cr, ObjectMOBuffer *objectBuffer, EditCoordSystem &coordSystem) { - if ((flags & F_VISIBLE) && innerLineWidth > 0.) { + if ((flags & F_VISIBLE) && innerLineWidth > 0.f) { if (state != INSENSITIVE) { RGBColor color; @@ -383,13 +383,13 @@ void Polyline::drawInnerGeometry(Cairo::RefPtr &cr, ObjectMOBuff } } - if (innerLineWidth > 0.) { + if (innerLineWidth > 0.f) { cr->fill_preserve(); cr->stroke(); } else { cr->fill(); } - } else if (innerLineWidth > 0.) { + } else if (innerLineWidth > 0.f) { rtengine::Coord currPos; for (unsigned int i = 0; i < points.size(); ++i) { @@ -459,7 +459,7 @@ void Polyline::drawToMOChannel (Cairo::RefPtr &cr, unsigned shor } if (filled) { - if (innerLineWidth > 0.) { + if (innerLineWidth > 0.f) { cr->fill_preserve(); cr->stroke(); } else { @@ -576,13 +576,13 @@ void Rectangle::drawInnerGeometry(Cairo::RefPtr &cr, ObjectMOBuf if (filled && state != INSENSITIVE) { cr->rectangle(tl.x + 0.5, tl.y + 0.5, br.x - tl.x, br.y - tl.y); - if (innerLineWidth > 0.) { + if (innerLineWidth > 0.f) { cr->fill_preserve(); cr->stroke(); } else { cr->fill(); } - } else if (innerLineWidth > 0.) { + } else if (innerLineWidth > 0.f) { cr->rectangle(tl.x + 0.5, tl.y + 0.5, br.x - tl.x, br.y - tl.y); if (state == INSENSITIVE) { @@ -634,7 +634,7 @@ void Rectangle::drawToMOChannel(Cairo::RefPtr &cr, unsigned shor cr->rectangle(tl.x + 0.5, tl.y + 0.5, br.x - tl.x, br.y - tl.y); if (filled) { - if (innerLineWidth > 0.) { + if (innerLineWidth > 0.f) { cr->fill_preserve(); cr->stroke(); } else { diff --git a/rtgui/epd.cc b/rtgui/epd.cc index b13effba3..d032cf28d 100644 --- a/rtgui/epd.cc +++ b/rtgui/epd.cc @@ -31,8 +31,8 @@ EdgePreservingDecompositionUI::EdgePreservingDecompositionUI () : FoldableToolPa strength = Gtk::manage(new Adjuster (M("TP_EPD_STRENGTH"), -1.0, 2.0, 0.01, 0.5)); gamma = Gtk::manage(new Adjuster (M("TP_EPD_GAMMA"), 0.8, 1.5, 0.01, 1.)); - edgeStopping = Gtk::manage(new Adjuster (M("TP_EPD_EDGESTOPPING"), 0.1, 4.0, 0.01, 0.5)); - scale = Gtk::manage(new Adjuster (M("TP_EPD_SCALE"), 0.1, 10.0, 0.01, 0.1)); + edgeStopping = Gtk::manage(new Adjuster (M("TP_EPD_EDGESTOPPING"), 0.1, 4.0, 0.01, 1.4)); + scale = Gtk::manage(new Adjuster (M("TP_EPD_SCALE"), 0.1, 10.0, 0.01, 1.0)); reweightingIterates = Gtk::manage(new Adjuster (M("TP_EPD_REWEIGHTINGITERATES"), 0, 9, 1, 0)); strength->setAdjusterListener(this); diff --git a/rtgui/exifpanel.h b/rtgui/exifpanel.h index 0894c21ad..d336d83f9 100644 --- a/rtgui/exifpanel.h +++ b/rtgui/exifpanel.h @@ -25,7 +25,7 @@ #include "toolpanel.h" #include "../rtexif/rtexif.h" -class ExifPanel : +class ExifPanel final : public Gtk::VBox, public ToolPanel { diff --git a/rtgui/filebrowser.h b/rtgui/filebrowser.h index 86ab59395..53f3f1f2b 100644 --- a/rtgui/filebrowser.h +++ b/rtgui/filebrowser.h @@ -56,7 +56,7 @@ public: /* * Class handling actions common to all thumbnails of the file browser */ -class FileBrowser : public ThumbBrowserBase, +class FileBrowser final : public ThumbBrowserBase, public LWButtonListener, public ExportPanelListener, public ProfileStoreListener, diff --git a/rtgui/filebrowserentry.h b/rtgui/filebrowserentry.h index ea5140ed6..67b953514 100644 --- a/rtgui/filebrowserentry.h +++ b/rtgui/filebrowserentry.h @@ -43,7 +43,7 @@ struct FileBrowserEntryIdleHelper { }; class FileThumbnailButtonSet; -class FileBrowserEntry : public ThumbBrowserEntryBase, +class FileBrowserEntry final : public ThumbBrowserEntryBase, public ThumbnailListener, public ThumbImageUpdateListener, public rtengine::NonCopyable diff --git a/rtgui/filecatalog.cc b/rtgui/filecatalog.cc index 109a1bb57..102c17daf 100644 --- a/rtgui/filecatalog.cc +++ b/rtgui/filecatalog.cc @@ -45,8 +45,6 @@ using namespace std; -#define CHECKTIME 2000 - FileCatalog::FileCatalog (CoarsePanel* cp, ToolBar* tb, FilePanel* filepanel) : filepanel(filepanel), selectedDirectoryId(1), @@ -55,6 +53,8 @@ FileCatalog::FileCatalog (CoarsePanel* cp, ToolBar* tb, FilePanel* filepanel) : fslistener(nullptr), iatlistener(nullptr), hbToolBar1STB(nullptr), + progressImage(nullptr), + progressLabel(nullptr), hasValidCurrentEFS(false), filterPanel(nullptr), exportPanel(nullptr), @@ -705,35 +705,38 @@ void FileCatalog::_refreshProgressBar () // The second, usually longer pass is done multithreaded down in the single entries and is NOT measured by this if (!inTabMode && (!previewsToLoad || std::floor(100.f * previewsLoaded / previewsToLoad) != std::floor(100.f * (previewsLoaded - 1) / previewsToLoad))) { GThreadLock lock; // All GUI access from idle_add callbacks or separate thread HAVE to be protected - Gtk::Notebook *nb = (Gtk::Notebook *)(filepanel->get_parent()); - Gtk::Grid* grid = Gtk::manage(new Gtk::Grid()); - Gtk::Label *label = nullptr; + if (!progressImage || !progressLabel) { + // create tab label once + Gtk::Notebook *nb = (Gtk::Notebook *)(filepanel->get_parent()); + Gtk::Grid* grid = Gtk::manage(new Gtk::Grid()); + progressImage = Gtk::manage(new RTImage("folder-closed.png")); + progressLabel = Gtk::manage(new Gtk::Label(M("MAIN_FRAME_FILEBROWSER"))); + grid->attach_next_to(*progressImage, options.mainNBVertical ? Gtk::POS_TOP : Gtk::POS_RIGHT, 1, 1); + grid->attach_next_to(*progressLabel, options.mainNBVertical ? Gtk::POS_TOP : Gtk::POS_RIGHT, 1, 1); + grid->set_tooltip_markup(M("MAIN_FRAME_FILEBROWSER_TOOLTIP")); + grid->show_all(); + if (options.mainNBVertical) { + progressLabel->set_angle(90); + } + if (nb) { + nb->set_tab_label(*filepanel, *grid); + } + } if (!previewsToLoad) { - grid->attach_next_to(*Gtk::manage(new RTImage("folder-closed.png")), options.mainNBVertical ? Gtk::POS_TOP : Gtk::POS_RIGHT, 1, 1); + progressImage->changeImage("folder-closed.png"); int filteredCount = min(fileBrowser->getNumFiltered(), previewsLoaded); - - label = Gtk::manage(new Gtk::Label(M("MAIN_FRAME_FILEBROWSER") + - (filteredCount != previewsLoaded ? " [" + Glib::ustring::format(filteredCount) + "/" : " (") - + Glib::ustring::format(previewsLoaded) + - (filteredCount != previewsLoaded ? "]" : ")"))); + progressLabel->set_text(M("MAIN_FRAME_FILEBROWSER") + + (filteredCount != previewsLoaded ? " [" + Glib::ustring::format(filteredCount) + "/" : " (") + + Glib::ustring::format(previewsLoaded) + + (filteredCount != previewsLoaded ? "]" : ")")); } else { - grid->attach_next_to(*Gtk::manage(new RTImage("magnifier.png")), options.mainNBVertical ? Gtk::POS_TOP : Gtk::POS_RIGHT, 1, 1); - label = Gtk::manage(new Gtk::Label(M("MAIN_FRAME_FILEBROWSER") + " [" + Glib::ustring::format(std::fixed, std::setprecision(0), std::setw(3), (double)previewsLoaded / previewsToLoad * 100 ) + "%]" )); + progressImage->changeImage("magnifier.png"); + progressLabel->set_text(M("MAIN_FRAME_FILEBROWSER") + " [" + + Glib::ustring::format(previewsLoaded) + "/" + + Glib::ustring::format(previewsToLoad) + "]" ); filepanel->loadingThumbs("", (double)previewsLoaded / previewsToLoad); } - - if (options.mainNBVertical) { - label->set_angle(90); - } - - grid->attach_next_to(*label, options.mainNBVertical ? Gtk::POS_TOP : Gtk::POS_RIGHT, 1, 1); - grid->set_tooltip_markup(M("MAIN_FRAME_FILEBROWSER_TOOLTIP")); - grid->show_all(); - - if (nb) { - nb->set_tab_label(*filepanel, *grid); - } } } diff --git a/rtgui/filecatalog.h b/rtgui/filecatalog.h index 8f7e5618f..194153921 100644 --- a/rtgui/filecatalog.h +++ b/rtgui/filecatalog.h @@ -43,7 +43,7 @@ class ToolBar; * - handling the thumbnail toolbar, * - monitoring the directory (for any change) */ -class FileCatalog : public Gtk::VBox, +class FileCatalog final : public Gtk::VBox, public PreviewLoaderListener, public FilterPanelListener, public FileBrowserListener, @@ -124,6 +124,9 @@ private: Gtk::Button* zoomInButton; Gtk::Button* zoomOutButton; + RTImage* progressImage; + Gtk::Label* progressLabel; + MyMutex dirEFSMutex; ExifFilterSettings dirEFS; ExifFilterSettings currentEFS; diff --git a/rtgui/filmnegative.cc b/rtgui/filmnegative.cc index 90cedf148..1b105a3ec 100644 --- a/rtgui/filmnegative.cc +++ b/rtgui/filmnegative.cc @@ -44,6 +44,17 @@ Adjuster* createExponentAdjuster(AdjusterListener* listener, const Glib::ustring return adj; } +Glib::ustring formatBaseValues(const std::array& rgb) +{ + if (rgb[0] <= 0.f && rgb[1] <= 0.f && rgb[2] <= 0.f) { + return "- - -"; + } else { + return Glib::ustring::format(std::fixed, std::setprecision(1), rgb[0]) + " " + + Glib::ustring::format(std::fixed, std::setprecision(1), rgb[1]) + " " + + Glib::ustring::format(std::fixed, std::setprecision(1), rgb[2]); + } +} + } FilmNegative::FilmNegative() : @@ -51,12 +62,17 @@ FilmNegative::FilmNegative() : EditSubscriber(ET_OBJECTS), evFilmNegativeExponents(ProcEventMapper::getInstance()->newEvent(FIRST, "HISTORY_MSG_FILMNEGATIVE_VALUES")), evFilmNegativeEnabled(ProcEventMapper::getInstance()->newEvent(FIRST, "HISTORY_MSG_FILMNEGATIVE_ENABLED")), + evFilmBaseValues(ProcEventMapper::getInstance()->newEvent(FIRST, "HISTORY_MSG_FILMNEGATIVE_FILMBASE")), + filmBaseValues({0.f, 0.f, 0.f}), fnp(nullptr), greenExp(createExponentAdjuster(this, M("TP_FILMNEGATIVE_GREEN"), 0.3, 4, 1.5)), // master exponent (green channel) redRatio(createExponentAdjuster(this, M("TP_FILMNEGATIVE_RED"), 0.3, 3, (2.04 / 1.5))), // ratio of red exponent to master exponent blueRatio(createExponentAdjuster(this, M("TP_FILMNEGATIVE_BLUE"), 0.3, 3, (1.29 / 1.5))), // ratio of blue exponent to master exponent spotgrid(Gtk::manage(new Gtk::Grid())), - spotbutton(Gtk::manage(new Gtk::ToggleButton(M("TP_FILMNEGATIVE_PICK")))) + spotbutton(Gtk::manage(new Gtk::ToggleButton(M("TP_FILMNEGATIVE_PICK")))), + filmBaseLabel(Gtk::manage(new Gtk::Label(M("TP_FILMNEGATIVE_FILMBASE_VALUES"), Gtk::ALIGN_START))), + filmBaseValuesLabel(Gtk::manage(new Gtk::Label("- - -"))), + filmBaseSpotButton(Gtk::manage(new Gtk::ToggleButton(M("TP_FILMNEGATIVE_FILMBASE_PICK")))) { spotgrid->get_style_context()->add_class("grid-spacing"); setExpandAlignProperties(spotgrid, true, false, Gtk::ALIGN_FILL, Gtk::ALIGN_CENTER); @@ -64,7 +80,10 @@ FilmNegative::FilmNegative() : setExpandAlignProperties(spotbutton, true, false, Gtk::ALIGN_FILL, Gtk::ALIGN_CENTER); spotbutton->get_style_context()->add_class("independent"); spotbutton->set_tooltip_text(M("TP_FILMNEGATIVE_GUESS_TOOLTIP")); - spotbutton->set_image (*Gtk::manage (new RTImage ("color-picker-small.png"))); + spotbutton->set_image(*Gtk::manage(new RTImage("color-picker-small.png"))); + + filmBaseSpotButton->set_tooltip_text(M("TP_FILMNEGATIVE_FILMBASE_TOOLTIP")); + setExpandAlignProperties(filmBaseValuesLabel, false, false, Gtk::ALIGN_START, Gtk::ALIGN_CENTER); // TODO make spot size configurable ? @@ -81,7 +100,7 @@ FilmNegative::FilmNegative() : // spotsize->set_active(0); // spotsize->append ("4"); - spotgrid->attach (*spotbutton, 0, 1, 1, 1); + spotgrid->attach(*spotbutton, 0, 1, 1, 1); // spotgrid->attach (*slab, 1, 0, 1, 1); // spotgrid->attach (*wbsizehelper, 2, 0, 1, 1); @@ -90,13 +109,26 @@ FilmNegative::FilmNegative() : pack_start(*blueRatio, Gtk::PACK_SHRINK, 0); pack_start(*spotgrid, Gtk::PACK_SHRINK, 0); + Gtk::HSeparator* const sep = Gtk::manage(new Gtk::HSeparator()); + sep->get_style_context()->add_class("grid-row-separator"); + pack_start(*sep, Gtk::PACK_SHRINK, 0); + + Gtk::Grid* const fbGrid = Gtk::manage(new Gtk::Grid()); + fbGrid->attach(*filmBaseLabel, 0, 0, 1, 1); + fbGrid->attach(*filmBaseValuesLabel, 1, 0, 1, 1); + pack_start(*fbGrid, Gtk::PACK_SHRINK, 0); + + pack_start(*filmBaseSpotButton, Gtk::PACK_SHRINK, 0); + spotbutton->signal_toggled().connect(sigc::mem_fun(*this, &FilmNegative::editToggled)); // spotsize->signal_changed().connect( sigc::mem_fun(*this, &WhiteBalance::spotSizeChanged) ); + filmBaseSpotButton->signal_toggled().connect(sigc::mem_fun(*this, &FilmNegative::baseSpotToggled)); + // Editing geometry; create the spot rectangle Rectangle* const spotRect = new Rectangle(); spotRect->filled = false; - + visibleGeometry.push_back(spotRect); // Stick a dummy rectangle over the whole image in mouseOverGeometry. @@ -134,6 +166,14 @@ void FilmNegative::read(const rtengine::procparams::ProcParams* pp, const Params greenExp->setValue(pp->filmNegative.greenExp); blueRatio->setValue(pp->filmNegative.blueRatio); + filmBaseValues[0] = pp->filmNegative.redBase; + filmBaseValues[1] = pp->filmNegative.greenBase; + filmBaseValues[2] = pp->filmNegative.blueBase; + + // If base values are not set in params, estimated values will be passed in later + // (after processing) via FilmNegListener + filmBaseValuesLabel->set_text(formatBaseValues(filmBaseValues)); + enableListener(); } @@ -142,14 +182,23 @@ void FilmNegative::write(rtengine::procparams::ProcParams* pp, ParamsEdited* ped pp->filmNegative.redRatio = redRatio->getValue(); pp->filmNegative.greenExp = greenExp->getValue(); pp->filmNegative.blueRatio = blueRatio->getValue(); + pp->filmNegative.enabled = getEnabled(); if (pedited) { pedited->filmNegative.redRatio = redRatio->getEditedState(); pedited->filmNegative.greenExp = greenExp->getEditedState(); pedited->filmNegative.blueRatio = blueRatio->getEditedState(); + pedited->filmNegative.baseValues = filmBaseValues[0] != pp->filmNegative.redBase + || filmBaseValues[1] != pp->filmNegative.greenBase + || filmBaseValues[2] != pp->filmNegative.blueBase; pedited->filmNegative.enabled = !get_inconsistent(); } + + pp->filmNegative.redBase = filmBaseValues[0]; + pp->filmNegative.greenBase = filmBaseValues[1]; + pp->filmNegative.blueBase = filmBaseValues[2]; + } void FilmNegative::setDefaults(const rtengine::procparams::ProcParams* defParams, const ParamsEdited* pedited) @@ -172,8 +221,8 @@ void FilmNegative::setDefaults(const rtengine::procparams::ProcParams* defParams void FilmNegative::setBatchMode(bool batchMode) { if (batchMode) { - spotConn.disconnect(); removeIfThere(this, spotgrid, false); + removeIfThere(this, filmBaseSpotButton, false); ToolPanel::setBatchMode(batchMode); redRatio->showEditedCB(); greenExp->showEditedCB(); @@ -205,16 +254,20 @@ void FilmNegative::enabledChanged() if (listener) { if (get_inconsistent()) { listener->panelChanged(evFilmNegativeEnabled, M("GENERAL_UNCHANGED")); - } - else if (getEnabled()) { + } else if (getEnabled()) { listener->panelChanged(evFilmNegativeEnabled, M("GENERAL_ENABLED")); - } - else { + } else { listener->panelChanged(evFilmNegativeEnabled, M("GENERAL_DISABLED")); } } } +void FilmNegative::filmBaseValuesChanged(std::array rgb) +{ + filmBaseValues = rgb; + filmBaseValuesLabel->set_text(formatBaseValues(filmBaseValues)); +} + void FilmNegative::setFilmNegProvider(FilmNegProvider* provider) { fnp = provider; @@ -227,7 +280,7 @@ void FilmNegative::setEditProvider(EditDataProvider* provider) CursorShape FilmNegative::getCursor(int objectID) const { - return CSSpotWB; + return CSSpotWB; } bool FilmNegative::mouseOver(int modifierKey) @@ -246,31 +299,57 @@ bool FilmNegative::button1Pressed(int modifierKey) EditSubscriber::action = EditSubscriber::Action::NONE; if (listener) { - refSpotCoords.push_back(provider->posImage); + if (spotbutton->get_active()) { - if (refSpotCoords.size() == 2) { - // User has selected 2 reference gray spots. Calculating new exponents - // from channel values and updating parameters. + refSpotCoords.push_back(provider->posImage); - std::array newExps; - if (fnp->getFilmNegativeExponents(refSpotCoords[0], refSpotCoords[1], newExps)) { + if (refSpotCoords.size() == 2) { + // User has selected 2 reference gray spots. Calculating new exponents + // from channel values and updating parameters. + + std::array newExps; + + if (fnp->getFilmNegativeExponents(refSpotCoords[0], refSpotCoords[1], newExps)) { + disableListener(); + // Leaving green exponent unchanged, setting red and blue exponents based on + // the ratios between newly calculated exponents. + redRatio->setValue(newExps[0] / newExps[1]); + blueRatio->setValue(newExps[2] / newExps[1]); + enableListener(); + + if (listener && getEnabled()) { + listener->panelChanged( + evFilmNegativeExponents, + Glib::ustring::compose( + "Ref=%1\nR=%2\nB=%3", + greenExp->getValue(), + redRatio->getValue(), + blueRatio->getValue() + ) + ); + } + } + + switchOffEditMode(); + } + + } else if (filmBaseSpotButton->get_active()) { + + std::array newBaseLev; + + if (fnp->getRawSpotValues(provider->posImage, 32, newBaseLev)) { disableListener(); - // Leaving green exponent unchanged, setting red and blue exponents based on - // the ratios between newly calculated exponents. - redRatio->setValue(newExps[0] / newExps[1]); - blueRatio->setValue(newExps[2] / newExps[1]); + + filmBaseValues = newBaseLev; + enableListener(); + const Glib::ustring vs = formatBaseValues(filmBaseValues); + + filmBaseValuesLabel->set_text(vs); + if (listener && getEnabled()) { - listener->panelChanged( - evFilmNegativeExponents, - Glib::ustring::compose( - "Ref=%1\nR=%2\nB=%3", - greenExp->getValue(), - redRatio->getValue(), - blueRatio->getValue() - ) - ); + listener->panelChanged(evFilmBaseValues, vs); } } @@ -292,11 +371,38 @@ void FilmNegative::switchOffEditMode() refSpotCoords.clear(); unsubscribe(); spotbutton->set_active(false); + filmBaseSpotButton->set_active(false); } void FilmNegative::editToggled() { if (spotbutton->get_active()) { + + filmBaseSpotButton->set_active(false); + refSpotCoords.clear(); + + subscribe(); + + int w, h; + getEditProvider()->getImageSize(w, h); + + // Stick a dummy rectangle over the whole image in mouseOverGeometry. + // This is to make sure the getCursor() call is fired everywhere. + Rectangle* const imgRect = static_cast(mouseOverGeometry.at(0)); + imgRect->setXYWH(0, 0, w, h); + } else { + refSpotCoords.clear(); + unsubscribe(); + } +} + +void FilmNegative::baseSpotToggled() +{ + if (filmBaseSpotButton->get_active()) { + + spotbutton->set_active(false); + refSpotCoords.clear(); + subscribe(); int w, h; diff --git a/rtgui/filmnegative.h b/rtgui/filmnegative.h index bca155ceb..0810a8c57 100644 --- a/rtgui/filmnegative.h +++ b/rtgui/filmnegative.h @@ -33,13 +33,15 @@ public: virtual ~FilmNegProvider() = default; virtual bool getFilmNegativeExponents(rtengine::Coord spotA, rtengine::Coord spotB, std::array& newExps) = 0; + virtual bool getRawSpotValues(rtengine::Coord spot, int spotSize, std::array& rawValues) = 0; }; class FilmNegative final : public ToolParamBlock, public AdjusterListener, public FoldableToolPanel, - public EditSubscriber + public EditSubscriber, + public rtengine::FilmNegListener { public: FilmNegative(); @@ -53,6 +55,8 @@ public: void adjusterChanged(Adjuster* a, double newval) override; void enabledChanged() override; + void filmBaseValuesChanged(std::array rgb) override; + void setFilmNegProvider(FilmNegProvider* provider); void setEditProvider(EditDataProvider* provider) override; @@ -66,12 +70,16 @@ public: private: void editToggled(); + void baseSpotToggled(); const rtengine::ProcEvent evFilmNegativeExponents; const rtengine::ProcEvent evFilmNegativeEnabled; + const rtengine::ProcEvent evFilmBaseValues; std::vector refSpotCoords; + std::array filmBaseValues; + FilmNegProvider* fnp; Adjuster* const greenExp; @@ -80,5 +88,9 @@ private: Gtk::Grid* const spotgrid; Gtk::ToggleButton* const spotbutton; - sigc::connection spotConn; + + Gtk::Label* const filmBaseLabel; + Gtk::Label* const filmBaseValuesLabel; + Gtk::ToggleButton* const filmBaseSpotButton; + }; diff --git a/rtgui/flatcurveeditorsubgroup.h b/rtgui/flatcurveeditorsubgroup.h index c358dde3b..865a0ef83 100644 --- a/rtgui/flatcurveeditorsubgroup.h +++ b/rtgui/flatcurveeditorsubgroup.h @@ -27,7 +27,7 @@ class FlatCurveEditor; class MyFlatCurve; -class FlatCurveEditorSubGroup: +class FlatCurveEditorSubGroup final : public CurveEditorSubGroup, public rtengine::NonCopyable { diff --git a/rtgui/gradient.cc b/rtgui/gradient.cc index 4f389e112..b46f8e1ca 100644 --- a/rtgui/gradient.cc +++ b/rtgui/gradient.cc @@ -164,7 +164,7 @@ void Gradient::updateGeometry(const int centerX, const int centerY, const double const auto decay = feather * rtengine::norm2 (imW, imH) / 200.0; rtengine::Coord origin (imW / 2 + centerX * imW / 200, imH / 2 + centerY * imH / 200); - const auto updateLine = [&](Geometry* geometry, const float radius, const float begin, const float end) + const auto updateLine = [&](Geometry* geometry, const double radius, const double begin, const double end) { const auto line = static_cast(geometry); line->begin = PolarCoord(radius, -degree + begin); @@ -173,7 +173,7 @@ void Gradient::updateGeometry(const int centerX, const int centerY, const double line->end += origin; }; - const auto updateLineWithDecay = [&](Geometry* geometry, const float radius, const float offSetAngle) + const auto updateLineWithDecay = [&](Geometry* geometry, const double radius, const double offSetAngle) { const auto line = static_cast(geometry); line->begin = PolarCoord (radius, -degree + 180.) + PolarCoord (decay, -degree + offSetAngle); diff --git a/rtgui/guiutils.cc b/rtgui/guiutils.cc index 02a28607f..d759751c3 100644 --- a/rtgui/guiutils.cc +++ b/rtgui/guiutils.cc @@ -20,7 +20,6 @@ #include "guiutils.h" #include "options.h" -#include "../rtengine/rt_math.h" #include "../rtengine/utils.h" #include "../rtengine/procparams.h" #include "rtimage.h" @@ -827,12 +826,6 @@ void MyExpander::set_expanded( bool expanded ) return; } - bool isVisible = expBox->is_visible(); - - if (isVisible == expanded) { - return; - } - if (!useEnabled) { if (expanded ) { statusImage->set(openedImage->get_surface()); diff --git a/rtgui/guiutils.h b/rtgui/guiutils.h index 97c72513b..d4c91734a 100644 --- a/rtgui/guiutils.h +++ b/rtgui/guiutils.h @@ -92,7 +92,7 @@ private: * } * */ -class GThreadLock +class GThreadLock final { public: GThreadLock() @@ -110,7 +110,7 @@ public: * * Will relock on destruction. */ -class GThreadUnLock +class GThreadUnLock final { public: GThreadUnLock() @@ -125,7 +125,7 @@ public: #pragma GCC diagnostic pop -class ConnectionBlocker +class ConnectionBlocker final { public: explicit ConnectionBlocker (Gtk::Widget *associatedWidget, sigc::connection& connection) : connection (associatedWidget ? &connection : nullptr), wasBlocked(false) @@ -152,7 +152,7 @@ private: /** * @brief Glue box to control visibility of the MyExpender's content ; also handle the frame around it */ -class ExpanderBox: public Gtk::EventBox +class ExpanderBox final : public Gtk::EventBox { private: Gtk::Container *pC; @@ -185,7 +185,7 @@ public: * * Warning: once you've instantiated this class with a text label or a widget label, you won't be able to revert to the other solution. */ -class MyExpander : public Gtk::VBox +class MyExpander final : public Gtk::VBox { public: typedef sigc::signal type_signal_enabled_toggled; @@ -295,7 +295,7 @@ public: /** * @brief subclass of Gtk::ScrolledWindow in order to handle the scrollwheel */ -class MyScrolledWindow : public Gtk::ScrolledWindow +class MyScrolledWindow final : public Gtk::ScrolledWindow { bool on_scroll_event (GdkEventScroll* event) override; @@ -310,7 +310,7 @@ public: /** * @brief subclass of Gtk::ScrolledWindow in order to handle the large toolbars (wider than available space) */ -class MyScrolledToolbar : public Gtk::ScrolledWindow +class MyScrolledToolbar final : public Gtk::ScrolledWindow { bool on_scroll_event (GdkEventScroll* event) override; @@ -340,7 +340,7 @@ public: /** * @brief subclass of Gtk::ComboBoxText in order to handle the scrollwheel */ -class MyComboBoxText : public Gtk::ComboBoxText +class MyComboBoxText final : public Gtk::ComboBoxText { int naturalWidth, minimumWidth; sigc::connection myConnection; @@ -360,7 +360,7 @@ public: /** * @brief subclass of Gtk::SpinButton in order to handle the scrollwheel */ -class MySpinButton : public Gtk::SpinButton +class MySpinButton final : public Gtk::SpinButton { protected: @@ -375,7 +375,7 @@ public: /** * @brief subclass of Gtk::HScale in order to handle the scrollwheel */ -class MyHScale : public Gtk::HScale +class MyHScale final : public Gtk::HScale { bool on_scroll_event (GdkEventScroll* event) override; @@ -385,7 +385,7 @@ class MyHScale : public Gtk::HScale /** * @brief subclass of Gtk::FileChooserButton in order to handle the scrollwheel */ -class MyFileChooserButton: public Gtk::Button { +class MyFileChooserButton final : public Gtk::Button { private: void show_chooser(); @@ -473,14 +473,14 @@ typedef enum RTNav { /** * @brief Handle the switch between text and image to be displayed in the HBox (to be used in a button/toolpanel) */ -class TextOrIcon : public Gtk::HBox +class TextOrIcon final : public Gtk::HBox { public: TextOrIcon (const Glib::ustring &filename, const Glib::ustring &labelTx, const Glib::ustring &tooltipTx); }; -class MyImageMenuItem : public Gtk::MenuItem +class MyImageMenuItem final : public Gtk::MenuItem { private: Gtk::Grid *box; @@ -493,7 +493,7 @@ public: const Gtk::Label* getLabel () const; }; -class MyProgressBar : public Gtk::ProgressBar +class MyProgressBar final : public Gtk::ProgressBar { private: int w; @@ -512,7 +512,7 @@ public: /** * @brief Define a gradient milestone */ -class GradientMilestone +class GradientMilestone final { public: double position; diff --git a/rtgui/histogrampanel.cc b/rtgui/histogrampanel.cc index dd0cbde46..b8338e4e8 100644 --- a/rtgui/histogrampanel.cc +++ b/rtgui/histogrampanel.cc @@ -518,26 +518,26 @@ void HistogramRGBArea::updateBackBuffer (int r, int g, int b, const Glib::ustrin // Luma cc->set_source_rgb(1.0, 1.0, 1.0); if (options.histogramDrawMode < 2) { - cc->move_to(Lab_L * (winw - 3.*s) / 100.0 + 0.5*s, 0); - cc->line_to(Lab_L * (winw - 3.*s) / 100.0 + 0.5*s, winh - 0); + cc->move_to(static_cast(Lab_L) * (winw - 3. * s) / 100.0 + 0.5 * s, 0); + cc->line_to(static_cast(Lab_L) * (winw - 3. * s) / 100.0 + 0.5 * s, winh - 0); } else { - cc->move_to(HistogramScaling::log (100, Lab_L) * (winw - 1.) / 100.0 + 0.5*s, 0); - cc->line_to(HistogramScaling::log (100, Lab_L) * (winw - 1.) / 100.0 + 0.5*s, winh - 0); + cc->move_to(HistogramScaling::log(100, Lab_L) * (winw - 1.) / 100.0 + 0.5 * s, 0); + cc->line_to(HistogramScaling::log(100, Lab_L) * (winw - 1.) / 100.0 + 0.5 * s, winh - 0); } cc->stroke(); } if (needChroma) { // Chroma - float chromaval = sqrt(Lab_a * Lab_a + Lab_b * Lab_b) / 1.8; + double chromaval = sqrt(Lab_a * Lab_a + Lab_b * Lab_b) / 1.8; // float chromaval = sqrt(Lab_a*Lab_a + Lab_b*Lab_b); cc->set_source_rgb(0.9, 0.9, 0.0); if (options.histogramDrawMode < 2) { - cc->move_to(chromaval * (winw - 1.) / 100.0 + 0.5*s, 0); - cc->line_to(chromaval * (winw - 1.) / 100.0 + 0.5*s, winh - 0); + cc->move_to(chromaval * (winw - 1.) / 100.0 + 0.5 * s, 0); + cc->line_to(chromaval * (winw - 1.) / 100.0 + 0.5 * s, winh - 0); } else { - cc->move_to(HistogramScaling::log (100, chromaval) * (winw - 1.) / 100.0 + 0.5*s, 0); - cc->line_to(HistogramScaling::log (100, chromaval) * (winw - 1.) / 100.0 + 0.5*s, winh - 0); + cc->move_to(HistogramScaling::log(100, chromaval) * (winw - 1.) / 100.0 + 0.5 * s, 0); + cc->line_to(HistogramScaling::log(100, chromaval) * (winw - 1.) / 100.0 + 0.5 * s, winh - 0); } cc->stroke(); } @@ -989,7 +989,7 @@ void HistogramArea::drawCurve(Cairo::RefPtr &cr, cr->set_line_width(s); cr->move_to (0, vsize - 1); - scale = scale <= 0.f ? 0.001f : scale; // avoid division by zero and negative values + scale = scale <= 0.0 ? 0.001 : scale; // avoid division by zero and negative values for (int i = 0; i < 256; i++) { double val = data[i] * (double)vsize / scale; diff --git a/rtgui/histogrampanel.h b/rtgui/histogrampanel.h index 4fd21bcc2..cec44ed03 100644 --- a/rtgui/histogrampanel.h +++ b/rtgui/histogrampanel.h @@ -53,7 +53,7 @@ public: double log (double vsize, double val); }; -class HistogramRGBArea : public Gtk::DrawingArea, public BackBuffer, private HistogramScaling, public rtengine::NonCopyable +class HistogramRGBArea final : public Gtk::DrawingArea, public BackBuffer, private HistogramScaling, public rtengine::NonCopyable { private: typedef const double (*TMatrix)[3]; @@ -116,7 +116,7 @@ public: virtual void toggleButtonMode() = 0; }; -class HistogramArea : public Gtk::DrawingArea, public BackBuffer, private HistogramScaling, public rtengine::NonCopyable +class HistogramArea final : public Gtk::DrawingArea, public BackBuffer, private HistogramScaling, public rtengine::NonCopyable { public: typedef sigc::signal type_signal_factor_changed; @@ -174,7 +174,7 @@ private: void get_preferred_width_for_height_vfunc (int height, int &minimum_width, int &natural_width) const override; }; -class HistogramPanel : public Gtk::Grid, public PointerMotionListener, public DrawModeListener, public rtengine::NonCopyable +class HistogramPanel final : public Gtk::Grid, public PointerMotionListener, public DrawModeListener, public rtengine::NonCopyable { protected: diff --git a/rtgui/hsvequalizer.cc b/rtgui/hsvequalizer.cc index ee3eb90a7..817ba1f4d 100644 --- a/rtgui/hsvequalizer.cc +++ b/rtgui/hsvequalizer.cc @@ -38,7 +38,7 @@ HSVEqualizer::HSVEqualizer () : FoldableToolPanel(this, "hsvequalizer", M("TP_HS // -0.1 rad < Hue < 1.6 rad for (int i = 0; i < 7; i++) { - float x = float(i) * (1.0f / 6.0); + float x = i / 6.0; Color::hsv2rgb01(x, 0.5f, 0.5f, R, G, B); bottomMilestones.push_back( GradientMilestone(double(x), double(R), double(G), double(B)) ); } diff --git a/rtgui/iccprofilecreator.h b/rtgui/iccprofilecreator.h index 2cd19e14f..8ee46a71d 100644 --- a/rtgui/iccprofilecreator.h +++ b/rtgui/iccprofilecreator.h @@ -27,7 +27,7 @@ class RTWindow; -class ICCProfileCreator : public Gtk::Dialog, public AdjusterListener +class ICCProfileCreator final : public Gtk::Dialog, public AdjusterListener { private: diff --git a/rtgui/imagearea.h b/rtgui/imagearea.h index 28b52dcd2..586bba7a7 100644 --- a/rtgui/imagearea.h +++ b/rtgui/imagearea.h @@ -34,7 +34,7 @@ class ImageAreaPanel; -class ImageArea : +class ImageArea final : public Gtk::DrawingArea, public CropWindowListener, public EditDataProvider, diff --git a/rtgui/imageareapanel.h b/rtgui/imageareapanel.h index 831371dbb..f52ca9060 100644 --- a/rtgui/imageareapanel.h +++ b/rtgui/imageareapanel.h @@ -22,7 +22,7 @@ class ImageArea; -class ImageAreaPanel : +class ImageAreaPanel final : public Gtk::VBox { diff --git a/rtgui/inspector.h b/rtgui/inspector.h index 8338259bf..1526f90be 100644 --- a/rtgui/inspector.h +++ b/rtgui/inspector.h @@ -40,7 +40,7 @@ public: //~InspectorBuffer(); }; -class Inspector : public Gtk::DrawingArea +class Inspector final : public Gtk::DrawingArea { private: diff --git a/rtgui/iptcpanel.h b/rtgui/iptcpanel.h index 15d117f87..100904d1a 100644 --- a/rtgui/iptcpanel.h +++ b/rtgui/iptcpanel.h @@ -25,7 +25,7 @@ #include "guiutils.h" #include "toolpanel.h" -class IPTCPanel : +class IPTCPanel final : public Gtk::VBox, public ToolPanel { diff --git a/rtgui/labcurve.cc b/rtgui/labcurve.cc index 491b02c4c..5f4febc0a 100644 --- a/rtgui/labcurve.cc +++ b/rtgui/labcurve.cc @@ -203,7 +203,7 @@ LCurve::LCurve () : FoldableToolPanel(this, "labcurves", M("TP_LABCURVE_LABEL"), for (int i = 0; i < 7; i++) { float R, G, B; - float x = float(i) * (1.0f / 6.0); + float x = i / 6.0; Color::hsv2rgb01(x, 0.5f, 0.5f, R, G, B); milestones.emplace_back(x, R, G, B); } diff --git a/rtgui/labgrid.cc b/rtgui/labgrid.cc index 516dbb825..d8a22b1d9 100644 --- a/rtgui/labgrid.cc +++ b/rtgui/labgrid.cc @@ -209,8 +209,8 @@ bool LabGridArea::on_draw(const ::Cairo::RefPtr &crf) float x, y, z; int ii = i - cells/2; int jj = j - cells/2; - float a = step * (ii + 0.5); - float b = step * (jj + 0.5); + float a = step * (ii + 0.5f); + float b = step * (jj + 0.5f); Color::Lab2XYZ(25000.f, a, b, x, y, z); Color::xyz2srgb(x, y, z, R, G, B); cr->set_source_rgb(R / 65535.f, G / 65535.f, B / 65535.f); @@ -231,10 +231,10 @@ bool LabGridArea::on_draw(const ::Cairo::RefPtr &crf) // drawing the connection line cr->set_antialias(Cairo::ANTIALIAS_DEFAULT); float loa, hia, lob, hib; - loa = .5f * (width + width * low_a); - hia = .5f * (width + width * high_a); - lob = .5f * (height + height * low_b); - hib = .5f * (height + height * high_b); + loa = .5 * (width + width * low_a); + hia = .5 * (width + width * high_a); + lob = .5 * (height + height * low_b); + hib = .5 * (height + height * high_b); cr->set_line_width(2. * double(s)); cr->set_source_rgb(0.6, 0.6, 0.6); cr->move_to(loa, lob); @@ -319,8 +319,8 @@ bool LabGridArea::on_motion_notify_event(GdkEventMotion *event) int height = get_allocated_height() - 2 * inset * s - padding.get_top() - padding.get_bottom(); const float mouse_x = std::min(double(std::max(event->x - inset * s - padding.get_right(), 0.)), double(width)); const float mouse_y = std::min(double(std::max(get_allocated_height() - 1 - event->y - inset * s - padding.get_bottom(), 0.)), double(height)); - const float ma = (2.0 * mouse_x - width) / (float)width; - const float mb = (2.0 * mouse_y - height) / (float)height; + const float ma = (2.f * mouse_x - width) / width; + const float mb = (2.f * mouse_y - height) / height; if (isDragged) { if (litPoint == LOW) { low_a = ma; diff --git a/rtgui/lockablecolorpicker.cc b/rtgui/lockablecolorpicker.cc index 071847424..0a08bb945 100644 --- a/rtgui/lockablecolorpicker.cc +++ b/rtgui/lockablecolorpicker.cc @@ -37,7 +37,7 @@ void LockableColorPicker::updateBackBuffer () int newW, newH; // -------------------- setting some key constants --------------------- - constexpr float circlePadding = 3.f; // keep this value odd + constexpr double circlePadding = 3.0; // keep this value odd constexpr double opacity = 0.62; // --------------------------------------------------------------------- @@ -121,18 +121,18 @@ void LockableColorPicker::updateBackBuffer () bbcr->set_antialias (Cairo::ANTIALIAS_SUBPIXEL); bbcr->set_line_width (0.); - float center = (float)size / 2.f + circlePadding; + double center = static_cast(size) / 2.0 + circlePadding; // black background of the whole color picker bbcr->set_line_width (0.); bbcr->set_source_rgba (0., 0., 0., opacity); - bbcr->arc_negative (center, center, center, 0., (double)rtengine::RT_PI); + bbcr->arc_negative (center, center, center, 0., rtengine::RT_PI); bbcr->line_to (0, 2. * center + textHeight); - bbcr->arc_negative (2. * textPadding, 2. * center + textHeight, 2. * textPadding, (double)rtengine::RT_PI, (double)rtengine::RT_PI / 2.); + bbcr->arc_negative (2. * textPadding, 2. * center + textHeight, 2. * textPadding, rtengine::RT_PI, rtengine::RT_PI / 2.); bbcr->line_to (textWidth, 2. * center + textHeight + 2. * textPadding); - bbcr->arc_negative (textWidth, 2. * center + textHeight, 2. * textPadding, (double)rtengine::RT_PI / 2., 0.); + bbcr->arc_negative (textWidth, 2. * center + textHeight, 2. * textPadding, rtengine::RT_PI / 2., 0.); bbcr->line_to (textWidth + 2. * textPadding, 2. * center + 2. * textPadding); - bbcr->arc_negative (textWidth, 2. * center + 2. * textPadding, 2. * textPadding, 0., (double)rtengine::RT_PI * 1.5); + bbcr->arc_negative (textWidth, 2. * center + 2. * textPadding, 2. * textPadding, 0., rtengine::RT_PI * 1.5); bbcr->line_to (2. * center, 2. * center); bbcr->close_path(); bbcr->set_line_join (Cairo::LINE_JOIN_BEVEL); @@ -222,7 +222,7 @@ void LockableColorPicker::updateBackBuffer () bbcr->set_antialias(Cairo::ANTIALIAS_SUBPIXEL); - float center = (float)size / 2.f + circlePadding; + double center = static_cast(size) / 2. + circlePadding; // light grey circle around the color mark bbcr->arc (center, center, center - circlePadding / 2., 0., 2. * (double)rtengine::RT_PI); diff --git a/rtgui/lockablecolorpicker.h b/rtgui/lockablecolorpicker.h index 77d2e8e9f..baeea41ef 100644 --- a/rtgui/lockablecolorpicker.h +++ b/rtgui/lockablecolorpicker.h @@ -33,7 +33,7 @@ public: virtual void switchPickerVisibility(bool isVisible) = 0; }; -class LockableColorPicker : BackBuffer +class LockableColorPicker final : BackBuffer { public: enum class Size { diff --git a/rtgui/mycurve.cc b/rtgui/mycurve.cc index 7401570c8..d460713fb 100644 --- a/rtgui/mycurve.cc +++ b/rtgui/mycurve.cc @@ -183,7 +183,7 @@ float MyCurve::getVal(LUTf &curve, int x) if (size_t(graphW) == curve.getSize()) { return curve[x]; } else { - return curve.getVal01(float(x) / graphW); + return curve.getVal01(x / graphW); } } diff --git a/rtgui/mydiagonalcurve.cc b/rtgui/mydiagonalcurve.cc index abd339ce0..ce6c6f3ec 100644 --- a/rtgui/mydiagonalcurve.cc +++ b/rtgui/mydiagonalcurve.cc @@ -323,7 +323,7 @@ void MyDiagonalCurve::draw (int handle) // draw the grid lines: cr->set_line_width (1.0 * s); c = style->get_border_color(state); - cr->set_source_rgb (c.get_red(), c.get_green(), c.get_blue()); + cr->set_source_rgba (c.get_red(), c.get_green(), c.get_blue(), 0.3); cr->set_antialias (Cairo::ANTIALIAS_NONE); for (int i = 0; i <= 10; i++) { @@ -358,14 +358,14 @@ void MyDiagonalCurve::draw (int handle) // draw upper and lower bounds if (curve.type == DCT_Parametric && activeParam > 0 && lpoint.getUpperBound() > 1 && upoint.getUpperBound() > 1) { cr->set_source_rgba (1.0, 1.0, 1.0, 0.1); - cr->move_to (graphX, getVal(upoint, 0) * -graphH + graphY); + cr->move_to (graphX, static_cast(getVal(upoint, 0)) * -graphH + graphY); for (int i = 1; i < graphW - 2; ++i) { - cr->line_to ((double)i + graphX, getVal(upoint, i) * -graphH + graphY); + cr->line_to ((double)i + graphX, static_cast(getVal(upoint, i)) * -graphH + graphY); } for (int i = graphW - 3; i >= 0; --i) { - cr->line_to ((double)i + graphX, getVal(lpoint, i) * -graphH + graphY); + cr->line_to ((double)i + graphX, static_cast(getVal(lpoint, i)) * -graphH + graphY); } cr->fill (); @@ -390,21 +390,21 @@ void MyDiagonalCurve::draw (int handle) if (n > 1) { if (pipetteR > -1.f) { cr->set_source_rgba (1., 0., 0., 0.5); // WARNING: assuming that red values are stored in pipetteR, which might not be the case! - cr->move_to (graphX + graphW*pipetteR, graphY + 1. * s); + cr->move_to (graphX + graphW * static_cast(pipetteR), graphY + 1. * s); cr->rel_line_to (0, -graphH - 1. * s); cr->stroke (); } if (pipetteG > -1.f) { cr->set_source_rgba (0., 1., 0., 0.5); // WARNING: assuming that green values are stored in pipetteG, which might not be the case! - cr->move_to (graphX + graphW*pipetteG, graphY + 1. * s); + cr->move_to (graphX + graphW * static_cast(pipetteG), graphY + 1. * s); cr->rel_line_to (0, -graphH - 1. * s); cr->stroke (); } if (pipetteB > -1.f) { cr->set_source_rgba (0., 0., 1., 0.5); // WARNING: assuming that blue values are stored in pipetteB, which might not be the case! - cr->move_to (graphX + graphW*pipetteB, graphY + 1. * s); + cr->move_to (graphX + graphW * static_cast(pipetteB), graphY + 1. * s); cr->rel_line_to (0, -graphH - 1. * s); cr->stroke (); } @@ -414,7 +414,7 @@ void MyDiagonalCurve::draw (int handle) cr->set_line_width (2. * s); c = style->get_color (state); cr->set_source_rgb (c.get_red(), c.get_green(), c.get_blue()); - cr->move_to (graphX + graphW*pipetteVal, graphY + 1. * s); + cr->move_to (graphX + graphW * static_cast(pipetteVal), graphY + 1. * s); cr->rel_line_to (0, -graphH - 1. * s); cr->stroke (); cr->set_line_width (1. * s); @@ -460,7 +460,7 @@ void MyDiagonalCurve::draw (int handle) // draw curve cr->set_source_rgb (c.get_red(), c.get_green(), c.get_blue()); - cr->move_to (graphX, getVal(point, 0) * -graphH + graphY); + cr->move_to (graphX, static_cast(getVal(point, 0)) * -graphH + graphY); for (int i = 1; i < graphW; ++i) { cr->line_to ((double)i + graphX, (double)getVal(point, i) * -graphH + graphY); diff --git a/rtgui/mydiagonalcurve.h b/rtgui/mydiagonalcurve.h index b38373006..b2b83c02e 100644 --- a/rtgui/mydiagonalcurve.h +++ b/rtgui/mydiagonalcurve.h @@ -41,7 +41,7 @@ public: std::vector x, y; // in case of parametric curves the curve parameters are stored in vector x. In other cases these vectors store the coordinates of the bullets. }; -class MyDiagonalCurve : public MyCurve +class MyDiagonalCurve final : public MyCurve { private: IdleRegister idle_register; diff --git a/rtgui/myflatcurve.cc b/rtgui/myflatcurve.cc index 362d34f35..da993987c 100644 --- a/rtgui/myflatcurve.cc +++ b/rtgui/myflatcurve.cc @@ -233,21 +233,21 @@ void MyFlatCurve::draw () if (n > 1) { if (pipetteR > -1.f) { cr->set_source_rgba (1., 0., 0., 0.5); // WARNING: assuming that red values are stored in pipetteR, which might not be the case! - cr->move_to (graphX + graphW*pipetteR, graphY + 1. * s); + cr->move_to (graphX + graphW * static_cast(pipetteR), graphY + 1. * s); cr->rel_line_to (0, -graphH - 1. * s); cr->stroke (); } if (pipetteG > -1.f) { cr->set_source_rgba (0., 1., 0., 0.5); // WARNING: assuming that green values are stored in pipetteG, which might not be the case! - cr->move_to (graphX + graphW*pipetteG, graphY + 1. * s); + cr->move_to (graphX + graphW * static_cast(pipetteG), graphY + 1. * s); cr->rel_line_to (0, -graphH - 1. * s); cr->stroke (); } if (pipetteB > -1.f) { cr->set_source_rgba (0., 0., 1., 0.5); // WARNING: assuming that blue values are stored in pipetteB, which might not be the case! - cr->move_to (graphX + graphW*pipetteB, graphY + 1. * s); + cr->move_to (graphX + graphW * static_cast(pipetteB), graphY + 1. * s); cr->rel_line_to (0, -graphH - 1. * s); cr->stroke (); } @@ -257,7 +257,7 @@ void MyFlatCurve::draw () cr->set_line_width (2. * s); c = style->get_color (state); cr->set_source_rgb (c.get_red(), c.get_green(), c.get_blue()); - cr->move_to (graphX + graphW*pipetteVal, graphY + 1. * s); + cr->move_to (graphX + graphW * static_cast(pipetteVal), graphY + 1. * s); cr->rel_line_to (0, -graphH - 1. * s); cr->stroke (); cr->set_line_width (1. * s); @@ -437,10 +437,10 @@ void MyFlatCurve::draw () // draw curve c = style->get_color(state); cr->set_source_rgb (c.get_red(), c.get_green(), c.get_blue()); - cr->move_to (graphX, getVal(point, 0) * -graphH + graphY); + cr->move_to (graphX, static_cast(getVal(point, 0)) * -graphH + graphY); for (int i = 1; i < graphW; ++i) { - cr->line_to ((double)i + graphX, (double)getVal(point, i) * -graphH + graphY); + cr->line_to ((double)i + graphX, static_cast(getVal(point, i)) * -graphH + graphY); } cr->stroke (); diff --git a/rtgui/myflatcurve.h b/rtgui/myflatcurve.h index 88d651a05..5da1d09ad 100644 --- a/rtgui/myflatcurve.h +++ b/rtgui/myflatcurve.h @@ -66,7 +66,7 @@ public: double centerY; }; -class MyFlatCurve : public MyCurve +class MyFlatCurve final : public MyCurve { protected: diff --git a/rtgui/navigator.h b/rtgui/navigator.h index c1c23c6dc..e9d40e309 100644 --- a/rtgui/navigator.h +++ b/rtgui/navigator.h @@ -25,7 +25,7 @@ class PreviewWindow; -class Navigator : +class Navigator final : public Gtk::Frame, public PointerMotionListener { diff --git a/rtgui/options.cc b/rtgui/options.cc index dcb16e1ea..7ae6c24aa 100644 --- a/rtgui/options.cc +++ b/rtgui/options.cc @@ -590,6 +590,15 @@ void Options::setDefaults() rtSettings.amchroma = 40;//between 20 and 140 low values increase effect..and also artifacts, high values reduces rtSettings.level0_cbdl = 0; rtSettings.level123_cbdl = 30; + rtSettings.itcwb_thres = 34;//between 10 to 55 + rtSettings.itcwb_sort = false; + rtSettings.itcwb_greenrange = 0;//between 0 to 2 + rtSettings.itcwb_greendeltatemp = 2;//between 0 and 4 + rtSettings.itcwb_forceextra = true; + rtSettings.itcwb_sizereference = 3;//between 1 and 5 + rtSettings.itcwb_delta = 1;//between 0 and 5 + rtSettings.itcwb_stdobserver10 = true; + rtSettings.itcwb_precis = 5;//3 or 5 or 9 rtSettings.protectred = 60; rtSettings.protectredh = 0.3; @@ -1494,6 +1503,42 @@ void Options::readFromFile(Glib::ustring fname) rtSettings.level123_cbdl = keyFile.get_double("Color Management", "CBDLlevel123"); } + if (keyFile.has_key("Color Management", "Itcwb_thres")) { + rtSettings.itcwb_thres = keyFile.get_integer("Color Management", "Itcwb_thres"); + } + + if (keyFile.has_key("Color Management", "Itcwb_sort")) { + rtSettings.itcwb_sort = keyFile.get_boolean("Color Management", "Itcwb_sort"); + } + + if (keyFile.has_key("Color Management", "Itcwb_forceextra")) { + rtSettings.itcwb_forceextra = keyFile.get_boolean("Color Management", "Itcwb_forceextra"); + } + + if (keyFile.has_key("Color Management", "Itcwb_stdobserver10")) { + rtSettings.itcwb_stdobserver10 = keyFile.get_boolean("Color Management", "Itcwb_stdobserver10"); + } + + if (keyFile.has_key("Color Management", "Itcwb_greenrange")) { + rtSettings.itcwb_greenrange = keyFile.get_integer("Color Management", "Itcwb_greenrange"); + } + + if (keyFile.has_key("Color Management", "Itcwb_greendeltatemp")) { + rtSettings.itcwb_greendeltatemp = keyFile.get_integer("Color Management", "Itcwb_greendeltatemp"); + } + + if (keyFile.has_key("Color Management", "Itcwb_sizereference")) { + rtSettings.itcwb_sizereference = keyFile.get_integer("Color Management", "Itcwb_sizereference"); + } + + if (keyFile.has_key("Color Management", "Itcwb_delta")) { + rtSettings.itcwb_delta = keyFile.get_integer("Color Management", "Itcwb_delta"); + } + + if (keyFile.has_key("Color Management", "Itcwb_precis")) { + rtSettings.itcwb_precis = keyFile.get_integer("Color Management", "Itcwb_precis"); + } + //if (keyFile.has_key ("Color Management", "Colortoningab")) rtSettings.colortoningab = keyFile.get_double("Color Management", "Colortoningab"); //if (keyFile.has_key ("Color Management", "Decaction")) rtSettings.decaction = keyFile.get_double("Color Management", "Decaction"); @@ -2158,6 +2203,16 @@ void Options::saveToFile(Glib::ustring fname) //keyFile.set_boolean ("Color Management", "Ciebadpixgauss", rtSettings.ciebadpixgauss); keyFile.set_double("Color Management", "CBDLlevel0", rtSettings.level0_cbdl); keyFile.set_double("Color Management", "CBDLlevel123", rtSettings.level123_cbdl); + keyFile.set_integer("Color Management", "Itcwb_thres", rtSettings.itcwb_thres); + keyFile.set_boolean("Color Management", "Itcwb_sort", rtSettings.itcwb_sort); + keyFile.set_integer("Color Management", "Itcwb_greenrange", rtSettings.itcwb_greenrange); + keyFile.set_integer("Color Management", "Itcwb_greendeltatemp", rtSettings.itcwb_greendeltatemp); + keyFile.set_boolean("Color Management", "Itcwb_forceextra", rtSettings.itcwb_forceextra); + keyFile.set_integer("Color Management", "Itcwb_sizereference", rtSettings.itcwb_sizereference); + keyFile.set_integer("Color Management", "Itcwb_delta", rtSettings.itcwb_delta); + keyFile.set_boolean("Color Management", "Itcwb_stdobserver10", rtSettings.itcwb_stdobserver10); + keyFile.set_integer("Color Management", "Itcwb_precis", rtSettings.itcwb_precis); + //keyFile.set_double ("Color Management", "Colortoningab", rtSettings.colortoningab); //keyFile.set_double ("Color Management", "Decaction", rtSettings.decaction); keyFile.set_string("Color Management", "ClutsDirectory", clutsDir); @@ -2270,8 +2325,18 @@ void Options::load(bool lightweight) const gchar* path; Glib::ustring dPath; +#ifdef __APPLE__ + // Build Application Support directory path for macOS. + const char* homedir = g_getenv("HOME"); // This returns the current container data dir in ~/Library + std::string homebuf{homedir}; + int homelength = strlen(homebuf.c_str()); + homebuf[homelength-44] = '\0'; // Terminate string after ${HOME}/Library + std::string homeconfig{homebuf}; + std::strcat(&homeconfig[0], "/Application Support/RawTherapee/config"); + path = homeconfig.c_str(); +#else path = g_getenv("RT_SETTINGS"); - +#endif if (path != nullptr) { rtdir = Glib::ustring(path); @@ -2280,6 +2345,7 @@ void Options::load(bool lightweight) throw Error(msg); } } else { + #ifdef WIN32 WCHAR pathW[MAX_PATH] = {0}; @@ -2312,9 +2378,14 @@ void Options::load(bool lightweight) rtdir = Glib::build_filename(argv0, "mysettings"); } - // Modify the path of the cache folder to the one provided in RT_CACHE environment variable + // Modify the path of the cache folder to the one provided in RT_CACHE environment variable. Build the cache folder name in macOS. +#ifdef __APPLE__ + std::string homecache{homebuf}; + std::strcat(&homecache[0], "/Application Support/RawTherapee/cache"); + path = homecache.c_str(); +#else path = g_getenv("RT_CACHE"); - +#endif if (path != nullptr) { cacheBaseDir = Glib::ustring(path); @@ -2323,6 +2394,7 @@ void Options::load(bool lightweight) throw Error(msg); } } + // No environment variable provided, so falling back to the multi user mode, if enabled else if (options.multiUser) { #ifdef WIN32 diff --git a/rtgui/options.h b/rtgui/options.h index c0ed2138b..b8a71c9cb 100644 --- a/rtgui/options.h +++ b/rtgui/options.h @@ -20,7 +20,15 @@ #include #include +#if defined __has_include +#if __has_include() #include +#else +#include +#endif +#else +#include +#endif #include "../rtengine/settings.h" #include diff --git a/rtgui/paramsedited.cc b/rtgui/paramsedited.cc index 9d11d8aad..09b3566bd 100644 --- a/rtgui/paramsedited.cc +++ b/rtgui/paramsedited.cc @@ -219,6 +219,7 @@ void ParamsEdited::set(bool v) colorappearance.adaplum = v; colorappearance.badpixsl = v; colorappearance.wbmodel = v; + colorappearance.illum = v; colorappearance.algo = v; colorappearance.jlight = v; @@ -243,10 +244,12 @@ void ParamsEdited::set(bool v) colorappearance.curveMode2 = v; colorappearance.curveMode3 = v; colorappearance.tempout = v; + colorappearance.autotempout = v; colorappearance.greenout = v; colorappearance.ybout = v; colorappearance.tempsc = v; colorappearance.greensc = v; + colorappearance.presetcat02 = v; //colorBoost.amount = v; //colorBoost.avoidclip = v; @@ -496,8 +499,19 @@ void ParamsEdited::set(bool v) wavelet.bluemed = v; wavelet.bluelow = v; wavelet.lipst = v; + wavelet.ballum = v; + wavelet.balchrom = v; + wavelet.chromfi = v; + wavelet.chromco = v; + wavelet.mergeL = v; + wavelet.mergeC = v; + wavelet.softrad = v; + wavelet.softradend = v; wavelet.Medgreinf = v; + wavelet.ushamethod = v; wavelet.avoid = v; + wavelet.showmask = v; + wavelet.oldsh = v; wavelet.tmr = v; wavelet.Lmethod = v; wavelet.CLmethod = v; @@ -512,10 +526,17 @@ void ParamsEdited::set(bool v) wavelet.TMmethod = v; wavelet.HSmethod = v; wavelet.Dirmethod = v; - wavelet.rescon = v; + wavelet.sigma = v; + wavelet.sigma = v; + wavelet.offset = v; + wavelet.lowthr = v; wavelet.resconH = v; wavelet.reschro = v; + wavelet.resblur = v; + wavelet.resblurc = v; wavelet.tmrs = v; + wavelet.edgs = v; + wavelet.scale = v; wavelet.gamma = v; wavelet.sup = v; wavelet.sky = v; @@ -531,21 +552,26 @@ void ParamsEdited::set(bool v) wavelet.chro = v; wavelet.contrast = v; wavelet.edgrad = v; + wavelet.edgeffect = v; wavelet.edgval = v; wavelet.edgthresh = v; wavelet.thr = v; wavelet.thrH = v; + wavelet.radius = v; wavelet.skinprotect = v; wavelet.hueskin = v; wavelet.hueskin2 = v; wavelet.hllev = v; wavelet.bllev = v; wavelet.edgcont = v; + wavelet.chrwav = v; + wavelet.bluwav = v; wavelet.level0noise = v; wavelet.level1noise = v; wavelet.level2noise = v; wavelet.level3noise = v; wavelet.ccwcurve = v; + wavelet.blcurve = v; wavelet.opacityCurveRG = v; wavelet.opacityCurveBY = v; wavelet.opacityCurveW = v; @@ -561,9 +587,11 @@ void ParamsEdited::set(bool v) // wavelet.enaedge = v; // wavelet.enares = v; wavelet.expfinal = v; + wavelet.expclari = v; wavelet.expcontrast = v; wavelet.expchroma = v; wavelet.expedge = v; + wavelet.expbl = v; wavelet.expresid = v; wavelet.exptoning = v; wavelet.expnoise = v; @@ -608,6 +636,7 @@ void ParamsEdited::set(bool v) filmNegative.redRatio = v; filmNegative.greenExp = v; filmNegative.blueRatio = v; + filmNegative.baseValues = v; exif = v; iptc = v; @@ -812,6 +841,7 @@ void ParamsEdited::initFrom(const std::vector& colorappearance.adaplum = colorappearance.adaplum && p.colorappearance.adaplum == other.colorappearance.adaplum; colorappearance.badpixsl = colorappearance.badpixsl && p.colorappearance.badpixsl == other.colorappearance.badpixsl; colorappearance.wbmodel = colorappearance.wbmodel && p.colorappearance.wbmodel == other.colorappearance.wbmodel; + colorappearance.illum = colorappearance.illum && p.colorappearance.illum == other.colorappearance.illum; colorappearance.algo = colorappearance.algo && p.colorappearance.algo == other.colorappearance.algo; colorappearance.jlight = colorappearance.jlight && p.colorappearance.jlight == other.colorappearance.jlight; colorappearance.qbright = colorappearance.qbright && p.colorappearance.qbright == other.colorappearance.qbright; @@ -835,10 +865,12 @@ void ParamsEdited::initFrom(const std::vector& colorappearance.curveMode2 = colorappearance.curveMode2 && p.colorappearance.curveMode2 == other.colorappearance.curveMode2; colorappearance.curveMode3 = colorappearance.curveMode3 && p.colorappearance.curveMode3 == other.colorappearance.curveMode3; colorappearance.tempout = colorappearance.tempout && p.colorappearance.tempout == other.colorappearance.tempout; + colorappearance.autotempout = colorappearance.autotempout && p.colorappearance.autotempout == other.colorappearance.autotempout; colorappearance.greenout = colorappearance.greenout && p.colorappearance.greenout == other.colorappearance.greenout; colorappearance.ybout = colorappearance.ybout && p.colorappearance.ybout == other.colorappearance.ybout; colorappearance.tempsc = colorappearance.tempsc && p.colorappearance.tempsc == other.colorappearance.tempsc; colorappearance.greensc = colorappearance.greensc && p.colorappearance.greensc == other.colorappearance.greensc; + colorappearance.presetcat02 = colorappearance.presetcat02 && p.colorappearance.presetcat02 == other.colorappearance.presetcat02; //colorBoost.amount = colorBoost.amount && p.colorBoost.amount == other.colorBoost.amount; //colorBoost.avoidclip = colorBoost.avoidclip && p.colorBoost.avoidclip == other.colorBoost.avoidclip; @@ -1091,8 +1123,19 @@ void ParamsEdited::initFrom(const std::vector& wavelet.greenlow = wavelet.greenlow && p.wavelet.greenlow == other.wavelet.greenlow; wavelet.bluelow = wavelet.bluelow && p.wavelet.bluelow == other.wavelet.bluelow; wavelet.lipst = wavelet.lipst && p.wavelet.lipst == other.wavelet.lipst; - wavelet.Medgreinf = wavelet.Medgreinf && p.wavelet.Medgreinf == other.wavelet.Medgreinf; + wavelet.bluehigh = wavelet.bluehigh && p.wavelet.bluehigh == other.wavelet.bluehigh; + wavelet.ballum = wavelet.ballum && p.wavelet.ballum == other.wavelet.ballum; + wavelet.balchrom = wavelet.balchrom && p.wavelet.balchrom == other.wavelet.balchrom; + wavelet.chromfi = wavelet.chromfi && p.wavelet.chromfi == other.wavelet.chromfi; + wavelet.chromco = wavelet.chromco && p.wavelet.chromco == other.wavelet.chromco; + wavelet.mergeL = wavelet.mergeL && p.wavelet.mergeL == other.wavelet.mergeL; + wavelet.mergeC = wavelet.mergeC && p.wavelet.mergeC == other.wavelet.mergeC; + wavelet.softrad = wavelet.softrad && p.wavelet.softrad == other.wavelet.softrad; + wavelet.softradend = wavelet.softradend && p.wavelet.softradend == other.wavelet.softradend; + wavelet.ushamethod = wavelet.ushamethod && p.wavelet.ushamethod == other.wavelet.ushamethod; wavelet.avoid = wavelet.avoid && p.wavelet.avoid == other.wavelet.avoid; + wavelet.showmask = wavelet.showmask && p.wavelet.showmask == other.wavelet.showmask; + wavelet.oldsh = wavelet.oldsh && p.wavelet.oldsh == other.wavelet.oldsh; wavelet.tmr = wavelet.tmr && p.wavelet.tmr == other.wavelet.tmr; wavelet.Lmethod = wavelet.Lmethod && p.wavelet.Lmethod == other.wavelet.Lmethod; wavelet.CLmethod = wavelet.CLmethod && p.wavelet.CLmethod == other.wavelet.CLmethod; @@ -1107,10 +1150,17 @@ void ParamsEdited::initFrom(const std::vector& wavelet.TMmethod = wavelet.TMmethod && p.wavelet.TMmethod == other.wavelet.TMmethod; wavelet.HSmethod = wavelet.HSmethod && p.wavelet.HSmethod == other.wavelet.HSmethod; wavelet.Dirmethod = wavelet.Dirmethod && p.wavelet.Dirmethod == other.wavelet.Dirmethod; + wavelet.sigma = wavelet.sigma && p.wavelet.sigma == other.wavelet.sigma; + wavelet.offset = wavelet.offset && p.wavelet.offset == other.wavelet.offset; + wavelet.lowthr = wavelet.lowthr && p.wavelet.lowthr == other.wavelet.lowthr; wavelet.rescon = wavelet.rescon && p.wavelet.rescon == other.wavelet.rescon; wavelet.resconH = wavelet.resconH && p.wavelet.resconH == other.wavelet.resconH; wavelet.reschro = wavelet.reschro && p.wavelet.reschro == other.wavelet.reschro; + wavelet.resblur = wavelet.resblur && p.wavelet.resblur == other.wavelet.resblur; + wavelet.resblurc = wavelet.resblurc && p.wavelet.resblurc == other.wavelet.resblurc; wavelet.tmrs = wavelet.tmrs && p.wavelet.tmrs == other.wavelet.tmrs; + wavelet.edgs = wavelet.edgs && p.wavelet.edgs == other.wavelet.edgs; + wavelet.scale = wavelet.scale && p.wavelet.scale == other.wavelet.scale; wavelet.gamma = wavelet.gamma && p.wavelet.gamma == other.wavelet.gamma; wavelet.sup = wavelet.sup && p.wavelet.sup == other.wavelet.sup; wavelet.sky = wavelet.sky && p.wavelet.sky == other.wavelet.sky; @@ -1126,15 +1176,19 @@ void ParamsEdited::initFrom(const std::vector& wavelet.chro = wavelet.chro && p.wavelet.chro == other.wavelet.chro; wavelet.contrast = wavelet.contrast && p.wavelet.contrast == other.wavelet.contrast; wavelet.edgrad = wavelet.edgrad && p.wavelet.edgrad == other.wavelet.edgrad; + wavelet.edgeffect = wavelet.edgeffect && p.wavelet.edgeffect == other.wavelet.edgeffect; wavelet.edgval = wavelet.edgval && p.wavelet.edgval == other.wavelet.edgval; wavelet.edgthresh = wavelet.edgthresh && p.wavelet.edgthresh == other.wavelet.edgthresh; wavelet.thr = wavelet.thr && p.wavelet.thr == other.wavelet.thr; wavelet.thrH = wavelet.thrH && p.wavelet.thrH == other.wavelet.thrH; + wavelet.radius = wavelet.radius && p.wavelet.radius == other.wavelet.radius; wavelet.hueskin = wavelet.hueskin && p.wavelet.hueskin == other.wavelet.hueskin; wavelet.hueskin2 = wavelet.hueskin2 && p.wavelet.hueskin2 == other.wavelet.hueskin2; wavelet.hllev = wavelet.hllev && p.wavelet.hllev == other.wavelet.hllev; wavelet.bllev = wavelet.bllev && p.wavelet.bllev == other.wavelet.bllev; wavelet.edgcont = wavelet.edgcont && p.wavelet.edgcont == other.wavelet.edgcont; + wavelet.chrwav = wavelet.chrwav && p.wavelet.chrwav == other.wavelet.chrwav; + wavelet.bluwav = wavelet.bluwav && p.wavelet.bluwav == other.wavelet.bluwav; wavelet.level0noise = wavelet.level0noise && p.wavelet.level0noise == other.wavelet.level0noise; wavelet.level1noise = wavelet.level1noise && p.wavelet.level1noise == other.wavelet.level1noise; wavelet.level2noise = wavelet.level2noise && p.wavelet.level2noise == other.wavelet.level2noise; @@ -1142,6 +1196,7 @@ void ParamsEdited::initFrom(const std::vector& wavelet.pastlev = wavelet.pastlev && p.wavelet.pastlev == other.wavelet.pastlev; wavelet.satlev = wavelet.satlev && p.wavelet.satlev == other.wavelet.satlev; wavelet.ccwcurve = wavelet.ccwcurve && p.wavelet.ccwcurve == other.wavelet.ccwcurve; + wavelet.blcurve = wavelet.blcurve && p.wavelet.blcurve == other.wavelet.blcurve; wavelet.opacityCurveRG = wavelet.opacityCurveRG && p.wavelet.opacityCurveRG == other.wavelet.opacityCurveRG; wavelet.opacityCurveBY = wavelet.opacityCurveBY && p.wavelet.opacityCurveBY == other.wavelet.opacityCurveBY; wavelet.opacityCurveW = wavelet.opacityCurveW && p.wavelet.opacityCurveW == other.wavelet.opacityCurveW; @@ -1154,10 +1209,12 @@ void ParamsEdited::initFrom(const std::vector& wavelet.expcontrast = wavelet.expcontrast && p.wavelet.expcontrast == other.wavelet.expcontrast; wavelet.expchroma = wavelet.expchroma && p.wavelet.expchroma == other.wavelet.expchroma; wavelet.expedge = wavelet.expedge && p.wavelet.expedge == other.wavelet.expedge; + wavelet.expbl = wavelet.expbl && p.wavelet.expbl == other.wavelet.expbl; wavelet.expresid = wavelet.expresid && p.wavelet.expresid == other.wavelet.expresid; wavelet.expfinal = wavelet.expfinal && p.wavelet.expfinal == other.wavelet.expfinal; wavelet.exptoning = wavelet.exptoning && p.wavelet.exptoning == other.wavelet.exptoning; wavelet.expnoise = wavelet.expnoise && p.wavelet.expnoise == other.wavelet.expnoise; + wavelet.expclari = wavelet.expclari && p.wavelet.expclari == other.wavelet.expclari; for (int level = 0; level < 9; ++level) { wavelet.c[level] = wavelet.c[level] && p.wavelet.c[level] == other.wavelet.c[level]; @@ -1195,6 +1252,9 @@ void ParamsEdited::initFrom(const std::vector& filmNegative.redRatio = filmNegative.redRatio && p.filmNegative.redRatio == other.filmNegative.redRatio; filmNegative.greenExp = filmNegative.greenExp && p.filmNegative.greenExp == other.filmNegative.greenExp; filmNegative.blueRatio = filmNegative.blueRatio && p.filmNegative.blueRatio == other.filmNegative.blueRatio; + filmNegative.baseValues = filmNegative.baseValues && p.filmNegative.redBase == other.filmNegative.redBase + && p.filmNegative.greenBase == other.filmNegative.greenBase + && p.filmNegative.blueBase == other.filmNegative.blueBase; // How the hell can we handle that??? // exif = exif && p.exif==other.exif @@ -2010,6 +2070,10 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.colorappearance.wbmodel = mods.colorappearance.wbmodel; } + if (colorappearance.illum) { + toEdit.colorappearance.illum = mods.colorappearance.illum; + } + if (colorappearance.algo) { toEdit.colorappearance.algo = mods.colorappearance.algo; } @@ -2018,6 +2082,10 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.colorappearance.tempout = mods.colorappearance.tempout; } + if (colorappearance.autotempout) { + toEdit.colorappearance.autotempout = mods.colorappearance.autotempout; + } + if (colorappearance.greenout) { toEdit.colorappearance.greenout = mods.colorappearance.greenout; } @@ -2087,6 +2155,10 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.colorappearance.tonecie = mods.colorappearance.tonecie; } + if (colorappearance.presetcat02) { + toEdit.colorappearance.presetcat02 = mods.colorappearance.presetcat02; + } + // if (colorappearance.sharpcie) toEdit.colorappearance.sharpcie = mods.colorappearance.sharpcie; if (impulseDenoise.enabled) { toEdit.impulseDenoise.enabled = mods.impulseDenoise.enabled; @@ -2947,6 +3019,38 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.wavelet.bluelow = mods.wavelet.bluelow; } + if (wavelet.ballum) { + toEdit.wavelet.ballum = mods.wavelet.ballum; + } + + if (wavelet.balchrom) { + toEdit.wavelet.balchrom = mods.wavelet.balchrom; + } + + if (wavelet.chromfi) { + toEdit.wavelet.chromfi = mods.wavelet.chromfi; + } + + if (wavelet.chromco) { + toEdit.wavelet.chromco = mods.wavelet.chromco; + } + + if (wavelet.mergeL) { + toEdit.wavelet.mergeL = mods.wavelet.mergeL; + } + + if (wavelet.mergeC) { + toEdit.wavelet.mergeC = mods.wavelet.mergeC; + } + + if (wavelet.softrad) { + toEdit.wavelet.softrad = mods.wavelet.softrad; + } + + if (wavelet.softradend) { + toEdit.wavelet.softradend = mods.wavelet.softradend; + } + if (wavelet.lipst) { toEdit.wavelet.lipst = mods.wavelet.lipst; } @@ -2955,10 +3059,22 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.wavelet.Medgreinf = mods.wavelet.Medgreinf; } + if (wavelet.ushamethod) { + toEdit.wavelet.ushamethod = mods.wavelet.ushamethod; + } + if (wavelet.avoid) { toEdit.wavelet.avoid = mods.wavelet.avoid; } + if (wavelet.showmask) { + toEdit.wavelet.showmask = mods.wavelet.showmask; + } + + if (wavelet.oldsh) { + toEdit.wavelet.oldsh = mods.wavelet.oldsh; + } + if (wavelet.tmr) { toEdit.wavelet.tmr = mods.wavelet.tmr; } @@ -3031,6 +3147,10 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.wavelet.thrH = dontforceSet && options.baBehav[ADDSET_WA_THRRH] ? toEdit.wavelet.thrH + mods.wavelet.thrH : mods.wavelet.thrH; } + if (wavelet.radius) { + toEdit.wavelet.radius = dontforceSet && options.baBehav[ADDSET_WA_RADIUS] ? toEdit.wavelet.radius + mods.wavelet.radius : mods.wavelet.radius; + } + if (wavelet.sup) { toEdit.wavelet.sup = mods.wavelet.sup; } @@ -3047,6 +3167,14 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.wavelet.edgcont = mods.wavelet.edgcont; } + if (wavelet.chrwav) { + toEdit.wavelet.chrwav = mods.wavelet.chrwav; + } + + if (wavelet.bluwav) { + toEdit.wavelet.bluwav = mods.wavelet.bluwav; + } + if (wavelet.level0noise) { toEdit.wavelet.level0noise = mods.wavelet.level0noise; } @@ -3075,6 +3203,10 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.wavelet.ccwcurve = mods.wavelet.ccwcurve; } + if (wavelet.blcurve) { + toEdit.wavelet.blcurve = mods.wavelet.blcurve; + } + if (wavelet.opacityCurveRG) { toEdit.wavelet.opacityCurveRG = mods.wavelet.opacityCurveRG; } @@ -3116,6 +3248,10 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.wavelet.expedge = mods.wavelet.expedge; } + if (wavelet.expbl) { + toEdit.wavelet.expbl = mods.wavelet.expbl; + } + if (wavelet.expresid) { toEdit.wavelet.expresid = mods.wavelet.expresid; } @@ -3124,6 +3260,10 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.wavelet.expfinal = mods.wavelet.expfinal; } + if (wavelet.expclari) { + toEdit.wavelet.expclari = mods.wavelet.expclari; + } + if (wavelet.exptoning) { toEdit.wavelet.exptoning = mods.wavelet.exptoning; } @@ -3164,6 +3304,30 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.wavelet.edgeampli = mods.wavelet.edgeampli; } + if (wavelet.sigma) { + toEdit.wavelet.sigma = mods.wavelet.sigma; + } + + if (wavelet.offset) { + toEdit.wavelet.offset = mods.wavelet.offset; + } + + if (wavelet.lowthr) { + toEdit.wavelet.lowthr = mods.wavelet.lowthr; + } + + if (wavelet.resblur) { + toEdit.wavelet.resblur = mods.wavelet.resblur; + } + + if (wavelet.edgeffect) { + toEdit.wavelet.edgeffect = mods.wavelet.edgeffect; + } + + if (wavelet.resblurc) { + toEdit.wavelet.resblurc = mods.wavelet.resblurc; + } + if (wavelet.resconH) { toEdit.wavelet.resconH = dontforceSet && options.baBehav[ADDSET_WA_RESCONH] ? toEdit.wavelet.resconH + mods.wavelet.resconH : mods.wavelet.resconH; } @@ -3176,6 +3340,14 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.wavelet.tmrs = dontforceSet && options.baBehav[ADDSET_WA_TMRS] ? toEdit.wavelet.tmrs + mods.wavelet.tmrs : mods.wavelet.tmrs; } + if (wavelet.edgs) { + toEdit.wavelet.edgs = dontforceSet && options.baBehav[ADDSET_WA_EDGS] ? toEdit.wavelet.edgs + mods.wavelet.edgs : mods.wavelet.edgs; + } + + if (wavelet.scale) { + toEdit.wavelet.scale = dontforceSet && options.baBehav[ADDSET_WA_SCALE] ? toEdit.wavelet.scale + mods.wavelet.scale : mods.wavelet.scale; + } + if (wavelet.gamma) { toEdit.wavelet.gamma = dontforceSet && options.baBehav[ADDSET_WA_GAMMA] ? toEdit.wavelet.gamma + mods.wavelet.gamma : mods.wavelet.gamma; } @@ -3340,6 +3512,12 @@ void ParamsEdited::combine(rtengine::procparams::ProcParams& toEdit, const rteng toEdit.filmNegative.blueRatio = mods.filmNegative.blueRatio; } + if (filmNegative.baseValues) { + toEdit.filmNegative.redBase = mods.filmNegative.redBase; + toEdit.filmNegative.greenBase = mods.filmNegative.greenBase; + toEdit.filmNegative.blueBase = mods.filmNegative.blueBase; + } + // Exif changes are added to the existing ones if (exif) { for (procparams::ExifPairs::const_iterator i = mods.exif.begin(); i != mods.exif.end(); ++i) { @@ -3386,7 +3564,7 @@ bool RetinexParamsEdited::isUnchanged() const bool FilmNegativeParamsEdited::isUnchanged() const { - return enabled && redRatio && greenExp && blueRatio; + return enabled && redRatio && greenExp && blueRatio && baseValues; } bool CaptureSharpeningParamsEdited::isUnchanged() const diff --git a/rtgui/paramsedited.h b/rtgui/paramsedited.h index 9c9f23939..edfdbeafb 100644 --- a/rtgui/paramsedited.h +++ b/rtgui/paramsedited.h @@ -275,6 +275,7 @@ struct ColorAppearanceParamsEdited { bool ybscen; bool badpixsl; bool wbmodel; + bool illum; bool algo; bool jlight; bool qbright; @@ -290,10 +291,12 @@ struct ColorAppearanceParamsEdited { bool datacie; bool tonecie; bool tempout; + bool autotempout; bool greenout; bool ybout; bool tempsc; bool greensc; + bool presetcat02; }; struct DirPyrDenoiseParamsEdited { @@ -515,7 +518,10 @@ struct WaveletParamsEdited { bool cbenab; bool lipst; bool Medgreinf; + bool ushamethod; bool avoid; + bool showmask; + bool oldsh; bool tmr; bool c[9]; bool ch[9]; @@ -532,10 +538,17 @@ struct WaveletParamsEdited { bool Tilesmethod; bool daubcoeffmethod; bool Dirmethod; + bool sigma; + bool offset; + bool lowthr; bool rescon; bool resconH; bool reschro; + bool resblur; + bool resblurc; bool tmrs; + bool edgs; + bool scale; bool gamma; bool sup; bool sky; @@ -551,21 +564,26 @@ struct WaveletParamsEdited { bool chroma; bool contrast; bool edgrad; + bool edgeffect; bool edgval; bool edgthresh; bool thr; bool thrH; + bool radius; bool skinprotect; bool hueskin; bool hueskin2; bool hllev; bool bllev; bool edgcont; + bool chrwav; + bool bluwav; bool level0noise; bool level1noise; bool level2noise; bool level3noise; bool ccwcurve; + bool blcurve; bool opacityCurveBY; bool opacityCurveRG; bool opacityCurveW; @@ -581,13 +599,23 @@ struct WaveletParamsEdited { bool bluemed; bool greenhigh; bool bluehigh; + bool ballum; + bool balchrom; + bool chromfi; + bool chromco; + bool mergeL; + bool mergeC; + bool softrad; + bool softradend; bool expcontrast; bool expchroma; bool expedge; + bool expbl; bool expresid; bool expfinal; bool exptoning; bool expnoise; + bool expclari; }; struct DirPyrEqualizerParamsEdited { @@ -712,6 +740,7 @@ struct FilmNegativeParamsEdited { bool redRatio; bool greenExp; bool blueRatio; + bool baseValues; bool isUnchanged() const; }; diff --git a/rtgui/partialpastedlg.cc b/rtgui/partialpastedlg.cc index 22f608ae4..b31852af2 100644 --- a/rtgui/partialpastedlg.cc +++ b/rtgui/partialpastedlg.cc @@ -986,6 +986,7 @@ void PartialPasteDlg::applyPaste (rtengine::procparams::ProcParams* dstPP, Param filterPE.filmNegative.redRatio = falsePE.filmNegative.redRatio; filterPE.filmNegative.greenExp = falsePE.filmNegative.greenExp; filterPE.filmNegative.blueRatio = falsePE.filmNegative.blueRatio; + filterPE.filmNegative.baseValues = falsePE.filmNegative.baseValues; } if (!captureSharpening->get_active ()) { diff --git a/rtgui/partialpastedlg.h b/rtgui/partialpastedlg.h index 1403e7c1b..75e18e83c 100644 --- a/rtgui/partialpastedlg.h +++ b/rtgui/partialpastedlg.h @@ -34,7 +34,7 @@ class ProcParams; struct ParamsEdited; -class PartialPasteDlg : public Gtk::Dialog +class PartialPasteDlg final : public Gtk::Dialog { public: diff --git a/rtgui/pdsharpening.cc b/rtgui/pdsharpening.cc index 18fa7aa2a..8bbf19620 100644 --- a/rtgui/pdsharpening.cc +++ b/rtgui/pdsharpening.cc @@ -58,7 +58,7 @@ PdSharpening::PdSharpening() : pack_start(*hb); Gtk::VBox* rld = Gtk::manage(new Gtk::VBox()); - dradius = Gtk::manage(new Adjuster(M("TP_SHARPENING_RADIUS"), 0.4, 1.15, 0.01, 0.75)); + dradius = Gtk::manage(new Adjuster(M("TP_SHARPENING_RADIUS"), 0.4, 2.0, 0.01, 0.75)); dradius->addAutoButton(); dradius->setAutoValue(true); dradiusOffset = Gtk::manage(new Adjuster(M("TP_SHARPENING_RADIUS_BOOST"), -0.5, 0.5, 0.01, 0.0)); diff --git a/rtgui/popupbutton.h b/rtgui/popupbutton.h index 87b1b73a6..a67339a9f 100644 --- a/rtgui/popupbutton.h +++ b/rtgui/popupbutton.h @@ -24,7 +24,7 @@ #include "popupcommon.h" -class PopUpButton : +class PopUpButton final : public Gtk::Button, public PopUpCommon { diff --git a/rtgui/ppversion.h b/rtgui/ppversion.h index 89f93ed44..6a670733b 100644 --- a/rtgui/ppversion.h +++ b/rtgui/ppversion.h @@ -1,11 +1,13 @@ #pragma once // This number has to be incremented whenever the PP3 file format is modified or the behaviour of a tool changes -#define PPVERSION 346 +#define PPVERSION 347 #define PPVERSION_AEXP 301 //value of PPVERSION when auto exposure algorithm was modified /* Log of version changes + 347 2019-11-17 + added special values in filmNegative for backwards compatibility with previous channel scaling method 346 2019-01-01 changed microcontrast uniformity 345 2018-10-21 diff --git a/rtgui/preferences.cc b/rtgui/preferences.cc index 2b36b792f..4edb4f2e2 100644 --- a/rtgui/preferences.cc +++ b/rtgui/preferences.cc @@ -395,8 +395,11 @@ Gtk::Widget* Preferences::getBatchProcPanel () appendBehavList (mi, M ("TP_WAVELET_THR"), ADDSET_WA_THRR, true); appendBehavList (mi, M ("TP_WAVELET_RESCONH"), ADDSET_WA_RESCONH, true); appendBehavList (mi, M ("TP_WAVELET_THRH"), ADDSET_WA_THRRH, true); + appendBehavList (mi, M ("TP_WAVELET_RADIUS"), ADDSET_WA_RADIUS, true); appendBehavList (mi, M ("TP_WAVELET_RESCHRO"), ADDSET_WA_RESCHRO, true); appendBehavList (mi, M ("TP_WAVELET_TMSTRENGTH"), ADDSET_WA_TMRS, true); + appendBehavList (mi, M ("TP_WAVELET_TMEDGS"), ADDSET_WA_EDGS, true); + appendBehavList (mi, M ("TP_WAVELET_TMSCALE"), ADDSET_WA_SCALE, true); appendBehavList (mi, M ("TP_WAVELET_SKY"), ADDSET_WA_SKYPROTECT, true); appendBehavList (mi, M ("TP_WAVELET_CONTRA"), ADDSET_WA_CONTRAST, true); appendBehavList (mi, M ("TP_WAVELET_STRENGTH"), ADDSET_WA_STRENGTH, true); @@ -781,7 +784,7 @@ Gtk::Widget* Preferences::getColorManPanel () const std::vector profiles = rtengine::ICCStore::getInstance ()->getProfiles (rtengine::ICCStore::ProfileType::MONITOR); - for (const auto profile : profiles) { + for (const auto& profile : profiles) { if (profile.find("file:") != 0) { std::string fileis_RTv4 = profile.substr(0, 4); @@ -850,7 +853,7 @@ Gtk::Widget* Preferences::getColorManPanel () const std::vector prtprofiles = rtengine::ICCStore::getInstance ()->getProfiles (rtengine::ICCStore::ProfileType::PRINTER); - for (const auto prtprofile : prtprofiles) { + for (const auto& prtprofile : prtprofiles) { prtProfile->append (prtprofile); } diff --git a/rtgui/preferences.h b/rtgui/preferences.h index 76a104ffa..a6cbe7939 100644 --- a/rtgui/preferences.h +++ b/rtgui/preferences.h @@ -29,7 +29,7 @@ class RTWindow; class Splash; -class Preferences : +class Preferences final : public Gtk::Dialog, public ProfileStoreListener { diff --git a/rtgui/previewhandler.h b/rtgui/previewhandler.h index d9c91f6ad..4fd9a1e82 100644 --- a/rtgui/previewhandler.h +++ b/rtgui/previewhandler.h @@ -44,7 +44,7 @@ struct PreviewHandlerIdleHelper { int pending; }; -class PreviewHandler : public rtengine::PreviewImageListener, public rtengine::NonCopyable +class PreviewHandler final : public rtengine::PreviewImageListener, public rtengine::NonCopyable { private: friend int setImageUI (void* data); diff --git a/rtgui/previewloader.h b/rtgui/previewloader.h index 9a74ee2eb..a8032fcaf 100644 --- a/rtgui/previewloader.h +++ b/rtgui/previewloader.h @@ -20,10 +20,15 @@ #include -#include - #include "../rtengine/noncopyable.h" +namespace Glib +{ + +class ustring; + +} + class FileBrowserEntry; class PreviewLoaderListener diff --git a/rtgui/profilepanel.h b/rtgui/profilepanel.h index b3c968682..c3a125c49 100644 --- a/rtgui/profilepanel.h +++ b/rtgui/profilepanel.h @@ -49,7 +49,7 @@ class PartialProfile; } class RTImage; -class ProfilePanel : +class ProfilePanel final : public Gtk::Grid, public PParamsChangeListener, public ProfileStoreListener, diff --git a/rtgui/profilestorecombobox.cc b/rtgui/profilestorecombobox.cc index bb294189f..a6085e7a9 100644 --- a/rtgui/profilestorecombobox.cc +++ b/rtgui/profilestorecombobox.cc @@ -182,7 +182,7 @@ Gtk::TreeIter ProfileStoreComboBox::findRowFromEntry (const ProfileStoreEntry *p Gtk::TreeIter ProfileStoreComboBox::findRowFromFullPath_ (Gtk::TreeModel::Children childs, int parentFolderId, const Glib::ustring &name) const { - for (const auto iter : childs) { + for (const auto& iter : childs) { const Gtk::TreeModel::Row row = *iter; // Hombre: is there a smarter way of knowing if this row has childs? const ProfileStoreEntry *pse = row[methodColumns.profileStoreEntry]; @@ -309,7 +309,7 @@ Gtk::TreeIter ProfileStoreComboBox::getRowFromLabel (const Glib::ustring &name) const Gtk::TreeModel::Children childs = refTreeModel->children(); if (!name.empty()) { - for (const auto iter : childs) { + for (const auto& iter : childs) { const Gtk::TreeModel::Row currRow = *iter; const ProfileStoreEntry *pse = currRow[methodColumns.profileStoreEntry]; diff --git a/rtgui/progressconnector.h b/rtgui/progressconnector.h index f4d1d8f7e..90c9f67f0 100644 --- a/rtgui/progressconnector.h +++ b/rtgui/progressconnector.h @@ -28,7 +28,7 @@ #undef THREAD_PRIORITY_NORMAL -class PLDBridge : +class PLDBridge final : public rtengine::ProgressListener { public: diff --git a/rtgui/renamedlg.h b/rtgui/renamedlg.h index f9447fbac..3c92965f8 100644 --- a/rtgui/renamedlg.h +++ b/rtgui/renamedlg.h @@ -26,7 +26,7 @@ class CacheImageData; -class RenameDialog : +class RenameDialog final : public Gtk::Dialog { diff --git a/rtgui/retinex.cc b/rtgui/retinex.cc index c78be375f..2fdd8f319 100644 --- a/rtgui/retinex.cc +++ b/rtgui/retinex.cc @@ -278,7 +278,7 @@ Retinex::Retinex () : FoldableToolPanel (this, "retinex", M ("TP_RETINEX_LABEL") for (int i = 0; i < 7; i++) { float R, G, B; - float x = float (i) * (1.0f / 6.0); + float x = i / 6.0; Color::hsv2rgb01 (x, 0.5f, 0.5f, R, G, B); milestones.push_back ( GradientMilestone (double (x), double (R), double (G), double (B)) ); } @@ -659,10 +659,16 @@ void Retinex::writeOptions (std::vector &tpOpen) tpOpen.push_back (expsettings->get_expanded ()); } -void Retinex::updateToolState (std::vector &tpOpen) +void Retinex::updateToolState(const std::vector& tpOpen) { + if (tpOpen.empty()) { + expsettings->set_expanded(false); + + return; + } + if (tpOpen.size() >= 10) { - expsettings->set_expanded (tpOpen.at (9)); + expsettings->set_expanded(tpOpen[9]); } } diff --git a/rtgui/retinex.h b/rtgui/retinex.h index ff524f854..dea65daab 100644 --- a/rtgui/retinex.h +++ b/rtgui/retinex.h @@ -104,32 +104,32 @@ protected: sigc::connection medianmapConn; public: - Retinex (); - ~Retinex () override; + Retinex(); + ~Retinex() override; - void read (const rtengine::procparams::ProcParams* pp, const ParamsEdited* pedited = nullptr) override; - void write (rtengine::procparams::ProcParams* pp, ParamsEdited* pedited = nullptr) override; - void setBatchMode (bool batchMode) override; - void setDefaults (const rtengine::procparams::ProcParams* defParams, const ParamsEdited* pedited = nullptr) override; - void trimValues (rtengine::procparams::ProcParams* pp) override; - void adjusterChanged (Adjuster* a, double newval) override; - void autoOpenCurve () override; - void medianmapChanged (); - void minmaxChanged (double cdma, double cdmin, double mini, double maxi, double Tmean, double Tsigma, double Tmin, double Tmax) override; - void updateLabel (); - void updateTrans (); - void neutral_pressed (); + void read(const rtengine::procparams::ProcParams* pp, const ParamsEdited* pedited = nullptr) override; + void write(rtengine::procparams::ProcParams* pp, ParamsEdited* pedited = nullptr) override; + void setBatchMode(bool batchMode) override; + void setDefaults(const rtengine::procparams::ProcParams* defParams, const ParamsEdited* pedited = nullptr) override; + void trimValues(rtengine::procparams::ProcParams* pp) override; + void adjusterChanged(Adjuster* a, double newval) override; + void autoOpenCurve() override; + void medianmapChanged(); + void minmaxChanged(double cdma, double cdmin, double mini, double maxi, double Tmean, double Tsigma, double Tmin, double Tmax) override; + void updateLabel(); + void updateTrans(); + void neutral_pressed(); - void enabledChanged () override; - void curveChanged (CurveEditor* ce) override; + void enabledChanged() override; + void curveChanged(CurveEditor* ce) override; void retinexMethodChanged(); void mapMethodChanged(); void viewMethodChanged(); void retinexColorSpaceChanged(); void gammaretinexChanged(); void ColorSpaceUpdateUI(); - void writeOptions (std::vector &tpOpen); - void updateToolState (std::vector &tpOpen); + void writeOptions(std::vector &tpOpen); + void updateToolState(const std::vector& tpOpen); void setAdjusterBehavior (bool strAdd, bool neighAdd, bool limdAdd, bool offsAdd, bool vartAdd, bool gamAdd, bool slopeAdd); void updateCurveBackgroundHistogram( const LUTu& histToneCurve, @@ -144,9 +144,8 @@ public: const LUTu& histLRETI ); - void colorForValue (double valX, double valY, enum ColorCaller::ElemType elemType, int callerId, ColorCaller* caller) override; + void colorForValue(double valX, double valY, enum ColorCaller::ElemType elemType, int callerId, ColorCaller* caller) override; private: - void foldAllButMe (GdkEventButton* event, MyExpander *expander); - + void foldAllButMe(GdkEventButton* event, MyExpander *expander); }; diff --git a/rtgui/rtimage.h b/rtgui/rtimage.h index b68becd82..eb1930d28 100644 --- a/rtgui/rtimage.h +++ b/rtgui/rtimage.h @@ -25,7 +25,7 @@ /** * @brief A derived class of Gtk::Image in order to handle theme-related icon sets. */ -class RTImage : public Gtk::Image, public RTScalable +class RTImage final : public Gtk::Image, public RTScalable { static double dpiBack; // used to keep track of master dpi change static int scaleBack; // used to keep track of master scale change diff --git a/rtgui/rtscalable.cc b/rtgui/rtscalable.cc index a48a95fd2..78202326a 100644 --- a/rtgui/rtscalable.cc +++ b/rtgui/rtscalable.cc @@ -68,7 +68,7 @@ double RTScalable::getDPI () double RTScalable::getTweakedDPI () { - return dpi * fontScale; + return dpi * static_cast(fontScale); } int RTScalable::getScale () diff --git a/rtgui/rtwindow.cc b/rtgui/rtwindow.cc index 514685a16..fc315e1b7 100644 --- a/rtgui/rtwindow.cc +++ b/rtgui/rtwindow.cc @@ -99,6 +99,8 @@ RTWindow::RTWindow () , bpanel (nullptr) , splash (nullptr) , btn_fullscreen (nullptr) + , iFullscreen (nullptr) + , iFullscreen_exit (nullptr) , epanel (nullptr) , fpanel (nullptr) { @@ -179,7 +181,7 @@ RTWindow::RTWindow () fontScale = options.fontSize / (float)RTScalable::baseFontSize; } if (rtengine::settings->verbose) { - printf("\"Non-Default\" font size(%d) * scale(%d) / fontScale(%.3f)\n", options.fontSize, (int)initialGdkScale, fontScale); + printf("\"Non-Default\" font size(%d) * scale(%d) / fontScale(%.3f)\n", options.fontSize, (int)initialGdkScale, static_cast(fontScale)); } } else { Glib::RefPtr style = Gtk::StyleContext::create(); @@ -209,7 +211,7 @@ RTWindow::RTWindow () if ((int)initialGdkScale > 1 || pt != RTScalable::baseFontSize) { css = Glib::ustring::compose ("* { font-size: %1pt}", pt * (int)initialGdkScale); if (rtengine::settings->verbose) { - printf("\"Default\" font size(%d) * scale(%d) / fontScale(%.3f)\n", pt, (int)initialGdkScale, fontScale); + printf("\"Default\" font size(%d) * scale(%d) / fontScale(%.3f)\n", pt, (int)initialGdkScale, static_cast(fontScale)); } } } diff --git a/rtgui/rtwindow.h b/rtgui/rtwindow.h index 4791ac6c1..c493c2db4 100644 --- a/rtgui/rtwindow.h +++ b/rtgui/rtwindow.h @@ -35,7 +35,7 @@ class BatchQueuePanel; class EditorPanel; class FilePanel; class PLDBridge; -class RTWindow : +class RTWindow final : public Gtk::Window, public rtengine::ProgressListener, public rtengine::NonCopyable diff --git a/rtgui/saveasdlg.h b/rtgui/saveasdlg.h index 448b37fd7..445452a54 100644 --- a/rtgui/saveasdlg.h +++ b/rtgui/saveasdlg.h @@ -22,7 +22,7 @@ #include "saveformatpanel.h" -class SaveAsDialog : +class SaveAsDialog final : public Gtk::Dialog, public FormatChangeListener { diff --git a/rtgui/shcselector.h b/rtgui/shcselector.h index 5c4421e0a..e03ca8e06 100644 --- a/rtgui/shcselector.h +++ b/rtgui/shcselector.h @@ -29,7 +29,7 @@ public: virtual void shcChanged() = 0; }; -class SHCSelector : public Gtk::DrawingArea, BackBuffer +class SHCSelector final : public Gtk::DrawingArea, BackBuffer { protected: diff --git a/rtgui/splash.h b/rtgui/splash.h index 363c51489..bc63cef91 100644 --- a/rtgui/splash.h +++ b/rtgui/splash.h @@ -20,7 +20,7 @@ #include -class SplashImage : +class SplashImage final : public Gtk::DrawingArea { @@ -39,7 +39,7 @@ public: }; //class Splash : public Gtk::Window { -class Splash : public Gtk::Dialog +class Splash final : public Gtk::Dialog { private: diff --git a/rtgui/thresholdselector.h b/rtgui/thresholdselector.h index f948b56ad..4ae86560e 100644 --- a/rtgui/thresholdselector.h +++ b/rtgui/thresholdselector.h @@ -113,10 +113,10 @@ protected: void updateBackBuffer(); Gtk::SizeRequestMode get_request_mode_vfunc () const override; - void get_preferred_height_vfunc (int& minimum_height, int& natural_height) const override; - void get_preferred_width_vfunc (int &minimum_width, int &natural_width) const override; - void get_preferred_height_for_width_vfunc (int width, int &minimum_height, int &natural_height) const override; - void get_preferred_width_for_height_vfunc (int height, int &minimum_width, int &natural_width) const override; + void get_preferred_height_vfunc (int& minimum_height, int& natural_height) const final; + void get_preferred_width_vfunc (int &minimum_width, int &natural_width) const final; + void get_preferred_height_for_width_vfunc (int width, int &minimum_height, int &natural_height) const final; + void get_preferred_width_for_height_vfunc (int height, int &minimum_width, int &natural_width) const final; void on_realize () override; bool on_draw(const ::Cairo::RefPtr< Cairo::Context> &cr) override; bool on_button_press_event (GdkEventButton* event) override; diff --git a/rtgui/thumbbrowserbase.cc b/rtgui/thumbbrowserbase.cc index 5f75ab413..c611b252d 100644 --- a/rtgui/thumbbrowserbase.cc +++ b/rtgui/thumbbrowserbase.cc @@ -87,7 +87,16 @@ void ThumbBrowserBase::scroll (int direction, double deltaX, double deltaY) } //GDK_SCROLL_SMOOTH can come in as many events with small deltas, don't quantize these to +/-1.0 so trackpads work well double coef; + double scroll_unit; + if (arrangement == TB_Vertical) { + scroll_unit = vscroll.get_adjustment()->get_step_increment(); + } else { + scroll_unit = hscroll.get_adjustment()->get_step_increment(); + } if(direction == GDK_SCROLL_SMOOTH) { +#ifdef GDK_WINDOWING_QUARTZ + scroll_unit = 1.0; +#endif coef = delta; } else if (direction == GDK_SCROLL_DOWN) { coef = +1.0; @@ -99,7 +108,7 @@ void ThumbBrowserBase::scroll (int direction, double deltaX, double deltaY) if (direction == GDK_SCROLL_UP || direction == GDK_SCROLL_DOWN || direction == GDK_SCROLL_SMOOTH) { if (arrangement == TB_Vertical) { double currValue = vscroll.get_value(); - double newValue = rtengine::LIM(currValue + coef * vscroll.get_adjustment()->get_step_increment(), + double newValue = rtengine::LIM(currValue + coef * scroll_unit, vscroll.get_adjustment()->get_lower (), vscroll.get_adjustment()->get_upper()); if (newValue != currValue) { @@ -107,7 +116,7 @@ void ThumbBrowserBase::scroll (int direction, double deltaX, double deltaY) } } else { double currValue = hscroll.get_value(); - double newValue = rtengine::LIM(currValue + coef * hscroll.get_adjustment()->get_step_increment(), + double newValue = rtengine::LIM(currValue + coef * scroll_unit, hscroll.get_adjustment()->get_lower(), hscroll.get_adjustment()->get_upper()); if (newValue != currValue) { diff --git a/rtgui/thumbbrowserbase.h b/rtgui/thumbbrowserbase.h index b4caac0a9..69017b183 100644 --- a/rtgui/thumbbrowserbase.h +++ b/rtgui/thumbbrowserbase.h @@ -60,10 +60,10 @@ class ThumbBrowserBase : bool on_draw(const ::Cairo::RefPtr< Cairo::Context> &cr) override; Gtk::SizeRequestMode get_request_mode_vfunc () const override; - void get_preferred_height_vfunc (int &minimum_height, int &natural_height) const override; - void get_preferred_width_vfunc (int &minimum_width, int &natural_width) const override; - void get_preferred_height_for_width_vfunc (int width, int &minimum_height, int &natural_height) const override; - void get_preferred_width_for_height_vfunc (int height, int &minimum_width, int &natural_width) const override; + void get_preferred_height_vfunc (int &minimum_height, int &natural_height) const final; + void get_preferred_width_vfunc (int &minimum_width, int &natural_width) const final; + void get_preferred_height_for_width_vfunc (int width, int &minimum_height, int &natural_height) const final; + void get_preferred_width_for_height_vfunc (int height, int &minimum_width, int &natural_width) const final; bool on_button_press_event (GdkEventButton* event) override; bool on_button_release_event (GdkEventButton* event) override; diff --git a/rtgui/thumbnail.cc b/rtgui/thumbnail.cc index 5295b9d61..7452c9d72 100644 --- a/rtgui/thumbnail.cc +++ b/rtgui/thumbnail.cc @@ -216,7 +216,7 @@ const ProcParams& Thumbnail::getProcParamsU () double ct; getCamWB (ct, pparams->wb.green); pparams->wb.temperature = ct; - } else if (pparams->wb.method == "Auto") { + } else if (pparams->wb.method == "autold") { double ct; getAutoWB (ct, pparams->wb.green, pparams->wb.equal, pparams->wb.tempBias); pparams->wb.temperature = ct; @@ -887,11 +887,6 @@ void Thumbnail::_loadThumbnail(bool firstTrial) } if ( cfs.thumbImgType == CacheImageData::FULL_THUMBNAIL ) { - if(!tpp->isAeValid()) { - // load aehistogram - tpp->readAEHistogram (getCacheFileName ("aehistograms", "")); - } - // load embedded profile tpp->readEmbProfile (getCacheFileName ("embprofiles", ".icc")); @@ -937,10 +932,6 @@ void Thumbnail::_saveThumbnail () // save thumbnail image tpp->writeImage (getCacheFileName ("images", "")); - if(!tpp->isAeValid()) { - // save aehistogram - tpp->writeAEHistogram (getCacheFileName ("aehistograms", "")); - } // save embedded profile tpp->writeEmbProfile (getCacheFileName ("embprofiles", ".icc")); diff --git a/rtgui/toolpanel.h b/rtgui/toolpanel.h index aecf1f39f..12b3eebcc 100644 --- a/rtgui/toolpanel.h +++ b/rtgui/toolpanel.h @@ -143,7 +143,7 @@ public: this->batchMode = batchMode; } - virtual Glib::ustring getToolName () { + Glib::ustring getToolName () { return toolName; } }; @@ -164,11 +164,11 @@ public: FoldableToolPanel(Gtk::Box* content, Glib::ustring toolName, Glib::ustring UILabel, bool need11 = false, bool useEnabled = false); - MyExpander* getExpander() override + MyExpander* getExpander() final { return exp; } - void setExpanded (bool expanded) override + void setExpanded (bool expanded) final { if (exp) { exp->set_expanded( expanded ); @@ -186,7 +186,7 @@ public: exp->show(); } } - bool getExpanded () override + bool getExpanded () final { if (exp) { return exp->get_expanded(); @@ -194,11 +194,11 @@ public: return false; } - void setParent (Gtk::Box* parent) override + void setParent (Gtk::Box* parent) final { parentContainer = parent; } - Gtk::Box* getParent () override + Gtk::Box* getParent () final { return parentContainer; } diff --git a/rtgui/toolpanelcoord.cc b/rtgui/toolpanelcoord.cc index 77cb5643b..dadc56d44 100644 --- a/rtgui/toolpanelcoord.cc +++ b/rtgui/toolpanelcoord.cc @@ -611,6 +611,7 @@ void ToolPanelCoordinator::initImage (rtengine::StagedImageProcessor* ipc_, bool ipc->setSizeListener (crop); ipc->setSizeListener (resize); ipc->setImageTypeListener (this); + ipc->setFilmNegListener (filmNegative); flatfield->setShortcutPath (Glib::path_get_dirname (ipc->getInitialImage()->getFileName())); icm->setRawMeta (raw, (const rtengine::FramesData*)pMetaData); @@ -635,40 +636,52 @@ void ToolPanelCoordinator::closeImage () void ToolPanelCoordinator::closeAllTools() { - - for (size_t i = 0; i < options.tpOpen.size(); i++) + for (size_t i = 0; i < options.tpOpen.size(); ++i) { if (i < expList.size()) { - expList.at (i)->set_expanded (false); + expList[i]->set_expanded(false); } + } } void ToolPanelCoordinator::openAllTools() { - - for (size_t i = 0; i < options.tpOpen.size(); i++) + for (size_t i = 0; i < options.tpOpen.size(); ++i) { if (i < expList.size()) { - expList.at (i)->set_expanded (true); + expList[i]->set_expanded(true); } + } } void ToolPanelCoordinator::updateToolState() { - - for (size_t i = 0; i < options.tpOpen.size(); i++) - if (i < expList.size()) { - expList.at (i)->set_expanded (options.tpOpen.at (i)); + if (options.tpOpen.empty()) { + for (auto expander : expList) { + expander->set_expanded(false); } + wavelet->updateToolState({}); + retinex->updateToolState({}); + + return; + } + + for (size_t i = 0; i < options.tpOpen.size(); ++i) { + if (i < expList.size()) { + expList[i]->set_expanded(options.tpOpen[i]); + } + } + if (options.tpOpen.size() > expList.size()) { - size_t sizeWavelet = options.tpOpen.size() - expList.size(); + const size_t sizeWavelet = options.tpOpen.size() - expList.size(); + std::vector temp; - for (size_t i = 0; i < sizeWavelet; i++) { - temp.push_back (options.tpOpen.at (i + expList.size())); + for (size_t i = 0; i < sizeWavelet; ++i) { + temp.push_back(options.tpOpen[i + expList.size()]); } - wavelet->updateToolState (temp); - retinex->updateToolState (temp); + wavelet->updateToolState(temp); + retinex->updateToolState(temp); } } @@ -1084,3 +1097,8 @@ bool ToolPanelCoordinator::getFilmNegativeExponents(rtengine::Coord spotA, rteng { return ipc && ipc->getFilmNegativeExponents(spotA.x, spotA.y, spotB.x, spotB.y, newExps); } + +bool ToolPanelCoordinator::getRawSpotValues(rtengine::Coord spot, int spotSize, std::array& rawValues) +{ + return ipc && ipc->getRawSpotValues(spot.x, spot.y, spotSize, rawValues); +} \ No newline at end of file diff --git a/rtgui/toolpanelcoord.h b/rtgui/toolpanelcoord.h index 53b27f158..3861052cd 100644 --- a/rtgui/toolpanelcoord.h +++ b/rtgui/toolpanelcoord.h @@ -297,6 +297,7 @@ public: // FilmNegProvider interface bool getFilmNegativeExponents(rtengine::Coord spotA, rtengine::Coord spotB, std::array& newExps) override; + bool getRawSpotValues(rtengine::Coord spot, int spotSize, std::array& rawValues) override; // rotatelistener interface void straightenRequested () override; @@ -315,11 +316,11 @@ public: // imageareatoollistener interface void spotWBselected(int x, int y, Thumbnail* thm = nullptr) override; - void sharpMaskSelected(bool sharpMask) override; + void sharpMaskSelected(bool sharpMask) override final; int getSpotWBRectSize() const override; void cropSelectionReady() override; void rotateSelectionReady(double rotate_deg, Thumbnail* thm = nullptr) override; - ToolBar* getToolBar() const override; + ToolBar* getToolBar() const final; CropGUIListener* startCropEditing(Thumbnail* thm = nullptr) override; void updateTPVScrollbar (bool hide); @@ -327,7 +328,7 @@ public: // ToolBarListener interface void toolSelected (ToolMode tool) override; - void editModeSwitchedOff () override; + void editModeSwitchedOff () final; void setEditProvider (EditDataProvider *provider); diff --git a/rtgui/wavelet.cc b/rtgui/wavelet.cc index 3981457e6..af159d480 100644 --- a/rtgui/wavelet.cc +++ b/rtgui/wavelet.cc @@ -14,7 +14,7 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . * - * 2014 Jacques Desmis + * 2014 - 2019Jacques Desmis */ #include "wavelet.h" @@ -26,6 +26,7 @@ #include "guiutils.h" #include "rtimage.h" #include "options.h" +#include "eventmapper.h" #include "../rtengine/color.h" using namespace rtengine; @@ -34,27 +35,27 @@ using namespace rtengine::procparams; namespace { - GradientMilestone makeHsvGm(double position, float h, float s, float v) - { - float r; - float g; - float b; - Color::hsv2rgb01(h, s, v, r, g, b); - return GradientMilestone(position, r, g, b); +GradientMilestone makeHsvGm(double position, float h, float s, float v) +{ + float r; + float g; + float b; + Color::hsv2rgb01(h, s, v, r, g, b); + return GradientMilestone(position, r, g, b); +} + +std::vector makeWholeHueRange() +{ + std::vector res; + res.reserve(7); + + for (int i = 0; i < 7; ++i) { + const float x = static_cast(i) / 6.0f; + res.push_back(makeHsvGm(x, x, 0.5f, 0.5f)); } - std::vector makeWholeHueRange() - { - std::vector res; - res.reserve(7); - - for (int i = 0; i < 7; ++i) { - const float x = static_cast(i) / 6.0f; - res.push_back(makeHsvGm(x, x, 0.5f, 0.5f)); - } - - return res; - } + return res; +} } @@ -62,6 +63,7 @@ Wavelet::Wavelet() : FoldableToolPanel(this, "wavelet", M("TP_WAVELET_LABEL"), true, true), curveEditorG(new CurveEditorGroup(options.lastWaveletCurvesDir, M("TP_WAVELET_CONTEDIT"))), CCWcurveEditorG(new CurveEditorGroup(options.lastWaveletCurvesDir, M("TP_WAVELET_CCURVE"))), + curveEditorbl(new CurveEditorGroup(options.lastWaveletCurvesDir, M("TP_WAVELET_BLCURVE"))), curveEditorRES(new CurveEditorGroup(options.lastWaveletCurvesDir)), curveEditorGAM(new CurveEditorGroup(options.lastWaveletCurvesDir)), separatorNeutral(Gtk::manage(new Gtk::HSeparator())), @@ -77,11 +79,21 @@ Wavelet::Wavelet() : lipst(Gtk::manage(new Gtk::CheckButton(M("TP_WAVELET_LIPST")))), avoid(Gtk::manage(new Gtk::CheckButton(M("TP_WAVELET_AVOID")))), tmr(Gtk::manage(new Gtk::CheckButton(M("TP_WAVELET_BALCHRO")))), + showmask(Gtk::manage(new Gtk::CheckButton(M("TP_WAVELET_SHOWMASK")))), + oldsh(Gtk::manage(new Gtk::CheckButton(M("TP_WAVELET_OLDSH")))), neutralchButton(Gtk::manage(new Gtk::Button(M("TP_WAVELET_NEUTRAL")))), + sigma(Gtk::manage(new Adjuster(M("TP_WAVELET_SIGMA"), 0.05, 2.5, 0.01, 1.))), + offset(Gtk::manage(new Adjuster(M("TP_WAVELET_WAVOFFSET"), 0.33, 1.66, 0.01, 1., Gtk::manage(new RTImage("circle-black-small.png")), Gtk::manage(new RTImage("circle-white-small.png"))))), + lowthr(Gtk::manage(new Adjuster(M("TP_WAVELET_WAVLOWTHR"), 20., 100., 0.5, 40.))), rescon(Gtk::manage(new Adjuster(M("TP_WAVELET_RESCON"), -100, 100, 1, 0))), resconH(Gtk::manage(new Adjuster(M("TP_WAVELET_RESCONH"), -100, 100, 1, 0))), reschro(Gtk::manage(new Adjuster(M("TP_WAVELET_RESCHRO"), -100, 100, 1, 0))), + resblur(Gtk::manage(new Adjuster(M("TP_WAVELET_RESBLUR"), 0, 100, 1, 0))), + resblurc(Gtk::manage(new Adjuster(M("TP_WAVELET_RESBLURC"), 0, 100, 1, 0))), + bluwav(Gtk::manage(new Adjuster(M("TP_WAVELET_BLUWAV"), 0.05, 2.5, 0.5, 1.))), tmrs(Gtk::manage(new Adjuster(M("TP_WAVELET_TMSTRENGTH"), -1.0, 2.0, 0.01, 0.0))), + edgs(Gtk::manage(new Adjuster(M("TP_WAVELET_TMEDGS"), 0.1, 4.0, 0.01, 1.4))), + scale(Gtk::manage(new Adjuster(M("TP_WAVELET_TMSCALE"), 0.1, 10.0, 0.01, 1.0))), gamma(Gtk::manage(new Adjuster(M("TP_WAVELET_COMPGAMMA"), 0.4, 2.0, 0.01, 1.0))), sup(Gtk::manage(new Adjuster(M("TP_WAVELET_SUPE"), -100, 350, 1, 0))), sky(Gtk::manage(new Adjuster(M("TP_WAVELET_SKY"), -100., 100.0, 1., 0.))), @@ -89,12 +101,14 @@ Wavelet::Wavelet() : chroma(Gtk::manage(new Adjuster(M("TP_WAVELET_CHRO"), 1, 9, 1, 5))), chro(Gtk::manage(new Adjuster(M("TP_WAVELET_CHR"), 0., 100., 1., 0.))), contrast(Gtk::manage(new Adjuster(M("TP_WAVELET_CONTRA"), -100, 100, 1, 0))), - thr(Gtk::manage(new Adjuster(M("TP_WAVELET_THR"), 0, 100, 1, 35))), - thrH(Gtk::manage(new Adjuster(M("TP_WAVELET_THRH"), 0, 100, 1, 65))), - skinprotect(Gtk::manage( new Adjuster(M("TP_WAVELET_SKIN"), -100, 100, 1, 0.) )), - edgrad(Gtk::manage( new Adjuster(M("TP_WAVELET_EDRAD"), 0, 100, 1, 15) )), - edgval(Gtk::manage( new Adjuster(M("TP_WAVELET_EDVAL"), 0, 100, 1, 0) )), - edgthresh(Gtk::manage(new Adjuster(M("TP_WAVELET_EDGTHRESH"), -50, 100, 1, 10 ))), + thr(Gtk::manage(new Adjuster(M("TP_WAVELET_THR"), 0, 100, 1, 30))), + thrH(Gtk::manage(new Adjuster(M("TP_WAVELET_THRH"), 0, 100, 1, 70))), + radius(Gtk::manage(new Adjuster(M("TP_WAVELET_RADIUS"), 0, 100, 1, 40))), + skinprotect(Gtk::manage(new Adjuster(M("TP_WAVELET_SKIN"), -100, 100, 1, 0.))), + edgrad(Gtk::manage(new Adjuster(M("TP_WAVELET_EDRAD"), 0, 100, 1, 15))), + edgeffect(Gtk::manage(new Adjuster(M("TP_WAVELET_EDEFFECT"), 0.05, 2.5, 0.01, 1.))), + edgval(Gtk::manage(new Adjuster(M("TP_WAVELET_EDVAL"), 0, 100, 1, 0))), + edgthresh(Gtk::manage(new Adjuster(M("TP_WAVELET_EDGTHRESH"), -50, 100, 1, 10))), strength(Gtk::manage(new Adjuster(M("TP_WAVELET_STRENGTH"), 0, 100, 1, 100))), balance(Gtk::manage(new Adjuster(M("TP_WAVELET_BALANCE"), -30, 100, 1, 0))), iter(Gtk::manage(new Adjuster(M("TP_WAVELET_ITER"), -3, 3, 1, 0))), @@ -116,6 +130,15 @@ Wavelet::Wavelet() : edgedetectthr2(Gtk::manage(new Adjuster(M("TP_WAVELET_EDGEDETECTTHR2"), -10, 100, 1, 0))), edgesensi(Gtk::manage(new Adjuster(M("TP_WAVELET_EDGESENSI"), 0, 100, 1, 60))), edgeampli(Gtk::manage(new Adjuster(M("TP_WAVELET_EDGEAMPLI"), 0, 100, 1, 10))), + ballum(Gtk::manage(new Adjuster(M("TP_WAVELET_BALLUM"), -2., 10., 0.5, 7., Gtk::manage(new RTImage("circle-white-small.png")), Gtk::manage(new RTImage("circle-black-small.png"))))), + balchrom(Gtk::manage(new Adjuster(M("TP_WAVELET_BALCHROM"), -100., 100., 1., 0., Gtk::manage(new RTImage("circle-blue-small.png")), Gtk::manage(new RTImage("circle-red-small.png"))))), + chromfi(Gtk::manage(new Adjuster(M("TP_WAVELET_CHROMFI"), 0.0, 150., 0.01, 0.))), + chromco(Gtk::manage(new Adjuster(M("TP_WAVELET_CHROMCO"), 0, 100., 0.01, 0.))), + mergeL(Gtk::manage(new Adjuster(M("TP_WAVELET_MERGEL"), -50, 100, 1, 40))), + mergeC(Gtk::manage(new Adjuster(M("TP_WAVELET_MERGEC"), -50, 100, 1, 20))), + softrad(Gtk::manage(new Adjuster(M("TP_WAVELET_SOFTRAD"), 0.0, 100., 0.5, 0.))), + softradend(Gtk::manage(new Adjuster(M("TP_WAVELET_SOFTRAD"), 0.0, 100., 0.5, 0.))), + chrwav(Gtk::manage(new Adjuster(M("TP_WAVELET_CHRWAV"), 0., 100., 0.5, 0.))), Lmethod(Gtk::manage(new MyComboBoxText())), CHmethod(Gtk::manage(new MyComboBoxText())), CHSLmethod(Gtk::manage(new MyComboBoxText())), @@ -130,12 +153,19 @@ Wavelet::Wavelet() : daubcoeffmethod(Gtk::manage(new MyComboBoxText())), Dirmethod(Gtk::manage(new MyComboBoxText())), Medgreinf(Gtk::manage(new MyComboBoxText())), + ushamethod(Gtk::manage(new MyComboBoxText())), chanMixerHLFrame(Gtk::manage(new Gtk::Frame(M("TP_COLORTONING_HIGHLIGHT")))), chanMixerMidFrame(Gtk::manage(new Gtk::Frame(M("TP_COLORTONING_MIDTONES")))), chanMixerShadowsFrame(Gtk::manage(new Gtk::Frame(M("TP_COLORTONING_SHADOWS")))), + shFrame(Gtk::manage(new Gtk::Frame(M("TP_WAVELET_SHFRAME")))), + contFrame(Gtk::manage(new Gtk::Frame(M("TP_WAVELET_CONTFRAME")))), + blurFrame(Gtk::manage(new Gtk::Frame(M("TP_WAVELET_BLURFRAME")))), + chromaFrame(Gtk::manage(new Gtk::Frame(M("TP_WAVELET_CHROMAFRAME")))), + chroFrame(Gtk::manage(new Gtk::Frame(M("TP_WAVELET_CHROFRAME")))), wavLabels(Gtk::manage(new Gtk::Label("---", Gtk::ALIGN_CENTER))), labmC(Gtk::manage(new Gtk::Label(M("TP_WAVELET_CTYPE") + ":"))), labmNP(Gtk::manage(new Gtk::Label(M("TP_WAVELET_NPTYPE") + ":"))), + usharpLabel(Gtk::manage(new Gtk::Label(M("TP_WAVELET_USHARP") + ":"))), expchroma(Gtk::manage(new MyExpander(true, M("TP_WAVELET_LEVCH")))), expcontrast(Gtk::manage(new MyExpander(true, M("TP_WAVELET_LEVF")))), expedge(Gtk::manage(new MyExpander(true, M("TP_WAVELET_EDGE")))), @@ -145,106 +175,139 @@ Wavelet::Wavelet() : expresid(Gtk::manage(new MyExpander(true, M("TP_WAVELET_RESID")))), expsettings(Gtk::manage(new MyExpander(false, M("TP_WAVELET_SETTINGS")))), exptoning(Gtk::manage(new MyExpander(true, M("TP_WAVELET_TON")))), - neutrHBox(Gtk::manage(new Gtk::HBox())) + expclari(Gtk::manage(new MyExpander(true, M("TP_WAVELET_CLARI")))), + expbl(Gtk::manage(new MyExpander(true, M("TP_WAVELET_BL")))), + neutrHBox(Gtk::manage(new Gtk::HBox())), + usharpHBox(Gtk::manage(new Gtk::HBox())) { CurveListener::setMulti(true); + auto m = ProcEventMapper::getInstance(); + EvWavenaclari = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVCLARI"); + EvWavushamet = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVUSHAMET"); + EvWavballum = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVBALLUM"); + EvWavbalchrom = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVBALCHROM"); + EvWavchromfi = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVCHROMFI"); + EvWavchromco = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVCHROMCO"); + EvWavmergeL = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVMERGEL"); + EvWavmergeC = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVMERGEC"); + EvWavsoftrad = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVSOFTRAD"); + EvWavsoftradend = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVSOFTRADEND"); + EvWavshowmask = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVSHOWMASK"); + EvWavedgs = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVEDGS"); + EvWavscale = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVSCALE"); + EvWavradius = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVRADIUS"); + EvWavsigma = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVSIGMA"); + EvWavenabl = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVBL"); + EvWavchrwav = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_chrwav"); + EvWavoldsh = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVOLDSH"); + EvWavoffset = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVOFFSET"); + EvWavlowthr = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_WAVLOWTHR"); + EvWavbluwav = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_BLUWAV"); + EvWavblshape = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_BLSHAPE"); + EvWavresblur = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_BLURWAV"); + EvWavresblurc = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_BLURCWAV"); + EvWavedgeffect = m->newEvent(DIRPYREQUALIZER, "HISTORY_MSG_EDGEFFECT"); + expsettings->signal_button_release_event().connect_notify(sigc::bind(sigc::mem_fun(this, &Wavelet::foldAllButMe), expsettings)); - expsettings->signal_button_release_event().connect_notify( sigc::bind( sigc::mem_fun(this, &Wavelet::foldAllButMe), expsettings) ); + expcontrast->signal_button_release_event().connect_notify(sigc::bind(sigc::mem_fun(this, &Wavelet::foldAllButMe), expcontrast)); + enableContrastConn = expcontrast->signal_enabled_toggled().connect(sigc::bind(sigc::mem_fun(this, &Wavelet::enableToggled), expcontrast)); - expcontrast->signal_button_release_event().connect_notify( sigc::bind( sigc::mem_fun(this, &Wavelet::foldAllButMe), expcontrast) ); - enableContrastConn = expcontrast->signal_enabled_toggled().connect ( sigc::bind( sigc::mem_fun(this, &Wavelet::enableToggled), expcontrast) ); + expchroma->signal_button_release_event().connect_notify(sigc::bind(sigc::mem_fun(this, &Wavelet::foldAllButMe), expchroma)); + enableChromaConn = expchroma->signal_enabled_toggled().connect(sigc::bind(sigc::mem_fun(this, &Wavelet::enableToggled), expchroma)); - expchroma->signal_button_release_event().connect_notify( sigc::bind ( sigc::mem_fun(this, &Wavelet::foldAllButMe), expchroma) ); - enableChromaConn = expchroma->signal_enabled_toggled().connect ( sigc::bind( sigc::mem_fun(this, &Wavelet::enableToggled), expchroma) ); + exptoning->signal_button_release_event().connect_notify(sigc::bind(sigc::mem_fun(this, &Wavelet::foldAllButMe), exptoning)); + enableToningConn = exptoning->signal_enabled_toggled().connect(sigc::bind(sigc::mem_fun(this, &Wavelet::enableToggled), exptoning)); - exptoning->signal_button_release_event().connect_notify( sigc::bind ( sigc::mem_fun(this, &Wavelet::foldAllButMe), exptoning) ); - enableToningConn = exptoning->signal_enabled_toggled().connect ( sigc::bind( sigc::mem_fun(this, &Wavelet::enableToggled), exptoning) ); + expnoise->signal_button_release_event().connect_notify(sigc::bind(sigc::mem_fun(this, &Wavelet::foldAllButMe), expnoise)); + enableNoiseConn = expnoise->signal_enabled_toggled().connect(sigc::bind(sigc::mem_fun(this, &Wavelet::enableToggled), expnoise)); - expnoise->signal_button_release_event().connect_notify( sigc::bind ( sigc::mem_fun(this, &Wavelet::foldAllButMe), expnoise) ); - enableNoiseConn = expnoise->signal_enabled_toggled().connect ( sigc::bind( sigc::mem_fun(this, &Wavelet::enableToggled), expnoise) ); + expedge->signal_button_release_event().connect_notify(sigc::bind(sigc::mem_fun(this, &Wavelet::foldAllButMe), expedge)); + enableEdgeConn = expedge->signal_enabled_toggled().connect(sigc::bind(sigc::mem_fun(this, &Wavelet::enableToggled), expedge)); - expedge->signal_button_release_event().connect_notify( sigc::bind ( sigc::mem_fun(this, &Wavelet::foldAllButMe), expedge) ); - enableEdgeConn = expedge->signal_enabled_toggled().connect ( sigc::bind( sigc::mem_fun(this, &Wavelet::enableToggled), expedge) ); + expbl->signal_button_release_event().connect_notify(sigc::bind(sigc::mem_fun(this, &Wavelet::foldAllButMe), expbl)); + enabletmConn = expbl->signal_enabled_toggled().connect(sigc::bind(sigc::mem_fun(this, &Wavelet::enableToggled), expbl)); - expgamut->signal_button_release_event().connect_notify( sigc::bind ( sigc::mem_fun(this, &Wavelet::foldAllButMe), expgamut) ); + expgamut->signal_button_release_event().connect_notify(sigc::bind(sigc::mem_fun(this, &Wavelet::foldAllButMe), expgamut)); - expresid->signal_button_release_event().connect_notify( sigc::bind ( sigc::mem_fun(this, &Wavelet::foldAllButMe), expresid) ); - enableResidConn = expresid->signal_enabled_toggled().connect ( sigc::bind( sigc::mem_fun(this, &Wavelet::enableToggled), expresid) ); + expresid->signal_button_release_event().connect_notify(sigc::bind(sigc::mem_fun(this, &Wavelet::foldAllButMe), expresid)); + enableResidConn = expresid->signal_enabled_toggled().connect(sigc::bind(sigc::mem_fun(this, &Wavelet::enableToggled), expresid)); - expfinal->signal_button_release_event().connect_notify( sigc::bind ( sigc::mem_fun(this, &Wavelet::foldAllButMe), expfinal) ); - enableFinalConn = expfinal->signal_enabled_toggled().connect ( sigc::bind( sigc::mem_fun(this, &Wavelet::enableToggled), expfinal) ); + expfinal->signal_button_release_event().connect_notify(sigc::bind(sigc::mem_fun(this, &Wavelet::foldAllButMe), expfinal)); + enableFinalConn = expfinal->signal_enabled_toggled().connect(sigc::bind(sigc::mem_fun(this, &Wavelet::enableToggled), expfinal)); + + expclari->signal_button_release_event().connect_notify(sigc::bind(sigc::mem_fun(this, &Wavelet::foldAllButMe), expclari)); + enableclariConn = expclari->signal_enabled_toggled().connect(sigc::bind(sigc::mem_fun(this, &Wavelet::enableToggled), expclari)); // Wavelet Settings - ToolParamBlock* const settingsBox = Gtk::manage (new ToolParamBlock()); + ToolParamBlock* const settingsBox = Gtk::manage(new ToolParamBlock()); - strength->setAdjusterListener (this); + strength->setAdjusterListener(this); - thres->set_tooltip_text (M("TP_WAVELET_LEVELS_TOOLTIP")); - thres->setAdjusterListener (this); + thres->set_tooltip_text(M("TP_WAVELET_LEVELS_TOOLTIP")); + thres->setAdjusterListener(this); - Tilesmethod->append (M("TP_WAVELET_TILESFULL")); - Tilesmethod->append (M("TP_WAVELET_TILESBIG")); - Tilesmethod->append (M("TP_WAVELET_TILESLIT")); - Tilesmethodconn = Tilesmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::TilesmethodChanged) ); - Tilesmethod->set_tooltip_text (M("TP_WAVELET_TILES_TOOLTIP")); + Tilesmethod->append(M("TP_WAVELET_TILESFULL")); + Tilesmethod->append(M("TP_WAVELET_TILESBIG")); +// Tilesmethod->append(M("TP_WAVELET_TILESLIT")); + Tilesmethodconn = Tilesmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::TilesmethodChanged)); + Tilesmethod->set_tooltip_text(M("TP_WAVELET_TILES_TOOLTIP")); Gtk::HBox* const tilesizeHBox = Gtk::manage(new Gtk::HBox()); Gtk::Label* const tilesizeLabel = Gtk::manage(new Gtk::Label(M("TP_WAVELET_TILESIZE") + ":")); tilesizeHBox->pack_start(*tilesizeLabel, Gtk::PACK_SHRINK, 4); tilesizeHBox->pack_start(*Tilesmethod); daubcoeffmethod->set_sensitive(true); - daubcoeffmethod->append (M("TP_WAVELET_DAUB2")); - daubcoeffmethod->append (M("TP_WAVELET_DAUB4")); - daubcoeffmethod->append (M("TP_WAVELET_DAUB6")); - daubcoeffmethod->append (M("TP_WAVELET_DAUB10")); - daubcoeffmethod->append (M("TP_WAVELET_DAUB14")); - daubcoeffmethodconn = daubcoeffmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::daubcoeffmethodChanged) ); - daubcoeffmethod->set_tooltip_text (M("TP_WAVELET_DAUB_TOOLTIP")); + daubcoeffmethod->append(M("TP_WAVELET_DAUB2")); + daubcoeffmethod->append(M("TP_WAVELET_DAUB4")); + daubcoeffmethod->append(M("TP_WAVELET_DAUB6")); + daubcoeffmethod->append(M("TP_WAVELET_DAUB10")); + daubcoeffmethod->append(M("TP_WAVELET_DAUB14")); + daubcoeffmethodconn = daubcoeffmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::daubcoeffmethodChanged)); + daubcoeffmethod->set_tooltip_text(M("TP_WAVELET_DAUB_TOOLTIP")); Gtk::Label* const daubcoeffLabel = Gtk::manage(new Gtk::Label(M("TP_WAVELET_DAUB") + ":")); Gtk::HBox* const daubcoeffHBox = Gtk::manage(new Gtk::HBox()); daubcoeffHBox->pack_start(*daubcoeffLabel, Gtk::PACK_SHRINK, 4); daubcoeffHBox->pack_start(*daubcoeffmethod); - Backmethod->append (M("TP_WAVELET_B0")); - Backmethod->append (M("TP_WAVELET_B1")); - Backmethod->append (M("TP_WAVELET_B2")); - Backmethodconn = Backmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::BackmethodChanged) ); + Backmethod->append(M("TP_WAVELET_B0")); + Backmethod->append(M("TP_WAVELET_B1")); + Backmethod->append(M("TP_WAVELET_B2")); + Backmethodconn = Backmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::BackmethodChanged)); Gtk::HBox* const backgroundHBox = Gtk::manage(new Gtk::HBox()); Gtk::Label* const backgroundLabel = Gtk::manage(new Gtk::Label(M("TP_WAVELET_BACKGROUND") + ":")); backgroundHBox->pack_start(*backgroundLabel, Gtk::PACK_SHRINK, 4); backgroundHBox->pack_start(*Backmethod); - CLmethod->append (M("TP_WAVELET_LEVDIR_ONE")); - CLmethod->append (M("TP_WAVELET_LEVDIR_INF")); - CLmethod->append (M("TP_WAVELET_LEVDIR_SUP")); - CLmethod->append (M("TP_WAVELET_LEVDIR_ALL")); - CLmethodconn = CLmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::CLmethodChanged) ); + CLmethod->append(M("TP_WAVELET_LEVDIR_ONE")); + CLmethod->append(M("TP_WAVELET_LEVDIR_INF")); + CLmethod->append(M("TP_WAVELET_LEVDIR_SUP")); + CLmethod->append(M("TP_WAVELET_LEVDIR_ALL")); + CLmethodconn = CLmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::CLmethodChanged)); Gtk::HBox* const levdirMainHBox = Gtk::manage(new Gtk::HBox()); Gtk::Label* const levdirMainLabel = Gtk::manage(new Gtk::Label(M("TP_WAVELET_PROC") + ":")); levdirMainHBox->pack_start(*levdirMainLabel, Gtk::PACK_SHRINK, 4); levdirMainHBox->pack_start(*CLmethod); //same Lmethod->set_sensitive(false); - Lmethod->set_sensitive(false); - Lmethod->append (M("TP_WAVELET_1")); - Lmethod->append (M("TP_WAVELET_2")); - Lmethod->append (M("TP_WAVELET_3")); - Lmethod->append (M("TP_WAVELET_4")); - Lmethod->append (M("TP_WAVELET_5")); - Lmethod->append (M("TP_WAVELET_6")); - Lmethod->append (M("TP_WAVELET_7")); - Lmethod->append (M("TP_WAVELET_8")); - Lmethod->append (M("TP_WAVELET_9")); - Lmethod->append (M("TP_WAVELET_SUPE")); - Lmethod->append (M("TP_WAVELET_RESID")); + Lmethod->append(M("TP_WAVELET_1")); + Lmethod->append(M("TP_WAVELET_2")); + Lmethod->append(M("TP_WAVELET_3")); + Lmethod->append(M("TP_WAVELET_4")); + Lmethod->append(M("TP_WAVELET_5")); + Lmethod->append(M("TP_WAVELET_6")); + Lmethod->append(M("TP_WAVELET_7")); + Lmethod->append(M("TP_WAVELET_8")); + Lmethod->append(M("TP_WAVELET_9")); + Lmethod->append(M("TP_WAVELET_SUPE")); + Lmethod->append(M("TP_WAVELET_RESID")); Lmethod->set_active(0); Dirmethod->set_sensitive(false); - Dirmethod->append (M("TP_WAVELET_DONE")); - Dirmethod->append (M("TP_WAVELET_DTWO")); - Dirmethod->append (M("TP_WAVELET_DTHR")); - Dirmethod->append (M("TP_WAVELET_DALL")); - Lmethodconn = Lmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::LmethodChanged) ); - Dirmethodconn = Dirmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::DirmethodChanged) ); + Dirmethod->append(M("TP_WAVELET_DONE")); + Dirmethod->append(M("TP_WAVELET_DTWO")); + Dirmethod->append(M("TP_WAVELET_DTHR")); + Dirmethod->append(M("TP_WAVELET_DALL")); + Lmethodconn = Lmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::LmethodChanged)); + Dirmethodconn = Dirmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::DirmethodChanged)); Gtk::HBox* const levdirSubHBox = Gtk::manage(new Gtk::HBox()); levdirSubHBox->pack_start(*Lmethod); levdirSubHBox->pack_start(*Dirmethod, Gtk::PACK_EXPAND_WIDGET, 2); // same, but 2 not 4? @@ -258,74 +321,86 @@ Wavelet::Wavelet() : settingsBox->pack_start(*levdirSubHBox); // Contrast - ToolParamBlock* const levBox = Gtk::manage (new ToolParamBlock()); + ToolParamBlock* const levBox = Gtk::manage(new ToolParamBlock()); - Gtk::HBox* const buttonBox = Gtk::manage (new Gtk::HBox(true, 10)); + Gtk::HBox* const buttonBox = Gtk::manage(new Gtk::HBox(true, 10)); levBox->pack_start(*buttonBox, Gtk::PACK_SHRINK, 2); - Gtk::Button* const contrastMinusButton = Gtk::manage (new Gtk::Button(M("TP_WAVELET_CONTRAST_MINUS"))); + Gtk::Button* const contrastMinusButton = Gtk::manage(new Gtk::Button(M("TP_WAVELET_CONTRAST_MINUS"))); buttonBox->pack_start(*contrastMinusButton); - contrastMinusPressedConn = contrastMinusButton->signal_pressed().connect( sigc::mem_fun(*this, &Wavelet::contrastMinusPressed)); + contrastMinusPressedConn = contrastMinusButton->signal_pressed().connect(sigc::mem_fun(*this, &Wavelet::contrastMinusPressed)); - Gtk::Button* const neutralButton = Gtk::manage (new Gtk::Button(M("TP_WAVELET_NEUTRAL"))); + Gtk::Button* const neutralButton = Gtk::manage(new Gtk::Button(M("TP_WAVELET_NEUTRAL"))); buttonBox->pack_start(*neutralButton); - neutralPressedConn = neutralButton->signal_pressed().connect( sigc::mem_fun(*this, &Wavelet::neutralPressed)); + neutralPressedConn = neutralButton->signal_pressed().connect(sigc::mem_fun(*this, &Wavelet::neutralPressed)); - Gtk::Button* const contrastPlusButton = Gtk::manage (new Gtk::Button(M("TP_WAVELET_CONTRAST_PLUS"))); + Gtk::Button* const contrastPlusButton = Gtk::manage(new Gtk::Button(M("TP_WAVELET_CONTRAST_PLUS"))); buttonBox->pack_start(*contrastPlusButton); - contrastPlusPressedConn = contrastPlusButton->signal_pressed().connect( sigc::mem_fun(*this, &Wavelet::contrastPlusPressed)); + contrastPlusPressedConn = contrastPlusButton->signal_pressed().connect(sigc::mem_fun(*this, &Wavelet::contrastPlusPressed)); buttonBox->show_all_children(); - for(int i = 0; i < 9; i++) { + for (int i = 0; i < 9; i++) { Glib::ustring ss; - switch( i ) { - case 0: - ss = Glib::ustring::compose( "%1 (%2)", (i + 1), M("TP_WAVELET_FINEST")); - break; + switch (i) { + case 0: + ss = Glib::ustring::compose("%1 (%2)", (i + 1), M("TP_WAVELET_FINEST")); + break; - case 8: - ss = Glib::ustring::compose( "%1 (%2)", (i + 1), M("TP_WAVELET_LARGEST")); - break; + case 8: + ss = Glib::ustring::compose("%1 (%2)", (i + 1), M("TP_WAVELET_LARGEST")); + break; - default: - ss = Glib::ustring::compose( "%1", (i + 1)); + default: + ss = Glib::ustring::compose("%1", (i + 1)); } correction[i] = Gtk::manage(new Adjuster(std::move(ss), -100, 350, 1, 0)); correction[i]->setAdjusterListener(this); levBox->pack_start(*correction[i]); } - levBox->pack_start(*sup); - sup->setAdjusterListener (this); + sup->setAdjusterListener(this); + Gtk::HSeparator* const separatorcont = Gtk::manage(new Gtk::HSeparator()); + levBox->pack_start(*separatorcont); + + sigma->setAdjusterListener(this); + levBox->pack_start(*sigma, Gtk::PACK_SHRINK); + offset->setAdjusterListener(this); + levBox->pack_start(*offset, Gtk::PACK_SHRINK); + sigma->set_tooltip_text(M("TP_WAVELET_SIGMA_TOOLTIP")); + offset->set_tooltip_text(M("TP_WAVELET_OFFSET_TOOLTIP")); + lowthr->setAdjusterListener(this); + lowthr->set_tooltip_text(M("TP_WAVELET_LOWTHR_TOOLTIP")); + levBox->pack_start(*lowthr, Gtk::PACK_SHRINK); + wavLabels->show(); - levBox->pack_start (*wavLabels); + levBox->pack_start(*wavLabels); Gtk::VBox* const contrastSHVBox = Gtk::manage(new Gtk::VBox); contrastSHVBox->set_spacing(2); - HSmethod->append (M("TP_WAVELET_HS1")); - HSmethod->append (M("TP_WAVELET_HS2")); - HSmethodconn = HSmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::HSmethodChanged) ); + HSmethod->append(M("TP_WAVELET_HS1")); + HSmethod->append(M("TP_WAVELET_HS2")); + HSmethodconn = HSmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::HSmethodChanged)); const std::vector milestones2 = { GradientMilestone(0.0, 0.0, 0.0, 0.0), GradientMilestone(1.0, 1.0, 1.0, 1.0) }; - hllev->setAdjusterListener (this); + hllev->setAdjusterListener(this); hllev->setBgGradient(milestones2); - threshold->setAdjusterListener (this); - threshold->set_tooltip_text (M("TP_WAVELET_THRESHOLD_TOOLTIP")); + threshold->setAdjusterListener(this); + threshold->set_tooltip_text(M("TP_WAVELET_THRESHOLD_TOOLTIP")); - bllev->setAdjusterListener (this); + bllev->setAdjusterListener(this); bllev->setBgGradient(milestones2); - threshold2->setAdjusterListener (this); - threshold2->set_tooltip_text (M("TP_WAVELET_THRESHOLD2_TOOLTIP")); + threshold2->setAdjusterListener(this); + threshold2->set_tooltip_text(M("TP_WAVELET_THRESHOLD2_TOOLTIP")); contrastSHVBox->pack_start(*HSmethod); contrastSHVBox->pack_start(*hllev); @@ -337,68 +412,68 @@ Wavelet::Wavelet() : levBox->pack_start(*contrastSHFrame); // Chromaticity - ToolParamBlock* const chBox = Gtk::manage (new ToolParamBlock()); + ToolParamBlock* const chBox = Gtk::manage(new ToolParamBlock()); Gtk::Label* const labmch = Gtk::manage(new Gtk::Label(M("TP_WAVELET_CHTYPE") + ":")); Gtk::HBox* const ctboxch = Gtk::manage(new Gtk::HBox()); - ctboxch->pack_start (*labmch, Gtk::PACK_SHRINK, 1); + ctboxch->pack_start(*labmch, Gtk::PACK_SHRINK, 1); - CHmethod->append (M("TP_WAVELET_CH1")); - CHmethod->append (M("TP_WAVELET_CH2")); - CHmethod->append (M("TP_WAVELET_CH3")); - CHmethodconn = CHmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::CHmethodChanged) ); + CHmethod->append(M("TP_WAVELET_CH1")); + CHmethod->append(M("TP_WAVELET_CH2")); + CHmethod->append(M("TP_WAVELET_CH3")); + CHmethodconn = CHmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::CHmethodChanged)); ctboxch->pack_start(*CHmethod); chBox->pack_start(*ctboxch); Gtk::HBox* const ctboxCH = Gtk::manage(new Gtk::HBox()); - ctboxCH->pack_start (*labmC, Gtk::PACK_SHRINK, 1); + ctboxCH->pack_start(*labmC, Gtk::PACK_SHRINK, 1); - CHSLmethod->append (M("TP_WAVELET_CHSL")); - CHSLmethod->append (M("TP_WAVELET_CHCU")); - CHSLmethodconn = CHSLmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::CHSLmethodChanged) ); + CHSLmethod->append(M("TP_WAVELET_CHSL")); + CHSLmethod->append(M("TP_WAVELET_CHCU")); + CHSLmethodconn = CHSLmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::CHSLmethodChanged)); ctboxCH->pack_start(*CHSLmethod); - Gtk::HSeparator* const separatorChromaMethod = Gtk::manage (new Gtk::HSeparator()); + Gtk::HSeparator* const separatorChromaMethod = Gtk::manage(new Gtk::HSeparator()); chBox->pack_start(*separatorChromaMethod, Gtk::PACK_SHRINK, 2); - chroma->set_tooltip_text (M("TP_WAVELET_CHRO_TOOLTIP")); + chroma->set_tooltip_text(M("TP_WAVELET_CHRO_TOOLTIP")); chBox->pack_start(*chroma); - chroma->setAdjusterListener (this); + chroma->setAdjusterListener(this); - satlev->setAdjusterListener (this); + satlev->setAdjusterListener(this); satlev->setBgGradient(milestones2); - pastlev->setAdjusterListener (this); + pastlev->setAdjusterListener(this); pastlev->setBgGradient(milestones2); chBox->pack_start(*pastlev); chBox->pack_start(*satlev); - chro->set_tooltip_text (M("TP_WAVELET_CHR_TOOLTIP")); + chro->set_tooltip_text(M("TP_WAVELET_CHR_TOOLTIP")); chBox->pack_start(*chro); - chro->setAdjusterListener (this); + chro->setAdjusterListener(this); - Gtk::HBox* const buttonchBox = Gtk::manage (new Gtk::HBox(true, 10)); - neutralchPressedConn = neutralchButton->signal_pressed().connect( sigc::mem_fun(*this, &Wavelet::neutralchPressed)); + Gtk::HBox* const buttonchBox = Gtk::manage(new Gtk::HBox(true, 10)); + neutralchPressedConn = neutralchButton->signal_pressed().connect(sigc::mem_fun(*this, &Wavelet::neutralchPressed)); chBox->pack_start(*separatorNeutral, Gtk::PACK_SHRINK, 2); buttonchBox->pack_start(*neutralchButton); buttonchBox->show_all_children(); chBox->pack_start(*buttonchBox, Gtk::PACK_SHRINK, 2); - for(int i = 0; i < 9; i++) { + for (int i = 0; i < 9; i++) { Glib::ustring ss; - switch( i ) { - case 0: - ss = Glib::ustring::compose( "%1 (%2)", (i + 1), M("TP_WAVELET_FINEST")); - break; + switch (i) { + case 0: + ss = Glib::ustring::compose("%1 (%2)", (i + 1), M("TP_WAVELET_FINEST")); + break; - case 8: - ss = Glib::ustring::compose( "%1 (%2)", (i + 1), M("TP_WAVELET_LARGEST")); - break; + case 8: + ss = Glib::ustring::compose("%1 (%2)", (i + 1), M("TP_WAVELET_LARGEST")); + break; - default: - ss = Glib::ustring::compose( "%1", (i + 1)); + default: + ss = Glib::ustring::compose("%1", (i + 1)); } correctionch[i] = Gtk::manage(new Adjuster(std::move(ss), -100, 100, 1, 0)); @@ -407,9 +482,9 @@ Wavelet::Wavelet() : } // Toning - ToolParamBlock* const tonBox = Gtk::manage (new ToolParamBlock()); + ToolParamBlock* const tonBox = Gtk::manage(new ToolParamBlock()); - opaCurveEditorG->setCurveListener (this); + opaCurveEditorG->setCurveListener(this); const WaveletParams default_params; @@ -420,9 +495,9 @@ Wavelet::Wavelet() : opaCurveEditorG->curveListComplete(); opaCurveEditorG->show(); - tonBox->pack_start( *opaCurveEditorG, Gtk::PACK_SHRINK, 2); + tonBox->pack_start(*opaCurveEditorG, Gtk::PACK_SHRINK, 2); - opacityCurveEditorG->setCurveListener (this); + opacityCurveEditorG->setCurveListener(this); opacityShapeBY = static_cast(opacityCurveEditorG->addCurve(CT_Flat, "", nullptr, false, false)); opacityShapeBY->setIdentityValue(0.); @@ -431,77 +506,118 @@ Wavelet::Wavelet() : opacityCurveEditorG->curveListComplete(); opacityCurveEditorG->show(); - tonBox->pack_start( *opacityCurveEditorG, Gtk::PACK_SHRINK, 2); + tonBox->pack_start(*opacityCurveEditorG, Gtk::PACK_SHRINK, 2); // Denoise and Refine - ToolParamBlock* const noiseBox = Gtk::manage (new ToolParamBlock()); + ToolParamBlock* const noiseBox = Gtk::manage(new ToolParamBlock()); - linkedg->set_active (true); - linkedgConn = linkedg->signal_toggled().connect( sigc::mem_fun(*this, &Wavelet::linkedgToggled) ); + linkedg->set_active(true); + linkedgConn = linkedg->signal_toggled().connect(sigc::mem_fun(*this, &Wavelet::linkedgToggled)); noiseBox->pack_start(*linkedg); - level0noise->setAdjusterListener (this); + level0noise->setAdjusterListener(this); level0noise->setUpdatePolicy(RTUP_DYNAMIC); - level1noise->setAdjusterListener (this); + level1noise->setAdjusterListener(this); level1noise->setUpdatePolicy(RTUP_DYNAMIC); - level2noise->setAdjusterListener (this); + level2noise->setAdjusterListener(this); level2noise->setUpdatePolicy(RTUP_DYNAMIC); - level3noise->setAdjusterListener (this); + level3noise->setAdjusterListener(this); level3noise->setUpdatePolicy(RTUP_DYNAMIC); + ballum->setAdjusterListener(this); - noiseBox->pack_start( *level0noise, Gtk::PACK_SHRINK, 0); - noiseBox->pack_start( *level1noise, Gtk::PACK_SHRINK, 0); - noiseBox->pack_start( *level2noise, Gtk::PACK_SHRINK, 0); - noiseBox->pack_start( *level3noise, Gtk::PACK_SHRINK, 0); + noiseBox->pack_start(*ballum); + noiseBox->pack_start(*level0noise, Gtk::PACK_SHRINK, 0); + noiseBox->pack_start(*level1noise, Gtk::PACK_SHRINK, 0); + noiseBox->pack_start(*level2noise, Gtk::PACK_SHRINK, 0); + noiseBox->pack_start(*level3noise, Gtk::PACK_SHRINK, 0); + + balchrom->setAdjusterListener(this); + chromfi->setAdjusterListener(this); + chromco->setAdjusterListener(this); + + chroFrame->set_label_align(0.025, 0.5); + ToolParamBlock* const chroBox = Gtk::manage(new ToolParamBlock()); + chroBox->pack_start(*balchrom); + chroBox->pack_start(*chromfi); + chroBox->pack_start(*chromco); + chroFrame->add(*chroBox); + noiseBox->pack_start(*chroFrame); + + +//Clarity + mergeL->setAdjusterListener(this); + mergeC->setAdjusterListener(this); + softrad->setAdjusterListener(this); + showmask->set_active(false); + showmaskConn = showmask->signal_toggled().connect(sigc::mem_fun(*this, &Wavelet::showmaskToggled)); + + ToolParamBlock* const clariBox = Gtk::manage(new ToolParamBlock()); + // ushamethod->append(M("TP_WAVELET_USH")); + ushamethod->append(M("TP_WAVELET_SHA")); + ushamethod->append(M("TP_WAVELET_CLA")); + ushamethodconn = ushamethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::ushamethodChanged)); + ushamethod->set_tooltip_text(M("TP_WAVELET_USH_TOOLTIP")); + usharpHBox->pack_start(*usharpLabel, Gtk::PACK_SHRINK, 0); + usharpHBox->pack_start(*ushamethod); + + clariBox->pack_start(*usharpHBox); + clariBox->pack_start(*mergeL); + clariBox->pack_start(*mergeC); + clariBox->pack_start(*softrad); + clariBox->pack_start(*showmask); // Edge Sharpness - ToolParamBlock* const edgBox = Gtk::manage (new ToolParamBlock()); + ToolParamBlock* const edgBox = Gtk::manage(new ToolParamBlock()); + edgeffect->setAdjusterListener(this); + edgBox->pack_start(*edgeffect); + edgeffect->set_tooltip_markup(M("TP_WAVELET_EDEFFECT_TOOLTIP")); edgval->setAdjusterListener(this); edgBox->pack_start(*edgval); + edgrad->setAdjusterListener(this); edgBox->pack_start(*edgrad); - edgrad->set_tooltip_markup (M("TP_WAVELET_EDRAD_TOOLTIP")); + edgrad->set_tooltip_markup(M("TP_WAVELET_EDRAD_TOOLTIP")); - edgthresh->setAdjusterListener (this); - edgthresh->set_tooltip_markup (M("TP_WAVELET_EDGTHRESH_TOOLTIP")); - edgBox->pack_start (*edgthresh); + edgthresh->setAdjusterListener(this); + edgthresh->set_tooltip_markup(M("TP_WAVELET_EDGTHRESH_TOOLTIP")); + edgBox->pack_start(*edgthresh); Gtk::Label* const labmedgr = Gtk::manage(new Gtk::Label(M("TP_WAVELET_MEDGREINF") + ":")); Gtk::HBox* const edbox = Gtk::manage(new Gtk::HBox()); - edbox->pack_start (*labmedgr, Gtk::PACK_SHRINK, 1); + edbox->pack_start(*labmedgr, Gtk::PACK_SHRINK, 1); - Medgreinf->append (M("TP_WAVELET_RE1")); - Medgreinf->append (M("TP_WAVELET_RE2")); - Medgreinf->append (M("TP_WAVELET_RE3")); - MedgreinfConn = Medgreinf->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::MedgreinfChanged) ); - Medgreinf->set_tooltip_markup (M("TP_WAVELET_EDGREINF_TOOLTIP")); + Medgreinf->append(M("TP_WAVELET_RE1")); + Medgreinf->append(M("TP_WAVELET_RE2")); + Medgreinf->append(M("TP_WAVELET_RE3")); + MedgreinfConn = Medgreinf->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::MedgreinfChanged)); + Medgreinf->set_tooltip_markup(M("TP_WAVELET_EDGREINF_TOOLTIP")); edbox->pack_start(*Medgreinf); edgBox->pack_start(*edbox); - Gtk::HSeparator* const separatorlc = Gtk::manage (new Gtk::HSeparator()); + Gtk::HSeparator* const separatorlc = Gtk::manage(new Gtk::HSeparator()); edgBox->pack_start(*separatorlc, Gtk::PACK_SHRINK, 2); Gtk::Label* const labmED = Gtk::manage(new Gtk::Label(M("TP_WAVELET_EDTYPE") + ":")); Gtk::HBox* const ctboxED = Gtk::manage(new Gtk::HBox()); - ctboxED->pack_start (*labmED, Gtk::PACK_SHRINK, 1); + ctboxED->pack_start(*labmED, Gtk::PACK_SHRINK, 1); - EDmethod->append (M("TP_WAVELET_EDSL")); - EDmethod->append (M("TP_WAVELET_EDCU")); - EDmethodconn = EDmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::EDmethodChanged) ); + EDmethod->append(M("TP_WAVELET_EDSL")); + EDmethod->append(M("TP_WAVELET_EDCU")); + EDmethodconn = EDmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::EDmethodChanged)); ctboxED->pack_start(*EDmethod); - edgBox->pack_start (*ctboxED); + edgBox->pack_start(*ctboxED); - edgcont->setAdjusterListener (this); + edgcont->setAdjusterListener(this); edgcont->setBgGradient(milestones2); - edgcont->set_tooltip_markup (M("TP_WAVELET_EDGCONT_TOOLTIP")); + edgcont->set_tooltip_markup(M("TP_WAVELET_EDGCONT_TOOLTIP")); // <-- Edge Sharpness Local Contrast curve - CCWcurveEditorG->setCurveListener (this); + CCWcurveEditorG->setCurveListener(this); ccshape = static_cast(CCWcurveEditorG->addCurve(CT_Flat, "", nullptr, false, false)); @@ -513,70 +629,94 @@ Wavelet::Wavelet() : CCWcurveEditorG->show(); // --> - edgBox->pack_start (*edgcont); + edgBox->pack_start(*edgcont); edgBox->pack_start(*CCWcurveEditorG, Gtk::PACK_SHRINK, 4); - medianlev->set_active (true); - medianlevConn = medianlev->signal_toggled().connect( sigc::mem_fun(*this, &Wavelet::medianlevToggled) ); - medianlev->set_tooltip_text (M("TP_WAVELET_MEDILEV_TOOLTIP")); + medianlev->set_active(true); + medianlevConn = medianlev->signal_toggled().connect(sigc::mem_fun(*this, &Wavelet::medianlevToggled)); + medianlev->set_tooltip_text(M("TP_WAVELET_MEDILEV_TOOLTIP")); - Gtk::HSeparator* const separatored1 = Gtk::manage (new Gtk::HSeparator()); + Gtk::HSeparator* const separatored1 = Gtk::manage(new Gtk::HSeparator()); edgBox->pack_start(*separatored1, Gtk::PACK_SHRINK, 2); Gtk::HBox* const eddebox = Gtk::manage(new Gtk::HBox()); - edgBox->pack_start (*eddebox); + edgBox->pack_start(*eddebox); edgBox->pack_start(*medianlev); - edgedetect->setAdjusterListener (this); - edgedetect->set_tooltip_text (M("TP_WAVELET_EDGEDETECT_TOOLTIP")); + edgedetect->setAdjusterListener(this); + edgedetect->set_tooltip_text(M("TP_WAVELET_EDGEDETECT_TOOLTIP")); edgBox->pack_start(*edgedetect); - edgedetectthr->setAdjusterListener (this); - edgedetectthr->set_tooltip_text (M("TP_WAVELET_EDGEDETECTTHR_TOOLTIP")); + edgedetectthr->setAdjusterListener(this); + edgedetectthr->set_tooltip_text(M("TP_WAVELET_EDGEDETECTTHR_TOOLTIP")); edgBox->pack_start(*edgedetectthr); - edgedetectthr2->setAdjusterListener (this); + edgedetectthr2->setAdjusterListener(this); edgBox->pack_start(*edgedetectthr2); edgBox->pack_start(*separatoredge, Gtk::PACK_SHRINK, 2); - lipst->set_active (true); - lipstConn = lipst->signal_toggled().connect( sigc::mem_fun(*this, &Wavelet::lipstToggled) ); + lipst->set_active(true); + lipstConn = lipst->signal_toggled().connect(sigc::mem_fun(*this, &Wavelet::lipstToggled)); // lipst->set_tooltip_text (M("TP_WAVELET_LIPST_TOOLTIP")); edgBox->pack_start(*lipst); - edgesensi->setAdjusterListener (this); + edgesensi->setAdjusterListener(this); edgBox->pack_start(*edgesensi); - edgeampli->setAdjusterListener (this); + edgeampli->setAdjusterListener(this); edgBox->pack_start(*edgeampli); - Gtk::VBox* const ctboxES = Gtk::manage (new Gtk::VBox()); + Gtk::VBox* const ctboxES = Gtk::manage(new Gtk::VBox()); ctboxES->set_spacing(2); Gtk::HBox* const ctboxNP = Gtk::manage(new Gtk::HBox()); - ctboxNP->pack_start (*labmNP, Gtk::PACK_SHRINK, 1); + ctboxNP->pack_start(*labmNP, Gtk::PACK_SHRINK, 1); - NPmethod->append (M("TP_WAVELET_NPNONE")); - NPmethod->append (M("TP_WAVELET_NPLOW")); - NPmethod->append (M("TP_WAVELET_NPHIGH")); - NPmethodconn = NPmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::NPmethodChanged) ); - NPmethod->set_tooltip_text (M("TP_WAVELET_NPTYPE_TOOLTIP")); + NPmethod->append(M("TP_WAVELET_NPNONE")); + NPmethod->append(M("TP_WAVELET_NPLOW")); + NPmethod->append(M("TP_WAVELET_NPHIGH")); + NPmethodconn = NPmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::NPmethodChanged)); + NPmethod->set_tooltip_text(M("TP_WAVELET_NPTYPE_TOOLTIP")); ctboxNP->pack_start(*NPmethod); ctboxES->pack_start(*ctboxNP); edgBox->pack_start(*ctboxES); -// Gamut - ToolParamBlock* const conBox = Gtk::manage (new ToolParamBlock()); +//Blur Wavelet + ToolParamBlock* const blBox = Gtk::manage(new ToolParamBlock()); + + curveEditorbl->setCurveListener(this); - median->set_active (true); - medianConn = median->signal_toggled().connect( sigc::mem_fun(*this, &Wavelet::medianToggled) ); + blshape = static_cast(curveEditorbl->addCurve(CT_Flat, "", nullptr, false, false)); + + blshape->setIdentityValue(0.); + blshape->setResetCurve(FlatCurveType(default_params.blcurve.at(0)), default_params.blcurve); + blshape->setTooltip(M("TP_WAVELET_CURVEEDITOR_CC_TOOLTIP")); + + curveEditorbl->curveListComplete(); + curveEditorbl->show(); + + blBox->pack_start(*bluwav); + bluwav->setAdjusterListener(this); + blBox->pack_start(*curveEditorbl, Gtk::PACK_SHRINK, 4); + + + chrwav->setAdjusterListener(this); + blBox->pack_start(*chrwav); + + + +// Gamut + ToolParamBlock* const conBox = Gtk::manage(new ToolParamBlock()); + + median->set_active(true); + medianConn = median->signal_toggled().connect(sigc::mem_fun(*this, &Wavelet::medianToggled)); conBox->pack_start(*median); - hueskin->set_tooltip_markup (M("TP_WAVELET_HUESKIN_TOOLTIP")); + hueskin->set_tooltip_markup(M("TP_WAVELET_HUESKIN_TOOLTIP")); //from -PI to +PI (radians) convert to hsv and draw bottombar const std::vector milestones = { @@ -599,13 +739,13 @@ Wavelet::Wavelet() : hueskin->setBgGradient(milestones); conBox->pack_start(*hueskin); - hueskin->setAdjusterListener (this); + hueskin->setAdjusterListener(this); skinprotect->setAdjusterListener(this); conBox->pack_start(*skinprotect); - skinprotect->set_tooltip_markup (M("TP_WAVELET_SKIN_TOOLTIP")); + skinprotect->set_tooltip_markup(M("TP_WAVELET_SKIN_TOOLTIP")); - curveEditorGAM->setCurveListener (this); + curveEditorGAM->setCurveListener(this); Chshape = static_cast(curveEditorGAM->addCurve(CT_Flat, M("TP_WAVELET_CURVEEDITOR_CH"))); Chshape->setTooltip(M("TP_WAVELET_CURVEEDITOR_CH_TOOLTIP")); @@ -613,74 +753,116 @@ Wavelet::Wavelet() : curveEditorGAM->curveListComplete(); Chshape->setBottomBarBgGradient(milestones); - conBox->pack_start (*curveEditorGAM, Gtk::PACK_SHRINK, 4); + conBox->pack_start(*curveEditorGAM, Gtk::PACK_SHRINK, 4); - avoid->set_active (true); - avoidConn = avoid->signal_toggled().connect( sigc::mem_fun(*this, &Wavelet::avoidToggled) ); + avoid->set_active(true); + avoidConn = avoid->signal_toggled().connect(sigc::mem_fun(*this, &Wavelet::avoidToggled)); conBox->pack_start(*avoid); // Residual Image - ToolParamBlock* const resBox = Gtk::manage (new ToolParamBlock()); + ToolParamBlock* const resBox = Gtk::manage(new ToolParamBlock()); + oldsh->set_active(true); + oldshConn = oldsh->signal_toggled().connect(sigc::mem_fun(*this, &Wavelet::oldshToggled)); - rescon->setAdjusterListener (this); - resBox->pack_start(*rescon, Gtk::PACK_SHRINK); - resBox->pack_start(*thr); - thr->setAdjusterListener (this); + rescon->setAdjusterListener(this); - resconH->setAdjusterListener (this); - resBox->pack_start(*resconH, Gtk::PACK_SHRINK); + thr->setAdjusterListener(this); - thrH->setAdjusterListener (this); - resBox->pack_start(*thrH, Gtk::PACK_SHRINK); + resconH->setAdjusterListener(this); - contrast->set_tooltip_text (M("TP_WAVELET_CONTRA_TOOLTIP")); - contrast->setAdjusterListener (this); - resBox->pack_start(*contrast); //keep the possibility to reinstall + thrH->setAdjusterListener(this); - reschro->setAdjusterListener (this); - resBox->pack_start(*reschro); + radius->setAdjusterListener(this); + radius->hide(); + shFrame->set_label_align(0.025, 0.5); + ToolParamBlock* const shBox = Gtk::manage(new ToolParamBlock()); + shBox->pack_start(*oldsh); + shBox->pack_start(*rescon, Gtk::PACK_SHRINK); + shBox->pack_start(*thr); + shBox->pack_start(*resconH, Gtk::PACK_SHRINK); + shBox->pack_start(*thrH, Gtk::PACK_SHRINK); + shBox->pack_start(*radius, Gtk::PACK_SHRINK); + shFrame->add(*shBox); + resBox->pack_start(*shFrame); + + + contrast->set_tooltip_text(M("TP_WAVELET_CONTRA_TOOLTIP")); + contrast->setAdjusterListener(this); + + reschro->setAdjusterListener(this); + resblur->setAdjusterListener(this); + resblurc->setAdjusterListener(this); + + blurFrame->set_label_align(0.025, 0.5); + ToolParamBlock* const blurBox = Gtk::manage(new ToolParamBlock()); + blurBox->pack_start(*resblur); + blurBox->pack_start(*resblurc); + blurFrame->add(*blurBox); + + chromaFrame->set_label_align(0.025, 0.5); + ToolParamBlock* const chromaBox = Gtk::manage(new ToolParamBlock()); + chromaBox->pack_start(*reschro); + chromaBox->pack_start(*hueskin2); + chromaBox->pack_start(*sky); + chromaFrame->add(*chromaBox); Gtk::Label* const labmTM = Gtk::manage(new Gtk::Label(M("TP_WAVELET_TMTYPE") + ":")); Gtk::HBox* const ctboxTM = Gtk::manage(new Gtk::HBox()); - ctboxTM->pack_start (*labmTM, Gtk::PACK_SHRINK, 1); + ctboxTM->pack_start(*labmTM, Gtk::PACK_SHRINK, 1); - Gtk::HSeparator* const separatorR0 = Gtk::manage (new Gtk::HSeparator()); - resBox->pack_start(*separatorR0, Gtk::PACK_SHRINK, 2); +// Gtk::HSeparator* const separatorR0 = Gtk::manage(new Gtk::HSeparator()); +// resBox->pack_start(*separatorR0, Gtk::PACK_SHRINK, 2); - TMmethod->append (M("TP_WAVELET_COMPCONT")); - TMmethod->append (M("TP_WAVELET_COMPTM")); - TMmethodconn = TMmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::TMmethodChanged) ); + TMmethod->append(M("TP_WAVELET_COMPCONT")); + TMmethod->append(M("TP_WAVELET_COMPTM")); + TMmethodconn = TMmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::TMmethodChanged)); ctboxTM->pack_start(*TMmethod); - resBox->pack_start (*ctboxTM); - tmrs->set_tooltip_text (M("TP_WAVELET_TMSTRENGTH_TOOLTIP")); + tmrs->set_tooltip_text(M("TP_WAVELET_TMSTRENGTH_TOOLTIP")); - resBox->pack_start(*tmrs); - tmrs->setAdjusterListener (this); + tmrs->setAdjusterListener(this); - gamma->set_tooltip_text (M("TP_WAVELET_COMPGAMMA_TOOLTIP")); - resBox->pack_start(*gamma); - gamma->setAdjusterListener (this); + gamma->set_tooltip_text(M("TP_WAVELET_COMPGAMMA_TOOLTIP")); + gamma->setAdjusterListener(this); - Gtk::HSeparator* const separatorR1 = Gtk::manage (new Gtk::HSeparator()); - resBox->pack_start(*separatorR1, Gtk::PACK_SHRINK, 2); + //edgs->set_tooltip_text(M("TP_WAVELET_TMEDGS_TOOLTIP")); - hueskin2->set_tooltip_markup (M("TP_WAVELET_HUESKY_TOOLTIP")); + edgs->setAdjusterListener(this); + + //scale->set_tooltip_text(M("TP_WAVELET_TMSCALE_TOOLTIP")); + + scale->setAdjusterListener(this); + + contFrame->set_label_align(0.025, 0.5); + ToolParamBlock* const contBox = Gtk::manage(new ToolParamBlock()); + contBox->pack_start(*contrast); //keep the possibility to reinstall + contBox->pack_start(*ctboxTM); + contBox->pack_start(*tmrs); + contBox->pack_start(*gamma); + contBox->pack_start(*edgs); + contBox->pack_start(*scale); + contFrame->add(*contBox); + resBox->pack_start(*contFrame); + +// Gtk::HSeparator* const separatorR1 = Gtk::manage(new Gtk::HSeparator()); +// resBox->pack_start(*separatorR1, Gtk::PACK_SHRINK, 2); + + hueskin2->set_tooltip_markup(M("TP_WAVELET_HUESKY_TOOLTIP")); hueskin2->setBgGradient(milestones); - resBox->pack_start(*hueskin2); - hueskin2->setAdjusterListener (this); + hueskin2->setAdjusterListener(this); - sky->set_tooltip_text (M("TP_WAVELET_SKY_TOOLTIP")); - sky->setAdjusterListener (this); + sky->set_tooltip_text(M("TP_WAVELET_SKY_TOOLTIP")); + sky->setAdjusterListener(this); - resBox->pack_start(*sky); // whole hue range const std::vector milestones3 = makeWholeHueRange(); - curveEditorRES->setCurveListener (this); + curveEditorRES->setCurveListener(this); + resBox->pack_start(*blurFrame); + resBox->pack_start(*chromaFrame); hhshape = static_cast(curveEditorRES->addCurve(CT_Flat, M("TP_WAVELET_CURVEEDITOR_HH"))); hhshape->setTooltip(M("TP_WAVELET_CURVEEDITOR_HH_TOOLTIP")); @@ -688,54 +870,54 @@ Wavelet::Wavelet() : curveEditorRES->curveListComplete(); hhshape->setBottomBarBgGradient(milestones3); - resBox->pack_start (*curveEditorRES, Gtk::PACK_SHRINK, 4); + resBox->pack_start(*curveEditorRES, Gtk::PACK_SHRINK, 4); // Toning and Color Balance - Gtk::HSeparator* const separatorCB = Gtk::manage (new Gtk::HSeparator()); + Gtk::HSeparator* const separatorCB = Gtk::manage(new Gtk::HSeparator()); - Gtk::VBox* const chanMixerHLBox = Gtk::manage (new Gtk::VBox()); - Gtk::VBox* const chanMixerMidBox = Gtk::manage (new Gtk::VBox()); - Gtk::VBox* const chanMixerShadowsBox = Gtk::manage (new Gtk::VBox()); + Gtk::VBox* const chanMixerHLBox = Gtk::manage(new Gtk::VBox()); + Gtk::VBox* const chanMixerMidBox = Gtk::manage(new Gtk::VBox()); + Gtk::VBox* const chanMixerShadowsBox = Gtk::manage(new Gtk::VBox()); - cbenab->set_active (true); - cbenabConn = cbenab->signal_toggled().connect( sigc::mem_fun(*this, &Wavelet::cbenabToggled) ); - cbenab->set_tooltip_text (M("TP_WAVELET_CB_TOOLTIP")); + cbenab->set_active(true); + cbenabConn = cbenab->signal_toggled().connect(sigc::mem_fun(*this, &Wavelet::cbenabToggled)); + cbenab->set_tooltip_text(M("TP_WAVELET_CB_TOOLTIP")); - Gtk::Image* const iblueR = Gtk::manage (new RTImage ("circle-blue-small.png")); - Gtk::Image* const iyelL = Gtk::manage (new RTImage ("circle-yellow-small.png")); - Gtk::Image* const imagL = Gtk::manage (new RTImage ("circle-magenta-small.png")); - Gtk::Image* const igreenR = Gtk::manage (new RTImage ("circle-green-small.png")); + Gtk::Image* const iblueR = Gtk::manage(new RTImage("circle-blue-small.png")); + Gtk::Image* const iyelL = Gtk::manage(new RTImage("circle-yellow-small.png")); + Gtk::Image* const imagL = Gtk::manage(new RTImage("circle-magenta-small.png")); + Gtk::Image* const igreenR = Gtk::manage(new RTImage("circle-green-small.png")); - Gtk::Image* const iblueRm = Gtk::manage (new RTImage ("circle-blue-small.png")); - Gtk::Image* const iyelLm = Gtk::manage (new RTImage ("circle-yellow-small.png")); - Gtk::Image* const imagLm = Gtk::manage (new RTImage ("circle-magenta-small.png")); - Gtk::Image* const igreenRm = Gtk::manage (new RTImage ("circle-green-small.png")); + Gtk::Image* const iblueRm = Gtk::manage(new RTImage("circle-blue-small.png")); + Gtk::Image* const iyelLm = Gtk::manage(new RTImage("circle-yellow-small.png")); + Gtk::Image* const imagLm = Gtk::manage(new RTImage("circle-magenta-small.png")); + Gtk::Image* const igreenRm = Gtk::manage(new RTImage("circle-green-small.png")); - Gtk::Image* const iblueRh = Gtk::manage (new RTImage ("circle-blue-small.png")); - Gtk::Image* const iyelLh = Gtk::manage (new RTImage ("circle-yellow-small.png")); - Gtk::Image* const imagLh = Gtk::manage (new RTImage ("circle-magenta-small.png")); - Gtk::Image* const igreenRh = Gtk::manage (new RTImage ("circle-green-small.png")); + Gtk::Image* const iblueRh = Gtk::manage(new RTImage("circle-blue-small.png")); + Gtk::Image* const iyelLh = Gtk::manage(new RTImage("circle-yellow-small.png")); + Gtk::Image* const imagLh = Gtk::manage(new RTImage("circle-magenta-small.png")); + Gtk::Image* const igreenRh = Gtk::manage(new RTImage("circle-green-small.png")); - greenhigh = Gtk::manage (new Adjuster ("", -100., 100., 1., 0., igreenRh, imagLh)); - bluehigh = Gtk::manage (new Adjuster ("", -100., 100., 1., 0., iblueRh, iyelLh)); - greenmed = Gtk::manage (new Adjuster ("", -100., 100., 1., 0., igreenRm, imagLm)); - bluemed = Gtk::manage (new Adjuster ("", -100., 100., 1., 0. , iblueRm , iyelLm)); - greenlow = Gtk::manage (new Adjuster ("", -100., 100., 1., 0., igreenR, imagL)); - bluelow = Gtk::manage (new Adjuster ("", -100., 100., 1., 0., iblueR , iyelL)); + greenhigh = Gtk::manage(new Adjuster("", -100., 100., 1., 0., igreenRh, imagLh)); + bluehigh = Gtk::manage(new Adjuster("", -100., 100., 1., 0., iblueRh, iyelLh)); + greenmed = Gtk::manage(new Adjuster("", -100., 100., 1., 0., igreenRm, imagLm)); + bluemed = Gtk::manage(new Adjuster("", -100., 100., 1., 0., iblueRm, iyelLm)); + greenlow = Gtk::manage(new Adjuster("", -100., 100., 1., 0., igreenR, imagL)); + bluelow = Gtk::manage(new Adjuster("", -100., 100., 1., 0., iblueR, iyelL)); - chanMixerHLBox->pack_start (*greenhigh); - chanMixerHLBox->pack_start (*bluehigh); - chanMixerMidBox->pack_start (*greenmed); - chanMixerMidBox->pack_start (*bluemed); - chanMixerShadowsBox->pack_start (*greenlow); - chanMixerShadowsBox->pack_start (*bluelow); + chanMixerHLBox->pack_start(*greenhigh); + chanMixerHLBox->pack_start(*bluehigh); + chanMixerMidBox->pack_start(*greenmed); + chanMixerMidBox->pack_start(*bluemed); + chanMixerShadowsBox->pack_start(*greenlow); + chanMixerShadowsBox->pack_start(*bluelow); - greenlow->setAdjusterListener (this); - bluelow->setAdjusterListener (this); - greenmed->setAdjusterListener (this); - bluemed->setAdjusterListener (this); - greenhigh->setAdjusterListener (this); - bluehigh->setAdjusterListener (this); + greenlow->setAdjusterListener(this); + bluelow->setAdjusterListener(this); + greenmed->setAdjusterListener(this); + bluemed->setAdjusterListener(this); + greenhigh->setAdjusterListener(this); + bluehigh->setAdjusterListener(this); resBox->pack_start(*separatorCB, Gtk::PACK_SHRINK); @@ -751,15 +933,15 @@ Wavelet::Wavelet() : //RTImage *resetImg = Gtk::manage (new RTImage ("undo-small.png", "redo-small.png")); //neutral->set_image(*resetImg); Gtk::Button* const neutral = Gtk::manage(new Gtk::Button(M("TP_COLORTONING_NEUTRAL"))); - neutral->set_tooltip_text (M("TP_COLORTONING_NEUTRAL_TIP")); - neutralconn = neutral->signal_pressed().connect( sigc::mem_fun(*this, &Wavelet::neutral_pressed) ); + neutral->set_tooltip_text(M("TP_COLORTONING_NEUTRAL_TIP")); + neutralconn = neutral->signal_pressed().connect(sigc::mem_fun(*this, &Wavelet::neutral_pressed)); neutral->show(); - neutrHBox->pack_start (*neutral, Gtk::PACK_EXPAND_WIDGET); + neutrHBox->pack_start(*neutral, Gtk::PACK_EXPAND_WIDGET); - resBox->pack_start (*neutrHBox); + resBox->pack_start(*neutrHBox); // Final Touchup - Gtk::VBox* const ctboxBA = Gtk::manage (new Gtk::VBox()); + Gtk::VBox* const ctboxBA = Gtk::manage(new Gtk::VBox()); ctboxBA->set_spacing(2); @@ -767,19 +949,20 @@ Wavelet::Wavelet() : //ctboxBA->pack_start(*separatorfin, Gtk::PACK_SHRINK, 2); Gtk::Label* const labmBA = Gtk::manage(new Gtk::Label(M("TP_WAVELET_BATYPE") + ":")); Gtk::HBox* const ctboxFI = Gtk::manage(new Gtk::HBox()); - ctboxFI->pack_start (*labmBA, Gtk::PACK_SHRINK, 1); + ctboxFI->pack_start(*labmBA, Gtk::PACK_SHRINK, 1); - BAmethod->append (M("TP_WAVELET_BANONE")); - BAmethod->append (M("TP_WAVELET_BASLI")); - BAmethod->append (M("TP_WAVELET_BACUR")); - BAmethodconn = BAmethod->signal_changed().connect ( sigc::mem_fun(*this, &Wavelet::BAmethodChanged) ); + BAmethod->append(M("TP_WAVELET_BANONE")); + BAmethod->append(M("TP_WAVELET_BASLI")); + BAmethod->append(M("TP_WAVELET_BACUR")); + BAmethodconn = BAmethod->signal_changed().connect(sigc::mem_fun(*this, &Wavelet::BAmethodChanged)); ctboxFI->pack_start(*BAmethod); ctboxBA->pack_start(*ctboxFI); - balance->setAdjusterListener (this); - balance->set_tooltip_text (M("TP_WAVELET_BALANCE_TOOLTIP")); + balance->setAdjusterListener(this); + balance->set_tooltip_text(M("TP_WAVELET_BALANCE_TOOLTIP")); + softradend->setAdjusterListener(this); - opacityCurveEditorW->setCurveListener (this); + opacityCurveEditorW->setCurveListener(this); opacityShape = static_cast(opacityCurveEditorW->addCurve(CT_Flat, "", nullptr, false, false)); opacityShape->setIdentityValue(0.); @@ -790,12 +973,12 @@ Wavelet::Wavelet() : opacityCurveEditorW->curveListComplete(); opacityCurveEditorW->show(); - iter->setAdjusterListener (this); - iter->set_tooltip_text (M("TP_WAVELET_ITER_TOOLTIP")); + iter->setAdjusterListener(this); + iter->set_tooltip_text(M("TP_WAVELET_ITER_TOOLTIP")); - Gtk::HSeparator* const separatorbalend = Gtk::manage (new Gtk::HSeparator()); + Gtk::HSeparator* const separatorbalend = Gtk::manage(new Gtk::HSeparator()); - opacityCurveEditorWL->setCurveListener (this); + opacityCurveEditorWL->setCurveListener(this); opacityShapeWL = static_cast(opacityCurveEditorWL->addCurve(CT_Flat, "", nullptr, false, false)); opacityShapeWL->setIdentityValue(0.); @@ -806,7 +989,7 @@ Wavelet::Wavelet() : opacityCurveEditorWL->curveListComplete(); opacityCurveEditorWL->show(); - curveEditorG->setCurveListener (this); + curveEditorG->setCurveListener(this); clshape = static_cast(curveEditorG->addCurve(CT_Diagonal, M("TP_WAVELET_CURVEEDITOR_CL"))); clshape->setTooltip(M("TP_WAVELET_CURVEEDITOR_CL_TOOLTIP")); @@ -815,54 +998,66 @@ Wavelet::Wavelet() : curveEditorG->curveListComplete(); - tmr->set_active (true); - tmr->set_tooltip_text (M("TP_WAVELET_BALCHRO_TOOLTIP")); - tmrConn = tmr->signal_toggled().connect( sigc::mem_fun(*this, &Wavelet::tmrToggled) ); + tmr->set_active(true); + tmr->set_tooltip_text(M("TP_WAVELET_BALCHRO_TOOLTIP")); + tmrConn = tmr->signal_toggled().connect(sigc::mem_fun(*this, &Wavelet::tmrToggled)); - ToolParamBlock* const finalBox = Gtk::manage (new ToolParamBlock()); + ToolParamBlock* const finalBox = Gtk::manage(new ToolParamBlock()); - finalBox->pack_start (*ctboxBA); + finalBox->pack_start(*ctboxBA); finalBox->pack_start(*balance); - finalBox->pack_start( *opacityCurveEditorW, Gtk::PACK_SHRINK, 2); + finalBox->pack_start(*opacityCurveEditorW, Gtk::PACK_SHRINK, 2); finalBox->pack_start(*iter); finalBox->pack_start(*tmr); finalBox->pack_start(*separatorbalend, Gtk::PACK_SHRINK, 2); - finalBox->pack_start( *opacityCurveEditorWL, Gtk::PACK_SHRINK, 2); + finalBox->pack_start(*opacityCurveEditorWL, Gtk::PACK_SHRINK, 2); - finalBox->pack_start (*curveEditorG, Gtk::PACK_SHRINK, 4); + finalBox->pack_start(*curveEditorG, Gtk::PACK_SHRINK, 4); + finalBox->pack_start(*softradend); //----------------------------- + + expsettings->add(*settingsBox, false); expsettings->setLevel(2); - pack_start (*expsettings); + pack_start(*expsettings); expcontrast->add(*levBox, false); expcontrast->setLevel(2); - pack_start (*expcontrast); + pack_start(*expcontrast); expchroma->add(*chBox, false); expchroma->setLevel(2); - pack_start (*expchroma); - - exptoning->add(*tonBox, false); - exptoning->setLevel(2); - pack_start (*exptoning); - - expnoise->add(*noiseBox, false); - expnoise->setLevel(2); - pack_start (*expnoise); - - expedge->add(*edgBox, false); - expedge->setLevel(2); - pack_start (*expedge); + pack_start(*expchroma); expgamut->add(*conBox, false); expgamut->setLevel(2); - pack_start (*expgamut); + pack_start(*expgamut); + + exptoning->add(*tonBox, false); + exptoning->setLevel(2); + pack_start(*exptoning); + + expnoise->add(*noiseBox, false); + expnoise->setLevel(2); + pack_start(*expnoise); + + expedge->add(*edgBox, false); + expedge->setLevel(2); + pack_start(*expedge); + + expbl->add(*blBox, false); + expbl->setLevel(2); + pack_start(*expbl); + + expclari->add(*clariBox, false); + expclari->setLevel(2); + pack_start(*expclari); + expresid->add(*resBox, false); expresid->setLevel(2); @@ -873,12 +1068,13 @@ Wavelet::Wavelet() : pack_start(*expfinal); } -Wavelet::~Wavelet () +Wavelet::~Wavelet() { idle_register.destroy(); delete opaCurveEditorG; delete opacityCurveEditorG; + delete curveEditorbl; delete CCWcurveEditorG; delete curveEditorRES; delete curveEditorGAM; @@ -888,27 +1084,26 @@ Wavelet::~Wavelet () } -void Wavelet::wavChanged (double nlevel) +void Wavelet::wavChanged(double nlevel) { if (!batchMode) { idle_register.add( - [this, nlevel]() -> bool - { - wavLabels->set_text( - Glib::ustring::compose( - M("TP_WAVELET_LEVLABEL"), - Glib::ustring::format(std::fixed, std::setprecision(0), nlevel) - ) - ); - return false; - } + [this, nlevel]() -> bool { + wavLabels->set_text( + Glib::ustring::compose( + M("TP_WAVELET_LEVLABEL"), + Glib::ustring::format(std::fixed, std::setprecision(0), nlevel) + ) + ); + return false; + } ); } } // Will only reset the channel mixer // WARNING! In mutiImage mode, and for sliders in ADD mode, this will reset the slider to 0, but not to the default value as in SET mode. -void Wavelet::neutral_pressed () +void Wavelet::neutral_pressed() { disableListener(); greenlow->resetValue(false); @@ -921,11 +1116,11 @@ void Wavelet::neutral_pressed () enableListener(); if (listener && getEnabled()) { - listener->panelChanged (EvWavNeutral, M("GENERAL_RESET")); + listener->panelChanged(EvWavNeutral, M("GENERAL_RESET")); } } -void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) +void Wavelet::read(const ProcParams* pp, const ParamsEdited* pedited) { /***************************************************************************************************** @@ -934,7 +1129,7 @@ void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) * *****************************************************************************************************/ - disableListener (); + disableListener(); Lmethodconn.block(true); CLmethodconn.block(true); Backmethodconn.block(true); @@ -949,6 +1144,7 @@ void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) TMmethodconn.block(true); HSmethodconn.block(true); MedgreinfConn.block(true); + ushamethodconn.block(true); cbenabConn.block(true); enableChromaConn.block(true); enableContrastConn.block(true); @@ -966,65 +1162,75 @@ void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) //HSmethod->set_active (1); // Note: default values are controlled in rtengine::ProcParams::SetDefaults if (pp->wavelet.HSmethod == "without") { - HSmethod->set_active (0); + HSmethod->set_active(0); } else if (pp->wavelet.HSmethod == "with") { - HSmethod->set_active (1); + HSmethod->set_active(1); } //CHmethod->set_active (1); if (pp->wavelet.CHmethod == "without") { - CHmethod->set_active (0); + CHmethod->set_active(0); } else if (pp->wavelet.CHmethod == "with") { - CHmethod->set_active (1); + CHmethod->set_active(1); } else if (pp->wavelet.CHmethod == "link") { - CHmethod->set_active (2); + CHmethod->set_active(2); } //Medgreinf->set_active (1); if (pp->wavelet.Medgreinf == "more") { - Medgreinf->set_active (0); + Medgreinf->set_active(0); } else if (pp->wavelet.Medgreinf == "none") { - Medgreinf->set_active (1); + Medgreinf->set_active(1); } else if (pp->wavelet.Medgreinf == "less") { - Medgreinf->set_active (2); + Medgreinf->set_active(2); + } + + //ushamethod +// if (pp->wavelet.ushamethod == "none") { +// ushamethod->set_active(0); +// } else + if (pp->wavelet.ushamethod == "sharp") { + ushamethod->set_active(0); + } else if (pp->wavelet.ushamethod == "clari") { + ushamethod->set_active(1); } //CHSLmethod->set_active (1); if (pp->wavelet.CHSLmethod == "SL") { - CHSLmethod->set_active (0); + CHSLmethod->set_active(0); } else if (pp->wavelet.CHSLmethod == "CU") { - CHSLmethod->set_active (1); + CHSLmethod->set_active(1); } //EDmethod->set_active (1); if (pp->wavelet.EDmethod == "SL") { - EDmethod->set_active (0); + EDmethod->set_active(0); } else if (pp->wavelet.EDmethod == "CU") { - EDmethod->set_active (1); + EDmethod->set_active(1); } if (pp->wavelet.NPmethod == "none") { - NPmethod->set_active (0); + NPmethod->set_active(0); } else if (pp->wavelet.NPmethod == "low") { - NPmethod->set_active (1); + NPmethod->set_active(1); } else if (pp->wavelet.NPmethod == "high") { - NPmethod->set_active (2); + NPmethod->set_active(2); } //BAmethod->set_active (0); if (pp->wavelet.BAmethod == "none") { - BAmethod->set_active (0); + BAmethod->set_active(0); } else if (pp->wavelet.BAmethod == "sli") { - BAmethod->set_active (1); + BAmethod->set_active(1); } else if (pp->wavelet.BAmethod == "cur") { - BAmethod->set_active (2); + BAmethod->set_active(2); } //TMmethod->set_active (1); if (pp->wavelet.TMmethod == "cont") { - TMmethod->set_active (0); + TMmethod->set_active(0); } else if (pp->wavelet.TMmethod == "tm") { - TMmethod->set_active (1); + TMmethod->set_active(1); } // else if (pp->wavelet.TMmethod=="both") @@ -1032,99 +1238,108 @@ void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) //Backmethod->set_active (3); if (pp->wavelet.Backmethod == "black") { - Backmethod->set_active (0); + Backmethod->set_active(0); } else if (pp->wavelet.Backmethod == "grey") { - Backmethod->set_active (1); + Backmethod->set_active(1); } else if (pp->wavelet.Backmethod == "resid") { - Backmethod->set_active (2); + Backmethod->set_active(2); } //CLmethod->set_active (3); if (pp->wavelet.CLmethod == "one") { - CLmethod->set_active (0); + CLmethod->set_active(0); } else if (pp->wavelet.CLmethod == "inf") { - CLmethod->set_active (1); + CLmethod->set_active(1); } else if (pp->wavelet.CLmethod == "sup") { - CLmethod->set_active (2); + CLmethod->set_active(2); } else if (pp->wavelet.CLmethod == "all") { - CLmethod->set_active (3); + CLmethod->set_active(3); } //Tilesmethod->set_active (2); if (pp->wavelet.Tilesmethod == "full") { - Tilesmethod->set_active (0); + Tilesmethod->set_active(0); } else if (pp->wavelet.Tilesmethod == "big") { - Tilesmethod->set_active (1); - } else if (pp->wavelet.Tilesmethod == "lit") { - Tilesmethod->set_active (2); + Tilesmethod->set_active(1); +// } else if (pp->wavelet.Tilesmethod == "lit") { +// Tilesmethod->set_active(2); } //daubcoeffmethod->set_active (4); if (pp->wavelet.daubcoeffmethod == "2_") { - daubcoeffmethod->set_active (0); + daubcoeffmethod->set_active(0); } else if (pp->wavelet.daubcoeffmethod == "4_") { - daubcoeffmethod->set_active (1); + daubcoeffmethod->set_active(1); } else if (pp->wavelet.daubcoeffmethod == "6_") { - daubcoeffmethod->set_active (2); + daubcoeffmethod->set_active(2); } else if (pp->wavelet.daubcoeffmethod == "10_") { - daubcoeffmethod->set_active (3); + daubcoeffmethod->set_active(3); } else if (pp->wavelet.daubcoeffmethod == "14_") { - daubcoeffmethod->set_active (4); + daubcoeffmethod->set_active(4); } //Dirmethod->set_active (3); if (pp->wavelet.Dirmethod == "one") { - Dirmethod->set_active (0); + Dirmethod->set_active(0); } else if (pp->wavelet.Dirmethod == "two") { - Dirmethod->set_active (1); + Dirmethod->set_active(1); } else if (pp->wavelet.Dirmethod == "thr") { - Dirmethod->set_active (2); + Dirmethod->set_active(2); } else if (pp->wavelet.Dirmethod == "all") { - Dirmethod->set_active (3); + Dirmethod->set_active(3); } int selectedLevel = pp->wavelet.Lmethod - 1; - Lmethod->set_active (selectedLevel == -1 ? 4 : selectedLevel); + Lmethod->set_active(selectedLevel == -1 ? 4 : selectedLevel); - ccshape->setCurve (pp->wavelet.ccwcurve); - opacityShapeRG->setCurve (pp->wavelet.opacityCurveRG); - opacityShapeBY->setCurve (pp->wavelet.opacityCurveBY); - opacityShape->setCurve (pp->wavelet.opacityCurveW); - opacityShapeWL->setCurve (pp->wavelet.opacityCurveWL); - hhshape->setCurve (pp->wavelet.hhcurve); - Chshape->setCurve (pp->wavelet.Chcurve); - clshape->setCurve (pp->wavelet.wavclCurve); - expcontrast->setEnabled (pp->wavelet.expcontrast); - expchroma->setEnabled (pp->wavelet.expchroma); - expedge->setEnabled (pp->wavelet.expedge); - expresid->setEnabled (pp->wavelet.expresid); - expfinal->setEnabled (pp->wavelet.expfinal); - exptoning->setEnabled (pp->wavelet.exptoning); - expnoise->setEnabled (pp->wavelet.expnoise); + ccshape->setCurve(pp->wavelet.ccwcurve); + blshape->setCurve(pp->wavelet.blcurve); + opacityShapeRG->setCurve(pp->wavelet.opacityCurveRG); + opacityShapeBY->setCurve(pp->wavelet.opacityCurveBY); + opacityShape->setCurve(pp->wavelet.opacityCurveW); + opacityShapeWL->setCurve(pp->wavelet.opacityCurveWL); + hhshape->setCurve(pp->wavelet.hhcurve); + Chshape->setCurve(pp->wavelet.Chcurve); + clshape->setCurve(pp->wavelet.wavclCurve); + expcontrast->setEnabled(pp->wavelet.expcontrast); + expchroma->setEnabled(pp->wavelet.expchroma); + expedge->setEnabled(pp->wavelet.expedge); + expbl->setEnabled(pp->wavelet.expbl); + expresid->setEnabled(pp->wavelet.expresid); + expfinal->setEnabled(pp->wavelet.expfinal); + exptoning->setEnabled(pp->wavelet.exptoning); + expnoise->setEnabled(pp->wavelet.expnoise); + expclari->setEnabled(pp->wavelet.expclari); setEnabled(pp->wavelet.enabled); - avoidConn.block (true); - avoid->set_active (pp->wavelet.avoid); - avoidConn.block (false); - tmrConn.block (true); - tmr->set_active (pp->wavelet.tmr); - tmrConn.block (false); - medianConn.block (true); - median->set_active (pp->wavelet.median); - medianConn.block (false); - medianlevConn.block (true); - medianlev->set_active (pp->wavelet.medianlev); - medianlevConn.block (false); - linkedgConn.block (true); - linkedg->set_active (pp->wavelet.linkedg); - linkedgConn.block (false); - cbenabConn.block (true); - cbenab->set_active (pp->wavelet.cbenab); - cbenabConn.block (false); + avoidConn.block(true); + avoid->set_active(pp->wavelet.avoid); + avoidConn.block(false); + showmaskConn.block(true); + showmask->set_active(pp->wavelet.showmask); + showmaskConn.block(false); + oldshConn.block(true); + oldsh->set_active(pp->wavelet.oldsh); + oldshConn.block(false); + tmrConn.block(true); + tmr->set_active(pp->wavelet.tmr); + tmrConn.block(false); + medianConn.block(true); + median->set_active(pp->wavelet.median); + medianConn.block(false); + medianlevConn.block(true); + medianlev->set_active(pp->wavelet.medianlev); + medianlevConn.block(false); + linkedgConn.block(true); + linkedg->set_active(pp->wavelet.linkedg); + linkedgConn.block(false); + cbenabConn.block(true); + cbenab->set_active(pp->wavelet.cbenab); + cbenabConn.block(false); - lipstConn.block (true); - lipst->set_active (pp->wavelet.lipst); - lipstConn.block (false); + lipstConn.block(true); + lipst->set_active(pp->wavelet.lipst); + lipstConn.block(false); //edgreinfConn.block (true); //edgreinf->set_active (pp->wavelet.edgreinf); //edgreinfConn.block (false); @@ -1135,23 +1350,34 @@ void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) lastcbenab = pp->wavelet.cbenab; lastlipst = pp->wavelet.lipst; lastavoid = pp->wavelet.avoid; + lastshowmask = pp->wavelet.showmask; + lastoldsh = pp->wavelet.oldsh; lasttmr = pp->wavelet.tmr; - rescon->setValue (pp->wavelet.rescon); - resconH->setValue (pp->wavelet.resconH); - reschro->setValue (pp->wavelet.reschro); - tmrs->setValue (pp->wavelet.tmrs); - gamma->setValue (pp->wavelet.gamma); - sup->setValue (pp->wavelet.sup); - sky->setValue (pp->wavelet.sky); - thres->setValue (pp->wavelet.thres); - chroma->setValue (pp->wavelet.chroma); - chro->setValue (pp->wavelet.chro); - contrast->setValue (pp->wavelet.contrast); - edgrad->setValue (pp->wavelet.edgrad); - edgval->setValue (pp->wavelet.edgval); - edgthresh->setValue (pp->wavelet.edgthresh); - thr->setValue (pp->wavelet.thr); - thrH->setValue (pp->wavelet.thrH); + sigma->setValue(pp->wavelet.sigma); + offset->setValue(pp->wavelet.offset); + lowthr->setValue(pp->wavelet.lowthr); + rescon->setValue(pp->wavelet.rescon); + resconH->setValue(pp->wavelet.resconH); + reschro->setValue(pp->wavelet.reschro); + resblur->setValue(pp->wavelet.resblur); + resblurc->setValue(pp->wavelet.resblurc); + tmrs->setValue(pp->wavelet.tmrs); + edgs->setValue(pp->wavelet.edgs); + scale->setValue(pp->wavelet.scale); + gamma->setValue(pp->wavelet.gamma); + sup->setValue(pp->wavelet.sup); + sky->setValue(pp->wavelet.sky); + thres->setValue(pp->wavelet.thres); + chroma->setValue(pp->wavelet.chroma); + chro->setValue(pp->wavelet.chro); + contrast->setValue(pp->wavelet.contrast); + edgrad->setValue(pp->wavelet.edgrad); + edgeffect->setValue(pp->wavelet.edgeffect); + edgval->setValue(pp->wavelet.edgval); + edgthresh->setValue(pp->wavelet.edgthresh); + thr->setValue(pp->wavelet.thr); + thrH->setValue(pp->wavelet.thrH); + radius->setValue(pp->wavelet.radius); skinprotect->setValue(pp->wavelet.skinprotect); hueskin->setValue(pp->wavelet.hueskin); hueskin2->setValue(pp->wavelet.hueskin2); @@ -1167,14 +1393,24 @@ void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) pastlev->setValue(pp->wavelet.pastlev); satlev->setValue(pp->wavelet.satlev); edgcont->setValue(pp->wavelet.edgcont); + chrwav->setValue(pp->wavelet.chrwav); + bluwav->setValue(pp->wavelet.bluwav); - greenlow->setValue (pp->wavelet.greenlow); - bluelow->setValue (pp->wavelet.bluelow); - greenmed->setValue (pp->wavelet.greenmed); - bluemed->setValue (pp->wavelet.bluemed); - greenhigh->setValue (pp->wavelet.greenhigh); - bluehigh->setValue (pp->wavelet.bluehigh); + greenlow->setValue(pp->wavelet.greenlow); + bluelow->setValue(pp->wavelet.bluelow); + greenmed->setValue(pp->wavelet.greenmed); + bluemed->setValue(pp->wavelet.bluemed); + greenhigh->setValue(pp->wavelet.greenhigh); + bluehigh->setValue(pp->wavelet.bluehigh); + mergeL->setValue(pp->wavelet.mergeL); + mergeC->setValue(pp->wavelet.mergeC); + softrad->setValue(pp->wavelet.softrad); + softradend->setValue(pp->wavelet.softradend); + ballum->setValue(pp->wavelet.ballum); + balchrom->setValue(pp->wavelet.balchrom); + chromfi->setValue(pp->wavelet.chromfi); + chromco->setValue(pp->wavelet.chromco); level0noise->setValue(pp->wavelet.level0noise); level1noise->setValue(pp->wavelet.level1noise); level2noise->setValue(pp->wavelet.level2noise); @@ -1254,83 +1490,112 @@ void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) Medgreinf->set_active_text(M("GENERAL_UNCHANGED")); } - set_inconsistent (multiImage && !pedited->wavelet.enabled); - ccshape->setUnChanged (!pedited->wavelet.ccwcurve); - expcontrast->set_inconsistent (!pedited->wavelet.expcontrast); - expchroma->set_inconsistent (!pedited->wavelet.expchroma); - expedge->set_inconsistent (!pedited->wavelet.expedge); - expresid->set_inconsistent (!pedited->wavelet.expresid); - expfinal->set_inconsistent (!pedited->wavelet.expfinal); - exptoning->set_inconsistent (!pedited->wavelet.exptoning); - expnoise->set_inconsistent (!pedited->wavelet.expnoise); - opacityShapeRG->setCurve (pp->wavelet.opacityCurveRG); - opacityShapeBY->setCurve (pp->wavelet.opacityCurveBY); - opacityShape->setCurve (pp->wavelet.opacityCurveW); - opacityShapeWL->setCurve (pp->wavelet.opacityCurveWL); - hhshape->setUnChanged (!pedited->wavelet.hhcurve); - Chshape->setUnChanged (!pedited->wavelet.Chcurve); - clshape->setUnChanged (!pedited->wavelet.wavclCurve); - avoid->set_inconsistent (!pedited->wavelet.avoid); - tmr->set_inconsistent (!pedited->wavelet.tmr); - edgthresh->setEditedState (pedited->wavelet.edgthresh ? Edited : UnEdited); - rescon->setEditedState (pedited->wavelet.rescon ? Edited : UnEdited); - resconH->setEditedState (pedited->wavelet.resconH ? Edited : UnEdited); - reschro->setEditedState (pedited->wavelet.reschro ? Edited : UnEdited); - tmrs->setEditedState (pedited->wavelet.tmrs ? Edited : UnEdited); - gamma->setEditedState (pedited->wavelet.gamma ? Edited : UnEdited); - sup->setEditedState (pedited->wavelet.sup ? Edited : UnEdited); - sky->setEditedState (pedited->wavelet.sky ? Edited : UnEdited); - thres->setEditedState (pedited->wavelet.thres ? Edited : UnEdited); - balance->setEditedState (pedited->wavelet.balance ? Edited : UnEdited); - iter->setEditedState (pedited->wavelet.iter ? Edited : UnEdited); - threshold->setEditedState (pedited->wavelet.threshold ? Edited : UnEdited); - threshold2->setEditedState (pedited->wavelet.threshold2 ? Edited : UnEdited); - edgedetect->setEditedState (pedited->wavelet.edgedetect ? Edited : UnEdited); - edgedetectthr->setEditedState (pedited->wavelet.edgedetectthr ? Edited : UnEdited); - edgedetectthr2->setEditedState (pedited->wavelet.edgedetectthr2 ? Edited : UnEdited); - edgesensi->setEditedState (pedited->wavelet.edgesensi ? Edited : UnEdited); - edgeampli->setEditedState (pedited->wavelet.edgeampli ? Edited : UnEdited); - chroma->setEditedState (pedited->wavelet.chroma ? Edited : UnEdited); - chro->setEditedState (pedited->wavelet.chro ? Edited : UnEdited); - - greenlow->setEditedState (pedited->wavelet.greenlow ? Edited : UnEdited); - bluelow->setEditedState (pedited->wavelet.bluelow ? Edited : UnEdited); - greenmed->setEditedState (pedited->wavelet.greenmed ? Edited : UnEdited); - bluemed->setEditedState (pedited->wavelet.bluemed ? Edited : UnEdited); - greenhigh->setEditedState (pedited->wavelet.greenhigh ? Edited : UnEdited); - bluehigh->setEditedState (pedited->wavelet.bluehigh ? Edited : UnEdited); - - median->set_inconsistent (!pedited->wavelet.median); - medianlev->set_inconsistent (!pedited->wavelet.medianlev); - linkedg->set_inconsistent (!pedited->wavelet.linkedg); -// edgreinf->set_inconsistent (!pedited->wavelet.edgreinf); - cbenab->set_inconsistent (!pedited->wavelet.cbenab); - lipst->set_inconsistent (!pedited->wavelet.lipst); - contrast->setEditedState (pedited->wavelet.contrast ? Edited : UnEdited); - edgrad->setEditedState (pedited->wavelet.edgrad ? Edited : UnEdited); - edgval->setEditedState (pedited->wavelet.edgval ? Edited : UnEdited); - thr->setEditedState (pedited->wavelet.thr ? Edited : UnEdited); - thrH->setEditedState (pedited->wavelet.thrH ? Edited : UnEdited); - skinprotect->setEditedState (pedited->wavelet.skinprotect ? Edited : UnEdited); - hueskin->setEditedState (pedited->wavelet.hueskin ? Edited : UnEdited); - hueskin2->setEditedState (pedited->wavelet.hueskin2 ? Edited : UnEdited); - hllev->setEditedState (pedited->wavelet.hllev ? Edited : UnEdited); - bllev->setEditedState (pedited->wavelet.bllev ? Edited : UnEdited); - pastlev->setEditedState (pedited->wavelet.pastlev ? Edited : UnEdited); - satlev->setEditedState (pedited->wavelet.satlev ? Edited : UnEdited); - strength->setEditedState(pedited->wavelet.strength ? Edited : UnEdited); - edgcont->setEditedState (pedited->wavelet.edgcont ? Edited : UnEdited); - level0noise->setEditedState (pedited->wavelet.level0noise ? Edited : UnEdited); - level1noise->setEditedState (pedited->wavelet.level1noise ? Edited : UnEdited); - level2noise->setEditedState (pedited->wavelet.level2noise ? Edited : UnEdited); - level3noise->setEditedState (pedited->wavelet.level3noise ? Edited : UnEdited); - - for(int i = 0; i < 9; i++) { - correction[i]->setEditedState (pedited->wavelet.c[i] ? Edited : UnEdited); + if (!pedited->wavelet.ushamethod) { + ushamethod->set_active_text(M("GENERAL_UNCHANGED")); } - for(int i = 0; i < 9; i++) { - correctionch[i]->setEditedState (pedited->wavelet.ch[i] ? Edited : UnEdited); + set_inconsistent(multiImage && !pedited->wavelet.enabled); + ccshape->setUnChanged(!pedited->wavelet.ccwcurve); + blshape->setUnChanged(!pedited->wavelet.blcurve); + expcontrast->set_inconsistent(!pedited->wavelet.expcontrast); + expchroma->set_inconsistent(!pedited->wavelet.expchroma); + expedge->set_inconsistent(!pedited->wavelet.expedge); + expbl->set_inconsistent(!pedited->wavelet.expbl); + expresid->set_inconsistent(!pedited->wavelet.expresid); + expfinal->set_inconsistent(!pedited->wavelet.expfinal); + expclari->set_inconsistent(!pedited->wavelet.expclari); + exptoning->set_inconsistent(!pedited->wavelet.exptoning); + expnoise->set_inconsistent(!pedited->wavelet.expnoise); + opacityShapeRG->setCurve(pp->wavelet.opacityCurveRG); + opacityShapeBY->setCurve(pp->wavelet.opacityCurveBY); + opacityShape->setCurve(pp->wavelet.opacityCurveW); + opacityShapeWL->setCurve(pp->wavelet.opacityCurveWL); + hhshape->setUnChanged(!pedited->wavelet.hhcurve); + Chshape->setUnChanged(!pedited->wavelet.Chcurve); + clshape->setUnChanged(!pedited->wavelet.wavclCurve); + avoid->set_inconsistent(!pedited->wavelet.avoid); + showmask->set_inconsistent(!pedited->wavelet.showmask); + oldsh->set_inconsistent(!pedited->wavelet.oldsh); + tmr->set_inconsistent(!pedited->wavelet.tmr); + edgthresh->setEditedState(pedited->wavelet.edgthresh ? Edited : UnEdited); + rescon->setEditedState(pedited->wavelet.rescon ? Edited : UnEdited); + sigma->setEditedState(pedited->wavelet.sigma ? Edited : UnEdited); + offset->setEditedState(pedited->wavelet.offset ? Edited : UnEdited); + lowthr->setEditedState(pedited->wavelet.lowthr ? Edited : UnEdited); + resconH->setEditedState(pedited->wavelet.resconH ? Edited : UnEdited); + reschro->setEditedState(pedited->wavelet.reschro ? Edited : UnEdited); + resblur->setEditedState(pedited->wavelet.resblur ? Edited : UnEdited); + resblurc->setEditedState(pedited->wavelet.resblurc ? Edited : UnEdited); + tmrs->setEditedState(pedited->wavelet.tmrs ? Edited : UnEdited); + edgs->setEditedState(pedited->wavelet.edgs ? Edited : UnEdited); + scale->setEditedState(pedited->wavelet.scale ? Edited : UnEdited); + gamma->setEditedState(pedited->wavelet.gamma ? Edited : UnEdited); + sup->setEditedState(pedited->wavelet.sup ? Edited : UnEdited); + sky->setEditedState(pedited->wavelet.sky ? Edited : UnEdited); + thres->setEditedState(pedited->wavelet.thres ? Edited : UnEdited); + balance->setEditedState(pedited->wavelet.balance ? Edited : UnEdited); + iter->setEditedState(pedited->wavelet.iter ? Edited : UnEdited); + threshold->setEditedState(pedited->wavelet.threshold ? Edited : UnEdited); + threshold2->setEditedState(pedited->wavelet.threshold2 ? Edited : UnEdited); + edgedetect->setEditedState(pedited->wavelet.edgedetect ? Edited : UnEdited); + edgedetectthr->setEditedState(pedited->wavelet.edgedetectthr ? Edited : UnEdited); + edgedetectthr2->setEditedState(pedited->wavelet.edgedetectthr2 ? Edited : UnEdited); + edgesensi->setEditedState(pedited->wavelet.edgesensi ? Edited : UnEdited); + edgeampli->setEditedState(pedited->wavelet.edgeampli ? Edited : UnEdited); + chroma->setEditedState(pedited->wavelet.chroma ? Edited : UnEdited); + chro->setEditedState(pedited->wavelet.chro ? Edited : UnEdited); + + greenlow->setEditedState(pedited->wavelet.greenlow ? Edited : UnEdited); + bluelow->setEditedState(pedited->wavelet.bluelow ? Edited : UnEdited); + greenmed->setEditedState(pedited->wavelet.greenmed ? Edited : UnEdited); + bluemed->setEditedState(pedited->wavelet.bluemed ? Edited : UnEdited); + greenhigh->setEditedState(pedited->wavelet.greenhigh ? Edited : UnEdited); + bluehigh->setEditedState(pedited->wavelet.bluehigh ? Edited : UnEdited); + mergeL->setEditedState(pedited->wavelet.mergeL ? Edited : UnEdited); + mergeC->setEditedState(pedited->wavelet.mergeC ? Edited : UnEdited); + softrad->setEditedState(pedited->wavelet.softrad ? Edited : UnEdited); + softradend->setEditedState(pedited->wavelet.softradend ? Edited : UnEdited); + + ballum->setEditedState(pedited->wavelet.ballum ? Edited : UnEdited); + balchrom->setEditedState(pedited->wavelet.balchrom ? Edited : UnEdited); + chromfi->setEditedState(pedited->wavelet.chromfi ? Edited : UnEdited); + chromco->setEditedState(pedited->wavelet.chromco ? Edited : UnEdited); + + median->set_inconsistent(!pedited->wavelet.median); + medianlev->set_inconsistent(!pedited->wavelet.medianlev); + linkedg->set_inconsistent(!pedited->wavelet.linkedg); +// edgreinf->set_inconsistent (!pedited->wavelet.edgreinf); + cbenab->set_inconsistent(!pedited->wavelet.cbenab); + lipst->set_inconsistent(!pedited->wavelet.lipst); + contrast->setEditedState(pedited->wavelet.contrast ? Edited : UnEdited); + edgrad->setEditedState(pedited->wavelet.edgrad ? Edited : UnEdited); + edgeffect->setEditedState(pedited->wavelet.edgeffect ? Edited : UnEdited); + edgval->setEditedState(pedited->wavelet.edgval ? Edited : UnEdited); + thr->setEditedState(pedited->wavelet.thr ? Edited : UnEdited); + thrH->setEditedState(pedited->wavelet.thrH ? Edited : UnEdited); + radius->setEditedState(pedited->wavelet.radius ? Edited : UnEdited); + skinprotect->setEditedState(pedited->wavelet.skinprotect ? Edited : UnEdited); + hueskin->setEditedState(pedited->wavelet.hueskin ? Edited : UnEdited); + hueskin2->setEditedState(pedited->wavelet.hueskin2 ? Edited : UnEdited); + hllev->setEditedState(pedited->wavelet.hllev ? Edited : UnEdited); + bllev->setEditedState(pedited->wavelet.bllev ? Edited : UnEdited); + pastlev->setEditedState(pedited->wavelet.pastlev ? Edited : UnEdited); + satlev->setEditedState(pedited->wavelet.satlev ? Edited : UnEdited); + strength->setEditedState(pedited->wavelet.strength ? Edited : UnEdited); + edgcont->setEditedState(pedited->wavelet.edgcont ? Edited : UnEdited); + chrwav->setEditedState(pedited->wavelet.chrwav ? Edited : UnEdited); + bluwav->setEditedState(pedited->wavelet.bluwav ? Edited : UnEdited); + level0noise->setEditedState(pedited->wavelet.level0noise ? Edited : UnEdited); + level1noise->setEditedState(pedited->wavelet.level1noise ? Edited : UnEdited); + level2noise->setEditedState(pedited->wavelet.level2noise ? Edited : UnEdited); + level3noise->setEditedState(pedited->wavelet.level3noise ? Edited : UnEdited); + + for (int i = 0; i < 9; i++) { + correction[i]->setEditedState(pedited->wavelet.c[i] ? Edited : UnEdited); + } + + for (int i = 0; i < 9; i++) { + correctionch[i]->setEditedState(pedited->wavelet.ch[i] ? Edited : UnEdited); } } @@ -1345,20 +1610,20 @@ void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) y = thres->getValue(); int z; - for(z = y; z < 9; z++) { + for (z = y; z < 9; z++) { correction[z]->hide(); } - for(z = 0; z < y; z++) { + for (z = 0; z < y; z++) { correction[z]->show(); } if (pp->wavelet.CHSLmethod == "SL") { - for(z = y; z < 9; z++) { + for (z = y; z < 9; z++) { correctionch[z]->hide(); } - for(z = 0; z < y; z++) { + for (z = 0; z < y; z++) { correctionch[z]->show(); } } @@ -1374,16 +1639,17 @@ void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) TMmethodUpdateUI(); //BackmethodUpdateUI(); CLmethodUpdateUI(); - lipstUpdateUI (); + lipstUpdateUI(); + oldshToggled(); //TilesmethodUpdateUI(); //daubcoeffmethodUpdateUI(); //DirmethodUpdateUI(); //LmethodUpdateUI(); - enabledUpdateUI (); - medianlevUpdateUI (); - cbenabUpdateUI (); + enabledUpdateUI(); + medianlevUpdateUI(); + cbenabUpdateUI(); - if(z == 9) { + if (z == 9) { sup->show(); } else { sup->hide(); @@ -1410,6 +1676,7 @@ void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) HSmethodconn.block(false); Dirmethodconn.block(false); MedgreinfConn.block(false); + ushamethodconn.block(false); enableChromaConn.block(false); enableContrastConn.block(false); enableEdgeConn.block(false); @@ -1418,12 +1685,13 @@ void Wavelet::read (const ProcParams* pp, const ParamsEdited* pedited) enableResidConn.block(false); enableToningConn.block(false); - enableListener (); + enableListener(); } -void Wavelet::setEditProvider (EditDataProvider *provider) +void Wavelet::setEditProvider(EditDataProvider *provider) { ccshape->setEditProvider(provider); + blshape->setEditProvider(provider); opacityShapeRG->setEditProvider(provider); opacityShapeBY->setEditProvider(provider); opacityShape->setEditProvider(provider); @@ -1433,41 +1701,53 @@ void Wavelet::setEditProvider (EditDataProvider *provider) clshape->setEditProvider(provider); } -void Wavelet::autoOpenCurve () +void Wavelet::autoOpenCurve() { ccshape->openIfNonlinear(); + blshape->openIfNonlinear(); //opacityShapeRG->openIfNonlinear(); //opacityShapeBY->openIfNonlinear(); } -void Wavelet::write (ProcParams* pp, ParamsEdited* pedited) +void Wavelet::write(ProcParams* pp, ParamsEdited* pedited) { pp->wavelet.enabled = getEnabled(); - pp->wavelet.avoid = avoid->get_active (); - pp->wavelet.tmr = tmr->get_active (); + pp->wavelet.avoid = avoid->get_active(); + pp->wavelet.showmask = showmask->get_active(); + pp->wavelet.oldsh = oldsh->get_active(); + pp->wavelet.tmr = tmr->get_active(); + pp->wavelet.sigma = sigma->getValue(); + pp->wavelet.offset = offset->getValue(); + pp->wavelet.lowthr = lowthr->getValue(); pp->wavelet.rescon = rescon->getValue(); pp->wavelet.resconH = resconH->getValue(); pp->wavelet.reschro = reschro->getValue(); + pp->wavelet.resblur = resblur->getValue(); + pp->wavelet.resblurc = resblurc->getValue(); pp->wavelet.tmrs = tmrs->getValue(); + pp->wavelet.edgs = edgs->getValue(); + pp->wavelet.scale = scale->getValue(); pp->wavelet.gamma = gamma->getValue(); pp->wavelet.sup = sup->getValue(); pp->wavelet.sky = sky->getValue(); pp->wavelet.thres = thres->getValue(); pp->wavelet.chroma = chroma->getValue(); pp->wavelet.chro = chro->getValue(); - pp->wavelet.median = median->get_active (); - pp->wavelet.medianlev = medianlev->get_active (); - pp->wavelet.linkedg = linkedg->get_active (); + pp->wavelet.median = median->get_active(); + pp->wavelet.medianlev = medianlev->get_active(); + pp->wavelet.linkedg = linkedg->get_active(); // pp->wavelet.edgreinf = edgreinf->get_active (); - pp->wavelet.cbenab = cbenab->get_active (); - pp->wavelet.lipst = lipst->get_active (); + pp->wavelet.cbenab = cbenab->get_active(); + pp->wavelet.lipst = lipst->get_active(); pp->wavelet.contrast = contrast->getValue(); pp->wavelet.edgrad = edgrad->getValue(); + pp->wavelet.edgeffect = edgeffect->getValue(); pp->wavelet.edgval = edgval->getValue(); pp->wavelet.edgthresh = edgthresh->getValue(); pp->wavelet.thr = thr->getValue(); pp->wavelet.thrH = thrH->getValue(); + pp->wavelet.radius = radius->getValue(); pp->wavelet.hueskin = hueskin->getValue (); pp->wavelet.hueskin2 = hueskin2->getValue (); pp->wavelet.skinprotect = skinprotect->getValue(); @@ -1481,38 +1761,51 @@ void Wavelet::write (ProcParams* pp, ParamsEdited* pedited) pp->wavelet.hllev = hllev->getValue (); pp->wavelet.bllev = bllev->getValue (); pp->wavelet.edgcont = edgcont->getValue (); + pp->wavelet.chrwav = chrwav->getValue(); + pp->wavelet.bluwav = bluwav->getValue(); pp->wavelet.level0noise = level0noise->getValue (); pp->wavelet.level1noise = level1noise->getValue (); pp->wavelet.level2noise = level2noise->getValue (); pp->wavelet.level3noise = level3noise->getValue (); - pp->wavelet.ccwcurve = ccshape->getCurve (); - pp->wavelet.opacityCurveRG = opacityShapeRG->getCurve (); - pp->wavelet.opacityCurveBY = opacityShapeBY->getCurve (); - pp->wavelet.opacityCurveW = opacityShape->getCurve (); - pp->wavelet.opacityCurveWL = opacityShapeWL->getCurve (); - pp->wavelet.hhcurve = hhshape->getCurve (); - pp->wavelet.Chcurve = Chshape->getCurve (); + pp->wavelet.ccwcurve = ccshape->getCurve(); + pp->wavelet.blcurve = blshape->getCurve(); + pp->wavelet.opacityCurveRG = opacityShapeRG->getCurve(); + pp->wavelet.opacityCurveBY = opacityShapeBY->getCurve(); + pp->wavelet.opacityCurveW = opacityShape->getCurve(); + pp->wavelet.opacityCurveWL = opacityShapeWL->getCurve(); + pp->wavelet.hhcurve = hhshape->getCurve(); + pp->wavelet.Chcurve = Chshape->getCurve(); pp->wavelet.pastlev = pastlev->getValue (); pp->wavelet.satlev = satlev->getValue (); pp->wavelet.strength = (int) strength->getValue(); pp->wavelet.balance = (int) balance->getValue(); + pp->wavelet.balchrom = balchrom->getValue(); + pp->wavelet.ballum = ballum->getValue(); + pp->wavelet.chromfi = chromfi->getValue(); + pp->wavelet.chromco = chromco->getValue(); - pp->wavelet.greenlow = greenlow->getValue (); - pp->wavelet.bluelow = bluelow->getValue (); - pp->wavelet.greenmed = greenmed->getValue (); - pp->wavelet.bluemed = bluemed->getValue (); - pp->wavelet.greenhigh = greenhigh->getValue (); - pp->wavelet.bluehigh = bluehigh->getValue (); + pp->wavelet.greenlow = greenlow->getValue(); + pp->wavelet.bluelow = bluelow->getValue(); + pp->wavelet.greenmed = greenmed->getValue(); + pp->wavelet.bluemed = bluemed->getValue(); + pp->wavelet.greenhigh = greenhigh->getValue(); + pp->wavelet.bluehigh = bluehigh->getValue(); + pp->wavelet.mergeL = mergeL->getValue(); + pp->wavelet.mergeC = mergeC->getValue(); + pp->wavelet.softrad = softrad->getValue(); + pp->wavelet.softradend = softradend->getValue(); pp->wavelet.expcontrast = expcontrast->getEnabled(); pp->wavelet.expchroma = expchroma->getEnabled(); pp->wavelet.expedge = expedge->getEnabled(); + pp->wavelet.expbl = expbl->getEnabled(); pp->wavelet.expresid = expresid->getEnabled(); pp->wavelet.expfinal = expfinal->getEnabled(); pp->wavelet.exptoning = exptoning->getEnabled(); pp->wavelet.expnoise = expnoise->getEnabled(); + pp->wavelet.expclari = expclari->getEnabled(); pp->wavelet.iter = (int) iter->getValue(); - pp->wavelet.wavclCurve = clshape->getCurve (); + pp->wavelet.wavclCurve = clshape->getCurve(); for (int i = 0; i < 9; i++) { pp->wavelet.c[i] = (int) correction[i]->getValue(); @@ -1525,6 +1818,8 @@ void Wavelet::write (ProcParams* pp, ParamsEdited* pedited) if (pedited) { pedited->wavelet.enabled = !get_inconsistent(); pedited->wavelet.avoid = !avoid->get_inconsistent(); + pedited->wavelet.showmask = !showmask->get_inconsistent(); + pedited->wavelet.oldsh = !oldsh->get_inconsistent(); pedited->wavelet.tmr = !tmr->get_inconsistent(); pedited->wavelet.median = !median->get_inconsistent(); pedited->wavelet.medianlev = !medianlev->get_inconsistent(); @@ -1532,6 +1827,7 @@ void Wavelet::write (ProcParams* pp, ParamsEdited* pedited) pedited->wavelet.cbenab = !cbenab->get_inconsistent(); pedited->wavelet.lipst = !lipst->get_inconsistent(); pedited->wavelet.Medgreinf = Medgreinf->get_active_text() != M("GENERAL_UNCHANGED"); + pedited->wavelet.ushamethod = ushamethod->get_active_text() != M("GENERAL_UNCHANGED"); pedited->wavelet.Lmethod = Lmethod->get_active_text() != M("GENERAL_UNCHANGED"); pedited->wavelet.CLmethod = CLmethod->get_active_text() != M("GENERAL_UNCHANGED"); pedited->wavelet.Backmethod = Backmethod->get_active_text() != M("GENERAL_UNCHANGED"); @@ -1546,10 +1842,17 @@ void Wavelet::write (ProcParams* pp, ParamsEdited* pedited) pedited->wavelet.HSmethod = HSmethod->get_active_text() != M("GENERAL_UNCHANGED"); pedited->wavelet.Dirmethod = Dirmethod->get_active_text() != M("GENERAL_UNCHANGED"); pedited->wavelet.edgthresh = edgthresh->getEditedState(); + pedited->wavelet.sigma = sigma->getEditedState(); + pedited->wavelet.offset = offset->getEditedState(); + pedited->wavelet.lowthr = lowthr->getEditedState(); pedited->wavelet.rescon = rescon->getEditedState(); pedited->wavelet.resconH = resconH->getEditedState(); pedited->wavelet.reschro = reschro->getEditedState(); + pedited->wavelet.resblur = resblur->getEditedState(); + pedited->wavelet.resblurc = resblurc->getEditedState(); pedited->wavelet.tmrs = tmrs->getEditedState(); + pedited->wavelet.edgs = edgs->getEditedState(); + pedited->wavelet.scale = scale->getEditedState(); pedited->wavelet.gamma = gamma->getEditedState(); pedited->wavelet.sup = sup->getEditedState(); pedited->wavelet.sky = sky->getEditedState(); @@ -1565,51 +1868,66 @@ void Wavelet::write (ProcParams* pp, ParamsEdited* pedited) pedited->wavelet.chro = chro->getEditedState(); pedited->wavelet.contrast = contrast->getEditedState(); pedited->wavelet.edgrad = edgrad->getEditedState(); + pedited->wavelet.edgeffect = edgeffect->getEditedState(); pedited->wavelet.edgval = edgval->getEditedState(); pedited->wavelet.thr = thr->getEditedState(); pedited->wavelet.thrH = thrH->getEditedState(); - pedited->wavelet.hueskin = hueskin->getEditedState (); - pedited->wavelet.hueskin2 = hueskin2->getEditedState (); + pedited->wavelet.radius = radius->getEditedState(); + pedited->wavelet.hueskin = hueskin->getEditedState(); + pedited->wavelet.hueskin2 = hueskin2->getEditedState(); pedited->wavelet.skinprotect = skinprotect->getEditedState(); - pedited->wavelet.hllev = hllev->getEditedState (); - pedited->wavelet.ccwcurve = !ccshape->isUnChanged (); - pedited->wavelet.edgcont = edgcont->getEditedState (); - pedited->wavelet.level0noise = level0noise->getEditedState (); - pedited->wavelet.level1noise = level1noise->getEditedState (); - pedited->wavelet.level2noise = level2noise->getEditedState (); - pedited->wavelet.level3noise = level3noise->getEditedState (); - pedited->wavelet.opacityCurveRG = !opacityShapeRG->isUnChanged (); - pedited->wavelet.opacityCurveBY = !opacityShapeBY->isUnChanged (); - pedited->wavelet.opacityCurveW = !opacityShape->isUnChanged (); - pedited->wavelet.opacityCurveWL = !opacityShapeWL->isUnChanged (); - pedited->wavelet.hhcurve = !hhshape->isUnChanged (); - pedited->wavelet.Chcurve = !Chshape->isUnChanged (); - pedited->wavelet.bllev = bllev->getEditedState (); - pedited->wavelet.pastlev = pastlev->getEditedState (); - pedited->wavelet.satlev = satlev->getEditedState (); - pedited->wavelet.strength = strength->getEditedState (); - pedited->wavelet.greenlow = greenlow->getEditedState (); - pedited->wavelet.bluelow = bluelow->getEditedState (); - pedited->wavelet.greenmed = greenmed->getEditedState (); - pedited->wavelet.bluemed = bluemed->getEditedState (); - pedited->wavelet.greenhigh = greenhigh->getEditedState (); - pedited->wavelet.bluehigh = bluehigh->getEditedState (); - pedited->wavelet.balance = balance->getEditedState (); - pedited->wavelet.iter = iter->getEditedState (); - pedited->wavelet.wavclCurve = !clshape->isUnChanged (); + pedited->wavelet.hllev = hllev->getEditedState(); + pedited->wavelet.ccwcurve = !ccshape->isUnChanged(); + pedited->wavelet.blcurve = !blshape->isUnChanged(); + pedited->wavelet.edgcont = edgcont->getEditedState(); + pedited->wavelet.chrwav = chrwav->getEditedState(); + pedited->wavelet.bluwav = bluwav->getEditedState(); + pedited->wavelet.level0noise = level0noise->getEditedState(); + pedited->wavelet.level1noise = level1noise->getEditedState(); + pedited->wavelet.level2noise = level2noise->getEditedState(); + pedited->wavelet.level3noise = level3noise->getEditedState(); + pedited->wavelet.opacityCurveRG = !opacityShapeRG->isUnChanged(); + pedited->wavelet.opacityCurveBY = !opacityShapeBY->isUnChanged(); + pedited->wavelet.opacityCurveW = !opacityShape->isUnChanged(); + pedited->wavelet.opacityCurveWL = !opacityShapeWL->isUnChanged(); + pedited->wavelet.hhcurve = !hhshape->isUnChanged(); + pedited->wavelet.Chcurve = !Chshape->isUnChanged(); + pedited->wavelet.bllev = bllev->getEditedState(); + pedited->wavelet.pastlev = pastlev->getEditedState(); + pedited->wavelet.satlev = satlev->getEditedState(); + pedited->wavelet.strength = strength->getEditedState(); + pedited->wavelet.greenlow = greenlow->getEditedState(); + pedited->wavelet.bluelow = bluelow->getEditedState(); + pedited->wavelet.greenmed = greenmed->getEditedState(); + pedited->wavelet.bluemed = bluemed->getEditedState(); + pedited->wavelet.greenhigh = greenhigh->getEditedState(); + pedited->wavelet.bluehigh = bluehigh->getEditedState(); + pedited->wavelet.ballum = ballum->getEditedState(); + pedited->wavelet.balchrom = balchrom->getEditedState(); + pedited->wavelet.chromfi = chromfi->getEditedState(); + pedited->wavelet.chromco = chromco->getEditedState(); + pedited->wavelet.mergeL = mergeL->getEditedState(); + pedited->wavelet.mergeC = mergeC->getEditedState(); + pedited->wavelet.softrad = softrad->getEditedState(); + pedited->wavelet.softradend = softradend->getEditedState(); + pedited->wavelet.balance = balance->getEditedState(); + pedited->wavelet.iter = iter->getEditedState(); + pedited->wavelet.wavclCurve = !clshape->isUnChanged(); pedited->wavelet.expcontrast = !expcontrast->get_inconsistent(); pedited->wavelet.expchroma = !expchroma->get_inconsistent(); pedited->wavelet.expedge = !expedge->get_inconsistent(); + pedited->wavelet.expbl = !expbl->get_inconsistent(); pedited->wavelet.expresid = !expresid->get_inconsistent(); pedited->wavelet.expfinal = !expfinal->get_inconsistent(); pedited->wavelet.exptoning = !exptoning->get_inconsistent(); pedited->wavelet.expnoise = !expnoise->get_inconsistent(); + pedited->wavelet.expclari = !expclari->get_inconsistent(); - for(int i = 0; i < 9; i++) { + for (int i = 0; i < 9; i++) { pedited->wavelet.c[i] = correction[i]->getEditedState(); } - for(int i = 0; i < 9; i++) { + for (int i = 0; i < 9; i++) { pedited->wavelet.ch[i] = correctionch[i]->getEditedState(); } @@ -1631,6 +1949,15 @@ void Wavelet::write (ProcParams* pp, ParamsEdited* pedited) pp->wavelet.Medgreinf = "less"; } +// if (ushamethod->get_active_row_number() == 0) { +// pp->wavelet.ushamethod = "none"; +// } else + if (ushamethod->get_active_row_number() == 0) { + pp->wavelet.ushamethod = "sharp"; + } else if (ushamethod->get_active_row_number() == 1) { + pp->wavelet.ushamethod = "clari"; + } + if (CHSLmethod->get_active_row_number() == 0) { pp->wavelet.CHSLmethod = "SL"; } else if (CHSLmethod->get_active_row_number() == 1) { @@ -1696,8 +2023,8 @@ void Wavelet::write (ProcParams* pp, ParamsEdited* pedited) pp->wavelet.Tilesmethod = "full"; } else if (Tilesmethod->get_active_row_number() == 1) { pp->wavelet.Tilesmethod = "big"; - } else if (Tilesmethod->get_active_row_number() == 2) { - pp->wavelet.Tilesmethod = "lit"; +// } else if (Tilesmethod->get_active_row_number() == 2) { +// pp->wavelet.Tilesmethod = "lit"; } if (daubcoeffmethod->get_active_row_number() == 0) { @@ -1725,31 +2052,33 @@ void Wavelet::write (ProcParams* pp, ParamsEdited* pedited) pp->wavelet.Lmethod = Lmethod->get_active_row_number() + 1; } -void Wavelet::curveChanged (CurveEditor* ce) +void Wavelet::curveChanged(CurveEditor* ce) { if (listener && getEnabled()) { if (ce == ccshape) { - listener->panelChanged (EvWavCCCurve, M("HISTORY_CUSTOMCURVE")); + listener->panelChanged(EvWavCCCurve, M("HISTORY_CUSTOMCURVE")); + } else if (ce == blshape) { + listener->panelChanged(EvWavblshape, M("HISTORY_CUSTOMCURVE")); } else if (ce == opacityShapeRG) { - listener->panelChanged (EvWavColor, M("HISTORY_CUSTOMCURVE")); + listener->panelChanged(EvWavColor, M("HISTORY_CUSTOMCURVE")); } else if (ce == opacityShapeBY) { - listener->panelChanged (EvWavOpac, M("HISTORY_CUSTOMCURVE")); + listener->panelChanged(EvWavOpac, M("HISTORY_CUSTOMCURVE")); } else if (ce == opacityShape) { - listener->panelChanged (EvWavopacity, M("HISTORY_CUSTOMCURVE")); + listener->panelChanged(EvWavopacity, M("HISTORY_CUSTOMCURVE")); } else if (ce == opacityShapeWL) { - listener->panelChanged (EvWavopacityWL, M("HISTORY_CUSTOMCURVE")); + listener->panelChanged(EvWavopacityWL, M("HISTORY_CUSTOMCURVE")); } else if (ce == hhshape) { - listener->panelChanged (EvWavHHCurve, M("HISTORY_CUSTOMCURVE")); + listener->panelChanged(EvWavHHCurve, M("HISTORY_CUSTOMCURVE")); } else if (ce == Chshape) { - listener->panelChanged (EvWavCHCurve, M("HISTORY_CUSTOMCURVE")); + listener->panelChanged(EvWavCHCurve, M("HISTORY_CUSTOMCURVE")); } else if (ce == clshape) { - listener->panelChanged (EvWavCLCurve, M("HISTORY_CUSTOMCURVE")); + listener->panelChanged(EvWavCLCurve, M("HISTORY_CUSTOMCURVE")); } } } -void Wavelet::setDefaults (const ProcParams* defParams, const ParamsEdited* pedited) +void Wavelet::setDefaults(const ProcParams* defParams, const ParamsEdited* pedited) { for (int i = 0; i < 9; i++) { @@ -1760,32 +2089,41 @@ void Wavelet::setDefaults (const ProcParams* defParams, const ParamsEdited* pedi correctionch[i]->setDefault(defParams->wavelet.ch[i]); } - strength->setDefault(defParams->wavelet.strength ); - balance->setDefault(defParams->wavelet.balance ); - iter->setDefault(defParams->wavelet.iter ); - rescon->setDefault (defParams->wavelet.rescon); - resconH->setDefault (defParams->wavelet.resconH); - reschro->setDefault (defParams->wavelet.reschro); - tmrs->setDefault (defParams->wavelet.tmrs); - gamma->setDefault (defParams->wavelet.gamma); - sup->setDefault (defParams->wavelet.sup); - sky->setDefault (defParams->wavelet.sky); - thres->setDefault (defParams->wavelet.thres); - threshold->setDefault (defParams->wavelet.threshold); - threshold2->setDefault (defParams->wavelet.threshold2); - edgedetect->setDefault (defParams->wavelet.edgedetect); - edgedetectthr->setDefault (defParams->wavelet.edgedetectthr); - edgedetectthr2->setDefault (defParams->wavelet.edgedetectthr2); - edgesensi->setDefault (defParams->wavelet.edgesensi); - edgeampli->setDefault (defParams->wavelet.edgeampli); - chroma->setDefault (defParams->wavelet.chroma); - chro->setDefault (defParams->wavelet.chro); - contrast->setDefault (defParams->wavelet.contrast); - edgrad->setDefault (defParams->wavelet.edgrad); - edgval->setDefault (defParams->wavelet.edgval); - edgthresh->setDefault (defParams->wavelet.edgthresh); - thr->setDefault (defParams->wavelet.thr); - thrH->setDefault (defParams->wavelet.thrH); + strength->setDefault(defParams->wavelet.strength); + balance->setDefault(defParams->wavelet.balance); + iter->setDefault(defParams->wavelet.iter); + sigma->setDefault(defParams->wavelet.sigma); + offset->setDefault(defParams->wavelet.offset); + lowthr->setDefault(defParams->wavelet.lowthr); + rescon->setDefault(defParams->wavelet.rescon); + resconH->setDefault(defParams->wavelet.resconH); + reschro->setDefault(defParams->wavelet.reschro); + resblur->setDefault(defParams->wavelet.resblur); + resblurc->setDefault(defParams->wavelet.resblurc); + tmrs->setDefault(defParams->wavelet.tmrs); + edgs->setDefault(defParams->wavelet.edgs); + scale->setDefault(defParams->wavelet.scale); + gamma->setDefault(defParams->wavelet.gamma); + sup->setDefault(defParams->wavelet.sup); + sky->setDefault(defParams->wavelet.sky); + thres->setDefault(defParams->wavelet.thres); + threshold->setDefault(defParams->wavelet.threshold); + threshold2->setDefault(defParams->wavelet.threshold2); + edgedetect->setDefault(defParams->wavelet.edgedetect); + edgedetectthr->setDefault(defParams->wavelet.edgedetectthr); + edgedetectthr2->setDefault(defParams->wavelet.edgedetectthr2); + edgesensi->setDefault(defParams->wavelet.edgesensi); + edgeampli->setDefault(defParams->wavelet.edgeampli); + chroma->setDefault(defParams->wavelet.chroma); + chro->setDefault(defParams->wavelet.chro); + contrast->setDefault(defParams->wavelet.contrast); + edgrad->setDefault(defParams->wavelet.edgrad); + edgeffect->setDefault(defParams->wavelet.edgeffect); + edgval->setDefault(defParams->wavelet.edgval); + edgthresh->setDefault(defParams->wavelet.edgthresh); + thr->setDefault(defParams->wavelet.thr); + thrH->setDefault(defParams->wavelet.thrH); + radius->setDefault(defParams->wavelet.radius); hueskin->setDefault (defParams->wavelet.hueskin); hueskin2->setDefault (defParams->wavelet.hueskin2); hllev->setDefault (defParams->wavelet.hllev); @@ -1793,32 +2131,57 @@ void Wavelet::setDefaults (const ProcParams* defParams, const ParamsEdited* pedi pastlev->setDefault (defParams->wavelet.pastlev); satlev->setDefault (defParams->wavelet.satlev); edgcont->setDefault (defParams->wavelet.edgcont); + chrwav->setDefault(defParams->wavelet.chrwav); + bluwav->setDefault(defParams->wavelet.bluwav); level0noise->setDefault (defParams->wavelet.level0noise); level1noise->setDefault (defParams->wavelet.level1noise); level2noise->setDefault (defParams->wavelet.level2noise); level3noise->setDefault (defParams->wavelet.level3noise); + ballum->setDefault(defParams->wavelet.ballum); + balchrom->setDefault(defParams->wavelet.balchrom); + chromfi->setDefault(defParams->wavelet.chromfi); + chromco->setDefault(defParams->wavelet.chromco); - greenlow->setDefault (defParams->wavelet.greenlow); - bluelow->setDefault (defParams->wavelet.bluelow); - greenmed->setDefault (defParams->wavelet.greenmed); - bluemed->setDefault (defParams->wavelet.bluemed); - greenhigh->setDefault (defParams->wavelet.greenhigh); - bluehigh->setDefault (defParams->wavelet.bluehigh); + greenlow->setDefault(defParams->wavelet.greenlow); + bluelow->setDefault(defParams->wavelet.bluelow); + greenmed->setDefault(defParams->wavelet.greenmed); + bluemed->setDefault(defParams->wavelet.bluemed); + greenhigh->setDefault(defParams->wavelet.greenhigh); + bluehigh->setDefault(defParams->wavelet.bluehigh); + mergeL->setDefault(defParams->wavelet.mergeL); + mergeC->setDefault(defParams->wavelet.mergeC); + softrad->setDefault(defParams->wavelet.softrad); + softradend->setDefault(defParams->wavelet.softradend); if (pedited) { - greenlow->setDefaultEditedState (pedited->wavelet.greenlow ? Edited : UnEdited); - bluelow->setDefaultEditedState (pedited->wavelet.bluelow ? Edited : UnEdited); - greenmed->setDefaultEditedState (pedited->wavelet.greenmed ? Edited : UnEdited); - bluemed->setDefaultEditedState (pedited->wavelet.bluemed ? Edited : UnEdited); - greenhigh->setDefaultEditedState (pedited->wavelet.greenhigh ? Edited : UnEdited); - bluehigh->setDefaultEditedState (pedited->wavelet.bluehigh ? Edited : UnEdited); + greenlow->setDefaultEditedState(pedited->wavelet.greenlow ? Edited : UnEdited); + bluelow->setDefaultEditedState(pedited->wavelet.bluelow ? Edited : UnEdited); + greenmed->setDefaultEditedState(pedited->wavelet.greenmed ? Edited : UnEdited); + bluemed->setDefaultEditedState(pedited->wavelet.bluemed ? Edited : UnEdited); + greenhigh->setDefaultEditedState(pedited->wavelet.greenhigh ? Edited : UnEdited); + bluehigh->setDefaultEditedState(pedited->wavelet.bluehigh ? Edited : UnEdited); + mergeL->setDefaultEditedState(pedited->wavelet.mergeL ? Edited : UnEdited); + mergeC->setDefaultEditedState(pedited->wavelet.mergeC ? Edited : UnEdited); + softrad->setDefaultEditedState(pedited->wavelet.softrad ? Edited : UnEdited); + softradend->setDefaultEditedState(pedited->wavelet.softradend ? Edited : UnEdited); + ballum->setDefaultEditedState(pedited->wavelet.ballum ? Edited : UnEdited); + balchrom->setDefaultEditedState(pedited->wavelet.balchrom ? Edited : UnEdited); + chromfi->setDefaultEditedState(pedited->wavelet.chromfi ? Edited : UnEdited); + chromco->setDefaultEditedState(pedited->wavelet.chromco ? Edited : UnEdited); - rescon->setDefault (defParams->wavelet.rescon); - resconH->setDefault (defParams->wavelet.resconH); - reschro->setDefault (defParams->wavelet.reschro); - tmrs->setDefault (defParams->wavelet.tmrs); - gamma->setDefault (defParams->wavelet.gamma); - sup->setDefault (defParams->wavelet.sup); + sigma->setDefault(defParams->wavelet.sigma); + offset->setDefault(defParams->wavelet.offset); + lowthr->setDefault(defParams->wavelet.lowthr); + rescon->setDefault(defParams->wavelet.rescon); + resconH->setDefault(defParams->wavelet.resconH); + reschro->setDefault(defParams->wavelet.reschro); + resblur->setDefault(defParams->wavelet.resblur); + resblurc->setDefault(defParams->wavelet.resblurc); + tmrs->setDefault(defParams->wavelet.tmrs); + edgs->setDefault(defParams->wavelet.edgs); + scale->setDefault(defParams->wavelet.scale); + gamma->setDefault(defParams->wavelet.gamma); + sup->setDefault(defParams->wavelet.sup); sky->setDefaultEditedState(pedited->wavelet.sky ? Edited : UnEdited); thres->setDefaultEditedState(pedited->wavelet.thres ? Edited : UnEdited); threshold->setDefaultEditedState(pedited->wavelet.threshold ? Edited : UnEdited); @@ -1832,10 +2195,12 @@ void Wavelet::setDefaults (const ProcParams* defParams, const ParamsEdited* pedi chro->setDefaultEditedState(pedited->wavelet.chro ? Edited : UnEdited); contrast->setDefaultEditedState(pedited->wavelet.contrast ? Edited : UnEdited); edgrad->setDefaultEditedState(pedited->wavelet.edgrad ? Edited : UnEdited); + edgeffect->setDefaultEditedState(pedited->wavelet.edgeffect ? Edited : UnEdited); edgval->setDefaultEditedState(pedited->wavelet.edgval ? Edited : UnEdited); - edgthresh->setDefault (defParams->wavelet.edgthresh); + edgthresh->setDefault(defParams->wavelet.edgthresh); thr->setDefaultEditedState(pedited->wavelet.thr ? Edited : UnEdited); thrH->setDefaultEditedState(pedited->wavelet.thrH ? Edited : UnEdited); + radius->setDefaultEditedState(pedited->wavelet.radius ? Edited : UnEdited); skinprotect->setDefaultEditedState(pedited->wavelet.skinprotect ? Edited : UnEdited); hueskin->setDefaultEditedState(pedited->wavelet.hueskin ? Edited : UnEdited); hueskin2->setDefaultEditedState(pedited->wavelet.hueskin2 ? Edited : UnEdited); @@ -1844,6 +2209,8 @@ void Wavelet::setDefaults (const ProcParams* defParams, const ParamsEdited* pedi pastlev->setDefaultEditedState(pedited->wavelet.pastlev ? Edited : UnEdited); satlev->setDefaultEditedState(pedited->wavelet.satlev ? Edited : UnEdited); edgcont->setDefaultEditedState(pedited->wavelet.edgcont ? Edited : UnEdited); + chrwav->setDefaultEditedState(pedited->wavelet.chrwav ? Edited : UnEdited); + bluwav->setDefaultEditedState(pedited->wavelet.bluwav ? Edited : UnEdited); strength->setDefaultEditedState(pedited->wavelet.strength ? Edited : UnEdited); balance->setDefaultEditedState(pedited->wavelet.balance ? Edited : UnEdited); iter->setDefaultEditedState(pedited->wavelet.iter ? Edited : UnEdited); @@ -1860,10 +2227,17 @@ void Wavelet::setDefaults (const ProcParams* defParams, const ParamsEdited* pedi correctionch[i]->setDefaultEditedState(pedited->wavelet.ch[i] ? Edited : UnEdited); } } else { + sigma->setDefaultEditedState(Irrelevant); + offset->setDefaultEditedState(Irrelevant); + lowthr->setDefaultEditedState(Irrelevant); rescon->setDefaultEditedState(Irrelevant); resconH->setDefaultEditedState(Irrelevant); reschro->setDefaultEditedState(Irrelevant); + resblur->setDefaultEditedState(Irrelevant); + resblurc->setDefaultEditedState(Irrelevant); tmrs->setDefaultEditedState(Irrelevant); + edgs->setDefaultEditedState(Irrelevant); + scale->setDefaultEditedState(Irrelevant); gamma->setDefaultEditedState(Irrelevant); sup->setDefaultEditedState(Irrelevant); sky->setDefaultEditedState(Irrelevant); @@ -1879,25 +2253,29 @@ void Wavelet::setDefaults (const ProcParams* defParams, const ParamsEdited* pedi chro->setDefaultEditedState(Irrelevant); contrast->setDefaultEditedState(Irrelevant); edgrad->setDefaultEditedState(Irrelevant); + edgeffect->setDefaultEditedState(Irrelevant); edgval->setDefaultEditedState(Irrelevant); edgthresh->setDefaultEditedState(Irrelevant); thr->setDefaultEditedState(Irrelevant); thrH->setDefaultEditedState(Irrelevant); + radius->setDefaultEditedState(Irrelevant); skinprotect->setDefaultEditedState(Irrelevant); - hueskin->setDefaultEditedState (Irrelevant); - hueskin2->setDefaultEditedState (Irrelevant); - hllev->setDefaultEditedState (Irrelevant); - bllev->setDefaultEditedState (Irrelevant); - edgcont->setDefaultEditedState (Irrelevant); - level0noise->setDefaultEditedState (Irrelevant); - level1noise->setDefaultEditedState (Irrelevant); - level2noise->setDefaultEditedState (Irrelevant); - level3noise->setDefaultEditedState (Irrelevant); - pastlev->setDefaultEditedState (Irrelevant); - satlev->setDefaultEditedState (Irrelevant); - strength->setDefaultEditedState (Irrelevant); - balance->setDefaultEditedState (Irrelevant); - iter->setDefaultEditedState (Irrelevant); + hueskin->setDefaultEditedState(Irrelevant); + hueskin2->setDefaultEditedState(Irrelevant); + hllev->setDefaultEditedState(Irrelevant); + bllev->setDefaultEditedState(Irrelevant); + edgcont->setDefaultEditedState(Irrelevant); + chrwav->setDefaultEditedState(Irrelevant); + bluwav->setDefaultEditedState(Irrelevant); + level0noise->setDefaultEditedState(Irrelevant); + level1noise->setDefaultEditedState(Irrelevant); + level2noise->setDefaultEditedState(Irrelevant); + level3noise->setDefaultEditedState(Irrelevant); + pastlev->setDefaultEditedState(Irrelevant); + satlev->setDefaultEditedState(Irrelevant); + strength->setDefaultEditedState(Irrelevant); + balance->setDefaultEditedState(Irrelevant); + iter->setDefaultEditedState(Irrelevant); for (int i = 0; i < 9; i++) { correction[i]->setDefaultEditedState(Irrelevant); @@ -1911,19 +2289,19 @@ void Wavelet::setDefaults (const ProcParams* defParams, const ParamsEdited* pedi void Wavelet::adjusterChanged(ThresholdAdjuster* a, double newBottom, double newTop) { - if (listener && (multiImage || getEnabled()) ) { - if(a == level0noise) { - listener->panelChanged (EvWavlev0nois, - Glib::ustring::compose(Glib::ustring(M("TP_WAVELET_NOIS") + ": %1" + "\n" + M("TP_WAVELET_STREN") + ": %2"), int(newTop), int(newBottom))); - } else if(a == level1noise) { - listener->panelChanged (EvWavlev1nois, - Glib::ustring::compose(Glib::ustring(M("TP_WAVELET_NOIS") + ": %1" + "\n" + M("TP_WAVELET_STREN") + ": %2"), int(newTop), int(newBottom))); - } else if(a == level2noise) { - listener->panelChanged (EvWavlev2nois, - Glib::ustring::compose(Glib::ustring(M("TP_WAVELET_NOIS") + ": %1" + "\n" + M("TP_WAVELET_STREN") + ": %2"), int(newTop), int(newBottom))); - } else if(a == level3noise) { - listener->panelChanged (EvWavlev3nois, - Glib::ustring::compose(Glib::ustring(M("TP_WAVELET_NOIS") + ": %1" + "\n" + M("TP_WAVELET_STREN") + ": %2"), int(newTop), int(newBottom))); + if (listener && (multiImage || getEnabled())) { + if (a == level0noise) { + listener->panelChanged(EvWavlev0nois, + Glib::ustring::compose(Glib::ustring(M("TP_WAVELET_NOIS") + ": %1" + "\n" + M("TP_WAVELET_STREN") + ": %2"), int(newTop), int(newBottom))); + } else if (a == level1noise) { + listener->panelChanged(EvWavlev1nois, + Glib::ustring::compose(Glib::ustring(M("TP_WAVELET_NOIS") + ": %1" + "\n" + M("TP_WAVELET_STREN") + ": %2"), int(newTop), int(newBottom))); + } else if (a == level2noise) { + listener->panelChanged(EvWavlev2nois, + Glib::ustring::compose(Glib::ustring(M("TP_WAVELET_NOIS") + ": %1" + "\n" + M("TP_WAVELET_STREN") + ": %2"), int(newTop), int(newBottom))); + } else if (a == level3noise) { + listener->panelChanged(EvWavlev3nois, + Glib::ustring::compose(Glib::ustring(M("TP_WAVELET_NOIS") + ": %1" + "\n" + M("TP_WAVELET_STREN") + ": %2"), int(newTop), int(newBottom))); } } @@ -1943,21 +2321,21 @@ void Wavelet::adjusterChanged(ThresholdAdjuster* a, int newBottomLeft, int newTo void Wavelet::adjusterChanged2(ThresholdAdjuster* a, int newBottomL, int newTopL, int newBottomR, int newTopR) { - if (listener && (multiImage || getEnabled()) ) { - if(a == hueskin) { - listener->panelChanged (EvWavHueskin, hueskin->getHistoryString()); - } else if(a == hueskin2) { - listener->panelChanged (EvWavHueskin2, hueskin2->getHistoryString()); - } else if(a == hllev) { - listener->panelChanged (EvWavlhl, hllev->getHistoryString()); - } else if(a == bllev) { - listener->panelChanged (EvWavlbl, bllev->getHistoryString()); - } else if(a == pastlev) { - listener->panelChanged (EvWavpast, pastlev->getHistoryString()); - } else if(a == satlev) { - listener->panelChanged (EvWavsat, satlev->getHistoryString()); - } else if(a == edgcont) { - listener->panelChanged (EvWavedgcont, edgcont->getHistoryString()); + if (listener && (multiImage || getEnabled())) { + if (a == hueskin) { + listener->panelChanged(EvWavHueskin, hueskin->getHistoryString()); + } else if (a == hueskin2) { + listener->panelChanged(EvWavHueskin2, hueskin2->getHistoryString()); + } else if (a == hllev) { + listener->panelChanged(EvWavlhl, hllev->getHistoryString()); + } else if (a == bllev) { + listener->panelChanged(EvWavlbl, bllev->getHistoryString()); + } else if (a == pastlev) { + listener->panelChanged(EvWavpast, pastlev->getHistoryString()); + } else if (a == satlev) { + listener->panelChanged(EvWavsat, satlev->getHistoryString()); + } else if (a == edgcont) { + listener->panelChanged(EvWavedgcont, edgcont->getHistoryString()); } } } @@ -1965,7 +2343,7 @@ void Wavelet::adjusterChanged2(ThresholdAdjuster* a, int newBottomL, int newTopL void Wavelet::HSmethodUpdateUI() { if (!batchMode) { - if(HSmethod->get_active_row_number() == 0) { //without + if (HSmethod->get_active_row_number() == 0) { //without hllev->hide(); bllev->hide(); threshold->hide(); @@ -1983,15 +2361,15 @@ void Wavelet::HSmethodChanged() { HSmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavHSmet, HSmethod->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavHSmet, HSmethod->get_active_text()); } } void Wavelet::CHmethodUpdateUI() { if (!batchMode) { - if(CHmethod->get_active_row_number() == 0) { + if (CHmethod->get_active_row_number() == 0) { CHSLmethod->show(); pastlev->hide(); satlev->hide(); @@ -2003,14 +2381,14 @@ void Wavelet::CHmethodUpdateUI() int y = thres->getValue(); int z; - for(z = y; z < 9; z++) { + for (z = y; z < 9; z++) { correctionch[z]->hide(); } - for(z = 0; z < y; z++) { + for (z = 0; z < y; z++) { correctionch[z]->show(); } - } else if(CHmethod->get_active_row_number() == 1) { + } else if (CHmethod->get_active_row_number() == 1) { CHSLmethod->show(); pastlev->show(); satlev->show(); @@ -2022,11 +2400,11 @@ void Wavelet::CHmethodUpdateUI() int y = thres->getValue(); int z; - for(z = y; z < 9; z++) { + for (z = y; z < 9; z++) { correctionch[z]->hide(); } - for(z = 0; z < y; z++) { + for (z = 0; z < y; z++) { correctionch[z]->show(); } } else { @@ -2050,8 +2428,8 @@ void Wavelet::CHmethodChanged() { CHmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavCHmet, CHmethod->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavCHmet, CHmethod->get_active_text()); } } @@ -2090,10 +2468,10 @@ void Wavelet::CHSLmethodChanged() void Wavelet::EDmethodUpdateUI() { if (!batchMode) { - if(EDmethod->get_active_row_number() == 0 ) { //SL + if (EDmethod->get_active_row_number() == 0) { //SL CCWcurveEditorG->hide(); edgcont->show(); - } else if(EDmethod->get_active_row_number() == 1) { //CU + } else if (EDmethod->get_active_row_number() == 1) { //CU CCWcurveEditorG->show(); edgcont->hide(); } @@ -2103,8 +2481,8 @@ void Wavelet::EDmethodChanged() { EDmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavEDmet, EDmethod->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavEDmet, EDmethod->get_active_text()); } } @@ -2118,8 +2496,8 @@ void Wavelet::NPmethodChanged() { NPmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavNPmet, NPmethod->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavNPmet, NPmethod->get_active_text()); } } @@ -2128,16 +2506,16 @@ void Wavelet::NPmethodChanged() void Wavelet::BAmethodUpdateUI() { if (!batchMode) { - if(BAmethod->get_active_row_number() == 0 ) { //none + if (BAmethod->get_active_row_number() == 0) { //none balance->hide(); opacityCurveEditorW->hide(); iter->hide(); - } else if(BAmethod->get_active_row_number() == 1) { //sli + } else if (BAmethod->get_active_row_number() == 1) { //sli opacityCurveEditorW->hide(); balance->show(); iter->show(); - } else if(BAmethod->get_active_row_number() == 2) { //CU + } else if (BAmethod->get_active_row_number() == 2) { //CU opacityCurveEditorW->show(); balance->hide(); iter->show(); @@ -2148,8 +2526,8 @@ void Wavelet::BAmethodChanged() { BAmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavBAmet, BAmethod->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavBAmet, BAmethod->get_active_text()); } } @@ -2166,14 +2544,22 @@ void Wavelet::TMmethodUpdateUI() } } */ + if (TMmethod->get_active_row_number() == 1) { + edgs->show(); + scale->show(); + } else if (TMmethod->get_active_row_number() == 0) { + edgs->hide(); + scale->hide(); + } + } void Wavelet::TMmethodChanged() { TMmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavTMmet, TMmethod->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavTMmet, TMmethod->get_active_text()); } } @@ -2187,8 +2573,8 @@ void Wavelet::BackmethodUpdateUI() { void Wavelet::BackmethodChanged() { //BackmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavBackmet, Backmethod->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavBackmet, Backmethod->get_active_text()); } } @@ -2196,19 +2582,19 @@ void Wavelet::CLmethodUpdateUI() { if (!batchMode) { if (CLmethod->get_active_row_number() == 0) { - CLmethod->set_active (0); + CLmethod->set_active(0); Lmethod->set_sensitive(true); Dirmethod->set_sensitive(true); } else if (CLmethod->get_active_row_number() == 1) { - CLmethod->set_active (1); + CLmethod->set_active(1); Lmethod->set_sensitive(true); Dirmethod->set_sensitive(true); } else if (CLmethod->get_active_row_number() == 2) { - CLmethod->set_active (2); + CLmethod->set_active(2); Lmethod->set_sensitive(true); Dirmethod->set_sensitive(true); } else if (CLmethod->get_active_row_number() == 3) { - CLmethod->set_active (3); + CLmethod->set_active(3); Lmethod->set_sensitive(false); Dirmethod->set_sensitive(false); } @@ -2219,8 +2605,8 @@ void Wavelet::CLmethodChanged() { CLmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavCLmet, CLmethod->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavCLmet, CLmethod->get_active_text()); } } @@ -2231,11 +2617,57 @@ void Wavelet::TilesmethodUpdateUI() { } */ + +void Wavelet::ushamethodChanged() +{ + if (ushamethod->get_active_row_number() == 1 && expclari->getEnabled() == true) { + Backmethod->set_active(2); + CLmethod->set_active(2); + Lmethod->set_active(6); + Lmethod->set_sensitive(true); + Dirmethod->set_sensitive(true); + Dirmethod->set_active(3); + CLmethod->set_sensitive(false); + Backmethod->set_sensitive(false); + } else if (ushamethod->get_active_row_number() == 0 && expclari->getEnabled() == true) { + Backmethod->set_active(0); + CLmethod->set_active(1); + Lmethod->set_active(2); + Dirmethod->set_active(3); + Lmethod->set_sensitive(true); + Dirmethod->set_sensitive(true); + CLmethod->set_sensitive(false); + Backmethod->set_sensitive(false); + /* } else if (ushamethod->get_active_row_number() == 0 || expclari->getEnabled() == false) { + Backmethod->set_active(1); + CLmethod->set_active(3); + Lmethod->set_active(3); + Dirmethod->set_active(3); + Lmethod->set_sensitive(false); + Dirmethod->set_sensitive(false); + */ + } else if (expclari->getEnabled() == false) { + Backmethod->set_active(1); + CLmethod->set_active(3); + Lmethod->set_active(3); + Dirmethod->set_active(3); + Lmethod->set_sensitive(false); + Dirmethod->set_sensitive(false); + CLmethod->set_sensitive(true); + Backmethod->set_sensitive(true); + } + + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavushamet, ushamethod->get_active_text()); + } +} + + void Wavelet::TilesmethodChanged() { //TilesmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavTilesmet, Tilesmethod->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavTilesmet, Tilesmethod->get_active_text()); } } @@ -2247,8 +2679,8 @@ void Wavelet::daubcoeffmethodUpdateUI() { void Wavelet::daubcoeffmethodChanged() { //daubcoeffmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavdaubcoeffmet, daubcoeffmethod->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavdaubcoeffmet, daubcoeffmethod->get_active_text()); } } @@ -2261,8 +2693,8 @@ void Wavelet::MedgreinfUpdateUI() { void Wavelet::MedgreinfChanged() { //MedgreinfUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavedgreinf, Medgreinf->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavedgreinf, Medgreinf->get_active_text()); } } @@ -2275,8 +2707,8 @@ void Wavelet::DirmethodUpdateUI() { void Wavelet::DirmethodChanged() { //DirmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavDirmeto, Dirmethod->get_active_text ()); + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavDirmeto, Dirmethod->get_active_text()); } } @@ -2289,74 +2721,99 @@ void Wavelet::LmethodUpdateUI() { void Wavelet::LmethodChanged() { //LmethodUpdateUI(); - if (listener && (multiImage || getEnabled()) ) { - listener->panelChanged (EvWavLmet, Lmethod->get_active_text ()); + if (ushamethod->get_active_row_number() == 0 && expclari->getEnabled() == true) { + if (Lmethod->get_active_row_number() > 3) { + Lmethod->set_active(3); + } + } + + if (ushamethod->get_active_row_number() == 1 && expclari->getEnabled() == true) { + if (Lmethod->get_active_row_number() < 4) { + Lmethod->set_active(4); + } + } + + if (listener && (multiImage || getEnabled())) { + listener->panelChanged(EvWavLmet, Lmethod->get_active_text()); } } -void Wavelet::setBatchMode (bool batchMode) +void Wavelet::setBatchMode(bool batchMode) { - Lmethod->append (M("GENERAL_UNCHANGED")); - CLmethod->append (M("GENERAL_UNCHANGED")); - Backmethod->append (M("GENERAL_UNCHANGED")); - Tilesmethod->append (M("GENERAL_UNCHANGED")); - daubcoeffmethod->append (M("GENERAL_UNCHANGED")); - CHmethod->append (M("GENERAL_UNCHANGED")); - Medgreinf->append (M("GENERAL_UNCHANGED")); - CHSLmethod->append (M("GENERAL_UNCHANGED")); - EDmethod->append (M("GENERAL_UNCHANGED")); - NPmethod->append (M("GENERAL_UNCHANGED")); - BAmethod->append (M("GENERAL_UNCHANGED")); - TMmethod->append (M("GENERAL_UNCHANGED")); - HSmethod->append (M("GENERAL_UNCHANGED")); - Dirmethod->append (M("GENERAL_UNCHANGED")); - CCWcurveEditorG->setBatchMode (batchMode); - opaCurveEditorG->setBatchMode (batchMode); - opacityCurveEditorG->setBatchMode (batchMode); - opacityCurveEditorW->setBatchMode (batchMode); - opacityCurveEditorWL->setBatchMode (batchMode); - curveEditorRES->setBatchMode (batchMode); - curveEditorGAM->setBatchMode (batchMode); - rescon->showEditedCB (); - resconH->showEditedCB (); - reschro->showEditedCB (); - tmrs->showEditedCB (); - gamma->showEditedCB (); - sup->showEditedCB (); - sky->showEditedCB (); - thres->showEditedCB (); - threshold->showEditedCB (); - threshold2->showEditedCB (); - edgedetect->showEditedCB (); - edgedetectthr->showEditedCB (); - edgedetectthr2->showEditedCB (); - edgesensi->showEditedCB (); - edgeampli->showEditedCB (); - chroma->showEditedCB (); - chro->showEditedCB (); - contrast->showEditedCB (); - edgrad->showEditedCB (); - edgval->showEditedCB (); - edgthresh->showEditedCB (); - thr->showEditedCB (); - thrH->showEditedCB (); + Lmethod->append(M("GENERAL_UNCHANGED")); + CLmethod->append(M("GENERAL_UNCHANGED")); + Backmethod->append(M("GENERAL_UNCHANGED")); + Tilesmethod->append(M("GENERAL_UNCHANGED")); + daubcoeffmethod->append(M("GENERAL_UNCHANGED")); + CHmethod->append(M("GENERAL_UNCHANGED")); + Medgreinf->append(M("GENERAL_UNCHANGED")); + ushamethod->append(M("GENERAL_UNCHANGED")); + CHSLmethod->append(M("GENERAL_UNCHANGED")); + EDmethod->append(M("GENERAL_UNCHANGED")); + NPmethod->append(M("GENERAL_UNCHANGED")); + BAmethod->append(M("GENERAL_UNCHANGED")); + TMmethod->append(M("GENERAL_UNCHANGED")); + HSmethod->append(M("GENERAL_UNCHANGED")); + Dirmethod->append(M("GENERAL_UNCHANGED")); + CCWcurveEditorG->setBatchMode(batchMode); + opaCurveEditorG->setBatchMode(batchMode); + opacityCurveEditorG->setBatchMode(batchMode); + opacityCurveEditorW->setBatchMode(batchMode); + opacityCurveEditorWL->setBatchMode(batchMode); + curveEditorbl->setBatchMode(batchMode); + curveEditorRES->setBatchMode(batchMode); + curveEditorGAM->setBatchMode(batchMode); + sigma->showEditedCB(); + offset->showEditedCB(); + lowthr->showEditedCB(); + rescon->showEditedCB(); + resconH->showEditedCB(); + reschro->showEditedCB(); + resblur->showEditedCB(); + resblurc->showEditedCB(); + tmrs->showEditedCB(); + edgs->showEditedCB(); + scale->showEditedCB(); + gamma->showEditedCB(); + sup->showEditedCB(); + sky->showEditedCB(); + thres->showEditedCB(); + threshold->showEditedCB(); + threshold2->showEditedCB(); + edgedetect->showEditedCB(); + edgedetectthr->showEditedCB(); + edgedetectthr2->showEditedCB(); + edgesensi->showEditedCB(); + edgeampli->showEditedCB(); + chroma->showEditedCB(); + chro->showEditedCB(); + contrast->showEditedCB(); + edgrad->showEditedCB(); + edgeffect->showEditedCB(); + edgval->showEditedCB(); + edgthresh->showEditedCB(); + thr->showEditedCB(); + thrH->showEditedCB(); + radius->showEditedCB(); skinprotect->showEditedCB(); - hueskin->showEditedCB (); - hueskin2->showEditedCB (); - hllev->showEditedCB (); - bllev->showEditedCB (); - pastlev->showEditedCB (); - satlev->showEditedCB (); - edgcont->showEditedCB (); - strength->showEditedCB (); - balance->showEditedCB (); - iter->showEditedCB (); - level0noise->showEditedCB (); - level1noise->showEditedCB (); - level2noise->showEditedCB (); - level3noise->showEditedCB (); + hueskin->showEditedCB(); + hueskin2->showEditedCB(); + hllev->showEditedCB(); + bllev->showEditedCB(); + pastlev->showEditedCB(); + satlev->showEditedCB(); + edgcont->showEditedCB(); + chrwav->showEditedCB(); + bluwav->showEditedCB(); + strength->showEditedCB(); + balance->showEditedCB(); + iter->showEditedCB(); + level0noise->showEditedCB(); + level1noise->showEditedCB(); + level2noise->showEditedCB(); + level3noise->showEditedCB(); - ToolPanel::setBatchMode (batchMode); + ToolPanel::setBatchMode(batchMode); for (int i = 0; i < 9; i++) { correction[i]->showEditedCB(); @@ -2367,170 +2824,218 @@ void Wavelet::setBatchMode (bool batchMode) } } -void Wavelet::adjusterUpdateUI (Adjuster* a) +void Wavelet::adjusterUpdateUI(Adjuster* a) { /* - if (!batchMode) { - if (a == tmrs ) { - float tm; - tm=tmrs->getValue(); - if(tm==0.f) tmr->hide(); - else tmr->show(); - } - else if (a == gamma ) { - float tm; - tm=tmrs->getValue(); - if(tm==0.f) tmr->hide(); - else tmr->show(); - ); - } - } + if (!batchMode) { + if (a == tmrs ) { + float tm; + tm=tmrs->getValue(); + if(tm==0.f) tmr->hide(); + else tmr->show(); + } + else if (a == gamma ) { + float tm; + tm=tmrs->getValue(); + if(tm==0.f) tmr->hide(); + else tmr->show(); + + } + } */ } void Wavelet::adjusterChanged(Adjuster* a, double newval) { - if (listener && (multiImage || getEnabled()) ) { + if (listener && (multiImage || getEnabled())) { if (a == edgthresh) { - listener->panelChanged (EvWavtiles, edgthresh->getTextValue()); - } else if (a == rescon ) { - listener->panelChanged (EvWavrescon, rescon->getTextValue()); - } else if (a == resconH ) { - listener->panelChanged (EvWavresconH, resconH->getTextValue()); - } else if (a == reschro ) { - listener->panelChanged (EvWavreschro, reschro->getTextValue()); - } else if (a == tmrs ) { + listener->panelChanged(EvWavtiles, edgthresh->getTextValue()); + } else if (a == rescon) { + listener->panelChanged(EvWavrescon, rescon->getTextValue()); + } else if (a == sigma) { + listener->panelChanged(EvWavsigma, sigma->getTextValue()); + } else if (a == offset) { + listener->panelChanged(EvWavoffset, offset->getTextValue()); + } else if (a == lowthr) { + listener->panelChanged(EvWavlowthr, lowthr->getTextValue()); + } else if (a == resconH) { + listener->panelChanged(EvWavresconH, resconH->getTextValue()); + } else if (a == reschro) { + listener->panelChanged(EvWavreschro, reschro->getTextValue()); + } else if (a == resblur) { + listener->panelChanged(EvWavresblur, resblur->getTextValue()); + } else if (a == resblurc) { + listener->panelChanged(EvWavresblurc, resblurc->getTextValue()); + } else if (a == tmrs) { adjusterUpdateUI(a); - listener->panelChanged (EvWavtmrs, tmrs->getTextValue()); - } else if (a == gamma ) { + listener->panelChanged(EvWavtmrs, tmrs->getTextValue()); + + if (tmrs->getValue() != 0 && TMmethod->get_active_row_number() == 1) { + edgs->show(); + scale->show(); + } else if (TMmethod->get_active_row_number() == 0) { + edgs->hide(); + scale->hide(); + } + } else if (a == gamma) { adjusterUpdateUI(a); - listener->panelChanged (EvWavgamma, gamma->getTextValue()); - } else if (a == sky ) { - listener->panelChanged (EvWavsky, sky->getTextValue()); - } else if (a == sup ) { - listener->panelChanged (EvWavsup, sup->getTextValue()); - } else if (a == chroma ) { - listener->panelChanged (EvWavchroma, chroma->getTextValue()); - } else if (a == chro ) { - listener->panelChanged (EvWavchro, chro->getTextValue()); - } else if (a == contrast ) { - listener->panelChanged (EvWavunif, contrast->getTextValue()); - } else if (a == thr ) { - listener->panelChanged (EvWavthr, thr->getTextValue()); - } else if (a == thrH ) { - listener->panelChanged (EvWavthrH, thrH->getTextValue()); - } else if (a == threshold ) { - listener->panelChanged (EvWavThreshold, threshold->getTextValue()); - } else if (a == threshold2 ) { - listener->panelChanged (EvWavThreshold2, threshold2->getTextValue()); - } else if (a == edgedetect ) { - listener->panelChanged (EvWavedgedetect, edgedetect->getTextValue()); - } else if (a == edgedetectthr ) { - listener->panelChanged (EvWavedgedetectthr, edgedetectthr->getTextValue()); - } else if (a == edgedetectthr2 ) { - listener->panelChanged (EvWavedgedetectthr2, edgedetectthr2->getTextValue()); - } else if (a == edgesensi ) { - listener->panelChanged (EvWavedgesensi, edgesensi->getTextValue()); - } else if (a == edgeampli ) { - listener->panelChanged (EvWavedgeampli, edgeampli->getTextValue()); - } else if (a == edgrad ) { - listener->panelChanged (EvWavedgrad, edgrad->getTextValue()); - } else if (a == edgval ) { - listener->panelChanged (EvWavedgval, edgval->getTextValue()); - } else if (a == thres ) { + listener->panelChanged(EvWavgamma, gamma->getTextValue()); + } else if (a == edgs) { + adjusterUpdateUI(a); + listener->panelChanged(EvWavedgs, edgs->getTextValue()); + } else if (a == scale) { + adjusterUpdateUI(a); + listener->panelChanged(EvWavscale, scale->getTextValue()); + } else if (a == sky) { + listener->panelChanged(EvWavsky, sky->getTextValue()); + } else if (a == sup) { + listener->panelChanged(EvWavsup, sup->getTextValue()); + } else if (a == chroma) { + listener->panelChanged(EvWavchroma, chroma->getTextValue()); + } else if (a == chro) { + listener->panelChanged(EvWavchro, chro->getTextValue()); + } else if (a == contrast) { + listener->panelChanged(EvWavunif, contrast->getTextValue()); + } else if (a == thr) { + listener->panelChanged(EvWavthr, thr->getTextValue()); + } else if (a == thrH) { + listener->panelChanged(EvWavthrH, thrH->getTextValue()); + } else if (a == radius) { + listener->panelChanged(EvWavradius, radius->getTextValue()); + } else if (a == threshold) { + listener->panelChanged(EvWavThreshold, threshold->getTextValue()); + } else if (a == threshold2) { + listener->panelChanged(EvWavThreshold2, threshold2->getTextValue()); + } else if (a == edgedetect) { + listener->panelChanged(EvWavedgedetect, edgedetect->getTextValue()); + } else if (a == edgedetectthr) { + listener->panelChanged(EvWavedgedetectthr, edgedetectthr->getTextValue()); + } else if (a == edgedetectthr2) { + listener->panelChanged(EvWavedgedetectthr2, edgedetectthr2->getTextValue()); + } else if (a == edgesensi) { + listener->panelChanged(EvWavedgesensi, edgesensi->getTextValue()); + } else if (a == edgeampli) { + listener->panelChanged(EvWavedgeampli, edgeampli->getTextValue()); + } else if (a == edgrad) { + listener->panelChanged(EvWavedgrad, edgrad->getTextValue()); + } else if (a == edgeffect) { + listener->panelChanged(EvWavedgeffect, edgeffect->getTextValue()); + } else if (a == edgval) { + listener->panelChanged(EvWavedgval, edgval->getTextValue()); + } else if (a == thres) { int y = thres->getValue(); int z; - for(z = y; z < 9; z++) { + for (z = y; z < 9; z++) { correction[z]->hide(); } - for(z = 0; z < y; z++) { + for (z = 0; z < y; z++) { correction[z]->show(); } - for(z = y; z < 9; z++) { + for (z = y; z < 9; z++) { correctionch[z]->hide(); } - for(z = 0; z < y; z++) { + for (z = 0; z < y; z++) { correctionch[z]->show(); } - if(z == 9) { + if (z == 9) { sup->show(); } else { sup->hide(); } - listener->panelChanged (EvWavthres, thres->getTextValue()); + listener->panelChanged(EvWavthres, thres->getTextValue()); } else if (a == skinprotect) { - listener->panelChanged (EvWavSkin, skinprotect->getTextValue()); + listener->panelChanged(EvWavSkin, skinprotect->getTextValue()); } else if (a == strength) { - listener->panelChanged (EvWavStrength, strength->getTextValue()); + listener->panelChanged(EvWavStrength, strength->getTextValue()); } else if (a == balance) { - listener->panelChanged (EvWavbalance, balance->getTextValue()); + listener->panelChanged(EvWavbalance, balance->getTextValue()); } else if (a == iter) { - listener->panelChanged (EvWaviter, iter->getTextValue()); - } else if (a == greenhigh ) { - listener->panelChanged (EvWavgreenhigh, greenhigh->getTextValue()); - } else if (a == bluehigh ) { - listener->panelChanged (EvWavbluehigh, bluehigh->getTextValue()); - } else if (a == greenmed ) { - listener->panelChanged (EvWavgreenmed, greenmed->getTextValue()); - } else if (a == bluemed ) { - listener->panelChanged (EvWavbluemed, bluemed->getTextValue()); - } else if (a == greenlow ) { - listener->panelChanged (EvWavgreenlow, greenlow->getTextValue()); - } else if (a == bluelow ) { - listener->panelChanged (EvWavbluelow, bluelow->getTextValue()); + listener->panelChanged(EvWaviter, iter->getTextValue()); + } else if (a == greenhigh) { + listener->panelChanged(EvWavgreenhigh, greenhigh->getTextValue()); + } else if (a == bluehigh) { + listener->panelChanged(EvWavbluehigh, bluehigh->getTextValue()); + } else if (a == ballum) { + listener->panelChanged(EvWavballum, ballum->getTextValue()); + } else if (a == balchrom) { + listener->panelChanged(EvWavbalchrom, balchrom->getTextValue()); + } else if (a == chromfi) { + listener->panelChanged(EvWavchromfi, chromfi->getTextValue()); + } else if (a == chromco) { + listener->panelChanged(EvWavchromco, chromco->getTextValue()); + } else if (a == mergeL) { + listener->panelChanged(EvWavmergeL, mergeL->getTextValue()); + } else if (a == mergeC) { + listener->panelChanged(EvWavmergeC, mergeC->getTextValue()); + } else if (a == softrad) { + listener->panelChanged(EvWavsoftrad, softrad->getTextValue()); + } else if (a == softradend) { + listener->panelChanged(EvWavsoftradend, softradend->getTextValue()); + } else if (a == greenmed) { + listener->panelChanged(EvWavgreenmed, greenmed->getTextValue()); + } else if (a == bluemed) { + listener->panelChanged(EvWavbluemed, bluemed->getTextValue()); + } else if (a == greenlow) { + listener->panelChanged(EvWavgreenlow, greenlow->getTextValue()); + } else if (a == bluelow) { + listener->panelChanged(EvWavbluelow, bluelow->getTextValue()); + } else if (a == chrwav) { + listener->panelChanged(EvWavchrwav, chrwav->getTextValue()); + } else if (a == bluwav) { + listener->panelChanged(EvWavbluwav, bluwav->getTextValue()); } if ((a == correction[0] || a == correction[1] || a == correction[2] || a == correction[3] || a == correction[4] || a == correction[5] || a == correction[6] || a == correction[7] || a == correction[8])) { - listener->panelChanged (EvWavelet, - Glib::ustring::compose("%1, %2, %3, %4, %5, %6, %7, %8, %9", - Glib::ustring::format(std::fixed, std::setprecision(0), correction[0]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correction[1]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correction[2]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correction[3]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correction[4]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correction[5]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correction[6]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correction[7]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correction[8]->getValue())) - ); - } else if (a == correctionch[0] || a == correctionch[1] || a == correctionch[2] || a == correctionch[3] || a == correctionch[4] || a == correctionch[5] || a == correctionch[6] || a == correctionch[7] || a == correctionch[8] ) { - listener->panelChanged (EvWaveletch, - Glib::ustring::compose("%1, %2, %3, %4, %5, %6, %7, %8, %9", - Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[0]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[1]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[2]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[3]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[4]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[5]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[6]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[7]->getValue()), - Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[8]->getValue())) - ); + listener->panelChanged(EvWavelet, + Glib::ustring::compose("%1, %2, %3, %4, %5, %6, %7, %8, %9", + Glib::ustring::format(std::fixed, std::setprecision(0), correction[0]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correction[1]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correction[2]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correction[3]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correction[4]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correction[5]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correction[6]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correction[7]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correction[8]->getValue())) + ); + } else if (a == correctionch[0] || a == correctionch[1] || a == correctionch[2] || a == correctionch[3] || a == correctionch[4] || a == correctionch[5] || a == correctionch[6] || a == correctionch[7] || a == correctionch[8]) { + listener->panelChanged(EvWaveletch, + Glib::ustring::compose("%1, %2, %3, %4, %5, %6, %7, %8, %9", + Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[0]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[1]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[2]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[3]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[4]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[5]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[6]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[7]->getValue()), + Glib::ustring::format(std::fixed, std::setprecision(0), correctionch[8]->getValue())) + ); } } } -void Wavelet::enabledUpdateUI () +void Wavelet::enabledUpdateUI() { if (!batchMode) { int y = thres->getValue(); int z; - for(z = y; z < 9; z++) { + for (z = y; z < 9; z++) { correction[z]->hide(); } - for(z = 0; z < y; z++) { + for (z = 0; z < y; z++) { correction[z]->show(); } - if(z == 9) { + if (z == 9) { sup->show(); } else { sup->hide(); @@ -2540,52 +3045,52 @@ void Wavelet::enabledUpdateUI () } } -void Wavelet::enabledChanged () +void Wavelet::enabledChanged() { enabledUpdateUI(); if (listener) { if (get_inconsistent()) { - listener->panelChanged (EvWavEnabled, M("GENERAL_UNCHANGED")); + listener->panelChanged(EvWavEnabled, M("GENERAL_UNCHANGED")); } else if (getEnabled()) { - listener->panelChanged (EvWavEnabled, M("GENERAL_ENABLED")); + listener->panelChanged(EvWavEnabled, M("GENERAL_ENABLED")); } else { - listener->panelChanged (EvWavEnabled, M("GENERAL_DISABLED")); + listener->panelChanged(EvWavEnabled, M("GENERAL_DISABLED")); } } } -void Wavelet::medianToggled () +void Wavelet::medianToggled() { if (multiImage) { if (median->get_inconsistent()) { - median->set_inconsistent (false); - medianConn.block (true); - median->set_active (false); - medianConn.block (false); + median->set_inconsistent(false); + medianConn.block(true); + median->set_active(false); + medianConn.block(false); } else if (lastmedian) { - median->set_inconsistent (true); + median->set_inconsistent(true); } - lastmedian = median->get_active (); + lastmedian = median->get_active(); } - if (listener && (multiImage || getEnabled ())) { + if (listener && (multiImage || getEnabled())) { if (median->get_inconsistent()) { - listener->panelChanged (EvWavmedian, M("GENERAL_UNCHANGED")); - } else if (median->get_active ()) { - listener->panelChanged (EvWavmedian, M("GENERAL_ENABLED")); + listener->panelChanged(EvWavmedian, M("GENERAL_UNCHANGED")); + } else if (median->get_active()) { + listener->panelChanged(EvWavmedian, M("GENERAL_ENABLED")); } else { - listener->panelChanged (EvWavmedian, M("GENERAL_DISABLED")); + listener->panelChanged(EvWavmedian, M("GENERAL_DISABLED")); } } } -void Wavelet::medianlevUpdateUI () +void Wavelet::medianlevUpdateUI() { if (!batchMode) { - if (medianlev->get_active ()) { + if (medianlev->get_active()) { edgedetect->show(); lipst->show(); separatoredge->show(); @@ -2597,7 +3102,7 @@ void Wavelet::medianlevUpdateUI () // edgeampli->show(); // NPmethod->show(); // labmNP->show(); - if (lipst->get_active ()) { + if (lipst->get_active()) { edgesensi->show(); edgeampli->show(); NPmethod->show(); @@ -2625,66 +3130,66 @@ void Wavelet::medianlevUpdateUI () } } -void Wavelet::medianlevToggled () +void Wavelet::medianlevToggled() { if (multiImage) { if (medianlev->get_inconsistent()) { - medianlev->set_inconsistent (false); - medianlevConn.block (true); - medianlev->set_active (false); - medianlevConn.block (false); + medianlev->set_inconsistent(false); + medianlevConn.block(true); + medianlev->set_active(false); + medianlevConn.block(false); } else if (lastmedianlev) { - medianlev->set_inconsistent (true); + medianlev->set_inconsistent(true); } - lastmedianlev = medianlev->get_active (); + lastmedianlev = medianlev->get_active(); } medianlevUpdateUI(); - if (listener && (multiImage || getEnabled ())) { + if (listener && (multiImage || getEnabled())) { if (medianlev->get_inconsistent()) { - listener->panelChanged (EvWavmedianlev, M("GENERAL_UNCHANGED")); - } else if (medianlev->get_active () ) { - listener->panelChanged (EvWavmedianlev, M("GENERAL_ENABLED")); + listener->panelChanged(EvWavmedianlev, M("GENERAL_UNCHANGED")); + } else if (medianlev->get_active()) { + listener->panelChanged(EvWavmedianlev, M("GENERAL_ENABLED")); } else { - listener->panelChanged (EvWavmedianlev, M("GENERAL_DISABLED")); + listener->panelChanged(EvWavmedianlev, M("GENERAL_DISABLED")); } } } -void Wavelet::linkedgToggled () +void Wavelet::linkedgToggled() { if (multiImage) { if (linkedg->get_inconsistent()) { - linkedg->set_inconsistent (false); - linkedgConn.block (true); - linkedg->set_active (false); - linkedgConn.block (false); + linkedg->set_inconsistent(false); + linkedgConn.block(true); + linkedg->set_active(false); + linkedgConn.block(false); } else if (lastlinkedg) { - linkedg->set_inconsistent (true); + linkedg->set_inconsistent(true); } - lastlinkedg = linkedg->get_active (); + lastlinkedg = linkedg->get_active(); } - if (listener && (multiImage || getEnabled ())) { + if (listener && (multiImage || getEnabled())) { if (linkedg->get_inconsistent()) { - listener->panelChanged (EvWavlinkedg, M("GENERAL_UNCHANGED")); - } else if (linkedg->get_active () ) { - listener->panelChanged (EvWavlinkedg, M("GENERAL_ENABLED")); + listener->panelChanged(EvWavlinkedg, M("GENERAL_UNCHANGED")); + } else if (linkedg->get_active()) { + listener->panelChanged(EvWavlinkedg, M("GENERAL_ENABLED")); } else { - listener->panelChanged (EvWavlinkedg, M("GENERAL_DISABLED")); + listener->panelChanged(EvWavlinkedg, M("GENERAL_DISABLED")); } } } -void Wavelet::cbenabUpdateUI () +void Wavelet::cbenabUpdateUI() { if (!batchMode) { - if(cbenab->get_active ()) { + if (cbenab->get_active()) { chanMixerHLFrame->show(); chanMixerMidFrame->show(); chanMixerShadowsFrame->show(); @@ -2698,40 +3203,40 @@ void Wavelet::cbenabUpdateUI () } } -void Wavelet::cbenabToggled () +void Wavelet::cbenabToggled() { if (multiImage) { if (cbenab->get_inconsistent()) { - cbenab->set_inconsistent (false); - cbenabConn.block (true); - cbenab->set_active (false); - cbenabConn.block (false); + cbenab->set_inconsistent(false); + cbenabConn.block(true); + cbenab->set_active(false); + cbenabConn.block(false); } else if (lastcbenab) { - cbenab->set_inconsistent (true); + cbenab->set_inconsistent(true); } - lastcbenab = cbenab->get_active (); + lastcbenab = cbenab->get_active(); } cbenabUpdateUI(); - if (listener && (multiImage || getEnabled ())) { - if (cbenab->get_inconsistent() ) { - listener->panelChanged (EvWavcbenab, M("GENERAL_UNCHANGED")); - } else if (cbenab->get_active () ) { - listener->panelChanged (EvWavcbenab, M("GENERAL_ENABLED")); + if (listener && (multiImage || getEnabled())) { + if (cbenab->get_inconsistent()) { + listener->panelChanged(EvWavcbenab, M("GENERAL_UNCHANGED")); + } else if (cbenab->get_active()) { + listener->panelChanged(EvWavcbenab, M("GENERAL_ENABLED")); } else { - listener->panelChanged (EvWavcbenab, M("GENERAL_DISABLED")); + listener->panelChanged(EvWavcbenab, M("GENERAL_DISABLED")); } } } -void Wavelet::lipstUpdateUI () +void Wavelet::lipstUpdateUI() { if (!batchMode) { - if (lipst->get_active ()) { + if (lipst->get_active()) { NPmethod->show(); edgesensi->show(); edgeampli->show(); @@ -2747,31 +3252,31 @@ void Wavelet::lipstUpdateUI () } -void Wavelet::lipstToggled () +void Wavelet::lipstToggled() { if (multiImage) { if (lipst->get_inconsistent()) { - lipst->set_inconsistent (false); - lipstConn.block (true); - lipst->set_active (false); - lipstConn.block (false); + lipst->set_inconsistent(false); + lipstConn.block(true); + lipst->set_active(false); + lipstConn.block(false); } else if (lastlipst) { - lipst->set_inconsistent (true); + lipst->set_inconsistent(true); } - lastlipst = lipst->get_active (); + lastlipst = lipst->get_active(); } lipstUpdateUI(); - if (listener && (multiImage || getEnabled ())) { + if (listener && (multiImage || getEnabled())) { if (lipst->get_inconsistent()) { - listener->panelChanged (EvWavlipst, M("GENERAL_UNCHANGED")); - } else if (lipst->get_active ()) { - listener->panelChanged (EvWavlipst, M("GENERAL_ENABLED")); + listener->panelChanged(EvWavlipst, M("GENERAL_UNCHANGED")); + } else if (lipst->get_active()) { + listener->panelChanged(EvWavlipst, M("GENERAL_ENABLED")); } else { - listener->panelChanged (EvWavlipst, M("GENERAL_DISABLED")); + listener->panelChanged(EvWavlipst, M("GENERAL_DISABLED")); } } } @@ -2802,62 +3307,120 @@ void Wavelet::edgreinfToggled () { } } */ -void Wavelet::avoidToggled () +void Wavelet::avoidToggled() { if (multiImage) { if (avoid->get_inconsistent()) { - avoid->set_inconsistent (false); - avoidConn.block (true); - avoid->set_active (false); - avoidConn.block (false); + avoid->set_inconsistent(false); + avoidConn.block(true); + avoid->set_active(false); + avoidConn.block(false); } else if (lastavoid) { - avoid->set_inconsistent (true); + avoid->set_inconsistent(true); } - lastavoid = avoid->get_active (); + lastavoid = avoid->get_active(); } - if (listener && (multiImage || getEnabled ())) { + if (listener && (multiImage || getEnabled())) { if (avoid->get_inconsistent()) { - listener->panelChanged (EvWavavoid, M("GENERAL_UNCHANGED")); - } else if (avoid->get_active ()) { - listener->panelChanged (EvWavavoid, M("GENERAL_ENABLED")); + listener->panelChanged(EvWavavoid, M("GENERAL_UNCHANGED")); + } else if (avoid->get_active()) { + listener->panelChanged(EvWavavoid, M("GENERAL_ENABLED")); } else { - listener->panelChanged (EvWavavoid, M("GENERAL_DISABLED")); + listener->panelChanged(EvWavavoid, M("GENERAL_DISABLED")); } } } -void Wavelet::tmrToggled () +void Wavelet::showmaskToggled() +{ + if (multiImage) { + if (showmask->get_inconsistent()) { + showmask->set_inconsistent(false); + showmaskConn.block(true); + showmask->set_active(false); + showmaskConn.block(false); + } else if (lastshowmask) { + showmask->set_inconsistent(true); + } + + lastshowmask = showmask->get_active(); + } + + if (listener && (multiImage || getEnabled())) { + if (showmask->get_inconsistent()) { + listener->panelChanged(EvWavshowmask, M("GENERAL_UNCHANGED")); + } else if (showmask->get_active()) { + listener->panelChanged(EvWavshowmask, M("GENERAL_ENABLED")); + } else { + listener->panelChanged(EvWavshowmask, M("GENERAL_DISABLED")); + } + } +} + +void Wavelet::oldshToggled() +{ + if (oldsh->get_active()) { + radius->hide(); + } else { + radius->show(); + } + + if (multiImage) { + if (oldsh->get_inconsistent()) { + oldsh->set_inconsistent(false); + oldshConn.block(true); + oldsh->set_active(false); + oldshConn.block(false); + } else if (lastoldsh) { + oldsh->set_inconsistent(true); + } + + lastoldsh = oldsh->get_active(); + } + + if (listener && (multiImage || getEnabled())) { + if (oldsh->get_inconsistent()) { + listener->panelChanged(EvWavoldsh, M("GENERAL_UNCHANGED")); + } else if (oldsh->get_active()) { + listener->panelChanged(EvWavoldsh, M("GENERAL_ENABLED")); + } else { + listener->panelChanged(EvWavoldsh, M("GENERAL_DISABLED")); + } + } +} + +void Wavelet::tmrToggled() { if (multiImage) { if (tmr->get_inconsistent()) { - tmr->set_inconsistent (false); - tmrConn.block (true); - tmr->set_active (false); - tmrConn.block (false); + tmr->set_inconsistent(false); + tmrConn.block(true); + tmr->set_active(false); + tmrConn.block(false); } else if (lasttmr) { - tmr->set_inconsistent (true); + tmr->set_inconsistent(true); } - lasttmr = tmr->get_active (); + lasttmr = tmr->get_active(); } - if (listener && (multiImage || getEnabled ())) { + if (listener && (multiImage || getEnabled())) { if (tmr->get_inconsistent()) { - listener->panelChanged (EvWavtmr, M("GENERAL_UNCHANGED")); - } else if (tmr->get_active ()) { - listener->panelChanged (EvWavtmr, M("GENERAL_ENABLED")); + listener->panelChanged(EvWavtmr, M("GENERAL_UNCHANGED")); + } else if (tmr->get_active()) { + listener->panelChanged(EvWavtmr, M("GENERAL_ENABLED")); } else { - listener->panelChanged (EvWavtmr, M("GENERAL_DISABLED")); + listener->panelChanged(EvWavtmr, M("GENERAL_DISABLED")); } } } -void Wavelet::colorForValue (double valX, double valY, enum ColorCaller::ElemType elemType, int callerId, ColorCaller *caller) +void Wavelet::colorForValue(double valX, double valY, enum ColorCaller::ElemType elemType, int callerId, ColorCaller *caller) { float R = 0.f, G = 0.f, B = 0.f; @@ -2897,7 +3460,7 @@ void Wavelet::colorForValue (double valX, double valY, enum ColorCaller::ElemTyp caller->ccGreen = double(G); caller->ccBlue = double(B); } -void Wavelet::setAdjusterBehavior (bool multiplieradd, bool thresholdadd, bool threshold2add, bool thresadd, bool chroadd, bool chromaadd, bool contrastadd, bool skinadd, bool reschroadd, bool tmrsadd, bool resconadd, bool resconHadd, bool thradd, bool thrHadd, bool skyadd, bool edgradadd, bool edgvaladd, bool strengthadd, bool gammaadd, bool edgedetectadd, bool edgedetectthradd , bool edgedetectthr2add) +void Wavelet::setAdjusterBehavior(bool multiplieradd, bool thresholdadd, bool threshold2add, bool thresadd, bool chroadd, bool chromaadd, bool contrastadd, bool skinadd, bool reschroadd, bool tmrsadd, bool edgsadd, bool scaleadd, bool resconadd, bool resconHadd, bool thradd, bool thrHadd, bool radiusadd, bool skyadd, bool edgradadd, bool edgvaladd, bool strengthadd, bool gammaadd, bool edgedetectadd, bool edgedetectthradd, bool edgedetectthr2add) { for (int i = 0; i < 9; i++) { @@ -2915,8 +3478,11 @@ void Wavelet::setAdjusterBehavior (bool multiplieradd, bool thresholdadd, bool t resconH->setAddMode(resconHadd); reschro->setAddMode(reschroadd); tmrs->setAddMode(tmrsadd); + edgs->setAddMode(edgsadd); + scale->setAddMode(scaleadd); thr->setAddMode(thradd); thrH->setAddMode(thrHadd); + radius->setAddMode(radiusadd); sky->setAddMode(skyadd); edgrad->setAddMode(edgradadd); edgval->setAddMode(edgvaladd); @@ -2928,7 +3494,7 @@ void Wavelet::setAdjusterBehavior (bool multiplieradd, bool thresholdadd, bool t } -void Wavelet::neutralPressed () +void Wavelet::neutralPressed() { for (int i = 0; i < 9; i++) { correction[i]->setValue(0); @@ -2936,7 +3502,7 @@ void Wavelet::neutralPressed () } } -void Wavelet::neutralchPressed () +void Wavelet::neutralchPressed() { for (int i = 0; i < 9; i++) { @@ -2946,7 +3512,7 @@ void Wavelet::neutralchPressed () } -void Wavelet::contrastPlusPressed () +void Wavelet::contrastPlusPressed() { for (int i = 0; i < 9; i++) { @@ -2957,7 +3523,7 @@ void Wavelet::contrastPlusPressed () } -void Wavelet::contrastMinusPressed () +void Wavelet::contrastMinusPressed() { for (int i = 0; i < 9; i++) { @@ -2967,7 +3533,7 @@ void Wavelet::contrastMinusPressed () } } -void Wavelet::foldAllButMe (GdkEventButton* event, MyExpander *expander) +void Wavelet::foldAllButMe(GdkEventButton* event, MyExpander *expander) { if (event->button == 3) { expsettings->set_expanded(expsettings == expander); @@ -2976,9 +3542,11 @@ void Wavelet::foldAllButMe (GdkEventButton* event, MyExpander *expander) exptoning->set_expanded(exptoning == expander); expnoise->set_expanded(expnoise == expander); expedge->set_expanded(expedge == expander); + expbl->set_expanded(expbl == expander); expgamut->set_expanded(expgamut == expander); expresid->set_expanded(expresid == expander); expfinal->set_expanded(expfinal == expander); + expclari->set_expanded(expclari == expander); } } @@ -2997,10 +3565,46 @@ void Wavelet::enableToggled(MyExpander *expander) event = EvWavenanoise; } else if (expander == expedge) { event = EvWavenaedge; + } else if (expander == expbl) { + event = EvWavenabl; } else if (expander == expresid) { event = EvWavenares; } else if (expander == expfinal) { event = EvWavenafin; + } else if (expander == expclari) { + if (expclari->getEnabled() == false) { + Backmethod->set_active(1); + CLmethod->set_active(3); + Lmethod->set_active(3); + Dirmethod->set_active(3); + Lmethod->set_sensitive(false); + Dirmethod->set_sensitive(false); + CLmethod->set_sensitive(true); + Backmethod->set_sensitive(true); + } else { + + if (ushamethod->get_active_row_number() == 1) { + Backmethod->set_active(2); + CLmethod->set_active(2); + Lmethod->set_active(6); + Lmethod->set_sensitive(true); + Dirmethod->set_sensitive(true); + Dirmethod->set_active(3); + CLmethod->set_sensitive(false); + Backmethod->set_sensitive(false); + } else if (ushamethod->get_active_row_number() == 0) { + Backmethod->set_active(0); + CLmethod->set_active(1); + Lmethod->set_active(2); + Dirmethod->set_active(3); + Lmethod->set_sensitive(true); + Dirmethod->set_sensitive(true); + CLmethod->set_sensitive(false); + Backmethod->set_sensitive(false); + } + } + + event = EvWavenaclari; } else // unknown expander, returning ! { @@ -3008,40 +3612,59 @@ void Wavelet::enableToggled(MyExpander *expander) } if (expander->get_inconsistent()) { - listener->panelChanged (event, M("GENERAL_UNCHANGED")); + listener->panelChanged(event, M("GENERAL_UNCHANGED")); } else if (expander->getEnabled()) { - listener->panelChanged (event, M("GENERAL_ENABLED")); + listener->panelChanged(event, M("GENERAL_ENABLED")); } else { - listener->panelChanged (event, M("GENERAL_DISABLED")); + listener->panelChanged(event, M("GENERAL_DISABLED")); } } } void Wavelet::writeOptions(std::vector &tpOpen) { - tpOpen.push_back (expsettings->get_expanded ()); - tpOpen.push_back (expcontrast->get_expanded ()); - tpOpen.push_back (expchroma->get_expanded ()); - tpOpen.push_back (exptoning->get_expanded ()); - tpOpen.push_back (expnoise->get_expanded ()); - tpOpen.push_back (expedge->get_expanded ()); - tpOpen.push_back (expgamut->get_expanded ()); - tpOpen.push_back (expresid->get_expanded ()); - tpOpen.push_back (expfinal->get_expanded ()); + tpOpen.push_back(expsettings->get_expanded()); + tpOpen.push_back(expcontrast->get_expanded()); + tpOpen.push_back(expchroma->get_expanded()); + tpOpen.push_back(exptoning->get_expanded()); + tpOpen.push_back(expnoise->get_expanded()); + tpOpen.push_back(expedge->get_expanded()); + tpOpen.push_back(expbl->get_expanded()); + tpOpen.push_back(expgamut->get_expanded()); + tpOpen.push_back(expresid->get_expanded()); + tpOpen.push_back(expfinal->get_expanded()); + tpOpen.push_back(expclari->get_expanded()); } -void Wavelet::updateToolState(std::vector &tpOpen) +void Wavelet::updateToolState(const std::vector& tpOpen) { - if(tpOpen.size() >= 9) { - expsettings->set_expanded(tpOpen.at(0)); - expcontrast->set_expanded(tpOpen.at(1)); - expchroma->set_expanded(tpOpen.at(2)); - exptoning->set_expanded(tpOpen.at(3)); - expnoise->set_expanded(tpOpen.at(4)); - expedge->set_expanded(tpOpen.at(5)); - expgamut->set_expanded(tpOpen.at(6)); - expresid->set_expanded(tpOpen.at(7)); - expfinal->set_expanded(tpOpen.at(8)); + if (tpOpen.empty()) { + expsettings->set_expanded(false); + expcontrast->set_expanded(false); + expchroma->set_expanded(false); + exptoning->set_expanded(false); + expnoise->set_expanded(false); + expedge->set_expanded(false); + expbl->set_expanded(false); + expgamut->set_expanded(false); + expresid->set_expanded(false); + expfinal->set_expanded(false); + expclari->set_expanded(false); + return; + } + + if (tpOpen.size() >= 11) { + expsettings->set_expanded(tpOpen[0]); + expcontrast->set_expanded(tpOpen[1]); + expchroma->set_expanded(tpOpen[2]); + exptoning->set_expanded(tpOpen[3]); + expnoise->set_expanded(tpOpen[4]); + expedge->set_expanded(tpOpen[5]); + expbl->set_expanded(tpOpen[6]); + expgamut->set_expanded(tpOpen[7]); + expresid->set_expanded(tpOpen[8]); + expfinal->set_expanded(tpOpen[9]); + expclari->set_expanded(tpOpen[10]); } } diff --git a/rtgui/wavelet.h b/rtgui/wavelet.h index 6551b58d4..d1b4bb7c3 100644 --- a/rtgui/wavelet.h +++ b/rtgui/wavelet.h @@ -20,12 +20,13 @@ #pragma once #include + #include "adjuster.h" -#include "toolpanel.h" -#include "curvelistener.h" -#include "thresholdadjuster.h" #include "colorprovider.h" +#include "curvelistener.h" #include "guiutils.h" +#include "thresholdadjuster.h" +#include "toolpanel.h" class CurveEditor; class CurveEditorGroup; @@ -43,21 +44,22 @@ class Wavelet final : public FoldableToolPanel { public: - Wavelet (); - ~Wavelet () override; + Wavelet(); + ~Wavelet() override; - bool wavComputed_ (); + bool wavComputed_(); void adjusterChanged(Adjuster* a, double newval) override; - void autoOpenCurve () override; - void curveChanged (CurveEditor* ce) override; - void read (const rtengine::procparams::ProcParams* pp, const ParamsEdited* pedited = nullptr) override; - void setAdjusterBehavior (bool multiplieradd, bool thresholdadd, bool threshold2add, bool thresadd, bool chroadd, bool chromaadd, bool contrastadd, bool skinadd, bool reschroadd, bool tmrsadd, bool resconadd, bool resconHadd, bool thradd, bool thrHadd, bool skyadd, bool edgradadd, bool edgvaladd, bool strengthadd, bool gammaadd, bool edgedetectadd, bool edgedetectthradd, bool edgedetectthr2add); - void setBatchMode (bool batchMode) override; - void setDefaults (const rtengine::procparams::ProcParams* defParams, const ParamsEdited* pedited = nullptr) override; - void setEditProvider (EditDataProvider *provider) override; - void updateToolState (std::vector &tpOpen); - void write (rtengine::procparams::ProcParams* pp, ParamsEdited* pedited = nullptr) override; - void writeOptions (std::vector &tpOpen); + void autoOpenCurve() override; + void curveChanged(CurveEditor* ce) override; + void read(const rtengine::procparams::ProcParams* pp, const ParamsEdited* pedited = nullptr) override; +// void setAdjusterBehavior(bool multiplieradd, bool thresholdadd, bool threshold2add, bool thresadd, bool chroadd, bool chromaadd, bool contrastadd, bool skinadd, bool reschroadd, bool tmrsadd, bool resconadd, bool resconHadd, bool thradd, bool thrHadd, bool skyadd, bool edgradadd, bool edgvaladd, bool strengthadd, bool gammaadd, bool edgedetectadd, bool edgedetectthradd, bool edgedetectthr2add); + void setAdjusterBehavior (bool multiplieradd, bool thresholdadd, bool threshold2add, bool thresadd, bool chroadd, bool chromaadd, bool contrastadd, bool skinadd, bool reschroadd, bool tmrsadd, bool edgsadd, bool scaleadd, bool resconadd, bool resconHadd, bool thradd, bool thrHadd, bool radiusadd, bool skyadd, bool edgradadd, bool edgvaladd, bool strengthadd, bool gammaadd, bool edgedetectadd, bool edgedetectthradd, bool edgedetectthr2add); + void setBatchMode(bool batchMode) override; + void setDefaults(const rtengine::procparams::ProcParams* defParams, const ParamsEdited* pedited = nullptr) override; + void setEditProvider(EditDataProvider *provider) override; + void updateToolState(const std::vector& tpOpen); + void write(rtengine::procparams::ProcParams* pp, ParamsEdited* pedited = nullptr) override; + void writeOptions(std::vector &tpOpen); void adjusterChanged(ThresholdAdjuster* a, double newBottom, double newTop) override; void adjusterChanged(ThresholdAdjuster* a, double newBottomLeft, double newTopLeft, double newBottomRight, double newTopRight) override; @@ -66,38 +68,67 @@ public: void adjusterChanged2(ThresholdAdjuster* a, int newBottomL, int newTopL, int newBottomR, int newTopR) override; private: - void foldAllButMe (GdkEventButton* event, MyExpander *expander); + rtengine::ProcEvent EvWavenaclari; + rtengine::ProcEvent EvWavushamet; + rtengine::ProcEvent EvWavballum; + rtengine::ProcEvent EvWavbalchrom; + rtengine::ProcEvent EvWavchromfi; + rtengine::ProcEvent EvWavchromco; + rtengine::ProcEvent EvWavmergeL; + rtengine::ProcEvent EvWavmergeC; + rtengine::ProcEvent EvWavsoftrad; + rtengine::ProcEvent EvWavsoftradend; + rtengine::ProcEvent EvWavshowmask; + rtengine::ProcEvent EvWavedgs; + rtengine::ProcEvent EvWavscale; + rtengine::ProcEvent EvWavradius; + rtengine::ProcEvent EvWavsigma; + rtengine::ProcEvent EvWavenabl; + rtengine::ProcEvent EvWavchrwav; + rtengine::ProcEvent EvWavoldsh; + rtengine::ProcEvent EvWavoffset; + rtengine::ProcEvent EvWavlowthr; + rtengine::ProcEvent EvWavbluwav; + rtengine::ProcEvent EvWavblshape; + rtengine::ProcEvent EvWavresblur; + rtengine::ProcEvent EvWavresblurc; + rtengine::ProcEvent EvWavedgeffect; - void colorForValue (double valX, double valY, enum ColorCaller::ElemType elemType, int callerId, ColorCaller* caller) override; - void BAmethodChanged (); - void NPmethodChanged (); - void BackmethodChanged (); - void CHSLmethodChanged (); - void CHmethodChanged (); - void CLmethodChanged (); - void DirmethodChanged (); - void EDmethodChanged (); - void HSmethodChanged (); - void LmethodChanged (); - void MedgreinfChanged (); - void TMmethodChanged (); - void TilesmethodChanged (); - void avoidToggled (); - void cbenabToggled (); - void contrastMinusPressed (); - void contrastPlusPressed (); - void daubcoeffmethodChanged (); - void enabledChanged () override; - void linkedgToggled (); - void lipstToggled (); - void medianToggled (); - void medianlevToggled (); - void neutralPressed (); - void neutral_pressed (); - void neutralchPressed (); - void tmrToggled (); + void foldAllButMe(GdkEventButton* event, MyExpander *expander); + + void colorForValue(double valX, double valY, enum ColorCaller::ElemType elemType, int callerId, ColorCaller* caller) override; + void BAmethodChanged(); + void NPmethodChanged(); + void BackmethodChanged(); + void CHSLmethodChanged(); + void CHmethodChanged(); + void CLmethodChanged(); + void DirmethodChanged(); + void EDmethodChanged(); + void HSmethodChanged(); + void LmethodChanged(); + void MedgreinfChanged(); + void TMmethodChanged(); + void TilesmethodChanged(); + void avoidToggled(); + void showmaskToggled (); + void oldshToggled (); + void cbenabToggled(); + void contrastMinusPressed(); + void contrastPlusPressed(); + void daubcoeffmethodChanged(); + void enabledChanged() override; + void linkedgToggled(); + void lipstToggled(); + void medianToggled(); + void medianlevToggled(); + void neutralPressed(); + void neutral_pressed(); + void neutralchPressed(); + void tmrToggled(); void updatewavLabel (); - void wavChanged (double nlevel) override; + void wavChanged(double nlevel) override; + void ushamethodChanged(); void HSmethodUpdateUI(); void CHmethodUpdateUI(); @@ -113,17 +144,18 @@ private: // void MedgreinfUpdateUI(); // void DirmethodUpdateUI(); // void LmethodUpdateUI(); - void adjusterUpdateUI (Adjuster* a); - void enabledUpdateUI (); - void medianlevUpdateUI (); - void cbenabUpdateUI (); - void lipstUpdateUI (); + void adjusterUpdateUI(Adjuster* a); + void enabledUpdateUI(); + void medianlevUpdateUI(); + void cbenabUpdateUI(); + void lipstUpdateUI(); - void enableToggled(MyExpander *expander); + void enableToggled(MyExpander* expander); CurveEditorGroup* const curveEditorG; CurveEditorGroup* const CCWcurveEditorG; + CurveEditorGroup* const curveEditorbl; CurveEditorGroup* const curveEditorRES; CurveEditorGroup* const curveEditorGAM; Gtk::HSeparator* const separatorNeutral; @@ -142,6 +174,7 @@ private: DiagonalCurveEditor* clshape; FlatCurveEditor* ccshape; + FlatCurveEditor* blshape; Gtk::CheckButton* const median; Gtk::CheckButton* const medianlev; Gtk::CheckButton* const linkedg; @@ -149,14 +182,24 @@ private: Gtk::CheckButton* const lipst; Gtk::CheckButton* const avoid; Gtk::CheckButton* const tmr; + Gtk::CheckButton* const showmask; + Gtk::CheckButton* const oldsh; Gtk::Button* const neutralchButton; Adjuster* correction[9]; Adjuster* correctionch[9]; + Adjuster* const sigma; + Adjuster* const offset; + Adjuster* const lowthr; Adjuster* const rescon; Adjuster* const resconH; Adjuster* const reschro; + Adjuster* const resblur; + Adjuster* const resblurc; + Adjuster* const bluwav; Adjuster* const tmrs; + Adjuster* const edgs; + Adjuster* const scale; Adjuster* const gamma; Adjuster* const sup; Adjuster* const sky; @@ -166,13 +209,16 @@ private: Adjuster* const contrast; Adjuster* const thr; Adjuster* const thrH; + Adjuster* const radius; Adjuster* const skinprotect; Adjuster* const edgrad; + Adjuster* const edgeffect; Adjuster* const edgval; Adjuster* const edgthresh; Adjuster* const strength; Adjuster* const balance; Adjuster* const iter; + Adjuster* greenlow; Adjuster* bluelow; Adjuster* greenmed; @@ -199,6 +245,16 @@ private: Adjuster* const edgedetectthr2; Adjuster* const edgesensi; Adjuster* const edgeampli; + Adjuster* const ballum; + Adjuster* const balchrom; + Adjuster* const chromfi; + Adjuster* const chromco; + Adjuster* const mergeL; + Adjuster* const mergeC; + Adjuster* const softrad; + Adjuster* const softradend; + Adjuster* const chrwav; + MyComboBoxText* const Lmethod; sigc::connection Lmethodconn; MyComboBoxText* const CHmethod; @@ -227,13 +283,22 @@ private: sigc::connection Dirmethodconn; MyComboBoxText* const Medgreinf; sigc::connection MedgreinfConn; + MyComboBoxText* const ushamethod; + sigc::connection ushamethodconn; + Gtk::Frame* const chanMixerHLFrame; Gtk::Frame* const chanMixerMidFrame; Gtk::Frame* const chanMixerShadowsFrame; + Gtk::Frame* const shFrame; + Gtk::Frame* const contFrame; + Gtk::Frame* const blurFrame; + Gtk::Frame* const chromaFrame; + Gtk::Frame* const chroFrame; Gtk::Label* const wavLabels; Gtk::Label* const labmC; Gtk::Label* const labmNP; + Gtk::Label* const usharpLabel; MyExpander* const expchroma; MyExpander* const expcontrast; MyExpander* const expedge; @@ -243,18 +308,21 @@ private: MyExpander* const expresid; MyExpander* const expsettings; MyExpander* const exptoning; + MyExpander* const expclari; + MyExpander* const expbl; Gtk::HBox* const neutrHBox; + Gtk::HBox* const usharpHBox; - sigc::connection enableChromaConn, enableContrastConn, enableEdgeConn, enableFinalConn; + sigc::connection enableChromaConn, enableContrastConn, enableEdgeConn, enabletmConn, enableFinalConn, enableclariConn; sigc::connection enableNoiseConn, enableResidConn, enableToningConn; - sigc::connection medianConn, avoidConn, tmrConn, medianlevConn, linkedgConn, lipstConn, cbenabConn, neutralconn; + sigc::connection medianConn, avoidConn, tmrConn, medianlevConn, linkedgConn, lipstConn, cbenabConn, neutralconn, showmaskConn, oldshConn; sigc::connection neutralPressedConn; sigc::connection contrastPlusPressedConn; sigc::connection contrastMinusPressedConn; sigc::connection neutralchPressedConn; - bool lastmedian, lastmedianlev, lastlinkedg, lastavoid, lastlipst, lasttmr, lastcbenab; + bool lastmedian, lastmedianlev, lastlinkedg, lastavoid, lastlipst, lasttmr, lastcbenab, lastshowmask, lastoldsh; int nextnlevel; IdleRegister idle_register; diff --git a/rtgui/whitebalance.cc b/rtgui/whitebalance.cc index 2ab09c10a..5d1c907df 100644 --- a/rtgui/whitebalance.cc +++ b/rtgui/whitebalance.cc @@ -142,7 +142,7 @@ static double wbTemp2Slider(double temp) return sval; } -WhiteBalance::WhiteBalance () : FoldableToolPanel(this, "whitebalance", M("TP_WBALANCE_LABEL"), false, true), wbp(nullptr), wblistener(nullptr) +WhiteBalance::WhiteBalance () : FoldableToolPanel(this, "whitebalance", M("TP_WBALANCE_LABEL"), true, true), wbp(nullptr), wblistener(nullptr) { Gtk::Grid* methodgrid = Gtk::manage(new Gtk::Grid()); @@ -175,6 +175,14 @@ WhiteBalance::WhiteBalance () : FoldableToolPanel(this, "whitebalance", M("TP_WB row[methodColumns.colId] = i + 100; } + if (currType == WBEntry::Type::AUTO) { + // Creating the auto category + row = *(refTreeModel->append()); + row[methodColumns.colIcon] = wbPixbufs[toUnderlying(currType)]; + row[methodColumns.colLabel] = M("TP_WBALANCE_AUTO_HEADER"); + row[methodColumns.colId] = i + 100; + } + if (currType == WBEntry::Type::WATER) { // Creating the under water subcategory header row = *(refTreeModel->append()); @@ -213,6 +221,7 @@ WhiteBalance::WhiteBalance () : FoldableToolPanel(this, "whitebalance", M("TP_WB || currType == WBEntry::Type::WATER || currType == WBEntry::Type::FLASH || currType == WBEntry::Type::LED + || currType == WBEntry::Type::AUTO ) { childrow = *(refTreeModel->append(row.children())); childrow[methodColumns.colIcon] = wbPixbufs[toUnderlying(currType)]; @@ -315,6 +324,9 @@ WhiteBalance::WhiteBalance () : FoldableToolPanel(this, "whitebalance", M("TP_WB Gtk::Image* itempbiasL = Gtk::manage (new RTImage ("circle-blue-small.png")); Gtk::Image* itempbiasR = Gtk::manage (new RTImage ("circle-yellow-small.png")); + StudLabel = Gtk::manage(new Gtk::Label("---", Gtk::ALIGN_CENTER)); + StudLabel->set_tooltip_text(M("TP_WBALANCE_STUDLABEL_TOOLTIP")); + temp = Gtk::manage (new Adjuster (M("TP_WBALANCE_TEMPERATURE"), MINTEMP, MAXTEMP, 5, CENTERTEMP, itempL, itempR, &wbSlider2Temp, &wbTemp2Slider)); green = Gtk::manage (new Adjuster (M("TP_WBALANCE_GREEN"), MINGREEN, MAXGREEN, 0.001, 1.0, igreenL, igreenR)); equal = Gtk::manage (new Adjuster (M("TP_WBALANCE_EQBLUERED"), MINEQUAL, MAXEQUAL, 0.001, 1.0, iblueredL, iblueredR)); @@ -335,6 +347,7 @@ WhiteBalance::WhiteBalance () : FoldableToolPanel(this, "whitebalance", M("TP_WB boxgreen->pack_start(*igreenL); boxgreen->pack_start(*green); boxgreen->pack_start(*igreenR);*/ + pack_start(*StudLabel); pack_start (*temp); //pack_start (*boxgreen); @@ -448,6 +461,7 @@ void WhiteBalance::optChanged () methconn.block(prevState); return; } + StudLabel->hide(); if (opt != row[methodColumns.colId]) { @@ -463,6 +477,12 @@ void WhiteBalance::optChanged () const WBEntry& currMethod = WBParams::getWbEntries()[methodId]; tempBias->set_sensitive(currMethod.type == WBEntry::Type::AUTO); + bool autit = (currMethod.ppLabel == "autitcgreen"); + if (autit) { + StudLabel->show(); + } else { + StudLabel->hide(); + } switch (currMethod.type) { case WBEntry::Type::CAMERA: @@ -547,6 +567,8 @@ void WhiteBalance::optChanged () void WhiteBalance::spotPressed () { + StudLabel->hide(); + if (wblistener) { wblistener->spotWBRequested (getSize()); } @@ -683,6 +705,13 @@ void WhiteBalance::read (const ProcParams* pp, const ParamsEdited* pedited) } tempBias->set_sensitive(wbValues.type == WBEntry::Type::AUTO); + bool autit = (wbValues.ppLabel == "autitcgreen"); + if (autit) { + StudLabel->show(); + } else { + StudLabel->hide(); + } + } setEnabled(pp->wb.enabled); @@ -868,7 +897,7 @@ int WhiteBalance::_setActiveMethod(Glib::ustring &label, Gtk::TreeModel::Childre if (row[methodColumns.colLabel] == label) { method->set_active(iter); - found = method->get_active_row_number(); + found = row[methodColumns.colId]; } if (found != -1) { @@ -901,15 +930,19 @@ inline Gtk::TreeRow WhiteBalance::getActiveMethod () return *(method->get_active()); } -void WhiteBalance::WBChanged(double temperature, double greenVal) +void WhiteBalance::WBChanged(double temperature, double greenVal, float studgood) { idle_register.add( - [this, temperature, greenVal]() -> bool + [this, temperature, greenVal, studgood]() -> bool { disableListener(); setEnabled(true); temp->setValue(temperature); green->setValue(greenVal); + StudLabel->set_text( + Glib::ustring::compose(M("TP_WBALANCE_STUDLABEL"), + Glib::ustring::format(std::fixed, std::setprecision(4), studgood)) + ); temp->setDefault(temperature); green->setDefault(greenVal); enableListener(); diff --git a/rtgui/whitebalance.h b/rtgui/whitebalance.h index b4d09f119..17e45e8bb 100644 --- a/rtgui/whitebalance.h +++ b/rtgui/whitebalance.h @@ -43,6 +43,9 @@ class WhiteBalance final : public ToolParamBlock, public AdjusterListener, publi WBLT_PP }; +private: + Gtk::Label* StudLabel; + protected: class MethodColumns : public Gtk::TreeModel::ColumnRecord { @@ -119,7 +122,7 @@ public: wblistener = l; } void setWB (int temp, double green); - void WBChanged (double temp, double green) override; + void WBChanged (double temp, double green, float studgood) override; void setAdjusterBehavior (bool tempadd, bool greenadd, bool equaladd, bool tempbiasadd); void trimValues (rtengine::procparams::ProcParams* pp) override; diff --git a/tools/generateRtexifUpdates b/tools/generateRtexifUpdates index 72a97862e..b4ace209d 100755 --- a/tools/generateRtexifUpdates +++ b/tools/generateRtexifUpdates @@ -32,7 +32,10 @@ echo #------------------------------------------------------------------------------ # Canon printf '%s\n' "Saving ${tmpdir}/canon_lenses" -xmlstarlet sel -T -t -m "taginfo/table/tag[@name='LensType']/values/key" -v "concat(@id,' ',val)" -n < <("$et" -listx -canon:all) | sort -fuV > "${tmpdir}/canon_lenses" +xmlstarlet sel -T -t \ + -m "taginfo/table/tag[@name='LensType']/values/key" \ + -v "concat(@id,' ',val)" \ + -n < <("$et" -listx -canon:all) | sort -fuV > "${tmpdir}/canon_lenses" #In :10.1 Sigma 50mm f/2.8 EX #Out: {10, "Sigma 50mm f/2.8 EX"}, @@ -55,7 +58,11 @@ sed -r -i \ # replace with '] = "' # append '";' printf '%s\n' "Saving ${tmpdir}/canon_cameras" -xmlstarlet sel -T -t -m "taginfo/table/tag[@name='CanonModelID']/values/key" -v "concat(@id,' ',val)" -n < <("$et" -listx -canon:all) | sort -fuV > "${tmpdir}/canon_cameras" +xmlstarlet sel -T -t \ + -m "taginfo/table/tag[@name='CanonModelID']/values/key" \ + -v "concat(@id,' ',val)" \ + -n < <("$et" -listx -canon:all) | sort -fuV > "${tmpdir}/canon_cameras" + sed -r -i \ -e 's/^/ choices[/' \ -e 's/\t/] = "/' \ @@ -65,28 +72,84 @@ sed -r -i \ #------------------------------------------------------------------------------ # Nikon LensIDs are composite tags printf '%s\n' "Saving ${tmpdir}/nikon" -xmlstarlet sel -T -t -m "taginfo/table/tag[@name='LensID']/values/key" -v "concat(@id,' ',val)" -n < <("$et" -listx -composite:all) > "${tmpdir}/nikon" -sed -r -i -e '/^... /d' -e 's/^/ {"/' -e 's/([A-F0-9]+)[A-F0-9.]*\t/\1", "/' -e 's/$/"},/' -e 's|(.* ")(.*) F([0-9]+)|\1\2 f/\3|' -e 's| F/([0-9]+)| f/\1|' "${tmpdir}/nikon" + +xmlstarlet sel -T -t \ + -m "taginfo/table/tag[@name='LensID']/values/key" \ + -v "concat(@id,' ',val)" \ + -n < <("$et" -listx -composite:all) > "${tmpdir}/nikon" + +sed -r -i \ + -e '/^... /d' \ + -e 's/^/ {"/' \ + -e 's/([A-F0-9]+)[A-F0-9.]*\t/\1", "/' \ + -e 's/$/"},/' \ + -e 's|(.* ")(.*) F([0-9]+)|\1\2 f/\3|' \ + -e 's| F/([0-9]+)| f/\1|' \ + "${tmpdir}/nikon" #------------------------------------------------------------------------------ # Olympus printf '%s\n' "Saving ${tmpdir}/olympus" -xmlstarlet sel -T -t -m "taginfo/table/tag[@name='LensType']/values/key" -v "concat(@id,' ',val)" -n < <("$et" -listx -olympus:all) | sort -fuV > "${tmpdir}/olympus" -sed -r -i -e '/0 00 00\tNone/d' -e 's/^/ lenses["0/' -e 's/\t/"] = "/' -e 's/$/";/' -e 's| F([0-9]+)| f/\1|g' "${tmpdir}/olympus" + +xmlstarlet sel -T -t \ + -m "taginfo/table/tag[@name='LensType']/values/key" \ + -v "concat(@id,' ',val)" \ + -n < <("$et" -listx -olympus:all) | sort -fuV > "${tmpdir}/olympus" + +sed -r -i \ + -e '/0 00 00\tNone/d' \ + -e 's/^/ lenses["0/' \ + -e 's/\t/"] = "/' \ + -e 's/$/";/' \ + -e 's| F([0-9]+)| f/\1|g' \ + "${tmpdir}/olympus" #------------------------------------------------------------------------------ # Pentax printf '%s\n' "Saving ${tmpdir}/pentax" -xmlstarlet sel -T -t -m "taginfo/table/tag[@name='LensType']/values/key" -v "concat(@id,' ',val)" -n < <("$et" -listx -pentax:all) | sort -fuV > "${tmpdir}/pentax" -sed -r -i -e 's/^/ choices.insert (p_t (256 * /' -e 's/([0-9]+) ([0-9]+)([0-9.]*)/\1 + \2/' -e 's/\t/, "/' -e 's/$/"));/' -e 's| F([0-9]+)| f/\1|' "${tmpdir}/pentax" + +xmlstarlet sel -T -t \ + -m "taginfo/table/tag[@name='LensType']/values/key" \ + -v "concat(@id,' ',val)" \ + -n < <("$et" -listx -pentax:all) | sort -fuV > "${tmpdir}/pentax" + +sed -r -i \ + -e 's/^/ choices.insert (p_t (256 * /' \ + -e 's/([0-9]+) ([0-9]+)([0-9.]*)/\1 + \2/' \ + -e 's/\t/, "/' \ + -e 's/$/"));/' \ + -e 's| F([0-9]+)| f/\1|' \ + "${tmpdir}/pentax" #------------------------------------------------------------------------------ # Sony printf '%s\n' "Saving ${tmpdir}/sony" -xmlstarlet sel -T -t -m "taginfo/table/tag[@name='LensType']/values/key" -v "concat(@id,' ',val)" -n < <("$et" -listx -sony:all) | sort -fuV > "${tmpdir}/sony" + +xmlstarlet sel -T -t \ + -m "taginfo/table/tag[@name='LensType']/values/key" \ + -v "concat(@id,' ',val)" \ + -n < <("$et" -listx -sony:all) | sort -fuV > "${tmpdir}/sony" + # Sony has more lenses under the LensType2 tag printf '%s\n' "Saving ${tmpdir}/sony-lenstype2" -xmlstarlet sel -T -t -m "taginfo/table/tag[@name='LensType2']/values/key" -v "concat(@id,' ',val)" -n < <("$et" -listx -sony:all) | sort -fuV > "${tmpdir}/sony-lenstype2" -sed -r -i -e 's/^/ {/' -e 's/([0-9]+)[0-9.]*\t/\1, "/' -e 's/$/"},/' -e 's| F([0-9]+)| f/\1|g' "${tmpdir}/sony" -sed -r -i -e '/255\tTamron Lens (255)/d' -e 's/([0-9]+)[0-9.]*\t/\1, "/' -e 's/^/ choices.insert (p_t (/' -e 's/$/"));/' -e 's| F([0-9]+)| f/\1|g' "${tmpdir}/sony-lenstype2" + +xmlstarlet sel -T -t \ + -m "taginfo/table/tag[@name='LensType2']/values/key" \ + -v "concat(@id,' ',val)" \ + -n < <("$et" -listx -sony:all) | sort -fuV > "${tmpdir}/sony-lenstype2" + +sed -r -i \ + -e 's/^/ {/' \ + -e 's/([0-9]+)[0-9.]*\t/\1, "/' \ + -e 's/$/"},/' \ + -e 's| F([0-9]+)| f/\1|g' \ + "${tmpdir}/sony" + +sed -r -i \ + -e '/255\tTamron Lens (255)/d' \ + -e 's/([0-9]+)[0-9.]*\t/\1, "/' \ + -e 's/^/ choices.insert (p_t (/' \ + -e 's/$/"));/' \ + -e 's| F([0-9]+)| f/\1|g' \ + "${tmpdir}/sony-lenstype2" diff --git a/tools/osx/Info.plist-bin.in b/tools/osx/Info.plist-bin.in deleted file mode 100644 index 33abd4f7a..000000000 --- a/tools/osx/Info.plist-bin.in +++ /dev/null @@ -1,10 +0,0 @@ - - - - - CFBundleName - RawTherapee-bin - CFBundleIdentifier - com.rawtherapee.rawtherapee - - diff --git a/tools/osx/Info.plist.in b/tools/osx/Info.plist.in index eec1ab490..6970ed4da 100644 --- a/tools/osx/Info.plist.in +++ b/tools/osx/Info.plist.in @@ -1,7 +1,45 @@ - + LSEnvironment + + XDG_DATA_DIRS + /Applications/RawTherapee.app/Contents/Resources/share + DYLD_FALLBACK_LIBRARY_PATH + /Applications/RawTherapee.app/Contents/Frameworks + GTK_PATH + /Applications/RawTherapee.app/Contents/Frameworks + GTK_IM_MODULE_FILE + /Applications/RawTherapee.app/Contents/Resources/etc/gtk-3.0/gtk.immodules + GTK_MODULES + /Applications/RawTherapee.app/Contents/Frameworks/im-quartz.so + XDG_DATA_HOME + /Applications/RawTherapee.app/Contents/Resources/share + GSETTINGS_SCHEMA_DIR + /Applications/RawTherapee.app/Contents/Resources/share/glib-2.0/schemas + GDK_PIXBUF_MODULE_FILE + /Applications/RawTherapee.app/Contents/Resources/etc/gtk-3.0/gdk-pixbuf.loaders + GDK_PIXBUF_MODULEDIR + /Applications/RawTherapee.app/Contents/Frameworks + FONTCONFIG_PATH + /Applications/RawTherapee.app/Contents/Resources/etc/fonts + LIBDIR + /Applications/RawTherapee.app/Contents/Frameworks + DATADIR + /Applications/RawTherapee.app/Contents/Resources + GDK_RENDERING + similar + GTK_OVERLAY_SCROLLING + 0 + GDK_NATIVE_WINDOWS + 1 + + ATSApplicationFontsPath + etc/fonts + LSMultipleInstancesProhibited + + LSMinimumSystemVersion + @minimum_macos_version@ CFBundleDevelopmentRegion English CFBundleDisplayName @@ -21,7 +59,7 @@ CFBundleTypeRole Editor LSIsAppleDefaultForType - + LSItemContentTypes com.rawtherapee.pp3 @@ -115,7 +153,7 @@ CFBundleIconFile rawtherapee.icns CFBundleIdentifier - com.rawtherapee.rawtherapee + com.rawtherapee.RawTherapee CFBundleInfoDictionaryVersion 6.0 CFBundleName @@ -133,7 +171,7 @@ @arch@ NSHighResolutionCapable - + NSHumanReadableCopyright Copyright © 2004-2010 Gábor Horváth, 2010-2017 RawTherapee Development Team UTExportedTypeDeclarations @@ -164,4 +202,4 @@ - + \ No newline at end of file diff --git a/tools/osx/executable_loader.in b/tools/osx/executable_loader.in deleted file mode 100644 index 429173d8e..000000000 --- a/tools/osx/executable_loader.in +++ /dev/null @@ -1,30 +0,0 @@ -#!/bin/sh - -cd "$(dirname "$0")" || exit 1 - -cwd="$(pwd)" -app="${cwd%/Contents/*}" -lib="${app}/Contents/Frameworks" -resources="${app}/Contents/Resources" -etc="${resources}"/etc -export XDG_DATA_DIRS="${resources}/share" -export DYLD_LIBRARY_PATH="${lib}" -export GTK_PATH="${lib}/gtk-3.0/3.0.0" -export XDG_DATA_HOME="${resources}/share" -export GSETTINGS_SCHEMA_DIR="${resources}/share/glib-2.0/schemas" -export GDK_PIXBUF_MODULE_FILE="${etc}/gtk-3.0/gdk-pixbuf.loaders" -export GDK_PIXBUF_MODULEDIR="${lib}/gdk-pixbuf-2.0/2.10.0/loaders" - -export RT_SETTINGS="${HOME}/Library/Application Support/RawTherapee/config" -export RT_CACHE="${HOME}/Library/Application Support/RawTherapee/cache" - -# Strip out system argument -case "$1" in - -psn_*) shift ;; -esac - -# Prevent crash when directory name contains special characters -AppleLocale=`defaults read -g AppleLocale` -export LANG=${AppleLocale%@*}.UTF-8 - -exec "${cwd}/bin/rawtherapee-bin" "$@" diff --git a/tools/osx/libiconv_1.14_rt.patch b/tools/osx/libiconv_1.14_rt.patch deleted file mode 100644 index 7a01b1373..000000000 --- a/tools/osx/libiconv_1.14_rt.patch +++ /dev/null @@ -1,30 +0,0 @@ -diff --git a/lib/iconv.c b/lib/iconv.c -index 3785296..24a0f07 100644 ---- a/lib/iconv.c -+++ b/lib/iconv.c -@@ -607,4 +607,25 @@ strong_alias (libiconv, iconv) - strong_alias (libiconv_close, iconv_close) - #endif - -+#undef iconv_open -+#undef iconv -+#undef iconv_close -+ -+LIBICONV_DLL_EXPORTED iconv_t iconv_open (const char* tocode, const char* fromcode) -+{ -+ return libiconv_open(tocode, fromcode); -+} -+ -+LIBICONV_DLL_EXPORTED size_t iconv (iconv_t icd, -+ ICONV_CONST char * * inbuf, size_t *inbytesleft, -+ char * * outbuf, size_t *outbytesleft) -+{ -+ return libiconv(icd, inbuf, inbytesleft, outbuf, outbytesleft); -+} -+ -+LIBICONV_DLL_EXPORTED int iconv_close (iconv_t icd) -+{ -+ return libiconv_close(icd); -+} -+ - #endif diff --git a/tools/osx/libiconv_1.15_rt.patch b/tools/osx/libiconv_1.15_rt.patch deleted file mode 100644 index ca434154b..000000000 --- a/tools/osx/libiconv_1.15_rt.patch +++ /dev/null @@ -1,30 +0,0 @@ -diff --git a/lib/iconv.c b/lib/iconv.c -index 31853a7..630a498 100644 ---- a/lib/iconv.c -+++ b/lib/iconv.c -@@ -611,4 +611,25 @@ strong_alias (libiconv, iconv) - strong_alias (libiconv_close, iconv_close) - #endif - -+#undef iconv_open -+#undef iconv -+#undef iconv_close -+ -+LIBICONV_DLL_EXPORTED iconv_t iconv_open (const char* tocode, const char* fromcode) -+{ -+ return libiconv_open(tocode, fromcode); -+} -+ -+LIBICONV_DLL_EXPORTED size_t iconv (iconv_t icd, -+ ICONV_CONST char * * inbuf, size_t *inbytesleft, -+ char * * outbuf, size_t *outbytesleft) -+{ -+ return libiconv(icd, inbuf, inbytesleft, outbuf, outbytesleft); -+} -+ -+LIBICONV_DLL_EXPORTED int iconv_close (iconv_t icd) -+{ -+ return libiconv_close(icd); -+} -+ - #endif diff --git a/tools/osx/macosx_bundle.sh b/tools/osx/macosx_bundle.sh index 3958326e8..9258810c0 100644 --- a/tools/osx/macosx_bundle.sh +++ b/tools/osx/macosx_bundle.sh @@ -34,27 +34,43 @@ function CheckLink { done } +function ModifyInstallNames { + find -E "${CONTENTS}" -type f -regex '.*/(rawtherapee-cli|rawtherapee|.*\.(dylib|so))' | while read -r x; do + msg "Modifying install names: ${x}" + { + # id + if [[ ${x:(-6)} == ".dylib" ]] || [[ f${x:(-3)} == ".so" ]]; then + install_name_tool -id /Applications/"${LIB}"/$(basename ${x}) ${x} + fi + GetDependencies "${x}" | while read -r y + do + install_name_tool -change ${y} /Applications/"${LIB}"/$(basename ${y}) ${x} + done + } | bash -v + done +} + # Source check -if [[ ! -d "${CMAKE_BUILD_TYPE}" ]]; then +if [[ ! -d $CMAKE_BUILD_TYPE ]]; then msgError "${PWD}/${CMAKE_BUILD_TYPE} folder does not exist. Please execute 'make install' first." exit 1 fi # Update project version -if [[ -x "$(which git)" && -d "${PROJECT_SOURCE_DIR}/.git" ]]; then +if [[ -x $(which git) && -d $PROJECT_SOURCE_DIR/.git ]]; then ### This section is copied from tools/generateReleaseInfo # Get version description. # Depending on whether you checked out a branch (dev) or a tag (release), # "git describe" will return "5.0-gtk2-2-g12345678" or "5.0-gtk2", respectively. gitDescribe="$(git describe --tags --always)" - + # Apple requires a numeric version of the form n.n.n # https://goo.gl/eWDQv6 - + # Get number of commits since tagging. This is what gitDescribe uses. # Works when checking out branch, tag or commit. gitCommitsSinceTag="$(git rev-list --count HEAD --not $(git tag --merged HEAD))" - + # Create numeric version. # This version is nonsense, either don't use it at all or use it only where you have no other choice, e.g. Inno Setup's VersionInfoVersion. # Strip everything after hyphen, e.g. "5.0-gtk2" -> "5.0", "5.1-rc1" -> "5.1" (ergo BS). @@ -65,21 +81,17 @@ if [[ -x "$(which git)" && -d "${PROJECT_SOURCE_DIR}/.git" ]]; then gitVersionNumericBS="${gitVersionNumericBS}.${gitCommitsSinceTag}" # Remove everything until after first hyphen: 5.0 fi ### Copy end. - + PROJECT_FULL_VERSION="$gitDescribe" PROJECT_VERSION="$gitVersionNumericBS" - fi MINIMUM_SYSTEM_VERSION="$(otool -l "${CMAKE_BUILD_TYPE}"/MacOS/rawtherapee | grep -A2 'LC_VERSION_MIN_MACOSX' | awk '$1 ~ /version/ { printf $2 }')" -if [[ -z "${MINIMUM_SYSTEM_VERSION}" ]]; then +if [[ -z $MINIMUM_SYSTEM_VERSION ]]; then MINIMUM_SYSTEM_VERSION="$(sw_vers -productVersion | cut -d. -f-2)" fi -case ${PROC_BIT_DEPTH} in - 64) arch=x86_64;; - 32) arch=i386;; -esac +arch=x86_64 cat <<__EOS__ PROJECT_NAME: ${PROJECT_NAME} @@ -92,6 +104,33 @@ GTK_PREFIX: ${GTK_PREFIX} PWD: ${PWD} __EOS__ +minimum_macos_version=${MINIMUM_SYSTEM_VERSION} + +# Retreive cached values from cmake + +#In: LOCAL_PREFIX:STRING=/opt +#Out: /opt +LOCAL_PREFIX="$(cmake .. -L -N | grep LOCAL_PREFIX)"; LOCAL_PREFIX="${LOCAL_PREFIX#*=}" + +#In: pkgcfg_lib_EXPAT_expat:FILEPATH=/opt/local/lib/libexpat.dylib +#Out: /opt/local/lib/libexpat.dylib +EXPATLIB="$(cmake .. -LA -N | grep pkgcfg_lib_EXPAT_expat)"; pkgcfg_lib_EXPAT_expat="${pkgcfg_lib_EXPAT_expat#*=}" + +#In: CODESIGNID:STRING=Developer ID Application: Doctor Who (1234567890) +#Out: Developer ID Application: Doctor Who (1234567890) +CODESIGNID="$(cmake .. -L -N | grep CODESIGNID)"; CODESIGNID="${CODESIGNID#*=}" + +#In: NOTARY:STRING=--username drwho@bbc.com --password abcd-efgh-hijk-lmno +#Out: --username drwho@bbc.com --password abcd-efgh-hijk-lmno +NOTARY="$(cmake .. -L -N | grep NOTARY)"; NOTARY="${NOTARY#*=}" + +# In: FANCY_DMG:BOOL=ON +# Out: ON +FANCY_DMG="$(cmake .. -L -N | grep FANCY_DMG)"; FANCY_DMG="${FANCY_DMG#*=}" +if [[ -n $FANCY_DMG ]]; then + echo "Fancy .dmg build is ON." +fi + APP="${PROJECT_NAME}.app" CONTENTS="${APP}/Contents" RESOURCES="${CONTENTS}/Resources" @@ -99,153 +138,184 @@ MACOS="${CONTENTS}/MacOS" LIB="${CONTENTS}/Frameworks" ETC="${RESOURCES}/etc" EXECUTABLE="${MACOS}/rawtherapee" -GDK_PREFIX="/usr/local/opt/gdk-pixbuf" +GDK_PREFIX="${LOCAL_PREFIX}/local/" msg "Removing old files:" -rm -rf "${APP}" "${PROJECT_NAME}_*.dmg" "*zip" +rm -rf "${APP}" *.dmg *.zip msg "Creating bundle container:" -install -d "${RESOURCES}" \ - "${MACOS}" \ - "${LIB}" \ - "${ETC}" +install -d "${RESOURCES}" +install -d "${MACOS}" +install -d "${LIB}" +install -d "${ETC}" -msg "Copying release files:" +msg "Copying binary executable files." ditto "${CMAKE_BUILD_TYPE}/MacOS" "${MACOS}" -ditto "Resources" "${RESOURCES}" -msg "Copying dependencies from ${GTK_PREFIX}:" -CheckLink "${EXECUTABLE}" +msg "Copying Resources directory." +cp AboutThisBuild.txt "${RESOURCES}" +ditto "${CMAKE_BUILD_TYPE}/Resources" "${RESOURCES}" -msg "Copying library modules from ${GTK_PREFIX}:" -ditto --arch "${arch}" {"${GDK_PREFIX}/lib","${LIB}"}/gdk-pixbuf-2.0 -ditto --arch "${arch}" {"${GTK_PREFIX}/lib","${LIB}"}/gtk-3.0 - -msg "Removing static libraries and cache files:" -find -E "${LIB}" -type f -regex '.*\.(a|la|cache)$' | while read -r; do rm "${REPLY}"; done - -msg "Copying configuration files from ${GTK_PREFIX}:" -install -d "${ETC}/gtk-3.0" - -# Make Frameworks folder flat -mv "${LIB}"/gdk-pixbuf-2.0/2*/loaders/*.so "${LIB}" -mv "${LIB}"/gtk-3.0/3*/immodules/*.so "${LIB}" -# the print*.so lead to errors when running gtk-query-immodules-3.0, just seeing what the app does without, since they are not in immodules -# and including them leads to errors and a completely empty gtk.immodules file -# mv "${LIB}"/gtk-3.0/3*/printbackends/*.so "${LIB}" -rm -r "${LIB}"/gtk-3.0 -rm -r "${LIB}"/gdk-pixbuf-2.0 - -"${GDK_PREFIX}"/bin/gdk-pixbuf-query-loaders "${LIB}"/libpix*.so > "${ETC}"/gtk-3.0/gdk-pixbuf.loaders -"${GTK_PREFIX}"/bin/gtk-query-immodules-3.0 "${LIB}"/im*.so > "${ETC}"/gtk-3.0/gtk.immodules -sed -i "" -e "s|${PWD}/RawTherapee.app/Contents/|/Applications/RawTherapee.app/Contents/|" "${ETC}/gtk-3.0/gdk-pixbuf.loaders" "${ETC}/gtk-3.0/gtk.immodules" - -mkdir -p ${RESOURCES}/share/glib-2.0 -cp -pRL {"/usr/local","${RESOURCES}"}/share/glib-2.0/schemas -"/usr/local/bin/glib-compile-schemas" "${RESOURCES}/share/glib-2.0/schemas" - -msg "Copying shared files from ${GTK_PREFIX}:" -cp -pRL {"/usr/local","${RESOURCES}"}/share/mime - -# GTK3 themes -ditto {"/usr/local","${RESOURCES}"}/share/themes/Mac/gtk-3.0/gtk-keys.css -ditto {"/usr/local","${RESOURCES}"}/share/themes/Default/gtk-3.0/gtk-keys.css -# Adwaita icons -iconfolders=("16x16/actions" "16x16/devices" "16x16/mimetypes" "16x16/places" "16x16/status" "48x48/devices") -for f in "${iconfolders[@]}"; do - mkdir -p ${RESOURCES}/share/icons/Adwaita/${f} - cp /usr/local/share/icons/Adwaita/${f}/* "${RESOURCES}"/share/icons/Adwaita/${f} -done -ditto {"/usr/local","${RESOURCES}"}/share/icons/Adwaita/index.theme -"/usr/local/bin/gtk-update-icon-cache" "${RESOURCES}/share/icons/Adwaita" - -# Copy libjpeg-turbo into the app bundle -cp /usr/local/lib/libjpeg.*.dylib "${CONTENTS}/Frameworks" - -# Copy libexpat into the app bundle (which is keg-only) -cp /usr/local/Cellar/expat/*/lib/libexpat.1.dylib "${CONTENTS}/Frameworks" - -# Copy libz into the app bundle -cp /usr/lib/libz.1.dylib "${CONTENTS}/Frameworks" - -# Copy libtiff into the app bundle -cp /usr/local/lib/libtiff.5.dylib "${CONTENTS}/Frameworks" +echo "\n--------\n" >> "${RESOURCES}/AboutThisBuild.txt" +echo "Bundle system: $(sysctl -n machdep.cpu.brand_string)" >> "${RESOURCES}/AboutThisBuild.txt" +echo "Bundle OS: $(sw_vers -productName) $(sw_vers -productVersion) $(sw_vers -buildVersion) $(uname -mrs)" >> "${RESOURCES}/AboutThisBuild.txt" +echo "Bundle date: $(date -Ru) UTC" >> "${RESOURCES}/AboutThisBuild.txt" +echo "Bundle epoch: $(date +%s)" >> "${RESOURCES}/AboutThisBuild.txt" +echo "Bundle UUID: $(uuidgen|tr 'A-Z' 'a-z')" >> "${RESOURCES}/AboutThisBuild.txt" # Copy the Lensfun database into the app bundle mkdir -p "${RESOURCES}/share/lensfun" -cp /usr/local/share/lensfun/version_2/* "${RESOURCES}/share/lensfun" +ditto ${LOCAL_PREFIX}/local/share/lensfun/version_2/* "${RESOURCES}/share/lensfun" # Copy liblensfun to Frameworks -cp /usr/local/lib/liblensfun.2.dylib "${CONTENTS}/Frameworks" +ditto ${LOCAL_PREFIX}/local/lib/liblensfun.2.dylib "${CONTENTS}/Frameworks/liblensfun.2.dylib" # Copy libomp to Frameworks -cp /usr/local/lib/libomp.dylib "${CONTENTS}/Frameworks" +ditto ${LOCAL_PREFIX}/local/lib/libomp.dylib "${CONTENTS}/Frameworks" + +msg "Copying dependencies from ${GTK_PREFIX}." +CheckLink "${EXECUTABLE}" + +# dylib install names +ModifyInstallNames + +# Copy libjpeg-turbo ("62") into the app bundle +ditto ${LOCAL_PREFIX}/local/lib/libjpeg.62.dylib "${CONTENTS}/Frameworks/libjpeg.62.dylib" + +# Copy libexpat into the app bundle (which is keg-only) +if [[ -d /usr/local/Cellar/expat ]]; then ditto /usr/local/Cellar/expat/*/lib/libexpat.1.dylib "${CONTENTS}/Frameworks"; else ditto "${EXPATLIB}" "${CONTENTS}/Frameworks/libexpat.1.dylib"; fi + +# Copy libz into the app bundle +ditto ${LOCAL_PREFIX}/local/lib/libz.1.dylib "${CONTENTS}/Frameworks" + +# Copy libpng16 to the app bundle +ditto ${LOCAL_PREFIX}/local/lib/libpng16.16.dylib "${CONTENTS}/Frameworks/libpng16.16.dylib" + +# Copy libtiff 5 into the app bundle +ditto ${LOCAL_PREFIX}/local/lib/libtiff.5.dylib "${CONTENTS}/Frameworks/libtiff.5.dylib" + +# Copy the Lensfun database into the app bundle +mkdir -p "${RESOURCES}/share/lensfun" +ditto ${LOCAL_PREFIX}/local/share/lensfun/version_2/* "${RESOURCES}/share/lensfun" + +# Copy liblensfun to Frameworks +ditto ${LOCAL_PREFIX}/local/lib/liblensfun.2.dylib "${CONTENTS}/Frameworks/liblensfun.2.dylib" + +# Copy libomp to Frameworks +ditto ${LOCAL_PREFIX}/local/lib/libomp.dylib "${CONTENTS}/Frameworks" + +# Prepare GTK+3 installation +msg "Copying configuration files from ${GTK_PREFIX}:" +install -d "${ETC}/gtk-3.0" +msg "Copying library modules from ${GTK_PREFIX}:" +ditto --arch "${arch}" {"${GTK_PREFIX}/lib","${LIB}"}/gdk-pixbuf-2.0 +ditto --arch "${arch}" {"${GTK_PREFIX}/lib","${LIB}"}/gtk-3.0 +msg "Removing static libraries and cache files:" +find -E "${LIB}" -type f -regex '.*\.(a|la|cache)$' | while read -r; do rm "${REPLY}"; done + +# Make Frameworks folder flat +msg "Flattening the Frameworks folder" +ditto "${LIB}"/gdk-pixbuf-2.0/2*/loaders/*.so "${LIB}" +ditto "${LIB}"/gtk-3.0/3*/immodules/*.{dylib,so} "${LIB}" +rm -r "${LIB}"/gtk-3.0 +rm -r "${LIB}"/gdk-pixbuf-2.0 + +# GTK+3 themes +msg "Copy GTK+3 theme and icon resources:" +ditto {"${LOCAL_PREFIX}/local","${RESOURCES}"}/share/themes/Mac/gtk-3.0/gtk-keys.css +ditto {"${LOCAL_PREFIX}/local","${RESOURCES}"}/share/themes/Default/gtk-3.0/gtk-keys.css + +# Adwaita icons +msg "Copy Adwaita icons" +iconfolders=("16x16/actions" "16x16/devices" "16x16/mimetypes" "16x16/places" "16x16/status" "48x48/devices") +for f in "${iconfolders[@]}"; do + mkdir -p ${RESOURCES}/share/icons/Adwaita/${f} + ditto ${LOCAL_PREFIX}/local/share/icons/Adwaita/${f}/* "${RESOURCES}"/share/icons/Adwaita/${f} +done +ditto {"${LOCAL_PREFIX}/local","${RESOURCES}"}/share/icons/Adwaita/index.theme +"${LOCAL_PREFIX}/local/bin/gtk-update-icon-cache" "${RESOURCES}/share/icons/Adwaita" +ditto "${LOCAL_PREFIX}/local/share/icons/hicolor" "${RESOURCES}/share/icons/hicolor" + +# pixbuf loaders & immodules +msg "Build GTK3 databases:" +"${LOCAL_PREFIX}"/local/bin/gdk-pixbuf-query-loaders "${LIB}"/libpix*.so > "${ETC}"/gtk-3.0/gdk-pixbuf.loaders +"${LOCAL_PREFIX}"/local/bin/gtk-query-immodules-3.0 "${LIB}"/im-* > "${ETC}"/gtk-3.0/gtk.immodules +sed -i "" -e "s|${PWD}/RawTherapee.app/Contents/|/Applications/RawTherapee.app/Contents/|" "${ETC}/gtk-3.0/gdk-pixbuf.loaders" "${ETC}/gtk-3.0/gtk.immodules" +sed -i "" -e "s|/opt/local/|/Applications/RawTherapee.app/Contents/Frameworks/|" "${ETC}/gtk-3.0/gtk.immodules" # Install names -find -E "${CONTENTS}" -type f -regex '.*/(rawtherapee-cli|rawtherapee|.*\.(dylib|so))' | while read -r x; do - msg "Modifying install names: ${x}" - { - # id - case ${x} in *.dylib) echo " install_name_tool -id '@rpath/$(basename "${x}")' '${x}'";; esac - # names - GetDependencies "${x}" | while read -r y; do - echo " install_name_tool -change '${y}' '@rpath/$(basename "${y}")' '${x}'" - done - } | bash -v -done +ModifyInstallNames -msg "Registering @loader_path into the executable:" -echo " install_name_tool -add_rpath @executable_path/../../Frameworks '${EXECUTABLE}'" | bash -v -echo " install_name_tool -add_rpath @loader_path/../Frameworks '${EXECUTABLE}-cli'" | bash -v +# Mime directory +msg "Copying shared files from ${GTK_PREFIX}:" +ditto {"${LOCAL_PREFIX}/local","${RESOURCES}"}/share/mime msg "Installing required application bundle files:" PROJECT_SOURCE_DATA_DIR="${PROJECT_SOURCE_DIR}/tools/osx" -ditto "${PROJECT_SOURCE_DIR}/build/Resources" "${RESOURCES}" -# Executable loader -# Note: executable is renamed to 'rawtherapee-bin'. -mkdir "${MACOS}/bin" -mv "${MACOS}/rawtherapee" "${MACOS}/bin/rawtherapee-bin" -install -m 0755 "${PROJECT_SOURCE_DATA_DIR}/executable_loader.in" "${MACOS}/rawtherapee" +ditto "${CMAKE_BUILD_TYPE}/Resources" "${RESOURCES}" +ditto "${PROJECT_SOURCE_DIR}/rtdata/fonts" "${ETC}/fonts" + # App bundle resources -cp "${PROJECT_SOURCE_DATA_DIR}/"{rawtherapee,profile}.icns "${RESOURCES}" -cp "${PROJECT_SOURCE_DATA_DIR}/PkgInfo" "${CONTENTS}" +ditto "${PROJECT_SOURCE_DATA_DIR}/"{rawtherapee,profile}.icns "${RESOURCES}" +ditto "${PROJECT_SOURCE_DATA_DIR}/PkgInfo" "${CONTENTS}" install -m 0644 "${PROJECT_SOURCE_DATA_DIR}/Info.plist.in" "${CONTENTS}/Info.plist" -install -m 0644 "${PROJECT_SOURCE_DATA_DIR}/Info.plist-bin.in" "${CONTENTS}/MacOS/bin/Info.plist" sed -i "" -e "s|@version@|${PROJECT_FULL_VERSION}| s|@shortVersion@|${PROJECT_VERSION}| s|@arch@|${arch}|" \ - "${CONTENTS}/Info.plist" +"${CONTENTS}/Info.plist" plutil -convert binary1 "${CONTENTS}/Info.plist" -plutil -convert binary1 "${CONTENTS}/MacOS/bin/Info.plist" -# Sign the app -CODESIGNID="$(cmake .. -LA -N | grep "CODESIGNID" | cut -d "=" -f2)" -if ! test -z "$CODESIGNID" ; then -install -m 0644 "${PROJECT_SOURCE_DATA_DIR}/rt.entitlements" "${CONTENTS}/Entitlements.plist" -plutil -convert binary1 "${CONTENTS}/Entitlements.plist" -install -m 0644 "${PROJECT_SOURCE_DATA_DIR}/rt-bin.entitlements" "${CONTENTS}/MacOS/bin/Entitlements.plist" -plutil -convert binary1 "${CONTENTS}/MacOS/bin/Entitlements.plist" -codesign -v -s "${CODESIGNID}" -i "com.rawtherapee.rawtherapee-bin" --timestamp -o runtime --entitlements "${APP}/Contents/MacOS/bin/Entitlements.plist" "${APP}/Contents/MacOS/bin/rawtherapee-bin" -codesign --deep --preserve-metadata=identifier,entitlements,runtime --strict -v -s "${CODESIGNID}" -i "com.rawtherapee.rawtherapee" --timestamp -o runtime --entitlements "${APP}/Contents/Entitlements.plist" "${APP}" +update-mime-database -V "${RESOURCES}/share/mime" + +msg "Build glib database:" +mkdir -p ${RESOURCES}/share/glib-2.0 +ditto {"${LOCAL_PREFIX}/local","${RESOURCES}"}/share/glib-2.0/schemas +"${LOCAL_PREFIX}/local/bin/glib-compile-schemas" "${RESOURCES}/share/glib-2.0/schemas" + +# Append an LC_RPATH +msg "Registering @rpath into the main executable." +install_name_tool -add_rpath /Applications/"${LIB}" "${EXECUTABLE}" + +ModifyInstallNames + +# fix @rpath in Frameworks +msg "Registering @rpath in Frameworks folder." +for frameworklibs in "${LIB}"/*{dylib,so}; do + install_name_tool -delete_rpath ${LOCAL_PREFIX}/local/lib "${frameworklibs}" + install_name_tool -add_rpath /Applications/"${LIB}" "${frameworklibs}" +done +install_name_tool -delete_rpath RawTherapee.app/Contents/Frameworks "${EXECUTABLE}"-cli +install_name_tool -add_rpath @executable_path "${EXECUTABLE}"-cli + +# Codesign the app +if [[ -n $CODESIGNID ]]; then + msg "Codesigning Application." + install -m 0644 "${PROJECT_SOURCE_DATA_DIR}"/rt.entitlements "${CMAKE_BUILD_TYPE}"/rt.entitlements + plutil -convert binary1 "${CMAKE_BUILD_TYPE}"/rt.entitlements + mv "${EXECUTABLE}"-cli "${LIB}" + for frameworklibs in "${LIB}"/*; do + codesign -v -s "${CODESIGNID}" -i com.rawtherapee.RawTherapee --force --verbose -o runtime --timestamp "${frameworklibs}" + done + codesign --timestamp --strict -v -s "${CODESIGNID}" -i com.rawtherapee.RawTherapee -o runtime --entitlements "${CMAKE_BUILD_TYPE}"/rt.entitlements "${APP}" spctl -a -vvvv "${APP}" fi # Notarize the app -NOTARY="$(cmake .. -LA -N | grep "NOTARY" | cut -d "=" -f2)" -if ! test -z "$NOTARY" ; then +if [[ -n $NOTARY ]]; then + msg "Notarizing the application:" ditto -c -k --sequesterRsrc --keepParent "${APP}" "${APP}.zip" - uuid=`xcrun altool --notarize-app --primary-bundle-id "com.rawtherapee.rawtherapee" ${NOTARY} --file "${APP}.zip" 2>&1 | grep 'RequestUUID' | awk '{ print $3 }'` + uuid=`xcrun altool --notarize-app --primary-bundle-id "com.rawtherapee.RawTherapee" ${NOTARY} --file "${APP}.zip" 2>&1 | grep 'RequestUUID' | awk '{ print $3 }'` echo "Result= $uuid" # Display identifier string sleep 15 while : - do + do fullstatus=`xcrun altool --notarization-info "$uuid" ${NOTARY} 2>&1` # get the status status1=`echo "$fullstatus" | grep 'Status\:' | awk '{ print $2 }'` - if [ "$status1" = "success" ]; then + if [[ $status1 = "success" ]]; then xcrun stapler staple *app # staple the ticket xcrun stapler validate -v *app echo "Notarization success" break - elif [ "$status1" = "in" ]; then + elif [[ $status1 = "in" ]]; then echo "Notarization still in progress, sleeping for 15 seconds and trying again" sleep 15 else @@ -258,37 +328,56 @@ fi function CreateDmg { local srcDir="$(mktemp -dt $$)" - + msg "Preparing disk image sources at ${srcDir}:" cp -R "${APP}" "${srcDir}" - cp AboutThisBuild.txt "${srcDir}" + cp "${RESOURCES}"/share/LICENSE.txt "${srcDir}" ln -s /Applications "${srcDir}" - + # Web bookmarks function CreateWebloc { defaults write "${srcDir}/$1" URL "$2" mv "${srcDir}/$1".{plist,webloc} } - CreateWebloc 'Website' 'http://www.rawtherapee.com/' - CreateWebloc 'Manual' 'http://rawpedia.rawtherapee.com/' - + CreateWebloc 'Website' 'https://www.rawtherapee.com/' + CreateWebloc 'Documentation' 'https://rawpedia.rawtherapee.com/' + CreateWebloc 'Forum' 'https://discuss.pixls.us/c/software/rawtherapee' + CreateWebloc 'Report Bug' 'https://github.com/Beep6581/RawTherapee/issues/new' + # Disk image name dmg_name="${PROJECT_NAME// /_}_OSX_${MINIMUM_SYSTEM_VERSION}_${PROC_BIT_DEPTH}_${PROJECT_FULL_VERSION}" lower_build_type="$(tr '[:upper:]' '[:lower:]' <<< "$CMAKE_BUILD_TYPE")" - if [[ ${lower_build_type} != release ]]; then + if [[ $lower_build_type != release ]]; then dmg_name="${dmg_name}_${lower_build_type}" fi - + msg "Creating disk image:" - hdiutil create -format UDBZ -fs HFS+ -srcdir "${srcDir}" -volname "${PROJECT_NAME}_${PROJECT_FULL_VERSION}" "${dmg_name}.dmg" - + if [[ ! -z $FANCY_DMG ]]; then + echo "Building Fancy .dmg" + mkdir "${srcDir}/.background" + cp -R "${PROJECT_SOURCE_DATA_DIR}/rtdmg.icns" "${srcDir}/.VolumeIcon.icns" + cp -R "${PROJECT_SOURCE_DATA_DIR}/rtdmg-bkgd.png" "${srcDir}/.background/background.png" + SetFile -c incC "${srcDir}/.VolumeIcon.icns" + create-dmg "${dmg_name}.dmg" "${srcDir}" \ + --volname "${PROJECT_NAME}_${PROJECT_FULL_VERSION}" \ + --volicon "${srcDir}/.VolumeIcon.icns" \ + --sandbox-safe \ + --no-internet-enable \ + --eula LICENSE.txt \ + --hdiutil-verbose \ + --rez /Library/Developer/CommandLineTools/usr/bin/Rez + else + hdiutil create -format UDBZ -fs HFS+ -srcdir "${srcDir}" -volname "${PROJECT_NAME}_${PROJECT_FULL_VERSION}" "${dmg_name}.dmg" + fi + # Sign disk image - if ! test -z "$CODESIGNID" ; then - codesign --deep --force -v -s "${CODESIGNID}" --timestamp "${dmg_name}.dmg" - fi - + if [[ -n $CODESIGNID ]]; then + codesign --deep --force -v -s "${CODESIGNID}" --timestamp "${dmg_name}.dmg" + fi + # Notarize the dmg - if ! test -z "$NOTARY" ; then + if ! test -z "$NOTARY"; then + msg "Notarizing the dmg:" zip "${dmg_name}.dmg.zip" "${dmg_name}.dmg" uuid=`xcrun altool --notarize-app --primary-bundle-id "com.rawtherapee" ${NOTARY} --file "${dmg_name}.dmg.zip" 2>&1 | grep 'RequestUUID' | awk '{ print $3 }'` echo "dmg Result= $uuid" # Display identifier string @@ -297,28 +386,31 @@ function CreateDmg { do fullstatus=`xcrun altool --notarization-info "$uuid" ${NOTARY} 2>&1` # get the status status1=`echo "$fullstatus" | grep 'Status\:' | awk '{ print $2 }'` - if [ "$status1" = "success" ]; then + if [[ $status1 = "success" ]]; then xcrun stapler staple "${dmg_name}.dmg" # staple the ticket xcrun stapler validate -v "${dmg_name}.dmg" echo "dmg Notarization success" break - elif [ "$status1" = "in" ]; then + elif [[ $status1 = "in" ]]; then echo "dmg Notarization still in progress, sleeping for 15 seconds and trying again" sleep 15 else echo "dmg Notarization failed fullstatus below" echo "$fullstatus" - exit 1 + exit 1 fi done fi - - + # Zip disk image for redistribution - zip "${dmg_name}.zip" "${dmg_name}.dmg" AboutThisBuild.txt + msg "Zipping disk image for redistribution:" + zip "${dmg_name}.zip" "${dmg_name}.dmg" rm "${dmg_name}.dmg" - msg "Removing disk image caches:" rm -rf "${srcDir}" } CreateDmg +msg "Finishing build:" +echo "Script complete." +# +# TODO filter out the benign errors diff --git a/tools/osx/rt-bin.entitlements b/tools/osx/rt-bin.entitlements deleted file mode 100644 index 9e5e269cb..000000000 --- a/tools/osx/rt-bin.entitlements +++ /dev/null @@ -1,8 +0,0 @@ - - - - -com.apple.security.inherit - - - \ No newline at end of file diff --git a/tools/osx/rt.entitlements b/tools/osx/rt.entitlements index 082661401..c571f1f41 100644 --- a/tools/osx/rt.entitlements +++ b/tools/osx/rt.entitlements @@ -1,20 +1,19 @@ - application-identifier - com.rawtherapee.rawtherapee + com.rawtherapee.RawTherapee com.apple.security.temporary-exception.files.absolute-path.read-write - "/" + / com.apple.security.cs.allow-dyld-environment-variables - + com.apple.security.files.user-selected.read-write - + com.apple.security.app-sandbox - + com.apple.security.files.downloads.read-write - + - + \ No newline at end of file diff --git a/tools/osx/rtdmg-bkgd.png b/tools/osx/rtdmg-bkgd.png new file mode 100644 index 000000000..ecd9b9d42 Binary files /dev/null and b/tools/osx/rtdmg-bkgd.png differ diff --git a/tools/osx/rtdmg.icns b/tools/osx/rtdmg.icns new file mode 100644 index 000000000..31b53c8ab Binary files /dev/null and b/tools/osx/rtdmg.icns differ