Add the pageref element
This instruction is useful if you want to get the number of the page containing a specific bookmark.
This commit is contained in:
@ -1,3 +1,4 @@
|
||||
export * from "./hyperlink";
|
||||
export * from "./bookmark";
|
||||
export * from "./outline-level";
|
||||
export * from "./pageref";
|
||||
|
24
src/file/paragraph/links/pageref-field-instruction.spec.ts
Normal file
24
src/file/paragraph/links/pageref-field-instruction.spec.ts
Normal file
@ -0,0 +1,24 @@
|
||||
import { expect } from "chai";
|
||||
|
||||
import { Formatter } from "export/formatter";
|
||||
import { PageRefFieldInstruction } from "./pageref-field-instruction";
|
||||
|
||||
describe("PageRef field instruction", () => {
|
||||
describe("#constructor()", () => {
|
||||
it("should construct a pageref field instruction without options", () => {
|
||||
const instruction = new PageRefFieldInstruction("anchor");
|
||||
const tree = new Formatter().format(instruction);
|
||||
|
||||
expect(tree).to.be.deep.equal({
|
||||
"w:instrText": [
|
||||
{
|
||||
_attr: {
|
||||
"xml:space": "preserve",
|
||||
},
|
||||
},
|
||||
"PAGEREF anchor",
|
||||
],
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
25
src/file/paragraph/links/pageref-field-instruction.ts
Normal file
25
src/file/paragraph/links/pageref-field-instruction.ts
Normal file
@ -0,0 +1,25 @@
|
||||
import { SpaceType } from "file/space-type";
|
||||
import { XmlAttributeComponent, XmlComponent } from "file/xml-components";
|
||||
import { IPageRefOptions } from "./pageref-properties";
|
||||
|
||||
class TextAttributes extends XmlAttributeComponent<{ readonly space: SpaceType }> {
|
||||
protected readonly xmlKeys = { space: "xml:space" };
|
||||
}
|
||||
|
||||
export class PageRefFieldInstruction extends XmlComponent {
|
||||
constructor(bookmarkId: string, options: IPageRefOptions = {}) {
|
||||
super("w:instrText");
|
||||
this.root.push(new TextAttributes({ space: SpaceType.PRESERVE }));
|
||||
|
||||
let instruction = `PAGEREF ${bookmarkId}`;
|
||||
|
||||
if (options.hyperlink) {
|
||||
instruction = `${instruction} \\h`;
|
||||
}
|
||||
if (options.useRelativePosition) {
|
||||
instruction = `${instruction} \\p`;
|
||||
}
|
||||
|
||||
this.root.push(instruction);
|
||||
}
|
||||
}
|
16
src/file/paragraph/links/pageref-properties.ts
Normal file
16
src/file/paragraph/links/pageref-properties.ts
Normal file
@ -0,0 +1,16 @@
|
||||
// Options according to https://www.ecma-international.org/publications/standards/Ecma-376.htm (at Part 1, Page 1234)
|
||||
|
||||
export interface IPageRefOptions {
|
||||
/**
|
||||
* \h option - Creates a hyperlink to the bookmarked paragraph.
|
||||
*/
|
||||
readonly hyperlink?: boolean;
|
||||
/**
|
||||
* \p option - Causes the field to display its position relative to the source
|
||||
* bookmark. If the PAGEREF field is on the same page as the
|
||||
* bookmark, it omits "on page #" and returns "above" or "below"
|
||||
* only. If the PAGEREF field is not on the same page as the
|
||||
* bookmark, the string "on page #" is used.
|
||||
*/
|
||||
readonly useRelativePosition?: boolean;
|
||||
}
|
76
src/file/paragraph/links/pageref.spec.ts
Normal file
76
src/file/paragraph/links/pageref.spec.ts
Normal file
@ -0,0 +1,76 @@
|
||||
import { expect } from "chai";
|
||||
|
||||
import { Formatter } from "export/formatter";
|
||||
import { PageRef } from "./pageref";
|
||||
|
||||
describe("PageRef", () => {
|
||||
describe("#constructor()", () => {
|
||||
it("should construct a pageref without options", () => {
|
||||
const pageref = new PageRef("some_bookmark");
|
||||
const tree = new Formatter().format(pageref);
|
||||
expect(tree).to.be.deep.equal({
|
||||
"w:r": [
|
||||
{
|
||||
"w:fldChar": {
|
||||
_attr: {
|
||||
"w:dirty": true,
|
||||
"w:fldCharType": "begin",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"w:instrText": [
|
||||
{
|
||||
_attr: {
|
||||
"xml:space": "preserve",
|
||||
},
|
||||
},
|
||||
"PAGEREF some_bookmark",
|
||||
],
|
||||
},
|
||||
{
|
||||
"w:fldChar": {
|
||||
_attr: {
|
||||
"w:fldCharType": "end",
|
||||
},
|
||||
},
|
||||
},
|
||||
],
|
||||
});
|
||||
});
|
||||
|
||||
it("should construct a pageref with all the options", () => {
|
||||
const pageref = new PageRef("some_bookmark", { hyperlink: true, useRelativePosition: true });
|
||||
const tree = new Formatter().format(pageref);
|
||||
expect(tree).to.be.deep.equal({
|
||||
"w:r": [
|
||||
{
|
||||
"w:fldChar": {
|
||||
_attr: {
|
||||
"w:dirty": true,
|
||||
"w:fldCharType": "begin",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"w:instrText": [
|
||||
{
|
||||
_attr: {
|
||||
"xml:space": "preserve",
|
||||
},
|
||||
},
|
||||
"PAGEREF some_bookmark \\h \\p",
|
||||
],
|
||||
},
|
||||
{
|
||||
"w:fldChar": {
|
||||
_attr: {
|
||||
"w:fldCharType": "end",
|
||||
},
|
||||
},
|
||||
},
|
||||
],
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
13
src/file/paragraph/links/pageref.ts
Normal file
13
src/file/paragraph/links/pageref.ts
Normal file
@ -0,0 +1,13 @@
|
||||
// See https://www.ecma-international.org/publications/standards/Ecma-376.htm (at Part 1, Page 1234)
|
||||
import { Begin, End } from "file/paragraph/run/field";
|
||||
import { Run } from "../run";
|
||||
import { PageRefFieldInstruction } from "./pageref-field-instruction";
|
||||
import type { IPageRefOptions } from "./pageref-properties";
|
||||
|
||||
export class PageRef extends Run {
|
||||
constructor(bookmarkId: string, options: IPageRefOptions = {}) {
|
||||
super({
|
||||
children: [new Begin(true), new PageRefFieldInstruction(bookmarkId, options), new End()],
|
||||
});
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user