Merging and appending documents- header / footer

In my application I have an option to apply a stationary to a document and save the file to PDF (or Word). I use the following code for this:

-------------

Public Shared Function MergeDocuments(WORDofPDF As String, contentDoc As Aspose.Words.Document)

Try

If File.Exists(System.Web.HttpContext.Current.Server.MapPath("templates" & WORDofPDF.ToLower & ".docx")) Then

Dim builderA As New DocumentBuilder(contentDoc)
Dim templateDoc As Document
templateDoc = New Document(System.Web.HttpContext.Current.Server.MapPath("templates" & WORDofPDF & ".docx"))

'Loop through all sections in the templateDoc document
For Each sectTemplate As Section In templateDoc.Sections
'Dim sectContent As Section = Nothing
Dim sectTemplateIndex As Integer = templateDoc.Sections.IndexOf(sectTemplate)
'Dim i As Integer
For Each sectContent As Section In contentDoc.Sections

'Remove existing headers and footers
'sectContent.ClearHeadersFooters()

'Loop throught all Headers/Footers in the templateDoc document
For Each hfB As HeaderFooter In sectTemplate.HeadersFooters

'Check whether current section from contentDoc contains
'Header/Footer with the same type as h/f from templateDoc
If sectContent.HeadersFooters(hfB.HeaderFooterType) IsNot Nothing Then
'Append content from h/f templateDoc to h/f contentDoc
For Each childB As Node In hfB.ChildNodes
'Import node
Dim childA As Node = contentDoc.ImportNode(childB, True, ImportFormatMode.KeepDifferentStyles)
'Appent node to h/f
sectContent.HeadersFooters(hfB.HeaderFooterType).AppendChild(childA)
Next
Else
'Copy whole h/f
Dim hfA As Node = contentDoc.ImportNode(hfB, True, ImportFormatMode.KeepDifferentStyles)
'Insert h/f
sectContent.HeadersFooters.Add(hfA)
End If
Next

Next

Next

contentDoc.RemoveUnusedResources()
'Save output document
Return contentDoc

Else

contentDoc.RemoveUnusedResources()
'Save output document
Return contentDoc

End If

Catch ex As Exception

'Save output document
Return contentDoc

End Try

End Function

-------------

I have one document with the stationary in it (templateDoc), this is basically a blank document with only an image in the header that spans the whole page (see attachment). Then there is one document with the actual content (contentDoc). I apply the header/footer from the templateDoc to the contentDoc. This works great, but one of my clients uses different stationary for the first page of their documents.

What I would like to do is the following: Have one templateDoc with two pages. The first page has the stationary for the first page, the second for all the other pages. If a document only has one page then it should use only the first page from the template. If the document has multiple sections, then it should still only use the stationary from the first page for the first page and the second page for the rest.

Could you tell me how I need to change the code in order to do this?

Hi Niels,

Thanks for your inquiry. HeaderFooter Class represents a container for the header or footer text of a section. In your case, I suggest you please use HeaderFirst type for the header for the first page of the section and HeaderPrimary type for Primary header, also used for odd numbered pages.

It would be great if you please share following detail here for our reference.

  • Please attach your input Word template documents (with one page and multiple pages).
  • Please attach your target Word document showing the desired behavior (with one page and multiple pages). You can use Microsoft Word to create your target Word document. I will investigate as to how you are expecting your final document be generated like.

One we have these documents, we will then provide you more information about your query along with code.

Hi Tahir,

Thank you for your quick response! I tried to do something with those page properties, but I couldn’t quite work it out, so your help is very much appreciated.

I have attached four files that should cover all possible scenarios:

Scenario 1: The template file only has one page with a stationary (template_one_stationary.docx). The header/footer from this document should be applied to all pages of the generated document (result_one_stationary.docx).

Scenario 2: The template file has two pages with a different stationary for the first and second page (template_two_stationaries.docx). The header/footer from the first page of this document should be applied to the first page of the generated document. The header/footer from the second page of this document should be applied to all the other pages, even if the document has different sections.

Does this help?

Regards,

Niels

Hi Tahir,
Thank you so much for the detailed answer, but i’m afraid I haven’t been clear enough in explaining what I am doing.
In my application lot’s of documents with content are created. These documents have no header or footer, because they are usually printed on paper that already has the logo etc. on it. Sometimes the document has to be sent by mail as PDF. In that case I want the user to be able to save the document that doesn’t have the logo and add a logo to it, then save it as PDF. The system I have now, that is based on example code from Aspose (see first message) works great.
What I understand from your example is that you start by using the template document and then add content to it, but that is not what I want (or can use). I already have a document with content and only want to add a header and footer to that document when a user choses to do so.
This is basically what happens in my program:

  1. The user uploads a template document that has a header and footer (template_one_stationary.docx OR template_two_stationaries.docx). They do this once, in the configuration.
  2. When they use the application they create lots of documents. Most of the time they only need to print this document on paper with a logo, so there are no headers or footers needed. Nothing needs to be done in this case.
  3. But now they want to save the document as PDF and mail it, but they don’t want just the blank document with text, they also want a logo etc. in it. To do this I now use the code from message 1 in this thread: the header and footer from the template are added to the document with text and is saved as PDF.

Edit: i’ve made a video to demonstrate this:
When I look at your example code, you already start with the template, but I can’t do that. What I am ultimately looking for is a change in the code I already have that does:
Check if the template document has 1 or 2 pages. If it has one then set PageSetup.DifferentFirstPageHeaderFooter to false and add the header and footer of this page to all pages of the content document. If the template document has 2 pages then set PageSetup.DifferentFirstPageHeaderFooter to true and apply the header/footer from the first page to the first page of the document and the second page to the rest of the document.
I will try to think of some code myself as well, but any more help is appreciated!

