3025f1d267578f32e9175a816c1d7412d60bf1ee
[ardour.git] / gtk2_ardour / io_selector.h
1 /*
2     Copyright (C) 2002-2007 Paul Davis 
3
4     This program is free software; you can redistribute it and/or modify
5     it under the terms of the GNU General Public License as published by
6     the Free Software Foundation; either version 2 of the License, or
7     (at your option) any later version.
8
9     This program is distributed in the hope that it will be useful,
10     but WITHOUT ANY WARRANTY; without even the implied warranty of
11     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12     GNU General Public License for more details.
13
14     You should have received a copy of the GNU General Public License
15     along with this program; if not, write to the Free Software
16     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17
18 */
19
20 #ifndef __ardour_ui_io_selector_h__
21 #define __ardour_ui_io_selector_h__
22
23 #include <gtkmm/box.h>
24 #include <gtkmm/checkbutton.h>
25 #include <gtkmm/table.h>
26 #include <gtkmm/frame.h>
27
28 #include "ardour_dialog.h"
29
30 namespace ARDOUR {
31         class Session;
32         class IO;
33         class PortInsert;
34 }
35
36 class PortGroup
37 {
38   public:
39         PortGroup (std::string const & n, std::string const & p) : name (n), prefix (p) {}
40
41         void add (std::string const & p);
42
43         std::string name;
44         std::string prefix;
45         std::vector<std::string> ports;
46 };
47
48 class GroupedPortList : public std::list<PortGroup>
49 {
50   public:
51         GroupedPortList (ARDOUR::Session &, boost::shared_ptr<ARDOUR::IO>, bool);
52
53         void refresh ();
54         int n_ports () const;
55         std::string get_port_by_index (int, bool with_prefix = true) const;
56
57   private:
58         ARDOUR::Session& _session;
59         boost::shared_ptr<ARDOUR::IO> _io;
60         bool _for_input;
61 };
62
63
64 /// A widget which provides a set of rotated text labels
65 class RotatedLabelSet : public Gtk::Widget {
66   public:
67         RotatedLabelSet (GroupedPortList&);
68         virtual ~RotatedLabelSet ();
69
70         void set_angle (int);
71         void set_base_dimensions (int, int);
72
73   protected:
74         virtual void on_size_request (Gtk::Requisition*);
75         virtual void on_size_allocate (Gtk::Allocation&);
76         virtual void on_realize ();
77         virtual void on_unrealize ();
78         virtual bool on_expose_event (GdkEventExpose*);
79
80         Glib::RefPtr<Gdk::Window> _gdk_window;
81
82   private:
83         std::pair<int, int> setup_layout (std::string const &);
84
85         GroupedPortList& _port_list; ///< list of ports to display
86         int _angle_degrees; ///< label rotation angle in degrees
87         double _angle_radians; ///< label rotation angle in radians
88         int _base_start; ///< offset to start of labels; see set_base_dimensions() for more details
89         int _base_width; ///< width of labels; see set_base_dimensions() for more details
90         Glib::RefPtr<Pango::Context> _pango_context;
91         Glib::RefPtr<Pango::Layout> _pango_layout;
92         Glib::RefPtr<Gdk::GC> _gc;
93         Gdk::Color _fg_colour;
94         Gdk::Color _bg_colour;
95 };
96
97
98
99 /// Widget for selecting what an IO is connected to
100 class IOSelector : public Gtk::VBox {
101   public:
102         IOSelector (ARDOUR::Session&, boost::shared_ptr<ARDOUR::IO>, bool);
103         ~IOSelector ();
104
105         void redisplay ();
106
107         enum Result {
108                 Cancelled,
109                 Accepted
110         };
111
112         sigc::signal<void, Result> Finished;
113
114   protected:
115         ARDOUR::Session& _session;
116
117   private:
118         void setup_table ();
119         void setup_row_labels ();
120         void setup_check_button_states ();
121         void check_button_toggled (int, int);
122         void add_port_button_clicked ();
123         void remove_port_button_clicked ();
124         void set_button_sensitivity ();
125         void ports_changed (ARDOUR::IOChange, void *);
126         void update_column_label_dimensions ();
127
128         GroupedPortList _port_list;
129         boost::shared_ptr<ARDOUR::IO> _io;
130         bool _for_input;
131         int _width;
132         int _height;
133         std::vector<Gtk::Label*> _row_labels;
134         std::vector<Gtk::EventBox*> _group_labels;
135         RotatedLabelSet _column_labels;
136         std::vector<std::vector<Gtk::CheckButton*> > _check_buttons;
137         bool _ignore_check_button_toggle; ///< check button toggle events are ignored when this is true
138         Gtk::Button _add_port_button;
139         Gtk::Button _remove_port_button;
140         Gtk::VBox _add_remove_box;
141         Gtk::HBox _table_hbox;
142         Gtk::Label _dummy;
143         bool _add_remove_box_added;
144         Gtk::Table _table;
145 };
146
147
148 class IOSelectorWindow : public ArdourDialog
149 {
150   public:
151         IOSelectorWindow (ARDOUR::Session&, boost::shared_ptr<ARDOUR::IO>, bool for_input, bool can_cancel = false);
152         ~IOSelectorWindow ();
153
154         IOSelector& selector() { return _selector; }
155
156   protected:
157         void on_map ();
158         
159   private:
160         IOSelector _selector;
161
162         /* overall operation buttons */
163
164         Gtk::Button ok_button;
165         Gtk::Button cancel_button;
166         Gtk::Button rescan_button;
167
168         void rescan ();
169         void cancel ();
170         void accept ();
171 };
172
173
174 class PortInsertUI : public Gtk::VBox
175 {
176   public: 
177         PortInsertUI (ARDOUR::Session&, boost::shared_ptr<ARDOUR::PortInsert>);
178         
179         void redisplay ();
180         void finished (IOSelector::Result);
181
182   private:
183         Gtk::HBox hbox;
184         IOSelector input_selector;
185         IOSelector output_selector;
186 };
187
188 class PortInsertWindow : public ArdourDialog
189 {
190   public: 
191         PortInsertWindow (ARDOUR::Session&, boost::shared_ptr<ARDOUR::PortInsert>, bool can_cancel = false);
192         
193   protected:
194         void on_map ();
195         
196   private:
197         PortInsertUI _portinsertui;
198         Gtk::VBox vbox;
199         
200         Gtk::Button ok_button;
201         Gtk::Button cancel_button;
202         Gtk::Button rescan_button;
203         Gtk::Frame button_frame;
204         
205         void rescan ();
206         void cancel ();
207         void accept ();
208
209         void plugin_going_away ();
210         sigc::connection going_away_connection;
211 };
212
213
214 #endif