r1014: Enable horizontal scrolling with the mouse wheel by pressing Ctrl.
[cinelerra_cv/ct.git] / cinelerra / tracking.C
blobd0cc7ef459939843863db73c05817e38b21b042a
1 #include "arender.h"
2 #include "condition.h"
3 #include "cplayback.h"
4 #include "cwindow.h"
5 #include "cwindowgui.h"
6 #include "edl.h"
7 #include "edlsession.h"
8 #include "levelwindow.h"
9 #include "levelwindowgui.h"
10 #include "localsession.h"
11 #include "mainclock.h"
12 #include "meterpanel.h"
13 #include "mwindow.h"
14 #include "mwindowgui.h"
15 #include "tracking.h"
16 #include "patchbay.h"
17 #include "playbackengine.h"
18 #include "renderengine.h"
19 #include "mainsession.h"
20 #include "trackcanvas.h"
24 // States
25 #define PLAYING 0
26 #define DONE 1
30 Tracking::Tracking(MWindow *mwindow)
31  : Thread(1, 0, 0)
33         this->gui = mwindow->gui;
34         this->mwindow = mwindow; 
35         follow_loop = 0; 
36         visible = 0;
37         pixel = 0;
38         state = DONE;
39         startup_lock = new Condition(0, "Tracking::startup_lock");
42 Tracking::~Tracking()
44         if(state == PLAYING)
45         {
46 // Stop loop
47                 state = DONE;
48 // Not working in NPTL for some reason
49 //              Thread::cancel();
50                 Thread::join();
51         }
54         delete startup_lock;
57 void Tracking::create_objects()
59 //      start();
62 int Tracking::start_playback(double new_position)
64         if(state != PLAYING)
65         {
66                 last_position = new_position;
67                 state = PLAYING;
68                 draw();
69                 Thread::start();
70                 startup_lock->lock("Tracking::start_playback");
71         }
72         return 0;
75 int Tracking::stop_playback()
77         if(state != DONE)
78         {
79 // Stop loop
80                 state = DONE;
81 // Not working in NPTL for some reason
82 //              Thread::cancel();
83                 Thread::join();
85 // Final position is updated continuously during playback
86 // Get final position
87                 double position = get_tracking_position();
88 // Update cursor
89                 update_tracker(position);
90         
91                 stop_meters();
92                 state = DONE;
93         }
94         return 0;
97 PlaybackEngine* Tracking::get_playback_engine()
99         return mwindow->cwindow->playback_engine;
102 double Tracking::get_tracking_position()
104         return get_playback_engine()->get_tracking_position();
107 int Tracking::get_pixel(double position)
109         return (int64_t)((position - mwindow->edl->local_session->view_start) *
110                 mwindow->edl->session->sample_rate / 
111                 mwindow->edl->local_session->zoom_sample + 
112                 0.5);
116 void Tracking::update_meters(int64_t position)
118         double output_levels[MAXCHANNELS];
119         int do_audio = get_playback_engine()->get_output_levels(output_levels, position);
121         if(do_audio)
122         {
123                 module_levels.remove_all();
124                 get_playback_engine()->get_module_levels(&module_levels, position);
126                 mwindow->cwindow->gui->lock_window("Tracking::update_meters 1");
127                 mwindow->cwindow->gui->meters->update(output_levels);
128                 mwindow->cwindow->gui->unlock_window();
130                 mwindow->lwindow->gui->lock_window("Tracking::update_meters 2");
131                 mwindow->lwindow->gui->panel->update(output_levels);
132                 mwindow->lwindow->gui->unlock_window();
134                 mwindow->gui->lock_window("Tracking::update_meters 3");
135                 mwindow->gui->patchbay->update_meters(&module_levels);
136                 mwindow->gui->unlock_window();
137         }
140 void Tracking::stop_meters()
142         mwindow->cwindow->gui->lock_window("Tracking::stop_meters 1");
143         mwindow->cwindow->gui->meters->stop_meters();
144         mwindow->cwindow->gui->unlock_window();
146         mwindow->gui->lock_window("Tracking::stop_meters 2");
147         mwindow->gui->patchbay->stop_meters();
148         mwindow->gui->unlock_window();
150         mwindow->lwindow->gui->lock_window("Tracking::stop_meters 3");
151         mwindow->lwindow->gui->panel->stop_meters();
152         mwindow->lwindow->gui->unlock_window();
158 void Tracking::update_tracker(double position)
162 void Tracking::draw()
164         gui->lock_window("Tracking::draw");
165         if(!visible)
166         {
167                 pixel = get_pixel(last_position);
168         }
170         gui->canvas->set_color(GREEN);
171         gui->canvas->set_inverse();
172         gui->canvas->draw_line(pixel, 0, pixel, gui->canvas->get_h());
173         gui->canvas->set_opaque();
174         gui->canvas->flash(pixel, 0, pixel + 1, gui->canvas->get_h());
175         visible ^= 1;
176         gui->unlock_window();
180 void Tracking::run()
182         startup_lock->unlock();
184         double position;
185         while(state != DONE)
186         {
187                 Thread::enable_cancel();
188                 timer.delay(1000 / TRACKING_RATE);
189                 Thread::disable_cancel();
191                 if(state != DONE)
192                 {
194 // can be stopped during wait
195                         if(get_playback_engine()->tracking_active)
196                         {
197 // Get position of cursor
198                                 position = get_tracking_position();
200 // Update cursor
201                                 update_tracker(position);
202                         }
203                 }
204         }