with the following function, I am trying to plot the calculated histogram of a 3 channel photo but when I use the function multiple times it only shows the windows of the last time that it was called and does not show previous ones. How can I change it to show all windows?
void showHistogram(std::vector<cv::Mat>& hists, vector<string> titles)
{
// Min/Max computation
double hmax[3] = { 0,0,0 };
double min;
cv::minMaxLoc(hists[0], &min, &hmax[0]);
cv::minMaxLoc(hists[1], &min, &hmax[1]);
cv::minMaxLoc(hists[2], &min, &hmax[2]);
std::string wname[3] = { "blue", "green", "red" };
cv::Scalar colors[3] = { cv::Scalar(255,0,0), cv::Scalar(0,255,0),
cv::Scalar(0,0,255) };
std::vector<cv::Mat> canvas(hists.size());
// Display each histogram in a canvas
for (int i = 0, end = hists.size(); i < end; i )
{
canvas[i] = cv::Mat::ones(125, hists[0].rows, CV_8UC3);
for (int j = 0, rows = canvas[i].rows; j < hists[0].rows - 1; j )
{
cv::line(
canvas[i],
cv::Point(j, rows),
cv::Point(j, rows - (hists[i].at<float>(j) * rows / hmax[i])),
hists.size() == 1 ? cv::Scalar(200, 200, 200) : colors[i],
1, 8, 0
);
}
if (hists.size() == 3) {
namedWindow(titles[i]);
cv::imshow(titles[i], canvas[i]);
}
else {
cv::imshow(hists.size() == 1 ? "value" : wname[i], canvas[i]);
}
}
}
CodePudding user response:
Only the last image is shown when the same window names are used, so you should add an unique thing to the window name to prevent them to be the same.
For example:
#include <sstream>
void showHistogram(std::vector<cv::Mat>& hists, vector<string> titles)
{
static int windowId = 0;
std::stringstream ss;
ss << (windowId ); // generate an unique ID for each call
// Min/Max computation
double hmax[3] = { 0,0,0 };
double min;
cv::minMaxLoc(hists[0], &min, &hmax[0]);
cv::minMaxLoc(hists[1], &min, &hmax[1]);
cv::minMaxLoc(hists[2], &min, &hmax[2]);
std::string wname[3] = { "blue", "green", "red" };
cv::Scalar colors[3] = { cv::Scalar(255,0,0), cv::Scalar(0,255,0),
cv::Scalar(0,0,255) };
std::vector<cv::Mat> canvas(hists.size());
// Display each histogram in a canvas
for (int i = 0, end = hists.size(); i < end; i )
{
canvas[i] = cv::Mat::ones(125, hists[0].rows, CV_8UC3);
for (int j = 0, rows = canvas[i].rows; j < hists[0].rows - 1; j )
{
cv::line(
canvas[i],
cv::Point(j, rows),
cv::Point(j, rows - (hists[i].at<float>(j) * rows / hmax[i])),
hists.size() == 1 ? cv::Scalar(200, 200, 200) : colors[i],
1, 8, 0
);
}
// add the ID to make the window titles unique
if (hists.size() == 3) {
namedWindow(titles[i] ss.str());
cv::imshow(titles[i] ss.str(), canvas[i]);
}
else {
cv::imshow((hists.size() == 1 ? "value" : wname[i]) ss.str(), canvas[i]);
}
}
}