13
0

Constrain height of group-tab to the editor's height

Previously the group-tab extended all the way down to the
last track. Potentially with a widget height of > 2^15 px.

This caused issues with gtk widgets (notably on Windows)
```
unhandled exception (type std::exception) in signal handler:
what: invalid value (typically too big) for the size of the input (surface, pattern, etc.)
```

This also prepares for Mixer Tab-Group to use the same
separation between visible and total extent.
This commit is contained in:
Robin Gareus 2024-06-22 04:46:09 +02:00
parent c94ca79798
commit bdd6eec95c
Signed by: rgareus
GPG Key ID: A090BCE02CF57F04
9 changed files with 71 additions and 32 deletions

View File

@ -591,11 +591,8 @@ Editor::Editor ()
vertical_adjustment.signal_value_changed().connect (sigc::mem_fun(*this, &Editor::tie_vertical_scrolling), true); vertical_adjustment.signal_value_changed().connect (sigc::mem_fun(*this, &Editor::tie_vertical_scrolling), true);
_track_canvas->signal_map_event().connect (sigc::mem_fun (*this, &Editor::track_canvas_map_handler)); _track_canvas->signal_map_event().connect (sigc::mem_fun (*this, &Editor::track_canvas_map_handler));
HBox* h = manage (new HBox);
_group_tabs = new EditorGroupTabs (this); _group_tabs = new EditorGroupTabs (this);
h->pack_start (*_group_tabs, PACK_SHRINK); controls_layout.add (edit_controls_vbox);
h->pack_start (edit_controls_vbox);
controls_layout.add (*h);
HSeparator* separator = manage (new HSeparator()); HSeparator* separator = manage (new HSeparator());
separator->set_name("TrackSeparator"); separator->set_name("TrackSeparator");
@ -609,6 +606,8 @@ Editor::Editor ()
controls_layout.signal_button_release_event().connect (sigc::mem_fun(*this, &Editor::edit_controls_button_event)); controls_layout.signal_button_release_event().connect (sigc::mem_fun(*this, &Editor::edit_controls_button_event));
controls_layout.signal_scroll_event().connect (sigc::mem_fun(*this, &Editor::control_layout_scroll), false); controls_layout.signal_scroll_event().connect (sigc::mem_fun(*this, &Editor::control_layout_scroll), false);
_group_tabs->signal_scroll_event().connect (sigc::mem_fun(*this, &Editor::control_layout_scroll), false);
_cursors = new MouseCursors; _cursors = new MouseCursors;
_cursors->set_cursor_set (UIConfiguration::instance().get_icon_set()); _cursors->set_cursor_set (UIConfiguration::instance().get_icon_set());
@ -641,15 +640,16 @@ Editor::Editor ()
axis_view_shadow->set_name("EditorWindow"); axis_view_shadow->set_name("EditorWindow");
axis_view_shadow->show(); axis_view_shadow->show();
edit_packer.attach (*axis_view_shadow, 0, 1, 0, 2, FILL, FILL|EXPAND, 0, 0); edit_packer.attach (*axis_view_shadow, 0, 1, 0, 2, FILL, FILL|EXPAND, 0, 0);
#endif #endif
/* labels for the time bars */ /* labels for the time bars */
edit_packer.attach (time_bars_event_box, 1, 2, 0, 1, FILL, SHRINK, 0, 0); edit_packer.attach (time_bars_event_box, 1, 3, 0, 1, FILL, SHRINK, 0, 0);
/* track controls */ /* track controls */
edit_packer.attach (controls_layout, 1, 2, 1, 2, FILL, FILL|EXPAND, 0, 0); edit_packer.attach (*_group_tabs, 1, 2, 1, 2, FILL, FILL|EXPAND, 0, 0);
edit_packer.attach (controls_layout, 2, 3, 1, 2, FILL, FILL|EXPAND, 0, 0);
/* canvas */ /* canvas */
edit_packer.attach (*_track_canvas_viewport, 2, 3, 0, 2, FILL|EXPAND, FILL|EXPAND, 0, 0); edit_packer.attach (*_track_canvas_viewport, 3, 4, 0, 2, FILL|EXPAND, FILL|EXPAND, 0, 0);
bottom_hbox.set_border_width (2); bottom_hbox.set_border_width (2);
bottom_hbox.set_spacing (3); bottom_hbox.set_spacing (3);

View File

@ -347,11 +347,6 @@ Editor::reset_controls_layout_width ()
req = edit_controls_vbox.size_request (); req = edit_controls_vbox.size_request ();
w = req.width; w = req.width;
if (_group_tabs->get_visible()) {
req = _group_tabs->size_request ();
w += req.width;
}
/* the controls layout has no horizontal scrolling, its visible /* the controls layout has no horizontal scrolling, its visible
width is always equal to the total width of its contents. width is always equal to the total width of its contents.
*/ */
@ -381,6 +376,7 @@ Editor::reset_controls_layout_height (int32_t h)
controls_layout.property_height() = h; controls_layout.property_height() = h;
_group_tabs->set_extent (h);
} }
bool bool
@ -1016,6 +1012,7 @@ Editor::tie_vertical_scrolling ()
_region_peak_cursor->hide (); _region_peak_cursor->hide ();
_summary->set_overlays_dirty (); _summary->set_overlays_dirty ();
} }
_group_tabs->set_offset (vertical_adjustment.get_value ());
} }
void void

