feat: Timestamp::time_delta & Headline::is_todo & Headline::is_done
This commit is contained in:
parent
f918bf4ca6
commit
f9d56cf899
2 changed files with 37 additions and 232 deletions
|
|
@ -76,6 +76,30 @@ impl Headline {
|
|||
})
|
||||
}
|
||||
|
||||
/// ```rust
|
||||
/// use orgize::{Org, ast::Headline};
|
||||
///
|
||||
/// let hdl = Org::parse("* TODO a").first_node::<Headline>().unwrap();
|
||||
/// assert!(hdl.is_todo());
|
||||
/// let hdl = Org::parse("* a").first_node::<Headline>().unwrap();
|
||||
/// assert!(!hdl.is_todo());
|
||||
/// ```
|
||||
pub fn is_todo(&self) -> bool {
|
||||
matches!(self.todo_type(), Some(TodoType::Todo))
|
||||
}
|
||||
|
||||
/// ```rust
|
||||
/// use orgize::{Org, ast::Headline};
|
||||
///
|
||||
/// let hdl = Org::parse("* DONE a").first_node::<Headline>().unwrap();
|
||||
/// assert!(hdl.is_done());
|
||||
/// let hdl = Org::parse("* a").first_node::<Headline>().unwrap();
|
||||
/// assert!(!hdl.is_done());
|
||||
/// ```
|
||||
pub fn is_done(&self) -> bool {
|
||||
matches!(self.todo_type(), Some(TodoType::Done))
|
||||
}
|
||||
|
||||
/// Returns parsed title
|
||||
///
|
||||
/// ```rust
|
||||
|
|
@ -250,235 +274,3 @@ impl Headline {
|
|||
.flat_map(|x| x.children().filter_map(Clock::cast))
|
||||
}
|
||||
}
|
||||
|
||||
// pub enum DocumentOrHeadline {
|
||||
// Document(Document),
|
||||
// Headline(Headline),
|
||||
// }
|
||||
|
||||
// impl From<Document> for DocumentOrHeadline {
|
||||
// fn from(value: Document) -> Self {
|
||||
// DocumentOrHeadline::Document(value)
|
||||
// }
|
||||
// }
|
||||
|
||||
// impl From<Headline> for DocumentOrHeadline {
|
||||
// fn from(value: Headline) -> Self {
|
||||
// DocumentOrHeadline::Headline(value)
|
||||
// }
|
||||
// }
|
||||
|
||||
// impl DocumentOrHeadline {
|
||||
// pub fn section(&self) -> Option<Section> {
|
||||
// match self {
|
||||
// DocumentOrHeadline::Document(v) => v.section(),
|
||||
// DocumentOrHeadline::Headline(v) => v.section(),
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
||||
// impl Org {
|
||||
// /// set the title of this headline
|
||||
// ///
|
||||
// /// ```rust
|
||||
// /// use orgize::Org;
|
||||
// ///
|
||||
// /// let mut org = Org::parse("* [#A]");
|
||||
// /// let hdl = org.document().first_headline().unwrap();
|
||||
// /// org.set_title(hdl, "world");
|
||||
// /// assert_eq!(org.to_org(), "* [#A] world");
|
||||
// /// let hdl = org.document().first_headline().unwrap();
|
||||
// /// org.set_title(hdl, "world!");
|
||||
// /// assert_eq!(org.to_org(), "* [#A] world!");
|
||||
// /// ```
|
||||
// pub fn set_title(&mut self, headline: Headline, title: &str) -> Option<HeadlineTitle> {
|
||||
// let bytes = title.as_bytes();
|
||||
// let title = match memchr(b'\n', bytes) {
|
||||
// Some(i) if i > 0 && bytes[i] == b'\r' => &title[0..i - 1],
|
||||
// Some(i) => &title[0..i],
|
||||
// _ => title,
|
||||
// };
|
||||
// let new_title = node(HEADLINE_TITLE, object_nodes(self.create_input(title)));
|
||||
|
||||
// if let Some(title) = headline.title() {
|
||||
// self.green = title.syntax.replace_with(new_title.into_node().unwrap());
|
||||
|
||||
// return Some(title);
|
||||
// }
|
||||
|
||||
// let mut child: Vec<_> = headline
|
||||
// .syntax
|
||||
// .green()
|
||||
// .children()
|
||||
// .map(|ch| ch.to_owned())
|
||||
// .collect();
|
||||
|
||||
// let index = support::child
|
||||
// .iter()
|
||||
// .enumerate()
|
||||
// .filter_map(|(idx, it)| {
|
||||
// if it.kind() == HEADLINE_STARS.into()
|
||||
// || it.kind() == HEADLINE_KEYWORD.into()
|
||||
// || it.kind() == HEADLINE_PRIORITY.into()
|
||||
// {
|
||||
// Some(idx + 1)
|
||||
// } else {
|
||||
// None
|
||||
// }
|
||||
// })
|
||||
// .last()
|
||||
// .unwrap_or_default();
|
||||
|
||||
// if index == child.len() {
|
||||
// child.push(token(WHITESPACE, " "));
|
||||
// child.push(new_title);
|
||||
// } else if child[index].kind() != WHITESPACE.into() {
|
||||
// child.insert(index, token(WHITESPACE, " "));
|
||||
// child.insert(index + 1, new_title);
|
||||
// } else {
|
||||
// child.insert(index, new_title);
|
||||
// }
|
||||
|
||||
// self.green = headline
|
||||
// .syntax
|
||||
// .replace_with(node(HEADLINE, child).into_node().unwrap());
|
||||
|
||||
// None
|
||||
// }
|
||||
|
||||
// /// set the section of this document or headline
|
||||
// ///
|
||||
// /// ```rust
|
||||
// /// use orgize::Org;
|
||||
// ///
|
||||
// /// let mut org = Org::parse("* hello");
|
||||
// ///
|
||||
// /// let hdl = org.document().first_headline().unwrap();
|
||||
// /// org.set_section(hdl, "world");
|
||||
// /// assert_eq!(org.to_org(), "* hello\nworld\n");
|
||||
// ///
|
||||
// /// let hdl = org.document().first_headline().unwrap();
|
||||
// /// org.set_section(hdl, "world!");
|
||||
// /// assert_eq!(org.to_org(), "* hello\nworld!\n");
|
||||
// ///
|
||||
// /// let doc = org.document();
|
||||
// /// org.set_section(doc, "doc");
|
||||
// /// assert_eq!(org.to_org(), "doc\n* hello\nworld!\n");
|
||||
// /// ```
|
||||
// pub fn set_section(
|
||||
// &mut self,
|
||||
// document_or_headline: impl Into<DocumentOrHeadline>,
|
||||
// section: &str,
|
||||
// ) -> Option<Section> {
|
||||
// let document_or_headline = document_or_headline.into();
|
||||
|
||||
// let section = section_text(self.create_input(section)).ok()?.1.as_str();
|
||||
|
||||
// let section = if section.ends_with('\n') {
|
||||
// section_node(self.create_input(section)).map(|(_, s)| s)
|
||||
// } else {
|
||||
// section_node(self.create_input(&format!("{section}\n"))).map(|(_, s)| s)
|
||||
// }
|
||||
// .ok()?;
|
||||
|
||||
// if let Some(old) = document_or_headline.section() {
|
||||
// self.green = old.syntax.replace_with(section.into_node().unwrap());
|
||||
|
||||
// return Some(old);
|
||||
// }
|
||||
|
||||
// match document_or_headline {
|
||||
// DocumentOrHeadline::Document(document) => {
|
||||
// let mut child: Vec<_> = document
|
||||
// .syntax
|
||||
// .green()
|
||||
// .children()
|
||||
// .map(|ch| ch.to_owned())
|
||||
// .collect();
|
||||
|
||||
// let headline_idx = child.iter().position(|it| it.kind() == HEADLINE.into());
|
||||
|
||||
// if let Some(idx) = headline_idx {
|
||||
// child.insert(idx, section);
|
||||
// } else {
|
||||
// child.push(section);
|
||||
// }
|
||||
|
||||
// self.green = document
|
||||
// .syntax
|
||||
// .replace_with(GreenNode::new(DOCUMENT.into(), child));
|
||||
|
||||
// None
|
||||
// }
|
||||
// DocumentOrHeadline::Headline(headline) => {
|
||||
// let mut child: Vec<_> = headline
|
||||
// .syntax
|
||||
// .green()
|
||||
// .children()
|
||||
// .map(|ch| ch.to_owned())
|
||||
// .collect();
|
||||
|
||||
// let new_line_idx = support::child
|
||||
// .iter()
|
||||
// .position(|it| it.kind() == NEW_LINE.into());
|
||||
|
||||
// if let Some(idx) = new_line_idx {
|
||||
// // add section *after* newline
|
||||
// if idx < support::child.len() {
|
||||
// support::child.insert(idx, section);
|
||||
// } else {
|
||||
// support::child.push(section);
|
||||
// }
|
||||
// } else {
|
||||
// support::child.push(token(NEW_LINE, "\n"));
|
||||
// support::child.push(section);
|
||||
// }
|
||||
|
||||
// self.green = headline
|
||||
// .syntax
|
||||
// .replace_with(GreenNode::new(HEADLINE.into(), support::child));
|
||||
|
||||
// None
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
||||
// /// set the level of this headline
|
||||
// ///
|
||||
// /// ```rust
|
||||
// /// use orgize::Org;
|
||||
// ///
|
||||
// /// let mut org = Org::parse("** 1\n** 2");
|
||||
// ///
|
||||
// /// let hdl = org.document().last_headline().unwrap();
|
||||
// /// org.set_level(hdl, 1);
|
||||
// /// assert_eq!(org.to_org(), "** 1\n* 2");
|
||||
// ///
|
||||
// /// let hdl = org.document().last_headline().unwrap();
|
||||
// /// org.set_level(hdl, 3);
|
||||
// /// assert_eq!(org.to_org(), "** 1\n* 2");
|
||||
// /// ```
|
||||
// pub fn set_level(&mut self, headline: Headline, level: usize) {
|
||||
// if level == 0 {
|
||||
// return;
|
||||
// }
|
||||
|
||||
// let min_level_in_siblings = headline
|
||||
// .syntax
|
||||
// .siblings(rowan::Direction::Next)
|
||||
// .chain(headline.syntax.siblings(rowan::Direction::Prev))
|
||||
// .filter_map(Headline::cast)
|
||||
// .filter_map(|headline| headline.level())
|
||||
// .min()
|
||||
// .unwrap_or(1);
|
||||
|
||||
// if level <= min_level_in_siblings {
|
||||
// if let Some(stars) = headline.stars() {
|
||||
// self.green = stars.replace_with(GreenToken::new(
|
||||
// SyntaxKind::HEADLINE_STARS.into(),
|
||||
// "*".repeat(level).as_str(),
|
||||
// ));
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
|
|
|||
|
|
@ -285,4 +285,17 @@ impl Timestamp {
|
|||
)?,
|
||||
))
|
||||
}
|
||||
|
||||
/// Returns chrono::TimeDelta between timestamp start and end
|
||||
///
|
||||
/// ```rust
|
||||
/// use orgize::{Org, ast::Timestamp};
|
||||
///
|
||||
/// let ts = Org::parse("[2003-09-16 Tue 09:39-10:39]").first_node::<Timestamp>().unwrap();
|
||||
/// assert_eq!(ts.time_delta().unwrap().num_hours(), 1);
|
||||
/// ```
|
||||
#[cfg(feature = "chrono")]
|
||||
pub fn time_delta(&self) -> Option<chrono::TimeDelta> {
|
||||
Some(self.end_to_chrono()? - self.start_to_chrono()?)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue