forked from unidoc/unioffice
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
examples: add PDF export and TOC generation examples
This only works on Windows as it uses OLE to drive MS Word, but it allows offloading complex functionality to the actual MS Word instead of implementing a Word renderer. Fixes unidoc#185
- Loading branch information
Showing
2 changed files
with
156 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,61 @@ | ||
// Copyright 2017 Baliance. All rights reserved. | ||
package main | ||
|
||
import ( | ||
"log" | ||
"os" | ||
"path/filepath" | ||
|
||
"baliance.com/gooxml/document" | ||
"github.com/go-ole/go-ole/oleutil" | ||
) | ||
|
||
// NOTE: This example can only run on Windows and requires that Word be installed. | ||
|
||
func main() { | ||
doc := document.New() | ||
|
||
para := doc.AddParagraph() | ||
run := para.AddRun() | ||
para.SetStyle("Title") | ||
run.AddText("Simple Document Formatting") | ||
|
||
para = doc.AddParagraph() | ||
para.SetStyle("Heading1") | ||
run = para.AddRun() | ||
run.AddText("Some Heading Text") | ||
|
||
para = doc.AddParagraph() | ||
para.SetStyle("Heading2") | ||
run = para.AddRun() | ||
run.AddText("Some Heading Text") | ||
doc.SaveToFile("simple.docx") | ||
|
||
cwd, _ := os.Getwd() | ||
ConvertToPDF(filepath.Join(cwd, "simple.docx"), filepath.Join(cwd, "simple.pdf")) | ||
} | ||
|
||
// ConvertToPDF uses go-ole to convert a docx to a PDF using the Word application | ||
func ConvertToPDF(source, destination string) { | ||
ole.CoInitialize(0) | ||
defer ole.CoUninitialize() | ||
|
||
iunk, err := oleutil.CreateObject("Word.Application") | ||
if err != nil { | ||
log.Fatalf("error creating Word object: %s", err) | ||
} | ||
|
||
word := iunk.MustQueryInterface(ole.IID_IDispatch) | ||
defer word.Release() | ||
|
||
// opening then saving works due to the call to doc.Settings.SetUpdateFieldsOnOpen(true) above | ||
|
||
docs := oleutil.MustGetProperty(word, "Documents").ToIDispatch() | ||
wordDoc := oleutil.MustCallMethod(docs, "Open", source).ToIDispatch() | ||
|
||
// file format constant comes from https://msdn.microsoft.com/en-us/vba/word-vba/articles/wdsaveformat-enumeration-word | ||
const wdFormatPDF = 17 | ||
oleutil.MustCallMethod(wordDoc, "SaveAs2", destination, wdFormatPDF) | ||
oleutil.MustCallMethod(wordDoc, "Close") | ||
oleutil.MustCallMethod(word, "Quit") | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,95 @@ | ||
// Copyright 2017 Baliance. All rights reserved. | ||
package main | ||
|
||
import ( | ||
"log" | ||
"os" | ||
"path/filepath" | ||
|
||
"baliance.com/gooxml/document" | ||
"baliance.com/gooxml/measurement" | ||
"baliance.com/gooxml/schema/soo/wml" | ||
|
||
"github.com/go-ole/go-ole/oleutil" | ||
) | ||
|
||
// NOTE: This example can only run on Windows and requires that Word be installed. | ||
|
||
var lorem = `Lorem ipsum dolor sit amet, consectetur adipiscing elit. Proin lobortis, lectus dictum feugiat tempus, sem neque finibus enim, sed eleifend sem nunc ac diam. Vestibulum tempus sagittis elementum` | ||
|
||
func main() { | ||
doc := document.New() | ||
|
||
// Force the TOC to update upon opening the document | ||
doc.Settings.SetUpdateFieldsOnOpen(true) | ||
|
||
// Add a TOC | ||
doc.AddParagraph().AddRun().AddField(document.FieldTOC) | ||
// followed by a page break | ||
doc.AddParagraph().Properties().AddSection(wml.ST_SectionMarkNextPage) | ||
|
||
nd := doc.Numbering.AddDefinition() | ||
for i := 0; i < 9; i++ { | ||
lvl := nd.AddLevel() | ||
lvl.SetFormat(wml.ST_NumberFormatNone) | ||
lvl.SetAlignment(wml.ST_JcLeft) | ||
if i%2 == 0 { | ||
lvl.SetFormat(wml.ST_NumberFormatBullet) | ||
lvl.RunProperties().SetFontFamily("Symbol") | ||
lvl.SetText("") | ||
} | ||
lvl.Properties().SetLeftIndent(0.5 * measurement.Distance(i) * measurement.Inch) | ||
} | ||
|
||
// and finally paragraphs at different heading levels | ||
for i := 0; i < 4; i++ { | ||
para := doc.AddParagraph() | ||
para.SetNumberingDefinition(nd) | ||
para.Properties().SetHeadingLevel(1) | ||
para.AddRun().AddText("First Level") | ||
|
||
doc.AddParagraph().AddRun().AddText(lorem) | ||
for i := 0; i < 3; i++ { | ||
para := doc.AddParagraph() | ||
para.SetNumberingDefinition(nd) | ||
para.Properties().SetHeadingLevel(2) | ||
para.AddRun().AddText("Second Level") | ||
doc.AddParagraph().AddRun().AddText(lorem) | ||
|
||
para = doc.AddParagraph() | ||
para.SetNumberingDefinition(nd) | ||
para.Properties().SetHeadingLevel(3) | ||
para.AddRun().AddText("Third Level") | ||
doc.AddParagraph().AddRun().AddText(lorem) | ||
} | ||
} | ||
doc.SaveToFile("toc.docx") | ||
|
||
cwd, _ := os.Getwd() | ||
UpdateFields(filepath.Join(cwd, "toc.docx")) | ||
} | ||
|
||
// UpdateFields uses go-ole to convert a docx to a PDF using the Word application | ||
func UpdateFields(source string) { | ||
ole.CoInitialize(0) | ||
defer ole.CoUninitialize() | ||
|
||
iunk, err := oleutil.CreateObject("Word.Application") | ||
if err != nil { | ||
log.Fatalf("error creating Word object: %s", err) | ||
} | ||
defer iunk.Release() | ||
|
||
word := iunk.MustQueryInterface(ole.IID_IDispatch) | ||
defer word.Release() | ||
|
||
docs := oleutil.MustGetProperty(word, "Documents").ToIDispatch() | ||
defer docs.Release() | ||
wordDoc := oleutil.MustCallMethod(docs, "Open", source).ToIDispatch() | ||
defer wordDoc.Release() | ||
|
||
const wdFormatXMLDocument = 12 | ||
oleutil.MustCallMethod(wordDoc, "SaveAs2", source, wdFormatXMLDocument) | ||
oleutil.MustCallMethod(wordDoc, "Close") | ||
oleutil.MustCallMethod(word, "Quit") | ||
} |