fix: js ppr change if (#408)

main
bokuweb 2022-01-17 15:27:24 +09:00 committed by GitHub
parent 87b0439ac8
commit 22c6724d05
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
11 changed files with 275 additions and 83 deletions

View File

@ -297,6 +297,21 @@ impl Paragraph {
self
}
pub fn delete(mut self, author: impl Into<String>, date: impl Into<String>) -> Self {
self.property.run_property.del = Some(Delete::new().author(author).date(date));
self
}
pub fn insert(mut self, author: impl Into<String>, date: impl Into<String>) -> Self {
self.property.run_property.ins = Some(Insert::new_with_empty().author(author).date(date));
self
}
pub fn paragraph_property_change(mut self, p: ParagraphPropertyChange) -> Self {
self.property = self.property.paragraph_property_change(p);
self
}
pub fn raw_text(&self) -> String {
let mut s = "".to_string();
// For now support only run and ins.
@ -447,5 +462,5 @@ mod tests {
.add_delete(Delete::new().add_run(Run::new().add_delete_text("!!!!!")))
.raw_text();
assert_eq!(b, "HelloWorld".to_owned());
}}
}
}

View File

@ -4,6 +4,7 @@ use crate::documents::*;
use crate::xml_builder::*;
#[derive(Serialize, Debug, Clone, PartialEq)]
#[serde(rename_all = "camelCase")]
pub struct ParagraphPropertyChange {
pub author: String,
pub date: String,

View File

@ -1,4 +1,5 @@
import { Paragraph, ParagraphProperty } from "./paragraph";
import { Paragraph } from "./paragraph";
import { ParagraphProperty } from "./paragraph-property";
import { Insert } from "./insert";
import { Delete } from "./delete";
import { Hyperlink } from "./hyperlink";
@ -607,6 +608,21 @@ export class Docx {
paragraph = paragraph.widow_control(true);
}
if (p.property.paragraphPropertyChange) {
let change = wasm.createParagraphPropertyChange();
change = change
.author(p.property.paragraphPropertyChange._author)
.date(p.property.paragraphPropertyChange._date);
if (p.property.paragraphPropertyChange._property.numbering) {
change = change.numbering(
p.property.paragraphPropertyChange._property.numbering.id,
p.property.paragraphPropertyChange._property.numbering.level
);
}
paragraph = paragraph.paragraph_property_change(change);
}
return paragraph;
}
@ -1145,6 +1161,7 @@ export const readDocx = (buf: Uint8Array) => {
};
export * from "./paragraph";
export * from "./paragraph-property";
export * from "./insert";
export * from "./delete";
export * from "./border";

View File

@ -3,7 +3,7 @@ import {
createDefaultParagraphProperty,
ParagraphProperty,
SpecialIndentKind,
} from "./paragraph";
} from "./paragraph-property";
import { RunFonts, RunProperty } from "./run";
export type LevelSuffixType = "nothing" | "tab" | "space";

View File