View File

@ -87,6 +87,13 @@ EditorGroupTabs::compute_tabs () const
void void
EditorGroupTabs::draw_tab (cairo_t* cr, Tab const & tab) EditorGroupTabs::draw_tab (cairo_t* cr, Tab const & tab)
{ {
const double from = tab.from - offset ();
const double to = tab.to - offset ();
if (from > visible_extent () || to < 0) {
return;
}
double const arc_radius = get_width(); double const arc_radius = get_width();
double r, g, b, a; double r, g, b, a;
@ -99,14 +106,14 @@ EditorGroupTabs::draw_tab (cairo_t* cr, Tab const & tab)
a = 1.0; a = 1.0;
cairo_set_source_rgba (cr, r, g, b, a); cairo_set_source_rgba (cr, r, g, b, a);
cairo_move_to (cr, 0, tab.from + arc_radius); cairo_move_to (cr, 0, from + arc_radius);
cairo_arc (cr, get_width(), tab.from + arc_radius, arc_radius, M_PI, 3 * M_PI / 2); cairo_arc (cr, get_width(), from + arc_radius, arc_radius, M_PI, 3 * M_PI / 2);
cairo_line_to (cr, get_width(), tab.to); cairo_line_to (cr, get_width(), to);
cairo_arc (cr, get_width(), tab.to - arc_radius, arc_radius, M_PI / 2, M_PI); cairo_arc (cr, get_width(), to - arc_radius, arc_radius, M_PI / 2, M_PI);
cairo_line_to (cr, 0, tab.from + arc_radius); cairo_line_to (cr, 0, from + arc_radius);
cairo_fill (cr); cairo_fill (cr);
if (tab.group && (tab.to - tab.from) > arc_radius) { if (tab.group && (to - from) > arc_radius) {
int text_width, text_height; int text_width, text_height;
Glib::RefPtr<Pango::Layout> layout; Glib::RefPtr<Pango::Layout> layout;
@ -114,10 +121,10 @@ EditorGroupTabs::draw_tab (cairo_t* cr, Tab const & tab)
layout->set_ellipsize (Pango::ELLIPSIZE_MIDDLE); layout->set_ellipsize (Pango::ELLIPSIZE_MIDDLE);
layout->set_text (tab.group->name ()); layout->set_text (tab.group->name ());
layout->set_width ((tab.to - tab.from - arc_radius) * PANGO_SCALE); layout->set_width ((to - from - arc_radius) * PANGO_SCALE);
layout->get_pixel_size (text_width, text_height); layout->get_pixel_size (text_width, text_height);
cairo_move_to (cr, (get_width() - text_height) * .5, (text_width + tab.to + tab.from) * .5); cairo_move_to (cr, (get_width() - text_height) * .5, (text_width + to + from) * .5);
Gtkmm2ext::Color c = Gtkmm2ext::contrasting_text_color (Gtkmm2ext::rgba_to_color (r, g, b, a)); Gtkmm2ext::Color c = Gtkmm2ext::contrasting_text_color (Gtkmm2ext::rgba_to_color (r, g, b, a));
Gtkmm2ext::color_to_rgba (c, r, g, b, a); Gtkmm2ext::color_to_rgba (c, r, g, b, a);
@ -133,7 +140,7 @@ EditorGroupTabs::draw_tab (cairo_t* cr, Tab const & tab)
double double
EditorGroupTabs::primary_coordinate (double, double y) const EditorGroupTabs::primary_coordinate (double, double y) const
{ {
return y; return y + offset ();
} }
RouteList RouteList

View File

@ -35,11 +35,12 @@ private:
void draw_tab (cairo_t *, Tab const &); void draw_tab (cairo_t *, Tab const &);
double primary_coordinate (double, double) const; double primary_coordinate (double, double) const;
ARDOUR::RouteList routes_for_tab (Tab const *) const; ARDOUR::RouteList routes_for_tab (Tab const *) const;
double extent () const {
return get_height();
}
void add_menu_items (Gtk::Menu *, ARDOUR::RouteGroup *); void add_menu_items (Gtk::Menu *, ARDOUR::RouteGroup *);
ARDOUR::RouteList selected_routes () const; ARDOUR::RouteList selected_routes () const;
double visible_extent () const {
return get_height();
}
}; };
#endif // __gtk_ardour_editor_group_tabs_h__ #endif // __gtk_ardour_editor_group_tabs_h__

View File

@ -52,6 +52,8 @@ GroupTabs::GroupTabs ()
: _menu (0) : _menu (0)
, _dragging (0) , _dragging (0)
, _dragging_new_tab (0) , _dragging_new_tab (0)
, _extent (-1)
, _offset (0)
{ {
add_events (Gdk::BUTTON_PRESS_MASK|Gdk::BUTTON_RELEASE_MASK|Gdk::POINTER_MOTION_MASK); add_events (Gdk::BUTTON_PRESS_MASK|Gdk::BUTTON_RELEASE_MASK|Gdk::POINTER_MOTION_MASK);
UIConfiguration::instance().ColorsChanged.connect (sigc::mem_fun (*this, &GroupTabs::queue_draw)); UIConfiguration::instance().ColorsChanged.connect (sigc::mem_fun (*this, &GroupTabs::queue_draw));
@ -82,6 +84,27 @@ GroupTabs::set_session (Session* s)
} }
} }
void
GroupTabs::set_extent (double extent)
{
if (_extent == extent) {
return;
}
_extent = extent;
set_dirty ();
queue_draw ();
}
void
GroupTabs::set_offset (double offset)
{
if (_offset == offset) {
return;
}
_offset = offset;
set_dirty ();
queue_draw ();
}
/** Handle a size request. /** Handle a size request.
* @param req GTK requisition * @param req GTK requisition

View File

@ -65,6 +65,9 @@ public:
void run_new_group_dialog (ARDOUR::RouteList const *, bool with_master); void run_new_group_dialog (ARDOUR::RouteList const *, bool with_master);
void set_extent (double);
void set_offset (double);
static void set_group_color (ARDOUR::RouteGroup *, uint32_t); static void set_group_color (ARDOUR::RouteGroup *, uint32_t);
static std::string group_gui_id (ARDOUR::RouteGroup *); static std::string group_gui_id (ARDOUR::RouteGroup *);
static uint32_t group_color (ARDOUR::RouteGroup *); static uint32_t group_color (ARDOUR::RouteGroup *);
@ -80,6 +83,15 @@ protected:
ARDOUR::RouteGroup* group; ///< route group ARDOUR::RouteGroup* group; ///< route group
}; };
/** @return Size of the widget along the primary axis */
virtual double visible_extent () const = 0;
/** @return Size of all contained strips along the primary axis */
double extent () const { return _extent < 0 ? visible_extent () : _extent; }
/** @return Scroll offset of \ref visible_extent along the primary axis */
double offset () const { return _offset; }
private: private:
static void emit_gui_changed_for_members (std::shared_ptr<ARDOUR::RouteList>); static void emit_gui_changed_for_members (std::shared_ptr<ARDOUR::RouteList>);
@ -102,10 +114,6 @@ private:
virtual double primary_coordinate (double x, double y) const = 0; virtual double primary_coordinate (double x, double y) const = 0;
virtual ARDOUR::RouteList routes_for_tab (Tab const * t) const = 0; virtual ARDOUR::RouteList routes_for_tab (Tab const * t) const = 0;
/** @return Size of the widget along the primary axis */
virtual double extent () const = 0;
virtual void add_menu_items (Gtk::Menu *, ARDOUR::RouteGroup *) {} virtual void add_menu_items (Gtk::Menu *, ARDOUR::RouteGroup *) {}
virtual ARDOUR::RouteList selected_routes () const = 0; virtual ARDOUR::RouteList selected_routes () const = 0;
@ -162,6 +170,8 @@ private:
double _drag_min; ///< minimum position for drag double _drag_min; ///< minimum position for drag
double _drag_max; ///< maximum position for drag double _drag_max; ///< maximum position for drag
double _drag_first; ///< first mouse pointer position during drag double _drag_first; ///< first mouse pointer position during drag
double _extent;
double _offset;
/** colors that have been used for new route group tabs */ /** colors that have been used for new route group tabs */
static std::list<Gdk::Color> _used_colors; static std::list<Gdk::Color> _used_colors;

View File

@ -34,7 +34,8 @@ private:
void draw_tab (cairo_t *, Tab const &); void draw_tab (cairo_t *, Tab const &);
double primary_coordinate (double, double) const; double primary_coordinate (double, double) const;
ARDOUR::RouteList routes_for_tab (Tab const *) const; ARDOUR::RouteList routes_for_tab (Tab const *) const;
double extent () const {
double visible_extent () const {
return get_width(); return get_width();
} }

View File

@ -39,7 +39,7 @@ RecorderGroupTabs::primary_coordinate (double, double y) const
} }
double double
RecorderGroupTabs::extent () const RecorderGroupTabs::visible_extent () const
{ {
return get_height (); return get_height ();
} }

View File

@ -34,7 +34,7 @@ private:
ARDOUR::RouteList routes_for_tab (Tab const*) const; ARDOUR::RouteList routes_for_tab (Tab const*) const;
ARDOUR::RouteList selected_routes () const; ARDOUR::RouteList selected_routes () const;
double primary_coordinate (double, double) const; double primary_coordinate (double, double) const;
double extent () const; double visible_extent () const;
RecorderUI* _recorder; RecorderUI* _recorder;
}; };