Hi Niels,

Thanks for sharing the detail.

*iflow:

If it has one then set PageSetup.DifferentFirstPageHeaderFooter to false and add the header and footer of this page to all pages of the content document.*

In this case, you need to copy the contents of header/footer from template document into target document’s header of type HeaderFooterType.HeaderPrimary.

*iflow:

If the template document has 2 pages then set PageSetup.DifferentFirstPageHeaderFooter to true and apply the header/footer from the first page to the first page of the document and the second page to the rest of the document.*

In this case, you need to copy the contents of First Page header into target document’s header of type HeaderFooterType.HeaderFirst.

For other pages of document, you need to copy the contents from template document into target document’s header of type HeaderFooterType.HeaderPrimary.

Please use following method to merge template document’s header/footer into your target document’s header/footer. Hope this helps you.

Public Shared Sub MergeHeaderFooter(srcDoc As Document, dstDoc As Document, headerType As HeaderFooterType)
For Each section As Section In dstDoc.Sections
Dim header As HeaderFooter = section.HeadersFooters(headerType)
If header Is Nothing Then
' There is no header of the specified type in the current section, create it.
header = New HeaderFooter(section.Document, headerType)
section.HeadersFooters.Add(header)
End If
For Each srcNode As Node In srcDoc.FirstSection.HeadersFooters(headerType).ChildNodes
Dim dstNode As Node = dstDoc.ImportNode(srcNode, True, ImportFormatMode.KeepSourceFormatting)
header.AppendChild(dstNode)
Next
Next
End Sub

Unfortunately I am having trouble using your example code to do what I want. I did manage to change my existing code to almost do what I want. I now use the following code:
Code Snippet

 Dim templateDoc As Document
 templateDoc = New Document(System.Web.HttpContext.Current.Server.MapPath("templates\" & WORDofPDF & ".docx"))

 If templateDoc.PageCount > 1 Then
 contentDoc.FirstSection.PageSetup.DifferentFirstPageHeaderFooter = True
 Else
 contentDoc.FirstSection.PageSetup.DifferentFirstPageHeaderFooter = False
 End If

 'Loop through all sections in the templateDoc document
 For Each sectTemplate As Section In templateDoc.Sections

 For Each sectContent As Section In contentDoc.Sections

 'Loop throught all Headers/Footers in the templateDoc document
 For Each hfB As HeaderFooter In sectTemplate.HeadersFooters

 'Check whether current section from contentDoc contains
 'Header/Footer with the same type as h/f from templateDoc
 If sectContent.HeadersFooters(hfB.HeaderFooterType) IsNot Nothing Then
 'Append content from h/f templateDoc to h/f contentDoc
 For Each childB As Node In hfB.ChildNodes
 'Import node
 Dim childA As Node = contentDoc.ImportNode(childB, True, ImportFormatMode.KeepDifferentStyles)
 'Appent node to h/f
 sectContent.HeadersFooters(hfB.HeaderFooterType).AppendChild(childA)
 Next
 Else
 'Copy whole h/f
 Dim hfA As Node = contentDoc.ImportNode(hfB, True, ImportFormatMode.KeepDifferentStyles)
 'Insert h/f
 sectContent.HeadersFooters.Add(hfA)
 End If
 Next

 Next

 Next

 contentDoc.RemoveUnusedResources()
 'Save output document
 Return contentDoc

The whole ‘section’ principle confuses me a little, so I am not sure how the above code exactly works and if there is anything I can do to improve it, but this code does what I want. If I have a template with 1 page it will apply the header of that page to all pages of the target document. If I have a template with two pages it will apply the header from the first page to the first page of the target document and the header from the second page to the rest of the pages.

So far, so good. But now I have a document that has two sections. What happens is:

Section 1: Page 1 gets headerfirst, page 2+ gets headerprimary.
Section 2: Page 1 gets headerfirst, page 2+ gets headerprimary.

This is not what I want though. Only page 1 should get headersfirst, all of the other pages should get headerprimary, even it is a new section.

Basically I don’t care about sections, I only care about pages:

If the template has a headerfirst and headerprimary then:

Page 1 = headerfirst
Page 2+ = headerprimary

If the template only has headerprimary then:

Page1+ = headerprimary
``
I think I am very close, but can't seem to get it right, so if you could help me some more I would really appreciate it.

What I would like to code is:

If the template document has a headerfirst and headerprimary then
Add headerfirst to first page of target document and add headerprimary to all other pages of target document
ElseIf the template document only has a headerprimary then
Add headerprimary to all pages of the target document

I just don't know the correct syntax to do this, if it is even possible.

Hi Niels,

Thanks for your inquiry. Your scenario is simple. If your final document contains multiple
sections, you can use HeadersFooters.LinkToPrevious method to links all
headers and footers to the corresponding headers and footers in the
previous section.
https://docs.aspose.com/words/net/working-with-headers-and-footers/

If document have multiple pages and sections, set PageSetup.DifferentFirstPageHeaderFooter to true for first section of document only.

Perhaps, you are missing something at your end. It would be great if you please share following detail for investigation purposes.

  • Please attach your input Word document.

  • Please create a standalone/runnable simple application (for example a Console
    Application Project
    ) that demonstrates the code (Aspose.Words code) you used to generate your output document

  • Please attach the output Word file that shows the undesired behavior.

  • Please attach your target Word document showing the desired behavior. You can
    use Microsoft Word to create your target Word document. I will investigate as to how you are expecting your final document be generated like.

Unfortunately, it is difficult to say what the problem is without the Document(s) and
simplified application. We need your Document(s) and simple project to reproduce the problem. As soon as you get these pieces of information to us we’ll start our investigation into your issue.