Added hanging indent to help output to make it more readable
This commit is contained in:
parent
fd6b3b1e2f
commit
4b8e38970a
|
@ -68,10 +68,6 @@ void NiceCmdLineOutput::printShortUsage(CmdLineInterface& cli, std::ostream& out
|
||||||
outStream << shortUsage << endl;
|
outStream << shortUsage << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
string wrapLongID(const string& s) {
|
|
||||||
return std::regex_replace(s, std::regex(", "), ",\n");
|
|
||||||
}
|
|
||||||
|
|
||||||
void NiceCmdLineOutput::printLongUsage(CmdLineInterface& cli, std::ostream& outStream) const {
|
void NiceCmdLineOutput::printLongUsage(CmdLineInterface& cli, std::ostream& outStream) const {
|
||||||
TablePrinter tablePrinter(&outStream, { 20, 56 });
|
TablePrinter tablePrinter(&outStream, { 20, 56 });
|
||||||
|
|
||||||
|
@ -83,7 +79,7 @@ void NiceCmdLineOutput::printLongUsage(CmdLineInterface& cli, std::ostream& outS
|
||||||
if (arg != xorArgGroup[0])
|
if (arg != xorArgGroup[0])
|
||||||
outStream << "-- or --" << endl;
|
outStream << "-- or --" << endl;
|
||||||
|
|
||||||
tablePrinter.printRow({ wrapLongID(arg->longID()), arg->getDescription() });
|
tablePrinter.printRow({ arg->longID(), arg->getDescription() });
|
||||||
}
|
}
|
||||||
outStream << endl;
|
outStream << endl;
|
||||||
}
|
}
|
||||||
|
@ -93,6 +89,6 @@ void NiceCmdLineOutput::printLongUsage(CmdLineInterface& cli, std::ostream& outS
|
||||||
for (auto arg : argList) {
|
for (auto arg : argList) {
|
||||||
if (xorHandler.contains(arg)) continue;
|
if (xorHandler.contains(arg)) continue;
|
||||||
|
|
||||||
tablePrinter.printRow({ wrapLongID(arg->longID()), arg->getDescription() });
|
tablePrinter.printRow({ arg->longID(), arg->getDescription() });
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -33,7 +33,7 @@ void TablePrinter::printRow(initializer_list<string> columns) const {
|
||||||
{
|
{
|
||||||
int columnIndex = 0;
|
int columnIndex = 0;
|
||||||
for (const string& column : columns) {
|
for (const string& column : columns) {
|
||||||
vector<string> lines = wrapString(column, columnWidths[columnIndex]);
|
vector<string> lines = wrapString(column, columnWidths[columnIndex], 2);
|
||||||
if (lines.size() > lineCount) lineCount = lines.size();
|
if (lines.size() > lineCount) lineCount = lines.size();
|
||||||
strings[columnIndex] = move(lines);
|
strings[columnIndex] = move(lines);
|
||||||
|
|
||||||
|
|
|
@ -25,8 +25,10 @@ vector<string> splitIntoLines(const string& s) {
|
||||||
return lines;
|
return lines;
|
||||||
}
|
}
|
||||||
|
|
||||||
vector<string> wrapSingleLineString(const string& s, int lineLength) {
|
vector<string> wrapSingleLineString(const string& s, int lineLength, int hangingIndent) {
|
||||||
if (lineLength <= 0) throw std::invalid_argument("lineLength must be > 0.");
|
if (lineLength <= 0) throw std::invalid_argument("lineLength must be > 0.");
|
||||||
|
if (hangingIndent < 0) throw std::invalid_argument("hangingIndent must be >= 0.");
|
||||||
|
if (hangingIndent >= lineLength) throw std::invalid_argument("hangingIndent must be < lineLength.");
|
||||||
if (s.find('\t') != std::string::npos) throw std::invalid_argument("s must not contain tabs.");
|
if (s.find('\t') != std::string::npos) throw std::invalid_argument("s must not contain tabs.");
|
||||||
if (s.find('\n') != std::string::npos) throw std::invalid_argument("s must not contain line breaks.");
|
if (s.find('\n') != std::string::npos) throw std::invalid_argument("s must not contain line breaks.");
|
||||||
|
|
||||||
|
@ -37,13 +39,14 @@ vector<string> wrapSingleLineString(const string& s, int lineLength) {
|
||||||
auto end = p + s.size();
|
auto end = p + s.size();
|
||||||
// Iterate over input string
|
// Iterate over input string
|
||||||
while (p <= end) {
|
while (p <= end) {
|
||||||
// If we're at a word boundary: update safeLineEnd
|
// If we're at a word boundary: update lineEnd
|
||||||
if (p == end || *p == ' ') {
|
if (p == end || *p == ' ' || *p == '|') {
|
||||||
lineEnd = p;
|
lineEnd = p;
|
||||||
}
|
}
|
||||||
|
|
||||||
// If we've hit lineLength or the end of the string: add a new result line
|
// If we've hit lineLength or the end of the string: add a new result line
|
||||||
if (p == end || p - lineBegin == lineLength) {
|
int currentIndent = lines.empty() ? 0 : hangingIndent;
|
||||||
|
if (p == end || p - lineBegin == lineLength - currentIndent) {
|
||||||
if (lineEnd == lineBegin) {
|
if (lineEnd == lineBegin) {
|
||||||
// The line contains a single word, which is too long. Split mid-word.
|
// The line contains a single word, which is too long. Split mid-word.
|
||||||
lineEnd = p;
|
lineEnd = p;
|
||||||
|
@ -52,7 +55,7 @@ vector<string> wrapSingleLineString(const string& s, int lineLength) {
|
||||||
// Add trimmed line to list
|
// Add trimmed line to list
|
||||||
string line(lineBegin, lineEnd);
|
string line(lineBegin, lineEnd);
|
||||||
boost::algorithm::trim_right(line);
|
boost::algorithm::trim_right(line);
|
||||||
lines.push_back(line);
|
lines.push_back(string(currentIndent, ' ') + line);
|
||||||
|
|
||||||
// Resume after the last line, skipping spaces
|
// Resume after the last line, skipping spaces
|
||||||
p = lineEnd;
|
p = lineEnd;
|
||||||
|
@ -66,10 +69,10 @@ vector<string> wrapSingleLineString(const string& s, int lineLength) {
|
||||||
return lines;
|
return lines;
|
||||||
}
|
}
|
||||||
|
|
||||||
vector<string> wrapString(const string& s, int lineLength) {
|
vector<string> wrapString(const string& s, int lineLength, int hangingIndent) {
|
||||||
vector<string> lines;
|
vector<string> lines;
|
||||||
for (string paragraph : splitIntoLines(s)) {
|
for (string paragraph : splitIntoLines(s)) {
|
||||||
auto paragraphLines = wrapSingleLineString(paragraph, lineLength);
|
auto paragraphLines = wrapSingleLineString(paragraph, lineLength, hangingIndent);
|
||||||
copy(paragraphLines.cbegin(), paragraphLines.cend(), back_inserter(lines));
|
copy(paragraphLines.cbegin(), paragraphLines.cend(), back_inserter(lines));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -5,6 +5,6 @@
|
||||||
|
|
||||||
std::vector<std::string> splitIntoLines(const std::string& s);
|
std::vector<std::string> splitIntoLines(const std::string& s);
|
||||||
|
|
||||||
std::vector<std::string> wrapSingleLineString(const std::string& s, int lineLength);
|
std::vector<std::string> wrapSingleLineString(const std::string& s, int lineLength, int hangingIndent = 0);
|
||||||
|
|
||||||
std::vector<std::string> wrapString(const std::string& s, int lineLength);
|
std::vector<std::string> wrapString(const std::string& s, int lineLength, int hangingIndent = 0);
|
||||||
|
|
Loading…
Reference in New Issue