Introduction
Some time ago I had to write a C# application that was able to convert documents into various formats. The hardest part was to find a way to create PDF files without the use of any third party products. Here is a solution.
Background
The source you see is out of a larger conversion-application. It is a "stand alone" projects, for educational use and describes a possible way of converting documents. I took me a lot of work to figure this out, so please don't copy the code; drop me a line if you wish to use a part of it. My comments are written in German, I had no time to build a proper release, sorry for that.
Using the code
The code listed below describes the main part of the program. I will give you a brief look, at the idea behind. Crystal reports (the .NET reporting system) is able to create PDF files. The only problem is it can only create PDF files out of a database. It requires an ole objects in the Database. But if you have a (very) close look at CR (IDA :-) ) you will find out that it is able to process, bmp, emf, and wmf. So we only have to insert this kind of data in to a table (as blob) and hand it over to CR. Emf can be created by using PowerPoint, PPT can read html, WinWord can create html. The only problem left is the organization of our pages, we have to split the document manually, I did this by using a Richtextbox.
Now that we know the Way we can convert a rtf into a PDF:
- We load the rtf into a richtextbox.
- We split in into parts. every part is loaded into WinWord, saved as html, the WinWord header is being destroyed, the html page is loaded into PowerPoint and saved as emf. The emf file is written into a Access database as a blob object.
- Crystal Reports gets a rpt "template" the database the report is being created and saved as PDF.
I tried to use Ole32 functions, but I didn't find a way to accomplish this, if you know a way in C#.NET please let me know.
private static void DoRTF2ALL(
CrystalDecisions.Shared.ExportFormatType outTp)
{
int lastsplit = 0;
int nextsplit = 0;
int pageheight= 650;
int pcount= 1;
Point xx;
object Unknown =Type.Missing;
Word.Application newApp;
PowerPoint.Application app;
PowerPoint.Presentation ppp;
string[] TempEnt;
RichTextBox rtf = new RichTextBox();
rtf.Height=25000;
rtf.Width=4048;
rtf.LoadFile(scrfile, RichTextBoxStreamType.RichText);
nCoreHlp.EmptyDB(WorkDir + "\\" + Database);
while ((lastsplit+1)<rtf.Text.Length) {
rtf.SelectionStart = 0;
rtf.SelectionLength =lastsplit;
rtf.Cut();
for (int r=0;r<=rtf.Text.Length;r++) {
xx = rtf.GetPositionFromCharIndex(r);
nextsplit = rtf.Text.Length;
if (int.Parse(xx.Y.ToString()) > pageheight)
{nextsplit=r-1;r=rtf.Text.Length;}
}
lastsplit=lastsplit+nextsplit;
rtf.SelectionStart = nextsplit;
rtf.SelectionLength =rtf.Text.Length-nextsplit;
rtf.Cut();
rtf.SaveFile(WorkDir + \\temp.rtf,
RichTextBoxStreamType.RichText);
newApp = new Word.Application();
newApp.Visible = false;
object Source=WorkDir + "\\temp.rtf";
object Target=WorkDir + "\\temp.html";
newApp.Documents.Open(ref Source,ref Unknown,
ref Unknown,ref Unknown,ref Unknown,
ref Unknown,ref Unknown,ref Unknown,
ref Unknown,ref Unknown,ref Unknown,
ref Unknown,ref Unknown,ref Unknown,ref Unknown);
object format = Word.WdSaveFormat.wdFormatHTML;
newApp.ActiveDocument.SaveAs(ref Target,ref format,
ref Unknown,ref Unknown,ref Unknown,
ref Unknown,ref Unknown,ref Unknown,
ref Unknown,ref Unknown,ref Unknown,
ref Unknown,ref Unknown,ref Unknown,
ref Unknown,ref Unknown);
newApp.Quit(ref Unknown,ref Unknown,ref Unknown);
StreamReader sr;
bool not=true;
while (not)
{
try
{
sr = new StreamReader(WorkDir + "\\temp.html");
not=false;
StreamWriter sw = new StreamWriter(WorkDir + "\\temp.txt");
String line;
while ((line = sr.ReadLine()) != null)
{
if (line.CompareTo(
"<meta name=ProgId content=FrontPage.Editor.Document>")!=0)
sw.WriteLine(line); else
sw.WriteLine("<meta name=ProgId content=Word.Documens>");
}
sr.Close();
sw.Flush();
sw.Close();
}
catch (Exception e){e=e;}
}
File.Delete(WorkDir + "\\temp.html");
File.Move(WorkDir + "\\temp.txt", WorkDir + "\\temp.html");
app = new PowerPoint.Application();
ppp = app.Presentations.Open(WorkDir + "\\temp.html",
0,
0,
Microsoft.Office.Core.MsoTriState.msoFalse);
ppp.SaveAs(WorkDir + "\\temp",
PowerPoint.PpSaveAsFileType.ppSaveAsEMF,
Microsoft.Office.Core.MsoTriState.msoFalse);
app.Quit();
TempEnt = Directory.GetFiles(WorkDir + "\\temp\\", "*.emf");
nCoreHlp.InsertDB1(WorkDir + "\\" + Database,TempEnt[0],pcount);
pcount++;
Console.WriteLine("1 Page Converted");
rtf.LoadFile(scrfile, RichTextBoxStreamType.RichText);
} ReportDocument doc = new ReportDocument();
doc.Load(WorkDir + "\\DtoD.rpt");
doc.Database.Tables[0].Location = (WorkDir + "\\DtoD.mdb");
doc.ExportOptions.ExportFormatType = outTp;
doc.ExportOptions.ExportDestinationType =
ExportDestinationType.DiskFile;
DiskFileDestinationOptions diskOpts = new DiskFileDestinationOptions();
diskOpts.DiskFileName = dstfile;
doc.ExportOptions.DestinationOptions = diskOpts;
doc.Export();
doc.Close();
Directory.Delete(WorkDir + "\\temp\\", true);
File.Delete(WorkDir + "\\temp.rtf");
File.Delete(WorkDir + "\\temp.html");
}
Points of Interest
MS-Office 2000 or < has to be installed. I included the Word & PowerPoint interfaces in the project , the C# dlls are only in the bin/debug directory, because of the file size.
History
- 1st version of the demo project.
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.