diff options
author | David Robillard <d@drobilla.net> | 2014-12-28 15:50:57 -0500 |
---|---|---|
committer | David Robillard <d@drobilla.net> | 2014-12-28 16:06:44 -0500 |
commit | 4c0cebf7f98ecd14873d26b6f4d8bdedd37cb994 (patch) | |
tree | 8efbd17e96fc1c56392ff77e2ef3d99e5f3af731 /gtk2_ardour/transform_dialog.h | |
parent | ec947ff8fd2cf229284f757b8bd6b0f96cbd6383 (diff) |
MIDI transform dialog.
Diffstat (limited to 'gtk2_ardour/transform_dialog.h')
-rw-r--r-- | gtk2_ardour/transform_dialog.h | 140 |
1 files changed, 140 insertions, 0 deletions
diff --git a/gtk2_ardour/transform_dialog.h b/gtk2_ardour/transform_dialog.h new file mode 100644 index 0000000000..5111aa7543 --- /dev/null +++ b/gtk2_ardour/transform_dialog.h @@ -0,0 +1,140 @@ +/* + Copyright (C) 2009-2014 Paul Davis + Author: David Robillard + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#ifndef __transform_dialog_h__ +#define __transform_dialog_h__ + +#include <list> +#include <string> + +#include <gtkmm/combobox.h> +#include <gtkmm/liststore.h> +#include <gtkmm/treemodel.h> +#include <gtkmm/spinbutton.h> + +#include "ardour/midi_model.h" +#include "ardour/transform.h" +#include "ardour/types.h" +#include "evoral/types.hpp" + +#include "ardour_dialog.h" + +/** Dialog for building a MIDI note transformation. + * + * This can build transformations with any number of operations, but is limited + * in power and can't build arbitrary transformations since there is no way to do + * conceptually parenthetical things (i.e. push things to the stack). + * + * With this, it is possible to build transformations that process a single + * value in a series of steps starting with a seed, like: "value = seed OP + * value OP value ..." where OP is +, -, *, or /, left associative with no + * precedence. This is simple and pretty clear to the user what's going to + * happen, though a bit limited. It would be nice if the GUI could build + * fancier transformations, but it's not obvious how to do this without making + * things more confusing. + */ +class TransformDialog : public ArdourDialog +{ +public: + TransformDialog(); + + ARDOUR::Transform::Program get(); + +private: + typedef ARDOUR::MidiModel::NoteDiffCommand::Property Property; + typedef ARDOUR::Transform::Value Value; + typedef ARDOUR::Transform::Value::Source Source; + typedef ARDOUR::Transform::Operation::Operator Operator; + typedef ARDOUR::Transform::Operation Operation; + + struct SourceCols : public Gtk::TreeModelColumnRecord { + SourceCols() { add(source); add(label); } + + Gtk::TreeModelColumn<Source> source; + Gtk::TreeModelColumn<std::string> label; + }; + + struct PropertyCols : public Gtk::TreeModelColumnRecord { + PropertyCols() { add(property); add(label); } + + Gtk::TreeModelColumn<Property> property; + Gtk::TreeModelColumn<std::string> label; + }; + + struct OperatorCols : public Gtk::TreeModelColumnRecord { + OperatorCols() { add(op); add(label); } + + Gtk::TreeModelColumn<Operator> op; + Gtk::TreeModelColumn<std::string> label; + }; + + struct Model { + Model(); + + SourceCols source_cols; + Glib::RefPtr<Gtk::ListStore> source_list; + PropertyCols property_cols; + Glib::RefPtr<Gtk::ListStore> property_list; + OperatorCols operator_cols; + Glib::RefPtr<Gtk::ListStore> operator_list; + }; + + struct ValueChooser : public Gtk::HBox { + ValueChooser(const Model& model); + + /** Append code to `ops` that pushes value to stack. */ + void get(std::list<Operation>& ops); + + void set_target_property(Property prop); + void source_changed(); + + const Model& model; ///< Models for combo boxes + Property target_property; ///< Property on source + Gtk::ComboBox source_combo; ///< Value source chooser + Gtk::ComboBox property_combo; ///< Property chooser + Gtk::SpinButton value_spinner; ///< Value or minimum for RANDOM + Gtk::Label to_label; ///< "to" label for RANDOM + Gtk::SpinButton max_spinner; ///< Maximum for RANDOM + }; + + struct OperationChooser : public Gtk::HBox { + OperationChooser(const Model& model); + + /** Append operations to `ops`. */ + void get(std::list<Operation>& ops); + + void remove_clicked(); + + const Model& model; + Gtk::ComboBox operator_combo; + ValueChooser value_chooser; + Gtk::Button remove_button; + }; + + void property_changed(); + void add_clicked(); + + Model _model; + Gtk::ComboBox _property_combo; + ValueChooser* _seed_chooser; + Gtk::VBox _operations_box; + Gtk::Button _add_button; +}; + +#endif /* __transform_dialog_h__ */ |