2 Copyright (C) 2006 Paul Davis
3 Written by Taybin Rutkin
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
21 #ifndef __ardour_audio_unit_h__
22 #define __ardour_audio_unit_h__
25 #include <boost/shared_ptr.hpp>
33 #include "ardour/plugin.h"
35 #include <AudioUnit/AudioUnit.h>
36 #include <AudioUnit/AudioUnitProperties.h>
37 #include "appleutility/AUParamInfo.h"
39 #include <boost/shared_ptr.hpp>
43 class CAComponentDescription;
44 struct AudioBufferList;
51 struct AUParameterDescriptor : public Plugin::ParameterDescriptor {
52 // additional fields to make operations more efficient
53 AudioUnitParameterID id;
55 AudioUnitElement element;
58 AudioUnitParameterUnit unit;
61 class AUPlugin : public ARDOUR::Plugin
64 AUPlugin (AudioEngine& engine, Session& session, boost::shared_ptr<CAComponent> comp);
65 AUPlugin (const AUPlugin& other);
68 std::string unique_id () const;
69 const char * label () const;
70 const char * name () const { return _info->name.c_str(); }
71 const char * maker () const { return _info->creator.c_str(); }
72 uint32_t parameter_count () const;
73 float default_value (uint32_t port);
74 framecnt_t signal_latency() const;
75 void set_parameter (uint32_t which, float val);
76 float get_parameter (uint32_t which) const;
78 int get_parameter_descriptor (uint32_t which, ParameterDescriptor&) const;
79 uint32_t nth_parameter (uint32_t which, bool& ok) const;
83 int set_block_size (pframes_t nframes);
85 int connect_and_run (BufferSet& bufs,
86 ChanMapping in, ChanMapping out,
87 pframes_t nframes, framecnt_t offset);
88 std::set<Evoral::Parameter> automatable() const;
89 std::string describe_parameter (Evoral::Parameter);
90 std::string state_node_name () const { return "audiounit"; }
91 void print_parameter (uint32_t, char*, uint32_t len) const;
93 bool parameter_is_audio (uint32_t) const;
94 bool parameter_is_control (uint32_t) const;
95 bool parameter_is_input (uint32_t) const;
96 bool parameter_is_output (uint32_t) const;
98 int set_state(const XMLNode& node, int);
100 PresetRecord save_preset (std::string name);
101 bool load_preset (PresetRecord);
102 std::string current_preset() const;
104 bool has_editor () const;
106 bool reconfigurable_io() const { return true; }
107 bool can_support_io_configuration (const ChanCount& in, ChanCount& out) const;
108 bool configure_io (ChanCount in, ChanCount out);
109 bool requires_fixed_size_buffers() const;
111 void set_fixed_size_buffers (bool yn) {
112 _requires_fixed_size_buffers = yn;
115 boost::shared_ptr<CAAudioUnit> get_au () { return unit; }
116 boost::shared_ptr<CAComponent> get_comp () const { return comp; }
118 OSStatus render_callback(AudioUnitRenderActionFlags *ioActionFlags,
119 const AudioTimeStamp *inTimeStamp,
121 UInt32 inNumberFrames,
122 AudioBufferList* ioData);
124 /* "host" callbacks */
126 OSStatus get_beat_and_tempo_callback (Float64* outCurrentBeat,
127 Float64* outCurrentTempo);
129 OSStatus get_musical_time_location_callback (UInt32* outDeltaSampleOffsetToNextBeat,
130 Float32* outTimeSig_Numerator,
131 UInt32* outTimeSig_Denominator,
132 Float64* outCurrentMeasureDownBeat);
134 OSStatus get_transport_state_callback (Boolean* outIsPlaying,
135 Boolean* outTransportStateChanged,
136 Float64* outCurrentSampleInTimeLine,
137 Boolean* outIsCycling,
138 Float64* outCycleStartBeat,
139 Float64* outCycleEndBeat);
141 static std::string maybe_fix_broken_au_id (const std::string&);
144 void find_presets ();
146 boost::shared_ptr<CAComponent> comp;
147 boost::shared_ptr<CAAudioUnit> unit;
150 int32_t input_channels;
151 int32_t output_channels;
152 std::vector<std::pair<int,int> > io_configs;
153 pframes_t _current_block_size;
154 framecnt_t _last_nframes;
155 bool _requires_fixed_size_buffers;
156 AudioBufferList* buffers;
157 bool _has_midi_input;
158 bool _has_midi_output;
160 /* despite all the cool work that apple did on their AU preset
161 system, they left factory presets and user presets as two
162 entirely different kinds of things, handled by two entirely
163 different parts of the API. Resolve this.
166 /* XXX these two maps should really be shared across all instances of this AUPlugin */
168 typedef std::map<std::string,std::string> UserPresetMap;
169 UserPresetMap user_preset_map;
170 typedef std::map<std::string,int> FactoryPresetMap;
171 FactoryPresetMap factory_preset_map;
173 UInt32 global_elements;
174 UInt32 output_elements;
175 UInt32 input_elements;
177 int set_output_format (AudioStreamBasicDescription&);
178 int set_input_format (AudioStreamBasicDescription&);
179 int set_stream_format (int scope, uint32_t cnt, AudioStreamBasicDescription&);
180 void discover_parameters ();
181 void add_state (XMLNode *) const;
183 std::vector<std::pair<uint32_t, uint32_t> > parameter_map;
184 uint32_t current_maxbuf;
185 framecnt_t current_offset;
186 framecnt_t cb_offset;
187 BufferSet* current_buffers;
188 framecnt_t frames_processed;
190 std::vector<AUParameterDescriptor> descriptors;
193 void discover_factory_presets ();
195 bool last_transport_rolling;
196 float last_transport_speed;
199 typedef boost::shared_ptr<AUPlugin> AUPluginPtr;
201 struct AUPluginCachedInfo {
202 std::vector<std::pair<int,int> > io_configs;
205 class AUPluginInfo : public PluginInfo {
207 AUPluginInfo (boost::shared_ptr<CAComponentDescription>);
210 PluginPtr load (Session& session);
212 bool needs_midi_input ();
213 bool is_effect () const;
214 bool is_effect_without_midi_input () const;
215 bool is_effect_with_midi_input () const;
216 bool is_instrument () const;
218 AUPluginCachedInfo cache;
220 static PluginInfoList* discover ();
221 static void get_names (CAComponentDescription&, std::string& name, std::string& maker);
222 static std::string stringify_descriptor (const CAComponentDescription&);
224 static int load_cached_info ();
227 boost::shared_ptr<CAComponentDescription> descriptor;
230 static void discover_music (PluginInfoList&);
231 static void discover_fx (PluginInfoList&);
232 static void discover_generators (PluginInfoList&);
233 static void discover_instruments (PluginInfoList&);
234 static void discover_by_description (PluginInfoList&, CAComponentDescription&);
235 static Glib::ustring au_cache_path ();
237 typedef std::map<std::string,AUPluginCachedInfo> CachedInfoMap;
238 static CachedInfoMap cached_info;
240 static bool cached_io_configuration (const std::string&, UInt32, CAComponent&, AUPluginCachedInfo&, const std::string& name);
241 static void add_cached_info (const std::string&, AUPluginCachedInfo&);
242 static void save_cached_info ();
245 typedef boost::shared_ptr<AUPluginInfo> AUPluginInfoPtr;
247 } // namespace ARDOUR
249 #endif // __ardour_audio_unit_h__