| 1 | use crate::display::{AnsiString, AnsiStrings}; |
| 2 | use std::ops::Deref; |
| 3 | |
| 4 | /// Return a substring of the given AnsiStrings sequence, while keeping the formatting. |
| 5 | pub fn sub_string<'a>( |
| 6 | start: usize, |
| 7 | len: usize, |
| 8 | strs: &AnsiStrings<'a>, |
| 9 | ) -> Vec<AnsiString<'static>> { |
| 10 | let mut vec = Vec::new(); |
| 11 | let mut pos = start; |
| 12 | let mut len_rem = len; |
| 13 | |
| 14 | for i in strs.0.iter() { |
| 15 | let frag_len = i.string.len(); |
| 16 | if pos >= frag_len { |
| 17 | pos -= frag_len; |
| 18 | continue; |
| 19 | } |
| 20 | if len_rem == 0 { |
| 21 | break; |
| 22 | } |
| 23 | |
| 24 | let end = pos + len_rem; |
| 25 | let pos_end = if end >= frag_len { frag_len } else { end }; |
| 26 | |
| 27 | vec.push(i.style_ref().paint(String::from(&i.string[pos..pos_end]))); |
| 28 | |
| 29 | if end <= frag_len { |
| 30 | break; |
| 31 | } |
| 32 | |
| 33 | len_rem -= pos_end - pos; |
| 34 | pos = 0; |
| 35 | } |
| 36 | |
| 37 | vec |
| 38 | } |
| 39 | |
| 40 | /// Return a concatenated copy of `strs` without the formatting, as an allocated `String`. |
| 41 | pub fn unstyle(strs: &AnsiStrings) -> String { |
| 42 | let mut s: String = String::new(); |
| 43 | |
| 44 | for i: &AnsiGenericString<'_, str> in strs.0.iter() { |
| 45 | s += i.string.deref(); |
| 46 | } |
| 47 | |
| 48 | s |
| 49 | } |
| 50 | |
| 51 | /// Return the unstyled length of AnsiStrings. This is equaivalent to `unstyle(strs).len()`. |
| 52 | pub fn unstyled_len(strs: &AnsiStrings) -> usize { |
| 53 | let mut l: usize = 0; |
| 54 | for i: &AnsiGenericString<'_, str> in strs.0.iter() { |
| 55 | l += i.string.len(); |
| 56 | } |
| 57 | l |
| 58 | } |
| 59 | |
| 60 | #[cfg (test)] |
| 61 | mod test { |
| 62 | use super::*; |
| 63 | use crate::Color::*; |
| 64 | |
| 65 | #[test ] |
| 66 | fn test() { |
| 67 | let l = [ |
| 68 | Black.paint("first" ), |
| 69 | Red.paint("-second" ), |
| 70 | White.paint("-third" ), |
| 71 | ]; |
| 72 | let a = AnsiStrings(&l); |
| 73 | assert_eq!(unstyle(&a), "first-second-third" ); |
| 74 | assert_eq!(unstyled_len(&a), 18); |
| 75 | |
| 76 | let l2 = [Black.paint("st" ), Red.paint("-second" ), White.paint("-t" )]; |
| 77 | assert_eq!(sub_string(3, 11, &a), l2); |
| 78 | } |
| 79 | } |
| 80 | |