Autor Beitrag
lapadula
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 180
Erhaltene Danke: 10



BeitragVerfasst: Di 18.04.17 21:08 
Guten Abend,

ich versuche mich gerade an iTextSharp. Ich möchte eine PDF-Datei erstellen, diese mit einwenig Text füllen und dann den Text markieren.

Es klappt alles soweit nur beim markieren, da versuche ich die PDF-Datei zu öffnen, jedoch taucht eine Exception auf, die besagt, dass auf diese Datei bereits zugegriffen wird.

Den FileStream habe ich versucht selber zu schließen und nun mit der using-Anweisung. Ich benutze diese zum ersten Mal und wollte fragen ob folgender Code üblich ist:

ausblenden C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
private void button2_Click(object sender, EventArgs e)
        {
            using (FileStream fs = new FileStream(@"C:\Users\pc\Desktop\forerunner.pdf", FileMode.Create, FileAccess.Write, FileShare.None))
            {
                using (Document doc = new Document())
                {
                    using (PdfWriter writer = PdfWriter.GetInstance(doc, fs))
                    {
                        doc.Open();
                        doc.Add(new Paragraph("Hello World"));
                    }
                }
                
            }
        }


Und meine zweite Frage wäre, warum die Datei trotzdem nicht geöffnet werden kann?

Hier der Komplette Code:

ausblenden volle Höhe C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
29:
30:
31:
32:
33:
34:
35:
36:
37:
38:
39:
40:
41:
42:
43:
44:
45:
46:
47:
48:
49:
50:
51:
52:
53:
54:
55:
56:
57:
58:
59:
60:
61:
62:
63:
64:
65:
66:
67:
68:
69:
70:
71:
72:
73:
74:
75:
76:
77:
78:
79:
80:
81:
82:
83:
using System;
using System.Windows.Forms;
using iTextSharp.text;
using iTextSharp.text.pdf;
using System.IO;
using iTextSharp.text.pdf.parser;
using System.Collections.Generic;
using System.Diagnostics;
using System.Net;

namespace TextSharp
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            try
            {
                GetPageNumber();
            }
            catch (Exception Ex)
            {
                MessageBox.Show(Ex.ToString());
            }
           
        }

        public void GetPageNumber()
        {
            string searchWord = textBox1.Text;

            //Process p = new Process();
            //p.StartInfo.FileName = @"C:\Users\pc\Desktop\forerunner.pdf";
            //p.Start();


            string strFileNameTextBox = System.IO.Path.GetFileName(@"C:\Users\pc\Desktop\forerunner.pdf");

            List<int> PageNumbers = Helper.ReadPdfFile(@"C:\Users\pc\Desktop\forerunner.pdf", searchWord);

            comboBox1.Items.Clear();
            foreach (int i in PageNumbers)
            {
                comboBox1.Items.Add(i);
            }
        }

        private void button2_Click(object sender, EventArgs e)
        {
            using (FileStream fs = new FileStream(@"C:\Users\pc\Desktop\forerunner.pdf", FileMode.Create, FileAccess.Write, FileShare.None))
            {
                using (Document doc = new Document())
                {
                    using (PdfWriter writer = PdfWriter.GetInstance(doc, fs))
                    {
                        doc.Open();
                        doc.Add(new Paragraph("Hello World"));
                    }
                }
                
            }
        }

        private void button3_Click(object sender, EventArgs e)
        {
            PdfReader pdfReader = new PdfReader(@"C:\Users\pc\Desktop\forerunner.pdf");
            PdfStamper pdfStamper = new PdfStamper(pdfReader, new FileStream(@"C:\Users\pc\Desktop\forerunner.pdf", FileMode.Create, FileAccess.Write, FileShare.None));

            PdfContentByte canvas = pdfStamper.GetUnderContent(1);
            canvas.SetColorFill(BaseColor.YELLOW);
            canvas.Rectangle(367866616);
            canvas.Fill();
            canvas.RestoreState();
            pdfStamper.Close();
            pdfReader.Close();
        }
    }
}


Edit: Ok die using-Anweisung zu verschachteln war keine Gute Idee. Nun habe ich den FileStream mittelns .Close() wieder geschlossen, reicht das nicht?


Moderiert von user profile iconChristian S.: Topic aus Basistechnologien verschoben am Di 18.04.2017 um 21:26
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4700
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Di 18.04.17 21:32 
Ohne ITextSharp jetzt genau zu kennen sieht das Handling mit dem using richtig aus. So sollte es funktioniren (wenn innerhalb von ITextSharp es halbwegs normal programmiert ist).

