import { clearBlockFormat , clearFormat , toggleBold , toggleBullet , toggleHeader , toggleItalic , toggleNumbering , toggleUnderline } from "roosterjs-editor-api" ; import { Editor , EditorPlugin } from "roosterjs-editor-core" ; import { PluginDomEvent , PluginEvent , PluginEventType } from "roosterjs-editor-types" ; import { NullFunction , Strings , toggleNonCompatBullet , toggleNonCompatNumbering } from "roosterjs-react-common" ; import { createLinkDialog , LinkDialogProps } from "../components/LinkDialog" ; import RoosterCommandBar from "../components/RoosterCommandBar" ; import RoosterCommandBarPluginInterface from "../schema/RoosterCommandBarPluginInterface" ; import { getCommandFromEvent , RoosterShortcutCommands } from "./RoosterCommandBarPlugin.Shortcuts" ; export const InsertLinkStringKeys = { LinkFieldLabel : "linkFieldLabel" , Title : "linkPromptTitle" , InsertButton : "insertLinkText" , CancelButton : "cancelLinkText" } ; export interface RoosterCommandBarPluginOptions { strings ? : Strings ; calloutClassName ? : string ; linkDialogClassName ? : string ; calloutOnDismiss ? : ( ev ? : any ) => void ; onShortcutTriggered ? : ( command : RoosterShortcutCommands ) => void ; disableListWorkaround ? : boolean ; useLegacyClearFormat ? : boolean ; } export default class RoosterCommandBarPlugin implements EditorPlugin , RoosterCommandBarPluginInterface { private static readonly EventTypesToRefreshFormatState : { [ eventType ] : boolean ; } = { [ PluginEventType . KeyUp ] : true , [ PluginEventType . MouseDown ] : true , [ PluginEventType . MouseUp ] : true , [ PluginEventType . ContentChanged ] : true } ; private editor : Editor ; private commandBars : RoosterCommandBar [ ] = [ ] ; private dialogDismiss : ( ) => void ; constructor ( private options = { } ) { } public getName ( ) { return 'RoosterCommandBar' ; } public initialize ( editor ) { this . editor = editor ; if ( ! editor ) { return ; } const doc = this . editor . getDocument ( ) ; if ( ! doc ) { return ; } } public dispose ( ) { if ( this . dialogDismiss ) { this . dialogDismiss ( ) ; this . dialogDismiss = null ; } if ( this . editor ) { this . editor = null ; } if ( this . commandBars . length > 0 ) { this . commandBars . forEach ( ( _ , i ) => ( this . commandBars [ i ] = undefined ) ) ; this . commandBars = [ ] ; } } public onPluginEvent ( event ) { if ( this . commandBars && RoosterCommandBarPlugin . EventTypesToRefreshFormatState [ event . eventType ] ) { this . commandBars . forEach ( commandBar => commandBar . refreshFormatState ( ) ) ; return ; } if ( event . eventType === PluginEventType . KeyDown ) { this . handleShortcuts ( event ) ; } } private handleShortcuts ( event ) { const pluginDomEvent = event as PluginDomEvent ; const keyboardEvent = pluginDomEvent . rawEvent as KeyboardEvent ; if ( keyboardEvent . defaultPrevented ) { return ; } const command = getCommandFromEvent ( event ) ; if ( command === RoosterShortcutCommands . None ) { return ; } const { disableListWorkaround , onShortcutTriggered = NullFunction } = this . options ; const editor = this . editor ; let commandExecuted = true ; switch ( command ) { case RoosterShortcutCommands . Bold : toggleBold ( editor ) ; break ; case RoosterShortcutCommands . Italic : toggleItalic ( editor ) ; break ; case RoosterShortcutCommands . Underline : toggleUnderline ( editor ) ; break ; case RoosterShortcutCommands . Undo : editor . undo ( ) ; break ; case RoosterShortcutCommands . Redo : editor . redo ( ) ; break ; case RoosterShortcutCommands . Bullet : ( disableListWorkaround ? toggleNonCompatBullet : toggleBullet ) ( editor ) ; break ; case RoosterShortcutCommands . Numbering : ( disableListWorkaround ? toggleNonCompatNumbering : toggleNumbering ) ( editor ) ; break ; case RoosterShortcutCommands . InsertLink : this . promptForLink ( ) ; break ; case RoosterShortcutCommands . ClearFormat : this . clearFormat ( ) ; break ; default : commandExecuted = false ; } if ( commandExecuted ) { onShortcutTriggered ( command ) ; keyboardEvent . preventDefault ( ) ; keyboardEvent . stopPropagation ( ) ; } } public getEditor ( ) { return this . editor ; } public registerRoosterCommandBar ( commandBar ) { if ( this . commandBars . indexOf ( commandBar ) < 0 ) { this . commandBars . push ( commandBar ) ; } } public unregisterRoosterCommandBar ( commandBar ) { const index = this . commandBars . indexOf ( commandBar ) ; if ( index >= 0 ) { this . commandBars . splice ( index , 1 ) ; } } public promptForLink ( ) { const { strings = { } , calloutOnDismiss : onDismiss , calloutClassName , linkDialogClassName : className } = this . options ; this . dialogDismiss = createLinkDialog ( document , { editor : this . editor , strings , onDismiss , className } as LinkDialogProps , calloutClassName ) ; } public clearFormat ( ) { const editor = this . editor ; this . editor . addUndoSnapshot ( ( ) => { if ( this . options . useLegacyClearFormat ) { clearFormat ( editor ) ; toggleHeader ( editor , 0 ) ; } else { clearBlockFormat ( editor ) ; } } ) ; } }