Home | History | Annotate | Download | only in layout
      1 /*
      2  **********************************************************************
      3  *   Copyright (C) 1998-2008, International Business Machines
      4  *   Corporation and others.  All Rights Reserved.
      5  **********************************************************************
      6  */
      7 
      8 #include "LETypes.h"
      9 #include "LEInsertionList.h"
     10 
     11 U_NAMESPACE_BEGIN
     12 
     13 #define ANY_NUMBER 1
     14 
     15 struct InsertionRecord
     16 {
     17     InsertionRecord *next;
     18     le_int32 position;
     19     le_int32 count;
     20     LEGlyphID glyphs[ANY_NUMBER];
     21 };
     22 
     23 UOBJECT_DEFINE_RTTI_IMPLEMENTATION(LEInsertionList)
     24 
     25 LEInsertionList::LEInsertionList(le_bool rightToLeft)
     26 : head(NULL), tail(NULL), growAmount(0), append(rightToLeft)
     27 {
     28     tail = (InsertionRecord *) &head;
     29 }
     30 
     31 LEInsertionList::~LEInsertionList()
     32 {
     33     reset();
     34 }
     35 
     36 void LEInsertionList::reset()
     37 {
     38     while (head != NULL) {
     39         InsertionRecord *record = head;
     40 
     41         head = head->next;
     42         LE_DELETE_ARRAY(record);
     43     }
     44 
     45     tail = (InsertionRecord *) &head;
     46     growAmount = 0;
     47 }
     48 
     49 le_int32 LEInsertionList::getGrowAmount()
     50 {
     51     return growAmount;
     52 }
     53 
     54 LEGlyphID *LEInsertionList::insert(le_int32 position, le_int32 count, LEErrorCode &success)
     55 {
     56     if (LE_FAILURE(success)) {
     57         return 0;
     58     }
     59 
     60     InsertionRecord *insertion = (InsertionRecord *) LE_NEW_ARRAY(char, sizeof(InsertionRecord) + (count - ANY_NUMBER) * sizeof (LEGlyphID));
     61     if (insertion == NULL) {
     62         success = LE_MEMORY_ALLOCATION_ERROR;
     63         return 0;
     64     }
     65 
     66     insertion->position = position;
     67     insertion->count = count;
     68 
     69     growAmount += count - 1;
     70 
     71     if (append) {
     72         // insert on end of list...
     73         insertion->next = NULL;
     74         tail->next = insertion;
     75         tail = insertion;
     76     } else {
     77         // insert on front of list...
     78         insertion->next = head;
     79         head = insertion;
     80     }
     81 
     82     return insertion->glyphs;
     83 }
     84 
     85 le_bool LEInsertionList::applyInsertions(LEInsertionCallback *callback)
     86 {
     87     for (InsertionRecord *rec = head; rec != NULL; rec = rec->next) {
     88         if (callback->applyInsertion(rec->position, rec->count, rec->glyphs)) {
     89             return TRUE;
     90         }
     91     }
     92 
     93     return FALSE;
     94 }
     95 
     96 U_NAMESPACE_END
     97