Was passiert in Helper.ReadPdfFile? Sieht auch nach einer Fileoperation auf dem File aus.

Für diesen Beitrag haben gedankt: lapadula
Frühlingsrolle
Ehemaliges Mitglied
Erhaltene Danke: 1



BeitragVerfasst: Di 18.04.17 22:03 
- Nachträglich durch die Entwickler-Ecke gelöscht -

Für diesen Beitrag haben gedankt: lapadula
lapadula Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 180
Erhaltene Danke: 10



BeitragVerfasst: Di 18.04.17 22:22 
In der Klasse Helper befindet sich nur die statische Methode ReadPdfFiles:

Wirft dann eine List<int> mit den SeitenNr. zurück, wo das zu suchende Wort gefunden wurde.

ausblenden C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
public static List<int> ReadPdfFile(string fileName, String searthText)
        {
            List<int> pages = new List<int>();
            if (File.Exists(fileName))
            {
                PdfReader pdfReader = new PdfReader(fileName);
                for (int page = 1; page <= pdfReader.NumberOfPages; page++)
                {
                    ITextExtractionStrategy strategy = new SimpleTextExtractionStrategy();

                    string currentPageText = PdfTextExtractor.GetTextFromPage(pdfReader, page, strategy);
                    if (currentPageText.Contains(searthText))
                    {
                        pages.Add(page);
                    }
                }
                pdfReader.Close();
            }
            return pages;
        }


Wenn ich meine using-Verschachtelung so lasse, tritt eine ObjectDisposedException auf.("Auf eine geschlossene Datei kann nicht zugegriffen werden").

Ohne using: Ich klicke zuerst auf button2, da wird die PDF erstellt und mit Inhalt gefüllt und auf button3 soll dann der Text markiert werden, in der 77. Zeile tritt dann die besagte Exception auf.

An iTextSharp sollte es eig. nicht liegen.
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4700
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Di 18.04.17 22:41 
Ich vermute der PDFWriter schließt den Stream schon selber und ein folgendes schließen des Streams knallt dann(soviel zu sauber programmiert ;) ). Ruf mal writer.CloseStream = false; vor doc.Open(); auf.
Nach Codeanalyse auf github (heißt ich habe es nicht ausprobiert) sollte das helfen.

Für diesen Beitrag haben gedankt: lapadula
Frühlingsrolle
Ehemaliges Mitglied
Erhaltene Danke: 1



BeitragVerfasst: Mi 19.04.17 03:16 
- Nachträglich durch die Entwickler-Ecke gelöscht -

Für diesen Beitrag haben gedankt: lapadula
lapadula Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 180
Erhaltene Danke: 10



BeitragVerfasst: Mi 19.04.17 18:10 
Ahso daran lag das also, danke!

Man kann also die PDFs nicht wirklich "bearbeiten", sondern man müsste die alte PDF im Anschluss löschen, verstehe ich das richtig?
Frühlingsrolle
Ehemaliges Mitglied
Erhaltene Danke: 1



BeitragVerfasst: Mi 19.04.17 22:53 
- Nachträglich durch die Entwickler-Ecke gelöscht -

Für diesen Beitrag haben gedankt: lapadula
lapadula Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 180
Erhaltene Danke: 10



BeitragVerfasst: Do 20.04.17 20:10 
Ok das ist soweit klar aber ich kann nicht die Datei lesen und gleichzeitig etwas reinschreiben. Bei Office scheint es genauso zu sein, dort wird ja auch eine temp Datei erstellt.

Es gäbe noch die Möglichkeit die Datei in ein byte Array zu lesen aber da besteht das Risiko bei einer Exception die temp-Datei und die Originale Datei zu verlieren.
Frühlingsrolle
Ehemaliges Mitglied
Erhaltene Danke: 1



BeitragVerfasst: Do 20.04.17 21:39 
- Nachträglich durch die Entwickler-Ecke gelöscht -

Für diesen Beitrag haben gedankt: lapadula
lapadula Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 180
Erhaltene Danke: 10



BeitragVerfasst: Do 20.04.17 23:37 
Okay das funktioniert tatsächlich :D

Hab mich darüber auf stackoverflow informiert und dort hieß es, es sei ohne eine temp-Datei oder byte array nicht möglich.

Vielen Dank für die Infos
Frühlingsrolle
Ehemaliges Mitglied
Erhaltene Danke: 1



BeitragVerfasst: Fr 21.04.17 00:56 
- Nachträglich durch die Entwickler-Ecke gelöscht -

Für diesen Beitrag haben gedankt: lapadula