Merge pull request #948 from devoidfury/bug/ooxml-conformance-fixes

Better conformance to Office Open XML schema
This commit is contained in:
Dolan
2021-05-24 01:45:36 +01:00
committed by GitHub
31 changed files with 385 additions and 461 deletions

View File

@ -39,17 +39,16 @@ describe("Body", () => {
"w:header": 708,
"w:footer": 708,
"w:gutter": 0,
"w:mirrorMargins": false,
},
},
},
{ "w:cols": { _attr: { "w:space": 708, "w:sep": false, "w:num": 1 } } },
{ "w:docGrid": { _attr: { "w:linePitch": 360 } } },
{
"w:pgNumType": {
_attr: {},
},
},
{ "w:cols": { _attr: { "w:space": 708, "w:sep": false, "w:num": 1 } } },
{ "w:docGrid": { _attr: { "w:linePitch": 360 } } },
],
},
],

View File

@ -8,7 +8,6 @@ export interface IPageMarginAttributes {
readonly header?: number;
readonly footer?: number;
readonly gutter?: number;
readonly mirror?: boolean;
}
export class PageMarginAttributes extends XmlAttributeComponent<IPageMarginAttributes> {
@ -20,6 +19,5 @@ export class PageMarginAttributes extends XmlAttributeComponent<IPageMarginAttri
header: "w:header",
footer: "w:footer",
gutter: "w:gutter",
mirror: "w:mirrorMargins",
};
}

View File

