اقرأ وكتابة ملفات مستند Word باستخدام POI
تستخدم وحدة HWPF من Apache POI خصيصًا لقراءة ملفات DOC وكتابةها. في HWPF ، نستخدم hwpfdocument لتمثيل مستند DOC Word. هناك العديد من المفاهيم في hwpfdocument:
النطاق : يمثل نطاقًا ، والذي يمكن أن يكون المستند بأكمله أو قسمًا معينًا أو فقرة (فقرة) أو فقرة (حرف) مع سمات شائعة.
القسم : قسم فرعي من وثيقة كلمة. يمكن أن تتكون مستند كلمة من أقسام فرعية متعددة.
الفقرة : فقرة من مستند Word ، يمكن أن يتكون القسم الفرعي من فقرات متعددة.
الحرف : يمكن أن تتكون فقرة نصية ذات نفس الخصائص ، والفقرة من أحرف متعددة.
الجدول : جدول.
TableRow : الصف المقابل للجدول.
Tablecell : الخلية المقابلة للجدول.
القسم ، الفقرة ، الحرف ، والجدول كلها ورثت من النطاق.
1 اقرأ ملف DOC Word
في التطبيقات اليومية ، من النادر جدًا أن نقرأ المعلومات من ملفات الكلمات ، ونكتب المحتوى في ملفات الكلمات في كثير من الأحيان. هناك طريقتان رئيسيتان لقراءة البيانات من ملفات DOC Word باستخدام POI: اقرأ من خلال WordExtractor وقراءة من خلال HWPFDOCUMITY . عند قراءة المعلومات داخل WordExtractor ، لا يزال يتم الحصول عليها من خلال HWPFDOCUMITY.
1.1 اقرأ الملفات من خلال WordExtractor
عند قراءة ملف باستخدام WordExtractor ، يمكننا فقط قراءة محتوى النص للملف وبعض الخصائص بناءً على المستند. بالنسبة لخصائص محتوى المستند ، لا يمكننا قراءته. إذا كنت ترغب في قراءة خصائص محتوى المستند ، فأنت بحاجة إلى استخدام HWPFDocument لقراءتها. فيما يلي مثال على استخدام WordExtractor لقراءة الملفات:
الفئة العامة hwpftest {suppresswarnings ("demecation") test public void testReadByExtractor () رمي الاستثناء {inputStream هو = جديد fileInputStream ("d: //test.doc") ؛ WordExtractor extractor = new WordExtractor (IS) ؛ // إخراج جميع نص Word document system.out.println (extractor.getText ()) ؛ System.out.println (extractor.getTextFrompieCes ()) ؛ // إخراج محتوى header system.out.println ("header:" + extractor.getheadertext ()) ؛ // إخراج محتوى نظام footer. // إخراج معلومات البيانات الوصفية لمستند Word الحالي ، بما في ذلك المؤلف ، وقت تعديل المستند ، إلخ // احصل على نص كل سلسلة فقرة paratexts [] = extractor.getParagraphText () ؛ لـ (int i = 0 ؛ i <paratexts.length ؛ i ++) {system.out.println ("paragraph" + (i + 1) + ":" + paratexts [i]) ؛ } // إخراج بعض المعلومات حول كلمة printinfo الحالية (extractor.getSummaryInformation ()) ؛ // إخراج بعض المعلومات حول الكلمة الحالية this.printinfo (extractor.getDocSummaryInformation ()) ؛ this.closestream (IS) ؛ } /** * الإخراج summaryInfomation * param info * /private void printInfo (info summaryInformation) {// uptor system.out.println (info.getauthor ()) ؛ // statistics system.out.println (info.getCharCount ()) ؛ // عدد الصفحات system.out.println (info.getPageCount ()) ؛ // title system.out.println (info.getTitle ()) ؛ // موضوع system.out.println (info.getSubject ()) ؛ } /** * documentsummaryinfomation * param info * /private void printinfo (documentSummaryInformation info) {// category system.out.println (info.getCategory ()) ؛ // Company System.out.println (info.getCompany ()) ؛ } / *** إغلاق دفق الإدخال* param هو* / private void letroseReam (inputStream is) {if (is! = null) {try {iS.Close () ؛ } catch (ioException e) {E.PrintStackTrace () ؛ }}}}1.2 اقرأ الملفات من خلال hwpfdocument
HWPFDOCUMENT هي ممثل لمستندات الكلمات الحالية ووظائفها أقوى من WordExtractor. من خلال ذلك ، يمكننا قراءة الجداول والقوائم وما إلى ذلك في المستند ، ويمكننا أيضًا إضافة وتعديل وحذف محتوى المستند. إنه فقط بعد الانتهاء من هذه الإضافات والتعديلات والحذف الجديدة ، يتم حفظ المعلومات ذات الصلة في HWPFDOCUMITY ، مما يعني أن ما قمنا بتغييره هو HWPFDOCUMITY ، وليس الملفات الموجودة على القرص. إذا كنا نريد أن تدخل هذه التعديلات سارية المفعول ، فيمكننا استدعاء طريقة الكتابة لـ HWPFDOCUMBENT لإخراج HWPFDOCUMITY المعدل إلى دفق الإخراج المحدد. يمكن أن يكون هذا دفق الإخراج للملف الأصلي ، أو دفق الإخراج للملف الجديد (يعادل حفظ AS) أو تدفقات الإخراج الأخرى. فيما يلي مثال على قراءة ملف من خلال hwpfdocument:
الفئة العامة hwpftest {test public void testReadByDoc () يلقي استثناء {inputStream هو = جديد fileInputStream ("d: //test.doc") ؛ hwpfdocument doc = new hwpfdocument (IS) ؛ // الإخراج معلومات إشارة مرجعية this.printinfo (doc.getBookmarks ()) ؛ // output text system.out.println (doc.getDocumentText ()) ؛ المدى = doc.getRange () ؛ // this.insertinfo (المدى) ؛ this.printinfo (المدى) ؛ // اقرأ الجدول this.readtable (المدى) ؛ // قراءة القائمة this.readlist (المدى) ؛ // حذف نطاق النطاق r = نطاق جديد (2 ، 5 ، doc) ؛ R.Delete () ؛ // حذف في الذاكرة ، إذا كنت بحاجة إلى حفظه في ملف ، فأنت بحاجة إلى كتابته مرة أخرى إلى الملف // اكتب hwpfdocument الحالي إلى Doc.write دفق الإخراج (FileOutputStream جديد ("d: //test.doc")) ؛ this.closestream (IS) ؛ } / *** أغلق دفق الإدخال* param هو* / private void levestream (inputStream is) {if (is! = null) {try {iS.Close () ؛ } catch (ioException e) {E.PrintStackTrace () ؛ }}} / *** معلومات الإشارة الإخراج* @Param Lundmarks* / private void printInfo (مرجعية مرجعية) {int count = parkmarks.getBookMarksCount () ؛ System.out.println ("عدد الإشارات المرجعية:" + العد) ؛ المرجعية المرجعية ؛ لـ (int i = 0 ؛ i <count ؛ i ++) {bookmark = lookmarks.getBookmark (i) ؛ System.out.println ("bookmark" + (i + 1) + "الاسم هو:" + bookmark.getName ()) ؛ System.out.println ("Start Position:" + bookmark.getStart ()) ؛ System.out.println ("End Position:" + bookmark.getend ()) ؛ }} /*** اقرأ الجدول* تمثل كل عودة عربة الفقرة ، لذلك بالنسبة للجدول ، تحتوي كل خلية على فقرة واحدة على الأقل ، وينتهي كل صف بفقرة. * @param range */private void readtable (المدى) {// نقل الجدول ضمن نطاق النطاق. TableIratorator TableIter = New TableIrator (المدى) ؛ جدول الجدول صف TableRow خلية المائدة بينما (tableIter.hasNext ()) {table = tableIter.next () ؛ int rownum = table.numrows () ؛ لـ (int j = 0 ؛ j <rownum ؛ j ++) {row = table.getRow (j) ؛ int cellnum = row.numcells () ؛ لـ (int k = 0 ؛ k <cellnum ؛ k ++) {cell = row.getCell (k) ؛ // إخراج نص خلية system.out.println (cell.text (). trim ()) ؛ }}}}} / *** قائمة القراءة* param Range* / private void readlist (نطاق النطاق) {int num = range.numparaphs () ؛ الفقرة. لـ (int i = 0 ؛ i <num ؛ i ++) {para = range.getParagraph (i) ؛ if (para.isinList ()) {system.out.println ("list:" + para.text ()) ؛ }}} /** * نطاق الإخراج * param range * /private void printinfo (نطاق النطاق) {// احصل على عدد الفقرات int paranum = range.numparaphs () ؛ system.out.println (paranum) ؛ لـ (int i = 0 ؛ i <paranum ؛ i ++) {// this.insertinfo (range.getParagraph (i)) ؛ System.out.println ("Paragraph" + (i + 1) + ":" + range.getParagraph (i) .text ()) ؛ if (i == (paranum-1)) {this.insertinfo (range.getParagraph (i)) ؛ }} int secnum = range.numsections () ؛ System.out.println (Secnum) ؛ قسم القسم ؛ لـ (int i = 0 ؛ i <secnum ؛ i ++) {section = range.getSection (i) ؛ system.out.println (section.getMarginleft ()) ؛ system.out.println (section.getMarginRight ()) ؛ system.out.println (section.getMarginRight ()) ؛ System.out.println (section.getMargintop ()) ؛ system.out.println (section.getMarginBottom ()) ؛ System.out.println (section.getPageHeight ()) ؛ system.out.println (section.text ()) ؛ }} / *** أدخل المحتوى في النطاق ، سيتم كتابته فقط في Memory* param Range* / private void insertinfo (Range Range) {Range.insertafter ("Hello") ؛ }}2 اكتب ملف DOC Word
عند كتابة ملفات Word Doc باستخدام POI ، يجب أن يكون لدينا أولاً ملف DOC ، لأنه عندما نكتب ملفات DOC ، فإننا نكتبها من خلال HWPFDOCUMITY ، ويجب إرفاق HWPFDOCUMPHING بملف مستند. لذا فإن الطريقة المعتادة هي إعداد ملف DOC أولاً بمحتوى فارغ على القرص الثابت ، ثم إنشاء HWPFDOCUMITY استنادًا إلى الملف الفارغ. بعد ذلك ، يمكننا إضافة محتوى جديد إلى HWPFDocument ثم كتابته إلى ملف مستند آخر. هذا يعادل استخدام POI لإنشاء ملف DOC Word.
في التطبيقات الفعلية ، عندما ننشئ ملفات الكلمات ، ننشئ نوعًا معينًا من الملفات. تم إصلاح تنسيق هذا النوع من الملف ، ولكن بعض الحقول مختلفة. لذلك في التطبيقات العملية ، لا يتعين علينا إنشاء محتوى ملف الكلمة بأكمله من خلال HWPFDocument. بدلاً من ذلك ، قم بإنشاء مستند Word جديد على القرص ، ومحتوىه هو محتوى ملف Word الذي نحتاج إلى إنشاءه ، ثم استخدام طريقة مشابهة لـ "$ {paramname}" لاستبدال بعض المحتويات التي تنتمي إلى المتغيرات. وبهذه الطريقة ، عندما نقوم بإنشاء ملف كلمة بناءً على معلومات معينة ، نحتاج فقط إلى الحصول على HWPFDOCUMITY استنادًا إلى ملف WORD ، ثم استدعاء طريقة REPLICETEXT () من النطاق لاستبدال المتغير المقابل بالقيمة المقابلة ، ثم كتابة HWPFDOCINGUME الحالية إلى دفق الإخراج الجديد. يتم استخدام هذه الطريقة بشكل متكرر في التطبيقات العملية لأنها لا يمكنها تقليل عبء العمل لدينا فحسب ، بل تجعل تنسيق النص أكثر وضوحًا أيضًا. دعنا نقدم مثالاً بناءً على هذه الطريقة.
لنفترض أن لدينا الآن بعض المعلومات المتغيرة ، ثم نحتاج إلى إنشاء ملف DOC Word بالتنسيق التالي من خلال هذه المعلومات:
وفقًا للوصف أعلاه ، فإن الخطوة الأولى هي إنشاء ملف DOC بالتنسيق المقابل كقالب ، ومحتوىه كما يلي:
باستخدام مثل هذا القالب ، يمكننا إنشاء HWPFDOCUMITY المقابل ، ثم استبدل المتغير المقابل بالقيمة المقابلة ، ثم إخراج HWPFDOCUMENT إلى دفق الإخراج المقابل. أدناه هو الرمز المقابل.
الفئة العامة HWPFTEST {test public void testWrite () يلقي استثناء {String templatepath = "d: //word//template.doc" ؛ inputStream هو = جديد fileInputStream (templatepath) ؛ hwpfdocument doc = new hwpfdocument (IS) ؛ النطاق المدى = doc.getRange () ؛ // استبدل $ {reportDate} في النطاق النطاق بمدى التاريخ الحالي. replacetext ("$ {reportDate}" ، new SimpleateFormat ("Yyyy-MM-DD"). Format (New Date ())) ؛ range.replacetext ("$ {appleamt}" ، "100.00") ؛ range.replacetext ("$ {bananaamt}" ، "200.00") ؛ Range.Replacetext ("$ {totalamt}" ، "300.00") ؛ OutputStream OS = جديد fileOutputStream ("d: //word/write.doc") ؛ // تصدير المستند إلى Doc.write (OS) ؛ this.closestream (OS) ؛ this.closestream (IS) ؛ } / *** إغلاق دفق الإدخال* param هو* / private void letroseReam (inputStream is) {if (is! = null) {try {iS.Close () ؛ } catch (ioException e) {E.PrintStackTrace () ؛ }}} / *** أغلق دفق الإخراج* param os* / private void letroseReam (OutputSream OS) {if (os! = null) {try {os.close () ؛ } catch (ioException e) {E.PrintStackTrace () ؛ }}}}}(ملاحظة: تستند هذه المقالة إلى POI3.9)
شكرا لك على القراءة ، آمل أن تساعدك. شكرا لك على دعمك لهذا الموقع!