Minor Tooling and UI Improvements (#1314)
* [wip]fix: disable fill and gradient tools on bmp images - aims to fix #1161 * [wip]fix: disable gradient tool for bmp images * fix: disable gradient tool for bitmap images - fixes https://github.com/GraphiteEditor/Graphite/issues/1161 * [wip]fix: disable menu bar elements if no open document * [WIP]feat: render certain menubar elements if document is open * fix: conditional menu bar rendering fixes - update menu bar on certain document actions - fix menu bar order on rendering all elements * refactor: change conditional menu elements property - use existing 'disabled' property * feat: render menu dropdown items conditionally * fix: revert formatter whitespace changes * refactor: improve variable naming and message usage - name menu bar bool flag better - use SendLayout message and remove unneeded calls
This commit is contained in:
parent
173398ad55
commit
9c2520111d
|
|
@ -37,12 +37,14 @@ pub struct MenuBarEntry {
|
||||||
pub shortcut: Option<ActionKeys>,
|
pub shortcut: Option<ActionKeys>,
|
||||||
pub action: WidgetHolder,
|
pub action: WidgetHolder,
|
||||||
pub children: MenuBarEntryChildren,
|
pub children: MenuBarEntryChildren,
|
||||||
|
pub disabled: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl MenuBarEntry {
|
impl MenuBarEntry {
|
||||||
pub fn new_root(label: String, children: MenuBarEntryChildren) -> Self {
|
pub fn new_root(label: String, disabled: bool, children: MenuBarEntryChildren) -> Self {
|
||||||
Self {
|
Self {
|
||||||
label,
|
label,
|
||||||
|
disabled,
|
||||||
children,
|
children,
|
||||||
..Default::default()
|
..Default::default()
|
||||||
}
|
}
|
||||||
|
|
@ -67,6 +69,7 @@ impl Default for MenuBarEntry {
|
||||||
shortcut: None,
|
shortcut: None,
|
||||||
action: MenuBarEntry::no_action(),
|
action: MenuBarEntry::no_action(),
|
||||||
children: MenuBarEntryChildren::empty(),
|
children: MenuBarEntryChildren::empty(),
|
||||||
|
disabled: false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -6,12 +6,15 @@ use crate::messages::portfolio::document::utility_types::clipboards::Clipboard;
|
||||||
use crate::messages::prelude::*;
|
use crate::messages::prelude::*;
|
||||||
|
|
||||||
#[derive(Debug, Clone, Default)]
|
#[derive(Debug, Clone, Default)]
|
||||||
pub struct MenuBarMessageHandler {}
|
pub struct MenuBarMessageHandler {
|
||||||
|
no_active_document: bool,
|
||||||
|
}
|
||||||
|
|
||||||
impl MessageHandler<MenuBarMessage, ()> for MenuBarMessageHandler {
|
impl MessageHandler<MenuBarMessage, bool> for MenuBarMessageHandler {
|
||||||
#[remain::check]
|
#[remain::check]
|
||||||
fn process_message(&mut self, message: MenuBarMessage, responses: &mut VecDeque<Message>, _data: ()) {
|
fn process_message(&mut self, message: MenuBarMessage, responses: &mut VecDeque<Message>, has_active_document: bool) {
|
||||||
use MenuBarMessage::*;
|
use MenuBarMessage::*;
|
||||||
|
self.no_active_document = !has_active_document;
|
||||||
|
|
||||||
#[remain::sorted]
|
#[remain::sorted]
|
||||||
match message {
|
match message {
|
||||||
|
|
@ -26,75 +29,13 @@ impl MessageHandler<MenuBarMessage, ()> for MenuBarMessageHandler {
|
||||||
|
|
||||||
impl PropertyHolder for MenuBarMessageHandler {
|
impl PropertyHolder for MenuBarMessageHandler {
|
||||||
fn properties(&self) -> Layout {
|
fn properties(&self) -> Layout {
|
||||||
Layout::MenuLayout(MenuLayout::new(vec![
|
let no_active_document = self.no_active_document;
|
||||||
MenuBarEntry {
|
|
||||||
icon: Some("GraphiteLogo".into()),
|
// enable these only if there's an active document
|
||||||
action: MenuBarEntry::create_action(|_| FrontendMessage::TriggerVisitLink { url: "https://graphite.rs".into() }.into()),
|
let conditional_menu_entries = vec![
|
||||||
..Default::default()
|
|
||||||
},
|
|
||||||
MenuBarEntry::new_root(
|
|
||||||
"File".into(),
|
|
||||||
MenuBarEntryChildren(vec![
|
|
||||||
vec![
|
|
||||||
MenuBarEntry {
|
|
||||||
label: "New…".into(),
|
|
||||||
icon: Some("File".into()),
|
|
||||||
action: MenuBarEntry::create_action(|_| DialogMessage::RequestNewDocumentDialog.into()),
|
|
||||||
shortcut: action_keys!(DialogMessageDiscriminant::RequestNewDocumentDialog),
|
|
||||||
children: MenuBarEntryChildren::empty(),
|
|
||||||
},
|
|
||||||
MenuBarEntry {
|
|
||||||
label: "Open…".into(),
|
|
||||||
shortcut: action_keys!(PortfolioMessageDiscriminant::OpenDocument),
|
|
||||||
action: MenuBarEntry::create_action(|_| PortfolioMessage::OpenDocument.into()),
|
|
||||||
..MenuBarEntry::default()
|
|
||||||
},
|
|
||||||
],
|
|
||||||
vec![
|
|
||||||
MenuBarEntry {
|
|
||||||
label: "Close".into(),
|
|
||||||
shortcut: action_keys!(PortfolioMessageDiscriminant::CloseActiveDocumentWithConfirmation),
|
|
||||||
action: MenuBarEntry::create_action(|_| PortfolioMessage::CloseActiveDocumentWithConfirmation.into()),
|
|
||||||
..MenuBarEntry::default()
|
|
||||||
},
|
|
||||||
MenuBarEntry {
|
|
||||||
label: "Close All".into(),
|
|
||||||
shortcut: action_keys!(DialogMessageDiscriminant::CloseAllDocumentsWithConfirmation),
|
|
||||||
action: MenuBarEntry::create_action(|_| DialogMessage::CloseAllDocumentsWithConfirmation.into()),
|
|
||||||
..MenuBarEntry::default()
|
|
||||||
},
|
|
||||||
],
|
|
||||||
vec![MenuBarEntry {
|
|
||||||
label: "Save".into(),
|
|
||||||
shortcut: action_keys!(DocumentMessageDiscriminant::SaveDocument),
|
|
||||||
action: MenuBarEntry::create_action(|_| DocumentMessage::SaveDocument.into()),
|
|
||||||
..MenuBarEntry::default()
|
|
||||||
}],
|
|
||||||
vec![
|
|
||||||
MenuBarEntry {
|
|
||||||
label: "Import…".into(),
|
|
||||||
shortcut: action_keys!(PortfolioMessageDiscriminant::Import),
|
|
||||||
action: MenuBarEntry::create_action(|_| PortfolioMessage::Import.into()),
|
|
||||||
..MenuBarEntry::default()
|
|
||||||
},
|
|
||||||
MenuBarEntry {
|
|
||||||
label: "Export…".into(),
|
|
||||||
shortcut: action_keys!(DialogMessageDiscriminant::RequestExportDialog),
|
|
||||||
action: MenuBarEntry::create_action(|_| DialogMessage::RequestExportDialog.into()),
|
|
||||||
..MenuBarEntry::default()
|
|
||||||
},
|
|
||||||
],
|
|
||||||
vec![MenuBarEntry {
|
|
||||||
label: "Preferences…".into(),
|
|
||||||
icon: Some("Settings".into()),
|
|
||||||
shortcut: action_keys!(DialogMessageDiscriminant::RequestPreferencesDialog),
|
|
||||||
action: MenuBarEntry::create_action(|_| DialogMessage::RequestPreferencesDialog.into()),
|
|
||||||
..MenuBarEntry::default()
|
|
||||||
}],
|
|
||||||
]),
|
|
||||||
),
|
|
||||||
MenuBarEntry::new_root(
|
MenuBarEntry::new_root(
|
||||||
"Edit".into(),
|
"Edit".into(),
|
||||||
|
no_active_document,
|
||||||
MenuBarEntryChildren(vec![
|
MenuBarEntryChildren(vec![
|
||||||
vec![
|
vec![
|
||||||
MenuBarEntry {
|
MenuBarEntry {
|
||||||
|
|
@ -136,6 +77,7 @@ impl PropertyHolder for MenuBarMessageHandler {
|
||||||
),
|
),
|
||||||
MenuBarEntry::new_root(
|
MenuBarEntry::new_root(
|
||||||
"Layer".into(),
|
"Layer".into(),
|
||||||
|
no_active_document,
|
||||||
MenuBarEntryChildren(vec![
|
MenuBarEntryChildren(vec![
|
||||||
vec![
|
vec![
|
||||||
MenuBarEntry {
|
MenuBarEntry {
|
||||||
|
|
@ -213,6 +155,7 @@ impl PropertyHolder for MenuBarMessageHandler {
|
||||||
),
|
),
|
||||||
MenuBarEntry::new_root(
|
MenuBarEntry::new_root(
|
||||||
"Document".into(),
|
"Document".into(),
|
||||||
|
no_active_document,
|
||||||
MenuBarEntryChildren(vec![vec![MenuBarEntry {
|
MenuBarEntryChildren(vec![vec![MenuBarEntry {
|
||||||
label: "Clear Artboards".into(),
|
label: "Clear Artboards".into(),
|
||||||
action: MenuBarEntry::create_action(|_| ArtboardMessage::ClearArtboards.into()),
|
action: MenuBarEntry::create_action(|_| ArtboardMessage::ClearArtboards.into()),
|
||||||
|
|
@ -221,6 +164,7 @@ impl PropertyHolder for MenuBarMessageHandler {
|
||||||
),
|
),
|
||||||
MenuBarEntry::new_root(
|
MenuBarEntry::new_root(
|
||||||
"View".into(),
|
"View".into(),
|
||||||
|
no_active_document,
|
||||||
MenuBarEntryChildren(vec![vec![
|
MenuBarEntryChildren(vec![vec![
|
||||||
MenuBarEntry {
|
MenuBarEntry {
|
||||||
label: "Zoom to Selected".into(),
|
label: "Zoom to Selected".into(),
|
||||||
|
|
@ -248,8 +192,84 @@ impl PropertyHolder for MenuBarMessageHandler {
|
||||||
},
|
},
|
||||||
]]),
|
]]),
|
||||||
),
|
),
|
||||||
|
];
|
||||||
|
|
||||||
|
let mut menu_bar_entries = vec![
|
||||||
|
MenuBarEntry {
|
||||||
|
icon: Some("GraphiteLogo".into()),
|
||||||
|
action: MenuBarEntry::create_action(|_| FrontendMessage::TriggerVisitLink { url: "https://graphite.rs".into() }.into()),
|
||||||
|
..Default::default()
|
||||||
|
},
|
||||||
|
MenuBarEntry::new_root(
|
||||||
|
"File".into(),
|
||||||
|
false,
|
||||||
|
MenuBarEntryChildren(vec![
|
||||||
|
vec![
|
||||||
|
MenuBarEntry {
|
||||||
|
label: "New…".into(),
|
||||||
|
icon: Some("File".into()),
|
||||||
|
action: MenuBarEntry::create_action(|_| DialogMessage::RequestNewDocumentDialog.into()),
|
||||||
|
shortcut: action_keys!(DialogMessageDiscriminant::RequestNewDocumentDialog),
|
||||||
|
children: MenuBarEntryChildren::empty(),
|
||||||
|
..MenuBarEntry::default()
|
||||||
|
},
|
||||||
|
MenuBarEntry {
|
||||||
|
label: "Open…".into(),
|
||||||
|
shortcut: action_keys!(PortfolioMessageDiscriminant::OpenDocument),
|
||||||
|
action: MenuBarEntry::create_action(|_| PortfolioMessage::OpenDocument.into()),
|
||||||
|
..MenuBarEntry::default()
|
||||||
|
},
|
||||||
|
],
|
||||||
|
vec![
|
||||||
|
MenuBarEntry {
|
||||||
|
label: "Close".into(),
|
||||||
|
shortcut: action_keys!(PortfolioMessageDiscriminant::CloseActiveDocumentWithConfirmation),
|
||||||
|
action: MenuBarEntry::create_action(|_| PortfolioMessage::CloseActiveDocumentWithConfirmation.into()),
|
||||||
|
disabled: no_active_document,
|
||||||
|
..MenuBarEntry::default()
|
||||||
|
},
|
||||||
|
MenuBarEntry {
|
||||||
|
label: "Close All".into(),
|
||||||
|
shortcut: action_keys!(DialogMessageDiscriminant::CloseAllDocumentsWithConfirmation),
|
||||||
|
action: MenuBarEntry::create_action(|_| DialogMessage::CloseAllDocumentsWithConfirmation.into()),
|
||||||
|
disabled: no_active_document,
|
||||||
|
..MenuBarEntry::default()
|
||||||
|
},
|
||||||
|
],
|
||||||
|
vec![MenuBarEntry {
|
||||||
|
label: "Save".into(),
|
||||||
|
shortcut: action_keys!(DocumentMessageDiscriminant::SaveDocument),
|
||||||
|
action: MenuBarEntry::create_action(|_| DocumentMessage::SaveDocument.into()),
|
||||||
|
disabled: no_active_document,
|
||||||
|
..MenuBarEntry::default()
|
||||||
|
}],
|
||||||
|
vec![
|
||||||
|
MenuBarEntry {
|
||||||
|
label: "Import…".into(),
|
||||||
|
shortcut: action_keys!(PortfolioMessageDiscriminant::Import),
|
||||||
|
action: MenuBarEntry::create_action(|_| PortfolioMessage::Import.into()),
|
||||||
|
..MenuBarEntry::default()
|
||||||
|
},
|
||||||
|
MenuBarEntry {
|
||||||
|
label: "Export…".into(),
|
||||||
|
shortcut: action_keys!(DialogMessageDiscriminant::RequestExportDialog),
|
||||||
|
action: MenuBarEntry::create_action(|_| DialogMessage::RequestExportDialog.into()),
|
||||||
|
disabled: no_active_document,
|
||||||
|
..MenuBarEntry::default()
|
||||||
|
},
|
||||||
|
],
|
||||||
|
vec![MenuBarEntry {
|
||||||
|
label: "Preferences…".into(),
|
||||||
|
icon: Some("Settings".into()),
|
||||||
|
shortcut: action_keys!(DialogMessageDiscriminant::RequestPreferencesDialog),
|
||||||
|
action: MenuBarEntry::create_action(|_| DialogMessage::RequestPreferencesDialog.into()),
|
||||||
|
..MenuBarEntry::default()
|
||||||
|
}],
|
||||||
|
]),
|
||||||
|
),
|
||||||
MenuBarEntry::new_root(
|
MenuBarEntry::new_root(
|
||||||
"Help".into(),
|
"Help".into(),
|
||||||
|
true,
|
||||||
MenuBarEntryChildren(vec![
|
MenuBarEntryChildren(vec![
|
||||||
vec![MenuBarEntry {
|
vec![MenuBarEntry {
|
||||||
label: "About Graphite".into(),
|
label: "About Graphite".into(),
|
||||||
|
|
@ -327,6 +347,11 @@ impl PropertyHolder for MenuBarMessageHandler {
|
||||||
],
|
],
|
||||||
]),
|
]),
|
||||||
),
|
),
|
||||||
]))
|
];
|
||||||
|
|
||||||
|
if !no_active_document {
|
||||||
|
menu_bar_entries.splice(2..2, conditional_menu_entries);
|
||||||
|
}
|
||||||
|
Layout::MenuLayout(MenuLayout::new(menu_bar_entries))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -33,11 +33,13 @@ pub struct PortfolioMessageHandler {
|
||||||
impl MessageHandler<PortfolioMessage, (&InputPreprocessorMessageHandler, &PreferencesMessageHandler)> for PortfolioMessageHandler {
|
impl MessageHandler<PortfolioMessage, (&InputPreprocessorMessageHandler, &PreferencesMessageHandler)> for PortfolioMessageHandler {
|
||||||
#[remain::check]
|
#[remain::check]
|
||||||
fn process_message(&mut self, message: PortfolioMessage, responses: &mut VecDeque<Message>, (ipp, preferences): (&InputPreprocessorMessageHandler, &PreferencesMessageHandler)) {
|
fn process_message(&mut self, message: PortfolioMessage, responses: &mut VecDeque<Message>, (ipp, preferences): (&InputPreprocessorMessageHandler, &PreferencesMessageHandler)) {
|
||||||
|
let has_active_document = self.active_document_id.is_some();
|
||||||
|
|
||||||
#[remain::sorted]
|
#[remain::sorted]
|
||||||
match message {
|
match message {
|
||||||
// Sub-messages
|
// Sub-messages
|
||||||
#[remain::unsorted]
|
#[remain::unsorted]
|
||||||
PortfolioMessage::MenuBar(message) => self.menu_bar_message_handler.process_message(message, responses, ()),
|
PortfolioMessage::MenuBar(message) => self.menu_bar_message_handler.process_message(message, responses, has_active_document),
|
||||||
#[remain::unsorted]
|
#[remain::unsorted]
|
||||||
PortfolioMessage::Document(message) => {
|
PortfolioMessage::Document(message) => {
|
||||||
if let Some(document_id) = self.active_document_id {
|
if let Some(document_id) = self.active_document_id {
|
||||||
|
|
@ -109,6 +111,7 @@ impl MessageHandler<PortfolioMessage, (&InputPreprocessorMessageHandler, &Prefer
|
||||||
let hint_data = HintData(vec![HintGroup(vec![])]);
|
let hint_data = HintData(vec![HintGroup(vec![])]);
|
||||||
responses.add(FrontendMessage::UpdateInputHints { hint_data });
|
responses.add(FrontendMessage::UpdateInputHints { hint_data });
|
||||||
}
|
}
|
||||||
|
|
||||||
// Actually delete the document (delay to delete document is required to let the document and properties panel messages above get processed)
|
// Actually delete the document (delay to delete document is required to let the document and properties panel messages above get processed)
|
||||||
responses.add(PortfolioMessage::DeleteDocument { document_id });
|
responses.add(PortfolioMessage::DeleteDocument { document_id });
|
||||||
|
|
||||||
|
|
@ -179,6 +182,7 @@ impl MessageHandler<PortfolioMessage, (&InputPreprocessorMessageHandler, &Prefer
|
||||||
|
|
||||||
if self.document_ids.is_empty() {
|
if self.document_ids.is_empty() {
|
||||||
self.active_document_id = None;
|
self.active_document_id = None;
|
||||||
|
responses.add(MenuBarMessage::SendLayout);
|
||||||
} else if self.active_document_id.is_some() {
|
} else if self.active_document_id.is_some() {
|
||||||
let document_id = if document_index == self.document_ids.len() {
|
let document_id = if document_index == self.document_ids.len() {
|
||||||
// If we closed the last document take the one previous (same as last)
|
// If we closed the last document take the one previous (same as last)
|
||||||
|
|
@ -195,6 +199,7 @@ impl MessageHandler<PortfolioMessage, (&InputPreprocessorMessageHandler, &Prefer
|
||||||
self.documents.clear();
|
self.documents.clear();
|
||||||
self.document_ids.clear();
|
self.document_ids.clear();
|
||||||
self.active_document_id = None;
|
self.active_document_id = None;
|
||||||
|
responses.add(MenuBarMessage::SendLayout);
|
||||||
}
|
}
|
||||||
PortfolioMessage::FontLoaded {
|
PortfolioMessage::FontLoaded {
|
||||||
font_family,
|
font_family,
|
||||||
|
|
@ -462,7 +467,10 @@ impl MessageHandler<PortfolioMessage, (&InputPreprocessorMessageHandler, &Prefer
|
||||||
responses.add(PortfolioMessage::UpdateDocumentWidgets);
|
responses.add(PortfolioMessage::UpdateDocumentWidgets);
|
||||||
responses.add(NavigationMessage::TranslateCanvas { delta: (0., 0.).into() });
|
responses.add(NavigationMessage::TranslateCanvas { delta: (0., 0.).into() });
|
||||||
}
|
}
|
||||||
PortfolioMessage::SetActiveDocument { document_id } => self.active_document_id = Some(document_id),
|
PortfolioMessage::SetActiveDocument { document_id } => {
|
||||||
|
self.active_document_id = Some(document_id);
|
||||||
|
responses.add(MenuBarMessage::SendLayout);
|
||||||
|
}
|
||||||
PortfolioMessage::SetImageBlobUrl {
|
PortfolioMessage::SetImageBlobUrl {
|
||||||
document_id,
|
document_id,
|
||||||
layer_path,
|
layer_path,
|
||||||
|
|
|
||||||
|
|
@ -7,6 +7,7 @@ use crate::messages::tool::utility_types::{EventToMessageMap, Fsm, ToolActionHan
|
||||||
use crate::messages::tool::utility_types::{HintData, HintGroup, HintInfo};
|
use crate::messages::tool::utility_types::{HintData, HintGroup, HintInfo};
|
||||||
|
|
||||||
use document_legacy::intersection::Quad;
|
use document_legacy::intersection::Quad;
|
||||||
|
use document_legacy::layers::layer_layer::CachedOutputData;
|
||||||
use document_legacy::layers::style::Fill;
|
use document_legacy::layers::style::Fill;
|
||||||
|
|
||||||
use glam::DVec2;
|
use glam::DVec2;
|
||||||
|
|
@ -103,6 +104,17 @@ impl Fsm for FillToolFsmState {
|
||||||
let quad = Quad::from_box([mouse_pos - tolerance, mouse_pos + tolerance]);
|
let quad = Quad::from_box([mouse_pos - tolerance, mouse_pos + tolerance]);
|
||||||
|
|
||||||
if let Some(path) = document.document_legacy.intersects_quad_root(quad, render_data).last() {
|
if let Some(path) = document.document_legacy.intersects_quad_root(quad, render_data).last() {
|
||||||
|
let is_bitmap = document
|
||||||
|
.document_legacy
|
||||||
|
.layer(path)
|
||||||
|
.ok()
|
||||||
|
.and_then(|layer| layer.as_layer().ok())
|
||||||
|
.map_or(false, |layer| matches!(layer.cached_output_data, CachedOutputData::BlobURL(_) | CachedOutputData::SurfaceId(_)));
|
||||||
|
|
||||||
|
if is_bitmap {
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
|
||||||
let color = match lmb_or_rmb {
|
let color = match lmb_or_rmb {
|
||||||
LeftPointerDown => global_tool_data.primary_color,
|
LeftPointerDown => global_tool_data.primary_color,
|
||||||
RightPointerDown => global_tool_data.secondary_color,
|
RightPointerDown => global_tool_data.secondary_color,
|
||||||
|
|
|
||||||
|
|
@ -11,6 +11,7 @@ use crate::messages::tool::utility_types::{HintData, HintGroup, HintInfo};
|
||||||
|
|
||||||
use document_legacy::intersection::Quad;
|
use document_legacy::intersection::Quad;
|
||||||
use document_legacy::layers::layer_info::Layer;
|
use document_legacy::layers::layer_info::Layer;
|
||||||
|
use document_legacy::layers::layer_layer::CachedOutputData;
|
||||||
use document_legacy::layers::style::{Fill, Gradient, GradientType, PathStyle, RenderData, Stroke};
|
use document_legacy::layers::style::{Fill, Gradient, GradientType, PathStyle, RenderData, Stroke};
|
||||||
use document_legacy::LayerId;
|
use document_legacy::LayerId;
|
||||||
use document_legacy::Operation;
|
use document_legacy::Operation;
|
||||||
|
|
@ -420,9 +421,6 @@ impl Fsm for GradientToolFsmState {
|
||||||
}
|
}
|
||||||
|
|
||||||
for path in document.selected_visible_layers() {
|
for path in document.selected_visible_layers() {
|
||||||
if !document.document_legacy.multiply_transforms(path).unwrap().inverse().is_finite() {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
let layer = document.document_legacy.layer(path).unwrap();
|
let layer = document.document_legacy.layer(path).unwrap();
|
||||||
|
|
||||||
if let Ok(Fill::Gradient(gradient)) = layer.style().map(|style| style.fill()) {
|
if let Ok(Fill::Gradient(gradient)) = layer.style().map(|style| style.fill()) {
|
||||||
|
|
@ -568,7 +566,18 @@ impl Fsm for GradientToolFsmState {
|
||||||
let quad = Quad::from_box([input.mouse.position - tolerance, input.mouse.position + tolerance]);
|
let quad = Quad::from_box([input.mouse.position - tolerance, input.mouse.position + tolerance]);
|
||||||
let intersection = document.document_legacy.intersects_quad_root(quad, render_data).pop();
|
let intersection = document.document_legacy.intersects_quad_root(quad, render_data).pop();
|
||||||
|
|
||||||
|
// the intersection is the layer where the gradient is being applied
|
||||||
if let Some(intersection) = intersection {
|
if let Some(intersection) = intersection {
|
||||||
|
let is_bitmap = document
|
||||||
|
.document_legacy
|
||||||
|
.layer(&intersection)
|
||||||
|
.ok()
|
||||||
|
.and_then(|layer| layer.as_layer().ok())
|
||||||
|
.map_or(false, |layer| matches!(layer.cached_output_data, CachedOutputData::BlobURL(_) | CachedOutputData::SurfaceId(_)));
|
||||||
|
if is_bitmap {
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
|
||||||
if !document.selected_layers_contains(&intersection) {
|
if !document.selected_layers_contains(&intersection) {
|
||||||
let replacement_selected_layers = vec![intersection.clone()];
|
let replacement_selected_layers = vec![intersection.clone()];
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -63,7 +63,7 @@
|
||||||
// New fields in `MenuListEntry`
|
// New fields in `MenuListEntry`
|
||||||
shortcutRequiresLock: entry.shortcut ? shortcutRequiresLock(entry.shortcut.keys) : undefined,
|
shortcutRequiresLock: entry.shortcut ? shortcutRequiresLock(entry.shortcut.keys) : undefined,
|
||||||
value: undefined,
|
value: undefined,
|
||||||
disabled: undefined,
|
disabled: entry.disabled ?? undefined,
|
||||||
font: undefined,
|
font: undefined,
|
||||||
ref: undefined,
|
ref: undefined,
|
||||||
});
|
});
|
||||||
|
|
|
||||||
|
|
@ -774,6 +774,7 @@ type MenuEntryCommon = {
|
||||||
export type MenuBarEntry = MenuEntryCommon & {
|
export type MenuBarEntry = MenuEntryCommon & {
|
||||||
action: Widget;
|
action: Widget;
|
||||||
children?: MenuBarEntry[][];
|
children?: MenuBarEntry[][];
|
||||||
|
disabled?: boolean,
|
||||||
};
|
};
|
||||||
|
|
||||||
// An entry in the all-encompassing MenuList component which defines all types of menus ranging from `MenuBarInput` to `DropdownInput` widgets
|
// An entry in the all-encompassing MenuList component which defines all types of menus ranging from `MenuBarInput` to `DropdownInput` widgets
|
||||||
|
|
@ -1300,6 +1301,7 @@ function createMenuLayoutRecursive(children: any[][]): MenuBarEntry[][] {
|
||||||
...entry,
|
...entry,
|
||||||
action: hoistWidgetHolders([entry.action])[0],
|
action: hoistWidgetHolders([entry.action])[0],
|
||||||
children: entry.children ? createMenuLayoutRecursive(entry.children) : undefined,
|
children: entry.children ? createMenuLayoutRecursive(entry.children) : undefined,
|
||||||
|
disabled: entry.disabled ?? false,
|
||||||
}))
|
}))
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue