diff options
Diffstat (limited to 'argparse/src/help.rs')
-rw-r--r-- | argparse/src/help.rs | 93 |
1 files changed, 93 insertions, 0 deletions
diff --git a/argparse/src/help.rs b/argparse/src/help.rs new file mode 100644 index 0000000..c7145be --- /dev/null +++ b/argparse/src/help.rs @@ -0,0 +1,93 @@ +use std::str::CharIndices; +use std::io::Result as IoResult; +use std::io::Write; + +use super::action::{IFlagAction, ParseResult}; +use super::action::ParseResult::Help; + +pub struct HelpAction; + +impl IFlagAction for HelpAction { + fn parse_flag(&self) -> ParseResult { + return Help; + } +} + + +struct WordsIter<'a> { + data: &'a str, + iter: CharIndices<'a>, +} + +impl<'a> WordsIter<'a> { + fn new(data: &'a str) -> WordsIter<'a> { + return WordsIter { + data: data, + iter: data.char_indices(), + }; + } +} + +impl<'a> Iterator for WordsIter<'a> { + type Item = &'a str; + fn next(&mut self) -> Option<&'a str> { + let word_start; + loop { + let (idx, ch) = match self.iter.next() { + None => return None, + Some((idx, ch)) => ((idx, ch)), + }; + match ch { + ' ' | '\t' | '\r' | '\n' => continue, + _ => { + word_start = idx; + break; + } + } + } + loop { + let (idx, ch) = match self.iter.next() { + None => break, + Some((idx, ch)) => ((idx, ch)), + }; + match ch { + ' ' | '\t' | '\r' | '\n' => { + return Some(&self.data[word_start..idx]); + } + _ => continue, + } + } + return Some(&self.data[word_start..self.data.len()]); + } +} + +pub fn wrap_text(buf: &mut Write, data: &str, width: usize, indent: usize) + -> IoResult<()> +{ + let mut witer = WordsIter::new(data); + let mut off = indent; + match witer.next() { + None => { + return Ok(()); + } + Some(word) => { + try!(buf.write(word.as_bytes())); + off += word.len(); + } + } + for word in witer { + if off + word.len() + 1 > width { + try!(buf.write(b"\n")); + for _ in 0..indent { + try!(buf.write(b" ")); + } + off = indent; + } else { + try!(buf.write(b" ")); + off += 1; + } + try!(buf.write(word.as_bytes())); + off += word.len(); + } + return Ok(()); +} |