From de963c54dedea70f8cd68052a97aadda1a9afdf8 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Sat, 27 Jul 2019 17:39:16 +0200 Subject: [PATCH 01/15] Further speedups for filebrowser/catalog --- rtgui/browserfilter.cc | 10 ++-- rtgui/browserfilter.h | 6 +- rtgui/filebrowser.cc | 66 +++++++------------- rtgui/filebrowser.h | 2 +- rtgui/filecatalog.cc | 30 +++++++--- rtgui/thumbbrowserbase.cc | 123 ++++++++++++++++++++++++++++++++------ rtgui/thumbbrowserbase.h | 7 ++- 7 files changed, 159 insertions(+), 85 deletions(-) diff --git a/rtgui/browserfilter.cc b/rtgui/browserfilter.cc index ab4c843a4..cd3af072e 100644 --- a/rtgui/browserfilter.cc +++ b/rtgui/browserfilter.cc @@ -19,11 +19,11 @@ #include "browserfilter.h" BrowserFilter::BrowserFilter () : - showTrash (true), - showNotTrash (true), - showOriginal (false), - multiselect (false), - exifFilterEnabled (false) + showTrash(true), + showNotTrash(true), + showOriginal(false), + exifFilterEnabled(false), + matchEqual(true) { for (int i = 0; i < 6; i++) { showRanked[i] = true; diff --git a/rtgui/browserfilter.h b/rtgui/browserfilter.h index 8880a364d..ac9818ce5 100644 --- a/rtgui/browserfilter.h +++ b/rtgui/browserfilter.h @@ -33,13 +33,11 @@ public: bool showOriginal; bool showEdited[2]; bool showRecentlySaved[2]; - bool multiselect; - - Glib::ustring queryString; - Glib::ustring queryFileName; bool exifFilterEnabled; + bool matchEqual; ExifFilterSettings exifFilter; + std::vector vFilterStrings; BrowserFilter (); }; diff --git a/rtgui/filebrowser.cc b/rtgui/filebrowser.cc index cc215e70a..7a32cd6b7 100644 --- a/rtgui/filebrowser.cc +++ b/rtgui/filebrowser.cc @@ -18,6 +18,7 @@ * You should have received a copy of the GNU General Public License * along with RawTherapee. If not, see . */ +#include #include #include @@ -622,7 +623,7 @@ void FileBrowser::addEntry_ (FileBrowserEntry* entry) initEntry(entry); } - redraw(false); + redraw(entry); } FileBrowserEntry* FileBrowser::delEntry (const Glib::ustring& fname) @@ -1461,12 +1462,12 @@ void FileBrowser::applyFilter (const BrowserFilter& filter) redraw (); } -bool FileBrowser::checkFilter (ThumbBrowserEntryBase* entryb) // true -> entry complies filter +bool FileBrowser::checkFilter (ThumbBrowserEntryBase* entryb) const // true -> entry complies filter { FileBrowserEntry* entry = static_cast(entryb); - if (filter.showOriginal && entry->getOriginal() != nullptr) { + if (filter.showOriginal && entry->getOriginal()) { return false; } @@ -1485,44 +1486,22 @@ bool FileBrowser::checkFilter (ThumbBrowserEntryBase* entryb) // true -> entry return false; } - // return false is query is not satisfied - if (!filter.queryFileName.empty()) { + // return false if query is not satisfied + if (!filter.vFilterStrings.empty()) { // check if image's FileName contains queryFileName (case insensitive) // TODO should we provide case-sensitive search option via preferences? - Glib::ustring FileName; - FileName = Glib::path_get_basename (entry->thumbnail->getFileName()); - FileName = FileName.uppercase(); - //printf("FileBrowser::checkFilter FileName = '%s'; find() result= %i \n",FileName.c_str(), FileName.find(filter.queryFileName.uppercase())); - - Glib::ustring decodedQueryFileName; - bool MatchEqual; - - // Determine the match mode - check if the first 2 characters are equal to "!=" - if (filter.queryFileName.find("!=") == 0) { - decodedQueryFileName = filter.queryFileName.substr (2, filter.queryFileName.length() - 2); - MatchEqual = false; - } else { - decodedQueryFileName = filter.queryFileName; - MatchEqual = true; - } - - // Consider that queryFileName consist of comma separated values (FilterString) - // Evaluate if ANY of these FilterString are contained in the filename - // This will construct OR filter within the filter.queryFileName + std::string FileName = Glib::path_get_basename(entry->thumbnail->getFileName()); + std::transform(FileName.begin(), FileName.end(), FileName.begin(), ::toupper); int iFilenameMatch = 0; - std::vector vFilterStrings = Glib::Regex::split_simple(",", decodedQueryFileName.uppercase()); - for(size_t i = 0; i < vFilterStrings.size(); i++) { - // ignore empty vFilterStrings. Otherwise filter will always return true if - // e.g. filter.queryFileName ends on "," and will stop being a filter - if (!vFilterStrings.at(i).empty()) { - if (FileName.find(vFilterStrings.at(i)) != Glib::ustring::npos) { - iFilenameMatch++; - } + for (const auto& entry : filter.vFilterStrings) { + if (FileName.find(entry) != std::string::npos) { + iFilenameMatch++; + break; } } - if (MatchEqual) { + if (filter.matchEqual) { if (iFilenameMatch == 0) { //none of the vFilterStrings found in FileName return false; } @@ -1531,10 +1510,10 @@ bool FileBrowser::checkFilter (ThumbBrowserEntryBase* entryb) // true -> entry return false; } } + } - /*experimental Regex support, this is unlikely to be useful to photographers*/ - //bool matchfound=Glib::Regex::match_simple(filter.queryFileName.uppercase(),FileName); - //if (!matchfound) return false; + if (!filter.exifFilterEnabled) { + return true; } // check exif filter @@ -1542,17 +1521,12 @@ bool FileBrowser::checkFilter (ThumbBrowserEntryBase* entryb) // true -> entry double tol = 0.01; double tol2 = 1e-8; - if (!filter.exifFilterEnabled) { - return true; - } - - Glib::ustring camera(cfs->getCamera()); - - if (!cfs->exifValid) - return (!filter.exifFilter.filterCamera || filter.exifFilter.cameras.count(camera) > 0) + if (!cfs->exifValid) { + return (!filter.exifFilter.filterCamera || filter.exifFilter.cameras.count(cfs->getCamera()) > 0) && (!filter.exifFilter.filterLens || filter.exifFilter.lenses.count(cfs->lens) > 0) && (!filter.exifFilter.filterFiletype || filter.exifFilter.filetypes.count(cfs->filetype) > 0) && (!filter.exifFilter.filterExpComp || filter.exifFilter.expcomp.count(cfs->expcomp) > 0); + } return (!filter.exifFilter.filterShutter || (rtengine::FramesMetaData::shutterFromString(rtengine::FramesMetaData::shutterToString(cfs->shutter)) >= filter.exifFilter.shutterFrom - tol2 && rtengine::FramesMetaData::shutterFromString(rtengine::FramesMetaData::shutterToString(cfs->shutter)) <= filter.exifFilter.shutterTo + tol2)) @@ -1560,7 +1534,7 @@ bool FileBrowser::checkFilter (ThumbBrowserEntryBase* entryb) // true -> entry && (!filter.exifFilter.filterFocalLen || (cfs->focalLen >= filter.exifFilter.focalFrom - tol && cfs->focalLen <= filter.exifFilter.focalTo + tol)) && (!filter.exifFilter.filterISO || (cfs->iso >= filter.exifFilter.isoFrom && cfs->iso <= filter.exifFilter.isoTo)) && (!filter.exifFilter.filterExpComp || filter.exifFilter.expcomp.count(cfs->expcomp) > 0) - && (!filter.exifFilter.filterCamera || filter.exifFilter.cameras.count(camera) > 0) + && (!filter.exifFilter.filterCamera || filter.exifFilter.cameras.count(cfs->getCamera()) > 0) && (!filter.exifFilter.filterLens || filter.exifFilter.lenses.count(cfs->lens) > 0) && (!filter.exifFilter.filterFiletype || filter.exifFilter.filetypes.count(cfs->filetype) > 0); } diff --git a/rtgui/filebrowser.h b/rtgui/filebrowser.h index b208a854d..cef99e08c 100644 --- a/rtgui/filebrowser.h +++ b/rtgui/filebrowser.h @@ -168,7 +168,7 @@ public: void buttonPressed (LWButton* button, int actionCode, void* actionData) override; void redrawNeeded (LWButton* button) override; - bool checkFilter (ThumbBrowserEntryBase* entry) override; + bool checkFilter (ThumbBrowserEntryBase* entry) const override; void rightClicked (ThumbBrowserEntryBase* entry) override; void doubleClicked (ThumbBrowserEntryBase* entry) override; bool keyPressed (GdkEventKey* event) override; diff --git a/rtgui/filecatalog.cc b/rtgui/filecatalog.cc index dbe540cb4..7c14873a2 100644 --- a/rtgui/filecatalog.cc +++ b/rtgui/filecatalog.cc @@ -1603,7 +1603,6 @@ BrowserFilter FileCatalog::getFilter () anyRankFilterActive || anyCLabelFilterActive || anyEditedFilterActive; } - filter.multiselect = false; /* * Step 2 @@ -1619,7 +1618,6 @@ BrowserFilter FileCatalog::getFilter () (anyEditedFilterActive && anyRecentlySavedFilterActive) || (anySupplementaryActive && (anyRankFilterActive || anyCLabelFilterActive || anyEditedFilterActive || anyRecentlySavedFilterActive))) { - filter.multiselect = true; filter.showRanked[0] = anyRankFilterActive ? bUnRanked->get_active () : true; filter.showCLabeled[0] = anyCLabelFilterActive ? bUnCLabeled->get_active () : true; @@ -1656,14 +1654,28 @@ BrowserFilter FileCatalog::getFilter () //TODO could use date:;iso: etc // default will be filename - /* // this is for safe execution if getFilter is called before Query object is instantiated - Glib::ustring tempQuery; - tempQuery=""; - if (Query) tempQuery = Query->get_text(); - */ - filter.queryString = Query->get_text(); // full query string from Query Entry - filter.queryFileName = Query->get_text(); // for now Query is only by file name + Glib::ustring decodedQueryFileName = Query->get_text(); // for now Query is only by file name + // Determine the match mode - check if the first 2 characters are equal to "!=" + if (decodedQueryFileName.find("!=") == 0) { + decodedQueryFileName = decodedQueryFileName.substr(2); + filter.matchEqual = false; + } else { + filter.matchEqual = true; + } + + // Consider that queryFileName consist of comma separated values (FilterString) + // Evaluate if ANY of these FilterString are contained in the filename + // This will construct OR filter within the queryFileName + filter.vFilterStrings.clear(); + const std::vector filterStrings = Glib::Regex::split_simple(",", decodedQueryFileName.uppercase()); + for (const auto& entry : filterStrings) { + // ignore empty filterStrings. Otherwise filter will always return true if + // e.g. queryFileName ends on "," and will stop being a filter + if (!entry.empty()) { + filter.vFilterStrings.push_back(entry); + } + } return filter; } diff --git a/rtgui/thumbbrowserbase.cc b/rtgui/thumbbrowserbase.cc index dba5390c1..a67eb7eec 100644 --- a/rtgui/thumbbrowserbase.cc +++ b/rtgui/thumbbrowserbase.cc @@ -28,7 +28,7 @@ using namespace std; ThumbBrowserBase::ThumbBrowserBase () - : location(THLOC_FILEBROWSER), inspector(nullptr), isInspectorActive(false), eventTime(0), lastClicked(nullptr), previewHeight(options.thumbSize), numOfCols(1), arrangement(TB_Horizontal) + : location(THLOC_FILEBROWSER), inspector(nullptr), isInspectorActive(false), eventTime(0), lastClicked(nullptr), previewHeight(options.thumbSize), numOfCols(1), lastRowHeight(0), arrangement(TB_Horizontal) { inW = -1; inH = -1; @@ -44,6 +44,8 @@ ThumbBrowserBase::ThumbBrowserBase () show_all (); + vscroll.get_adjustment()->set_lower(0); + hscroll.get_adjustment()->set_lower(0); vscroll.signal_value_changed().connect( sigc::mem_fun(*this, &ThumbBrowserBase::scrollChanged) ); hscroll.signal_value_changed().connect( sigc::mem_fun(*this, &ThumbBrowserBase::scrollChanged) ); @@ -543,7 +545,6 @@ void ThumbBrowserBase::configScrollBars () auto ha = hscroll.get_adjustment(); int iw = internal.get_width(); ha->set_upper(inW); - ha->set_lower(0); ha->set_step_increment(!fd.empty() ? fd[0]->getEffectiveWidth() : 0); ha->set_page_increment(iw); ha->set_page_size(iw); @@ -558,7 +559,6 @@ void ThumbBrowserBase::configScrollBars () auto va = vscroll.get_adjustment(); va->set_upper(inH); - va->set_lower(0); const auto height = !fd.empty() ? fd[0]->getEffectiveHeight() : 0; va->set_step_increment(height); va->set_page_increment(height == 0 ? ih : (ih / height) * height); @@ -572,8 +572,22 @@ void ThumbBrowserBase::configScrollBars () } } -void ThumbBrowserBase::arrangeFiles(bool checkfilter) +void ThumbBrowserBase::arrangeFiles(ThumbBrowserEntryBase* entry) { + + if (fd.empty()) { + // nothing to arrange + resizeThumbnailArea(0, 0); + return; + } + if(entry && entry->filtered) { + // a filtered entry was added, nothing to arrange, but has to be marked not drawable + MYREADERLOCK(l, entryRW); + entry->drawable = false; + MYREADERLOCK_RELEASE(l); + return; + } + MYREADERLOCK(l, entryRW); // GUI already locked by ::redraw, the only caller of this method for now. @@ -581,17 +595,22 @@ void ThumbBrowserBase::arrangeFiles(bool checkfilter) //GThreadLock lock; int rowHeight = 0; - for (const auto entry : fd) { - if (checkfilter) { - // apply filter - entry->filtered = !checkFilter(entry); - } + if (entry) { + // we got the reference to the added entry, makes calculation of rowHeight O(1) + lastRowHeight = rowHeight = std::max(lastRowHeight, entry->getMinimalHeight()); + } else { - // compute size of the items - if (!entry->filtered) { - rowHeight = std::max(entry->getMinimalHeight(), rowHeight); + lastRowHeight = 0; + for (const auto thumb : fd) { + // apply filter + thumb->filtered = !checkFilter(thumb); + // compute max rowHeight + if (!thumb->filtered) { + rowHeight = std::max(thumb->getMinimalHeight(), rowHeight); + } } } + if (arrangement == TB_Horizontal) { numOfCols = 1; @@ -622,14 +641,16 @@ void ThumbBrowserBase::arrangeFiles(bool checkfilter) const int availWidth = internal.get_width(); // initial number of columns + int oldNumOfCols = numOfCols; numOfCols = 0; int colsWidth = 0; for (unsigned int i = 0; i < fd.size(); ++i) { if (!fd[i]->filtered && colsWidth + fd[i]->getMinimalWidth() <= availWidth) { - colsWidth += fd[numOfCols]->getMinimalWidth(); + colsWidth += fd[i]->getMinimalWidth(); ++numOfCols; if(colsWidth > availWidth) { + --numOfCols; break; } } @@ -640,6 +661,7 @@ void ThumbBrowserBase::arrangeFiles(bool checkfilter) } std::vector colWidths; + std::vector oldColWidths; for (; numOfCols > 0; --numOfCols) { // compute column widths @@ -663,10 +685,77 @@ void ThumbBrowserBase::arrangeFiles(bool checkfilter) } } + if (oldNumOfCols == numOfCols) { + int oldColsWidth = 0; + for (; oldNumOfCols > 0; --oldNumOfCols) { + // compute old column widths + oldColWidths.assign(oldNumOfCols, 0); + + for (unsigned int i = 0, j = 0; i < fd.size(); ++i) { + if (fd[i] != entry && !fd[i]->filtered && fd[i]->getMinimalWidth() > oldColWidths[j % oldNumOfCols]) { + oldColWidths[j % oldNumOfCols] = fd[i]->getMinimalWidth(); + } + + if (fd[i] != entry && !fd[i]->filtered) { + ++j; + } + } + // if not wider than the space available, arrange it and we are ready + oldColsWidth = std::accumulate(oldColWidths.begin(), oldColWidths.end(), 0); + + if (oldNumOfCols == 1 || oldColsWidth < availWidth) { + break; + } + } + } + + bool arrangeAll = true; + if (entry && oldNumOfCols == numOfCols && oldColWidths.size() > 0) { + arrangeAll = false; + for (int i = 0; i < numOfCols; ++i) { + if(colWidths[i] != oldColWidths[i]) { + arrangeAll = true; + break; + } + } + } + // arrange files int curry = 0; + size_t ct = 0; + if (entry && !arrangeAll) { + int i = 0; + // Find currently added entry + for (; ct < fd.size() && fd[ct] != entry; i += !fd[ct]->filtered, ++ct) { + } + //Calculate the position of currently added entry + const int row = i / numOfCols; + const int col = i % numOfCols; + curry = row * rowHeight; + int currx = 0; + for (int c = 0; c < col; ++c) { + currx += colWidths[c]; + } + // arrange all entries in the row beginning with the currently added one + for (int i = col; ct < fd.size() && i < numOfCols; ++i, ++ct) { + for (; ct < fd.size() && fd[ct]->filtered; ++ct) { + fd[ct]->drawable = false; + } + if (ct < fd.size()) { + fd[ct]->setPosition(currx, curry, colWidths[i], rowHeight); + fd[ct]->drawable = true; + currx += colWidths[i]; + } + } + + if (currx > 0) { // there were thumbnails placed in the row + curry += rowHeight; + } + } + + // arrange remaining entries, if any, that's the most expensive part + for (; ct < fd.size();) { - for (unsigned int ct = 0; ct < fd.size();) { // arrange items in the row int currx = 0; @@ -689,7 +778,7 @@ void ThumbBrowserBase::arrangeFiles(bool checkfilter) MYREADERLOCK_RELEASE(l); // This will require a Writer access - resizeThumbnailArea (colsWidth, curry); + resizeThumbnailArea(colsWidth, curry); } } @@ -979,11 +1068,11 @@ bool ThumbBrowserBase::Internal::on_scroll_event (GdkEventScroll* event) } -void ThumbBrowserBase::redraw (bool checkfilter) +void ThumbBrowserBase::redraw (ThumbBrowserEntryBase* entry) { GThreadLock lock; - arrangeFiles(checkfilter); + arrangeFiles(entry); queue_draw(); } diff --git a/rtgui/thumbbrowserbase.h b/rtgui/thumbbrowserbase.h index ae561db43..e9e69416c 100644 --- a/rtgui/thumbbrowserbase.h +++ b/rtgui/thumbbrowserbase.h @@ -174,12 +174,13 @@ protected: int previewHeight; int numOfCols; + int lastRowHeight; Arrangement arrangement; std::set editedFiles; - void arrangeFiles (bool checkfilter = true); + void arrangeFiles (ThumbBrowserEntryBase* entry = nullptr); void zoomChanged (bool zoomIn); public: @@ -201,7 +202,7 @@ public: return fd; } void on_style_updated () override; - void redraw (bool checkfilter = true); // arrange files and draw area + void redraw (ThumbBrowserEntryBase* entry = nullptr); // arrange files and draw area void refreshThumbImages (); // refresh thumbnail sizes, re-generate thumbnail images, arrange and draw void refreshQuickThumbImages (); // refresh thumbnail sizes, re-generate thumbnail images, arrange and draw void refreshEditedState (const std::set& efiles); @@ -214,7 +215,7 @@ public: void setArrangement (Arrangement a); void enableTabMode(bool enable); // set both thumb sizes and arrangements - virtual bool checkFilter (ThumbBrowserEntryBase* entry) + virtual bool checkFilter (ThumbBrowserEntryBase* entry) const { return true; } From e748f424274579267deed21993cf8a62e8479a8e Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Sat, 27 Jul 2019 21:26:00 +0200 Subject: [PATCH 02/15] Some code cleanups --- rtgui/thumbbrowserbase.cc | 115 +++++++++++++++++++------------------- 1 file changed, 56 insertions(+), 59 deletions(-) diff --git a/rtgui/thumbbrowserbase.cc b/rtgui/thumbbrowserbase.cc index a67eb7eec..88c2c3cce 100644 --- a/rtgui/thumbbrowserbase.cc +++ b/rtgui/thumbbrowserbase.cc @@ -661,7 +661,6 @@ void ThumbBrowserBase::arrangeFiles(ThumbBrowserEntryBase* entry) } std::vector colWidths; - std::vector oldColWidths; for (; numOfCols > 0; --numOfCols) { // compute column widths @@ -685,71 +684,69 @@ void ThumbBrowserBase::arrangeFiles(ThumbBrowserEntryBase* entry) } } - if (oldNumOfCols == numOfCols) { - int oldColsWidth = 0; - for (; oldNumOfCols > 0; --oldNumOfCols) { - // compute old column widths - oldColWidths.assign(oldNumOfCols, 0); - - for (unsigned int i = 0, j = 0; i < fd.size(); ++i) { - if (fd[i] != entry && !fd[i]->filtered && fd[i]->getMinimalWidth() > oldColWidths[j % oldNumOfCols]) { - oldColWidths[j % oldNumOfCols] = fd[i]->getMinimalWidth(); - } - - if (fd[i] != entry && !fd[i]->filtered) { - ++j; - } - } - // if not wider than the space available, arrange it and we are ready - oldColsWidth = std::accumulate(oldColWidths.begin(), oldColWidths.end(), 0); - - if (oldNumOfCols == 1 || oldColsWidth < availWidth) { - break; - } - } - } - bool arrangeAll = true; - if (entry && oldNumOfCols == numOfCols && oldColWidths.size() > 0) { - arrangeAll = false; - for (int i = 0; i < numOfCols; ++i) { - if(colWidths[i] != oldColWidths[i]) { - arrangeAll = true; - break; - } - } - } - // arrange files int curry = 0; size_t ct = 0; - if (entry && !arrangeAll) { - int i = 0; - // Find currently added entry - for (; ct < fd.size() && fd[ct] != entry; i += !fd[ct]->filtered, ++ct) { - } - //Calculate the position of currently added entry - const int row = i / numOfCols; - const int col = i % numOfCols; - curry = row * rowHeight; - int currx = 0; - for (int c = 0; c < col; ++c) { - currx += colWidths[c]; - } - // arrange all entries in the row beginning with the currently added one - for (int i = col; ct < fd.size() && i < numOfCols; ++i, ++ct) { - for (; ct < fd.size() && fd[ct]->filtered; ++ct) { - fd[ct]->drawable = false; - } - if (ct < fd.size()) { - fd[ct]->setPosition(currx, curry, colWidths[i], rowHeight); - fd[ct]->drawable = true; - currx += colWidths[i]; + if (entry) { + std::vector oldColWidths; + if (oldNumOfCols == numOfCols) { + for (; oldNumOfCols > 0; --oldNumOfCols) { + // compute old column widths + oldColWidths.assign(oldNumOfCols, 0); + + for (unsigned int i = 0, j = 0; i < fd.size(); ++i) { + if (fd[i] != entry && !fd[i]->filtered && fd[i]->getMinimalWidth() > oldColWidths[j % oldNumOfCols]) { + oldColWidths[j % oldNumOfCols] = fd[i]->getMinimalWidth(); + } + + if (fd[i] != entry && !fd[i]->filtered) { + ++j; + } + } + if (oldNumOfCols == 1 || std::accumulate(oldColWidths.begin(), oldColWidths.end(), 0) < availWidth) { + break; + } } } - if (currx > 0) { // there were thumbnails placed in the row - curry += rowHeight; + if (oldNumOfCols == numOfCols) { + arrangeAll = false; + for (int i = 0; i < numOfCols; ++i) { + if(colWidths[i] != oldColWidths[i]) { + arrangeAll = true; + break; + } + } + } + if (!arrangeAll) { + int i = 0; + // Find currently added entry + for (; ct < fd.size() && fd[ct] != entry; i += !fd[ct]->filtered, ++ct) { + } + //Calculate the position of currently added entry + const int row = i / numOfCols; + const int col = i % numOfCols; + curry = row * rowHeight; + int currx = 0; + for (int c = 0; c < col; ++c) { + currx += colWidths[c]; + } + // arrange all entries in the row beginning with the currently added one + for (int i = col; ct < fd.size() && i < numOfCols; ++i, ++ct) { + for (; ct < fd.size() && fd[ct]->filtered; ++ct) { + fd[ct]->drawable = false; + } + if (ct < fd.size()) { + fd[ct]->setPosition(currx, curry, colWidths[i], rowHeight); + fd[ct]->drawable = true; + currx += colWidths[i]; + } + } + + if (currx > 0) { // there were thumbnails placed in the row + curry += rowHeight; + } } } From 4e4106b4e796707cb1e4f0e3d9c6b149de21be9e Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Mon, 29 Jul 2019 14:41:36 +0200 Subject: [PATCH 03/15] Minor cleanups --- rtgui/filebrowser.cc | 2 +- rtgui/filebrowserentry.cc | 22 +++++++++++----------- rtgui/filecatalog.cc | 16 ++++++++-------- 3 files changed, 20 insertions(+), 20 deletions(-) diff --git a/rtgui/filebrowser.cc b/rtgui/filebrowser.cc index 7a32cd6b7..4326c1666 100644 --- a/rtgui/filebrowser.cc +++ b/rtgui/filebrowser.cc @@ -1496,7 +1496,7 @@ bool FileBrowser::checkFilter (ThumbBrowserEntryBase* entryb) const // true -> for (const auto& entry : filter.vFilterStrings) { if (FileName.find(entry) != std::string::npos) { - iFilenameMatch++; + ++iFilenameMatch; break; } } diff --git a/rtgui/filebrowserentry.cc b/rtgui/filebrowserentry.cc index 4b1764824..8b518335c 100644 --- a/rtgui/filebrowserentry.cc +++ b/rtgui/filebrowserentry.cc @@ -251,32 +251,32 @@ void FileBrowserEntry::_updateImage(rtengine::IImage8* img, double s, const rten bool newLandscape = img->getWidth() > img->getHeight(); bool rotated = false; - if (preh == img->getHeight ()) { + if (preh == img->getHeight()) { + const bool resize = !preview || prew != img->getWidth(); prew = img->getWidth (); GThreadLock lock; // Check if image has been rotated since last time - rotated = preview != nullptr && newLandscape != landscape; + rotated = preview && newLandscape != landscape; - guint8* temp = preview; - preview = nullptr; - delete [] temp; - temp = new guint8 [prew * preh * 3]; - memcpy (temp, img->getData(), prew * preh * 3); - preview = temp; + if (resize) { + delete [] preview; + preview = new guint8 [prew * preh * 3]; + } + memcpy(preview, img->getData(), prew * preh * 3); updateBackBuffer (); } landscape = newLandscape; - img->free (); + img->free(); - if (parent != nullptr) { + if (parent) { if (rotated) { parent->thumbRearrangementNeeded(); } else if (redrawRequests == 0) { - parent->redrawNeeded (this); + parent->redrawNeeded(this); } } } diff --git a/rtgui/filecatalog.cc b/rtgui/filecatalog.cc index 7c14873a2..63ebc7676 100644 --- a/rtgui/filecatalog.cc +++ b/rtgui/filecatalog.cc @@ -804,28 +804,28 @@ void FileCatalog::previewsFinishedUI () { GThreadLock lock; // All GUI access from idle_add callbacks or separate thread HAVE to be protected - redrawAll (); + redrawAll(); previewsToLoad = 0; if (filterPanel) { - filterPanel->set_sensitive (true); + filterPanel->set_sensitive(true); - if ( !hasValidCurrentEFS ) { - MyMutex::MyLock lock(dirEFSMutex); + if (!hasValidCurrentEFS) { + MyMutex::MyLock myLock(dirEFSMutex); currentEFS = dirEFS; - filterPanel->setFilter ( dirEFS, true ); + filterPanel->setFilter(dirEFS, true); } else { - filterPanel->setFilter ( currentEFS, false ); + filterPanel->setFilter(currentEFS, false); } } if (exportPanel) { - exportPanel->set_sensitive (true); + exportPanel->set_sensitive(true); } // restart anything that might have been loaded low quality fileBrowser->refreshQuickThumbImages(); - fileBrowser->applyFilter (getFilter()); // refresh total image count + fileBrowser->applyFilter(getFilter()); // refresh total image count _refreshProgressBar(); } filepanel->loadingThumbs(M("PROGRESSBAR_READY"), 0); From 0ed517d972eaca5ebd712accf574c87d6815daab Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Wed, 31 Jul 2019 16:08:25 +0200 Subject: [PATCH 04/15] cppcheck: more explicit contructors --- rtengine/curves.h | 4 ++-- rtengine/imagedata.h | 2 +- rtengine/improcfun.h | 2 +- rtengine/procparams.h | 4 ++-- rtgui/curveeditorgroup.h | 2 +- rtgui/guiutils.h | 2 +- rtgui/popupcommon.h | 2 +- rtgui/rtimage.h | 10 +++++----- rtgui/rtsurface.h | 2 +- 9 files changed, 15 insertions(+), 15 deletions(-) diff --git a/rtengine/curves.h b/rtengine/curves.h index deed5d0fe..98ce68015 100644 --- a/rtengine/curves.h +++ b/rtengine/curves.h @@ -468,7 +468,7 @@ protected: void NURBS_set (); public: - DiagonalCurve (const std::vector& points, int ppn = CURVES_MIN_POLY_POINTS); + explicit DiagonalCurve (const std::vector& points, int ppn = CURVES_MIN_POLY_POINTS); ~DiagonalCurve () override; double getVal (double t) const override; @@ -493,7 +493,7 @@ private: public: - FlatCurve (const std::vector& points, bool isPeriodic = true, int ppn = CURVES_MIN_POLY_POINTS); + explicit FlatCurve (const std::vector& points, bool isPeriodic = true, int ppn = CURVES_MIN_POLY_POINTS); ~FlatCurve () override; double getVal (double t) const override; diff --git a/rtengine/imagedata.h b/rtengine/imagedata.h index d06820296..774547487 100644 --- a/rtengine/imagedata.h +++ b/rtengine/imagedata.h @@ -98,7 +98,7 @@ private: unsigned int dcrawFrameCount; public: - FramesData (const Glib::ustring& fname, std::unique_ptr rml = nullptr, bool firstFrameOnly = false); + explicit FramesData (const Glib::ustring& fname, std::unique_ptr rml = nullptr, bool firstFrameOnly = false); ~FramesData () override; void setDCRawFrameCount (unsigned int frameCount); diff --git a/rtengine/improcfun.h b/rtengine/improcfun.h index cd1650f6e..d3e6f4032 100644 --- a/rtengine/improcfun.h +++ b/rtengine/improcfun.h @@ -200,7 +200,7 @@ public: double lumimul[3]; - ImProcFunctions(const ProcParams* iparams, bool imultiThread = true) + explicit ImProcFunctions(const ProcParams* iparams, bool imultiThread = true) : monitorTransform(nullptr), params(iparams), scale(1), multiThread(imultiThread), lumimul{} {} ~ImProcFunctions(); bool needsLuminanceOnly() diff --git a/rtengine/procparams.h b/rtengine/procparams.h index 46eb530bc..369af85fa 100644 --- a/rtengine/procparams.h +++ b/rtengine/procparams.h @@ -1634,8 +1634,8 @@ class PartialProfile : { public: PartialProfile(bool createInstance = false, bool paramsEditedValue = false); - PartialProfile(ProcParams* pp, ParamsEdited* pe = nullptr, bool fullCopy = false); - PartialProfile(const ProcParams* pp, const ParamsEdited* pe = nullptr); + explicit PartialProfile(ProcParams* pp, ParamsEdited* pe = nullptr, bool fullCopy = false); + explicit PartialProfile(const ProcParams* pp, const ParamsEdited* pe = nullptr); void deleteInstance(); void clearGeneral(); int load(const Glib::ustring& fName); diff --git a/rtgui/curveeditorgroup.h b/rtgui/curveeditorgroup.h index 80a1a95a4..ae0ebee07 100644 --- a/rtgui/curveeditorgroup.h +++ b/rtgui/curveeditorgroup.h @@ -70,7 +70,7 @@ public: * dialogs. */ - CurveEditorGroup(Glib::ustring& curveDir, Glib::ustring groupLabel = ""); + explicit CurveEditorGroup(Glib::ustring& curveDir, Glib::ustring groupLabel = ""); ~CurveEditorGroup() override; void newLine(); void curveListComplete(); diff --git a/rtgui/guiutils.h b/rtgui/guiutils.h index e4c38f347..73cd27171 100644 --- a/rtgui/guiutils.h +++ b/rtgui/guiutils.h @@ -400,7 +400,7 @@ protected: void set_none(); public: - MyFileChooserButton(const Glib::ustring &title, Gtk::FileChooserAction action=Gtk::FILE_CHOOSER_ACTION_OPEN); + explicit MyFileChooserButton(const Glib::ustring &title, Gtk::FileChooserAction action=Gtk::FILE_CHOOSER_ACTION_OPEN); sigc::signal &signal_selection_changed(); sigc::signal &signal_file_set(); diff --git a/rtgui/popupcommon.h b/rtgui/popupcommon.h index f939dbe96..92d6a6214 100644 --- a/rtgui/popupcommon.h +++ b/rtgui/popupcommon.h @@ -47,7 +47,7 @@ public: type_signal_item_selected signal_item_selected(); Gtk::Grid* buttonGroup; // this is the widget to be packed - PopUpCommon (Gtk::Button* button, const Glib::ustring& label = ""); + explicit PopUpCommon (Gtk::Button* button, const Glib::ustring& label = ""); virtual ~PopUpCommon (); bool addEntry (const Glib::ustring& fileName, const Glib::ustring& label); int getEntryCount () const; diff --git a/rtgui/rtimage.h b/rtgui/rtimage.h index 5679f6edc..244d0030a 100644 --- a/rtgui/rtimage.h +++ b/rtgui/rtimage.h @@ -38,11 +38,11 @@ protected: public: RTImage (); RTImage (RTImage &other); - RTImage (Glib::RefPtr &pixbuf); - RTImage (Cairo::RefPtr &surf); - RTImage(Cairo::RefPtr other); - RTImage (Glib::RefPtr &other); - RTImage (const Glib::ustring& fileName, const Glib::ustring& rtlFileName = Glib::ustring()); + explicit RTImage (Glib::RefPtr &pixbuf); + explicit RTImage (Cairo::RefPtr &surf); + explicit RTImage(Cairo::RefPtr other); + explicit RTImage (Glib::RefPtr &other); + explicit RTImage (const Glib::ustring& fileName, const Glib::ustring& rtlFileName = Glib::ustring()); void setImage (const Glib::ustring& fileName, const Glib::ustring& rtlFileName = Glib::ustring()); void changeImage (const Glib::ustring& imageName); diff --git a/rtgui/rtsurface.h b/rtgui/rtsurface.h index c314ab1c1..b442b7493 100644 --- a/rtgui/rtsurface.h +++ b/rtgui/rtsurface.h @@ -30,7 +30,7 @@ class RTSurface : { public: RTSurface(); - RTSurface(const Glib::ustring& fileName, const Glib::ustring& rtlFileName = {}); + explicit RTSurface(const Glib::ustring& fileName, const Glib::ustring& rtlFileName = {}); void setImage(const Glib::ustring& fileName, const Glib::ustring& rtlFileName = {}); From 4101102ddf930dc24de14900b64d6a007ad01305 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Wed, 31 Jul 2019 20:02:35 +0200 Subject: [PATCH 05/15] cppcheck: further fixes --- rtengine/EdgePreservingDecomposition.cc | 33 +++++++-------- rtengine/color.cc | 39 ------------------ rtengine/color.h | 54 +++++++------------------ rtengine/imagedata.cc | 4 +- rtexif/rtexif.h | 10 ++--- rtgui/bqentryupdater.cc | 3 +- rtgui/editorpanel.cc | 2 +- rtgui/guiutils.cc | 38 +++++------------ rtgui/histogrampanel.cc | 5 --- rtgui/iccprofilecreator.cc | 26 ++++-------- rtgui/icmpanel.cc | 2 - rtgui/imagearea.cc | 5 +-- rtgui/inspector.cc | 4 -- rtgui/rtimage.cc | 4 +- rtgui/rtwindow.cc | 4 +- rtgui/splash.cc | 4 +- rtgui/thresholdselector.cc | 13 +----- rtgui/whitebalance.cc | 1 - 18 files changed, 62 insertions(+), 189 deletions(-) diff --git a/rtengine/EdgePreservingDecomposition.cc b/rtengine/EdgePreservingDecomposition.cc index 6bda5d437..85b7ce243 100644 --- a/rtengine/EdgePreservingDecomposition.cc +++ b/rtengine/EdgePreservingDecomposition.cc @@ -401,13 +401,10 @@ bool MultiDiagonalSymmetricMatrix::CreateIncompleteCholeskyFactorization(int Max //How many diagonals in the decomposition? MaxFillAbove++; //Conceptually, now "fill" includes an existing diagonal. Simpler in the math that follows. - int j, mic, fp; - mic = 1; - fp = 1; + int mic = 1; for(int ii = 1; ii < m; ii++) { - fp = rtengine::min(StartRows[ii] - StartRows[ii - 1], MaxFillAbove); //Guaranteed positive since StartRows must be created in increasing order. - mic = mic + fp; + mic += rtengine::min(StartRows[ii] - StartRows[ii - 1], MaxFillAbove); //Guaranteed positive since StartRows must be created in increasing order. } //Initialize the decomposition - setup memory, start rows, etc. @@ -421,7 +418,7 @@ bool MultiDiagonalSymmetricMatrix::CreateIncompleteCholeskyFactorization(int Max for(int ii = 1; ii < m; ii++) { //Set j to the number of diagonals to be created corresponding to a diagonal on this source matrix... - j = rtengine::min(StartRows[ii] - StartRows[ii - 1], MaxFillAbove); + int j = rtengine::min(StartRows[ii] - StartRows[ii - 1], MaxFillAbove); //...and create those diagonals. I want to take a moment to tell you about how much I love minimalistic loops: very much. while(j-- != 0) @@ -491,7 +488,7 @@ bool MultiDiagonalSymmetricMatrix::CreateIncompleteCholeskyFactorization(int Max findmap[j] = FindIndex( icStartRows[j]); } - for(j = 0; j < n; j++) { + for(int j = 0; j < n; j++) { //Calculate d for this column. d[j] = Diagonals[0][j]; @@ -557,12 +554,11 @@ void MultiDiagonalSymmetricMatrix::CholeskyBackSolve(float* RESTRICT x, float* R float* RESTRICT *d = IncompleteCholeskyFactorization->Diagonals; int* RESTRICT s = IncompleteCholeskyFactorization->StartRows; int M = IncompleteCholeskyFactorization->m, N = IncompleteCholeskyFactorization->n; - int i, j; if(M != DIAGONALSP1) { // can happen in theory - for(j = 0; j < N; j++) { + for(int j = 0; j < N; j++) { float sub = b[j]; // using local var to reduce memory writes, gave a big speedup - i = 1; + int i = 1; int c = j - s[i]; while(c >= 0) { @@ -574,9 +570,9 @@ void MultiDiagonalSymmetricMatrix::CholeskyBackSolve(float* RESTRICT x, float* R x[j] = sub; // only one memory-write per j } } else { // that's the case almost every time - for(j = 0; j <= s[M - 1]; j++) { + for(int j = 0; j <= s[M - 1]; j++) { float sub = b[j]; // using local var to reduce memory writes, gave a big speedup - i = 1; + int i = 1; int c = j - s[1]; while(c >= 0) { @@ -588,7 +584,7 @@ void MultiDiagonalSymmetricMatrix::CholeskyBackSolve(float* RESTRICT x, float* R x[j] = sub; // only one memory-write per j } - for(j = s[M - 1] + 1; j < N; j++) { + for(int j = s[M - 1] + 1; j < N; j++) { float sub = b[j]; // using local var to reduce memory writes, gave a big speedup for(int i = DIAGONALSP1 - 1; i > 0; i--) { // using a constant upperbound allows the compiler to unroll this loop (gives a good speedup) @@ -605,14 +601,15 @@ void MultiDiagonalSymmetricMatrix::CholeskyBackSolve(float* RESTRICT x, float* R #pragma omp parallel for #endif - for(j = 0; j < N; j++) { + for(int j = 0; j < N; j++) { x[j] = x[j] / d[0][j]; } if(M != DIAGONALSP1) { // can happen in theory + int j = N; while(j-- > 0) { float sub = x[j]; // using local var to reduce memory writes, gave a big speedup - i = 1; + int i = 1; int c = j + s[1]; while(c < N) { @@ -624,9 +621,9 @@ void MultiDiagonalSymmetricMatrix::CholeskyBackSolve(float* RESTRICT x, float* R x[j] = sub; // only one memory-write per j } } else { // that's the case almost every time - for(j = N - 1; j >= (N - 1) - s[M - 1]; j--) { + for(int j = N - 1; j >= (N - 1) - s[M - 1]; j--) { float sub = x[j]; // using local var to reduce memory writes, gave a big speedup - i = 1; + int i = 1; int c = j + s[1]; while(c < N) { @@ -638,7 +635,7 @@ void MultiDiagonalSymmetricMatrix::CholeskyBackSolve(float* RESTRICT x, float* R x[j] = sub; // only one memory-write per j } - for(j = (N - 2) - s[M - 1]; j >= 0; j--) { + for(int j = (N - 2) - s[M - 1]; j >= 0; j--) { float sub = x[j]; // using local var to reduce memory writes, gave a big speedup for(int i = DIAGONALSP1 - 1; i > 0; i--) { // using a constant upperbound allows the compiler to unroll this loop (gives a good speedup) diff --git a/rtengine/color.cc b/rtengine/color.cc index 3f2a75788..7c12c0ca5 100644 --- a/rtengine/color.cc +++ b/rtengine/color.cc @@ -2016,45 +2016,6 @@ void Color::Lch2Luv(float c, float h, float &u, float &v) v = c * sincosval.y; } -// NOT TESTED -void Color::XYZ2Luv (float X, float Y, float Z, float &L, float &u, float &v) -{ - - X /= 65535.f; - Y /= 65535.f; - Z /= 65535.f; - - if (Y > float(eps)) { - L = 116.f * std::cbrt(Y) - 16.f; - } else { - L = float(kappa) * Y; - } - - u = 13.f * L * float(u0); - v = 13.f * L * float(v0); -} - -// NOT TESTED -void Color::Luv2XYZ (float L, float u, float v, float &X, float &Y, float &Z) -{ - if (L > float(epskap)) { - float t = (L + 16.f) / 116.f; - Y = t * t * t; - } else { - Y = L / float(kappa); - } - - float a = ((52.f * L) / (u + 13.f * L * float(u0)) - 1.f) / 3.f; - float d = Y * (((39 * L) / (v + 13 * float(v0))) - 5.f); - float b = -5.f * Y; - X = (d - b) / (a + 1.f / 3.f); - - Z = X * a + b; - - X *= 65535.f; - Y *= 65535.f; - Z *= 65535.f; -} /* * Gamut mapping algorithm diff --git a/rtengine/color.h b/rtengine/color.h index fb4eea458..5bf178636 100644 --- a/rtengine/color.h +++ b/rtengine/color.h @@ -240,20 +240,20 @@ public: static inline void rgb2slfloat(float r, float g, float b, float &s, float &l) { - float m = min(r, g, b); - float M = max(r, g, b); - float C = M - m; + float minVal = min(r, g, b); + float maxVal = max(r, g, b); + float C = maxVal - minVal; - l = (M + m) * 7.6295109e-6f; // (0.5f / 65535.f) + l = (maxVal + minVal) * 7.6295109e-6f; // (0.5f / 65535.f) if (C < 0.65535f) { // 0.00001f * 65535.f s = 0.f; } else { if (l <= 0.5f) { - s = C / (M + m); + s = C / (maxVal + minVal); } else { - s = C / (131070.f - (M + m)); // 131070.f = 2.f * 65535.f + s = C / (131070.f - (maxVal + minVal)); // 131070.f = 2.f * 65535.f } } } @@ -261,11 +261,11 @@ public: static inline void rgb2hslfloat(float r, float g, float b, float &h, float &s, float &l) { - float m = min(r, g, b); - float M = max(r, g, b); - float C = M - m; + float minVal = min(r, g, b); + float maxVal = max(r, g, b); + float C = maxVal - minVal; - l = (M + m) * 7.6295109e-6f; // (0.5f / 65535.f) + l = (maxVal + minVal) * 7.6295109e-6f; // (0.5f / 65535.f) if (C < 0.65535f) { // 0.00001f * 65535.f h = 0.f; @@ -273,14 +273,14 @@ public: } else { if (l <= 0.5f) { - s = C / (M + m); + s = C / (maxVal + minVal); } else { - s = C / (131070.f - (M + m)); // 131070.f = 2.f * 65535.f + s = C / (131070.f - (maxVal + minVal)); // 131070.f = 2.f * 65535.f } - if ( r == M ) { + if ( r == maxVal ) { h = (g - b); - } else if ( g == M ) { + } else if ( g == maxVal ) { h = (2.f * C) + (b - r); } else { h = (4.f * C) + (r - g); @@ -686,32 +686,6 @@ public: static void Lch2Luv(float c, float h, float &u, float &v); - /** - * @brief Convert the XYZ values to Luv values - * Warning: this method has never been used/tested so far - * @param x X coordinate [0 ; 65535] ; can be negative or superior to 65535 - * @param y Y coordinate [0 ; 65535] ; can be negative or superior to 65535 - * @param z Z coordinate [0 ; 65535] ; can be negative or superior to 65535 - * @param L 'L' channel [0 ; 32768] (return value) - * @param u 'u' channel [-42000 ; 42000] ; can be more than 42000 (return value) - * @param v 'v' channel [-42000 ; 42000] ; can be more than 42000 (return value) - */ - static void XYZ2Luv (float X, float Y, float Z, float &L, float &u, float &v); - - - /** - * @brief Convert the Luv values to XYZ values - * Warning: this method has never been used/tested so far - * @param L 'L' channel [0 ; 32768] - * @param u 'u' channel [-42000 ; 42000] ; can be more than 42000 - * @param v 'v' channel [-42000 ; 42000] ; can be more than 42000 - * @param x X coordinate [0 ; 65535] ; can be negative or superior to 65535 (return value) - * @param y Y coordinate [0 ; 65535] ; can be negative or superior to 65535 (return value) - * @param z Z coordinate [0 ; 65535] ; can be negative or superior to 65535 (return value) - */ - static void Luv2XYZ (float L, float u, float v, float &X, float &Y, float &Z); - - /** * @brief Return "f" in function of CIE's kappa and epsilon constants * @param f f can be fx fy fz where: diff --git a/rtengine/imagedata.cc b/rtengine/imagedata.cc index faa7ad5ed..b074cdbb2 100644 --- a/rtengine/imagedata.cc +++ b/rtengine/imagedata.cc @@ -258,7 +258,6 @@ FrameData::FrameData(rtexif::TagDirectory* frameRootDir_, rtexif::TagDirectory* tag = exif->getTag("SubjectDistance"); if (tag) { - int num, denom; tag->toRational(num, denom); } else { // Second try, XMP data @@ -524,8 +523,7 @@ FrameData::FrameData(rtexif::TagDirectory* frameRootDir_, rtexif::TagDirectory* focal_len = flt->toDouble (); } } else if ((flt = mnote->getTagP ("FocalLength"))) { - rtexif::Tag* flt = mnote->getTag ("FocalLength"); - focal_len = flt->toDouble (); + focal_len = mnote->getTag("FocalLength")->toDouble (); } if (mnote->getTag ("FocalLengthIn35mmFilm")) { diff --git a/rtexif/rtexif.h b/rtexif/rtexif.h index 43b296746..534484c3e 100644 --- a/rtexif/rtexif.h +++ b/rtexif/rtexif.h @@ -405,7 +405,6 @@ public: // Get the value as a double virtual double toDouble (const Tag* t, int ofs = 0) { - double ud, dd; switch (t->getType()) { case SBYTE: @@ -428,10 +427,11 @@ public: return (double) ((int)sget4 (t->getValue() + ofs, t->getOrder())); case SRATIONAL: - case RATIONAL: - ud = (int)sget4 (t->getValue() + ofs, t->getOrder()); - dd = (int)sget4 (t->getValue() + ofs + 4, t->getOrder()); - return dd == 0. ? 0. : (double)ud / (double)dd; + case RATIONAL: { + const double dividend = (int)sget4 (t->getValue() + ofs, t->getOrder()); + const double divisor = (int)sget4 (t->getValue() + ofs + 4, t->getOrder()); + return divisor == 0. ? 0. : dividend / divisor; + } case FLOAT: return double (sget4 (t->getValue() + ofs, t->getOrder())); diff --git a/rtgui/bqentryupdater.cc b/rtgui/bqentryupdater.cc index f5adf56f9..46aedc869 100644 --- a/rtgui/bqentryupdater.cc +++ b/rtgui/bqentryupdater.cc @@ -100,13 +100,12 @@ void BatchQueueEntryUpdater::processThread () break; } - rtengine::IImage8* img = nullptr; bool newBuffer = false; if (current.thumbnail && current.pparams) { // the thumbnail and the pparams are provided, it means that we have to build the original preview image double tmpscale; - img = current.thumbnail->processThumbImage (*current.pparams, current.oh, tmpscale); + rtengine::IImage8* img = current.thumbnail->processThumbImage (*current.pparams, current.oh, tmpscale); //current.thumbnail->decreaseRef (); // WARNING: decreasing refcount (and maybe deleting) thumbnail, with or without processed image if (img) { diff --git a/rtgui/editorpanel.cc b/rtgui/editorpanel.cc index c59561903..1f8e83c3e 100644 --- a/rtgui/editorpanel.cc +++ b/rtgui/editorpanel.cc @@ -1377,7 +1377,7 @@ void EditorPanel::info_toggled () infoString = M ("QINFO_NOEXIF"); } - iareapanel->imageArea->setInfoText (infoString); + iareapanel->imageArea->setInfoText (std::move(infoString)); iareapanel->imageArea->infoEnabled (info->get_active ()); } diff --git a/rtgui/guiutils.cc b/rtgui/guiutils.cc index eb3704076..eda07af03 100644 --- a/rtgui/guiutils.cc +++ b/rtgui/guiutils.cc @@ -298,17 +298,14 @@ void drawCrop (Cairo::RefPtr cr, int imx, int imy, int imw, int cr->line_to (rectx1, recty1); cr->stroke (); cr->set_source_rgba (0.0, 0.0, 0.0, 0.618); - std::valarray ds (1); - ds[0] = 4; - cr->set_dash (ds, 0); + cr->set_dash (std::valarray({4}), 0); cr->move_to (rectx1, recty1); cr->line_to (rectx2, recty1); cr->line_to (rectx2, recty2); cr->line_to (rectx1, recty2); cr->line_to (rectx1, recty1); cr->stroke (); - ds.resize (0); - cr->set_dash (ds, 0); + cr->set_dash (std::valarray(), 0); if (cparams.guide != "Rule of diagonals" && cparams.guide != "Golden Triangle 1" && cparams.guide != "Golden Triangle 2") { // draw guide lines @@ -446,14 +443,11 @@ void drawCrop (Cairo::RefPtr cr, int imx, int imy, int imw, int cr->line_to (rectx2, recty2); cr->stroke (); cr->set_source_rgba (0.0, 0.0, 0.0, 0.618); - std::valarray ds (1); - ds[0] = 4; - cr->set_dash (ds, 0); + cr->set_dash (std::valarray({4}), 0); cr->move_to (rectx1, recty1); cr->line_to (rectx2, recty2); cr->stroke (); - ds.resize (0); - cr->set_dash (ds, 0); + cr->set_dash (std::valarray(), 0); double height = recty2 - recty1; double width = rectx2 - rectx1; @@ -470,14 +464,11 @@ void drawCrop (Cairo::RefPtr cr, int imx, int imy, int imw, int cr->line_to (rectx1 + x, recty1 + y); cr->stroke (); cr->set_source_rgba (0.0, 0.0, 0.0, 0.618); - ds.resize (1); - ds[0] = 4; - cr->set_dash (ds, 0); + cr->set_dash (std::valarray({4}), 0); cr->move_to (rectx1, recty2); cr->line_to (rectx1 + x, recty1 + y); cr->stroke (); - ds.resize (0); - cr->set_dash (ds, 0); + cr->set_dash (std::valarray(), 0); x = width - (a * b) / height; y = (b * (d - a)) / width; @@ -486,14 +477,11 @@ void drawCrop (Cairo::RefPtr cr, int imx, int imy, int imw, int cr->line_to (rectx1 + x, recty1 + y); cr->stroke (); cr->set_source_rgba (0.0, 0.0, 0.0, 0.618); - ds.resize (1); - ds[0] = 4; - cr->set_dash (ds, 0); + cr->set_dash (std::valarray({4}), 0); cr->move_to (rectx2, recty1); cr->line_to (rectx1 + x, recty1 + y); cr->stroke (); - ds.resize (0); - cr->set_dash (ds, 0); + cr->set_dash (std::valarray(), 0); } } @@ -675,12 +663,6 @@ MyExpander::MyExpander(bool useEnabled, Glib::ustring titleLabel) : statusImage->set_can_focus(false); - Glib::ustring str("-"); - - if (!titleLabel.empty()) { - str = titleLabel; - } - label = Gtk::manage(new Gtk::Label()); setExpandAlignProperties(label, true, false, Gtk::ALIGN_START, Gtk::ALIGN_CENTER); label->set_markup(Glib::ustring("") + escapeHtmlChars(titleLabel) + Glib::ustring("")); @@ -1604,7 +1586,7 @@ bool BackBuffer::setDrawRectangle(Glib::RefPtr window, int newX, in x = newX; y = newY; - if (newH > 0) { + if (newW > 0) { w = newW; } if (newH > 0) { @@ -1637,7 +1619,7 @@ bool BackBuffer::setDrawRectangle(Cairo::Format format, int newX, int newY, int x = newX; y = newY; - if (newH > 0) { + if (newW > 0) { w = newW; } if (newH > 0) { diff --git a/rtgui/histogrampanel.cc b/rtgui/histogrampanel.cc index 49960b2db..12da0cc0d 100644 --- a/rtgui/histogrampanel.cc +++ b/rtgui/histogrampanel.cc @@ -464,7 +464,6 @@ void HistogramRGBArea::updateBackBuffer (int r, int g, int b, const Glib::ustrin if (surface) { Cairo::RefPtr cc = Cairo::Context::create(surface); - Glib::RefPtr style = get_style_context(); cc->set_source_rgba (0., 0., 0., 0.); cc->set_operator (Cairo::OPERATOR_CLEAR); @@ -616,7 +615,6 @@ void HistogramRGBArea::on_realize () { Gtk::DrawingArea::on_realize(); - Glib::RefPtr window = get_window(); add_events(Gdk::BUTTON_PRESS_MASK); } @@ -984,7 +982,6 @@ void HistogramArea::on_realize () { Gtk::DrawingArea::on_realize(); - Glib::RefPtr window = get_window(); add_events(Gdk::POINTER_MOTION_MASK | Gdk::BUTTON_PRESS_MASK | Gdk::BUTTON_RELEASE_MASK); } @@ -1037,8 +1034,6 @@ void HistogramArea::drawMarks(Cairo::RefPtr &cr, bool HistogramArea::on_draw(const ::Cairo::RefPtr< Cairo::Context> &cr) { - Glib::RefPtr window = get_window(); - if (get_width() != oldwidth || get_height() != oldheight || isDirty ()) { updateBackBuffer (); } diff --git a/rtgui/iccprofilecreator.cc b/rtgui/iccprofilecreator.cc index 0ab1ac61d..ed880bd0e 100644 --- a/rtgui/iccprofilecreator.cc +++ b/rtgui/iccprofilecreator.cc @@ -674,8 +674,6 @@ void ICCProfileCreator::savePressed() //necessary for V2 profile if (!v2except) { - std::string is_RTv4 = ""; - //used partially for v4, and in case of if we want to back to old manner for v2 if (primariesPreset == "ACES-AP0" && rtengine::ICCStore::getInstance()->outputProfileExist(options.rtSettings.ACESp0)) { sNewProfile = options.rtSettings.ACESp0; @@ -687,11 +685,9 @@ void ICCProfileCreator::savePressed() sNewProfile = options.rtSettings.adobe; sPrimariesPreset = "Medium"; } else if (primariesPreset == "ProPhoto" && rtengine::ICCStore::getInstance()->outputProfileExist(options.rtSettings.prophoto)) { - is_RTv4 = options.rtSettings.prophoto.substr(0, 4); - - if (is_RTv4 == "RTv4") { + if (options.rtSettings.prophoto.substr(0, 4) == "RTv4") { options.rtSettings.prophoto = "RTv2_Large"; - }; + } sNewProfile = options.rtSettings.prophoto; @@ -703,32 +699,26 @@ void ICCProfileCreator::savePressed() sNewProfile = options.rtSettings.srgb; sPrimariesPreset = "sRGB"; } else if (primariesPreset == "Widegamut" && rtengine::ICCStore::getInstance()->outputProfileExist(options.rtSettings.widegamut)) { - is_RTv4 = options.rtSettings.widegamut.substr(0, 4); - - if (is_RTv4 == "RTv4") { + if (options.rtSettings.widegamut.substr(0, 4) == "RTv4") { options.rtSettings.widegamut = "RTv2_Wide"; - }; + } sNewProfile = options.rtSettings.widegamut; sPrimariesPreset = "Wide"; } else if (primariesPreset == "BestRGB" && rtengine::ICCStore::getInstance()->outputProfileExist(options.rtSettings.best)) { - is_RTv4 = options.rtSettings.best.substr(0, 4); - - if (is_RTv4 == "RTv4") { + if (options.rtSettings.best.substr(0, 4) == "RTv4") { options.rtSettings.best = "RTv2_Best"; - }; + } sNewProfile = options.rtSettings.best; sPrimariesPreset = "Best"; } else if (primariesPreset == "BetaRGB" && rtengine::ICCStore::getInstance()->outputProfileExist(options.rtSettings.beta)) { sNewProfile = options.rtSettings.beta; - is_RTv4 = options.rtSettings.beta.substr(0, 4); - - if (is_RTv4 == "RTv4") { + if (options.rtSettings.beta.substr(0, 4) == "RTv4") { options.rtSettings.widegamut = "RTv2_Beta"; - }; + } sPrimariesPreset = "Beta"; } else if (primariesPreset == "BruceRGB" && rtengine::ICCStore::getInstance()->outputProfileExist(options.rtSettings.bruce)) { diff --git a/rtgui/icmpanel.cc b/rtgui/icmpanel.cc index e7efa20e9..c0944eef6 100644 --- a/rtgui/icmpanel.cc +++ b/rtgui/icmpanel.cc @@ -617,8 +617,6 @@ void ICMPanel::write(ProcParams* pp, ParamsEdited* pedited) } else { pp->icm.inputProfile = ""; // just a directory } - - Glib::ustring p = Glib::path_get_dirname(ipDialog->get_filename()); } pp->icm.workingProfile = wProfNames->get_active_text(); diff --git a/rtgui/imagearea.cc b/rtgui/imagearea.cc index 886d9ff5b..24b793fd9 100644 --- a/rtgui/imagearea.cc +++ b/rtgui/imagearea.cc @@ -29,7 +29,6 @@ ImageArea::ImageArea (ImageAreaPanel* p) : parent(p), fullImageWidth(0), fullImageHeight(0) { - infotext = ""; cropgl = nullptr; pmlistener = nullptr; pmhlistener = nullptr; @@ -148,7 +147,7 @@ void ImageArea::on_style_updated () void ImageArea::setInfoText (Glib::ustring text) { - infotext = text; + infotext = std::move(text); Glib::RefPtr context = get_pango_context () ; Pango::FontDescription fontd(get_style_context()->get_font()); @@ -160,7 +159,7 @@ void ImageArea::setInfoText (Glib::ustring text) // create text layout Glib::RefPtr ilayout = create_pango_layout(""); - ilayout->set_markup(text); + ilayout->set_markup(infotext); // get size of the text block int iw, ih; diff --git a/rtgui/inspector.cc b/rtgui/inspector.cc index a183a3419..85c5f463d 100644 --- a/rtgui/inspector.cc +++ b/rtgui/inspector.cc @@ -83,7 +83,6 @@ InspectorBuffer::~InspectorBuffer() { Inspector::Inspector () : currImage(nullptr), zoom(0.0), active(false) { - Glib::RefPtr style = get_style_context(); set_name("Inspector"); } @@ -115,7 +114,6 @@ bool Inspector::on_draw(const ::Cairo::RefPtr< Cairo::Context> &cr) // compute the displayed area rtengine::Coord availableSize; rtengine::Coord topLeft; - rtengine::Coord displayedSize; rtengine::Coord dest(0, 0); availableSize.x = win->get_width(); availableSize.y = win->get_height(); @@ -125,7 +123,6 @@ bool Inspector::on_draw(const ::Cairo::RefPtr< Cairo::Context> &cr) if (imW < availableSize.x) { // center the image in the available space along X topLeft.x = 0; - displayedSize.x = availableSize.x; dest.x = (availableSize.x - imW) / 2; } else { // partial image display @@ -139,7 +136,6 @@ bool Inspector::on_draw(const ::Cairo::RefPtr< Cairo::Context> &cr) if (imH < availableSize.y) { // center the image in the available space along Y topLeft.y = 0; - displayedSize.y = availableSize.y; dest.y = (availableSize.y - imH) / 2; } else { // partial image display diff --git a/rtgui/rtimage.cc b/rtgui/rtimage.cc index cd687f252..593ac95df 100644 --- a/rtgui/rtimage.cc +++ b/rtgui/rtimage.cc @@ -37,12 +37,10 @@ int RTImage::scaleBack = 0; RTImage::RTImage () {} -RTImage::RTImage (RTImage &other) +RTImage::RTImage (RTImage &other) : surface(other.surface), pixbuf(other.pixbuf) { dpiBack = other.dpiBack; scaleBack = other.scaleBack; - pixbuf = other.pixbuf; - surface = other.surface; if (pixbuf) { set(pixbuf); } else if (surface) { diff --git a/rtgui/rtwindow.cc b/rtgui/rtwindow.cc index 6158cb76a..85b902727 100644 --- a/rtgui/rtwindow.cc +++ b/rtgui/rtwindow.cc @@ -173,8 +173,8 @@ RTWindow::RTWindow () } else { Glib::RefPtr style = Gtk::StyleContext::create(); Pango::FontDescription pfd = style->get_font(Gtk::STATE_FLAG_NORMAL); - int pt; if (pfd.get_set_fields() & Pango::FONT_MASK_SIZE) { + int pt; int fontSize = pfd.get_size(); bool isPix = pfd.get_size_is_absolute(); int resolution = (int)style->get_screen()->get_resolution(); @@ -254,8 +254,6 @@ RTWindow::RTWindow () #if defined(__APPLE__) { osxApp = (GtkosxApplication *)g_object_new (GTKOSX_TYPE_APPLICATION, NULL); - gboolean falseval = FALSE; - gboolean trueval = TRUE; RTWindow *rtWin = this; g_signal_connect (osxApp, "NSApplicationBlockTermination", G_CALLBACK (osx_should_quit_cb), rtWin); g_signal_connect (osxApp, "NSApplicationWillTerminate", G_CALLBACK (osx_will_quit_cb), rtWin); diff --git a/rtgui/splash.cc b/rtgui/splash.cc index d608ccd97..36b796c4d 100644 --- a/rtgui/splash.cc +++ b/rtgui/splash.cc @@ -27,15 +27,13 @@ extern Glib::ustring creditsPath; extern Glib::ustring licensePath; extern Glib::ustring versionString; -SplashImage::SplashImage () +SplashImage::SplashImage () : surface(RTImage::createImgSurfFromFile("splash.png")) { - surface = RTImage::createImgSurfFromFile ("splash.png"); } bool SplashImage::on_draw(const ::Cairo::RefPtr< Cairo::Context> &cr) { - Glib::RefPtr window = get_window(); cr->set_source(surface, 0., 0.); cr->rectangle(0, 0, surface->get_width(), surface->get_height()); cr->fill(); diff --git a/rtgui/thresholdselector.cc b/rtgui/thresholdselector.cc index e1e6fc36f..9b5250862 100644 --- a/rtgui/thresholdselector.cc +++ b/rtgui/thresholdselector.cc @@ -30,7 +30,7 @@ ThresholdSelector::ThresholdSelector(double minValueBottom, double maxValueBottom, double defBottom, Glib::ustring labelBottom, unsigned int precisionBottom, double minValueTop, double maxValueTop, double defTop, Glib::ustring labelTop, unsigned int precisionTop, ThresholdCurveProvider* curveProvider) - : coloredBar(RTO_Left2Right) + : separatedLabelBottom(std::move(labelBottom)), separatedLabelTop(std::move(labelTop)), coloredBar(RTO_Left2Right) { positions[TS_BOTTOMLEFT] = defPos[TS_BOTTOMLEFT] = defBottom; positions[TS_TOPLEFT] = defPos[TS_TOPLEFT] = defTop; @@ -40,8 +40,6 @@ ThresholdSelector::ThresholdSelector(double minValueBottom, double maxValueBotto this->precisionBottom = precisionBottom; doubleThresh = false; - separatedLabelBottom = labelBottom; - separatedLabelTop = labelTop; bgCurveProvider = curveProvider; separatedSliders = true; @@ -66,9 +64,6 @@ ThresholdSelector::ThresholdSelector(double minValue, double maxValue, double de this->precisionBottom = precision; doubleThresh = false; - separatedLabelBottom = ""; - separatedLabelTop = ""; - #ifndef NDEBUG if (startAtOne) { @@ -106,9 +101,6 @@ ThresholdSelector::ThresholdSelector(double minValue, double maxValue, double de this->precisionBottom = precision; doubleThresh = true; - separatedLabelBottom = ""; - separatedLabelTop = ""; - #ifndef NDEBUG if (startAtOne) { @@ -329,14 +321,13 @@ void ThresholdSelector::updateBackBuffer() if (pts.size() >= 4) { std::vector::iterator i = pts.begin(); - double x = *i; ++i; double y = *i; ++i; cr->move_to (xStart, ih*y + yStart); for (; i < pts.end(); ) { - x = *i; + double x = *i; ++i; y = *i; ++i; diff --git a/rtgui/whitebalance.cc b/rtgui/whitebalance.cc index 761dc5e04..aa3443829 100644 --- a/rtgui/whitebalance.cc +++ b/rtgui/whitebalance.cc @@ -382,7 +382,6 @@ void WhiteBalance::adjusterChanged(Adjuster* a, double newval) return; } - Glib::ustring colLabel = row[methodColumns.colLabel]; const std::pair ppMethod = findWBEntry (row[methodColumns.colLabel], WBLT_GUI); const std::pair wbCustom = findWBEntry ("Custom", WBLT_PP); From 41fc34c5c6fa5c1672ba99deb19d9c5709eb94e8 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Wed, 31 Jul 2019 20:21:16 +0200 Subject: [PATCH 06/15] Do not assign empty strings on creation of std::string or Glib::ustring --- rtengine/procparams.cc | 2 +- rtengine/profilestore.cc | 2 +- rtengine/rtlensfun.cc | 2 +- rtgui/batchqueue.cc | 4 ++-- rtgui/batchqueueentry.cc | 1 - rtgui/coordinateadjuster.cc | 2 +- rtgui/curveeditorgroup.cc | 2 +- rtgui/exifpanel.cc | 2 +- rtgui/favoritbrowser.cc | 2 +- rtgui/filecatalog.cc | 2 -- rtgui/flatfield.cc | 1 - rtgui/icmpanel.cc | 4 +--- rtgui/main-cli.cc | 4 ++-- rtgui/profilepanel.cc | 2 +- 14 files changed, 13 insertions(+), 19 deletions(-) diff --git a/rtengine/procparams.cc b/rtengine/procparams.cc index 2118213d5..10d03270f 100644 --- a/rtengine/procparams.cc +++ b/rtengine/procparams.cc @@ -65,7 +65,7 @@ Glib::ustring relativePathIfInside(const Glib::ustring &procparams_fname, bool f return embedded_fname; } - Glib::ustring prefix = ""; + Glib::ustring prefix; if (embedded_fname.length() > 5 && embedded_fname.substr(0, 5) == "file:") { embedded_fname = embedded_fname.substr(5); diff --git a/rtengine/profilestore.cc b/rtengine/profilestore.cc index 437ef6ec6..82074053f 100644 --- a/rtengine/profilestore.cc +++ b/rtengine/profilestore.cc @@ -535,7 +535,7 @@ PartialProfile *ProfileStore::loadDynamicProfile (const FramesMetaData *im) return ret; } -ProfileStoreEntry::ProfileStoreEntry() : label (""), type (PSET_FOLDER), parentFolderId (0), folderId (0) {} +ProfileStoreEntry::ProfileStoreEntry() : type (PSET_FOLDER), parentFolderId (0), folderId (0) {} ProfileStoreEntry::ProfileStoreEntry (Glib::ustring label, PSEType type, unsigned short parentFolder, unsigned short folder) : label (label), type (type), parentFolderId (parentFolder), folderId (folder) {} diff --git a/rtengine/rtlensfun.cc b/rtengine/rtlensfun.cc index 3cea8c484..5f0ffdd91 100644 --- a/rtengine/rtlensfun.cc +++ b/rtengine/rtlensfun.cc @@ -132,7 +132,7 @@ Glib::ustring LFModifier::getDisplayString() const return "NONE"; } else { Glib::ustring ret; - Glib::ustring sep = ""; + Glib::ustring sep; if (flags_ & LF_MODIFY_DISTORTION) { ret += "distortion"; sep = ", "; diff --git a/rtgui/batchqueue.cc b/rtgui/batchqueue.cc index 239057b87..3fb2cd438 100644 --- a/rtgui/batchqueue.cc +++ b/rtgui/batchqueue.cc @@ -811,7 +811,7 @@ Glib::ustring BatchQueue::calcAutoFileNameBase (const Glib::ustring& origFileNam break; } - Glib::ustring tok = ""; + Glib::ustring tok; while ((i < origFileName.size()) && !(origFileName[i] == '\\' || origFileName[i] == '/')) { tok = tok + origFileName[i++]; @@ -857,7 +857,7 @@ Glib::ustring BatchQueue::calcAutoFileNameBase (const Glib::ustring& origFileNam // constructing full output path // printf ("path=|%s|\n", options.savePath.c_str()); - Glib::ustring path = ""; + Glib::ustring path; if (options.saveUsePathTemplate) { unsigned int ix = 0; diff --git a/rtgui/batchqueueentry.cc b/rtgui/batchqueueentry.cc index 23982095c..78e3991c7 100644 --- a/rtgui/batchqueueentry.cc +++ b/rtgui/batchqueueentry.cc @@ -40,7 +40,6 @@ BatchQueueEntry::BatchQueueEntry (rtengine::ProcessingJob* pjob, const rtengine: job(pjob), params(new rtengine::procparams::ProcParams(pparams)), progress(0), - outFileName(""), sequence(0), forceFormatOpts(false), fast_pipeline(job->fastPipeline()), diff --git a/rtgui/coordinateadjuster.cc b/rtgui/coordinateadjuster.cc index 2525a07e5..5065606d9 100644 --- a/rtgui/coordinateadjuster.cc +++ b/rtgui/coordinateadjuster.cc @@ -23,7 +23,7 @@ #include "curveeditorgroup.h" Axis::Axis() - : label(""), decimal(5), increment(0.001), pageIncrement(0.01), rangeLowerBound(0.), rangeUpperBound(1.) + : decimal(5), increment(0.001), pageIncrement(0.01), rangeLowerBound(0.), rangeUpperBound(1.) {} Axis::Axis(Glib::ustring label, unsigned int decimal, double increment, double pageIncrement, double valMin = 0.0, double valMax = 1.0) diff --git a/rtgui/curveeditorgroup.cc b/rtgui/curveeditorgroup.cc index 10aff907c..495e4324b 100644 --- a/rtgui/curveeditorgroup.cc +++ b/rtgui/curveeditorgroup.cc @@ -397,7 +397,7 @@ void CurveEditorGroup::setUnChanged (bool uc, CurveEditor* ce) } } -CurveEditorSubGroup::CurveEditorSubGroup(Glib::ustring& curveDir) : curveDir(curveDir), lastFilename(""), valLinear(0), valUnchanged(0), parent(nullptr) +CurveEditorSubGroup::CurveEditorSubGroup(Glib::ustring& curveDir) : curveDir(curveDir), valLinear(0), valUnchanged(0), parent(nullptr) { leftBar = nullptr; bottomBar = nullptr; diff --git a/rtgui/exifpanel.cc b/rtgui/exifpanel.cc index 6c196e575..f9324e90c 100644 --- a/rtgui/exifpanel.cc +++ b/rtgui/exifpanel.cc @@ -632,7 +632,7 @@ Glib::ustring ExifPanel::getSelection (bool onlyeditable) Gtk::TreeModel::iterator iter = exifTreeModel->get_iter (rows[0]); - Glib::ustring ret = ""; + Glib::ustring ret; bool first = true; bool editable = false; diff --git a/rtgui/favoritbrowser.cc b/rtgui/favoritbrowser.cc index 0e1b4490b..09deacfab 100644 --- a/rtgui/favoritbrowser.cc +++ b/rtgui/favoritbrowser.cc @@ -20,7 +20,7 @@ #include "multilangmgr.h" #include "rtimage.h" -FavoritBrowser::FavoritBrowser () : listener (NULL), lastSelectedDir ("") +FavoritBrowser::FavoritBrowser () : listener (NULL) { scrollw = Gtk::manage (new Gtk::ScrolledWindow ()); diff --git a/rtgui/filecatalog.cc b/rtgui/filecatalog.cc index dbe540cb4..98e805d3a 100644 --- a/rtgui/filecatalog.cc +++ b/rtgui/filecatalog.cc @@ -457,8 +457,6 @@ FileCatalog::FileCatalog (CoarsePanel* cp, ToolBar* tb, FilePanel* filepanel) : hScrollPos[i] = 0; vScrollPos[i] = 0; } - - selectedDirectory = ""; } FileCatalog::~FileCatalog() diff --git a/rtgui/flatfield.cc b/rtgui/flatfield.cc index 25482909e..f69b90170 100644 --- a/rtgui/flatfield.cc +++ b/rtgui/flatfield.cc @@ -86,7 +86,6 @@ FlatField::FlatField () : FoldableToolPanel(this, "flatfield", M("TP_FLATFIELD_L flatFieldFileReset->signal_clicked().connect( sigc::mem_fun(*this, &FlatField::flatFieldFile_Reset), true ); flatFieldAutoSelectconn = flatFieldAutoSelect->signal_toggled().connect ( sigc::mem_fun(*this, &FlatField::flatFieldAutoSelectChanged), true); flatFieldBlurTypeconn = flatFieldBlurType->signal_changed().connect( sigc::mem_fun(*this, &FlatField::flatFieldBlurTypeChanged) ); - lastShortcutPath = ""; // Set filename filters b_filter_asCurrent = false; diff --git a/rtgui/icmpanel.cc b/rtgui/icmpanel.cc index c0944eef6..a6857eaa9 100644 --- a/rtgui/icmpanel.cc +++ b/rtgui/icmpanel.cc @@ -34,7 +34,7 @@ using namespace rtengine::procparams; extern Options options; -ICMPanel::ICMPanel() : FoldableToolPanel(this, "icm", M("TP_ICM_LABEL")), iunchanged(nullptr), icmplistener(nullptr), lastRefFilename(""), camName("") +ICMPanel::ICMPanel() : FoldableToolPanel(this, "icm", M("TP_ICM_LABEL")), iunchanged(nullptr), icmplistener(nullptr) { auto m = ProcEventMapper::getInstance(); EvICMprimariMethod = m->newEvent(GAMMA, "HISTORY_MSG_ICM_OUTPUT_PRIMARIES"); @@ -304,8 +304,6 @@ ICMPanel::ICMPanel() : FoldableToolPanel(this, "icm", M("TP_ICM_LABEL")), iuncha ipDialog->set_show_hidden(true); // ProgramData is hidden on Windows #endif - oldip = ""; - wprofnamesconn = wProfNames->signal_changed().connect(sigc::mem_fun(*this, &ICMPanel::wpChanged)); oprofnamesconn = oProfNames->signal_changed().connect(sigc::mem_fun(*this, &ICMPanel::opChanged)); orendintentconn = oRendIntent->signal_changed().connect(sigc::mem_fun(*this, &ICMPanel::oiChanged)); diff --git a/rtgui/main-cli.cc b/rtgui/main-cli.cc index cbea1d477..f71d7099d 100644 --- a/rtgui/main-cli.cc +++ b/rtgui/main-cli.cc @@ -256,7 +256,7 @@ int processLineParams ( int argc, char **argv ) { rtengine::procparams::PartialProfile *rawParams = nullptr, *imgParams = nullptr; std::vector inputFiles; - Glib::ustring outputPath = ""; + Glib::ustring outputPath; std::vector processingParams; bool outputDirectory = false; bool leaveUntouched = false; @@ -271,7 +271,7 @@ int processLineParams ( int argc, char **argv ) int subsampling = 3; int bits = -1; bool isFloat = false; - std::string outputType = ""; + std::string outputType; unsigned errors = 0; for ( int iArg = 1; iArg < argc; iArg++) { diff --git a/rtgui/profilepanel.cc b/rtgui/profilepanel.cc index af39695fa..c969d13c0 100644 --- a/rtgui/profilepanel.cc +++ b/rtgui/profilepanel.cc @@ -42,7 +42,7 @@ void ProfilePanel::cleanup () delete partialProfileDlg; } -ProfilePanel::ProfilePanel () : storedPProfile(nullptr), lastFilename(""), imagePath(""), lastSavedPSE(nullptr), customPSE(nullptr) +ProfilePanel::ProfilePanel () : storedPProfile(nullptr), lastSavedPSE(nullptr), customPSE(nullptr) { tpc = nullptr; From 46cbb652d5384af6243546935ccc5ab0ed491b00 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Thu, 1 Aug 2019 14:02:38 +0200 Subject: [PATCH 07/15] cppcheck: further fixes --- rtengine/curves.h | 4 ++-- rtengine/dfmanager.cc | 4 ++-- rtengine/ffmanager.cc | 4 ++-- rtengine/ipshadowshighlights.cc | 20 ++++++++++---------- rtengine/pdaflinesfilter.h | 6 ++++-- rtengine/rawimagesource.cc | 1 + rtexif/nikonattribs.cc | 2 +- rtexif/rtexif.h | 2 +- rtgui/adjuster.cc | 8 ++++---- rtgui/batchqueue.h | 4 +++- rtgui/batchqueueentry.h | 3 ++- rtgui/crop.cc | 9 +++------ rtgui/cropwindow.h | 3 ++- rtgui/curveeditor.h | 3 ++- rtgui/diagonalcurveeditorsubgroup.h | 3 ++- rtgui/editorpanel.h | 4 +++- rtgui/filebrowser.h | 4 +++- rtgui/filebrowserentry.h | 4 +++- rtgui/filecatalog.h | 4 +++- rtgui/filepanel.h | 4 +++- rtgui/filmnegative.h | 3 --- rtgui/flatcurveeditorsubgroup.h | 3 ++- rtgui/histogrampanel.h | 7 ++++--- rtgui/mycurve.h | 3 ++- rtgui/previewhandler.h | 3 ++- rtgui/profilepanel.h | 3 ++- rtgui/rtwindow.h | 3 ++- rtgui/saveformatpanel.h | 3 ++- rtgui/toolpanel.h | 3 ++- rtgui/toolpanelcoord.h | 4 +++- 30 files changed, 77 insertions(+), 54 deletions(-) diff --git a/rtengine/curves.h b/rtengine/curves.h index 98ce68015..55068630a 100644 --- a/rtengine/curves.h +++ b/rtengine/curves.h @@ -31,7 +31,7 @@ #include "../rtgui/mydiagonalcurve.h" #include "color.h" #include "pipettebuffer.h" - +#include "noncopyable.h" #include "LUT.h" #define CURVES_MIN_POLY_POINTS 1000 @@ -479,7 +479,7 @@ public: }; }; -class FlatCurve : public Curve +class FlatCurve : public Curve, public rtengine::NonCopyable { private: diff --git a/rtengine/dfmanager.cc b/rtengine/dfmanager.cc index c41c8a180..311921c52 100644 --- a/rtengine/dfmanager.cc +++ b/rtengine/dfmanager.cc @@ -328,8 +328,8 @@ void DFManager::init(const Glib::ustring& pathname) } else { printf( "%s: MEAN of \n ", i.key().c_str()); - for( std::list::iterator iter = i.pathNames.begin(); iter != i.pathNames.end(); ++iter ) { - printf( "%s, ", iter->c_str() ); + for(std::list::iterator path = i.pathNames.begin(); path != i.pathNames.end(); ++path) { + printf("%s, ", path->c_str()); } printf("\n"); diff --git a/rtengine/ffmanager.cc b/rtengine/ffmanager.cc index 6e4977076..56660a82a 100644 --- a/rtengine/ffmanager.cc +++ b/rtengine/ffmanager.cc @@ -277,8 +277,8 @@ void FFManager::init(const Glib::ustring& pathname) } else { printf( "%s: MEAN of \n ", i.key().c_str()); - for( std::list::iterator iter = i.pathNames.begin(); iter != i.pathNames.end(); ++iter ) { - printf( "%s, ", iter->c_str() ); + for(std::list::iterator path = i.pathNames.begin(); path != i.pathNames.end(); ++path) { + printf("%s, ", path->c_str()); } printf("\n"); diff --git a/rtengine/ipshadowshighlights.cc b/rtengine/ipshadowshighlights.cc index 6ce66d9b3..2433ca13c 100644 --- a/rtengine/ipshadowshighlights.cc +++ b/rtengine/ipshadowshighlights.cc @@ -106,10 +106,10 @@ void ImProcFunctions::shadowsHighlights(LabImage *lab) #pragma omp parallel for if (multiThread) #endif for (int l = 0; l < 32768; ++l) { - auto base = pow_F(l / 32768.f, gamma); + auto val = pow_F(l / 32768.f, gamma); // get a bit more contrast in the shadows - base = sh_contrast.getVal(base); - f[l] = base * 32768.f; + val = sh_contrast.getVal(val); + f[l] = val * 32768.f; } } else { #ifdef _OPENMP @@ -119,10 +119,10 @@ void ImProcFunctions::shadowsHighlights(LabImage *lab) float l, a, b; float R = c, G = c, B = c; rgb2lab(R, G, B, l, a, b); - auto base = pow_F(l / 32768.f, gamma); + auto val = pow_F(l / 32768.f, gamma); // get a bit more contrast in the shadows - base = sh_contrast.getVal(base); - l = base * 32768.f; + val = sh_contrast.getVal(val); + l = val * 32768.f; lab2rgb(l, a, b, R, G, B); f[c] = G; } @@ -133,8 +133,8 @@ void ImProcFunctions::shadowsHighlights(LabImage *lab) #pragma omp parallel for if (multiThread) #endif for (int l = 0; l < 32768; ++l) { - auto base = pow_F(l / 32768.f, gamma); - f[l] = base * 32768.f; + auto val = pow_F(l / 32768.f, gamma); + f[l] = val * 32768.f; } } else { #ifdef _OPENMP @@ -144,8 +144,8 @@ void ImProcFunctions::shadowsHighlights(LabImage *lab) float l, a, b; float R = c, G = c, B = c; rgb2lab(R, G, B, l, a, b); - auto base = pow_F(l / 32768.f, gamma); - l = base * 32768.f; + auto val = pow_F(l / 32768.f, gamma); + l = val * 32768.f; lab2rgb(l, a, b, R, G, B); f[c] = G; } diff --git a/rtengine/pdaflinesfilter.h b/rtengine/pdaflinesfilter.h index b1f7bf650..3ae406ec8 100644 --- a/rtengine/pdaflinesfilter.h +++ b/rtengine/pdaflinesfilter.h @@ -20,12 +20,14 @@ #pragma once -#include "rawimagesource.h" #include +#include "rawimagesource.h" +#include "noncopyable.h" namespace rtengine { -class PDAFLinesFilter { +class PDAFLinesFilter: public rtengine::NonCopyable +{ public: explicit PDAFLinesFilter(RawImage *ri); ~PDAFLinesFilter(); diff --git a/rtengine/rawimagesource.cc b/rtengine/rawimagesource.cc index 9f310508f..6cb6fff16 100644 --- a/rtengine/rawimagesource.cc +++ b/rtengine/rawimagesource.cc @@ -429,6 +429,7 @@ RawImageSource::RawImageSource () , plistener(nullptr) , scale_mul{} , c_black{} + , c_white{} , cblacksom{} , ref_pre_mul{} , refwb_red(0.0) diff --git a/rtexif/nikonattribs.cc b/rtexif/nikonattribs.cc index 1c6ead006..678b4b568 100644 --- a/rtexif/nikonattribs.cc +++ b/rtexif/nikonattribs.cc @@ -380,7 +380,7 @@ public: } } - std::string EffectiveMaxApertureString = ""; + std::string EffectiveMaxApertureString; if (!d100) { int EffectiveMaxApertureValue; diff --git a/rtexif/rtexif.h b/rtexif/rtexif.h index 534484c3e..e1e1d6668 100644 --- a/rtexif/rtexif.h +++ b/rtexif/rtexif.h @@ -190,7 +190,7 @@ public: }; // a table of tags: id are offset from beginning and not identifiers -class TagDirectoryTable: public TagDirectory +class TagDirectoryTable: public TagDirectory, public rtengine::NonCopyable { protected: unsigned char *values; // Tags values are saved internally here diff --git a/rtgui/adjuster.cc b/rtgui/adjuster.cc index 0d2c2961f..5a3f783db 100644 --- a/rtgui/adjuster.cc +++ b/rtgui/adjuster.cc @@ -631,21 +631,21 @@ void Adjuster::setSliderValue(double val) if (val >= logPivot) { double range = vMax - logPivot; double x = (val - logPivot) / range; - val = (vMin + mid) + std::log(x * (logBase - 1.0) + 1.0) / std::log(logBase) * mid; + val = (vMin + mid) + std::log1p(x * (logBase - 1.0)) / std::log(logBase) * mid; } else { double range = logPivot - vMin; double x = (logPivot - val) / range; - val = (vMin + mid) - std::log(x * (logBase - 1.0) + 1.0) / std::log(logBase) * mid; + val = (vMin + mid) - std::log1p(x * (logBase - 1.0)) / std::log(logBase) * mid; } } else { if (val >= logPivot) { double range = vMax - logPivot; double x = (val - logPivot) / range; - val = logPivot + std::log(x * (logBase - 1.0) + 1.0) / std::log(logBase) * range; + val = logPivot + std::log1p(x * (logBase - 1.0)) / std::log(logBase) * range; } else { double range = logPivot - vMin; double x = (logPivot - val) / range; - val = logPivot - std::log(x * (logBase - 1.0) + 1.0) / std::log(logBase) * range; + val = logPivot - std::log1p(x * (logBase - 1.0)) / std::log(logBase) * range; } } } diff --git a/rtgui/batchqueue.h b/rtgui/batchqueue.h index 95d92aef2..6f1b8f7f8 100644 --- a/rtgui/batchqueue.h +++ b/rtgui/batchqueue.h @@ -29,6 +29,7 @@ #include "options.h" #include "threadutils.h" #include "thumbbrowserbase.h" +#include "../rtengine/noncopyable.h" class BatchQueueListener { @@ -44,7 +45,8 @@ class FileCatalog; class BatchQueue final : public ThumbBrowserBase, public rtengine::BatchProcessingListener, - public LWButtonListener + public LWButtonListener, + public rtengine::NonCopyable { public: explicit BatchQueue (FileCatalog* aFileCatalog); diff --git a/rtgui/batchqueueentry.h b/rtgui/batchqueueentry.h index 0ea56e403..4972eaf7a 100644 --- a/rtgui/batchqueueentry.h +++ b/rtgui/batchqueueentry.h @@ -26,6 +26,7 @@ #include "thumbbrowserentrybase.h" #include "thumbnail.h" #include "bqentryupdater.h" +#include "../rtengine/noncopyable.h" class BatchQueueEntry; struct BatchQueueEntryIdleHelper { @@ -34,7 +35,7 @@ struct BatchQueueEntryIdleHelper { int pending; }; -class BatchQueueEntry : public ThumbBrowserEntryBase, public BQEntryUpdateListener +class BatchQueueEntry : public ThumbBrowserEntryBase, public BQEntryUpdateListener, public rtengine::NonCopyable { guint8* opreview; diff --git a/rtgui/crop.cc b/rtgui/crop.cc index 781a916a1..a8b12819e 100644 --- a/rtgui/crop.cc +++ b/rtgui/crop.cc @@ -1400,24 +1400,19 @@ void Crop::cropResized (int &x, int &y, int& x2, int& y2) y2 = maxh - 1; } - int X, Y; int W; if (x < x2) { W = x2 - x + 1; - X = x; } else { W = x - x2 + 1; - X = x2; } - int H; + int Y; if (y < y2) { - H = y2 - y + 1; Y = y; } else { - H = y - y2 + 1; Y = y2; } @@ -1425,6 +1420,7 @@ void Crop::cropResized (int &x, int &y, int& x2, int& y2) W = maxw; } + int H; if (fixr->get_active()) { double r = getRatio (); @@ -1457,6 +1453,7 @@ void Crop::cropResized (int &x, int &y, int& x2, int& y2) } } + int X; if (x < x2) { W = x2 - x + 1; X = x; diff --git a/rtgui/cropwindow.h b/rtgui/cropwindow.h index 6e2097d3b..26edf69ee 100644 --- a/rtgui/cropwindow.h +++ b/rtgui/cropwindow.h @@ -31,6 +31,7 @@ #include "cursormanager.h" #include "editbuffer.h" #include "editcoordsys.h" +#include "../rtengine/noncopyable.h" class CropWindow; @@ -45,7 +46,7 @@ public: }; class ImageArea; -class CropWindow : public LWButtonListener, public CropDisplayHandler, public EditCoordSystem, public ObjectMOBuffer +class CropWindow : 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 1227edc0f..e38d3f205 100644 --- a/rtgui/curveeditor.h +++ b/rtgui/curveeditor.h @@ -25,6 +25,7 @@ #include "editcallbacks.h" #include "mydiagonalcurve.h" #include "myflatcurve.h" +#include "../rtengine/noncopyable.h" class CurveEditorGroup; class CurveEditorSubGroup; @@ -38,7 +39,7 @@ class CurveEditorSubGroup; /** @brief This class is an interface between RT and the curve editor group * It handles the methods related to a specific curve. It is created by CurveEditorGroup::addCurve */ -class CurveEditor : public EditSubscriber +class CurveEditor : public EditSubscriber, public rtengine::NonCopyable { friend class CurveEditorGroup; diff --git a/rtgui/diagonalcurveeditorsubgroup.h b/rtgui/diagonalcurveeditorsubgroup.h index 54f424dc6..68047e0c2 100644 --- a/rtgui/diagonalcurveeditorsubgroup.h +++ b/rtgui/diagonalcurveeditorsubgroup.h @@ -21,10 +21,11 @@ #include #include "curveeditorgroup.h" +#include "../rtengine/noncopyable.h" class DiagonalCurveEditor; -class DiagonalCurveEditorSubGroup : public CurveEditorSubGroup, public SHCListener, public AdjusterListener +class DiagonalCurveEditorSubGroup : public CurveEditorSubGroup, public SHCListener, public AdjusterListener, public rtengine::NonCopyable { friend class DiagonalCurveEditor; diff --git a/rtgui/editorpanel.h b/rtgui/editorpanel.h index de5360646..7fe79b827 100644 --- a/rtgui/editorpanel.h +++ b/rtgui/editorpanel.h @@ -34,6 +34,7 @@ #include "navigator.h" #include "progressconnector.h" #include "filepanel.h" +#include "../rtengine/noncopyable.h" class EditorPanel; class MyProgressBar; @@ -52,7 +53,8 @@ class EditorPanel final : public rtengine::ProgressListener, public ThumbnailListener, public HistoryBeforeLineListener, - public rtengine::HistogramListener + public rtengine::HistogramListener, + public rtengine::NonCopyable { public: explicit EditorPanel (FilePanel* filePanel = nullptr); diff --git a/rtgui/filebrowser.h b/rtgui/filebrowser.h index b208a854d..9c7a86f74 100644 --- a/rtgui/filebrowser.h +++ b/rtgui/filebrowser.h @@ -30,6 +30,7 @@ #include "exportpanel.h" #include "extprog.h" #include "profilestorecombobox.h" +#include "../rtengine/noncopyable.h" class ProfileStoreLabel; class FileBrowser; @@ -56,7 +57,8 @@ public: class FileBrowser : public ThumbBrowserBase, public LWButtonListener, public ExportPanelListener, - public ProfileStoreListener + public ProfileStoreListener, + public rtengine::NonCopyable { private: typedef sigc::signal type_trash_changed; diff --git a/rtgui/filebrowserentry.h b/rtgui/filebrowserentry.h index 5122de55f..bd3a266aa 100644 --- a/rtgui/filebrowserentry.h +++ b/rtgui/filebrowserentry.h @@ -34,6 +34,7 @@ #include "thumbimageupdater.h" #include "thumbnail.h" #include "thumbnaillistener.h" +#include "../rtengine/noncopyable.h" class FileBrowserEntry; @@ -46,7 +47,8 @@ struct FileBrowserEntryIdleHelper { class FileThumbnailButtonSet; class FileBrowserEntry : public ThumbBrowserEntryBase, public ThumbnailListener, - public ThumbImageUpdateListener + public ThumbImageUpdateListener, + public rtengine::NonCopyable { double scale; diff --git a/rtgui/filecatalog.h b/rtgui/filecatalog.h index 2f3054bcf..0ff2fb1e8 100644 --- a/rtgui/filecatalog.h +++ b/rtgui/filecatalog.h @@ -32,6 +32,7 @@ #include "previewloader.h" #include "multilangmgr.h" #include "threadutils.h" +#include "../rtengine/noncopyable.h" class FilePanel; /* @@ -44,7 +45,8 @@ class FileCatalog : public Gtk::VBox, public PreviewLoaderListener, public FilterPanelListener, public FileBrowserListener, - public ExportPanelListener + public ExportPanelListener, + public rtengine::NonCopyable { public: typedef sigc::slot DirSelectionSlot; diff --git a/rtgui/filepanel.h b/rtgui/filepanel.h index df61cb60d..0385c48d3 100644 --- a/rtgui/filepanel.h +++ b/rtgui/filepanel.h @@ -31,12 +31,14 @@ #include "filterpanel.h" #include "exportpanel.h" #include "progressconnector.h" +#include "../rtengine/noncopyable.h" class RTWindow; class FilePanel final : public Gtk::HPaned, - public FileSelectionListener + public FileSelectionListener, + public rtengine::NonCopyable { public: FilePanel (); diff --git a/rtgui/filmnegative.h b/rtgui/filmnegative.h index e967f535c..a1efdc455 100644 --- a/rtgui/filmnegative.h +++ b/rtgui/filmnegative.h @@ -28,8 +28,6 @@ #include "toolpanel.h" #include "wbprovider.h" -#include "../rtengine/noncopyable.h" - class FilmNegProvider { public: @@ -39,7 +37,6 @@ public: }; class FilmNegative : - public rtengine::NonCopyable, public ToolParamBlock, public AdjusterListener, public FoldableToolPanel, diff --git a/rtgui/flatcurveeditorsubgroup.h b/rtgui/flatcurveeditorsubgroup.h index ab2abedfb..f931bf660 100644 --- a/rtgui/flatcurveeditorsubgroup.h +++ b/rtgui/flatcurveeditorsubgroup.h @@ -21,10 +21,11 @@ #include #include "curveeditorgroup.h" +#include "../rtengine/noncopyable.h" class FlatCurveEditor; -class FlatCurveEditorSubGroup: public CurveEditorSubGroup +class FlatCurveEditorSubGroup: public CurveEditorSubGroup, public rtengine::NonCopyable { friend class FlatCurveEditor; diff --git a/rtgui/histogrampanel.h b/rtgui/histogrampanel.h index f34b07c39..f66d2e654 100644 --- a/rtgui/histogrampanel.h +++ b/rtgui/histogrampanel.h @@ -28,6 +28,7 @@ #include "guiutils.h" #include "pointermotionlistener.h" +#include "../rtengine/noncopyable.h" class HistogramArea; struct HistogramAreaIdleHelper { @@ -51,7 +52,7 @@ public: double log (double vsize, double val); }; -class HistogramRGBArea : public Gtk::DrawingArea, public BackBuffer, private HistogramScaling +class HistogramRGBArea : public Gtk::DrawingArea, public BackBuffer, private HistogramScaling, public rtengine::NonCopyable { private: typedef const double (*TMatrix)[3]; @@ -114,7 +115,7 @@ public: virtual void toggleButtonMode() = 0; }; -class HistogramArea : public Gtk::DrawingArea, public BackBuffer, private HistogramScaling +class HistogramArea : public Gtk::DrawingArea, public BackBuffer, private HistogramScaling, public rtengine::NonCopyable { public: typedef sigc::signal type_signal_factor_changed; @@ -172,7 +173,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 +class HistogramPanel : public Gtk::Grid, public PointerMotionListener, public DrawModeListener, public rtengine::NonCopyable { protected: diff --git a/rtgui/mycurve.h b/rtgui/mycurve.h index 82dd4a1a4..81a747bcd 100644 --- a/rtgui/mycurve.h +++ b/rtgui/mycurve.h @@ -28,6 +28,7 @@ #include "../rtengine/LUT.h" #include "guiutils.h" #include "options.h" +#include "../rtengine/noncopyable.h" #define RADIUS 3.5 /** radius of the control points ; must be x.5 to target the center of a pixel */ #define CBAR_WIDTH 10 /** inner width of the colored bar (border excluded) */ @@ -55,7 +56,7 @@ enum SnapToType { class MyCurveIdleHelper; class CurveEditor; -class MyCurve : public Gtk::DrawingArea, public BackBuffer, public ColorCaller, public CoordinateProvider +class MyCurve : public Gtk::DrawingArea, public BackBuffer, public ColorCaller, public CoordinateProvider, public rtengine::NonCopyable { friend class MyCurveIdleHelper; diff --git a/rtgui/previewhandler.h b/rtgui/previewhandler.h index fcd0a0c5f..7a93ed480 100644 --- a/rtgui/previewhandler.h +++ b/rtgui/previewhandler.h @@ -28,6 +28,7 @@ #include "guiutils.h" #include "../rtengine/rtengine.h" +#include "../rtengine/noncopyable.h" class PreviewListener { @@ -44,7 +45,7 @@ struct PreviewHandlerIdleHelper { int pending; }; -class PreviewHandler : public rtengine::PreviewImageListener +class PreviewHandler : public rtengine::PreviewImageListener, public rtengine::NonCopyable { private: friend int setImageUI (void* data); diff --git a/rtgui/profilepanel.h b/rtgui/profilepanel.h index b0fb42ab7..bc42f96c3 100644 --- a/rtgui/profilepanel.h +++ b/rtgui/profilepanel.h @@ -28,8 +28,9 @@ #include "guiutils.h" #include "profilestorecombobox.h" #include "rtimage.h" +#include "../rtengine/noncopyable.h" -class ProfilePanel : public Gtk::Grid, public PParamsChangeListener, public ProfileStoreListener +class ProfilePanel : public Gtk::Grid, public PParamsChangeListener, public ProfileStoreListener, public rtengine::NonCopyable { private: diff --git a/rtgui/rtwindow.h b/rtgui/rtwindow.h index 5b58ab0eb..d037d8875 100644 --- a/rtgui/rtwindow.h +++ b/rtgui/rtwindow.h @@ -29,8 +29,9 @@ #if defined(__APPLE__) #include #endif +#include "../rtengine/noncopyable.h" -class RTWindow : public Gtk::Window, public rtengine::ProgressListener +class RTWindow : public Gtk::Window, public rtengine::ProgressListener, public rtengine::NonCopyable { private: diff --git a/rtgui/saveformatpanel.h b/rtgui/saveformatpanel.h index e25210b97..7d7210282 100644 --- a/rtgui/saveformatpanel.h +++ b/rtgui/saveformatpanel.h @@ -23,6 +23,7 @@ #include "adjuster.h" #include "guiutils.h" #include "options.h" +#include "../rtengine/noncopyable.h" class FormatChangeListener { @@ -31,7 +32,7 @@ public: virtual void formatChanged(const Glib::ustring& format) = 0; }; -class SaveFormatPanel : public Gtk::Grid, public AdjusterListener +class SaveFormatPanel : public Gtk::Grid, public AdjusterListener, public rtengine::NonCopyable { protected: diff --git a/rtgui/toolpanel.h b/rtgui/toolpanel.h index 2da5f1bba..1d3630c6d 100644 --- a/rtgui/toolpanel.h +++ b/rtgui/toolpanel.h @@ -26,6 +26,7 @@ #include "guiutils.h" #include "multilangmgr.h" #include "paramsedited.h" +#include "../rtengine/noncopyable.h" class ToolPanel; class FoldableToolPanel; @@ -51,7 +52,7 @@ public: ToolParamBlock(); }; -class ToolPanel +class ToolPanel : public rtengine::NonCopyable { protected: diff --git a/rtgui/toolpanelcoord.h b/rtgui/toolpanelcoord.h index 5569861ae..a1b26b29f 100644 --- a/rtgui/toolpanelcoord.h +++ b/rtgui/toolpanelcoord.h @@ -83,6 +83,7 @@ #include "dehaze.h" #include "guiutils.h" #include "filmnegative.h" +#include "../rtengine/noncopyable.h" class ImageEditorCoordinator; @@ -99,7 +100,8 @@ class ToolPanelCoordinator : public ICMPanelListener, public ImageAreaToolListener, public rtengine::ImageTypeListener, - public FilmNegProvider + public FilmNegProvider, + public rtengine::NonCopyable { protected: WhiteBalance* whitebalance; From 1b8dd7c49a524952281fc4812e0baf6d77127156 Mon Sep 17 00:00:00 2001 From: Morgan Hardwood Date: Mon, 5 Aug 2019 12:11:18 +0200 Subject: [PATCH 08/15] Added camera model aliases Partly related to #5400 --- rtdata/dcpprofiles/camera_model_aliases.json | 2 ++ 1 file changed, 2 insertions(+) diff --git a/rtdata/dcpprofiles/camera_model_aliases.json b/rtdata/dcpprofiles/camera_model_aliases.json index 61fc2bf57..32db0db52 100644 --- a/rtdata/dcpprofiles/camera_model_aliases.json +++ b/rtdata/dcpprofiles/camera_model_aliases.json @@ -16,6 +16,8 @@ "Canon EOS 1000D": ["Canon EOS Kiss Digital F", "Canon EOS DIGITAL REBEL XS"], "Canon EOS 1200D": ["Canon EOS Kiss X70", "Canon EOS REBEL T5"], "Canon EOS 1300D": ["Canon EOS Kiss X80", "Canon EOS Rebel T6"], + "Canon EOS 2000D": ["Canon EOS 1500D", "Canon EOS Kiss X90", "Canon EOS Rebel T7"], + "Canon EOS 4000D": ["Canon EOS 3000D", "Canon EOS Rebel T100"], "MINOLTA DYNAX 5D": ["Minolta Maxxum 5D", "Minolta Alpha 5D", "Minolta Alpha Sweet"], "MINOLTA DYNAX 7D": ["Minolta Maxxum 7D", "Minolta Alpha 7D"], From 972d6907d560569e97ea41bab315ab5ea0855b17 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Tue, 6 Aug 2019 14:51:30 +0200 Subject: [PATCH 09/15] raw crop for OLYMPUS TG-5 and TG-6 --- rtengine/camconst.json | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/rtengine/camconst.json b/rtengine/camconst.json index 9551d5e16..9d96975c8 100644 --- a/rtengine/camconst.json +++ b/rtengine/camconst.json @@ -1725,9 +1725,15 @@ Camera constants: { // Quality B, "make_model": "OLYMPUS TG-5", "dcraw_matrix": [ 10899,-3833,-1082,-2112,10736,1575,-267,1452,5269 ], // DNG_V9.12 D65 + "raw_crop": [ 0, 0, -18, 0 ], // 18 pixels at right are garbage "ranges": { "white": 4050 } // safe for worst case detected, nominal is 4093 }, + { // Quality C, only raw crop + "make_model": "OLYMPUS TG-6", + "raw_crop": [ 0, 0, -24, 0 ] // 24 pixels at right are garbage + }, + { // Quality C, only green equilibration "make_model" : ["OLYMPUS E-3", "OLYMPUS E-520"], "global_green_equilibration" : true From 5e9a409dba357b9d9860e496fdbf73e190141f06 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Tue, 6 Aug 2019 17:34:14 +0200 Subject: [PATCH 10/15] cbdl code cleanup --- rtengine/array2D.h | 6 + rtengine/dirpyr_equalizer.cc | 975 ++++++++++++----------------------- rtengine/helpersse2.h | 2 +- rtengine/improcfun.cc | 2 +- rtengine/improcfun.h | 7 +- 5 files changed, 338 insertions(+), 654 deletions(-) diff --git a/rtengine/array2D.h b/rtengine/array2D.h index 48a789bf8..84728f043 100644 --- a/rtengine/array2D.h +++ b/rtengine/array2D.h @@ -214,6 +214,12 @@ public: return ptr; } + // use as pointer to T** + operator const T* const *() + { + return ptr; + } + // use as pointer to data operator T*() { diff --git a/rtengine/dirpyr_equalizer.cc b/rtengine/dirpyr_equalizer.cc index 4a30b48a8..94826e06e 100644 --- a/rtengine/dirpyr_equalizer.cc +++ b/rtengine/dirpyr_equalizer.cc @@ -16,7 +16,7 @@ * * (C) 2010 Emil Martinec * - */ +*/ #include #include @@ -25,404 +25,55 @@ #include "rt_math.h" #include "opthelper.h" -#define RANGEFN(i) ((1000.0f / (i + 1000.0f))) -#define DIRWT(i1,j1,i,j) ( domker[(i1-i)/scale+halfwin][(j1-j)/scale+halfwin] * RANGEFN(fabsf((data_fine[i1][j1]-data_fine[i][j]))) ) - -namespace rtengine -{ - -constexpr int maxlevel = 6; -constexpr float noise = 2000; - -//sequence of scales -constexpr int scales[maxlevel] = {1, 2, 4, 8, 16, 32}; -extern const Settings* settings; - -//sequence of scales - -void ImProcFunctions :: dirpyr_equalizer(float ** src, float ** dst, int srcwidth, int srcheight, float ** l_a, float ** l_b, const double * mult, const double dirpyrThreshold, const double skinprot, float b_l, float t_l, float t_r, int scaleprev) -{ - int lastlevel = maxlevel; - - float atten123 = (float) settings->level123_cbdl; - - if(atten123 > 50.f) { - atten123 = 50.f; - } - - if(atten123 < 0.f) { - atten123 = 0.f; - } - - float atten0 = (float) settings->level0_cbdl; - - if(atten0 > 40.f) { - atten123 = 40.f; - } - - if(atten0 < 0.f) { - atten0 = 0.f; - } - - if((t_r - t_l) < 0.55f) { - t_l = t_r + 0.55f; //avoid too small range - } - - - while (lastlevel > 0 && fabs(mult[lastlevel - 1] - 1) < 0.001) { - lastlevel--; - //printf("last level to process %d \n",lastlevel); - } - - if (lastlevel == 0) { - return; - } - - int level; - float multi[maxlevel] = {1.f, 1.f, 1.f, 1.f, 1.f, 1.f}; - float scalefl[maxlevel]; - - for(int lv = 0; lv < maxlevel; lv++) { - scalefl[lv] = ((float) scales[lv]) / (float) scaleprev; - - if(lv >= 1) { - if(scalefl[lv] < 1.f) { - multi[lv] = (atten123 * ((float) mult[lv] - 1.f) / 100.f) + 1.f; //modulate action if zoom < 100% - } else { - multi[lv] = (float) mult[lv]; - } - } else { - if(scalefl[lv] < 1.f) { - multi[lv] = (atten0 * ((float) mult[lv] - 1.f) / 100.f) + 1.f; //modulate action if zoom < 100% - } else { - multi[lv] = (float) mult[lv]; - } - } - - } - - multi_array2D dirpyrlo (srcwidth, srcheight); - - level = 0; - - //int thresh = 100 * mult[5]; - int scale = (int)(scales[level]) / scaleprev; - - if(scale < 1) { - scale = 1; - } - - - dirpyr_channel(src, dirpyrlo[0], srcwidth, srcheight, 0, scale); - - level = 1; - - while(level < lastlevel) { - - scale = (int)(scales[level]) / scaleprev; - - if(scale < 1) { - scale = 1; - } - - dirpyr_channel(dirpyrlo[level - 1], dirpyrlo[level], srcwidth, srcheight, level, scale); - - level ++; - } - - float **tmpHue = nullptr, **tmpChr = nullptr; - - if(skinprot != 0.f) { - // precalculate hue and chroma, use SSE, if available - // by precalculating these values we can greatly reduce the number of calculations in idirpyr_eq_channel() - // but we need two additional buffers for this preprocessing - tmpHue = new float*[srcheight]; - - for (int i = 0; i < srcheight; i++) { - tmpHue[i] = new float[srcwidth]; - } - -#ifdef __SSE2__ -#ifdef _OPENMP - #pragma omp parallel for -#endif - - for(int i = 0; i < srcheight; i++) { - int j; - - for(j = 0; j < srcwidth - 3; j += 4) { - _mm_storeu_ps(&tmpHue[i][j], xatan2f(LVFU(l_b[i][j]), LVFU(l_a[i][j]))); - } - - for(; j < srcwidth; j++) { - tmpHue[i][j] = xatan2f(l_b[i][j], l_a[i][j]); - } - } - -#else -#ifdef _OPENMP - #pragma omp parallel for -#endif - - for(int i = 0; i < srcheight; i++) { - for(int j = 0; j < srcwidth; j++) { - tmpHue[i][j] = xatan2f(l_b[i][j], l_a[i][j]); - } - } - -#endif - tmpChr = new float*[srcheight]; - - for (int i = 0; i < srcheight; i++) { - tmpChr[i] = new float[srcwidth]; - } - -#ifdef __SSE2__ -#ifdef _OPENMP - #pragma omp parallel -#endif - { - __m128 div = _mm_set1_ps(327.68f); -#ifdef _OPENMP - #pragma omp for -#endif - - for(int i = 0; i < srcheight; i++) { - int j; - - for(j = 0; j < srcwidth - 3; j += 4) { - _mm_storeu_ps(&tmpChr[i][j], vsqrtf(SQRV(LVFU(l_b[i][j])) + SQRV(LVFU(l_a[i][j]))) / div); - } - - for(; j < srcwidth; j++) { - tmpChr[i][j] = sqrtf(SQR((l_b[i][j])) + SQR((l_a[i][j]))) / 327.68f; - } - } - } -#else -#ifdef _OPENMP - #pragma omp parallel for -#endif - - for(int i = 0; i < srcheight; i++) { - for(int j = 0; j < srcwidth; j++) { - tmpChr[i][j] = sqrtf(SQR((l_b[i][j])) + SQR((l_a[i][j]))) / 327.68f; - } - } - -#endif - } - - // with the current implementation of idirpyr_eq_channel we can safely use the buffer from last level as buffer, saves some memory - float ** buffer = dirpyrlo[lastlevel - 1]; - - for(int level = lastlevel - 1; level > 0; level--) { - idirpyr_eq_channel(dirpyrlo[level], dirpyrlo[level - 1], buffer, srcwidth, srcheight, level, multi, dirpyrThreshold, tmpHue, tmpChr, skinprot, b_l, t_l, t_r); - } - - scale = scales[0]; - - idirpyr_eq_channel(dirpyrlo[0], dst, buffer, srcwidth, srcheight, 0, multi, dirpyrThreshold, tmpHue, tmpChr, skinprot, b_l, t_l, t_r); - - if(skinprot != 0.f) { - for (int i = 0; i < srcheight; i++) { - delete [] tmpChr[i]; - } - - delete [] tmpChr; - - for (int i = 0; i < srcheight; i++) { - delete [] tmpHue[i]; - } - - delete [] tmpHue; - } - -#ifdef _OPENMP - #pragma omp parallel for -#endif - - for (int i = 0; i < srcheight; i++) - for (int j = 0; j < srcwidth; j++) { - dst[i][j] = /*CLIP*/(buffer[i][j]); // TODO: Really a clip necessary? - } +namespace { +float rangeFn(float i) { + return 1.f / (i + 1000.f); } - - -void ImProcFunctions :: dirpyr_equalizercam (CieImage *ncie, float ** src, float ** dst, int srcwidth, int srcheight, float ** h_p, float ** C_p, const double * mult, const double dirpyrThreshold, const double skinprot, bool execdir, float b_l, float t_l, float t_r, int scaleprev) -{ - int lastlevel = maxlevel; - - if(settings->verbose) { - printf("CAM dirpyr scaleprev=%i\n", scaleprev); - } - - float atten123 = (float) settings->level123_cbdl; - - if(atten123 > 50.f) { - atten123 = 50.f; - } - - if(atten123 < 0.f) { - atten123 = 0.f; - } - -// printf("atten=%f\n",atten); - float atten0 = (float) settings->level0_cbdl; - - if(atten0 > 40.f) { - atten123 = 40.f; - } - - if(atten0 < 0.f) { - atten0 = 0.f; - } - - if((t_r - t_l) < 0.55f) { - t_l = t_r + 0.55f; //avoid too small range - } - - while (fabs(mult[lastlevel - 1] - 1) < 0.001 && lastlevel > 0) { - lastlevel--; - //printf("last level to process %d \n",lastlevel); - } - - if (lastlevel == 0) { - return; - } - - int level; - - float multi[maxlevel] = {1.f, 1.f, 1.f, 1.f, 1.f, 1.f}; - float scalefl[maxlevel]; - - for(int lv = 0; lv < maxlevel; lv++) { - scalefl[lv] = ((float) scales[lv]) / (float) scaleprev; - - // if(scalefl[lv] < 1.f) multi[lv] = 1.f; else multi[lv]=(float) mult[lv]; - if (lv >= 1) { - if(scalefl[lv] < 1.f) { - multi[lv] = (atten123 * ((float) mult[lv] - 1.f) / 100.f) + 1.f; - } else { - multi[lv] = (float) mult[lv]; - } - } else { - if(scalefl[lv] < 1.f) { - multi[lv] = (atten0 * ((float) mult[lv] - 1.f) / 100.f) + 1.f; - } else { - multi[lv] = (float) mult[lv]; - } - } - - - } - - if(settings->verbose) { - printf("CAM CbDL mult0=%f 1=%f 2=%f 3=%f 4=%f 5=%f\n", multi[0], multi[1], multi[2], multi[3], multi[4], multi[5]); - } - - - - - multi_array2D dirpyrlo (srcwidth, srcheight); - - level = 0; - - int scale = (int)(scales[level]) / scaleprev; - - if(scale < 1) { - scale = 1; - } - - dirpyr_channel(src, dirpyrlo[0], srcwidth, srcheight, 0, scale); - - level = 1; - - while(level < lastlevel) { - scale = (int)(scales[level]) / scaleprev; - - if(scale < 1) { - scale = 1; - } - - dirpyr_channel(dirpyrlo[level - 1], dirpyrlo[level], srcwidth, srcheight, level, scale); - - level ++; - } - - - // with the current implementation of idirpyr_eq_channel we can safely use the buffer from last level as buffer, saves some memory - float ** buffer = dirpyrlo[lastlevel - 1]; - - for(int level = lastlevel - 1; level > 0; level--) { - idirpyr_eq_channelcam(dirpyrlo[level], dirpyrlo[level - 1], buffer, srcwidth, srcheight, level, multi, dirpyrThreshold , h_p, C_p, skinprot, b_l, t_l, t_r); - } - - idirpyr_eq_channelcam(dirpyrlo[0], dst, buffer, srcwidth, srcheight, 0, multi, dirpyrThreshold, h_p, C_p, skinprot, b_l, t_l, t_r); - - - if(execdir) { -#ifdef _OPENMP - #pragma omp parallel for schedule(dynamic,16) -#endif - - for (int i = 0; i < srcheight; i++) - for (int j = 0; j < srcwidth; j++) { - if(ncie->J_p[i][j] > 8.f && ncie->J_p[i][j] < 92.f) { - dst[i][j] = /*CLIP*/( buffer[i][j] ); // TODO: Really a clip necessary? - } else { - dst[i][j] = src[i][j]; - } - } - } else { - for (int i = 0; i < srcheight; i++) - for (int j = 0; j < srcwidth; j++) { - dst[i][j] = /*CLIP*/( buffer[i][j] ); // TODO: Really a clip necessary? - } - } -} - -void ImProcFunctions::dirpyr_channel(float ** data_fine, float ** data_coarse, int width, int height, int level, int scale) +void dirpyr_channel(const float * const * data_fine, float ** data_coarse, int width, int height, int level, int scale) { // scale is spacing of directional averaging weights // calculate weights, compute directionally weighted average - if(level > 1) { + if (level > 1) { //generate domain kernel - int domker[5][5] = {{1, 1, 1, 1, 1}, {1, 2, 2, 2, 1}, {1, 2, 2, 2, 1}, {1, 2, 2, 2, 1}, {1, 1, 1, 1, 1}}; - // int domker[5][5] = {{1,1,1,1,1},{1,1,1,1,1},{1,1,1,1,1},{1,1,1,1,1},{1,1,1,1,1}}; - static const int halfwin = 2; - const int scalewin = halfwin * scale; + // multiplied each value of domker by 1000 to avoid multiplication by 1000 inside the loop +#ifdef __SSE2__ + const float domkerv[5][5][4] ALIGNED16 = {{{1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}}, + {{1000, 1000, 1000, 1000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {1000, 1000, 1000, 1000}}, + {{1000, 1000, 1000, 1000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {1000, 1000, 1000, 1000}}, + {{1000, 1000, 1000, 1000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {1000, 1000, 1000, 1000}}, + {{1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}}}; +#endif + const float domker[5][5] = {{1000, 1000, 1000, 1000, 1000}, + {1000, 2000, 2000, 2000, 1000}, + {1000, 2000, 2000, 2000, 1000}, + {1000, 2000, 2000, 2000, 1000}, + {1000, 1000, 1000, 1000, 1000}}; + constexpr int halfwin = 2; #ifdef _OPENMP #pragma omp parallel #endif { + const int scalewin = halfwin * scale; #ifdef __SSE2__ - __m128 thousandv = _mm_set1_ps( 1000.0f ); - __m128 dirwtv, valv, normv, dftemp1v, dftemp2v; -// multiplied each value of domkerv by 1000 to avoid multiplication by 1000 inside the loop - float domkerv[5][5][4] ALIGNED16 = {{{1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}}, {{1000, 1000, 1000, 1000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {1000, 1000, 1000, 1000}}, {{1000, 1000, 1000, 1000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {1000, 1000, 1000, 1000}}, {{1000, 1000, 1000, 1000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {2000, 2000, 2000, 2000}, {1000, 1000, 1000, 1000}}, {{1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}, {1000, 1000, 1000, 1000}}}; -#endif // __SSE2__ - - int j; -#ifdef _OPENMP - #pragma omp for //schedule (dynamic,8) + const vfloat thousandv = F2V(1000.f); #endif - for(int i = 0; i < height; i++) { - float dirwt; +#ifdef _OPENMP + #pragma omp for +#endif - for(j = 0; j < scalewin; j++) { + for (int i = 0; i < height; i++) { + int j; + for (j = 0; j < scalewin; j++) { float val = 0.f; float norm = 0.f; - - for(int inbr = max(0, i - scalewin); inbr <= min(height - 1, i + scalewin); inbr += scale) { + for (int inbr = max(0, i - scalewin); inbr <= min(height - 1, i + scalewin); inbr += scale) { for (int jnbr = max(0, j - scalewin); jnbr <= j + scalewin; jnbr += scale) { - //printf("i=%d ",(inbr-i)/scale+halfwin); - dirwt = DIRWT(inbr, jnbr, i, j); + const float dirwt = domker[(inbr - i) / scale + halfwin][(jnbr - j)/ scale + halfwin] * rangeFn(fabsf(data_fine[inbr][jnbr] - data_fine[i][j])); val += dirwt * data_fine[inbr][jnbr]; norm += dirwt; } @@ -433,174 +84,125 @@ void ImProcFunctions::dirpyr_channel(float ** data_fine, float ** data_coarse, i #ifdef __SSE2__ - for(; j < width - scalewin - 3; j += 4) { - valv = _mm_setzero_ps(); - normv = _mm_setzero_ps(); - dftemp1v = LVFU(data_fine[i][j]); + for (; j < width - scalewin - 3; j += 4) { + vfloat valv = ZEROV; + vfloat normv = ZEROV; + const vfloat dftemp1v = LVFU(data_fine[i][j]); - for(int inbr = MAX(0, i - scalewin); inbr <= MIN(height - 1, i + scalewin); inbr += scale) { - int indexihlp = (inbr - i) / scale + halfwin; - - for (int jnbr = j - scalewin, indexjhlp = 0; jnbr <= j + scalewin; jnbr += scale, indexjhlp++) { - dftemp2v = LVFU(data_fine[inbr][jnbr]); - dirwtv = LVF(domkerv[indexihlp][indexjhlp]) / (vabsf(dftemp1v - dftemp2v) + thousandv); + for (int inbr = MAX(0, i - scalewin); inbr <= MIN(height - 1, i + scalewin); inbr += scale) { + const int indexihlp = (inbr - i) / scale + halfwin; + for (int jnbr = j - scalewin, indexjhlp = 0; jnbr <= j + scalewin; jnbr += scale, ++indexjhlp) { + const vfloat dftemp2v = LVFU(data_fine[inbr][jnbr]); + const vfloat dirwtv = LVF(domkerv[indexihlp][indexjhlp]) / (vabsf(dftemp1v - dftemp2v) + thousandv); valv += dirwtv * dftemp2v; normv += dirwtv; } } - - _mm_storeu_ps( &data_coarse[i][j], valv / normv); //low pass filter + STVFU(data_coarse[i][j], valv / normv); //low pass filter } - - for(; j < width - scalewin; j++) { - float val = 0.f; - float norm = 0.f; - - for(int inbr = max(0, i - scalewin); inbr <= min(height - 1, i + scalewin); inbr += scale) { - for (int jnbr = j - scalewin; jnbr <= j + scalewin; jnbr += scale) { - dirwt = DIRWT(inbr, jnbr, i, j); - val += dirwt * data_fine[inbr][jnbr]; - norm += dirwt; - } - } - - data_coarse[i][j] = val / norm; //low pass filter - } - -#else - - for(; j < width - scalewin; j++) { - float val = 0.f; - float norm = 0.f; - - for(int inbr = max(0, i - scalewin); inbr <= min(height - 1, i + scalewin); inbr += scale) { - for (int jnbr = j - scalewin; jnbr <= j + scalewin; jnbr += scale) { - dirwt = DIRWT(inbr, jnbr, i, j); - val += dirwt * data_fine[inbr][jnbr]; - norm += dirwt; - } - } - - data_coarse[i][j] = val / norm; //low pass filter - } - #endif - - for(; j < width; j++) { + for (; j < width - scalewin; j++) { float val = 0.f; float norm = 0.f; - for(int inbr = max(0, i - scalewin); inbr <= min(height - 1, i + scalewin); inbr += scale) { - for (int jnbr = j - scalewin; jnbr <= min(width - 1, j + scalewin); jnbr += scale) { - dirwt = DIRWT(inbr, jnbr, i, j); + for (int inbr = max(0, i - scalewin); inbr <= min(height - 1, i + scalewin); inbr += scale) { + for (int jnbr = j - scalewin; jnbr <= j + scalewin; jnbr += scale) { + const float dirwt = domker[(inbr - i) / scale + halfwin][(jnbr - j)/ scale + halfwin] * rangeFn(fabsf(data_fine[inbr][jnbr] - data_fine[i][j])); val += dirwt * data_fine[inbr][jnbr]; norm += dirwt; } } + data_coarse[i][j] = val / norm; //low pass filter + } + for (; j < width; j++) { + float val = 0.f; + float norm = 0.f; + + for (int inbr = max(0, i - scalewin); inbr <= min(height - 1, i + scalewin); inbr += scale) { + for (int jnbr = j - scalewin; jnbr <= min(width - 1, j + scalewin); jnbr += scale) { + const float dirwt = domker[(inbr - i) / scale + halfwin][(jnbr - j)/ scale + halfwin] * rangeFn(fabsf(data_fine[inbr][jnbr] - data_fine[i][j])); + val += dirwt * data_fine[inbr][jnbr]; + norm += dirwt; + } + } data_coarse[i][j] = val / norm; //low pass filter } } } } else { // level <=1 means that all values of domker would be 1.0f, so no need for multiplication -// const int scalewin = scale; #ifdef _OPENMP #pragma omp parallel #endif { #ifdef __SSE2__ - __m128 thousandv = _mm_set1_ps( 1000.0f ); - __m128 dirwtv, valv, normv, dftemp1v, dftemp2v; -#endif // __SSE2__ - int j; + const vfloat thousandv = F2V(1000.0f); +#endif #ifdef _OPENMP #pragma omp for schedule(dynamic,16) #endif - for(int i = 0; i < height; i++) + for (int i = 0; i < height; i++) { - float dirwt; - - for(j = 0; j < scale; j++) { + int j = 0; + for (; j < scale; j++) { float val = 0.f; float norm = 0.f; - for(int inbr = max(0, i - scale); inbr <= min(height - 1, i + scale); inbr += scale) { + for (int inbr = max(0, i - scale); inbr <= min(height - 1, i + scale); inbr += scale) { for (int jnbr = max(0, j - scale); jnbr <= j + scale; jnbr += scale) { - dirwt = RANGEFN(fabsf(data_fine[inbr][jnbr] - data_fine[i][j])); + const float dirwt = rangeFn(fabsf(data_fine[inbr][jnbr] - data_fine[i][j])); val += dirwt * data_fine[inbr][jnbr]; norm += dirwt; } } - data_coarse[i][j] = val / norm; //low pass filter } #ifdef __SSE2__ - for(; j < width - scale - 3; j += 4) { - valv = _mm_setzero_ps(); - normv = _mm_setzero_ps(); - dftemp1v = LVFU(data_fine[i][j]); + for (; j < width - scale - 3; j += 4) { + vfloat valv = ZEROV; + vfloat normv = ZEROV; + const vfloat dftemp1v = LVFU(data_fine[i][j]); - for(int inbr = MAX(0, i - scale); inbr <= MIN(height - 1, i + scale); inbr += scale) { + for (int inbr = MAX(0, i - scale); inbr <= MIN(height - 1, i + scale); inbr += scale) { for (int jnbr = j - scale; jnbr <= j + scale; jnbr += scale) { - dftemp2v = LVFU(data_fine[inbr][jnbr]); - dirwtv = thousandv / (vabsf(dftemp2v - dftemp1v) + thousandv); + const vfloat dftemp2v = LVFU(data_fine[inbr][jnbr]); + const vfloat dirwtv = thousandv / (vabsf(dftemp2v - dftemp1v) + thousandv); valv += dirwtv * dftemp2v; normv += dirwtv; } } - - _mm_storeu_ps( &data_coarse[i][j], valv / normv); //low pass filter + STVFU(data_coarse[i][j], valv / normv); //low pass filter } - - for(; j < width - scale; j++) { - float val = 0.f; - float norm = 0.f; - - for(int inbr = max(0, i - scale); inbr <= min(height - 1, i + scale); inbr += scale) { - for (int jnbr = j - scale; jnbr <= j + scale; jnbr += scale) { - dirwt = RANGEFN(fabsf(data_fine[inbr][jnbr] - data_fine[i][j])); - val += dirwt * data_fine[inbr][jnbr]; - norm += dirwt; - } - } - - data_coarse[i][j] = val / norm; //low pass filter - } - -#else - - for(; j < width - scale; j++) { - float val = 0.f; - float norm = 0.f; - - for(int inbr = max(0, i - scale); inbr <= min(height - 1, i + scale); inbr += scale) { - for (int jnbr = j - scale; jnbr <= j + scale; jnbr += scale) { - dirwt = RANGEFN(fabsf(data_fine[inbr][jnbr] - data_fine[i][j])); - val += dirwt * data_fine[inbr][jnbr]; - norm += dirwt; - } - } - - data_coarse[i][j] = val / norm; //low pass filter - } - #endif - for(; j < width; j++) { + for (; j < width - scale; j++) { float val = 0.f; float norm = 0.f; - for(int inbr = max(0, i - scale); inbr <= min(height - 1, i + scale); inbr += scale) { - for (int jnbr = j - scale; jnbr <= min(width - 1, j + scale); jnbr += scale) { - dirwt = RANGEFN(fabsf(data_fine[inbr][jnbr] - data_fine[i][j])); + for (int inbr = max(0, i - scale); inbr <= min(height - 1, i + scale); inbr += scale) { + for (int jnbr = j - scale; jnbr <= j + scale; jnbr += scale) { + const float dirwt = rangeFn(fabsf(data_fine[inbr][jnbr] - data_fine[i][j])); val += dirwt * data_fine[inbr][jnbr]; norm += dirwt; } } + data_coarse[i][j] = val / norm; //low pass filter + } + for (; j < width; j++) { + float val = 0.f; + float norm = 0.f; + + for (int inbr = max(0, i - scale); inbr <= min(height - 1, i + scale); inbr += scale) { + for (int jnbr = j - scale; jnbr <= min(width - 1, j + scale); jnbr += scale) { + const float dirwt = rangeFn(fabsf(data_fine[inbr][jnbr] - data_fine[i][j])); + val += dirwt * data_fine[inbr][jnbr]; + norm += dirwt; + } + } data_coarse[i][j] = val / norm; //low pass filter } } @@ -608,218 +210,297 @@ void ImProcFunctions::dirpyr_channel(float ** data_fine, float ** data_coarse, i } } -void ImProcFunctions::idirpyr_eq_channel(float ** data_coarse, float ** data_fine, float ** buffer, int width, int height, int level, float mult[maxlevel], const double dirpyrThreshold, float ** hue, float ** chrom, const double skinprot, float b_l, float t_l, float t_r) +void fillLut(LUTf &irangefn, int level, double dirpyrThreshold, float mult, float skinprot) { + + float multbis; + if (level == 4 && mult > 1.f) { + multbis = 1.f + 0.65f * (mult - 1.f); + } else if (level == 5 && mult > 1.f) { + multbis = 1.f + 0.45f * (mult - 1.f); + } else { + multbis = mult; //multbis to reduce artifacts for high values mult + } + + 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)); + + for (int i = 0; i < 0x20000; i++) { + if (abs(i - 0x10000) > noisehi || multbis < 1.0) { + irangefn[i] = multbis + offs; + } else { + if (abs(i - 0x10000) < noiselo) { + irangefn[i] = 1.f + offs; + } else { + irangefn[i] = 1.f + offs + (multbis - 1.f) * (noisehi - abs(i - 0x10000)) / (noisehi - noiselo + 0.01f); + } + } + } +} + +void idirpyr_eq_channel(const float * const * data_coarse, const float * const * data_fine, float ** buffer, int width, int height, int level, float mult, const double dirpyrThreshold, const float * const * hue, const float * const * chrom, const double skinprot, float b_l, float t_l, float t_r) { const float skinprotneg = -skinprot; const float factorHard = (1.f - skinprotneg / 100.f); - float offs; + LUTf irangefn(0x20000); + fillLut(irangefn, level, dirpyrThreshold, mult, skinprot); - if(skinprot == 0.f) { - offs = 0.f; - } else { - offs = -1.f; - } - - float multbis[maxlevel]; - - multbis[level] = mult[level]; //multbis to reduce artifacts for high values mult - - if(level == 4 && mult[level] > 1.f) { - multbis[level] = 1.f + 0.65f * (mult[level] - 1.f); - } - - if(level == 5 && mult[level] > 1.f) { - multbis[level] = 1.f + 0.45f * (mult[level] - 1.f); - } - - LUTf irangefn (0x20000); - { - const float noisehi = 1.33f * noise * dirpyrThreshold / expf(level * log(3.0)), noiselo = 0.66f * noise * dirpyrThreshold / expf(level * log(3.0)); - //printf("level=%i multlev=%f noisehi=%f noiselo=%f skinprot=%f\n",level,mult[level], noisehi, noiselo, skinprot); - - for (int i = 0; i < 0x20000; i++) { - if (abs(i - 0x10000) > noisehi || multbis[level] < 1.0) { - irangefn[i] = multbis[level] + offs; - } else { - if (abs(i - 0x10000) < noiselo) { - irangefn[i] = 1.f + offs ; - } else { - irangefn[i] = 1.f + offs + (multbis[level] - 1.f) * (noisehi - abs(i - 0x10000)) / (noisehi - noiselo + 0.01f) ; - } - } - } - } - - if(skinprot == 0.f) + if (!skinprot) { #ifdef _OPENMP #pragma omp parallel for schedule(dynamic,16) #endif - for(int i = 0; i < height; i++) { - for(int j = 0; j < width; j++) { - float hipass = (data_fine[i][j] - data_coarse[i][j]); + for (int i = 0; i < height; i++) { + for (int j = 0; j < width; j++) { + const float hipass = data_fine[i][j] - data_coarse[i][j]; buffer[i][j] += irangefn[hipass + 0x10000] * hipass; } } - else if(skinprot > 0.f) + } else if (skinprot > 0.f) { #ifdef _OPENMP #pragma omp parallel for schedule(dynamic,16) #endif - for(int i = 0; i < height; i++) { - for(int j = 0; j < width; j++) { + for (int i = 0; i < height; i++) { + for (int j = 0; j < width; j++) { float scale = 1.f; - float hipass = (data_fine[i][j] - data_coarse[i][j]); - // These values are precalculated now - float modhue = hue[i][j]; - float modchro = chrom[i][j]; - Color::SkinSatCbdl ((data_fine[i][j]) / 327.68f, modhue, modchro, skinprot, scale, true, b_l, t_l, t_r); - buffer[i][j] += (1.f + (irangefn[hipass + 0x10000]) * scale) * hipass ; + const float hipass = data_fine[i][j] - data_coarse[i][j]; + rtengine::Color::SkinSatCbdl(data_fine[i][j] / 327.68f, hue[i][j], chrom[i][j], skinprot, scale, true, b_l, t_l, t_r); + buffer[i][j] += (1.f + (irangefn[hipass + 0x10000]) * scale) * hipass; } } - else + } else { #ifdef _OPENMP #pragma omp parallel for schedule(dynamic,16) #endif - for(int i = 0; i < height; i++) { - for(int j = 0; j < width; j++) { + for (int i = 0; i < height; i++) { + for (int j = 0; j < width; j++) { float scale = 1.f; - float hipass = (data_fine[i][j] - data_coarse[i][j]); - // These values are precalculated now - float modhue = hue[i][j]; - float modchro = chrom[i][j]; - Color::SkinSatCbdl ((data_fine[i][j]) / 327.68f, modhue, modchro, skinprotneg, scale, false, b_l, t_l, t_r); - float correct = irangefn[hipass + 0x10000]; + const float hipass = data_fine[i][j] - data_coarse[i][j]; + rtengine::Color::SkinSatCbdl(data_fine[i][j] / 327.68f, hue[i][j], chrom[i][j], skinprotneg, scale, false, b_l, t_l, t_r); + const float correct = irangefn[hipass + 0x10000]; if (scale == 1.f) {//image hard - buffer[i][j] += (1.f + (correct) * (factorHard)) * hipass ; + buffer[i][j] += (1.f + correct * factorHard) * hipass; } else { //image soft with scale < 1 ==> skin - buffer[i][j] += (1.f + (correct)) * hipass ; + buffer[i][j] += (1.f + correct) * hipass; } } } + } } - -void ImProcFunctions::idirpyr_eq_channelcam(float ** data_coarse, float ** data_fine, float ** buffer, int width, int height, int level, float mult[maxlevel], const double dirpyrThreshold, float ** l_a_h, float ** l_b_c, const double skinprot, float b_l, float t_l, float t_r) +void idirpyr_eq_channelcam(const float * const * data_coarse, const float * const * data_fine, float ** buffer, int width, int height, int level, float mult, const double dirpyrThreshold, const float * const * h_p, const float * const * C_p, const double skinprot, float b_l, float t_l, float t_r) { const float skinprotneg = -skinprot; - const float factorHard = (1.f - skinprotneg / 100.f); + const float factorHard = 1.f - skinprotneg / 100.f; - float offs; + LUTf irangefn(0x20000); + fillLut(irangefn, level, dirpyrThreshold, mult, skinprot); - if(skinprot == 0.f) { - offs = 0.f; + if (!skinprot) { +#ifdef _OPENMP + #pragma omp parallel for schedule(dynamic,16) +#endif + for (int i = 0; i < height; i++) { + for (int j = 0; j < width; j++) { + const float hipass = data_fine[i][j] - data_coarse[i][j]; + buffer[i][j] += irangefn[hipass + 0x10000] * hipass; + } + } + } else if (skinprot > 0.f) { +#ifdef _OPENMP + #pragma omp parallel for schedule(dynamic,16) +#endif + for (int i = 0; i < height; i++) { + for (int j = 0; j < width; j++) { + const float hipass = data_fine[i][j] - data_coarse[i][j]; + float scale = 1.f; + rtengine::Color::SkinSatCbdlCam(data_fine[i][j] / 327.68f, h_p[i][j] , C_p[i][j], skinprot, scale, true, b_l, t_l, t_r); + buffer[i][j] += (1.f + (irangefn[hipass + 0x10000]) * scale) * hipass; + } + } } else { - offs = -1.f; - } - - float multbis[maxlevel]; - - multbis[level] = mult[level]; //multbis to reduce artifacts for high values mult - - if(level == 4 && mult[level] > 1.f) { - multbis[level] = 1.f + 0.65f * (mult[level] - 1.f); - } - - if(level == 5 && mult[level] > 1.f) { - multbis[level] = 1.f + 0.45f * (mult[level] - 1.f); - } - - LUTf irangefn (0x20000); - { - const float noisehi = 1.33f * noise * dirpyrThreshold / expf(level * log(3.0)), noiselo = 0.66f * noise * dirpyrThreshold / expf(level * log(3.0)); - - //printf("level=%i multlev=%f noisehi=%f noiselo=%f skinprot=%f\n",level,mult[level], noisehi, noiselo, skinprot); - for (int i = 0; i < 0x20000; i++) { - if (abs(i - 0x10000) > noisehi || multbis[level] < 1.0) { - irangefn[i] = multbis[level] + offs; - } else { - if (abs(i - 0x10000) < noiselo) { - irangefn[i] = 1.f + offs ; - } else { - irangefn[i] = 1.f + offs + (multbis[level] - 1.f) * (noisehi - abs(i - 0x10000)) / (noisehi - noiselo + 0.01f) ; - } - } - } - } - - if(skinprot == 0.f) #ifdef _OPENMP #pragma omp parallel for schedule(dynamic,16) #endif - for(int i = 0; i < height; i++) { - for(int j = 0; j < width; j++) { - float hipass = (data_fine[i][j] - data_coarse[i][j]); - buffer[i][j] += irangefn[hipass + 0x10000] * hipass ; - } - } - else if(skinprot > 0.f) -#ifdef _OPENMP - #pragma omp parallel for schedule(dynamic,16) -#endif - for(int i = 0; i < height; i++) { - for(int j = 0; j < width; j++) { - float hipass = (data_fine[i][j] - data_coarse[i][j]); + for (int i = 0; i < height; i++) { + for (int j = 0; j < width; j++) { + const float hipass = data_fine[i][j] - data_coarse[i][j]; float scale = 1.f; - Color::SkinSatCbdlCam ((data_fine[i][j]) / 327.68f, l_a_h[i][j] , l_b_c[i][j], skinprot, scale, true, b_l, t_l, t_r); - buffer[i][j] += (1.f + (irangefn[hipass + 0x10000]) * scale) * hipass ; - } - } - else -#ifdef _OPENMP - #pragma omp parallel for schedule(dynamic,16) -#endif - for(int i = 0; i < height; i++) { - for(int j = 0; j < width; j++) { - float hipass = (data_fine[i][j] - data_coarse[i][j]); - float scale = 1.f; - float correct; - correct = irangefn[hipass + 0x10000]; - Color::SkinSatCbdlCam ((data_fine[i][j]) / 327.68f, l_a_h[i][j], l_b_c[i][j] , skinprotneg, scale, false, b_l, t_l, t_r); + const float correct = irangefn[hipass + 0x10000]; + rtengine::Color::SkinSatCbdlCam(data_fine[i][j] / 327.68f, h_p[i][j], C_p[i][j], skinprotneg, scale, false, b_l, t_l, t_r); if (scale == 1.f) {//image hard - buffer[i][j] += (1.f + (correct) * factorHard) * hipass ; - + buffer[i][j] += (1.f + correct * factorHard) * hipass; } else { //image soft - buffer[i][j] += (1.f + (correct)) * hipass ; + buffer[i][j] += (1.f + correct) * hipass; } } } + } +} - // if(gamutlab) { - // ImProcFunctions::badpixcam (buffer[i][j], 6.0, 10, 2);//for bad pixels - // } +} - /* if(gamutlab) {//disabled - float Lprov1=(buffer[i][j])/327.68f; - float R,G,B; - #ifdef _DEBUG - bool neg=false; - bool more_rgb=false; - //gamut control : Lab values are in gamut - Color::gamutLchonly(modhue,Lprov1,modchro, R, G, B, wip, highlight, 0.15f, 0.96f, neg, more_rgb); - #else - //gamut control : Lab values are in gamut - Color::gamutLchonly(modhue,Lprov1,modchro, R, G, B, wip, highlight, 0.15f, 0.96f); - #endif - // Color::gamutLchonly(modhue,Lprov1,modchro, R, G, B, wip, highlight, 0.15f, 0.96f);//gamut control in Lab mode ..not in CIECAM - buffer[i][j]=Lprov1*327.68f; - float2 sincosval = xsincosf(modhue); - l_a_h[i][j]=327.68f*modchro*sincosval.y; - l_b_c[i][j]=327.68f*modchro*sincosval.x; +namespace rtengine +{ + +extern const Settings* settings; + +void ImProcFunctions::dirpyr_equalizer(const float * const * src, float ** dst, int srcwidth, int srcheight, const float * const * l_a, const float * const * l_b, const double * mult, const double dirpyrThreshold, const double skinprot, float b_l, float t_l, float t_r, int scaleprev) +{ + //sequence of scales + constexpr int maxlevel = 6; + constexpr int scales[maxlevel] = {1, 2, 4, 8, 16, 32}; + const float atten123 = rtengine::LIM(settings->level123_cbdl, 0.f, 50.f); + const float atten0 = rtengine::LIM(settings->level0_cbdl, 0.f, 40.f); + + int lastlevel = maxlevel; + while (lastlevel > 0 && fabs(mult[lastlevel - 1] - 1) < 0.001) { + --lastlevel; + } + + if (lastlevel == 0) { + return; + } + + float multi[maxlevel]; + + for (int lv = 0; lv < maxlevel; ++lv) { + if (scales[lv] < scaleprev) { + const float factor = lv >= 1 ? atten123 : atten0; + multi[lv] = (factor * ((float) mult[lv] - 1.f) / 100.f) + 1.f; //modulate action if zoom < 100% + } else { + multi[lv] = mult[lv]; + } + } + + multi_array2D dirpyrlo (srcwidth, srcheight); + + dirpyr_channel(src, dirpyrlo[0], srcwidth, srcheight, 0, std::max(scales[0] / scaleprev, 1)); + + for (int level = 1; level < lastlevel; ++level) { + dirpyr_channel(dirpyrlo[level - 1], dirpyrlo[level], srcwidth, srcheight, level, std::max(scales[level] / scaleprev, 1)); + } + + array2D tmpHue, tmpChr; + + if (skinprot) { + // precalculate hue and chroma, use SSE, if available + // by precalculating these values we can greatly reduce the number of calculations in idirpyr_eq_channel() + // but we need two additional buffers for this preprocessing + tmpHue(srcwidth, srcheight); + tmpChr(srcwidth, srcheight); + +#ifdef _OPENMP + #pragma omp parallel +#endif + { +#ifdef __SSE2__ + const vfloat div = F2V(327.68f); +#endif +#ifdef _OPENMP + #pragma omp for +#endif + + for (int i = 0; i < srcheight; i++) { + int j = 0; +#ifdef __SSE2__ + for (; j < srcwidth - 3; j += 4) { + const vfloat lav = LVFU(l_a[i][j]); + const vfloat lbv = LVFU(l_b[i][j]); + STVFU(tmpHue[i][j], xatan2f(lbv, lav)); + STVFU(tmpChr[i][j], vsqrtf(SQRV(lbv) + SQRV(lav)) / div); + } +#endif + for (; j < srcwidth; j++) { + tmpHue[i][j] = xatan2f(l_b[i][j], l_a[i][j]); + tmpChr[i][j] = sqrtf(SQR((l_b[i][j])) + SQR((l_a[i][j]))) / 327.68f; + } } - */ + } + } + + // with the current implementation of idirpyr_eq_channel we can safely use the buffer from last level as buffer, saves some memory + float** buffer = dirpyrlo[lastlevel - 1]; + + for (int level = lastlevel - 1; level > 0; --level) { + idirpyr_eq_channel(dirpyrlo[level], dirpyrlo[level - 1], buffer, srcwidth, srcheight, level, multi[level], dirpyrThreshold, tmpHue, tmpChr, skinprot, b_l, t_l, t_r); + } + + idirpyr_eq_channel(dirpyrlo[0], dst, buffer, srcwidth, srcheight, 0, multi[0], dirpyrThreshold, tmpHue, tmpChr, skinprot, b_l, t_l, t_r); + +#ifdef _OPENMP + #pragma omp parallel for +#endif + + for (int i = 0; i < srcheight; i++) { + for (int j = 0; j < srcwidth; j++) { + dst[i][j] = buffer[i][j]; + } + } } -// float hipass = (data_fine[i][j]-data_coarse[i][j]); -// buffer[i][j] += irangefn[hipass+0x10000] * hipass ; +void ImProcFunctions::dirpyr_equalizercam(const CieImage *ncie, float ** src, float ** dst, int srcwidth, int srcheight, const float * const * h_p, const float * const * C_p, const double * mult, const double dirpyrThreshold, const double skinprot, float b_l, float t_l, float t_r, int scaleprev) +{ -#undef DIRWT_L -#undef DIRWT_AB + //sequence of scales + constexpr int maxlevel = 6; + constexpr int scales[maxlevel] = {1, 2, 4, 8, 16, 32}; + const float atten123 = rtengine::LIM(settings->level123_cbdl, 0.f, 50.f); + const float atten0 = rtengine::LIM(settings->level0_cbdl, 0.f, 40.f); -#undef NRWT_L -#undef NRWT_AB + int lastlevel = maxlevel; + while (fabs(mult[lastlevel - 1] - 1) < 0.001 && lastlevel > 0) { + --lastlevel; + } + if (lastlevel == 0) { + return; + } + + float multi[maxlevel]; + + for (int lv = 0; lv < maxlevel; lv++) { + if (scales[lv] < scaleprev) { + const float factor = lv >= 1 ? atten123 : atten0; + multi[lv] = (factor * ((float) mult[lv] - 1.f) / 100.f) + 1.f; + } else { + multi[lv] = mult[lv]; + } + } + + multi_array2D dirpyrlo (srcwidth, srcheight); + + dirpyr_channel(src, dirpyrlo[0], srcwidth, srcheight, 0, std::max(scales[0] / scaleprev, 1)); + + for (int level = 1; level < lastlevel; ++level) { + dirpyr_channel(dirpyrlo[level - 1], dirpyrlo[level], srcwidth, srcheight, level, std::max(scales[level] / scaleprev, 1)); + } + + // with the current implementation of idirpyr_eq_channel we can safely use the buffer from last level as buffer, saves some memory + float ** buffer = dirpyrlo[lastlevel - 1]; + + for (int level = lastlevel - 1; level > 0; --level) { + idirpyr_eq_channelcam(dirpyrlo[level], dirpyrlo[level - 1], buffer, srcwidth, srcheight, level, multi[level], dirpyrThreshold , h_p, C_p, skinprot, b_l, t_l, t_r); + } + + idirpyr_eq_channelcam(dirpyrlo[0], dst, buffer, srcwidth, srcheight, 0, multi[0], dirpyrThreshold, h_p, C_p, skinprot, b_l, t_l, t_r); + +#ifdef _OPENMP + #pragma omp parallel for schedule(dynamic,16) +#endif + + for (int i = 0; i < srcheight; i++) { + for (int j = 0; j < srcwidth; j++) { + if (ncie->J_p[i][j] > 8.f && ncie->J_p[i][j] < 92.f) { + dst[i][j] = buffer[i][j]; + } else { + dst[i][j] = src[i][j]; + } + } + } } +} diff --git a/rtengine/helpersse2.h b/rtengine/helpersse2.h index 74780cf48..e8c489b04 100644 --- a/rtengine/helpersse2.h +++ b/rtengine/helpersse2.h @@ -29,7 +29,7 @@ typedef __m128 vfloat; typedef __m128i vint2; // -#define LVF(x) _mm_load_ps((float*)&x) +#define LVF(x) _mm_load_ps((const float*)&x) #define LVFU(x) _mm_loadu_ps(&x) #define STVF(x,y) _mm_store_ps(&x,y) #define STVFU(x,y) _mm_storeu_ps(&x,y) diff --git a/rtengine/improcfun.cc b/rtengine/improcfun.cc index 85954abfa..1e6e3842b 100644 --- a/rtengine/improcfun.cc +++ b/rtengine/improcfun.cc @@ -1720,7 +1720,7 @@ void ImProcFunctions::ciecam_02float (CieImage* ncie, float adap, int pW, int pw float t_l = static_cast (params->dirpyrequalizer.hueskin.getTopLeft()) / 100.0f; float t_r = static_cast (params->dirpyrequalizer.hueskin.getTopRight()) / 100.0f; lab->deleteLab(); - dirpyr_equalizercam (ncie, ncie->sh_p, ncie->sh_p, ncie->W, ncie->H, ncie->h_p, ncie->C_p, params->dirpyrequalizer.mult, params->dirpyrequalizer.threshold, params->dirpyrequalizer.skinprotect, true, b_l, t_l, t_r, scale); //contrast by detail adapted to CIECAM + dirpyr_equalizercam (ncie, ncie->sh_p, ncie->sh_p, ncie->W, ncie->H, ncie->h_p, ncie->C_p, params->dirpyrequalizer.mult, params->dirpyrequalizer.threshold, params->dirpyrequalizer.skinprotect, b_l, t_l, t_r, scale); //contrast by detail adapted to CIECAM lab->reallocLab(); } diff --git a/rtengine/improcfun.h b/rtengine/improcfun.h index cd1650f6e..1083da735 100644 --- a/rtengine/improcfun.h +++ b/rtengine/improcfun.h @@ -332,11 +332,8 @@ public: float MadRgb(const float * DataList, int datalen); // pyramid wavelet - void dirpyr_equalizer(float ** src, float ** dst, int srcwidth, int srcheight, float ** l_a, float ** l_b, const double * mult, const double dirpyrThreshold, const double skinprot, float b_l, float t_l, float t_r, int scale); //Emil's directional pyramid wavelet - void dirpyr_equalizercam(CieImage* ncie, float ** src, float ** dst, int srcwidth, int srcheight, float ** h_p, float ** C_p, const double * mult, const double dirpyrThreshold, const double skinprot, bool execdir, float b_l, float t_l, float t_r, int scale); //Emil's directional pyramid wavelet - void dirpyr_channel(float ** data_fine, float ** data_coarse, int width, int height, int level, int scale); - void idirpyr_eq_channel(float ** data_coarse, float ** data_fine, float ** buffer, int width, int height, int level, float multi[6], const double dirpyrThreshold, float ** l_a_h, float ** l_b_c, const double skinprot, float b_l, float t_l, float t_r); - void idirpyr_eq_channelcam(float ** data_coarse, float ** data_fine, float ** buffer, int width, int height, int level, float multi[6], const double dirpyrThreshold, float ** l_a_h, float ** l_b_c, const double skinprot, float b_l, float t_l, float t_r); + void dirpyr_equalizer(const float * const * src, float ** dst, int srcwidth, int srcheight, const float * const * l_a, const float * const * l_b, const double * mult, double dirpyrThreshold, double skinprot, float b_l, float t_l, float t_r, int scale); //Emil's directional pyramid wavelet + void dirpyr_equalizercam(const CieImage* ncie, float ** src, float ** dst, int srcwidth, int srcheight, const float * const * h_p, const float * const * C_p, const double * mult, const double dirpyrThreshold, const double skinprot, float b_l, float t_l, float t_r, int scale); //Emil's directional pyramid wavelet void defringe(LabImage* lab); void defringecam(CieImage* ncie); void badpixcam(CieImage* ncie, double rad, int thr, int mode, float chrom, bool hotbad); From 4fedfb2b264b9f3aa8f4e01d3ee724e988dd3601 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Tue, 6 Aug 2019 22:10:38 +0200 Subject: [PATCH 11/15] cppcheck: further fixes --- rtengine/dcrop.cc | 147 ++++++++++++++++++------------------- rtengine/diagonalcurves.cc | 43 +++++------ rtengine/histmatching.cc | 2 +- rtengine/iptransform.cc | 7 +- rtgui/cropwindow.cc | 4 +- rtgui/metadatapanel.cc | 3 +- rtgui/mydiagonalcurve.cc | 6 -- rtgui/myflatcurve.cc | 3 +- rtgui/paramsedited.cc | 13 ++-- rtgui/thumbnail.cc | 7 +- 10 files changed, 101 insertions(+), 134 deletions(-) diff --git a/rtengine/dcrop.cc b/rtengine/dcrop.cc index 6acbc0047..69af056bf 100644 --- a/rtengine/dcrop.cc +++ b/rtengine/dcrop.cc @@ -204,10 +204,8 @@ void Crop::update(int todo) } int numtiles_W, numtiles_H, tilewidth, tileheight, tileWskip, tileHskip; - int kall = 2; - parent->ipf.Tile_calc(tilesize, overlap, kall, widIm, heiIm, numtiles_W, numtiles_H, tilewidth, tileheight, tileWskip, tileHskip); - kall = 0; + parent->ipf.Tile_calc(tilesize, overlap, 2, widIm, heiIm, numtiles_W, numtiles_H, tilewidth, tileheight, tileWskip, tileHskip); float *min_b = new float [9]; float *min_r = new float [9]; @@ -653,10 +651,9 @@ void Crop::update(int todo) if (todo & M_LINDENOISE) { if (skip == 1 && denoiseParams.enabled) { - int kall = 0; float nresi, highresi; - parent->ipf.RGB_denoise(kall, origCrop, origCrop, calclum, parent->denoiseInfoStore.ch_M, parent->denoiseInfoStore.max_r, parent->denoiseInfoStore.max_b, parent->imgsrc->isRAW(), /*Roffset,*/ denoiseParams, parent->imgsrc->getDirPyrDenoiseExpComp(), noiseLCurve, noiseCCurve, nresi, highresi); + parent->ipf.RGB_denoise(0, origCrop, origCrop, calclum, parent->denoiseInfoStore.ch_M, parent->denoiseInfoStore.max_r, parent->denoiseInfoStore.max_b, parent->imgsrc->isRAW(), /*Roffset,*/ denoiseParams, parent->imgsrc->getDirPyrDenoiseExpComp(), noiseLCurve, noiseCCurve, nresi, highresi); if (parent->adnListener) { parent->adnListener->noiseChanged(nresi, highresi); @@ -885,9 +882,6 @@ void Crop::update(int todo) if (skip == 1) { if ((params.colorappearance.enabled && !settings->autocielab) || (!params.colorappearance.enabled)) { parent->ipf.impulsedenoise(labnCrop); - } - - if ((params.colorappearance.enabled && !settings->autocielab) || (!params.colorappearance.enabled)) { parent->ipf.defringe(labnCrop); } @@ -900,7 +894,6 @@ void Crop::update(int todo) } // if (skip==1) { - WaveletParams WaveParams = params.wavelet; if (params.dirpyrequalizer.cbdlMethod == "aft") { if (((params.colorappearance.enabled && !settings->autocielab) || (!params.colorappearance.enabled))) { @@ -909,81 +902,81 @@ void Crop::update(int todo) } } - int kall = 0; - int minwin = min(labnCrop->W, labnCrop->H); - int maxlevelcrop = 10; - - // if(cp.mul[9]!=0)maxlevelcrop=10; - // adap maximum level wavelet to size of crop - if (minwin * skip < 1024) { - maxlevelcrop = 9; //sampling wavelet 512 - } - - if (minwin * skip < 512) { - maxlevelcrop = 8; //sampling wavelet 256 - } - - if (minwin * skip < 256) { - maxlevelcrop = 7; //sampling 128 - } - - if (minwin * skip < 128) { - maxlevelcrop = 6; - } - - if (minwin < 64) { - maxlevelcrop = 5; - } - - int realtile; - - if (params.wavelet.Tilesmethod == "big") { - realtile = 22; - } else /*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; - - parent->ipf.Tile_calc(tilesize, overlap, kall, labnCrop->W, labnCrop->H, numtiles_W, numtiles_H, tilewidth, tileheight, tileWskip, tileHskip); - //now we have tile dimensions, overlaps - //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% - int minsizetile = min(tilewidth, tileheight); - int maxlev2 = 10; - - if (minsizetile < 1024 && maxlevelcrop == 10) { - maxlev2 = 9; - } - - if (minsizetile < 512) { - maxlev2 = 8; - } - - if (minsizetile < 256) { - maxlev2 = 7; - } - - if (minsizetile < 128) { - maxlev2 = 6; - } - - int maxL = min(maxlev2, maxlevelcrop); - - if (parent->awavListener) { - parent->awavListener->wavChanged(float (maxL)); - } - if ((params.wavelet.enabled)) { + WaveletParams WaveParams = params.wavelet; + int kall = 0; + int minwin = min(labnCrop->W, labnCrop->H); + int maxlevelcrop = 10; + + // if(cp.mul[9]!=0)maxlevelcrop=10; + // adap maximum level wavelet to size of crop + if (minwin * skip < 1024) { + maxlevelcrop = 9; //sampling wavelet 512 + } + + if (minwin * skip < 512) { + maxlevelcrop = 8; //sampling wavelet 256 + } + + if (minwin * skip < 256) { + maxlevelcrop = 7; //sampling 128 + } + + if (minwin * skip < 128) { + maxlevelcrop = 6; + } + + if (minwin < 64) { + maxlevelcrop = 5; + } + + int realtile; + + if (params.wavelet.Tilesmethod == "big") { + realtile = 22; + } else /*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; + + parent->ipf.Tile_calc(tilesize, overlap, kall, labnCrop->W, labnCrop->H, numtiles_W, numtiles_H, tilewidth, tileheight, tileWskip, tileHskip); + //now we have tile dimensions, overlaps + //%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% + int minsizetile = min(tilewidth, tileheight); + int maxlev2 = 10; + + if (minsizetile < 1024 && maxlevelcrop == 10) { + maxlev2 = 9; + } + + if (minsizetile < 512) { + maxlev2 = 8; + } + + if (minsizetile < 256) { + maxlev2 = 7; + } + + if (minsizetile < 128) { + maxlev2 = 6; + } + + int maxL = min(maxlev2, maxlevelcrop); + + if (parent->awavListener) { + parent->awavListener->wavChanged(float (maxL)); + } + WavCurve wavCLVCurve; WavOpacityCurveRG waOpacityCurveRG; WavOpacityCurveBY waOpacityCurveBY; WavOpacityCurveW waOpacityCurveW; WavOpacityCurveWL waOpacityCurveWL; LUTf wavclCurve; - LUTu dummy; params.wavelet.getCurves(wavCLVCurve, waOpacityCurveRG, waOpacityCurveBY, waOpacityCurveW, waOpacityCurveWL); diff --git a/rtengine/diagonalcurves.cc b/rtengine/diagonalcurves.cc index b4c88fd68..dd85b87de 100644 --- a/rtengine/diagonalcurves.cc +++ b/rtengine/diagonalcurves.cc @@ -230,7 +230,6 @@ void DiagonalCurve::NURBS_set () poly_x.clear(); poly_y.clear(); unsigned int sc_xsize = j - 1; - j = 0; // adding the initial horizontal segment, if any if (x[0] > 0.) { @@ -314,18 +313,13 @@ inline void catmull_rom_spline(int n_points, double space = (t2-t1) / n_points; - double t; - int i; - double c, d, A1_x, A1_y, A2_x, A2_y, A3_x, A3_y; - double B1_x, B1_y, B2_x, B2_y, C_x, C_y; - res_x.push_back(p1_x); res_y.push_back(p1_y); // special case, a segment at 0 or 1 is computed exactly if (p1_y == p2_y && (p1_y == 0 || p1_y == 1)) { - for (i = 1; i < n_points-1; ++i) { - t = p1_x + space * i; + for (int i = 1; i < n_points-1; ++i) { + double t = p1_x + space * i; if (t >= p2_x) { break; } @@ -333,38 +327,38 @@ inline void catmull_rom_spline(int n_points, res_y.push_back(p1_y); } } else { - for (i = 1; i < n_points-1; ++i) { - t = t1 + space * i; + for (int i = 1; i < n_points-1; ++i) { + double t = t1 + space * i; - c = (t1 - t)/(t1 - t0); - d = (t - t0)/(t1 - t0); - A1_x = c * p0_x + d * p1_x; - A1_y = c * p0_y + d * p1_y; + double c = (t1 - t)/(t1 - t0); + double d = (t - t0)/(t1 - t0); + double A1_x = c * p0_x + d * p1_x; + double A1_y = c * p0_y + d * p1_y; c = (t2 - t)/(t2 - t1); d = (t - t1)/(t2 - t1); - A2_x = c * p1_x + d * p2_x; - A2_y = c * p1_y + d * p2_y; + double A2_x = c * p1_x + d * p2_x; + double A2_y = c * p1_y + d * p2_y; c = (t3 - t)/(t3 - t2); d = (t - t2)/(t3 - t2); - A3_x = c * p2_x + d * p3_x; - A3_y = c * p2_y + d * p3_y; + double A3_x = c * p2_x + d * p3_x; + double A3_y = c * p2_y + d * p3_y; c = (t2 - t)/(t2 - t0); d = (t - t0)/(t2 - t0); - B1_x = c * A1_x + d * A2_x; - B1_y = c * A1_y + d * A2_y; + double B1_x = c * A1_x + d * A2_x; + double B1_y = c * A1_y + d * A2_y; c = (t3 - t)/(t3 - t1); d = (t - t1)/(t3 - t1); - B2_x = c * A2_x + d * A3_x; - B2_y = c * A2_y + d * A3_y; + double B2_x = c * A2_x + d * A3_x; + double B2_y = c * A2_y + d * A3_y; c = (t2 - t)/(t2 - t1); d = (t - t1)/(t2 - t1); - C_x = c * B1_x + d * B2_x; - C_y = c * B1_y + d * B2_y; + double C_x = c * B1_x + d * B2_x; + double C_y = c * B1_y + d * B2_y; res_x.push_back(C_x); res_y.push_back(C_y); @@ -512,7 +506,6 @@ double DiagonalCurve::getVal (double t) const ++d; } return LIM01(*(poly_y.begin() + d)); - break; } case DCT_NURBS : { diff --git a/rtengine/histmatching.cc b/rtengine/histmatching.cc index e48f2017a..f9268ea5d 100644 --- a/rtengine/histmatching.cc +++ b/rtengine/histmatching.cc @@ -329,8 +329,8 @@ 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)); - int cx = 0, cy = 0; if (std::abs(thumb_ratio - target_ratio) > 0.01) { + int cx = 0, cy = 0; if (thumb_ratio > target_ratio) { // crop the height int ch = th - (tw * float(sh) / float(sw)); diff --git a/rtengine/iptransform.cc b/rtengine/iptransform.cc index beca624a8..5b1e7c458 100644 --- a/rtengine/iptransform.cc +++ b/rtengine/iptransform.cc @@ -435,12 +435,7 @@ static void calcGradientParams (int oW, int oH, const GradientParams& gradient, if (gp.transpose) { gp.bright_top = !gp.bright_top; - } - - if (gp.transpose) { - int tmp = w; - w = h; - h = tmp; + std::swap(w, h); } gp.scale = 1.0 / pow (2, gradient_stops); diff --git a/rtgui/cropwindow.cc b/rtgui/cropwindow.cc index b29aa5eeb..5839a5edb 100644 --- a/rtgui/cropwindow.cc +++ b/rtgui/cropwindow.cc @@ -2198,8 +2198,6 @@ void CropWindow::updateHoveredPicker (rtengine::Coord *imgPos) } rtengine::Coord cropPos; - float r=0.f, g=0.f, b=0.f; - float rpreview=0.f, gpreview=0.f, bpreview=0.f; if (imgPos) { imageCoordToCropImage(imgPos->x, imgPos->y, cropPos.x, cropPos.y); hoveredPicker->setPosition (*imgPos); @@ -2215,6 +2213,8 @@ void CropWindow::updateHoveredPicker (rtengine::Coord *imgPos) MyMutex::MyLock lock(cropHandler.cimg); if (validity == LockableColorPicker::Validity::INSIDE) { + float r=0.f, g=0.f, b=0.f; + float rpreview=0.f, gpreview=0.f, bpreview=0.f; cropHandler.colorPick(cropPos, r, g, b, rpreview, gpreview, bpreview, hoveredPicker->getSize()); hoveredPicker->setRGB (r, g, b, rpreview, gpreview, bpreview); } diff --git a/rtgui/metadatapanel.cc b/rtgui/metadatapanel.cc index ee97a7dfe..fed7622ea 100644 --- a/rtgui/metadatapanel.cc +++ b/rtgui/metadatapanel.cc @@ -26,9 +26,8 @@ using namespace rtengine; using namespace rtengine::procparams; -MetaDataPanel::MetaDataPanel() +MetaDataPanel::MetaDataPanel() : EvMetaDataMode(ProcEventMapper::getInstance()->newEvent(M_VOID, "HISTORY_MSG_METADATA_MODE")) { - EvMetaDataMode = ProcEventMapper::getInstance()->newEvent(M_VOID, "HISTORY_MSG_METADATA_MODE"); Gtk::HBox *box = Gtk::manage(new Gtk::HBox()); box->pack_start(*Gtk::manage(new Gtk::Label(M("TP_METADATA_MODE") + ": ")), Gtk::PACK_SHRINK, 4); diff --git a/rtgui/mydiagonalcurve.cc b/rtgui/mydiagonalcurve.cc index a3e7b9375..8dc8aca56 100644 --- a/rtgui/mydiagonalcurve.cc +++ b/rtgui/mydiagonalcurve.cc @@ -637,13 +637,8 @@ bool MyDiagonalCurve::handleEvents (GdkEvent* event) setDirty(true); draw (lit_point); new_type = CSArrow; - retval = true; } } - - if (buttonPressed) { - retval = true; - } } else { // if (edited_point > -1) if (event->button.button == 3) { // do we edit another point? @@ -679,7 +674,6 @@ bool MyDiagonalCurve::handleEvents (GdkEvent* event) newBoundaries.at(1).minVal = 0.; newBoundaries.at(1).maxVal = 1.; - retval = true; editedPos.at(0) = curve.x.at(edited_point); editedPos.at(1) = curve.y.at(edited_point); coordinateAdjuster->switchAdjustedPoint(editedPos, newBoundaries); diff --git a/rtgui/myflatcurve.cc b/rtgui/myflatcurve.cc index 9796141d5..ebd0a9d0c 100644 --- a/rtgui/myflatcurve.cc +++ b/rtgui/myflatcurve.cc @@ -556,7 +556,7 @@ bool MyFlatCurve::getHandles(int n) if (!n) { // first point, the left handle is then computed with the last point's right handle prevX = curve.x.at(N - 1) - 1.0; - nextX = curve.x.at(n + 1); + nextX = curve.x.at(1); } else if (n == N - 1) { // last point, the right handle is then computed with the first point's left handle prevX = curve.x.at(n - 1); @@ -745,7 +745,6 @@ bool MyFlatCurve::handleEvents (GdkEvent* event) newBoundaries.at(2).maxVal = 1.; newBoundaries.at(3).minVal = 0.; newBoundaries.at(3).maxVal = 1.; - retval = true; editedPos.at(0) = curve.x.at(edited_point); editedPos.at(1) = curve.y.at(edited_point); editedPos.at(2) = curve.leftTangent.at(edited_point); diff --git a/rtgui/paramsedited.cc b/rtgui/paramsedited.cc index 952b08161..cb3d4151c 100644 --- a/rtgui/paramsedited.cc +++ b/rtgui/paramsedited.cc @@ -1112,20 +1112,17 @@ void ParamsEdited::initFrom(const std::vector& wavelet.exptoning = wavelet.exptoning && p.wavelet.exptoning == other.wavelet.exptoning; wavelet.expnoise = wavelet.expnoise && p.wavelet.expnoise == other.wavelet.expnoise; - for (int i = 0; i < 9; i++) { - wavelet.c[i] = wavelet.c[i] && p.wavelet.c[i] == other.wavelet.c[i]; - } - - for (int i = 0; i < 9; i++) { - wavelet.ch[i] = wavelet.ch[i] && p.wavelet.ch[i] == other.wavelet.ch[i]; + for (int level = 0; level < 9; ++level) { + wavelet.c[level] = wavelet.c[level] && p.wavelet.c[level] == other.wavelet.c[level]; + wavelet.ch[level] = wavelet.ch[level] && p.wavelet.ch[level] == other.wavelet.ch[level]; } dirpyrequalizer.enabled = dirpyrequalizer.enabled && p.dirpyrequalizer.enabled == other.dirpyrequalizer.enabled; dirpyrequalizer.gamutlab = dirpyrequalizer.gamutlab && p.dirpyrequalizer.gamutlab == other.dirpyrequalizer.gamutlab; dirpyrequalizer.cbdlMethod = dirpyrequalizer.cbdlMethod && p.dirpyrequalizer.cbdlMethod == other.dirpyrequalizer.cbdlMethod; - for (int i = 0; i < 6; i++) { - dirpyrequalizer.mult[i] = dirpyrequalizer.mult[i] && p.dirpyrequalizer.mult[i] == other.dirpyrequalizer.mult[i]; + for (int level = 0; level < 6; ++level) { + dirpyrequalizer.mult[level] = dirpyrequalizer.mult[level] && p.dirpyrequalizer.mult[level] == other.dirpyrequalizer.mult[level]; } dirpyrequalizer.threshold = dirpyrequalizer.threshold && p.dirpyrequalizer.threshold == other.dirpyrequalizer.threshold; diff --git a/rtgui/thumbnail.cc b/rtgui/thumbnail.cc index eedff3029..79291c423 100644 --- a/rtgui/thumbnail.cc +++ b/rtgui/thumbnail.cc @@ -232,8 +232,6 @@ const ProcParams& Thumbnail::getProcParamsU () rtengine::procparams::ProcParams* Thumbnail::createProcParamsForUpdate(bool returnParams, bool force, bool flaggingMode) { - static int index = 0; // Will act as unique identifier during the session - // try to load the last saved parameters from the cache or from the paramfile file ProcParams* ldprof = nullptr; @@ -285,6 +283,7 @@ rtengine::procparams::ProcParams* Thumbnail::createProcParamsForUpdate(bool retu imageMetaData = rtengine::FramesMetaData::fromFile (fname, nullptr, true); } + static int index = 0; // Will act as unique identifier during the session Glib::ustring tmpFileName( Glib::build_filename(options.cacheBaseDir, Glib::ustring::compose("CPB_temp_%1.txt", index++)) ); const rtexif::TagDirectory* exifDir = nullptr; @@ -1020,9 +1019,7 @@ int Thumbnail::getRank () const void Thumbnail::setRank (int rank) { - if (pparams->rank != rank) { - pparams->rank = rank; - } + pparams->rank = rank; pparamsValid = true; } From 4c99c9cf014e10f40b79ccb460cdbcebfc8d3b54 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Wed, 7 Aug 2019 15:32:52 +0200 Subject: [PATCH 12/15] cppcheck: further fixes --- rtengine/dcp.cc | 14 ------ rtengine/ex1simple.cc | 94 ---------------------------------------- rtengine/hilite_recon.cc | 25 +++++------ rtengine/ipresize.cc | 71 ++++++++++++++---------------- rtengine/rtetest.cc | 82 ----------------------------------- rtengine/tmo_fattal02.cc | 14 +++--- 6 files changed, 52 insertions(+), 248 deletions(-) delete mode 100644 rtengine/ex1simple.cc delete mode 100644 rtengine/rtetest.cc diff --git a/rtengine/dcp.cc b/rtengine/dcp.cc index 56855b604..6c948717a 100644 --- a/rtengine/dcp.cc +++ b/rtengine/dcp.cc @@ -334,8 +334,6 @@ double xyCoordToTemperature(const std::array& white_xy) // Search for line pair coordinate is between. double last_dt = 0.0; - double last_dv = 0.0; - double last_du = 0.0; for (uint32_t index = 1; index <= 30; ++index) { // Convert slope to delta-u and delta-v, with length 1. @@ -371,23 +369,11 @@ double xyCoordToTemperature(const std::array& white_xy) // Interpolate the temperature. res = 1.0e6 / (temp_table[index - 1].r * f + temp_table[index].r * (1.0 - f)); - - // Find delta from black body point to test coordinate. - uu = u - (temp_table [index - 1].u * f + temp_table [index].u * (1.0 - f)); - vv = v - (temp_table [index - 1].v * f + temp_table [index].v * (1.0 - f)); - // Interpolate vectors along slope. - du = du * (1.0 - f) + last_du * f; - dv = dv * (1.0 - f) + last_dv * f; - len = sqrt (du * du + dv * dv); - du /= len; - dv /= len; break; } // Try next line pair. last_dt = dt; - last_du = du; - last_dv = dv; } return res; diff --git a/rtengine/ex1simple.cc b/rtengine/ex1simple.cc deleted file mode 100644 index ddaa89177..000000000 --- a/rtengine/ex1simple.cc +++ /dev/null @@ -1,94 +0,0 @@ -/* - * This file is part of RawTherapee. - * - * Copyright (c) 2004-2010 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 "rtengine.h" -#include -//#include -#include - -class PListener : - public rtengine::ProgressListener -{ -public: - void setProgressStr(const Glib::ustring& str) - { - std::cout << str << std::endl; - } - void setProgress (double p) - { - std::cout << p << std::endl; - } - void setProgressState(bool inProcessing) - { - } - void error(const Glib::ustring& descr) - { - } -}; - -int main (int argc, char* argv[]) -{ - if (argc < 4) { - std::cout << "Usage: rtcmd " << std::endl; - exit(1); - } - - Glib::thread_init (); - - // create and fill settings - rtengine::Settings* s = rtengine::Settings::create (); - s->demosaicMethod = "hphd"; - s->colorCorrectionSteps = 2; - s->iccDirectory = ""; - s->colorimetricIntent = 1; - s->monitorProfile = ""; - // init rtengine - rtengine::init (s); - // the settings can be modified later through the "s" pointer without calling any api function - - // Create a listener object. Any class is appropriate that inherits from rtengine::ProgressListener - PListener pl; - - // Load the image given in the first command line parameter - rtengine::InitialImage* ii; - int errorCode; - ii = rtengine::InitialImage::load (argv[1], true, errorCode, &pl); - - if (!ii) { - ii = rtengine::InitialImage::load (argv[1], false, errorCode, &pl); - } - - if (!ii) { - std::cout << "Input file not supported." << std::endl; - exit(2); - } - - // create an instance of ProcParams structure that holds the image processing settings. You find the memory map in a separate file and the non-basic types like strings and vectors can be manipulated through helper functions - rtengine::procparams::ProcParams params; - params.load (argv[2]); - - /* First, simplest scenario. Develop image and save it in a file */ - // create a processing job with the loaded image and the current processing parameters - rtengine::ProcessingJob* job = ProcessingJob::create (i, params); - // process image. The error is given back in errorcode. - rtengine::IImage16* res = rtengine::processImage (job, errorCode, &pl); - // save image to disk - res->saveToFile (argv[3]); - // through "res" you can access width/height and pixel data, too -} - diff --git a/rtengine/hilite_recon.cc b/rtengine/hilite_recon.cc index b0a7e6229..7134ac34f 100644 --- a/rtengine/hilite_recon.cc +++ b/rtengine/hilite_recon.cc @@ -970,8 +970,8 @@ void RawImageSource::HLRecovery_inpaint(float** red, float** green, float** blue for (int c = 0; c < 3; ++c) { lab[i2][c] = 0; - for (int j = 0; j < 3; ++j) { - lab[i2][c] += trans[c][j] * cam[i2][j]; + for (int j2 = 0; j2 < 3; ++j2) { + lab[i2][c] += trans[c][j2] * cam[i2][j2]; } } @@ -996,8 +996,8 @@ void RawImageSource::HLRecovery_inpaint(float** red, float** green, float** blue for (int c = 0; c < 3; ++c) { cam[0][c] = 0.f; - for (int j = 0; j < 3; ++j) { - cam[0][c] += itrans[c][j] * lab[0][j]; + for (int j2 = 0; j2 < 3; ++j2) { + cam[0][c] += itrans[c][j2] * lab[0][j2]; } } @@ -1081,12 +1081,11 @@ void RawImageSource::HLRecovery_inpaint(float** red, float** green, float** blue //now correct clipped channels if (pixel[0] > max_f[0] && pixel[1] > max_f[1] && pixel[2] > max_f[2]) { //all channels clipped - const float Y = 0.299f * clipfix[0] + 0.587f * clipfix[1] + 0.114f * clipfix[2]; - const float factor = whitept / Y; - red[i + miny][j + minx] = clipfix[0] * factor; - green[i + miny][j + minx] = clipfix[1] * factor; - blue[i + miny][j + minx] = clipfix[2] * factor; + const float mult = whitept / (0.299f * clipfix[0] + 0.587f * clipfix[1] + 0.114f * clipfix[2]); + red[i + miny][j + minx] = clipfix[0] * mult; + green[i + miny][j + minx] = clipfix[1] * mult; + blue[i + miny][j + minx] = clipfix[2] * mult; } else {//some channels clipped const float notclipped[3] = { pixel[0] <= max_f[0] ? 1.f : 0.f, @@ -1113,11 +1112,11 @@ void RawImageSource::HLRecovery_inpaint(float** red, float** green, float** blue Y = 0.299f * red[i + miny][j + minx] + 0.587f * green[i + miny][j + minx] + 0.114f * blue[i + miny][j + minx]; if (Y > whitept) { - const float factor = whitept / Y; + const float mult = whitept / Y; - red[i + miny][j + minx] *= factor; - green[i + miny][j + minx] *= factor; - blue[i + miny][j + minx] *= factor; + red[i + miny][j + minx] *= mult; + green[i + miny][j + minx] *= mult; + blue[i + miny][j + minx] *= mult; } } } diff --git a/rtengine/ipresize.cc b/rtengine/ipresize.cc index 823beb23e..2a66e68cb 100644 --- a/rtengine/ipresize.cc +++ b/rtengine/ipresize.cc @@ -186,8 +186,8 @@ void ImProcFunctions::Lanczos (const Imagefloat* src, Imagefloat* dst, float sca void ImProcFunctions::Lanczos (const LabImage* src, LabImage* dst, float scale) { const float delta = 1.0f / scale; - const float a = 3.0f; - const float sc = min (scale, 1.0f); + constexpr float a = 3.0f; + const float sc = min(scale, 1.0f); const int support = static_cast (2.0f * a / sc) + 1; // storage for precomputed parameters for horizontal interpolation @@ -268,66 +268,61 @@ void ImProcFunctions::Lanczos (const LabImage* src, LabImage* dst, float scale) } // Do vertical interpolation. Store results. + int j = 0; #ifdef __SSE2__ - int j; __m128 Lv, av, bv, wkv; for (j = 0; j < src->W - 3; j += 4) { - Lv = _mm_setzero_ps(); - av = _mm_setzero_ps(); - bv = _mm_setzero_ps(); + Lv = ZEROV; + av = ZEROV; + bv = ZEROV; for (int ii = ii0; ii < ii1; ii++) { int k = ii - ii0; - wkv = _mm_set1_ps (w[k]); - Lv += wkv * LVFU (src->L[ii][j]); - av += wkv * LVFU (src->a[ii][j]); - bv += wkv * LVFU (src->b[ii][j]); + wkv = F2V(w[k]); + Lv += wkv * LVFU(src->L[ii][j]); + av += wkv * LVFU(src->a[ii][j]); + bv += wkv * LVFU(src->b[ii][j]); } - STVF (lL[j], Lv); - STVF (la[j], av); - STVF (lb[j], bv); + STVF(lL[j], Lv); + STVF(la[j], av); + STVF(lb[j], bv); } - -#else - int j = 0; #endif - for (; j < src->W; j++) { - float L = 0.0f, a = 0.0f, b = 0.0f; + for (; j < src->W; ++j) { + float Ll = 0.0f, La = 0.0f, Lb = 0.0f; - for (int ii = ii0; ii < ii1; ii++) { + for (int ii = ii0; ii < ii1; ++ii) { int k = ii - ii0; - L += w[k] * src->L[ii][j]; - a += w[k] * src->a[ii][j]; - b += w[k] * src->b[ii][j]; + Ll += w[k] * src->L[ii][j]; + La += w[k] * src->a[ii][j]; + Lb += w[k] * src->b[ii][j]; } - lL[j] = L; - la[j] = a; - lb[j] = b; + lL[j] = Ll; + la[j] = La; + lb[j] = Lb; } // Do horizontal interpolation - for (int j = 0; j < dst->W; j++) { + for (int x = 0; x < dst->W; ++x) { + float * wh = wwh + support * x; + float Ll = 0.0f, La = 0.0f, Lb = 0.0f; - float * wh = wwh + support * j; + for (int jj = jj0[x]; jj < jj1[x]; ++jj) { + int k = jj - jj0[x]; - float L = 0.0f, a = 0.0f, b = 0.0f; - - for (int jj = jj0[j]; jj < jj1[j]; jj++) { - int k = jj - jj0[j]; - - L += wh[k] * lL[jj]; - a += wh[k] * la[jj]; - b += wh[k] * lb[jj]; + Ll += wh[k] * lL[jj]; + La += wh[k] * la[jj]; + Lb += wh[k] * lb[jj]; } - dst->L[i][j] = L; - dst->a[i][j] = a; - dst->b[i][j] = b; + dst->L[i][x] = Ll; + dst->a[i][x] = La; + dst->b[i][x] = Lb; } } } diff --git a/rtengine/rtetest.cc b/rtengine/rtetest.cc deleted file mode 100644 index bd81dbb0d..000000000 --- a/rtengine/rtetest.cc +++ /dev/null @@ -1,82 +0,0 @@ -/* - * This file is part of RawTherapee. - * - * Copyright (c) 2004-2010 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 "rtengine.h" -#include -//#include -#include - -class PListener : - public rtengine::ProgressListener -{ -public: - void setProgressStr(const Glib::ustring& str) - { - std::cout << str << std::endl; - } - void setProgress(double p) - { - std::cout << p << std::endl; - } - void setProgressState(bool inProcessing) - { - } - void error(const Glib::ustring& descr) - { - } -}; - -int main (int argc, char* argv[]) -{ - if (argc < 4) { - std::cout << "Usage: rtcmd " << std::endl; - exit(1); - } - - rtengine::Settings s; - s.demosaicMethod = "hphd"; - s.colorCorrectionSteps = 2; - s.iccDirectory = ""; - s.colorimetricIntent = 1; - s.monitorProfile = ""; - - Glib::thread_init (); - rtengine::init (s, ""); - PListener pl; - - rtengine::InitialImage* ii; - int errorCode; - ii = rtengine::InitialImage::load (argv[1], true, errorCode, &pl); - - if (!ii) { - ii = rtengine::InitialImage::load (argv[1], false, errorCode, &pl); - } - - if (!ii) { - std::cout << "Input file not supported." << std::endl; - exit(2); - } - - rtengine::procparams::ProcParams params; - params.load (argv[2]); - - rtengine::ProcessingJob* job = ProcessingJob::create (ii, params); - rtengine::IImage16* res = rtengine::processImage (job, errorCode, &pl); - res->saveToFile (argv[3]); -} - diff --git a/rtengine/tmo_fattal02.cc b/rtengine/tmo_fattal02.cc index 32755319e..76da1f03d 100644 --- a/rtengine/tmo_fattal02.cc +++ b/rtengine/tmo_fattal02.cc @@ -476,14 +476,14 @@ void tmo_fattal02 (size_t width, Array2Df* H = new Array2Df (width, height); float temp = 100.f / maxLum; - float eps = 1e-4f; #ifdef _OPENMP #pragma omp parallel if(multithread) #endif { + const float eps = 1e-4f; #ifdef __SSE2__ - vfloat epsv = F2V (eps); - vfloat tempv = F2V (temp); + const vfloat epsv = F2V(eps); + const vfloat tempv = F2V(temp); #endif #ifdef _OPENMP #pragma omp for schedule(dynamic,16) @@ -926,13 +926,13 @@ void solve_pde_fft (Array2Df *F, Array2Df *U, Array2Df *buf, bool multithread)/* // a solution which has no positive values: U_new(x,y)=U(x,y)-max // (not really needed but good for numerics as we later take exp(U)) //DEBUG_STR << "solve_pde_fft: removing constant from solution" << std::endl; - float max = 0.f; + float maxVal = 0.f; #ifdef _OPENMP - #pragma omp parallel for reduction(max:max) if(multithread) + #pragma omp parallel for reduction(max:maxVal) if(multithread) #endif for (int i = 0; i < width * height; i++) { - max = std::max (max, (*U) (i)); + maxVal = std::max(maxVal, (*U)(i)); } #ifdef _OPENMP @@ -940,7 +940,7 @@ void solve_pde_fft (Array2Df *F, Array2Df *U, Array2Df *buf, bool multithread)/* #endif for (int i = 0; i < width * height; i++) { - (*U) (i) -= max; + (*U) (i) -= maxVal; } } From cf1d7e5920368238b244f9bf4dc646cac826abb2 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Wed, 7 Aug 2019 16:53:44 +0200 Subject: [PATCH 13/15] Update profilestorecombobox.cc Do not use std::move on return --- rtgui/profilestorecombobox.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rtgui/profilestorecombobox.cc b/rtgui/profilestorecombobox.cc index 96bbc32fa..53756f342 100644 --- a/rtgui/profilestorecombobox.cc +++ b/rtgui/profilestorecombobox.cc @@ -334,7 +334,7 @@ Gtk::TreeIter ProfileStoreComboBox::getRowFromLabel (Glib::ustring name) const ProfileStoreEntry *pse = currRow[methodColumns.profileStoreEntry]; if (pse->label == name) { - return std::move(currRow); + return currRow; } } } From d765c06cf44ab8167e14c7cbc32a37c81662d366 Mon Sep 17 00:00:00 2001 From: Ingo Weyrich Date: Thu, 8 Aug 2019 11:43:47 +0200 Subject: [PATCH 14/15] 2 bugs in colour toning, fixes #5403 --- rtengine/improcfun.cc | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/rtengine/improcfun.cc b/rtengine/improcfun.cc index 1e6e3842b..8d6272a06 100644 --- a/rtengine/improcfun.cc +++ b/rtengine/improcfun.cc @@ -2255,7 +2255,7 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer bool hasColorToningLabGrid = params->colorToning.enabled && params->colorToning.method == "LabGrid"; // float satLimit = float(params->colorToning.satProtectionThreshold)/100.f*0.7f+0.3f; // float satLimitOpacity = 1.f-(float(params->colorToning.saturatedOpacity)/100.f); - float strProtect = (float (params->colorToning.strength) / 100.f); + float strProtect = pow_F((float (params->colorToning.strength) / 100.f), 0.4f); /* // Debug output - Color LUTf points @@ -2793,7 +2793,6 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer const float krh = rh / (rh + gh + bh); const float kgh = gh / (rh + gh + bh); const float kbh = bh / (rh + gh + bh); - strProtect = pow_F(strProtect, 0.4f); constexpr int mode = 0; for (int i = istart, ti = 0; i < tH; i++, ti++) { for (int j = jstart, tj = 0; j < tW; j++, tj++) { @@ -2806,7 +2805,6 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer else if (params->colorToning.method == "Splitco") { constexpr float reducac = 0.3f; constexpr int mode = 0; - strProtect = pow_F(strProtect, 0.4f); for (int i = istart, ti = 0; i < tH; i++, ti++) { for (int j = jstart, tj = 0; j < tW; j++, tj++) { const float r = rtemp[ti * TS + tj]; @@ -3483,7 +3481,6 @@ void ImProcFunctions::rgbProc (Imagefloat* working, LabImage* lab, PipetteBuffer const float krh = rh / (rh + gh + bh); const float kgh = gh / (rh + gh + bh); const float kbh = bh / (rh + gh + bh); - strProtect = pow_F(strProtect, 0.4f); constexpr int mode = 1; #ifdef _OPENMP #pragma omp parallel for schedule(dynamic, 5) From 82e329ca836c2372456bea98c4141b1db1f10e96 Mon Sep 17 00:00:00 2001 From: Roel Baars <6567747+Thanatomanic@users.noreply.github.com> Date: Thu, 8 Aug 2019 13:10:55 +0200 Subject: [PATCH 15/15] Fix SHM-color toning behavior in shadows. Fixes #5403 --- rtengine/improcfun.cc | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/rtengine/improcfun.cc b/rtengine/improcfun.cc index 8d6272a06..23dc4b1ba 100644 --- a/rtengine/improcfun.cc +++ b/rtengine/improcfun.cc @@ -3785,11 +3785,12 @@ void ImProcFunctions::toningsmh(float r, float g, float b, float &ro, float &go, { const float corr = 20000.f * RedLow * kl * rlo; + if (RedLow > 0.f) { + r += corr; + } else { g -= corr; b -= corr; - } else { - r += corr; } // r = CLIP(r); @@ -3799,27 +3800,28 @@ void ImProcFunctions::toningsmh(float r, float g, float b, float &ro, float &go, { const float corr = 20000.f * GreenLow * kl * rlo; + if (GreenLow > 0.f) { + g += corr; + } else { r -= corr; b -= corr; - } else { - g += corr; } // r = CLIP(r); - // b = CLIP(b); // g = CLIP(g); + // b = CLIP(b); } { - const float corr = 20000.f * BlueLow * kl * rlob; + const float corr = 20000.f * BlueLow * kl * rlo; if (BlueLow > 0.f) { + b += corr; + } else { r -= corr; g -= corr; - } else { - b += corr; } // r = CLIP(r);