Using the SDK I'm building Word documents that contain reports. These documents need to have TOC. Does anybody have a complete solution that I can follow in order to understand how to do this?
(I've read everything on http://openxmldeveloper.org/)
Using the SDK I'm building Word documents that contain reports. These documents need to have TOC. Does anybody have a complete solution that I can follow in order to understand how to do this?
(I've read everything on http://openxmldeveloper.org/)
Have a look at Fourth and Final Screen-Cast in Series on Adding/Updating the TOC in OpenXML WordprocessingML Documents by Eric White.
Hope that helps!
UPDATE:
According FAQ from MSDN Forums I see that this feature is not supported:
8) How to generate TOC (table of contents) in Word document?
Open XML SDK 2.0 does not have this feature supported. But you can generate a small TOC through Word app, and reflect the TOC parts with Document Reflector component in Open XML SDK Productivity Tool to see how to generate a TOC programmatically. For more detailed information, please refer to:
MSDN forum thread: Generating Table of Contents and Applying a Custom Style,
MSDN forum thread: How can i Create dir for word document.
UPDATE 2
Based on our comments below I could propose to use this scenario:
All of that look a bit tricky, but I hope that helps.
Thanks to Dmitri Pavlov (@DmitryPavlov) for the help.
I don't want to give an answer to my own question, but this is just to illustrate the steps that I’ve taken.
The advice for anyone interested is to watch the 5-part screen-cast by Eric White - Exploring Tables-of-Contents in Open XML WordprocessingML Documents. This has all the info with respect to adding and updating a TOC (am much more).
My solution was to use a Template (just a regular empty document that had styles for everything I needed: Header 1-5, TOC style, etc.). This is particularly useful as a quick fix for the styles issue (the new document, that has the TOC, will have a new style.xml created; this file has some additional data; as a result the hierarchy in the TOC isn’t as expected – i.e., header 2 is the child of header 1, header 3 is a child of header 2, etc.).
Therefore:
Create a Word document and add all the elements that you expect to be added later programmatically (e.g., Header 1-5, Table of Contents, etc.). Delete all the contents and save the document (the reason for this is to create styles for all the necessary elements).
I personally added the template (the file created at step #1) as a resource in my project.
In your code, create a new copy of the template (this will be the actual file that you will work on). I used:
byte[] stream = Properties.Resources.Template;
File.WriteAllBytes(@"D:\Template.docx", stream);
File.Copy(@"D:\Template.docx", @"D:\New.docx");
Flush all the data to this document.
Add the source files from screen-cast 2, 3 or 4 to your project (for this please see screen-cast 3) - at the end of those posts you will find a link to download TocAdder.zip. Or just add a reference to TocAdder.dll.
Insert the TOC. Just an example:
using (WordprocessingDocument wdoc = WordprocessingDocument.Open(@"D:\New.docx", true))
{
XElement firstPara = wdoc
.MainDocumentPart
.GetXDocument()
.Descendants(W.p)
.FirstOrDefault();
TocAdder.AddToc(wdoc, firstPara,
@"TOC \o '1-3' \h \z \u", null, null);
}
Replace the styles in the newly created document with the ones from the template. You can use this resource from MSDN: Replacing the Styles Parts in Word 2010 Documents by Using the Open XML SDK 2.0. Again, an example:
string fromDoc = @"D:\Template.docx";
string toDoc = @"D:\New.docx";
var node = WDExtractStyles(fromDoc, false);
if (node != null)
WDReplaceStyles(toDoc, node, false);
node = WDExtractStyles(fromDoc);
if (node != null)
WDReplaceStyles(toDoc, node);
Optionally use one of the methods described in screen-cast 3, 4 or 5 in order to get around the problem with the modal dialog box that Word puts up.
Hope this will be useful for somebody.