@ -0,0 +1,100 @@
import { RunProperty, createDefaultRunProperty } from "./run";
export type AlignmentType =
| "center"
| "left"
| "right"
| "both"
| "justified"
| "distribute"
| "end";
export type SpecialIndentKind = "firstLine" | "hanging";
export type LineSpacingType = "atLeast" | "auto" | "exact";
export class LineSpacing {
_before?: number;
_after?: number;
_beforeLines?: number;
_afterLines?: number;
_line?: number;
_lineRule?: LineSpacingType;
before(v: number) {
this._before = v;
return this;
}
after(v: number) {
this._after = v;
return this;
}
beforeLines(v: number) {
this._beforeLines = v;
return this;
}
afterLines(v: number) {
this._afterLines = v;
return this;
}
line(v: number) {
this._line = v;
return this;
}
lineRule(v: LineSpacingType) {
this._lineRule = v;
return this;
}
}
export type ParagraphProperty = {
align?: AlignmentType;
styleId?: string;
indent?: {
left: number;
specialIndentKind?: SpecialIndentKind;
specialIndentSize?: number;
};
numbering?: {
id: number;
level: number;
};
lineSpacing?: LineSpacing;
runProperty: RunProperty;
keepNext: boolean;
keepLines: boolean;
pageBreakBefore: boolean;
widowControl: boolean;
paragraphPropertyChange?: ParagraphPropertyChange;
};
export const createDefaultParagraphProperty = (): ParagraphProperty => {
return {
runProperty: createDefaultRunProperty(),
keepNext: false,
keepLines: false,
pageBreakBefore: false,
widowControl: false,
};
};
export class ParagraphPropertyChange {
_author: string = "";
_date: string = "";
_property: ParagraphProperty = createDefaultParagraphProperty();
author(a: string) {
this._author = a;
return this;
}
date(a: string) {
this._date = a;
return this;
}
property(p: ParagraphProperty) {
this._property = p;
return this;
}
}

View File

@ -1,4 +1,12 @@
import { Run, RunProperty, RunFonts, createDefaultRunProperty } from "./run";
import { Run, RunFonts } from "./run";
import {
createDefaultParagraphProperty,
ParagraphProperty,
LineSpacing,
AlignmentType,
SpecialIndentKind,
ParagraphPropertyChange,
} from "./paragraph-property";
import { Insert } from "./insert";
import { Delete } from "./delete";
import { BookmarkStart } from "./bookmark-start";
@ -17,83 +25,6 @@ export type ParagraphChild =
| Comment
| CommentEnd;
export type AlignmentType =
| "center"
| "left"
| "right"
| "both"
| "justified"
| "distribute"
| "end";
export type SpecialIndentKind = "firstLine" | "hanging";
export type LineSpacingType = "atLeast" | "auto" | "exact";
export class LineSpacing {
_before?: number;
_after?: number;
_beforeLines?: number;
_afterLines?: number;
_line?: number;
_lineRule?: LineSpacingType;
before(v: number) {
this._before = v;
return this;
}
after(v: number) {
this._after = v;
return this;
}
beforeLines(v: number) {
this._beforeLines = v;
return this;
}
afterLines(v: number) {
this._afterLines = v;
return this;
}
line(v: number) {
this._line = v;
return this;
}
lineRule(v: LineSpacingType) {
this._lineRule = v;
return this;
}
}
export type ParagraphProperty = {
align?: AlignmentType;
styleId?: string;
indent?: {
left: number;
specialIndentKind?: SpecialIndentKind;
specialIndentSize?: number;
};
numbering?: {
id: number;
level: number;
};
lineSpacing?: LineSpacing;
runProperty: RunProperty;
keepNext: boolean;
keepLines: boolean;
pageBreakBefore: boolean;
widowControl: boolean;
};
export const createDefaultParagraphProperty = (): ParagraphProperty => {
return {
runProperty: createDefaultRunProperty(),
keepNext: false,
keepLines: false,
pageBreakBefore: false,
widowControl: false,
};
};
export class Paragraph {
hasNumberings = false;
children: ParagraphChild[] = [];
@ -209,4 +140,19 @@ export class Paragraph {
this.property.runProperty = { ...this.property.runProperty, fonts };
return this;
}
delete(author: string, date: string) {
this.property.runProperty.del = { author, date };
return this;
}
insert(author: string, date: string) {
this.property.runProperty.ins = { author, date };
return this;
}
paragraphPropertyChange(propertyChange: ParagraphPropertyChange) {
this.property.paragraphPropertyChange = propertyChange;
return this;
}
}

View File

