@rshirohara/repixe-rekurke
Version:
repixe plugin that turns pixiv novel format into kakuyomu novel format to support rekurke.
163 lines (162 loc) • 4.86 kB
JavaScript
export function convertRoot(tree, options) {
return {
type: "root",
children: [...tree.children]
.flatMap((node) => convertRootChildren(node, options))
.filter((node) => node !== undefined),
};
}
export function convertRootChildren(node, options) {
return [node].flatMap((node) => {
switch (node.type) {
case "heading":
case "pageBreak":
case "paragraph": {
return convertFlowContent(node, options).filter((node) => node !== undefined);
}
case "break":
case "image":
case "link":
case "pageReference":
case "ruby":
case "text": {
return convertPhrasingContent(node, options).filter((node) => node !== undefined);
}
default: {
return undefined;
}
}
});
}
// FlowContent
export function convertFlowContent(node, options) {
return [node].flatMap((node) => {
switch (node.type) {
case "heading": {
return convertHeading(node, options);
}
case "pageBreak": {
return convertPageBreak(node, options);
}
case "paragraph": {
return convertParagraph(node, options);
}
default: {
return undefined;
}
}
});
}
function convertHeading(node, options) {
return {
type: "paragraph",
children: [...node.children]
.flatMap((node) => convertInlinePhrasingContent(node, options))
.filter((node) => node !== undefined),
};
}
function convertPageBreak(_, options) {
if (options.preserveUnmatchedSyntax) {
return {
type: "paragraph",
children: [{ type: "text", value: "[newpage]" }],
};
}
return undefined;
}
function convertParagraph(node, options) {
return {
type: "paragraph",
children: [...node.children]
.flatMap((node) => convertPhrasingContent(node, options))
.filter((node) => node !== undefined),
};
}
// PhrasingContent
export function convertPhrasingContent(node, options) {
return [node].flatMap((node) => {
switch (node.type) {
case "break": {
return convertBreak(node, options);
}
case "image": {
return convertImage(node, options);
}
case "link": {
return convertLink(node, options);
}
case "pageReference": {
return convertPageReference(node, options);
}
case "ruby":
case "text": {
return convertInlinePhrasingContent(node, options).filter((node) => node !== undefined);
}
default: {
return undefined;
}
}
});
}
function convertBreak(_node, _options) {
return { type: "break" };
}
function convertImage(node, options) {
if (options.preserveUnmatchedSyntax) {
return {
type: "text",
value: `[pixivimage:${node.illustId}${node.pageNumber !== undefined ? `-${node.pageNumber}` : ""}]`,
};
}
return undefined;
}
function convertLink(node, options) {
if (options.preserveUnmatchedSyntax) {
const text = [...node.children]
.map((node) => {
switch (node.type) {
case "ruby": {
return `[[rb: ${node.value} > ${node.ruby}]]`;
}
case "text": {
return node.value;
}
default: {
return "";
}
}
})
.join("");
return [{ type: "text", value: `[[jumpuri: ${text} > ${node.url}]]` }];
}
return [...node.children]
.flatMap((node) => convertInlinePhrasingContent(node, options))
.filter((node) => node !== undefined);
}
function convertPageReference(node, options) {
if (options.preserveUnmatchedSyntax) {
return { type: "text", value: `[jump:${node.pageNumber}]` };
}
return undefined;
}
export function convertInlinePhrasingContent(node, options) {
return [node].flatMap((node) => {
switch (node.type) {
case "ruby": {
return convertRuby(node, options);
}
case "text": {
return convertText(node, options);
}
default: {
return undefined;
}
}
});
}
function convertRuby(node, _) {
return { type: "ruby", value: node.value, ruby: node.ruby };
}
function convertText(node, _) {
return { type: "text", value: node.value };
}