Main Page | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Class Members | File Members

labels.C

Go to the documentation of this file.
00001 #include "clip.h"
00002 #include "edl.h"
00003 #include "edlsession.h"
00004 #include "filexml.h"
00005 #include "labels.h"
00006 #include "mwindow.h"
00007 #include "mwindowgui.h"
00008 #include "patchbay.h"
00009 #include "recordlabel.h"
00010 #include "mainsession.h"
00011 #include "stringfile.h"
00012 #include "theme.h"
00013 #include "timebar.h"
00014 #include <string.h>
00015 
00016 
00017 
00018 Labels::Labels(EDL *edl, char *xml_tag)
00019  : List<Label>()
00020 {
00021         this->edl = edl;
00022         this->xml_tag = xml_tag;
00023 }
00024 
00025 Labels::~Labels()
00026 {
00027         delete_all();
00028 }
00029 
00030 void Labels::dump()
00031 {
00032         for(Label *current = first; current; current = NEXT)
00033         {
00034                 printf("  label: %f\n", current->position);
00035         }
00036 }
00037 
00038 void Labels::insert_labels(Labels *labels, double start, double length, int paste_silence)
00039 {
00040         Label *new_label;
00041         Label *old_label;
00042 
00043 
00044 //printf("Labels::insert_labels 1 %f\n", start);
00045 
00046 // Insert silence in old labels
00047         if(paste_silence)
00048         {
00049                 for(old_label = first; old_label; old_label = old_label->next)
00050                 {
00051                         if(old_label->position > start ||
00052                                 edl->equivalent(old_label->position, start))
00053                                 old_label->position += length;
00054                 }
00055         }
00056 
00057 
00058 // Insert one new label at a time
00059         for(new_label = labels->first; new_label; new_label = new_label->next)
00060         {
00061                 int exists = 0;
00062 //printf("Labels::insert_labels 2 %f\n", new_label->position + start);
00063 
00064 // Check every old label for existence
00065                 for(old_label = first; old_label; old_label = old_label->next)
00066                 {
00067                         if(edl->equivalent(old_label->position, new_label->position + start))
00068                         {
00069                                 exists = 1;
00070                                 break;
00071                         }
00072                         else
00073                         if(old_label->position > new_label->position + start)
00074                                 break;
00075                 }
00076 
00077                 if(!exists)
00078                 {
00079                         if(old_label)
00080                                 insert_before(old_label, new Label(edl, this, new_label->position + start));
00081                         else
00082                                 append(new Label(edl, this, new_label->position + start));
00083                 }
00084         }
00085 }
00086 
00087 int Labels::toggle_label(double start, double end)
00088 {
00089         Label *current;
00090 //printf("Labels::toggle_label 1 %f %f\n", start, end);
00091 
00092 // handle selection start
00093 // find label the selectionstart is after
00094         for(current = first; 
00095                 current && current->position < start && !edl->equivalent(current->position, start); 
00096                 current = NEXT)
00097         {
00098 //printf("Labels::toggle_label 2 %f %f %f\n", start, end, current->position);
00099                 ;
00100         }
00101 
00102         if(current)
00103         {
00104 //printf("Labels::toggle_label 3 %f %f %f\n", start, end, current->position);
00105                 if(edl->equivalent(current->position, start))
00106                 {        // remove it
00107 //printf("Labels::toggle_label 1\n");
00108                         remove(current);
00109                 }
00110                 else
00111                 {        // insert before it
00112                         current = insert_before(current, new Label(edl, this, start));
00113                 }
00114         }
00115         else
00116         {           // insert after last
00117 //printf("Labels::toggle_label 1\n");
00118                 current = append(new Label(edl, this, start));
00119         }
00120 
00121 // handle selection end
00122         if(!EQUIV(start, end))
00123         {
00124 //printf("Labels::toggle_label 2 %.16e %.16e\n", start, end);
00125 // find label the selectionend is after
00126                 for(current = first; 
00127                         current && current->position < end && !edl->equivalent(current->position, end); 
00128                         current = NEXT)
00129                 {
00130                         ;
00131                 }
00132 
00133                 if(current)
00134                 {
00135                         if(edl->equivalent(current->position, end))
00136                         {
00137                                 remove(current);
00138                         }
00139                         else
00140                         {
00141                                 current = insert_before(current, new Label(edl, this, end));
00142                         }
00143                 }
00144                 else
00145                 {
00146                         current = append(new Label(edl, this, end));
00147                 }
00148         }
00149         return 0;
00150 }
00151 
00152 int Labels::delete_all()
00153 {
00154         while(last)
00155                 remove(last);
00156         return 0;
00157 }
00158 
00159 int Labels::copy(double start, double end, FileXML *xml)
00160 {
00161         char string[BCTEXTLEN];
00162         xml->tag.set_title(xml_tag);
00163         xml->append_tag();
00164         xml->append_newline();
00165 
00166         Label *current;
00167         sprintf(string, xml_tag);
00168         string[strlen(string) - 1] = 0;
00169         for(current = label_of(start); 
00170                 current && current->position <= end; 
00171                 current = NEXT)
00172         {
00173                 xml->tag.set_title(string);
00174                 xml->tag.set_property("SAMPLE", (double)current->position - start);
00175 //printf("Labels::copy %f\n", current->position - start);
00176                 xml->append_tag();
00177         }
00178         
00179         sprintf(string, "/%s", xml_tag);
00180         xml->tag.set_title(string);
00181         xml->append_tag();
00182         xml->append_newline();
00183         xml->append_newline();
00184         return 0;
00185 }
00186 
00187 int Labels::copy_length(long start, long end) // return number of Labels in selection
00188 {
00189         int result = 0;
00190         Label *current;
00191         
00192         for(current = label_of(start); current && current->position <= end; current = NEXT)
00193         {
00194                 result++;
00195         }
00196         return result;
00197 }
00198 
00199 void Labels::copy_from(Labels *labels)
00200 {
00201         while(last) delete last;
00202 
00203         for(Label *current = labels->first; current; current = NEXT)
00204         {
00205                 append(new Label(edl, this, current->position));
00206         }
00207 }
00208 
00209 
00210 Labels& Labels::operator=(Labels &that)
00211 {
00212         copy_from(&that);
00213 printf("Labels::operator= 1\n");
00214         return *this;
00215 }
00216 
00217 
00218 int Labels::save(FileXML *xml)
00219 {
00220         xml->tag.set_title("LABELS");
00221         xml->append_tag();
00222         xml->append_newline();
00223 
00224         Label *current;
00225 
00226         for(current = first; current; current = NEXT)
00227         {
00228                 xml->tag.set_title("LABEL");
00229                 xml->tag.set_property("SAMPLE", (double)current->position);
00230                 xml->append_tag();
00231         }
00232         
00233         xml->append_newline();
00234         xml->tag.set_title("/LABELS");
00235         xml->append_tag();
00236         xml->append_newline();
00237         xml->append_newline();
00238         return 0;
00239 }
00240 
00241 int Labels::load(FileXML *xml, uint32_t load_flags)
00242 {
00243         int result = 0;
00244         char string1[BCTEXTLEN], string2[BCTEXTLEN];
00245 
00246         sprintf(string1, "/%s", xml_tag);
00247         strcpy(string2, xml_tag);
00248         string2[strlen(string2) - 1] = 0;
00249 
00250         do{
00251                 result = xml->read_tag();
00252                 if(!result)
00253                 {
00254                         if(xml->tag.title_is(string1))
00255                         {
00256                                 result = 1;
00257                         }
00258                         else
00259                         if(xml->tag.title_is(string2))
00260                         {
00261                                 double position = xml->tag.get_property("SAMPLE", (double)-1);
00262 //printf("Labels::load %f\n", position);
00263                                 if(position > -1)
00264                                 {
00265                                         Label *current = label_of(position);
00266                                         current = insert_before(current, new Label(edl, this, position));
00267                                 }
00268                         }
00269                         else
00270                         if(xml->tag.title_is("INPOINT"))
00271                         {
00272                                 double position = xml->tag.get_property("SAMPLE", (double)-1);
00273                                 if(position > -1)
00274                                 {
00275                                         ;
00276                                 }
00277                         }
00278                         else
00279                         if(xml->tag.title_is("OUTPOINT"))
00280                         {
00281                                 double position = xml->tag.get_property("SAMPLE", (double)-1);
00282                                 if(position > -1)
00283                                 {
00284                                         ;
00285                                 }
00286                         }
00287                 }
00288         }while(!result);
00289         return 0;
00290 }
00291 
00292 
00293 
00294 int Labels::clear(double start, double end, int follow)
00295 {
00296         Label *current;
00297         Label *next;
00298 
00299 //printf("Labels::clear 1\n");
00300         current = label_of(start);
00301 //printf("Labels::clear 2\n");
00302 // remove selected labels
00303         while(current && current->position < end)
00304         {
00305                 next = NEXT;
00306                 delete current;              
00307                 current = next;
00308         }
00309 // Shift later labels
00310 //printf("Labels::clear 3\n");
00311         if(follow)
00312         {
00313                 while(current)
00314                 {
00315                         current->position -= end - start;   // shift labels forward
00316                         current = NEXT;
00317                 }
00318 //printf("Labels::clear 4\n");
00319                 optimize();
00320 //printf("Labels::clear 5\n");
00321         }
00322 
00323         return 0;
00324 }
00325 
00326 
00327 Label* Labels::prev_label(double position)
00328 {
00329         Label *current;
00330 
00331 // Test for label under cursor position
00332         for(current = first; 
00333                 current && !edl->equivalent(current->position, position); 
00334                 current = NEXT)
00335                 ;
00336 
00337 // Test for label after cursor position
00338         if(!current)
00339                 for(current = first;
00340                         current && current->position < position;
00341                         current = NEXT)
00342                         ;
00343 
00344 // Test for label before cursor position
00345         if(!current) 
00346                 current = last;
00347         else
00348 // Get previous label
00349                 current = PREVIOUS;
00350 
00351         return current;
00352 }
00353 
00354 Label* Labels::next_label(double position)
00355 {
00356         Label *current;
00357 
00358 // Test for label under cursor position
00359         for(current = first; 
00360                 current && !edl->equivalent(current->position, position); 
00361                 current = NEXT)
00362                 ;
00363 
00364 // Test for label before cursor position
00365         if(!current)
00366                 for(current = last;
00367                         current && current->position > position;
00368                         current = PREVIOUS)
00369                         ;
00370 
00371 // Test for label after cursor position
00372         if(!current)
00373                 current = first;
00374         else
00375 // Get next label
00376                 current = NEXT;
00377 
00378         return current;
00379 }
00380 
00381 int Labels::insert(double start, double length)
00382 {      // shift every label including the first one back
00383         Label *current;
00384 
00385         for(current = label_of(start); current; current = NEXT)
00386         {
00387                 current->position += length;
00388         }
00389         return 0;
00390 }
00391 
00392 int Labels::paste_silence(double start, double end)
00393 {
00394         insert(start, end - start);
00395         optimize();
00396         return 0;
00397 }
00398 
00399 int Labels::modify_handles(double oldposition, 
00400         double newposition, 
00401         int currentend, 
00402         int handle_mode,
00403         int edit_labels)
00404 {
00405         if(edit_labels &&
00406                 handle_mode == MOVE_ALL_EDITS)
00407         {
00408                 if(currentend == 0)          // left handle
00409                 {
00410                         if(newposition < oldposition)
00411                         {
00412                                 insert(oldposition, oldposition - newposition);    // shift all labels right
00413                         }
00414                         else
00415                         {
00416                                 clear(oldposition, newposition);   // clear selection
00417                         }
00418                 }
00419                 else
00420                 {                            // right handle
00421                         if(newposition < oldposition)
00422                         {
00423                                 clear(newposition, oldposition);
00424                         }
00425                         else
00426                         {
00427                                 insert(oldposition, newposition - oldposition);
00428                         }
00429                 }
00430         }
00431         return 0;
00432 }
00433 
00434 int Labels::optimize()
00435 {
00436         int result = 1;
00437         Label *current;
00438 
00439         while(result)
00440         {
00441                 result = 0;
00442                 
00443                 for(current = first; current && NEXT && !result;)
00444                 {
00445                         Label *next = NEXT;
00446                         if(current->position == next->position)
00447                         {
00448                                 delete current;
00449                                 result  = 1;
00450                         }
00451                         current = next;
00452                 }
00453         }
00454         return 0;
00455 }
00456 
00457 Label* Labels::label_of(double position)
00458 {
00459         Label *current;
00460 
00461         for(current = first; current; current = NEXT)
00462         {
00463                 if(current->position >= position) return current;
00464         }
00465         return 0;
00466 }
00467 
00468 
00469 
00470 
00471 
00472 
00473 
00474 
00475 
00476 
00477 Label::Label()
00478  : ListItem<Label>()
00479 {
00480 }
00481 
00482 Label::Label(EDL *edl, Labels *labels, double position)
00483  : ListItem<Label>()
00484 {
00485         this->edl = edl;
00486         this->labels = labels;
00487         this->position = position;
00488 }
00489 
00490 
00491 Label::~Label()
00492 {
00493 //      if(toggle) delete toggle;
00494 }
00495 
00496 LabelToggle::LabelToggle(MWindow *mwindow, 
00497         Label *label, 
00498         int x, 
00499         int y, 
00500         long position)
00501  : BC_Label(x, y, 0)
00502 {
00503         this->mwindow = mwindow;
00504         this->label = label;
00505 }
00506 
00507 LabelToggle::~LabelToggle() { }
00508 
00509 int LabelToggle::handle_event()
00510 {
00511         return 0;
00512 }
00513 

Generated on Sun Jan 8 13:38:56 2006 for Cinelerra-svn by  doxygen 1.4.4