00001 #include "auto.h"
00002 #include "cache.h"
00003 #include "commonrender.h"
00004 #include "condition.h"
00005 #include "edl.h"
00006 #include "edlsession.h"
00007 #include "intautos.h"
00008 #include "localsession.h"
00009 #include "mainsession.h"
00010 #include "module.h"
00011 #include "mwindow.h"
00012 #include "patchbay.h"
00013 #include "patch.h"
00014 #include "playabletracks.h"
00015 #include "preferences.h"
00016 #include "renderengine.h"
00017 #include "track.h"
00018 #include "tracks.h"
00019 #include "transportque.h"
00020 #include "virtualconsole.h"
00021
00022 CommonRender::CommonRender(RenderEngine *renderengine)
00023 : Thread(1, 0, 0)
00024 {
00025 this->renderengine = renderengine;
00026 reset_parameters();
00027 start_lock = new Condition(0, "CommonRender::start_lock");
00028 }
00029
00030 CommonRender::~CommonRender()
00031 {
00032 delete_vconsole();
00033 if(modules)
00034 {
00035 for(int i = 0; i < total_modules; i++)
00036 delete modules[i];
00037 delete [] modules;
00038 }
00039 delete start_lock;
00040 }
00041
00042 void CommonRender::reset_parameters()
00043 {
00044 total_modules = 0;
00045 modules = 0;
00046 vconsole = 0;
00047 done = 0;
00048 interrupt = 0;
00049 last_playback = 0;
00050 asynchronous = 0;
00051 restart_plugins = 0;
00052 }
00053
00054 void CommonRender::arm_command()
00055 {
00056 int64_t temp_length = 1;
00057
00058 current_position = tounits(renderengine->command->playbackstart, 0);
00059
00060 init_output_buffers();
00061
00062 last_playback = 0;
00063 if(test_reconfigure(current_position, temp_length))
00064 {
00065 restart_playback();
00066 }
00067 else
00068 {
00069 vconsole->start_playback();
00070 }
00071
00072 done = 0;
00073 interrupt = 0;
00074 last_playback = 0;
00075 restart_plugins = 0;
00076 }
00077
00078
00079
00080 void CommonRender::create_modules()
00081 {
00082
00083 Track *current = renderengine->edl->tracks->first;
00084 int module = 0;
00085
00086 if(!modules)
00087 {
00088 total_modules = get_total_tracks();
00089 modules = new Module*[total_modules];
00090
00091 for(module = 0; module < total_modules && current; current = NEXT)
00092 {
00093 if(current->data_type == data_type)
00094 {
00095 modules[module] = new_module(current);
00096 modules[module]->create_objects();
00097 module++;
00098 }
00099 }
00100 }
00101 else
00102
00103 {
00104 for(module = 0; module < total_modules; module++)
00105 {
00106 modules[module]->create_objects();
00107 }
00108 }
00109 }
00110
00111 void CommonRender::start_plugins()
00112 {
00113
00114 if(restart_plugins)
00115 {
00116 for(int i = 0; i < total_modules; i++)
00117 {
00118 modules[i]->render_init();
00119 }
00120 }
00121 }
00122
00123 int CommonRender::test_reconfigure(int64_t position, int64_t &length)
00124 {
00125 if(!vconsole) return 1;
00126 if(!modules) return 1;
00127
00128 return vconsole->test_reconfigure(position, length, last_playback);
00129 }
00130
00131
00132 void CommonRender::build_virtual_console()
00133 {
00134
00135 if(!vconsole)
00136 {
00137 vconsole = new_vconsole_object();
00138 }
00139
00140
00141 vconsole->create_objects();
00142 }
00143
00144 void CommonRender::start_command()
00145 {
00146 if(renderengine->command->realtime)
00147 {
00148 Thread::set_realtime(renderengine->edl->session->real_time_playback &&
00149 data_type == TRACK_AUDIO);
00150 Thread::start();
00151 start_lock->lock("CommonRender::start_command");
00152 }
00153 }
00154
00155 int CommonRender::restart_playback()
00156 {
00157 delete_vconsole();
00158 create_modules();
00159 build_virtual_console();
00160 start_plugins();
00161
00162 done = 0;
00163 interrupt = 0;
00164 last_playback = 0;
00165 restart_plugins = 0;
00166 return 0;
00167 }
00168
00169 void CommonRender::delete_vconsole()
00170 {
00171 if(vconsole) delete vconsole;
00172 vconsole = 0;
00173 }
00174
00175 int CommonRender::get_boundaries(int64_t ¤t_render_length)
00176 {
00177 int64_t loop_end = tounits(renderengine->edl->local_session->loop_end, 1);
00178 int64_t loop_start = tounits(renderengine->edl->local_session->loop_start, 0);
00179 int64_t start_position = tounits(renderengine->command->start_position, 0);
00180 int64_t end_position = tounits(renderengine->command->end_position, 1);
00181
00182
00183
00184 if(renderengine->command->single_frame() ||
00185 (!renderengine->edl->local_session->loop_playback &&
00186 !renderengine->command->infinite))
00187 {
00188 if(renderengine->command->get_direction() == PLAY_FORWARD)
00189 {
00190 if(current_position + current_render_length >= end_position)
00191 {
00192 last_playback = 1;
00193 current_render_length = end_position - current_position;
00194 }
00195 }
00196
00197 else
00198 {
00199 if(current_position - current_render_length <= start_position)
00200 {
00201 last_playback = 1;
00202 current_render_length = current_position - start_position;
00203 }
00204 }
00205 }
00206
00207
00208 if(!renderengine->command->single_frame() &&
00209 renderengine->edl->local_session->loop_playback &&
00210 !renderengine->command->infinite)
00211 {
00212 if(renderengine->command->get_direction() == PLAY_FORWARD)
00213 {
00214 int64_t segment_end = current_position + current_render_length;
00215 if(segment_end > loop_end)
00216 {
00217 current_render_length = loop_end - current_position;
00218 }
00219 }
00220 else
00221 {
00222 int64_t segment_end = current_position - current_render_length;
00223 if(segment_end < loop_start)
00224 {
00225 current_render_length = current_position - loop_start;
00226 }
00227 }
00228 }
00229
00230 if(renderengine->command->single_frame())
00231 current_render_length = 1;
00232
00233 if(current_render_length < 0) current_render_length = 0;
00234 return 0;
00235 }
00236
00237 void CommonRender::run()
00238 {
00239 start_lock->unlock();
00240 }
00241
00242
00243
00244
00245
00246
00247
00248
00249
00250
00251
00252
00253
00254
00255
00256
00257
00258
00259
00260
00261
00262 CommonRender::CommonRender(MWindow *mwindow, RenderEngine *renderengine)
00263 : Thread()
00264 {
00265 this->mwindow = mwindow;
00266 this->renderengine = renderengine;
00267 current_position = 0;
00268 interrupt = 0;
00269 done = 0;
00270 last_playback = 0;
00271 vconsole = 0;
00272 asynchronous = 1;
00273 }
00274
00275
00276 int CommonRender::wait_for_completion()
00277 {
00278 join();
00279 }
00280
00281
00282
00283
00284
00285 int CommonRender::advance_position(int64_t current_render_length)
00286 {
00287 int64_t loop_end = tounits(renderengine->edl->local_session->loop_end, 1);
00288 int64_t loop_start = tounits(renderengine->edl->local_session->loop_start, 0);
00289
00290
00291 if(renderengine->command->get_direction() == PLAY_REVERSE)
00292 current_position -= current_render_length;
00293 else
00294 current_position += current_render_length;
00295
00296
00297 if(renderengine->edl->local_session->loop_playback &&
00298 !renderengine->command->infinite)
00299 {
00300 if(renderengine->command->get_direction() == PLAY_REVERSE)
00301 {
00302 if(current_position <= loop_start)
00303 current_position = loop_end;
00304 }
00305 else
00306 {
00307 if(current_position >= loop_end)
00308 current_position = loop_start + (current_position - loop_end);
00309 }
00310 }
00311 return 0;
00312 }
00313
00314 int64_t CommonRender::tounits(double position, int round)
00315 {
00316 return (int64_t)position;
00317 }
00318
00319 double CommonRender::fromunits(int64_t position)
00320 {
00321 return (double)position;
00322 }