diff --git a/demo/demo26.ts b/demo/demo26.ts new file mode 100644 index 0000000000..9fa560d260 --- /dev/null +++ b/demo/demo26.ts @@ -0,0 +1,22 @@ +// Creates two paragraphs, one with a border and one without +// Import from 'docx' rather than '../build' if you install from npm +import * as fs from "fs"; +import { Document, Packer, Paragraph } from "../build"; + +const doc = new Document(); + +const paragraph = new Paragraph("No border!"); + +doc.addParagraph(paragraph); + +const borderParagraph = new Paragraph("I have borders on my top and bottom sides!").createBorder(); +borderParagraph.Borders.addTopBorder(); +borderParagraph.Borders.addBottomBorder(); + +doc.addParagraph(borderParagraph); + +const packer = new Packer(); + +packer.toBuffer(doc).then((buffer) => { + fs.writeFileSync("My Document.docx", buffer); +}); diff --git a/src/file/paragraph/formatting/border.ts b/src/file/paragraph/formatting/border.ts index 9ceb0c1336..f37854a3c7 100644 --- a/src/file/paragraph/formatting/border.ts +++ b/src/file/paragraph/formatting/border.ts @@ -1,23 +1,63 @@ // http://officeopenxml.com/WPborders.php import { Attributes, XmlComponent } from "file/xml-components"; -class Border extends XmlComponent { +class BorderProperty extends XmlComponent { + public setProperties(color: string, space: string, value: string, size: string): XmlComponent { + const attrs = new Attributes({ + color: color, + space: space, + val: value, + sz: size, + }); + this.root.push(attrs); + + return this; + } +} + +export class Border extends XmlComponent { constructor() { - super("w:bottom"); - this.root.push( - new Attributes({ - color: "auto", - space: "1", - val: "single", - sz: "6", - }), - ); + super("w:pBdr"); + } + + public addTopBorder(color: string = "auto", space: string = "1", value: string = "single", size: string = "6"): XmlComponent { + const top = new BorderProperty("w:top"); + top.setProperties(color, space, value, size); + this.root.push(top); + + return this; + } + + public addBottomBorder(color: string = "auto", space: string = "1", value: string = "single", size: string = "6"): XmlComponent { + const bottom = new BorderProperty("w:bottom"); + bottom.setProperties(color, space, value, size); + this.root.push(bottom); + + return this; + } + + public addLeftBorder(color: string = "auto", space: string = "1", value: string = "single", size: string = "6"): XmlComponent { + const left = new BorderProperty("w:left"); + left.setProperties(color, space, value, size); + this.root.push(left); + + return this; + } + + public addRightBorder(color: string = "auto", space: string = "1", value: string = "single", size: string = "6"): XmlComponent { + const right = new BorderProperty("w:right"); + right.setProperties(color, space, value, size); + this.root.push(right); + + return this; } } export class ThematicBreak extends XmlComponent { constructor() { super("w:pBdr"); - this.root.push(new Border()); + const bottom = new BorderProperty("w:bottom"); + bottom.setProperties("auto", "1", "single", "6"); + this.root.push(bottom); } } diff --git a/src/file/paragraph/paragraph.spec.ts b/src/file/paragraph/paragraph.spec.ts index e00fa6167c..2413769b1e 100644 --- a/src/file/paragraph/paragraph.spec.ts +++ b/src/file/paragraph/paragraph.spec.ts @@ -144,6 +144,51 @@ describe("Paragraph", () => { }); }); + describe("#paragraphBorders()", () => { + it("should add a left and right border to a paragraph", () => { + paragraph.createBorder(); + paragraph.Borders.addLeftBorder(); + paragraph.Borders.addRightBorder(); + const tree = new Formatter().format(paragraph); + expect(tree).to.deep.equal({ + "w:p": [ + { + "w:pPr": [ + { + "w:pBdr": [ + { + "w:left": [ + { + _attr: { + "w:color": "auto", + "w:space": "1", + "w:sz": "6", + "w:val": "single", + }, + }, + ], + }, + { + "w:right": [ + { + _attr: { + "w:color": "auto", + "w:space": "1", + "w:sz": "6", + "w:val": "single", + }, + }, + ], + }, + ], + }, + ], + }, + ], + }); + }); + }); + describe("#pageBreak()", () => { it("should add page break to JSON", () => { paragraph.pageBreak(); diff --git a/src/file/paragraph/paragraph.ts b/src/file/paragraph/paragraph.ts index 09348b2eaa..42b34e0c0d 100644 --- a/src/file/paragraph/paragraph.ts +++ b/src/file/paragraph/paragraph.ts @@ -6,7 +6,7 @@ import { XmlComponent } from "file/xml-components"; import { Alignment } from "./formatting/alignment"; import { Bidirectional } from "./formatting/bidirectional"; -import { ThematicBreak } from "./formatting/border"; +import { Border, ThematicBreak } from "./formatting/border"; import { IIndentAttributesProperties, Indent } from "./formatting/indent"; import { KeepLines, KeepNext } from "./formatting/keep"; import { PageBreak, PageBreakBefore } from "./formatting/page-break"; @@ -30,6 +30,15 @@ export class Paragraph extends XmlComponent { } } + public get Borders(): Border { + return this.properties.paragraphBorder; + } + + public createBorder(): Paragraph { + this.properties.createBorder(); + return this; + } + public addRun(run: Run): Paragraph { this.root.push(run); return this; diff --git a/src/file/paragraph/properties.ts b/src/file/paragraph/properties.ts index 93fba4ce31..5f0c651246 100644 --- a/src/file/paragraph/properties.ts +++ b/src/file/paragraph/properties.ts @@ -1,9 +1,17 @@ // http://officeopenxml.com/WPparagraphProperties.php import { XmlComponent } from "file/xml-components"; +import { Border } from "./formatting/border"; export class ParagraphProperties extends XmlComponent { + public paragraphBorder: Border; + constructor() { super("w:pPr"); + this.paragraphBorder = new Border(); + } + + public createBorder(): void { + this.push(this.paragraphBorder); } public push(item: XmlComponent): void {