1 /* GSequencer - Advanced GTK Sequencer 2 * Copyright (C) 2005-2021 Joël Krähemann 3 * 4 * This file is part of GSequencer. 5 * 6 * GSequencer is free software: you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License as published by 8 * the Free Software Foundation, either version 3 of the License, or 9 * (at your option) any later version. 10 * 11 * GSequencer is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 * GNU General Public License for more details. 15 * 16 * You should have received a copy of the GNU General Public License 17 * along with GSequencer. If not, see <http://www.gnu.org/licenses/>. 18 */ 19 20 #ifndef __AGS_AUDIO_SIGNAL_H__ 21 #define __AGS_AUDIO_SIGNAL_H__ 22 23 #include <glib.h> 24 #include <glib-object.h> 25 26 #include <ags/libags.h> 27 28 #include <ags/audio/ags_note.h> 29 30 G_BEGIN_DECLS 31 32 #define AGS_TYPE_AUDIO_SIGNAL (ags_audio_signal_get_type()) 33 #define AGS_AUDIO_SIGNAL(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), AGS_TYPE_AUDIO_SIGNAL, AgsAudioSignal)) 34 #define AGS_AUDIO_SIGNAL_CLASS(class) (G_TYPE_CHECK_CLASS_CAST((class), AGS_TYPE_AUDIO_SIGNAL, AgsAudioSignalClass)) 35 #define AGS_IS_AUDIO_SIGNAL(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), AGS_TYPE_AUDIO_SIGNAL)) 36 #define AGS_IS_AUDIO_SIGNAL_CLASS(class) (G_TYPE_CHECK_CLASS_TYPE ((class), AGS_TYPE_AUDIO_SIGNAL)) 37 #define AGS_AUDIO_SIGNAL_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), AGS_TYPE_AUDIO_SIGNAL, AgsAudioSignalClass)) 38 39 #define AGS_AUDIO_SIGNAL_GET_OBJ_MUTEX(obj) (&(((AgsAudioSignal *) obj)->obj_mutex)) 40 #define AGS_AUDIO_SIGNAL_GET_STREAM_MUTEX(obj) (&(((AgsAudioSignal *) obj)->stream_mutex)) 41 42 typedef struct _AgsAudioSignal AgsAudioSignal; 43 typedef struct _AgsAudioSignalClass AgsAudioSignalClass; 44 45 /** 46 * AgsAudioSignalFlags: 47 * @AGS_AUDIO_SIGNAL_ADDED_TO_REGISTRY: the audio signal was added to registry, see #AgsConnectable::add_to_registry() 48 * @AGS_AUDIO_SIGNAL_CONNECTED: indicates the audio signal was connected by calling #AgsConnectable::connect() 49 * @AGS_AUDIO_SIGNAL_TEMPLATE: the audio signal acts as a template 50 * @AGS_AUDIO_SIGNAL_RT_TEMPLATE: the audio signal acts as a realtime template 51 * @AGS_AUDIO_SIGNAL_MASTER: the audio signal needs master 52 * @AGS_AUDIO_SIGNAL_FEED: the audio signal needs feed 53 * @AGS_AUDIO_SIGNAL_RECYCLED: the audio signal is recycled 54 * @AGS_AUDIO_SIGNAL_STREAM: the audio signal needs stream 55 * @AGS_AUDIO_SIGNAL_SLICE_ALLOC: the audio signal allocates from slice 56 * 57 * Enum values to control the behavior or indicate internal state of #AgsAudioSignal by 58 * enable/disable as flags. 59 */ 60 typedef enum{ 61 AGS_AUDIO_SIGNAL_ADDED_TO_REGISTRY = 1, 62 AGS_AUDIO_SIGNAL_CONNECTED = 1 << 1, 63 AGS_AUDIO_SIGNAL_TEMPLATE = 1 << 2, 64 AGS_AUDIO_SIGNAL_RT_TEMPLATE = 1 << 3, 65 AGS_AUDIO_SIGNAL_MASTER = 1 << 4, 66 AGS_AUDIO_SIGNAL_FEED = 1 << 5, 67 AGS_AUDIO_SIGNAL_RECYCLED = 1 << 6, 68 AGS_AUDIO_SIGNAL_STREAM = 1 << 7, 69 AGS_AUDIO_SIGNAL_SLICE_ALLOC = 1 << 8, 70 }AgsAudioSignalFlags; 71 72 struct _AgsAudioSignal 73 { 74 GObject gobject; 75 76 guint flags; 77 78 GRecMutex obj_mutex; 79 80 AgsUUID *uuid; 81 82 GObject *recycling; 83 84 GObject *output_soundcard; 85 gint output_soundcard_channel; 86 87 GObject *input_soundcard; 88 gint input_soundcard_channel; 89 90 guint samplerate; 91 guint buffer_size; 92 guint format; 93 guint word_size; 94 95 guint length; 96 guint first_frame; 97 guint last_frame; // the last frame at stream_end 98 99 guint frame_count; // initial size 100 guint loop_start; 101 guint loop_end; 102 103 gdouble delay; 104 guint attack; 105 106 AgsComplex damping; 107 AgsComplex vibration; 108 guint timbre_start; 109 guint timbre_end; 110 111 GObject *template; 112 113 GObject *rt_template; 114 GList *note; 115 116 GObject *recall_id; // AGS_TYPE_RECALL_ID to identify the AgsAudioSignal 117 118 GRecMutex stream_mutex; 119 120 GList *stream; 121 GList *stream_current; 122 GList *stream_end; 123 }; 124 125 struct _AgsAudioSignalClass 126 { 127 GObjectClass gobject; 128 129 void (*add_note)(AgsAudioSignal *audio_signal, 130 GObject *note); 131 void (*remove_note)(AgsAudioSignal *audio_signal, 132 GObject *note); 133 134 void (*refresh_data)(AgsAudioSignal *audio_signal); 135 }; 136 137 GType ags_audio_signal_get_type(); 138 GType ags_audio_signal_flags_get_type(); 139 140 GRecMutex* ags_audio_signal_get_obj_mutex(AgsAudioSignal *audio_signal); 141 142 void ags_audio_signal_stream_lock(AgsAudioSignal *audio_signal); 143 void ags_audio_signal_stream_unlock(AgsAudioSignal *audio_signal); 144 145 gboolean ags_audio_signal_test_flags(AgsAudioSignal *audio_signal, guint flags); 146 void ags_audio_signal_set_flags(AgsAudioSignal *audio_signal, guint flags); 147 void ags_audio_signal_unset_flags(AgsAudioSignal *audio_signal, guint flags); 148 149 void* ags_stream_alloc(guint buffer_size, 150 guint format); 151 void ags_stream_free(void *buffer); 152 153 void* ags_stream_slice_alloc(guint buffer_size, 154 guint format); 155 void ags_stream_slice_free(guint buffer_size, 156 guint format, 157 void *buffer); 158 159 /* parent */ 160 GObject* ags_audio_signal_get_recycling(AgsAudioSignal *audio_signal); 161 void ags_audio_signal_set_recycling(AgsAudioSignal *audio_signal, GObject *recycling); 162 163 /* soundcard */ 164 GObject* ags_audio_signal_get_output_soundcard(AgsAudioSignal *audio_signal); 165 void ags_audio_signal_set_output_soundcard(AgsAudioSignal *audio_signal, GObject *output_soundcard); 166 167 GObject* ags_audio_signal_get_input_soundcard(AgsAudioSignal *audio_signal); 168 void ags_audio_signal_set_input_soundcard(AgsAudioSignal *audio_signal, GObject *input_soundcard); 169 170 /* presets */ 171 guint ags_audio_signal_get_samplerate(AgsAudioSignal *audio_signal); 172 void ags_audio_signal_set_samplerate(AgsAudioSignal *audio_signal, guint samplerate); 173 174 guint ags_audio_signal_get_buffer_size(AgsAudioSignal *audio_signal); 175 void ags_audio_signal_set_buffer_size(AgsAudioSignal *audio_signal, guint buffer_size); 176 177 guint ags_audio_signal_get_format(AgsAudioSignal *audio_signal); 178 void ags_audio_signal_set_format(AgsAudioSignal *audio_signal, guint format); 179 180 /* children */ 181 GList* ags_audio_signal_get_note(AgsAudioSignal *audio_signal); 182 void ags_audio_signal_set_note(AgsAudioSignal *audio_signal, GList *note); 183 184 void ags_audio_signal_add_note(AgsAudioSignal *audio_signal, 185 GObject *note); 186 void ags_audio_signal_remove_note(AgsAudioSignal *audio_signal, 187 GObject *note); 188 189 GList* ags_audio_signal_get_stream(AgsAudioSignal *audio_signal); 190 void ags_audio_signal_set_stream(AgsAudioSignal *audio_signal, GList *stream); 191 192 /* presets related */ 193 void ags_audio_signal_refresh_data(AgsAudioSignal *audio_signal); 194 195 /* control */ 196 void ags_audio_signal_add_stream(AgsAudioSignal *audio_signal); 197 void ags_audio_signal_stream_resize(AgsAudioSignal *audio_signal, guint length); 198 void ags_audio_signal_stream_safe_resize(AgsAudioSignal *audio_signal, guint length); 199 200 void ags_audio_signal_clear(AgsAudioSignal *audio_signal); 201 202 void ags_audio_signal_duplicate_stream(AgsAudioSignal *audio_signal, 203 AgsAudioSignal *template); 204 205 void ags_audio_signal_feed(AgsAudioSignal *audio_signal, 206 AgsAudioSignal *template, 207 guint frame_count); 208 void ags_audio_signal_feed_extended(AgsAudioSignal *audio_signal, 209 AgsAudioSignal *template, 210 guint frame_count, guint old_frame_count, 211 gboolean do_open, gboolean do_close); 212 213 void ags_audio_signal_open_feed(AgsAudioSignal *audio_signal, 214 AgsAudioSignal *template, 215 guint frame_count, guint old_frame_count); 216 void ags_audio_signal_continue_feed(AgsAudioSignal *audio_signal, 217 AgsAudioSignal *template, 218 guint frame_count, guint old_frame_count); 219 void ags_audio_signal_close_feed(AgsAudioSignal *audio_signal, 220 AgsAudioSignal *template, 221 guint frame_count, guint old_frame_count); 222 223 /* query */ 224 guint ags_audio_signal_get_length_till_current(AgsAudioSignal *audio_signal); 225 gboolean ags_audio_signal_contains_note(AgsAudioSignal *audio_signal, 226 AgsNote *note); 227 228 AgsAudioSignal* ags_audio_signal_get_template(GList *audio_signal); 229 GList* ags_audio_signal_get_rt_template(GList *audio_signal); 230 231 GList* ags_audio_signal_find_stream_current(GList *audio_signal, 232 GObject *recall_id); 233 GList* ags_audio_signal_find_by_recall_id(GList *audio_signal, 234 GObject *recall_id); 235 236 gboolean ags_audio_signal_is_active(GList *audio_signal, 237 GObject *recall_id); 238 239 /* instantiate */ 240 AgsAudioSignal* ags_audio_signal_new(GObject *output_soundcard, 241 GObject *recycling, 242 GObject *recall_id); 243 244 AgsAudioSignal* ags_audio_signal_new_with_length(GObject *output_soundcard, 245 GObject *recycling, 246 GObject *recall_id, 247 guint length); 248 249 G_END_DECLS 250 251 #endif /*__AGS_AUDIO_SIGNAL_H__*/ 252