import CodeMirror from 'codemirror';import SyntaxBase from '../src/core/SyntaxBase';import { FormulaMenu } from '@/toolbars/BubbleFormula';export interface CherryExternalsOptions { [key: string]: any;}export interface CustomMenuType { [key: string]: any;}type CherryToolbarsCustomType = { CustomMenuType: CustomMenuType}type CherryCustomOptions = { CustomToolbar: CherryToolbarsCustomType}export interface Cherry<T extends CherryCustomOptions = CherryCustomOptions> { options: CherryOptions<T>;}export type CherryOptions<T extends CherryCustomOptions = CherryCustomOptions> = Partial<_CherryOptions<T>>;export interface _CherryOptions<T extends CherryCustomOptions = CherryCustomOptions> { openai: any; externals: CherryExternalsOptions; engine: CherryEngineOptions; editor: CherryEditorOptions; toolbars: CherryToolbarsOptions<T['CustomToolbar']> | undefined; // 打开draw.io编辑页的url,如果为空则drawio按钮失效 drawioIframeUrl: string; // drawio iframe的样式 drawioIframeStyle: string; fileUpload: CherryFileUploadHandler; fileTypeLimitMap: { video: string, audio: string, image: string, word: string, pdf: string, file: string, }; multipleFileSelection: { video: boolean; audio: boolean; image: boolean; word: boolean; pdf: boolean; file: boolean; }; nameSpace: string; theme: { className: string, label: string }[]; themeNameSpace: string, themeSettings: { themeList: { className: string, label: string }[], mainTheme: string, codeBlockTheme: string, inlineCodeTheme: 'red' | 'black', toolbarTheme: 'light' | 'dark', } callback: { urlProcessor?: (url: string, srcType: 'image' | 'audio' | 'video' | 'autolink' | 'link', callback?: any) => string; fileUpload?: CherryFileUploadHandler; fileUploadMulti?: CherryFileUploadHandler; afterChange?: CherryLifecycle; afterInit?: CherryLifecycle; beforeImageMounted?: (srcProp: string, src: string) => { srcProp: string; src: string }; onClickPreview?: (e: MouseEvent) => void; onCopyCode?: (e: ClipboardEvent, code: string) => string | false; changeString2Pinyin?: (str: string) => string; onPaste?: (clipboardData: ClipboardEvent['clipboardData'], cherry: Cherry) => string | boolean; onExpandCode?: (e: MouseEvent, code: string) => string; onUnExpandCode?: (e: MouseEvent, code: string) => string; }; event: { focus?: ({ e: MouseEvent, cherry: Cherry }) => void; blur?: ({ e: MouseEvent, cherry: Cherry }) => void; afterChange?: CherryLifecycle; afterInit?: CherryLifecycle; selectionChange?: ({ selections: [], lastSelections: [], info }) => void; afterChangeLocale?: (locale: string) => void; changeMainTheme?: (theme: string) => void; changeCodeBlockTheme?: (theme: string) => void; }; previewer: CherryPreviewerOptions; isPreviewOnly: boolean; autoScrollByCursor: boolean; forceAppend: boolean; autoScrollByHashAfterInit: boolean; id?: string; el?: HTMLElement; value: string; instanceId?: string; locale: string; locales: { [locale: string]: Record<string, string> }}export interface CustomSyntaxRegConfig { syntaxClass: typeof SyntaxBase; before?: string; after?: string; force?: boolean;}export interface CherryEngineOptions { global?: { classicBr?: boolean; urlProcessor?: (url: string, srcType: 'image' | 'audio' | 'video' | 'autolink' | 'link', callback?: any) => string; htmlWhiteList?: string; htmlBlackList?: string, flowSessionContext?: boolean; flowSessionCursor?: string; }; syntax?: { // 语法开关 // 'hookName': false, // 语法配置 // 'hookName': { // // } link?: { target?: '_blank' | '', rel?: '_blank' | 'nofollow' | '', }, autoLink?: { target?: '_blank' | '', rel?: '_blank' | 'nofollow' | '', enableShortLink?: boolean, shortLinkLength?: number, }, list?: { listNested?: boolean, // 同级列表类型转换后变为子级 indentSpace?: number, // 默认2个空格缩进 }, table: { enableChart?: boolean, selfClosing?: boolean, // 自动闭合,为true时,当输入第一行table内容时,cherry会自动按表格进行解析 // chartRenderEngine: EChartsTableEngine, // externals: ['echarts'], }, inlineCode?: { // theme: 'red', }, codeBlock?: { // theme: 'dark', // 默认为深色主题 wrap?: boolean, // 超出长度是否换行,false则显示滚动条 lineNumber?: boolean, // 默认显示行号 copyCode?: boolean, // 是否显示“复制”按钮 editCode?: boolean, // 是否显示“编辑”按钮 changeLang?: boolean, // 是否显示“切换语言”按钮 expandCode?: boolean, // 是否展开/收起代码块,当代码块行数大于10行时,会自动收起代码块 selfClosing?: boolean, // 自动闭合,为true时,当md中有奇数个```时,会自动在md末尾追加一个``` customRenderer?: { // 自定义语法渲染器 }, mermaid?: { svg2img?: boolean, // 是否将mermaid生成的画图变成img格式 }, indentedCodeBlock?: boolean, customBtns?: { 'html': '', 'onClick': (event: MouseEvent, code: string, language: string) => {}, }[], }, emoji?: { useUnicode?: boolean, // 是否使用unicode进行渲染 }, fontEmphasis?: { allowWhitespace?: boolean, selfClosing?: boolean, // 自动闭合,为true时,当输入**XXX时,会自动在末尾追加** }, strikethrough?: { needWhitespace?: boolean, }, mathBlock?: { engine?: 'katex' | 'MathJax', // katex或MathJax src?: string, plugins?: boolean, // 加载插件 }, inlineMath?: { engine?: 'katex' | 'MathJax', // katex或MathJax src?: string, }, toc?: { allowMultiToc?: boolean, showAutoNumber?: boolean, }, header?: { anchorStyle?: 'default' | 'autonumber' | 'none', strict?: boolean, }, htmlBlock?: { filterStyle?: boolean, }, }; customSyntax?: Record<string, CustomSyntaxRegConfig['syntaxClass'] | CustomSyntaxRegConfig>;}export type EditorMode = | 'editOnly' | 'previewOnly' | 'edit&preview';export interface CherryEditorOptions { id?: string; // textarea 的id属性值 name?: string; // textarea 的name属性值 autoSave2Textarea?: boolean; // 是否自动将编辑区的内容回写到textarea里 theme?: string; height?: string; defaultModel?: EditorMode; convertWhenPaste?: boolean; keyMap?: 'sublime' | 'vim'; codemirror?: object; writingStyle?: string; editor?: CodeMirror.Editor; keepDocumentScrollAfterInit?: boolean; showFullWidthMark?: boolean; showSuggestList?: boolean;}export type CherryLifecycle = (text: string, html: string) => void;export interface CherryPreviewerOptions { dom?: HTMLDivElement | false; className?: string; enablePreviewerBubble?: boolean; floatWhenClosePreviewer?: boolean; // 配置图片懒加载的逻辑 lazyLoadImg?: { // 加载图片时如果需要展示loaing图,则配置loading图的地址 loadingImgPath?: string; // 同一时间最多有几个图片请求,最大同时加载6张图片 maxNumPerTime?: 1 | 2 | 3 | 4 | 5 | 6, // 不进行懒加载处理的图片数量,如果为0,即所有图片都进行懒加载处理, 如果设置为-1,则所有图片都不进行懒加载处理 noLoadImgNum?: number, // 首次自动加载几张图片(不论图片是否滚动到视野内),autoLoadImgNum = -1 表示会自动加载完所有图片 autoLoadImgNum?: -1 | number; // 针对加载失败的图片 或 beforeLoadOneImgCallback 返回false 的图片,最多尝试加载几次,为了防止死循环,最多5次。以图片的src为纬度统计重试次数 maxTryTimesPerSrc?: 0 | 1 | 2 | 3 | 4 | 5, // 加载一张图片之前的回调函数,函数return false 会终止加载操作 beforeLoadOneImgCallback?: (img: HTMLImageElement) => void | boolean; // 加载一张图片失败之后的回调函数 failLoadOneImgCallback?: (img: HTMLImageElement) => void; // 加载一张图片之后的回调函数,如果图片加载失败,则不会回调该函数 afterLoadOneImgCallback?: (img: HTMLImageElement) => void; // 加载完所有图片后调用的回调函数 afterLoadAllImgCallback?: () => void; };}export type CherryToolbarSeparator = '|';export type CherryDefaultToolbar = | 'audio' | 'bar-table' | 'bold' | 'br' | 'checklist' | 'code' | 'codeTheme' | 'color' | 'copy' | 'detail' | 'drawIo' | 'export' | 'file' | 'fullScreen' | 'formula' | 'graph' | 'h1' | 'h2' | 'h3' | 'header' | 'hr' | 'image' | 'insert' | 'italic' | 'justify' | 'line-table' | 'link' | 'list' | 'mobilePreview' | 'ol' | 'panel' | 'pdf' | 'publish' | 'quickTable' | 'quote' | 'redo' | 'ruby' | 'settings' | 'size' | 'strikethrough' | 'sub' | 'sup' | 'switchModel' | 'table' | 'theme' | 'toc' | 'togglePreview' | 'underline' | 'undo' | 'ul' | 'video' | 'word' | 'wordCount';export type CherryDefaultBubbleToolbar = | CherryToolbarSeparator | 'bold' | 'italic' | 'strikethrough' | 'sub' | 'sup' | 'size' | 'color';export type CherryDefaultFloatToolbar = | CherryToolbarSeparator | 'h1' | 'h2' | 'h3' | 'checklist' | 'quote' | 'quickTable' | 'code';export type SupportPlatform = 'wechat' | 'toutiao';export interface CherryPublishToolbarOption { name: string; key: SupportPlatform; icon?: string; iconName?: string; serviceUrl: string; injectPayload?: Record<string, any> | (() => Promise<Record<string, any>>) | (() => Record<string, any>);}export interface CherryFormulaToolbarOption { showLatexLive?: boolean; templateConfig?: boolean | Record<string, FormulaMenu>;}export interface CherryToolbarConfig { publish?: CherryPublishToolbarOption[] formula?: CherryFormulaToolbarOption changeLocale?: CherryChangeLocaleToolbarOption[]}export interface CherryChangeLocaleToolbarOption { locale: string; name: string;}export interface CherryToolbarsOptions<F extends CherryToolbarsCustomType = CherryToolbarsCustomType> { theme?: 'light' | 'dark'; toolbar?: | (CherryDefaultBubbleToolbar | CherryDefaultToolbar | keyof Partial<F['CustomMenuType']> | { [K in (keyof Partial<F['CustomMenuType']>) | CherryDefaultToolbar]?: (keyof F['CustomMenuType'] | CherryDefaultToolbar)[] })[] | false; toolbarRight?: | (CherryDefaultBubbleToolbar | CherryDefaultToolbar)[] | false; toc?: false | { updateLocationHash?: boolean, defaultModel?: 'pure' | 'full', showAutoNumber?: boolean, position?: 'absolute' | 'fixed', cssText?: string, }; hiddenToolbar?: any[]; showToolbar?: boolean; sidebar?: any[] | false; bubble?: any[] | false; float?: any[] | false; customMenu?: Record<string, any>; shortcutKey?: Object | false; shortcutKeySettings?: { isReplace?: boolean, shortcutKeyMap?: { [shortcutKey: string]: ShortcutKeyMapStruct }; }; config?: CherryToolbarConfig;}export interface CherryFileUploadHandler { (file: File, callback: (url: string, params?: { name?: string, poster?: string, isBorder?: boolean, isShadow?: boolean, isRadius?: boolean; width?: string, height?: string } ) => void): void;}type ShortcutKeyMapStruct = { hookName: string; aliasName: string; [x: string]: string | number;}