Add comprehensive models and script for handling inline scripts and structured data
- Implement `remove-inline-scripts.js` to externalize Next.js inline scripts, enhancing CSP compliance. - Add models for `Book`, `Character`, `Story`, `Editor`, `System`, and `BookSerie` with relevant properties and utilities. - Include macOS entitlements plist for app development with advanced permissions. - Add utility functions to handle script hashing, cookie management, and content formatting.
This commit is contained in:
196
lib/models/Chapter.ts
Normal file
196
lib/models/Chapter.ts
Normal file
@@ -0,0 +1,196 @@
|
||||
import {SelectBoxProps} from "@/shared/interface";
|
||||
|
||||
export interface ActChapter {
|
||||
chapterInfoId: string;
|
||||
chapterId: string;
|
||||
title: string;
|
||||
chapterOrder: number;
|
||||
actId: number;
|
||||
incidentId?: string;
|
||||
plotPointId?: string;
|
||||
summary: string;
|
||||
goal: string;
|
||||
}
|
||||
|
||||
export interface ChapterListProps {
|
||||
chapterId: string;
|
||||
title: string;
|
||||
summary?: string;
|
||||
chapterOrder?: number;
|
||||
goal?: string;
|
||||
}
|
||||
|
||||
export interface ChapterProps {
|
||||
chapterId: string;
|
||||
chapterOrder: number;
|
||||
title: string;
|
||||
chapterContent: ChapterContent;
|
||||
}
|
||||
|
||||
export interface ChapterContent {
|
||||
version: number;
|
||||
content: string;
|
||||
wordsCount: number;
|
||||
}
|
||||
|
||||
export interface ChapterVersion {
|
||||
value: number;
|
||||
label: 'Invite' | 'Brouillon' | 'Perfectionnement' | 'Révision' | 'Finale';
|
||||
}
|
||||
|
||||
export type TiptapNode = {
|
||||
type: string;
|
||||
content?: TiptapNode[];
|
||||
text?: string;
|
||||
attrs?: {
|
||||
[key: string]: any;
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
export const chapterVersions: SelectBoxProps[] = [
|
||||
{value: '1', label: 'chapterVersions.prompt'},
|
||||
{value: '2', label: 'chapterVersions.draft'},
|
||||
{value: '3', label: 'chapterVersions.refine'},
|
||||
{value: '4', label: 'chapterVersions.review'},
|
||||
{value: '5', label: 'chapterVersions.final'},
|
||||
];
|
||||
|
||||
export default class Chapter {
|
||||
public static getPageCount(text: string): number {
|
||||
const charactersPerLine = 90;
|
||||
const linesPerPage = 40;
|
||||
|
||||
const lines: string[] = text.split('\n');
|
||||
let totalLines: number = 0;
|
||||
|
||||
lines.forEach((line: string) => {
|
||||
const lineLength: number = line.length;
|
||||
const estimatedLines: number = Math.ceil(lineLength / charactersPerLine);
|
||||
totalLines += estimatedLines;
|
||||
});
|
||||
|
||||
// Calcul du nombre de pages
|
||||
return Math.ceil(totalLines / linesPerPage);
|
||||
}
|
||||
static convertTiptapToHTML(node: TiptapNode): string {
|
||||
let html = '';
|
||||
|
||||
switch (node.type) {
|
||||
case 'doc':
|
||||
if (node.content) {
|
||||
node.content.forEach(childNode => {
|
||||
html += this.convertTiptapToHTML(childNode);
|
||||
});
|
||||
}
|
||||
break;
|
||||
|
||||
case 'paragraph':
|
||||
html += '<p>';
|
||||
if (node.content) {
|
||||
node.content.forEach(childNode => {
|
||||
html += this.convertTiptapToHTML(childNode);
|
||||
});
|
||||
}
|
||||
html += '</p>';
|
||||
break;
|
||||
|
||||
case 'text':
|
||||
let textContent = node.text || '';
|
||||
|
||||
// Apply attributes like bold, italic, etc.
|
||||
if (node.attrs) {
|
||||
if (node.attrs.bold) {
|
||||
textContent = `<strong>${textContent}</strong>`;
|
||||
}
|
||||
if (node.attrs.italic) {
|
||||
textContent = `<em>${textContent}</em>`;
|
||||
}
|
||||
if (node.attrs.underline) {
|
||||
textContent = `<u>${textContent}</u>`;
|
||||
}
|
||||
if (node.attrs.strike) {
|
||||
textContent = `<s>${textContent}</s>`;
|
||||
}
|
||||
if (node.attrs.link) {
|
||||
textContent = `<a href="${node.attrs.link.href}">${textContent}</a>`;
|
||||
}
|
||||
}
|
||||
|
||||
html += textContent;
|
||||
break;
|
||||
|
||||
case 'heading':
|
||||
const level = node.attrs?.level || 1;
|
||||
html += `<h${level}>`;
|
||||
if (node.content) {
|
||||
node.content.forEach(childNode => {
|
||||
html += this.convertTiptapToHTML(childNode);
|
||||
});
|
||||
}
|
||||
html += `</h${level}>`;
|
||||
break;
|
||||
|
||||
case 'bulletList':
|
||||
html += '<ul>';
|
||||
if (node.content) {
|
||||
node.content.forEach(childNode => {
|
||||
html += this.convertTiptapToHTML(childNode);
|
||||
});
|
||||
}
|
||||
html += '</ul>';
|
||||
break;
|
||||
|
||||
case 'orderedList':
|
||||
html += '<ol>';
|
||||
if (node.content) {
|
||||
node.content.forEach(childNode => {
|
||||
html += this.convertTiptapToHTML(childNode);
|
||||
});
|
||||
}
|
||||
html += '</ol>';
|
||||
break;
|
||||
|
||||
case 'listItem':
|
||||
html += '<li>';
|
||||
if (node.content) {
|
||||
node.content.forEach(childNode => {
|
||||
html += this.convertTiptapToHTML(childNode);
|
||||
});
|
||||
}
|
||||
html += '</li>';
|
||||
break;
|
||||
|
||||
case 'blockquote':
|
||||
html += '<blockquote>';
|
||||
if (node.content) {
|
||||
node.content.forEach(childNode => {
|
||||
html += this.convertTiptapToHTML(childNode);
|
||||
});
|
||||
}
|
||||
html += '</blockquote>';
|
||||
break;
|
||||
|
||||
case 'codeBlock':
|
||||
html += '<pre><code>';
|
||||
if (node.content) {
|
||||
node.content.forEach(childNode => {
|
||||
html += this.convertTiptapToHTML(childNode);
|
||||
});
|
||||
}
|
||||
html += '</code></pre>';
|
||||
break;
|
||||
|
||||
default:
|
||||
console.warn(`Unhandled node type: ${node.type}`);
|
||||
if (node.content) {
|
||||
node.content.forEach(childNode => {
|
||||
html += this.convertTiptapToHTML(childNode);
|
||||
});
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
return html;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user