MIDI branch becomes trunk

git-svn-id: svn://localhost/ardour2/trunk@1815 d708f5d6-7413-0410-9779-e7cbd77b26cf
This commit is contained in:
Paul Davis
2007-05-10 02:34:20 +00:00
1159 changed files with 32211 additions and 66641 deletions

View File

@@ -408,14 +408,13 @@ deps = \
{
'glib-2.0' : '2.10.1',
'gthread-2.0' : '2.10.1',
'gtk+-2.0' : '2.10.0',
'gtk+-2.0' : '2.8.1',
'libxml-2.0' : '2.6.0',
'samplerate' : '0.1.0',
'raptor' : '1.4.2',
'lrdf' : '0.4.0',
'jack' : '0.101.1',
'libgnomecanvas-2.0' : '2.0',
'cairo' : '1.2.4'
'jack' : '0.105.0',
'libgnomecanvas-2.0' : '2.0'
}
def DependenciesRequiredMessage():
@@ -492,12 +491,6 @@ libraries['xml'].ParseConfig('pkg-config --cflags --libs libxml-2.0')
libraries['xslt'] = LibraryInfo()
libraries['xslt'].ParseConfig('pkg-config --cflags --libs libxslt')
libraries['cairo'] = LibraryInfo()
libraries['cairo'].ParseConfig ('pkg-config --cflags --libs cairo')
libraries['pangocairo'] = LibraryInfo()
libraries['pangocairo'].ParseConfig ('pkg-config --cflags --libs pangocairo')
libraries['glib2'] = LibraryInfo()
libraries['glib2'].ParseConfig ('pkg-config --cflags --libs glib-2.0')
libraries['glib2'].ParseConfig ('pkg-config --cflags --libs gobject-2.0')
@@ -507,9 +500,6 @@ libraries['glib2'].ParseConfig ('pkg-config --cflags --libs gthread-2.0')
libraries['gtk2'] = LibraryInfo()
libraries['gtk2'].ParseConfig ('pkg-config --cflags --libs gtk+-2.0')
libraries['gtk2-unix-print'] = LibraryInfo()
libraries['gtk2-unix-print'].ParseConfig ('pkg-config --cflags --libs gtk+-unix-print-2.0')
libraries['pango'] = LibraryInfo()
libraries['pango'].ParseConfig ('pkg-config --cflags --libs pango')
@@ -802,18 +792,25 @@ libraries['dmalloc'] = conf.Finish ()
#
conf = Configure(env)
if conf.CheckCHeader('alsa/asoundlib.h'):
if conf.CheckCHeader('jack/midiport.h'):
libraries['sysmidi'] = LibraryInfo (LIBS='jack')
env['SYSMIDI'] = 'JACK MIDI'
subst_dict['%MIDITAG%'] = "control"
subst_dict['%MIDITYPE%'] = "jack"
print "Using JACK MIDI"
elif conf.CheckCHeader('alsa/asoundlib.h'):
libraries['sysmidi'] = LibraryInfo (LIBS='asound')
env['SYSMIDI'] = 'ALSA Sequencer'
subst_dict['%MIDITAG%'] = "seq"
subst_dict['%MIDITYPE%'] = "alsa/sequencer"
print "Using ALSA MIDI"
elif conf.CheckCHeader('/System/Library/Frameworks/CoreMIDI.framework/Headers/CoreMIDI.h'):
# this line is needed because scons can't handle -framework in ParseConfig() yet.
libraries['sysmidi'] = LibraryInfo (LINKFLAGS= '-framework CoreMIDI -framework CoreFoundation -framework CoreAudio -framework CoreServices -framework AudioUnit -framework AudioToolbox -bind_at_load')
env['SYSMIDI'] = 'CoreMIDI'
subst_dict['%MIDITAG%'] = "ardour"
subst_dict['%MIDITYPE%'] = "coremidi"
print "Using CoreMIDI"
else:
print "It appears you don't have the required MIDI libraries installed. For Linux this means you are missing the development package for ALSA libraries."
sys.exit (1)
@@ -865,9 +862,12 @@ if env['SYSLIBS']:
LIBPATH='#libs/libsndfile',
CPPPATH=['#libs/libsndfile/src'])
# libraries['libglademm'] = LibraryInfo()
# libraries['libglademm'].ParseConfig ('pkg-config --cflags --libs libglademm-2.4')
# libraries['flowcanvas'] = LibraryInfo(LIBS='flowcanvas', LIBPATH='#/libs/flowcanvas', CPPPATH='#libs/flowcanvas')
libraries['soundtouch'] = LibraryInfo()
libraries['soundtouch'].ParseConfig ('pkg-config --cflags --libs soundtouch-1.0')
libraries['soundtouch'].ParseConfig ('pkg-config --cflags --libs libSoundTouch')
# Comment the previous line and uncomment this for Debian:
#libraries['soundtouch'].ParseConfig ('pkg-config --cflags --libs libSoundTouch')
@@ -909,9 +909,6 @@ else:
libraries['glibmm2'] = LibraryInfo(LIBS='glibmm2',
LIBPATH='#libs/glibmm2',
CPPPATH='#libs/glibmm2')
libraries['cairomm'] = LibraryInfo(LIBS='cairomm',
LIBPATH='#libs/cairomm',
CPPPATH='#libs/cairomm')
libraries['pangomm'] = LibraryInfo(LIBS='pangomm',
LIBPATH='#libs/gtkmm2/pango',
CPPPATH='#libs/gtkmm2/pango')
@@ -934,6 +931,9 @@ else:
libraries['sndfile-ardour'] = LibraryInfo(LIBS='libsndfile-ardour',
LIBPATH='#libs/libsndfile',
CPPPATH=['#libs/libsndfile', '#libs/libsndfile/src'])
# libraries['libglademm'] = LibraryInfo(LIBS='libglademm',
# LIBPATH='#libs/libglademm',
# CPPPATH='#libs/libglademm')
libraries['appleutility'] = LibraryInfo(LIBS='libappleutility',
LIBPATH='#libs/appleutility',
CPPPATH='#libs/appleutility')
@@ -962,7 +962,6 @@ else:
gtk_subdirs = [
'libs/glibmm2',
'libs/cairomm',
'libs/gtkmm2/pango',
'libs/gtkmm2/atk',
'libs/gtkmm2/gdk',
@@ -1029,6 +1028,14 @@ else:
config_prefix = '$DESTDIR' + final_config_prefix
# For colorgcc
if os.environ.has_key('PATH'):
env['PATH'] = os.environ['PATH']
if os.environ.has_key('TERM'):
env['TERM'] = os.environ['TERM']
if os.environ.has_key('HOME'):
env['HOME'] = os.environ['HOME']
#
# everybody needs this
#
@@ -1083,8 +1090,8 @@ if conf.CheckCHeader('/System/Library/Frameworks/CoreAudio.framework/Versions/A/
subst_dict['%JACK_INPUT%'] = "coreaudio:Built-in Audio:in"
subst_dict['%JACK_OUTPUT%'] = "coreaudio:Built-in Audio:out"
else:
subst_dict['%JACK_INPUT%'] = "alsa_pcm:playback_"
subst_dict['%JACK_OUTPUT%'] = "alsa_pcm:capture_"
subst_dict['%JACK_INPUT%'] = "system:playback_"
subst_dict['%JACK_OUTPUT%'] = "system:capture_"
# posix_memalign available
if not conf.CheckFunc('posix_memalign'):

View File

@@ -19,9 +19,6 @@ gtkardour.Append(DOMAIN=domain, MAJOR=1,MINOR=0,MICRO=2)
gtkardour.Append(CCFLAGS="-DPACKAGE=\\\"" + domain + "\\\"")
gtkardour.Append(CXXFLAGS="-DPACKAGE=\\\"" + domain + "\\\"")
gtkardour.Append(CXXFLAGS="-DLIBSIGC_DISABLE_DEPRECATED")
gtkardour.Append(CXXFLAGS="-DGLIBMM_DISABLE_DEPRECATED")
gtkardour.Append(CXXFLAGS="-DGDKMM_DISABLE_DEPRECATED")
gtkardour.Append(CXXFLAGS="-DGTKMM_DISABLE_DEPRECATED")
gtkardour.Append(CPPPATH="#/") # for top level svn_revision.h
#gtkardour.Append(CXXFLAGS="-DFLOWCANVAS_AA")
gtkardour.Append(PACKAGE=domain)
@@ -42,7 +39,6 @@ gtkardour.Merge ([
libraries['flac'],
libraries['lrdf'],
libraries['glibmm2'],
libraries['cairomm'],
libraries['pangomm'],
libraries['atkmm'],
libraries['gdkmm2'],
@@ -97,12 +93,14 @@ ardour_ui_ed.cc
ardour_ui_mixer.cc
ardour_ui_options.cc
audio_clock.cc
route_time_axis.cc
audio_time_axis.cc
audio_region_editor.cc
automation_gain_line.cc
automation_line.cc
automation_pan_line.cc
automation_time_axis.cc
midi_time_axis.cc
midi_streamview.cc
axis_view.cc
canvas-imageframe.c
canvas-simpleline.c
@@ -183,11 +181,12 @@ public_editor.cc
redirect_automation_line.cc
redirect_automation_time_axis.cc
redirect_box.cc
audio_region_editor.cc
region_gain_line.cc
region_selection.cc
region_view.cc
audio_region_view.cc
midi_region_view.cc
tape_region_view.cc
route_params_ui.cc
route_redirect_selection.cc
route_ui.cc
@@ -196,10 +195,10 @@ sfdb_ui.cc
send_ui.cc
streamview.cc
audio_streamview.cc
tape_region_view.cc
tempo_dialog.cc
time_axis_view.cc
time_axis_view_item.cc
route_time_axis.cc
time_selection.cc
utils.cc
version.cc

View File

@@ -44,6 +44,7 @@ static const char* channel_setup_names[] = {
N_("6 Channels"),
N_("8 Channels"),
N_("Manual Setup"),
"MIDI",
0
};
@@ -157,6 +158,18 @@ AddRouteDialog::track ()
return track_button.get_active ();
}
ARDOUR::DataType
AddRouteDialog::type ()
{
// FIXME: ew
const string str = channel_combo.get_active_text();
if (str == _("MIDI"))
return ARDOUR::DataType::MIDI;
else
return ARDOUR::DataType::AUDIO;
}
string
AddRouteDialog::name_template ()
{
@@ -192,7 +205,7 @@ AddRouteDialog::channels ()
string str = channel_combo.get_active_text();
int chns;
if (str == _("Mono")) {
if (str == _("Mono") || str == _("MIDI")) {
return 1;
} else if (str == _("Stereo")) {
return 2;

View File

@@ -32,6 +32,7 @@
#include <gtkmm/comboboxtext.h>
#include <ardour/types.h>
#include <ardour/data_type.h>
class AddRouteDialog : public Gtk::Dialog
{
@@ -40,6 +41,7 @@ class AddRouteDialog : public Gtk::Dialog
~AddRouteDialog ();
bool track ();
ARDOUR::DataType type();
std::string name_template ();
int channels ();
int count ();

View File

@@ -6,7 +6,7 @@ export ARDOUR_PATH=gtk2_ardour/icons:gtk2_ardour/pixmaps:gtk2_ardour
export GTK_PATH=libs/clearlooks
export LD_LIBRARY_PATH=libs/surfaces/control_protocol:libs/ardour:libs/midi++2:libs/pbd:libs/soundtouch:libs/gtkmm2ext:libs/sigc++2:libs/glibmm2:libs/gtkmm2/atk:libs/gtkmm2/pango:libs/gtkmm2/gdk:libs/gtkmm2/gtk:libs/libgnomecanvasmm:libs/cairomm:libs/libsndfile:libs/appleutility:$LD_LIBRARY_PATH
export LD_LIBRARY_PATH=libs/surfaces/control_protocol:libs/ardour:libs/midi++2:libs/pbd:libs/soundtouch:libs/gtkmm2ext:libs/sigc++2:libs/glibmm2:libs/gtkmm2/atk:libs/gtkmm2/pango:libs/gtkmm2/gdk:libs/gtkmm2/gtk:libs/libgnomecanvasmm:libs/libsndfile:libs/appleutility:$LD_LIBRARY_PATH
# DYLD_LIBRARY_PATH is for darwin.
export DYLD_LIBRARY_PATH=$LD_LIBRARY_PATH

View File

@@ -3,9 +3,12 @@ cWaveFormClip 1.0 0.0 0.0 0.90
cMutedWaveForm 0.35 0.35 0.35 1.0
cSelectedFrameBase 0.71 0.57 0.66 1.0
cFrameBase 0.75 0.75 0.76 1.0
cAudioTrackBase 0.78 0.83 0.85 0.41
cAudioTrackOutline 0.00 0.00 0.00 1.00
cAudioTrackBase 0.80 0.80 1.0 0.5
cAudioBusBase 0.86 0.82 0.92 0.41
cMidiTrackOutline 0.00 0.00 0.00 1.00
cMidiTrackBase 1.0 0.85 0.85 0.5
cMidiBusBase 0.75 0.65 0.65 0.41
cMeterBar 0.40 0.40 0.45 1.0
cTempoBar 0.45 0.45 0.50 1.0
cMarkerBar 0.50 0.50 0.55 1.0

View File

@@ -333,10 +333,10 @@
<menuitem action='CrossfadesShort'/>
</menu>
<menu action='Layering'>
<menuitem action='LayerLaterHigher'/>
<menuitem action='LayerMoveAddHigher'/>
<menuitem action='LayerAddHigher'/>
</menu>
<menuitem action='LayerLaterHigher'/>
<menuitem action='LayerMoveAddHigher'/>
<menuitem action='LayerAddHigher'/>
</menu>
<separator/>
<menuitem action='SendMTC'/>
<menuitem action='SendMMC'/>

View File

@@ -88,6 +88,7 @@ style "default_base" = "medium_text"
GtkWidget::cursor_color = {1.0, 1.0, 1.0 }
GtkButton::default_border = { 0, 0, 0, 0 }
GtkButton::default_outside_border = { 0, 0, 0, 0 }
GtkButton::button_relief = GTK_RELIEF_NONE
GtkTreeView::vertical-padding = 0
GtkTreeView::horizontal-padding = 0
GtkTreeView::even-row-color = { 0, 0, 0 }
@@ -119,9 +120,9 @@ style "default_base" = "medium_text"
engine "clearlooks"
{
menubarstyle = 2 # 0 = flat, 1 = sunken, 2 = flat gradient
menuitemstyle = 1 # 0 = flat, 1 = 3d-ish (gradient), 2 = 3d-ish (button)
listviewitemstyle = 1 # 0 = flat, 1 = 3d-ish (gradient)
menubarstyle = 0 # 0 = flat, 1 = sunken, 2 = flat gradient
menuitemstyle = 0 # 0 = flat, 1 = 3d-ish (gradient), 2 = 3d-ish (button)
listviewitemstyle = 0 # 0 = flat, 1 = 3d-ish (gradient)
progressbarstyle = 1 # 0 = candy bar, 1 = fancy candy bar, 2 = flat
}
}
@@ -140,14 +141,14 @@ style "transport_base" = "medium_bold_text"
bg[INSENSITIVE] = { 0, 0, 0 }
bg[SELECTED] = { 0, 0, 0 }
}
/*
style "black_mackie_menu_bar"
{
font_name = "sans bold 9"
fg[NORMAL] = { 1.0, 1.0, 1.0 }
bg[NORMAL] = { 0, 0, 0 }
}
*/
style "default_buttons_menus"
{
font_name = "sans 8"
@@ -497,7 +498,7 @@ style "xrun_warn"
bg[NORMAL] = { 1.0, 0.48, 0.46 }
bg[ACTIVE] = { 0.09, 1.0, 0.46 }
}
/*
style "menu_bar_base" = "default_base"
{
bg[NORMAL] = { 0.2, 0.2, 0.3 }
@@ -506,7 +507,7 @@ style "menu_bar_base" = "default_base"
bg[INSENSITIVE] = { 0, 0, 0 }
bg[SELECTED] = { 0, 0, 0 }
}
*/
style "fatal_message" = "medium_text"
{
fg[ACTIVE] = { 1.0, 0, 1.0 }
@@ -692,6 +693,14 @@ style "editor_time_ruler" = "small_text"
bg[NORMAL] = { 0.09, 0.09, 0.09 }
}
style "audio_bus_base"
{
font_name = "sans 6"
fg[NORMAL] = { 0.77, 0.77, 0.72 }
fg[NORMAL] = { 0.7, 0.8, 0.2 }
bg[NORMAL] = { 0.20, 0.20, 0.26 }
}
style "audio_track_base" = "default_base"
{
font_name = "sans 6"
@@ -703,7 +712,7 @@ style "audio_track_base" = "default_base"
bg[SELECTED] = { 0.20, 0.20, 0.20 }
}
style "audio_bus_base"
style "midi_bus_base"
{
font_name = "sans 6"
fg[NORMAL] = { 0.77, 0.77, 0.72 }
@@ -712,6 +721,17 @@ style "audio_bus_base"
bg[NORMAL] = "#444466"
}
style "midi_track_base" = "default_base"
{
font_name = "sans 6"
fg[NORMAL] = { 0.77, 0.77, 0.72 }
bg[NORMAL] = { 0.48, 0.30, 0.32 }
bg[ACTIVE] = { 0.20, 0.20, 0.20 }
bg[PRELIGHT] = { 0.20, 0.20, 0.20 }
bg[INSENSITIVE] = { 0.20, 0.20, 0.20 }
bg[SELECTED] = { 0.20, 0.20, 0.20 }
}
style "track_name_display"
{
font_name = "sans medium 8"
@@ -1253,7 +1273,7 @@ widget "*TransportRecButton-alternate*" style:highest "transport_rec_button_alte
widget "*TransportRecButton*" style:highest "transport_rec_button"
widget "*RecordingXrunWarningWindow" style:highest "xrun_warn"
widget "*RecordingXrunWarningWindow*" style:highest "xrun_warn"
widget "*MainMenuBar" style:highest "menu_bar_base"
/*widget "*MainMenuBar" style:highest "menu_bar_base"*/
widget "*ErrorMessage" style:highest "error_message"
widget "*FatalMessage" style:highest "fatal_message"
widget "*InfoMessage" style:highest "info_message"
@@ -1340,8 +1360,9 @@ widget "*AudioTrackControlsBaseSelected" style:highest "edit_controls_base_selec
widget "*BusControlsBaseSelected" style:highest "edit_controls_base_selected"
widget "*AutomationTrackControlsBase" style:highest "automation_track_controls_base"
widget "*AutomationTrackControlsBaseSelected" style:highest "edit_controls_base_selected"
widget "*EditorMenuBar*" style:highest "black_mackie_menu_bar"
/*widget "*EditorMenuBar*" style:highest "black_mackie_menu_bar"
widget "*MainMenuBar*" style:highest "black_mackie_menu_bar"
*/
widget "*ZoomClickBox" style:highest "medium_bold_entry"
widget "*PluginParameterLabel" style:highest "medium_text"
widget "*PluginNameInfo" style:highest "plugin_name_text"

View File

@@ -17,6 +17,9 @@
*/
#define __STDC_FORMAT_MACROS 1
#include <stdint.h>
#include <algorithm>
#include <cmath>
#include <fcntl.h>
@@ -61,6 +64,7 @@
#include <ardour/recent_sessions.h>
#include <ardour/port.h>
#include <ardour/audio_track.h>
#include <ardour/midi_track.h>
#include "actions.h"
#include "ardour_ui.h"
@@ -715,7 +719,7 @@ ARDOUR_UI::count_recenabled_streams (Route& route)
{
Track* track = dynamic_cast<Track*>(&route);
if (track && track->diskstream()->record_enabled()) {
rec_enabled_streams += track->n_inputs();
rec_enabled_streams += track->n_inputs().get_total();
}
}
@@ -1014,11 +1018,45 @@ ARDOUR_UI::open_session ()
void
ARDOUR_UI::session_add_midi_track ()
ARDOUR_UI::session_add_midi_route (bool disk, uint32_t how_many)
{
cerr << _("Patience is a virtue.\n");
list<boost::shared_ptr<MidiTrack> > tracks;
if (session == 0) {
warning << _("You cannot add a track without a session already loaded.") << endmsg;
return;
}
try {
if (disk) {
tracks = session->new_midi_track (ARDOUR::Normal, how_many);
if (tracks.size() != how_many) {
if (how_many == 1) {
error << _("could not create a new midi track") << endmsg;
} else {
error << string_compose (_("could not create %1 new midi tracks"), how_many) << endmsg;
}
}
} /*else {
if ((route = session->new_midi_route ()) == 0) {
error << _("could not create new midi bus") << endmsg;
}
}*/
}
catch (...) {
MessageDialog msg (*editor,
_("There are insufficient JACK ports available\n\
to create a new track or bus.\n\
You should save Ardour, exit and\n\
restart JACK with more ports."));
msg.run ();
}
}
void
ARDOUR_UI::session_add_audio_route (bool track, int32_t input_channels, int32_t output_channels, ARDOUR::TrackMode mode, uint32_t how_many)
{
@@ -1553,7 +1591,7 @@ ARDOUR_UI::name_io_setup (AudioEngine& engine,
bool in)
{
if (in) {
if (io.n_inputs() == 0) {
if (io.n_inputs().get_total() == 0) {
buf = _("none");
return;
}
@@ -1572,7 +1610,7 @@ ARDOUR_UI::name_io_setup (AudioEngine& engine,
} else {
if (io.n_outputs() == 0) {
if (io.n_outputs().get_total() == 0) {
buf = _("none");
return;
}
@@ -2336,15 +2374,15 @@ ARDOUR_UI::add_route (Gtk::Window* float_window)
}
ResponseType r = (ResponseType) add_route_dialog->run ();
add_route_dialog->hide();
switch (r) {
case RESPONSE_ACCEPT:
break;
default:
return;
break;
case RESPONSE_ACCEPT:
break;
default:
return;
break;
}
if ((count = add_route_dialog->count()) <= 0) {
@@ -2359,17 +2397,28 @@ ARDOUR_UI::add_route (Gtk::Window* float_window)
AutoConnectOption oac = Config->get_output_auto_connect();
if (oac & AutoConnectMaster) {
output_chan = (session->master_out() ? session->master_out()->n_inputs() : input_chan);
output_chan = (session->master_out() ? session->master_out()->n_inputs().get(DataType::AUDIO) : input_chan);
} else {
output_chan = input_chan;
}
/* XXX do something with name template */
if (track) {
session_add_audio_track (input_chan, output_chan, add_route_dialog->mode(), count);
} else {
session_add_audio_bus (input_chan, output_chan, count);
if (add_route_dialog->type() == ARDOUR::DataType::MIDI) {
if (track) {
session_add_midi_track(count);
} else {
MessageDialog msg (*editor,
_("Sorry, MIDI Busses are not supported at this time."));
msg.run ();
//session_add_midi_bus();
}
} else {
if (track) {
session_add_audio_track (input_chan, output_chan, add_route_dialog->mode(), count);
} else {
session_add_audio_bus (input_chan, output_chan, count);
}
}
}

View File

@@ -196,7 +196,13 @@ class ARDOUR_UI : public Gtkmm2ext::UI
session_add_audio_route (false, input_channels, output_channels, ARDOUR::Normal, how_many);
}
void session_add_midi_track ();
void session_add_midi_track (uint32_t how_many) {
session_add_midi_route (true, how_many);
}
/*void session_add_midi_bus () {
session_add_midi_route (false);
}*/
void set_engine (ARDOUR::AudioEngine&);
gint start_engine ();
@@ -448,7 +454,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI
Gtk::ToggleButton solo_alert_button;
Gtk::VBox alert_box;
void solo_blink (bool);
void audition_blink (bool);
@@ -543,6 +549,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI
void save_template ();
void session_add_audio_route (bool disk, int32_t input_channels, int32_t output_channels, ARDOUR::TrackMode mode, uint32_t how_many);
void session_add_midi_route (bool disk, uint32_t how_many);
void set_transport_sensitivity (bool);

View File

@@ -202,13 +202,17 @@ ARDOUR_UI::install_actions ()
ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_toggle_action (common_actions, X_("ToggleBigClock"), _("Big Clock"), mem_fun(*this, &ARDOUR_UI::toggle_big_clock_window));
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::register_action (common_actions, X_("About"), _("About"), mem_fun(*this, &ARDOUR_UI::show_splash));
act = ActionManager::register_action (common_actions, X_("About"), _("About"), mem_fun(*this, &ARDOUR_UI::show_splash));
act = ActionManager::register_toggle_action (common_actions, X_("ToggleColorManager"), _("Colors"), mem_fun(*this, &ARDOUR_UI::toggle_color_manager));
ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_action (common_actions, X_("AddAudioTrack"), _("Add Audio Track"), bind (mem_fun(*this, &ARDOUR_UI::session_add_audio_track), 1, 1, ARDOUR::Normal, 1));
ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_action (common_actions, X_("AddAudioBus"), _("Add Audio Bus"), bind (mem_fun(*this, &ARDOUR_UI::session_add_audio_bus), 1, 1, 1));
ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_action (common_actions, X_("AddMIDITrack"), _("Add MIDI Track"), bind (mem_fun(*this, &ARDOUR_UI::session_add_midi_track), 1));
ActionManager::session_sensitive_actions.push_back (act);
//act = ActionManager::register_action (common_actions, X_("AddMidiBus"), _("Add Midi Bus"), mem_fun(*this, &ARDOUR_UI::session_add_midi_bus));
//ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_action (common_actions, X_("Save"), _("Save"), bind (mem_fun(*this, &ARDOUR_UI::save_state), string("")));
ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_action (common_actions, X_("RemoveLastCapture"), _("Remove Last Capture"), mem_fun(*this, &ARDOUR_UI::remove_last_capture));

View File

@@ -43,6 +43,77 @@ AUPluginUI::AUPluginUI (boost::shared_ptr<PluginInsert> insert)
throw failed_constructor ();
}
OSStatus err = noErr;
CAComponentDescription desc;
Component carbonViewComponent = NULL;
AudioUnitCarbonView carbonView = NULL;
GetComponentInfo(au->get_comp()->Comp(), &desc, 0, 0, 0);
carbonViewComponent = get_carbon_view_component(desc.componentSubType);
err = OpenAComponent(carbonViewComponent, &carbonView);
Rect rec;
rec.top = 0;
rec.left = 0;
rec.bottom = 400;
rec.right = 500;
ProcessSerialNumber ourPSN;
/* Here we will set the MacOSX native section of the process to the foreground for putting up this
* dialog box. First step is to get our process serial number. We do this by calling
* GetCurrentProcess.
* First Argument: On success this PSN will be our PSN on return.
* Return Value: A Macintosh error indicating success or failure.
*/
err = GetCurrentProcess(&ourPSN);
//If no error then set this process to be frontmost.
if (err == noErr) {
/* Calling SetFrontProcess to make us frontmost.
* First Argument: The Process Serial Number of the process we want to make frontmost. Here
* of course we pass our process serial number
* Return Value: An error value indicating success or failure. We just ignore the return
* value here.
*/
(void)SetFrontProcess(&ourPSN);
} else {
error << "couldn't get current process" << endmsg;
}
err = CreateNewWindow (kDocumentWindowClass, kWindowStandardFloatingAttributes, &rec, &wr);
ComponentResult auResult;
ControlRef rootControl = NULL;
GetRootControl(wr, &rootControl);
int width = 500;
int height = 400;
Float32Point location = {30, 30};
Float32Point size = {width, height};
ControlRef audioUnitControl = NULL;
auResult = AudioUnitCarbonViewCreate(carbonView,
au->get_au()->AU(),
wr,
rootControl,
&location,
&size,
&audioUnitControl);
ShowWindow (wr);
BringToFront (wr);
// AudioUnitCarbonViewSetEventListener(carbonView, EventListener, this);
#if 0
set_name ("PluginEditor");
add_events (Gdk::KEY_PRESS_MASK|Gdk::KEY_RELEASE_MASK|Gdk::BUTTON_PRESS_MASK|Gdk::BUTTON_RELEASE_MASK);
signal_delete_event().connect (bind (sigc::ptr_fun (just_hide_it), reinterpret_cast<Window*> (this)));
#endif
insert->GoingAway.connect (mem_fun(*this, &AUPluginUI::plugin_going_away));
info << "AUPluginUI created" << endmsg;
}
@@ -51,3 +122,39 @@ AUPluginUI::~AUPluginUI ()
// nothing to do here - plugin destructor destroys the GUI
}
void
AUPluginUI::plugin_going_away (ARDOUR::Redirect* ignored)
{
ENSURE_GUI_THREAD(bind (mem_fun(*this, &AUPluginUI::plugin_going_away), ignored));
delete_when_idle (this);
}
Component
AUPluginUI::get_carbon_view_component(OSType subtype)
{
ComponentDescription desc;
Component component;
desc.componentType = kAudioUnitCarbonViewComponentType; // 'auvw'
desc.componentSubType = subtype;
desc.componentManufacturer = 0;
desc.componentFlags = 0;
desc.componentFlagsMask = 0;
// First see if we can find a carbon view designed specifically for this
// plug-in:
component = FindNextComponent(NULL, &desc);
if (component)
return component;
// If not, grab the generic carbon view, which will create a GUI for
// any Audio Unit.
desc.componentSubType = kAUCarbonViewSubType_Generic;
component = FindNextComponent(NULL, &desc);
return component;
}

View File

@@ -38,7 +38,11 @@ class AUPluginUI
~AUPluginUI ();
private:
WindowRef wr;
boost::shared_ptr<ARDOUR::AUPlugin> au;
void plugin_going_away (ARDOUR::Redirect*);
Component get_carbon_view_component(OSType subtype);
};
#endif // __au_plugin_ui_h__

View File

@@ -14,7 +14,6 @@
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.
*/
#include <cmath>
@@ -323,6 +322,34 @@ AudioRegionView::region_scale_amplitude_changed ()
}
}
void
AudioRegionView::region_renamed ()
{
// FIXME: ugly duplication with RegionView...
string str;
if (_region->locked()) {
str += '>';
str += _region->name();
str += '<';
} else {
str = _region->name();
}
// ... because of this
if (audio_region()->speed_mismatch (trackview.session().frame_rate())) {
str = string ("*") + str;
}
if (_region->muted()) {
str = string ("!") + str;
}
set_item_name (str, this);
set_name_text (str);
}
void
AudioRegionView::region_resized (Change what_changed)
{
@@ -385,16 +412,12 @@ AudioRegionView::region_muted ()
}
}
void
AudioRegionView::set_height (gdouble height)
{
uint32_t wcnt = waves.size();
// FIXME: ick
TimeAxisViewItem::set_height (height - 2);
RegionView::set_height(height);
_height = height;
uint32_t wcnt = waves.size();
for (uint32_t n=0; n < wcnt; ++n) {
gdouble ht;
@@ -761,7 +784,7 @@ AudioRegionView::create_waves ()
return;
}
uint32_t nchans = atv.get_diskstream()->n_channels();
uint32_t nchans = atv.get_diskstream()->n_channels().get(DataType::AUDIO);
/* in tmp_waves, set up null pointers for each channel so the vector is allocated */
for (uint32_t n = 0; n < nchans; ++n) {
@@ -777,7 +800,7 @@ AudioRegionView::create_waves ()
wave_caches.push_back (WaveView::create_cache ());
if (wait_for_data) {
if (audio_region()->source(n)->peaks_ready (bind (mem_fun(*this, &AudioRegionView::peaks_ready_handler), n), data_ready_connection)) {
if (audio_region()->audio_source(n)->peaks_ready (bind (mem_fun(*this, &AudioRegionView::peaks_ready_handler), n), data_ready_connection)) {
create_one_wave (n, true);
} else {
}
@@ -791,7 +814,7 @@ void
AudioRegionView::create_one_wave (uint32_t which, bool direct)
{
RouteTimeAxisView& atv (*(dynamic_cast<RouteTimeAxisView*>(&trackview))); // ick
uint32_t nchans = atv.get_diskstream()->n_channels();
uint32_t nchans = atv.get_diskstream()->n_channels().get(DataType::AUDIO);
uint32_t n;
uint32_t nwaves = std::min (nchans, audio_region()->n_channels());
gdouble ht;
@@ -1046,7 +1069,7 @@ AudioRegionView::add_ghost (AutomationTimeAxisView& atv)
GhostRegion* ghost = new GhostRegion (atv, unit_position);
uint32_t nchans;
nchans = rtv->get_diskstream()->n_channels();
nchans = rtv->get_diskstream()->n_channels().get(DataType::AUDIO);
for (uint32_t n = 0; n < nchans; ++n) {

View File

@@ -119,6 +119,22 @@ class AudioRegionView : public RegionView
WaveformRectified = 0x8,
WaveformLogScaled = 0x10,
};
vector<ArdourCanvas::WaveView *> waves;
vector<ArdourCanvas::WaveView *> tmp_waves; ///< see ::create_waves()
ArdourCanvas::Polygon* sync_mark; ///< polgyon for sync position
ArdourCanvas::SimpleLine* zero_line;
ArdourCanvas::Polygon* fade_in_shape;
ArdourCanvas::Polygon* fade_out_shape;
ArdourCanvas::SimpleRect* fade_in_handle;
ArdourCanvas::SimpleRect* fade_out_handle;
AudioRegionGainLine * gain_line;
double _amplitude_above_axis;
uint32_t _flags;
uint32_t fade_color;
void reset_fade_shapes ();
void reset_fade_in_shape ();
@@ -132,6 +148,7 @@ class AudioRegionView : public RegionView
void region_moved (void *);
void region_muted ();
void region_scale_amplitude_changed ();
void region_renamed ();
void create_waves ();
void create_one_wave (uint32_t, bool);
@@ -148,20 +165,6 @@ class AudioRegionView : public RegionView
void color_handler (ColorID, uint32_t);
vector<GnomeCanvasWaveViewCache*> wave_caches;
vector<ArdourCanvas::WaveView *> waves;
vector<ArdourCanvas::WaveView *> tmp_waves; ///< see ::create_waves()
ArdourCanvas::Polygon* sync_mark; ///< polgyon for sync position
ArdourCanvas::SimpleLine* zero_line;
ArdourCanvas::Polygon* fade_in_shape;
ArdourCanvas::Polygon* fade_out_shape;
ArdourCanvas::SimpleRect* fade_in_handle;
ArdourCanvas::SimpleRect* fade_out_handle;
AudioRegionGainLine* gain_line;
double _amplitude_above_axis;
uint32_t _flags;
uint32_t fade_color;
};
#endif /* __gtk_ardour_audio_region_view_h__ */

View File

@@ -61,7 +61,7 @@ AudioStreamView::AudioStreamView (AudioTimeAxisView& tv)
_waveform_scale = LinearWaveform;
_waveform_shape = Traditional;
if (tv.is_audio_track())
if (tv.is_track())
stream_base_color = color_map[cAudioTrackBase];
else
stream_base_color = color_map[cAudioBusBase];
@@ -72,7 +72,6 @@ AudioStreamView::AudioStreamView (AudioTimeAxisView& tv)
_amplitude_above_axis = 1.0;
use_rec_regions = tv.editor.show_waveforms_recording ();
last_rec_peak_frame = 0;
}
@@ -248,7 +247,6 @@ AudioStreamView::remove_region_view (boost::weak_ptr<Region> weak_r)
}
}
StreamView::remove_region_view(r);
}
@@ -475,20 +473,22 @@ AudioStreamView::setup_rec_box ()
SourceList sources;
for (list<sigc::connection>::iterator prc = peak_ready_connections.begin(); prc != peak_ready_connections.end(); ++prc) {
for (list<sigc::connection>::iterator prc = rec_data_ready_connections.begin(); prc != rec_data_ready_connections.end(); ++prc) {
(*prc).disconnect();
}
peak_ready_connections.clear();
rec_data_ready_connections.clear();
// FIXME
boost::shared_ptr<AudioDiskstream> ads = boost::dynamic_pointer_cast<AudioDiskstream>(_trackview.get_diskstream());
assert(ads);
for (uint32_t n=0; n < ads->n_channels(); ++n) {
for (uint32_t n=0; n < ads->n_channels().get(DataType::AUDIO); ++n) {
boost::shared_ptr<AudioFileSource> src = boost::static_pointer_cast<AudioFileSource> (ads->write_source (n));
if (src) {
sources.push_back (src);
peak_ready_connections.push_back (src->PeakRangeReady.connect (bind (mem_fun (*this, &AudioStreamView::rec_peak_range_ready), boost::weak_ptr<Source>(src))));
rec_data_ready_connections.push_back (src->PeakRangeReady.connect (bind
(mem_fun (*this, &AudioStreamView::rec_peak_range_ready), boost::weak_ptr<Source>(src))));
}
}
@@ -501,6 +501,7 @@ AudioStreamView::setup_rec_box ()
boost::shared_ptr<AudioRegion> region (boost::dynamic_pointer_cast<AudioRegion>
(RegionFactory::create (sources, start, 1 , "", 0, (Region::Flag)(Region::DefaultFlags | Region::DoNotSaveState), false)));
assert(region);
region->set_position (_trackview.session().transport_frame(), this);
rec_regions.push_back (region);
@@ -572,14 +573,14 @@ AudioStreamView::setup_rec_box ()
/* disconnect rapid update */
screen_update_connection.disconnect();
for (list<sigc::connection>::iterator prc = peak_ready_connections.begin(); prc != peak_ready_connections.end(); ++prc) {
for (list<sigc::connection>::iterator prc = rec_data_ready_connections.begin(); prc != rec_data_ready_connections.end(); ++prc) {
(*prc).disconnect();
}
peak_ready_connections.clear();
rec_data_ready_connections.clear();
rec_updating = false;
rec_active = false;
last_rec_peak_frame = 0;
last_rec_data_frame = 0;
/* remove temp regions */
@@ -631,15 +632,15 @@ AudioStreamView::rec_peak_range_ready (nframes_t start, nframes_t cnt, boost::we
// this is called from the peak building thread
if (rec_peak_ready_map.size() == 0 || start+cnt > last_rec_peak_frame) {
last_rec_peak_frame = start + cnt;
if (rec_data_ready_map.size() == 0 || start+cnt > last_rec_data_frame) {
last_rec_data_frame = start + cnt;
}
rec_peak_ready_map[src] = true;
rec_data_ready_map[src] = true;
if (rec_peak_ready_map.size() == _trackview.get_diskstream()->n_channels()) {
if (rec_data_ready_map.size() == _trackview.get_diskstream()->n_channels().get(DataType::AUDIO)) {
this->update_rec_regions ();
rec_peak_ready_map.clear();
rec_data_ready_map.clear();
}
}
@@ -672,9 +673,9 @@ AudioStreamView::update_rec_regions ()
if (region == rec_regions.back() && rec_active) {
if (last_rec_peak_frame > region->start()) {
if (last_rec_data_frame > region->start()) {
nframes_t nlen = last_rec_peak_frame - region->start();
nframes_t nlen = last_rec_data_frame - region->start();
if (nlen != region->length()) {

View File

@@ -99,17 +99,12 @@ class AudioStreamView : public StreamView
void color_handler (ColorID id, uint32_t val);
double _amplitude_above_axis;
typedef list<CrossfadeView*> CrossfadeViewList;
CrossfadeViewList crossfade_views;
bool crossfades_visible;
list<sigc::connection> peak_ready_connections;
nframes_t last_rec_peak_frame;
map<boost::shared_ptr<ARDOUR::Source>, bool> rec_peak_ready_map;
WaveformShape _waveform_shape;
WaveformScale _waveform_scale;
};

View File

@@ -96,11 +96,19 @@ AudioTimeAxisView::AudioTimeAxisView (PublicEditor& ed, Session& sess, boost::sh
ignore_toggle = false;
mute_button->set_active (false);
solo_button->set_active (false);
if (is_audio_track())
controls_ebox.set_name ("AudioTimeAxisViewControlsBaseUnselected");
else // bus
controls_ebox.set_name ("AudioBusControlsBaseUnselected");
/* map current state of the route */
redirects_changed (0);
reset_redirect_automation_curves ();
ensure_xml_node ();
set_state (*xml_node);
@@ -426,7 +434,7 @@ AudioTimeAxisView::update_pans ()
/* we don't draw lines for "greater than stereo" panning.
*/
if (_route->n_outputs() > 2) {
if (_route->n_outputs().get(DataType::AUDIO) > 2) {
return;
}

View File

@@ -98,6 +98,8 @@ ColorManager::load (string path)
return -1;
}
cerr << "Loading color definition file " << path << endl;
while (in) {
string name;
double r, g, b, a;

View File

@@ -27,6 +27,9 @@ COLORID(cFrameBase)
COLORID(cAudioTrackBase)
COLORID(cAudioTrackOutline)
COLORID(cAudioBusBase)
COLORID(cMidiTrackBase)
COLORID(cMidiTrackOutline)
COLORID(cMidiBusBase)
COLORID(cTimeStretchFill)
COLORID(cTimeStretchOutline)
COLORID(cAutomationLine)

View File

@@ -1043,8 +1043,7 @@ CrossfadeEditor::make_waves (boost::shared_ptr<AudioRegion> region, WhichFade wh
gdouble yoff = n * ht;
if (region->source(n)->peaks_ready (bind (mem_fun(*this, &CrossfadeEditor::peaks_ready), region, which), peaks_ready_connection)) {
if (region->audio_source(n)->peaks_ready (bind (mem_fun(*this, &CrossfadeEditor::peaks_ready), region, which), peaks_ready_connection)) {
WaveView* waveview = new WaveView (*(canvas->root()));
waveview->property_data_src() = region.get();

View File

@@ -88,7 +88,7 @@ CrossfadeView::CrossfadeView (ArdourCanvas::Group *parent,
CrossfadeView::~CrossfadeView ()
{
GoingAway (this) ; /* EMIT_SIGNAL */
GoingAway (this) ; /* EMIT_SIGNAL */
}
void

View File

@@ -94,6 +94,7 @@ using namespace Glib;
using namespace Gtkmm2ext;
using namespace Editing;
using PBD::internationalize;
using PBD::atoi;
const double Editor::timebar_height = 15.0;
@@ -231,8 +232,8 @@ Editor::Editor ()
selection->PointsChanged.connect (mem_fun(*this, &Editor::point_selection_changed));
clicked_regionview = 0;
clicked_trackview = 0;
clicked_audio_trackview = 0;
clicked_axisview = 0;
clicked_routeview = 0;
clicked_crossfadeview = 0;
clicked_control_point = 0;
latest_regionview = 0;
@@ -443,7 +444,7 @@ Editor::Editor ()
edit_packer.set_border_width (0);
edit_packer.set_name ("EditorWindow");
edit_packer.attach (edit_vscrollbar, 0, 1, 1, 3, FILL, FILL|EXPAND, 0, 0);
edit_packer.attach (edit_vscrollbar, 3, 4, 1, 2, FILL, FILL|EXPAND, 0, 0);
edit_packer.attach (time_button_frame, 0, 2, 0, 1, FILL, FILL, 0, 0);
edit_packer.attach (time_canvas_event_box, 2, 3, 0, 1, FILL|EXPAND, FILL, 0, 0);
@@ -1062,8 +1063,8 @@ Editor::connect_to_session (Session *t)
session_connections.push_back (session->TransportStateChange.connect (mem_fun(*this, &Editor::map_transport_state)));
session_connections.push_back (session->PositionChanged.connect (mem_fun(*this, &Editor::map_position_change)));
session_connections.push_back (session->RouteAdded.connect (mem_fun(*this, &Editor::handle_new_route)));
session_connections.push_back (session->AudioRegionAdded.connect (mem_fun(*this, &Editor::handle_new_audio_region)));
session_connections.push_back (session->AudioRegionRemoved.connect (mem_fun(*this, &Editor::handle_audio_region_removed)));
session_connections.push_back (session->RegionAdded.connect (mem_fun(*this, &Editor::handle_new_region)));
session_connections.push_back (session->RegionRemoved.connect (mem_fun(*this, &Editor::handle_region_removed)));
session_connections.push_back (session->DurationChanged.connect (mem_fun(*this, &Editor::handle_new_duration)));
session_connections.push_back (session->edit_group_added.connect (mem_fun(*this, &Editor::add_edit_group)));
session_connections.push_back (session->edit_group_removed.connect (mem_fun(*this, &Editor::edit_groups_changed)));
@@ -1156,10 +1157,10 @@ Editor::connect_to_session (Session *t)
for (i = rows.begin(); i != rows.end(); ++i) {
TimeAxisView *tv = (*i)[route_display_columns.tv];
AudioTimeAxisView *atv;
RouteTimeAxisView *rtv;
if ((atv = dynamic_cast<AudioTimeAxisView*>(tv)) != 0) {
if (atv->route()->master()) {
if ((rtv = dynamic_cast<RouteTimeAxisView*>(tv)) != 0) {
if (rtv->route()->master()) {
route_list_display.get_selection()->unselect (i);
}
}
@@ -1308,7 +1309,7 @@ Editor::popup_track_context_menu (int button, int32_t time, ItemType item_type,
break;
case StreamItem:
if (clicked_audio_trackview->get_diskstream()) {
if (clicked_routeview->is_track()) {
build_menu_function = &Editor::build_track_context_menu;
} else {
build_menu_function = &Editor::build_track_bus_context_menu;
@@ -1364,7 +1365,7 @@ Editor::popup_track_context_menu (int button, int32_t time, ItemType item_type,
return;
}
if (clicked_audio_trackview && clicked_audio_trackview->audio_track()) {
if (clicked_routeview && clicked_routeview->audio_track()) {
/* Bounce to disk */
@@ -1373,7 +1374,7 @@ Editor::popup_track_context_menu (int button, int32_t time, ItemType item_type,
edit_items.push_back (SeparatorElem());
switch (clicked_audio_trackview->audio_track()->freeze_state()) {
switch (clicked_routeview->audio_track()->freeze_state()) {
case AudioTrack::NoFreeze:
edit_items.push_back (MenuElem (_("Freeze"), mem_fun(*this, &Editor::freeze_route)));
break;
@@ -1423,7 +1424,7 @@ Editor::build_track_region_context_menu (nframes_t frame)
MenuList& edit_items = track_region_context_menu.items();
edit_items.clear();
AudioTimeAxisView* atv = dynamic_cast<AudioTimeAxisView*> (clicked_trackview);
AudioTimeAxisView* atv = dynamic_cast<AudioTimeAxisView*> (clicked_axisview);
if (atv) {
boost::shared_ptr<Diskstream> ds;
@@ -1450,7 +1451,7 @@ Editor::build_track_crossfade_context_menu (nframes_t frame)
MenuList& edit_items = track_crossfade_context_menu.items();
edit_items.clear ();
AudioTimeAxisView* atv = dynamic_cast<AudioTimeAxisView*> (clicked_trackview);
AudioTimeAxisView* atv = dynamic_cast<AudioTimeAxisView*> (clicked_axisview);
if (atv) {
boost::shared_ptr<Diskstream> ds;
@@ -1949,7 +1950,7 @@ Editor::add_bus_context_items (Menu_Helpers::MenuList& edit_items)
void
Editor::set_snap_to (SnapType st)
{
{
snap_type = st;
string str = snap_type_strings[(int) st];
@@ -3607,7 +3608,7 @@ void
Editor::new_playlists ()
{
begin_reversible_command (_("new playlists"));
mapover_audio_tracks (mem_fun (*this, &Editor::mapped_use_new_playlist));
mapover_tracks (mem_fun (*this, &Editor::mapped_use_new_playlist));
commit_reversible_command ();
}
@@ -3615,7 +3616,7 @@ void
Editor::copy_playlists ()
{
begin_reversible_command (_("copy playlists"));
mapover_audio_tracks (mem_fun (*this, &Editor::mapped_use_copy_playlist));
mapover_tracks (mem_fun (*this, &Editor::mapped_use_copy_playlist));
commit_reversible_command ();
}
@@ -3623,24 +3624,24 @@ void
Editor::clear_playlists ()
{
begin_reversible_command (_("clear playlists"));
mapover_audio_tracks (mem_fun (*this, &Editor::mapped_clear_playlist));
mapover_tracks (mem_fun (*this, &Editor::mapped_clear_playlist));
commit_reversible_command ();
}
void
Editor::mapped_use_new_playlist (AudioTimeAxisView& atv, uint32_t sz)
Editor::mapped_use_new_playlist (RouteTimeAxisView& atv, uint32_t sz)
{
atv.use_new_playlist (sz > 1 ? false : true);
}
void
Editor::mapped_use_copy_playlist (AudioTimeAxisView& atv, uint32_t sz)
Editor::mapped_use_copy_playlist (RouteTimeAxisView& atv, uint32_t sz)
{
atv.use_copy_playlist (sz > 1 ? false : true);
}
void
Editor::mapped_clear_playlist (AudioTimeAxisView& atv, uint32_t sz)
Editor::mapped_clear_playlist (RouteTimeAxisView& atv, uint32_t sz)
{
atv.clear_playlist ();
}

View File

@@ -72,6 +72,7 @@ namespace ARDOUR {
class Session;
class AudioFilter;
class Crossfade;
class ChanCount;
}
namespace LADSPA {
@@ -79,7 +80,6 @@ namespace LADSPA {
}
class TimeAxisView;
class RouteTimeAxisView;
class AudioTimeAxisView;
class AutomationTimeAxisView;
class AudioRegionView;
@@ -410,8 +410,8 @@ class Editor : public PublicEditor
void clear_marker_display ();
void mouse_add_new_marker (nframes_t where);
TimeAxisView* clicked_trackview;
AudioTimeAxisView* clicked_audio_trackview;
TimeAxisView* clicked_axisview;
RouteTimeAxisView* clicked_routeview;
RegionView* clicked_regionview;
RegionView* latest_regionview;
uint32_t clicked_selection;
@@ -420,16 +420,16 @@ class Editor : public PublicEditor
void sort_track_selection ();
void get_relevant_audio_tracks (std::set<AudioTimeAxisView*>& relevant_tracks);
void get_relevant_tracks (std::set<RouteTimeAxisView*>& relevant_tracks);
void get_equivalent_regions (RegionView* rv, std::vector<RegionView*>&);
void mapover_audio_tracks (sigc::slot<void,AudioTimeAxisView&,uint32_t> sl);
void mapover_tracks (sigc::slot<void,RouteTimeAxisView&,uint32_t> sl);
/* functions to be passed to mapover_audio_tracks(), possibly with sigc::bind()-supplied arguments */
/* functions to be passed to mapover_tracks(), possibly with sigc::bind()-supplied arguments */
void mapped_get_equivalent_regions (RouteTimeAxisView&, uint32_t, RegionView*, vector<RegionView*>*);
void mapped_use_new_playlist (AudioTimeAxisView&, uint32_t);
void mapped_use_copy_playlist (AudioTimeAxisView&, uint32_t);
void mapped_clear_playlist (AudioTimeAxisView&, uint32_t);
void mapped_use_new_playlist (RouteTimeAxisView&, uint32_t);
void mapped_use_copy_playlist (RouteTimeAxisView&, uint32_t);
void mapped_clear_playlist (RouteTimeAxisView&, uint32_t);
/* end */
@@ -852,14 +852,14 @@ class Editor : public PublicEditor
int ensure_cursor (nframes_t* pos);
void handle_new_audio_region (boost::weak_ptr<ARDOUR::AudioRegion>);
void handle_audio_region_removed (boost::weak_ptr<ARDOUR::AudioRegion>);
void add_audio_region_to_region_display (boost::shared_ptr<ARDOUR::AudioRegion>);
void handle_new_region (boost::weak_ptr<ARDOUR::Region>);
void handle_region_removed (boost::weak_ptr<ARDOUR::Region>);
void add_region_to_region_display (boost::shared_ptr<ARDOUR::Region>);
void region_hidden (boost::shared_ptr<ARDOUR::Region>);
void redisplay_regions ();
void insert_into_tmp_audio_regionlist(boost::shared_ptr<ARDOUR::AudioRegion>);
void insert_into_tmp_regionlist(boost::shared_ptr<ARDOUR::Region>);
list<boost::shared_ptr<ARDOUR::AudioRegion> > tmp_audio_region_list;
list<boost::shared_ptr<ARDOUR::Region> > tmp_region_list;
void cut_copy (Editing::CutCopyOp);
void cut_copy_points (Editing::CutCopyOp);
@@ -952,7 +952,7 @@ class Editor : public PublicEditor
void amplitude_zoom (gdouble scale);
void amplitude_zoom_step (bool in);
void insert_region_list_drag (boost::shared_ptr<ARDOUR::AudioRegion>, int x, int y);
void insert_region_list_drag (boost::shared_ptr<ARDOUR::Region>, int x, int y);
void insert_region_list_selection (float times);
void add_external_audio_action (Editing::ImportMode);
@@ -1626,7 +1626,7 @@ class Editor : public PublicEditor
void external_edit_region ();
int write_audio_selection (TimeSelection&);
bool write_audio_range (ARDOUR::AudioPlaylist&, uint32_t channels, list<ARDOUR::AudioRange>&);
bool write_audio_range (ARDOUR::AudioPlaylist&, const ARDOUR::ChanCount& channels, list<ARDOUR::AudioRange>&);
void write_selection ();
@@ -1634,7 +1634,8 @@ class Editor : public PublicEditor
UndoAction get_memento() const;
XMLNode *before; /* used in *_reversible_command */
XMLNode *before; /* used in *_reversible_command */
void begin_reversible_command (string cmd_name);
void commit_reversible_command ();

View File

@@ -263,7 +263,7 @@ Editor::import_sndfile (vector<ustring> paths, ImportMode mode, AudioTrack* trac
/* import thread finished - see if we should build a new track */
if (!import_status.new_regions.empty()) {
boost::shared_ptr<AudioRegion> region (import_status.new_regions.front());
boost::shared_ptr<AudioRegion> region = boost::dynamic_pointer_cast<AudioRegion>(import_status.new_regions.front());
finish_bringing_in_audio (region, region->n_channels(), region->n_channels(), track, pos, mode);
}
@@ -402,7 +402,7 @@ Editor::embed_sndfile (vector<Glib::ustring> paths, bool split, bool multiple_fi
if ((s = session->source_by_path_and_channel (path, n)) == 0) {
source = boost::dynamic_pointer_cast<AudioFileSource> (SourceFactory::createReadable
(*session, path, n,
(DataType::AUDIO, *session, path, n,
(mode == ImportAsTapeTrack ?
AudioFileSource::Destructive :
AudioFileSource::Flag (0))));
@@ -436,7 +436,7 @@ Editor::embed_sndfile (vector<Glib::ustring> paths, bool split, bool multiple_fi
Region::Flag (Region::DefaultFlags|Region::WholeFile|Region::External)));
if (Config->get_output_auto_connect() & AutoConnectMaster) {
output_chan = (session->master_out() ? session->master_out()->n_inputs() : input_chan);
output_chan = (session->master_out() ? session->master_out()->n_inputs().get(DataType::AUDIO) : input_chan);
} else {
output_chan = input_chan;
}

View File

@@ -23,7 +23,7 @@
#include "editor.h"
#include "editing.h"
#include "audio_time_axis.h"
#include "region_view.h"
#include "audio_region_view.h"
#include "selection.h"
using namespace ARDOUR;

View File

@@ -477,7 +477,7 @@ Editor::drop_paths (const RefPtr<Gdk::DragContext>& context,
guint info, guint time)
{
TimeAxisView* tvp;
AudioTimeAxisView* tv;
RouteTimeAxisView* tv;
double cy;
vector<ustring> paths;
string spath;
@@ -513,7 +513,7 @@ Editor::drop_paths (const RefPtr<Gdk::DragContext>& context,
nframes_t pos = 0;
do_embed (paths, false, ImportAsTrack, 0, pos, false);
} else if ((tv = dynamic_cast<AudioTimeAxisView*>(tvp)) != 0) {
} else if ((tv = dynamic_cast<RouteTimeAxisView*>(tvp)) != 0) {
/* check that its an audio track, not a bus */
@@ -538,11 +538,8 @@ Editor::drop_regions (const RefPtr<Gdk::DragContext>& context,
for (uint32_t i = 0; i < sr->cnt; ++i) {
boost::shared_ptr<Region> r = sr->data[i];
boost::shared_ptr<AudioRegion> ar;
if ((ar = boost::dynamic_pointer_cast<AudioRegion>(r)) != 0) {
insert_region_list_drag (ar, x, y);
}
insert_region_list_drag (r, x, y);
}
context->drag_finish (true, false, time);

View File

@@ -222,8 +222,8 @@ Editor::canvas_region_view_event (GdkEvent *event, ArdourCanvas::Item* item, Reg
case GDK_3BUTTON_PRESS:
clicked_regionview = rv;
clicked_control_point = 0;
clicked_trackview = &rv->get_time_axis_view();
clicked_audio_trackview = dynamic_cast<AudioTimeAxisView*>(clicked_trackview);
clicked_axisview = &rv->get_time_axis_view();
clicked_routeview = dynamic_cast<RouteTimeAxisView*>(clicked_axisview);
ret = button_press_handler (item, event, RegionItem);
break;
@@ -261,8 +261,8 @@ Editor::canvas_stream_view_event (GdkEvent *event, ArdourCanvas::Item* item, Rou
case GDK_3BUTTON_PRESS:
clicked_regionview = 0;
clicked_control_point = 0;
clicked_trackview = tv;
clicked_audio_trackview = dynamic_cast<AudioTimeAxisView*>(tv);
clicked_axisview = tv;
clicked_routeview = dynamic_cast<RouteTimeAxisView*>(tv);
ret = button_press_handler (item, event, StreamItem);
break;
@@ -298,8 +298,8 @@ Editor::canvas_automation_track_event (GdkEvent *event, ArdourCanvas::Item* item
case GDK_3BUTTON_PRESS:
clicked_regionview = 0;
clicked_control_point = 0;
clicked_trackview = atv;
clicked_audio_trackview = 0;
clicked_axisview = atv;
clicked_routeview = 0;
ret = button_press_handler (item, event, AutomationTrackItem);
break;
@@ -339,8 +339,8 @@ Editor::canvas_fade_in_event (GdkEvent *event, ArdourCanvas::Item* item, AudioRe
case GDK_BUTTON_PRESS:
clicked_regionview = rv;
clicked_control_point = 0;
clicked_trackview = &rv->get_time_axis_view();
clicked_audio_trackview = dynamic_cast<AudioTimeAxisView*>(clicked_trackview);
clicked_axisview = &rv->get_time_axis_view();
clicked_routeview = dynamic_cast<RouteTimeAxisView*>(clicked_axisview);
if (event->button.button == 3) {
return button_press_handler (item, event, FadeInItem);
}
@@ -377,8 +377,8 @@ Editor::canvas_fade_in_handle_event (GdkEvent *event, ArdourCanvas::Item* item,
case GDK_3BUTTON_PRESS:
clicked_regionview = rv;
clicked_control_point = 0;
clicked_trackview = &rv->get_time_axis_view();
clicked_audio_trackview = dynamic_cast<AudioTimeAxisView*>(clicked_trackview);
clicked_axisview = &rv->get_time_axis_view();
clicked_routeview = dynamic_cast<RouteTimeAxisView*>(clicked_axisview);
ret = button_press_handler (item, event, FadeInHandleItem);
break;
@@ -418,8 +418,8 @@ Editor::canvas_fade_out_event (GdkEvent *event, ArdourCanvas::Item* item, AudioR
case GDK_BUTTON_PRESS:
clicked_regionview = rv;
clicked_control_point = 0;
clicked_trackview = &rv->get_time_axis_view();
clicked_audio_trackview = dynamic_cast<AudioTimeAxisView*>(clicked_trackview);
clicked_axisview = &rv->get_time_axis_view();
clicked_routeview = dynamic_cast<RouteTimeAxisView*>(clicked_axisview);
if (event->button.button == 3) {
return button_press_handler (item, event, FadeOutItem);
}
@@ -456,8 +456,8 @@ Editor::canvas_fade_out_handle_event (GdkEvent *event, ArdourCanvas::Item* item,
case GDK_3BUTTON_PRESS:
clicked_regionview = rv;
clicked_control_point = 0;
clicked_trackview = &rv->get_time_axis_view();
clicked_audio_trackview = dynamic_cast<AudioTimeAxisView*>(clicked_trackview);
clicked_axisview = &rv->get_time_axis_view();
clicked_routeview = dynamic_cast<RouteTimeAxisView*>(clicked_axisview);
ret = button_press_handler (item, event, FadeOutHandleItem);
break;
@@ -498,7 +498,7 @@ Editor::canvas_crossfade_view_event (GdkEvent* event, ArdourCanvas::Item* item,
switch (event->type) {
case GDK_BUTTON_PRESS:
clicked_crossfadeview = xfv;
clicked_trackview = &clicked_crossfadeview->get_time_axis_view();
clicked_axisview = &clicked_crossfadeview->get_time_axis_view();
if (event->button.button == 3) {
return button_press_handler (item, event, CrossfadeViewItem);
}
@@ -569,8 +569,8 @@ Editor::canvas_control_point_event (GdkEvent *event, ArdourCanvas::Item* item, C
case GDK_2BUTTON_PRESS:
case GDK_3BUTTON_PRESS:
clicked_control_point = cp;
clicked_trackview = &cp->line.trackview;
clicked_audio_trackview = dynamic_cast<AudioTimeAxisView*>(clicked_trackview);
clicked_axisview = &cp->line.trackview;
clicked_routeview = dynamic_cast<RouteTimeAxisView*>(clicked_axisview);
clicked_regionview = 0;
break;
@@ -735,8 +735,8 @@ Editor::canvas_region_view_name_highlight_event (GdkEvent* event, ArdourCanvas::
case GDK_3BUTTON_PRESS:
clicked_regionview = rv;
clicked_control_point = 0;
clicked_trackview = &clicked_regionview->get_time_axis_view();
clicked_audio_trackview = dynamic_cast<AudioTimeAxisView*>(clicked_trackview);
clicked_axisview = &clicked_regionview->get_time_axis_view();
clicked_routeview = dynamic_cast<RouteTimeAxisView*>(clicked_axisview);
ret = button_press_handler (item, event, RegionViewNameHighlight);
break;
case GDK_BUTTON_RELEASE:
@@ -775,8 +775,8 @@ Editor::canvas_region_view_name_event (GdkEvent *event, ArdourCanvas::Item* item
case GDK_3BUTTON_PRESS:
clicked_regionview = rv;
clicked_control_point = 0;
clicked_trackview = &clicked_regionview->get_time_axis_view();
clicked_audio_trackview = dynamic_cast<AudioTimeAxisView*>(clicked_trackview);
clicked_axisview = &clicked_regionview->get_time_axis_view();
clicked_routeview = dynamic_cast<RouteTimeAxisView*>(clicked_axisview);
ret = button_press_handler (item, event, RegionViewName);
break;
case GDK_BUTTON_RELEASE:

View File

@@ -40,6 +40,7 @@
#include <ardour/audio_diskstream.h>
#include <ardour/audioregion.h>
#include <ardour/audioplaylist.h>
#include <ardour/chan_count.h>
#include <ardour/source_factory.h>
#include <ardour/audiofilesource.h>
@@ -127,6 +128,7 @@ int
Editor::write_region_selection (RegionSelection& regions)
{
for (RegionSelection::iterator i = regions.begin(); i != regions.end(); ++i) {
// FIXME
AudioRegionView* arv = dynamic_cast<AudioRegionView*>(*i);
if (arv)
if (write_region ("", arv->audio_region()) == false)
@@ -207,7 +209,7 @@ Editor::write_region (string path, boost::shared_ptr<AudioRegion> region)
try {
fs = boost::dynamic_pointer_cast<AudioFileSource> (SourceFactory::createWritable (*session, path, false, session->frame_rate()));
fs = boost::dynamic_pointer_cast<AudioFileSource> (SourceFactory::createWritable (DataType::AUDIO, *session, path, false, session->frame_rate()));
}
catch (failed_constructor& err) {
@@ -301,7 +303,7 @@ Editor::write_audio_selection (TimeSelection& ts)
}
bool
Editor::write_audio_range (AudioPlaylist& playlist, uint32_t channels, list<AudioRange>& range)
Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list<AudioRange>& range)
{
boost::shared_ptr<AudioFileSource> fs;
const nframes_t chunk_size = 4096;
@@ -314,6 +316,8 @@ Editor::write_audio_range (AudioPlaylist& playlist, uint32_t channels, list<Audi
string path;
vector<boost::shared_ptr<AudioFileSource> > sources;
uint32_t channels = count.get(DataType::AUDIO);
for (uint32_t n=0; n < channels; ++n) {
for (cnt = 0; cnt < 999999; ++cnt) {
@@ -339,7 +343,7 @@ Editor::write_audio_range (AudioPlaylist& playlist, uint32_t channels, list<Audi
path = s;
try {
fs = boost::dynamic_pointer_cast<AudioFileSource> (SourceFactory::createWritable (*session, path, false, session->frame_rate()));
fs = boost::dynamic_pointer_cast<AudioFileSource> (SourceFactory::createWritable (DataType::AUDIO, *session, path, false, session->frame_rate()));
}
catch (failed_constructor& err) {

View File

@@ -121,7 +121,7 @@ Editor::add_imageframe_marker_time_axis(const string & track_name, TimeAxisView*
void
Editor::popup_imageframe_edit_menu(int button, int32_t time, ArdourCanvas::Item* ifv, bool with_item)
{
ImageFrameTimeAxis* ifta = dynamic_cast<ImageFrameTimeAxis*>(clicked_trackview) ;
ImageFrameTimeAxis* ifta = dynamic_cast<ImageFrameTimeAxis*>(clicked_axisview) ;
if(ifta)
{
@@ -138,7 +138,7 @@ Editor::popup_imageframe_edit_menu(int button, int32_t time, ArdourCanvas::Item*
void
Editor::popup_marker_time_axis_edit_menu(int button, int32_t time, ArdourCanvas::Item* ifv, bool with_item)
{
MarkerTimeAxis* mta = dynamic_cast<MarkerTimeAxis*>(clicked_trackview) ;
MarkerTimeAxis* mta = dynamic_cast<MarkerTimeAxis*>(clicked_axisview) ;
if(mta)
{
@@ -185,9 +185,9 @@ Editor::canvas_imageframe_item_view_event (GdkEvent *event, ArdourCanvas::Item*
case GDK_BUTTON_PRESS:
case GDK_2BUTTON_PRESS:
case GDK_3BUTTON_PRESS:
clicked_trackview = &ifv->get_time_axis_view();
clicked_axisview = &ifv->get_time_axis_view();
iftag = ifv->get_time_axis_group() ;
dynamic_cast<ImageFrameTimeAxis*>(clicked_trackview)->get_view()->set_selected_imageframe_view(iftag, ifv);
dynamic_cast<ImageFrameTimeAxis*>(clicked_axisview)->get_view()->set_selected_imageframe_view(iftag, ifv);
ret = button_press_handler (item, event, ImageFrameItem) ;
break ;
case GDK_BUTTON_RELEASE:
@@ -213,9 +213,9 @@ Editor::canvas_imageframe_start_handle_event (GdkEvent *event, ArdourCanvas::Ite
case GDK_BUTTON_PRESS:
case GDK_2BUTTON_PRESS:
case GDK_3BUTTON_PRESS:
clicked_trackview = &ifv->get_time_axis_view() ;
clicked_axisview = &ifv->get_time_axis_view() ;
iftag = ifv->get_time_axis_group() ;
dynamic_cast<ImageFrameTimeAxis*>(clicked_trackview)->get_view()->set_selected_imageframe_view(iftag, ifv);
dynamic_cast<ImageFrameTimeAxis*>(clicked_axisview)->get_view()->set_selected_imageframe_view(iftag, ifv);
ret = button_press_handler (item, event, ImageFrameHandleStartItem) ;
break ;
@@ -248,9 +248,9 @@ Editor::canvas_imageframe_end_handle_event (GdkEvent *event, ArdourCanvas::Item*
case GDK_BUTTON_PRESS:
case GDK_2BUTTON_PRESS:
case GDK_3BUTTON_PRESS:
clicked_trackview = &ifv->get_time_axis_view() ;
clicked_axisview = &ifv->get_time_axis_view() ;
iftag = ifv->get_time_axis_group() ;
dynamic_cast<ImageFrameTimeAxis*>(clicked_trackview)->get_view()->set_selected_imageframe_view(iftag, ifv);
dynamic_cast<ImageFrameTimeAxis*>(clicked_axisview)->get_view()->set_selected_imageframe_view(iftag, ifv);
ret = button_press_handler (item, event, ImageFrameHandleEndItem) ;
break ;
@@ -281,7 +281,7 @@ Editor::canvas_imageframe_view_event (GdkEvent* event, ArdourCanvas::Item* item,
case GDK_BUTTON_PRESS:
case GDK_2BUTTON_PRESS:
case GDK_3BUTTON_PRESS:
clicked_trackview = ifta ;
clicked_axisview = ifta ;
ret = button_press_handler (item, event, ImageFrameTimeAxisItem) ;
break ;
case GDK_BUTTON_RELEASE:
@@ -304,7 +304,7 @@ Editor::canvas_marker_time_axis_view_event (GdkEvent* event, ArdourCanvas::Item*
case GDK_BUTTON_PRESS:
case GDK_2BUTTON_PRESS:
case GDK_3BUTTON_PRESS:
clicked_trackview = mta ;
clicked_axisview = mta ;
ret = button_press_handler(item, event, MarkerTimeAxisItem) ;
break ;
case GDK_BUTTON_RELEASE:
@@ -327,8 +327,8 @@ Editor::canvas_markerview_item_view_event (GdkEvent* event, ArdourCanvas::Item*
case GDK_BUTTON_PRESS:
case GDK_2BUTTON_PRESS:
case GDK_3BUTTON_PRESS:
clicked_trackview = &mta->get_time_axis_view() ;
dynamic_cast<MarkerTimeAxis*>(clicked_trackview)->get_view()->set_selected_time_axis_item(mta);
clicked_axisview = &mta->get_time_axis_view() ;
dynamic_cast<MarkerTimeAxis*>(clicked_axisview)->get_view()->set_selected_time_axis_item(mta);
ret = button_press_handler(item, event, MarkerViewItem) ;
break ;
case GDK_BUTTON_RELEASE:
@@ -352,8 +352,8 @@ Editor::canvas_markerview_start_handle_event (GdkEvent* event, ArdourCanvas::Ite
case GDK_BUTTON_PRESS:
case GDK_2BUTTON_PRESS:
case GDK_3BUTTON_PRESS:
clicked_trackview = &mta->get_time_axis_view() ;
dynamic_cast<MarkerTimeAxis*>(clicked_trackview)->get_view()->set_selected_time_axis_item(mta) ;
clicked_axisview = &mta->get_time_axis_view() ;
dynamic_cast<MarkerTimeAxis*>(clicked_axisview)->get_view()->set_selected_time_axis_item(mta) ;
ret = button_press_handler(item, event, MarkerViewHandleStartItem) ;
break ;
case GDK_BUTTON_RELEASE:
@@ -383,8 +383,8 @@ Editor::canvas_markerview_end_handle_event (GdkEvent* event, ArdourCanvas::Item*
case GDK_BUTTON_PRESS:
case GDK_2BUTTON_PRESS:
case GDK_3BUTTON_PRESS:
clicked_trackview = &mta->get_time_axis_view() ;
dynamic_cast<MarkerTimeAxis*>(clicked_trackview)->get_view()->set_selected_time_axis_item(mta) ;
clicked_axisview = &mta->get_time_axis_view() ;
dynamic_cast<MarkerTimeAxis*>(clicked_axisview)->get_view()->set_selected_time_axis_item(mta) ;
ret = button_press_handler(item, event, MarkerViewHandleEndItem) ;
break ;
case GDK_BUTTON_RELEASE:
@@ -422,7 +422,7 @@ Editor::canvas_markerview_end_handle_event (GdkEvent* event, ArdourCanvas::Item*
void
Editor::start_imageframe_grab(ArdourCanvas::Item* item, GdkEvent* event)
{
ImageFrameView* ifv = ((ImageFrameTimeAxis*)clicked_trackview)->get_view()->get_selected_imageframe_view() ;
ImageFrameView* ifv = ((ImageFrameTimeAxis*)clicked_axisview)->get_view()->get_selected_imageframe_view() ;
drag_info.copy = false ;
drag_info.item = item ;
drag_info.data = ifv ;
@@ -455,7 +455,7 @@ Editor::start_imageframe_grab(ArdourCanvas::Item* item, GdkEvent* event)
void
Editor::start_markerview_grab(ArdourCanvas::Item* item, GdkEvent* event)
{
MarkerView* mv = ((MarkerTimeAxis*)clicked_trackview)->get_view()->get_selected_time_axis_item() ;
MarkerView* mv = ((MarkerTimeAxis*)clicked_axisview)->get_view()->get_selected_time_axis_item() ;
drag_info.copy = false ;
drag_info.item = item ;
drag_info.data = mv ;
@@ -613,7 +613,7 @@ void
Editor::imageframe_start_handle_op(ArdourCanvas::Item* item, GdkEvent* event)
{
// get the selected item from the parent time axis
ImageFrameTimeAxis* ifta = dynamic_cast<ImageFrameTimeAxis*>(clicked_trackview) ;
ImageFrameTimeAxis* ifta = dynamic_cast<ImageFrameTimeAxis*>(clicked_axisview) ;
if(ifta)
{
ImageFrameView* ifv = ifta->get_view()->get_selected_imageframe_view() ;
@@ -641,7 +641,7 @@ void
Editor::imageframe_end_handle_op(ArdourCanvas::Item* item, GdkEvent* event)
{
// get the selected item from the parent time axis
ImageFrameTimeAxis* ifta = dynamic_cast<ImageFrameTimeAxis*>(clicked_trackview) ;
ImageFrameTimeAxis* ifta = dynamic_cast<ImageFrameTimeAxis*>(clicked_axisview) ;
if(ifta)
{
@@ -838,7 +838,7 @@ Editor::imageframe_end_handle_end_trim (ArdourCanvas::Item* item, GdkEvent* even
void
Editor::markerview_item_start_handle_op(ArdourCanvas::Item* item, GdkEvent* event)
{
MarkerView* mv = reinterpret_cast<MarkerTimeAxis*>(clicked_trackview)->get_view()->get_selected_time_axis_item() ;
MarkerView* mv = reinterpret_cast<MarkerTimeAxis*>(clicked_axisview)->get_view()->get_selected_time_axis_item() ;
if (mv == 0)
{
@@ -861,7 +861,7 @@ Editor::markerview_item_start_handle_op(ArdourCanvas::Item* item, GdkEvent* even
void
Editor::markerview_item_end_handle_op(ArdourCanvas::Item* item, GdkEvent* event)
{
MarkerView* mv = reinterpret_cast<MarkerTimeAxis*>(clicked_trackview)->get_view()->get_selected_time_axis_item() ;
MarkerView* mv = reinterpret_cast<MarkerTimeAxis*>(clicked_axisview)->get_view()->get_selected_time_axis_item() ;
if (mv == 0)
{
fatal << _("programming error: no MarkerView selected") << endmsg ;

View File

@@ -296,8 +296,8 @@ Editor::session_going_away ()
cut_buffer->clear ();
clicked_regionview = 0;
clicked_trackview = 0;
clicked_audio_trackview = 0;
clicked_axisview = 0;
clicked_routeview = 0;
clicked_crossfadeview = 0;
entered_regionview = 0;
entered_track = 0;

View File

@@ -34,6 +34,7 @@
#include "time_axis_view.h"
#include "audio_time_axis.h"
#include "audio_region_view.h"
#include "midi_region_view.h"
#include "marker.h"
#include "streamview.h"
#include "region_gain_line.h"
@@ -53,6 +54,7 @@
#include <ardour/playlist.h>
#include <ardour/audioplaylist.h>
#include <ardour/audioregion.h>
#include <ardour/midi_region.h>
#include <ardour/dB.h>
#include <ardour/utils.h>
#include <ardour/region_factory.h>
@@ -972,7 +974,7 @@ Editor::button_release_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemT
case MouseObject:
switch (item_type) {
case AutomationTrackItem:
dynamic_cast<AutomationTimeAxisView*>(clicked_trackview)->add_automation_event
dynamic_cast<AutomationTimeAxisView*>(clicked_axisview)->add_automation_event
(item,
event,
where,
@@ -999,7 +1001,7 @@ Editor::button_release_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemT
break;
case AutomationTrackItem:
dynamic_cast<AutomationTimeAxisView*>(clicked_trackview)->
dynamic_cast<AutomationTimeAxisView*>(clicked_axisview)->
add_automation_event (item, event, where, event->button.y);
return true;
break;
@@ -2667,10 +2669,10 @@ Editor::start_region_grab (ArdourCanvas::Item* item, GdkEvent* event)
start_grab (event);
double speed = 1.0;
TimeAxisView* tvp = clicked_trackview;
TimeAxisView* tvp = clicked_axisview;
RouteTimeAxisView* tv = dynamic_cast<RouteTimeAxisView*>(tvp);
if (tv && tv->is_audio_track()) {
if (tv && tv->is_track()) {
speed = tv->get_diskstream()->speed();
}
@@ -2699,11 +2701,11 @@ Editor::start_region_copy_grab (ArdourCanvas::Item* item, GdkEvent* event)
start_grab(event);
TimeAxisView* tv = &clicked_regionview->get_time_axis_view();
RouteTimeAxisView* atv = dynamic_cast<RouteTimeAxisView*>(tv);
RouteTimeAxisView* rtv = dynamic_cast<RouteTimeAxisView*>(tv);
double speed = 1.0;
if (atv && atv->is_audio_track()) {
speed = atv->get_diskstream()->speed();
if (rtv && rtv->is_track()) {
speed = rtv->get_diskstream()->speed();
}
drag_info.last_trackview = &clicked_regionview->get_time_axis_view();
@@ -2732,10 +2734,10 @@ Editor::start_region_brush_grab (ArdourCanvas::Item* item, GdkEvent* event)
start_grab (event);
double speed = 1.0;
TimeAxisView* tvp = clicked_trackview;
TimeAxisView* tvp = clicked_axisview;
RouteTimeAxisView* tv = dynamic_cast<RouteTimeAxisView*>(tvp);
if (tv && tv->is_audio_track()) {
if (tv && tv->is_track()) {
speed = tv->get_diskstream()->speed();
}
@@ -2773,17 +2775,20 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event)
for (list<RegionView*>::const_iterator i = selection->regions.by_layer().begin(); i != selection->regions.by_layer().end(); ++i) {
RegionView* rv;
RegionView* nrv;
AudioRegionView* arv;
rv = (*i);
if ((arv = dynamic_cast<AudioRegionView*>(rv)) == 0) {
/* XXX handle MIDI here */
AudioRegionView* arv = dynamic_cast<AudioRegionView*>(rv);
MidiRegionView* mrv = dynamic_cast<MidiRegionView*>(rv);
if (arv) {
nrv = new AudioRegionView (*arv);
} else if (mrv) {
nrv = new MidiRegionView (*mrv);
} else {
continue;
}
nrv = new AudioRegionView (*arv);
nrv->get_canvas_group()->show ();
new_regionviews.push_back (nrv);
@@ -2807,15 +2812,15 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event)
/* Which trackview is this ? */
TimeAxisView* tvp = trackview_by_y_position (drag_info.current_pointer_y);
AudioTimeAxisView* tv = dynamic_cast<AudioTimeAxisView*>(tvp);
RouteTimeAxisView* tv = dynamic_cast<RouteTimeAxisView*>(tvp);
/* The region motion is only processed if the pointer is over
an audio track.
*/
if (!tv || !tv->is_audio_track()) {
if (!tv || !tv->is_track()) {
/* To make sure we hide the verbose canvas cursor when the mouse is
not held over and audiotrack.
not held over a track.
*/
hide_verbose_canvas_cursor ();
return;
@@ -2843,30 +2848,30 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event)
for (TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) {
TimeAxisView *tracklist_timeview;
tracklist_timeview = (*i);
AudioTimeAxisView* atv2 = dynamic_cast<AudioTimeAxisView*>(tracklist_timeview);
RouteTimeAxisView* rtv2 = dynamic_cast<RouteTimeAxisView*>(tracklist_timeview);
list<TimeAxisView*> children_list;
/* zeroes are audio tracks. ones are other types. */
if (!atv2->hidden()) {
if (!rtv2->hidden()) {
if (visible_y_high < atv2->order) {
visible_y_high = atv2->order;
if (visible_y_high < rtv2->order) {
visible_y_high = rtv2->order;
}
if (visible_y_low > atv2->order) {
visible_y_low = atv2->order;
if (visible_y_low > rtv2->order) {
visible_y_low = rtv2->order;
}
if (!atv2->is_audio_track()) {
tracks = tracks |= (0x01 << atv2->order);
if (!rtv2->is_track()) {
tracks = tracks |= (0x01 << rtv2->order);
}
height_list[atv2->order] = (*i)->height;
height_list[rtv2->order] = (*i)->height;
children = 1;
if ((children_list = atv2->get_child_list()).size() > 0) {
if ((children_list = rtv2->get_child_list()).size() > 0) {
for (list<TimeAxisView*>::iterator j = children_list.begin(); j != children_list.end(); ++j) {
tracks = tracks |= (0x01 << (atv2->order + children));
height_list[atv2->order + children] = (*j)->height;
tracks = tracks |= (0x01 << (rtv2->order + children));
height_list[rtv2->order + children] = (*j)->height;
numtracks++;
children++;
}
@@ -2901,27 +2906,27 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event)
rv2->get_canvas_frame()->get_bounds (ix1, iy1, ix2, iy2);
rv2->get_canvas_group()->i2w (ix1, iy1);
TimeAxisView* tvp2 = trackview_by_y_position (iy1);
RouteTimeAxisView* atv2 = dynamic_cast<RouteTimeAxisView*>(tvp2);
RouteTimeAxisView* rtv2 = dynamic_cast<RouteTimeAxisView*>(tvp2);
if (atv2->order != original_pointer_order) {
if (rtv2->order != original_pointer_order) {
/* this isn't the pointer track */
if (canvas_pointer_y_span > 0) {
/* moving up the canvas */
if ((atv2->order - canvas_pointer_y_span) >= visible_y_low) {
if ((rtv2->order - canvas_pointer_y_span) >= visible_y_low) {
int32_t visible_tracks = 0;
while (visible_tracks < canvas_pointer_y_span ) {
visible_tracks++;
while (height_list[atv2->order - (visible_tracks - n)] == 0) {
while (height_list[rtv2->order - (visible_tracks - n)] == 0) {
/* we're passing through a hidden track */
n--;
}
}
if (tracks[atv2->order - (canvas_pointer_y_span - n)] != 0x00) {
if (tracks[rtv2->order - (canvas_pointer_y_span - n)] != 0x00) {
clamp_y_axis = true;
}
@@ -2933,7 +2938,7 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event)
/*moving down the canvas*/
if ((atv2->order - (canvas_pointer_y_span - n)) <= visible_y_high) { // we will overflow
if ((rtv2->order - (canvas_pointer_y_span - n)) <= visible_y_high) { // we will overflow
int32_t visible_tracks = 0;
@@ -2941,11 +2946,11 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event)
while (visible_tracks > canvas_pointer_y_span ) {
visible_tracks--;
while (height_list[atv2->order - (visible_tracks - n)] == 0) {
while (height_list[rtv2->order - (visible_tracks - n)] == 0) {
n++;
}
}
if ( tracks[atv2->order - ( canvas_pointer_y_span - n)] != 0x00) {
if ( tracks[rtv2->order - ( canvas_pointer_y_span - n)] != 0x00) {
clamp_y_axis = true;
}
@@ -2958,9 +2963,9 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event)
} else {
/* this is the pointer's track */
if ((atv2->order - pointer_y_span) > visible_y_high) { // we will overflow
if ((rtv2->order - pointer_y_span) > visible_y_high) { // we will overflow
clamp_y_axis = true;
} else if ((atv2->order - pointer_y_span) < visible_y_low) { // we will underflow
} else if ((rtv2->order - pointer_y_span) < visible_y_low) { // we will underflow
clamp_y_axis = true;
}
}
@@ -3110,14 +3115,14 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event)
rv->get_canvas_frame()->get_bounds (ix1, iy1, ix2, iy2);
rv->get_canvas_group()->i2w (ix1, iy1);
TimeAxisView* tvp2 = trackview_by_y_position (iy1);
AudioTimeAxisView* canvas_atv = dynamic_cast<AudioTimeAxisView*>(tvp2);
AudioTimeAxisView* temp_atv;
RouteTimeAxisView* canvas_rtv = dynamic_cast<RouteTimeAxisView*>(tvp2);
RouteTimeAxisView* temp_rtv;
if ((pointer_y_span != 0) && !clamp_y_axis) {
y_delta = 0;
int32_t x = 0;
for (j = height_list.begin(); j!= height_list.end(); j++) {
if (x == canvas_atv->order) {
if (x == canvas_rtv->order) {
/* we found the track the region is on */
if (x != original_pointer_order) {
/*this isn't from the same track we're dragging from */
@@ -3155,14 +3160,14 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event)
/* find out where we'll be when we move and set height accordingly */
tvp2 = trackview_by_y_position (iy1 + y_delta);
temp_atv = dynamic_cast<AudioTimeAxisView*>(tvp2);
rv->set_height (temp_atv->height);
temp_rtv = dynamic_cast<RouteTimeAxisView*>(tvp2);
rv->set_height (temp_rtv->height);
/* if you un-comment the following, the region colours will follow the track colours whilst dragging,
personally, i think this can confuse things, but never mind.
*/
//const GdkColor& col (temp_atv->view->get_region_color());
//const GdkColor& col (temp_rtv->view->get_region_color());
//rv->set_color (const_cast<GdkColor&>(col));
break;
}
@@ -3230,7 +3235,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event
pair<set<boost::shared_ptr<Playlist> >::iterator,bool> insert_result;
bool nocommit = true;
double speed;
RouteTimeAxisView* atv;
RouteTimeAxisView* rtv;
bool regionview_y_movement;
bool regionview_x_movement;
vector<RegionView*> copies;
@@ -3239,14 +3244,8 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event
motion handler.
*/
if (drag_info.first_move) {
if (drag_info.first_move && !(drag_info.copy && drag_info.x_constrained)) {
/* just a click */
if (drag_info.copy) {
for (list<RegionView*>::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) {
copies.push_back (*i);
}
}
goto out;
}
@@ -3273,9 +3272,9 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event
/* adjust for track speed */
speed = 1.0;
atv = dynamic_cast<AudioTimeAxisView*> (drag_info.last_trackview);
if (atv && atv->get_diskstream()) {
speed = atv->get_diskstream()->speed();
rtv = dynamic_cast<RouteTimeAxisView*> (drag_info.last_trackview);
if (rtv && rtv->get_diskstream()) {
speed = rtv->get_diskstream()->speed();
}
regionview_x_movement = (drag_info.last_frame_position != (nframes_t) (rv->region()->position()/speed));
@@ -3317,11 +3316,11 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event
rv->get_canvas_frame()->get_bounds (ix1, iy1, ix2, iy2);
rv->get_canvas_group()->i2w (ix1, iy1);
TimeAxisView* tvp2 = trackview_by_y_position (iy1);
AudioTimeAxisView* atv2 = dynamic_cast<AudioTimeAxisView*>(tvp2);
RouteTimeAxisView* rtv2 = dynamic_cast<RouteTimeAxisView*>(tvp2);
boost::shared_ptr<Playlist> from_playlist = rv->region()->playlist();
boost::shared_ptr<Playlist> to_playlist = atv2->playlist();
boost::shared_ptr<Playlist> to_playlist = rtv2->playlist();
where = (nframes_t) (unit_to_frame (ix1) * speed);
boost::shared_ptr<Region> new_region (RegionFactory::create (rv->region()));
@@ -3355,7 +3354,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event
latest_regionview = 0;
sigc::connection c = atv2->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view));
sigc::connection c = rtv2->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view));
session->add_command (new MementoCommand<Playlist>(*to_playlist, &to_playlist->get_state(), 0));
to_playlist->add_region (new_region, where);
session->add_command (new MementoCommand<Playlist>(*to_playlist, 0, &to_playlist->get_state()));
@@ -3416,10 +3415,10 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event
if (regionview_x_movement) {
double ownspeed = 1.0;
atv = dynamic_cast<AudioTimeAxisView*> (&(rv->get_time_axis_view()));
rtv = dynamic_cast<RouteTimeAxisView*> (&(rv->get_time_axis_view()));
if (atv && atv->get_diskstream()) {
ownspeed = atv->get_diskstream()->speed();
if (rtv && rtv->get_diskstream()) {
ownspeed = rtv->get_diskstream()->speed();
}
/* base the new region position on the current position of the regionview.*/
@@ -3456,14 +3455,14 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event
}
/* add it */
latest_regionview = 0;
sigc::connection c = atv->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view));
to_playlist->add_region (newregion, (nframes_t) (where * atv->get_diskstream()->speed()));
sigc::connection c = rtv->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view));
to_playlist->add_region (newregion, (nframes_t) (where * rtv->get_diskstream()->speed()));
c.disconnect ();
if (latest_regionview) {
atv->reveal_dependent_views (*latest_regionview);
rtv->reveal_dependent_views (*latest_regionview);
selection->add (latest_regionview);
}
@@ -3509,10 +3508,10 @@ Editor::region_view_item_click (AudioRegionView& rv, GdkEventButton* event)
if (Keyboard::modifier_state_contains (event->state, Keyboard::Control)) {
TimeAxisView* tv = &rv.get_time_axis_view();
AudioTimeAxisView* atv = dynamic_cast<AudioTimeAxisView*>(tv);
RouteTimeAxisView* rtv = dynamic_cast<RouteTimeAxisView*>(tv);
double speed = 1.0;
if (atv && atv->is_audio_track()) {
speed = atv->get_diskstream()->speed();
if (rtv && rtv->is_track()) {
speed = rtv->get_diskstream()->speed();
}
if (Keyboard::modifier_state_equals (event->state, Keyboard::ModifierMask (Keyboard::Control|Keyboard::Alt))) {
@@ -3688,7 +3687,7 @@ Editor::start_selection_grab (ArdourCanvas::Item* item, GdkEvent* event)
*/
latest_regionview = 0;
sigc::connection c = clicked_audio_trackview->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view));
sigc::connection c = clicked_routeview->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view));
/* A selection grab currently creates two undo/redo operations, one for
creating the new region and another for moving it.
@@ -3696,11 +3695,11 @@ Editor::start_selection_grab (ArdourCanvas::Item* item, GdkEvent* event)
begin_reversible_command (_("selection grab"));
boost::shared_ptr<Playlist> playlist = clicked_trackview->playlist();
boost::shared_ptr<Playlist> playlist = clicked_axisview->playlist();
XMLNode *before = &(playlist->get_state());
clicked_trackview->playlist()->add_region (region, selection->time[clicked_selection].start);
XMLNode *after = &(playlist->get_state());
XMLNode *before = &(playlist->get_state());
clicked_routeview->playlist()->add_region (region, selection->time[clicked_selection].start);
XMLNode *after = &(playlist->get_state());
session->add_command(new MementoCommand<Playlist>(*playlist, before, after));
commit_reversible_command ();
@@ -3723,7 +3722,7 @@ Editor::start_selection_grab (ArdourCanvas::Item* item, GdkEvent* event)
start_grab (event);
drag_info.last_trackview = clicked_trackview;
drag_info.last_trackview = clicked_axisview;
drag_info.last_frame_position = latest_regionview->region()->position();
drag_info.pointer_frame_offset = drag_info.grab_frame - drag_info.last_frame_position;
@@ -3769,8 +3768,8 @@ Editor::start_selection_op (ArdourCanvas::Item* item, GdkEvent* event, Selection
break;
case SelectionStartTrim:
if (clicked_trackview) {
clicked_trackview->order_selection_trims (item, true);
if (clicked_axisview) {
clicked_axisview->order_selection_trims (item, true);
}
start_grab (event, trimmer_cursor);
start = selection->time[clicked_selection].start;
@@ -3778,8 +3777,8 @@ Editor::start_selection_op (ArdourCanvas::Item* item, GdkEvent* event, Selection
break;
case SelectionEndTrim:
if (clicked_trackview) {
clicked_trackview->order_selection_trims (item, false);
if (clicked_axisview) {
clicked_axisview->order_selection_trims (item, false);
}
start_grab (event, trimmer_cursor);
end = selection->time[clicked_selection].end;
@@ -3854,7 +3853,7 @@ Editor::drag_selection (ArdourCanvas::Item* item, GdkEvent* event)
drag_info.copy = false;
} else {
/* new selection-> */
clicked_selection = selection->set (clicked_trackview, start, end);
clicked_selection = selection->set (clicked_axisview, start, end);
}
}
break;
@@ -3958,10 +3957,10 @@ void
Editor::start_trim (ArdourCanvas::Item* item, GdkEvent* event)
{
double speed = 1.0;
TimeAxisView* tvp = clicked_trackview;
AudioTimeAxisView* tv = dynamic_cast<AudioTimeAxisView*>(tvp);
TimeAxisView* tvp = clicked_axisview;
RouteTimeAxisView* tv = dynamic_cast<RouteTimeAxisView*>(tvp);
if (tv && tv->is_audio_track()) {
if (tv && tv->is_track()) {
speed = tv->get_diskstream()->speed();
}
@@ -4016,11 +4015,11 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event)
*/
double speed = 1.0;
TimeAxisView* tvp = clicked_trackview;
TimeAxisView* tvp = clicked_axisview;
RouteTimeAxisView* tv = dynamic_cast<RouteTimeAxisView*>(tvp);
pair<set<boost::shared_ptr<Playlist> >::iterator,bool> insert_result;
if (tv && tv->is_audio_track()) {
if (tv && tv->is_track()) {
speed = tv->get_diskstream()->speed();
}
@@ -4144,10 +4143,10 @@ Editor::single_contents_trim (RegionView& rv, nframes_t frame_delta, bool left_d
nframes_t new_bound;
double speed = 1.0;
TimeAxisView* tvp = clicked_trackview;
TimeAxisView* tvp = clicked_axisview;
RouteTimeAxisView* tv = dynamic_cast<RouteTimeAxisView*>(tvp);
if (tv && tv->is_audio_track()) {
if (tv && tv->is_track()) {
speed = tv->get_diskstream()->speed();
}
@@ -4184,10 +4183,10 @@ Editor::single_start_trim (RegionView& rv, nframes_t frame_delta, bool left_dire
nframes_t new_bound;
double speed = 1.0;
TimeAxisView* tvp = clicked_trackview;
AudioTimeAxisView* tv = dynamic_cast<AudioTimeAxisView*>(tvp);
TimeAxisView* tvp = clicked_axisview;
RouteTimeAxisView* tv = dynamic_cast<RouteTimeAxisView*>(tvp);
if (tv && tv->is_audio_track()) {
if (tv && tv->is_track()) {
speed = tv->get_diskstream()->speed();
}
@@ -4218,10 +4217,10 @@ Editor::single_end_trim (RegionView& rv, nframes_t frame_delta, bool left_direct
nframes_t new_bound;
double speed = 1.0;
TimeAxisView* tvp = clicked_trackview;
AudioTimeAxisView* tv = dynamic_cast<AudioTimeAxisView*>(tvp);
TimeAxisView* tvp = clicked_axisview;
RouteTimeAxisView* tv = dynamic_cast<RouteTimeAxisView*>(tvp);
if (tv && tv->is_audio_track()) {
if (tv && tv->is_track()) {
speed = tv->get_diskstream()->speed();
}
@@ -4877,14 +4876,14 @@ Editor::mouse_brush_insert_region (RegionView* rv, nframes_t pos)
return;
}
RouteTimeAxisView* atv = dynamic_cast<RouteTimeAxisView*>(&arv->get_time_axis_view());
RouteTimeAxisView* rtv = dynamic_cast<RouteTimeAxisView*>(&arv->get_time_axis_view());
if (atv == 0 || !atv->is_audio_track()) {
if (rtv == 0 || !rtv->is_track()) {
return;
}
boost::shared_ptr<Playlist> playlist = atv->playlist();
double speed = atv->get_diskstream()->speed();
boost::shared_ptr<Playlist> playlist = rtv->playlist();
double speed = rtv->get_diskstream()->speed();
XMLNode &before = playlist->get_state();
playlist->add_region (boost::dynamic_pointer_cast<AudioRegion> (RegionFactory::create (arv->audio_region())), (nframes_t) (pos * speed));

View File

@@ -146,11 +146,11 @@ Editor::split_regions_at (nframes_t where, RegionSelection& regions)
void
Editor::remove_clicked_region ()
{
if (clicked_audio_trackview == 0 || clicked_regionview == 0) {
if (clicked_routeview == 0 || clicked_regionview == 0) {
return;
}
boost::shared_ptr<Playlist> playlist = clicked_audio_trackview->playlist();
boost::shared_ptr<Playlist> playlist = clicked_routeview->playlist();
begin_reversible_command (_("remove region"));
XMLNode &before = playlist->get_state();
@@ -530,11 +530,11 @@ Editor::build_region_boundary_cache ()
}
float speed = 1.0f;
AudioTimeAxisView *atav;
RouteTimeAxisView *rtav;
if (ontrack != 0 && (atav = dynamic_cast<AudioTimeAxisView*>(ontrack)) != 0 ) {
if (atav->get_diskstream() != 0) {
speed = atav->get_diskstream()->speed();
if (ontrack != 0 && (rtav = dynamic_cast<RouteTimeAxisView*>(ontrack)) != 0 ) {
if (rtav->get_diskstream() != 0) {
speed = rtav->get_diskstream()->speed();
}
}
@@ -579,7 +579,7 @@ Editor::find_next_region (nframes_t frame, RegionPoint point, int32_t dir, Track
float track_speed;
nframes_t track_frame;
AudioTimeAxisView *atav;
RouteTimeAxisView *rtav;
for (i = tracks.begin(); i != tracks.end(); ++i) {
@@ -587,9 +587,9 @@ Editor::find_next_region (nframes_t frame, RegionPoint point, int32_t dir, Track
boost::shared_ptr<Region> r;
track_speed = 1.0f;
if ( (atav = dynamic_cast<AudioTimeAxisView*>(*i)) != 0 ) {
if (atav->get_diskstream()!=0)
track_speed = atav->get_diskstream()->speed();
if ( (rtav = dynamic_cast<RouteTimeAxisView*>(*i)) != 0 ) {
if (rtav->get_diskstream()!=0)
track_speed = rtav->get_diskstream()->speed();
}
track_frame = session_frame_to_track_frame(frame, track_speed);
@@ -651,10 +651,10 @@ Editor::cursor_to_region_point (Cursor* cursor, RegionPoint point, int32_t dir)
r = find_next_region (pos, point, dir, selection->tracks, &ontrack);
} else if (clicked_trackview) {
} else if (clicked_axisview) {
TrackViewList t;
t.push_back (clicked_trackview);
t.push_back (clicked_axisview);
r = find_next_region (pos, point, dir, t, &ontrack);
@@ -682,11 +682,11 @@ Editor::cursor_to_region_point (Cursor* cursor, RegionPoint point, int32_t dir)
}
float speed = 1.0f;
AudioTimeAxisView *atav;
RouteTimeAxisView *rtav;
if ( ontrack != 0 && (atav = dynamic_cast<AudioTimeAxisView*>(ontrack)) != 0 ) {
if (atav->get_diskstream() != 0) {
speed = atav->get_diskstream()->speed();
if ( ontrack != 0 && (rtav = dynamic_cast<RouteTimeAxisView*>(ontrack)) != 0 ) {
if (rtav->get_diskstream() != 0) {
speed = rtav->get_diskstream()->speed();
}
}
@@ -1248,7 +1248,7 @@ Editor::add_location_from_selection ()
return;
}
if (session == 0 || clicked_trackview == 0) {
if (session == 0 || clicked_axisview == 0) {
return;
}
@@ -1482,13 +1482,13 @@ Editor::unhide_ranges ()
/* INSERT/REPLACE */
void
Editor::insert_region_list_drag (boost::shared_ptr<AudioRegion> region, int x, int y)
Editor::insert_region_list_drag (boost::shared_ptr<Region> region, int x, int y)
{
double wx, wy;
double cx, cy;
TimeAxisView *tv;
nframes_t where;
AudioTimeAxisView *atv = 0;
RouteTimeAxisView *rtv = 0;
boost::shared_ptr<Playlist> playlist;
track_canvas.window_to_world (x, y, wx, wy);
@@ -1511,11 +1511,11 @@ Editor::insert_region_list_drag (boost::shared_ptr<AudioRegion> region, int x, i
return;
}
if ((atv = dynamic_cast<AudioTimeAxisView*>(tv)) == 0) {
if ((rtv = dynamic_cast<RouteTimeAxisView*>(tv)) == 0) {
return;
}
if ((playlist = atv->playlist()) == 0) {
if ((playlist = rtv->playlist()) == 0) {
return;
}
@@ -1534,8 +1534,8 @@ Editor::insert_region_list_selection (float times)
RouteTimeAxisView *tv = 0;
boost::shared_ptr<Playlist> playlist;
if (clicked_audio_trackview != 0) {
tv = clicked_audio_trackview;
if (clicked_routeview != 0) {
tv = clicked_routeview;
} else if (!selection->tracks.empty()) {
if ((tv = dynamic_cast<RouteTimeAxisView*>(selection->tracks.front())) == 0) {
return;
@@ -1878,7 +1878,7 @@ Editor::interthread_cancel_clicked ()
void
Editor::region_from_selection ()
{
if (clicked_trackview == 0) {
if (clicked_axisview == 0) {
return;
}
@@ -1908,7 +1908,7 @@ Editor::region_from_selection ()
}
current = boost::dynamic_pointer_cast<AudioRegion> (current_r);
// FIXME: audio only
assert(current); // FIXME
if (current != 0) {
internal_start = start - current->position();
session->region_name (new_name, current->name(), true);
@@ -1987,6 +1987,8 @@ Editor::new_region_from_selection ()
void
Editor::separate_region_from_selection ()
{
// FIXME: TYPE
bool doing_undo = false;
if (selection->time.empty()) {
@@ -1999,37 +2001,34 @@ Editor::separate_region_from_selection ()
for (TrackSelection::iterator i = selection->tracks.begin(); i != selection->tracks.end(); ++i) {
AudioTimeAxisView* atv;
RouteTimeAxisView* rtv;
if ((rtv = dynamic_cast<RouteTimeAxisView*> ((*i))) != 0) {
if ((atv = dynamic_cast<AudioTimeAxisView*> ((*i))) != 0) {
Track* t = dynamic_cast<Track*>(rtv->track());
if (atv->is_audio_track()) {
/* no edits to destructive tracks */
if (atv->audio_track()->audio_diskstream()->destructive()) {
continue;
}
if ((playlist = atv->playlist()) != 0) {
if (t != 0 && ! t->diskstream()->destructive()) {
if ((playlist = rtv->playlist()) != 0) {
if (!doing_undo) {
begin_reversible_command (_("separate"));
doing_undo = true;
}
XMLNode *before;
if (doing_undo)
before = &(playlist->get_state());
XMLNode *before;
if (doing_undo)
before = &(playlist->get_state());
/* XXX need to consider musical time selections here at some point */
double speed = atv->get_diskstream()->speed();
double speed = t->diskstream()->speed();
for (list<AudioRange>::iterator t = selection->time.begin(); t != selection->time.end(); ++t) {
playlist->partition ((nframes_t)((*t).start * speed), (nframes_t)((*t).end * speed), true);
}
if (doing_undo)
session->add_command(new MementoCommand<Playlist>(*playlist, before, &playlist->get_state()));
if (doing_undo)
session->add_command(new MementoCommand<Playlist>(*playlist, before, &playlist->get_state()));
}
}
}
@@ -2041,6 +2040,8 @@ Editor::separate_region_from_selection ()
void
Editor::separate_regions_using_location (Location& loc)
{
// FIXME: TYPE
bool doing_undo = false;
if (loc.is_mark()) {
@@ -2057,31 +2058,28 @@ Editor::separate_regions_using_location (Location& loc)
for (TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) {
//for (TrackSelection::iterator i = selection->tracks.begin(); i != selection->tracks.end(); ++i) {
AudioTimeAxisView* atv;
RouteTimeAxisView* rtv;
if ((rtv = dynamic_cast<RouteTimeAxisView*> ((*i))) != 0) {
if ((atv = dynamic_cast<AudioTimeAxisView*> ((*i))) != 0) {
Track* t = dynamic_cast<Track*>(rtv->track());
if (atv->is_audio_track()) {
if (t != 0 && ! t->diskstream()->destructive()) {
if ((playlist = rtv->playlist()) != 0) {
/* no edits to destructive tracks */
if (atv->audio_track()->audio_diskstream()->destructive()) {
continue;
}
if ((playlist = atv->playlist()) != 0) {
XMLNode *before;
XMLNode *before;
if (!doing_undo) {
begin_reversible_command (_("separate"));
doing_undo = true;
}
if (doing_undo)
before = &(playlist->get_state());
if (doing_undo)
before = &(playlist->get_state());
/* XXX need to consider musical time selections here at some point */
double speed = atv->get_diskstream()->speed();
double speed = rtv->get_diskstream()->speed();
playlist->partition ((nframes_t)(loc.start() * speed), (nframes_t)(loc.end() * speed), true);
@@ -2109,19 +2107,15 @@ Editor::crop_region_to_selection ()
for (TrackSelection::iterator i = selection->tracks.begin(); i != selection->tracks.end(); ++i) {
AudioTimeAxisView* atv;
RouteTimeAxisView* rtv;
if ((atv = dynamic_cast<AudioTimeAxisView*> ((*i))) != 0) {
if (atv->is_audio_track()) {
if ((rtv = dynamic_cast<RouteTimeAxisView*> ((*i))) != 0) {
Track* t = dynamic_cast<Track*>(rtv->track());
if (t != 0 && ! t->diskstream()->destructive()) {
/* no edits to destructive tracks */
if (atv->audio_track()->audio_diskstream()->destructive()) {
continue;
}
if ((playlist = atv->playlist()) != 0) {
if ((playlist = rtv->playlist()) != 0) {
playlists.push_back (playlist);
}
}
@@ -2189,8 +2183,7 @@ Editor::region_fill_track ()
// FIXME
boost::shared_ptr<AudioRegion> ar = boost::dynamic_pointer_cast<AudioRegion>(region);
if (!ar)
continue;
assert(ar);
boost::shared_ptr<Playlist> pl = region->playlist();
@@ -2204,7 +2197,7 @@ Editor::region_fill_track ()
return;
}
XMLNode &before = pl->get_state();
XMLNode &before = pl->get_state();
pl->add_region (RegionFactory::create (ar), ar->last_frame(), times);
session->add_command (new MementoCommand<Playlist>(*pl, &before, &pl->get_state()));
}
@@ -2215,7 +2208,7 @@ Editor::region_fill_track ()
void
Editor::region_fill_selection ()
{
if (clicked_audio_trackview == 0 || !clicked_audio_trackview->is_audio_track()) {
if (clicked_routeview == 0 || !clicked_routeview->is_audio_track()) {
return;
}
@@ -2341,7 +2334,7 @@ Editor::align_relative (RegionPoint what)
}
struct RegionSortByTime {
bool operator() (const AudioRegionView* a, const AudioRegionView* b) {
bool operator() (const RegionView* a, const RegionView* b) {
return a->region()->position() < b->region()->position();
}
};
@@ -2464,11 +2457,11 @@ Editor::trim_region_to_edit_cursor ()
boost::shared_ptr<Region> region (clicked_regionview->region());
float speed = 1.0f;
AudioTimeAxisView *atav;
RouteTimeAxisView *rtav;
if ( clicked_trackview != 0 && (atav = dynamic_cast<AudioTimeAxisView*>(clicked_trackview)) != 0 ) {
if (atav->get_diskstream() != 0) {
speed = atav->get_diskstream()->speed();
if ( clicked_axisview != 0 && (rtav = dynamic_cast<RouteTimeAxisView*>(clicked_axisview)) != 0 ) {
if (rtav->get_diskstream() != 0) {
speed = rtav->get_diskstream()->speed();
}
}
@@ -2490,11 +2483,11 @@ Editor::trim_region_from_edit_cursor ()
boost::shared_ptr<Region> region (clicked_regionview->region());
float speed = 1.0f;
AudioTimeAxisView *atav;
RouteTimeAxisView *rtav;
if ( clicked_trackview != 0 && (atav = dynamic_cast<AudioTimeAxisView*>(clicked_trackview)) != 0 ) {
if (atav->get_diskstream() != 0) {
speed = atav->get_diskstream()->speed();
if ( clicked_axisview != 0 && (rtav = dynamic_cast<RouteTimeAxisView*>(clicked_axisview)) != 0 ) {
if (rtav->get_diskstream() != 0) {
speed = rtav->get_diskstream()->speed();
}
}
@@ -2509,11 +2502,11 @@ Editor::trim_region_from_edit_cursor ()
void
Editor::unfreeze_route ()
{
if (clicked_audio_trackview == 0 || !clicked_audio_trackview->is_audio_track()) {
if (clicked_routeview == 0 || !clicked_routeview->is_track()) {
return;
}
clicked_audio_trackview->audio_track()->unfreeze ();
clicked_routeview->track()->unfreeze ();
}
void*
@@ -2526,7 +2519,7 @@ Editor::_freeze_thread (void* arg)
void*
Editor::freeze_thread ()
{
clicked_audio_trackview->audio_track()->freeze (*current_interthread_info);
clicked_routeview->audio_track()->freeze (*current_interthread_info);
return 0;
}
@@ -2540,7 +2533,7 @@ Editor::freeze_progress_timeout (void *arg)
void
Editor::freeze_route ()
{
if (clicked_audio_trackview == 0 || !clicked_audio_trackview->is_audio_track()) {
if (clicked_routeview == 0 || !clicked_routeview->is_track()) {
return;
}
@@ -2604,15 +2597,15 @@ Editor::bounce_range_selection ()
for (TrackViewList::iterator i = views.begin(); i != views.end(); ++i) {
AudioTimeAxisView* atv;
RouteTimeAxisView* rtv;
if ((atv = dynamic_cast<AudioTimeAxisView*> (*i)) == 0) {
if ((rtv = dynamic_cast<RouteTimeAxisView*> (*i)) == 0) {
continue;
}
boost::shared_ptr<Playlist> playlist;
if ((playlist = atv->playlist()) == 0) {
if ((playlist = rtv->playlist()) == 0) {
return;
}
@@ -2622,9 +2615,9 @@ Editor::bounce_range_selection ()
itt.cancel = false;
itt.progress = false;
XMLNode &before = playlist->get_state();
atv->audio_track()->bounce_range (start, cnt, itt);
XMLNode &after = playlist->get_state();
XMLNode &before = playlist->get_state();
rtv->track()->bounce_range (start, cnt, itt);
XMLNode &after = playlist->get_state();
session->add_command (new MementoCommand<Playlist> (*playlist, &before, &after));
}
@@ -2736,14 +2729,14 @@ struct lt_playlist {
struct PlaylistMapping {
TimeAxisView* tv;
boost::shared_ptr<AudioPlaylist> pl;
boost::shared_ptr<Playlist> pl;
PlaylistMapping (TimeAxisView* tvp) : tv (tvp) {}
};
void
Editor::cut_copy_regions (CutCopyOp op)
{
{
/* we can't use a std::map here because the ordering is important, and we can't trivially sort
a map when we want ordered access to both elements. i think.
*/
@@ -2764,7 +2757,7 @@ Editor::cut_copy_regions (CutCopyOp op)
first_position = min ((*x)->region()->position(), first_position);
if (op == Cut || op == Clear) {
boost::shared_ptr<AudioPlaylist> pl = boost::dynamic_pointer_cast<AudioPlaylist>((*x)->region()->playlist());
boost::shared_ptr<Playlist> pl = (*x)->region()->playlist();
if (pl) {
@@ -2796,7 +2789,7 @@ Editor::cut_copy_regions (CutCopyOp op)
for (RegionSelection::iterator x = selection->regions.begin(); x != selection->regions.end(); ) {
boost::shared_ptr<AudioPlaylist> pl = boost::dynamic_pointer_cast<AudioPlaylist>((*x)->region()->playlist());
boost::shared_ptr<Playlist> pl = (*x)->region()->playlist();
if (!pl) {
/* impossible, but this handles it for the future */
@@ -2804,7 +2797,7 @@ Editor::cut_copy_regions (CutCopyOp op)
}
TimeAxisView& tv = (*x)->get_trackview();
boost::shared_ptr<AudioPlaylist> npl;
boost::shared_ptr<Playlist> npl;
RegionSelection::iterator tmp;
tmp = x;
@@ -2821,34 +2814,32 @@ Editor::cut_copy_regions (CutCopyOp op)
assert (z != pmap.end());
if (!(*z).pl) {
npl = boost::dynamic_pointer_cast<AudioPlaylist> (PlaylistFactory::create (*session, "cutlist", true));
npl = PlaylistFactory::create (pl->data_type(), *session, "cutlist", true);
npl->freeze();
(*z).pl = npl;
} else {
npl = (*z).pl;
}
boost::shared_ptr<AudioRegion> ar = boost::dynamic_pointer_cast<AudioRegion>((*x)->region());
boost::shared_ptr<Region> r = (*x)->region();
boost::shared_ptr<Region> _xx;
assert (r != 0);
switch (op) {
case Cut:
if (!ar) break;
_xx = RegionFactory::create ((*x)->region());
npl->add_region (_xx, (*x)->region()->position() - first_position);
pl->remove_region (((*x)->region()));
_xx = RegionFactory::create (r);
npl->add_region (_xx, r->position() - first_position);
pl->remove_region (r);
break;
case Copy:
if (!ar) break;
/* copy region before adding, so we're not putting same object into two different playlists */
npl->add_region (RegionFactory::create ((*x)->region()), (*x)->region()->position() - first_position);
npl->add_region (RegionFactory::create (r), r->position() - first_position);
break;
case Clear:
pl->remove_region (((*x)->region()));
pl->remove_region (r);
break;
}
@@ -2971,15 +2962,15 @@ Editor::paste_named_selection (float times)
for (t = selection->tracks.begin(); t != selection->tracks.end(); ++t) {
AudioTimeAxisView* atv;
RouteTimeAxisView* rtv;
boost::shared_ptr<Playlist> pl;
boost::shared_ptr<AudioPlaylist> apl;
if ((atv = dynamic_cast<AudioTimeAxisView*> (*t)) == 0) {
if ((rtv = dynamic_cast<RouteTimeAxisView*> (*t)) == 0) {
continue;
}
if ((pl = atv->playlist()) == 0) {
if ((pl = rtv->playlist()) == 0) {
continue;
}
@@ -2990,7 +2981,7 @@ Editor::paste_named_selection (float times)
tmp = chunk;
++tmp;
XMLNode &before = apl->get_state();
XMLNode &before = apl->get_state();
apl->paste (*chunk, edit_cursor->current_frame, times);
session->add_command(new MementoCommand<AudioPlaylist>(*apl, &before, &apl->get_state()));
@@ -3017,8 +3008,8 @@ Editor::duplicate_some_regions (RegionSelection& regions, float times)
boost::shared_ptr<Region> r ((*i)->region());
TimeAxisView& tv = (*i)->get_time_axis_view();
AudioTimeAxisView* atv = dynamic_cast<AudioTimeAxisView*> (&tv);
sigc::connection c = atv->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view));
RouteTimeAxisView* rtv = dynamic_cast<RouteTimeAxisView*> (&tv);
sigc::connection c = rtv->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view));
playlist = (*i)->region()->playlist();
XMLNode &before = playlist->get_state();

View File

@@ -50,26 +50,26 @@ using namespace Glib;
using namespace Editing;
void
Editor::handle_audio_region_removed (boost::weak_ptr<AudioRegion> wregion)
Editor::handle_region_removed (boost::weak_ptr<Region> wregion)
{
ENSURE_GUI_THREAD (mem_fun (*this, &Editor::redisplay_regions));
redisplay_regions ();
}
void
Editor::handle_new_audio_region (boost::weak_ptr<AudioRegion> wregion)
Editor::handle_new_region (boost::weak_ptr<Region> wregion)
{
ENSURE_GUI_THREAD (bind (mem_fun (*this, &Editor::handle_new_audio_region), wregion));
ENSURE_GUI_THREAD (bind (mem_fun (*this, &Editor::handle_new_region), wregion));
/* don't copy region - the one we are being notified
about belongs to the session, and so it will
never be edited.
*/
boost::shared_ptr<AudioRegion> region (wregion.lock());
boost::shared_ptr<Region> region (wregion.lock());
if (region) {
add_audio_region_to_region_display (region);
add_region_to_region_display (region);
}
}
@@ -82,7 +82,7 @@ Editor::region_hidden (boost::shared_ptr<Region> r)
}
void
Editor::add_audio_region_to_region_display (boost::shared_ptr<AudioRegion> region)
Editor::add_region_to_region_display (boost::shared_ptr<Region> region)
{
string str;
TreeModel::Row row;
@@ -242,14 +242,14 @@ Editor::region_list_selection_changed()
}
void
Editor::insert_into_tmp_audio_regionlist(boost::shared_ptr<AudioRegion> region)
Editor::insert_into_tmp_regionlist(boost::shared_ptr<Region> region)
{
/* keep all whole files at the beginning */
if (region->whole_file()) {
tmp_audio_region_list.push_front (region);
tmp_region_list.push_front (region);
} else {
tmp_audio_region_list.push_back (region);
tmp_region_list.push_back (region);
}
}
@@ -265,13 +265,13 @@ Editor::redisplay_regions ()
sorting.
*/
tmp_audio_region_list.clear();
session->foreach_audio_region (this, &Editor::insert_into_tmp_audio_regionlist);
tmp_region_list.clear();
session->foreach_region (this, &Editor::insert_into_tmp_regionlist);
for (list<boost::shared_ptr<AudioRegion> >::iterator r = tmp_audio_region_list.begin(); r != tmp_audio_region_list.end(); ++r) {
add_audio_region_to_region_display (*r);
for (list<boost::shared_ptr<Region> >::iterator r = tmp_region_list.begin(); r != tmp_region_list.end(); ++r) {
add_region_to_region_display (*r);
}
tmp_audio_region_list.clear();
tmp_region_list.clear();
region_list_display.set_model (region_list_model);
}

View File

@@ -20,17 +20,20 @@
#include <algorithm>
#include <cstdlib>
#include <cmath>
#include <cassert>
#include "editor.h"
#include "keyboard.h"
#include "ardour_ui.h"
#include "audio_time_axis.h"
#include "midi_time_axis.h"
#include "mixer_strip.h"
#include "gui_thread.h"
#include "actions.h"
#include <pbd/unknown_type.h>
#include <ardour/route.h>
#include <ardour/audio_track.h>
#include "i18n.h"
@@ -39,13 +42,14 @@ using namespace ARDOUR;
using namespace PBD;
using namespace Gtk;
void
Editor::handle_new_route (Session::RouteList& routes)
{
ENSURE_GUI_THREAD(bind (mem_fun(*this, &Editor::handle_new_route), routes));
TimeAxisView *tv;
AudioTimeAxisView *atv;
RouteTimeAxisView *rtv;
TreeModel::Row parent;
TreeModel::Row row;
@@ -56,7 +60,12 @@ Editor::handle_new_route (Session::RouteList& routes)
continue;
}
tv = new AudioTimeAxisView (*this, *session, route, track_canvas);
if (route->default_type() == ARDOUR::DataType::AUDIO)
tv = new AudioTimeAxisView (*this, *session, route, track_canvas);
else if (route->default_type() == ARDOUR::DataType::MIDI)
tv = new MidiTimeAxisView (*this, *session, route, track_canvas);
else
throw unknown_type();
#if 0
if (route_display_model->children().size() == 0) {
@@ -96,10 +105,10 @@ Editor::handle_new_route (Session::RouteList& routes)
ignore_route_list_reorder = true;
if ((atv = dynamic_cast<AudioTimeAxisView*> (tv)) != 0) {
if ((rtv = dynamic_cast<RouteTimeAxisView*> (tv)) != 0) {
/* added a new fresh one at the end */
if (atv->route()->order_key(N_("editor")) == -1) {
atv->route()->set_order_key (N_("editor"), route_display_model->children().size()-1);
if (rtv->route()->order_key(N_("editor")) == -1) {
rtv->route()->set_order_key (N_("editor"), route_display_model->children().size()-1);
}
}
@@ -191,9 +200,9 @@ Editor::hide_track_in_display (TimeAxisView& tv)
}
}
AudioTimeAxisView* atv = dynamic_cast<AudioTimeAxisView*> (&tv);
RouteTimeAxisView* rtv = dynamic_cast<RouteTimeAxisView*> (&tv);
if (atv && current_mixer_strip && (atv->route() == current_mixer_strip->route())) {
if (rtv && current_mixer_strip && (rtv->route() == current_mixer_strip->route())) {
// this will hide the mixer strip
set_selected_mixer_strip (tv);
}
@@ -235,7 +244,7 @@ Editor::redisplay_route_list ()
for (n = 0, order = 0, position = 0, i = rows.begin(); i != rows.end(); ++i) {
TimeAxisView *tv = (*i)[route_display_columns.tv];
AudioTimeAxisView* at;
RouteTimeAxisView* rt;
if (tv == 0) {
// just a "title" row
@@ -248,8 +257,8 @@ Editor::redisplay_route_list ()
to tracks.
*/
if ((at = dynamic_cast<AudioTimeAxisView*> (tv)) != 0) {
at->route()->set_order_key (N_("editor"), order);
if ((rt = dynamic_cast<RouteTimeAxisView*> (tv)) != 0) {
rt->route()->set_order_key (N_("editor"), order);
++order;
}
}

View File

@@ -251,7 +251,7 @@ Editor::ruler_mouse_motion (GdkEventMotion* ev)
if (session == 0 || !ruler_pressed_button) {
return FALSE;
}
double wcx=0,wcy=0;
double cx=0,cy=0;
@@ -271,18 +271,20 @@ Editor::ruler_mouse_motion (GdkEventMotion* ev)
nframes_t one_page = (nframes_t) rint (canvas_width * frames_per_unit);
nframes_t rightmost_frame = leftmost_frame + one_page;
jack_nframes_t frame = pixel_to_frame (cx);
if (autoscroll_timeout_tag < 0) {
if (where > rightmost_frame) {
if (frame > rightmost_frame) {
if (rightmost_frame < max_frames) {
start_canvas_autoscroll (1);
}
} else if (where <= leftmost_frame) {
} else if (frame < leftmost_frame) {
if (leftmost_frame > 0) {
start_canvas_autoscroll (-1);
}
}
} else {
if (where >= leftmost_frame && where < rightmost_frame) {
if (frame >= leftmost_frame && frame < rightmost_frame) {
stop_canvas_autoscroll ();
}
}

View File

@@ -217,7 +217,7 @@ Editor::set_selected_track (TimeAxisView& view, Selection::Operation op, bool no
bool
Editor::set_selected_track_from_click (bool press, Selection::Operation op, bool no_remove)
{
if (!clicked_trackview) {
if (!clicked_routeview) {
return false;
}
@@ -225,7 +225,7 @@ Editor::set_selected_track_from_click (bool press, Selection::Operation op, bool
return false;
}
return set_selected_track (*clicked_trackview, op, no_remove);
return set_selected_track (*clicked_routeview, op, no_remove);
}
bool
@@ -249,19 +249,19 @@ Editor::set_selected_control_point_from_click (Selection::Operation op, bool no_
}
void
Editor::get_relevant_audio_tracks (set<AudioTimeAxisView*>& relevant_tracks)
Editor::get_relevant_tracks (set<RouteTimeAxisView*>& relevant_tracks)
{
/* step one: get all selected tracks and all tracks in the relevant edit groups */
for (TrackSelection::iterator ti = selection->tracks.begin(); ti != selection->tracks.end(); ++ti) {
AudioTimeAxisView* atv = dynamic_cast<AudioTimeAxisView*>(*ti);
RouteTimeAxisView* rtv = dynamic_cast<RouteTimeAxisView*>(*ti);
if (!atv) {
if (!rtv) {
continue;
}
RouteGroup* group = atv->route()->edit_group();
RouteGroup* group = rtv->route()->edit_group();
if (group && group->is_active()) {
@@ -269,32 +269,32 @@ Editor::get_relevant_audio_tracks (set<AudioTimeAxisView*>& relevant_tracks)
for (TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) {
AudioTimeAxisView* tatv;
RouteTimeAxisView* trtv;
if ((tatv = dynamic_cast<AudioTimeAxisView*> (*i)) != 0) {
if ((trtv = dynamic_cast<RouteTimeAxisView*> (*i)) != 0) {
if (tatv->route()->edit_group() == group) {
relevant_tracks.insert (tatv);
if (trtv->route()->edit_group() == group) {
relevant_tracks.insert (trtv);
}
}
}
} else {
relevant_tracks.insert (atv);
relevant_tracks.insert (rtv);
}
}
}
void
Editor::mapover_audio_tracks (slot<void,AudioTimeAxisView&,uint32_t> sl)
Editor::mapover_tracks (slot<void,RouteTimeAxisView&,uint32_t> sl)
{
set<AudioTimeAxisView*> relevant_tracks;
set<RouteTimeAxisView*> relevant_tracks;
get_relevant_audio_tracks (relevant_tracks);
get_relevant_tracks (relevant_tracks);
uint32_t sz = relevant_tracks.size();
for (set<AudioTimeAxisView*>::iterator ati = relevant_tracks.begin(); ati != relevant_tracks.end(); ++ati) {
sl (**ati, sz);
for (set<RouteTimeAxisView*>::iterator rti = relevant_tracks.begin(); rti != relevant_tracks.end(); ++rti) {
sl (**rti, sz);
}
}
@@ -330,7 +330,7 @@ Editor::mapped_get_equivalent_regions (RouteTimeAxisView& tv, uint32_t ignored,
void
Editor::get_equivalent_regions (RegionView* basis, vector<RegionView*>& equivalent_regions)
{
mapover_audio_tracks (bind (mem_fun (*this, &Editor::mapped_get_equivalent_regions), basis, &equivalent_regions));
mapover_tracks (bind (mem_fun (*this, &Editor::mapped_get_equivalent_regions), basis, &equivalent_regions));
/* add clicked regionview since we skipped all other regions in the same track as the one it was in */
@@ -343,7 +343,7 @@ Editor::set_selected_regionview_from_click (bool press, Selection::Operation op,
vector<RegionView*> all_equivalent_regions;
bool commit = false;
if (!clicked_regionview || !clicked_audio_trackview) {
if (!clicked_regionview || !clicked_routeview) {
return false;
}
@@ -387,7 +387,7 @@ Editor::set_selected_regionview_from_click (bool press, Selection::Operation op,
if (press) {
if (selection->selected (clicked_audio_trackview)) {
if (selection->selected (clicked_routeview)) {
get_equivalent_regions (clicked_regionview, all_equivalent_regions);
} else {
all_equivalent_regions.push_back (clicked_regionview);
@@ -409,7 +409,7 @@ Editor::set_selected_regionview_from_click (bool press, Selection::Operation op,
case Selection::Set:
if (!clicked_regionview->get_selected()) {
if (selection->selected (clicked_audio_trackview)) {
if (selection->selected (clicked_routeview)) {
get_equivalent_regions (clicked_regionview, all_equivalent_regions);
} else {
all_equivalent_regions.push_back (clicked_regionview);
@@ -497,11 +497,11 @@ Editor::set_selected_regionview_from_click (bool press, Selection::Operation op,
one that was clicked.
*/
set<AudioTimeAxisView*> relevant_tracks;
set<RouteTimeAxisView*> relevant_tracks;
get_relevant_audio_tracks (relevant_tracks);
get_relevant_tracks (relevant_tracks);
for (set<AudioTimeAxisView*>::iterator t = relevant_tracks.begin(); t != relevant_tracks.end(); ++t) {
for (set<RouteTimeAxisView*>::iterator t = relevant_tracks.begin(); t != relevant_tracks.end(); ++t) {
(*t)->get_selectables (first_frame, last_frame, -1.0, -1.0, results);
}
@@ -690,11 +690,11 @@ Editor::select_all_in_track (Selection::Operation op)
{
list<Selectable *> touched;
if (!clicked_trackview) {
if (!clicked_routeview) {
return;
}
clicked_trackview->get_selectables (0, max_frames, 0, DBL_MAX, touched);
clicked_routeview->get_selectables (0, max_frames, 0, DBL_MAX, touched);
switch (op) {
case Selection::Toggle:
@@ -746,11 +746,11 @@ Editor::invert_selection_in_track ()
{
list<Selectable *> touched;
if (!clicked_trackview) {
if (!clicked_routeview) {
return;
}
clicked_trackview->get_inverted_selectables (*selection, touched);
clicked_routeview->get_inverted_selectables (*selection, touched);
selection->set (touched);
}

View File

@@ -180,10 +180,10 @@ Editor::hide_measures ()
ArdourCanvas::SimpleLine *
Editor::get_time_line ()
{
ArdourCanvas::SimpleLine *line;
ArdourCanvas::SimpleLine *line;
if (free_measure_lines.empty()) {
line = new ArdourCanvas::SimpleLine (*time_line_group);
line = new ArdourCanvas::SimpleLine (*time_line_group);
used_measure_lines.push_back (line);
} else {
line = free_measure_lines.front();
@@ -214,8 +214,8 @@ Editor::draw_measures ()
gdouble xpos;
double x1, x2, y1, y2, beat_density;
uint32_t beats = 0;
uint32_t bars = 0;
uint32_t beats = 0;
uint32_t bars = 0;
uint32_t color;
if (current_bbt_points == 0 || current_bbt_points->empty()) {
@@ -239,7 +239,7 @@ Editor::draw_measures ()
*/
return;
}
for (i = current_bbt_points->begin(); i != current_bbt_points->end(); ++i) {
switch ((*i).type) {

View File

@@ -55,6 +55,8 @@ using namespace sigc;
using namespace Gtk;
using namespace Gtkmm2ext;
using PBD::internationalize;
static const gchar *sample_rates[] = {
N_("22.05kHz"),
N_("44.1kHz"),
@@ -214,28 +216,28 @@ ExportDialog::ExportDialog(PublicEditor& e)
takes a reference.
*/
vector<string> pop_strings = I18N (sample_rates);
vector<string> pop_strings = I18N(sample_rates);
Gtkmm2ext::set_popdown_strings (sample_rate_combo, pop_strings);
sample_rate_combo.set_active_text (pop_strings.front());
pop_strings = I18N (src_quality);
pop_strings = I18N(src_quality);
Gtkmm2ext::set_popdown_strings (src_quality_combo, pop_strings);
src_quality_combo.set_active_text (pop_strings.front());
pop_strings = I18N (dither_types);
pop_strings = I18N(dither_types);
Gtkmm2ext::set_popdown_strings (dither_type_combo, pop_strings);
dither_type_combo.set_active_text (pop_strings.front());
pop_strings = I18N (channel_strings);
pop_strings = I18N(channel_strings);
Gtkmm2ext::set_popdown_strings (channel_count_combo, pop_strings);
channel_count_combo.set_active_text (pop_strings.front());
pop_strings = I18N ((const char **) sndfile_header_formats_strings);
pop_strings = I18N((const char **) sndfile_header_formats_strings);
Gtkmm2ext::set_popdown_strings (header_format_combo, pop_strings);
header_format_combo.set_active_text (pop_strings.front());
pop_strings = I18N ((const char **) sndfile_bitdepth_formats_strings);
pop_strings = I18N((const char **) sndfile_bitdepth_formats_strings);
Gtkmm2ext::set_popdown_strings (bitdepth_format_combo, pop_strings);
bitdepth_format_combo.set_active_text (pop_strings.front());
pop_strings = I18N ((const char **) sndfile_endian_formats_strings);
pop_strings = I18N((const char **) sndfile_endian_formats_strings);
Gtkmm2ext::set_popdown_strings (endian_format_combo, pop_strings);
endian_format_combo.set_active_text (pop_strings.front());
pop_strings = I18N (cue_file_types);
pop_strings = I18N(cue_file_types);
Gtkmm2ext::set_popdown_strings (cue_file_combo, pop_strings);
cue_file_combo.set_active_text (pop_strings.front());
@@ -492,7 +494,7 @@ ExportDialog::set_state()
}
TreeModel::Children rows = master_selector.get_model()->children();
for (uint32_t r = 0; r < session->master_out()->n_outputs(); ++r) {
for (uint32_t r = 0; r < session->master_out()->n_outputs().get(DataType::AUDIO); ++r) {
if (nchns == 2) {
if (r % 2) {
rows[r][exp_cols.right] = true;
@@ -1094,9 +1096,9 @@ ExportDialog::fill_lists ()
continue;
}
for (uint32_t i=0; i < route->n_outputs(); ++i) {
for (uint32_t i=0; i < route->n_outputs().get(DataType::AUDIO); ++i) {
string name;
if (route->n_outputs() == 1) {
if (route->n_outputs().get(DataType::AUDIO) == 1) {
name = route->name();
} else {
name = string_compose("%1: out-%2", route->name(), i+1);

View File

@@ -43,6 +43,7 @@
#include <ardour/session.h>
#include <ardour/route.h>
#include <ardour/meter.h>
#include "i18n.h"
@@ -137,9 +138,12 @@ GainMeter::GainMeter (boost::shared_ptr<IO> io, Session& s)
fader_vbox->pack_start (*fader_centering_box, false, false, 0);
hbox.set_spacing (2);
hbox.pack_start (*fader_vbox, true, true);
set_width(Narrow);
if (_io->default_type() == ARDOUR::DataType::AUDIO) {
hbox.pack_start (*fader_vbox, true, true);
}
set_width (Narrow);
Route* r;
@@ -317,11 +321,11 @@ GainMeter::update_meters ()
for (n = 0, i = meters.begin(); i != meters.end(); ++i, ++n) {
if ((*i).packed) {
peak = _io->peak_input_power (n);
peak = _io->peak_meter().peak_power (n);
(*i).meter->set (log_meter (peak));
mpeak = _io->max_peak_power(n);
mpeak = _io->peak_meter().max_peak_power(n);
if (mpeak > max_peak) {
max_peak = mpeak;
@@ -385,7 +389,7 @@ GainMeter::hide_all_meters ()
void
GainMeter::setup_meters ()
{
uint32_t nmeters = _io->n_outputs();
uint32_t nmeters = _io->n_outputs().get(DataType::AUDIO);
guint16 width;
hide_all_meters ();
@@ -397,16 +401,16 @@ GainMeter::setup_meters ()
switch (r->meter_point()) {
case MeterPreFader:
case MeterInput:
nmeters = r->n_inputs();
nmeters = r->n_inputs().get(DataType::AUDIO);
break;
case MeterPostFader:
nmeters = r->n_outputs();
nmeters = r->n_outputs().get(DataType::AUDIO);
break;
}
} else {
nmeters = _io->n_outputs();
nmeters = _io->n_outputs().get(DataType::AUDIO);
}
@@ -489,7 +493,7 @@ GainMeter::reset_peak_display ()
{
Route * r;
if ((r = dynamic_cast<Route*> (_io.get())) != 0) {
r->reset_max_peak_meters();
r->peak_meter().reset_max();
}
max_peak = -INFINITY;

View File

@@ -183,7 +183,43 @@ IOSelector::IOSelector (Session& sess, boost::shared_ptr<IO> ior, bool input)
port_button_box.set_border_width (5);
port_button_box.pack_start (add_port_button, false, false);
// The IO selector only works for single typed IOs
const ARDOUR::DataType t = io->default_type();
if (for_input) {
if (io->input_maximum().get(t) < 0 || io->input_maximum().get(t) > (size_t) io->n_inputs().get(t)) {
add_port_button.set_sensitive (true);
} else {
add_port_button.set_sensitive (false);
}
} else {
if (io->output_maximum().get(t) < 0 || io->output_maximum().get(t) > (size_t) io->n_outputs().get(t)) {
add_port_button.set_sensitive (true);
} else {
add_port_button.set_sensitive (false);
}
}
port_button_box.pack_start (remove_port_button, false, false);
if (for_input) {
if (io->input_minimum().get(t) < 0 || io->input_minimum().get(t) < (size_t) io->n_inputs().get(t)) {
remove_port_button.set_sensitive (true);
} else {
remove_port_button.set_sensitive (false);
}
} else {
if (io->output_minimum().get(t) < 0 || io->output_minimum().get(t) < (size_t) io->n_outputs().get(t)) {
remove_port_button.set_sensitive (true);
} else {
remove_port_button.set_sensitive (false);
}
}
port_button_box.pack_start (clear_connections_button, false, false);
port_and_button_box.set_border_width (5);
@@ -224,9 +260,11 @@ IOSelector::~IOSelector ()
void
IOSelector::set_button_sensitivity ()
{
DataType t = io->default_type();
if (for_input) {
if (io->input_maximum() < 0 || io->input_maximum() > (int) io->n_inputs()) {
if (io->input_maximum().get(t) < 0 || io->input_maximum().get(t) > io->n_inputs().get(t)) {
add_port_button.set_sensitive (true);
} else {
add_port_button.set_sensitive (false);
@@ -234,7 +272,7 @@ IOSelector::set_button_sensitivity ()
} else {
if (io->output_maximum() < 0 || io->output_maximum() > (int) io->n_outputs()) {
if (io->output_maximum().get(t) < 0 || io->output_maximum().get(t) > io->n_outputs().get(t)) {
add_port_button.set_sensitive (true);
} else {
add_port_button.set_sensitive (false);
@@ -243,14 +281,14 @@ IOSelector::set_button_sensitivity ()
}
if (for_input) {
if (io->n_inputs() && (io->input_minimum() < 0 || io->input_minimum() < (int) io->n_inputs())) {
if (io->n_inputs().get(t) && (io->input_minimum().get(t) < 0 || io->input_minimum().get(t) < io->n_inputs().get(t))) {
remove_port_button.set_sensitive (true);
} else {
remove_port_button.set_sensitive (false);
}
} else {
if (io->n_outputs() && (io->output_minimum() < 0 || io->output_minimum() < (int) io->n_outputs())) {
if (io->n_outputs().get(t) && (io->output_minimum().get(t) < 0 || io->output_minimum().get(t) < io->n_outputs().get(t))) {
remove_port_button.set_sensitive (true);
} else {
remove_port_button.set_sensitive (false);
@@ -380,10 +418,13 @@ IOSelector::display_ports ()
Port *port;
uint32_t limit;
// The IO selector only works for single typed IOs
const ARDOUR::DataType t = io->default_type();
if (for_input) {
limit = io->n_inputs();
limit = io->n_inputs().get(t);
} else {
limit = io->n_outputs();
limit = io->n_outputs().get(t);
}
for (slist<TreeView *>::iterator i = port_displays.begin(); i != port_displays.end(); ) {
@@ -448,7 +489,7 @@ IOSelector::display_ports ()
if (for_input) {
if (io->input_maximum() == 1) {
if (io->input_maximum().get(io->default_type()) == 1) {
selected_port = port;
selected_port_tview = tview;
} else {
@@ -459,7 +500,7 @@ IOSelector::display_ports ()
} else {
if (io->output_maximum() == 1) {
if (io->output_maximum().get(t) == 1) {
selected_port = port;
selected_port_tview = tview;
} else {
@@ -511,7 +552,9 @@ IOSelector::port_selection_changed (GdkEventButton *ev, TreeView* treeview)
if (for_input) {
if ((status = io->connect_input (selected_port, other_port_name, this)) == 0) {
Port *p = session.engine().get_port_by_name (other_port_name);
p->enable_metering();
if (p) {
p->enable_metering();
}
}
} else {
status = io->connect_output (selected_port, other_port_name, this);
@@ -538,6 +581,9 @@ IOSelector::add_port ()
{
/* add a new port, then hide the button if we're up to the maximum allowed */
// The IO selector only works for single typed IOs
const ARDOUR::DataType t = io->default_type();
if (for_input) {
try {
@@ -569,15 +615,17 @@ IOSelector::remove_port ()
{
uint32_t nports;
// The IO selector only works for single typed IOs
const ARDOUR::DataType t = io->default_type();
// always remove last port
if (for_input) {
if ((nports = io->n_inputs()) > 0) {
if ((nports = io->n_inputs().get(t)) > 0) {
io->remove_input_port (io->input(nports-1), this);
}
} else {
if ((nports = io->n_outputs()) > 0) {
if ((nports = io->n_outputs().get(t)) > 0) {
io->remove_output_port (io->output(nports-1), this);
}
}
@@ -616,7 +664,9 @@ IOSelector::connection_button_release (GdkEventButton *ev, TreeView *treeview)
if (for_input) {
Port *p = session.engine().get_port_by_name (connected_port_name);
p->disable_metering();
if (p) {
p->disable_metering();
}
io->disconnect_input (port, connected_port_name, this);
} else {
io->disconnect_output (port, connected_port_name, this);
@@ -704,11 +754,11 @@ IOSelector::redisplay ()
display_ports ();
if (for_input) {
if (io->input_maximum() != 0) {
if (io->input_maximum().get(io->default_type()) != 0) {
rescan ();
}
} else {
if (io->output_maximum() != 0) {
if (io->output_maximum().get(io->default_type()) != 0) {
rescan();
}
}

View File

@@ -129,7 +129,6 @@ LadspaPluginUI::build ()
int button_row, button_col;
int output_rows, output_cols;
int button_rows, button_cols;
guint32 n_ins=0, n_outs = 0;
prefheight = 30;
hpacker.set_spacing (10);
@@ -264,9 +263,6 @@ LadspaPluginUI::build ()
}
}
n_ins = plugin->get_info()->n_inputs;
n_outs = plugin->get_info()->n_outputs;
if (box->children().empty()) {
hpacker.remove (*frame);
}
@@ -758,3 +754,4 @@ LadspaPluginUI::setup_scale_values(guint32 port_index, ControlUI* cui)
return enums;
}

View File

@@ -191,7 +191,7 @@ int main (int argc, char *argv[])
#endif
{
ARDOUR::AudioEngine *engine;
ARDOUR::AudioEngine *engine = NULL;
vector<Glib::ustring> null_file_list;
Glib::thread_init();
@@ -251,7 +251,7 @@ int main (int argc, char *argv[])
PBD::ID::init ();
try {
try {
ui = new ARDOUR_UI (&argc, &argv, which_ui_rcfile());
} catch (failed_constructor& err) {
error << _("could not create ARDOUR GUI") << endmsg;
@@ -269,7 +269,7 @@ int main (int argc, char *argv[])
}
}
try {
try {
ARDOUR::init (use_vst, try_hw_optimization);
setup_gtk_ardour_enums ();
Config->set_current_owner (ConfigVariableBase::Interface);
@@ -282,6 +282,8 @@ int main (int argc, char *argv[])
error << string_compose (_("Could not connect to JACK server as \"%1\""), jack_client_name) << endmsg;
return -1;
}
ARDOUR::setup_midi(*engine);
ui->set_engine (*engine);

View File

@@ -0,0 +1,115 @@
/*
Copyright (C) 2001-2006 Paul Davis
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.
*/
#include <cmath>
#include <cassert>
#include <algorithm>
#include <gtkmm.h>
#include <gtkmm2ext/gtk_ui.h>
#include <ardour/playlist.h>
#include <ardour/midi_region.h>
#include <ardour/midi_source.h>
#include <ardour/midi_diskstream.h>
#include "streamview.h"
#include "midi_region_view.h"
#include "midi_time_axis.h"
#include "simplerect.h"
#include "simpleline.h"
#include "public_editor.h"
//#include "midi_region_editor.h"
#include "ghostregion.h"
#include "midi_time_axis.h"
#include "utils.h"
#include "rgb_macros.h"
#include "gui_thread.h"
#include "i18n.h"
using namespace sigc;
using namespace ARDOUR;
using namespace PBD;
using namespace Editing;
using namespace ArdourCanvas;
MidiRegionView::MidiRegionView (ArdourCanvas::Group *parent, RouteTimeAxisView &tv, boost::shared_ptr<MidiRegion> r, double spu,
Gdk::Color& basic_color)
: RegionView (parent, tv, r, spu, basic_color)
{
}
MidiRegionView::MidiRegionView (ArdourCanvas::Group *parent, RouteTimeAxisView &tv, boost::shared_ptr<MidiRegion> r, double spu,
Gdk::Color& basic_color, TimeAxisViewItem::Visibility visibility)
: RegionView (parent, tv, r, spu, basic_color, visibility)
{
}
void
MidiRegionView::init (Gdk::Color& basic_color, bool wfd)
{
// FIXME: Some redundancy here with RegionView::init. Need to figure out
// where order is important and where it isn't...
// FIXME
RegionView::init(basic_color, /*wfd*/false);
compute_colors (basic_color);
reset_width_dependent_items ((double) _region->length() / samples_per_unit);
set_height (trackview.height);
region_muted ();
region_resized (BoundsChanged);
region_locked ();
_region->StateChanged.connect (mem_fun(*this, &MidiRegionView::region_changed));
set_colors ();
}
MidiRegionView::~MidiRegionView ()
{
in_destructor = true;
RegionViewGoingAway (this); /* EMIT_SIGNAL */
}
boost::shared_ptr<ARDOUR::MidiRegion>
MidiRegionView::midi_region() const
{
// "Guaranteed" to succeed...
return boost::dynamic_pointer_cast<MidiRegion>(_region);
}
void
MidiRegionView::show_region_editor ()
{
cerr << "No MIDI region editor." << endl;
}
GhostRegion*
MidiRegionView::add_ghost (AutomationTimeAxisView& atv)
{
throw; // FIXME
return NULL;
}

View File

@@ -0,0 +1,84 @@
/*
Copyright (C) 2001-2006 Paul Davis
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 __gtk_ardour_midi_region_view_h__
#define __gtk_ardour_midi_region_view_h__
#include <vector>
#include <libgnomecanvasmm.h>
#include <libgnomecanvasmm/polygon.h>
#include <sigc++/signal.h>
#include <ardour/midi_region.h>
#include "region_view.h"
#include "route_time_axis.h"
#include "time_axis_view_item.h"
#include "automation_line.h"
#include "enums.h"
#include "canvas.h"
#include "color.h"
namespace ARDOUR {
class MidiRegion;
};
class MidiTimeAxisView;
class GhostRegion;
class AutomationTimeAxisView;
class MidiRegionView : public RegionView
{
public:
MidiRegionView (ArdourCanvas::Group *,
RouteTimeAxisView&,
boost::shared_ptr<ARDOUR::MidiRegion>,
double initial_samples_per_unit,
Gdk::Color& basic_color);
~MidiRegionView ();
virtual void init (Gdk::Color& base_color, bool wait_for_data = false);
boost::shared_ptr<ARDOUR::MidiRegion> midi_region() const;
void show_region_editor ();
GhostRegion* add_ghost (AutomationTimeAxisView&);
protected:
/* this constructor allows derived types
to specify their visibility requirements
to the TimeAxisViewItem parent class
*/
MidiRegionView (ArdourCanvas::Group *,
RouteTimeAxisView&,
boost::shared_ptr<ARDOUR::MidiRegion>,
double samples_per_unit,
Gdk::Color& basic_color,
TimeAxisViewItem::Visibility);
void region_moved (void *);
void set_flags (XMLNode *);
void store_flags ();
};
#endif /* __gtk_ardour_midi_region_view_h__ */

View File

@@ -0,0 +1,408 @@
/*
Copyright (C) 2001, 2006 Paul Davis
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.
*/
#include <cmath>
#include <cassert>
#include <gtkmm.h>
#include <gtkmm2ext/gtk_ui.h>
#include <ardour/midi_playlist.h>
#include <ardour/midi_region.h>
#include <ardour/midi_source.h>
#include <ardour/midi_diskstream.h>
#include <ardour/midi_track.h>
#include <ardour/smf_source.h>
#include <ardour/region_factory.h>
#include "midi_streamview.h"
#include "region_view.h"
#include "midi_region_view.h"
#include "midi_time_axis.h"
#include "canvas-simplerect.h"
#include "region_selection.h"
#include "selection.h"
#include "public_editor.h"
#include "ardour_ui.h"
#include "rgb_macros.h"
#include "gui_thread.h"
#include "utils.h"
#include "color.h"
using namespace ARDOUR;
using namespace PBD;
using namespace Editing;
MidiStreamView::MidiStreamView (MidiTimeAxisView& tv)
: StreamView (tv)
{
if (tv.is_track())
stream_base_color = color_map[cMidiTrackBase];
else
stream_base_color = color_map[cMidiBusBase];
canvas_rect->property_fill_color_rgba() = stream_base_color;
canvas_rect->property_outline_color_rgba() = color_map[cAudioTrackOutline];
//use_rec_regions = tv.editor.show_waveforms_recording ();
use_rec_regions = true;
}
MidiStreamView::~MidiStreamView ()
{
}
void
MidiStreamView::add_region_view_internal (boost::shared_ptr<Region> r, bool wait_for_waves)
{
ENSURE_GUI_THREAD (bind (mem_fun (*this, &MidiStreamView::add_region_view), r));
boost::shared_ptr<MidiRegion> region = boost::dynamic_pointer_cast<MidiRegion> (r);
if (region == 0) {
return;
}
MidiRegionView *region_view;
list<RegionView *>::iterator i;
for (i = region_views.begin(); i != region_views.end(); ++i) {
if ((*i)->region() == r) {
/* great. we already have a MidiRegionView for this Region. use it again. */
(*i)->set_valid (true);
return;
}
}
// can't we all just get along?
assert(_trackview.midi_track()->mode() != Destructive);
region_view = new MidiRegionView (canvas_group, _trackview, region,
_samples_per_unit, region_color);
region_view->init (region_color, wait_for_waves);
region_views.push_front (region_view);
/* follow global waveform setting */
// FIXME
//region_view->set_waveform_visible(_trackview.editor.show_waveforms());
/* catch regionview going away */
region->GoingAway.connect (bind (mem_fun (*this, &MidiStreamView::remove_region_view), region));
RegionViewAdded (region_view);
}
// FIXME: code duplication with AudioStreamVIew
void
MidiStreamView::redisplay_diskstream ()
{
list<RegionView *>::iterator i, tmp;
for (i = region_views.begin(); i != region_views.end(); ++i) {
(*i)->set_valid (false);
}
if (_trackview.is_midi_track()) {
_trackview.get_diskstream()->playlist()->foreach_region (static_cast<StreamView*>(this), &StreamView::add_region_view);
}
for (i = region_views.begin(); i != region_views.end(); ) {
tmp = i;
tmp++;
if (!(*i)->is_valid()) {
delete *i;
region_views.erase (i);
}
i = tmp;
}
/* now fix layering */
for (RegionViewList::iterator i = region_views.begin(); i != region_views.end(); ++i) {
region_layered (*i);
}
}
void
MidiStreamView::setup_rec_box ()
{
// cerr << _trackview.name() << " streamview SRB\n";
if (_trackview.session().transport_rolling()) {
if (!rec_active &&
_trackview.session().record_status() == Session::Recording &&
_trackview.get_diskstream()->record_enabled()) {
if (use_rec_regions && rec_regions.size() == rec_rects.size()) {
/* add a new region, but don't bother if they set use_rec_regions mid-record */
MidiRegion::SourceList sources;
// FIXME
boost::shared_ptr<MidiDiskstream> mds = boost::dynamic_pointer_cast<MidiDiskstream>(_trackview.get_diskstream());
assert(mds);
sources.push_back(mds->write_source());
rec_data_ready_connections.push_back (mds->write_source()->ViewDataRangeReady.connect (bind (mem_fun (*this, &MidiStreamView::rec_data_range_ready), mds->write_source())));
// handle multi
jack_nframes_t start = 0;
if (rec_regions.size() > 0) {
start = rec_regions.back()->start() + _trackview.get_diskstream()->get_captured_frames(rec_regions.size()-1);
}
boost::shared_ptr<MidiRegion> region (boost::dynamic_pointer_cast<MidiRegion>
(RegionFactory::create (sources, start, 1 , "", 0, (Region::Flag)(Region::DefaultFlags | Region::DoNotSaveState), false)));
assert(region);
region->set_position (_trackview.session().transport_frame(), this);
rec_regions.push_back (region);
// rec regions are destroyed in setup_rec_box
/* we add the region later */
}
/* start a new rec box */
MidiTrack* mt = _trackview.midi_track(); /* we know what it is already */
boost::shared_ptr<MidiDiskstream> ds = mt->midi_diskstream();
jack_nframes_t frame_pos = ds->current_capture_start ();
gdouble xstart = _trackview.editor.frame_to_pixel (frame_pos);
gdouble xend;
uint32_t fill_color;
assert(_trackview.midi_track()->mode() == Normal);
xend = xstart;
fill_color = color_map[cRecordingRectFill];
ArdourCanvas::SimpleRect * rec_rect = new Gnome::Canvas::SimpleRect (*canvas_group);
rec_rect->property_x1() = xstart;
rec_rect->property_y1() = 1.0;
rec_rect->property_x2() = xend;
rec_rect->property_y2() = (double) _trackview.height - 1;
rec_rect->property_outline_color_rgba() = color_map[cRecordingRectOutline];
rec_rect->property_fill_color_rgba() = fill_color;
RecBoxInfo recbox;
recbox.rectangle = rec_rect;
recbox.start = _trackview.session().transport_frame();
recbox.length = 0;
rec_rects.push_back (recbox);
screen_update_connection.disconnect();
screen_update_connection = ARDOUR_UI::instance()->SuperRapidScreenUpdate.connect (mem_fun (*this, &MidiStreamView::update_rec_box));
rec_updating = true;
rec_active = true;
} else if (rec_active &&
(_trackview.session().record_status() != Session::Recording ||
!_trackview.get_diskstream()->record_enabled())) {
screen_update_connection.disconnect();
rec_active = false;
rec_updating = false;
}
} else {
// cerr << "\tNOT rolling, rec_rects = " << rec_rects.size() << " rec_regions = " << rec_regions.size() << endl;
if (!rec_rects.empty() || !rec_regions.empty()) {
/* disconnect rapid update */
screen_update_connection.disconnect();
for (list<sigc::connection>::iterator prc = rec_data_ready_connections.begin(); prc != rec_data_ready_connections.end(); ++prc) {
(*prc).disconnect();
}
rec_data_ready_connections.clear();
rec_updating = false;
rec_active = false;
last_rec_data_frame = 0;
/* remove temp regions */
for (list<boost::shared_ptr<Region> >::iterator iter = rec_regions.begin(); iter != rec_regions.end();) {
list<boost::shared_ptr<Region> >::iterator tmp;
tmp = iter;
++tmp;
(*iter)->drop_references ();
iter = tmp;
}
rec_regions.clear();
// cerr << "\tclear " << rec_rects.size() << " rec rects\n";
/* transport stopped, clear boxes */
for (vector<RecBoxInfo>::iterator iter=rec_rects.begin(); iter != rec_rects.end(); ++iter) {
RecBoxInfo &rect = (*iter);
delete rect.rectangle;
}
rec_rects.clear();
}
}
}
void
MidiStreamView::update_rec_regions ()
{
if (use_rec_regions) {
uint32_t n = 0;
for (list<boost::shared_ptr<Region> >::iterator iter = rec_regions.begin(); iter != rec_regions.end(); n++) {
list<boost::shared_ptr<Region> >::iterator tmp;
tmp = iter;
++tmp;
if (!canvas_item_visible (rec_rects[n].rectangle)) {
/* rect already hidden, this region is done */
iter = tmp;
continue;
}
boost::shared_ptr<MidiRegion> region = boost::dynamic_pointer_cast<MidiRegion>(*iter);
assert(region);
jack_nframes_t origlen = region->length();
if (region == rec_regions.back() && rec_active) {
if (last_rec_data_frame > region->start()) {
jack_nframes_t nlen = last_rec_data_frame - region->start();
if (nlen != region->length()) {
region->freeze ();
region->set_position (_trackview.get_diskstream()->get_capture_start_frame(n), this);
region->set_length (nlen, this);
region->thaw ("updated");
if (origlen == 1) {
/* our special initial length */
add_region_view_internal (region, false);
}
/* also update rect */
ArdourCanvas::SimpleRect * rect = rec_rects[n].rectangle;
gdouble xend = _trackview.editor.frame_to_pixel (region->position() + region->length());
rect->property_x2() = xend;
}
}
} else {
jack_nframes_t nlen = _trackview.get_diskstream()->get_captured_frames(n);
if (nlen != region->length()) {
if (region->source(0)->length() >= region->start() + nlen) {
region->freeze ();
region->set_position (_trackview.get_diskstream()->get_capture_start_frame(n), this);
region->set_length (nlen, this);
region->thaw ("updated");
if (origlen == 1) {
/* our special initial length */
add_region_view_internal (region, false);
}
/* also hide rect */
ArdourCanvas::Item * rect = rec_rects[n].rectangle;
rect->hide();
}
}
}
iter = tmp;
}
}
}
void
MidiStreamView::rec_data_range_ready (jack_nframes_t start, jack_nframes_t cnt, boost::shared_ptr<Source> src)
{
// this is called from the butler thread for now
// yeah we need a "peak" building thread or something, though there's not really any
// work for it to do... whatever. :)
ENSURE_GUI_THREAD(bind (mem_fun (*this, &MidiStreamView::rec_data_range_ready), start, cnt, src));
//cerr << "REC DATA: " << start << " --- " << cnt << endl;
if (rec_data_ready_map.size() == 0 || start+cnt > last_rec_data_frame) {
last_rec_data_frame = start + cnt;
}
rec_data_ready_map[src] = true;
if (rec_data_ready_map.size() == _trackview.get_diskstream()->n_channels().get(DataType::MIDI)) {
this->update_rec_regions ();
rec_data_ready_map.clear();
}
}
void
MidiStreamView::color_handler (ColorID id, uint32_t val)
{
switch (id) {
case cMidiTrackBase:
if (_trackview.is_midi_track()) {
canvas_rect->property_fill_color_rgba() = val;
}
break;
case cMidiBusBase:
if (!_trackview.is_midi_track()) {
canvas_rect->property_fill_color_rgba() = val;
}
break;
case cMidiTrackOutline:
canvas_rect->property_outline_color_rgba() = val;
break;
default:
break;
}
}

View File

@@ -0,0 +1,75 @@
/*
Copyright (C) 2001, 2006 Paul Davis
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 __ardour_midi_streamview_h__
#define __ardour_midi_streamview_h__
#include <list>
#include <map>
#include <cmath>
#include <ardour/location.h>
#include "enums.h"
#include "simplerect.h"
#include "color.h"
#include "streamview.h"
namespace Gdk {
class Color;
}
namespace ARDOUR {
class Route;
class Diskstream;
class Crossfade;
class PeakData;
class MidiRegion;
class Source;
}
class PublicEditor;
class Selectable;
class MidiTimeAxisView;
class MidiRegionView;
class RegionSelection;
class CrossfadeView;
class Selection;
class MidiStreamView : public StreamView
{
public:
MidiStreamView (MidiTimeAxisView&);
~MidiStreamView ();
void set_selected_regionviews (RegionSelection&);
void get_selectables (jack_nframes_t start, jack_nframes_t end, list<Selectable* >&);
void get_inverted_selectables (Selection&, list<Selectable* >& results);
private:
void setup_rec_box ();
void rec_data_range_ready (jack_nframes_t start, jack_nframes_t cnt, boost::shared_ptr<ARDOUR::Source> src);
void update_rec_regions ();
void add_region_view_internal (boost::shared_ptr<ARDOUR::Region>, bool wait_for_waves);
void redisplay_diskstream ();
void color_handler (ColorID id, uint32_t val);
};
#endif /* __ardour_midi_streamview_h__ */

View File

@@ -0,0 +1,233 @@
/*
Copyright (C) 2000 Paul Davis
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.
*/
#include <cstdlib>
#include <cmath>
#include <algorithm>
#include <string>
#include <vector>
#include <sigc++/bind.h>
#include <pbd/error.h>
#include <pbd/stl_delete.h>
#include <pbd/whitespace.h>
#include <gtkmm2ext/gtk_ui.h>
#include <gtkmm2ext/selector.h>
#include <gtkmm2ext/stop_signal.h>
#include <gtkmm2ext/bindable_button.h>
#include <gtkmm2ext/utils.h>
#include <ardour/midi_playlist.h>
#include <ardour/midi_diskstream.h>
#include <ardour/insert.h>
#include <ardour/ladspa_plugin.h>
#include <ardour/location.h>
#include <ardour/playlist.h>
#include <ardour/session.h>
#include <ardour/session_playlist.h>
#include <ardour/utils.h>
#include "ardour_ui.h"
#include "midi_time_axis.h"
#include "automation_time_axis.h"
#include "canvas_impl.h"
#include "crossfade_view.h"
#include "enums.h"
#include "gui_thread.h"
#include "keyboard.h"
#include "playlist_selector.h"
#include "plugin_selector.h"
#include "plugin_ui.h"
#include "point_selection.h"
#include "prompter.h"
#include "public_editor.h"
#include "redirect_automation_line.h"
#include "redirect_automation_time_axis.h"
#include "region_view.h"
#include "rgb_macros.h"
#include "selection.h"
#include "simplerect.h"
#include "midi_streamview.h"
#include "utils.h"
#include <ardour/midi_track.h>
#include "i18n.h"
using namespace ARDOUR;
using namespace PBD;
using namespace Gtk;
using namespace Editing;
MidiTimeAxisView::MidiTimeAxisView (PublicEditor& ed, Session& sess, boost::shared_ptr<Route> rt, Canvas& canvas)
: AxisView(sess), // FIXME: won't compile without this, why??
RouteTimeAxisView(ed, sess, rt, canvas)
{
subplugin_menu.set_name ("ArdourContextMenu");
_view = new MidiStreamView (*this);
ignore_toggle = false;
mute_button->set_active (false);
solo_button->set_active (false);
if (is_midi_track())
controls_ebox.set_name ("MidiTimeAxisViewControlsBaseUnselected");
else // bus
controls_ebox.set_name ("MidiBusControlsBaseUnselected");
/* map current state of the route */
redirects_changed (0);
ensure_xml_node ();
set_state (*xml_node);
_route->redirects_changed.connect (mem_fun(*this, &MidiTimeAxisView::redirects_changed));
if (is_track()) {
controls_ebox.set_name ("MidiTrackControlsBaseUnselected");
controls_base_selected_name = "MidiTrackControlsBaseSelected";
controls_base_unselected_name = "MidiTrackControlsBaseUnselected";
/* ask for notifications of any new RegionViews */
_view->RegionViewAdded.connect (mem_fun(*this, &MidiTimeAxisView::region_view_added));
_view->attach ();
} else { /* bus */
throw; // what the?
controls_ebox.set_name ("MidiBusControlsBaseUnselected");
controls_base_selected_name = "MidiBusControlsBaseSelected";
controls_base_unselected_name = "MidiBusControlsBaseUnselected";
}
}
MidiTimeAxisView::~MidiTimeAxisView ()
{
}
guint32
MidiTimeAxisView::show_at (double y, int& nth, Gtk::VBox *parent)
{
ensure_xml_node ();
xml_node->add_property ("shown_editor", "yes");
return TimeAxisView::show_at (y, nth, parent);
}
void
MidiTimeAxisView::hide ()
{
ensure_xml_node ();
xml_node->add_property ("shown_editor", "no");
TimeAxisView::hide ();
}
void
MidiTimeAxisView::set_state (const XMLNode& node)
{
const XMLProperty *prop;
TimeAxisView::set_state (node);
if ((prop = node.property ("shown_editor")) != 0) {
if (prop->value() == "no") {
_marked_for_display = false;
} else {
_marked_for_display = true;
}
} else {
_marked_for_display = true;
}
XMLNodeList nlist = node.children();
XMLNodeConstIterator niter;
XMLNode *child_node;
for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
child_node = *niter;
// uh... do stuff..
}
}
// FIXME: duplicated in audio_time_axis.cc
/*static string
legalize_for_xml_node (string str)
{
string::size_type pos;
string legal_chars = "abcdefghijklmnopqrtsuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_+=:";
string legal;
legal = str;
pos = 0;
while ((pos = legal.find_first_not_of (legal_chars, pos)) != string::npos) {
legal.replace (pos, 1, "_");
pos += 1;
}
return legal;
}*/
void
MidiTimeAxisView::route_active_changed ()
{
RouteUI::route_active_changed ();
if (is_track()) {
if (_route->active()) {
controls_ebox.set_name ("MidiTrackControlsBaseUnselected");
controls_base_selected_name = "MidiTrackControlsBaseSelected";
controls_base_unselected_name = "MidiTrackControlsBaseUnselected";
} else {
controls_ebox.set_name ("MidiTrackControlsBaseInactiveUnselected");
controls_base_selected_name = "MidiTrackControlsBaseInactiveSelected";
controls_base_unselected_name = "MidiTrackControlsBaseInactiveUnselected";
}
} else {
throw; // wha?
if (_route->active()) {
controls_ebox.set_name ("BusControlsBaseUnselected");
controls_base_selected_name = "BusControlsBaseSelected";
controls_base_unselected_name = "BusControlsBaseUnselected";
} else {
controls_ebox.set_name ("BusControlsBaseInactiveUnselected");
controls_base_selected_name = "BusControlsBaseInactiveSelected";
controls_base_unselected_name = "BusControlsBaseInactiveUnselected";
}
}
}
XMLNode*
MidiTimeAxisView::get_child_xml_node (const string & childname)
{
return RouteUI::get_child_xml_node (childname);
}

View File

@@ -0,0 +1,87 @@
/*
Copyright (C) 2006 Paul Davis
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 __ardour_midi_time_axis_h__
#define __ardour_midi_time_axis_h__
#include <gtkmm/table.h>
#include <gtkmm/button.h>
#include <gtkmm/box.h>
#include <gtkmm/menu.h>
#include <gtkmm/menuitem.h>
#include <gtkmm/radiomenuitem.h>
#include <gtkmm/checkmenuitem.h>
#include <gtkmm2ext/selector.h>
#include <list>
#include <ardour/types.h>
#include <ardour/region.h>
#include "ardour_dialog.h"
#include "route_ui.h"
#include "enums.h"
#include "route_time_axis.h"
#include "canvas.h"
#include "color.h"
namespace ARDOUR {
class Session;
class MidiDiskstream;
class RouteGroup;
class Redirect;
class Insert;
class Location;
class MidiPlaylist;
}
class PublicEditor;
class Selection;
class Selectable;
class AutomationLine;
class AutomationGainLine;
class AutomationPanLine;
class RedirectAutomationLine;
class TimeSelection;
class AutomationTimeAxisView;
class MidiTimeAxisView : public RouteTimeAxisView
{
public:
MidiTimeAxisView (PublicEditor&, ARDOUR::Session&, boost::shared_ptr<ARDOUR::Route>, ArdourCanvas::Canvas& canvas);
virtual ~MidiTimeAxisView ();
/* overridden from parent to store display state */
guint32 show_at (double y, int& nth, Gtk::VBox *parent);
void hide ();
void set_state (const XMLNode&);
XMLNode* get_child_xml_node (const string & childname);
private:
void route_active_changed ();
//void redirects_changed (void *); FIXME?
void add_redirect_to_subplugin_menu (ARDOUR::Redirect *);
Gtk::Menu subplugin_menu;
};
#endif /* __ardour_midi_time_axis_h__ */

View File

@@ -1,5 +1,5 @@
/*
Copyright (C) 2000-2002 Paul Davis
Copyright (C) 2000-2006 Paul Davis
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
@@ -14,7 +14,6 @@
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.
*/
#include <cmath>
@@ -623,7 +622,7 @@ MixerStrip::add_connection_to_input_menu (ARDOUR::Connection* c)
MenuList& citems = input_menu.items();
if (c->nports() == _route->n_inputs()) {
if (c->nports() == _route->n_inputs().get_total()) {
citems.push_back (CheckMenuElem (c->name(), bind (mem_fun(*this, &MixerStrip::connection_input_chosen), c)));
@@ -646,7 +645,7 @@ MixerStrip::add_connection_to_output_menu (ARDOUR::Connection* c)
return;
}
if (c->nports() == _route->n_outputs()) {
if (c->nports() == _route->n_outputs().get_total()) {
MenuList& citems = output_menu.items();
citems.push_back (CheckMenuElem (c->name(), bind (mem_fun(*this, &MixerStrip::connection_output_chosen), c)));
@@ -1161,7 +1160,15 @@ MixerStrip::route_active_changed ()
{
RouteUI::route_active_changed ();
if (is_audio_track()) {
if (is_midi_track()) {
if (_route->active()) {
set_name ("MidiTrackStripBase");
gpm.set_meter_strip_name ("MidiTrackStripBase");
} else {
set_name ("MidiTrackStripBaseInactive");
gpm.set_meter_strip_name ("MidiTrackStripBaseInactive");
}
} else if (is_audio_track()) {
if (_route->active()) {
set_name ("AudioTrackStripBase");
gpm.set_meter_strip_name ("AudioTrackStripBase");
@@ -1170,7 +1177,7 @@ MixerStrip::route_active_changed ()
gpm.set_meter_strip_name ("AudioTrackStripBaseInactive");
}
gpm.set_fader_name ("AudioTrackFader");
} else { // FIXME: assumed audio bus
} else {
if (_route->active()) {
set_name ("AudioBusStripBase");
gpm.set_meter_strip_name ("AudioBusStripBase");

View File

@@ -263,7 +263,7 @@ PannerUI::update_pan_state ()
void
PannerUI::setup_pan ()
{
uint32_t nouts = _io->n_outputs ();
uint32_t nouts = _io->n_outputs ().get(ARDOUR::DataType::AUDIO);
if (nouts == 0 || nouts == 1) {
@@ -362,7 +362,7 @@ PannerUI::setup_pan ()
}
update_pan_sensitive ();
panner->reset (_io->n_inputs());
panner->reset (_io->n_inputs().get(ARDOUR::DataType::AUDIO));
panner->set_size_request (-1, 61);
/* and finally, add it to the panner frame */
@@ -449,7 +449,7 @@ PannerUI::effective_pan_display ()
return;
}
switch (_io->n_outputs()) {
switch (_io->n_outputs().get(ARDOUR::DataType::AUDIO)) {
case 0:
case 1:
/* relax */
@@ -460,7 +460,7 @@ PannerUI::effective_pan_display ()
break;
default:
//panner->move_puck (pan_value (v, right), 0.5);
//panner->move_puck (pan_value (v, right), 0.5);
break;
}
}
@@ -486,7 +486,7 @@ PannerUI::pan_changed (void *src)
panning_link_button.set_sensitive (true);
}
uint32_t nouts = _io->n_outputs();
uint32_t nouts = _io->n_outputs().get(ARDOUR::DataType::AUDIO);
switch (nouts) {
case 0:
@@ -543,7 +543,7 @@ PannerUI::pan_value_changed (uint32_t which)
{
ENSURE_GUI_THREAD (bind (mem_fun(*this, &PannerUI::pan_value_changed), which));
if (_io->n_outputs() > 1 && which < _io->panner().size()) {
if (_io->n_outputs().get(ARDOUR::DataType::AUDIO) > 1 && which < _io->panner().size()) {
float xpos;
float val = pan_adjustments[which]->get_value ();
@@ -613,7 +613,7 @@ PannerUI::update_pan_sensitive ()
{
bool sensitive = !(_io->panner().automation_state() & Play);
switch (_io->n_outputs()) {
switch (_io->n_outputs().get(ARDOUR::DataType::AUDIO)) {
case 0:
case 1:
break;

View File

@@ -0,0 +1,195 @@
/* XPM */
static const gchar *h_meter_strip_xpm[] = {
"186 5 187 2",
" c None",
". c #2BFE00",
"+ c #2DFE00",
"@ c #2FFE01",
"# c #32FE01",
"$ c #34FE02",
"% c #36FE02",
"& c #38FE03",
"* c #3BFE03",
"= c #3DFD04",
"- c #3FFD04",
"; c #41FD05",
"> c #44FD05",
", c #46FD06",
"' c #48FD06",
") c #4AFD07",
"! c #4DFD07",
"~ c #4FFD08",
"{ c #51FC08",
"] c #53FC09",
"^ c #56FC09",
"/ c #58FC09",
"( c #5AFC0A",
"_ c #5CFC0A",
": c #5FFC0B",
"< c #61FC0B",
"[ c #63FB0C",
"} c #65FB0C",
"| c #68FB0D",
"1 c #6AFB0D",
"2 c #6CFB0E",
"3 c #6EFB0E",
"4 c #71FB0F",
"5 c #73FB0F",
"6 c #75FB10",
"7 c #77FA10",
"8 c #7AFA11",
"9 c #7CFA11",
"0 c #7EFA12",
"a c #80FA12",
"b c #83FA12",
"c c #85FA13",
"d c #87FA13",
"e c #89FA14",
"f c #8CF914",
"g c #8EF915",
"h c #90F915",
"i c #92F916",
"j c #95F916",
"k c #97F917",
"l c #99F917",
"m c #9BF918",
"n c #9EF818",
"o c #A0F819",
"p c #A2F819",
"q c #A4F81A",
"r c #A7F81A",
"s c #A9F81A",
"t c #ABF81B",
"u c #ADF81B",
"v c #B0F81C",
"w c #B2F71C",
"x c #B4F71D",
"y c #B6F71D",
"z c #B9F71E",
"A c #BBF71E",
"B c #BDF71F",
"C c #BFF71F",
"D c #C2F720",
"E c #C4F720",
"F c #C6F621",
"G c #C8F621",
"H c #CBF622",
"I c #CDF622",
"J c #CFF623",
"K c #D1F623",
"L c #D4F624",
"M c #D6F624",
"N c #D8F524",
"O c #DAF525",
"P c #DDF525",
"Q c #DFF526",
"R c #E1F526",
"S c #E3F527",
"T c #E6F527",
"U c #E8F528",
"V c #EAF528",
"W c #ECF429",
"X c #EFF429",
"Y c #F1F42A",
"Z c #F3F42A",
"` c #F5F42B",
" . c #F8F42B",
".. c #FAF42C",
"+. c #FCF42C",
"@. c #FFF42D",
"#. c #FFF22C",
"$. c #FFF12B",
"%. c #FFF02A",
"&. c #FFEF2A",
"*. c #FFEE29",
"=. c #FFED28",
"-. c #FFEC28",
";. c #FFEB27",
">. c #FFE926",
",. c #FFE826",
"'. c #FFE725",
"). c #FFE624",
"!. c #FFE524",
"~. c #FFE423",
"{. c #FFE322",
"]. c #FFE222",
"^. c #FFE021",
"/. c #FFDF20",
"(. c #FFDE20",
"_. c #FFDD1F",
":. c #FFDC1E",
"<. c #FFDB1E",
"[. c #FFDA1D",
"}. c #FFD91C",
"|. c #FFD71B",
"1. c #FFD61B",
"2. c #FFD51A",
"3. c #FFD419",
"4. c #FFD319",
"5. c #FFD218",
"6. c #FFD117",
"7. c #FFD017",
"8. c #FFCF16",
"9. c #FFCD15",
"0. c #FFCC15",
"a. c #FFCB14",
"b. c #FFCA13",
"c. c #FFC913",
"d. c #FFC812",
"e. c #FFC711",
"f. c #FFC611",
"g. c #FFC410",
"h. c #FFC30F",
"i. c #FFC20F",
"j. c #FFC10E",
"k. c #FFC00D",
"l. c #FFBF0C",
"m. c #FFBE0C",
"n. c #FFBD0B",
"o. c #FFBB0A",
"p. c #FFBA0A",
"q. c #FFB909",
"r. c #FFB808",
"s. c #FFB708",
"t. c #FFB607",
"u. c #FFB506",
"v. c #FFB406",
"w. c #FFB205",
"x. c #FFB104",
"y. c #FFB004",
"z. c #FFAF03",
"A. c #FFAE02",
"B. c #FFAD02",
"C. c #FFAC01",
"D. c #FFAB00",
"E. c #FFA900",
"F. c #F11F00",
"G. c #F21E00",
"H. c #F21C00",
"I. c #F31B00",
"J. c #F31A00",
"K. c #F41800",
"L. c #F41700",
"M. c #F51600",
"N. c #F61400",
"O. c #F61300",
"P. c #F71100",
"Q. c #F71000",
"R. c #F80F00",
"S. c #F90D00",
"T. c #F90C00",
"U. c #FA0B00",
"V. c #FA0900",
"W. c #FB0800",
"X. c #FC0600",
"Y. c #FC0500",
"Z. c #FD0400",
"`. c #FD0200",
" + c #FE0100",
".+ c #FE0000",
"++ c #FF0000",
". + @ # $ % & * = - ; > , ' ) ! ~ { ] ^ / ( _ : < [ } | 1 2 3 4 5 6 7 8 9 0 a b c d e f g h i j k l m n o p q r s t u v w x y z A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ` ...+.@.@.#.$.%.&.*.=.-.;.>.,.'.).!.~.{.].^./.(._.:.<.[.}.|.1.2.3.4.5.6.7.8.9.0.a.b.c.d.e.f.g.h.i.j.k.l.m.n.o.p.q.r.s.t.u.v.w.x.y.z.A.B.C.D.E.F.G.H.I.J.K.L.M.N.O.P.Q.R.S.T.U.V.W.X.Y.Z.`. +.+",
". + @ # $ % & * = - ; > , ' ) ! ~ { ] ^ / ( _ : < [ } | 1 2 3 4 5 6 7 8 9 0 a b c d e f g h i j k l m n o p q r s t u v w x y z A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ` ...+.@.@.#.$.%.&.*.=.-.;.>.,.'.).!.~.{.].^./.(._.:.<.[.}.|.1.2.3.4.5.6.7.8.9.0.a.b.c.d.e.f.g.h.i.j.k.l.m.n.o.p.q.r.s.t.u.v.w.x.y.z.A.B.C.D.E.F.G.H.I.J.K.L.M.N.O.P.Q.R.S.T.U.V.W.X.Y.Z.`. +.+",
". + @ # $ % & * = - ; > , ' ) ! ~ { ] ^ / ( _ : < [ } | 1 2 3 4 5 6 7 8 9 0 a b c d e f g h i j k l m n o p q r s t u v w x y z A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ` ...+.@.@.#.$.%.&.*.=.-.;.>.,.'.).!.~.{.].^./.(._.:.<.[.}.|.1.2.3.4.5.6.7.8.9.0.a.b.c.d.e.f.g.h.i.j.k.l.m.n.o.p.q.r.s.t.u.v.w.x.y.z.A.B.C.D.E.F.G.H.I.J.K.L.M.N.O.P.Q.R.S.T.U.V.W.X.Y.Z.`. +++",
". + @ # $ % & * = - ; > , ' ) ! ~ { ] ^ / ( _ : < [ } | 1 2 3 4 5 6 7 8 9 0 a b c d e f g h i j k l m n o p q r s t u v w x y z A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ` ...+.@.@.#.$.%.&.*.=.-.;.>.,.'.).!.~.{.].^./.(._.:.<.[.}.|.1.2.3.4.5.6.7.8.9.0.a.b.c.d.e.f.g.h.i.j.k.l.m.n.o.p.q.r.s.t.u.v.w.x.y.z.A.B.C.D.E.F.G.H.I.J.K.L.M.N.O.P.Q.R.S.T.U.V.W.X.Y.Z.`. +++",
". + @ # $ % & * = - ; > , ' ) ! ~ { ] ^ / ( _ : < [ } | 1 2 3 4 5 6 7 8 9 0 a b c d e f g h i j k l m n o p q r s t u v w x y z A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ` ...+.@.@.#.$.%.&.*.=.-.;.>.,.'.).!.~.{.].^./.(._.:.<.[.}.|.1.2.3.4.5.6.7.8.9.0.a.b.c.d.e.f.g.h.i.j.k.l.m.n.o.p.q.r.s.t.u.v.w.x.y.z.A.B.C.D.E.F.G.H.I.J.K.L.M.N.O.P.Q.R.S.T.U.V.W.X.Y.Z.`. +++"};

View File

@@ -1,21 +1,22 @@
/* XPM */
static const gchar * left_arrow_xpm[] = {
"12 15 3 1",
static char * left_arrow_xpm[] = {
"12 12 7 1",
" c None",
". c #000000",
"+ c #FFFFFF",
" ..+. ",
" ..++. ",
" ..+++. ",
" ..+++.. ",
" ..+++.. ",
" ..+++.. ",
" ..+++.. ",
" .+++.. ",
" ..+++.. ",
" ..+++.. ",
" ..+++.. ",
" ..+++.. ",
" ..+++. ",
" ..++. ",
" ..+. "};
"@ c #020202",
"# c #0B0B0B",
"$ c #131313",
"% c #121212",
" .... ",
" ..++. ",
" ..++.. ",
" ..++.. ",
" ..++.. ",
" ..++.. ",
" ..++@. ",
" ..++#. ",
" ..++$. ",
" ..++%. ",
" ..++. ",
" .... "};

View File

@@ -1,21 +1,22 @@
/* XPM */
static const gchar * right_arrow_xpm[] = {
"12 15 3 1",
static char * right_arrow_xpm[] = {
"12 12 7 1",
" c None",
". c #000000",
"+ c #FFFFFF",
" .+.. ",
" .++.. ",
" .+++.. ",
" ..+++.. ",
" ..+++.. ",
" ..+++.. ",
" ..+++.. ",
" ..+++. ",
" ..+++.. ",
" ..+++.. ",
" ..+++.. ",
" ..+++.. ",
" .+++.. ",
" .++.. ",
" .+.. "};
"@ c #020202",
"# c #0B0B0B",
"$ c #131313",
"% c #121212",
" .... ",
" .++.. ",
" ..++.. ",
" ..++.. ",
" ..++.. ",
" ..++.. ",
" .@++.. ",
" .#++.. ",
" .$++.. ",
" .%++.. ",
" .++.. ",
" .... "};

View File

@@ -0,0 +1,483 @@
/* XPM */
static const gchar * v_meter_strip_xpm[] = {
"5 250 230 2",
" c None",
". c #FE0000",
"+ c #FF0000",
"@ c #FE0100",
"# c #FD0200",
"$ c #FD0300",
"% c #FD0400",
"& c #FC0500",
"* c #FC0600",
"= c #FC0700",
"- c #FB0800",
"; c #FA0900",
"> c #FA0A00",
", c #FA0B00",
"' c #F90C00",
") c #F90D00",
"! c #F80E00",
"~ c #F80F00",
"{ c #F71000",
"] c #F71100",
"^ c #F61200",
"/ c #F61300",
"( c #F61400",
"_ c #F51600",
": c #F41700",
"< c #F41800",
"[ c #F31A00",
"} c #F31B00",
"| c #F21C00",
"1 c #F21E00",
"2 c #F11F00",
"3 c #F54A00",
"4 c #FFA900",
"5 c #FFAB00",
"6 c #FFAC01",
"7 c #FFAD02",
"8 c #FFAE02",
"9 c #FFAF03",
"0 c #FFB004",
"a c #FFB104",
"b c #FFB205",
"c c #FFB406",
"d c #FFB506",
"e c #FFB607",
"f c #FFB708",
"g c #FFB808",
"h c #FFB909",
"i c #FFBA0A",
"j c #FFBB0A",
"k c #FFBC0A",
"l c #FFBD0B",
"m c #FFBE0C",
"n c #FFBF0C",
"o c #FFC00D",
"p c #FFC10E",
"q c #FFC20F",
"r c #FFC30F",
"s c #FFC410",
"t c #FFC511",
"u c #FFC611",
"v c #FFC711",
"w c #FFC812",
"x c #FFC913",
"y c #FFCA13",
"z c #FFCB14",
"A c #FFCC15",
"B c #FFCD15",
"C c #FFCF16",
"D c #FFD017",
"E c #FFD117",
"F c #FFD218",
"G c #FFD319",
"H c #FFD419",
"I c #FFD51A",
"J c #FFD61B",
"K c #FFD71B",
"L c #FFD81C",
"M c #FFD91C",
"N c #FFDA1D",
"O c #FFDB1E",
"P c #FFDC1E",
"Q c #FFDD1F",
"R c #FFDE20",
"S c #FFDF20",
"T c #FFE021",
"U c #FFE222",
"V c #FFE322",
"W c #FFE423",
"X c #FFE524",
"Y c #FFE624",
"Z c #FFE725",
"` c #FFE826",
" . c #FFE926",
".. c #FFEA26",
"+. c #FFEB27",
"@. c #FFEC28",
"#. c #FFED28",
"$. c #FFEE29",
"%. c #FFEF2A",
"&. c #FFF02A",
"*. c #FFF12B",
"=. c #FFF22C",
"-. c #FFF32D",
";. c #FFF42D",
">. c #FDF42C",
",. c #FBF42C",
"'. c #FAF42C",
"). c #F8F42B",
"!. c #F6F42B",
"~. c #F4F42B",
"{. c #F3F42A",
"]. c #F1F42A",
"^. c #F0F429",
"/. c #EEF429",
"(. c #ECF429",
"_. c #EAF528",
":. c #E9F528",
"<. c #E7F528",
"[. c #E5F527",
"}. c #E3F527",
"|. c #E2F526",
"1. c #E0F526",
"2. c #DFF526",
"3. c #DDF525",
"4. c #DBF525",
"5. c #D9F525",
"6. c #D8F524",
"7. c #D6F624",
"8. c #D5F624",
"9. c #D3F624",
"0. c #D1F623",
"a. c #CFF623",
"b. c #CEF622",
"c. c #CCF622",
"d. c #CBF622",
"e. c #C9F621",
"f. c #C7F621",
"g. c #C5F621",
"h. c #C4F720",
"i. c #C2F720",
"j. c #C0F71F",
"k. c #BEF71F",
"l. c #BDF71F",
"m. c #BBF71E",
"n. c #BAF71E",
"o. c #B8F71E",
"p. c #B6F71D",
"q. c #B5F71D",
"r. c #B3F71D",
"s. c #B2F71C",
"t. c #B0F81C",
"u. c #AEF81B",
"v. c #ACF81B",
"w. c #ABF81B",
"x. c #A9F81A",
"y. c #A8F81A",
"z. c #A6F81A",
"A. c #A4F81A",
"B. c #A2F819",
"C. c #A1F819",
"D. c #9FF819",
"E. c #9EF818",
"F. c #9BF918",
"G. c #9AF917",
"H. c #98F917",
"I. c #97F917",
"J. c #95F916",
"K. c #93F916",
"L. c #91F916",
"M. c #90F915",
"N. c #8EF915",
"O. c #8DF914",
"P. c #8BF914",
"Q. c #89FA14",
"R. c #87FA13",
"S. c #86FA13",
"T. c #84FA13",
"U. c #83FA12",
"V. c #81FA12",
"W. c #7FFA12",
"X. c #7DFA12",
"Y. c #7CFA11",
"Z. c #7AFA11",
"`. c #78FA10",
" + c #76FA10",
".+ c #75FB10",
"++ c #73FB0F",
"@+ c #72FB0F",
"#+ c #70FB0F",
"$+ c #6EFB0E",
"%+ c #6DFB0E",
"&+ c #6BFB0E",
"*+ c #6AFB0D",
"=+ c #68FB0D",
"-+ c #66FB0C",
";+ c #64FB0C",
">+ c #63FB0C",
",+ c #61FC0B",
"'+ c #60FC0B",
")+ c #5EFC0B",
"!+ c #5CFC0A",
"~+ c #5AFC0A",
"{+ c #59FC09",
"]+ c #57FC09",
"^+ c #56FC09",
"/+ c #53FC09",
"(+ c #52FC08",
"_+ c #50FC08",
":+ c #4FFD08",
"<+ c #4DFD07",
"[+ c #4BFD07",
"}+ c #49FD07",
"|+ c #48FD06",
"1+ c #46FD06",
"2+ c #45FD05",
"3+ c #43FD05",
"4+ c #41FD05",
"5+ c #3FFD04",
"6+ c #3EFD04",
"7+ c #3CFD04",
"8+ c #3BFE03",
"9+ c #39FE03",
"0+ c #37FE02",
"a+ c #35FE02",
"b+ c #34FE02",
"c+ c #32FE01",
"d+ c #30FE01",
"e+ c #2EFE01",
"f+ c #2DFE00",
"g+ c #2BFE00",
". . + + + ",
". . + + + ",
"@ @ @ @ @ ",
"# # # # # ",
"$ $ $ $ $ ",
"% % % % % ",
"& & & & & ",
"* * * * * ",
"= = = = = ",
"- - - - - ",
"; ; ; ; ; ",
"> > > > > ",
", , , , , ",
"' ' ' ' ' ",
") ) ) ) ) ",
"! ! ! ! ! ",
"~ ~ ~ ~ ~ ",
"{ { { { { ",
"] ] ] ] ] ",
"^ ^ ^ ^ ^ ",
"/ / / / / ",
"( ( ( ( ( ",
"_ _ _ _ _ ",
": : : : : ",
": : : : : ",
"< < < < < ",
"[ [ [ [ [ ",
"} } } } } ",
"} } } } } ",
"| | | | | ",
"1 1 1 1 1 ",
"2 2 2 2 2 ",
"3 3 3 3 3 ",
"4 4 4 4 4 ",
"5 5 5 5 5 ",
"6 6 6 6 6 ",
"6 6 6 6 6 ",
"7 7 7 7 7 ",
"8 8 8 8 8 ",
"9 9 9 9 9 ",
"9 9 9 9 9 ",
"0 0 0 0 0 ",
"a a a a a ",
"a a a a a ",
"b b b b b ",
"c c c c c ",
"d d d d d ",
"d d d d d ",
"e e e e e ",
"f f f f f ",
"g g g g g ",
"g g g g g ",
"h h h h h ",
"i i i i i ",
"j j j j j ",
"k k k k k ",
"l l l l l ",
"m m m m m ",
"n n n n n ",
"n n n n n ",
"o o o o o ",
"p p p p p ",
"q q q q q ",
"q q q q q ",
"r r r r r ",
"s s s s s ",
"t t t t t ",
"u u u u u ",
"v v v v v ",
"w w w w w ",
"x x x x x ",
"x x x x x ",
"y y y y y ",
"z z z z z ",
"A A A A A ",
"A A A A A ",
"B B B B B ",
"C C C C C ",
"D D D D D ",
"D D D D D ",
"E E E E E ",
"F F F F F ",
"G G G G G ",
"G G G G G ",
"H H H H H ",
"I I I I I ",
"I I I I I ",
"J J J J J ",
"K K K K K ",
"L L L L L ",
"M M M M M ",
"N N N N N ",
"O O O O O ",
"P P P P P ",
"P P P P P ",
"Q Q Q Q Q ",
"R R R R R ",
"S S S S S ",
"S S S S S ",
"T T T T T ",
"U U U U U ",
"V V V V V ",
"V V V V V ",
"W W W W W ",
"X X X X X ",
"Y Y Y Y Y ",
"Y Y Y Y Y ",
"Z Z Z Z Z ",
"` ` ` ` ` ",
" . . . . .",
"..........",
"+.+.+.+.+.",
"@.@.@.@.@.",
"#.#.#.#.#.",
"#.#.#.#.#.",
"$.$.$.$.$.",
"%.%.%.%.%.",
"&.&.&.&.&.",
"&.&.&.&.&.",
"*.*.*.*.*.",
"=.=.=.=.=.",
"-.-.-.-.-.",
";.;.;.;.;.",
";.;.;.;.;.",
">.>.>.>.>.",
",.,.,.,.,.",
"'.'.'.'.'.",
").).).).).",
"!.!.!.!.!.",
"~.~.~.~.~.",
"{.{.{.{.{.",
"].].].].].",
"^.^.^.^.^.",
"/././././.",
"(.(.(.(.(.",
"_._._._._.",
":.:.:.:.:.",
"<.<.<.<.<.",
"[.[.[.[.[.",
"}.}.}.}.}.",
"|.|.|.|.|.",
"1.1.1.1.1.",
"2.2.2.2.2.",
"3.3.3.3.3.",
"4.4.4.4.4.",
"5.5.5.5.5.",
"6.6.6.6.6.",
"7.7.7.7.7.",
"8.8.8.8.8.",
"9.9.9.9.9.",
"0.0.0.0.0.",
"a.a.a.a.a.",
"b.b.b.b.b.",
"c.c.c.c.c.",
"d.d.d.d.d.",
"e.e.e.e.e.",
"f.f.f.f.f.",
"g.g.g.g.g.",
"h.h.h.h.h.",
"i.i.i.i.i.",
"j.j.j.j.j.",
"k.k.k.k.k.",
"l.l.l.l.l.",
"m.m.m.m.m.",
"n.n.n.n.n.",
"o.o.o.o.o.",
"p.p.p.p.p.",
"q.q.q.q.q.",
"r.r.r.r.r.",
"s.s.s.s.s.",
"t.t.t.t.t.",
"u.u.u.u.u.",
"v.v.v.v.v.",
"w.w.w.w.w.",
"x.x.x.x.x.",
"y.y.y.y.y.",
"z.z.z.z.z.",
"A.A.A.A.A.",
"B.B.B.B.B.",
"C.C.C.C.C.",
"D.D.D.D.D.",
"E.E.E.E.E.",
"F.F.F.F.F.",
"G.G.G.G.G.",
"H.H.H.H.H.",
"I.I.I.I.I.",
"J.J.J.J.J.",
"K.K.K.K.K.",
"L.L.L.L.L.",
"M.M.M.M.M.",
"N.N.N.N.N.",
"O.O.O.O.O.",
"P.P.P.P.P.",
"Q.Q.Q.Q.Q.",
"R.R.R.R.R.",
"S.S.S.S.S.",
"T.T.T.T.T.",
"U.U.U.U.U.",
"V.V.V.V.V.",
"W.W.W.W.W.",
"X.X.X.X.X.",
"Y.Y.Y.Y.Y.",
"Z.Z.Z.Z.Z.",
"`.`.`.`.`.",
" + + + + +",
".+.+.+.+.+",
"++++++++++",
"@+@+@+@+@+",
"#+#+#+#+#+",
"$+$+$+$+$+",
"%+%+%+%+%+",
"&+&+&+&+&+",
"*+*+*+*+*+",
"=+=+=+=+=+",
"-+-+-+-+-+",
";+;+;+;+;+",
">+>+>+>+>+",
",+,+,+,+,+",
"'+'+'+'+'+",
")+)+)+)+)+",
"!+!+!+!+!+",
"~+~+~+~+~+",
"{+{+{+{+{+",
"]+]+]+]+]+",
"^+^+^+^+^+",
"/+/+/+/+/+",
"(+(+(+(+(+",
"_+_+_+_+_+",
":+:+:+:+:+",
"<+<+<+<+<+",
"[+[+[+[+[+",
"}+}+}+}+}+",
"|+|+|+|+|+",
"1+1+1+1+1+",
"2+2+2+2+2+",
"3+3+3+3+3+",
"4+4+4+4+4+",
"5+5+5+5+5+",
"6+6+6+6+6+",
"7+7+7+7+7+",
"8+8+8+8+8+",
"9+9+9+9+9+",
"0+0+0+0+0+",
"a+a+a+a+a+",
"b+b+b+b+b+",
"c+c+c+c+c+",
"d+d+d+d+d+",
"e+e+e+e+e+",
"f+f+f+f+f+",
"g+g+g+g+g+"};

View File

@@ -211,4 +211,3 @@ PlugUIBase::bypass_toggled ()
insert->set_active (!x, this);
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -62,6 +62,7 @@ class ControlPoint;
class SelectionRect;
class CrossfadeView;
class RouteTimeAxisView;
class RegionView;
class AudioRegionView;
class TempoMarker;
class MeterMarker;
@@ -159,7 +160,6 @@ class PublicEditor : public Gtk::Window, public PBD::StatefulThingWithGoingAway
sigc::signal<void> ZoomChanged;
sigc::signal<void> Resized;
sigc::signal<void> Realized;
sigc::signal<void> GoingAway;
sigc::signal<void,nframes_t> UpdateAllTransportClocks;
Glib::RefPtr<Gtk::ActionGroup> editor_actions;

View File

@@ -294,7 +294,7 @@ RedirectBox::redirect_button_press_event (GdkEventButton *ev)
}
if (redirect && (Keyboard::is_edit_event (ev) || (ev->button == 1 && ev->type == GDK_2BUTTON_PRESS && ev->state == 0))) {
if (redirect && (Keyboard::is_edit_event (ev) || (ev->button == 1 && ev->type == GDK_2BUTTON_PRESS))) {
if (_session.engine().connected()) {
/* XXX giving an error message here is hard, because we may be in the midst of a button press */
@@ -339,7 +339,7 @@ RedirectBox::redirect_button_release_event (GdkEventButton *ev)
show_redirect_menu(ev->time);
ret = true;
} else if (redirect && ev->button == 2 && ev->state == GDK_BUTTON2_MASK) {
} else if (redirect && ev->button == 2 && Keyboard::modifier_state_equals (ev->state, Gdk::BUTTON2_MASK)) {
redirect->set_active (!redirect->active(), this);
ret = true;
@@ -453,8 +453,8 @@ RedirectBox::weird_plugin_dialog (Plugin& p, uint32_t streams, boost::shared_ptr
p.name(),
p.get_info()->n_inputs,
p.get_info()->n_outputs,
io->n_inputs(),
io->n_outputs(),
io->n_inputs().get_total(),
io->n_outputs().get_total(),
streams));
}
@@ -481,10 +481,11 @@ void
RedirectBox::choose_send ()
{
boost::shared_ptr<Send> send (new Send (_session, _placement));
send->set_default_type(_route->default_type());
/* XXX need redirect lock on route */
send->ensure_io (0, _route->max_redirect_outs(), false, this);
send->ensure_io (ChanCount::ZERO, _route->max_redirect_outs(), false, this);
IOSelectorWindow *ios = new IOSelectorWindow (_session, send, false, true);
@@ -1070,6 +1071,7 @@ RedirectBox::edit_redirect (boost::shared_ptr<Redirect> redirect)
send_ui->get_window()->raise ();
} else {
send_ui->show_all ();
send_ui->present ();
}
} else {
@@ -1114,6 +1116,7 @@ RedirectBox::edit_redirect (boost::shared_ptr<Redirect> redirect)
plugin_ui->get_window()->raise ();
} else {
plugin_ui->show_all ();
plugin_ui->present ();
}
#ifdef HAVE_AUDIOUNIT
} else if (type == ARDOUR::AudioUnit) {
@@ -1124,12 +1127,18 @@ RedirectBox::edit_redirect (boost::shared_ptr<Redirect> redirect)
plugin_ui = reinterpret_cast<AUPluginUI*> (plugin_insert->get_gui());
}
// raise window, somehow
if (plugin_ui->is_visible()) {
plugin_ui->get_window()->raise ();
} else {
plugin_ui->show_all ();
plugin_ui->present ();
}
#endif
} else {
warning << "Unsupported plugin sent to RedirectBox::edit_redirect()" << endmsg;
return;
}
} else if ((port_insert = boost::dynamic_pointer_cast<PortInsert> (insert)) != 0) {
if (!_session.engine().connected()) {
@@ -1151,7 +1160,7 @@ RedirectBox::edit_redirect (boost::shared_ptr<Redirect> redirect)
if (io_selector->is_visible()) {
io_selector->get_window()->raise ();
} else {
io_selector->show_all ();
io_selector->present ();
}
}
}

View File

@@ -108,4 +108,3 @@ AudioRegionGainLine::end_drag (ControlPoint* cp)
AutomationLine::end_drag(cp);
}

View File

@@ -49,6 +49,8 @@ class AudioRegionGainLine : public AutomationLine
private:
ARDOUR::Session& session;
AudioRegionView& rv;
UndoAction get_memento();
};

View File

@@ -254,6 +254,14 @@ RegionView::reset_width_dependent_items (double pixel_width)
_pixel_width = pixel_width;
}
void
RegionView::set_height (gdouble height)
{
TimeAxisViewItem::set_height (height - 2);
_height = height;
}
void
RegionView::region_layered ()
{
@@ -410,10 +418,9 @@ RegionView::region_renamed ()
str = _region->name();
}
if (_region->speed_mismatch (trackview.session().frame_rate())) {
str = string ("*") + str;
}
// speed mismatch handled in audio_region_view.cc
// FIXME: come up with more elegant solution for this
if (_region->muted()) {
str = string ("!") + str;
}

View File

@@ -60,7 +60,7 @@ class RegionView : public TimeAxisViewItem
void set_valid (bool yn) { valid = yn; }
virtual void set_height (double) = 0;
virtual void set_height (double);
virtual void set_samples_per_unit (double);
virtual bool set_duration (nframes_t, void*);
@@ -101,14 +101,14 @@ class RegionView : public TimeAxisViewItem
double samples_per_unit,
Gdk::Color& basic_color,
TimeAxisViewItem::Visibility);
virtual void region_resized (ARDOUR::Change);
void region_moved (void *);
virtual void region_muted ();
void region_locked ();
void region_opacity ();
void region_layered ();
void region_renamed ();
virtual void region_renamed ();
void region_sync_changed ();
static gint _lock_toggle (ArdourCanvas::Item*, GdkEvent*, void*);
@@ -118,7 +118,7 @@ class RegionView : public TimeAxisViewItem
virtual void compute_colors (Gdk::Color&);
virtual void set_frame_color ();
virtual void reset_width_dependent_items (double pixel_width);
virtual void color_handler (ColorID, uint32_t) {}
boost::shared_ptr<ARDOUR::Region> _region;

View File

@@ -177,8 +177,12 @@ RouteTimeAxisView::RouteTimeAxisView (PublicEditor& ed, Session& sess, boost::sh
y_position = -1;
_route->mute_changed.connect (mem_fun(*this, &RouteUI::mute_changed));
_route->solo_changed.connect (mem_fun(*this, &RouteUI::solo_changed));
_route->redirects_changed.connect (mem_fun(*this, &RouteTimeAxisView::redirects_changed));
_route->name_changed.connect (mem_fun(*this, &RouteTimeAxisView::route_name_changed));
_route->solo_safe_changed.connect (mem_fun(*this, &RouteUI::solo_changed));
if (is_track()) {

View File

@@ -39,6 +39,8 @@
#include <ardour/audioengine.h>
#include <ardour/audio_track.h>
#include <ardour/audio_diskstream.h>
#include <ardour/midi_track.h>
#include <ardour/midi_diskstream.h>
#include "i18n.h"
using namespace sigc;
@@ -89,9 +91,6 @@ RouteUI::RouteUI (boost::shared_ptr<ARDOUR::Route> rt, ARDOUR::Session& sess, co
_session.SoloChanged.connect (mem_fun(*this, &RouteUI::solo_changed_so_update_mute));
update_solo_display ();
update_mute_display ();
if (is_track()) {
boost::shared_ptr<Track> t = boost::dynamic_pointer_cast<Track>(_route);
@@ -105,6 +104,9 @@ RouteUI::RouteUI (boost::shared_ptr<ARDOUR::Route> rt, ARDOUR::Session& sess, co
update_rec_display ();
}
mute_button->unset_flags (Gtk::CAN_FOCUS);
solo_button->unset_flags (Gtk::CAN_FOCUS);
_route->RemoteControlIDChanged.connect (mem_fun(*this, &RouteUI::refresh_remote_control_menu));
@@ -330,7 +332,7 @@ RouteUI::rec_enable_press(GdkEventButton* ev)
} else {
reversibly_apply_audio_track_boolean ("rec-enable change", &AudioTrack::set_record_enable, !audio_track()->record_enabled(), this);
reversibly_apply_track_boolean ("rec-enable change", &Track::set_record_enable, !track()->record_enabled(), this);
}
}
@@ -648,13 +650,13 @@ RouteUI::reversibly_apply_route_boolean (string name, void (Route::*func)(bool,
}
void
RouteUI::reversibly_apply_audio_track_boolean (string name, void (AudioTrack::*func)(bool, void *), bool yn, void *arg)
RouteUI::reversibly_apply_track_boolean (string name, void (Track::*func)(bool, void *), bool yn, void *arg)
{
_session.begin_reversible_command (name);
XMLNode &before = audio_track()->get_state();
bind (mem_fun (*audio_track(), func), yn, arg)();
XMLNode &after = audio_track()->get_state();
_session.add_command (new MementoCommand<AudioTrack>(*audio_track(), &before, &after));
XMLNode &before = track()->get_state();
bind (mem_fun (*track(), func), yn, arg)();
XMLNode &after = track()->get_state();
_session.add_command (new MementoCommand<Track>(*track(), &before, &after));
_session.commit_reversible_command ();
}
@@ -965,6 +967,18 @@ RouteUI::audio_track() const
return dynamic_cast<AudioTrack*>(_route.get());
}
bool
RouteUI::is_midi_track () const
{
return dynamic_cast<MidiTrack*>(_route.get()) != 0;
}
MidiTrack*
RouteUI::midi_track() const
{
return dynamic_cast<MidiTrack*>(_route.get());
}
boost::shared_ptr<Diskstream>
RouteUI::get_diskstream () const
{

View File

@@ -31,6 +31,7 @@
namespace ARDOUR {
class AudioTrack;
class MidiTrack;
}
namespace Gtk {
@@ -49,12 +50,14 @@ class RouteUI : public virtual AxisView
bool is_track() const;
bool is_audio_track() const;
bool is_midi_track() const;
boost::shared_ptr<ARDOUR::Route> route() const { return _route; }
// FIXME: make these return shared_ptr
ARDOUR::Track* track() const;
ARDOUR::AudioTrack* audio_track() const;
ARDOUR::MidiTrack* midi_track() const;
boost::shared_ptr<ARDOUR::Diskstream> get_diskstream() const;
@@ -156,7 +159,7 @@ class RouteUI : public virtual AxisView
void set_remote_control_id (uint32_t id, Gtk::CheckMenuItem* item);
void reversibly_apply_route_boolean (string name, void (ARDOUR::Route::*func)(bool, void*), bool, void *);
void reversibly_apply_audio_track_boolean (string name, void (ARDOUR::AudioTrack::*func)(bool, void*), bool, void *);
void reversibly_apply_track_boolean (string name, void (ARDOUR::Track::*func)(bool, void*), bool, void *);
};
#endif /* __ardour_route_ui__ */

View File

@@ -199,7 +199,7 @@ SoundFileBox::play_btn_clicked ()
for (int n = 0; n < sf_info.channels; ++n) {
try {
afs = boost::dynamic_pointer_cast<AudioFileSource> (SourceFactory::createReadable (*_session, path, n, AudioFileSource::Flag (0)));
afs = boost::dynamic_pointer_cast<AudioFileSource> (SourceFactory::createReadable (DataType::AUDIO, *_session, path, n, AudioFileSource::Flag (0)));
srclist.push_back(afs);
} catch (failed_constructor& err) {

View File

@@ -56,6 +56,7 @@ StreamView::StreamView (RouteTimeAxisView& tv)
, use_rec_regions(tv.editor.show_waveforms_recording())
, region_color(_trackview.color())
, stream_base_color(0xFFFFFFFF)
, last_rec_data_frame(0)
{
/* set_position() will position the group */

View File

@@ -143,6 +143,10 @@ protected:
vector<sigc::connection> playlist_connections;
sigc::connection playlist_change_connection;
list<sigc::connection> rec_data_ready_connections;
jack_nframes_t last_rec_data_frame;
map<boost::shared_ptr<ARDOUR::Source>, bool> rec_data_ready_map;
};
#endif /* __ardour_streamview_h__ */

View File

@@ -67,7 +67,7 @@ TapeAudioRegionView::init (Gdk::Color& basic_color, bool wfw)
/* every time the wave data changes and peaks are ready, redraw */
for (uint32_t n = 0; n < audio_region()->n_channels(); ++n) {
audio_region()->source(n)->PeaksReady.connect (bind (mem_fun(*this, &TapeAudioRegionView::update), n));
audio_region()->audio_source(n)->PeaksReady.connect (bind (mem_fun(*this, &TapeAudioRegionView::update), n));
}
}

View File

@@ -131,8 +131,8 @@ TimeAxisView::TimeAxisView (ARDOUR::Session& sess, PublicEditor& ed, TimeAxisVie
controls_vbox.pack_start (controls_table, false, false);
controls_vbox.show ();
controls_ebox.set_name ("TimeAxisViewControlsBaseUnselected");
//controls_ebox.set_name ("TimeAxisViewControlsBaseUnselected");
controls_ebox.add (controls_vbox);
controls_ebox.add_events (BUTTON_PRESS_MASK|BUTTON_RELEASE_MASK|SCROLL_MASK);
controls_ebox.set_flags (CAN_FOCUS);
@@ -978,7 +978,8 @@ TimeAxisView::compute_controls_size_info ()
one_row_table.attach (*buttons[0], 6, 7, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND, 0, 0);
one_row_table.show_all ();
Gtk::Requisition req (one_row_table.size_request ());
Gtk::Requisition req(one_row_table.size_request ());
// height required to show 1 row of buttons

View File

@@ -62,12 +62,10 @@ class TimeAxisViewItem;
class Selection;
class Selectable;
/**
* TimeAxisView defines the abstract base class for time-axis views.
/** Abstract base class for time-axis views (horizontal editor 'strips')
*
* This class provides the basic LHS controls and display methods. This should be
* extended to create functional time-axis based views.
*
*/
class TimeAxisView : public virtual AxisView
{
@@ -104,13 +102,13 @@ class TimeAxisView : public virtual AxisView
PublicEditor& editor;
TrackHeight height_style;
uint32_t height; /* in canvas units */
uint32_t effective_height; /* in canvas units */
double y_position;
int order;
uint32_t height; /* in canvas units */
uint32_t effective_height; /* in canvas units */
double y_position;
int order;
ArdourCanvas::Group *canvas_display;
Gtk::VBox *control_parent;
ArdourCanvas::Group *canvas_display;
Gtk::VBox *control_parent;
/* The Standard LHS Controls */
Gtk::Frame controls_frame;
@@ -122,14 +120,13 @@ class TimeAxisView : public virtual AxisView
Gtk::HBox name_hbox;
Gtk::Frame name_frame;
Gtkmm2ext::FocusEntry name_entry;
void hide_name_label ();
void hide_name_entry ();
void show_name_label ();
void show_name_entry ();
/**
* Display this TrackView as the nth component of the parent box, at y.
/** Display this TrackView as the nth component of the parent box, at y.
*
* @param y
* @param nth
@@ -140,9 +137,7 @@ class TimeAxisView : public virtual AxisView
bool touched (double top, double bot);
/**
* Hides this TrackView
*/
/** Hides this TrackView */
virtual void hide ();
bool hidden() const { return _hidden; }
@@ -235,49 +230,39 @@ class TimeAxisView : public virtual AxisView
virtual bool name_entry_focus_in (GdkEventFocus *ev);
virtual bool name_entry_focus_out (GdkEventFocus *ev);
/**
* Handle mouse relaese on our LHS control name ebox.
/** Handle mouse relaese on our LHS control name ebox.
*
*@ param ev the event
*/
virtual bool controls_ebox_button_release (GdkEventButton *ev);
virtual bool controls_ebox_scroll (GdkEventScroll *ev);
/**
* Displays the standard LHS control menu at when.
/** Display the standard LHS control menu at when.
*
* @param when the popup activation time
*/
virtual void popup_display_menu (guint32 when);
/**
* Build the standard LHS control menu.
/** Build the standard LHS control menu.
* Subclasses should extend this method to add their own menu options.
*
*/
virtual void build_display_menu ();
/**
* Do anything that needs to be done to dynamically reset
* the LHS control menu.
/** Do whatever needs to be done to dynamically reset the LHS control menu.
*/
virtual bool handle_display_menu_map_event (GdkEventAny *ev) { return false; }
/**
* Build the standard LHS control size menu for the default heights options.
*
/** Build the standard LHS control size menu for the default heights options.
*/
virtual void build_size_menu();
/**
* Displays the standard LHS controls size menu for the track heights
/** Displays the standard LHS controls size menu for the track heights
*
* @parem when the popup activation time
* @param when the popup activation time
*/
void popup_size_menu(guint32 when);
/**
* Handle the size option of out main menu.
/** Handle the size option of our main menu.
*
* @param ev the event
*/
@@ -292,8 +277,7 @@ class TimeAxisView : public virtual AxisView
TimeAxisView* parent;
/* find the parent with state */
/** Find the parent with state */
TimeAxisView* get_parent_with_state();
std::vector<TimeAxisView*> children;

1
libs/.cvsignore Normal file
View File

@@ -0,0 +1 @@
.DS_Store

View File

@@ -17,7 +17,6 @@ domain = 'libardour'
ardour.Append(DOMAIN = domain, MAJOR = 2, MINOR = 0, MICRO = 0)
ardour.Append(CXXFLAGS = "-DPACKAGE=\\\"" + domain + "\\\"")
ardour.Append(CXXFLAGS="-DLIBSIGC_DISABLE_DEPRECATED")
ardour.Append(CXXFLAGS="-DGLIBMM_DISABLE_DEPRECATED")
ardour.Append(PACKAGE = domain)
ardour.Append(POTFILE = domain + '.pot')
@@ -28,17 +27,33 @@ ardour.Append(POTFILE = domain + '.pot')
ardour.Append(CPPPATH = '#libs/surfaces/control_protocol')
ardour_files=Split("""
chan_count.cc
diskstream.cc
track.cc
audio_diskstream.cc
audio_library.cc
audio_playlist.cc
track.cc
audio_track.cc
audioengine.cc
port.cc
audio_port.cc
midi_port.cc
port_set.cc
buffer.cc
buffer_set.cc
meter.cc
amp.cc
panner.cc
audiofilesource.cc
audiofilter.cc
audioregion.cc
audiosource.cc
midi_source.cc
midi_diskstream.cc
midi_playlist.cc
midi_track.cc
midi_region.cc
smf_source.cc
auditioner.cc
automation.cc
automation_event.cc
@@ -61,13 +76,11 @@ ladspa_plugin.cc
location.cc
mtc_slave.cc
named_selection.cc
panner.cc
pcm_utils.cc
playlist.cc
playlist_factory.cc
plugin.cc
plugin_manager.cc
port.cc
recent_sessions.cc
redirect.cc
region.cc

102
libs/ardour/amp.cc Normal file
View File

@@ -0,0 +1,102 @@
/*
Copyright (C) 2006 Paul Davis
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.
*/
#include <ardour/amp.h>
#include <algorithm>
#include <cmath>
#include <ardour/buffer_set.h>
#include <ardour/buffer.h>
namespace ARDOUR {
/** Apply a declicked gain to the audio buffers of @a bufs */
void
Amp::run (BufferSet& bufs, nframes_t nframes, gain_t initial, gain_t target, bool invert_polarity)
{
if (nframes == 0)
return;
if (bufs.count().get(DataType::AUDIO) == 0)
return;
// assert(bufs.buffer_capacity(DataType::AUDIO) >= nframes);
// if we don't need to declick, defer to apply_simple_gain
if (initial == target) {
if (target == 0.0) {
for (BufferSet::audio_iterator i = bufs.audio_begin(); i != bufs.audio_end(); ++i) {
memset (i->data(), 0, sizeof (Sample) * nframes);
}
} else if (target != 1.0) {
for (BufferSet::audio_iterator i = bufs.audio_begin(); i != bufs.audio_end(); ++i) {
apply_gain_to_buffer (i->data(), nframes, target);
}
}
return;
}
const nframes_t declick = std::min ((nframes_t)128, nframes);
gain_t delta;
double fractional_shift = -1.0/declick;
double fractional_pos;
gain_t polscale = invert_polarity ? -1.0f : 1.0f;
if (target < initial) {
/* fade out: remove more and more of delta from initial */
delta = -(initial - target);
} else {
/* fade in: add more and more of delta from initial */
delta = target - initial;
}
for (BufferSet::audio_iterator i = bufs.audio_begin(); i != bufs.audio_end(); ++i) {
Sample* const buffer = i->data();
fractional_pos = 1.0;
for (nframes_t nx = 0; nx < declick; ++nx) {
buffer[nx] *= polscale * (initial + (delta * (0.5 + 0.5 * cos (M_PI * fractional_pos))));
fractional_pos += fractional_shift;
}
/* now ensure the rest of the buffer has the target value applied, if necessary. */
if (declick != nframes) {
if (invert_polarity) {
target = -target;
}
if (target == 0.0) {
memset (&buffer[declick], 0, sizeof (Sample) * (nframes - declick));
} else if (target != 1.0) {
apply_gain_to_buffer (&buffer[declick], nframes - declick, target);
}
}
}
}
void
Amp::apply_simple_gain (BufferSet& bufs, nframes_t nframes, gain_t target)
{
}
} // namespace ARDOUR

42
libs/ardour/ardour/amp.h Normal file
View File

@@ -0,0 +1,42 @@
/*
Copyright (C) 2006 Paul Davis
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 __ardour_amp_h__
#define __ardour_amp_h__
#include <ardour/types.h>
namespace ARDOUR {
class BufferSet;
/** Applies a declick operation to all audio inputs, passing the same number of
* audio outputs, and passing through any other types unchanged.
*/
class Amp {
public:
static void run (BufferSet& bufs, nframes_t nframes, gain_t initial, gain_t target, bool invert_polarity);
static void apply_simple_gain(BufferSet& bufs, nframes_t nframes, gain_t target);
};
} // namespace ARDOUR
#endif // __ardour_amp_h__

View File

@@ -46,6 +46,8 @@ namespace ARDOUR {
int init (bool with_vst, bool try_optimization);
int cleanup ();
int setup_midi(AudioEngine& engine);
std::string get_ardour_revision ();

View File

@@ -0,0 +1,103 @@
/*
Copyright (C) 2002 Paul Davis
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.
$Id: port.h 712 2006-07-28 01:08:57Z drobilla $
*/
#ifndef __ardour_audio_port_h__
#define __ardour_audio_port_h__
#include <sigc++/signal.h>
#include <pbd/failed_constructor.h>
#include <ardour/ardour.h>
#include <jack/jack.h>
#include <ardour/port.h>
#include <ardour/buffer.h>
namespace ARDOUR {
class AudioEngine;
class AudioPort : public Port {
public:
virtual ~AudioPort() {
free (_port);
}
void cycle_start(nframes_t nframes) {
_buffer.set_data ((Sample*) jack_port_get_buffer (_port, nframes), nframes);
}
void cycle_end() {}
DataType type() const { return DataType(DataType::AUDIO); }
Buffer& get_buffer () {
return _buffer;
}
AudioBuffer& get_audio_buffer() {
return _buffer;
}
void reset_overs () {
_short_overs = 0;
_long_overs = 0;
_overlen = 0;
}
void reset_peak_meter () {
_peak = 0;
}
void reset_meters () {
reset_peak_meter ();
reset_overs ();
}
float peak_db() const { return _peak_db; }
jack_default_audio_sample_t peak() const { return _peak; }
uint32_t short_overs () const { return _short_overs; }
uint32_t long_overs () const { return _long_overs; }
static void set_short_over_length (nframes_t);
static void set_long_over_length (nframes_t);
protected:
friend class AudioEngine;
AudioPort (jack_port_t *port);
void reset ();
/* engine isn't supposed to access below here */
AudioBuffer _buffer;
nframes_t _overlen;
jack_default_audio_sample_t _peak;
float _peak_db;
uint32_t _short_overs;
uint32_t _long_overs;
static nframes_t _long_over_length;
static nframes_t _short_over_length;
};
} // namespace ARDOUR
#endif /* __ardour_audio_port_h__ */

View File

@@ -53,7 +53,7 @@ class AudioTrack : public Track
int use_diskstream (string name);
int use_diskstream (const PBD::ID& id);
int export_stuff (vector<Sample*>& buffers, uint32_t nbufs, nframes_t nframes, nframes_t end_frame);
int export_stuff (BufferSet& bufs, nframes_t nframes, nframes_t end_frame);
void freeze (InterThreadInfo&);
void unfreeze ();
@@ -65,15 +65,9 @@ class AudioTrack : public Track
protected:
XMLNode& state (bool full);
void passthru_silence (nframes_t start_frame, nframes_t end_frame,
nframes_t nframes, nframes_t offset, int declick,
bool meter);
uint32_t n_process_buffers ();
int _set_state (const XMLNode&, bool call_base);
int _set_state (const XMLNode&, bool call_base);
private:
int set_diskstream (boost::shared_ptr<AudioDiskstream>, void *);
int deprecated_use_diskstream_connections ();

View File

@@ -64,8 +64,11 @@ class AUPlugin : public ARDOUR::Plugin
void deactivate ();
void set_block_size (nframes_t nframes);
int connect_and_run (vector<Sample*>& bufs, uint32_t maxbuf, int32_t& in, int32_t& out, nframes_t nframes, nframes_t offset);
int connect_and_run (BufferSet& bufs, uint32_t& in, uint32_t& out, nframes_t nframes, nframes_t offset);
std::set<uint32_t> automatable() const;
void store_state (ARDOUR::PluginState&);
void restore_state (ARDOUR::PluginState&);
string describe_parameter (uint32_t);
string state_node_name () const { return "audiounit"; }
void print_parameter (uint32_t, char*, uint32_t len) const;

View File

@@ -46,6 +46,8 @@ class Port;
class AudioEngine : public sigc::trackable
{
public:
typedef std::set<Port*> Ports;
AudioEngine (std::string client_name);
virtual ~AudioEngine ();
@@ -113,11 +115,11 @@ class AudioEngine : public sigc::trackable
Port *register_input_port (DataType type, const std::string& portname);
Port *register_output_port (DataType type, const std::string& portname);
int unregister_port (Port *);
int unregister_port (Port &);
int connect (const std::string& source, const std::string& destination);
int disconnect (const std::string& source, const std::string& destination);
int disconnect (Port *);
int disconnect (Port &);
const char ** get_ports (const std::string& port_name_pattern, const std::string& type_name_pattern, uint32_t flags);
@@ -127,21 +129,19 @@ class AudioEngine : public sigc::trackable
void get_physical_outputs (std::vector<std::string>&);
void get_physical_inputs (std::vector<std::string>&);
std::string get_nth_physical_output (uint32_t n) {
return get_nth_physical (n, JackPortIsInput);
std::string get_nth_physical_output (DataType type, uint32_t n) {
return get_nth_physical (type, n, JackPortIsInput);
}
std::string get_nth_physical_input (uint32_t n) {
return get_nth_physical (n, JackPortIsOutput);
std::string get_nth_physical_input (DataType type, uint32_t n) {
return get_nth_physical (type, n, JackPortIsOutput);
}
nframes_t get_port_total_latency (const Port&);
void update_total_latencies ();
/* the caller may not delete the object pointed to by
the return value
/** Caller may not delete the object pointed to by the return value
*/
Port *get_port_by_name (const std::string& name, bool keep = true);
enum TransportState {
@@ -213,7 +213,6 @@ class AudioEngine : public sigc::trackable
bool reconnect_on_halt;
int _usecs_per_cycle;
typedef std::set<Port*> Ports;
SerializedRCUManager<Ports> ports;
int process_callback (nframes_t nframes);
@@ -223,9 +222,9 @@ class AudioEngine : public sigc::trackable
typedef std::list<PortConnection> PortConnections;
PortConnections port_connections;
void remove_connections_for (Port*);
void remove_connections_for (Port&);
std::string get_nth_physical (uint32_t which, int flags);
std::string get_nth_physical (DataType type, uint32_t n, int flags);
static int _xrun_callback (void *arg);
static int _graph_order_callback (void *arg);

View File

@@ -121,7 +121,7 @@ class AudioFileSource : public AudioSource {
to cause issues.
*/
virtual void handle_header_position_change () {}
virtual void handle_header_position_change ();
protected:

View File

@@ -44,7 +44,7 @@ class AudioPlaylist : public ARDOUR::Playlist
AudioPlaylist (boost::shared_ptr<const AudioPlaylist>, string name, bool hidden = false);
AudioPlaylist (boost::shared_ptr<const AudioPlaylist>, nframes_t start, nframes_t cnt, string name, bool hidden = false);
~AudioPlaylist (); /* public should use unref() */
~AudioPlaylist ();
void clear (bool with_signals=true);

View File

@@ -1,5 +1,5 @@
/*
Copyright (C) 2000-2001 Paul Davis
Copyright (C) 2000-2006 Paul Davis
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
@@ -54,24 +54,18 @@ class AudioRegion : public Region
~AudioRegion();
bool source_equivalent (boost::shared_ptr<const Region>) const;
bool speed_mismatch (float) const;
boost::shared_ptr<AudioSource> source (uint32_t n=0) const { if (n < sources.size()) return sources[n]; else return sources[0]; }
boost::shared_ptr<AudioSource> audio_source (uint32_t n=0) const;
void set_scale_amplitude (gain_t);
void set_scale_amplitude (gain_t);
gain_t scale_amplitude() const { return _scale_amplitude; }
void normalize_to (float target_in_dB = 0.0f);
uint32_t n_channels() const { return sources.size(); }
vector<string> master_source_names();
bool envelope_active () const { return _flags & Region::EnvelopeActive; }
bool fade_in_active () const { return _flags & Region::FadeIn; }
bool fade_out_active () const { return _flags & Region::FadeOut; }
bool captured() const { return !(_flags & (Region::Flag (Region::Import|Region::External))); }
Curve& fade_in() { return _fade_in; }
Curve& fade_out() { return _fade_out; }
@@ -129,8 +123,6 @@ class AudioRegion : public Region
int exportme (ARDOUR::Session&, ARDOUR::AudioExportSpecification&);
boost::shared_ptr<Region> get_parent() const;
/* xfade/fade interactions */
void suspend_fade_in ();
@@ -138,8 +130,6 @@ class AudioRegion : public Region
void resume_fade_in ();
void resume_fade_out ();
void set_playlist (boost::weak_ptr<Playlist>);
private:
friend class RegionFactory;
@@ -165,10 +155,6 @@ class AudioRegion : public Region
nframes_t read_frames = 0,
nframes_t skip_frames = 0) const;
bool verify_start (nframes_t position);
bool verify_length (nframes_t position);
bool verify_start_mutable (nframes_t& start);
bool verify_start_and_length (nframes_t start, nframes_t length);
void recompute_at_start ();
void recompute_at_end ();
@@ -178,13 +164,6 @@ class AudioRegion : public Region
void source_offset_changed ();
void listen_to_my_curves ();
void source_deleted ();
SourceList sources;
/** Used when timefx are applied, so we can always use the original source. */
SourceList master_sources;
mutable Curve _fade_in;
FadeShape _fade_in_shape;
mutable Curve _fade_out;
@@ -196,6 +175,13 @@ class AudioRegion : public Region
protected:
int set_live_state (const XMLNode&, Change&, bool send);
virtual bool verify_start (nframes_t);
virtual bool verify_start_and_length (nframes_t, nframes_t);
virtual bool verify_start_mutable (nframes_t&_start);
virtual bool verify_length (nframes_t);
/*virtual void recompute_at_start () = 0;
virtual void recompute_at_end () = 0;*/
};
} /* namespace ARDOUR */

View File

@@ -52,20 +52,7 @@ const nframes_t frames_per_peak = 256;
AudioSource (Session&, ustring name);
AudioSource (Session&, const XMLNode&);
virtual ~AudioSource ();
/* one could argue that this should belong to Source, but other data types
generally do not come with a model of "offset along an audio timeline"
so its here in AudioSource for now.
*/
virtual nframes_t natural_position() const { return 0; }
/* returns the number of items in this `audio_source' */
virtual nframes_t length() const {
return _length;
}
virtual nframes_t available_peaks (double zoom) const;
virtual nframes_t read (Sample *dst, nframes_t start, nframes_t cnt) const;
@@ -116,7 +103,6 @@ const nframes_t frames_per_peak = 256;
bool _peaks_built;
mutable Glib::Mutex _lock;
nframes_t _length;
ustring peakpath;
ustring _captured_for;
@@ -135,8 +121,6 @@ const nframes_t frames_per_peak = 256;
virtual ustring peak_path(ustring audio_path) = 0;
virtual ustring old_peak_path(ustring audio_path) = 0;
void update_length (nframes_t pos, nframes_t cnt);
private:
int peakfile;
nframes_t peak_leftover_cnt;

View File

@@ -19,19 +19,16 @@
#ifndef __ardour_buffer_h__
#define __ardour_buffer_h__
#define _XOPEN_SOURCE 600
#include <cstdlib> // for posix_memalign
#include <cstdlib>
#include <cassert>
#include <iostream>
#include <ardour/types.h>
#include <ardour/data_type.h>
#include <ardour/runtime_functions.h>
namespace ARDOUR {
/* Yes, this is a bit of a mess right now. I'll clean it up when everything
* using it works out.. */
/** A buffer of recordable/playable data.
*
* This is a datatype-agnostic base class for all buffers (there are no
@@ -44,12 +41,11 @@ namespace ARDOUR {
class Buffer
{
public:
Buffer(DataType type, size_t capacity)
: _type(type), _capacity(capacity), _size(0)
{}
virtual ~Buffer() {}
/** Factory function */
static Buffer* create(DataType type, size_t capacity);
/** Maximum capacity of buffer.
* Note in some cases the entire buffer may not contain valid data, use size. */
size_t capacity() const { return _capacity; }
@@ -61,10 +57,30 @@ public:
* Based on this you can static cast a Buffer* to the desired type. */
DataType type() const { return _type; }
bool silent() const { return _silent; }
/** Clear (eg zero, or empty) buffer starting at TIME @a offset */
virtual void silence(nframes_t len, nframes_t offset=0) = 0;
/** Clear the entire buffer */
virtual void clear() { silence(_capacity, 0); }
virtual void read_from(const Buffer& src, nframes_t offset, nframes_t len) = 0;
protected:
Buffer(DataType type, size_t capacity)
: _type(type), _capacity(capacity), _size(0), _silent(true)
{}
DataType _type;
size_t _capacity;
size_t _size;
bool _silent;
private:
// Prevent copies (undefined)
Buffer(const Buffer& copy);
void operator=(const Buffer& other);
};
@@ -75,32 +91,140 @@ protected:
class AudioBuffer : public Buffer
{
public:
AudioBuffer(size_t capacity)
: Buffer(DataType::AUDIO, capacity)
, _data(NULL)
AudioBuffer(size_t capacity);
~AudioBuffer();
void silence(nframes_t len, nframes_t offset=0)
{
_size = capacity; // For audio buffers, size = capacity (always)
#ifdef NO_POSIX_MEMALIGN
_data = (Sample *) malloc(sizeof(Sample) * capacity);
#else
posix_memalign((void**)_data, 16, sizeof(Sample) * capacity);
#endif
assert(_data);
memset(_data, 0, sizeof(Sample) * capacity);
if (!_silent) {
assert(_capacity > 0);
assert(offset + len <= _capacity);
memset(_data + offset, 0, sizeof (Sample) * len);
if (offset == 0 && len == _capacity) {
_silent = true;
}
}
}
/** Read @a len frames FROM THE START OF @a src into self at @a offset */
void read_from(const Buffer& src, nframes_t len, nframes_t offset)
{
assert(_capacity > 0);
assert(src.type() == _type == DataType::AUDIO);
assert(offset + len <= _capacity);
memcpy(_data + offset, ((AudioBuffer&)src).data(), sizeof(Sample) * len);
_silent = src.silent();
}
/** Accumulate (add)@a len frames FROM THE START OF @a src into self at @a offset */
void accumulate_from(const AudioBuffer& src, nframes_t len, nframes_t offset)
{
assert(_capacity > 0);
assert(offset + len <= _capacity);
Sample* const dst_raw = _data + offset;
const Sample* const src_raw = src.data();
for (nframes_t n = 0; n < len; ++n) {
dst_raw[n] += src_raw[n];
}
_silent = (src.silent() && _silent);
}
/** Accumulate (add) @a len frames FROM THE START OF @a src into self at @a offset
* scaling by @a gain_coeff */
void accumulate_with_gain_from(const AudioBuffer& src, nframes_t len, nframes_t offset, gain_t gain_coeff)
{
assert(_capacity > 0);
assert(offset + len <= _capacity);
Sample* const dst_raw = _data + offset;
const Sample* const src_raw = src.data();
mix_buffers_with_gain (dst_raw, src_raw, len, gain_coeff);
_silent = ( (src.silent() && _silent) || (_silent && gain_coeff == 0) );
}
void apply_gain(gain_t gain, nframes_t len, nframes_t offset=0) {
apply_gain_to_buffer (_data + offset, len, gain);
}
const Sample* data() const { return _data; }
Sample* data() { return _data; }
/** Set the data contained by this buffer manually (for setting directly to jack buffer).
*
* Constructor MUST have been passed capacity=0 or this will die (to prevent mem leaks).
*/
void set_data(Sample* data, size_t size)
{
assert(!_owns_data); // prevent leaks
_capacity = size;
_size = size;
_data = data;
_silent = false;
}
const Sample* data () const { return _data; }
Sample* data () { return _data; }
const Sample* data(nframes_t nframes, nframes_t offset) const
{ assert(offset + nframes <= _capacity); return _data + offset; }
Sample* data (nframes_t nframes, nframes_t offset)
{ assert(offset + nframes <= _capacity); return _data + offset; }
private:
// These are undefined (prevent copies)
AudioBuffer(const AudioBuffer& copy);
AudioBuffer& operator=(const AudioBuffer& copy);
bool _owns_data;
Sample* _data; ///< Actual buffer contents
};
/** Buffer containing 8-bit unsigned char (MIDI) data. */
class MidiBuffer : public Buffer
{
public:
MidiBuffer(size_t capacity);
~MidiBuffer();
void silence(nframes_t dur, nframes_t offset=0);
void read_from(const Buffer& src, nframes_t nframes, nframes_t offset);
bool push_back(const MidiEvent& event);
const MidiEvent& operator[](size_t i) const { assert(i < _size); return _events[i]; }
MidiEvent& operator[](size_t i) { assert(i < _size); return _events[i]; }
static size_t max_event_size() { return MAX_EVENT_SIZE; }
//void set_size(size_t size) { _size = size; }
//const RawMidi* data() const { return _data; }
//RawMidi* data() { return _data; }
private:
// These are undefined (prevent copies)
MidiBuffer(const MidiBuffer& copy);
MidiBuffer& operator=(const MidiBuffer& copy);
// FIXME: Jack needs to tell us this
static const size_t MAX_EVENT_SIZE = 4; // bytes
/* We use _size as "number of events", so the size of _data is
* (_size * MAX_EVENT_SIZE)
*/
MidiEvent* _events; ///< Event structs that point to offsets in _data
RawMidi* _data; ///< MIDI, straight up. No time stamps.
};
} // namespace ARDOUR
#endif // __ardour_buffer_h__

View File

@@ -0,0 +1,159 @@
/*
Copyright (C) 2006 Paul Davis
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 __ardour_buffer_set_h__
#define __ardour_buffer_set_h__
#include <cassert>
#include <vector>
#include <ardour/chan_count.h>
#include <ardour/data_type.h>
namespace ARDOUR {
class Buffer;
class AudioBuffer;
class MidiBuffer;
class PortSet;
/** A set of buffers of various types.
*
* These are mainly accessed from Session and passed around as scratch buffers
* (eg as parameters to run() methods) to do in-place signal processing.
*
* There are two types of counts associated with a BufferSet - available,
* and the 'use count'. Available is the actual number of allocated buffers
* (and so is the maximum acceptable value for the use counts).
*
* The use counts are how things determine the form of their input and inform
* others the form of their output (eg what they did to the BufferSet).
* Setting the use counts is realtime safe.
*/
class BufferSet
{
public:
BufferSet();
~BufferSet();
void clear();
void attach_buffers(PortSet& ports);
void ensure_buffers(const ChanCount& count, size_t buffer_capacity);
void ensure_buffers(DataType type, size_t num_buffers, size_t buffer_capacity);
const ChanCount& available() const { return _available; }
ChanCount& available() { return _available; }
const ChanCount& count() const { return _count; }
ChanCount& count() { return _count; }
void set_count(const ChanCount& count) { _count = count; }
size_t buffer_capacity(DataType type) const;
Buffer& get(DataType type, size_t i)
{
assert(i <= _count.get(type));
return *_buffers[type.to_index()][i];
}
AudioBuffer& get_audio(size_t i)
{
return (AudioBuffer&)get(DataType::AUDIO, i);
}
MidiBuffer& get_midi(size_t i)
{
return (MidiBuffer&)get(DataType::MIDI, i);
}
void read_from(BufferSet& in, jack_nframes_t nframes, jack_nframes_t offset=0);
// ITERATORS
// FIXME: this is a filthy copy-and-paste mess
// FIXME: litter these with assertions
class audio_iterator {
public:
AudioBuffer& operator*() { return _set.get_audio(_index); }
AudioBuffer* operator->() { return &_set.get_audio(_index); }
audio_iterator& operator++() { ++_index; return *this; } // yes, prefix only
bool operator==(const audio_iterator& other) { return (_index == other._index); }
bool operator!=(const audio_iterator& other) { return (_index != other._index); }
private:
friend class BufferSet;
audio_iterator(BufferSet& list, size_t index) : _set(list), _index(index) {}
BufferSet& _set;
size_t _index;
};
audio_iterator audio_begin() { return audio_iterator(*this, 0); }
audio_iterator audio_end() { return audio_iterator(*this, _count.get(DataType::AUDIO)); }
class iterator {
public:
Buffer& operator*() { return _set.get(_type, _index); }
Buffer* operator->() { return &_set.get(_type, _index); }
iterator& operator++() { ++_index; return *this; } // yes, prefix only
bool operator==(const iterator& other) { return (_index == other._index); }
bool operator!=(const iterator& other) { return (_index != other._index); }
iterator operator=(const iterator& other) { _set = other._set; _type = other._type; _index = other._index; return *this; }
private:
friend class BufferSet;
iterator(BufferSet& list, DataType type, size_t index)
: _set(list), _type(type), _index(index) {}
BufferSet& _set;
DataType _type;
size_t _index;
};
iterator begin(DataType type) { return iterator(*this, type, 0); }
iterator end(DataType type) { return iterator(*this, type, _count.get(type)); }
private:
typedef std::vector<Buffer*> BufferVec;
/// Vector of vectors, indexed by DataType::to_index()
std::vector<BufferVec> _buffers;
/// Use counts (there may be more actual buffers than this)
ChanCount _count;
/// Available counts (number of buffers actually allocated)
ChanCount _available;
/// Whether we (don't) 'own' the contained buffers (are a mirror of a PortSet)
bool _is_mirror;
};
} // namespace ARDOUR
#endif // __ardour_buffer_set_h__

View File

@@ -0,0 +1,115 @@
/*
Copyright (C) 2006 Paul Davis
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.
$Id: insert.cc 712 2006-07-28 01:08:57Z drobilla $
*/
#ifndef __ardour_chan_count_h__
#define __ardour_chan_count_h__
#include <ardour/data_type.h>
namespace ARDOUR {
class ChanCount {
public:
ChanCount() { reset(); }
// Convenience constructor for making single-typed streams (stereo, mono, etc)
ChanCount(DataType type, size_t channels)
{
reset();
set(type, channels);
}
void reset()
{
for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
_counts[(*t).to_index()] = 0;
}
}
void set(DataType type, size_t count) { _counts[type.to_index()] = count; }
size_t get(DataType type) const { return _counts[type.to_index()]; }
size_t get_total() const
{
size_t ret = 0;
for (size_t i=0; i < DataType::num_types; ++i)
ret += _counts[i];
return ret;
}
bool operator==(const ChanCount& other) const
{
for (size_t i=0; i < DataType::num_types; ++i)
if (_counts[i] != other._counts[i])
return false;
return true;
}
bool operator!=(const ChanCount& other) const
{
return ! (*this == other);
}
bool operator<(const ChanCount& other) const
{
for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
if (_counts[(*t).to_index()] > other._counts[(*t).to_index()]) {
return false;
}
}
return (*this != other);
}
bool operator<=(const ChanCount& other) const
{
return ( (*this < other) || (*this == other) );
}
bool operator>(const ChanCount& other) const
{
for (DataType::iterator t = DataType::begin(); t != DataType::end(); ++t) {
if (_counts[(*t).to_index()] < other._counts[(*t).to_index()]) {
return false;
}
}
return (*this != other);
}
bool operator>=(const ChanCount& other) const
{
return ( (*this > other) || (*this == other) );
}
static const ChanCount INFINITE;
static const ChanCount ZERO;
private:
size_t _counts[DataType::num_types];
};
} // namespace ARDOUR
#endif // __ardour_chan_count_h__

View File

@@ -19,54 +19,103 @@
#ifndef __ardour_data_type_h__
#define __ardour_data_type_h__
#include <string>
#include <ardour/data_type.h>
#include <jack/jack.h>
namespace ARDOUR {
/** A type of Data Ardour is capable of processing.
*
* The majority of this class is dedicated to conversion to and from various
* other type representations, simple comparison between then, etc. This code
* is deliberately 'ugly' so other code doesn't have to be.
*/
class DataType
{
public:
/// WARNING: make REALLY sure you don't mess up indexes if you change this
enum Symbol {
NIL = 0,
AUDIO,
MIDI
};
/** Number of types (not including NIL).
* WARNING: make sure this matches Symbol!
*/
static const size_t num_types = 2;
DataType(const Symbol& symbol)
: _symbol(symbol)
{}
/** Construct from a string (Used for loading from XML) */
DataType(const string& str) {
/** Construct from a string (Used for loading from XML and Ports)
* The string can be as in an XML file (eg "audio" or "midi"), or a
* Jack type string (from jack_port_type) */
DataType(const std::string& str) {
if (str == "audio")
_symbol = AUDIO;
//else if (str == "midi")
// _symbol = MIDI;
else if (str == JACK_DEFAULT_AUDIO_TYPE)
_symbol = AUDIO;
else if (str == "midi")
_symbol = MIDI;
else if (str == JACK_DEFAULT_MIDI_TYPE)
_symbol = MIDI;
else
_symbol = NIL;
}
bool operator==(const Symbol symbol) { return _symbol == symbol; }
bool operator!=(const Symbol symbol) { return _symbol != symbol; }
/** Get the Jack type this DataType corresponds to */
const char* to_jack_type() {
const char* to_jack_type() const {
switch (_symbol) {
case AUDIO: return JACK_DEFAULT_AUDIO_TYPE;
//case MIDI: return JACK_DEFAULT_MIDI_TYPE;
case MIDI: return JACK_DEFAULT_MIDI_TYPE;
default: return "";
}
}
/** Inverse of the from-string constructor */
const char* to_string() {
const char* to_string() const {
switch (_symbol) {
case AUDIO: return "audio";
//case MIDI: return "midi";
case MIDI: return "midi";
default: return "unknown"; // reeeally shouldn't ever happen
}
}
//Symbol to_symbol() const { return _symbol; }
inline size_t to_index() const { return (size_t)_symbol - 1; }
/** DataType iterator, for writing generic loops that iterate over all
* available types.
*/
class iterator {
public:
iterator(size_t index) : _index(index) {}
DataType operator*() { return DataType((Symbol)_index); }
iterator& operator++() { ++_index; return *this; } // yes, prefix only
bool operator==(const iterator& other) { return (_index == other._index); }
bool operator!=(const iterator& other) { return (_index != other._index); }
private:
friend class DataType;
size_t _index;
};
static iterator begin() { return iterator(1); }
static iterator end() { return iterator(num_types+1); }
bool operator==(const Symbol symbol) { return (_symbol == symbol); }
bool operator!=(const Symbol symbol) { return (_symbol != symbol); }
bool operator==(const DataType other) { return (_symbol == other._symbol); }
bool operator!=(const DataType other) { return (_symbol != other._symbol); }
private:
Symbol _symbol;
};

View File

@@ -114,7 +114,7 @@ class Diskstream : public PBD::StatefulDestructible
nframes_t get_capture_start_frame (uint32_t n=0);
nframes_t get_captured_frames (uint32_t n=0);
uint32_t n_channels() { return _n_channels; }
ChanCount n_channels() { return _n_channels; }
static nframes_t disk_io_frames() { return disk_io_chunk_frames; }
static void set_disk_io_chunk_frames (uint32_t n) { disk_io_chunk_frames = n; }
@@ -123,7 +123,6 @@ class Diskstream : public PBD::StatefulDestructible
virtual XMLNode& get_state(void) = 0;
virtual int set_state(const XMLNode& node) = 0;
// FIXME: makes sense for all diskstream types?
virtual void monitor_input (bool) {}
nframes_t capture_offset() const { return _capture_offset; }
@@ -230,8 +229,8 @@ class Diskstream : public PBD::StatefulDestructible
virtual void get_input_sources () = 0;
virtual void check_record_status (nframes_t transport_frame, nframes_t nframes, bool can_record) = 0;
virtual void set_align_style_from_io() {}
virtual void setup_destructive_playlist () = 0;
virtual void use_destructive_playlist () = 0;
virtual void setup_destructive_playlist () {}
virtual void use_destructive_playlist () {}
static nframes_t disk_io_chunk_frames;
std::vector<CaptureInfo*> capture_info;
@@ -242,7 +241,7 @@ class Diskstream : public PBD::StatefulDestructible
string _name;
ARDOUR::Session& _session;
ARDOUR::IO* _io;
uint32_t _n_channels;
ChanCount _n_channels;
boost::shared_ptr<Playlist> _playlist;

View File

@@ -27,6 +27,7 @@
#include <sigc++/signal.h>
#include <ardour/ardour.h>
#include <ardour/redirect.h>
#include <ardour/plugin_state.h>
#include <ardour/types.h>
class XMLNode;
@@ -49,7 +50,8 @@ class Insert : public Redirect
virtual ~Insert() { }
virtual void run (vector<Sample *>& bufs, uint32_t nbufs, nframes_t nframes, nframes_t offset) = 0;
virtual void run (BufferSet& bufs, nframes_t start_frame, nframes_t end_frame, nframes_t nframes, nframes_t offset) = 0;
virtual void activate () {}
virtual void deactivate () {}
@@ -71,12 +73,13 @@ class PortInsert : public Insert
int set_state(const XMLNode&);
void init ();
void run (vector<Sample *>& bufs, uint32_t nbufs, nframes_t nframes, nframes_t offset);
void run (BufferSet& bufs, nframes_t start_frame, nframes_t end_frame, nframes_t nframes, nframes_t offset);
nframes_t latency();
uint32_t output_streams() const;
uint32_t input_streams() const;
ChanCount output_streams() const;
ChanCount input_streams() const;
int32_t can_support_input_configuration (int32_t) const;
int32_t configure_io (int32_t magic, int32_t in, int32_t out);
@@ -102,17 +105,18 @@ class PluginInsert : public Insert
XMLNode& get_state(void);
int set_state(const XMLNode&);
void run (vector<Sample *>& bufs, uint32_t nbufs, nframes_t nframes, nframes_t offset);
void run (BufferSet& bufs, nframes_t start_frame, nframes_t end_frame, nframes_t nframes, nframes_t offset);
void silence (nframes_t nframes, nframes_t offset);
void activate ();
void deactivate ();
void set_block_size (nframes_t nframes);
uint32_t output_streams() const;
uint32_t input_streams() const;
uint32_t natural_output_streams() const;
uint32_t natural_input_streams() const;
ChanCount output_streams() const;
ChanCount input_streams() const;
ChanCount natural_output_streams() const;
ChanCount natural_input_streams() const;
int set_count (uint32_t num);
uint32_t get_count () const { return _plugins.size(); }
@@ -153,8 +157,9 @@ class PluginInsert : public Insert
void parameter_changed (uint32_t, float);
vector<boost::shared_ptr<Plugin> > _plugins;
void automation_run (vector<Sample *>& bufs, uint32_t nbufs, nframes_t nframes, nframes_t offset);
void connect_and_run (vector<Sample *>& bufs, uint32_t nbufs, nframes_t nframes, nframes_t offset, bool with_auto, nframes_t now = 0);
void automation_run (BufferSet& bufs, nframes_t nframes, nframes_t offset);
void connect_and_run (BufferSet& bufs, nframes_t nframes, nframes_t offset, bool with_auto, nframes_t now = 0);
void init ();
void set_automatable ();

View File

@@ -38,6 +38,8 @@
#include <ardour/curve.h>
#include <ardour/types.h>
#include <ardour/data_type.h>
#include <ardour/port_set.h>
#include <ardour/chan_count.h>
using std::string;
using std::vector;
@@ -48,9 +50,13 @@ namespace ARDOUR {
class Session;
class AudioEngine;
class Port;
class Connection;
class Panner;
class PeakMeter;
class Port;
class AudioPort;
class MidiPort;
class BufferSet;
/** A collection of input and output ports with connections.
*
@@ -67,50 +73,48 @@ class IO : public PBD::StatefulDestructible
int input_min = -1, int input_max = -1,
int output_min = -1, int output_max = -1,
DataType default_type = DataType::AUDIO);
IO (Session&, const XMLNode&, DataType default_type = DataType::AUDIO);
virtual ~IO();
int input_minimum() const { return _input_minimum; }
int input_maximum() const { return _input_maximum; }
int output_minimum() const { return _output_minimum; }
int output_maximum() const { return _output_maximum; }
void set_input_minimum (int n);
void set_input_maximum (int n);
void set_output_minimum (int n);
void set_output_maximum (int n);
DataType default_type() const { return _default_type; }
ChanCount input_minimum() const { return _input_minimum; }
ChanCount input_maximum() const { return _input_maximum; }
ChanCount output_minimum() const { return _output_minimum; }
ChanCount output_maximum() const { return _output_maximum; }
void set_input_minimum (ChanCount n);
void set_input_maximum (ChanCount n);
void set_output_minimum (ChanCount n);
void set_output_maximum (ChanCount n);
DataType default_type() const { return _default_type; }
void set_default_type(DataType t) { _default_type = t; }
const string& name() const { return _name; }
virtual int set_name (string str, void *src);
virtual void silence (nframes_t, nframes_t offset);
// These should be moved in to a separate object that manipulates an IO
void pan (vector<Sample*>& bufs, uint32_t nbufs, nframes_t nframes, nframes_t offset, gain_t gain_coeff);
void pan_automated (vector<Sample*>& bufs, uint32_t nbufs, nframes_t start_frame, nframes_t end_frame,
nframes_t nframes, nframes_t offset);
void collect_input (vector<Sample*>&, uint32_t nbufs, nframes_t nframes, nframes_t offset);
void deliver_output (vector<Sample*>&, uint32_t nbufs, nframes_t nframes, nframes_t offset);
void deliver_output_no_pan (vector<Sample*>&, uint32_t nbufs, nframes_t nframes, nframes_t offset);
void collect_input (BufferSet& bufs, nframes_t nframes, nframes_t offset);
void deliver_output (BufferSet& bufs, nframes_t start_frame, nframes_t end_frame,
nframes_t nframes, nframes_t offset);
void just_meter_input (nframes_t start_frame, nframes_t end_frame,
nframes_t nframes, nframes_t offset);
virtual uint32_t n_process_buffers () { return 0; }
virtual void set_gain (gain_t g, void *src);
void inc_gain (gain_t delta, void *src);
gain_t gain () const { return _desired_gain; }
virtual gain_t effective_gain () const;
void set_phase_invert (bool yn, void *src);
bool phase_invert() const { return _phase_invert; }
Panner& panner() { return *_panner; }
Panner& panner() { return *_panner; }
PeakMeter& peak_meter() { return *_meter; }
const Panner& panner() const { return *_panner; }
int ensure_io (uint32_t, uint32_t, bool clear, void *src);
int ensure_io (ChanCount in, ChanCount out, bool clear, void *src);
int use_input_connection (Connection&, void *src);
int use_output_connection (Connection&, void *src);
@@ -139,24 +143,34 @@ class IO : public PBD::StatefulDestructible
nframes_t input_latency() const;
void set_port_latency (nframes_t);
const PortSet& inputs() const { return _inputs; }
const PortSet& outputs() const { return _outputs; }
Port *output (uint32_t n) const {
if (n < _noutputs) {
return _outputs[n];
if (n < _outputs.num_ports()) {
return _outputs.port(n);
} else {
return 0;
}
}
Port *input (uint32_t n) const {
if (n < _ninputs) {
return _inputs[n];
if (n < _inputs.num_ports()) {
return _inputs.port(n);
} else {
return 0;
}
}
uint32_t n_inputs () const { return _ninputs; }
uint32_t n_outputs () const { return _noutputs; }
AudioPort* audio_input(uint32_t n) const;
AudioPort* audio_output(uint32_t n) const;
MidiPort* midi_input(uint32_t n) const;
MidiPort* midi_output(uint32_t n) const;
const ChanCount& n_inputs () const { return _inputs.count(); }
const ChanCount& n_outputs () const { return _outputs.count(); }
void attach_buffers(ChanCount ignored);
sigc::signal<void,IOChange,void*> input_changed;
sigc::signal<void,IOChange,void*> output_changed;
@@ -169,46 +183,26 @@ class IO : public PBD::StatefulDestructible
int set_state (const XMLNode&);
static int disable_connecting (void);
static int enable_connecting (void);
static int disable_ports (void);
static int enable_ports (void);
static int disable_panners (void);
static int reset_panners (void);
static sigc::signal<int> PortsLegal;
static sigc::signal<int> PannersLegal;
static sigc::signal<int> ConnectingLegal;
static sigc::signal<void,uint32_t> MoreOutputs;
static sigc::signal<int> PortsCreated;
static sigc::signal<int> PortsLegal;
static sigc::signal<int> PannersLegal;
static sigc::signal<int> ConnectingLegal;
static sigc::signal<void,ChanCount> MoreChannels;
static sigc::signal<int> PortsCreated;
PBD::Controllable& gain_control() {
return _gain_control;
}
/* Peak metering */
float peak_input_power (uint32_t n) {
if (_ninputs == 0) {
return minus_infinity();
} else if (n < std::max (_ninputs, _noutputs)) {
return _visible_peak_power[n];
} else {
return minus_infinity();
}
}
float max_peak_power (uint32_t n) {
if (_ninputs == 0) {
return minus_infinity();
} else if (n < std::max (_ninputs, _noutputs)) {
return _max_peak_power[n];
} else {
return minus_infinity();
}
}
void reset_max_peak_meters ();
static void update_meters();
@@ -222,11 +216,11 @@ class IO : public PBD::StatefulDestructible
/* automation */
static void set_automation_interval (jack_nframes_t frames) {
static void set_automation_interval (nframes_t frames) {
_automation_interval = frames;
}
static jack_nframes_t automation_interval() {
static nframes_t automation_interval() {
return _automation_interval;
}
@@ -277,33 +271,28 @@ class IO : public PBD::StatefulDestructible
protected:
Session& _session;
Panner* _panner;
BufferSet* _output_buffers; //< Set directly to output port buffers
gain_t _gain;
gain_t _effective_gain;
gain_t _desired_gain;
Glib::Mutex declick_lock;
vector<Port*> _outputs;
vector<Port*> _inputs;
vector<float> _peak_power;
vector<float> _visible_peak_power;
vector<float> _max_peak_power;
PortSet _outputs;
PortSet _inputs;
PeakMeter* _meter;
string _name;
Connection* _input_connection;
Connection* _output_connection;
bool no_panner_reset;
bool _phase_invert;
XMLNode* deferred_state;
DataType _default_type;
bool _ignore_gain_on_deliver;
virtual void set_deferred_state() {}
void reset_peak_meters();
void reset_panner ();
virtual uint32_t pans_required() const { return _ninputs; }
static void apply_declick (vector<Sample*>&, uint32_t nbufs, nframes_t nframes,
gain_t initial, gain_t target, bool invert_polarity);
virtual uint32_t pans_required() const
{ return _inputs.count().get(DataType::AUDIO); }
struct GainControllable : public PBD::Controllable {
GainControllable (std::string name, IO& i) : Controllable (name), io (i) {}
@@ -339,10 +328,9 @@ class IO : public PBD::StatefulDestructible
static bool connecting_legal;
static bool ports_legal;
private:
BufferSet& output_buffers() { return *_output_buffers; }
uint32_t _ninputs;
uint32_t _noutputs;
private:
/* are these the best variable names ever, or what? */
@@ -359,10 +347,10 @@ class IO : public PBD::StatefulDestructible
sigc::connection port_legal_c;
sigc::connection panner_legal_c;
int _input_minimum;
int _input_maximum;
int _output_minimum;
int _output_maximum;
ChanCount _input_minimum;
ChanCount _input_maximum;
ChanCount _output_minimum;
ChanCount _output_maximum;
static int parse_io_string (const string&, vector<string>& chns);
@@ -372,8 +360,8 @@ class IO : public PBD::StatefulDestructible
int set_sources (vector<string>&, void *src, bool add);
int set_destinations (vector<string>&, void *src, bool add);
int ensure_inputs (uint32_t, bool clear, bool lockit, void *src);
int ensure_outputs (uint32_t, bool clear, bool lockit, void *src);
int ensure_inputs (ChanCount, bool clear, bool lockit, void *src);
int ensure_outputs (ChanCount, bool clear, bool lockit, void *src);
void drop_input_connection ();
void drop_output_connection ();
@@ -389,8 +377,8 @@ class IO : public PBD::StatefulDestructible
void setup_peak_meters ();
void meter ();
bool ensure_inputs_locked (uint32_t, bool clear, void *src);
bool ensure_outputs_locked (uint32_t, bool clear, void *src);
bool ensure_inputs_locked (ChanCount, bool clear, void *src);
bool ensure_outputs_locked (ChanCount, bool clear, void *src);
int32_t find_input_port_hole ();
int32_t find_output_port_hole ();

View File

@@ -32,6 +32,7 @@
#include <jack/types.h>
#include <ardour/ladspa.h>
#include <ardour/plugin_state.h>
#include <ardour/plugin.h>
#include <ardour/ladspa_plugin.h>
@@ -81,7 +82,9 @@ class LadspaPlugin : public ARDOUR::Plugin
}
void set_block_size (nframes_t nframes) {}
int connect_and_run (vector<Sample*>& bufs, uint32_t maxbuf, int32_t& in, int32_t& out, nframes_t nframes, nframes_t offset);
int connect_and_run (BufferSet& bufs, uint32_t& in, uint32_t& out, nframes_t nframes, nframes_t offset);
void store_state (ARDOUR::PluginState&);
void restore_state (ARDOUR::PluginState&);
string describe_parameter (uint32_t);
string state_node_name() const { return "ladspa"; }
void print_parameter (uint32_t, char*, uint32_t len) const;

View File

@@ -0,0 +1,76 @@
/*
Copyright (C) 2006 Paul Davis
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 __ardour_meter_h__
#define __ardour_meter_h__
#include <vector>
#include <ardour/types.h>
#include <pbd/fastlog.h>
namespace ARDOUR {
class BufferSet;
class ChanCount;
class Session;
/** Meters peaks on the input and stores them for access.
*/
class PeakMeter {
public:
PeakMeter(Session& s) : _session(s) {}
void setup (const ChanCount& in);
void reset ();
void reset_max ();
/** Compute peaks */
void run (BufferSet& bufs, nframes_t nframes, nframes_t offset=0);
float peak_power (uint32_t n) {
if (n < _visible_peak_power.size()) {
return _visible_peak_power[n];
} else {
return minus_infinity();
}
}
float max_peak_power (uint32_t n) {
if (n < _max_peak_power.size()) {
return _max_peak_power[n];
} else {
return minus_infinity();
}
}
private:
friend class IO;
void meter();
Session& _session;
std::vector<float> _peak_power;
std::vector<float> _visible_peak_power;
std::vector<float> _max_peak_power;
};
} // namespace ARDOUR
#endif // __ardour_meter_h__

View File

@@ -0,0 +1,165 @@
/*
Copyright (C) 2000 Paul Davis
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.
$Id: diskstream.h 579 2006-06-12 19:56:37Z essej $
*/
#ifndef __ardour_midi_diskstream_h__
#define __ardour_midi_diskstream_h__
#include <sigc++/signal.h>
#include <cmath>
#include <cassert>
#include <string>
#include <queue>
#include <map>
#include <vector>
#include <time.h>
#include <pbd/fastlog.h>
#include <pbd/ringbufferNPT.h>
#include <ardour/ardour.h>
#include <ardour/configuration.h>
#include <ardour/session.h>
#include <ardour/route_group.h>
#include <ardour/route.h>
#include <ardour/port.h>
#include <ardour/utils.h>
#include <ardour/diskstream.h>
#include <ardour/midi_playlist.h>
#include <ardour/midi_ring_buffer.h>
struct tm;
namespace ARDOUR {
class MidiEngine;
class Send;
class Session;
class MidiPlaylist;
class SMFSource;
class IO;
class MidiDiskstream : public Diskstream
{
public:
MidiDiskstream (Session &, const string& name, Diskstream::Flag f = Recordable);
MidiDiskstream (Session &, const XMLNode&);
~MidiDiskstream();
float playback_buffer_load() const;
float capture_buffer_load() const;
void get_playback(MidiBuffer& dst, nframes_t start, nframes_t end);
void set_record_enabled (bool yn);
boost::shared_ptr<MidiPlaylist> midi_playlist () { return boost::dynamic_pointer_cast<MidiPlaylist>(_playlist); }
int use_playlist (boost::shared_ptr<Playlist>);
int use_new_playlist ();
int use_copy_playlist ();
/* stateful */
XMLNode& get_state(void);
int set_state(const XMLNode& node);
void monitor_input (bool);
boost::shared_ptr<SMFSource> write_source () { return _write_source; }
int set_destructive (bool yn); // doom!
protected:
friend class Session;
/* the Session is the only point of access for these
because they require that the Session is "inactive"
while they are called.
*/
void set_pending_overwrite(bool);
int overwrite_existing_buffers ();
void set_block_size (nframes_t);
int internal_playback_seek (nframes_t distance);
int can_internal_playback_seek (nframes_t distance);
int rename_write_sources ();
void reset_write_sources (bool, bool force = false);
void non_realtime_input_change ();
protected:
int seek (nframes_t which_sample, bool complete_refill = false);
protected:
friend class MidiTrack;
int process (nframes_t transport_frame, nframes_t nframes, nframes_t offset, bool can_record, bool rec_monitors_input);
bool commit (nframes_t nframes);
private:
/* The two central butler operations */
int do_flush (Session::RunContext context, bool force = false);
int do_refill ();
int do_refill_with_alloc();
int read (nframes_t& start, nframes_t cnt, bool reversed);
void finish_capture (bool rec_monitors_input);
void transport_stopped (struct tm&, time_t, bool abort);
void init (Diskstream::Flag);
int use_new_write_source (uint32_t n=0);
int find_and_use_playlist (const string&);
void allocate_temporary_buffers ();
int use_pending_capture_data (XMLNode& node);
void get_input_sources ();
void check_record_status (nframes_t transport_frame, nframes_t nframes, bool can_record);
void set_align_style_from_io();
void engage_record_enable ();
void disengage_record_enable ();
// FIXME: This is basically a single ChannelInfo.. abstractify that concept?
MidiRingBuffer* _playback_buf;
MidiRingBuffer* _capture_buf;
//RawMidi* _current_playback_buffer;
//RawMidi* _current_capture_buffer;
//RawMidi* _playback_wrap_buffer;
//RawMidi* _capture_wrap_buffer;
MidiPort* _source_port;
boost::shared_ptr<SMFSource> _write_source;
RingBufferNPT<CaptureTransition>* _capture_transition_buf;
//RingBufferNPT<RawMidi>::rw_vector _playback_vector;
//RingBufferNPT<RawMidi>::rw_vector _capture_vector;
nframes_t _last_flush_frame;
};
}; /* namespace ARDOUR */
#endif /* __ardour_midi_diskstream_h__ */

View File

@@ -0,0 +1,136 @@
/* Definitions to ease working with raw MIDI.
*
* Adapted from ALSA's asounddef.h
*
* This library is free software; you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 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 Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*
*/
#ifndef MIDI_H
#define MIDI_H
/**
* \defgroup midi MIDI Definitions
* MIDI command and controller number definitions.
* \{
*/
// Commands:
#define MIDI_CMD_NOTE_OFF 0x80 /**< note off */
#define MIDI_CMD_NOTE_ON 0x90 /**< note on */
#define MIDI_CMD_NOTE_PRESSURE 0xA0 /**< key pressure */
#define MIDI_CMD_CONTROL 0xB0 /**< control change */
#define MIDI_CMD_PGM_CHANGE 0xC0 /**< program change */
#define MIDI_CMD_CHANNEL_PRESSURE 0xD0 /**< channel pressure */
#define MIDI_CMD_BENDER 0xE0 /**< pitch bender */
#define MIDI_CMD_COMMON_SYSEX 0xF0 /**< sysex (system exclusive) begin */
#define MIDI_CMD_COMMON_MTC_QUARTER 0xF1 /**< MTC quarter frame */
#define MIDI_CMD_COMMON_SONG_POS 0xF2 /**< song position */
#define MIDI_CMD_COMMON_SONG_SELECT 0xF3 /**< song select */
#define MIDI_CMD_COMMON_TUNE_REQUEST 0xF6 /**< tune request */
#define MIDI_CMD_COMMON_SYSEX_END 0xF7 /**< end of sysex */
#define MIDI_CMD_COMMON_CLOCK 0xF8 /**< clock */
#define MIDI_CMD_COMMON_TICK 0xF9 /**< tick */
#define MIDI_CMD_COMMON_START 0xFA /**< start */
#define MIDI_CMD_COMMON_CONTINUE 0xFB /**< continue */
#define MIDI_CMD_COMMON_STOP 0xFC /**< stop */
#define MIDI_CMD_COMMON_SENSING 0xFE /**< active sensing */
#define MIDI_CMD_COMMON_RESET 0xFF /**< reset */
// Controllers:
#define MIDI_CTL_MSB_BANK 0x00 /**< Bank selection */
#define MIDI_CTL_MSB_MODWHEEL 0x01 /**< Modulation */
#define MIDI_CTL_MSB_BREATH 0x02 /**< Breath */
#define MIDI_CTL_MSB_FOOT 0x04 /**< Foot */
#define MIDI_CTL_MSB_PORTAMENTO_TIME 0x05 /**< Portamento time */
#define MIDI_CTL_MSB_DATA_ENTRY 0x06 /**< Data entry */
#define MIDI_CTL_MSB_MAIN_VOLUME 0x07 /**< Main volume */
#define MIDI_CTL_MSB_BALANCE 0x08 /**< Balance */
#define MIDI_CTL_MSB_PAN 0x0A /**< Panpot */
#define MIDI_CTL_MSB_EXPRESSION 0x0B /**< Expression */
#define MIDI_CTL_MSB_EFFECT1 0x0C /**< Effect1 */
#define MIDI_CTL_MSB_EFFECT2 0x0D /**< Effect2 */
#define MIDI_CTL_MSB_GENERAL_PURPOSE1 0x10 /**< General purpose 1 */
#define MIDI_CTL_MSB_GENERAL_PURPOSE2 0x11 /**< General purpose 2 */
#define MIDI_CTL_MSB_GENERAL_PURPOSE3 0x12 /**< General purpose 3 */
#define MIDI_CTL_MSB_GENERAL_PURPOSE4 0x13 /**< General purpose 4 */
#define MIDI_CTL_LSB_BANK 0x20 /**< Bank selection */
#define MIDI_CTL_LSB_MODWHEEL 0x21 /**< Modulation */
#define MIDI_CTL_LSB_BREATH 0x22 /**< Breath */
#define MIDI_CTL_LSB_FOOT 0x24 /**< Foot */
#define MIDI_CTL_LSB_PORTAMENTO_TIME 0x25 /**< Portamento time */
#define MIDI_CTL_LSB_DATA_ENTRY 0x26 /**< Data entry */
#define MIDI_CTL_LSB_MAIN_VOLUME 0x27 /**< Main volume */
#define MIDI_CTL_LSB_BALANCE 0x28 /**< Balance */
#define MIDI_CTL_LSB_PAN 0x2A /**< Panpot */
#define MIDI_CTL_LSB_EXPRESSION 0x2B /**< Expression */
#define MIDI_CTL_LSB_EFFECT1 0x2C /**< Effect1 */
#define MIDI_CTL_LSB_EFFECT2 0x2D /**< Effect2 */
#define MIDI_CTL_LSB_GENERAL_PURPOSE1 0x30 /**< General purpose 1 */
#define MIDI_CTL_LSB_GENERAL_PURPOSE2 0x31 /**< General purpose 2 */
#define MIDI_CTL_LSB_GENERAL_PURPOSE3 0x32 /**< General purpose 3 */
#define MIDI_CTL_LSB_GENERAL_PURPOSE4 0x33 /**< General purpose 4 */
#define MIDI_CTL_SUSTAIN 0x40 /**< Sustain pedal */
#define MIDI_CTL_PORTAMENTO 0x41 /**< Portamento */
#define MIDI_CTL_SOSTENUTO 0x42 /**< Sostenuto */
#define MIDI_CTL_SUSTENUTO 0x42 /**< Sostenuto (a typo in the older version) */
#define MIDI_CTL_SOFT_PEDAL 0x43 /**< Soft pedal */
#define MIDI_CTL_LEGATO_FOOTSWITCH 0x44 /**< Legato foot switch */
#define MIDI_CTL_HOLD2 0x45 /**< Hold2 */
#define MIDI_CTL_SC1_SOUND_VARIATION 0x46 /**< SC1 Sound Variation */
#define MIDI_CTL_SC2_TIMBRE 0x47 /**< SC2 Timbre */
#define MIDI_CTL_SC3_RELEASE_TIME 0x48 /**< SC3 Release Time */
#define MIDI_CTL_SC4_ATTACK_TIME 0x49 /**< SC4 Attack Time */
#define MIDI_CTL_SC5_BRIGHTNESS 0x4A /**< SC5 Brightness */
#define MIDI_CTL_SC6 0x4B /**< SC6 */
#define MIDI_CTL_SC7 0x4C /**< SC7 */
#define MIDI_CTL_SC8 0x4D /**< SC8 */
#define MIDI_CTL_SC9 0x4E /**< SC9 */
#define MIDI_CTL_SC10 0x4F /**< SC10 */
#define MIDI_CTL_GENERAL_PURPOSE5 0x50 /**< General purpose 5 */
#define MIDI_CTL_GENERAL_PURPOSE6 0x51 /**< General purpose 6 */
#define MIDI_CTL_GENERAL_PURPOSE7 0x52 /**< General purpose 7 */
#define MIDI_CTL_GENERAL_PURPOSE8 0x53 /**< General purpose 8 */
#define MIDI_CTL_PORTAMENTO_CONTROL 0x54 /**< Portamento control */
#define MIDI_CTL_E1_REVERB_DEPTH 0x5B /**< E1 Reverb Depth */
#define MIDI_CTL_E2_TREMOLO_DEPTH 0x5C /**< E2 Tremolo Depth */
#define MIDI_CTL_E3_CHORUS_DEPTH 0x5D /**< E3 Chorus Depth */
#define MIDI_CTL_E4_DETUNE_DEPTH 0x5E /**< E4 Detune Depth */
#define MIDI_CTL_E5_PHASER_DEPTH 0x5F /**< E5 Phaser Depth */
#define MIDI_CTL_DATA_INCREMENT 0x60 /**< Data Increment */
#define MIDI_CTL_DATA_DECREMENT 0x61 /**< Data Decrement */
#define MIDI_CTL_NONREG_PARM_NUM_LSB 0x62 /**< Non-registered parameter number */
#define MIDI_CTL_NONREG_PARM_NUM_MSB 0x63 /**< Non-registered parameter number */
#define MIDI_CTL_REGIST_PARM_NUM_LSB 0x64 /**< Registered parameter number */
#define MIDI_CTL_REGIST_PARM_NUM_MSB 0x65 /**< Registered parameter number */
#define MIDI_CTL_ALL_SOUNDS_OFF 0x78 /**< All sounds off */
#define MIDI_CTL_RESET_CONTROLLERS 0x79 /**< Reset Controllers */
#define MIDI_CTL_LOCAL_CONTROL_SWITCH 0x7A /**< Local control switch */
#define MIDI_CTL_ALL_NOTES_OFF 0x7B /**< All notes off */
#define MIDI_CTL_OMNI_OFF 0x7C /**< Omni off */
#define MIDI_CTL_OMNI_ON 0x7D /**< Omni on */
#define MIDI_CTL_MONO1 0x7E /**< Mono1 */
#define MIDI_CTL_MONO2 0x7F /**< Mono2 */
//@}
/** \} */
#endif /* MIDI_H */

View File

@@ -0,0 +1,79 @@
/*
Copyright (C) 2006 Paul Davis
Written by Dave Robillard, 2006
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 __ardour_midi_playlist_h__
#define __ardour_midi_playlist_h__
#include <vector>
#include <list>
#include <ardour/ardour.h>
#include <ardour/playlist.h>
namespace ARDOUR
{
class Session;
class Region;
class MidiRegion;
class Source;
class MidiRingBuffer;
class MidiPlaylist : public ARDOUR::Playlist
{
public:
MidiPlaylist (Session&, const XMLNode&, bool hidden = false);
MidiPlaylist (Session&, string name, bool hidden = false);
MidiPlaylist (boost::shared_ptr<const MidiPlaylist> other, string name, bool hidden = false);
MidiPlaylist (boost::shared_ptr<const MidiPlaylist> other, nframes_t start, nframes_t cnt,
string name, bool hidden = false);
~MidiPlaylist ();
nframes_t read (MidiRingBuffer& buf,
nframes_t start, nframes_t cnt, uint32_t chan_n=0);
int set_state (const XMLNode&);
UndoAction get_memento() const;
bool destroy_region (boost::shared_ptr<Region>);
protected:
/* playlist "callbacks" */
void flush_notifications ();
void finalize_split_region (boost::shared_ptr<Region> original, boost::shared_ptr<Region> left, boost::shared_ptr<Region> right);
void check_dependents (boost::shared_ptr<Region> region, bool norefresh);
void refresh_dependents (boost::shared_ptr<Region> region);
void remove_dependents (boost::shared_ptr<Region> region);
private:
XMLNode& state (bool full_state);
void dump () const;
bool region_changed (Change, boost::shared_ptr<Region>);
};
} /* namespace ARDOUR */
#endif /* __ardour_midi_playlist_h__ */

View File

@@ -0,0 +1,69 @@
/*
Copyright (C) 2002 Paul Davis
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.
$Id: port.h 712 2006-07-28 01:08:57Z drobilla $
*/
#ifndef __ardour_midi_port_h__
#define __ardour_midi_port_h__
#include <sigc++/signal.h>
#include <pbd/failed_constructor.h>
#include <ardour/ardour.h>
#include <jack/jack.h>
#include <jack/midiport.h>
#include <ardour/port.h>
#include <ardour/buffer.h>
namespace ARDOUR {
class MidiEngine;
class MidiPort : public Port {
public:
virtual ~MidiPort();
DataType type() const { return DataType(DataType::MIDI); }
Buffer& get_buffer() {
return _buffer;
}
MidiBuffer& get_midi_buffer() {
return _buffer;
}
void cycle_start(nframes_t nframes);
void cycle_end();
size_t capacity() { return _buffer.capacity(); }
size_t size() { return _buffer.size(); }
protected:
friend class AudioEngine;
MidiPort (jack_port_t *port);
/* engine isn't supposed to access below here */
MidiBuffer _buffer;
nframes_t _nframes_this_cycle;
};
} // namespace ARDOUR
#endif /* __ardour_midi_port_h__ */

View File

@@ -0,0 +1,101 @@
/*
Copyright (C) 2000-2006 Paul Davis
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.
$Id: midiregion.h 733 2006-08-01 17:19:38Z drobilla $
*/
#ifndef __ardour_midi_region_h__
#define __ardour_midi_region_h__
#include <vector>
#include <pbd/fastlog.h>
#include <pbd/undo.h>
#include <ardour/ardour.h>
#include <ardour/region.h>
#include <ardour/gain.h>
#include <ardour/logcurve.h>
#include <ardour/export.h>
class XMLNode;
namespace ARDOUR {
class Route;
class Playlist;
class Session;
class MidiFilter;
class MidiSource;
class MidiRingBuffer;
class MidiRegion : public Region
{
public:
~MidiRegion();
boost::shared_ptr<MidiSource> midi_source (uint32_t n=0) const;
nframes_t read_at (MidiRingBuffer& dst,
nframes_t position,
nframes_t dur,
uint32_t chan_n = 0,
nframes_t read_frames = 0,
nframes_t skip_frames = 0) const;
nframes_t master_read_at (MidiRingBuffer& dst,
nframes_t position,
nframes_t dur,
uint32_t chan_n=0) const;
XMLNode& state (bool);
int set_state (const XMLNode&);
int separate_by_channel (ARDOUR::Session&, vector<MidiRegion*>&) const;
UndoAction get_memento() const;
private:
friend class RegionFactory;
MidiRegion (boost::shared_ptr<MidiSource>, nframes_t start, nframes_t length);
MidiRegion (boost::shared_ptr<MidiSource>, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags);
MidiRegion (SourceList &, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags);
MidiRegion (boost::shared_ptr<const MidiRegion>, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags);
MidiRegion (boost::shared_ptr<const MidiRegion>);
MidiRegion (boost::shared_ptr<MidiSource>, const XMLNode&);
MidiRegion (SourceList &, const XMLNode&);
private:
friend class Playlist;
private:
nframes_t _read_at (const SourceList&, MidiRingBuffer& dst,
nframes_t position,
nframes_t dur,
uint32_t chan_n = 0,
nframes_t read_frames = 0,
nframes_t skip_frames = 0) const;
void recompute_at_start ();
void recompute_at_end ();
};
} /* namespace ARDOUR */
#endif /* __ardour_midi_region_h__ */

View File

@@ -0,0 +1,226 @@
/*
Copyright (C) 2006 Paul Davis
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 __ardour_midi_ring_buffer_h__
#define __ardour_midi_ring_buffer_h__
#include <algorithm>
#include <ardour/types.h>
#include <pbd/ringbufferNPT.h>
#include <ardour/buffer.h>
namespace ARDOUR {
/** A MIDI RingBuffer
* (necessary because MIDI events are variable sized so a generic RB won't do).
*
* ALL publically accessible sizes refer to event COUNTS. What actually goes
* on in here is none of the callers business :)
*/
class MidiRingBuffer {
public:
MidiRingBuffer (size_t size)
: _size(size)
, _max_event_size(MidiBuffer::max_event_size())
, _ev_buf(new MidiEvent[size])
, _raw_buf(new RawMidi[size * _max_event_size])
{
reset ();
assert(read_space() == 0);
assert(write_space() == size - 1);
}
virtual ~MidiRingBuffer() {
delete[] _ev_buf;
delete[] _raw_buf;
}
void reset () {
/* !!! NOT THREAD SAFE !!! */
g_atomic_int_set (&_write_ptr, 0);
g_atomic_int_set (&_read_ptr, 0);
}
size_t write_space () {
size_t w, r;
w = g_atomic_int_get (&_write_ptr);
r = g_atomic_int_get (&_read_ptr);
if (w > r) {
return ((r - w + _size) % _size) - 1;
} else if (w < r) {
return (r - w) - 1;
} else {
return _size - 1;
}
}
size_t read_space () {
size_t w, r;
w = g_atomic_int_get (&_write_ptr);
r = g_atomic_int_get (&_read_ptr);
if (w > r) {
return w - r;
} else {
return (w - r + _size) % _size;
}
}
size_t capacity() const { return _size; }
/** Read one event and appends it to @a out. */
//size_t read(MidiBuffer& out);
/** Write one event (@a in) */
size_t write(const MidiEvent& in); // deep copies in
/** Read events all events up to time @a end into @a out, leaving stamps intact.
* Any events before @a start will be dropped. */
size_t read(MidiBuffer& out, nframes_t start, nframes_t end);
/** Write all events from @a in, applying @a offset to all time stamps */
size_t write(const MidiBuffer& in, nframes_t offset = 0);
inline void clear_event(size_t index);
private:
// _event_ indices
mutable gint _write_ptr;
mutable gint _read_ptr;
size_t _size; // size (capacity) in events
size_t _max_event_size; // ratio of raw_buf size to ev_buf size
MidiEvent* _ev_buf; // these point into...
RawMidi* _raw_buf; // this
};
/** Just for sanity checking */
inline void
MidiRingBuffer::clear_event(size_t index)
{
memset(&_ev_buf[index].buffer, 0, _max_event_size);
_ev_buf[index].time = 0;
_ev_buf[index].size = 0;
_ev_buf[index].buffer = 0;
}
inline size_t
MidiRingBuffer::write (const MidiEvent& ev)
{
//static nframes_t last_write_time = 0;
assert(ev.size > 0);
size_t priv_write_ptr = g_atomic_int_get(&_write_ptr);
if (write_space () == 0) {
return 0;
} else {
//assert(ev.time >= last_write_time);
const size_t raw_index = priv_write_ptr * _max_event_size;
MidiEvent* const write_ev = &_ev_buf[priv_write_ptr];
*write_ev = ev;
memcpy(&_raw_buf[raw_index], ev.buffer, ev.size);
write_ev->buffer = &_raw_buf[raw_index];
g_atomic_int_set(&_write_ptr, (priv_write_ptr + 1) % _size);
//printf("MRB - wrote %xd %d %d with time %u at index %zu (raw index %zu)\n",
// write_ev->buffer[0], write_ev->buffer[1], write_ev->buffer[2], write_ev->time,
// priv_write_ptr, raw_index);
assert(write_ev->size = ev.size);
//last_write_time = ev.time;
//printf("(W) read space: %zu\n", read_space());
return 1;
}
}
inline size_t
MidiRingBuffer::read(MidiBuffer& dst, nframes_t start, nframes_t end)
{
if (read_space() == 0)
return 0;
size_t priv_read_ptr = g_atomic_int_get(&_read_ptr);
nframes_t time = _ev_buf[priv_read_ptr].time;
size_t count = 0;
size_t limit = read_space();
while (time <= end && limit > 0) {
MidiEvent* const read_ev = &_ev_buf[priv_read_ptr];
if (time >= start) {
dst.push_back(*read_ev);
//printf("MRB - read %#X %d %d with time %u at index %zu\n",
// read_ev->buffer[0], read_ev->buffer[1], read_ev->buffer[2], read_ev->time,
// priv_read_ptr);
} else {
printf("MRB - SKIPPING - %#X %d %d with time %u at index %zu\n",
read_ev->buffer[0], read_ev->buffer[1], read_ev->buffer[2], read_ev->time,
priv_read_ptr);
break;
}
clear_event(priv_read_ptr);
++count;
--limit;
priv_read_ptr = (priv_read_ptr + 1) % _size;
assert(read_ev->time <= end);
time = _ev_buf[priv_read_ptr].time;
}
g_atomic_int_set(&_read_ptr, priv_read_ptr);
//printf("(R) read space: %zu\n", read_space());
return count;
}
inline size_t
MidiRingBuffer::write(const MidiBuffer& in, nframes_t offset)
{
size_t num_events = in.size();
size_t to_write = std::min(write_space(), num_events);
// FIXME: double copy :/
for (size_t i=0; i < to_write; ++i) {
MidiEvent ev = in[i];
ev.time += offset;
write(ev);
}
return to_write;
}
} // namespace ARDOUR
#endif // __ardour_midi_ring_buffer_h__

Some files were not shown because too many files have changed in this diff Show More