diff --git a/components/h2pas/h2pasconvert.pas b/components/h2pas/h2pasconvert.pas index 6c0a38769a..eed7ba4aa4 100644 --- a/components/h2pas/h2pasconvert.pas +++ b/components/h2pas/h2pasconvert.pas @@ -25,7 +25,7 @@ interface uses Classes, SysUtils, LCLProc, LazConfigStorage, XMLPropStorage, Forms, Controls, Dialogs, FileUtil, FileProcs, - IDEExternToolIntf, IDEDialogs; + TextTools, IDEExternToolIntf, IDEDialogs, LazIDEIntf, IDEMsgIntf; type TH2PasProject = class; @@ -163,11 +163,21 @@ type property OutputDirectory: string read FOutputDirectory write SetOutputDirectory; end; + { TH2PasTool } + + TH2PasTool = class(TIDEExternalToolOptions) + private + FH2PasFile: TH2PasFile; + public + property H2PasFile: TH2PasFile read FH2PasFile write FH2PasFile; + end; + { TH2PasConverter } TH2PasConverter = class(TPersistent) private FAutoOpenLastProject: boolean; + FExecuting: boolean; Fh2pasFilename: string; FModified: boolean; FProject: TH2PasProject; @@ -180,6 +190,7 @@ type procedure SetProjectHistory(const AValue: TStrings); procedure SetWindowBounds(const AValue: TRect); procedure Seth2pasFilename(const AValue: string); + procedure OnParseH2PasLine(Sender: TObject; Line: TIDEScanMessageLine); public constructor Create; destructor Destroy; override; @@ -195,6 +206,10 @@ type function Execute: TModalResult; function ConvertFile(AFile: TH2PasFile): TModalResult; function GetH2PasFilename: string; + function FindH2PasErrorMessage: integer; + function GetH2PasErrorPostion(const Line: string; + out aFilename: string; + out LineNumber, Column: integer): boolean; public property Project: TH2PasProject read FProject write SetProject; property ProjectHistory: TStrings read FProjectHistory write SetProjectHistory; @@ -205,6 +220,7 @@ type write SetAutoOpenLastProject; property h2pasFilename: string read Fh2pasFilename write Seth2pasFilename; property Modified: boolean read FModified write FModified; + property Executing: boolean read FExecuting; end; implementation @@ -848,6 +864,26 @@ end; { TH2PasConverter } +procedure TH2PasConverter.OnParseH2PasLine(Sender: TObject; + Line: TIDEScanMessageLine); +var + Tool: TH2PasTool; + LineNumber: String; + MsgType: String; + Msg: String; +begin + if Line.Tool is TH2PasTool then begin + Tool:=TH2PasTool(Line.Tool); + if REMatches(Line.Line,'^at line ([0-9]+) (error) : (.*)$') then begin + LineNumber:=REVar(1); + MsgType:=REVar(2); + Msg:=REVar(3); + Line.Line:=Tool.H2PasFile.Filename+'('+LineNumber+') '+MsgType+': '+Msg; + end; + //DebugLn(['TH2PasConverter.OnParseH2PasLine ',Line.Line]); + end; +end; + function TH2PasConverter.GetCurrentProjectFilename: string; begin if FProjectHistory.Count>0 then @@ -1036,18 +1072,27 @@ var AFile: TH2PasFile; CurResult: TModalResult; begin - Result:=mrOk; + if FExecuting then begin + DebugLn(['TH2PasConverter.Execute FAILED: Already executing']); + exit(mrCancel); + end; - // convert every c header file - for i:=0 to Project.CHeaderFileCount-1 do begin - AFile:=Project.CHeaderFiles[i]; - if not AFile.Enabled then continue; - CurResult:=ConvertFile(AFile); - if CurResult=mrAbort then begin - DebugLn(['TH2PasConverter.Execute aborted on file ',AFile.Filename]); - exit(mrAbort); + Result:=mrOK; + FExecuting:=true; + try + // convert every c header file + for i:=0 to Project.CHeaderFileCount-1 do begin + AFile:=Project.CHeaderFiles[i]; + if not AFile.Enabled then continue; + CurResult:=ConvertFile(AFile); + if CurResult=mrAbort then begin + DebugLn(['TH2PasConverter.Execute aborted on file ',AFile.Filename]); + exit(mrAbort); + end; + if CurResult<>mrOK then Result:=mrCancel; end; - if CurResult<>mrOK then Result:=mrCancel; + finally + FExecuting:=false; end; end; @@ -1056,7 +1101,7 @@ var OutputFilename: String; TempCHeaderFilename: String; InputFilename: String; - Tool: TExternalToolOptions; + Tool: TH2PasTool; begin Result:=mrCancel; @@ -1082,15 +1127,20 @@ begin // TODO: run converters for .h file to make it compatible for h2pas // run h2pas - Tool:=TExternalToolOptions.Create; + Tool:=TH2PasTool.Create; try Tool.Title:='h2pas'; + Tool.H2PasFile:=AFile; Tool.Filename:=GetH2PasFilename; Tool.CmdLineParams:=AFile.GetH2PasParameters(TempCHeaderFilename); Tool.ScanOutput:=true; Tool.ShowAllOutput:=true; Tool.WorkingDirectory:=Project.BaseDir; + Tool.OnParseLine:=@OnParseH2PasLine; DebugLn(['TH2PasConverter.ConvertFile Tool.Filename="',Tool.Filename,'" Tool.CmdLineParams="',Tool.CmdLineParams,'"']); + Result:=LazarusIDE.RunExternalTool(Tool); + if Result<>mrOk then exit(mrAbort); + if FindH2PasErrorMessage>=0 then exit(mrAbort); finally Tool.Free; end; @@ -1105,6 +1155,37 @@ begin Result:=FindDefaultExecutablePath(h2pasFilename); end; +function TH2PasConverter.FindH2PasErrorMessage: integer; +var + i: Integer; + Line: TIDEMessageLine; +begin + for i:=0 to IDEMessagesWindow.LinesCount-1 do begin + Line:=IDEMessagesWindow.Lines[i]; + if REMatches(Line.Msg,'^(.*)\([0-9]+\)') then begin + Result:=i; + exit; + end; + end; + Result:=-1; +end; + +function TH2PasConverter.GetH2PasErrorPostion(const Line: string; + out aFilename: string; out LineNumber, Column: integer): boolean; +begin + Result:=REMatches(Line,'^(.*)\(([0-9]+)\)'); + if Result then begin + aFilename:=REVar(1); + LineNumber:=StrToIntDef(REVar(2),-1); + Column:=1; + end else begin + aFilename:=''; + LineNumber:=-1; + Column:=-1; + end; +end; + end. + diff --git a/components/h2pas/h2pasdlg.lfm b/components/h2pas/h2pasdlg.lfm index 511b946367..38868b48fe 100644 --- a/components/h2pas/h2pasdlg.lfm +++ b/components/h2pas/h2pasdlg.lfm @@ -7,18 +7,19 @@ object H2PasDialog: TH2PasDialog OnCreate = FormCreate OnDestroy = FormDestroy OnKeyDown = FormKeyDown - PixelsPerInch = 112 + PixelsPerInch = 75 + Position = poDesktopCenter HorzScrollBar.Page = 784 VertScrollBar.Page = 500 - Left = 326 + Left = 258 Height = 501 - Top = 178 + Top = 143 Width = 785 object MainPageControl: TPageControl - ActivePage = h2pasOptionsTabSheet + ActivePage = ConvertTabSheet Align = alTop Anchors = [akTop, akLeft, akRight, akBottom] - TabIndex = 1 + TabIndex = 2 TabOrder = 0 AnchorSideBottom.Control = OpenSettingsButton Height = 465 @@ -117,7 +118,7 @@ object H2PasDialog: TH2PasDialog AnchorSideTop.Side = asrCenter Left = 6 Height = 13 - Top = 116 + Top = 281 Width = 81 end object OutputExtLabel: TLabel @@ -128,7 +129,7 @@ object H2PasDialog: TH2PasDialog AnchorSideTop.Side = asrCenter Left = 6 Height = 13 - Top = 301 + Top = 313 Width = 86 end object OutputDirLabel: TLabel @@ -139,161 +140,42 @@ object H2PasDialog: TH2PasDialog AnchorSideTop.Side = asrCenter Left = 6 Height = 13 - Top = 330 + Top = 342 Width = 85 end - object UseExternalCheckBox: TCheckBox - Caption = 'UseExternalCheckBox' - OnChange = UseExternalCheckBoxChange - TabOrder = 0 - Left = 6 - Height = 20 - Top = 7 - Width = 150 - end - object UseExternalLibnameCheckBox: TCheckBox - BorderSpacing.Top = 6 - Caption = 'UseExternalLibnameCheckBox' - OnChange = UseExternalLibnameCheckBoxChange - TabOrder = 1 - AnchorSideTop.Control = UseExternalCheckBox - AnchorSideTop.Side = asrBottom - Left = 6 - Height = 20 - Top = 33 - Width = 197 - end - object ConstantsInsteadOfEnumsCheckBox: TCheckBox - BorderSpacing.Top = 6 - Caption = 'ConstantsInsteadOfEnumsCheckBox' - OnChange = ConstantsInsteadOfEnumsCheckBoxChange - TabOrder = 2 - AnchorSideTop.Control = UseExternalLibnameCheckBox - AnchorSideTop.Side = asrBottom - Left = 6 - Height = 20 - Top = 59 - Width = 229 - end - object IncludeFileCheckBox: TCheckBox - BorderSpacing.Top = 6 - Caption = 'IncludeFileCheckBox' - OnChange = IncludeFileCheckBoxChange - TabOrder = 3 - AnchorSideTop.Control = ConstantsInsteadOfEnumsCheckBox - AnchorSideTop.Side = asrBottom - Left = 6 - Height = 20 - Top = 85 - Width = 146 - end object LibnameEdit: TEdit BorderSpacing.Left = 6 BorderSpacing.Top = 6 OnEditingDone = LibnameEditEditingDone - TabOrder = 4 + TabOrder = 0 Text = 'LibnameEdit' AnchorSideLeft.Control = LibNameLabel AnchorSideLeft.Side = asrBottom - AnchorSideTop.Control = IncludeFileCheckBox AnchorSideTop.Side = asrBottom Left = 93 Height = 23 - Top = 111 + Top = 276 Width = 113 end - object PforPointersCheckBox: TCheckBox - BorderSpacing.Top = 6 - Caption = 'PforPointersCheckBox' - OnChange = PforPointersCheckBoxChange - TabOrder = 5 - AnchorSideTop.Control = LibnameEdit - AnchorSideTop.Side = asrBottom - Left = 6 - Height = 20 - Top = 140 - Width = 151 - end - object StripCommentsCheckBox: TCheckBox - BorderSpacing.Top = 6 - Caption = 'StripCommentsCheckBox' - OnChange = StripCommentsCheckBoxChange - TabOrder = 6 - AnchorSideTop.Control = PforPointersCheckBox - AnchorSideTop.Side = asrBottom - Left = 6 - Height = 20 - Top = 166 - Width = 166 - end - object TforTypedefsCheckBox: TCheckBox - BorderSpacing.Top = 6 - Caption = 'TforTypedefsCheckBox' - OnChange = TforTypedefsCheckBoxChange - TabOrder = 7 - AnchorSideTop.Control = StripCommentsCheckBox - AnchorSideTop.Side = asrBottom - Left = 6 - Height = 20 - Top = 192 - Width = 156 - end - object VarParamsCheckBox: TCheckBox - BorderSpacing.Top = 6 - Caption = 'VarParamsCheckBox' - OnChange = VarParamsCheckBoxChange - TabOrder = 8 - AnchorSideTop.Control = TforTypedefsCheckBox - AnchorSideTop.Side = asrBottom - Left = 6 - Height = 20 - Top = 218 - Width = 145 - end - object Win32HeaderCheckBox: TCheckBox - BorderSpacing.Top = 6 - Caption = 'Win32HeaderCheckBox' - OnChange = Win32HeaderCheckBoxChange - TabOrder = 9 - AnchorSideTop.Control = VarParamsCheckBox - AnchorSideTop.Side = asrBottom - Left = 6 - Height = 20 - Top = 244 - Width = 160 - end - object PalmOSSYSTrapCheckBox: TCheckBox - BorderSpacing.Top = 6 - Caption = 'PalmOSSYSTrapCheckBox' - OnChange = PalmOSSYSTrapCheckBoxChange - TabOrder = 10 - AnchorSideTop.Control = Win32HeaderCheckBox - AnchorSideTop.Side = asrBottom - Left = 6 - Height = 20 - Top = 270 - Width = 179 - end object OutputExtEdit: TEdit BorderSpacing.Left = 6 BorderSpacing.Top = 6 OnEditingDone = OutputExtEditEditingDone - TabOrder = 11 + TabOrder = 1 Text = 'OutputExtEdit' AnchorSideLeft.Control = OutputExtLabel AnchorSideLeft.Side = asrBottom - AnchorSideTop.Control = PalmOSSYSTrapCheckBox AnchorSideTop.Side = asrBottom Left = 98 Height = 23 - Top = 296 + Top = 308 Width = 80 end object OutputDirEdit: TEdit BorderSpacing.Left = 6 BorderSpacing.Top = 6 OnEditingDone = OutputDirEditEditingDone - TabOrder = 12 + TabOrder = 2 Text = 'OutputDirEdit' AnchorSideLeft.Control = OutputDirLabel AnchorSideLeft.Side = asrBottom @@ -301,7 +183,7 @@ object H2PasDialog: TH2PasDialog AnchorSideTop.Side = asrBottom Left = 97 Height = 23 - Top = 325 + Top = 337 Width = 397 end object OutputDirBrowseButton: TButton @@ -309,7 +191,7 @@ object H2PasDialog: TH2PasDialog BorderSpacing.InnerBorder = 4 Caption = '...' OnClick = OutputDirBrowseButtonClick - TabOrder = 13 + TabOrder = 3 AnchorSideLeft.Control = OutputDirEdit AnchorSideLeft.Side = asrBottom AnchorSideTop.Control = OutputDirEdit @@ -317,9 +199,405 @@ object H2PasDialog: TH2PasDialog AnchorSideBottom.Side = asrBottom Left = 494 Height = 23 - Top = 325 + Top = 337 Width = 32 end + object h2pasOptionsCheckGroup: TCheckGroup + AutoFill = True + Caption = 'h2pasOptionsCheckGroup' + ChildSizing.LeftRightSpacing = 6 + ChildSizing.TopBottomSpacing = 6 + ChildSizing.EnlargeHorizontal = crsHomogenousChildResize + ChildSizing.EnlargeVertical = crsHomogenousChildResize + ChildSizing.ShrinkHorizontal = crsScaleChilds + ChildSizing.ShrinkVertical = crsScaleChilds + ChildSizing.Layout = cclLeftToRightThenTopToBottom + ChildSizing.ControlsPerLine = 2 + Columns = 2 + OnItemClick = h2pasOptionsCheckGroupItemClick + TabOrder = 4 + Left = 6 + Height = 264 + Top = 4 + Width = 768 + end + end + object ConvertTabSheet: TTabSheet + Caption = 'ConvertTabSheet' + ClientHeight = 435 + ClientWidth = 781 + Left = 2 + Height = 435 + Top = 28 + Width = 781 + object ConvertButton: TButton + AutoSize = True + BorderSpacing.InnerBorder = 4 + Caption = 'ConvertButton' + OnClick = ConvertButtonClick + TabOrder = 0 + Left = 14 + Height = 26 + Top = 12 + Width = 93 + end + object ConvertErrorGroupBox: TGroupBox + Anchors = [akTop, akLeft, akRight] + Caption = 'ConvertErrorGroupBox' + ClientHeight = 130 + ClientWidth = 764 + TabOrder = 1 + Left = 6 + Height = 147 + Top = 52 + Width = 768 + object ConvertErrorSynEdit: TSynEdit + Align = alClient + Font.Height = -12 + Font.Name = 'courier' + Height = 130 + Name = 'ConvertErrorSynEdit' + ParentColor = False + TabOrder = 0 + Width = 764 + BookMarkOptions.Xoffset = 30 + BookMarkOptions.OnChange = nil + Gutter.ShowLineNumbers = True + Gutter.OnChange = nil + Gutter.CodeFoldingWidth = 14 + Highlighter = SynCppSyn1 + Keystrokes = < + item + Command = 3 + ShortCut = 38 + end + item + Command = 103 + ShortCut = 8230 + end + item + Command = 211 + ShortCut = 16422 + end + item + Command = 4 + ShortCut = 40 + end + item + Command = 104 + ShortCut = 8232 + end + item + Command = 212 + ShortCut = 16424 + end + item + Command = 1 + ShortCut = 37 + end + item + Command = 101 + ShortCut = 8229 + end + item + Command = 5 + ShortCut = 16421 + end + item + Command = 105 + ShortCut = 24613 + end + item + Command = 2 + ShortCut = 39 + end + item + Command = 102 + ShortCut = 8231 + end + item + Command = 6 + ShortCut = 16423 + end + item + Command = 106 + ShortCut = 24615 + end + item + Command = 10 + ShortCut = 34 + end + item + Command = 110 + ShortCut = 8226 + end + item + Command = 14 + ShortCut = 16418 + end + item + Command = 114 + ShortCut = 24610 + end + item + Command = 9 + ShortCut = 33 + end + item + Command = 109 + ShortCut = 8225 + end + item + Command = 13 + ShortCut = 16417 + end + item + Command = 113 + ShortCut = 24609 + end + item + Command = 7 + ShortCut = 36 + end + item + Command = 107 + ShortCut = 8228 + end + item + Command = 15 + ShortCut = 16420 + end + item + Command = 115 + ShortCut = 24612 + end + item + Command = 8 + ShortCut = 35 + end + item + Command = 108 + ShortCut = 8227 + end + item + Command = 16 + ShortCut = 16419 + end + item + Command = 116 + ShortCut = 24611 + end + item + Command = 223 + ShortCut = 45 + end + item + Command = 201 + ShortCut = 16429 + end + item + Command = 604 + ShortCut = 8237 + end + item + Command = 502 + ShortCut = 46 + end + item + Command = 603 + ShortCut = 8238 + end + item + Command = 501 + ShortCut = 8 + end + item + Command = 501 + ShortCut = 8200 + end + item + Command = 504 + ShortCut = 16392 + end + item + Command = 601 + ShortCut = 32776 + end + item + Command = 602 + ShortCut = 40968 + end + item + Command = 509 + ShortCut = 13 + end + item + Command = 199 + ShortCut = 16449 + end + item + Command = 201 + ShortCut = 16451 + end + item + Command = 610 + ShortCut = 24649 + end + item + Command = 509 + ShortCut = 16461 + end + item + Command = 510 + ShortCut = 16462 + end + item + Command = 503 + ShortCut = 16468 + end + item + Command = 611 + ShortCut = 24661 + end + item + Command = 604 + ShortCut = 16470 + end + item + Command = 603 + ShortCut = 16472 + end + item + Command = 507 + ShortCut = 16473 + end + item + Command = 506 + ShortCut = 24665 + end + item + Command = 601 + ShortCut = 16474 + end + item + Command = 602 + ShortCut = 24666 + end + item + Command = 301 + ShortCut = 16432 + end + item + Command = 302 + ShortCut = 16433 + end + item + Command = 303 + ShortCut = 16434 + end + item + Command = 304 + ShortCut = 16435 + end + item + Command = 305 + ShortCut = 16436 + end + item + Command = 306 + ShortCut = 16437 + end + item + Command = 307 + ShortCut = 16438 + end + item + Command = 308 + ShortCut = 16439 + end + item + Command = 309 + ShortCut = 16440 + end + item + Command = 310 + ShortCut = 16441 + end + item + Command = 351 + ShortCut = 24624 + end + item + Command = 352 + ShortCut = 24625 + end + item + Command = 353 + ShortCut = 24626 + end + item + Command = 354 + ShortCut = 24627 + end + item + Command = 355 + ShortCut = 24628 + end + item + Command = 356 + ShortCut = 24629 + end + item + Command = 357 + ShortCut = 24630 + end + item + Command = 358 + ShortCut = 24631 + end + item + Command = 359 + ShortCut = 24632 + end + item + Command = 360 + ShortCut = 24633 + end + item + Command = 231 + ShortCut = 24654 + end + item + Command = 232 + ShortCut = 24643 + end + item + Command = 233 + ShortCut = 24652 + end + item + Command = 612 + ShortCut = 9 + end + item + Command = 613 + ShortCut = 8201 + end + item + Command = 250 + ShortCut = 24642 + end> + Lines.Strings = ( + 'ConvertErrorSynEdit' + ) + Options = [eoAutoIndent, eoDragDropEditing, eoGroupUndo, eoShowScrollHint, eoShowSpecialChars, eoSmartTabDelete, eoSmartTabs, eoTabsToSpaces, eoTrimTrailingSpaces, eoBracketHighlight] + ReadOnly = True + SelectedColor.OnChange = nil + Cursor = crIBeam + Height = 130 + Width = 764 + end + end end object SettingsTabSheet: TTabSheet Caption = 'SettingsTabSheet' @@ -347,7 +625,7 @@ object H2PasDialog: TH2PasDialog Left = 6 Height = 20 Top = 42 - Width = 219 + Width = 216 end object SaveSettingsAsButton: TButton AutoSize = True @@ -389,6 +667,17 @@ object H2PasDialog: TH2PasDialog Top = 4 Width = 35 end + object NewSettingsButton: TButton + AutoSize = True + BorderSpacing.InnerBorder = 4 + Caption = 'NewSettingsButton' + OnClick = NewSettingsButtonClick + TabOrder = 4 + Left = 6 + Height = 26 + Top = 124 + Width = 118 + end end end object OpenSettingsButton: TButton @@ -441,4 +730,10 @@ object H2PasDialog: TH2PasDialog Top = 470 Width = 81 end + object SynCppSyn1: TSynCppSyn + DefaultFilter = 'C++-Quelltexte (*.c,*.cpp,*.h,*.hpp,*.hh)|*.c;*.cpp;*.h;*.hpp;*.hh' + Enabled = False + left = 174 + top = 92 + end end diff --git a/components/h2pas/h2pasdlg.lrs b/components/h2pas/h2pasdlg.lrs index 437b6f9ae5..ea7737f46b 100644 --- a/components/h2pas/h2pasdlg.lrs +++ b/components/h2pas/h2pasdlg.lrs @@ -83,49 +83,107 @@ LazarusResources.Add('TH2PasDialog','FORMDATA',[ +'ClientWidth'#3#13#3#4'Left'#2#2#6'Height'#3#179#1#3'Top'#2#28#5'Width'#3#13 +#3#0#7'TButton'#13'ConvertButton'#8'AutoSize'#9#25'BorderSpacing.InnerBorder' +#2#4#7'Caption'#6#13'ConvertButton'#7'OnClick'#7#18'ConvertButtonClick'#8'Ta' - +'bOrder'#2#0#4'Left'#2#14#6'Height'#2#26#3'Top'#2#12#5'Width'#2']'#0#0#0#9'T' - +'TabSheet'#16'SettingsTabSheet'#7'Caption'#6#16'SettingsTabSheet'#12'ClientH' - +'eight'#3#179#1#11'ClientWidth'#3#13#3#4'Left'#2#2#6'Height'#3#179#1#3'Top'#2 - +#28#5'Width'#3#13#3#0#6'TLabel'#18'H2PasFilenameLabel'#7'Caption'#6#18'H2Pas' - +'FilenameLabel'#5'Color'#7#6'clNone'#11'ParentColor'#8#21'AnchorSideTop.Cont' - +'rol'#7#17'H2PasFilenameEdit'#18'AnchorSideTop.Side'#7#9'asrCenter'#4'Left'#2 - +#6#6'Height'#2#13#3'Top'#2#9#5'Width'#2'x'#0#0#9'TCheckBox'#30'OpenLastProje' - +'ctOnStartCheckBox'#7'Caption'#6#30'OpenLastProjectOnStartCheckBox'#8'OnChan' - +'ge'#7'$OpenLastProjectOnStartCheckBoxChange'#8'TabOrder'#2#0#4'Left'#2#6#6 - +'Height'#2#20#3'Top'#2'*'#5'Width'#3#216#0#0#0#7'TButton'#20'SaveSettingsAsB' - +'utton'#8'AutoSize'#9#25'BorderSpacing.InnerBorder'#2#4#7'Caption'#6#20'Save' - +'SettingsAsButton'#7'OnClick'#7#25'SaveSettingsAsButtonClick'#8'TabOrder'#2#1 - +#4'Left'#2#6#6'Height'#2#26#3'Top'#2'R'#5'Width'#3#137#0#0#0#5'TEdit'#17'H2P' - +'asFilenameEdit'#18'BorderSpacing.Left'#2#6#17'BorderSpacing.Top'#2#6#13'OnE' - +'ditingDone'#7#28'H2PasFilenameEditEditingDone'#8'TabOrder'#2#2#4'Text'#6#17 - +'H2PasFilenameEdit'#22'AnchorSideLeft.Control'#7#18'H2PasFilenameLabel'#19'A' - +'nchorSideLeft.Side'#7#9'asrBottom'#4'Left'#3#132#0#6'Height'#2#23#3'Top'#2#4 - +#5'Width'#3'`'#1#0#0#7'TButton'#25'h2pasFilenameBrowseButton'#7'Anchors'#11#5 - +'akTop'#6'akLeft'#8'akBottom'#0#25'BorderSpacing.InnerBorder'#2#4#7'Caption' - +#6#3'...'#7'OnClick'#7#30'h2pasFilenameBrowseButtonClick'#8'TabOrder'#2#3#22 - +'AnchorSideLeft.Control'#7#17'H2PasFilenameEdit'#19'AnchorSideLeft.Side'#7#9 - +'asrBottom'#21'AnchorSideTop.Control'#7#17'H2PasFilenameEdit'#24'AnchorSideB' - +'ottom.Control'#7#17'H2PasFilenameEdit'#21'AnchorSideBottom.Side'#7#9'asrBot' - +'tom'#4'Left'#3#228#1#6'Height'#2#23#3'Top'#2#4#5'Width'#2'#'#0#0#7'TButton' - +#17'NewSettingsButton'#8'AutoSize'#9#25'BorderSpacing.InnerBorder'#2#4#7'Cap' - +'tion'#6#17'NewSettingsButton'#7'OnClick'#7#22'NewSettingsButtonClick'#8'Tab' - +'Order'#2#4#4'Left'#2#6#6'Height'#2#26#3'Top'#2'|'#5'Width'#2'v'#0#0#0#0#7'T' - +'Button'#18'OpenSettingsButton'#7'Anchors'#11#6'akLeft'#8'akBottom'#0#8'Auto' - +'Size'#9#20'BorderSpacing.Around'#2#5#25'BorderSpacing.InnerBorder'#2#4#7'Ca' - +'ption'#6#18'OpenSettingsButton'#7'OnClick'#7#23'OpenSettingsButtonClick'#8 - +'TabOrder'#2#1#22'AnchorSideLeft.Control'#7#5'Owner'#24'AnchorSideBottom.Con' - +'trol'#7#5'Owner'#21'AnchorSideBottom.Side'#7#9'asrBottom'#4'Left'#2#5#6'Hei' - +'ght'#2#26#3'Top'#3#214#1#5'Width'#2'|'#0#0#7'TButton'#18'SaveSettingsButton' - +#7'Anchors'#11#6'akLeft'#8'akBottom'#0#8'AutoSize'#9#20'BorderSpacing.Around' - +#2#5#25'BorderSpacing.InnerBorder'#2#4#7'Caption'#6#18'SaveSettingsButton'#7 - +'OnClick'#7#23'SaveSettingsButtonClick'#8'TabOrder'#2#2#22'AnchorSideLeft.Co' - +'ntrol'#7#18'OpenSettingsButton'#19'AnchorSideLeft.Side'#7#9'asrBottom'#24'A' - +'nchorSideBottom.Control'#7#5'Owner'#21'AnchorSideBottom.Side'#7#9'asrBottom' - +#4'Left'#3#134#0#6'Height'#2#26#3'Top'#3#214#1#5'Width'#2'z'#0#0#7'TButton' - +#11'CloseButton'#7'Anchors'#11#7'akRight'#8'akBottom'#0#8'AutoSize'#9#20'Bor' - +'derSpacing.Around'#2#5#25'BorderSpacing.InnerBorder'#2#4#7'Caption'#6#11'Cl' - +'oseButton'#7'OnClick'#7#16'CloseButtonClick'#8'TabOrder'#2#3#23'AnchorSideR' - +'ight.Control'#7#5'Owner'#20'AnchorSideRight.Side'#7#9'asrBottom'#24'AnchorS' - +'ideBottom.Control'#7#5'Owner'#21'AnchorSideBottom.Side'#7#9'asrBottom'#4'Le' - +'ft'#3#187#2#6'Height'#2#26#3'Top'#3#214#1#5'Width'#2'Q'#0#0#0 + +'bOrder'#2#0#4'Left'#2#14#6'Height'#2#26#3'Top'#2#12#5'Width'#2']'#0#0#9'TGr' + +'oupBox'#20'ConvertErrorGroupBox'#7'Anchors'#11#5'akTop'#6'akLeft'#7'akRight' + +#0#7'Caption'#6#20'ConvertErrorGroupBox'#12'ClientHeight'#3#130#0#11'ClientW' + +'idth'#3#252#2#8'TabOrder'#2#1#4'Left'#2#6#6'Height'#3#147#0#3'Top'#2'4'#5'W' + +'idth'#3#0#3#0#8'TSynEdit'#19'ConvertErrorSynEdit'#5'Align'#7#8'alClient'#11 + +'Font.Height'#2#244#9'Font.Name'#6#7'courier'#6'Height'#3#130#0#4'Name'#6#19 + +'ConvertErrorSynEdit'#11'ParentColor'#8#8'TabOrder'#2#0#5'Width'#3#252#2#23 + +'BookMarkOptions.Xoffset'#2#30#24'BookMarkOptions.OnChange'#13#22'Gutter.Sho' + +'wLineNumbers'#9#15'Gutter.OnChange'#13#23'Gutter.CodeFoldingWidth'#2#14#11 + +'Highlighter'#7#10'SynCppSyn1'#10'Keystrokes'#14#1#7'Command'#2#3#8'ShortCut' + +#2'&'#0#1#7'Command'#2'g'#8'ShortCut'#3'& '#0#1#7'Command'#3#211#0#8'ShortCu' + +'t'#3'&@'#0#1#7'Command'#2#4#8'ShortCut'#2'('#0#1#7'Command'#2'h'#8'ShortCut' + +#3'( '#0#1#7'Command'#3#212#0#8'ShortCut'#3'(@'#0#1#7'Command'#2#1#8'ShortCu' + +'t'#2'%'#0#1#7'Command'#2'e'#8'ShortCut'#3'% '#0#1#7'Command'#2#5#8'ShortCut' + +#3'%@'#0#1#7'Command'#2'i'#8'ShortCut'#3'%`'#0#1#7'Command'#2#2#8'ShortCut'#2 + +''''#0#1#7'Command'#2'f'#8'ShortCut'#3''' '#0#1#7'Command'#2#6#8'ShortCut'#3 + +'''@'#0#1#7'Command'#2'j'#8'ShortCut'#3'''`'#0#1#7'Command'#2#10#8'ShortCut' + +#2'"'#0#1#7'Command'#2'n'#8'ShortCut'#3'" '#0#1#7'Command'#2#14#8'ShortCut'#3 + +'"@'#0#1#7'Command'#2'r'#8'ShortCut'#3'"`'#0#1#7'Command'#2#9#8'ShortCut'#2 + +'!'#0#1#7'Command'#2'm'#8'ShortCut'#3'! '#0#1#7'Command'#2#13#8'ShortCut'#3 + +'!@'#0#1#7'Command'#2'q'#8'ShortCut'#3'!`'#0#1#7'Command'#2#7#8'ShortCut'#2 + +'$'#0#1#7'Command'#2'k'#8'ShortCut'#3'$ '#0#1#7'Command'#2#15#8'ShortCut'#3 + +'$@'#0#1#7'Command'#2's'#8'ShortCut'#3'$`'#0#1#7'Command'#2#8#8'ShortCut'#2 + +'#'#0#1#7'Command'#2'l'#8'ShortCut'#3'# '#0#1#7'Command'#2#16#8'ShortCut'#3 + +'#@'#0#1#7'Command'#2't'#8'ShortCut'#3'#`'#0#1#7'Command'#3#223#0#8'ShortCut' + +#2'-'#0#1#7'Command'#3#201#0#8'ShortCut'#3'-@'#0#1#7'Command'#3'\'#2#8'Short' + +'Cut'#3'- '#0#1#7'Command'#3#246#1#8'ShortCut'#2'.'#0#1#7'Command'#3'['#2#8 + +'ShortCut'#3'. '#0#1#7'Command'#3#245#1#8'ShortCut'#2#8#0#1#7'Command'#3#245 + +#1#8'ShortCut'#3#8' '#0#1#7'Command'#3#248#1#8'ShortCut'#3#8'@'#0#1#7'Comman' + +'d'#3'Y'#2#8'ShortCut'#4#8#128#0#0#0#1#7'Command'#3'Z'#2#8'ShortCut'#4#8#160 + +#0#0#0#1#7'Command'#3#253#1#8'ShortCut'#2#13#0#1#7'Command'#3#199#0#8'ShortC' + +'ut'#3'A@'#0#1#7'Command'#3#201#0#8'ShortCut'#3'C@'#0#1#7'Command'#3'b'#2#8 + +'ShortCut'#3'I`'#0#1#7'Command'#3#253#1#8'ShortCut'#3'M@'#0#1#7'Command'#3 + +#254#1#8'ShortCut'#3'N@'#0#1#7'Command'#3#247#1#8'ShortCut'#3'T@'#0#1#7'Comm' + +'and'#3'c'#2#8'ShortCut'#3'U`'#0#1#7'Command'#3'\'#2#8'ShortCut'#3'V@'#0#1#7 + +'Command'#3'['#2#8'ShortCut'#3'X@'#0#1#7'Command'#3#251#1#8'ShortCut'#3'Y@'#0 + +#1#7'Command'#3#250#1#8'ShortCut'#3'Y`'#0#1#7'Command'#3'Y'#2#8'ShortCut'#3 + +'Z@'#0#1#7'Command'#3'Z'#2#8'ShortCut'#3'Z`'#0#1#7'Command'#3'-'#1#8'ShortCu' + +'t'#3'0@'#0#1#7'Command'#3'.'#1#8'ShortCut'#3'1@'#0#1#7'Command'#3'/'#1#8'Sh' + +'ortCut'#3'2@'#0#1#7'Command'#3'0'#1#8'ShortCut'#3'3@'#0#1#7'Command'#3'1'#1 + +#8'ShortCut'#3'4@'#0#1#7'Command'#3'2'#1#8'ShortCut'#3'5@'#0#1#7'Command'#3 + +'3'#1#8'ShortCut'#3'6@'#0#1#7'Command'#3'4'#1#8'ShortCut'#3'7@'#0#1#7'Comman' + +'d'#3'5'#1#8'ShortCut'#3'8@'#0#1#7'Command'#3'6'#1#8'ShortCut'#3'9@'#0#1#7'C' + +'ommand'#3'_'#1#8'ShortCut'#3'0`'#0#1#7'Command'#3'`'#1#8'ShortCut'#3'1`'#0#1 + +#7'Command'#3'a'#1#8'ShortCut'#3'2`'#0#1#7'Command'#3'b'#1#8'ShortCut'#3'3`' + +#0#1#7'Command'#3'c'#1#8'ShortCut'#3'4`'#0#1#7'Command'#3'd'#1#8'ShortCut'#3 + ,'5`'#0#1#7'Command'#3'e'#1#8'ShortCut'#3'6`'#0#1#7'Command'#3'f'#1#8'ShortCu' + +'t'#3'7`'#0#1#7'Command'#3'g'#1#8'ShortCut'#3'8`'#0#1#7'Command'#3'h'#1#8'Sh' + +'ortCut'#3'9`'#0#1#7'Command'#3#231#0#8'ShortCut'#3'N`'#0#1#7'Command'#3#232 + +#0#8'ShortCut'#3'C`'#0#1#7'Command'#3#233#0#8'ShortCut'#3'L`'#0#1#7'Command' + +#3'd'#2#8'ShortCut'#2#9#0#1#7'Command'#3'e'#2#8'ShortCut'#3#9' '#0#1#7'Comma' + +'nd'#3#250#0#8'ShortCut'#3'B`'#0#0#13'Lines.Strings'#1#6#19'ConvertErrorSynE' + +'dit'#0#7'Options'#11#12'eoAutoIndent'#17'eoDragDropEditing'#11'eoGroupUndo' + +#16'eoShowScrollHint'#18'eoShowSpecialChars'#16'eoSmartTabDelete'#11'eoSmart' + +'Tabs'#14'eoTabsToSpaces'#20'eoTrimTrailingSpaces'#18'eoBracketHighlight'#0#8 + +'ReadOnly'#9#22'SelectedColor.OnChange'#13#6'Cursor'#7#7'crIBeam'#6'Height'#3 + +#130#0#5'Width'#3#252#2#0#0#0#0#9'TTabSheet'#16'SettingsTabSheet'#7'Caption' + +#6#16'SettingsTabSheet'#12'ClientHeight'#3#179#1#11'ClientWidth'#3#13#3#4'Le' + +'ft'#2#2#6'Height'#3#179#1#3'Top'#2#28#5'Width'#3#13#3#0#6'TLabel'#18'H2PasF' + +'ilenameLabel'#7'Caption'#6#18'H2PasFilenameLabel'#5'Color'#7#6'clNone'#11'P' + +'arentColor'#8#21'AnchorSideTop.Control'#7#17'H2PasFilenameEdit'#18'AnchorSi' + +'deTop.Side'#7#9'asrCenter'#4'Left'#2#6#6'Height'#2#13#3'Top'#2#9#5'Width'#2 + +'x'#0#0#9'TCheckBox'#30'OpenLastProjectOnStartCheckBox'#7'Caption'#6#30'Open' + +'LastProjectOnStartCheckBox'#8'OnChange'#7'$OpenLastProjectOnStartCheckBoxCh' + +'ange'#8'TabOrder'#2#0#4'Left'#2#6#6'Height'#2#20#3'Top'#2'*'#5'Width'#3#216 + +#0#0#0#7'TButton'#20'SaveSettingsAsButton'#8'AutoSize'#9#25'BorderSpacing.In' + +'nerBorder'#2#4#7'Caption'#6#20'SaveSettingsAsButton'#7'OnClick'#7#25'SaveSe' + +'ttingsAsButtonClick'#8'TabOrder'#2#1#4'Left'#2#6#6'Height'#2#26#3'Top'#2'R' + +#5'Width'#3#137#0#0#0#5'TEdit'#17'H2PasFilenameEdit'#18'BorderSpacing.Left'#2 + +#6#17'BorderSpacing.Top'#2#6#13'OnEditingDone'#7#28'H2PasFilenameEditEditing' + +'Done'#8'TabOrder'#2#2#4'Text'#6#17'H2PasFilenameEdit'#22'AnchorSideLeft.Con' + +'trol'#7#18'H2PasFilenameLabel'#19'AnchorSideLeft.Side'#7#9'asrBottom'#4'Lef' + +'t'#3#132#0#6'Height'#2#23#3'Top'#2#4#5'Width'#3'`'#1#0#0#7'TButton'#25'h2pa' + +'sFilenameBrowseButton'#7'Anchors'#11#5'akTop'#6'akLeft'#8'akBottom'#0#25'Bo' + +'rderSpacing.InnerBorder'#2#4#7'Caption'#6#3'...'#7'OnClick'#7#30'h2pasFilen' + +'ameBrowseButtonClick'#8'TabOrder'#2#3#22'AnchorSideLeft.Control'#7#17'H2Pas' + +'FilenameEdit'#19'AnchorSideLeft.Side'#7#9'asrBottom'#21'AnchorSideTop.Contr' + +'ol'#7#17'H2PasFilenameEdit'#24'AnchorSideBottom.Control'#7#17'H2PasFilename' + +'Edit'#21'AnchorSideBottom.Side'#7#9'asrBottom'#4'Left'#3#228#1#6'Height'#2 + +#23#3'Top'#2#4#5'Width'#2'#'#0#0#7'TButton'#17'NewSettingsButton'#8'AutoSize' + +#9#25'BorderSpacing.InnerBorder'#2#4#7'Caption'#6#17'NewSettingsButton'#7'On' + +'Click'#7#22'NewSettingsButtonClick'#8'TabOrder'#2#4#4'Left'#2#6#6'Height'#2 + +#26#3'Top'#2'|'#5'Width'#2'v'#0#0#0#0#7'TButton'#18'OpenSettingsButton'#7'An' + +'chors'#11#6'akLeft'#8'akBottom'#0#8'AutoSize'#9#20'BorderSpacing.Around'#2#5 + +#25'BorderSpacing.InnerBorder'#2#4#7'Caption'#6#18'OpenSettingsButton'#7'OnC' + +'lick'#7#23'OpenSettingsButtonClick'#8'TabOrder'#2#1#22'AnchorSideLeft.Contr' + +'ol'#7#5'Owner'#24'AnchorSideBottom.Control'#7#5'Owner'#21'AnchorSideBottom.' + +'Side'#7#9'asrBottom'#4'Left'#2#5#6'Height'#2#26#3'Top'#3#214#1#5'Width'#2'|' + +#0#0#7'TButton'#18'SaveSettingsButton'#7'Anchors'#11#6'akLeft'#8'akBottom'#0 + +#8'AutoSize'#9#20'BorderSpacing.Around'#2#5#25'BorderSpacing.InnerBorder'#2#4 + +#7'Caption'#6#18'SaveSettingsButton'#7'OnClick'#7#23'SaveSettingsButtonClick' + +#8'TabOrder'#2#2#22'AnchorSideLeft.Control'#7#18'OpenSettingsButton'#19'Anch' + +'orSideLeft.Side'#7#9'asrBottom'#24'AnchorSideBottom.Control'#7#5'Owner'#21 + +'AnchorSideBottom.Side'#7#9'asrBottom'#4'Left'#3#134#0#6'Height'#2#26#3'Top' + +#3#214#1#5'Width'#2'z'#0#0#7'TButton'#11'CloseButton'#7'Anchors'#11#7'akRigh' + +'t'#8'akBottom'#0#8'AutoSize'#9#20'BorderSpacing.Around'#2#5#25'BorderSpacin' + +'g.InnerBorder'#2#4#7'Caption'#6#11'CloseButton'#7'OnClick'#7#16'CloseButton' + +'Click'#8'TabOrder'#2#3#23'AnchorSideRight.Control'#7#5'Owner'#20'AnchorSide' + +'Right.Side'#7#9'asrBottom'#24'AnchorSideBottom.Control'#7#5'Owner'#21'Ancho' + +'rSideBottom.Side'#7#9'asrBottom'#4'Left'#3#187#2#6'Height'#2#26#3'Top'#3#214 + +#1#5'Width'#2'Q'#0#0#10'TSynCppSyn'#10'SynCppSyn1'#13'DefaultFilter'#6'BC++-' + +'Quelltexte (*.c,*.cpp,*.h,*.hpp,*.hh)|*.c;*.cpp;*.h;*.hpp;*.hh'#7'Enabled'#8 + +#4'left'#3#174#0#3'top'#2'\'#0#0#0 ]); diff --git a/components/h2pas/h2pasdlg.pas b/components/h2pas/h2pasdlg.pas index e523c78f33..5c24d1875b 100644 --- a/components/h2pas/h2pasdlg.pas +++ b/components/h2pas/h2pasdlg.pas @@ -28,6 +28,8 @@ uses SynEdit, SynHighlighterCPP, FileProcs, IDEMsgIntf, MenuIntf, IDECommands, BaseIDEIntf, IDEDialogs, LazIDEIntf, + SrcEditorIntf, + CodeToolManager, CodeCache, H2PasStrConsts, H2PasConvert; type @@ -35,20 +37,13 @@ type { TH2PasDialog } TH2PasDialog = class(TForm) - h2pasOptionsCheckGroup: TCheckGroup; - ConvertButton: TButton; - NewSettingsButton: TButton; - h2pasFilenameBrowseButton: TButton; - H2PasFilenameEdit: TEdit; - H2PasFilenameLabel: TLabel; - OutputDirBrowseButton: TButton; MainPageControl: TPageControl; + SynCppSyn1: TSynCppSyn; // c header files FilesTabSheet: TTabSheet; CHeaderFilesSplitter1: TSplitter; AddCHeaderFilesButton: TButton; - ConvertTabSheet: TTabSheet; UnselectAllCHeaderFilesButton: TButton; SelectAllCHeaderFilesButton: TButton; DeleteCHeaderFilesButton: TButton; @@ -56,15 +51,27 @@ type // h2pas h2pasOptionsTabSheet: TTabSheet; + h2pasOptionsCheckGroup: TCheckGroup; LibnameEdit: TEdit; LibNameLabel: TLabel; OutputExtEdit: TEdit; OutputExtLabel: TLabel; OutputDirEdit: TEdit; OutputDirLabel: TLabel; + OutputDirBrowseButton: TButton; + + // convert + ConvertTabSheet: TTabSheet; + ConvertButton: TButton; + ConvertErrorGroupBox: TGroupBox; + ConvertErrorSynEdit: TSynEdit; // settings SettingsTabSheet: TTabSheet; + h2pasFilenameBrowseButton: TButton; + H2PasFilenameEdit: TEdit; + H2PasFilenameLabel: TLabel; + NewSettingsButton: TButton; SaveSettingsAsButton: TButton; OpenLastProjectOnStartCheckBox: TCheckBox; @@ -106,6 +113,7 @@ type procedure UpdateProjectChanged; // show project settings procedure UpdateCaption; procedure ClearMessages; + procedure UpdateHighlighter; // project settings procedure UpdateFilesPage; @@ -122,6 +130,8 @@ type function OnIDESavedAll(Sender: TObject): TModalResult; public function Convert: TModalResult; + procedure ShowH2PasError(MsgLine: integer); + procedure ClearError; function SaveSettings: TModalResult; function SaveGlobalSettings: TModalResult; @@ -213,6 +223,9 @@ begin FConverter:=TH2PasConverter.Create; LoadGlobalSettings; + ClearError; + UpdateHighlighter; + // create project if Converter.AutoOpenLastProject and FileExists(Converter.CurrentProjectFilename) then @@ -509,6 +522,13 @@ begin IDEMessagesWindow.Clear; end; +procedure TH2PasDialog.UpdateHighlighter; +begin + SourceEditorWindow.GetHighlighterSettings(SynCppSyn1); + SourceEditorWindow.GetEditorControlSettings(ConvertErrorSynEdit); + ConvertErrorSynEdit.Gutter.ShowLineNumbers:=true; +end; + procedure TH2PasDialog.UpdateFilesPage; var i: Integer; @@ -647,6 +667,7 @@ end; function TH2PasDialog.Convert: TModalResult; begin Result:=mrCancel; + ClearError; if not Project.HasEnabledFiles then begin IDEMessageDialog('Nothing to do', @@ -670,6 +691,62 @@ begin LazarusIDE.SaveSourceEditorChangesToCodeCache(-1); Result:=Converter.Execute; + if Result<>mrOk then begin + ShowH2PasError(-1); + end; +end; + +procedure TH2PasDialog.ShowH2PasError(MsgLine: integer); +var + Line: TIDEMessageLine; + LineNumber: integer; + Column: integer; + CodeBuf: TCodeBuffer; + NewPos: TPoint; + Filename: string; + s: String; +begin + if MsgLine<0 then + MsgLine:=Converter.FindH2PasErrorMessage; + if (MsgLine<0) or (MsgLine>=IDEMessagesWindow.LinesCount) then begin + ClearError; + exit; + end; + + Line:=IDEMessagesWindow.Lines[MsgLine]; + if not Converter.GetH2PasErrorPostion(Line.Msg,Filename,LineNumber,Column) + then exit; + DebugLn(['TH2PasDialog.ShowH2PasError LineNumber=',LineNumber,' Column=',Column,' Filename=',Filename]); + + // open error position in synedit + CodeBuf:=CodeToolBoss.LoadFile(Filename,false,false); + if CodeBuf=nil then exit; + ConvertErrorSynEdit.BeginUpdate; + CodeBuf.AssignTo(ConvertErrorSynEdit.Lines,false); + NewPos:=Point(Column,LineNumber); + if NewPos.Y<1 then NewPos.Y:=1; + if NewPos.X<1 then NewPos.X:=1; + ConvertErrorSynEdit.LogicalCaretXY:=NewPos; + ConvertErrorSynEdit.TopLine:=NewPos.Y-3; + ConvertErrorSynEdit.EndUpdate; + + // show error position in groupbox + s:='Error: '; + if LineNumber>=1 then + s:=s+IntToStr(LineNumber); + if Column>=1 then begin + if LineNumber>=1 then + s:=s+','; + s:=s+IntToStr(Column); + end; + s:=s+' '+Filename; + ConvertErrorGroupBox.Caption:=s; +end; + +procedure TH2PasDialog.ClearError; +begin + ConvertErrorSynEdit.Lines.Clear; + ConvertErrorGroupBox.Caption:='No error'; end; function TH2PasDialog.SaveSettings: TModalResult; @@ -845,3 +922,4 @@ initialization end. + diff --git a/ide/checkcompileropts.pas b/ide/checkcompileropts.pas index 7fe16bafba..77a6982376 100644 --- a/ide/checkcompileropts.pas +++ b/ide/checkcompileropts.pas @@ -45,7 +45,7 @@ type procedure Add(const Msg, CurDir: String; ProgressLine: boolean; OriginalIndex: integer); procedure AddMsg(const Msg, CurDir: String; OriginalIndex: integer); - procedure AddProgress(const Msg, CurDir: String; OriginalIndex: integer); + procedure AddProgress(Line: TIDEScanMessageLine); public property Options: TCompilerOptions read FOptions write SetOptions; property Test: TCompilerOptionsTest read FTest; @@ -228,10 +228,9 @@ begin Add(Msg,CurDir,false,OriginalIndex); end; -procedure TCheckCompilerOptsDlg.AddProgress(const Msg, CurDir: String; - OriginalIndex: integer); +procedure TCheckCompilerOptsDlg.AddProgress(Line: TIDEScanMessageLine); begin - Add(Msg,CurDir,false,OriginalIndex); + Add(Line.Line,Line.WorkingDirectory,false,Line.LineNumber); end; initialization diff --git a/ide/compiler.pp b/ide/compiler.pp index 6a5a55951c..7b0705030b 100644 --- a/ide/compiler.pp +++ b/ide/compiler.pp @@ -157,7 +157,7 @@ begin if OutputFilter<>nil then begin OutputFilter.Options:=[ofoSearchForFPCMessages,ofoExceptionOnError]; OutputFilter.CompilerOptions:=AProject.CompilerOptions; - OutputFilter.Execute(TheProcess); + OutputFilter.Execute(TheProcess,Self); end else begin TheProcess.Execute; end; @@ -185,8 +185,9 @@ end; procedure TCompiler.WriteError(const Msg: string); begin DebugLn('TCompiler.WriteError ',Msg); - if OutputFilter<>nil then - OutputFilter.ReadLine(Msg,true); + if OutputFilter<>nil then begin + OutputFilter.ReadConstLine(Msg,true); + end; end; diff --git a/ide/editoroptions.pp b/ide/editoroptions.pp index 29e3fc559b..b0c3f81a4f 100644 --- a/ide/editoroptions.pp +++ b/ide/editoroptions.pp @@ -81,7 +81,7 @@ uses type TPreviewEditor = TSynEdit; TPreviewPasSyn = TSynFreePascalSyn; - TCustomSyn = TSynCustomHighlighter; + TCustomSyn = TSynCustomHighlighter; TSynHighlightElement = TSynHighlighterAttributes; TCustomSynClass = class of TCustomSyn; diff --git a/ide/exttooldialog.pas b/ide/exttooldialog.pas index 9248175f39..1137bd7f1e 100644 --- a/ide/exttooldialog.pas +++ b/ide/exttooldialog.pas @@ -81,9 +81,9 @@ type function Load(Config: TConfigStorage): TModalResult; function Load(Config: TConfigStorage; const Path: string): TModalResult; procedure LoadShortCuts(KeyCommandRelationList: TKeyCommandRelationList); - function Run(ExtTool: TExternalToolOptions; + function Run(ExtTool: TIDEExternalToolOptions; Macros: TTransferMacroList): TModalResult; - function Run(ExtTool: TExternalToolOptions; + function Run(ExtTool: TIDEExternalToolOptions; Macros: TTransferMacroList; TheOutputFilter: TOutputFilter; CompilerOptions: TBaseCompilerOptions): TModalResult; @@ -164,6 +164,7 @@ begin end; { TExternalToolList } + function TExternalToolList.GetToolOpts(Index: integer): TExternalToolOptions; begin Result:=TExternalToolOptions(inherited Items[Index]); @@ -281,7 +282,7 @@ begin end; end; -function TExternalToolList.Run(ExtTool: TExternalToolOptions; +function TExternalToolList.Run(ExtTool: TIDEExternalToolOptions; Macros: TTransferMacroList): TModalResult; begin Result:=Run(ExtTool,Macros,nil,nil); @@ -295,7 +296,7 @@ begin Run(Items[Index],Macros); end; -function TExternalToolList.Run(ExtTool: TExternalToolOptions; +function TExternalToolList.Run(ExtTool: TIDEExternalToolOptions; Macros: TTransferMacroList; TheOutputFilter: TOutputFilter; CompilerOptions: TBaseCompilerOptions): TModalResult; var WorkingDir, Filename, Params, CmdLine, Title: string; @@ -368,8 +369,8 @@ begin try Result:=mrCancel; try - if TheOutputFilter.Execute(TheProcess) then begin - TheOutputFilter.ReadLine('"'+Title+'" completed',true); + if TheOutputFilter.Execute(TheProcess,Self,ExtTool) then begin + TheOutputFilter.ReadConstLine('"'+Title+'" completed',true); end; if TheOutputFilter.ErrorExists then begin ErrorOccurred:=true; diff --git a/ide/exttooleditdlg.pas b/ide/exttooleditdlg.pas index 85b96ce934..ea40dc9c07 100644 --- a/ide/exttooleditdlg.pas +++ b/ide/exttooleditdlg.pas @@ -48,6 +48,20 @@ uses KeyMapping, TransferMacros, IDEProcs, LazarusIDEStrConsts; type + { TExternalToolOptions } + + TExternalToolOptions = class(TIDEExternalToolOptions) + private + fKey: word; + fShift: TShiftState; + public + procedure Assign(Source: TPersistent); override; + procedure Clear; override; + // key and shift are loaded with the keymapping in the editoroptions + property Key: word read fKey write fKey; + property Shift: TShiftState read fShift write fShift; + end; + { the editor dialog for a single external tool } @@ -83,7 +97,7 @@ type procedure MacrosInsertButtonClick(Sender: TObject); procedure MacrosListboxClick(Sender: TObject); private - fOptions: TExternalToolOptions; + fOptions: TExternalToolOptions; fTransferMacros: TTransferMacroList; GrabbingKey: integer; // 0=none, 1=Default key procedure ActivateGrabbing(AGrabbingKey: integer); @@ -687,4 +701,26 @@ begin MacrosInsertButton.Enabled:=(MacrosListbox.ItemIndex>=0); end; +{ TExternalToolOptions } + +procedure TExternalToolOptions.Assign(Source: TPersistent); +var + Src: TExternalToolOptions; +begin + if Source is TExternalToolOptions then begin + Src:=TExternalToolOptions(Source); + fKey:=Src.fKey; + fShift:=Src.fShift; + end else begin + inherited Assign(Source); + end; +end; + +procedure TExternalToolOptions.Clear; +begin + fKey:=VK_UNKNOWN; + fShift:=[]; + inherited Clear; +end; + end. diff --git a/ide/main.pp b/ide/main.pp index e48a18669e..54272a96c7 100644 --- a/ide/main.pp +++ b/ide/main.pp @@ -696,6 +696,7 @@ type // external tools function PrepareForCompile: TModalResult; override; + function RunExternalTool(Tool: TIDEExternalToolOptions): TModalResult; override; function DoRunExternalTool(Index: integer): TModalResult; function DoSaveBuildIDEConfigs(Flags: TBuildLazarusFlags): TModalResult; override; function DoBuildLazarus(Flags: TBuildLazarusFlags): TModalResult; override; @@ -8521,6 +8522,13 @@ begin end; end; +function TMainIDE.RunExternalTool(Tool: TIDEExternalToolOptions): TModalResult; +begin + SourceNotebook.ClearErrorLines; + Result:=EnvironmentOptions.ExternalTools.Run(Tool,MacroList); + DoCheckFilesOnDisk; +end; + function TMainIDE.DoCheckSyntax: TModalResult; var ActiveUnitInfo:TUnitInfo; diff --git a/ide/mainbase.pas b/ide/mainbase.pas index 40be7e0ba8..c52f437bd5 100644 --- a/ide/mainbase.pas +++ b/ide/mainbase.pas @@ -1233,7 +1233,7 @@ function TMainIDEBase.DoCheckAmbiguousSources(const AFilename: string; begin Result:=mrOk; if Compiling then begin - TheOutputFilter.ReadLine(Format(lisWarningAmbiguousFileFoundSourceFileIs, + TheOutputFilter.ReadConstLine(Format(lisWarningAmbiguousFileFoundSourceFileIs, ['"', AmbiguousFilename, '"', '"', AFilename, '"']), true); end; end; diff --git a/ide/msgview.pp b/ide/msgview.pp index 78a8ba6e16..dd4608961c 100644 --- a/ide/msgview.pp +++ b/ide/msgview.pp @@ -37,28 +37,12 @@ unit MsgView; interface uses - Classes, - AVL_Tree, - ClipBrd, - Controls, - DialogProcs, - Dialogs, - EnvironmentOpts, - FileUtil, - Forms, - IDECommands, - IDEOptionDefs, - IDEProcs, - InputHistory, - KeyMapping, - LazarusIDEStrConsts, - LCLProc, - LResources, - MenuIntf, - IDEMsgIntf, - Menus, + Classes, SysUtils, AVL_Tree, + LCLProc, LResources, ClipBrd, Controls, Dialogs, FileUtil, Forms, Menus, StdCtrls, - SysUtils; + IDEExternToolIntf, IDECommands, MenuIntf, IDEMsgIntf, + DialogProcs, EnvironmentOpts, + LazarusIDEStrConsts, IDEOptionDefs, IDEProcs, InputHistory, KeyMapping; type @@ -128,7 +112,7 @@ type procedure Add(const Msg, CurDir: string; ProgressLine, VisibleLine: boolean; OriginalIndex: integer); procedure AddMsg(const Msg, CurDir: string; OriginalIndex: integer); override; - procedure AddProgress(const Msg, CurDir: string; OriginalIndex: integer); + procedure AddProgress(ScanLine: TIDEScanMessageLine); procedure AddSeparator; procedure CollectLineParts(Sender: TObject; SrcLines: TIDEMessageLineList); procedure ClearTillLastSeparator; @@ -419,10 +403,9 @@ begin Add(Msg, CurDir, False, True, OriginalIndex); end; -procedure TMessagesView.AddProgress(const Msg, CurDir: string; - OriginalIndex: integer); +procedure TMessagesView.AddProgress(ScanLine: TIDEScanMessageLine); begin - Add(Msg, CurDir, True, True, OriginalIndex); + Add(ScanLine.Line, ScanLine.WorkingDirectory, True, True,ScanLine.LineNumber); end; procedure TMessagesView.AddSeparator; diff --git a/ide/outputfilter.pas b/ide/outputfilter.pas index ae8f203451..923677686b 100644 --- a/ide/outputfilter.pas +++ b/ide/outputfilter.pas @@ -37,11 +37,12 @@ interface uses Classes, Math, SysUtils, Forms, Controls, CompilerOptions, Project, Process, - IDEProcs, DynQueue, FileUtil, LclProc, LazConf, AsyncProcess, IDEMsgIntf; + AsyncProcess, LCLProc, DynQueue, FileUtil, + IDEMsgIntf, IDEExternToolIntf, + IDEProcs, LazConf; type - TOnOutputString = procedure(const Msg, Directory: String; - OriginalIndex: integer) of object; + TOnOutputString = procedure(Line: TIDEScanMessageLine) of object; TOnAddFilteredLine = procedure(const Msg, Directory: String; OriginalIndex: integer) of object; TOnGetIncludePath = function(const Directory: string; @@ -87,7 +88,22 @@ type end; TOFOnEndReading = procedure(Sender: TObject; Lines: TIDEMessageLineList) - of object; + of object; + + TOutputFilter = class; + + { TOFScanLine } + + TOFScanLine = class(TIDEScanMessageLine) + private + FFilter: TOutputFilter; + public + constructor Create(TheFilter: TOutputFilter); + procedure Init(const aLine, aWorkDir: string; const aLineNumber: integer); + procedure LineChanged(const OldValue: string); override; + procedure WorkingDirectoryChanged(const OldValue: string); override; + property Filter: TOutputFilter read FFilter; + end; { TOutputFilter } @@ -95,6 +111,7 @@ type private FAsyncDataAvailable: boolean; FAsyncProcessTerminated: boolean; + FCaller: TObject; FCompilerOptions: TBaseCompilerOptions; FBufferingOutputLock: integer; fCurrentDirectory: string; @@ -109,6 +126,7 @@ type fOnGetIncludePath: TOnGetIncludePath; fOnAddFilteredLine: TOnAddFilteredLine; fOptions: TOuputFilterOptions; + FScanLine: TOFScanLine; FStopExecute: boolean; FLasTOutputLineParts: integer; fLastOutputTime: TDateTime; @@ -116,6 +134,7 @@ type fLastSearchedIncFilename: string; fProcess: TProcess; FAsyncOutput: TDynamicDataQueue; + FTool: TIDEExternalToolOptions; procedure DoAddFilteredLine(const s: string; OriginalIndex: integer = -1); procedure DoAddLastLinkerMessages(SkipLastLine: boolean); procedure DoAddLastAssemblerMessages; @@ -128,7 +147,8 @@ type public ErrorExists: boolean; Aborted: boolean; - function Execute(TheProcess: TProcess): boolean; + function Execute(TheProcess: TProcess; aCaller: TObject = nil; + aTool: TIDEExternalToolOptions = nil): boolean; function GetSourcePosition(const Line: string; var Filename:string; var CaretXY: TPoint; var MsgType: TErrorType): boolean; procedure Clear; @@ -138,7 +158,8 @@ type MainSrcFile: string): boolean; function IsHintForParameterSenderNotUsed(const OutputLine: string): boolean; function IsParsing: boolean; - procedure ReadLine(const s: string; DontFilterLine: boolean); + procedure ReadLine(var s: string; DontFilterLine: boolean); + procedure ReadConstLine(const s: string; DontFilterLine: boolean); function ReadFPCompilerLine(const s: string): boolean; function ReadMakeLine(const s: string): boolean; procedure WriteOutput(Flush: boolean); @@ -154,15 +175,18 @@ type property LastMessageType: TOutputMessageType read fLastMessageType; property OnGetIncludePath: TOnGetIncludePath read fOnGetIncludePath write fOnGetIncludePath; - property OnReadLine: TOnOutputString read fOnReadLine write fOnReadLine; + property OnReadLine: TOnOutputString read fOnReadLine write fOnReadLine;// used by the messages window property OnAddFilteredLine: TOnAddFilteredLine - read fOnAddFilteredLine write fOnAddFilteredLine; + read fOnAddFilteredLine write fOnAddFilteredLine;// used by the messages window property Options: TOuputFilterOptions read fOptions write fOptions; property CompilerOptions: TBaseCompilerOptions read FCompilerOptions write FCompilerOptions; property CurrentMessageParts: TStrings read GetCurrentMessageParts; property AsyncProcessTerminated: boolean read FAsyncProcessTerminated; property OnEndReading: TOFOnEndReading read FOnEndReading write FOnEndReading; + property Caller: TObject read FCaller; + property ScanLine: TOFScanLine read FScanLine; + property Tool: TIDEExternalToolOptions read FTool; end; EOutputFilterError = class(Exception) @@ -212,7 +236,8 @@ begin fLastSearchedIncFilename:=''; end; -function TOutputFilter.Execute(TheProcess: TProcess): boolean; +function TOutputFilter.Execute(TheProcess: TProcess; aCaller: TObject; + aTool: TIDEExternalToolOptions): boolean; const BufSize = 4096; var @@ -223,6 +248,10 @@ begin Result:=true; Clear; fProcess:=TheProcess; + FCaller:=aCaller; + FTool:=aTool; + FScanLine:=TOFScanLine.Create(Self); + //debugln('TOutputFilter.Execute A CurrentDirectory="',TheProcess.CurrentDirectory,'"'); fCurrentDirectory:=TrimFilename(fProcess.CurrentDirectory); if fCurrentDirectory='' then fCurrentDirectory:=GetCurrentDir; @@ -250,7 +279,7 @@ begin fProcess.Terminate(0); Aborted:=true; Result:=false; - ReadLine('aborted',true); + ReadConstLine('aborted',true); break; end; @@ -314,10 +343,13 @@ begin fProcess:=nil; FreeAndNil(FAsyncOutput); if Assigned(OnEndReading) then OnEndReading(Self,fOutput); + FreeAndNil(FScanLine); + FTool:=nil; + FCaller:=nil; end; end; -procedure TOutputFilter.ReadLine(const s: string; DontFilterLine: boolean); +procedure TOutputFilter.ReadLine(var s: string; DontFilterLine: boolean); // this is called for every line written by the external tool (=Output) // it parses the output begin @@ -326,8 +358,17 @@ begin fLastErrorType:=etNone; fOutput.Add(s); WriteOutput(false); - if Assigned(OnReadLine) then - OnReadLine(s,fCurrentDirectory,fOutput.Count-1); + if FScanLine<>nil then begin + FScanLine.Init(s,fCurrentDirectory,fOutput.Count-1); + if Tool<>nil then begin + Tool.ParseLine(Self,FScanLine); + s:=FScanLine.Line; + end; + if Assigned(OnReadLine) then begin + OnReadLine(FScanLine); + s:=FScanLine.Line; + end; + end; if DontFilterLine then begin DoAddFilteredLine(s); @@ -342,6 +383,15 @@ begin end; end; +procedure TOutputFilter.ReadConstLine(const s: string; DontFilterLine: boolean + ); +var + Line: String; +begin + Line:=s; + ReadLine(Line,DontFilterLine); +end; + function TOutputFilter.ReadFPCompilerLine(const s: string): boolean; { returns true, if it is a compiler message Examples for freepascal compiler messages: @@ -1207,6 +1257,32 @@ begin FOriginalIndices[Index2]:=i; end; +{ TOFScanLine } + +constructor TOFScanLine.Create(TheFilter: TOutputFilter); +begin + FFilter:=TheFilter; + inherited Create(Filter.Caller,Filter.Tool); +end; + +procedure TOFScanLine.Init(const aLine, aWorkDir: string; + const aLineNumber: integer); +begin + Line:=aLine; + WorkingDirectory:=aWorkDir; + SetLineNumber(aLineNumber); +end; + +procedure TOFScanLine.LineChanged(const OldValue: string); +begin + +end; + +procedure TOFScanLine.WorkingDirectoryChanged(const OldValue: string); +begin + +end; + end. diff --git a/ide/uniteditor.pp b/ide/uniteditor.pp index 92e20154fc..c32ca94eb6 100644 --- a/ide/uniteditor.pp +++ b/ide/uniteditor.pp @@ -669,6 +669,7 @@ type procedure PasteClicked(Sender: TObject); procedure CopyFilenameClicked(Sender: TObject); + // bookmarks Procedure ToggleBookmark(Value: Integer); Procedure SetBookmark(Value: Integer); Procedure GotoBookmark(Value: Integer); @@ -676,6 +677,8 @@ type Procedure ReloadEditorOptions; procedure CheckFont; Procedure GetSynEditPreviewSettings(APreviewEditor: TObject); + function GetEditorControlSettings(EditControl: TControl): boolean; override; + function GetHighlighterSettings(Highlighter: TObject): boolean; override; Property CodeTemplateModul: TSynEditAutoComplete read FCodeTemplateModul write FCodeTemplateModul; @@ -5014,7 +5017,6 @@ Begin Notebook.Pages.Delete(PageIndex); //writeln('TSourceNotebook.CloseFile C PageIndex=',PageIndex,' Notebook.PageCount=',Notebook.PageCount); UpdateStatusBar; - ActiveControl:=Notebook.Page[Notebook.PageIndex]; end else begin //writeln('TSourceNotebook.CloseFile D PageIndex=',PageIndex); @@ -5689,6 +5691,29 @@ begin ASynEdit.Highlighter:=Highlighters[lshFreePascal]; end; +function TSourceNotebook.GetEditorControlSettings(EditControl: TControl + ): boolean; +begin + Result:=true; + if EditControl is TSynEdit then begin + EditorOpts.GetSynEditSettings(TSynEdit(EditControl)); + Result:=true; + end else begin + Result:=false; + end; +end; + +function TSourceNotebook.GetHighlighterSettings(Highlighter: TObject): boolean; +begin + Result:=true; + if Highlighter is TSynCustomHighlighter then begin + EditorOpts.GetHighlighterSettings(TSynCustomHighlighter(Highlighter)); + Result:=true; + end else begin + Result:=false; + end; +end; + procedure TSourceNotebook.ClearErrorLines; var i: integer; begin diff --git a/ideintf/ideexterntoolintf.pas b/ideintf/ideexterntoolintf.pas index fba5d8ef25..242ef4f799 100644 --- a/ideintf/ideexterntoolintf.pas +++ b/ideintf/ideexterntoolintf.pas @@ -20,124 +20,152 @@ unit IDEExternToolIntf; interface uses - Classes, SysUtils, LCLType, LazConfigStorage, Forms, Controls, - BaseIDEIntf; + Classes, SysUtils, LCLType, LazConfigStorage, Forms, Controls, BaseIDEIntf; { The xml format version: When the format changes (new values, changed formats) we can distinguish old files and are able to convert them. } -const ExternalToolOptionsFormat = '1.0'; +const + ExternalToolOptionsVersion = '1'; type + TIDEExternalToolOptions = class; + + { TIDEScanMessageLine } + + TIDEScanMessageLine = class(TPersistent) + private + FCaller: TObject; + FLine: string; + FLineNumber: integer; + FTool: TIDEExternalToolOptions; + FWorkingDirectory: string; + procedure SetLine(const AValue: string); + procedure SetWorkingDirectory(const AValue: string); + protected + procedure SetTool(const AValue: TIDEExternalToolOptions); + procedure SetLineNumber(const NewLineNumber: integer); + procedure LineChanged(const OldValue: string); virtual; abstract; + procedure WorkingDirectoryChanged(const OldValue: string); virtual; abstract; + public + constructor Create(TheCaller: TObject = nil; TheTool: TIDEExternalToolOptions = nil); + property Caller: TObject read FCaller; + property Line: string read FLine write SetLine; + property WorkingDirectory: string read FWorkingDirectory write SetWorkingDirectory; + property LineNumber: integer read FLineNumber; + property Tool: TIDEExternalToolOptions read FTool; + end; + + + TOnIDEExtToolParseLine = procedure(Sender: TObject; + Line: TIDEScanMessageLine) of object; + { - TExternalToolOptions - the storage object for a single external tool + TIDEExternalToolOptions - the storage object for a single external tool } - TExternalToolOptions = class + TIDEExternalToolOptions = class(TPersistent) private fCmdLineParams: string; FEnvironmentOverrides: TStringList; fFilename: string; - fKey: word; + FOnParseLine: TOnIDEExtToolParseLine; FScanOutput: boolean; fScanOutputForFPCMessages: boolean; fScanOutputForMakeMessages: boolean; - fShift: TShiftState; FShowAllOutput: boolean; fTitle: string; fWorkingDirectory: string; procedure SetScanOutput(const AValue: boolean); procedure SetShowAllOutput(const AValue: boolean); public - procedure Assign(Source: TExternalToolOptions); constructor Create; destructor Destroy; override; - procedure Clear; + procedure Assign(Source: TPersistent); override; + procedure Clear; virtual; function NeedsOutputFilter: boolean; - function Load(Config: TConfigStorage): TModalResult; - function Save(Config: TConfigStorage): TModalResult; + function Load(Config: TConfigStorage): TModalResult; virtual; + function Save(Config: TConfigStorage): TModalResult; virtual; function ShortDescription: string; procedure AssignEnvironmentTo(Strings: TStrings); + procedure ParseLine(Sender: TObject; Line: TIDEScanMessageLine); virtual; property CmdLineParams: string read fCmdLineParams write fCmdLineParams; property Filename: string read fFilename write fFilename; - property Key: word read fKey write fKey; property Title: string read fTitle write fTitle; property ScanOutputForFPCMessages: boolean read fScanOutputForFPCMessages write fScanOutputForFPCMessages; property ScanOutputForMakeMessages: boolean read fScanOutputForMakeMessages write fScanOutputForMakeMessages; - property Shift: TShiftState read fShift write fShift; property WorkingDirectory: string read fWorkingDirectory write fWorkingDirectory; property EnvironmentOverrides: TStringList read FEnvironmentOverrides; property ScanOutput: boolean read FScanOutput write SetScanOutput; property ShowAllOutput: boolean read FShowAllOutput write SetShowAllOutput; + property OnParseLine: TOnIDEExtToolParseLine read FOnParseLine write FOnParseLine; end; implementation -{ TExternalToolOptions } +{ TIDEExternalToolOptions } -procedure TExternalToolOptions.SetScanOutput(const AValue: boolean); +procedure TIDEExternalToolOptions.SetScanOutput(const AValue: boolean); begin if FScanOutput=AValue then exit; FScanOutput:=AValue; end; -procedure TExternalToolOptions.SetShowAllOutput(const AValue: boolean); +procedure TIDEExternalToolOptions.SetShowAllOutput(const AValue: boolean); begin if FShowAllOutput=AValue then exit; FShowAllOutput:=AValue; end; -procedure TExternalToolOptions.Assign(Source: TExternalToolOptions); +procedure TIDEExternalToolOptions.Assign(Source: TPersistent); +var + Src: TIDEExternalToolOptions; begin if Source=Self then exit; - if Source=nil then - Clear - else begin - fTitle:=Source.fTitle; - fFilename:=Source.fFilename; - fCmdLineParams:=Source.fCmdLineParams; - fWorkingDirectory:=Source.fWorkingDirectory; - fKey:=Source.fKey; - fShift:=Source.fShift; - fScanOutputForFPCMessages:=Source.fScanOutputForFPCMessages; - fScanOutputForMakeMessages:=Source.fScanOutputForMakeMessages; - FScanOutput:=Source.FScanOutput; - FShowAllOutput:=Source.FShowAllOutput; - end; + if Source is TIDEExternalToolOptions then begin + Src:=TIDEExternalToolOptions(Source); + fTitle:=Src.fTitle; + fFilename:=Src.fFilename; + fCmdLineParams:=Src.fCmdLineParams; + fWorkingDirectory:=Src.fWorkingDirectory; + fScanOutputForFPCMessages:=Src.fScanOutputForFPCMessages; + fScanOutputForMakeMessages:=Src.fScanOutputForMakeMessages; + FScanOutput:=Src.FScanOutput; + FShowAllOutput:=Src.FShowAllOutput; + end else + inherited Assign(Source); end; -constructor TExternalToolOptions.Create; +constructor TIDEExternalToolOptions.Create; begin inherited Create; FEnvironmentOverrides:=TStringList.Create; Clear; end; -destructor TExternalToolOptions.Destroy; +destructor TIDEExternalToolOptions.Destroy; begin FEnvironmentOverrides.Free; inherited Destroy; end; -procedure TExternalToolOptions.Clear; +procedure TIDEExternalToolOptions.Clear; begin fTitle:=''; fFilename:=''; fCmdLineParams:=''; fWorkingDirectory:=''; - fKey:=VK_UNKNOWN; - fShift:=[]; fScanOutputForFPCMessages:=false; fScanOutputForMakeMessages:=false; FScanOutput:=false; FShowAllOutput:=false; end; -function TExternalToolOptions.Load(Config: TConfigStorage): TModalResult; +function TIDEExternalToolOptions.Load(Config: TConfigStorage): TModalResult; begin Clear; fTitle:=Config.GetValue('Title/Value',''); @@ -150,13 +178,12 @@ begin 'ScanOutputForMakeMessages/Value',false); FShowAllOutput:=Config.GetValue('ShowAllOutput/Value',false); Config.GetValue('EnvironmentOverrides/',FEnvironmentOverrides); - // key and shift are loaded with the keymapping in the editoroptions Result:=mrOk; end; -function TExternalToolOptions.Save(Config: TConfigStorage): TModalResult; +function TIDEExternalToolOptions.Save(Config: TConfigStorage): TModalResult; begin - Config.SetValue('Format/Version',ExternalToolOptionsFormat); + Config.SetValue('Format/Version',ExternalToolOptionsVersion); Config.SetDeleteValue('Title/Value',fTitle,''); Config.SetDeleteValue('Filename/Value',fFilename,''); Config.SetDeleteValue('CmdLineParams/Value',fCmdLineParams,''); @@ -169,25 +196,70 @@ begin false); Config.SetDeleteValue('ShowAllOutput/Value',FShowAllOutput,false); Config.SetValue('EnvironmentOverrides/',FEnvironmentOverrides); - // key and shift are saved with the keymapping in the editoroptions Result:=mrOk; end; -function TExternalToolOptions.ShortDescription: string; +function TIDEExternalToolOptions.ShortDescription: string; begin Result:=Title; end; -procedure TExternalToolOptions.AssignEnvironmentTo(Strings: TStrings); +procedure TIDEExternalToolOptions.AssignEnvironmentTo(Strings: TStrings); begin BaseIDEIntf.AssignEnvironmentTo(Strings,EnvironmentOverrides); end; -function TExternalToolOptions.NeedsOutputFilter: boolean; +procedure TIDEExternalToolOptions.ParseLine(Sender: TObject; + Line: TIDEScanMessageLine); +begin + if Assigned(OnParseLine) then + OnParseLine(Sender,Line); +end; + +function TIDEExternalToolOptions.NeedsOutputFilter: boolean; begin Result:=ScanOutput or ScanOutputForFPCMessages or ScanOutputForMakeMessages or ShowAllOutput; end; +{ TIDEScanMessageLine } + +procedure TIDEScanMessageLine.SetLine(const AValue: string); +var + OldLine: String; +begin + if FLine=AValue then exit; + OldLine:=FLine; + FLine:=AValue; + LineChanged(OldLine); +end; + +procedure TIDEScanMessageLine.SetWorkingDirectory(const AValue: string); +var + OldDir: String; +begin + if FWorkingDirectory=AValue then exit; + OldDir:=FWorkingDirectory; + FWorkingDirectory:=AValue; + WorkingDirectoryChanged(OldDir); +end; + +procedure TIDEScanMessageLine.SetTool(const AValue: TIDEExternalToolOptions); +begin + FTool:=AValue; +end; + +procedure TIDEScanMessageLine.SetLineNumber(const NewLineNumber: integer); +begin + FLineNumber:=NewLineNumber; +end; + +constructor TIDEScanMessageLine.Create(TheCaller: TObject; + TheTool: TIDEExternalToolOptions); +begin + FCaller:=TheCaller; + FTool:=TheTool; +end; + end. diff --git a/ideintf/idemsgintf.pas b/ideintf/idemsgintf.pas index 179cd986b3..71e58ce157 100644 --- a/ideintf/idemsgintf.pas +++ b/ideintf/idemsgintf.pas @@ -22,7 +22,7 @@ unit IDEMsgIntf; interface uses - Classes, SysUtils, Forms, LCLProc, TextTools, IDECommands; + Classes, SysUtils, Forms, LCLProc, TextTools, IDECommands, IDEExternToolIntf; type @@ -184,7 +184,7 @@ type property Lines[Index: integer]: TIDEMessageLine read GetLines; default; function LinesCount: integer; virtual; abstract; end; - + var IDEMsgQuickFixes: TIDEMsgQuickFixItems; // initialized by the IDE IDEMessagesWindow: TIDEMessagesWindowInterface;// initialized by the IDE diff --git a/ideintf/lazideintf.pas b/ideintf/lazideintf.pas index 5889ac6b39..f8d60adb06 100644 --- a/ideintf/lazideintf.pas +++ b/ideintf/lazideintf.pas @@ -23,7 +23,7 @@ interface uses Classes, SysUtils, LCLProc, Forms, Controls, Dialogs, PropEdits, LazHelpHTML, - ProjectIntf, SrcEditorIntf; + IDEExternToolIntf, ProjectIntf, SrcEditorIntf; type // open file flags @@ -132,10 +132,12 @@ type constructor Create(TheOwner: TComponent); override; destructor Destroy; override; + // find file function FindUnitFile(const AFilename: string): string; virtual; abstract; function FindSourceFile(const AFilename, BaseDirectory: string; Flags: TFindSourceFlags): string; virtual; abstract; + // file function DoNewEditorFile(NewFileDescriptor: TProjectFileDescriptor; NewFilename: string; const NewSource: string; NewFlags: TNewFlags): TModalResult; @@ -154,6 +156,8 @@ type const CursorPosition: TPoint; TopLine: integer; PageIndex: integer; Flags: TOpenFlags): TModalResult; virtual; abstract; + // project + property ActiveProject: TLazProject read GetActiveProject; function DoNewProject(ProjectDesc: TProjectDescriptor): TModalResult; virtual; abstract; function DoSaveProject(Flags: TSaveFlags): TModalResult; virtual; abstract; function DoCloseProject: TModalResult; virtual; abstract; @@ -162,6 +166,7 @@ type function DoPublishProject(Flags: TSaveFlags; ShowDialog: boolean): TModalResult; virtual; abstract; + // configs function GetPrimaryConfigPath: String; virtual; abstract; function GetSecondaryConfigPath: String; virtual; abstract; procedure CopySecondaryConfigFile(const AFilename: String); virtual; abstract; @@ -169,13 +174,16 @@ type function CreateNewUniqueFilename(const Prefix, Ext: string; NewOwner: TObject; Flags: TSearchIDEFileFlags; TryWithoutNumber: boolean): string; virtual; abstract; - + + // macros function SubstituteMacros(var s: string): boolean; virtual; abstract; + // codetools function BeginCodeTools: boolean; virtual; abstract; procedure DoJumpToCodeToolBossError; virtual; abstract; procedure SaveSourceEditorChangesToCodeCache(PageIndex: integer); virtual; abstract; - + + // progress and error messages function ShowProgress(const SomeText: string; Step, MaxStep: integer): boolean; virtual; abstract; // False if canceled by user function DoJumpToCompilerMessage(Index:integer; @@ -183,13 +191,15 @@ type procedure DoJumpToNextError(DirectionDown: boolean); virtual; abstract; procedure DoShowMessagesView; virtual; abstract; + // designer function GetDesignerWithProjectFile(AFile: TLazProjectFile; LoadForm: boolean): TIDesigner; virtual; abstract; function GetProjectFileWithRootComponent(AComponent: TComponent): TLazProjectFile; virtual; abstract; function GetProjectFileWithDesigner(ADesigner: TIDesigner): TLazProjectFile; virtual; abstract; - public - property ActiveProject: TLazProject read GetActiveProject; + // external tools + function RunExternalTool(Tool: TIDEExternalToolOptions): TModalResult; virtual; abstract; + // events procedure RemoveAllHandlersOfObject(AnObject: TObject); procedure AddHandlerOnSavingAll(const OnSaveAllEvent: TModalResultFunction; diff --git a/ideintf/srceditorintf.pas b/ideintf/srceditorintf.pas index 6ef11429fc..9793f2d819 100644 --- a/ideintf/srceditorintf.pas +++ b/ideintf/srceditorintf.pas @@ -136,6 +136,9 @@ type write SetActiveEditor; function Count: integer; virtual; abstract; property Items[Index: integer]: TSourceEditorInterface read GetItems; default; + + function GetEditorControlSettings(EditControl: TControl): boolean; virtual; abstract; + function GetHighlighterSettings(Highlighter: TObject): boolean; virtual; abstract; end;