Updates for set_type_hint() and the sfdb_ui.
[ardour.git] / gtk2_ardour / sfdb_ui.cc
1 /*
2     Copyright (C) 2005 Paul Davis 
3     Written by Taybin Rutkin
4
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.
9
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.
14
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.
18
19
20 */
21
22 #include <gtkmm/box.h>
23 #include <gtkmm/stock.h>
24
25 #include <ardour/audio_library.h>
26 #include <ardour/sndfile_helpers.h>
27
28 #include "sfdb_ui.h"
29
30 #include "i18n.h"
31
32 std::string length2string (const int32_t frames, const int32_t sample_rate);
33
34 SoundFileBox::SoundFileBox ()
35         :
36         _session(0),
37         current_pid(0),
38         fields(Gtk::ListStore::create(label_columns)),
39         main_box (false, 3),
40         top_box (true, 4),
41         bottom_box (true, 4),
42         play_btn(_("Play")),
43         stop_btn(_("Stop")),
44         add_field_btn(_("Add Field...")),
45         remove_field_btn(_("Remove Field"))
46 {
47         set_name (X_("SoundFileBox"));
48         border_frame.set_label (_("Soundfile Info"));
49         border_frame.add (main_box);
50
51         pack_start (border_frame);
52         set_border_width (4);
53
54         path_box.set_spacing (4);
55         path_box.pack_start (path, false, false);
56         path_box.pack_start (path_entry, true, true);
57
58         main_box.set_border_width (4);
59
60         main_box.pack_start(label, false, false);
61         main_box.pack_start(path_box, false, false);
62         main_box.pack_start(length, false, false);
63         main_box.pack_start(format, false, false);
64         main_box.pack_start(channels, false, false);
65         main_box.pack_start(samplerate, false, false);
66         main_box.pack_start(field_view, true, true);
67         main_box.pack_start(top_box, false, false);
68         main_box.pack_start(bottom_box, false, false);
69
70         field_view.set_size_request(200, 150);
71         top_box.set_homogeneous(true);
72         top_box.pack_start(add_field_btn);
73         top_box.pack_start(remove_field_btn);
74
75         remove_field_btn.set_sensitive(false);
76
77         bottom_box.set_homogeneous(true);
78         bottom_box.pack_start(play_btn);
79         bottom_box.pack_start(stop_btn);
80
81         play_btn.signal_clicked().connect (mem_fun (*this, &SoundFileBox::play_btn_clicked));
82         stop_btn.signal_clicked().connect (mem_fun (*this, &SoundFileBox::stop_btn_clicked));
83
84         add_field_btn.signal_clicked().connect
85                         (mem_fun (*this, &SoundFileBox::add_field_clicked));
86         remove_field_btn.signal_clicked().connect
87                         (mem_fun (*this, &SoundFileBox::remove_field_clicked));
88
89         field_view.get_selection()->signal_changed().connect (mem_fun (*this, &SoundFileBox::field_selected));
90         ARDOUR::Library->fields_changed.connect (mem_fun (*this, &SoundFileBox::setup_fields));
91
92         show_all();
93         stop_btn.hide();
94 }
95
96 void
97 SoundFileBox::set_session(ARDOUR::Session* s)
98 {
99         _session = s;
100
101     if (!_session) {
102                 play_btn.set_sensitive(false);
103         } else {
104                 _session->AuditionActive.connect(mem_fun (*this, &SoundFileBox::audition_status_changed));
105         }
106 }
107
108 int
109 SoundFileBox::setup_labels (string filename) 
110 {
111     SNDFILE *sf;
112
113     if ((sf = sf_open ((char *) filename.c_str(), SFM_READ, &sf_info)) < 0) {
114         error << string_compose(_("file \"%1\" could not be opened"), filename) << endmsg;
115         return -1;
116     }
117
118     if (sf_info.frames == 0 && sf_info.channels == 0 &&
119                 sf_info.samplerate == 0 && sf_info.format == 0 &&
120                 sf_info.sections == 0) {
121                 /* .. ok, its not a sound file */
122             error << string_compose(_("file \"%1\" appears not to be an audio file"), filename) << endmsg;
123             return -1;
124         }
125
126         label.set_alignment (0.0f, 0.0f);
127     label.set_text ("Label: " + ARDOUR::Library->get_label(filename));
128
129         path.set_text ("Path: ");
130         path_entry.set_text (filename);
131         path_entry.set_position (-1);
132
133         length.set_alignment (0.0f, 0.0f);
134         length.set_text (string_compose("Length: %1", length2string(sf_info.frames, sf_info.samplerate)));
135
136         format.set_alignment (0.0f, 0.0f);
137         format.set_text (string_compose("Format: %1, %2", 
138                                 sndfile_major_format(sf_info.format),
139                                 sndfile_minor_format(sf_info.format)));
140
141         channels.set_alignment (0.0f, 0.0f);
142         channels.set_text (string_compose("Channels: %1", sf_info.channels));
143
144         samplerate.set_alignment (0.0f, 0.0f);
145         samplerate.set_text (string_compose("Samplerate: %1", sf_info.samplerate));
146
147         return 0;
148 }
149
150 void
151 SoundFileBox::setup_fields ()
152 {}
153
154 void
155 SoundFileBox::play_btn_clicked ()
156 {}
157
158 void
159 SoundFileBox::stop_btn_clicked ()
160 {}
161
162 void
163 SoundFileBox::add_field_clicked ()
164 {}
165
166 void
167 SoundFileBox::remove_field_clicked ()
168 {}
169
170 void
171 SoundFileBox::audition_status_changed (bool state)
172 {}
173
174 void
175 SoundFileBox::field_selected ()
176 {}
177
178 bool
179 SoundFileBox::update (std::string filename)
180 {
181         return true;
182 }
183
184 SoundFileBrowser::SoundFileBrowser (std::string title)
185         :
186         ArdourDialog(title),
187         chooser(Gtk::FILE_CHOOSER_ACTION_OPEN)
188 {
189         get_vbox()->pack_start(chooser);
190         chooser.set_preview_widget(preview);
191
192         chooser.signal_update_preview().connect(mem_fun(*this, &SoundFileBrowser::update_preview));
193 }
194
195 void
196 SoundFileBrowser::set_session (ARDOUR::Session* s)
197 {
198         preview.set_session(s);
199 }
200
201 void
202 SoundFileBrowser::update_preview ()
203 {
204         chooser.set_preview_widget_active(preview.update(chooser.get_filename()));
205 }
206
207 SoundFileChooser::SoundFileChooser (std::string title)
208         :
209         SoundFileBrowser(title)
210 {
211         add_button (Gtk::Stock::OPEN, Gtk::RESPONSE_OK);
212         add_button (Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
213 }
214
215 SoundFileOmega::SoundFileOmega (std::string title)
216         :
217         SoundFileBrowser(title),
218         embed_btn (_("Embed")),
219         import_btn (_("Import")),
220         split_check (_("Split Channels"))
221 {
222         get_action_area()->pack_start(embed_btn);
223         get_action_area()->pack_start(import_btn);
224         add_button (Gtk::Stock::CLOSE, Gtk::RESPONSE_CLOSE);
225
226         chooser.set_extra_widget(split_check);
227
228         embed_btn.signal_clicked().connect (mem_fun (*this, &SoundFileOmega::embed_clicked));
229         import_btn.signal_clicked().connect (mem_fun (*this, &SoundFileOmega::import_clicked));
230 }
231
232 void
233 SoundFileOmega::embed_clicked ()
234 {
235         Embedded (chooser.get_filenames(), split_check.get_active());
236 }
237
238 void
239 SoundFileOmega::import_clicked ()
240 {
241         Imported (chooser.get_filenames(), split_check.get_active());
242 }
243
244 std::string
245 length2string (const int32_t frames, const int32_t sample_rate)
246 {
247     int secs = (int) (frames / (float) sample_rate);
248     int hrs =  secs / 3600;
249     secs -= (hrs * 3600);
250     int mins = secs / 60;
251     secs -= (mins * 60);
252
253     int total_secs = (hrs * 3600) + (mins * 60) + secs;
254     int frames_remaining = frames - (total_secs * sample_rate);
255     float fractional_secs = (float) frames_remaining / sample_rate;
256
257     char duration_str[32];
258     sprintf (duration_str, "%02d:%02d:%05.2f", hrs, mins, (float) secs + fractional_secs);
259
260     return duration_str;
261 }
262