r1007: Make configure detect and work on amd64.
[cinelerra_cv/mob.git] / plugins / delayaudio / delayaudio.C
blob084c636d51b0886559f84eb7fab302cad093857c
1 #include "bcdisplayinfo.h"
2 #include "clip.h"
3 #include "bchash.h"
4 #include "delayaudio.h"
5 #include "filexml.h"
6 #include "picon_png.h"
7 #include "vframe.h"
9 #include <string.h>
11 #include <libintl.h>
12 #define _(String) gettext(String)
13 #define gettext_noop(String) String
14 #define N_(String) gettext_noop (String)
17 PluginClient* new_plugin(PluginServer *server)
19         return new DelayAudio(server);
23 DelayAudio::DelayAudio(PluginServer *server)
24  : PluginAClient(server)
26         reset();
27         load_defaults();
30 DelayAudio::~DelayAudio()
32         if(thread)
33         {
34                 thread->window->set_done(0);
35                 thread->completion.lock();
36                 delete thread;
37         }
39         save_defaults();
40         delete defaults;
41         
42         if(buffer) delete [] buffer;
47 VFrame* DelayAudio::new_picon()
49         return new VFrame(picon_png);
52 char* DelayAudio::plugin_title() { return N_("Delay audio"); }
53 int DelayAudio::is_realtime() { return 1; }
56 void DelayAudio::reset()
58         need_reconfigure = 1;
59         buffer = 0;
60         thread = 0;
63 void DelayAudio::load_configuration()
65         KeyFrame *prev_keyframe;
66         prev_keyframe = get_prev_keyframe(get_source_position());
67         
68         DelayAudioConfig old_config;
69         old_config.copy_from(config);
70         read_data(prev_keyframe);
72         if(!old_config.equivalent(config))
73         {
74 // Reconfigure
75                 need_reconfigure = 1;
76         }
79 int DelayAudio::load_defaults()
81         char directory[BCTEXTLEN];
83         sprintf(directory, "%sdelayaudio.rc", BCASTDIR);
84         defaults = new BC_Hash(directory);
85         defaults->load();
86         config.length = defaults->get("LENGTH", (double)1);
87         return 0;
92 int DelayAudio::save_defaults()
94         defaults->update("LENGTH", config.length);
95         defaults->save();
96         return 0;
99 void DelayAudio::read_data(KeyFrame *keyframe)
101         FileXML input;
102         input.set_shared_string(keyframe->data, strlen(keyframe->data));
104         int result = 0;
105         while(!result)
106         {
107                 result = input.read_tag();
109                 if(!result)
110                 {
111                         if(input.tag.title_is("DELAYAUDIO"))
112                         {
113                                 config.length = input.tag.get_property("LENGTH", (double)config.length);
114                         }
115                 }
116         }
120 void DelayAudio::save_data(KeyFrame *keyframe)
122         FileXML output;
123         output.set_shared_string(keyframe->data, MESSAGESIZE);
125         output.tag.set_title("DELAYAUDIO");
126         output.tag.set_property("LENGTH", (double)config.length);
127         output.append_tag();
128         output.append_newline();
129         output.terminate_string();
132 void DelayAudio::reconfigure()
134         input_start = (int64_t)(config.length * PluginAClient::project_sample_rate + 0.5);
135         int64_t new_allocation = input_start + PluginClient::in_buffer_size;
136         double *new_buffer = new double[new_allocation];
137         bzero(new_buffer, sizeof(double) * new_allocation);
139 // printf("DelayAudio::reconfigure %f %d %d %d\n", 
140 // config.length, 
141 // PluginAClient::project_sample_rate, 
142 // PluginClient::in_buffer_size,
143 // new_allocation);
144 // 
147         if(buffer)
148         {
149                 int size = MIN(new_allocation, allocation);
151                 memcpy(new_buffer, 
152                         buffer, 
153                         (size - PluginClient::in_buffer_size) * sizeof(double));
154                 delete [] buffer;
155         }
157         allocation = new_allocation;
158         buffer = new_buffer;
159         allocation = new_allocation;
160         need_reconfigure = 0;
163 int DelayAudio::process_realtime(int64_t size, double *input_ptr, double *output_ptr)
165         load_configuration();
166         if(need_reconfigure) reconfigure();
168 // printf("DelayAudio::process_realtime %d %d\n",
169 // input_start, size);
173         memcpy(buffer + input_start, input_ptr, size * sizeof(double));
174         memcpy(output_ptr, buffer, size * sizeof(double));
176         for(int i = size, j = 0; i < allocation; i++, j++)
177         {
178                 buffer[j] = buffer[i];
179         }
181         return 0;
184 int DelayAudio::show_gui()
186         load_configuration();
187         
188         thread = new DelayAudioThread(this);
189         thread->start();
190         return 0;
193 int DelayAudio::set_string()
195         if(thread) thread->window->set_title(gui_string);
196         return 0;
199 void DelayAudio::raise_window()
201         if(thread)
202         {
203                 thread->window->raise_window();
204                 thread->window->flush();
205         }
208 void DelayAudio::update_gui()
210         if(thread)
211         {
212                 load_configuration();
213                 thread->window->lock_window();
214                 thread->window->update_gui();
215                 thread->window->unlock_window();
216         }
230 DelayAudioThread::DelayAudioThread(DelayAudio *plugin)
231  : Thread()
233         this->plugin = plugin;
234         set_synchronous(0);
235         completion.lock();
241 DelayAudioThread::~DelayAudioThread()
243         delete window;
247 void DelayAudioThread::run()
249         BC_DisplayInfo info;
250         
251         window = new DelayAudioWindow(plugin,
252                 info.get_abs_cursor_x() - 125, 
253                 info.get_abs_cursor_y() - 115);
254         
255         window->create_objects();
256         int result = window->run_window();
257         completion.unlock();
258 // Last command executed in thread
259         if(result) plugin->client_side_close();
271 DelayAudioWindow::DelayAudioWindow(DelayAudio *plugin, int x, int y)
272  : BC_Window(plugin->gui_string, 
273         x, 
274         y, 
275         200, 
276         80, 
277         200, 
278         80, 
279         0, 
280         0,
281         1)
283         this->plugin = plugin;
286 DelayAudioWindow::~DelayAudioWindow()
290 int DelayAudioWindow::create_objects()
292         add_subwindow(new BC_Title(10, 10, _("Delay seconds:")));
293         add_subwindow(length = new DelayAudioTextBox(plugin, 10, 40));
294         update_gui();
295         show_window();
296         flush();
297         return 0;
300 int DelayAudioWindow::close_event()
302 // Set result to 1 to indicate a client side close
303         set_done(1);
304         return 1;
307 void DelayAudioWindow::update_gui()
309         char string[BCTEXTLEN];
310         sprintf(string, "%.04f", plugin->config.length);
311         length->update(string);
325 DelayAudioTextBox::DelayAudioTextBox(DelayAudio *plugin, int x, int y)
326  : BC_TextBox(x, y, 150, 1, "")
328         this->plugin = plugin;
331 DelayAudioTextBox::~DelayAudioTextBox()
335 int DelayAudioTextBox::handle_event()
337         plugin->config.length = atof(get_text());
338         if(plugin->config.length < 0) plugin->config.length = 0;
339         plugin->send_configure_change();
340         return 1;
350 DelayAudioConfig::DelayAudioConfig()
352         length = 1;
354         
355 int DelayAudioConfig::equivalent(DelayAudioConfig &that)
357         return(EQUIV(this->length, that.length));
360 void DelayAudioConfig::copy_from(DelayAudioConfig &that)
362         this->length = that.length;