@openpresentation/opf-editor 0.7.1 → 0.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +50 -13
- package/dist/blocks.d.ts +2 -0
- package/dist/blocks.js +33 -0
- package/dist/canvas.d.ts +9 -0
- package/dist/canvas.js +33 -4
- package/dist/color-authoring.js +20 -0
- package/dist/exact-source.js +318 -0
- package/dist/font-defaults.js +25 -0
- package/dist/galleries.js +48 -8
- package/dist/index.d.ts +9 -2
- package/dist/index.js +21 -5
- package/dist/layout.d.ts +1 -1
- package/dist/layout.js +1 -1
- package/dist/presentation-ids.js +68 -0
- package/dist/rich-text-toolbar.js +2 -1
- package/dist/schema-inspector.js +4 -2
- package/dist/switches.d.ts +77 -0
- package/dist/switches.js +344 -0
- package/dist/transfer.js +5 -9
- package/package.json +50 -12
package/dist/galleries.js
CHANGED
|
@@ -117,6 +117,53 @@ export async function loadOpfGallery(input, options = {}) {
|
|
|
117
117
|
})),
|
|
118
118
|
};
|
|
119
119
|
}
|
|
120
|
+
const FONT_SCHEME_ENUMS = {
|
|
121
|
+
type: ["sans-serif", "serif", "monospace"],
|
|
122
|
+
app: ["PowerPoint", "Google Slides"],
|
|
123
|
+
languageFamily: ["latin", "ea", "cs"],
|
|
124
|
+
};
|
|
125
|
+
// A Font role object ({ family, weight?, style?, letterSpacing? }), or undefined.
|
|
126
|
+
function fontRole(value) {
|
|
127
|
+
if (typeof value === "string") return value ? { family: value } : undefined;
|
|
128
|
+
if (!value || typeof value !== "object" || typeof value.family !== "string")
|
|
129
|
+
return undefined;
|
|
130
|
+
const role = { family: value.family };
|
|
131
|
+
if (typeof value.weight === "number" && Number.isFinite(value.weight))
|
|
132
|
+
role.weight = value.weight;
|
|
133
|
+
if (value.style === "normal" || value.style === "italic")
|
|
134
|
+
role.style = value.style;
|
|
135
|
+
if (
|
|
136
|
+
typeof value.letterSpacing === "number" &&
|
|
137
|
+
Number.isFinite(value.letterSpacing)
|
|
138
|
+
)
|
|
139
|
+
role.letterSpacing = value.letterSpacing;
|
|
140
|
+
return role;
|
|
141
|
+
}
|
|
142
|
+
// Keep every font-scheme role that the catalog record schema defines: the OOXML
|
|
143
|
+
// pair and `code`. Gallery `heading`/`body` (string or Font object) map onto
|
|
144
|
+
// major/minor only, never role objects, so a later inline design.fontScheme
|
|
145
|
+
// major/minor override still wins (resolveFontFamilies checks roles before the
|
|
146
|
+
// pair). `accent` is not part of the record schema and is dropped.
|
|
147
|
+
function fontSchemeRecord(source, id) {
|
|
148
|
+
const record = {
|
|
149
|
+
$schema: "https://openpresentation.org/schema/opf-font-scheme/v1",
|
|
150
|
+
id,
|
|
151
|
+
name: source.name ?? id,
|
|
152
|
+
major:
|
|
153
|
+
typeof source.major === "string"
|
|
154
|
+
? source.major
|
|
155
|
+
: fontRole(source.heading)?.family,
|
|
156
|
+
minor:
|
|
157
|
+
typeof source.minor === "string"
|
|
158
|
+
? source.minor
|
|
159
|
+
: fontRole(source.body)?.family,
|
|
160
|
+
};
|
|
161
|
+
for (const [field, values] of Object.entries(FONT_SCHEME_ENUMS))
|
|
162
|
+
if (values.includes(source[field])) record[field] = source[field];
|
|
163
|
+
const code = fontRole(source.code);
|
|
164
|
+
if (code) record.code = code;
|
|
165
|
+
return record;
|
|
166
|
+
}
|
|
120
167
|
function attachDefinition(document, descriptor) {
|
|
121
168
|
const source = descriptor.metadata?.source,
|
|
122
169
|
category = descriptor.category ?? descriptor.metadata?.category;
|
|
@@ -161,14 +208,7 @@ function attachDefinition(document, descriptor) {
|
|
|
161
208
|
}
|
|
162
209
|
: {}),
|
|
163
210
|
};
|
|
164
|
-
} else if (kind === "fontSchemes")
|
|
165
|
-
record = {
|
|
166
|
-
$schema: "https://openpresentation.org/schema/opf-font-scheme/v1",
|
|
167
|
-
id,
|
|
168
|
-
name: source.name ?? id,
|
|
169
|
-
major: source.major ?? source.heading,
|
|
170
|
-
minor: source.minor ?? source.body,
|
|
171
|
-
};
|
|
211
|
+
} else if (kind === "fontSchemes") record = fontSchemeRecord(source, id);
|
|
172
212
|
else {
|
|
173
213
|
record = {
|
|
174
214
|
...source,
|
package/dist/index.d.ts
CHANGED
|
@@ -1,5 +1,8 @@
|
|
|
1
1
|
import type { PaginationOptions, PaginationResult } from "@openpresentation/opf/pagination";
|
|
2
2
|
import type { Composition, ComposeSlideOptions, SlideComposition } from "@openpresentation/opf/composition";
|
|
3
|
+
/** Reported when a font-scheme id matches no inline or bundled record; the default font scheme (`aptos`) is the base. */
|
|
4
|
+
export interface FontSchemeDiagnostic { code: "unresolved-font-scheme"; path: string; message: string; id: string; fallback: string }
|
|
5
|
+
export interface EditorDiagnosticOptions { onDiagnostic?: (diagnostic: FontSchemeDiagnostic) => void }
|
|
3
6
|
export declare const packageName = "@openpresentation/opf-editor";
|
|
4
7
|
|
|
5
8
|
export declare const releaseLane: Readonly<{
|
|
@@ -26,6 +29,7 @@ export type JsonPatchOperation =
|
|
|
26
29
|
export interface OPFValidationSummary {
|
|
27
30
|
valid: boolean;
|
|
28
31
|
errors: unknown[];
|
|
32
|
+
warnings: unknown[];
|
|
29
33
|
result: unknown;
|
|
30
34
|
}
|
|
31
35
|
|
|
@@ -57,8 +61,8 @@ export interface EditorEvent {
|
|
|
57
61
|
}
|
|
58
62
|
|
|
59
63
|
export interface EditorSession {
|
|
60
|
-
paginateSlide(slideIndex: number, options?: PaginationOptions, meta?: Record<string, unknown>): { change: EditorChange | null; pagination: PaginationResult };
|
|
61
|
-
composeSlide(slideIndex: number, options?: ComposeSlideOptions): SlideComposition;
|
|
64
|
+
paginateSlide(slideIndex: number, options?: PaginationOptions & EditorDiagnosticOptions, meta?: Record<string, unknown>): { change: EditorChange | null; pagination: PaginationResult };
|
|
65
|
+
composeSlide(slideIndex: number, options?: ComposeSlideOptions & EditorDiagnosticOptions): SlideComposition;
|
|
62
66
|
setComposition(slideIndex: number, composition: Composition, meta?: Record<string, unknown>): EditorChange;
|
|
63
67
|
readonly document: unknown;
|
|
64
68
|
readonly validation: OPFValidationSummary;
|
|
@@ -158,6 +162,9 @@ export declare function invertJsonPatch(document: unknown, operations: JsonPatch
|
|
|
158
162
|
|
|
159
163
|
export declare function validateOpfDocument(document: unknown, validator?: (document: unknown) => unknown): OPFValidationSummary;
|
|
160
164
|
|
|
165
|
+
/** Font families the slide resolves to (slide, deck, theme, then the shared default scheme). */
|
|
166
|
+
export declare function resolveSlideFonts(document: unknown, slideIndex?: number, options?: EditorDiagnosticOptions): { heading?: string; body?: string; code?: string; [role: string]: string | undefined };
|
|
167
|
+
|
|
161
168
|
export declare function createEditorSession(input: unknown, options?: CreateEditorSessionOptions): EditorSession;
|
|
162
169
|
|
|
163
170
|
export declare function createSvgTraceBinding(
|
package/dist/index.js
CHANGED
|
@@ -1,4 +1,6 @@
|
|
|
1
1
|
import { paginateSlide } from "@openpresentation/opf/pagination";
|
|
2
|
+
import { collectReservedPresentationIds } from "./presentation-ids.js";
|
|
3
|
+
import { DEFAULT_FONT_SCHEME, resolveFontSchemeReference } from "./font-defaults.js";
|
|
2
4
|
import { composeSlide, resolveCanvasDimensions, resolveFontFamilies } from "@openpresentation/opf/composition";
|
|
3
5
|
import {
|
|
4
6
|
catalogKinds,
|
|
@@ -6,7 +8,7 @@ import {
|
|
|
6
8
|
validatePresentation
|
|
7
9
|
} from "@openpresentation/opf";
|
|
8
10
|
|
|
9
|
-
function resolveCompositionOptions(document, slideIndex, options = {}) {
|
|
11
|
+
function resolveCompositionOptions(document, slideIndex, { onDiagnostic, ...options } = {}) {
|
|
10
12
|
const slide = document.slides?.[slideIndex];
|
|
11
13
|
if (!Number.isInteger(slideIndex) || !slide) throw new OPFEditorError("slide-index-out-of-range", "Slide index is out of range.");
|
|
12
14
|
const inline = document.catalogs?.layouts?.records ?? [];
|
|
@@ -16,12 +18,22 @@ function resolveCompositionOptions(document, slideIndex, options = {}) {
|
|
|
16
18
|
const themeId = typeof themeReference === "string" ? themeReference : themeReference.id;
|
|
17
19
|
const theme = document.catalogs?.themes?.records?.find(record => record.id === themeId)
|
|
18
20
|
?? bundledCatalogs.themes.find(record => record.id === themeId);
|
|
19
|
-
const reference = slide.design?.fontScheme ?? document.design?.fontScheme ?? theme?.fontScheme ??
|
|
20
|
-
const
|
|
21
|
-
const fontScheme =
|
|
21
|
+
const reference = slide.design?.fontScheme ?? document.design?.fontScheme ?? theme?.fontScheme ?? DEFAULT_FONT_SCHEME;
|
|
22
|
+
const fontPath = slide.design?.fontScheme !== undefined ? `slides.${slideIndex}.design.fontScheme` : document.design?.fontScheme !== undefined ? "design.fontScheme" : slide.design?.theme !== undefined ? `slides.${slideIndex}.design.theme` : "design.theme";
|
|
23
|
+
const { scheme: fontScheme, diagnostic } = resolveFontSchemeReference(reference, id => document.catalogs?.fontSchemes?.records?.find(record=>record.id===id) ?? bundledCatalogs.fontSchemes.find(record=>record.id===id), fontPath);
|
|
24
|
+
if (diagnostic) onDiagnostic?.(diagnostic);
|
|
22
25
|
return { ...resolveCanvasDimensions(slide.design?.dimensions ?? document.design?.dimensions ?? theme?.dimensions), fonts:resolveFontFamilies(fontScheme), contentAlignment:slide.design?.contentAlignment??document.design?.contentAlignment, titleAlignment:slide.design?.titleAlignment??document.design?.titleAlignment, contentBox:slide.design?.contentBox??document.design?.contentBox, presentation:document, ...options, layout, slideIndex };
|
|
23
26
|
}
|
|
24
27
|
|
|
28
|
+
/**
|
|
29
|
+
* The font families a slide resolves to (`heading`, `body`, `code`), by the same slide, deck,
|
|
30
|
+
* theme, default order that composition, pagination and export use. Hosts read this after a
|
|
31
|
+
* font-scheme or theme switch to show the fonts the preview now uses.
|
|
32
|
+
*/
|
|
33
|
+
export function resolveSlideFonts(document, slideIndex = 0, options = {}) {
|
|
34
|
+
return resolveCompositionOptions(document, slideIndex, options).fonts;
|
|
35
|
+
}
|
|
36
|
+
|
|
25
37
|
export const packageName = "@openpresentation/opf-editor";
|
|
26
38
|
|
|
27
39
|
export const releaseLane = Object.freeze({
|
|
@@ -142,6 +154,7 @@ export function validateOpfDocument(document, validator = validatePresentation)
|
|
|
142
154
|
return {
|
|
143
155
|
valid,
|
|
144
156
|
errors: Array.isArray(result?.errors) ? result.errors : [],
|
|
157
|
+
warnings: Array.isArray(result?.warnings) ? result.warnings : [],
|
|
145
158
|
result
|
|
146
159
|
};
|
|
147
160
|
}
|
|
@@ -243,7 +256,10 @@ export function createEditorSession(input, options = {}) {
|
|
|
243
256
|
},
|
|
244
257
|
paginateSlide(slideIndex, options = {}, meta = {}) {
|
|
245
258
|
const resolved = resolveCompositionOptions(document, slideIndex, options);
|
|
246
|
-
const pagination = paginateSlide(document.slides[slideIndex], {
|
|
259
|
+
const pagination = paginateSlide(document.slides[slideIndex], {
|
|
260
|
+
...resolved,
|
|
261
|
+
reservedIds: collectReservedPresentationIds(document),
|
|
262
|
+
});
|
|
247
263
|
// Pagination can persist a readability policy without adding a page. Commit
|
|
248
264
|
// that change too, so preview/export use the same minimum that was evaluated.
|
|
249
265
|
if (pagination.slides.length === 1 && jsonEqual(pagination.slides[0], document.slides[slideIndex])) return { change: null, pagination };
|
package/dist/layout.d.ts
CHANGED
|
@@ -5,6 +5,6 @@ export declare function prepareTrackResize(document:unknown,flow:ComposedFlow,bo
|
|
|
5
5
|
document:unknown;patches:JsonPatchOperation[];composition:Composition;fraction:number;
|
|
6
6
|
};
|
|
7
7
|
|
|
8
|
-
export {prepareBlockMove,listBlockContainers,prepareBlockInsert,prepareBlockDuplicate,prepareBlockRemove,createContentBlock} from './blocks.js';
|
|
8
|
+
export {prepareBlockMove,listBlockContainers,prepareBlockInsert,prepareBlockDuplicate,prepareBlockRemove,prepareBlockReplace,createContentBlock} from './blocks.js';
|
|
9
9
|
|
|
10
10
|
export type {PreparedBlockChange,ContentBlockKind} from './blocks.js';
|
package/dist/layout.js
CHANGED
|
@@ -31,4 +31,4 @@ export function prepareTrackResize(document, flow, boundary, fraction) {
|
|
|
31
31
|
return {document:next,patches,composition,fraction:share};
|
|
32
32
|
}
|
|
33
33
|
|
|
34
|
-
export {prepareBlockMove,listBlockContainers,prepareBlockInsert,prepareBlockDuplicate,prepareBlockRemove,createContentBlock} from './blocks.js';
|
|
34
|
+
export {prepareBlockMove,listBlockContainers,prepareBlockInsert,prepareBlockDuplicate,prepareBlockRemove,prepareBlockReplace,createContentBlock} from './blocks.js';
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
/** Shared slide and content-payload id collection (matches @openpresentation/opf pagination). */
|
|
2
|
+
|
|
3
|
+
const promotedRegionKeys = [
|
|
4
|
+
"left", "center", "right", "left+center", "center+right", "left+center+right",
|
|
5
|
+
"top", "middle", "bottom", "top+middle", "middle+bottom", "top+middle+bottom",
|
|
6
|
+
"top:left", "top:center", "top:right", "top:left+center", "top:center+right", "top:left+center+right",
|
|
7
|
+
"middle:left", "middle:center", "middle:right", "middle:left+center", "middle:center+right", "middle:left+center+right",
|
|
8
|
+
"bottom:left", "bottom:center", "bottom:right", "bottom:left+center", "bottom:center+right", "bottom:left+center+right",
|
|
9
|
+
"top+middle:left", "top+middle:center", "top+middle:right", "top+middle:left+center", "top+middle:center+right", "top+middle:left+center+right",
|
|
10
|
+
"middle+bottom:left", "middle+bottom:center", "middle+bottom:right", "middle+bottom:left+center", "middle+bottom:center+right", "middle+bottom:left+center+right",
|
|
11
|
+
"top+middle+bottom:left", "top+middle+bottom:center", "top+middle+bottom:right", "top+middle+bottom:left+center", "top+middle+bottom:center+right", "top+middle+bottom:left+center+right",
|
|
12
|
+
];
|
|
13
|
+
|
|
14
|
+
const MAX_COMPOSITION_DEPTH = 8;
|
|
15
|
+
|
|
16
|
+
function isRecord(value) {
|
|
17
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
export function visitContentPayloads(slide, slidePath, visit) {
|
|
21
|
+
const walk = (payload, path, depth, ancestors) => {
|
|
22
|
+
visit(payload, path);
|
|
23
|
+
if (!Array.isArray(payload.blocks) || depth >= MAX_COMPOSITION_DEPTH || ancestors.includes(payload)) return;
|
|
24
|
+
const nested = [...ancestors, payload];
|
|
25
|
+
payload.blocks.forEach((block, index) => {
|
|
26
|
+
if (isRecord(block)) walk(block, path ? `${path}.blocks.${index}` : `blocks.${index}`, depth + 1, nested);
|
|
27
|
+
});
|
|
28
|
+
};
|
|
29
|
+
if (Array.isArray(slide?.blocks)) {
|
|
30
|
+
slide.blocks.forEach((block, index) => {
|
|
31
|
+
if (isRecord(block)) walk(block, slidePath ? `${slidePath}.blocks.${index}` : `blocks.${index}`, 0, []);
|
|
32
|
+
});
|
|
33
|
+
}
|
|
34
|
+
for (const key of promotedRegionKeys) {
|
|
35
|
+
const region = slide?.[key];
|
|
36
|
+
if (isRecord(region)) walk(region, slidePath ? `${slidePath}.${key}` : key, 0, []);
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
export function slideIds(slide) {
|
|
41
|
+
const ids = typeof slide?.id === "string" ? [slide.id] : [];
|
|
42
|
+
if (isRecord(slide)) {
|
|
43
|
+
visitContentPayloads(slide, "", (payload) => {
|
|
44
|
+
if (typeof payload.id === "string") ids.push(payload.id);
|
|
45
|
+
});
|
|
46
|
+
}
|
|
47
|
+
return ids;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
export function collectReservedPresentationIds(document) {
|
|
51
|
+
const ids = [];
|
|
52
|
+
for (const slide of document.slides ?? []) ids.push(...slideIds(slide));
|
|
53
|
+
return ids.filter(Boolean);
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
function remapNodeId(node, ids) {
|
|
57
|
+
if (typeof node.id !== "string") return;
|
|
58
|
+
const base = node.id;
|
|
59
|
+
let suffix = 2;
|
|
60
|
+
while (ids.has(node.id)) node.id = `${base}-${suffix++}`;
|
|
61
|
+
ids.add(node.id);
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
/** Remap slide and payload ids when inserting slides (shared document namespace). */
|
|
65
|
+
export function remapSlideTreeIds(slide, ids) {
|
|
66
|
+
remapNodeId(slide, ids);
|
|
67
|
+
visitContentPayloads(slide, "", (payload) => remapNodeId(payload, ids));
|
|
68
|
+
}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import {richTextContent, formatRichTextRange, replaceRichTextRange} from './rich-text.js';
|
|
2
|
+
import { isAuthoringColorRef } from './color-authoring.js';
|
|
2
3
|
|
|
3
4
|
/** Native SVG selection stays on the exact rendered glyphs; no HTML reflow. */
|
|
4
5
|
export function createRichTextToolbar(root, {editor, report, beforeChange, onProperties, onTyping, validateChange, onChange}) {
|
|
@@ -80,7 +81,7 @@ export function createRichTextToolbar(root, {editor, report, beforeChange, onPro
|
|
|
80
81
|
toolbar.append(input);return input;
|
|
81
82
|
}
|
|
82
83
|
const color=field('Text color');
|
|
83
|
-
color.onchange=()=>{try {if(color.value
|
|
84
|
+
color.onchange=()=>{try {if(color.value&&!isAuthoringColorRef(color.value))throw new Error('Use a hex color, scheme slot or role, or var:<id> (for example #2563eb, accent2, text, or var:risk).');apply({color:color.value||null});}catch(error){report(error);}};
|
|
84
85
|
const size=field('Font size (pt)','number');size.min='0.1';size.step='0.5';size.style.width='80px';
|
|
85
86
|
size.onchange=()=>{try{apply({fontSize:size.value?Number(size.value):null});}catch(error){report(error);}};
|
|
86
87
|
const family=field('Font family');family.onchange=()=>{try{apply({fontFamily:family.value||null});}catch(error){report(error);}};
|
package/dist/schema-inspector.js
CHANGED
|
@@ -17,8 +17,10 @@ export function createSchemaInspector(container, {editor,path='',onDraft,onCommi
|
|
|
17
17
|
function check(){
|
|
18
18
|
const validation=validateOpfDocument(draft);
|
|
19
19
|
apply.disabled=!dirty||!validation.valid;
|
|
20
|
-
|
|
21
|
-
|
|
20
|
+
const warningNote=validation.warnings?.length?` · ${validation.warnings.length} warning${validation.warnings.length===1?'':'s'}`:'';
|
|
21
|
+
status.textContent=dirty?`Draft changes · apply to save${warningNote}`:`No pending changes${warningNote}`;
|
|
22
|
+
const issues=[...(validation.valid?[]:validation.errors.slice(0,3).map(error=>`${error.path||'/'}: ${error.message}`)),...(validation.warnings?.slice(0,2).map(warning=>`${warning.path||'/'}: ${warning.message}`)??[])];
|
|
23
|
+
showError(issues.join('\n'));
|
|
22
24
|
if(validation.valid)try{onDraft?.({document:structuredClone(draft),path:selected,dirty});}catch(error){showError(`Preview: ${error.message}`);onError?.(error);}
|
|
23
25
|
}
|
|
24
26
|
function mutate(operations,redraw=true){draft=applyJsonPatch(draft,operations);dirty=JSON.stringify(draft)!==base;if(redraw)render();check();}
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
import type { EditorChange, EditorSession, JsonPatchOperation } from "./index.js";
|
|
2
|
+
|
|
3
|
+
/** The 14 pptx.gallery dimensions. */
|
|
4
|
+
export declare const SWITCH_DIMENSIONS: readonly [
|
|
5
|
+
"layouts",
|
|
6
|
+
"color-schemes",
|
|
7
|
+
"font-schemes",
|
|
8
|
+
"languages",
|
|
9
|
+
"backgrounds",
|
|
10
|
+
"narratives",
|
|
11
|
+
"charts",
|
|
12
|
+
"themes",
|
|
13
|
+
"audiences",
|
|
14
|
+
"tones",
|
|
15
|
+
"socials",
|
|
16
|
+
"headers-footers",
|
|
17
|
+
"blocks",
|
|
18
|
+
"image-treatments",
|
|
19
|
+
];
|
|
20
|
+
export type SwitchDimension = (typeof SWITCH_DIMENSIONS)[number];
|
|
21
|
+
|
|
22
|
+
export interface DimensionSwitchOptions {
|
|
23
|
+
/** Required for layouts and charts; for design dimensions it scopes the switch to one slide (default: the deck). */
|
|
24
|
+
slideIndex?: number;
|
|
25
|
+
/** blocks: the complete block (`slides.0.blocks.1`) or one-payload slide/region to replace. charts: the block holding the chart (default: the slide's first chart). */
|
|
26
|
+
path?: string | string[];
|
|
27
|
+
/** A gallery item's catalog record, added inline in the same transaction when the id is not already defined. */
|
|
28
|
+
record?: Record<string, unknown> & { id: string };
|
|
29
|
+
/** Extra caller-loaded catalog records by kind. */
|
|
30
|
+
catalogs?: Record<string, unknown>;
|
|
31
|
+
catalogSources?: Record<string, unknown>;
|
|
32
|
+
/** themes: also write the theme's color scheme, font scheme, background and dimensions to the deck design (default true). */
|
|
33
|
+
bundle?: boolean;
|
|
34
|
+
/** Deck-scope design switches: remove slide-level values that would hide the switch. */
|
|
35
|
+
clearSlideOverrides?: boolean;
|
|
36
|
+
/** socials: which document field holds the handle (default "speaker") and, for an array, which entry (default 0). */
|
|
37
|
+
owner?: "speaker" | "organization";
|
|
38
|
+
index?: number;
|
|
39
|
+
/** blocks: media source for the image and video kinds. */
|
|
40
|
+
source?: string;
|
|
41
|
+
/** Session change metadata (switchDimension only). */
|
|
42
|
+
meta?: Record<string, unknown>;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
export type DimensionSwitchValue =
|
|
46
|
+
| string
|
|
47
|
+
| string[]
|
|
48
|
+
| { platform: string; handle: string }
|
|
49
|
+
| { header?: unknown; footer?: unknown }
|
|
50
|
+
| { slideImage?: unknown; imageFill?: string | null }
|
|
51
|
+
| Record<string, unknown>;
|
|
52
|
+
|
|
53
|
+
export interface PreparedDimensionSwitch {
|
|
54
|
+
dimension: SwitchDimension;
|
|
55
|
+
scope: "deck" | "slide" | "block";
|
|
56
|
+
slideIndex?: number;
|
|
57
|
+
document: unknown;
|
|
58
|
+
patches: JsonPatchOperation[];
|
|
59
|
+
changed: boolean;
|
|
60
|
+
/** Slides whose own design hides a deck-level switch. */
|
|
61
|
+
shadowed: number[];
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
export interface DimensionSwitchChange extends Omit<EditorChange, "document" | "patches"> {
|
|
65
|
+
document: unknown;
|
|
66
|
+
patches: JsonPatchOperation[];
|
|
67
|
+
dimension: SwitchDimension;
|
|
68
|
+
scope: "deck" | "slide" | "block";
|
|
69
|
+
slideIndex?: number;
|
|
70
|
+
changed: boolean;
|
|
71
|
+
shadowed: number[];
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
/** Compute and validate the patch for one dimension without changing any session. */
|
|
75
|
+
export declare function prepareDimensionSwitch(document: unknown, dimension: SwitchDimension, value: DimensionSwitchValue, options?: DimensionSwitchOptions): PreparedDimensionSwitch;
|
|
76
|
+
/** Apply one dimension switch to a session as a single undoable transaction. */
|
|
77
|
+
export declare function switchDimension(editor: EditorSession, dimension: SwitchDimension, value: DimensionSwitchValue, options?: DimensionSwitchOptions): DimensionSwitchChange;
|