From: Lucian Poston <lucian.poston@gmail.com>
To: git@vger.kernel.org
Cc: "Lucian Poston" <lucian.poston@gmail.com>,
"Junio C Hamano" <junkio@cox.net>,
"Junio C Hamano" <gitster@pobox.com>,
"Johannes Schindelin" <johannes.schindelin@gmx.de>,
"Michael J Gruber" <git@drmicha.warpmail.net>,
"Bo Yang" <struggleyb.nku@gmail.com>,
"Zbigniew Jędrzejewski-Szmek" <zbyszek@in.waw.pl>
Subject: [PATCH 1/1] Fix --stat width calculations to handle --graph
Date: Tue, 20 Mar 2012 00:38:17 -0700 [thread overview]
Message-ID: <1332229097-19262-2-git-send-email-lucian.poston@gmail.com> (raw)
In-Reply-To: <1332229097-19262-1-git-send-email-lucian.poston@gmail.com>
Adjusted stat width calculations to take into consideration the diff output
prefix e.g. the graph prefix generated by `git log --graph --stat`.
This change fixes the line wrapping that occurs when diff stats are large
enough to be scaled to fit within the terminal's columns. This issue only
appears when using --stat and --graph together on large diffs.
Adjusted stat output tests accordingly. The scaled output tests are closer to
the target 5:3 ratio.
Added test that verifies the output of --stat --graph is truncated to fit
within the available terminal $COLUMNS
Signed-off-by: Lucian Poston <lucian.poston@gmail.com>
---
diff.c | 55 ++++++++++++++++++++++++++++++++---------------
t/t4052-stat-output.sh | 24 +++++++++++++++++++-
2 files changed, 59 insertions(+), 20 deletions(-)
diff --git a/diff.c b/diff.c
index 377ec1e..3a26561 100644
--- a/diff.c
+++ b/diff.c
@@ -1382,7 +1382,9 @@ static void show_stats(struct diffstat_t *data, struct diff_options *options)
int total_files = data->nr;
int width, name_width, graph_width, number_width = 4, count;
const char *reset, *add_c, *del_c;
- const char *line_prefix = "";
+ const char *line_prefix = "", *line_prefix_iter;
+ unsigned int line_prefix_length = 0;
+ unsigned int reserved_character_count;
int extra_shown = 0;
struct strbuf *msg = NULL;
@@ -1392,6 +1394,18 @@ static void show_stats(struct diffstat_t *data, struct diff_options *options)
if (options->output_prefix) {
msg = options->output_prefix(options, options->output_prefix_data);
line_prefix = msg->buf;
+
+ /*
+ * line_prefix can contain color codes, so only pipes '|' and
+ * spaces ' ' are counted.
+ */
+ line_prefix_iter = line_prefix;
+ while (*line_prefix_iter != '\0') {
+ if (*line_prefix_iter == ' ' || *line_prefix_iter == '|') {
+ line_prefix_length++;
+ }
+ line_prefix_iter += 1;
+ }
}
count = options->stat_count ? options->stat_count : data->nr;
@@ -1427,22 +1441,27 @@ static void show_stats(struct diffstat_t *data, struct diff_options *options)
* We have width = stat_width or term_columns() columns total.
* We want a maximum of min(max_len, stat_name_width) for the name part.
* We want a maximum of min(max_change, stat_graph_width) for the +- part.
- * We also need 1 for " " and 4 + decimal_width(max_change)
- * for " | NNNN " and one the empty column at the end, altogether
- * 6 + decimal_width(max_change).
+ * Each line needs space for the following characters:
+ * - line_prefix_length for the line_prefix
+ * - 1 for the initial " "
+ * - 4 + decimal_width(max_change) for " | NNNN "
+ * - 1 for the empty column at the end,
+ * Altogether, the reserved_character_count totals
+ * 6 + line_prefix_length + decimal_width(max_change).
*
* If there's not enough space, we will use the smaller of
* stat_name_width (if set) and 5/8*width for the filename,
- * and the rest for constant elements + graph part, but no more
+ * and the rest for reserved characters + graph part, but no more
* than stat_graph_width for the graph part.
- * (5/8 gives 50 for filename and 30 for the constant parts + graph
- * for the standard terminal size).
+ * (5/8 gives 50 for filename and 30 for the reserved characters + graph
+ * for the standard terminal size assuming there is no line prefix).
*
* In other words: stat_width limits the maximum width, and
* stat_name_width fixes the maximum width of the filename,
* and is also used to divide available columns if there
* aren't enough.
*/
+ reserved_character_count = 6 + number_width + line_prefix_length;
if (options->stat_width == -1)
width = term_columns();
@@ -1453,11 +1472,11 @@ static void show_stats(struct diffstat_t *data, struct diff_options *options)
options->stat_graph_width = diff_stat_graph_width;
/*
- * Guarantee 3/8*16==6 for the graph part
- * and 5/8*16==10 for the filename part
+ * Guarantees at least 6 characters for the graph part [16 * 3/8]
+ * and at least 10 for the filename part [16 * 5/8]
*/
- if (width < 16 + 6 + number_width)
- width = 16 + 6 + number_width;
+ if (width < 16 + reserved_character_count)
+ width = 16 + reserved_character_count;
/*
* First assign sizes that are wanted, ignoring available width.
@@ -1472,16 +1491,16 @@ static void show_stats(struct diffstat_t *data, struct diff_options *options)
/*
* Adjust adjustable widths not to exceed maximum width
*/
- if (name_width + number_width + 6 + graph_width > width) {
- if (graph_width > width * 3/8 - number_width - 6)
- graph_width = width * 3/8 - number_width - 6;
+ if (reserved_character_count + name_width + graph_width > width) {
+ if (graph_width > (width - reserved_character_count) * 3/8)
+ graph_width = (width - reserved_character_count) * 3/8;
if (options->stat_graph_width &&
- graph_width > options->stat_graph_width)
+ graph_width > options->stat_graph_width)
graph_width = options->stat_graph_width;
- if (name_width > width - number_width - 6 - graph_width)
- name_width = width - number_width - 6 - graph_width;
+ if (name_width > width - reserved_character_count - graph_width)
+ name_width = width - reserved_character_count - graph_width;
else
- graph_width = width - number_width - 6 - name_width;
+ graph_width = width - reserved_character_count - name_width;
}
/*
diff --git a/t/t4052-stat-output.sh b/t/t4052-stat-output.sh
index 328aa8f..84dd8bb 100755
--- a/t/t4052-stat-output.sh
+++ b/t/t4052-stat-output.sh
@@ -162,7 +162,7 @@ test_expect_success 'preparation for long filename tests' '
'
cat >expect <<'EOF'
- ...aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa | 1000 ++++++++++++
+ ...aaaaaaaaaaaaaaaaaaaaaaaaaaaaa | 1000 ++++++++++++++++++
EOF
while read cmd args
do
@@ -179,7 +179,7 @@ log -1 --stat
EOF
cat >expect80 <<'EOF'
- ...aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa | 1000 ++++++++++++++++++++
+ ...aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa | 1000 ++++++++++++++++++++++++++
EOF
cat >expect200 <<'EOF'
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa | 1000 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
@@ -198,6 +198,26 @@ respects expect200 show --stat
respects expect200 log -1 --stat
EOF
+cat >expect80graphed <<'EOF'
+| ...aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa | 1000 +++++++++++++++++++++++++
+EOF
+cat >expect80 <<'EOF'
+ ...aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa | 1000 ++++++++++++++++++++++++++
+EOF
+while read verb expect cmd args
+do
+ test_expect_success "$cmd $verb 80 COLUMNS (long filename)" '
+ COLUMNS=80 git $cmd $args >output
+ grep " | " output >actual &&
+ test_cmp "$expect" actual
+ '
+done <<\EOF
+respects expect80 show --stat
+respects expect80 log -1 --stat
+respects expect80graphed show --stat --graph
+respects expect80graphed log -1 --stat --graph
+EOF
+
cat >expect <<'EOF'
abcd | 1000 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
EOF
--
1.7.3.4
next prev parent reply other threads:[~2012-03-20 7:39 UTC|newest]
Thread overview: 7+ messages / expand[flat|nested] mbox.gz Atom feed top
2012-03-20 7:38 [PATCH 0/1] Adjust diff stat width calculations so lines do not wrap in terminal when using --graph Lucian Poston
2012-03-20 7:38 ` Lucian Poston [this message]
2012-03-20 16:17 ` [PATCH 1/1] Fix --stat width calculations to handle --graph Johannes Schindelin
2012-03-20 17:23 ` Junio C Hamano
2012-03-22 19:33 ` Lucian Poston
2012-03-20 17:09 ` Junio C Hamano
2012-03-22 19:39 ` Lucian Poston
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1332229097-19262-2-git-send-email-lucian.poston@gmail.com \
--to=lucian.poston@gmail.com \
--cc=git@drmicha.warpmail.net \
--cc=git@vger.kernel.org \
--cc=gitster@pobox.com \
--cc=johannes.schindelin@gmx.de \
--cc=junkio@cox.net \
--cc=struggleyb.nku@gmail.com \
--cc=zbyszek@in.waw.pl \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).