home *** CD-ROM | disk | FTP | other *** search
/ PSION CD 2 / PsionCDVol2.iso / Programs / 720 / PDF090B4-SorceCode / pdf / FontEncoding.cpp < prev    next >
Encoding:
C/C++ Source or Header  |  2000-09-30  |  4.0 KB  |  168 lines

  1. //========================================================================
  2. //
  3. // FontEncoding.cc
  4. //
  5. // Copyright 1999 Derek B. Noonburg
  6. //
  7. //========================================================================
  8. //
  9. // Ported to EPOC by Sander van der Wal
  10. //
  11. // $Log: FontEncoding.cpp $
  12. // Revision 1.3  2000-09-20 20:48:58+02  svdwal
  13. // bugfix from xpdf 0.91
  14. //
  15. // Revision 1.2  2000-09-17 13:38:24+02  svdwal
  16. // Ported
  17. //
  18.  
  19. #ifdef __GNUC__
  20. #pragma implementation
  21. #endif
  22.  
  23. #ifdef __SYMBIAN32__
  24. #include <e32def.h> // remove warning about NULL redefinition
  25. #endif
  26.  
  27. // --0 C Library
  28. #include <string.h>
  29.  
  30. // --o GooLib
  31. #include "gmem.h"
  32. #include "FontEncoding.h"
  33.  
  34.  
  35. //------------------------------------------------------------------------
  36. // FontEncoding
  37. //------------------------------------------------------------------------
  38.  
  39. inline int FontEncoding::hash(const char *name) const {
  40.   register Guint h = (Guint)name[0] & 0xff;
  41.   if (h && name[1])
  42.     h = h * 61 + ((Guint)name[1] & 0xff);
  43.   return (int)(h % (Guint)fontEncHashSize);
  44. }
  45.  
  46.  
  47. void FontEncoding::ConstructL()
  48. {
  49.   register int i;
  50.  
  51.   freeEnc = gTrue;
  52.   encoding = (const char **)User::AllocL(256 * sizeof(char *));
  53.   size = 256;
  54.   for (i = 0; i < 256; ++i)
  55.     encoding[i] = 0;
  56.   for (i = 0; i < fontEncHashSize; ++i)
  57.     hashTab[i] = -1;
  58. }
  59.  
  60.  
  61. void FontEncoding::Construct(const char* const encoding[], int size) {
  62.   register int i;
  63.  
  64.   freeEnc = gFalse;
  65.   this->encoding = (const char**) encoding;
  66.   this->size = size;
  67.   for (i = 0; i < fontEncHashSize; ++i)
  68.     hashTab[i] = -1;
  69.   for (i = 0; i < size; ++i) {
  70.     if (encoding[i])
  71.       addChar1(i, encoding[i]);
  72.   }
  73. }
  74.  
  75.  
  76. void FontEncoding::ConstructL(FontEncoding *fontEnc)
  77. {
  78.   freeEnc = gTrue;
  79.   encoding = (const char **)User::AllocL(fontEnc->size * sizeof(char *));
  80.   // zeroed so cleanup in destructor works
  81.   size = 0;
  82.   for (register int i = 0; i < fontEnc->size; ++i) {
  83.     encoding[i] = fontEnc->encoding[i] ? copyStringL(fontEnc->encoding[i]) : NULL;
  84.     size++;
  85.   }
  86.   Mem::Copy(hashTab, fontEnc->hashTab, fontEncHashSize * sizeof(short));
  87. }
  88.  
  89. FontEncoding *FontEncoding::copyL()
  90.   FontEncoding* self = new(ELeave) FontEncoding();
  91.   CleanupStack::PushL(self);
  92.   self->ConstructL(this);
  93.   CleanupStack::Pop(); // self
  94.   return self;
  95. }
  96.  
  97. void FontEncoding::addChar(register int code, const char *name) {
  98.  
  99.   // replace character associated with code
  100.   if (encoding[code]) {
  101.     register int h = hash(encoding[code]);
  102.     for (register int i = 0; i < fontEncHashSize; ++i) {
  103.       if (hashTab[h] == code) {
  104.         hashTab[h] = -2;
  105.         break;
  106.       }
  107.       if (++h == fontEncHashSize)
  108.         h = 0;
  109.     }
  110.     User::Free((void*)encoding[code]);
  111.     encoding[code] = 0;
  112.   }
  113.  
  114.   // associate name with code
  115.   encoding[code] = name;
  116.  
  117.   // insert name in hash table
  118.   addChar1(code, name);
  119. }
  120.  
  121. void FontEncoding::addChar1(register int code, const char *name) {
  122.  
  123.   // insert name in hash table
  124.   register int h = hash(name); 
  125.   for (register int i = 0; i < fontEncHashSize; ++i) {
  126.     register int code2 = hashTab[h];
  127.     if (code2 < 0) {
  128.       hashTab[h] = code;
  129.       break;
  130.     } 
  131.     else if (encoding[code2] && !strcmp(encoding[code2], name)) {
  132.       // keep the highest code for each char -- this is needed because
  133.       // X won't display chars with codes < 32
  134.       if (code > code2)
  135.         hashTab[h] = code;
  136.       break;
  137.     }
  138.     if (++h == fontEncHashSize)
  139.       h = 0;
  140.   }
  141. }
  142.  
  143. FontEncoding::~FontEncoding() {
  144.  
  145.   if (freeEnc) {
  146.     if (encoding) {
  147.       for (register int i = 0; i < size; ++i)
  148.         User::Free((void*)encoding[i]);
  149.     }
  150.     User::Free(encoding);
  151.   }
  152. }
  153.  
  154. int FontEncoding::getCharCode(const char *name) const {
  155.  
  156.   register int h = hash(name);
  157.   for (register int i = 0; i < fontEncHashSize; ++i) {
  158.     register int code = hashTab[h];
  159.     if (code == -1 ||
  160.         (code >= 0 && encoding[code] && !strcmp(encoding[code], name)))
  161.       return code;
  162.     if (++h >= fontEncHashSize)
  163.       h = 0;
  164.   }
  165.   return -1;
  166. }
  167.