diff --git a/Pasfmt.Main.pas b/Pasfmt.Main.pas index bd0c4e7..1c546c7 100644 --- a/Pasfmt.Main.pas +++ b/Pasfmt.Main.pas @@ -39,6 +39,8 @@ TPlugin = class(TObject) procedure OnSettingsActionExecute(Sender: TObject); procedure Format; + procedure RegisterKeyboardBinding; + procedure UnregisterKeyboardBinding; procedure ConfigureFormatter(var Formatter: TEditBufferFormatter); public constructor Create; @@ -115,8 +117,15 @@ constructor TPlugin.Create; FPasfmtMenu.Add(MenuItem); (BorlandIDEServices as INTAServices).AddActionMenu('CustomToolsItem', nil, FPasfmtMenu); - FKeyboardBindingIndex := - (BorlandIDEServices as IOTAKeyboardServices).AddKeyboardBinding(TPasfmtKeyboardBinding.Create); + + RegisterKeyboardBinding; + PasfmtSettings.OnFormatHotkeyChanged := + procedure + begin + UnregisterKeyboardBinding; + RegisterKeyboardBinding; + end; + FAddInOptions := TPasfmtAddInOptions.Create; (BorlandIDEServices as INTAEnvironmentOptionsServices).RegisterAddInOptions(FAddInOptions); @@ -141,7 +150,7 @@ destructor TPlugin.Destroy; (BorlandIDEServices as IOTAEditorServices).RemoveNotifier(FEditorIndex); (BorlandIDEServices as IOTAAboutBoxServices).RemovePluginInfo(FInfoIndex); (BorlandIDEServices as INTAEnvironmentOptionsServices).UnregisterAddInOptions(FAddInOptions); - (BorlandIDEServices as IOTAKeyboardServices).RemoveKeyboardBinding(FKeyboardBindingIndex); + UnregisterKeyboardBinding; FreeAndNil(FPasfmtMenu); FreeAndNil(FBitmaps); inherited; @@ -192,6 +201,17 @@ procedure TPlugin.OnSettingsActionExecute(Sender: TObject); (BorlandIDEServices as IOTAServices).GetEnvironmentOptions.EditOptions('', 'Pasfmt'); end; +procedure TPlugin.RegisterKeyboardBinding; +begin + FKeyboardBindingIndex := + (BorlandIDEServices as IOTAKeyboardServices).AddKeyboardBinding(TPasfmtKeyboardBinding.Create); +end; + +procedure TPlugin.UnregisterKeyboardBinding; +begin + (BorlandIDEServices as IOTAKeyboardServices).RemoveKeyboardBinding(FKeyboardBindingIndex); +end; + procedure TPlugin.OnFormatKeyPress( const Context: IOTAKeyContext; KeyCode: TShortCut; @@ -229,7 +249,7 @@ function TPlugin.GetPluginVersion: string; procedure TPasfmtKeyboardBinding.BindKeyboard(const BindingServices: IOTAKeyBindingServices); begin BindingServices - .AddKeyBinding([ShortCut(Ord('F'), [ssCtrl, ssAlt])], GPlugin.OnFormatKeyPress, nil, 0, '', 'PasfmtFormatItem'); + .AddKeyBinding([PasfmtSettings.FormatHotkey], GPlugin.OnFormatKeyPress, nil, 0, '', 'PasfmtFormatItem'); end; function TPasfmtKeyboardBinding.GetBindingType: TBindingType; diff --git a/Pasfmt.Settings.pas b/Pasfmt.Settings.pas index 35a833b..9372b64 100644 --- a/Pasfmt.Settings.pas +++ b/Pasfmt.Settings.pas @@ -4,7 +4,9 @@ interface uses Pasfmt.Log, - System.Win.Registry; + System.Win.Registry, + System.Classes, + System.SysUtils; type TPasfmtSettings = class(TObject) @@ -15,6 +17,7 @@ TPasfmtSettings = class(TObject) CFormatOnSaveName = 'Format On Save'; CFormatTimeoutName = 'Format Timeout'; CMaxFileKiBWithUndoHistory = 'Max File Size With Undo History'; + CFormatHotkey = 'Format Hotkey'; private FRegistry: TRegistry; FBaseKey: string; @@ -24,12 +27,16 @@ TPasfmtSettings = class(TObject) FFormatOnSave: Boolean; FFormatTimeout: Integer; FMaxFileKiBWithUndoHistory: Integer; + FFormatHotkey: TShortCut; + + FFormatHotkeyChanged: TProc; procedure SetLogLevel(Value: TLogLevel); procedure SetExecutablePath(Value: string); procedure SetFormatOnSave(Value: Boolean); procedure SetFormatTimeout(Value: Integer); procedure SetMaxFileKiBWithUndoHistory(Value: Integer); + procedure SetFormatHotkey(Value: TShortCut); public constructor Create; destructor Destroy; override; @@ -41,6 +48,9 @@ TPasfmtSettings = class(TObject) property FormatOnSave: Boolean read FFormatOnSave write SetFormatOnSave; property FormatTimeout: Integer read FFormatTimeout write SetFormatTimeout; property MaxFileKiBWithUndoHistory: Integer read FMaxFileKiBWithUndoHistory write SetMaxFileKiBWithUndoHistory; + property FormatHotkey: TShortCut read FFormatHotkey write SetFormatHotkey; + + property OnFormatHotkeyChanged: TProc write FFormatHotkeyChanged; end; function PasfmtSettings: TPasfmtSettings; @@ -49,8 +59,8 @@ implementation uses ToolsAPI, - System.SysUtils, - Winapi.Windows; + Winapi.Windows, + Vcl.Menus; var GSettings: TPasfmtSettings; @@ -72,6 +82,7 @@ constructor TPasfmtSettings.Create; FBaseKey := (BorlandIDEServices as IOTAServices).GetBaseRegistryKey + '\Pasfmt'; FRegistry := TRegistry.Create(KEY_ALL_ACCESS); FRegistry.RootKey := HKEY_CURRENT_USER; + FFormatHotkeyChanged := nil; end; //______________________________________________________________________________________________________________________ @@ -96,6 +107,24 @@ procedure TPasfmtSettings.SetExecutablePath(Value: string); end; end; +procedure TPasfmtSettings.SetFormatHotkey(Value: TShortCut); +begin + if FFormatHotkey = Value then + exit; + + FFormatHotkey := Value; + + FRegistry.OpenKey(FBaseKey, True); + try + FRegistry.WriteString(CFormatHotkey, ShortCutToText(Value)); + finally + FRegistry.CloseKey; + end; + + if Assigned(FFormatHotkeyChanged) then + FFormatHotkeyChanged; +end; + //______________________________________________________________________________________________________________________ procedure TPasfmtSettings.SetFormatOnSave(Value: Boolean); @@ -163,6 +192,7 @@ procedure TPasfmtSettings.Load; FFormatOnSave := False; FFormatTimeout := 500; FMaxFileKiBWithUndoHistory := 1024; + FFormatHotkey := ShortCut(Ord('F'), [ssCtrl, ssAlt]); if FRegistry.ValueExists(CLogLevelName) then FLogLevel := TLogLevel(FRegistry.ReadInteger(CLogLevelName)) @@ -188,6 +218,11 @@ procedure TPasfmtSettings.Load; FMaxFileKiBWithUndoHistory := FRegistry.ReadInteger(CMaxFileKiBWithUndoHistory) else FRegistry.WriteInteger(CMaxFileKiBWithUndoHistory, FMaxFileKiBWithUndoHistory); + + if FRegistry.ValueExists(CFormatHotkey) then + FFormatHotkey := TextToShortCut(FRegistry.ReadString(CFormatHotkey)) + else + FRegistry.WriteString(CFormatHotkey, ShortCutToText(FFormatHotkey)); finally FRegistry.CloseKey; end; diff --git a/Pasfmt.SettingsFrame.dfm b/Pasfmt.SettingsFrame.dfm index 59326c1..4ee9c3a 100644 --- a/Pasfmt.SettingsFrame.dfm +++ b/Pasfmt.SettingsFrame.dfm @@ -2,21 +2,21 @@ object PasfmtSettingsFrame: TPasfmtSettingsFrame Left = 0 Top = 0 Width = 392 - Height = 376 + Height = 395 Constraints.MinHeight = 180 Constraints.MinWidth = 390 TabOrder = 0 object LogLevelLabel: TLabel Left = 3 - Top = 48 + Top = 105 Width = 116 Height = 15 Caption = 'Minimum log severity' end object ExePathLabel: TLabel Left = 3 - Top = 205 - Width = 103 + Top = 262 + Width = 102 Height = 15 Caption = 'Executable location' end @@ -29,26 +29,35 @@ object PasfmtSettingsFrame: TPasfmtSettingsFrame end object TimeoutLabel: TLabel Left = 3 - Top = 104 + Top = 161 Width = 110 Height = 15 Caption = 'Format timeout (ms)' end object FastModeThresholdLabel: TLabel Left = 3 - Top = 155 - Width = 220 + Top = 212 + Width = 219 Height = 15 Cursor = crHelp Hint = - 'To avoid performance issues with updating large files, a faster method ' + - 'is used when the file size exceeds this configured threshold.'#13#10'This ' + - 'faster method unfortunately clears the undo history of the edit buffer.' + 'To avoid performance issues with updating large files, a faster ' + + 'method is used when the file size exceeds this configured thresh' + + 'old.'#13#10'This faster method unfortunately clears the undo history o' + + 'f the edit buffer.' Caption = 'Maximum file size with undo history (KiB)' end + object FormatHotkeyLabel: TLabel + Left = 3 + Top = 49 + Width = 75 + Height = 15 + Cursor = crHelp + Caption = 'Fomat Hotkey' + end object LogLevelCombo: TComboBox Left = 11 - Top = 66 + Top = 123 Width = 129 Height = 23 Style = csDropDownList @@ -62,7 +71,7 @@ object PasfmtSettingsFrame: TPasfmtSettingsFrame end object ExePathBrowseButton: TButton Left = 309 - Top = 304 + Top = 361 Width = 71 Height = 23 Caption = 'Browse...' @@ -71,7 +80,7 @@ object PasfmtSettingsFrame: TPasfmtSettingsFrame end object ExePathRadioGroup: TRadioGroup Left = 3 - Top = 210 + Top = 267 Width = 185 Height = 65 ItemIndex = 0 @@ -84,7 +93,7 @@ object PasfmtSettingsFrame: TPasfmtSettingsFrame end object ExePathEdit: TEdit Left = 29 - Top = 275 + Top = 332 Width = 351 Height = 23 TabOrder = 1 @@ -99,7 +108,7 @@ object PasfmtSettingsFrame: TPasfmtSettingsFrame end object TimeoutEdit: TEdit Left = 11 - Top = 122 + Top = 179 Width = 129 Height = 23 NumbersOnly = True @@ -110,7 +119,7 @@ object PasfmtSettingsFrame: TPasfmtSettingsFrame end object FastModeThresholdEdit: TEdit Left = 11 - Top = 173 + Top = 230 Width = 129 Height = 23 NumbersOnly = True @@ -119,10 +128,19 @@ object PasfmtSettingsFrame: TPasfmtSettingsFrame TabOrder = 6 Text = '1024' end + object FormatHotkeyEdit: THotKey + Left = 11 + Top = 67 + Width = 121 + Height = 23 + HotKey = 0 + Modifiers = [] + TabOrder = 7 + end object ExeChooseDialog: TOpenDialog Filter = 'Executable files (*.exe)|*.exe' Options = [ofHideReadOnly, ofPathMustExist, ofFileMustExist, ofEnableSizing] Left = 291 - Top = 52 + Top = 109 end end diff --git a/Pasfmt.SettingsFrame.pas b/Pasfmt.SettingsFrame.pas index e45a033..3a225b4 100644 --- a/Pasfmt.SettingsFrame.pas +++ b/Pasfmt.SettingsFrame.pas @@ -9,7 +9,8 @@ interface Vcl.Dialogs, ToolsAPI, Vcl.StdCtrls, - Vcl.ExtCtrls; + Vcl.ExtCtrls, + Vcl.ComCtrls; type TPasfmtSettingsFrame = class(TFrame) @@ -26,6 +27,8 @@ TPasfmtSettingsFrame = class(TFrame) TimeoutEdit: TEdit; FastModeThresholdEdit: TEdit; FastModeThresholdLabel: TLabel; + FormatHotkeyEdit: THotKey; + FormatHotkeyLabel: TLabel; procedure ExePathBrowseButtonClick(Sender: TObject); procedure ExePathRadioGroupClick(Sender: TObject); public @@ -71,6 +74,7 @@ procedure TPasfmtAddInOptions.FrameCreated(AFrame: TCustomFrame); FFrame.OnSaveCheckBox.Checked := PasfmtSettings.FormatOnSave; FFrame.TimeoutEdit.Text := IntToStr(PasfmtSettings.FormatTimeout); FFrame.FastModeThresholdEdit.Text := IntToStr(PasfmtSettings.MaxFileKiBWithUndoHistory); + FFrame.FormatHotkeyEdit.HotKey := PasfmtSettings.FormatHotkey; end; //______________________________________________________________________________________________________________________ @@ -104,6 +108,8 @@ procedure TPasfmtAddInOptions.DialogClosed(Accepted: Boolean); if TryStrToInt(FFrame.FastModeThresholdEdit.Text, NewThreshold) then begin PasfmtSettings.MaxFileKiBWithUndoHistory := NewThreshold; end; + + PasfmtSettings.FormatHotkey := FFrame.FormatHotkeyEdit.HotKey; end; FFrame := nil; diff --git a/README.md b/README.md index cdb8c9a..c205aad 100644 --- a/README.md +++ b/README.md @@ -22,6 +22,8 @@ and opinionated formatter for Delphi code, into the IDE. With a file open in the editor, a format can be triggered with `Ctrl+Alt+F` (`Tools > Pasfmt > Format`). +The hotkey for formatting can be changed in the settings menu (`Tools > Pasfmt > Settings...`) + The formatter can optionally be triggered on save; this can be enabled in `Tools > Pasfmt > Settings...` by toggling `Format on save`.