satdump/src-interface/viewer2/viewer.cpp

333 lines
15 KiB
C++
Raw Normal View History

2024-12-29 20:13:58 +01:00
#include "viewer.h"
// #include "image_handler.h"
// #include "radiation_handler.h"
// #include "scatterometer_handler.h"
2024-12-31 17:01:12 +01:00
// #include "core/config.h"
// #include "products/dataset.h"
2025-04-15 19:06:12 +01:00
#include "common/event_bus.h"
2024-12-29 20:13:58 +01:00
#include "common/utils.h"
2024-12-31 17:01:12 +01:00
// #include "resources.h"
2025-04-15 19:06:12 +01:00
#include "core/plugin.h"
2024-12-29 20:13:58 +01:00
#include "core/style.h"
2025-04-15 19:06:12 +01:00
#include "dsp/cyclo_test.h"
2025-04-21 23:17:21 +02:00
#include "dsp/flowgraph/dsp_flowgraph_handler.h"
2025-04-15 19:06:12 +01:00
#include "handler/dataset/dataset_handler.h"
2025-04-06 13:17:30 +02:00
#include "handler/dummy_handler.h"
#include "handler/product/image_product_handler.h" // TODOREWORK CLEAN
#include "handler/projection/projection_handler.h"
#include "handler/trash/trash_handler.h"
2025-04-15 19:06:12 +01:00
#include "handler/vector/shapefile_handler.h"
2025-03-14 11:12:18 +01:00
// TODOREWORK
#include "resources.h"
2024-12-29 20:13:58 +01:00
2025-03-15 23:37:59 +01:00
// TODOREWORK
2025-03-22 11:51:53 +01:00
#include "dsp/newrec.h"
2025-04-15 19:06:12 +01:00
#include "dsp/waterfall_test.h"
2025-03-15 23:37:59 +01:00
2025-04-06 10:27:54 +02:00
#include "common/image/io.h"
2025-04-03 19:12:28 +02:00
#include "tools_todoreworkmove/lut_generator.h"
2025-04-15 19:06:12 +01:00
#include "imgui/imgui_filedrop.h"
2024-12-29 20:13:58 +01:00
namespace satdump
{
2024-12-31 17:01:12 +01:00
namespace viewer
2024-12-29 20:13:58 +01:00
{
2025-04-15 19:06:12 +01:00
ViewerApplication::ViewerApplication() : Application("viewer")
2024-12-29 20:13:58 +01:00
{
2025-01-02 17:04:32 +01:00
master_handler = std::make_shared<DummyHandler>("MasterHandlerViewer");
2025-03-22 11:51:53 +01:00
// Add trashcan
trash_handler = std::make_shared<DummyHandler>("TrashHandlerViewer");
2025-03-14 14:39:05 +01:00
auto trash_h = std::make_shared<TrashHandler>();
trash_h->setCanBeDragged(false);
2025-03-22 11:51:53 +01:00
trash_handler->addSubHandler(trash_h);
trash_handler->setCanBeDraggedTo(false);
2025-04-15 19:06:12 +01:00
// Enable dropping files onto the viewer. TODOREWORK, check the viewer IS active!?
eventBus->register_handler<imgui_utils::FileDropEvent>(
[this](const imgui_utils::FileDropEvent &v)
{
for (auto &f : v.files)
openProductOrDataset(f);
});
2025-05-15 14:04:34 +02:00
eventBus->register_handler<GetLastSelectedOfTypeEvent>(
[this](const GetLastSelectedOfTypeEvent &v)
{
if (last_selected_handler.count(v.type))
v.h = last_selected_handler[v.type];
else
v.h = 0;
});
openProductOrDataset("/home/alan/Downloads/SatDump_NEWPRODS/metop_test/dataset.json");
2024-12-31 17:01:12 +01:00
}
2024-12-29 20:13:58 +01:00
2024-12-31 17:01:12 +01:00
ViewerApplication::~ViewerApplication()
2024-12-29 20:13:58 +01:00
{
2025-01-03 10:03:04 +01:00
if (file_open_thread.joinable())
file_open_thread.join();
2024-12-29 20:13:58 +01:00
}
2024-12-31 17:01:12 +01:00
void ViewerApplication::drawPanel()
2024-12-29 20:13:58 +01:00
{
2024-12-31 17:01:12 +01:00
ImGui::SetNextItemWidth(ImGui::GetWindowWidth() / 2);
2024-12-29 20:13:58 +01:00
2024-12-31 17:01:12 +01:00
if (ImGui::CollapsingHeader("General", ImGuiTreeNodeFlags_DefaultOpen))
2024-12-29 20:13:58 +01:00
{
2025-05-15 14:04:34 +02:00
auto prev_curr = curr_handler;
2024-12-31 17:01:12 +01:00
if (ImGui::BeginTable("##masterhandlertable", 1, ImGuiTableFlags_RowBg | ImGuiTableFlags_Borders))
{
ImGui::TableSetupColumn("##masterhandlertable_col", ImGuiTableColumnFlags_None);
ImGui::TableNextColumn();
2024-12-29 20:13:58 +01:00
2024-12-31 17:01:12 +01:00
master_handler->drawTreeMenu(curr_handler);
2025-03-22 11:51:53 +01:00
trash_handler->drawTreeMenu(curr_handler);
2024-12-29 20:13:58 +01:00
2024-12-31 17:01:12 +01:00
ImGui::EndTable();
}
2024-12-29 20:13:58 +01:00
2025-05-15 14:04:34 +02:00
if (prev_curr != curr_handler)
last_selected_handler.insert_or_assign(curr_handler->getID(), curr_handler);
2025-01-02 17:04:32 +01:00
if (curr_handler)
curr_handler->drawMenu();
}
}
void ViewerApplication::drawMenuBar()
{
2025-01-03 10:03:04 +01:00
// Handle File Stuff TODOREWORK?
{
2025-05-03 12:12:36 +02:00
if (file_open_dialog && file_open_dialog->is_ready())
2025-01-03 10:03:04 +01:00
{
2025-05-03 12:12:36 +02:00
std::string prod_path = file_open_dialog->result();
2025-01-03 10:03:04 +01:00
delete file_open_dialog;
file_open_dialog = nullptr;
2025-05-03 12:12:36 +02:00
if (prod_path.size() > 0)
openProductOrDataset(prod_path);
else
logger->trace("No file selected");
2025-01-03 10:03:04 +01:00
}
}
2025-01-02 17:04:32 +01:00
if (ImGui::BeginMenuBar())
{
if (ImGui::BeginMenu("File"))
2025-01-01 05:57:58 +01:00
{
if (ImGui::MenuItem("Open File") && !file_open_dialog) // TODOREWORK switch to general thing
2025-05-04 20:59:44 +02:00
file_open_dialog = new fileutils::FileSelTh({{"All Files", "*"}}, ""); // TODOREWORK remember path?
2025-01-02 17:04:32 +01:00
if (ImGui::BeginMenu("Hardcoded"))
2025-01-01 05:57:58 +01:00
{
2025-01-02 17:04:32 +01:00
if (ImGui::MenuItem("Load KMSS"))
2025-01-07 19:07:51 +01:00
openProductOrDataset("/home/alan/Downloads/SatDump_NEWPRODS/KMSS_24/dataset.json");
2025-01-02 17:04:32 +01:00
if (ImGui::MenuItem("Load Sterna"))
2025-01-07 19:07:51 +01:00
openProductOrDataset("/home/alan/Downloads/SatDump_NEWPRODS/aws_pfm_cadu/dataset.json");
2025-01-02 17:04:32 +01:00
if (ImGui::MenuItem("Load MSUGS"))
2025-01-03 10:03:04 +01:00
openProductOrDataset("/home/alan/Downloads/20241231_132953_ARKTIKA-M 2_dat/MSUGS_VIS1/product.cbor");
2025-01-02 17:04:32 +01:00
if (ImGui::MenuItem("Load MSUGS 2"))
2025-01-07 19:07:51 +01:00
openProductOrDataset("/home/alan/Downloads/SatDump_NEWPRODS/20250104_071415_ELEKTRO-L_3_dat/dataset.json");
2025-01-03 16:26:39 +01:00
if (ImGui::MenuItem("Load MetOp"))
openProductOrDataset("/home/alan/Downloads/SatDump_NEWPRODS/metop_test/dataset.json");
2025-01-05 19:57:26 +01:00
if (ImGui::MenuItem("Load L3"))
openProductOrDataset("/data_ssd/ELEKTRO-L3/20250104_071415_ELEKTRO-L 3.dat_OUT/dataset.json");
if (ImGui::MenuItem("Load JPSS-1"))
openProductOrDataset("/home/alan/Downloads/SatDump_NEWPRODS/202411271228_NOAA_20/dataset.json");
if (ImGui::MenuItem("Load JPSS-2"))
openProductOrDataset("/home/alan/Downloads/SatDump_NEWPRODS/n21_day/dataset.json");
2025-01-14 19:05:15 +01:00
if (ImGui::MenuItem("Load APT"))
openProductOrDataset("/home/alan/Downloads/audio_137912500Hz_11-39-56_04-03-2024_wav/dataset.json");
2025-01-15 22:00:47 +01:00
if (ImGui::MenuItem("Load GOES"))
openProductOrDataset("/home/alan/Downloads/SatDump_NEWPRODS/goes_hrit_jvital2013_cadu/IMAGES/GOES-16/Full Disk/2024-04-17_18-00-20/product.cbor");
2025-02-03 07:48:52 +01:00
if (ImGui::MenuItem("Load Shapefile"))
{
auto shp_h = std::make_shared<ShapefileHandler>(resources::getResourcePath("maps/ne_10m_admin_0_countries.shp"));
master_handler->addSubHandler(shp_h);
}
2025-01-03 10:03:04 +01:00
2025-02-07 14:31:18 +01:00
if (ImGui::MenuItem("Load Shapefile FRA_1"))
{
auto shp_h = std::make_shared<ShapefileHandler>("/home/alan/Downloads/gadm41_FRA_shp/gadm41_FRA_1.shp");
master_handler->addSubHandler(shp_h);
}
if (ImGui::MenuItem("Load Shapefile FRA_2"))
{
auto shp_h = std::make_shared<ShapefileHandler>("/home/alan/Downloads/gadm41_FRA_shp/gadm41_FRA_2.shp");
master_handler->addSubHandler(shp_h);
}
2025-01-02 17:04:32 +01:00
ImGui::EndMenu();
2025-01-01 05:57:58 +01:00
}
2025-01-02 17:04:32 +01:00
ImGui::EndMenu();
}
if (ImGui::BeginMenu("Handler"))
{
if (ImGui::BeginMenu("Add"))
2025-01-01 05:57:58 +01:00
{
2025-02-09 16:34:06 +01:00
if (ImGui::MenuItem("Dataset"))
logger->error("Dummy Menu!");
if (ImGui::MenuItem("Projection"))
master_handler->addSubHandler(std::make_shared<ProjectionHandler>());
2025-03-09 10:16:40 +01:00
if (ImGui::MenuItem("DSP Flowgraph"))
2025-04-15 19:06:12 +01:00
master_handler->addSubHandler(std::make_shared<DSPFlowGraphHandler>());
2025-02-10 20:09:03 +01:00
if (ImGui::MenuItem("BitView TEST"))
{
std::vector<std::shared_ptr<Handler>> e;
eventBus->fire_event<RequestHandlersEvent>({e});
2025-05-10 22:20:46 +02:00
// if (e.size() > 0)
// master_handler->addSubHandler(e[0]);
for (auto &h : e)
master_handler->addSubHandler(h);
2025-02-10 20:09:03 +01:00
}
2025-03-15 23:37:59 +01:00
if (ImGui::MenuItem("Waterfall TEST"))
master_handler->addSubHandler(std::make_shared<WaterfallTestHandler>());
2025-03-22 11:51:53 +01:00
if (ImGui::MenuItem("NewRec TEST"))
2025-04-12 09:56:37 +02:00
master_handler->addSubHandler(std::make_shared<NewRecHandler>());
if (ImGui::MenuItem("CycloHelper TEST"))
master_handler->addSubHandler(std::make_shared<CycloHelperHandler>());
2025-04-03 19:12:28 +02:00
if (ImGui::MenuItem("Lut Generator"))
master_handler->addSubHandler(std::make_shared<LutGeneratorHandler>());
2025-01-02 17:04:32 +01:00
ImGui::EndMenu();
2025-01-01 05:57:58 +01:00
}
2025-01-04 23:03:13 +01:00
if (curr_handler && ImGui::BeginMenu("Config"))
{
if (ImGui::MenuItem("JSON To Clipboard"))
ImGui::SetClipboardText(curr_handler->getConfig().dump(4).c_str());
if (ImGui::MenuItem("JSON From Clipboard"))
curr_handler->setConfig(nlohmann::json::parse(ImGui::GetClipboardText()));
ImGui::EndMenu();
}
2025-01-02 17:04:32 +01:00
ImGui::EndMenu();
}
if (curr_handler)
{
if (ImGui::BeginMenu("Current"))
2025-01-01 05:57:58 +01:00
{
2025-01-02 17:04:32 +01:00
curr_handler->drawMenuBar();
ImGui::EndMenu();
2025-01-01 05:57:58 +01:00
}
}
2024-12-29 20:13:58 +01:00
2025-03-25 21:33:06 +01:00
eventBus->fire_event<RenderLoadMenuElementsEvent>({});
2025-01-02 17:04:32 +01:00
ImGui::EndMenuBar();
2024-12-29 20:13:58 +01:00
}
}
2025-04-15 19:06:12 +01:00
void ViewerApplication::drawContents() { ImGui::Text("No handler selected!"); }
2024-12-29 20:13:58 +01:00
2024-12-31 17:01:12 +01:00
void ViewerApplication::drawUI()
2024-12-29 20:13:58 +01:00
{
2024-12-31 17:01:12 +01:00
ImVec2 viewer_size = ImGui::GetContentRegionAvail();
2024-12-29 20:13:58 +01:00
2025-01-03 10:03:04 +01:00
if (ImGui::BeginTable("##wiever_table", 2, ImGuiTableFlags_Resizable | ImGuiTableFlags_SizingStretchProp | ImGuiTableFlags_BordersInnerV))
2024-12-29 20:13:58 +01:00
{
2024-12-31 17:01:12 +01:00
ImGui::TableSetupColumn("##panel_v", ImGuiTableColumnFlags_None, viewer_size.x * panel_ratio);
ImGui::TableSetupColumn("##view", ImGuiTableColumnFlags_None, viewer_size.x * (1.0f - panel_ratio));
ImGui::TableNextColumn();
2024-12-29 20:13:58 +01:00
2024-12-31 17:01:12 +01:00
float left_width = ImGui::GetColumnWidth(0);
float right_width = viewer_size.x - left_width;
if (left_width != last_width && last_width != -1)
panel_ratio = left_width / viewer_size.x;
last_width = left_width;
2024-12-29 20:13:58 +01:00
2025-01-02 17:04:32 +01:00
ImGui::BeginChild("ViewerChildPanel", {left_width, float(viewer_size.y - 10)}, false, ImGuiWindowFlags_MenuBar);
drawMenuBar();
2024-12-31 17:01:12 +01:00
drawPanel();
ImGui::EndChild();
2024-12-29 20:13:58 +01:00
2024-12-31 17:01:12 +01:00
ImGui::TableNextColumn();
ImGui::BeginGroup();
2024-12-29 20:13:58 +01:00
2024-12-31 17:01:12 +01:00
if (curr_handler)
2025-04-28 19:43:01 +02:00
curr_handler->drawContents({float(right_width - 9 * ui_scale), float(viewer_size.y)});
2025-01-02 17:04:32 +01:00
else
drawContents();
2024-12-29 20:13:58 +01:00
2024-12-31 17:01:12 +01:00
ImGui::EndGroup();
ImGui::EndTable();
2024-12-29 20:13:58 +01:00
}
}
2025-01-03 10:03:04 +01:00
2025-04-06 10:27:54 +02:00
void ViewerApplication::openProductOrDataset(std::string path) // TODOREWORK Rename!
2025-01-03 10:03:04 +01:00
{
if (file_open_thread.joinable())
file_open_thread.join();
auto fun = [this, path]()
{
2025-04-06 10:27:54 +02:00
try
2025-01-03 10:03:04 +01:00
{
2025-04-06 10:27:54 +02:00
if (!std::filesystem::path(path).has_extension())
{
logger->error("Invalid file, no extension!");
return;
}
2025-01-03 10:03:04 +01:00
2025-04-06 10:27:54 +02:00
// TODOREWORK Load more than just image products
if (std::filesystem::path(path).extension().string() == ".cbor")
{
logger->trace("Viewer loading product " + path);
2025-04-06 10:27:54 +02:00
try
{
std::shared_ptr<ProductHandler> prod_h = std::make_shared<ImageProductHandler>(products::loadProduct(path));
master_handler->addSubHandler(prod_h);
}
catch (std::exception &e)
{
logger->error("Error loading product! Maybe not a valid product? Details : %s", e.what());
}
}
2025-04-06 10:27:54 +02:00
else if (std::filesystem::path(path).extension().string() == ".json")
{
logger->trace("Viewer loading dataset " + path);
2025-04-06 10:27:54 +02:00
try
{
products::DataSet dataset;
dataset.load(path);
std::shared_ptr<DatasetHandler> dat_h = std::make_shared<DatasetHandler>(std::filesystem::path(path).parent_path().string(), dataset);
master_handler->addSubHandler(dat_h);
}
catch (std::exception &e)
{
logger->error("Error loading dataset! Maybe not a valid dataset? Details : %s", e.what());
}
}
2025-04-06 10:27:54 +02:00
else if (std::filesystem::path(path).extension().string() == ".shp")
{
logger->trace("Viewer loading shapefile " + path);
2025-04-06 10:27:54 +02:00
master_handler->addSubHandler(std::make_shared<ShapefileHandler>(path));
}
2025-04-06 10:27:54 +02:00
else
{
logger->trace("Viewer loading image " + path);
2025-04-06 10:27:54 +02:00
image::Image img;
image::load_img(img, path);
if (img.size() > 0)
master_handler->addSubHandler(std::make_shared<ImageHandler>(img, std::filesystem::path(path).stem().string()));
else
logger->error("Could not open this file as image!"); // TODOREWORK Probably check before this?
}
2025-01-03 10:03:04 +01:00
}
2025-04-06 10:27:54 +02:00
catch (std::exception &e)
2025-02-03 07:52:21 +01:00
{
2025-04-06 10:27:54 +02:00
logger->error("Error opening file! => %s", e.what());
2025-02-03 07:52:21 +01:00
}
2025-01-03 10:03:04 +01:00
};
file_open_thread = std::thread(fun);
}
2025-04-15 19:06:12 +01:00
} // namespace viewer
}; // namespace satdump