add tempo adjustment
authorPaul Davis <paul@linuxaudiosystems.com>
Fri, 4 Aug 2017 22:09:31 +0000 (18:09 -0400)
committerPaul Davis <paul@linuxaudiosystems.com>
Fri, 4 Aug 2017 22:09:31 +0000 (18:09 -0400)
tools/bb/bb.cc
tools/bb/bb.h
tools/bb/gui.cc
tools/bb/gui.h

index 0689b513f294a9121d613bbb38a9d78720362c6a..668630c0f95d52cabfff8dbcea425768d8253a7d 100644 (file)
@@ -144,6 +144,7 @@ BeatBox::BeatBox (int sr)
        , _running (false)
        , _measures (2)
        , _tempo (120)
+       , _tempo_request (0)
        , _meter_beats (4)
        , _meter_beat_type (4)
        , _input (0)
@@ -183,19 +184,19 @@ BeatBox::register_ports (jack_client_t* jack)
 }
 
 void
-BeatBox::start ()
+BeatBox::compute_tempo_clocks ()
 {
-       /* compute tempo, beat steps etc. */
-
-       /*
-          superclocks_per_minute = superclock_ticks_per_second * 60;
-          beats_per_minute = _tempo;
-          whole_notes_per_minute = beats_per_minute / _meter_beat_type;
-       */
-
        whole_note_superclocks = (superclock_ticks_per_second * 60) / (_tempo / _meter_beat_type);
        beat_superclocks = whole_note_superclocks / _meter_beat_type;
        measure_superclocks = beat_superclocks * _meter_beats;
+}
+
+void
+BeatBox::start ()
+{
+       /* compute tempo, beat steps etc. */
+
+       compute_tempo_clocks ();
 
        /* we can start */
 
@@ -208,6 +209,12 @@ BeatBox::stop ()
        _start_requested = false;
 }
 
+void
+BeatBox::set_tempo (float bpm)
+{
+       _tempo_request = bpm;
+}
+
 int
 BeatBox::process (int nsamples)
 {
@@ -230,6 +237,18 @@ BeatBox::process (int nsamples)
                return 0;
        }
 
+       if (_tempo_request) {
+               double ratio = _tempo / _tempo_request;
+               _tempo = _tempo_request;
+               _tempo_request = 0;
+
+               compute_tempo_clocks ();
+
+               for (Events::iterator ee = _current_events.begin(); ee != _current_events.end(); ++ee) {
+                       (*ee)->time = llrintf ((*ee)->time * ratio);
+               }
+       }
+
        superclock_t process_start = superclock_cnt - last_start;
        superclock_t process_end = process_start + superclocks;
        const superclock_t loop_length = _measures * measure_superclocks;
@@ -324,6 +343,7 @@ BeatBox::process (int nsamples)
                event_pool.pop_back ();
 
                e->time = quantized_time;
+               e->whole_note_superclocks = whole_note_superclocks;
                e->size = in_event.size;
                memcpy (e->buf, in_event.buffer, in_event.size);
 
index e16b9360a82215db4570ab21651d08f89fc4284b..79a24d69291edeccd5e37ed7c0eaf9001b5296c0 100644 (file)
@@ -44,6 +44,7 @@ class BeatBox {
        bool _running;
        int   _measures;
        float _tempo;
+       float _tempo_request;
        int   _meter_beats;
        int   _meter_beat_type;
        jack_port_t* _input;
@@ -60,6 +61,7 @@ class BeatBox {
 
        struct Event {
                superclock_t time;
+               superclock_t whole_note_superclocks;
                size_t       size;
                unsigned char  buf[24];
 
@@ -77,6 +79,8 @@ class BeatBox {
 
        typedef std::vector<Event*> EventPool;
        EventPool  event_pool;
+
+       void compute_tempo_clocks ();
 };
 
 
index cdb34eb124b3844c06f86ffe55221e23b905df12..0bb894e3c27b0a432031cf2191673632a6b6bc88 100644 (file)
@@ -14,6 +14,8 @@ BBGUI::BBGUI (int* argc, char** argv[], jack_client_t* j, BeatBox* bb)
        , quantize_whole (quantize_group, "Whole")
        , play_button ("Run")
        , clear_button ("Clear")
+       , tempo_adjustment (bb->tempo(), 1, 300, 1, 10)
+       , tempo_spinner (tempo_adjustment)
 {
        quantize_off.signal_toggled().connect (sigc::bind (sigc::mem_fun (*this, &BBGUI::set_quantize), 0));
        quantize_32nd.signal_toggled().connect (sigc::bind (sigc::mem_fun (*this, &BBGUI::set_quantize), 32));
@@ -37,6 +39,10 @@ BBGUI::BBGUI (int* argc, char** argv[], jack_client_t* j, BeatBox* bb)
        misc_button_box.pack_start (play_button);
        misc_button_box.pack_start (clear_button);
 
+       tempo_adjustment.signal_value_changed().connect (sigc::mem_fun (*this, &BBGUI::tempo_changed));
+
+       misc_button_box.pack_start (tempo_spinner);
+
        global_vbox.pack_start (misc_button_box);
        global_vbox.pack_start (quantize_button_box, true, true);
        window.add (global_vbox);
@@ -54,6 +60,13 @@ BBGUI::run ()
        main.run ();
 }
 
+void
+BBGUI::tempo_changed ()
+{
+       float t = tempo_adjustment.get_value();
+       bbox->set_tempo (t);
+}
+
 void
 BBGUI::set_quantize (int divisor)
 {
index d3d9dc5e00ca1aa26e9e41193c62ee90d9dcef76..4c08d5e4abb4fd5b7fff7b18e5f3261c83cd14ab 100644 (file)
@@ -31,13 +31,18 @@ class BBGUI {
        Gtk::ToggleButton play_button;
        Gtk::Button clear_button;
 
+       Gtk::Adjustment tempo_adjustment;
+       Gtk::SpinButton tempo_spinner;
+
        Gtk::VBox global_vbox;
        Gtk::VBox quantize_button_box;
        Gtk::HBox misc_button_box;
 
+
        void set_quantize (int divisor);
        void toggle_play ();
        void clear ();
+       void tempo_changed ();
 };
 
 #endif /* __bb_gui_h__ */