You can not select more than 25 topics Topics must start with a chinese character,a letter or number, can include dashes ('-') and can be up to 35 characters long.

text_table.cpp 3.7 kB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107
  1. #include "text_table.h"
  2. using namespace mgb;
  3. namespace {
  4. inline void mid(std::ostream& os, const std::string& str, size_t max_w) {
  5. size_t l = (max_w - str.length()) / 2 + str.length();
  6. size_t r = max_w - l;
  7. os << std::setw(l) << std::right << str;
  8. if (r > 0)
  9. os << std::setw(r) << ' ';
  10. }
  11. inline size_t char_length(char c) {
  12. return c ? 1 : 0;
  13. }
  14. } // namespace
  15. void TextTable::adjuster_last_row() {
  16. if (m_rows.empty())
  17. return;
  18. auto& row = m_rows.back();
  19. if (row.params.horizontal == 0 or row.params.vertical == 0) {
  20. row.params.corner = 0;
  21. }
  22. if (row.params.horizontal != 0 && row.params.vertical != 0 &&
  23. row.params.corner == 0) {
  24. row.params.corner = row.params.horizontal;
  25. }
  26. }
  27. void TextTable::show(std::ostream& os) {
  28. if (m_rows.empty())
  29. return;
  30. auto& last_row = m_rows.front();
  31. bool first = true;
  32. for (auto& row : m_rows) {
  33. auto& lrow =
  34. (last_row.values.size() * char_length(last_row.params.horizontal)) >
  35. (row.values.size() * char_length(row.params.horizontal))
  36. ? last_row
  37. : row;
  38. // line before row
  39. if (lrow.params.horizontal) {
  40. if (not first)
  41. os << std::endl;
  42. os << m_prefix;
  43. if (lrow.params.corner)
  44. os << lrow.params.corner;
  45. size_t skip_size = 0;
  46. // table name
  47. if (first) {
  48. os << m_name;
  49. skip_size = m_name.length();
  50. }
  51. for (size_t i = 0; i < lrow.values.size(); ++i) {
  52. auto max_w = m_cols_max_w.at(i) + m_padding * 2;
  53. if (max_w + char_length(lrow.params.corner) <= skip_size) {
  54. skip_size = skip_size - max_w - char_length(lrow.params.corner);
  55. continue;
  56. }
  57. size_t rest = max_w + char_length(lrow.params.corner) - skip_size;
  58. skip_size = 0;
  59. if (rest > char_length(lrow.params.corner)) {
  60. os << std::string(
  61. rest - char_length(lrow.params.corner),
  62. lrow.params.horizontal);
  63. rest = char_length(lrow.params.corner);
  64. }
  65. if (rest > 0 && lrow.params.corner)
  66. os << lrow.params.corner;
  67. }
  68. } else if (first) {
  69. os << m_prefix << ' ' << m_name;
  70. }
  71. first = false;
  72. os << std::endl << m_prefix;
  73. if (row.params.vertical)
  74. os << row.params.vertical;
  75. // row
  76. for (size_t i = 0; i < row.values.size(); ++i) {
  77. auto& str = row.values.at(i);
  78. auto max_w = m_cols_max_w.at(i) + 2 * m_padding;
  79. if (row.params.align == Align::Mid) {
  80. mid(os, str, max_w);
  81. } else if (row.params.align == Align::Left) {
  82. os << std::setw(max_w) << std::left << str;
  83. } else {
  84. os << std::setw(max_w) << std::right << str;
  85. }
  86. if (row.params.vertical)
  87. os << row.params.vertical;
  88. }
  89. last_row = row;
  90. }
  91. if (last_row.params.horizontal) {
  92. os << std::endl << m_prefix;
  93. if (last_row.params.corner)
  94. os << last_row.params.corner;
  95. for (size_t i = 0; i < last_row.values.size(); ++i) {
  96. auto max_w = m_cols_max_w.at(i);
  97. std::string tmp(max_w + m_padding * 2, last_row.params.horizontal);
  98. os << tmp;
  99. if (last_row.params.corner)
  100. os << last_row.params.corner;
  101. }
  102. }
  103. }