Compare commits
4 Commits
67e9331535
...
c50c9b6779
| Author | SHA1 | Date | |
|---|---|---|---|
| c50c9b6779 | |||
| e4091c0c3f | |||
| c4de8acec5 | |||
| 0da68c8801 |
@ -21,6 +21,8 @@ pub struct Config {
|
|||||||
pub font_family: String,
|
pub font_family: String,
|
||||||
#[serde(default = "default_font_size")]
|
#[serde(default = "default_font_size")]
|
||||||
pub font_size: f32,
|
pub font_size: f32,
|
||||||
|
#[serde(default = "default_syntax_highlighting")]
|
||||||
|
pub syntax_highlighting: bool,
|
||||||
// pub vim_mode: bool,
|
// pub vim_mode: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -45,18 +47,22 @@ fn default_font_family() -> String {
|
|||||||
fn default_font_size() -> f32 {
|
fn default_font_size() -> f32 {
|
||||||
14.0
|
14.0
|
||||||
}
|
}
|
||||||
|
fn default_syntax_highlighting() -> bool {
|
||||||
|
false
|
||||||
|
}
|
||||||
|
|
||||||
impl Default for Config {
|
impl Default for Config {
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
Self {
|
Self {
|
||||||
auto_hide_toolbar: false,
|
auto_hide_toolbar: default_auto_hide_toolbar(),
|
||||||
hide_tab_bar: true,
|
hide_tab_bar: default_hide_tab_bar(),
|
||||||
show_line_numbers: false,
|
show_line_numbers: default_show_line_numbers(),
|
||||||
word_wrap: true,
|
word_wrap: default_word_wrap(),
|
||||||
theme: Theme::default(),
|
theme: Theme::default(),
|
||||||
line_side: false,
|
line_side: default_line_side(),
|
||||||
font_family: "Proportional".to_string(),
|
font_family: default_font_family(),
|
||||||
font_size: 14.0,
|
font_size: default_font_size(),
|
||||||
|
syntax_highlighting: default_syntax_highlighting(),
|
||||||
// vim_mode: false,
|
// vim_mode: false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,21 +1,10 @@
|
|||||||
use super::editor::TextEditor;
|
use super::editor::TextEditor;
|
||||||
use crate::app::config::Config;
|
use crate::app::config::Config;
|
||||||
use crate::app::tab::Tab;
|
|
||||||
use crate::app::theme;
|
use crate::app::theme;
|
||||||
|
|
||||||
impl TextEditor {
|
impl TextEditor {
|
||||||
pub fn from_config(config: Config) -> Self {
|
pub fn from_config(config: Config) -> Self {
|
||||||
Self {
|
Self {
|
||||||
tabs: vec![Tab::new_empty(1)],
|
|
||||||
active_tab_index: 0,
|
|
||||||
tab_counter: 1,
|
|
||||||
show_about: false,
|
|
||||||
show_shortcuts: false,
|
|
||||||
show_find: false,
|
|
||||||
show_preferences: false,
|
|
||||||
pending_unsaved_action: None,
|
|
||||||
force_quit_confirmed: false,
|
|
||||||
clean_quit_requested: false,
|
|
||||||
show_line_numbers: config.show_line_numbers,
|
show_line_numbers: config.show_line_numbers,
|
||||||
word_wrap: config.word_wrap,
|
word_wrap: config.word_wrap,
|
||||||
auto_hide_toolbar: config.auto_hide_toolbar,
|
auto_hide_toolbar: config.auto_hide_toolbar,
|
||||||
@ -24,30 +13,8 @@ impl TextEditor {
|
|||||||
line_side: config.line_side,
|
line_side: config.line_side,
|
||||||
font_family: config.font_family,
|
font_family: config.font_family,
|
||||||
font_size: config.font_size,
|
font_size: config.font_size,
|
||||||
font_size_input: None,
|
syntax_highlighting: config.syntax_highlighting,
|
||||||
zoom_factor: 1.0,
|
..Default::default()
|
||||||
menu_interaction_active: false,
|
|
||||||
tab_bar_rect: None,
|
|
||||||
menu_bar_stable_until: None,
|
|
||||||
text_processing_result: std::sync::Arc::new(std::sync::Mutex::new(Default::default())),
|
|
||||||
_processing_thread_handle: None,
|
|
||||||
find_query: String::new(),
|
|
||||||
replace_query: String::new(),
|
|
||||||
find_matches: Vec::new(),
|
|
||||||
current_match_index: None,
|
|
||||||
case_sensitive_search: false,
|
|
||||||
show_replace_section: false,
|
|
||||||
prev_show_find: false,
|
|
||||||
focus_find: false,
|
|
||||||
// vim_mode: config.vim_mode,
|
|
||||||
previous_cursor_position: None,
|
|
||||||
previous_content: String::new(),
|
|
||||||
previous_cursor_char_index: None,
|
|
||||||
current_cursor_line: 0,
|
|
||||||
previous_cursor_line: 0,
|
|
||||||
font_settings_changed: false,
|
|
||||||
text_needs_processing: false,
|
|
||||||
should_select_current_match: false,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -87,6 +54,7 @@ impl TextEditor {
|
|||||||
line_side: self.line_side,
|
line_side: self.line_side,
|
||||||
font_family: self.font_family.to_string(),
|
font_family: self.font_family.to_string(),
|
||||||
font_size: self.font_size,
|
font_size: self.font_size,
|
||||||
|
syntax_highlighting: self.syntax_highlighting,
|
||||||
// vim_mode: self.vim_mode,
|
// vim_mode: self.vim_mode,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -20,6 +20,7 @@ impl Default for TextEditor {
|
|||||||
word_wrap: true,
|
word_wrap: true,
|
||||||
auto_hide_toolbar: false,
|
auto_hide_toolbar: false,
|
||||||
hide_tab_bar: true,
|
hide_tab_bar: true,
|
||||||
|
syntax_highlighting: false,
|
||||||
theme: Theme::default(),
|
theme: Theme::default(),
|
||||||
line_side: false,
|
line_side: false,
|
||||||
font_family: "Proportional".to_string(),
|
font_family: "Proportional".to_string(),
|
||||||
|
|||||||
@ -45,6 +45,7 @@ pub struct TextEditor {
|
|||||||
pub(crate) word_wrap: bool,
|
pub(crate) word_wrap: bool,
|
||||||
pub(crate) auto_hide_toolbar: bool,
|
pub(crate) auto_hide_toolbar: bool,
|
||||||
pub(crate) hide_tab_bar: bool,
|
pub(crate) hide_tab_bar: bool,
|
||||||
|
pub(crate) syntax_highlighting: bool,
|
||||||
pub(crate) theme: Theme,
|
pub(crate) theme: Theme,
|
||||||
pub(crate) line_side: bool,
|
pub(crate) line_side: bool,
|
||||||
pub(crate) font_family: String,
|
pub(crate) font_family: String,
|
||||||
|
|||||||
@ -2,35 +2,32 @@ use std::collections::hash_map::DefaultHasher;
|
|||||||
use std::hash::{Hash, Hasher};
|
use std::hash::{Hash, Hasher};
|
||||||
use std::path::PathBuf;
|
use std::path::PathBuf;
|
||||||
|
|
||||||
pub fn compute_content_hash(content: &str, hasher: &mut DefaultHasher) -> u64 {
|
pub fn compute_content_hash(content: &str) -> u64 {
|
||||||
content.hash(hasher);
|
let mut hasher = DefaultHasher::new();
|
||||||
hasher.finish()
|
content.hash(&mut hasher);
|
||||||
|
let hash = hasher.finish();
|
||||||
|
hash
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
pub struct Tab {
|
pub struct Tab {
|
||||||
pub content: String,
|
pub content: String,
|
||||||
pub original_content_hash: u64,
|
pub original_content_hash: u64,
|
||||||
pub last_content_hash: u64,
|
|
||||||
pub file_path: Option<PathBuf>,
|
pub file_path: Option<PathBuf>,
|
||||||
pub is_modified: bool,
|
pub is_modified: bool,
|
||||||
pub title: String,
|
pub title: String,
|
||||||
pub hasher: DefaultHasher,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Tab {
|
impl Tab {
|
||||||
pub fn new_empty(tab_number: usize) -> Self {
|
pub fn new_empty(tab_number: usize) -> Self {
|
||||||
let content = String::new();
|
let content = String::new();
|
||||||
let mut hasher = DefaultHasher::new();
|
let hash = compute_content_hash(&content);
|
||||||
let hash = compute_content_hash(&content, &mut hasher);
|
|
||||||
Self {
|
Self {
|
||||||
original_content_hash: hash,
|
original_content_hash: hash,
|
||||||
last_content_hash: hash,
|
|
||||||
content,
|
content,
|
||||||
file_path: None,
|
file_path: None,
|
||||||
is_modified: false,
|
is_modified: false,
|
||||||
title: format!("new_{tab_number}"),
|
title: format!("new_{tab_number}"),
|
||||||
hasher,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -38,19 +35,16 @@ impl Tab {
|
|||||||
let title = file_path
|
let title = file_path
|
||||||
.file_name()
|
.file_name()
|
||||||
.and_then(|n| n.to_str())
|
.and_then(|n| n.to_str())
|
||||||
.unwrap_or("Untitled")
|
.unwrap_or("UNKNOWN")
|
||||||
.to_string();
|
.to_string();
|
||||||
|
|
||||||
let mut hasher = DefaultHasher::new();
|
let hash = compute_content_hash(&content);
|
||||||
let hash = compute_content_hash(&content, &mut hasher);
|
|
||||||
Self {
|
Self {
|
||||||
original_content_hash: hash,
|
original_content_hash: hash,
|
||||||
last_content_hash: hash,
|
|
||||||
content,
|
content,
|
||||||
file_path: Some(file_path),
|
file_path: Some(file_path),
|
||||||
is_modified: false,
|
is_modified: false,
|
||||||
title,
|
title,
|
||||||
hasher,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -63,15 +57,13 @@ impl Tab {
|
|||||||
if self.title.starts_with("new_") {
|
if self.title.starts_with("new_") {
|
||||||
self.is_modified = !self.content.is_empty();
|
self.is_modified = !self.content.is_empty();
|
||||||
} else {
|
} else {
|
||||||
let current_hash = compute_content_hash(&self.content, &mut self.hasher);
|
let current_hash = compute_content_hash(&self.content);
|
||||||
self.is_modified = current_hash != self.last_content_hash;
|
self.is_modified = current_hash != self.original_content_hash;
|
||||||
self.last_content_hash = current_hash;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn mark_as_saved(&mut self) {
|
pub fn mark_as_saved(&mut self) {
|
||||||
self.original_content_hash = compute_content_hash(&self.content, &mut self.hasher);
|
self.original_content_hash = compute_content_hash(&self.content);
|
||||||
self.last_content_hash = self.original_content_hash;
|
|
||||||
self.is_modified = false;
|
self.is_modified = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -80,6 +80,8 @@ pub(super) fn editor_view_ui(ui: &mut egui::Ui, app: &mut TextEditor) -> egui::R
|
|||||||
let show_shortcuts = app.show_shortcuts;
|
let show_shortcuts = app.show_shortcuts;
|
||||||
let word_wrap = app.word_wrap;
|
let word_wrap = app.word_wrap;
|
||||||
let font_size = app.font_size;
|
let font_size = app.font_size;
|
||||||
|
let font_id = app.get_font_id();
|
||||||
|
let syntax_highlighting_enabled = app.syntax_highlighting;
|
||||||
|
|
||||||
let reset_zoom_key = egui::Id::new("editor_reset_zoom");
|
let reset_zoom_key = egui::Id::new("editor_reset_zoom");
|
||||||
let should_reset_zoom = ui
|
let should_reset_zoom = ui
|
||||||
@ -164,26 +166,29 @@ pub(super) fn editor_view_ui(ui: &mut egui::Ui, app: &mut TextEditor) -> egui::R
|
|||||||
f32::INFINITY
|
f32::INFINITY
|
||||||
};
|
};
|
||||||
|
|
||||||
// Determine the language for syntax highlighting
|
|
||||||
let language = get_language_from_extension(active_tab.file_path.as_deref());
|
let language = get_language_from_extension(active_tab.file_path.as_deref());
|
||||||
|
|
||||||
// Create a code theme based on the current system theme visuals
|
|
||||||
let theme = create_code_theme_from_visuals(ui.visuals(), font_size);
|
let theme = create_code_theme_from_visuals(ui.visuals(), font_size);
|
||||||
|
|
||||||
let mut layouter = |ui: &egui::Ui, string: &dyn egui::TextBuffer, wrap_width: f32| {
|
let mut layouter = |ui: &egui::Ui, string: &dyn egui::TextBuffer, wrap_width: f32| {
|
||||||
let text = string.as_str();
|
let text = string.as_str();
|
||||||
let mut layout_job = if language == "txt" {
|
let mut layout_job = if syntax_highlighting_enabled && language != "txt" {
|
||||||
syntax_highlighting::highlight(ui.ctx(), &ui.style().clone(), &theme, text, "")
|
|
||||||
} else {
|
|
||||||
syntax_highlighting::highlight(ui.ctx(), &ui.style().clone(), &theme, text, &language)
|
syntax_highlighting::highlight(ui.ctx(), &ui.style().clone(), &theme, text, &language)
|
||||||
|
} else {
|
||||||
|
syntax_highlighting::highlight(ui.ctx(), &ui.style().clone(), &theme, text, "")
|
||||||
};
|
};
|
||||||
|
|
||||||
|
if syntax_highlighting_enabled && language != "txt" {
|
||||||
|
for section in &mut layout_job.sections {
|
||||||
|
section.format.font_id = font_id.clone();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
layout_job.wrap.max_width = wrap_width;
|
layout_job.wrap.max_width = wrap_width;
|
||||||
ui.fonts(|f| f.layout_job(layout_job))
|
ui.fonts(|f| f.layout_job(layout_job))
|
||||||
};
|
};
|
||||||
|
|
||||||
let text_edit = egui::TextEdit::multiline(&mut active_tab.content)
|
let text_edit = egui::TextEdit::multiline(&mut active_tab.content)
|
||||||
.frame(false)
|
.frame(false)
|
||||||
.font(egui::TextStyle::Monospace)
|
|
||||||
.code_editor()
|
.code_editor()
|
||||||
.desired_width(desired_width)
|
.desired_width(desired_width)
|
||||||
.desired_rows(0)
|
.desired_rows(0)
|
||||||
@ -248,11 +253,6 @@ pub(super) fn editor_view_ui(ui: &mut egui::Ui, app: &mut TextEditor) -> egui::R
|
|||||||
|
|
||||||
app.previous_content = content.to_owned();
|
app.previous_content = content.to_owned();
|
||||||
app.previous_cursor_char_index = current_cursor_pos;
|
app.previous_cursor_char_index = current_cursor_pos;
|
||||||
|
|
||||||
if let Some(active_tab) = app.get_active_tab_mut() {
|
|
||||||
active_tab.last_content_hash =
|
|
||||||
crate::app::tab::compute_content_hash(&active_tab.content, &mut active_tab.hasher);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if app.font_settings_changed || app.text_needs_processing {
|
if app.font_settings_changed || app.text_needs_processing {
|
||||||
|
|||||||
@ -185,6 +185,10 @@ pub(crate) fn menu_bar(app: &mut TextEditor, ctx: &egui::Context) {
|
|||||||
app.save_config();
|
app.save_config();
|
||||||
ui.close_kind(UiKind::Menu);
|
ui.close_kind(UiKind::Menu);
|
||||||
}
|
}
|
||||||
|
if ui.checkbox(&mut app.syntax_highlighting, "Syntax Highlighting").clicked() {
|
||||||
|
app.save_config();
|
||||||
|
ui.close_kind(UiKind::Menu);
|
||||||
|
}
|
||||||
if ui.checkbox(&mut app.word_wrap, "Word Wrap").clicked() {
|
if ui.checkbox(&mut app.word_wrap, "Word Wrap").clicked() {
|
||||||
app.save_config();
|
app.save_config();
|
||||||
ui.close_kind(UiKind::Menu);
|
ui.close_kind(UiKind::Menu);
|
||||||
@ -276,21 +280,15 @@ pub(crate) fn menu_bar(app: &mut TextEditor, ctx: &egui::Context) {
|
|||||||
|
|
||||||
if app.hide_tab_bar {
|
if app.hide_tab_bar {
|
||||||
let tab_title = if let Some(tab) = app.get_active_tab() {
|
let tab_title = if let Some(tab) = app.get_active_tab() {
|
||||||
tab.title.to_owned()
|
tab.get_display_title()
|
||||||
} else {
|
} else {
|
||||||
let empty_tab = crate::app::tab::Tab::new_empty(1);
|
let empty_tab = crate::app::tab::Tab::new_empty(1);
|
||||||
empty_tab.title.to_owned()
|
empty_tab.get_display_title()
|
||||||
};
|
};
|
||||||
|
|
||||||
let window_width = ctx.screen_rect().width();
|
let window_width = ctx.screen_rect().width();
|
||||||
let font_id = ui.style().text_styles[&egui::TextStyle::Body].to_owned();
|
let font_id = ui.style().text_styles[&egui::TextStyle::Body].to_owned();
|
||||||
|
|
||||||
let tab_title = if app.get_active_tab().is_some_and(|tab| tab.is_modified) {
|
|
||||||
format!("{tab_title}*")
|
|
||||||
} else {
|
|
||||||
tab_title
|
|
||||||
};
|
|
||||||
|
|
||||||
let text_galley = ui.fonts(|fonts| {
|
let text_galley = ui.fonts(|fonts| {
|
||||||
fonts.layout_job(egui::text::LayoutJob::simple_singleline(
|
fonts.layout_job(egui::text::LayoutJob::simple_singleline(
|
||||||
tab_title,
|
tab_title,
|
||||||
|
|||||||
@ -3,86 +3,92 @@ use eframe::egui::{self, Frame};
|
|||||||
|
|
||||||
pub(crate) fn tab_bar(app: &mut TextEditor, ctx: &egui::Context) {
|
pub(crate) fn tab_bar(app: &mut TextEditor, ctx: &egui::Context) {
|
||||||
let frame = Frame::NONE.fill(ctx.style().visuals.panel_fill);
|
let frame = Frame::NONE.fill(ctx.style().visuals.panel_fill);
|
||||||
let response = egui::TopBottomPanel::top("tab_bar")
|
let tab_bar = egui::TopBottomPanel::top("tab_bar")
|
||||||
.frame(frame)
|
.frame(frame)
|
||||||
.show(ctx, |ui| {
|
.show(ctx, |ui| {
|
||||||
ui.horizontal(|ui| {
|
egui::ScrollArea::horizontal()
|
||||||
let mut tab_to_close_unmodified = None;
|
.auto_shrink([false, true])
|
||||||
let mut tab_to_close_modified = None;
|
.scroll_bar_visibility(egui::scroll_area::ScrollBarVisibility::AlwaysHidden)
|
||||||
let mut tab_to_switch = None;
|
.scroll_source(egui::scroll_area::ScrollSource::DRAG)
|
||||||
let mut add_new_tab = false;
|
.show(ui, |ui| {
|
||||||
|
ui.horizontal(|ui| {
|
||||||
|
let mut tab_to_close_unmodified = None;
|
||||||
|
let mut tab_to_close_modified = None;
|
||||||
|
let mut tab_to_switch = None;
|
||||||
|
let mut add_new_tab = false;
|
||||||
|
|
||||||
let tabs_len = app.tabs.len();
|
let tabs_len = app.tabs.len();
|
||||||
let active_tab_index = app.active_tab_index;
|
let active_tab_index = app.active_tab_index;
|
||||||
|
|
||||||
let tabs_info: Vec<(String, bool)> = app
|
let tabs_info: Vec<(String, bool)> = app
|
||||||
.tabs
|
.tabs
|
||||||
.iter()
|
.iter()
|
||||||
.map(|tab| (tab.get_display_title(), tab.is_modified))
|
.map(|tab| (tab.get_display_title(), tab.is_modified))
|
||||||
.collect();
|
.collect();
|
||||||
|
|
||||||
for (i, (title, is_modified)) in tabs_info.iter().enumerate() {
|
for (i, (title, is_modified)) in tabs_info.iter().enumerate() {
|
||||||
let is_active = i == active_tab_index;
|
let is_active = i == active_tab_index;
|
||||||
|
|
||||||
let mut label_text = if is_active {
|
let mut label_text = if is_active {
|
||||||
egui::RichText::new(title).strong()
|
egui::RichText::new(title).strong()
|
||||||
} else {
|
} else {
|
||||||
egui::RichText::new(title).color(ui.visuals().weak_text_color())
|
egui::RichText::new(title).color(ui.visuals().weak_text_color())
|
||||||
};
|
};
|
||||||
|
|
||||||
if *is_modified {
|
if *is_modified {
|
||||||
label_text = label_text.italics();
|
label_text = label_text.italics();
|
||||||
}
|
}
|
||||||
|
|
||||||
let tab_response =
|
let tab_response = ui.add(egui::Label::new(label_text).selectable(false).sense(egui::Sense::click()));
|
||||||
ui.add(egui::Label::new(label_text).sense(egui::Sense::click()));
|
if tab_response.clicked() {
|
||||||
if tab_response.clicked() {
|
tab_to_switch = Some(i);
|
||||||
tab_to_switch = Some(i);
|
}
|
||||||
}
|
|
||||||
|
if tabs_len > 1 {
|
||||||
|
let visuals = ui.visuals();
|
||||||
|
let close_button = egui::Button::new("×")
|
||||||
|
.small()
|
||||||
|
.fill(visuals.panel_fill)
|
||||||
|
.stroke(egui::Stroke::new(0.0, egui::Color32::from_rgb(0, 0, 0)));
|
||||||
|
let close_response = ui.add(close_button);
|
||||||
|
if close_response.clicked() {
|
||||||
|
if *is_modified {
|
||||||
|
tab_to_close_modified = Some(i);
|
||||||
|
} else {
|
||||||
|
tab_to_close_unmodified = Some(i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ui.separator();
|
||||||
|
}
|
||||||
|
|
||||||
if tabs_len > 1 {
|
|
||||||
let visuals = ui.visuals();
|
let visuals = ui.visuals();
|
||||||
let close_button = egui::Button::new("×")
|
let add_button = egui::Button::new("+")
|
||||||
.small()
|
.small()
|
||||||
.fill(visuals.panel_fill)
|
.fill(visuals.panel_fill)
|
||||||
.stroke(egui::Stroke::new(0.0, egui::Color32::from_rgb(0, 0, 0)));
|
.stroke(egui::Stroke::new(0.0, egui::Color32::from_rgb(0, 0, 0)));
|
||||||
let close_response = ui.add(close_button);
|
if ui.add(add_button).clicked() {
|
||||||
if close_response.clicked() {
|
add_new_tab = true;
|
||||||
if *is_modified {
|
|
||||||
tab_to_close_modified = Some(i);
|
|
||||||
} else {
|
|
||||||
tab_to_close_unmodified = Some(i);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
ui.separator();
|
if let Some(tab_index) = tab_to_switch {
|
||||||
}
|
app.switch_to_tab(tab_index);
|
||||||
|
}
|
||||||
let visuals = ui.visuals();
|
if let Some(tab_index) = tab_to_close_unmodified {
|
||||||
let add_button = egui::Button::new("+")
|
app.close_tab(tab_index);
|
||||||
.small()
|
}
|
||||||
.fill(visuals.panel_fill)
|
if let Some(tab_index) = tab_to_close_modified {
|
||||||
.stroke(egui::Stroke::new(0.0, egui::Color32::from_rgb(0, 0, 0)));
|
app.switch_to_tab(tab_index);
|
||||||
if ui.add(add_button).clicked() {
|
app.pending_unsaved_action = Some(UnsavedAction::CloseTab(tab_index));
|
||||||
add_new_tab = true;
|
}
|
||||||
}
|
if add_new_tab {
|
||||||
|
app.add_new_tab();
|
||||||
if let Some(tab_index) = tab_to_switch {
|
}
|
||||||
app.switch_to_tab(tab_index);
|
});
|
||||||
}
|
});
|
||||||
if let Some(tab_index) = tab_to_close_unmodified {
|
|
||||||
app.close_tab(tab_index);
|
|
||||||
}
|
|
||||||
if let Some(tab_index) = tab_to_close_modified {
|
|
||||||
app.switch_to_tab(tab_index);
|
|
||||||
app.pending_unsaved_action = Some(UnsavedAction::CloseTab(tab_index));
|
|
||||||
}
|
|
||||||
if add_new_tab {
|
|
||||||
app.add_new_tab();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
app.tab_bar_rect = Some(response.response.rect);
|
app.tab_bar_rect = Some(tab_bar.response.rect);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user