diff --git a/src/cargo/util/progress.rs b/src/cargo/util/progress.rs index fa5f36036..f212a496e 100644 --- a/src/cargo/util/progress.rs +++ b/src/cargo/util/progress.rs @@ -75,6 +75,7 @@ struct Format { max_width: usize, max_print: usize, term_integration: TerminalIntegration, + unicode: bool, } /// Controls terminal progress integration via OSC sequences. @@ -229,6 +230,7 @@ impl<'gctx> Progress<'gctx> { // even on narrow (e.g. 80 char) terminals. max_print: 50, term_integration: TerminalIntegration::from_config(gctx), + unicode: gctx.shell().err_unicode(), }, name: name.to_string(), done: false, @@ -261,8 +263,7 @@ impl<'gctx> Progress<'gctx> { /// * `cur` should be how far along the progress is. /// * `max` is the maximum value for the progress bar. /// * `msg` is a small piece of text to display at the end of the progress - /// bar. It will be truncated with `...` if it does not fit on the - /// terminal. + /// bar. It will be truncated with `…` if it does not fit on the terminal. /// /// This may not actually update the display if `tick` is being called too /// quickly. @@ -521,7 +522,10 @@ impl Format { fn render(&self, string: &mut String, msg: &str) { let mut avail_msg_len = self.max_width - string.len() - 15; let mut ellipsis_pos = 0; - if avail_msg_len <= 3 { + + let (ellipsis, ellipsis_width) = if self.unicode { ("…", 1) } else { ("...", 3) }; + + if avail_msg_len <= ellipsis_width { return; } for c in msg.chars() { @@ -529,12 +533,12 @@ impl Format { if avail_msg_len >= display_width { avail_msg_len -= display_width; string.push(c); - if avail_msg_len >= 3 { + if avail_msg_len >= ellipsis_width { ellipsis_pos = string.len(); } } else { string.truncate(ellipsis_pos); - string.push_str("..."); + string.push_str(ellipsis); break; } } @@ -569,6 +573,7 @@ fn test_progress_status() { max_print: 40, max_width: 60, term_integration: TerminalIntegration::new(false), + unicode: true, }; assert_eq!( format.progress_status(0, 4, ""), @@ -610,7 +615,7 @@ fn test_progress_status() { ); assert_eq!( format.progress_status(3, 4, ": msg that's just fit"), - Some("[=============> ] 3/4: msg that's just...".to_string()) + Some("[=============> ] 3/4: msg that's just f…".to_string()) ); // combining diacritics have width zero and thus can fit max_width. @@ -623,16 +628,16 @@ fn test_progress_status() { // some non-ASCII ellipsize test assert_eq!( format.progress_status(3, 4, "_123456789123456e\u{301}\u{301}8\u{301}90a"), - Some("[=============> ] 3/4_123456789123456e\u{301}\u{301}...".to_string()) + Some("[=============> ] 3/4_123456789123456e\u{301}\u{301}8\u{301}9…".to_string()) ); assert_eq!( format.progress_status(3, 4, ":每個漢字佔據了兩個字元"), - Some("[=============> ] 3/4:每個漢字佔據了...".to_string()) + Some("[=============> ] 3/4:每個漢字佔據了兩…".to_string()) ); assert_eq!( // handle breaking at middle of character format.progress_status(3, 4, ":-每個漢字佔據了兩個字元"), - Some("[=============> ] 3/4:-每個漢字佔據了...".to_string()) + Some("[=============> ] 3/4:-每個漢字佔據了兩…".to_string()) ); } @@ -643,6 +648,7 @@ fn test_progress_status_percentage() { max_print: 40, max_width: 60, term_integration: TerminalIntegration::new(false), + unicode: true, }; assert_eq!( format.progress_status(0, 77, ""), @@ -669,6 +675,7 @@ fn test_progress_status_too_short() { max_print: 25, max_width: 25, term_integration: TerminalIntegration::new(false), + unicode: true, }; assert_eq!( format.progress_status(1, 1, ""), @@ -680,6 +687,7 @@ fn test_progress_status_too_short() { max_print: 24, max_width: 24, term_integration: TerminalIntegration::new(false), + unicode: true, }; assert_eq!(format.progress_status(1, 1, ""), None); }