Replacing the Styles Parts in Word 2010 Documents by Using the Open XML SDK 2.0
Summary: Use the strongly typed classes in the Open XML SDK 2.0 to replace the styles in a Word document with an XDocument instance that contains the styles or stylesWithEffects part from a Microsoft Word document, without loading the document into Word.
Applies to: Microsoft Office 2010 | Visual Studio 2010 | 2007 Microsoft Office system
Published: February 2011
Provided by: Ken Getz, MCW Technologies, LLC
The Open XML file formats make it possible to retrieve and modify blocks of content from Word documents, but doing so requires some effort. The Open XML SDK 2.0 adds strongly typed classes that simplify access to the Open XML file formats. The SDK simplifies the tasks of retrieving and replacing, for example, an XDocument instance that contains the document styles or stylesWithEffects part. Given the XML content, you could archive the information, modify and reapply it, or apply it to a new document. The code sample included with this Visual How To shows how to the use the SDK to replace the styles or stylesWithEffects part, assuming that you know how to retrieve the part from an existing document. For more information about how to retrieve the styles or stylesWithEffects part from a Word document, see Extracting Styles from Word 2010 Documents by Using the Open XML SDK 2.0.
The sample provided with this Visual How To includes the code necessary to replace the styles or styleWithEffects part in a document, given an XDocument instance that contains the same part for a Word 2007 or Word 2010 document. The sample code includes the procedure that retrieves the part as an XDocument instance, as well, but this Visual How To assumes that you know how to do that The following sections describe the code in detail. Be aware that, for a document created in Word 2007, there will only be a single styles part; Word 2010 adds a second stylesWithEffects part. To provide for relaying a document from Word 2010 to Word 2007 and back, Word 2010 maintains both the original styles part and the new styles part. The Open XML specification requires that Microsoft Word disregard any parts that it does not recognize; Word 2007 does not recognize the stylesWithEffects part that Word 2010 adds to the document. This code example shows how to extract and replace both parts, although the code is effectively the same for both parts. The sample code replaces both style parts with the style information in the specified XDocument.
Setting Up References
To use the code from the Open XML SDK 2.0, you must add a few references to your project. The sample project already includes these references, but in your own code, you must explicitly reference the following assemblies:
Also, include the following using/Imports statements at the top of the code file.
Examining the Procedure
Public Sub WDReplaceStyles( ByVal fileName As String, ByVal newStyles As XDocument, Optional ByVal setStylesWithEffectsPart As Boolean = True) )
The procedure examines the document you specify, looking for the styles with effects (or the previous styles) part. If the requested styles part exists, the procedure saves the supplied XDocument into the selected styles part. To call the procedure, pass the required parameter values, as shown in the example code. To use the sample code, provide documents named C:\temp\StylesFrom.docx and C:\temp\StylesTo.docx. The StylesFrom document should contain some specific style information (it may contain modified versions of the built-in styles Header 1, Header 2, and so on) which the example can copy into the StylesTo document. The sample relies on the WDExtractStyles procedure that is included in the sample code. This procedure also allows you to select whether you want to extra the stylesWithEffects part, or the older styles part.
Private Const fromDoc As String = "C:\Temp\StylesFrom.docx" Private Const toDoc As String = "C:\Temp\StylesTo.docx" Dim node = WDExtractStyles("C:\temp\StylesFrom.docx", True) If node IsNot Nothing Then WDReplaceStyles("c:\temp\StylesTo.docx", node, True) End If
The sample code calls this same procedure twice; once for each of the styles parts. If you pass in a Word 2007 document that does not contain a stylesWithEffects part, the code drops out without attempting to extract or replace the part.
Accessing the Document
The code starts by opening the document, using the WordprocessingDocument.Open method and indicating that the document should be open for read/write access (the final true parameter). Given the open document, the code uses the MainDocumentPart property to navigate to the main document, and then prepares a variable named stylesPart to hold a reference to the styles part.
Using document = WordprocessingDocument.Open(fileName, True) Dim docPart = document.MainDocumentPart Dim stylesPart As StylesPart = Nothing ' Code removed here… End Using
Finding the Correct Styles Part
The code next retrieves a reference to the requested styles part, using the setStylesWithEffectsPart boolean parameter. Based on this value, the code retrieves a specific property of the docPart variable, and stores it in the stylesPart variable.
If setStylesWithEffectsPart Then stylesPart = docPart.StylesWithEffectsPart Else stylesPart = docPart.StyleDefinitionsPart End If
Saving the Part Contents
Assuming that the style part exists, the code must save the entire contents of the XDocument passed to the procedure to the style part. Each part provides a GetStream method, which returns a Stream. The code passes the Stream instance to the constructor of the StreamWriter class, creating a stream writer around the part stream. Finally, the code calls the Save method of the XDocument parameter, saving its contents into the styles part (this sequence of steps is quite common when working with XDocuments and Open XML parts─you will see it used often).
If stylesPart IsNot Nothing Then newStyles.Save(New StreamWriter( stylesPart.GetStream(FileMode.Create, FileAccess.Write))) End If If stylesPart IsNot Nothing Then Using reader = XmlNodeReader.Create( stylesPart.GetStream(FileMode.Open, FileAccess.Read)) ' Create the XDocument: styles = XDocument.Load(reader) End Using End If
The following code example contains the complete sample procedure.
Public Sub WDReplaceStyles( ByVal fileName As String, ByVal newStyles As XDocument, Optional ByVal setStylesWithEffectsPart As Boolean = True) Using document = WordprocessingDocument.Open(fileName, True) Dim docPart = document.MainDocumentPart Dim stylesPart As StylesPart = Nothing If setStylesWithEffectsPart Then stylesPart = docPart.StylesWithEffectsPart Else stylesPart = docPart.StyleDefinitionsPart End If If stylesPart IsNot Nothing Then newStyles.Save(New StreamWriter( stylesPart.GetStream(FileMode.Create, FileAccess.Write))) End If End Using End Sub
The sample included with this Visual How To demonstrates code that retrieves the two styles parts from a Word document and saves the information into the styles parts of a second document. To use the sample, install the Open XML SDK 2.0, available from the link listed in the Explore It section. The sample also uses a modified version of code included as part of a set of code snippets for the Open XML SDK 2.0. The Explore It section also includes a link to the full set of snippets, although you can use the sample without downloading and installing the snippets.
If you run the sample code in this Visual How To, starting with a source document that contains specific styles, you should find that those styles appear in the output document after running the code. This technique allows you to create a library of styles that you could apply to documents. Normally, you might use this technique to modify document templates, because if you are using Word styles, you most likely base your documents on particular templates that define their styles. Whether you apply the style to the template or to the document directly, using this technique allows you to modify the styles without needing to open the document in Microsoft Word.
The sample application demonstrates only a handful of the available properties and methods provided by the Open XML SDK 2.0 that you can interact with when modifying document structure. For more information, investigate the documentation included with the Open XML SDK 2.0 Productivity Tool: Click the Open XML SDK Documentation tab in the lower-left corner of the application window, and search for the class you need to study. Although the documentation does not always include code examples, given the sample shown here and the documentation, you should be able to successfully modify the sample application.
Watch the video
About the Author