egami
C++ Image Processing program
|
00001 00009 #ifndef CATALOGUE_HPP_INCLUDED 00010 #define CATALOGUE_HPP_INCLUDED 00011 00012 #include <map> 00013 #include <memory> 00014 #include <string> 00015 #include <type_traits> 00016 #include <utility> 00017 #include <vector> 00018 00019 #include <gtkmm/label.h> 00020 #include <gtkmm/notebook.h> 00021 #include <gtkmm/widget.h> 00022 00023 #include "display_page.hpp" 00024 #include "processing_page.hpp" 00025 #include "utils.hpp" 00026 00027 class Display_unit; 00028 00038 template <class Tab, class Page> 00039 class Catalogue: public Gtk::Notebook { 00040 static_assert(std::is_base_of<Gtk::Widget, Tab>::value, "The Tab type of a Catalogue must have Gtk::Widget as a base class"); 00041 static_assert(std::is_base_of<Gtk::Widget, Page>::value, "The Page type of a Catalogue must have Gtk::Widget as a base class"); 00042 00043 protected: 00044 typedef std::map<unsigned, std::pair<std::shared_ptr<Tab>, std::shared_ptr<Page>>> Pages; 00045 00046 public: 00047 Catalogue(); 00048 00058 unsigned append(std::shared_ptr<Tab> tab, std::shared_ptr<Page> page); 00059 00067 void remove(unsigned id); 00068 00069 protected: 00070 Pages pages; 00071 }; 00072 00076 class Display_catalogue: public Catalogue<Display_page_header, Display_page>, Singleton<Display_catalogue> { 00077 public: 00078 Display_catalogue(); 00079 00085 void open_image(const std::string &filepath); 00086 00087 void undo_current(); 00088 void redo_current(); 00089 bool save(); 00090 void save_as(const std::string&); 00091 00095 static std::shared_ptr<Display_page> current_page(); 00096 static std::vector<std::shared_ptr<Display_unit>> all_units(); 00097 00098 static void add_page(const std::string &title, Display_unit *unit); 00099 00100 private: 00101 static Display_catalogue *instance; 00102 }; 00103 00107 class Processing_catalogue: public Catalogue<Gtk::Label, Processing_page>, Singleton<Processing_catalogue> { 00108 public: 00109 Processing_catalogue(); 00110 00111 private: 00120 template<class Page_type> 00121 void create_processing_group(const std::string &name); 00122 }; 00123 00124 00125 template <class Tab, class Page> 00126 Catalogue<Tab,Page>::Catalogue(){ 00127 set_border_width(4); 00128 set_show_tabs(); 00129 } 00130 00131 template <class Tab, class Page> 00132 unsigned Catalogue<Tab,Page>::append(std::shared_ptr<Tab> tab, std::shared_ptr<Page> page){ 00133 static unsigned cpt=0; 00134 pages.insert(typename Pages::value_type(cpt, std::make_pair(tab, page))); 00135 append_page(*page, *tab); 00136 show_all_children(); 00137 return cpt++; 00138 } 00139 00140 template <class Tab, class Page> 00141 void Catalogue<Tab,Page>::remove(unsigned id){ 00142 typename Pages::iterator target=pages.find(id); 00143 if(target==pages.end()) 00144 throw std::runtime_error("Trying to remove a page with the non existing id "+std::to_string(id)); 00145 remove_page(*target->second.second); 00146 pages.erase(target); 00147 } 00148 00149 template<class Page_type> 00150 void Processing_catalogue::create_processing_group(const std::string &name){ 00151 static_assert(std::is_base_of<Processing_page, Page_type>::value, "Trying to create a processing group not based on Processing_page."); 00152 append(std::shared_ptr<Gtk::Label>(new Gtk::Label(name)), std::shared_ptr<Page_type>(new Page_type(name))); 00153 } 00154 00155 #endif