@ -17,6 +17,16 @@ export type TextBorder = {
export type VertAlignType = "baseline" | "superscript" | "subscript";
export type RunPropertyDel = {
author: string;
date: string;
};
export type RunPropertyIns = {
author: string;
date: string;
};
export type RunProperty = {
size?: number;
color?: string;
@ -30,6 +40,8 @@ export type RunProperty = {
fonts?: RunFonts;
spacing?: number;
textBorder?: TextBorder;
ins?: RunPropertyIns;
del?: RunPropertyDel;
};
export const createDefaultRunProperty = (): RunProperty => {
@ -183,6 +195,16 @@ export class Run {
return this;
}
delete(author: string, date: string) {
this.property = { ...this.property, del: { author, date } };
return this;
}
insert(author: string, date: string) {
this.property = { ...this.property, ins: { author, date } };
return this;
}
textBorder(type: BorderType, size: number, space: number, color: string) {
this.property = {
...this.property,

View File

@ -2,7 +2,7 @@ import * as wasm from "./pkg";
import { createDefaultTableCellMargins, TableProperty } from "./table";
import { RunProperty, createDefaultRunProperty } from "./run";
import { createDefaultParagraphProperty, ParagraphProperty } from "./paragraph";
import { createDefaultParagraphProperty, ParagraphProperty } from "./paragraph-property";
export type StyleType =
| "paragraph"

View File

@ -1,6 +1,41 @@
use super::*;
use wasm_bindgen::prelude::*;
#[wasm_bindgen]
pub struct ParagraphPropertyChange(docx_rs::ParagraphPropertyChange);
#[wasm_bindgen(js_name = createParagraphPropertyChange)]
pub fn create_paragraph_property_change() -> ParagraphPropertyChange {
ParagraphPropertyChange(docx_rs::ParagraphPropertyChange::new())
}
#[wasm_bindgen]
impl ParagraphPropertyChange {
pub fn author(mut self, author: &str) -> Self {
self.0 = self.0.author(author);
self
}
pub fn date(mut self, date: &str) -> Self {
self.0 = self.0.date(date);
self
}
// TODO: For now only numbering supported.
pub fn numbering(mut self, id: usize, level: usize) -> Self {
let id = docx_rs::NumberingId::new(id);
let level = docx_rs::IndentLevel::new(level);
self.0.property = Box::new(self.0.property.numbering(id, level));
self
}
}
impl ParagraphPropertyChange {
pub fn take(self) -> docx_rs::ParagraphPropertyChange {
self.0
}
}
#[wasm_bindgen]
#[derive(Debug)]
pub struct Paragraph(docx_rs::Paragraph);
@ -141,6 +176,11 @@ impl Paragraph {
self.0 = self.0.widow_control(v);
self
}
pub fn paragraph_property_change(mut self, p: ParagraphPropertyChange) -> Self {
self.0.property = self.0.property.paragraph_property_change(p.take());
self
}
}
impl Paragraph {

View File

@ -22583,6 +22583,33 @@ exports[`writer should write nested table 3`] = `
</w:num></w:numbering>"
`;
exports[`writer should write pPrChange with inserted numbering 1`] = `
"<?xml version=\\"1.0\\" encoding=\\"UTF-8\\"?>
<Relationships xmlns=\\"http://schemas.openxmlformats.org/package/2006/relationships\\">
<Relationship Id=\\"rId1\\" Type=\\"http://schemas.openxmlformats.org/officeDocument/2006/relationships/styles\\" Target=\\"styles.xml\\" />
<Relationship Id=\\"rId2\\" Type=\\"http://schemas.openxmlformats.org/officeDocument/2006/relationships/fontTable\\" Target=\\"fontTable.xml\\" />
<Relationship Id=\\"rId3\\" Type=\\"http://schemas.openxmlformats.org/officeDocument/2006/relationships/settings\\" Target=\\"settings.xml\\" />
<Relationship Id=\\"rId5\\" Type=\\"http://schemas.microsoft.com/office/2011/relationships/commentsExtended\\" Target=\\"commentsExtended.xml\\" />
<Relationship Id=\\"rId7\\" Type=\\"http://schemas.openxmlformats.org/officeDocument/2006/relationships/numbering\\" Target=\\"numbering.xml\\" />
</Relationships>"
`;
exports[`writer should write pPrChange with inserted numbering 2`] = `
"<?xml version=\\"1.0\\" encoding=\\"UTF-8\\" standalone=\\"yes\\"?>
<w:document xmlns:o=\\"urn:schemas-microsoft-com:office:office\\" xmlns:r=\\"http://schemas.openxmlformats.org/officeDocument/2006/relationships\\" xmlns:v=\\"urn:schemas-microsoft-com:vml\\" xmlns:w=\\"http://schemas.openxmlformats.org/wordprocessingml/2006/main\\" xmlns:w10=\\"urn:schemas-microsoft-com:office:word\\" xmlns:wp=\\"http://schemas.openxmlformats.org/drawingml/2006/wordprocessingDrawing\\" xmlns:wps=\\"http://schemas.microsoft.com/office/word/2010/wordprocessingShape\\" xmlns:wpg=\\"http://schemas.microsoft.com/office/word/2010/wordprocessingGroup\\" xmlns:mc=\\"http://schemas.openxmlformats.org/markup-compatibility/2006\\" xmlns:wp14=\\"http://schemas.microsoft.com/office/word/2010/wordprocessingDrawing\\" xmlns:w14=\\"http://schemas.microsoft.com/office/word/2010/wordml\\" xmlns:w15=\\"http://schemas.microsoft.com/office/word/2012/wordml\\" mc:Ignorable=\\"w14 wp14\\">
<w:body><w:p w14:paraId=\\"00000005\\"><w:pPr><w:rPr /><w:numPr><w:numId w:val=\\"1\\" /><w:ilvl w:val=\\"0\\" /></w:numPr><w:pPrChange w:id=\\"0\\" w:author=\\"bokuweb\\" w:date=\\"\\"><w:pPr><w:rPr /></w:pPr></w:pPrChange></w:pPr><w:r><w:rPr /><w:t xml:space=\\"preserve\\">Hello world!!</w:t></w:r></w:p><w:sectPr><w:pgSz w:w=\\"11906\\" w:h=\\"16838\\" /><w:pgMar w:top=\\"1985\\" w:right=\\"1701\\" w:bottom=\\"1701\\" w:left=\\"1701\\" w:header=\\"851\\" w:footer=\\"992\\" w:gutter=\\"0\\" /><w:cols w:space=\\"425\\" /><w:docGrid w:type=\\"lines\\" w:linePitch=\\"360\\" /></w:sectPr></w:body>
</w:document>"
`;
exports[`writer should write pPrChange with inserted numbering 3`] = `
"<?xml version=\\"1.0\\" encoding=\\"UTF-8\\" standalone=\\"yes\\"?>
<w:numbering xmlns:r=\\"http://schemas.openxmlformats.org/officeDocument/2006/relationships\\" xmlns:o=\\"urn:schemas-microsoft-com:office:office\\" xmlns:v=\\"urn:schemas-microsoft-com:vml\\" xmlns:w=\\"http://schemas.openxmlformats.org/wordprocessingml/2006/main\\"><w:abstractNum w:abstractNumId=\\"1\\"><w:lvl w:ilvl=\\"0\\"><w:start w:val=\\"1\\" /><w:numFmt w:val=\\"decimal\\" /><w:lvlText w:val=\\"%1.\\" /><w:lvlJc w:val=\\"left\\" /><w:pPr><w:rPr /><w:ind w:left=\\"420\\" w:right=\\"0\\" w:hanging=\\"420\\" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl=\\"1\\"><w:start w:val=\\"1\\" /><w:numFmt w:val=\\"decimal\\" /><w:lvlText w:val=\\"(%2)\\" /><w:lvlJc w:val=\\"left\\" /><w:pPr><w:rPr /><w:ind w:left=\\"840\\" w:right=\\"0\\" w:hanging=\\"420\\" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl=\\"2\\"><w:start w:val=\\"1\\" /><w:numFmt w:val=\\"decimalEnclosedCircle\\" /><w:lvlText w:val=\\"%3\\" /><w:lvlJc w:val=\\"left\\" /><w:pPr><w:rPr /><w:ind w:left=\\"1260\\" w:right=\\"0\\" w:hanging=\\"420\\" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl=\\"3\\"><w:start w:val=\\"1\\" /><w:numFmt w:val=\\"decimal\\" /><w:lvlText w:val=\\"%4.\\" /><w:lvlJc w:val=\\"left\\" /><w:pPr><w:rPr /><w:ind w:left=\\"1680\\" w:right=\\"0\\" w:hanging=\\"420\\" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl=\\"4\\"><w:start w:val=\\"1\\" /><w:numFmt w:val=\\"decimal\\" /><w:lvlText w:val=\\"(%5)\\" /><w:lvlJc w:val=\\"left\\" /><w:pPr><w:rPr /><w:ind w:left=\\"2100\\" w:right=\\"0\\" w:hanging=\\"420\\" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl=\\"5\\"><w:start w:val=\\"1\\" /><w:numFmt w:val=\\"decimalEnclosedCircle\\" /><w:lvlText w:val=\\"%6\\" /><w:lvlJc w:val=\\"left\\" /><w:pPr><w:rPr /><w:ind w:left=\\"2520\\" w:right=\\"0\\" w:hanging=\\"420\\" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl=\\"6\\"><w:start w:val=\\"1\\" /><w:numFmt w:val=\\"decimal\\" /><w:lvlText w:val=\\"%7.\\" /><w:lvlJc w:val=\\"left\\" /><w:pPr><w:rPr /><w:ind w:left=\\"2940\\" w:right=\\"0\\" w:hanging=\\"420\\" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl=\\"7\\"><w:start w:val=\\"1\\" /><w:numFmt w:val=\\"decimal\\" /><w:lvlText w:val=\\"(%8)\\" /><w:lvlJc w:val=\\"left\\" /><w:pPr><w:rPr /><w:ind w:left=\\"3360\\" w:right=\\"0\\" w:hanging=\\"420\\" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl=\\"8\\"><w:start w:val=\\"1\\" /><w:numFmt w:val=\\"decimalEnclosedCircle\\" /><w:lvlText w:val=\\"%9\\" /><w:lvlJc w:val=\\"left\\" /><w:pPr><w:rPr /><w:ind w:left=\\"3780\\" w:right=\\"0\\" w:hanging=\\"420\\" /></w:pPr><w:rPr /></w:lvl></w:abstractNum><w:num w:numId=\\"1\\">
<w:abstractNumId w:val=\\"1\\" />
</w:num><w:num w:numId=\\"1\\">
<w:abstractNumId w:val=\\"0\\" />
</w:num></w:numbering>"
`;
exports[`writer should write page margin 1`] = `
"<?xml version=\\"1.0\\" encoding=\\"UTF-8\\"?>
<Relationships xmlns=\\"http://schemas.openxmlformats.org/package/2006/relationships\\">

View File

@ -596,4 +596,28 @@ describe("writer", () => {
}
}
});
test("should write pPrChange with inserted numbering", () => {
const p = new w.Paragraph()
.addRun(new w.Run().addText("Hello world!!"))
.numbering(1, 0)
.paragraphPropertyChange(
new w.ParagraphPropertyChange().author("bokuweb")
);
const num = new w.Numbering(1, 0);
const buffer = new w.Docx().addParagraph(p).addNumbering(num).build();
writeFileSync(
"../output/js/pprchange_with_inserted_numbering.docx",
buffer
);
const z = new Zip(Buffer.from(buffer));
for (const e of z.getEntries()) {
if (e.entryName.match(/document.xml|numbering.xml/)) {
expect(z.readAsText(e)).toMatchSnapshot();
}
}
});
});