1 50 51 package com.lowagie.text.rtf; 52 53 import java.awt.Color ; 54 import java.io.ByteArrayInputStream ; 55 import java.io.ByteArrayOutputStream ; 56 import java.io.IOException ; 57 import java.io.InputStream ; 58 import java.io.OutputStream ; 59 import java.text.ParsePosition ; 60 import java.text.SimpleDateFormat ; 61 import java.util.ArrayList ; 62 import java.util.Calendar ; 63 import java.util.Date ; 64 import java.util.Iterator ; 65 import java.util.ListIterator ; 66 67 import com.lowagie.text.Anchor; 68 import com.lowagie.text.Annotation; 69 import com.lowagie.text.Chunk; 70 import com.lowagie.text.DocWriter; 71 import com.lowagie.text.Document; 72 import com.lowagie.text.DocumentException; 73 import com.lowagie.text.Element; 74 import com.lowagie.text.ExceptionConverter; 75 import com.lowagie.text.Font; 76 import com.lowagie.text.HeaderFooter; 77 import com.lowagie.text.Image; 78 import com.lowagie.text.ListItem; 79 import com.lowagie.text.Meta; 80 import com.lowagie.text.PageSize; 81 import com.lowagie.text.Paragraph; 82 import com.lowagie.text.Phrase; 83 import com.lowagie.text.Rectangle; 84 import com.lowagie.text.Section; 85 import com.lowagie.text.SimpleTable; 86 import com.lowagie.text.Table; 87 import com.lowagie.text.pdf.codec.wmf.MetaDo; 88 89 141 public class RtfWriter extends DocWriter { 142 145 146 149 150 151 public static final byte escape = (byte) '\\'; 152 153 154 private static final byte[] extendedEscape = "\\*\\".getBytes(); 155 156 157 protected static final byte delimiter = (byte) ' '; 158 159 160 private static final byte commaDelimiter = (byte) ';'; 161 162 163 public static final byte openGroup = (byte) '{'; 164 165 166 public static final byte closeGroup = (byte) '}'; 167 168 171 172 173 private static final byte[] docBegin = "rtf1".getBytes(); 174 175 176 private static final byte[] ansi = "ansi".getBytes(); 177 178 179 private static final byte[] ansiCodepage = "ansicpg".getBytes(); 180 181 184 185 186 private static final byte[] fontTable = "fonttbl".getBytes(); 187 188 189 protected static final byte fontNumber = (byte) 'f'; 190 191 192 protected static final byte[] fontSize = "fs".getBytes(); 193 194 195 protected static final byte[] fontColor = "cf".getBytes(); 196 197 198 private static final byte[] fontModern = "fmodern".getBytes(); 199 200 201 private static final byte[] fontSwiss = "fswiss".getBytes(); 202 203 204 private static final byte[] fontRoman = "froman".getBytes(); 205 206 207 private static final byte[] fontTech = "ftech".getBytes(); 208 209 210 private static final byte[] fontCharset = "fcharset".getBytes(); 211 212 213 private static final byte[] fontCourier = "Courier".getBytes(); 214 215 216 private static final byte[] fontArial = "Arial".getBytes(); 217 218 219 private static final byte[] fontSymbol = "Symbol".getBytes(); 220 221 222 private static final byte[] fontTimesNewRoman = "Times New Roman".getBytes(); 223 224 225 private static final byte[] fontWindings = "Windings".getBytes(); 226 227 228 private static final byte[] defaultFont = "deff".getBytes(); 229 230 231 private static final byte[] firstIndent = "fi".getBytes(); 232 233 234 private static final byte[] listIndent = "li".getBytes(); 235 236 237 private static final byte[] rightIndent = "ri".getBytes(); 238 239 242 243 244 private static final byte[] sectionDefaults = "sectd".getBytes(); 245 246 247 private static final byte[] section = "sect".getBytes(); 248 249 250 public static final byte[] paragraphDefaults = "pard".getBytes(); 251 252 253 public static final byte[] paragraph = "par".getBytes(); 254 255 256 public static final byte[] sectionPageWidth = "pgwsxn".getBytes(); 257 258 259 public static final byte[] sectionPageHeight = "pghsxn".getBytes(); 260 261 264 265 266 private static final byte[] listtableGroup = "listtable".getBytes(); 267 268 269 private static final byte[] listoverridetableGroup = "listoverridetable".getBytes(); 270 271 272 private static final byte[] listDefinition = "list".getBytes(); 273 274 275 private static final byte[] listTemplateID = "listtemplateid".getBytes(); 276 277 278 private static final byte[] hybridList = "hybrid".getBytes(); 279 280 281 private static final byte[] listLevelDefinition = "listlevel".getBytes(); 282 283 284 private static final byte[] listLevelTypeOld = "levelnfc".getBytes(); 285 286 287 private static final byte[] listLevelTypeNew = "levelnfcn".getBytes(); 288 289 290 private static final byte[] listLevelAlignOld = "leveljc".getBytes(); 291 292 293 private static final byte[] listLevelAlignNew = "leveljcn".getBytes(); 294 295 296 private static final byte[] listLevelStartAt = "levelstartat".getBytes(); 297 298 299 private static final byte[] listLevelTextDefinition = "leveltext".getBytes(); 300 301 302 private static final byte[] listLevelTextLength = "\'0".getBytes(); 303 304 305 private static final byte[] listLevelTextStyleNumbers = "\'00.".getBytes(); 306 307 308 private static final byte[] listLevelTextStyleBullet = "u-3913 ?".getBytes(); 309 310 311 private static final byte[] listLevelNumbersDefinition = "levelnumbers".getBytes(); 312 313 314 private static final byte[] listLevelNumbers = "\\'0".getBytes(); 315 316 317 private static final byte[] tabStop = "tx".getBytes(); 318 319 320 private static final byte[] listBegin = "ls".getBytes(); 321 322 323 private static final byte[] listCurrentLevel = "ilvl".getBytes(); 324 325 326 private static final byte[] listTextOld = "listtext".getBytes(); 327 328 329 private static final byte[] tab = "tab".getBytes(); 330 331 332 private static final byte[] listBulletOld = "\'b7".getBytes(); 333 334 335 private static final byte[] listID = "listid".getBytes(); 336 337 338 private static final byte[] listOverride = "listoverride".getBytes(); 339 340 341 private static final byte[] listOverrideCount = "listoverridecount".getBytes(); 342 343 346 347 348 protected static final byte bold = (byte) 'b'; 349 350 351 protected static final byte italic = (byte) 'i'; 352 353 354 protected static final byte[] underline = "ul".getBytes(); 355 356 357 protected static final byte[] strikethrough = "strike".getBytes(); 358 359 360 public static final byte[] alignLeft = "ql".getBytes(); 361 362 363 public static final byte[] alignCenter = "qc".getBytes(); 364 365 366 public static final byte[] alignRight = "qr".getBytes(); 367 368 369 public static final byte[] alignJustify = "qj".getBytes(); 370 371 374 375 376 private static final byte[] colorTable = "colortbl".getBytes(); 377 378 379 private static final byte[] colorRed = "red".getBytes(); 380 381 382 private static final byte[] colorGreen = "green".getBytes(); 383 384 385 private static final byte[] colorBlue = "blue".getBytes(); 386 387 390 391 392 private static final byte[] infoBegin = "info".getBytes(); 393 394 395 private static final byte[] metaAuthor = "author".getBytes(); 396 397 398 private static final byte[] metaSubject = "subject".getBytes(); 399 400 401 private static final byte[] metaKeywords = "keywords".getBytes(); 402 403 404 private static final byte[] metaTitle = "title".getBytes(); 405 406 407 private static final byte[] metaProducer = "operator".getBytes(); 408 409 410 private static final byte[] metaCreationDate = "creationdate".getBytes(); 411 412 413 private static final byte[] year = "yr".getBytes(); 414 415 416 private static final byte[] month = "mo".getBytes(); 417 418 419 private static final byte[] day = "dy".getBytes(); 420 421 422 private static final byte[] hour = "hr".getBytes(); 423 424 425 private static final byte[] minute = "min".getBytes(); 426 427 428 private static final byte[] second = "sec".getBytes(); 429 430 431 private static final byte[] startSuper = "super".getBytes(); 432 433 434 private static final byte[] startSub = "sub".getBytes(); 435 436 437 private static final byte[] endSuperSub = "nosupersub".getBytes(); 438 439 442 443 444 private static final byte[] titlePage = "titlepg".getBytes(); 445 446 447 private static final byte[] facingPages = "facingp".getBytes(); 448 449 450 private static final byte[] headerBegin = "header".getBytes(); 451 452 453 private static final byte[] footerBegin = "footer".getBytes(); 454 455 private static final byte[] headerlBegin = "headerl".getBytes(); 457 458 private static final byte[] footerlBegin = "footerl".getBytes(); 459 460 private static final byte[] headerrBegin = "headerr".getBytes(); 461 462 private static final byte[] footerrBegin = "footerr".getBytes(); 463 464 private static final byte[] headerfBegin = "headerf".getBytes(); 465 466 private static final byte[] footerfBegin = "footerf".getBytes(); 467 468 471 472 473 private static final byte[] rtfPaperWidth = "paperw".getBytes(); 474 475 476 private static final byte[] rtfPaperHeight = "paperh".getBytes(); 477 478 479 private static final byte[] rtfMarginLeft = "margl".getBytes(); 480 481 482 private static final byte[] rtfMarginRight = "margr".getBytes(); 483 484 485 private static final byte[] rtfMarginTop = "margt".getBytes(); 486 487 488 private static final byte[] rtfMarginBottom = "margb".getBytes(); 489 490 491 private static final byte[] newPage = "page".getBytes(); 492 493 494 private static final byte[] landscapeTag1 = "landscape".getBytes(); 495 496 497 private static final byte[] landscapeTag2 = "lndscpsxn".getBytes(); 498 499 502 503 504 private static final byte[] annotationID = "atnid".getBytes(); 505 506 507 private static final byte[] annotationAuthor = "atnauthor".getBytes(); 508 509 510 private static final byte[] annotation = "annotation".getBytes(); 511 512 515 516 517 private static final byte[] pictureGroup = "shppict".getBytes(); 518 519 520 private static final byte[] picture = "pict".getBytes(); 521 522 523 private static final byte[] picturePNG = "pngblip".getBytes(); 524 525 526 private static final byte[] pictureJPEG = "jpegblip".getBytes(); 527 528 529 private static final byte[] pictureBMP = "dibitmap0".getBytes(); 530 531 532 private static final byte[] pictureWMF = "wmetafile8".getBytes(); 533 534 535 private static final byte[] pictureWidth = "picw".getBytes(); 536 537 538 private static final byte[] pictureHeight = "pich".getBytes(); 539 540 541 private static final byte[] pictureScaleX = "picscalex".getBytes(); 542 543 544 private static final byte[] pictureScaleY = "picscaley".getBytes(); 545 546 549 550 551 protected static final byte[] field = "field".getBytes(); 552 553 554 protected static final byte[] fieldContent = "fldinst".getBytes(); 555 556 557 protected static final byte[] fieldPage = "PAGE".getBytes(); 558 559 560 protected static final byte[] fieldHyperlink = "HYPERLINK".getBytes(); 561 562 563 protected static final byte[] fieldDisplay = "fldrslt".getBytes(); 564 565 566 567 568 572 573 574 private ArrayList fontList = new ArrayList (); 575 576 577 private ArrayList colorList = new ArrayList (); 578 579 580 private ByteArrayOutputStream content = null; 581 582 583 private ByteArrayOutputStream info = null; 584 585 586 private ByteArrayOutputStream listtable = null; 587 588 589 private ByteArrayOutputStream listoverride = null; 590 591 592 private HeaderFooter header = null; 593 594 595 private HeaderFooter footer = null; 596 597 598 private int marginLeft = 1800; 599 600 601 private int marginRight = 1800; 602 603 604 private int marginTop = 1440; 605 606 607 private int marginBottom = 1440; 608 609 610 private int pageWidth = 11906; 611 612 613 private int pageHeight = 16838; 614 615 616 public final static double TWIPSFACTOR = 20; 618 619 private int currentListID = 1; 620 621 622 private ArrayList listIds = null; 623 624 625 private int listLevel = 0; 626 627 628 private int maxListLevel = 0; 629 630 631 private boolean writeTOC = false; 632 633 634 private boolean hasTitlePage = false; 635 636 637 private boolean inHeaderFooter = false; 638 639 640 private boolean inTable = false; 641 642 643 private boolean landscape = false; 644 645 646 647 653 654 protected RtfWriter(Document doc, OutputStream os) { 655 super(doc, os); 656 document.addDocListener(this); 657 initDefaults(); 658 } 659 660 661 662 667 public void setGenerateTOCEntries(boolean writeTOC) { 668 this.writeTOC = writeTOC; 669 } 670 671 676 public boolean getGeneratingTOCEntries() { 677 return writeTOC; 678 } 679 680 685 public void setHasTitlePage(boolean hasTitlePage) { 686 this.hasTitlePage = hasTitlePage; 687 } 688 689 694 public boolean getHasTitlePage() { 695 return hasTitlePage; 696 } 697 698 704 public void setLandscape(boolean landscape) { 705 this.landscape = landscape; 706 } 707 708 713 public boolean getLandscape() { 714 return landscape; 715 } 716 717 718 719 726 public static RtfWriter getInstance(Document document, OutputStream os) { 727 return new RtfWriter(document, os); 728 } 729 730 734 public void open() { 735 super.open(); 736 } 737 738 745 public void close() { 746 if (open) { 747 writeDocument(); 748 super.close(); 749 } 750 } 751 752 756 public void setFooter(HeaderFooter footer) { 757 this.footer = footer; 758 processHeaderFooter(this.footer); 759 } 760 761 765 public void setHeader(HeaderFooter header) { 766 this.header = header; 767 processHeaderFooter(this.header); 768 } 769 770 773 public void resetFooter() { 774 setFooter(null); 775 } 776 777 780 public void resetHeader() { 781 setHeader(null); 782 } 783 784 790 public boolean newPage() { 791 try { 792 content.write(escape); 793 content.write(newPage); 794 content.write(escape); 795 content.write(paragraph); 796 } catch (IOException e) { 797 throw new ExceptionConverter(e); 798 } 799 return true; 800 } 801 802 812 public boolean setMargins(float marginLeft, float marginRight, float marginTop, float marginBottom) { 813 this.marginLeft = (int) (marginLeft * TWIPSFACTOR); 814 this.marginRight = (int) (marginRight * TWIPSFACTOR); 815 this.marginTop = (int) (marginTop * TWIPSFACTOR); 816 this.marginBottom = (int) (marginBottom * TWIPSFACTOR); 817 return true; 818 } 819 820 827 public boolean setPageSize(Rectangle pageSize) { 828 if (!parseFormat(pageSize, false)) { 829 pageWidth = (int) (pageSize.getWidth() * TWIPSFACTOR); 830 pageHeight = (int) (pageSize.getHeight() * TWIPSFACTOR); 831 landscape = pageWidth > pageHeight; 832 } 833 return true; 834 } 835 836 846 public boolean writeTOC(String tocTitle, Font titleFont, boolean showTOCasEntry, Font showTOCEntryFont) { 847 try { 848 RtfTOC toc = new RtfTOC(tocTitle, titleFont); 849 if (showTOCasEntry) { 850 toc.addTOCAsTOCEntry(tocTitle, showTOCEntryFont); 851 } 852 add(new Paragraph(toc)); 853 } catch (DocumentException de) { 854 return false; 855 } 856 return true; 857 } 858 859 866 public boolean add(Element element) throws DocumentException { 867 if (pause) { 868 return false; 869 } 870 return addElement(element, content); 871 } 872 873 874 875 876 883 protected boolean addElement(Element element, ByteArrayOutputStream out) throws DocumentException { 884 try { 885 switch (element.type()) { 886 case Element.CHUNK: 887 writeChunk((Chunk) element, out); 888 break; 889 case Element.PARAGRAPH: 890 writeParagraph((Paragraph) element, out); 891 break; 892 case Element.ANCHOR: 893 writeAnchor((Anchor) element, out); 894 break; 895 case Element.PHRASE: 896 writePhrase((Phrase) element, out); 897 break; 898 case Element.CHAPTER: 899 case Element.SECTION: 900 writeSection((Section) element, out); 901 break; 902 case Element.LIST: 903 writeList((com.lowagie.text.List) element, out); 904 break; 905 case Element.TABLE: 906 try { 907 writeTable((Table) element, out); 908 } 909 catch(ClassCastException cce) { 910 writeTable(((SimpleTable)element).createTable(), out); 911 } 912 break; 913 case Element.ANNOTATION: 914 writeAnnotation((Annotation) element, out); 915 break; 916 case Element.IMGRAW: 917 case Element.IMGTEMPLATE: 918 case Element.JPEG: 919 Image img = (Image)element; 920 writeImage(img, out); 921 break; 922 923 case Element.AUTHOR: 924 writeMeta(metaAuthor, (Meta) element); 925 break; 926 case Element.SUBJECT: 927 writeMeta(metaSubject, (Meta) element); 928 break; 929 case Element.KEYWORDS: 930 writeMeta(metaKeywords, (Meta) element); 931 break; 932 case Element.TITLE: 933 writeMeta(metaTitle, (Meta) element); 934 break; 935 case Element.PRODUCER: 936 writeMeta(metaProducer, (Meta) element); 937 break; 938 case Element.CREATIONDATE: 939 writeMeta(metaCreationDate, (Meta) element); 940 break; 941 } 942 } catch (IOException e) { 943 return false; 944 } 945 return true; 946 } 947 948 957 private void writeSection(Section sectionElement, ByteArrayOutputStream out) throws IOException , DocumentException { 958 if (sectionElement.type() == Element.CHAPTER) { 959 out.write(escape); 960 out.write(sectionDefaults); 961 writeSectionDefaults(out); 962 } 963 if (sectionElement.getTitle() != null) { 964 if (writeTOC) { 965 StringBuffer title = new StringBuffer (""); 966 for (ListIterator li = sectionElement.getTitle().getChunks().listIterator(); li.hasNext();) { 967 title.append(((Chunk) li.next()).getContent()); 968 } 969 add(new RtfTOCEntry(title.toString(), sectionElement.getTitle().getFont())); 970 } else { 971 add(sectionElement.getTitle()); 972 } 973 out.write(escape); 974 out.write(paragraph); 975 } 976 sectionElement.process(this); 977 if (sectionElement.type() == Element.CHAPTER) { 978 out.write(escape); 979 out.write(section); 980 } 981 if (sectionElement.type() == Element.SECTION) { 982 out.write(escape); 983 out.write(paragraph); 984 } 985 } 986 987 995 private void writeParagraph(Paragraph paragraphElement, ByteArrayOutputStream out) throws IOException { 996 out.write(escape); 997 out.write(paragraphDefaults); 998 if (inTable) { 999 out.write(escape); 1000 out.write(RtfCell.cellInTable); 1001 } 1002 switch (paragraphElement.getAlignment()) { 1003 case Element.ALIGN_LEFT: 1004 out.write(escape); 1005 out.write(alignLeft); 1006 break; 1007 case Element.ALIGN_RIGHT: 1008 out.write(escape); 1009 out.write(alignRight); 1010 break; 1011 case Element.ALIGN_CENTER: 1012 out.write(escape); 1013 out.write(alignCenter); 1014 break; 1015 case Element.ALIGN_JUSTIFIED: 1016 case Element.ALIGN_JUSTIFIED_ALL: 1017 out.write(escape); 1018 out.write(alignJustify); 1019 break; 1020 } 1021 out.write(escape); 1022 out.write(listIndent); 1023 writeInt(out, (int) (paragraphElement.getIndentationLeft() * TWIPSFACTOR)); 1024 out.write(escape); 1025 out.write(rightIndent); 1026 writeInt(out, (int) (paragraphElement.getIndentationRight() * TWIPSFACTOR)); 1027 Iterator chunks = paragraphElement.getChunks().iterator(); 1028 while (chunks.hasNext()) { 1029 Chunk ch = (Chunk) chunks.next(); 1030 ch.setFont(paragraphElement.getFont().difference(ch.getFont())); 1031 } 1032 ByteArrayOutputStream save = content; 1033 content = out; 1034 paragraphElement.process(this); 1035 content = save; 1036 if (!inTable) { 1037 out.write(escape); 1038 out.write(paragraph); 1039 } 1040 } 1041 1042 1050 private void writePhrase(Phrase phrase, ByteArrayOutputStream out) throws IOException { 1051 out.write(escape); 1052 out.write(paragraphDefaults); 1053 if (inTable) { 1054 out.write(escape); 1055 out.write(RtfCell.cellInTable); 1056 } 1057 Iterator chunks = phrase.getChunks().iterator(); 1058 while (chunks.hasNext()) { 1059 Chunk ch = (Chunk) chunks.next(); 1060 ch.setFont(phrase.getFont().difference(ch.getFont())); 1061 } 1062 ByteArrayOutputStream save = content; 1063 content = out; 1064 phrase.process(this); 1065 content = save; 1066 } 1067 1068 1076 private void writeAnchor(Anchor anchor, ByteArrayOutputStream out) throws IOException { 1077 if (anchor.getUrl() != null) { 1078 out.write(openGroup); 1079 out.write(escape); 1080 out.write(field); 1081 out.write(openGroup); 1082 out.write(extendedEscape); 1083 out.write(fieldContent); 1084 out.write(openGroup); 1085 out.write(fieldHyperlink); 1086 out.write(delimiter); 1087 out.write(anchor.getUrl().toString().getBytes()); 1088 out.write(closeGroup); 1089 out.write(closeGroup); 1090 out.write(openGroup); 1091 out.write(escape); 1092 out.write(fieldDisplay); 1093 out.write(delimiter); 1094 writePhrase(anchor, out); 1095 out.write(closeGroup); 1096 out.write(closeGroup); 1097 } else { 1098 writePhrase(anchor, out); 1099 } 1100 } 1101 1102 1111 private void writeChunk(Chunk chunk, ByteArrayOutputStream out) throws IOException , DocumentException { 1112 if (chunk instanceof RtfField) { 1113 ((RtfField) chunk).write(this, out); 1114 } else { 1115 if (chunk.getImage() != null) { 1116 writeImage(chunk.getImage(), out); 1117 } else { 1118 writeInitialFontSignature(out, chunk); 1119 out.write(filterSpecialChar(chunk.getContent(), false).getBytes()); 1120 writeFinishingFontSignature(out, chunk); 1121 } 1122 } 1123 } 1124 1125 1126 protected void writeInitialFontSignature(OutputStream out, Chunk chunk) throws IOException { 1127 Font font = chunk.getFont(); 1128 1129 out.write(escape); 1130 out.write(fontNumber); 1131 if (!font.getFamilyname().equalsIgnoreCase("unknown")) { 1132 writeInt(out, addFont(font)); 1133 } else { 1134 writeInt(out, 0); 1135 } 1136 out.write(escape); 1137 out.write(fontSize); 1138 if (font.getSize() > 0) { 1139 writeInt(out, (int) (font.getSize() * 2)); 1140 } else { 1141 writeInt(out, 20); 1142 } 1143 out.write(escape); 1144 out.write(fontColor); 1145 writeInt(out, addColor(font.getColor())); 1146 if (font.isBold()) { 1147 out.write(escape); 1148 out.write(bold); 1149 } 1150 if (font.isItalic()) { 1151 out.write(escape); 1152 out.write(italic); 1153 } 1154 if (font.isUnderlined()) { 1155 out.write(escape); 1156 out.write(underline); 1157 } 1158 if (font.isStrikethru()) { 1159 out.write(escape); 1160 out.write(strikethrough); 1161 } 1162 1163 1166 if (chunk.getAttributes() != null) { 1167 Float f = (Float ) chunk.getAttributes().get(Chunk.SUBSUPSCRIPT); 1168 if (f != null) 1169 if (f.floatValue() > 0) { 1170 out.write(escape); 1171 out.write(startSuper); 1172 } else if (f.floatValue() < 0) { 1173 out.write(escape); 1174 out.write(startSub); 1175 } 1176 } 1177 1178 out.write(delimiter); 1179 } 1180 1181 1182 protected void writeFinishingFontSignature(OutputStream out, Chunk chunk) throws IOException { 1183 Font font = chunk.getFont(); 1184 1185 if (font.isBold()) { 1186 out.write(escape); 1187 out.write(bold); 1188 writeInt(out, 0); 1189 } 1190 if (font.isItalic()) { 1191 out.write(escape); 1192 out.write(italic); 1193 writeInt(out, 0); 1194 } 1195 if (font.isUnderlined()) { 1196 out.write(escape); 1197 out.write(underline); 1198 writeInt(out, 0); 1199 } 1200 if (font.isStrikethru()) { 1201 out.write(escape); 1202 out.write(strikethrough); 1203 writeInt(out, 0); 1204 } 1205 1206 1209 if (chunk.getAttributes() != null) { 1210 Float f = (Float ) chunk.getAttributes().get(Chunk.SUBSUPSCRIPT); 1211 if (f != null) 1212 if (f.floatValue() != 0) { 1213 out.write(escape); 1214 out.write(endSuperSub); 1215 } 1216 } 1217 } 1218 1219 1228 private void writeListElement(ListItem listItem, ByteArrayOutputStream out) throws IOException , DocumentException { 1229 Iterator chunks = listItem.getChunks().iterator(); 1230 while (chunks.hasNext()) { 1231 Chunk ch = (Chunk) chunks.next(); 1232 addElement(ch, out); 1233 } 1234 out.write(escape); 1235 out.write(paragraph); 1236 } 1237 1238 1247 private void writeList(com.lowagie.text.List list, ByteArrayOutputStream out) throws IOException , DocumentException { 1248 int type = 0; 1249 int align = 0; 1250 int fontNr = addFont(new Font(Font.SYMBOL, 10, Font.NORMAL, new Color (0, 0, 0))); 1251 if (!list.isNumbered()) type = 23; 1252 if (listLevel == 0) { 1253 maxListLevel = 0; 1254 listtable.write(openGroup); 1255 listtable.write(escape); 1256 listtable.write(listDefinition); 1257 int i = getRandomInt(); 1258 listtable.write(escape); 1259 listtable.write(listTemplateID); 1260 writeInt(listtable, i); 1261 listtable.write(escape); 1262 listtable.write(hybridList); 1263 listtable.write((byte) '\n'); 1264 } 1265 if (listLevel >= maxListLevel) { 1266 maxListLevel++; 1267 listtable.write(openGroup); 1268 listtable.write(escape); 1269 listtable.write(listLevelDefinition); 1270 listtable.write(escape); 1271 listtable.write(listLevelTypeOld); 1272 writeInt(listtable, type); 1273 listtable.write(escape); 1274 listtable.write(listLevelTypeNew); 1275 writeInt(listtable, type); 1276 listtable.write(escape); 1277 listtable.write(listLevelAlignOld); 1278 writeInt(listtable, align); 1279 listtable.write(escape); 1280 listtable.write(listLevelAlignNew); 1281 writeInt(listtable, align); 1282 listtable.write(escape); 1283 listtable.write(listLevelStartAt); 1284 writeInt(listtable, 1); 1285 listtable.write(openGroup); 1286 listtable.write(escape); 1287 listtable.write(listLevelTextDefinition); 1288 listtable.write(escape); 1289 listtable.write(listLevelTextLength); 1290 if (list.isNumbered()) { 1291 writeInt(listtable, 2); 1292 } else { 1293 writeInt(listtable, 1); 1294 } 1295 listtable.write(escape); 1296 if (list.isNumbered()) { 1297 listtable.write(listLevelTextStyleNumbers); 1298 } else { 1299 listtable.write(listLevelTextStyleBullet); 1300 } 1301 listtable.write(commaDelimiter); 1302 listtable.write(closeGroup); 1303 listtable.write(openGroup); 1304 listtable.write(escape); 1305 listtable.write(listLevelNumbersDefinition); 1306 if (list.isNumbered()) { 1307 listtable.write(delimiter); 1308 listtable.write(listLevelNumbers); 1309 writeInt(listtable, listLevel + 1); 1310 } 1311 listtable.write(commaDelimiter); 1312 listtable.write(closeGroup); 1313 if (!list.isNumbered()) { 1314 listtable.write(escape); 1315 listtable.write(fontNumber); 1316 writeInt(listtable, fontNr); 1317 } 1318 listtable.write(escape); 1319 listtable.write(firstIndent); 1320 writeInt(listtable, (int) (list.getIndentationLeft() * TWIPSFACTOR * -1)); 1321 listtable.write(escape); 1322 listtable.write(listIndent); 1323 writeInt(listtable, (int) ((list.getIndentationLeft() + list.getSymbolIndent()) * TWIPSFACTOR)); 1324 listtable.write(escape); 1325 listtable.write(rightIndent); 1326 writeInt(listtable, (int) (list.getIndentationRight() * TWIPSFACTOR)); 1327 listtable.write(escape); 1328 listtable.write(tabStop); 1329 writeInt(listtable, (int) (list.getSymbolIndent() * TWIPSFACTOR)); 1330 listtable.write(closeGroup); 1331 listtable.write((byte) '\n'); 1332 } 1333 out.write(escape); 1335 out.write(paragraphDefaults); 1336 out.write(escape); 1337 out.write(alignLeft); 1338 out.write(escape); 1339 out.write(firstIndent); 1340 writeInt(out, (int) (list.getIndentationLeft() * TWIPSFACTOR * -1)); 1341 out.write(escape); 1342 out.write(listIndent); 1343 writeInt(out, (int) ((list.getIndentationLeft() + list.getSymbolIndent()) * TWIPSFACTOR)); 1344 out.write(escape); 1345 out.write(rightIndent); 1346 writeInt(out, (int) (list.getIndentationRight() * TWIPSFACTOR)); 1347 out.write(escape); 1348 out.write(fontSize); 1349 writeInt(out, 20); 1350 out.write(escape); 1351 out.write(listBegin); 1352 writeInt(out, currentListID); 1353 if (listLevel > 0) { 1354 out.write(escape); 1355 out.write(listCurrentLevel); 1356 writeInt(out, listLevel); 1357 } 1358 out.write(openGroup); 1359 ListIterator listItems = list.getItems().listIterator(); 1360 Element listElem; 1361 int count = 1; 1362 while (listItems.hasNext()) { 1363 listElem = (Element) listItems.next(); 1364 if (listElem.type() == Element.CHUNK) { 1365 listElem = new ListItem((Chunk) listElem); 1366 } 1367 if (listElem.type() == Element.LISTITEM) { 1368 out.write(openGroup); 1369 out.write(escape); 1370 out.write(listTextOld); 1371 out.write(escape); 1372 out.write(paragraphDefaults); 1373 out.write(escape); 1374 out.write(fontNumber); 1375 if (list.isNumbered()) { 1376 writeInt(out, addFont(new Font(Font.TIMES_ROMAN, Font.NORMAL, 10, new Color (0, 0, 0)))); 1377 } else { 1378 writeInt(out, fontNr); 1379 } 1380 out.write(escape); 1381 out.write(firstIndent); 1382 writeInt(out, (int) (list.getIndentationLeft() * TWIPSFACTOR * -1)); 1383 out.write(escape); 1384 out.write(listIndent); 1385 writeInt(out, (int) ((list.getIndentationLeft() + list.getSymbolIndent()) * TWIPSFACTOR)); 1386 out.write(escape); 1387 out.write(rightIndent); 1388 writeInt(out, (int) (list.getIndentationRight() * TWIPSFACTOR)); 1389 out.write(delimiter); 1390 if (list.isNumbered()) { 1391 writeInt(out, count); 1392 out.write(".".getBytes()); 1393 } else { 1394 out.write(escape); 1395 out.write(listBulletOld); 1396 } 1397 out.write(escape); 1398 out.write(tab); 1399 out.write(closeGroup); 1400 writeListElement((ListItem) listElem, out); 1401 count++; 1402 } else if (listElem.type() == Element.LIST) { 1403 listLevel++; 1404 writeList((com.lowagie.text.List) listElem, out); 1405 listLevel--; 1406 out.write(escape); 1407 out.write(paragraphDefaults); 1408 out.write(escape); 1409 out.write(alignLeft); 1410 out.write(escape); 1411 out.write(firstIndent); 1412 writeInt(out, (int) (list.getIndentationLeft() * TWIPSFACTOR * -1)); 1413 out.write(escape); 1414 out.write(listIndent); 1415 writeInt(out, (int) ((list.getIndentationLeft() + list.getSymbolIndent()) * TWIPSFACTOR)); 1416 out.write(escape); 1417 out.write(rightIndent); 1418 writeInt(out, (int) (list.getIndentationRight() * TWIPSFACTOR)); 1419 out.write(escape); 1420 out.write(fontSize); 1421 writeInt(out, 20); 1422 out.write(escape); 1423 out.write(listBegin); 1424 writeInt(out, currentListID); 1425 if (listLevel > 0) { 1426 out.write(escape); 1427 out.write(listCurrentLevel); 1428 writeInt(out, listLevel); 1429 } 1430 } 1431 out.write((byte) '\n'); 1432 } 1433 out.write(closeGroup); 1434 if (listLevel == 0) { 1435 int i = getRandomInt(); 1436 listtable.write(escape); 1437 listtable.write(listID); 1438 writeInt(listtable, i); 1439 listtable.write(closeGroup); 1440 listtable.write((byte) '\n'); 1441 listoverride.write(openGroup); 1442 listoverride.write(escape); 1443 listoverride.write(listOverride); 1444 listoverride.write(escape); 1445 listoverride.write(listID); 1446 writeInt(listoverride, i); 1447 listoverride.write(escape); 1448 listoverride.write(listOverrideCount); 1449 writeInt(listoverride, 0); 1450 listoverride.write(escape); 1451 listoverride.write(listBegin); 1452 writeInt(listoverride, currentListID); 1453 currentListID++; 1454 listoverride.write(closeGroup); 1455 listoverride.write((byte) '\n'); 1456 } 1457 out.write(escape); 1458 out.write(paragraphDefaults); 1459 } 1460 1461 1472 private void writeTable(Table table, ByteArrayOutputStream out) throws IOException , DocumentException { 1473 inTable = true; 1474 table.complete(); 1475 RtfTable rtfTable = new RtfTable(this); 1476 rtfTable.importTable(table, pageWidth - marginLeft - marginRight); 1477 rtfTable.writeTable(out); 1478 inTable = false; 1479 } 1480 1481 1482 1493 private void writeImage(Image image, ByteArrayOutputStream out) throws IOException , DocumentException { 1494 int type = image.getOriginalType(); 1495 if (!(type == Image.ORIGINAL_JPEG || type == Image.ORIGINAL_BMP 1496 || type == Image.ORIGINAL_PNG || type == Image.ORIGINAL_WMF)) 1497 throw new DocumentException("Only BMP, PNG, WMF and JPEG images are supported by the RTF Writer"); 1498 switch (image.getAlignment()) { 1499 case Element.ALIGN_LEFT: 1500 out.write(escape); 1501 out.write(alignLeft); 1502 break; 1503 case Element.ALIGN_RIGHT: 1504 out.write(escape); 1505 out.write(alignRight); 1506 break; 1507 case Element.ALIGN_CENTER: 1508 out.write(escape); 1509 out.write(alignCenter); 1510 break; 1511 case Element.ALIGN_JUSTIFIED: 1512 out.write(escape); 1513 out.write(alignJustify); 1514 break; 1515 } 1516 out.write(openGroup); 1517 out.write(extendedEscape); 1518 out.write(pictureGroup); 1519 out.write(openGroup); 1520 out.write(escape); 1521 out.write(picture); 1522 out.write(escape); 1523 switch (type) { 1524 case Image.ORIGINAL_JPEG: 1525 out.write(pictureJPEG); 1526 break; 1527 case Image.ORIGINAL_PNG: 1528 out.write(picturePNG); 1529 break; 1530 case Image.ORIGINAL_WMF: 1531 case Image.ORIGINAL_BMP: 1532 out.write(pictureWMF); 1533 break; 1534 } 1535 out.write(escape); 1536 out.write(pictureWidth); 1537 writeInt(out, (int) (image.getPlainWidth() * TWIPSFACTOR)); 1538 out.write(escape); 1539 out.write(pictureHeight); 1540 writeInt(out, (int) (image.getPlainHeight() * TWIPSFACTOR)); 1541 1542 1543 1552 1553 if (image.getWidth() > 0) { 1554 out.write(escape); 1555 out.write(pictureScaleX); 1556 writeInt(out, (int) (100 / image.getWidth() * image.getPlainWidth())); 1557 } 1558 if (image.getHeight() > 0) { 1559 out.write(escape); 1560 out.write(pictureScaleY); 1561 writeInt(out, (int) (100 / image.getHeight() * image.getPlainHeight())); 1562 } 1563 out.write(delimiter); 1564 InputStream imgIn; 1565 if (type == Image.ORIGINAL_BMP) { 1566 imgIn = new ByteArrayInputStream (MetaDo.wrapBMP(image)); 1567 } 1568 else { 1569 if (image.getOriginalData() == null) { 1570 imgIn = image.getUrl().openStream(); 1571 } else { 1572 imgIn = new ByteArrayInputStream (image.getOriginalData()); 1573 } 1574 if (type == Image.ORIGINAL_WMF) { long skipLength = 22; 1576 while(skipLength > 0) { 1577 skipLength = skipLength - imgIn.skip(skipLength); 1578 } 1579 } 1580 } 1581 int buffer = -1; 1582 int count = 0; 1583 out.write((byte) '\n'); 1584 while ((buffer = imgIn.read()) != -1) { 1585 String helperStr = Integer.toHexString(buffer); 1586 if (helperStr.length() < 2) helperStr = "0" + helperStr; 1587 out.write(helperStr.getBytes()); 1588 count++; 1589 if (count == 64) { 1590 out.write((byte) '\n'); 1591 count = 0; 1592 } 1593 } 1594 imgIn.close(); 1595 out.write(closeGroup); 1596 out.write(closeGroup); 1597 out.write((byte) '\n'); 1598 } 1599 1600 1608 private void writeAnnotation(Annotation annotationElement, ByteArrayOutputStream out) throws IOException { 1609 int id = getRandomInt(); 1610 out.write(openGroup); 1611 out.write(extendedEscape); 1612 out.write(annotationID); 1613 out.write(delimiter); 1614 writeInt(out, id); 1615 out.write(closeGroup); 1616 out.write(openGroup); 1617 out.write(extendedEscape); 1618 out.write(annotationAuthor); 1619 out.write(delimiter); 1620 out.write(annotationElement.title().getBytes()); 1621 out.write(closeGroup); 1622 out.write(openGroup); 1623 out.write(extendedEscape); 1624 out.write(annotation); 1625 out.write(escape); 1626 out.write(paragraphDefaults); 1627 out.write(delimiter); 1628 out.write(annotationElement.content().getBytes()); 1629 out.write(closeGroup); 1630 } 1631 1632 1644 private void writeMeta(byte[] metaName, Meta meta) throws IOException { 1645 info.write(openGroup); 1646 try { 1647 info.write(escape); 1648 info.write(metaName); 1649 info.write(delimiter); 1650 if (meta.type() == Meta.CREATIONDATE) { 1651 writeFormatedDateTime(meta.getContent()); 1652 } else { 1653 info.write(meta.getContent().getBytes()); 1654 } 1655 } finally { 1656 info.write(closeGroup); 1657 } 1658 } 1659 1660 1667 private void writeFormatedDateTime(String date) throws IOException { 1668 Calendar cal = Calendar.getInstance(); 1669 SimpleDateFormat sdf = new SimpleDateFormat ("EEE MMM dd HH:mm:ss zzz yyyy"); 1670 ParsePosition pp = new ParsePosition (0); 1671 Date d = sdf.parse(date, pp); 1672 if (d == null) { 1673 d = new Date (); 1674 } 1675 cal.setTime(d); 1676 info.write(escape); 1677 info.write(year); 1678 writeInt(info, cal.get(Calendar.YEAR)); 1679 info.write(escape); 1680 info.write(month); 1681 writeInt(info, cal.get(Calendar.MONTH)); 1682 info.write(escape); 1683 info.write(day); 1684 writeInt(info, cal.get(Calendar.DAY_OF_MONTH)); 1685 info.write(escape); 1686 info.write(hour); 1687 writeInt(info, cal.get(Calendar.HOUR_OF_DAY)); 1688 info.write(escape); 1689 info.write(minute); 1690 writeInt(info, cal.get(Calendar.MINUTE)); 1691 info.write(escape); 1692 info.write(second); 1693 writeInt(info, cal.get(Calendar.SECOND)); 1694 } 1695 1696 1704 protected int addFont(Font newFont) { 1705 int fn = -1; 1706 1707 for (int i = 0; i < fontList.size(); i++) { 1708 if (newFont.getFamilyname().equals(((Font) fontList.get(i)).getFamilyname())) { 1709 fn = i; 1710 } 1711 } 1712 if (fn == -1) { 1713 fontList.add(newFont); 1714 return fontList.size() - 1; 1715 } 1716 return fn; 1717 } 1718 1719 1727 protected int addColor(Color newColor) { 1728 int cn = 0; 1729 if (newColor == null) { 1730 return cn; 1731 } 1732 cn = colorList.indexOf(newColor); 1733 if (cn == -1) { 1734 colorList.add(newColor); 1735 return colorList.size() - 1; 1736 } 1737 return cn; 1738 } 1739 1740 1746 private boolean writeDocument() { 1747 try { 1748 writeDocumentIntro(); 1749 writeFontList(); 1750 os.write((byte) '\n'); 1751 writeColorList(); 1752 os.write((byte) '\n'); 1753 writeList(); 1754 os.write((byte) '\n'); 1755 writeInfoGroup(); 1756 os.write((byte) '\n'); 1757 writeDocumentFormat(); 1758 os.write((byte) '\n'); 1759 ByteArrayOutputStream hf = new ByteArrayOutputStream (); 1760 writeSectionDefaults(hf); 1761 hf.writeTo(os); 1762 content.writeTo(os); 1763 os.write(closeGroup); 1764 return true; 1765 } catch (IOException e) { 1766 System.err.println(e.getMessage()); 1767 return false; 1768 } 1769 1770 } 1771 1772 1775 private void writeDocumentIntro() throws IOException { 1776 os.write(openGroup); 1777 os.write(escape); 1778 os.write(docBegin); 1779 os.write(escape); 1780 os.write(ansi); 1781 os.write(escape); 1782 os.write(ansiCodepage); 1783 writeInt(os, 1252); 1784 os.write((byte)'\n'); 1785 os.write(escape); 1786 os.write(defaultFont); 1787 writeInt(os, 0); 1788 } 1789 1790 1794 private void writeFontList() throws IOException { 1795 Font fnt; 1796 1797 os.write(openGroup); 1798 os.write(escape); 1799 os.write(fontTable); 1800 for (int i = 0; i < fontList.size(); i++) { 1801 fnt = (Font) fontList.get(i); 1802 os.write(openGroup); 1803 os.write(escape); 1804 os.write(fontNumber); 1805 writeInt(os, i); 1806 os.write(escape); 1807 switch (Font.getFamilyIndex(fnt.getFamilyname())) { 1808 case Font.COURIER: 1809 os.write(fontModern); 1810 os.write(escape); 1811 os.write(fontCharset); 1812 writeInt(os, 0); 1813 os.write(delimiter); 1814 os.write(fontCourier); 1815 break; 1816 case Font.HELVETICA: 1817 os.write(fontSwiss); 1818 os.write(escape); 1819 os.write(fontCharset); 1820 writeInt(os, 0); 1821 os.write(delimiter); 1822 os.write(fontArial); 1823 break; 1824 case Font.SYMBOL: 1825 os.write(fontRoman); 1826 os.write(escape); 1827 os.write(fontCharset); 1828 writeInt(os, 2); 1829 os.write(delimiter); 1830 os.write(fontSymbol); 1831 break; 1832 case Font.TIMES_ROMAN: 1833 os.write(fontRoman); 1834 os.write(escape); 1835 os.write(fontCharset); 1836 writeInt(os, 0); 1837 os.write(delimiter); 1838 os.write(fontTimesNewRoman); 1839 break; 1840 case Font.ZAPFDINGBATS: 1841 os.write(fontTech); 1842 os.write(escape); 1843 os.write(fontCharset); 1844 writeInt(os, 0); 1845 os.write(delimiter); 1846 os.write(fontWindings); 1847 break; 1848 default: 1849 os.write(fontRoman); 1850 os.write(escape); 1851 os.write(fontCharset); 1852 writeInt(os, 0); 1853 os.write(delimiter); 1854 os.write(filterSpecialChar(fnt.getFamilyname(), true).getBytes()); 1855 } 1856 os.write(commaDelimiter); 1857 os.write(closeGroup); 1858 } 1859 os.write(closeGroup); 1860 } 1861 1862 1866 private void writeColorList() throws IOException { 1867 Color color = null; 1868 1869 os.write(openGroup); 1870 os.write(escape); 1871 os.write(colorTable); 1872 for (int i = 0; i < colorList.size(); i++) { 1873 color = (Color ) colorList.get(i); 1874 os.write(escape); 1875 os.write(colorRed); 1876 writeInt(os, color.getRed()); 1877 os.write(escape); 1878 os.write(colorGreen); 1879 writeInt(os, color.getGreen()); 1880 os.write(escape); 1881 os.write(colorBlue); 1882 writeInt(os, color.getBlue()); 1883 os.write(commaDelimiter); 1884 } 1885 os.write(closeGroup); 1886 } 1887 1888 1892 private void writeInfoGroup() throws IOException { 1893 os.write(openGroup); 1894 os.write(escape); 1895 os.write(infoBegin); 1896 info.writeTo(os); 1897 os.write(closeGroup); 1898 } 1899 1900 1904 private void writeList() throws IOException { 1905 listtable.write(closeGroup); 1906 listoverride.write(closeGroup); 1907 listtable.writeTo(os); 1908 os.write((byte) '\n'); 1909 listoverride.writeTo(os); 1910 } 1911 1912 1919 public final static void writeInt(OutputStream out, int i) throws IOException { 1920 out.write(Integer.toString(i).getBytes()); 1921 } 1922 1923 1929 private int getRandomInt() { 1930 boolean ok = false; 1931 Integer newInt = null; 1932 Integer oldInt = null; 1933 while (!ok) { 1934 newInt = new Integer ((int) (Math.random() * Integer.MAX_VALUE)); 1935 ok = true; 1936 for (int i = 0; i < listIds.size(); i++) { 1937 oldInt = (Integer ) listIds.get(i); 1938 if (oldInt.equals(newInt)) { 1939 ok = true; 1940 } 1941 } 1942 } 1943 listIds.add(newInt); 1944 return newInt.intValue(); 1945 } 1946 1947 1953 public void writeHeadersFooters(ByteArrayOutputStream os) throws IOException { 1954 if (this.footer instanceof RtfHeaderFooters) { 1955 RtfHeaderFooters rtfHf = (RtfHeaderFooters) this.footer; 1956 HeaderFooter hf = rtfHf.get(RtfHeaderFooters.ALL_PAGES); 1957 if (hf != null) { 1958 writeHeaderFooter(hf, footerBegin, os); 1959 } 1960 hf = rtfHf.get(RtfHeaderFooters.LEFT_PAGES); 1961 if (hf != null) { 1962 writeHeaderFooter(hf, footerlBegin, os); 1963 } 1964 hf = rtfHf.get(RtfHeaderFooters.RIGHT_PAGES); 1965 if (hf != null) { 1966 writeHeaderFooter(hf, footerrBegin, os); 1967 } 1968 hf = rtfHf.get(RtfHeaderFooters.FIRST_PAGE); 1969 if (hf != null) { 1970 writeHeaderFooter(hf, footerfBegin, os); 1971 } 1972 } else { 1973 writeHeaderFooter(this.footer, footerBegin, os); 1974 } 1975 if (this.header instanceof RtfHeaderFooters) { 1976 RtfHeaderFooters rtfHf = (RtfHeaderFooters) this.header; 1977 HeaderFooter hf = rtfHf.get(RtfHeaderFooters.ALL_PAGES); 1978 if (hf != null) { 1979 writeHeaderFooter(hf, headerBegin, os); 1980 } 1981 hf = rtfHf.get(RtfHeaderFooters.LEFT_PAGES); 1982 if (hf != null) { 1983 writeHeaderFooter(hf, headerlBegin, os); 1984 } 1985 hf = rtfHf.get(RtfHeaderFooters.RIGHT_PAGES); 1986 if (hf != null) { 1987 writeHeaderFooter(hf, headerrBegin, os); 1988 } 1989 hf = rtfHf.get(RtfHeaderFooters.FIRST_PAGE); 1990 if (hf != null) { 1991 writeHeaderFooter(hf, headerfBegin, os); 1992 } 1993 } else { 1994 writeHeaderFooter(this.header, headerBegin, os); 1995 } 1996 } 1997 1998 2006 private void writeHeaderFooter(HeaderFooter headerFooter, byte[] hfType, ByteArrayOutputStream target) throws IOException { 2007 inHeaderFooter = true; 2008 try { 2009 target.write(openGroup); 2010 target.write(escape); 2011 target.write(hfType); 2012 target.write(delimiter); 2013 if (headerFooter != null) { 2014 if (headerFooter instanceof RtfHeaderFooter && ((RtfHeaderFooter) headerFooter).content() != null) { 2015 this.addElement(((RtfHeaderFooter) headerFooter).content(), target); 2016 } else { 2017 Paragraph par = new Paragraph(); 2018 par.setAlignment(headerFooter.alignment()); 2019 if (headerFooter.getBefore() != null) { 2020 par.add(headerFooter.getBefore()); 2021 } 2022 if (headerFooter.isNumbered()) { 2023 par.add(new RtfPageNumber("", headerFooter.getBefore().getFont())); 2024 } 2025 if (headerFooter.getAfter() != null) { 2026 par.add(headerFooter.getAfter()); 2027 } 2028 this.addElement(par, target); 2029 } 2030 } 2031 target.write(closeGroup); 2032 } catch (DocumentException e) { 2033 throw new IOException ("DocumentException - " + e.getMessage()); 2034 } 2035 inHeaderFooter = false; 2036 } 2037 2038 2043 private void writeDocumentFormat() throws IOException { 2044 os.write(escape); 2046 os.write(rtfPaperWidth); 2047 writeInt(os, pageWidth); 2048 os.write(escape); 2049 os.write(rtfPaperHeight); 2050 writeInt(os, pageHeight); 2051 os.write(escape); 2052 os.write(rtfMarginLeft); 2053 writeInt(os, marginLeft); 2054 os.write(escape); 2055 os.write(rtfMarginRight); 2056 writeInt(os, marginRight); 2057 os.write(escape); 2058 os.write(rtfMarginTop); 2059 writeInt(os, marginTop); 2060 os.write(escape); 2061 os.write(rtfMarginBottom); 2062 writeInt(os, marginBottom); 2063 } 2065 2066 2070 private void initDefaults() { 2071 fontList.clear(); 2072 colorList.clear(); 2073 info = new ByteArrayOutputStream (); 2074 content = new ByteArrayOutputStream (); 2075 listtable = new ByteArrayOutputStream (); 2076 listoverride = new ByteArrayOutputStream (); 2077 document.addProducer(); 2078 document.addCreationDate(); 2079 addFont(new Font(Font.TIMES_ROMAN, 10, Font.NORMAL)); 2080 addColor(new Color (0, 0, 0)); 2081 addColor(new Color (255, 255, 255)); 2082 listIds = new ArrayList (); 2083 try { 2084 listtable.write(openGroup); 2085 listtable.write(extendedEscape); 2086 listtable.write(listtableGroup); 2087 listtable.write((byte) '\n'); 2088 listoverride.write(openGroup); 2089 listoverride.write(extendedEscape); 2090 listoverride.write(listoverridetableGroup); 2091 listoverride.write((byte) '\n'); 2092 } catch (IOException e) { 2093 System.err.println("InitDefaultsError" + e); 2094 } 2095 } 2096 2097 2103 private void writeSectionDefaults(ByteArrayOutputStream out) throws IOException { 2104 if (header instanceof RtfHeaderFooters || footer instanceof RtfHeaderFooters) { 2105 RtfHeaderFooters rtfHeader = (RtfHeaderFooters) header; 2106 RtfHeaderFooters rtfFooter = (RtfHeaderFooters) footer; 2107 if ((rtfHeader != null && (rtfHeader.get(RtfHeaderFooters.LEFT_PAGES) != null || rtfHeader.get(RtfHeaderFooters.RIGHT_PAGES) != null)) || (rtfFooter != null && (rtfFooter.get(RtfHeaderFooters.LEFT_PAGES) != null || rtfFooter.get(RtfHeaderFooters.RIGHT_PAGES) != null))) { 2108 out.write(escape); 2109 out.write(facingPages); 2110 } 2111 } 2112 if (hasTitlePage) { 2113 out.write(escape); 2114 out.write(titlePage); 2115 } 2116 writeHeadersFooters(out); 2117 if (landscape) { 2118 out.write(escape); 2121 out.write(landscapeTag2); 2122 out.write(escape); 2123 out.write(sectionPageWidth); 2124 writeInt(out, pageWidth); 2125 out.write(escape); 2126 out.write(sectionPageHeight); 2127 writeInt(out, pageHeight); 2128 } else { 2129 out.write(escape); 2130 out.write(sectionPageWidth); 2131 writeInt(out, pageWidth); 2132 out.write(escape); 2133 out.write(sectionPageHeight); 2134 writeInt(out, pageHeight); 2135 } 2136 } 2137 2138 2147 private boolean parseFormat(Rectangle pageSize, boolean rotate) { 2148 if (rotate) { 2149 pageSize = pageSize.rotate(); 2150 } 2151 if (rectEquals(pageSize, PageSize.A3)) { 2152 pageWidth = 16837; 2153 pageHeight = 23811; 2154 landscape = rotate; 2155 return true; 2156 } 2157 if (rectEquals(pageSize, PageSize.A4)) { 2158 pageWidth = 11907; 2159 pageHeight = 16840; 2160 landscape = rotate; 2161 return true; 2162 } 2163 if (rectEquals(pageSize, PageSize.A5)) { 2164 pageWidth = 8391; 2165 pageHeight = 11907; 2166 landscape = rotate; 2167 return true; 2168 } 2169 if (rectEquals(pageSize, PageSize.A6)) { 2170 pageWidth = 5959; 2171 pageHeight = 8420; 2172 landscape = rotate; 2173 return true; 2174 } 2175 if (rectEquals(pageSize, PageSize.B4)) { 2176 pageWidth = 14570; 2177 pageHeight = 20636; 2178 landscape = rotate; 2179 return true; 2180 } 2181 if (rectEquals(pageSize, PageSize.B5)) { 2182 pageWidth = 10319; 2183 pageHeight = 14572; 2184 landscape = rotate; 2185 return true; 2186 } 2187 if (rectEquals(pageSize, PageSize.HALFLETTER)) { 2188 pageWidth = 7927; 2189 pageHeight = 12247; 2190 landscape = rotate; 2191 return true; 2192 } 2193 if (rectEquals(pageSize, PageSize.LETTER)) { 2194 pageWidth = 12242; 2195 pageHeight = 15842; 2196 landscape = rotate; 2197 return true; 2198 } 2199 if (rectEquals(pageSize, PageSize.LEGAL)) { 2200 pageWidth = 12252; 2201 pageHeight = 20163; 2202 landscape = rotate; 2203 return true; 2204 } 2205 if (!rotate && parseFormat(pageSize, true)) { 2206 int x = pageWidth; 2207 pageWidth = pageHeight; 2208 pageHeight = x; 2209 return true; 2210 } 2211 return false; 2212 } 2213 2214 2220 private boolean rectEquals(Rectangle rect1, Rectangle rect2) { 2221 return (rect1.getWidth() == rect2.getWidth()) && (rect1.getHeight() == rect2.getHeight()); 2222 } 2223 2224 2229 public boolean writingHeaderFooter() { 2230 return inHeaderFooter; 2231 } 2232 2233 2240 public final static String filterSpecialChar(String str, boolean useHex) { 2241 int length = str.length(); 2242 int z = (int) 'z'; 2243 StringBuffer ret = new StringBuffer (length); 2244 for (int i = 0; i < length; i++) { 2245 char ch = str.charAt(i); 2246 2247 if (ch == '\\') { 2248 ret.append("\\\\"); 2249 } else if (ch == '\n') { 2250 ret.append("\\par "); 2251 } else if (((int) ch) > z) { 2252 if(useHex) { 2253 ret.append("\\\'").append(Long.toHexString((long) ch)); 2254 } else { 2255 ret.append("\\u").append((long) ch).append('?'); 2256 } 2257 } else { 2258 ret.append(ch); 2259 } 2260 } 2261 String s = ret.toString(); 2262 if(s.indexOf("$newpage$") >= 0) { 2263 String before = s.substring(0, s.indexOf("$newpage$")); 2264 String after = s.substring(s.indexOf("$newpage$") + 9); 2265 ret = new StringBuffer (before); 2266 ret.append("\\page\\par "); 2267 ret.append(after); 2268 return ret.toString(); 2269 } 2270 return s; 2271 } 2272 2273 private void addHeaderFooterFontColor(HeaderFooter hf) { 2274 if(hf instanceof RtfHeaderFooter) { 2275 RtfHeaderFooter rhf = (RtfHeaderFooter) hf; 2276 if(rhf.content() instanceof Chunk) { 2277 addFont(((Chunk) rhf.content()).getFont()); 2278 addColor(((Chunk) rhf.content()).getFont().getColor()); 2279 } else if(rhf.content() instanceof Phrase) { 2280 addFont(((Phrase) rhf.content()).getFont()); 2281 addColor(((Phrase) rhf.content()).getFont().getColor()); 2282 } 2283 } 2284 if(hf.getBefore() != null) { 2285 addFont(hf.getBefore().getFont()); 2286 addColor(hf.getBefore().getFont().getColor()); 2287 } 2288 if(hf.getAfter() != null) { 2289 addFont(hf.getAfter().getFont()); 2290 addColor(hf.getAfter().getFont().getColor()); 2291 } 2292 } 2293 2294 private void processHeaderFooter(HeaderFooter hf) { 2295 if(hf != null) { 2296 if(hf instanceof RtfHeaderFooters) { 2297 RtfHeaderFooters rhf = (RtfHeaderFooters) hf; 2298 if(rhf.get(RtfHeaderFooters.ALL_PAGES) != null) { 2299 addHeaderFooterFontColor(rhf.get(RtfHeaderFooters.ALL_PAGES)); 2300 } 2301 if(rhf.get(RtfHeaderFooters.LEFT_PAGES) != null) { 2302 addHeaderFooterFontColor(rhf.get(RtfHeaderFooters.LEFT_PAGES)); 2303 } 2304 if(rhf.get(RtfHeaderFooters.RIGHT_PAGES) != null) { 2305 addHeaderFooterFontColor(rhf.get(RtfHeaderFooters.RIGHT_PAGES)); 2306 } 2307 if(rhf.get(RtfHeaderFooters.FIRST_PAGE) != null) { 2308 addHeaderFooterFontColor(rhf.get(RtfHeaderFooters.FIRST_PAGE)); 2309 } 2310 } else { 2311 addHeaderFooterFontColor(hf); 2312 } 2313 } 2314 } 2315 2316 2319 public boolean setMarginMirroring(boolean MarginMirroring) { 2320 return false; 2321 } 2322 2323} 2324 2325 | Popular Tags |