ratatui_widgets/clear.rs
1//! The [`Clear`] widget allows you to clear a certain area to allow overdrawing (e.g. for popups).
2use ratatui_core::buffer::Buffer;
3use ratatui_core::layout::Rect;
4use ratatui_core::widgets::Widget;
5
6/// A widget to clear/reset a certain area to allow overdrawing (e.g. for popups).
7///
8/// This widget **cannot be used to clear the terminal on the first render** as `ratatui` assumes
9/// the render area is empty. Use `Terminal::clear` instead.
10///
11/// # Examples
12///
13/// ```
14/// use ratatui::Frame;
15/// use ratatui::layout::Rect;
16/// use ratatui::widgets::{Block, Clear};
17///
18/// fn draw_on_clear(f: &mut Frame, area: Rect) {
19/// let block = Block::bordered().title("Block");
20/// f.render_widget(Clear, area); // <- this will clear/reset the area first
21/// f.render_widget(block, area); // now render the block widget
22/// }
23/// ```
24///
25/// # Popup Example
26///
27/// For a more complete example how to utilize `Clear` to realize popups see
28/// the example `examples/popup.rs`
29#[derive(Debug, Default, Clone, Eq, PartialEq, Hash)]
30pub struct Clear;
31
32impl Widget for Clear {
33 fn render(self, area: Rect, buf: &mut Buffer) {
34 Widget::render(&self, area, buf);
35 }
36}
37
38impl Widget for &Clear {
39 fn render(self, area: Rect, buf: &mut Buffer) {
40 for x in area.left()..area.right() {
41 for y in area.top()..area.bottom() {
42 buf[(x, y)].reset();
43 }
44 }
45 }
46}
47
48#[cfg(test)]
49mod tests {
50 use ratatui_core::buffer::Buffer;
51 use ratatui_core::layout::Rect;
52 use ratatui_core::widgets::Widget;
53
54 use super::*;
55
56 #[test]
57 fn render() {
58 let mut buffer = Buffer::with_lines(["xxxxxxxxxxxxxxx"; 7]);
59 let clear = Clear;
60 clear.render(Rect::new(1, 2, 3, 4), &mut buffer);
61 let expected = Buffer::with_lines([
62 "xxxxxxxxxxxxxxx",
63 "xxxxxxxxxxxxxxx",
64 "x xxxxxxxxxxx",
65 "x xxxxxxxxxxx",
66 "x xxxxxxxxxxx",
67 "x xxxxxxxxxxx",
68 "xxxxxxxxxxxxxxx",
69 ]);
70 assert_eq!(buffer, expected);
71 }
72}