Skip to main content

iced_markdown_editor/
features.rs

1//! Optional Markdown features, switched on or off at runtime.
2//!
3//! The editor supports the GFM extensions strikethrough, task lists and
4//! tables. Each can be turned off with [`Features`]. A disabled feature:
5//!
6//! * is not recognised when Markdown is loaded (the text stays a normal
7//!   paragraph, e.g. `| a | b |` or `~~text~~`),
8//! * has no toolbar button,
9//! * ignores its [`Command`]s and shortcuts ([`Features::allows`]),
10//! * is not created by autoformat (typing `[ ] ` or `| a | b |` + Enter).
11//!
12//! Set the features before loading the document. Switching a feature off
13//! later turns its content into text; switching it on again does not
14//! restore it.
15//!
16//! These are not Cargo features; Cargo features (`syntect`, `images`) add
17//! code, these switch editor behaviour.
18//!
19//! ```
20//! use iced_markdown_editor::{EditorState, Features};
21//!
22//! let mut editor = EditorState::new().features(Features {
23//!     tables: false,
24//!     ..Features::default()
25//! });
26//! editor.set_markdown("| a |\n| - |\n");
27//! assert!(!editor.formatting().table);
28//! assert_eq!(editor.markdown(), "\\| a \\|\n\\| - \\|\n");
29//! ```
30
31use crate::doc::BlockKind;
32use crate::widget::Command;
33
34/// Optional Markdown features. All are enabled by default.
35#[derive(Debug, Clone, Copy, PartialEq, Eq)]
36pub struct Features {
37    /// GFM tables.
38    pub tables: bool,
39    /// GFM task lists (`- [ ]`, `- [x]`).
40    pub task_lists: bool,
41    /// GFM strikethrough (`~~text~~`).
42    pub strikethrough: bool,
43}
44
45impl Default for Features {
46    fn default() -> Self {
47        Self::ALL
48    }
49}
50
51impl Features {
52    /// Every feature enabled (the default).
53    pub const ALL: Self = Self {
54        tables: true,
55        task_lists: true,
56        strikethrough: true,
57    };
58
59    /// Plain CommonMark: every optional feature disabled.
60    pub const COMMONMARK: Self = Self {
61        tables: false,
62        task_lists: false,
63        strikethrough: false,
64    };
65
66    /// Whether `command` belongs to an enabled feature. Commands of disabled
67    /// features do nothing; use this to hide them in a custom toolbar.
68    pub fn allows(&self, command: &Command) -> bool {
69        match command {
70            Command::ToggleStrike => self.strikethrough,
71            Command::SetBlock(BlockKind::Task) | Command::ToggleChecked => self.task_lists,
72            Command::InsertTable { .. }
73            | Command::InsertRow { .. }
74            | Command::InsertColumn { .. }
75            | Command::DeleteRow
76            | Command::DeleteColumn
77            | Command::DeleteTable
78            | Command::SetColumnAlign(_) => self.tables,
79            _ => true,
80        }
81    }
82}