Allow buffer text to be reset

This commit is contained in:
Jeremy Soller 2022-10-19 13:15:07 -06:00
parent b32c64e892
commit 0cbc3c3cfa
No known key found for this signature in database
GPG key ID: 87F211AF2BE4C2FE
4 changed files with 58 additions and 21 deletions

View file

@ -18,5 +18,11 @@ git = "https://github.com/pop-os/libcosmic"
branch = "cosmic-design-system" branch = "cosmic-design-system"
#path = "../../../libcosmic" #path = "../../../libcosmic"
[dependencies.rfd]
version = "0.10"
#TODO: iced portal
#default-features = false
#features = ["xdg-portal"]
[features] [features]
mono = [] mono = []

View file

@ -5,15 +5,20 @@ use cosmic::{
Application, Application,
Command, Command,
Element, Element,
Length,
Theme, Theme,
widget::{ widget::{
column, column,
horizontal_space,
pick_list, pick_list,
row, row,
text, text,
}, },
}, },
settings, settings,
widget::{
button,
},
}; };
use cosmic_text::{ use cosmic_text::{
FontMatches, FontMatches,
@ -94,6 +99,7 @@ pub struct Window {
#[allow(dead_code)] #[allow(dead_code)]
#[derive(Clone, Copy, Debug)] #[derive(Clone, Copy, Debug)]
pub enum Message { pub enum Message {
Open,
MetricsChanged(TextMetrics), MetricsChanged(TextMetrics),
ThemeChanged(&'static str), ThemeChanged(&'static str),
} }
@ -105,26 +111,26 @@ impl Application for Window {
type Theme = Theme; type Theme = Theme;
fn new(_flags: ()) -> (Self, Command<Self::Message>) { fn new(_flags: ()) -> (Self, Command<Self::Message>) {
let text = if let Some(arg) = env::args().nth(1) {
fs::read_to_string(&arg).expect("failed to open file")
} else {
#[cfg(feature = "mono")]
let default_text = include_str!("../../../sample/mono.txt");
#[cfg(not(feature = "mono"))]
let default_text = include_str!("../../../sample/proportional.txt");
default_text.to_string()
};
let font_size_i = 1; // Body let font_size_i = 1; // Body
let buffer = Mutex::new(TextBuffer::new( let mut buffer = TextBuffer::new(
unsafe { FONT_MATCHES.as_ref().unwrap() }, unsafe { FONT_MATCHES.as_ref().unwrap() },
&text,
FONT_SIZES[font_size_i], FONT_SIZES[font_size_i],
)); );
if let Some(arg) = env::args().nth(1) {
match fs::read_to_string(&arg) {
Ok(text) => {
buffer.set_text(&text);
},
Err(err) => {
log::error!("failed to open '{}': {}", arg, err);
}
}
}
let window = Window { let window = Window {
theme: Theme::Dark, theme: Theme::Dark,
buffer, buffer: Mutex::new(buffer),
}; };
(window, Command::none()) (window, Command::none())
} }
@ -139,6 +145,20 @@ impl Application for Window {
fn update(&mut self, message: Message) -> iced::Command<Self::Message> { fn update(&mut self, message: Message) -> iced::Command<Self::Message> {
match message { match message {
Message::Open => {
if let Some(path) = rfd::FileDialog::new().pick_file() {
let mut buffer = self.buffer.lock().unwrap();
match fs::read_to_string(&path) {
Ok(text) => {
buffer.set_text(&text);
},
Err(err) => {
buffer.set_text("");
log::error!("failed to open '{}': {}", path.display(), err);
}
}
}
},
Message::MetricsChanged(metrics) => { Message::MetricsChanged(metrics) => {
let mut buffer = self.buffer.lock().unwrap(); let mut buffer = self.buffer.lock().unwrap();
buffer.set_metrics(metrics); buffer.set_metrics(metrics);
@ -175,6 +195,8 @@ impl Application for Window {
column![ column![
row![ row![
button!("Open").on_press(Message::Open),
horizontal_space(Length::Fill),
text("Theme:"), text("Theme:"),
theme_picker, theme_picker,
text("Font Size:"), text("Font Size:"),

View file

@ -84,13 +84,13 @@ fn main() {
let line_x = 8 * display_scale; let line_x = 8 * display_scale;
let mut buffer = TextBuffer::new( let mut buffer = TextBuffer::new(
&font_matches, &font_matches,
&text,
font_sizes[font_size_i] font_sizes[font_size_i]
); );
buffer.set_size( buffer.set_size(
window.width() as i32 - line_x * 2, window.width() as i32 - line_x * 2,
window.height() as i32 window.height() as i32
); );
buffer.set_text(&text);
let mut ctrl_pressed = false; let mut ctrl_pressed = false;
let mut mouse_x = -1; let mut mouse_x = -1;

View file

@ -114,16 +114,11 @@ pub struct TextBuffer<'a> {
impl<'a> TextBuffer<'a> { impl<'a> TextBuffer<'a> {
pub fn new( pub fn new(
font_matches: &'a FontMatches<'a>, font_matches: &'a FontMatches<'a>,
text: &str,
metrics: TextMetrics, metrics: TextMetrics,
) -> Self { ) -> Self {
let mut text_lines: Vec<String> = text.lines().map(String::from).collect();
if text_lines.is_empty() {
text_lines.push(String::new());
}
Self { Self {
font_matches, font_matches,
text_lines, text_lines: Vec::new(),
shape_lines: Vec::new(), shape_lines: Vec::new(),
layout_lines: Vec::new(), layout_lines: Vec::new(),
metrics, metrics,
@ -294,6 +289,20 @@ impl<'a> TextBuffer<'a> {
&self.layout_lines &self.layout_lines
} }
/// Set text of buffer
pub fn set_text(&mut self, text: &str) {
self.text_lines = text.lines().map(String::from).collect();
if self.text_lines.is_empty() {
self.text_lines.push(String::new());
}
self.shape_lines.clear();
self.layout_lines.clear();
self.scroll = 0;
self.cursor = TextCursor::default();
self.select_opt = None;
self.shape_until_scroll();
}
/// Get the lines of the original text /// Get the lines of the original text
pub fn text_lines(&self) -> &[String] { pub fn text_lines(&self) -> &[String] {
&self.text_lines &self.text_lines