1 /** 2 * D Documentation Generator 3 * Copyright: © 2014 Economic Modeling Specialists, Intl. 4 * © 2014 Ferdinand Majerech 5 * © 2021 Eugene Stulin 6 * Authors: Brian Schott, Ferdinand Majerech, Eugene Stulin 7 * License: $(LINK2 http://www.boost.org/LICENSE_1_0.txt Boost License 1.0) 8 */ 9 module formatter; 10 11 import dparse.ast; 12 import dparse.lexer; 13 import dparse.formatter; 14 import std.stdio; 15 16 17 /******************************************************************************* 18 * Modified D formatter for Harbored. 19 * 20 * Currently the only modification is that multi-parameter parameter lists 21 * are split into multiple lines. 22 */ 23 class HarboredFormatter(Sink) : Formatter!Sink { 24 /// Nesting level for nested parameter lists (see format(const Parameters)). 25 private uint level; 26 27 /// Function to process types with for cross-referencing. 28 private string delegate(string) @safe nothrow crossReference; 29 30 /** 31 * Params: 32 * 33 * sink = the output range that the formatted source code 34 * is placed in 35 * processCode = Function to process types with for cross-referencing. 36 * useTabs = if true, tabs are used for indent levels instead of spaces 37 * style = the brace style 38 * indentWidth = the number of spaces used for indentation 39 * if useTabs is false 40 */ 41 this(Sink sink, 42 string delegate(string) @safe nothrow crossReference, 43 bool useTabs = false, 44 IndentStyle style = IndentStyle.allman, 45 uint indentWidth = 4) { 46 this.crossReference = crossReference; 47 super(sink, useTabs, style, indentWidth); 48 } 49 50 alias format = Formatter!Sink.format; 51 52 /** A modified version of (libdparse) std.d.formatter.Formatter.format(const Parameters) 53 * to format each parameter on a separate line. 54 */ 55 override void format(const Parameters parameters) { 56 debug(verbose) writeln("Parameters (HarboredFormatter)"); 57 58 // No need to break the list into multiple lines for a single argument 59 // TODO ability to set this in "doxyfile" 60 const maxParamsForSingleLineParamList = 1; 61 if (parameters.parameters.length <= maxParamsForSingleLineParamList) { 62 super.format(parameters); 63 return; 64 } 65 level++; 66 scope(exit) level--; 67 put("("); 68 foreach (count, param; parameters.parameters) { 69 if (count) put(", "); 70 put("\n"); 71 foreach(i; 0..level) 72 put(" "); 73 format(param); 74 } 75 if (parameters.hasVarargs) { 76 if (parameters.parameters.length) 77 put(", "); 78 put("\n"); 79 foreach(i; 0..level) 80 put(" "); 81 put("..."); 82 } 83 if (level > 1) { 84 put("\n"); 85 foreach(i; 0..level) { 86 put(" "); 87 } 88 } 89 put("\n)"); 90 } 91 92 // Overridden for builtin type referencing. 93 override void format(const Type2 type2) { 94 debug(verbose) writeln("Type2 (HarboredFormatter)"); 95 96 /** 97 IdType builtinType; 98 Symbol symbol; 99 TypeofExpression typeofExpression; 100 IdentifierOrTemplateChain identifierOrTemplateChain; 101 IdType typeConstructor; 102 Type type; 103 **/ 104 105 if (type2.typeIdentifierPart !is null) { 106 format(type2.typeIdentifierPart); 107 } else if (type2.typeofExpression !is null) { 108 format(type2.typeofExpression); 109 if (type2.typeIdentifierPart) 110 { 111 put("."); 112 format(type2.typeIdentifierPart); 113 } 114 return; 115 } else if (type2.typeConstructor != tok!"") { 116 put(tokenRep(type2.typeConstructor)); 117 put("("); 118 format(type2.type); 119 put(")"); 120 } else { 121 // Link to language reference for builtin types. 122 put(`<a href="http://dlang.org/type.html#basic-data-types">`); 123 put(tokenRep(type2.builtinType)); 124 put("</a>"); 125 } 126 } 127 128 // Overridden for cross-referencing. 129 override void format(const Token token) { 130 debug(verbose) writeln("Token (HarboredFormatter) ", tokenRep(token)); 131 put(crossReference(tokenRep(token))); 132 } 133 134 } 135