fmt_text.c 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167
  1. /*
  2. * fmt_text.c
  3. * Copyright (C) 2004 A.J. van Os; Released under GNU GPL
  4. *
  5. * Description:
  6. * Functions to deal with the Formatted Text format
  7. *
  8. * Based on patches send by: Ofir Reichenberg <ofir@qlusters.com>
  9. *
  10. * The credit should go to him, but all the bugs are mine.
  11. */
  12. #include <string.h>
  13. #include "antiword.h"
  14. /* The character set */
  15. static encoding_type eEncoding = encoding_neutral;
  16. /* Current vertical position information */
  17. static long lYtopCurr = 0;
  18. /* Local representation of the non-breaking space */
  19. static UCHAR ucNbsp = 0;
  20. /*
  21. * vPrologueFMT - set options and perform the Formatted Text initialization
  22. */
  23. void
  24. vPrologueFMT(diagram_type *pDiag, const options_type *pOptions)
  25. {
  26. fail(pDiag == NULL);
  27. fail(pOptions == NULL);
  28. eEncoding = pOptions->eEncoding;
  29. pDiag->lXleft = 0;
  30. pDiag->lYtop = 0;
  31. lYtopCurr = 0;
  32. } /* end of vPrologueFMT */
  33. /*
  34. * vPrintFMT - print a Formatted Text string
  35. */
  36. static void
  37. vPrintFMT(FILE *pFile,
  38. const char *szString, size_t tStringLength, USHORT usFontstyle)
  39. {
  40. const UCHAR *pucByte, *pucStart, *pucLast, *pucNonSpace;
  41. fail(szString == NULL);
  42. if (szString == NULL || szString[0] == '\0' || tStringLength == 0) {
  43. return;
  44. }
  45. if (eEncoding == encoding_utf_8) {
  46. fprintf(pFile, "%.*s", (int)tStringLength, szString);
  47. return;
  48. }
  49. if (ucNbsp == 0) {
  50. ucNbsp = ucGetNbspCharacter();
  51. DBG_HEX_C(ucNbsp != 0xa0, ucNbsp);
  52. }
  53. pucStart = (UCHAR *)szString;
  54. pucLast = pucStart + tStringLength - 1;
  55. pucNonSpace = pucLast;
  56. while ((*pucNonSpace == (UCHAR)' ' || *pucNonSpace == ucNbsp) &&
  57. pucNonSpace > pucStart) {
  58. pucNonSpace--;
  59. }
  60. /* 1: The spaces at the start */
  61. pucByte = pucStart;
  62. while ((*pucByte == (UCHAR)' ' || *pucByte == ucNbsp) &&
  63. pucByte <= pucLast) {
  64. (void)putc(' ', pFile);
  65. pucByte++;
  66. }
  67. if (pucByte > pucLast) {
  68. /* There is no text, just spaces */
  69. return;
  70. }
  71. /* 2: Start the *bold*, /italic/ and _underline_ */
  72. if (bIsBold(usFontstyle)) {
  73. (void)putc('*', pFile);
  74. }
  75. if (bIsItalic(usFontstyle)) {
  76. (void)putc('/', pFile);
  77. }
  78. if (bIsUnderline(usFontstyle)) {
  79. (void)putc('_', pFile);
  80. }
  81. /* 3: The text itself */
  82. while (pucByte <= pucNonSpace) {
  83. if (*pucByte == ucNbsp) {
  84. (void)putc(' ', pFile);
  85. } else {
  86. (void)putc((char)*pucByte, pFile);
  87. }
  88. pucByte++;
  89. }
  90. /* 4: End the *bold*, /italic/ and _underline_ */
  91. if (bIsUnderline(usFontstyle)) {
  92. (void)putc('_', pFile);
  93. }
  94. if (bIsItalic(usFontstyle)) {
  95. (void)putc('/', pFile);
  96. }
  97. if (bIsBold(usFontstyle)) {
  98. (void)putc('*', pFile);
  99. }
  100. /* 5: The spaces at the end */
  101. while (pucByte <= pucLast) {
  102. (void)putc(' ', pFile);
  103. pucByte++;
  104. }
  105. } /* end of vPrintFMT */
  106. /*
  107. * vMoveTo - move to the given X,Y coordinates
  108. *
  109. * Move the current position of the given diagram to its X,Y coordinates,
  110. * start on a new page if needed
  111. */
  112. static void
  113. vMoveTo(diagram_type *pDiag)
  114. {
  115. int iCount, iNbr;
  116. fail(pDiag == NULL);
  117. fail(pDiag->pOutFile == NULL);
  118. if (pDiag->lYtop != lYtopCurr) {
  119. iNbr = iDrawUnits2Char(pDiag->lXleft);
  120. for (iCount = 0; iCount < iNbr; iCount++) {
  121. (void)putc(FILLER_CHAR, pDiag->pOutFile);
  122. }
  123. lYtopCurr = pDiag->lYtop;
  124. }
  125. } /* end of vMoveTo */
  126. /*
  127. * vSubstringFMT - print a sub string
  128. */
  129. void
  130. vSubstringFMT(diagram_type *pDiag,
  131. const char *szString, size_t tStringLength, long lStringWidth,
  132. USHORT usFontstyle)
  133. {
  134. fail(pDiag == NULL || szString == NULL);
  135. fail(pDiag->pOutFile == NULL);
  136. fail(pDiag->lXleft < 0);
  137. fail(tStringLength != strlen(szString));
  138. if (szString[0] == '\0' || tStringLength == 0) {
  139. return;
  140. }
  141. vMoveTo(pDiag);
  142. vPrintFMT(pDiag->pOutFile, szString, tStringLength, usFontstyle);
  143. pDiag->lXleft += lStringWidth;
  144. } /* end of vSubstringFMT */