2 Copyright (C) 2006 Paul Davis
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2 of the License, or
7 (at your option) any later version.
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18 #include "pbd/error.h"
20 #include "ardour/amp.h"
21 #include "ardour/audioengine.h"
22 #include "ardour/audiofilesource.h"
23 #include "ardour/audioplaylist.h"
24 #include "ardour/audioregion.h"
25 #include "ardour/debug.h"
26 #include "ardour/delivery.h"
27 #include "ardour/disk_reader.h"
28 #include "ardour/disk_writer.h"
29 #include "ardour/event_type_map.h"
30 #include "ardour/io_processor.h"
31 #include "ardour/meter.h"
32 #include "ardour/midi_playlist.h"
33 #include "ardour/midi_region.h"
34 #include "ardour/monitor_control.h"
35 #include "ardour/playlist.h"
36 #include "ardour/playlist_factory.h"
37 #include "ardour/port.h"
38 #include "ardour/processor.h"
39 #include "ardour/profile.h"
40 #include "ardour/region_factory.h"
41 #include "ardour/record_enable_control.h"
42 #include "ardour/record_safe_control.h"
43 #include "ardour/route_group_specialized.h"
44 #include "ardour/session.h"
45 #include "ardour/session_playlists.h"
46 #include "ardour/smf_source.h"
47 #include "ardour/track.h"
48 #include "ardour/types_convert.h"
49 #include "ardour/utils.h"
54 using namespace ARDOUR;
57 Track::Track (Session& sess, string name, PresentationInfo::Flag flag, TrackMode mode, DataType default_type)
58 : Route (sess, name, flag, default_type)
59 , _saved_meter_point (_meter_point)
61 , _alignment_choice (Automatic)
63 _freeze_record.state = NoFreeze;
68 DEBUG_TRACE (DEBUG::Destruction, string_compose ("track %1 destructor\n", _name));
71 _disk_reader->set_route (boost::shared_ptr<Route>());
72 _disk_reader.reset ();
76 _disk_writer->set_route (boost::shared_ptr<Route>());
77 _disk_writer.reset ();
88 DiskIOProcessor::Flag dflags = DiskIOProcessor::Recordable;
90 if (_mode == Destructive && !Profile->get_trx()) {
91 dflags = DiskIOProcessor::Flag (dflags | DiskIOProcessor::Destructive);
94 _disk_reader.reset (new DiskReader (_session, name(), dflags));
95 _disk_reader->set_block_size (_session.get_block_size ());
96 _disk_reader->set_route (boost::dynamic_pointer_cast<Route> (shared_from_this()));
97 _disk_reader->set_owner (this);
99 _disk_writer.reset (new DiskWriter (_session, name(), dflags));
100 _disk_writer->set_block_size (_session.get_block_size ());
101 _disk_writer->set_route (boost::dynamic_pointer_cast<Route> (shared_from_this()));
102 _disk_writer->set_owner (this);
104 set_align_choice_from_io ();
106 use_new_playlist (data_type());
108 boost::shared_ptr<Route> rp (boost::dynamic_pointer_cast<Route> (shared_from_this()));
109 boost::shared_ptr<Track> rt = boost::dynamic_pointer_cast<Track> (rp);
111 _record_enable_control.reset (new RecordEnableControl (_session, EventTypeMap::instance().to_symbol (RecEnableAutomation), *this));
112 add_control (_record_enable_control);
114 _record_safe_control.reset (new RecordSafeControl (_session, EventTypeMap::instance().to_symbol (RecSafeAutomation), *this));
115 add_control (_record_safe_control);
117 _monitoring_control.reset (new MonitorControl (_session, EventTypeMap::instance().to_symbol (MonitoringAutomation), *this));
118 add_control (_monitoring_control);
120 _session.config.ParameterChanged.connect_same_thread (*this, boost::bind (&Track::parameter_changed, this, _1));
122 _monitoring_control->Changed.connect_same_thread (*this, boost::bind (&Track::monitoring_changed, this, _1, _2));
123 _record_safe_control->Changed.connect_same_thread (*this, boost::bind (&Track::record_safe_changed, this, _1, _2));
124 _record_enable_control->Changed.connect_same_thread (*this, boost::bind (&Track::record_enable_changed, this, _1, _2));
126 _input->changed.connect_same_thread (*this, boost::bind (&Track::input_changed, this));
132 Track::input_changed ()
134 if (_disk_writer && _alignment_choice == Automatic) {
135 set_align_choice_from_io ();
140 Track::state (bool save_template)
142 XMLNode& root (Route::state (save_template));
144 if (_playlists[DataType::AUDIO]) {
145 root.set_property (X_("audio-playlist"), _playlists[DataType::AUDIO]->id().to_s());
148 if (_playlists[DataType::MIDI]) {
149 root.set_property (X_("midi-playlist"), _playlists[DataType::MIDI]->id().to_s());
152 root.add_child_nocopy (_monitoring_control->get_state ());
153 root.add_child_nocopy (_record_safe_control->get_state ());
154 root.add_child_nocopy (_record_enable_control->get_state ());
156 root.set_property (X_("saved-meter-point"), _saved_meter_point);
157 root.set_property (X_("alignment-choice"), _alignment_choice);
163 Track::set_state (const XMLNode& node, int version)
165 if (Route::set_state (node, version)) {
169 if (version >= 3000 && version < 6000) {
170 if (XMLNode* ds_node = find_named_node (node, "Diskstream")) {
172 if (ds_node->get_property ("playlist", name)) {
174 ds_node->set_property ("active", true);
176 _disk_writer->set_state (*ds_node, version);
177 _disk_reader->set_state (*ds_node, version);
180 if (ds_node->get_property (X_("capture-alignment"), ac)) {
181 set_align_choice (ac, true);
184 if (boost::shared_ptr<AudioPlaylist> pl = boost::dynamic_pointer_cast<AudioPlaylist> (_session.playlists->by_name (name))) {
185 use_playlist (DataType::AUDIO, pl);
188 if (boost::shared_ptr<MidiPlaylist> pl = boost::dynamic_pointer_cast<MidiPlaylist> (_session.playlists->by_name (name))) {
189 use_playlist (DataType::MIDI, pl);
196 std::string playlist_id;
198 if (node.get_property (X_("audio-playlist"), playlist_id)) {
199 find_and_use_playlist (DataType::AUDIO, PBD::ID (playlist_id));
202 if (node.get_property (X_("midi-playlist"), playlist_id)) {
203 find_and_use_playlist (DataType::MIDI, PBD::ID (playlist_id));
206 XMLNodeList nlist = node.children();
207 for (XMLNodeConstIterator niter = nlist.begin(); niter != nlist.end(); ++niter) {
210 if (child->name() == Controllable::xml_node_name) {
212 if (!child->get_property ("name", name)) {
216 if (name == _record_enable_control->name()) {
217 _record_enable_control->set_state (*child, version);
218 } else if (name == _record_safe_control->name()) {
219 _record_safe_control->set_state (*child, version);
220 } else if (name == _monitoring_control->name()) {
221 _monitoring_control->set_state (*child, version);
226 if (!node.get_property (X_("saved-meter-point"), _saved_meter_point)) {
227 _saved_meter_point = _meter_point;
233 if (node.get_property (X_("alignment-choice"), ac)) {
234 set_align_choice (ac, true);
240 Track::FreezeRecord::~FreezeRecord ()
242 for (vector<FreezeRecordProcessorInfo*>::iterator i = processor_info.begin(); i != processor_info.end(); ++i) {
248 Track::freeze_state() const
250 return _freeze_record.state;
254 Track::declick_in_progress () const
256 return _disk_reader->declick_in_progress ();
262 bool will_record = true;
263 for (PortSet::iterator i = _input->ports().begin(); i != _input->ports().end() && will_record; ++i) {
272 Track::prep_record_enabled (bool yn)
274 if (yn && _record_safe_control->get_value()) {
278 if (!can_be_record_enabled()) {
282 /* keep track of the meter point as it was before we rec-enabled */
283 if (!_disk_writer->record_enabled()) {
284 _saved_meter_point = _meter_point;
290 will_follow = _disk_writer->prep_record_enable ();
292 will_follow = _disk_writer->prep_record_disable ();
297 if (_meter_point != MeterCustom) {
298 set_meter_point (MeterInput);
301 set_meter_point (_saved_meter_point);
309 Track::record_enable_changed (bool, Controllable::GroupControlDisposition)
311 _disk_writer->set_record_enabled (_record_enable_control->get_value());
315 Track::record_safe_changed (bool, Controllable::GroupControlDisposition)
317 _disk_writer->set_record_safe (_record_safe_control->get_value());
321 Track::can_be_record_safe ()
323 return !_record_enable_control->get_value() && _disk_writer && _session.writable() && (_freeze_record.state != Frozen);
327 Track::can_be_record_enabled ()
329 return !_record_safe_control->get_value() && _disk_writer && !_disk_writer->record_safe() && _session.writable() && (_freeze_record.state != Frozen);
333 Track::parameter_changed (string const & p)
335 if (p == "track-name-number") {
336 resync_track_name ();
338 else if (p == "track-name-take") {
339 resync_track_name ();
341 else if (p == "take-name") {
342 if (_session.config.get_track_name_take()) {
343 resync_track_name ();
349 Track::resync_track_name ()
355 Track::set_name (const string& str)
363 if (_record_enable_control->get_value()) {
364 /* when re-arm'ed the file (named after the track) is already ready to rolll */
368 string diskstream_name = "";
369 if (_session.config.get_track_name_take () && !_session.config.get_take_name ().empty()) {
370 // Note: any text is fine, legalize_for_path() fixes this later
371 diskstream_name += _session.config.get_take_name ();
372 diskstream_name += "_";
374 const int64_t tracknumber = track_number();
375 if (tracknumber > 0 && _session.config.get_track_name_number()) {
376 char num[64], fmt[10];
377 snprintf(fmt, sizeof(fmt), "%%0%d" PRId64, _session.track_number_decimals());
378 snprintf(num, sizeof(num), fmt, tracknumber);
379 diskstream_name += num;
380 diskstream_name += "_";
382 diskstream_name += str;
384 if (diskstream_name == _diskstream_name) {
387 _diskstream_name = diskstream_name;
389 _disk_writer->set_write_source_name (diskstream_name);
391 boost::shared_ptr<Track> me = boost::dynamic_pointer_cast<Track> (shared_from_this ());
393 if (_playlists[data_type()]->all_regions_empty () && _session.playlists->playlists_for_track (me).size() == 1) {
394 /* Only rename the diskstream (and therefore the playlist) if
395 a) the playlist has never had a region added to it and
396 b) there is only one playlist for this track.
398 If (a) is not followed, people can get confused if, say,
399 they have notes about a playlist with a given name and then
400 it changes (see mantis #4759).
402 If (b) is not followed, we rename the current playlist and not
403 the other ones, which is a bit confusing (see mantis #4977).
405 _disk_reader->set_name (str);
406 _disk_writer->set_name (str);
409 for (uint32_t n = 0; n < DataType::num_types; ++n) {
411 _playlists[n]->set_name (str);
415 /* save state so that the statefile fully reflects any filename changes */
417 if ((ret = Route::set_name (str)) == 0) {
418 _session.save_state ("");
424 boost::shared_ptr<Playlist>
427 return _playlists[data_type()];
431 Track::request_input_monitoring (bool m)
433 for (PortSet::iterator i = _input->ports().begin(); i != _input->ports().end(); ++i) {
434 AudioEngine::instance()->request_input_monitoring ((*i)->name(), m);
439 Track::ensure_input_monitoring (bool m)
441 for (PortSet::iterator i = _input->ports().begin(); i != _input->ports().end(); ++i) {
442 AudioEngine::instance()->ensure_input_monitoring ((*i)->name(), m);
447 Track::destructive () const
449 return _disk_writer->destructive ();
452 list<boost::shared_ptr<Source> > &
453 Track::last_capture_sources ()
455 return _disk_writer->last_capture_sources ();
459 Track::steal_write_source_name()
461 return _disk_writer->steal_write_source_name ();
465 Track::reset_write_sources (bool r, bool force)
467 _disk_writer->reset_write_sources (r, force);
471 Track::playback_buffer_load () const
473 return _disk_reader->buffer_load ();
477 Track::capture_buffer_load () const
479 return _disk_writer->buffer_load ();
485 return _disk_reader->do_refill ();
489 Track::do_flush (RunContext c, bool force)
491 return _disk_writer->do_flush (c, force);
495 Track::set_pending_overwrite (bool o)
497 _disk_reader->set_pending_overwrite (o);
501 Track::seek (samplepos_t p, bool complete_refill)
503 if (_disk_reader->seek (p, complete_refill)) {
506 return _disk_writer->seek (p, complete_refill);
510 Track::can_internal_playback_seek (samplecnt_t p)
512 return _disk_reader->can_internal_playback_seek (p);
516 Track::internal_playback_seek (samplecnt_t p)
518 return _disk_reader->internal_playback_seek (p);
522 Track::non_realtime_locate (samplepos_t p)
524 Route::non_realtime_locate (p);
528 Track::overwrite_existing_buffers ()
530 return _disk_reader->overwrite_existing_buffers ();
534 Track::get_captured_samples (uint32_t n) const
536 return _disk_writer->get_captured_samples (n);
540 Track::transport_looped (samplepos_t p)
542 return _disk_writer->transport_looped (p);
546 Track::transport_stopped_wallclock (struct tm & n, time_t t, bool g)
548 _disk_writer->transport_stopped_wallclock (n, t, g);
552 Track::pending_overwrite () const
554 return _disk_reader->pending_overwrite ();
558 Track::set_slaved (bool s)
560 _disk_reader->set_slaved (s);
561 _disk_writer->set_slaved (s);
567 return _disk_reader->output_streams();
571 Track::get_capture_start_sample (uint32_t n) const
573 return _disk_writer->get_capture_start_sample (n);
577 Track::alignment_style () const
579 return _disk_writer->alignment_style ();
583 Track::alignment_choice () const
585 return _alignment_choice;
589 Track::current_capture_start () const
591 return _disk_writer->current_capture_start ();
595 Track::current_capture_end () const
597 return _disk_writer->current_capture_end ();
601 Track::playlist_modified ()
603 _disk_reader->playlist_modified ();
607 Track::find_and_use_playlist (DataType dt, PBD::ID const & id)
609 boost::shared_ptr<Playlist> playlist;
611 if ((playlist = _session.playlists->by_id (id)) == 0) {
616 error << string_compose(_("DiskIOProcessor: \"%1\" isn't an playlist"), id.to_s()) << endmsg;
620 return use_playlist (dt, playlist);
624 Track::use_playlist (DataType dt, boost::shared_ptr<Playlist> p)
628 if ((ret = _disk_reader->use_playlist (dt, p)) == 0) {
629 if ((ret = _disk_writer->use_playlist (dt, p)) == 0) {
630 p->set_orig_track_id (id());
638 _session.set_dirty ();
639 PlaylistChanged (); /* EMIT SIGNAL */
645 Track::use_copy_playlist ()
647 assert (_playlists[data_type()]);
649 if (_playlists[data_type()] == 0) {
650 error << string_compose(_("DiskIOProcessor %1: there is no existing playlist to make a copy of!"), _name) << endmsg;
655 boost::shared_ptr<Playlist> playlist;
657 newname = Playlist::bump_name (_playlists[data_type()]->name(), _session);
659 if ((playlist = PlaylistFactory::create (_playlists[data_type()], newname)) == 0) {
663 playlist->reset_shares();
665 return use_playlist (data_type(), playlist);
669 Track::use_new_playlist (DataType dt)
672 boost::shared_ptr<Playlist> playlist = _playlists[dt];
675 newname = Playlist::bump_name (playlist->name(), _session);
677 newname = Playlist::bump_name (_name, _session);
680 playlist = PlaylistFactory::create (dt, _session, newname, is_private_route());
686 return use_playlist (dt, playlist);
690 Track::set_align_choice (AlignChoice ac, bool force)
692 _alignment_choice = ac;
695 set_align_choice_from_io ();
698 _disk_writer->set_align_style (CaptureTime, force);
700 case UseExistingMaterial:
701 _disk_writer->set_align_style (ExistingMaterial, force);
707 Track::set_align_style (AlignStyle s, bool force)
709 _disk_writer->set_align_style (s, force);
713 Track::set_align_choice_from_io ()
715 bool have_physical = false;
719 vector<string> connections;
720 boost::shared_ptr<Port> p;
724 p = _input->nth (n++);
730 if (p->get_connections (connections) != 0) {
731 if (AudioEngine::instance()->port_is_physical (connections[0])) {
732 have_physical = true;
737 connections.clear ();
742 // compensate for latency when bouncing from master or mixbus.
743 // we need to use "ExistingMaterial" to pick up the master bus' latency
744 // see also Route::direct_feeds_according_to_reality
746 ios.push_back (_input);
747 if (_session.master_out() && ios.fed_by (_session.master_out()->output())) {
748 have_physical = true;
750 for (uint32_t n = 0; n < NUM_MIXBUSES && !have_physical; ++n) {
751 if (_session.get_mixbus (n) && ios.fed_by (_session.get_mixbus(n)->output())) {
752 have_physical = true;
758 _disk_writer->set_align_style (ExistingMaterial);
760 _disk_writer->set_align_style (CaptureTime);
765 Track::set_block_size (pframes_t n)
767 Route::set_block_size (n);
768 _disk_reader->set_block_size (n);
769 _disk_writer->set_block_size (n);
773 Track::adjust_playback_buffering ()
776 _disk_reader->adjust_buffering ();
781 Track::adjust_capture_buffering ()
784 _disk_writer->adjust_buffering ();
789 Track::monitoring_changed (bool, Controllable::GroupControlDisposition)
791 for (ProcessorList::iterator i = _processors.begin(); i != _processors.end(); ++i) {
792 (*i)->monitoring_changed ();
797 Track::metering_state () const
800 if (_session.transport_rolling ()) {
801 // audio_track.cc || midi_track.cc roll() runs meter IFF:
802 rv = _meter_point == MeterInput && ((_monitoring_control->monitoring_choice() & MonitorInput) || _disk_writer->record_enabled());
804 // track no_roll() always metering if
805 rv = _meter_point == MeterInput;
807 return rv ? MeteringInput : MeteringRoute;
811 Track::set_processor_state (XMLNode const & node, XMLProperty const* prop, ProcessorList& new_order, bool& must_configure)
813 if (Route::set_processor_state (node, prop, new_order, must_configure)) {
817 cerr << name() << " looking for state for track procs, DR = " << _disk_reader << endl;
819 if (prop->value() == "diskreader") {
821 _disk_reader->set_state (node, Stateful::current_state_version);
822 new_order.push_back (_disk_reader);
825 } else if (prop->value() == "diskwriter") {
827 _disk_writer->set_state (node, Stateful::current_state_version);
828 new_order.push_back (_disk_writer);
833 error << string_compose(_("unknown Processor type \"%1\"; ignored"), prop->value()) << endmsg;
838 Track::use_captured_sources (SourceList& srcs, CaptureInfos const & capture_info)
844 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource> (srcs.front());
845 boost::shared_ptr<SMFSource> mfs = boost::dynamic_pointer_cast<SMFSource> (srcs.front());
848 use_captured_audio_sources (srcs, capture_info);
852 use_captured_midi_sources (srcs, capture_info);
857 Track::use_captured_midi_sources (SourceList& srcs, CaptureInfos const & capture_info)
859 if (srcs.empty() || data_type() != DataType::MIDI) {
863 boost::shared_ptr<SMFSource> mfs = boost::dynamic_pointer_cast<SMFSource> (srcs.front());
864 boost::shared_ptr<Playlist> pl = _playlists[DataType::MIDI];
865 boost::shared_ptr<MidiRegion> midi_region;
866 CaptureInfos::const_iterator ci;
872 samplecnt_t total_capture = 0;
874 for (total_capture = 0, ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
875 total_capture += (*ci)->samples;
878 /* we will want to be able to keep (over)writing the source
879 but we don't want it to be removable. this also differs
880 from the audio situation, where the source at this point
881 must be considered immutable. luckily, we can rely on
882 MidiSource::mark_streaming_write_completed() to have
883 already done the necessary work for that.
886 string whole_file_region_name;
887 whole_file_region_name = region_name_from_path (mfs->name(), true);
889 /* Register a new region with the Session that
890 describes the entire source. Do this first
891 so that any sub-regions will obviously be
892 children of this one (later!)
898 plist.add (Properties::name, whole_file_region_name);
899 plist.add (Properties::whole_file, true);
900 plist.add (Properties::automatic, true);
901 plist.add (Properties::start, 0);
902 plist.add (Properties::length, total_capture);
903 plist.add (Properties::layer, 0);
905 boost::shared_ptr<Region> rx (RegionFactory::create (srcs, plist));
907 midi_region = boost::dynamic_pointer_cast<MidiRegion> (rx);
908 midi_region->special_set_position (capture_info.front()->start);
911 catch (failed_constructor& err) {
912 error << string_compose(_("%1: could not create region for complete midi file"), _name) << endmsg;
916 pl->clear_changes ();
919 /* Session sample time of the initial capture in this pass, which is where the source starts */
920 samplepos_t initial_capture = 0;
921 if (!capture_info.empty()) {
922 initial_capture = capture_info.front()->start;
925 BeatsSamplesConverter converter (_session.tempo_map(), capture_info.front()->start);
926 const samplepos_t preroll_off = _session.preroll_record_trim_len ();
928 for (ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
932 RegionFactory::region_name (region_name, mfs->name(), false);
934 DEBUG_TRACE (DEBUG::CaptureAlignment, string_compose ("%1 capture start @ %2 length %3 add new region %4\n",
935 _name, (*ci)->start, (*ci)->samples, region_name));
938 // cerr << _name << ": based on ci of " << (*ci)->start << " for " << (*ci)->samples << " add a region\n";
943 /* start of this region is the offset between the start of its capture and the start of the whole pass */
944 plist.add (Properties::start, (*ci)->start - initial_capture);
945 plist.add (Properties::length, (*ci)->samples);
946 plist.add (Properties::length_beats, converter.from((*ci)->samples).to_double());
947 plist.add (Properties::name, region_name);
949 boost::shared_ptr<Region> rx (RegionFactory::create (srcs, plist));
950 midi_region = boost::dynamic_pointer_cast<MidiRegion> (rx);
951 if (preroll_off > 0) {
952 midi_region->trim_front ((*ci)->start - initial_capture + preroll_off);
956 catch (failed_constructor& err) {
957 error << _("MidiDiskstream: could not create region for captured midi!") << endmsg;
958 continue; /* XXX is this OK? */
961 cerr << "add new region, len = " << (*ci)->samples << " @ " << (*ci)->start << endl;
963 pl->add_region (midi_region, (*ci)->start + preroll_off, 1, _session.config.get_layered_record_mode ());
967 _session.add_command (new StatefulDiffCommand (pl));
971 Track::use_captured_audio_sources (SourceList& srcs, CaptureInfos const & capture_info)
973 if (srcs.empty() || data_type() != DataType::AUDIO) {
977 boost::shared_ptr<AudioFileSource> afs = boost::dynamic_pointer_cast<AudioFileSource> (srcs.front());
978 boost::shared_ptr<Playlist> pl = _playlists[DataType::AUDIO];
979 boost::shared_ptr<AudioRegion> region;
985 /* destructive tracks have a single, never changing region */
989 /* send a signal that any UI can pick up to do the right thing. there is
990 a small problem here in that a UI may need the peak data to be ready
991 for the data that was recorded and this isn't interlocked with that
992 process. this problem is deferred to the UI.
995 pl->LayeringChanged(); // XXX this may not get the UI to do the right thing
999 string whole_file_region_name;
1000 whole_file_region_name = region_name_from_path (afs->name(), true);
1002 /* Register a new region with the Session that
1003 describes the entire source. Do this first
1004 so that any sub-regions will obviously be
1005 children of this one (later!)
1011 plist.add (Properties::start, afs->last_capture_start_sample());
1012 plist.add (Properties::length, afs->length(0));
1013 plist.add (Properties::name, whole_file_region_name);
1014 boost::shared_ptr<Region> rx (RegionFactory::create (srcs, plist));
1015 rx->set_automatic (true);
1016 rx->set_whole_file (true);
1018 region = boost::dynamic_pointer_cast<AudioRegion> (rx);
1019 region->special_set_position (afs->natural_position());
1023 catch (failed_constructor& err) {
1024 error << string_compose(_("%1: could not create region for complete audio file"), _name) << endmsg;
1028 pl->clear_changes ();
1029 pl->set_capture_insertion_in_progress (true);
1032 const samplepos_t preroll_off = _session.preroll_record_trim_len ();
1033 samplecnt_t buffer_position = afs->last_capture_start_sample ();
1034 CaptureInfos::const_iterator ci;
1036 for (ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
1040 RegionFactory::region_name (region_name, whole_file_region_name, false);
1042 DEBUG_TRACE (DEBUG::CaptureAlignment, string_compose ("%1 capture bufpos %5 start @ %2 length %3 add new region %4\n",
1043 _name, (*ci)->start, (*ci)->samples, region_name, buffer_position));
1049 plist.add (Properties::start, buffer_position);
1050 plist.add (Properties::length, (*ci)->samples);
1051 plist.add (Properties::name, region_name);
1053 boost::shared_ptr<Region> rx (RegionFactory::create (srcs, plist));
1054 region = boost::dynamic_pointer_cast<AudioRegion> (rx);
1055 if (preroll_off > 0) {
1056 region->trim_front (buffer_position + preroll_off);
1060 catch (failed_constructor& err) {
1061 error << _("AudioDiskstream: could not create region for captured audio!") << endmsg;
1062 continue; /* XXX is this OK? */
1065 pl->add_region (region, (*ci)->start + preroll_off, 1, _session.config.get_layered_record_mode());
1066 pl->set_layer (region, DBL_MAX);
1068 buffer_position += (*ci)->samples;
1072 pl->set_capture_insertion_in_progress (false);
1073 _session.add_command (new StatefulDiffCommand (pl));