Article by Sheela E.N, Sonata Software Limited
This article explains on how to create WordProcessingML document using LINQ to XML and Open XML SDK April 2008 CTP in Visual Studio 2008 C# project.
1. Create a C # windows project; add a reference to openxml dll
· In the Add Reference dialog box, click the .NET tab.
· Scroll to the Microsoft.Office.DocumentFormat.OpenXml option, select it, and then click OK.
· In the Add Reference dialog box, click the Browse tab.
· Select WindowsBase.dll from C:\Program Files\Reference Assemblies\Microsoft\Framework\v3.0
2. Import the namespace to refer to the Open XML SDK and LINQ to XML
using Microsoft.Office.DocumentFormat.OpenXml.Packaging;
using Microsoft.Office.DocumentFormat.OpenXml;
using System.Xml.Linq;
3. Declare local variables to store namespace for wordprocessing, drawingml, picture etc
XNamespace r = "http://schemas.openxmlformats.org/officeDocument/2006/relationships";
XNamespace wp = "http://schemas.openxmlformats.org/drawingml/2006/wordprocessingDrawing";
XNamespace w = "http://schemas.openxmlformats.org/wordprocessingml/2006/main";
XNamespace dml = "http://schemas.openxmlformats.org/drawingml/2006/main";
XNamespace dp = "http://schemas.openxmlformats.org/drawingml/2006/picture";
4. Create WordProcessingML document using Open XML SDK and add a main part
WordprocessingDocument doc = WordprocessingDocument.Create(filepath,WordprocessingDocumentType.Document);
MainDocumentPart mainPart = doc.AddMainDocumentPart();
5. Retrieve the text from the textbox control placed on the form and get each paragraph.
string content = textBox1.Text;
string[] _SplitStr = content.Split('\n');
6. Create document and body element for WordprocessingML‘s main document part (document.xml by default) using LINQ to XML
XElement document = new XElement(w.GetName("document"), new XAttribute(XNamespace.Xmlns + "w", w.NamespaceName));
XElement body = new XElement(w.GetName("body"));
7. Create paragraph node (w:p) with run and text for each of the paragraph in the textbox’s content
for (int row = 0; row < _SplitStr.Length; row++)
{
XElement para=new XElement(w.GetName("p"),
new XElement(w.GetName("r"),
new XElement(w.GetName("t"), _SplitStr[row])));
body.Add(para);
}
8. Add content of the body element to the document created in step 6
document.Add(body);
9. To place the picture in the document, create drawing and graphic elements using LINQ to XML to refer to the image
XElement graphic = new XElement(dml.GetName("graphic"),new XAttribute(XNamespace.Xmlns + "dml", dml.NamespaceName), new XElement(dml.GetName("graphicData"),new XAttribute("uri", dp.NamespaceName), new XElement(dp.GetName("pic"),new XAttribute(XNamespace.Xmlns + "dp", dp.NamespaceName),
new XElement(dp.GetName("nvPicPr"), …….. …… ….. ….
XElement drawing = new XElement(w.GetName("drawing"),
new XElement(wp.GetName("inline"),new XElement(wp.GetName("extent"),
new XAttribute("cx", 4448175), new XAttribute("cy", 1181100)),…. ….. ….. ….
XElement picture = new XElement(w.GetName("p"), new XElement(w.GetName("r"), drawing));
10. Add the picture element to the body element created in step 6
body.Add(picture);
11. Put the entire xml into the main document part
using (XmlWriter xmlWriter = XmlWriter.Create(mainPart.GetStream()))
document.WriteTo(xmlWriter);
12. Add a new image part and add to the main document part.
ImagePart imgPart = mainPart.AddImagePart(ImagePartType.Jpeg, "rId1");
13. Read the image file and stream it into the image part
using (Stream targetStream = imgPart.GetStream())
{
using (FileStream sourceStream = new FileStream("../../image1.jpeg",
FileMode.Open, FileAccess.Read))
{
byte[] buffer = new byte[1024];
int nrBytesWritten = sourceStream.Read(buffer, 0, 1024);
while (nrBytesWritten > 0)
{
targetStream.Write(buffer, 0, nrBytesWritten);
nrBytesWritten = sourceStream.Read(buffer, 0, 1024);
}
}
}
14. Close the document handler
doc.Close();
This is a simple demo which demonstrates ease of use of OpenXML SDK April 2008 CTP and LINQ to XML to create WordprocessingML document. The example demo is attached with the article as a zip file.