1 module dls.tools.formatter; 2 3 import dfmt.config : BraceStyle; 4 import dfmt.editorconfig : EOL; 5 import dfmt.formatter; 6 import dls.tools.configuration : Configuration; 7 import dls.tools.tool : Tool; 8 9 private immutable EOL[Configuration.FormatterConfiguration.EndOfLine] eolMap; 10 private immutable BraceStyle[Configuration.FormatterConfiguration.BraceStyle] braceStyleMap; 11 12 static this() 13 { 14 //dfmt off 15 eolMap = [ 16 Configuration.FormatterConfiguration.EndOfLine.lf : EOL.lf, 17 Configuration.FormatterConfiguration.EndOfLine.cr : EOL.cr, 18 Configuration.FormatterConfiguration.EndOfLine.crlf : EOL.crlf 19 ]; 20 21 braceStyleMap = [ 22 Configuration.FormatterConfiguration.BraceStyle.allman : BraceStyle.allman, 23 Configuration.FormatterConfiguration.BraceStyle.otbs : BraceStyle.otbs, 24 Configuration.FormatterConfiguration.BraceStyle.stroustrup : BraceStyle.stroustrup 25 ]; 26 //dfmt on 27 } 28 29 class Formatter : Tool 30 { 31 import dls.protocol.interfaces : FormattingOptions; 32 import dls.util.uri : Uri; 33 34 auto format(Uri uri, FormattingOptions options) 35 { 36 import dfmt.config : Config; 37 import dfmt.editorconfig : IndentStyle, OptionalBoolean; 38 import dls.protocol.definitions : TextEdit; 39 import dls.util.document : Document; 40 import std.outbuffer : OutBuffer; 41 42 const document = Document[uri]; 43 auto contents = cast(ubyte[]) document.toString(); 44 auto config = Config(); 45 auto buffer = new OutBuffer(); 46 auto result = new TextEdit(); 47 48 result.range.end.line = document.lines.length; 49 result.range.end.character = document.lines[$ - 1].length; 50 51 auto toOptBool(bool b) 52 { 53 return b ? OptionalBoolean.t : OptionalBoolean.f; 54 } 55 56 config.indent_style = options.insertSpaces ? IndentStyle.space : IndentStyle.tab; 57 config.indent_size = cast(typeof(config.indent_size)) options.tabSize; 58 config.tab_width = config.indent_size; 59 config.end_of_line = eolMap[_configuration.formatter.endOfLine]; 60 config.max_line_length = _configuration.formatter.maxLineLength; 61 config.dfmt_brace_style = braceStyleMap[_configuration.formatter.dfmtBraceStyle]; 62 config.dfmt_soft_max_line_length = _configuration.formatter.dfmtSoftMaxLineLength; 63 config.dfmt_align_switch_statements = toOptBool( 64 _configuration.formatter.dfmtAlignSwitchStatements); 65 config.dfmt_outdent_attributes = toOptBool(_configuration.formatter.dfmtOutdentAttributes); 66 config.dfmt_split_operator_at_line_end = toOptBool( 67 _configuration.formatter.dfmtSplitOperatorAtLineEnd); 68 config.dfmt_space_after_cast = toOptBool(_configuration.formatter.dfmtSpaceAfterCast); 69 config.dfmt_space_after_keywords = toOptBool( 70 _configuration.formatter.dfmtSpaceAfterKeywords); 71 config.dfmt_space_before_function_parameters = toOptBool( 72 _configuration.formatter.dfmtSpaceBeforeFunctionParameters); 73 config.dfmt_selective_import_space = toOptBool( 74 _configuration.formatter.dfmtSpaceBeforeFunctionParameters); 75 config.dfmt_compact_labeled_statements = _configuration.formatter.dfmtCompactLabeledStatements 76 ? OptionalBoolean.t : OptionalBoolean.f; 77 78 dfmt.formatter.format(uri, contents, buffer, &config); 79 result.newText = buffer.toString(); 80 81 return [result]; 82 } 83 }