Limit region-based automation to the edges of regions. Fixes #3201.
git-svn-id: svn://localhost/ardour2/branches/3.0@7662 d708f5d6-7413-0410-9779-e7cbd77b26cf
This commit is contained in:
parent
b2bf4eee3d
commit
822ee79d84
@ -65,6 +65,7 @@ AutomationLine::AutomationLine (const string& name, TimeAxisView& tv, ArdourCanv
|
||||
, alist (al)
|
||||
, _parent_group (parent)
|
||||
, _time_converter (converter ? (*converter) : default_converter)
|
||||
, _maximum_time (max_frames)
|
||||
{
|
||||
points_visible = false;
|
||||
update_pending = false;
|
||||
@ -1322,3 +1323,12 @@ AutomationLine::memento_command_binder ()
|
||||
{
|
||||
return new SimpleMementoCommandBinder<AutomationList> (*alist.get());
|
||||
}
|
||||
|
||||
/** Set the maximum time that points on this line can be at, relative
|
||||
* to the start of the track or region that it is on.
|
||||
*/
|
||||
void
|
||||
AutomationLine::set_maximum_time (framepos_t t)
|
||||
{
|
||||
_maximum_time = t;
|
||||
}
|
||||
|
@ -138,6 +138,11 @@ class AutomationLine : public sigc::trackable, public PBD::StatefulDestructible
|
||||
return _time_converter;
|
||||
}
|
||||
|
||||
void set_maximum_time (ARDOUR::framepos_t);
|
||||
ARDOUR::framepos_t maximum_time () const {
|
||||
return _maximum_time;
|
||||
}
|
||||
|
||||
protected:
|
||||
|
||||
std::string _name;
|
||||
@ -218,6 +223,9 @@ class AutomationLine : public sigc::trackable, public PBD::StatefulDestructible
|
||||
|
||||
PBD::ScopedConnectionList _list_connections;
|
||||
|
||||
/** maximum time that a point on this line can be at, relative to the start of its region or track */
|
||||
ARDOUR::framecnt_t _maximum_time;
|
||||
|
||||
friend class AudioRegionGainLine;
|
||||
};
|
||||
|
||||
|
@ -86,6 +86,7 @@ AutomationRegionView::create_line (boost::shared_ptr<ARDOUR::AutomationList> lis
|
||||
_line->set_height ((uint32_t)rint(trackview.current_height() - NAME_HIGHLIGHT_SIZE));
|
||||
_line->show();
|
||||
_line->show_all_control_points();
|
||||
_line->set_maximum_time (_region->length());
|
||||
}
|
||||
|
||||
bool
|
||||
@ -177,6 +178,10 @@ AutomationRegionView::set_height (double h)
|
||||
bool
|
||||
AutomationRegionView::set_position (nframes64_t pos, void* src, double* ignored)
|
||||
{
|
||||
if (_line) {
|
||||
_line->set_maximum_time (_region->length ());
|
||||
}
|
||||
|
||||
return RegionView::set_position(pos, src, ignored);
|
||||
}
|
||||
|
||||
@ -186,8 +191,9 @@ AutomationRegionView::reset_width_dependent_items (double pixel_width)
|
||||
{
|
||||
RegionView::reset_width_dependent_items(pixel_width);
|
||||
|
||||
if (_line)
|
||||
if (_line) {
|
||||
_line->reset();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -196,8 +202,10 @@ AutomationRegionView::region_resized (const PBD::PropertyChange& what_changed)
|
||||
{
|
||||
RegionView::region_resized(what_changed);
|
||||
|
||||
if (_line)
|
||||
if (_line) {
|
||||
_line->reset();
|
||||
_line->set_maximum_time (_region->length());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
@ -2736,12 +2736,12 @@ ControlPointDrag::start_grab (GdkEvent* event, Gdk::Cursor* /*cursor*/)
|
||||
|
||||
// start the grab at the center of the control point so
|
||||
// the point doesn't 'jump' to the mouse after the first drag
|
||||
_time_axis_view_grab_x = _point->get_x();
|
||||
_time_axis_view_grab_y = _point->get_y();
|
||||
_fixed_grab_x = _point->get_x();
|
||||
_fixed_grab_y = _point->get_y();
|
||||
|
||||
float const fraction = 1 - (_point->get_y() / _point->line().height());
|
||||
|
||||
_point->line().start_drag_single (_point, _time_axis_view_grab_x, fraction);
|
||||
_point->line().start_drag_single (_point, _fixed_grab_x, fraction);
|
||||
|
||||
_editor->set_verbose_canvas_cursor (_point->line().get_verbose_cursor_string (fraction),
|
||||
event->button.x + 10, event->button.y + 10);
|
||||
@ -2760,9 +2760,10 @@ ControlPointDrag::motion (GdkEvent* event, bool)
|
||||
dy *= 0.1;
|
||||
}
|
||||
|
||||
/* coordinate in TimeAxisView's space */
|
||||
double cx = _time_axis_view_grab_x + _cumulative_x_drag + dx;
|
||||
double cy = _time_axis_view_grab_y + _cumulative_y_drag + dy;
|
||||
/* coordinate in pixels relative to the start of the region (for region-based automation)
|
||||
or track (for track-based automation) */
|
||||
double cx = _fixed_grab_x + _cumulative_x_drag + dx;
|
||||
double cy = _fixed_grab_y + _cumulative_y_drag + dy;
|
||||
|
||||
// calculate zero crossing point. back off by .01 to stay on the
|
||||
// positive side of zero
|
||||
@ -2774,25 +2775,27 @@ ControlPointDrag::motion (GdkEvent* event, bool)
|
||||
}
|
||||
|
||||
if (_x_constrained) {
|
||||
cx = _time_axis_view_grab_x;
|
||||
cx = _fixed_grab_x;
|
||||
}
|
||||
if (_y_constrained) {
|
||||
cy = _time_axis_view_grab_y;
|
||||
cy = _fixed_grab_y;
|
||||
}
|
||||
|
||||
_cumulative_x_drag = cx - _time_axis_view_grab_x;
|
||||
_cumulative_y_drag = cy - _time_axis_view_grab_y;
|
||||
_cumulative_x_drag = cx - _fixed_grab_x;
|
||||
_cumulative_y_drag = cy - _fixed_grab_y;
|
||||
|
||||
cx = max (0.0, cx);
|
||||
cy = max (0.0, cy);
|
||||
cy = min ((double) _point->line().height(), cy);
|
||||
|
||||
nframes64_t cx_frames = _editor->unit_to_frame (cx);
|
||||
framepos_t cx_frames = _editor->unit_to_frame (cx);
|
||||
|
||||
if (!_x_constrained) {
|
||||
_editor->snap_to_with_modifier (cx_frames, event);
|
||||
}
|
||||
|
||||
cx_frames = min (cx_frames, _point->line().maximum_time());
|
||||
|
||||
float const fraction = 1.0 - (cy / _point->line().height());
|
||||
|
||||
bool const push = Keyboard::modifier_state_contains (event->button.state, Keyboard::PrimaryModifier);
|
||||
@ -2875,8 +2878,8 @@ LineDrag::start_grab (GdkEvent* event, Gdk::Cursor* /*cursor*/)
|
||||
|
||||
/* store grab start in parent frame */
|
||||
|
||||
_time_axis_view_grab_x = cx;
|
||||
_time_axis_view_grab_y = cy;
|
||||
_fixed_grab_x = cx;
|
||||
_fixed_grab_y = cy;
|
||||
|
||||
double fraction = 1.0 - (cy / _line->height());
|
||||
|
||||
@ -2897,9 +2900,9 @@ LineDrag::motion (GdkEvent* event, bool)
|
||||
dy *= 0.1;
|
||||
}
|
||||
|
||||
double cy = _time_axis_view_grab_y + _cumulative_y_drag + dy;
|
||||
double cy = _fixed_grab_y + _cumulative_y_drag + dy;
|
||||
|
||||
_cumulative_y_drag = cy - _time_axis_view_grab_y;
|
||||
_cumulative_y_drag = cy - _fixed_grab_y;
|
||||
|
||||
cy = max (0.0, cy);
|
||||
cy = min ((double) _line->height(), cy);
|
||||
|
@ -596,8 +596,8 @@ public:
|
||||
private:
|
||||
|
||||
ControlPoint* _point;
|
||||
double _time_axis_view_grab_x;
|
||||
double _time_axis_view_grab_y;
|
||||
double _fixed_grab_x;
|
||||
double _fixed_grab_y;
|
||||
double _cumulative_x_drag;
|
||||
double _cumulative_y_drag;
|
||||
static double const _zero_gain_fraction;
|
||||
@ -621,8 +621,8 @@ public:
|
||||
private:
|
||||
|
||||
AutomationLine* _line;
|
||||
double _time_axis_view_grab_x;
|
||||
double _time_axis_view_grab_y;
|
||||
double _fixed_grab_x;
|
||||
double _fixed_grab_y;
|
||||
uint32_t _before;
|
||||
uint32_t _after;
|
||||
double _cumulative_y_drag;
|
||||
|
Loading…
Reference in New Issue
Block a user