mirror of
https://github.com/gwm17/Specter.git
synced 2024-11-22 18:28:52 -05:00
Removed viewport functionality for now, due to linux issues. Added in basic stats for histogram regions
This commit is contained in:
parent
1aa7a41596
commit
e049927049
|
@ -1,12 +1,23 @@
|
|||
#include "SpectrumPanel.h"
|
||||
#include "implot.h"
|
||||
#include "misc/cpp/imgui_stdlib.h"
|
||||
#include "IconsFontAwesome5.h"
|
||||
|
||||
namespace Navigator {
|
||||
|
||||
std::string GenerateStatString(const std::string& name, const StatResults& results, bool is2D = true)
|
||||
{
|
||||
std::stringstream stream;
|
||||
stream << "Region: " << name << "\n" << "Integral: " << results.integral << "\n";
|
||||
if (results.integral == 0)
|
||||
return stream.str();
|
||||
stream << "Centroid X: " << results.cent_x << " Std. Dev. X: " << results.sigma_x << " FWHM X: " << 2.355 * results.sigma_x << "\n";
|
||||
if(is2D)
|
||||
stream << "Centroid Y: " << results.cent_y << " Std. Dev. Y: " << results.sigma_y << " FWHM Y: " << 2.355 * results.sigma_y << "\n";
|
||||
return stream.str();
|
||||
}
|
||||
|
||||
SpectrumPanel::SpectrumPanel() :
|
||||
m_zoomedFlag(false), m_cutModeFlag(false), m_zoomedGram(), m_totalSlots(1)
|
||||
m_zoomedFlag(false), m_cutModeFlag(false), m_zoomedGram(), m_nRegions(0), m_totalSlots(1)
|
||||
{
|
||||
m_tableSizes[0] = 1; m_tableSizes[1] = 1;
|
||||
}
|
||||
|
@ -20,43 +31,21 @@ namespace Navigator {
|
|||
//CutMap& cutMap = CutMap::GetInstance();
|
||||
static bool acceptCutFlag = false;
|
||||
bool result = false;
|
||||
//static std::string selectedRegion = "";
|
||||
if (ImGui::Begin("Active View"))
|
||||
{
|
||||
if (histoList.size() > 0)
|
||||
{
|
||||
if (m_zoomedFlag && m_zoomedGram.name != "")
|
||||
{
|
||||
if(ImGui::Button(ICON_FA_CUT " Draw Cut"))
|
||||
{
|
||||
m_newCutParams = CutParams();
|
||||
m_newCutX.resize(0);
|
||||
m_newCutY.resize(0);
|
||||
ImGui::OpenPopup(ICON_FA_CUT " New Cut Dialog");
|
||||
}
|
||||
if(ImGui::BeginPopupModal(ICON_FA_CUT " New Cut Dialog"))
|
||||
{
|
||||
m_newCutParams.x_par = m_zoomedGram.x_par;
|
||||
m_newCutParams.y_par = m_zoomedGram.y_par;
|
||||
ImGui::InputText("Cut Name", &m_newCutParams.name);
|
||||
ImGui::BulletText("%s", ("X Parameter: "+m_newCutParams.x_par).c_str());
|
||||
ImGui::BulletText("%s", ("Y Parameter: "+m_newCutParams.y_par).c_str());
|
||||
if(ImGui::Button("Accept & Draw"))
|
||||
{
|
||||
m_cutModeFlag = true;
|
||||
ImGui::CloseCurrentPopup();
|
||||
}
|
||||
ImGui::SameLine();
|
||||
if(ImGui::Button("Cancel"))
|
||||
{
|
||||
ImGui::CloseCurrentPopup();
|
||||
}
|
||||
ImGui::EndPopup();
|
||||
}
|
||||
RenderCutButton();
|
||||
ImGui::SameLine();
|
||||
if(ImGui::Button("Clear"))
|
||||
{
|
||||
HistogramMap::GetInstance().ClearHistogram(m_zoomedGram.name);
|
||||
}
|
||||
ImGui::SameLine();
|
||||
RenderRemoveRegionButton();
|
||||
|
||||
if (ImPlot::BeginPlot(m_zoomedGram.name.c_str(), ImVec2(-1, -1)))
|
||||
{
|
||||
|
@ -96,6 +85,26 @@ namespace Navigator {
|
|||
}
|
||||
ImPlot::PlotLine(m_newCutParams.name.c_str(), m_newCutX.data(), m_newCutY.data(), m_newCutX.size());
|
||||
}
|
||||
|
||||
if (ImPlot::IsPlotSelected()) {
|
||||
auto& select = ImPlot::GetPlotSelection();
|
||||
if (ImGui::IsMouseClicked(ImPlot::GetInputMap().SelectCancel)) {
|
||||
ImPlot::CancelPlotSelection();
|
||||
m_integralRegions.emplace_back(select, "integralRegion_"+std::to_string(m_nRegions), m_zoomedGram.name);
|
||||
m_nRegions++;
|
||||
}
|
||||
}
|
||||
for (size_t i = 0; i < m_integralRegions.size(); i++)
|
||||
{
|
||||
auto& region = m_integralRegions[i];
|
||||
if (m_zoomedGram.name == region.histogram_name)
|
||||
{
|
||||
ImPlot::DragRect(i, ®ion.region.X.Min, ®ion.region.Y.Min, ®ion.region.X.Max, ®ion.region.Y.Max, ImVec4(1, 0, 1, 1));
|
||||
StatResults results = HistogramMap::GetInstance().AnalyzeHistogramRegion(m_zoomedGram.name, region.region);
|
||||
ImPlot::PlotText(GenerateStatString(region.name, results, m_zoomedGram.y_par != "None").c_str(), (region.region.X.Max + region.region.X.Min) * 0.5,
|
||||
(region.region.Y.Min + region.region.Y.Max) * 0.5);
|
||||
}
|
||||
}
|
||||
ImPlot::EndPlot();
|
||||
}
|
||||
if (acceptCutFlag)
|
||||
|
@ -181,6 +190,15 @@ namespace Navigator {
|
|||
m_zoomedFlag = true;
|
||||
m_zoomedGram = spec;
|
||||
}
|
||||
|
||||
for (size_t i = 0; i < m_integralRegions.size(); i++)
|
||||
{
|
||||
auto& region = m_integralRegions[i];
|
||||
if (spec.name == region.histogram_name)
|
||||
{
|
||||
ImPlot::DragRect(i, ®ion.region.X.Min, ®ion.region.Y.Min, ®ion.region.X.Max, ®ion.region.Y.Max, ImVec4(1, 0, 1, 1));
|
||||
}
|
||||
}
|
||||
ImPlot::EndPlot();
|
||||
}
|
||||
i++;
|
||||
|
@ -193,4 +211,82 @@ namespace Navigator {
|
|||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
void SpectrumPanel::RenderCutButton()
|
||||
{
|
||||
if (ImGui::Button(ICON_FA_CUT " Draw Cut"))
|
||||
{
|
||||
m_newCutParams = CutParams();
|
||||
m_newCutX.resize(0);
|
||||
m_newCutY.resize(0);
|
||||
ImGui::OpenPopup(ICON_FA_CUT " New Cut Dialog");
|
||||
}
|
||||
if (ImGui::BeginPopupModal(ICON_FA_CUT " New Cut Dialog"))
|
||||
{
|
||||
m_newCutParams.x_par = m_zoomedGram.x_par;
|
||||
m_newCutParams.y_par = m_zoomedGram.y_par;
|
||||
ImGui::InputText("Cut Name", &m_newCutParams.name);
|
||||
ImGui::BulletText("%s", ("X Parameter: " + m_newCutParams.x_par).c_str());
|
||||
ImGui::BulletText("%s", ("Y Parameter: " + m_newCutParams.y_par).c_str());
|
||||
if (ImGui::Button("Accept & Draw"))
|
||||
{
|
||||
m_cutModeFlag = true;
|
||||
ImGui::CloseCurrentPopup();
|
||||
}
|
||||
ImGui::SameLine();
|
||||
if (ImGui::Button("Cancel"))
|
||||
{
|
||||
ImGui::CloseCurrentPopup();
|
||||
}
|
||||
ImGui::EndPopup();
|
||||
}
|
||||
}
|
||||
|
||||
void SpectrumPanel::RenderRemoveRegionButton()
|
||||
{
|
||||
static std::string selectedRegion = "";
|
||||
if (ImGui::Button("Delete Region"))
|
||||
{
|
||||
selectedRegion = "";
|
||||
ImGui::OpenPopup("Remove Integral Region");
|
||||
}
|
||||
if (ImGui::BeginPopupModal("Remove Integral Region"))
|
||||
{
|
||||
if (ImGui::BeginCombo("Region", selectedRegion.c_str()))
|
||||
{
|
||||
for (auto& region : m_integralRegions)
|
||||
{
|
||||
if (region.histogram_name == m_zoomedGram.name)
|
||||
{
|
||||
if (ImGui::Selectable(region.name.c_str(), region.name == selectedRegion, ImGuiSelectableFlags_DontClosePopups))
|
||||
selectedRegion = region.name;
|
||||
}
|
||||
}
|
||||
ImGui::EndCombo();
|
||||
}
|
||||
if (ImGui::Button("Ok"))
|
||||
{
|
||||
RemoveSelectedRegion(selectedRegion);
|
||||
ImGui::CloseCurrentPopup();
|
||||
}
|
||||
ImGui::SameLine();
|
||||
if (ImGui::Button("Cancel"))
|
||||
{
|
||||
ImGui::CloseCurrentPopup();
|
||||
}
|
||||
ImGui::EndPopup();
|
||||
}
|
||||
}
|
||||
|
||||
void SpectrumPanel::RemoveSelectedRegion(const std::string& region)
|
||||
{
|
||||
for (size_t i=0; i<m_integralRegions.size(); i++)
|
||||
{
|
||||
if (m_integralRegions[i].name == region)
|
||||
{
|
||||
m_integralRegions.erase(m_integralRegions.begin() + i);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -5,9 +5,21 @@
|
|||
#include "Navigator/ParameterMap.h"
|
||||
#include "Navigator/CutMap.h"
|
||||
#include "imgui.h"
|
||||
#include "implot.h"
|
||||
|
||||
namespace Navigator {
|
||||
|
||||
struct NAV_API IntegrationRegion
|
||||
{
|
||||
IntegrationRegion(const ImPlotRect& rect, const std::string& n, const std::string& hist_n) :
|
||||
region(rect), name(n), histogram_name(hist_n)
|
||||
{
|
||||
}
|
||||
ImPlotRect region;
|
||||
std::string name = "";
|
||||
std::string histogram_name = "";
|
||||
};
|
||||
|
||||
class NAV_API SpectrumPanel
|
||||
{
|
||||
public:
|
||||
|
@ -19,12 +31,17 @@ namespace Navigator {
|
|||
inline const bool IsZoomed() { return m_zoomedFlag; }
|
||||
|
||||
private:
|
||||
void RenderCutButton();
|
||||
void RenderRemoveRegionButton();
|
||||
void RemoveSelectedRegion(const std::string& region);
|
||||
std::vector<HistogramParameters> m_selectedGrams;
|
||||
std::vector<IntegrationRegion> m_integralRegions;
|
||||
bool m_zoomedFlag;
|
||||
bool m_cutModeFlag;
|
||||
HistogramParameters m_zoomedGram;
|
||||
int m_tableSizes[2];
|
||||
int m_totalSlots;
|
||||
int m_nRegions;
|
||||
CutParams m_newCutParams;
|
||||
std::vector<double> m_newCutX;
|
||||
std::vector<double> m_newCutY;
|
||||
|
|
|
@ -79,6 +79,35 @@ namespace Navigator {
|
|||
m_binCounts[i] = 0;
|
||||
}
|
||||
|
||||
StatResults Histogram1D::AnalyzeRegion(double x_min, double x_max, double y_min, double y_max)
|
||||
{
|
||||
int bin_min, bin_max;
|
||||
StatResults results;
|
||||
|
||||
if (x_min <= m_params.min_x)
|
||||
bin_min = 0;
|
||||
else
|
||||
bin_min = int((x_min - m_params.min_x) / (m_binWidth));
|
||||
|
||||
if (x_max >= m_params.max_x)
|
||||
bin_max = m_params.nbins_x - 1;
|
||||
else
|
||||
bin_max = int((x_max - m_params.min_x) / (m_binWidth));
|
||||
|
||||
for (int i = bin_min; i <= bin_max; i++)
|
||||
{
|
||||
results.integral += m_binCounts[i];
|
||||
results.cent_x += m_binCounts[i] * (m_params.min_x + m_binWidth * i);
|
||||
}
|
||||
if (results.integral == 0)
|
||||
return results;
|
||||
|
||||
results.cent_x /= double(results.integral);
|
||||
for (int i = bin_min; i <= bin_max; i++)
|
||||
results.sigma_x += m_binCounts[i] * ((m_params.min_x + m_binWidth * i) - results.cent_x) * ((m_params.min_x + m_binWidth * i) - results.cent_x);
|
||||
results.sigma_x = std::sqrt(results.sigma_x / (results.integral - 1));
|
||||
return results;
|
||||
}
|
||||
|
||||
/*
|
||||
2D Histogram class
|
||||
|
@ -158,4 +187,64 @@ namespace Navigator {
|
|||
m_binCounts[i] = 0;
|
||||
m_maxBinContent = 0;
|
||||
}
|
||||
|
||||
StatResults Histogram2D::AnalyzeRegion(double x_min, double x_max, double y_min, double y_max)
|
||||
{
|
||||
int xbin_min, xbin_max, ybin_min, ybin_max;
|
||||
int curbin;
|
||||
|
||||
StatResults results;
|
||||
|
||||
if (x_min <= m_params.min_x)
|
||||
xbin_min = 0;
|
||||
else
|
||||
xbin_min = int((x_min - m_params.min_x) / (m_binWidthX));
|
||||
|
||||
if (x_max >= m_params.max_x)
|
||||
xbin_max = m_params.nbins_x - 1;
|
||||
else
|
||||
xbin_max = int((x_max - m_params.min_x) / (m_binWidthX));
|
||||
|
||||
if (y_min <= m_params.min_y)
|
||||
ybin_max = m_params.nbins_y - 1;
|
||||
else
|
||||
ybin_max = int((m_params.max_y - y_min)) / m_binWidthY;
|
||||
|
||||
if (y_max >= m_params.max_y)
|
||||
ybin_min = 0;
|
||||
else
|
||||
ybin_min = int((m_params.max_y - y_max)) / m_binWidthY;
|
||||
|
||||
for (int y = ybin_min; y <= ybin_max; y++)
|
||||
{
|
||||
for (int x = xbin_min; x <= xbin_max; x++)
|
||||
{
|
||||
curbin = y * m_params.nbins_x + x;
|
||||
results.integral += m_binCounts[curbin];
|
||||
results.cent_x += m_binCounts[curbin] * (m_params.min_x + m_binWidthX * x);
|
||||
results.cent_y += m_binCounts[curbin] * (m_params.max_y - m_binWidthY * y);
|
||||
}
|
||||
}
|
||||
|
||||
if (results.integral == 0)
|
||||
return results;
|
||||
|
||||
results.cent_x /= results.integral;
|
||||
results.cent_y /= results.integral;
|
||||
for (int y = ybin_min; y <= ybin_max; y++)
|
||||
{
|
||||
for (int x = xbin_min; x <= xbin_max; x++)
|
||||
{
|
||||
curbin = y * m_params.nbins_x + x;
|
||||
results.sigma_x += m_binCounts[curbin] * ((m_params.min_x + m_binWidthX * x) - results.cent_x) * ((m_params.min_x + m_binWidthX * x) - results.cent_x);
|
||||
results.sigma_y += m_binCounts[curbin] * ((m_params.max_y - m_binWidthY * y) - results.cent_y) * ((m_params.max_y - m_binWidthY * y) - results.cent_y);
|
||||
}
|
||||
}
|
||||
|
||||
results.sigma_x = std::sqrt(results.sigma_x / (results.integral - 1));
|
||||
results.sigma_y = std::sqrt(results.sigma_y / (results.integral - 1));
|
||||
|
||||
return results;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -5,6 +5,15 @@
|
|||
|
||||
namespace Navigator {
|
||||
|
||||
struct NAV_API StatResults
|
||||
{
|
||||
int integral = 0.0;
|
||||
double cent_x = 0.0;
|
||||
double cent_y = 0.0;
|
||||
double sigma_x = 0.0;
|
||||
double sigma_y = 0.0;
|
||||
};
|
||||
|
||||
struct NAV_API HistogramParameters
|
||||
{
|
||||
HistogramParameters() {}
|
||||
|
@ -48,6 +57,7 @@ namespace Navigator {
|
|||
virtual void FillData() { NAV_WARN("Trying to fill a default histogram!"); }
|
||||
virtual void Draw() {}
|
||||
virtual void ClearData() {}
|
||||
virtual StatResults AnalyzeRegion(double x_min, double x_max, double y_min = 0.0, double y_max = 0.0) { return StatResults(); }
|
||||
inline virtual bool Is1D() const { return false; }
|
||||
inline virtual bool Is2D() const { return false; }
|
||||
inline HistogramParameters& GetParameters() { return m_params; }
|
||||
|
@ -70,6 +80,7 @@ namespace Navigator {
|
|||
virtual void FillData() override;
|
||||
virtual void Draw() override;
|
||||
virtual void ClearData() override;
|
||||
virtual StatResults AnalyzeRegion(double x_min, double x_max, double y_min = 0.0, double y_max = 0.0) override;
|
||||
inline virtual bool Is1D() const override { return true; }
|
||||
inline virtual bool Is2D() const override { return false; }
|
||||
|
||||
|
@ -90,6 +101,7 @@ namespace Navigator {
|
|||
virtual void FillData() override;
|
||||
virtual void Draw() override;
|
||||
virtual void ClearData() override;
|
||||
virtual StatResults AnalyzeRegion(double x_min, double x_max, double y_min = 0.0, double y_max = 0.0) override;
|
||||
inline virtual bool Is1D() const override { return false; }
|
||||
inline virtual bool Is2D() const override { return true; }
|
||||
|
||||
|
|
|
@ -1,6 +1,8 @@
|
|||
#include "HistogramMap.h"
|
||||
#include "ParameterMap.h"
|
||||
|
||||
#include "implot.h"
|
||||
|
||||
namespace Navigator {
|
||||
|
||||
HistogramMap* HistogramMap::s_instance = new HistogramMap();
|
||||
|
@ -100,6 +102,16 @@ namespace Navigator {
|
|||
return m_nullResult;
|
||||
}
|
||||
|
||||
StatResults HistogramMap::AnalyzeHistogramRegion(const std::string& name, const ImPlotRect& region)
|
||||
{
|
||||
std::lock_guard<std::mutex> guard(m_histoMutex);
|
||||
auto iter = m_map.find(name);
|
||||
if (iter != m_map.end())
|
||||
return iter->second->AnalyzeRegion(region.X.Min, region.X.Max, region.Y.Min, region.Y.Max);
|
||||
else
|
||||
return StatResults();
|
||||
}
|
||||
|
||||
std::vector<HistogramParameters> HistogramMap::GetListOfHistograms()
|
||||
{
|
||||
std::lock_guard<std::mutex> guard(m_histoMutex);
|
||||
|
|
|
@ -6,6 +6,8 @@
|
|||
|
||||
#include <thread>
|
||||
|
||||
struct ImPlotRect;
|
||||
|
||||
namespace Navigator {
|
||||
|
||||
class NAV_API HistogramMap
|
||||
|
@ -19,7 +21,6 @@ namespace Navigator {
|
|||
void AddHistogram(const HistogramParameters& params);
|
||||
|
||||
void RemoveHistogram(const std::string& name);
|
||||
|
||||
|
||||
void AddCutToHistogramDraw(const std::string& cutname, const std::string& histoname);
|
||||
void AddCutToHistogramApplied(const std::string& cutname, const std::string& histoname);
|
||||
|
@ -33,6 +34,7 @@ namespace Navigator {
|
|||
void DrawHistogram(const std::string& name);
|
||||
|
||||
const HistogramParameters& GetHistogramParams(const std::string& name);
|
||||
StatResults AnalyzeHistogramRegion(const std::string& name, const ImPlotRect& region);
|
||||
|
||||
std::vector<HistogramParameters> GetListOfHistograms();
|
||||
|
||||
|
|
|
@ -34,7 +34,9 @@ namespace Navigator {
|
|||
ImGuiIO& io = ImGui::GetIO();
|
||||
io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard;
|
||||
io.ConfigFlags |= ImGuiConfigFlags_DockingEnable;
|
||||
io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable;
|
||||
//Viewports are real wonky on Linux and sometimes on Mac
|
||||
// Can currently cause assertion failure on checking number of monitors in ImGui sanity checks.
|
||||
//io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable;
|
||||
|
||||
ImGui::StyleColorsDark();
|
||||
ImPlot::StyleColorsDark();
|
||||
|
@ -54,7 +56,7 @@ namespace Navigator {
|
|||
config.GlyphMinAdvanceX = 13.0f; // Use if you want to make the icon monospaced
|
||||
config.PixelSnapH = true;
|
||||
static const ImWchar icon_ranges[] = { ICON_MIN_FA, ICON_MAX_FA, 0 };
|
||||
io.Fonts->AddFontFromFileTTF("fonts/fa-solid-900.ttf", 15.0f, &config, icon_ranges);
|
||||
io.Fonts->AddFontFromFileTTF("fonts/fa-solid-900.ttf", 13.0f, &config, icon_ranges);
|
||||
|
||||
Application& app = Application::Get();
|
||||
GLFWwindow* window = static_cast<GLFWwindow*>(app.GetWindow().GetNativeWindow());
|
||||
|
|
Loading…
Reference in New Issue
Block a user