@ -2,7 +2,7 @@ import { XmlComponent } from "file/xml-components";
import { PageMarginAttributes } from "./page-margin-attributes";
export class PageMargin extends XmlComponent {
constructor(top: number, right: number, bottom: number, left: number, header: number, footer: number, gutter: number, mirror: boolean) {
constructor(top: number, right: number, bottom: number, left: number, header: number, footer: number, gutter: number) {
super("w:pgMar");
this.root.push(
new PageMarginAttributes({
@ -13,7 +13,6 @@ export class PageMargin extends XmlComponent {
header: header,
footer: footer,
gutter: gutter,
mirror: mirror,
}),
);
}

View File

@ -32,7 +32,6 @@ describe("SectionProperties", () => {
header: 708,
footer: 708,
gutter: 0,
mirror: false,
},
pageNumbers: {
start: 10,
@ -61,8 +60,10 @@ describe("SectionProperties", () => {
expect(Object.keys(tree)).to.deep.equal(["w:sectPr"]);
expect(tree["w:sectPr"]).to.be.an.instanceof(Array);
expect(tree["w:sectPr"][0]).to.deep.equal({ "w:pgSz": { _attr: { "w:h": 16838, "w:w": 11906, "w:orient": "portrait" } } });
expect(tree["w:sectPr"][1]).to.deep.equal({
expect(tree["w:sectPr"][0]).to.deep.equal({ "w:headerReference": { _attr: { "r:id": "rId100", "w:type": "default" } } });
expect(tree["w:sectPr"][1]).to.deep.equal({ "w:footerReference": { _attr: { "r:id": "rId200", "w:type": "even" } } });
expect(tree["w:sectPr"][2]).to.deep.equal({ "w:pgSz": { _attr: { "w:h": 16838, "w:w": 11906, "w:orient": "portrait" } } });
expect(tree["w:sectPr"][3]).to.deep.equal({
"w:pgMar": {
_attr: {
"w:bottom": 1440,
@ -72,16 +73,15 @@ describe("SectionProperties", () => {
"w:left": 1440,
"w:header": 708,
"w:gutter": 0,
"w:mirrorMargins": false,
},
},
});
expect(tree["w:sectPr"][2]).to.deep.equal({ "w:cols": { _attr: { "w:space": 708, "w:sep": true, "w:num": 1 } } });
expect(tree["w:sectPr"][3]).to.deep.equal({ "w:docGrid": { _attr: { "w:linePitch": 360 } } });
expect(tree["w:sectPr"][4]).to.deep.equal({ "w:headerReference": { _attr: { "r:id": "rId100", "w:type": "default" } } });
expect(tree["w:sectPr"][5]).to.deep.equal({ "w:footerReference": { _attr: { "r:id": "rId200", "w:type": "even" } } });
expect(tree["w:sectPr"][6]).to.deep.equal({ "w:pgNumType": { _attr: { "w:fmt": "cardinalText", "w:start": 10 } } });
expect(tree["w:sectPr"][4]).to.deep.equal({ "w:pgNumType": { _attr: { "w:fmt": "cardinalText", "w:start": 10 } } });
expect(tree["w:sectPr"][5]).to.deep.equal({ "w:cols": { _attr: { "w:space": 708, "w:sep": true, "w:num": 1 } } });
expect(tree["w:sectPr"][6]).to.deep.equal({ "w:vAlign": { _attr: { "w:val": "top" } } });
expect(tree["w:sectPr"][7]).to.deep.equal({ "w:titlePg": { _attr: { "w:val": "1" } } });
expect(tree["w:sectPr"][8]).to.deep.equal({ "w:docGrid": { _attr: { "w:linePitch": 360 } } });
});
it("should create section properties with no options", () => {
@ -100,12 +100,11 @@ describe("SectionProperties", () => {
"w:left": 1440,
"w:header": 708,
"w:gutter": 0,
"w:mirrorMargins": false,
},
},
});
expect(tree["w:sectPr"][2]).to.deep.equal({ "w:cols": { _attr: { "w:space": 708, "w:sep": false, "w:num": 1 } } });
expect(tree["w:sectPr"][3]).to.deep.equal({ "w:docGrid": { _attr: { "w:linePitch": 360 } } });
expect(tree["w:sectPr"][3]).to.deep.equal({ "w:cols": { _attr: { "w:space": 708, "w:sep": false, "w:num": 1 } } });
expect(tree["w:sectPr"][4]).to.deep.equal({ "w:docGrid": { _attr: { "w:linePitch": 360 } } });
});
it("should create section properties with changed options", () => {
@ -130,7 +129,6 @@ describe("SectionProperties", () => {
"w:left": 1440,
"w:header": 708,
"w:gutter": 0,
"w:mirrorMargins": false,
},
},
});
@ -158,7 +156,6 @@ describe("SectionProperties", () => {
"w:left": 1440,
"w:header": 708,
"w:gutter": 0,
"w:mirrorMargins": false,
},
},
});
@ -187,7 +184,6 @@ describe("SectionProperties", () => {
"w:left": 1440,
"w:header": 708,
"w:gutter": 0,
"w:mirrorMargins": false,
},
},
});

View File

@ -63,7 +63,6 @@ export class SectionProperties extends XmlComponent {
header = 708,
footer = 708,
gutter = 0,
mirror = false,
} = {},
pageNumbers: {
start: pageNumberStart = undefined,
@ -89,20 +88,16 @@ export class SectionProperties extends XmlComponent {
}: ISectionPropertiesOptions = {}) {
super("w:sectPr");
this.root.push(new PageSize(width, height, orientation));
this.root.push(new PageMargin(top, right, bottom, left, header, footer, gutter, mirror));
this.root.push(new Columns(space, count, separate));
this.root.push(new DocumentGrid(linePitch));
this.addHeaders(headerWrapperGroup);
this.addFooters(footerWrapperGroup);
this.root.push(new PageNumberType(pageNumberStart, pageNumberFormatType, pageNumberSeparator));
if (lineNumberCountBy || lineNumberStart || lineNumberRestart || lineNumberDistance) {
this.root.push(new LineNumberType(lineNumberCountBy, lineNumberStart, lineNumberRestart, lineNumberDistance));
if (type) {
this.root.push(new Type(type));
}
this.root.push(new PageSize(width, height, orientation));
this.root.push(new PageMargin(top, right, bottom, left, header, footer, gutter));
if (pageBorders || pageBorderTop || pageBorderRight || pageBorderBottom || pageBorderLeft) {
this.root.push(
new PageBorders({
@ -115,17 +110,23 @@ export class SectionProperties extends XmlComponent {
);
}
if (titlePage) {
this.root.push(new TitlePage());
if (lineNumberCountBy || lineNumberStart || lineNumberRestart || lineNumberDistance) {
this.root.push(new LineNumberType(lineNumberCountBy, lineNumberStart, lineNumberRestart, lineNumberDistance));
}
this.root.push(new PageNumberType(pageNumberStart, pageNumberFormatType, pageNumberSeparator));
this.root.push(new Columns(space, count, separate));
if (verticalAlign) {
this.root.push(new SectionVerticalAlign(verticalAlign));
}
if (type) {
this.root.push(new Type(type));
if (titlePage) {
this.root.push(new TitlePage());
}
this.root.push(new DocumentGrid(linePitch));
}
private addHeaders(headers: IHeaderFooterGroup<HeaderWrapper>): void {

View File

@ -111,7 +111,7 @@ describe("Drawing", () => {
{
"pic:cNvPr": {
_attr: {
desc: "",
descr: "",
id: 0,
name: "",
},
@ -166,14 +166,6 @@ describe("Drawing", () => {
{
_attr: {},
},
{
"a:ext": {
_attr: {
cx: 952500,
cy: 952500,
},
},
},
{
"a:off": {
_attr: {
@ -182,6 +174,14 @@ describe("Drawing", () => {
},
},
},
{
"a:ext": {
_attr: {
cx: 952500,
cy: 952500,
},
},
},
],
},
{
@ -341,7 +341,7 @@ describe("Drawing", () => {
{
"pic:cNvPr": {
_attr: {
desc: "",
descr: "",
id: 0,
name: "",
},
@ -396,14 +396,6 @@ describe("Drawing", () => {
{
_attr: {},
},
{
"a:ext": {
_attr: {
cx: 952500,
cy: 952500,
},
},
},
{
"a:off": {
_attr: {
@ -412,6 +404,14 @@ describe("Drawing", () => {
},
},
},
{
"a:ext": {
_attr: {
cx: 952500,
cy: 952500,
},
},
},
],
},
{

View File

@ -8,6 +8,6 @@ export class NonVisualPropertiesAttributes extends XmlAttributeComponent<{
protected readonly xmlKeys = {
id: "id",
name: "name",
descr: "desc",
descr: "descr",
};
}

View File

@ -24,14 +24,6 @@ describe("Form", () => {
{
_attr: {},
},
{
"a:ext": {
_attr: {
cx: 100,
cy: 100,
},
},
},
{
"a:off": {
_attr: {
@ -40,6 +32,14 @@ describe("Form", () => {
},
},
},
{
"a:ext": {
_attr: {
cx: 100,
cy: 100,
},
},
},
],
});
});
@ -70,14 +70,6 @@ describe("Form", () => {
flipV: true,
},
},
{
"a:ext": {
_attr: {
cx: 100,
cy: 100,
},
},
},
{
"a:off": {
_attr: {
@ -86,6 +78,14 @@ describe("Form", () => {
},
},
},
{
"a:ext": {
_attr: {
cx: 100,
cy: 100,
},
},
},
],
});
});

View File

@ -34,8 +34,8 @@ export class Form extends XmlComponent {
this.extents = new Extents(options.emus.x, options.emus.y);
this.root.push(this.extents);
this.root.push(new Offset());
this.root.push(this.extents);
}
public setXY(x: number, y: number): void {

View File

@ -25,8 +25,8 @@ describe("File", () => {
const tree = new Formatter().format(doc.Document.View.Body);
expect(tree["w:body"][0]["w:sectPr"][4]["w:headerReference"]._attr["w:type"]).to.equal("default");
expect(tree["w:body"][0]["w:sectPr"][5]["w:footerReference"]._attr["w:type"]).to.equal("default");
expect(tree["w:body"][0]["w:sectPr"][0]["w:headerReference"]._attr["w:type"]).to.equal("default");
expect(tree["w:body"][0]["w:sectPr"][1]["w:footerReference"]._attr["w:type"]).to.equal("default");
});
it("should create with first headers and footers", () => {
@ -45,8 +45,8 @@ describe("File", () => {
});
const tree = new Formatter().format(doc.Document.View.Body);
expect(tree["w:body"][0]["w:sectPr"][4]["w:headerReference"]._attr["w:type"]).to.equal("first");
expect(tree["w:body"][0]["w:sectPr"][5]["w:footerReference"]._attr["w:type"]).to.equal("first");
expect(tree["w:body"][0]["w:sectPr"][0]["w:headerReference"]._attr["w:type"]).to.equal("first");
expect(tree["w:body"][0]["w:sectPr"][1]["w:footerReference"]._attr["w:type"]).to.equal("first");
});
it("should create with correct headers", () => {
@ -70,13 +70,13 @@ describe("File", () => {
const tree = new Formatter().format(doc.Document.View.Body);
expect(tree["w:body"][0]["w:sectPr"][4]["w:headerReference"]._attr["w:type"]).to.equal("default");
expect(tree["w:body"][0]["w:sectPr"][5]["w:headerReference"]._attr["w:type"]).to.equal("first");
expect(tree["w:body"][0]["w:sectPr"][6]["w:headerReference"]._attr["w:type"]).to.equal("even");
expect(tree["w:body"][0]["w:sectPr"][0]["w:headerReference"]._attr["w:type"]).to.equal("default");
expect(tree["w:body"][0]["w:sectPr"][1]["w:headerReference"]._attr["w:type"]).to.equal("first");
expect(tree["w:body"][0]["w:sectPr"][2]["w:headerReference"]._attr["w:type"]).to.equal("even");
expect(tree["w:body"][0]["w:sectPr"][7]["w:footerReference"]._attr["w:type"]).to.equal("default");
expect(tree["w:body"][0]["w:sectPr"][8]["w:footerReference"]._attr["w:type"]).to.equal("first");
expect(tree["w:body"][0]["w:sectPr"][9]["w:footerReference"]._attr["w:type"]).to.equal("even");
expect(tree["w:body"][0]["w:sectPr"][3]["w:footerReference"]._attr["w:type"]).to.equal("default");
expect(tree["w:body"][0]["w:sectPr"][4]["w:footerReference"]._attr["w:type"]).to.equal("first");
expect(tree["w:body"][0]["w:sectPr"][5]["w:footerReference"]._attr["w:type"]).to.equal("even");
});
it("should add child", () => {
@ -129,12 +129,16 @@ describe("File", () => {
"w:gutter": 0,
"w:header": 708,
"w:left": 1440,
"w:mirrorMargins": false,
"w:right": 1440,
"w:top": 1440,
},
},
},
{
"w:pgNumType": {
_attr: {},
},
},
{
"w:cols": {
_attr: {
@ -151,11 +155,6 @@ describe("File", () => {
},
},
},
{
"w:pgNumType": {
_attr: {},
},
},
],
},
],

View File

@ -623,41 +623,6 @@ describe("AbstractNumbering", () => {
fill: "00FFFF",
color: "FF0000",
},
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
shadingComplexScript: true,
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
shadingComplexScript: false,
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
@ -666,18 +631,34 @@ describe("AbstractNumbering", () => {
fill: "00FFFF",
color: "FF0000",
},
shadingComplexScript: {
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "00FF00",
color: "FF0000",
},
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "00FF00" } } },
],
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
];
shadingTests.forEach(({ shadow, shading, shadingComplexScript, expected }) => {
shadingTests.forEach(({ shadow, shading, expected }) => {
it("#shadow correctly", () => {
const abstractNumbering = new AbstractNumbering(1, [
{
@ -685,7 +666,7 @@ describe("AbstractNumbering", () => {
format: LevelFormat.LOWER_ROMAN,
text: "%0.",
style: {
run: { shadow, shading, shadingComplexScript },
run: { shadow, shading },
},
},
]);

View File

@ -111,33 +111,35 @@ export class LevelBase extends XmlComponent {
constructor({ level, format, text, alignment = AlignmentType.START, start = 1, style, suffix }: ILevelsOptions) {
super("w:lvl");
this.root.push(
new LevelAttributes({
ilvl: level,
tentative: 1,
}),
);
this.root.push(new Start(start));
this.root.push(new LevelJc(alignment));
if (format) {
this.root.push(new NumberFormat(format));
}
if (suffix) {
this.root.push(new Suffix(suffix));
}
if (text) {
this.root.push(new LevelText(text));
}
this.root.push(new LevelJc(alignment));
this.paragraphProperties = new ParagraphProperties(style && style.paragraph);
this.runProperties = new RunProperties(style && style.run);
this.root.push(this.paragraphProperties);
this.root.push(this.runProperties);
if (suffix) {
this.root.push(new Suffix(suffix));
}
this.root.push(
new LevelAttributes({
ilvl: level,
tentative: 1,
}),
);
}
}

View File

@ -43,7 +43,7 @@ export class Paragraph extends XmlComponent {
this.properties = new ParagraphProperties({});
this.root.push(this.properties);
this.root.push(new TextRun(options));
return;
return this;
}
this.properties = new ParagraphProperties(options);

View File

@ -66,70 +66,15 @@ export class ParagraphProperties extends IgnoreIfEmptyXmlComponent {
super("w:pPr");
if (!options) {
return;
}
if (options.border) {
this.push(new Border(options.border));
}
if (options.spacing) {
this.push(new Spacing(options.spacing));
}
if (options.outlineLevel !== undefined) {
this.push(new OutlineLevel(options.outlineLevel));
}
if (options.alignment) {
this.push(new Alignment(options.alignment));
return this;
}
if (options.heading) {
this.push(new Style(options.heading));
}
if (options.bidirectional) {
this.push(new Bidirectional());
}
if (options.thematicBreak) {
this.push(new ThematicBreak());
}
if (options.pageBreakBefore) {
this.push(new PageBreakBefore());
}
if (options.contextualSpacing) {
this.push(new ContextualSpacing(options.contextualSpacing));
}
if (options.indent) {
this.push(new Indent(options.indent));
}
if (options.keepLines) {
this.push(new KeepLines());
}
if (options.keepNext) {
this.push(new KeepNext());
}
if (options.tabStops) {
for (const tabStop of options.tabStops) {
this.push(new TabStop(tabStop.type, tabStop.position, tabStop.leader));
}
}
if (options.style) {
this.push(new Style(options.style));
}
if (options.bullet) {
this.push(new Style("ListParagraph"));
this.push(new NumberProperties(1, options.bullet.level));
}
if (options.numbering) {
@ -138,6 +83,37 @@ export class ParagraphProperties extends IgnoreIfEmptyXmlComponent {
this.push(new Style("ListParagraph"));
}
}
}
if (options.style) {
this.push(new Style(options.style));
}
if (options.keepNext) {
this.push(new KeepNext());
}
if (options.keepLines) {
this.push(new KeepLines());
}
if (options.pageBreakBefore) {
this.push(new PageBreakBefore());
}
if (options.frame) {
this.push(new FrameProperties(options.frame));
}
if (options.widowControl) {
this.push(new WidowControl(options.widowControl));
}
if (options.bullet) {
this.push(new NumberProperties(1, options.bullet.level));
}
if (options.numbering) {
this.numberingReferences.push({
reference: options.numbering.reference,
instance: options.numbering.instance ?? 0,
@ -146,24 +122,54 @@ export class ParagraphProperties extends IgnoreIfEmptyXmlComponent {
this.push(new NumberProperties(`${options.numbering.reference}-${options.numbering.instance ?? 0}`, options.numbering.level));
}
if (options.rightTabStop) {
this.push(new TabStop(TabStopType.RIGHT, options.rightTabStop));
if (options.border) {
this.push(new Border(options.border));
}
if (options.leftTabStop) {
this.push(new TabStop(TabStopType.LEFT, options.leftTabStop));
if (options.thematicBreak) {
this.push(new ThematicBreak());
}
if (options.shading) {
this.push(new Shading(options.shading.type, options.shading.fill, options.shading.color));
}
if (options.widowControl) {
this.push(new WidowControl(options.widowControl));
if (options.rightTabStop) {
this.push(new TabStop(TabStopType.RIGHT, options.rightTabStop));
}
if (options.frame) {
this.push(new FrameProperties(options.frame));
if (options.tabStops) {
for (const tabStop of options.tabStops) {
this.push(new TabStop(tabStop.type, tabStop.position, tabStop.leader));
}
}
if (options.leftTabStop) {
this.push(new TabStop(TabStopType.LEFT, options.leftTabStop));
}
if (options.bidirectional) {
this.push(new Bidirectional());
}
if (options.spacing) {
this.push(new Spacing(options.spacing));
}
if (options.indent) {
this.push(new Indent(options.indent));
}
if (options.contextualSpacing) {
this.push(new ContextualSpacing(options.contextualSpacing));
}
if (options.alignment) {
this.push(new Alignment(options.alignment));
}
if (options.outlineLevel !== undefined) {
this.push(new OutlineLevel(options.outlineLevel));
}
}

View File

@ -199,16 +199,3 @@ export class Shading extends XmlComponent {
);
}
}
export class ShadowComplexScript extends XmlComponent {
constructor(value: string, fill: string, color: string) {
super("w:shdCs");
this.root.push(
new Attributes({
val: value,
fill: fill,
color: color,
}),
);
}
}

View File

@ -168,7 +168,7 @@ describe("ImageRun", () => {
{
"pic:cNvPr": {
_attr: {
desc: "",
descr: "",
id: 0,
name: "",
},
@ -224,14 +224,6 @@ describe("ImageRun", () => {
rot: 2700000,
},
},
{
"a:ext": {
_attr: {
cx: 1905000,
cy: 1905000,
},
},
},
{
"a:off": {
_attr: {
@ -240,6 +232,14 @@ describe("ImageRun", () => {
},
},
},
{
"a:ext": {
_attr: {
cx: 1905000,
cy: 1905000,
},
},
},
],
},
{
@ -418,7 +418,7 @@ describe("ImageRun", () => {
{
"pic:cNvPr": {
_attr: {
desc: "",
descr: "",
id: 0,
name: "",
},
@ -474,14 +474,6 @@ describe("ImageRun", () => {
rot: 2700000,
},
},
{
"a:ext": {
_attr: {
cx: 1905000,
cy: 1905000,
},
},
},
{
"a:off": {
_attr: {
@ -490,6 +482,14 @@ describe("ImageRun", () => {
},
},
},
{
"a:ext": {
_attr: {
cx: 1905000,
cy: 1905000,
},
},
},
],
},
{
@ -671,7 +671,7 @@ describe("ImageRun", () => {
{
"pic:cNvPr": {
_attr: {
desc: "",
descr: "",
id: 0,
name: "",
},
@ -727,14 +727,6 @@ describe("ImageRun", () => {
rot: 2700000,
},
},
{
"a:ext": {
_attr: {
cx: 1905000,
cy: 1905000,
},
},
},
{
"a:off": {
_attr: {
@ -743,6 +735,14 @@ describe("ImageRun", () => {
},
},
},
{
"a:ext": {
_attr: {
cx: 1905000,
cy: 1905000,
},
},
},
],
},
{
@ -927,7 +927,7 @@ describe("ImageRun", () => {
{
"pic:cNvPr": {
_attr: {
desc: "",
descr: "",
id: 0,
name: "",
},
@ -983,14 +983,6 @@ describe("ImageRun", () => {
rot: 2700000,
},
},
{
"a:ext": {
_attr: {
cx: 1905000,
cy: 1905000,
},
},
},
{
"a:off": {
_attr: {
@ -999,6 +991,14 @@ describe("ImageRun", () => {
},
},
},
{
"a:ext": {
_attr: {
cx: 1905000,
cy: 1905000,
},
},
},
],
},
{

View File

@ -16,7 +16,6 @@ import {
ItalicsComplexScript,
RightToLeft,
Shading,
ShadowComplexScript,
Size,
SizeComplexScript,
SmallCaps,
@ -63,7 +62,6 @@ export interface IRunStylePropertiesOptions {
readonly fill: string;
readonly color: string;
};
readonly shadingComplexScript?: boolean | IRunStylePropertiesOptions["shading"];
readonly shadow?: IRunStylePropertiesOptions["shading"];
readonly emboss?: boolean;
readonly imprint?: boolean;
@ -185,11 +183,6 @@ export class RunProperties extends IgnoreIfEmptyXmlComponent {
if (shading) {
this.push(new Shading(shading.type, shading.fill, shading.color));
}
const shdCs =
options.shadingComplexScript === undefined || options.shadingComplexScript === true ? shading : options.shadingComplexScript;
if (shdCs) {
this.push(new ShadowComplexScript(shdCs.type, shdCs.fill, shdCs.color));
}
}
public push(item: XmlComponent): void {

View File

@ -243,18 +243,7 @@ describe("Run", () => {
expect(tree).to.deep.equal({
"w:r": [
{
"w:rPr": [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{
"w:shdCs": {
_attr: {
"w:val": "pct10",
"w:fill": "00FFFF",
"w:color": "FF0000",
},
},
},
],
"w:rPr": [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
],
});

View File

@ -6,7 +6,7 @@ export class TextRun extends Run {
if (typeof options === "string") {
super({});
this.root.push(new Text(options));
return;
return this;
}
super(options);

View File

@ -153,6 +153,12 @@ describe("External styles factory", () => {
});
});
it("should throw when style element isn't found", () => {
expect(() => new ExternalStylesFactory().newInstance(`<?xml version="1.0" encoding="UTF-8" standalone="yes"?><foo/>`)).to.throw(
"can not find styles element",
);
});
it("should parse styles elements", () => {
// tslint:disable-next-line:no-any
const importedStyle = new ExternalStylesFactory().newInstance(externalStyles) as any;

View File

@ -782,41 +782,6 @@ describe("CharacterStyle", () => {
fill: "00FFFF",
color: "FF0000",
},
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
shadingComplexScript: true,
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
shadingComplexScript: false,
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
@ -825,22 +790,38 @@ describe("CharacterStyle", () => {
fill: "00FFFF",
color: "FF0000",
},
shadingComplexScript: {
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "00FF00",
color: "FF0000",
},
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "00FF00" } } },
],
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
];
shadingTests.forEach(({ shadow, shading, shadingComplexScript, expected }) => {
shadingTests.forEach(({ shadow, shading, expected }) => {
it("#shadow correctly", () => {
const style = new StyleForCharacter({
id: "myStyleId",
run: { shadow, shading, shadingComplexScript },
run: { shadow, shading },
});
const tree = new Formatter().format(style);
expect(tree).to.deep.equal({

View File

@ -658,41 +658,6 @@ describe("ParagraphStyle", () => {
fill: "00FFFF",
color: "FF0000",
},
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
shadingComplexScript: true,
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
shadingComplexScript: false,
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
@ -701,22 +666,38 @@ describe("ParagraphStyle", () => {
fill: "00FFFF",
color: "FF0000",
},
shadingComplexScript: {
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "00FF00",
color: "FF0000",
},
expected: [
{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } },
{ "w:shdCs": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "00FF00" } } },
],
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
{
shading: {
type: ShadingType.PERCENT_10,
fill: "00FFFF",
color: "FF0000",
},
expected: [{ "w:shd": { _attr: { "w:val": "pct10", "w:fill": "00FFFF", "w:color": "FF0000" } } }],
},
];
shadingTests.forEach(({ shadow, shading, shadingComplexScript, expected }) => {
shadingTests.forEach(({ shadow, shading, expected }) => {
it("#shadow correctly", () => {
const style = new StyleForParagraph({
id: "myStyleId",
run: { shadow, shading, shadingComplexScript },
run: { shadow, shading },
});
const tree = new Formatter().format(style);
expect(tree).to.deep.equal({

View File

@ -19,6 +19,14 @@ describe("TableCellMargin", () => {
},
},
},
{
"w:start": {
_attr: {
"w:type": "dxa",
"w:w": 0,
},
},
},
{
"w:bottom": {
_attr: {
@ -35,14 +43,6 @@ describe("TableCellMargin", () => {
},
},
},
{
"w:start": {
_attr: {
"w:type": "dxa",
"w:w": 0,
},
},
},
],
});
});
@ -65,6 +65,14 @@ describe("TableCellMargin", () => {
},
},
},
{
"w:start": {
_attr: {
"w:type": "dxa",
"w:w": 5,
},
},
},
{
"w:bottom": {
_attr: {
@ -81,14 +89,6 @@ describe("TableCellMargin", () => {
},
},
},
{
"w:start": {
_attr: {
"w:type": "dxa",
"w:w": 5,
},
},
},
],
});
});

View File

@ -14,8 +14,8 @@ export class TableCellMargin extends XmlComponent {
constructor({ top = 0, left = 0, right = 0, bottom = 0 }: ITableCellMarginOptions) {
super("w:tcMar");
this.root.push(new TopCellMargin(top));
this.root.push(new LeftCellMargin(left));
this.root.push(new BottomCellMargin(bottom));
this.root.push(new RightCellMargin(right));
this.root.push(new LeftCellMargin(left));
}
}

View File

@ -90,6 +90,14 @@ describe("TableCellProperties", () => {
},
},
},
{
"w:start": {
_attr: {
"w:type": "dxa",
"w:w": 0,
},
},
},
{
"w:bottom": {
_attr: {
@ -106,14 +114,6 @@ describe("TableCellProperties", () => {
},
},
},
{
"w:start": {
_attr: {
"w:type": "dxa",
"w:w": 0,
},
},
},
],
},
],

View File

@ -21,7 +21,6 @@ export class TableCellProperties extends IgnoreIfEmptyXmlComponent {
constructor() {
super("w:tcPr");
this.cellBorder = new TableCellBorders();
this.root.push(this.cellBorder);
}
public get Borders(): TableCellBorders {
@ -69,4 +68,10 @@ export class TableCellProperties extends IgnoreIfEmptyXmlComponent {
return this;
}
public addBorders(): TableCellProperties {
this.root.push(this.cellBorder);
return this;
}
}

View File

@ -354,6 +354,14 @@ describe("TableCell", () => {
},
},
},
{
"w:start": {
_attr: {
"w:type": "dxa",
"w:w": 1,
},
},
},
{
"w:bottom": {
_attr: {
@ -370,14 +378,6 @@ describe("TableCell", () => {
},
},
},
{
"w:start": {
_attr: {
"w:type": "dxa",
"w:w": 1,
},
},
},
],
},
],
@ -568,15 +568,6 @@ describe("TableCell", () => {
},
},
},
{
"w:bottom": {
_attr: {
"w:color": "blue",
"w:sz": 3,
"w:val": "double",
},
},
},
{
"w:left": {
_attr: {
@ -586,6 +577,15 @@ describe("TableCell", () => {
},
},
},
{
"w:bottom": {
_attr: {
"w:color": "blue",
"w:sz": 3,
"w:val": "double",
},
},
},
{
"w:right": {
_attr: {

View File

@ -57,12 +57,12 @@ export class TableCell extends XmlComponent {
this.root.push(child);
}
if (options.verticalAlign) {
properties.setVerticalAlign(options.verticalAlign);
if (options.width) {
properties.setWidth(options.width.size, options.width.type);
}
if (options.textDirection) {
properties.setTextDirection(options.textDirection);
if (options.columnSpan) {
properties.addGridSpan(options.columnSpan);
}
if (options.verticalMerge) {
@ -72,35 +72,36 @@ export class TableCell extends XmlComponent {
properties.addVerticalMerge(VerticalMergeType.RESTART);
}
if (options.margins) {
properties.addMargins(options.margins);
if (options.borders) {
properties.addBorders();
if (options.borders.top) {
properties.Borders.addTopBorder(options.borders.top.style, options.borders.top.size, options.borders.top.color);
}
if (options.borders.left) {
properties.Borders.addLeftBorder(options.borders.left.style, options.borders.left.size, options.borders.left.color);
}
if (options.borders.bottom) {
properties.Borders.addBottomBorder(options.borders.bottom.style, options.borders.bottom.size, options.borders.bottom.color);
}
if (options.borders.right) {
properties.Borders.addRightBorder(options.borders.right.style, options.borders.right.size, options.borders.right.color);
}
}
if (options.shading) {
properties.setShading(options.shading);
}
if (options.columnSpan) {
properties.addGridSpan(options.columnSpan);
if (options.margins) {
properties.addMargins(options.margins);
}
if (options.width) {
properties.setWidth(options.width.size, options.width.type);
if (options.textDirection) {
properties.setTextDirection(options.textDirection);
}
if (options.borders) {
if (options.borders.top) {
properties.Borders.addTopBorder(options.borders.top.style, options.borders.top.size, options.borders.top.color);
}
if (options.borders.bottom) {
properties.Borders.addBottomBorder(options.borders.bottom.style, options.borders.bottom.size, options.borders.bottom.color);
}
if (options.borders.left) {
properties.Borders.addLeftBorder(options.borders.left.style, options.borders.left.size, options.borders.left.color);
}
if (options.borders.right) {
properties.Borders.addRightBorder(options.borders.right.style, options.borders.right.size, options.borders.right.color);
}
if (options.verticalAlign) {
properties.setVerticalAlign(options.verticalAlign);
}
}

View File

@ -35,10 +35,6 @@ export class TableCellMargin extends IgnoreIfEmptyXmlComponent {
constructor(options: ITableCellMarginOptions) {
super("w:tblCellMar");
if (options.bottom) {
this.root.push(new BaseTableCellMargin("w:bottom", options.bottom));
}
if (options.top) {
this.root.push(new BaseTableCellMargin("w:top", options.top));
}
@ -47,6 +43,10 @@ export class TableCellMargin extends IgnoreIfEmptyXmlComponent {
this.root.push(new BaseTableCellMargin("w:left", options.left));
}
if (options.bottom) {
this.root.push(new BaseTableCellMargin("w:bottom", options.bottom));
}
if (options.right) {
this.root.push(new BaseTableCellMargin("w:right", options.right));
}

View File

@ -35,34 +35,34 @@ export class TableProperties extends IgnoreIfEmptyXmlComponent {
this.root.push(new TableStyle(options.style));
}
this.root.push(new TableCellMargin(options.cellMargin || {}));
if (options.float) {
this.root.push(new TableFloatProperties(options.float));
}
if (options.borders) {
this.root.push(new TableBorders(options.borders));
if (options.visuallyRightToLeft) {
this.root.push(new VisuallyRightToLeft());
}
if (options.width) {
this.root.push(new PreferredTableWidth(options.width.type, options.width.size));
}
if (options.float) {
this.root.push(new TableFloatProperties(options.float));
}
if (options.layout) {
this.root.push(new TableLayout(options.layout));
}
if (options.alignment) {
this.root.push(new Alignment(options.alignment));
}
if (options.borders) {
this.root.push(new TableBorders(options.borders));
}
if (options.shading) {
this.root.push(new TableShading(options.shading));
}
if (options.visuallyRightToLeft) {
this.root.push(new VisuallyRightToLeft());
if (options.layout) {
this.root.push(new TableLayout(options.layout));
}
this.root.push(new TableCellMargin(options.cellMargin || {}));
}
}

View File

@ -14,14 +14,6 @@ import { TableRow } from "./table-row";
const DEFAULT_TABLE_PROPERTIES = {
"w:tblCellMar": [
{
"w:bottom": {
_attr: {
"w:type": "auto",
"w:w": 0,
},
},
},
{
"w:top": {
_attr: {
@ -38,6 +30,14 @@ const DEFAULT_TABLE_PROPERTIES = {
},
},
},
{
"w:bottom": {
_attr: {
"w:type": "auto",
"w:w": 0,
},
},
},
{
"w:right": {
_attr: {
@ -177,7 +177,7 @@ describe("Table", () => {
};
expect(tree).to.deep.equal({
"w:tbl": [
{ "w:tblPr": [DEFAULT_TABLE_PROPERTIES, BORDERS, WIDTHS] },
{ "w:tblPr": [WIDTHS, BORDERS, DEFAULT_TABLE_PROPERTIES] },
{
"w:tblGrid": [{ "w:gridCol": { _attr: { "w:w": 100 } } }, { "w:gridCol": { _attr: { "w:w": 100 } } }],
},
@ -223,7 +223,7 @@ describe("Table", () => {
const cellP = { "w:p": [{ "w:r": [{ "w:t": [{ _attr: { "xml:space": "preserve" } }, "hello"] }] }] };
expect(tree).to.deep.equal({
"w:tbl": [
{ "w:tblPr": [DEFAULT_TABLE_PROPERTIES, BORDERS, WIDTHS] },
{ "w:tblPr": [WIDTHS, BORDERS, DEFAULT_TABLE_PROPERTIES] },
{
"w:tblGrid": [{ "w:gridCol": { _attr: { "w:w": 100 } } }, { "w:gridCol": { _attr: { "w:w": 100 } } }],
},
@ -270,7 +270,7 @@ describe("Table", () => {
const tree = new Formatter().format(table);
expect(tree).to.have.property("w:tbl").which.is.an("array").with.has.length.at.least(1);
expect(tree["w:tbl"][0]).to.deep.equal({
"w:tblPr": [DEFAULT_TABLE_PROPERTIES, BORDERS, WIDTHS, { "w:tblLayout": { _attr: { "w:type": "fixed" } } }],
"w:tblPr": [WIDTHS, BORDERS, { "w:tblLayout": { _attr: { "w:type": "fixed" } } }, DEFAULT_TABLE_PROPERTIES],
});
});
@ -290,7 +290,7 @@ describe("Table", () => {
const tree = new Formatter().format(table);
expect(tree).to.have.property("w:tbl").which.is.an("array").with.has.length.at.least(1);
expect(tree["w:tbl"][0]).to.deep.equal({
"w:tblPr": [DEFAULT_TABLE_PROPERTIES, BORDERS, WIDTHS, { "w:jc": { _attr: { "w:val": "center" } } }],
"w:tblPr": [WIDTHS, { "w:jc": { _attr: { "w:val": "center" } } }, BORDERS, DEFAULT_TABLE_PROPERTIES],
});
});
@ -315,8 +315,6 @@ describe("Table", () => {
expect(tree).to.have.property("w:tbl").which.is.an("array").with.has.length.at.least(1);
expect(tree["w:tbl"][0]).to.deep.equal({
"w:tblPr": [
DEFAULT_TABLE_PROPERTIES,
BORDERS,
{
"w:tblW": {
_attr: {
@ -325,7 +323,9 @@ describe("Table", () => {
},
},
},
BORDERS,
{ "w:tblLayout": { _attr: { "w:type": "fixed" } } },
DEFAULT_TABLE_PROPERTIES,
],
});
});
@ -477,9 +477,6 @@ describe("Table", () => {
expect(tree).to.have.property("w:tbl").which.is.an("array").with.has.length.at.least(1);
expect(tree["w:tbl"][0]).to.deep.equal({
"w:tblPr": [
DEFAULT_TABLE_PROPERTIES,
BORDERS,
WIDTHS,
{
"w:tblpPr": {
_attr: {
@ -496,6 +493,9 @@ describe("Table", () => {
},
},
},
WIDTHS,
BORDERS,
DEFAULT_TABLE_PROPERTIES,
],
});
});