diff --git a/lazproj/coedit.lpi b/lazproj/coedit.lpi
index b85c391c..17a584c8 100644
--- a/lazproj/coedit.lpi
+++ b/lazproj/coedit.lpi
@@ -137,7 +137,7 @@
-
+
@@ -369,6 +369,13 @@
+
+
+
+
+
+
+
diff --git a/lazproj/coedit.lpr b/lazproj/coedit.lpr
index 700f4047..6e13bb22 100644
--- a/lazproj/coedit.lpr
+++ b/lazproj/coedit.lpr
@@ -10,7 +10,7 @@ uses
ce_observer, ce_libman, ce_tools, ce_dcd, ce_main, ce_writableComponent,
ce_symstring, ce_staticmacro, ce_inspectors, ce_editoroptions, ce_dockoptions,
ce_shortcutseditor, ce_mru, ce_processes, ce_dubproject, ce_dialogs,
-ce_dubprojeditor, ce_gdb, ce_controls;
+ce_dubprojeditor, ce_gdb, ce_controls, ce_dfmt;
{$R *.res}
diff --git a/src/ce_dfmt.lfm b/src/ce_dfmt.lfm
new file mode 100644
index 00000000..e6dd4024
--- /dev/null
+++ b/src/ce_dfmt.lfm
@@ -0,0 +1,73 @@
+inherited CEDfmtWidget: TCEDfmtWidget
+ Left = 562
+ Height = 365
+ Top = 245
+ Width = 458
+ Caption = 'Dfmt commander'
+ ClientHeight = 365
+ ClientWidth = 458
+ inherited Back: TPanel
+ Left = 4
+ Height = 357
+ Top = 4
+ Width = 450
+ BorderSpacing.Around = 4
+ ClientHeight = 357
+ ClientWidth = 450
+ inherited Content: TPanel
+ Height = 357
+ Width = 450
+ ClientHeight = 357
+ ClientWidth = 450
+ object dfmtOptionEditor: TTIPropertyGrid[0]
+ Left = 4
+ Height = 313
+ Top = 4
+ Width = 442
+ Align = alClient
+ BorderSpacing.Around = 4
+ CheckboxForBoolean = False
+ DefaultValueFont.Color = clWindowText
+ Filter = [tkInteger, tkChar, tkEnumeration, tkFloat, tkSet, tkMethod, tkSString, tkLString, tkAString, tkWString, tkVariant, tkArray, tkRecord, tkInterface, tkClass, tkObject, tkWChar, tkBool, tkInt64, tkQWord, tkDynArray, tkInterfaceRaw, tkProcVar, tkUString, tkUChar, tkHelper]
+ Indent = 10
+ NameFont.Color = clWindowText
+ OnEditorFilter = dfmtOptionEditorEditorFilter
+ PreferredSplitterX = 220
+ SplitterX = 220
+ ValueFont.Color = clGreen
+ end
+ object pnlFooter: TPanel[1]
+ Left = 4
+ Height = 32
+ Top = 321
+ Width = 442
+ Align = alBottom
+ BorderSpacing.Around = 4
+ BevelOuter = bvLowered
+ ClientHeight = 32
+ ClientWidth = 442
+ TabOrder = 1
+ object btnCancel: TSpeedButton
+ Left = 375
+ Height = 26
+ Hint = 'restore previous format'
+ Top = 3
+ Width = 30
+ Align = alRight
+ BorderSpacing.Left = 2
+ BorderSpacing.Around = 2
+ end
+ object btnApply: TSpeedButton
+ Left = 409
+ Height = 26
+ Hint = 'apply formating'
+ Top = 3
+ Width = 30
+ Align = alRight
+ BorderSpacing.Left = 2
+ BorderSpacing.Around = 2
+ end
+ end
+ end
+ end
+end
diff --git a/src/ce_dfmt.pas b/src/ce_dfmt.pas
new file mode 100644
index 00000000..a2341a7b
--- /dev/null
+++ b/src/ce_dfmt.pas
@@ -0,0 +1,227 @@
+unit ce_dfmt;
+
+{$I ce_defines.inc}
+
+interface
+
+uses
+ Classes, SysUtils, FileUtil, RTTIGrids, Forms, Controls, Graphics, ExtCtrls,
+ Menus, Buttons, process, ce_widget, ce_interfaces, ce_observer, ce_synmemo,
+ ce_writableComponent, ce_common, ce_sharedres, PropEdits, ObjectInspector;
+
+type
+
+ DfmtEol = (cr, lf, crlf);
+ DfmtIdentstyle = (tab, space);
+ DfmtBraceStyle = (allman, otbs, stroustrup);
+
+ // wraps dfmt options to build the command line with ease
+ // and allows to save the options between session.
+ TCEDmtWrapper = class(TWritableLfmTextComponent)
+ private
+ fEol: DfmtEol;
+ fTabStyle: DfmtIdentstyle;
+ fIdentSize: integer;
+ fTabWidth: integer;
+ fHardLLen: integer;
+ fSoftLLen: integer;
+ fBraceStyle: DfmtBraceStyle;
+ fSpaceCast: boolean;
+ fSplitOp: boolean;
+ fCompactLbl: boolean;
+ fSpaceSelImp: boolean;
+ published
+ property endOfline: DfmtEol read fEol write fEol default lf;
+ property identationStyle: DfmtIdentstyle read fTabStyle write fTabStyle default space;
+ property identSize: integer read fIdentSize write fIdentSize default 4;
+ property tabWidth: integer read fTabWidth write fTabWidth default 8;
+ property hardLineLen: integer read fHardLLen write fHardLLen default 120;
+ property softLineLen: integer read fSoftLLen write fSoftLLen default 80;
+ property braceStyle: DfmtBraceStyle read fBraceStyle write fBraceStyle default allman;
+ property spaceAfterCast: boolean read fSpaceCast write fSpaceCast default true;
+ property spaceAfterImport: boolean read fSpaceSelImp write fSpaceSelImp default true;
+ property splitOpAtPrevLine: boolean read fSplitOp write fSplitOp default true;
+ property compactLabeledStatements: boolean read fCompactLbl write fCompactLbl default true;
+ public
+ constructor create(AOwner: TComponent); override;
+ procedure getCommandLine(str: TStrings);
+ end;
+
+ { TCEDfmtWidget }
+
+ TCEDfmtWidget = class(TCEWidget, ICEMultiDocObserver)
+ btnApply: TSpeedButton;
+ btnCancel: TSpeedButton;
+ pnlFooter: TPanel;
+ dfmtOptionEditor: TTIPropertyGrid;
+ procedure dfmtOptionEditorEditorFilter(Sender: TObject;
+ aEditor: TPropertyEditor; var aShow: boolean);
+ private
+ fDoc: TCESynMemo;
+ fBackup: TStringList;
+ fDmtWrapper: TCEDmtWrapper;
+ //
+ procedure docNew(aDoc: TCESynMemo);
+ procedure docFocused(aDoc: TCESynMemo);
+ procedure docChanged(aDoc: TCESynMemo);
+ procedure docClosing(aDoc: TCESynMemo);
+ //
+ procedure doApply(sender: TObject);
+ procedure doCancel(sender: TObject);
+ public
+ constructor create(aOwner: TComponent); override;
+ destructor destroy; override;
+ end;
+
+implementation
+{$R *.lfm}
+
+const
+ optFname = 'dfmt.txt';
+
+{$REGION Standard Comp/Obj------------------------------------------------------}
+constructor TCEDfmtWidget.create(aOwner: TComponent);
+var
+ fname: string;
+begin
+ inherited;
+ fDmtWrapper := TCEDmtWrapper.Create(self);
+ fBackup := TStringList.Create;
+ //
+ fname := getCoeditDocPath + optFname;
+ if fileExists(fname) then
+ fDmtWrapper.loadFromFile(fname);
+ //
+ btnCancel.OnClick := @doCancel;
+ btnApply.OnClick := @doApply;
+ AssignPng(btnCancel, 'cancel');
+ AssignPng(btnApply, 'accept');
+ //
+ dfmtOptionEditor.TIObject := fDmtWrapper;
+end;
+
+destructor TCEDfmtWidget.destroy;
+begin
+ dfmtOptionEditor.TIObject := nil;
+ fDmtWrapper.saveToFile(getCoeditDocPath + optFname);
+ fBackup.Free;
+ inherited;
+end;
+
+constructor TCEDmtWrapper.create(AOwner: TComponent);
+begin
+ inherited;
+ fEol := lf;
+ fTabStyle := DfmtIdentstyle.space;
+ fIdentSize := 4;
+ fTabWidth := 8;
+ fHardLLen := 120;
+ fSoftLLen := 80;
+ fBraceStyle := DfmtBraceStyle.allman;
+ fSpaceCast := true;
+ fSpaceSelImp := true;
+ fSplitOp := true;
+ fCompactLbl := true;
+end;
+
+procedure TCEDfmtWidget.dfmtOptionEditorEditorFilter(Sender: TObject;
+ aEditor: TPropertyEditor; var aShow: boolean);
+begin
+ case aEditor.GetName of
+ 'Tag', 'Name': aShow := false;
+ else aShow := true;
+ end;
+end;
+{$ENDREGION}
+
+{$REGION ICEMultiDocObserver ---------------------------------------------------}
+procedure TCEDfmtWidget.docNew(aDoc: TCESynMemo);
+begin
+ fDoc := aDoc;
+end;
+
+procedure TCEDfmtWidget.docFocused(aDoc: TCESynMemo);
+begin
+ if aDoc = fDoc
+ then exit;
+ fDoc := aDoc;
+end;
+
+procedure TCEDfmtWidget.docChanged(aDoc: TCESynMemo);
+begin
+end;
+
+procedure TCEDfmtWidget.docClosing(aDoc: TCESynMemo);
+begin
+ if fDoc <> aDoc then
+ exit;
+ fDoc := nil;
+end;
+{$ENDREGION}
+
+{$REGION Dfmt things -----------------------------------------------------------}
+procedure TCEDmtWrapper.getCommandLine(str: TStrings);
+const
+ eol: array[DfmtEol] of string = ('cr', 'lf', 'crlf');
+ falsetrue: array[boolean] of string = ('false', 'true');
+ idtstyle: array[DfmtIdentstyle] of string = ('tab', 'space');
+ brc: array[DfmtBraceStyle] of string = ('allman', 'otbs', 'stroustrup');
+begin
+ str.Add('--end_of_line=' + eol[endOfline]);
+ str.Add('--max_line_length=' + intToStr(hardLineLen));
+ str.Add('--soft_max_line_length=' + intToStr(softLineLen));
+ str.Add('--indent_size=' + intToStr(identSize));
+ str.Add('--indent_style=' + idtstyle[identationStyle]);
+ str.Add('--tab_width=' + intToStr(tabWidth));
+ str.Add('--brace_style=' + brc[braceStyle]);
+ str.Add('--split_operator_at_line_end=' + falsetrue[splitOpAtPrevLine]);
+ str.Add('--space_after_cast=' + falsetrue[spaceAfterCast]);
+ str.Add('--selective_import_space=' + falsetrue[spaceAfterImport]);
+ str.Add('--compact_labeled_statements=' + falsetrue[compactLabeledStatements]);
+end;
+
+procedure TCEDfmtWidget.doApply(sender: TObject);
+var
+ inp: string;
+ prc: TProcess;
+ str: TStringList;
+begin
+ if not assigned(fDoc) then
+ exit;
+
+ fBackup.Assign(fDoc.Lines);
+ prc := TProcess.create(nil);
+ try
+ fDmtWrapper.getCommandLine(prc.Parameters);
+ prc.Options:= prc.Options + [poUsePipes, poStderrToOutPut];
+ prc.Executable:= exeFullName('dfmt' + exeExt);
+ prc.Execute;
+ inp := fDoc.Lines.Text;
+ prc.Input.Write(inp[1], length(inp));
+ prc.CloseInput;
+ while prc.Running do (*!*);
+ try
+ str := TStringList.Create;
+ processOutputToStrings(prc,str);
+ fDoc.SelectAll;
+ fDoc.SelText:= str.Text;
+ except
+ fDoc.Lines.Assign(fBackup);
+ end;
+ finally
+ prc.free;
+ str.free;
+ end;
+end;
+
+procedure TCEDfmtWidget.doCancel(sender: TObject);
+begin
+ if not assigned(fDoc) then
+ exit;
+
+ fDoc.Lines.Assign(fBackup);
+end;
+{$ENDREGION}
+
+end.
+
diff --git a/src/ce_infos.lfm b/src/ce_infos.lfm
index 307cffee..877844c8 100644
--- a/src/ce_infos.lfm
+++ b/src/ce_infos.lfm
@@ -1,38 +1,38 @@
inherited CEInfoWidget: TCEInfoWidget
Left = 713
- Height = 401
+ Height = 423
Top = 245
- Width = 406
+ Width = 411
BorderIcons = [biSystemMenu, biMinimize, biMaximize]
Caption = 'About'
- ClientHeight = 401
- ClientWidth = 406
+ ClientHeight = 423
+ ClientWidth = 411
inherited Back: TPanel
- Height = 401
- Width = 406
- ClientHeight = 401
- ClientWidth = 406
+ Height = 423
+ Width = 411
+ ClientHeight = 423
+ ClientWidth = 411
inherited Content: TPanel
- Height = 401
- Width = 406
- ClientHeight = 401
- ClientWidth = 406
+ Height = 423
+ Width = 411
+ ClientHeight = 423
+ ClientWidth = 411
object GroupBox1: TGroupBox[0]
Left = 4
Height = 105
Top = 4
- Width = 398
+ Width = 403
Align = alTop
BorderSpacing.Around = 4
Caption = 'about'
ClientHeight = 75
- ClientWidth = 394
+ ClientWidth = 399
TabOrder = 0
object Label1: TLabel
Left = 0
Height = 75
Top = 0
- Width = 394
+ Width = 399
Align = alClient
Alignment = taCenter
AutoSize = False
@@ -46,20 +46,20 @@ inherited CEInfoWidget: TCEInfoWidget
end
object GroupBox2: TGroupBox[1]
Left = 4
- Height = 284
+ Height = 306
Top = 113
- Width = 398
+ Width = 403
Align = alClient
BorderSpacing.Around = 4
Caption = 'tools status'
- ClientHeight = 254
- ClientWidth = 394
+ ClientHeight = 276
+ ClientWidth = 399
TabOrder = 1
object boxTools: TScrollBox
Left = 4
- Height = 246
+ Height = 268
Top = 4
- Width = 386
+ Width = 391
HorzScrollBar.Page = 1
VertScrollBar.Page = 1
Align = alClient
diff --git a/src/ce_infos.pas b/src/ce_infos.pas
index 3f3bb8fe..9b059a19 100644
--- a/src/ce_infos.pas
+++ b/src/ce_infos.pas
@@ -176,7 +176,11 @@ begin
fIsModal := true;
fIsDockable := false;
//
- toolItem := TToolInfo.Construct(self, tikOptional, 'gdc',
+ toolItem := TToolInfo.Construct(self, tikOptional, 'dfmt',
+ 'optional, the D source code formater, needed by the Dfmt commander widget');
+ toolItem.Parent := boxTools;
+ toolItem.ReAlign;
+ toolItem := TToolInfo.Construct(self, tikOptional, 'dfmt',
'optional, the GDC D compiler');
toolItem.Parent := boxTools;
toolItem.ReAlign;
diff --git a/src/ce_main.pas b/src/ce_main.pas
index d2fa54bc..8bd6cde2 100644
--- a/src/ce_main.pas
+++ b/src/ce_main.pas
@@ -12,7 +12,7 @@ uses
ce_widget, ce_messages, ce_interfaces, ce_editor, ce_projinspect, ce_projconf,
ce_search, ce_miniexplorer, ce_libman, ce_libmaneditor, ce_todolist, ce_observer,
ce_toolseditor, ce_procinput, ce_optionseditor, ce_symlist, ce_mru, ce_processes,
- ce_infos, ce_dubproject, ce_dialogs, ce_dubprojeditor, ce_gdb;
+ ce_infos, ce_dubproject, ce_dialogs, ce_dubprojeditor, ce_gdb, ce_dfmt;
type
@@ -225,6 +225,7 @@ type
fInfoWidg: TCEInfoWidget;
fDubProjWidg: TCEDubProjectEditorWidget;
fGdbWidg: TCEGdbWidget;
+ fDfmtWidg: TCEDfmtWidget;
fFirstShown: boolean;
fProjFromCommandLine: boolean;
@@ -812,6 +813,7 @@ begin
fInfoWidg := TCEInfoWidget.create(self);
fDubProjWidg:= TCEDubProjectEditorWidget.create(self);
fGdbWidg := TCEGdbWidget.create(self);
+ fDfmtWidg := TCEDfmtWidget.create(self);
getMessageDisplay(fMsgs);
@@ -830,6 +832,7 @@ begin
fWidgList.addWidget(@fInfoWidg);
fWidgList.addWidget(@fDubProjWidg);
fWidgList.addWidget(@fGdbWidg);
+ fWidgList.addWidget(@fDfmtWidg);
fWidgList.sort(@CompareWidgCaption);
for widg in fWidgList do
diff --git a/wiki/wiki.todo.txt b/wiki/wiki.todo.txt
index 091a6833..cc90ac5f 100644
--- a/wiki/wiki.todo.txt
+++ b/wiki/wiki.todo.txt
@@ -3,4 +3,5 @@
- project config widget, base/overridden config specifications. Note about pre/post build proc as their options cant be overridden.
- project config widget, base/overridden config. screenshot for widget view 'All categories'.
- applications options (MRU & reload last stuff).
-- editor, toolbar description, split view description + screenshot.
\ No newline at end of file
+- editor, toolbar description, split view description + screenshot.
+- widget section for Dfmt commander.
\ No newline at end of file