/* Copyright (C) 2009 Paul Davis Author: Sakari Bergen 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_export_graph_builder_h__ #define __ardour_export_graph_builder_h__ #include "ardour/export_handler.h" #include "audiographer/utils/identity_vertex.h" #include #include namespace AudioGrapher { class SampleRateConverter; class PeakReader; class Normalizer; template class Chunker; template class SampleFormatConverter; template class Interleaver; template class SndfileWriter; template class SilenceTrimmer; template class TmpFile; template class Threader; template class AllocatingProcessContext; } namespace ARDOUR { class ExportTimespan; class Session; class ExportGraphBuilder { private: typedef ExportHandler::FileSpec FileSpec; typedef boost::shared_ptr > FloatSinkPtr; typedef boost::shared_ptr > IdentityVertexPtr; typedef std::map ChannelMap; public: ExportGraphBuilder (Session const & session); ~ExportGraphBuilder (); int process (framecnt_t frames, bool last_cycle); bool process_normalize (); // returns true when finished bool will_normalize() { return !normalizers.empty(); } unsigned get_normalize_cycle_count() const; void reset (); void set_current_timespan (boost::shared_ptr span); void add_config (FileSpec const & config); private: void add_split_config (FileSpec const & config); class Encoder { public: template boost::shared_ptr > init (FileSpec const & new_config); void add_child (FileSpec const & new_config); bool operator== (FileSpec const & other_config) const; static int get_real_format (FileSpec const & config); private: typedef boost::shared_ptr > FloatWriterPtr; typedef boost::shared_ptr > IntWriterPtr; typedef boost::shared_ptr > ShortWriterPtr; template void init_writer (boost::shared_ptr > & writer); void copy_files (std::string orig_path); FileSpec config; std::list filenames; PBD::ScopedConnection copy_files_connection; // Only one of these should be available at a time FloatWriterPtr float_writer; IntWriterPtr int_writer; ShortWriterPtr short_writer; }; // sample format converter class SFC { public: // This constructor so that this can be constructed like a Normalizer SFC (ExportGraphBuilder &, FileSpec const & new_config, framecnt_t max_frames); FloatSinkPtr sink (); void add_child (FileSpec const & new_config); bool operator== (FileSpec const & other_config) const; private: typedef boost::shared_ptr > FloatConverterPtr; typedef boost::shared_ptr > IntConverterPtr; typedef boost::shared_ptr > ShortConverterPtr; FileSpec config; boost::ptr_list children; int data_width; // Only one of these should be available at a time FloatConverterPtr float_converter; IntConverterPtr int_converter; ShortConverterPtr short_converter; }; class Normalizer { public: Normalizer (ExportGraphBuilder & parent, FileSpec const & new_config, framecnt_t max_frames); FloatSinkPtr sink (); void add_child (FileSpec const & new_config); bool operator== (FileSpec const & other_config) const; unsigned get_normalize_cycle_count() const; /// Returns true when finished bool process (); private: typedef boost::shared_ptr PeakReaderPtr; typedef boost::shared_ptr NormalizerPtr; typedef boost::shared_ptr > TmpFilePtr; typedef boost::shared_ptr > ThreaderPtr; typedef boost::shared_ptr > BufferPtr; void start_post_processing(); ExportGraphBuilder & parent; FileSpec config; framecnt_t max_frames_out; BufferPtr buffer; PeakReaderPtr peak_reader; TmpFilePtr tmp_file; NormalizerPtr normalizer; ThreaderPtr threader; boost::ptr_list children; PBD::ScopedConnection post_processing_connection; }; // sample rate converter class SRC { public: SRC (ExportGraphBuilder & parent, FileSpec const & new_config, framecnt_t max_frames); FloatSinkPtr sink (); void add_child (FileSpec const & new_config); bool operator== (FileSpec const & other_config) const; private: typedef boost::shared_ptr SRConverterPtr; template void add_child_to_list (FileSpec const & new_config, boost::ptr_list & list); ExportGraphBuilder & parent; FileSpec config; boost::ptr_list children; boost::ptr_list normalized_children; SRConverterPtr converter; framecnt_t max_frames_out; }; // Silence trimmer + adder class SilenceHandler { public: SilenceHandler (ExportGraphBuilder & parent, FileSpec const & new_config, framecnt_t max_frames); FloatSinkPtr sink (); void add_child (FileSpec const & new_config); bool operator== (FileSpec const & other_config) const; private: typedef boost::shared_ptr > SilenceTrimmerPtr; ExportGraphBuilder & parent; FileSpec config; boost::ptr_list children; SilenceTrimmerPtr silence_trimmer; framecnt_t max_frames_in; }; // channel configuration class ChannelConfig { public: ChannelConfig (ExportGraphBuilder & parent, FileSpec const & new_config, ChannelMap & channel_map); void add_child (FileSpec const & new_config); bool operator== (FileSpec const & other_config) const; private: typedef boost::shared_ptr > InterleaverPtr; typedef boost::shared_ptr > ChunkerPtr; ExportGraphBuilder & parent; FileSpec config; boost::ptr_list children; InterleaverPtr interleaver; ChunkerPtr chunker; framecnt_t max_frames_out; }; Session const & session; boost::shared_ptr timespan; // Roots for export processor trees typedef boost::ptr_list ChannelConfigList; ChannelConfigList channel_configs; // The sources of all data, each channel is read only once ChannelMap channels; framecnt_t process_buffer_frames; std::list normalizers; Glib::ThreadPool thread_pool; }; } // namespace ARDOUR #endif /* __ardour_export_graph_builder_h__ */