summaryrefslogtreecommitdiff
path: root/gtk2_ardour
diff options
context:
space:
mode:
authorCarl Hetherington <carl@carlh.net>2008-12-18 17:46:28 +0000
committerCarl Hetherington <carl@carlh.net>2008-12-18 17:46:28 +0000
commit883eeb8cf2c717bc0fd121882b484897742f7f28 (patch)
treece39523da16319dc917fdf4a5f5d964b499f4006 /gtk2_ardour
parent058e7f2c0198a1e4036dd0b4de89cf815a0c1e68 (diff)
Implement #826: edit-click on automation points allows value edit.
git-svn-id: svn://localhost/ardour2/branches/3.0@4329 d708f5d6-7413-0410-9779-e7cbd77b26cf
Diffstat (limited to 'gtk2_ardour')
-rw-r--r--gtk2_ardour/SConscript1
-rw-r--r--gtk2_ardour/automation_line.cc105
-rw-r--r--gtk2_ardour/automation_line.h26
-rw-r--r--gtk2_ardour/editor.h1
-rw-r--r--gtk2_ardour/editor_mouse.cc27
-rw-r--r--gtk2_ardour/region_gain_line.cc2
-rw-r--r--gtk2_ardour/region_view.h4
7 files changed, 137 insertions, 29 deletions
diff --git a/gtk2_ardour/SConscript b/gtk2_ardour/SConscript
index ea649dea6a..111722fd30 100644
--- a/gtk2_ardour/SConscript
+++ b/gtk2_ardour/SConscript
@@ -137,6 +137,7 @@ canvas-simpleline.c
canvas-simplerect.c
canvas-waveview.c
control_point.cc
+control_point_dialog.cc
crossfade_edit.cc
crossfade_view.cc
curvetest.cc
diff --git a/gtk2_ardour/automation_line.cc b/gtk2_ardour/automation_line.cc
index 06510b13e7..5e8d2c5514 100644
--- a/gtk2_ardour/automation_line.cc
+++ b/gtk2_ardour/automation_line.cc
@@ -64,7 +64,7 @@ AutomationLine::AutomationLine (const string& name, TimeAxisView& tv, ArdourCanv
_interpolation = al->interpolation();
points_visible = false;
update_pending = false;
- _vc_uses_gain_mapping = false;
+ _uses_gain_mapping = false;
no_draw = false;
_visible = true;
terminal_points_can_slide = true;
@@ -84,8 +84,9 @@ AutomationLine::AutomationLine (const string& name, TimeAxisView& tv, ArdourCanv
trackview.session().register_with_memento_command_factory(alist->id(), this);
- if (alist->parameter().type() == GainAutomation)
- set_verbose_cursor_uses_gain_mapping (true);
+ if (alist->parameter().type() == GainAutomation) {
+ set_uses_gain_mapping (true);
+ }
set_interpolation(alist->interpolation());
}
@@ -176,10 +177,10 @@ AutomationLine::set_line_color (uint32_t color)
}
void
-AutomationLine::set_verbose_cursor_uses_gain_mapping (bool yn)
+AutomationLine::set_uses_gain_mapping (bool yn)
{
- if (yn != _vc_uses_gain_mapping) {
- _vc_uses_gain_mapping = yn;
+ if (yn != _uses_gain_mapping) {
+ _uses_gain_mapping = yn;
reset ();
}
}
@@ -195,6 +196,41 @@ AutomationLine::nth (uint32_t n)
}
void
+AutomationLine::modify_point_y (ControlPoint& cp, double y)
+{
+ /* clamp y-coord appropriately. y is supposed to be a normalized fraction (0.0-1.0),
+ and needs to be converted to a canvas unit distance.
+ */
+
+ y = max (0.0, y);
+ y = min (1.0, y);
+ y = _height - (y * _height);
+
+ double const x = trackview.editor.frame_to_unit ((*cp.model())->when);
+
+ trackview.editor.current_session()->begin_reversible_command (_("automation event move"));
+ trackview.editor.current_session()->add_command (new MementoCommand<AutomationList>(*alist.get(), &get_state(), 0));
+
+ cp.move_to (x, y, ControlPoint::Full);
+ reset_line_coords (cp);
+
+ if (line_points.size() > 1) {
+ line->property_points() = line_points;
+ }
+
+ alist->freeze ();
+ sync_model_with_view_point (cp, false, 0);
+ alist->thaw ();
+
+ update_pending = false;
+
+ trackview.editor.current_session()->add_command (new MementoCommand<AutomationList>(*alist.get(), 0, &alist->get_state()));
+ trackview.editor.current_session()->commit_reversible_command ();
+ trackview.editor.current_session()->set_dirty ();
+}
+
+
+void
AutomationLine::modify_view_point (ControlPoint& cp, double x, double y, bool with_push)
{
double delta = 0.0;
@@ -602,19 +638,35 @@ AutomationLine::determine_visible_control_points (ALPoints& points)
}
string
-AutomationLine::get_verbose_cursor_string (double fraction)
+AutomationLine::get_verbose_cursor_string (double fraction) const
+{
+ std::string s = fraction_to_string (fraction);
+ if (_uses_gain_mapping) {
+ s += " dB";
+ }
+
+ return s;
+}
+
+/**
+ * @param fraction y fraction
+ * @return string representation of this value, using dB if appropriate.
+ */
+
+string
+AutomationLine::fraction_to_string (double fraction) const
{
char buf[32];
- if (_vc_uses_gain_mapping) {
+ if (_uses_gain_mapping) {
if (fraction == 0.0) {
- snprintf (buf, sizeof (buf), "-inf dB");
+ snprintf (buf, sizeof (buf), "-inf");
} else {
- snprintf (buf, sizeof (buf), "%.1fdB", coefficient_to_dB (slider_position_to_gain (fraction)));
+ snprintf (buf, sizeof (buf), "%.1f", coefficient_to_dB (slider_position_to_gain (fraction)));
}
} else {
- view_to_model_y(fraction);
- if (EventTypeMap::instance().is_integer(alist->parameter())) {
+ view_to_model_y (fraction);
+ if (EventTypeMap::instance().is_integer (alist->parameter())) {
snprintf (buf, sizeof (buf), "%d", (int)fraction);
} else {
snprintf (buf, sizeof (buf), "%.2f", fraction);
@@ -624,6 +676,31 @@ AutomationLine::get_verbose_cursor_string (double fraction)
return buf;
}
+
+/**
+ * @param s Value string in the form as returned by fraction_to_string.
+ * @return Corresponding y fraction.
+ */
+
+double
+AutomationLine::string_to_fraction (string const & s) const
+{
+ if (s == "-inf") {
+ return 0;
+ }
+
+ double v;
+ sscanf (s.c_str(), "%lf", &v);
+
+ if (_uses_gain_mapping) {
+ v = gain_to_slider_position (dB_to_coefficient (v));
+ } else {
+ model_to_view_y (v);
+ }
+
+ return v;
+}
+
bool
AutomationLine::invalid_point (ALPoints& p, uint32_t index)
{
@@ -1165,7 +1242,7 @@ AutomationLine::set_state (const XMLNode &node)
}
void
-AutomationLine::view_to_model_y (double& y)
+AutomationLine::view_to_model_y (double& y) const
{
/* TODO: This should be more generic ... */
if (alist->parameter().type() == GainAutomation) {
@@ -1183,7 +1260,7 @@ AutomationLine::view_to_model_y (double& y)
}
void
-AutomationLine::model_to_view_y (double& y)
+AutomationLine::model_to_view_y (double& y) const
{
/* TODO: This should be more generic ... */
if (alist->parameter().type() == GainAutomation) {
diff --git a/gtk2_ardour/automation_line.h b/gtk2_ardour/automation_line.h
index 7fd9dd3447..3444de3cb2 100644
--- a/gtk2_ardour/automation_line.h
+++ b/gtk2_ardour/automation_line.h
@@ -36,9 +36,6 @@
#include <ardour/automation_list.h>
-using std::vector;
-using std::string;
-
class AutomationLine;
class ControlPoint;
class PointSelection;
@@ -66,8 +63,8 @@ class AutomationLine : public sigc::trackable, public PBD::StatefulThingWithGoin
void set_selected_points (PointSelection&);
void get_selectables (nframes_t& start, nframes_t& end,
double botfrac, double topfrac,
- list<Selectable*>& results);
- void get_inverted_selectables (Selection&, list<Selectable*>& results);
+ std::list<Selectable*>& results);
+ void get_inverted_selectables (Selection&, std::list<Selectable*>& results);
virtual void remove_point (ControlPoint&);
bool control_points_adjacent (double xval, uint32_t& before, uint32_t& after);
@@ -94,7 +91,8 @@ class AutomationLine : public sigc::trackable, public PBD::StatefulThingWithGoin
void show ();
void hide ();
void set_height (guint32);
- void set_verbose_cursor_uses_gain_mapping (bool yn);
+ void set_uses_gain_mapping (bool yn);
+ bool get_uses_gain_mapping () const { return _uses_gain_mapping; }
TimeAxisView& trackview;
@@ -105,9 +103,11 @@ class AutomationLine : public sigc::trackable, public PBD::StatefulThingWithGoin
void show_selection();
void hide_selection ();
- virtual string get_verbose_cursor_string (double);
- virtual void view_to_model_y (double&);
- virtual void model_to_view_y (double&);
+ string get_verbose_cursor_string (double) const;
+ string fraction_to_string (double) const;
+ double string_to_fraction (string const &) const;
+ void view_to_model_y (double&) const;
+ void model_to_view_y (double&) const;
void set_list(boost::shared_ptr<ARDOUR::AutomationList> list);
boost::shared_ptr<ARDOUR::AutomationList> the_list() const { return alist; }
@@ -125,6 +125,8 @@ class AutomationLine : public sigc::trackable, public PBD::StatefulThingWithGoin
int set_state (const XMLNode&);
void set_colors();
+ void modify_point_y (ControlPoint&, double);
+
protected:
string _name;
@@ -133,7 +135,7 @@ class AutomationLine : public sigc::trackable, public PBD::StatefulThingWithGoin
boost::shared_ptr<ARDOUR::AutomationList> alist;
bool _visible : 1;
- bool _vc_uses_gain_mapping : 1;
+ bool _uses_gain_mapping : 1;
bool terminal_points_can_slide : 1;
bool update_pending : 1;
bool no_draw : 1;
@@ -144,7 +146,7 @@ class AutomationLine : public sigc::trackable, public PBD::StatefulThingWithGoin
ArdourCanvas::Group* group;
ArdourCanvas::Line* line; /* line */
ArdourCanvas::Points line_points; /* coordinates for canvas line */
- vector<ControlPoint*> control_points; /* visible control points */
+ std::vector<ControlPoint*> control_points; /* visible control points */
struct ALPoint {
double x;
@@ -180,7 +182,7 @@ class AutomationLine : public sigc::trackable, public PBD::StatefulThingWithGoin
ARDOUR::AutomationList::InterpolationStyle _interpolation;
- void modify_view_point(ControlPoint&, double, double, bool with_push);
+ void modify_view_point (ControlPoint&, double, double, bool with_push);
void reset_line_coords (ControlPoint&);
double control_point_box_size ();
diff --git a/gtk2_ardour/editor.h b/gtk2_ardour/editor.h
index 4ce8b1bcd2..e9f83ddf68 100644
--- a/gtk2_ardour/editor.h
+++ b/gtk2_ardour/editor.h
@@ -1603,6 +1603,7 @@ public:
void edit_meter_section (ARDOUR::MeterSection*);
void edit_tempo_marker (ArdourCanvas::Item*);
void edit_meter_marker (ArdourCanvas::Item*);
+ void edit_control_point (ArdourCanvas::Item*);
void marker_menu_edit ();
void marker_menu_remove ();
diff --git a/gtk2_ardour/editor_mouse.cc b/gtk2_ardour/editor_mouse.cc
index 4b4ed86164..b652d129f6 100644
--- a/gtk2_ardour/editor_mouse.cc
+++ b/gtk2_ardour/editor_mouse.cc
@@ -49,6 +49,7 @@
#include "keyboard.h"
#include "editing.h"
#include "rgb_macros.h"
+#include "control_point_dialog.h"
#include <ardour/types.h>
#include <ardour/profile.h>
@@ -1071,6 +1072,10 @@ Editor::button_release_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemT
}
break;
+ case ControlPointItem:
+ edit_control_point (item);
+ break;
+
default:
break;
}
@@ -3203,6 +3208,28 @@ Editor::control_point_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent
}
void
+Editor::edit_control_point (ArdourCanvas::Item* item)
+{
+ ControlPoint* p = reinterpret_cast<ControlPoint *> (item->get_data ("control_point"));
+
+ if (p == 0) {
+ fatal << _("programming error: control point canvas item has no control point object pointer!") << endmsg;
+ /*NOTREACHED*/
+ }
+
+ ControlPointDialog d (p);
+ d.set_position (Gtk::WIN_POS_MOUSE);
+ ensure_float (d);
+
+ if (d.run () != RESPONSE_ACCEPT) {
+ return;
+ }
+
+ p->line().modify_point_y (*p, d.get_y_fraction ());
+}
+
+
+void
Editor::start_line_grab_from_regionview (ArdourCanvas::Item* item, GdkEvent* event)
{
switch (mouse_mode) {
diff --git a/gtk2_ardour/region_gain_line.cc b/gtk2_ardour/region_gain_line.cc
index 61f7dde0c7..204148bd77 100644
--- a/gtk2_ardour/region_gain_line.cc
+++ b/gtk2_ardour/region_gain_line.cc
@@ -47,7 +47,7 @@ AudioRegionGainLine::AudioRegionGainLine (const string & name, Session& s, Audio
assert(l->parameter().type() == EnvelopeAutomation);
group->raise_to_top ();
- set_verbose_cursor_uses_gain_mapping (true);
+ set_uses_gain_mapping (true);
terminal_points_can_slide = false;
}
diff --git a/gtk2_ardour/region_view.h b/gtk2_ardour/region_view.h
index 987b2d66a9..b9258396d9 100644
--- a/gtk2_ardour/region_view.h
+++ b/gtk2_ardour/region_view.h
@@ -130,7 +130,7 @@ class RegionView : public TimeAxisViewItem
RegionEditor* editor;
- vector<ControlPoint *> control_points;
+ std::vector<ControlPoint *> control_points;
double current_visible_sync_position;
bool valid; ///< see StreamView::redisplay_diskstream()
@@ -142,7 +142,7 @@ class RegionView : public TimeAxisViewItem
bool wait_for_data;
sigc::connection data_ready_connection;
- vector<GhostRegion*> ghosts;
+ std::vector<GhostRegion*> ghosts;
typedef std::map<const Evoral::Parameter, boost::shared_ptr<AutomationRegionView> > AutomationChildren;
AutomationChildren _automation_children;