mirror of
https://github.com/GraphiteEditor/Graphite.git
synced 2026-09-30 16:38:12 +08:00
integrated grid shape in shape-tool
This commit is contained in:
Vendored
+2
-1
@@ -52,5 +52,6 @@
|
|||||||
"files.insertFinalNewline": true,
|
"files.insertFinalNewline": true,
|
||||||
"files.associations": {
|
"files.associations": {
|
||||||
"*.graphite": "json"
|
"*.graphite": "json"
|
||||||
}
|
},
|
||||||
|
"rust-analyzer.checkOnSave": false
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -356,6 +356,10 @@ pub fn get_text_id(layer: LayerNodeIdentifier, network_interface: &NodeNetworkIn
|
|||||||
NodeGraphLayer::new(layer, network_interface).upstream_node_id_from_name("Text")
|
NodeGraphLayer::new(layer, network_interface).upstream_node_id_from_name("Text")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn get_grid_id(layer: LayerNodeIdentifier, network_interface: &NodeNetworkInterface) -> Option<NodeId> {
|
||||||
|
NodeGraphLayer::new(layer, network_interface).upstream_node_id_from_name("Grid")
|
||||||
|
}
|
||||||
|
|
||||||
/// Gets properties from the Text node
|
/// Gets properties from the Text node
|
||||||
pub fn get_text(layer: LayerNodeIdentifier, network_interface: &NodeNetworkInterface) -> Option<(&String, &Font, TypesettingConfig, bool)> {
|
pub fn get_text(layer: LayerNodeIdentifier, network_interface: &NodeNetworkInterface) -> Option<(&String, &Font, TypesettingConfig, bool)> {
|
||||||
let inputs = NodeGraphLayer::new(layer, network_interface).find_node_inputs("Text")?;
|
let inputs = NodeGraphLayer::new(layer, network_interface).find_node_inputs("Text")?;
|
||||||
|
|||||||
@@ -0,0 +1,179 @@
|
|||||||
|
use super::shape_utility::ShapeToolModifierKey;
|
||||||
|
use super::shape_utility::update_radius_sign;
|
||||||
|
use super::*;
|
||||||
|
use crate::messages::portfolio::document::graph_operation::utility_types::TransformIn;
|
||||||
|
use crate::messages::portfolio::document::node_graph::document_node_definitions::resolve_document_node_type;
|
||||||
|
use crate::messages::portfolio::document::overlays::utility_types::OverlayContext;
|
||||||
|
use crate::messages::portfolio::document::utility_types::document_metadata::LayerNodeIdentifier;
|
||||||
|
use crate::messages::portfolio::document::utility_types::network_interface::{InputConnector, NodeTemplate};
|
||||||
|
use crate::messages::tool::common_functionality::gizmos::shape_gizmos::number_of_points_dial::NumberOfPointsDial;
|
||||||
|
use crate::messages::tool::common_functionality::gizmos::shape_gizmos::number_of_points_dial::NumberOfPointsDialState;
|
||||||
|
use crate::messages::tool::common_functionality::gizmos::shape_gizmos::point_radius_handle::PointRadiusHandle;
|
||||||
|
use crate::messages::tool::common_functionality::gizmos::shape_gizmos::point_radius_handle::PointRadiusHandleState;
|
||||||
|
use crate::messages::tool::common_functionality::graph_modification_utils;
|
||||||
|
use crate::messages::tool::common_functionality::shape_editor::ShapeState;
|
||||||
|
use crate::messages::tool::common_functionality::shapes::shape_utility::ShapeGizmoHandler;
|
||||||
|
use crate::messages::tool::common_functionality::shapes::shape_utility::polygon_outline;
|
||||||
|
use crate::messages::tool::tool_messages::tool_prelude::*;
|
||||||
|
use glam::DAffine2;
|
||||||
|
use graph_craft::document::NodeInput;
|
||||||
|
use graph_craft::document::value::TaggedValue;
|
||||||
|
use graphene_std::vector::misc::GridType;
|
||||||
|
use std::collections::VecDeque;
|
||||||
|
|
||||||
|
// #[derive(Clone, Debug, Default)]
|
||||||
|
// pub struct PolygonGizmoHandler {
|
||||||
|
// number_of_points_dial: NumberOfPointsDial,
|
||||||
|
// point_radius_handle: PointRadiusHandle,
|
||||||
|
// }
|
||||||
|
|
||||||
|
// impl ShapeGizmoHandler for PolygonGizmoHandler {
|
||||||
|
// fn is_any_gizmo_hovered(&self) -> bool {
|
||||||
|
// self.number_of_points_dial.is_hovering() || self.point_radius_handle.hovered()
|
||||||
|
// }
|
||||||
|
|
||||||
|
// fn handle_state(&mut self, selected_star_layer: LayerNodeIdentifier, mouse_position: DVec2, document: &DocumentMessageHandler, responses: &mut VecDeque<Message>) {
|
||||||
|
// self.number_of_points_dial.handle_actions(selected_star_layer, mouse_position, document, responses);
|
||||||
|
// self.point_radius_handle.handle_actions(selected_star_layer, document, mouse_position, responses);
|
||||||
|
// }
|
||||||
|
|
||||||
|
// fn handle_click(&mut self) {
|
||||||
|
// if self.number_of_points_dial.is_hovering() {
|
||||||
|
// self.number_of_points_dial.update_state(NumberOfPointsDialState::Dragging);
|
||||||
|
// return;
|
||||||
|
// }
|
||||||
|
|
||||||
|
// if self.point_radius_handle.hovered() {
|
||||||
|
// self.point_radius_handle.update_state(PointRadiusHandleState::Dragging);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// fn handle_update(&mut self, drag_start: DVec2, document: &DocumentMessageHandler, input: &InputPreprocessorMessageHandler, responses: &mut VecDeque<Message>) {
|
||||||
|
// if self.number_of_points_dial.is_dragging() {
|
||||||
|
// self.number_of_points_dial.update_number_of_sides(document, input, responses, drag_start);
|
||||||
|
// }
|
||||||
|
|
||||||
|
// if self.point_radius_handle.is_dragging_or_snapped() {
|
||||||
|
// self.point_radius_handle.update_inner_radius(document, input, responses, drag_start);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// fn overlays(
|
||||||
|
// &self,
|
||||||
|
// document: &DocumentMessageHandler,
|
||||||
|
// selected_polygon_layer: Option<LayerNodeIdentifier>,
|
||||||
|
// input: &InputPreprocessorMessageHandler,
|
||||||
|
// shape_editor: &mut &mut ShapeState,
|
||||||
|
// mouse_position: DVec2,
|
||||||
|
// overlay_context: &mut OverlayContext,
|
||||||
|
// ) {
|
||||||
|
// self.number_of_points_dial.overlays(document, selected_polygon_layer, shape_editor, mouse_position, overlay_context);
|
||||||
|
// self.point_radius_handle.overlays(selected_polygon_layer, document, input, mouse_position, overlay_context);
|
||||||
|
|
||||||
|
// polygon_outline(selected_polygon_layer, document, overlay_context);
|
||||||
|
// }
|
||||||
|
|
||||||
|
// fn dragging_overlays(
|
||||||
|
// &self,
|
||||||
|
// document: &DocumentMessageHandler,
|
||||||
|
// input: &InputPreprocessorMessageHandler,
|
||||||
|
// shape_editor: &mut &mut ShapeState,
|
||||||
|
// mouse_position: DVec2,
|
||||||
|
// overlay_context: &mut OverlayContext,
|
||||||
|
// ) {
|
||||||
|
// if self.number_of_points_dial.is_dragging() {
|
||||||
|
// self.number_of_points_dial.overlays(document, None, shape_editor, mouse_position, overlay_context);
|
||||||
|
// }
|
||||||
|
|
||||||
|
// if self.point_radius_handle.is_dragging_or_snapped() {
|
||||||
|
// self.point_radius_handle.overlays(None, document, input, mouse_position, overlay_context);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// fn cleanup(&mut self) {
|
||||||
|
// self.number_of_points_dial.cleanup();
|
||||||
|
// self.point_radius_handle.cleanup();
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
#[derive(Default)]
|
||||||
|
pub struct Grid;
|
||||||
|
|
||||||
|
impl Grid {
|
||||||
|
pub fn create_node(grid_type: GridType) -> NodeTemplate {
|
||||||
|
let node_type = resolve_document_node_type("Grid").expect("Grid can't be found");
|
||||||
|
node_type.node_template_input_override([
|
||||||
|
None,
|
||||||
|
Some(NodeInput::value(TaggedValue::GridType(grid_type), false)),
|
||||||
|
Some(NodeInput::value(TaggedValue::DVec2(DVec2::ZERO), false)),
|
||||||
|
])
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn update_shape(
|
||||||
|
document: &DocumentMessageHandler,
|
||||||
|
ipp: &InputPreprocessorMessageHandler,
|
||||||
|
layer: LayerNodeIdentifier,
|
||||||
|
grid_type: GridType,
|
||||||
|
shape_tool_data: &mut ShapeToolData,
|
||||||
|
modifier: ShapeToolModifierKey,
|
||||||
|
responses: &mut VecDeque<Message>,
|
||||||
|
) {
|
||||||
|
let [center, lock_ratio, _, _] = modifier;
|
||||||
|
|
||||||
|
let start = shape_tool_data.data.viewport_drag_start(document);
|
||||||
|
let end = ipp.mouse.position;
|
||||||
|
|
||||||
|
let mut dimensions = (start - end).abs();
|
||||||
|
|
||||||
|
let mut translation = shape_tool_data.data.viewport_drag_start(document);
|
||||||
|
let mut scale = (end - start).signum();
|
||||||
|
|
||||||
|
match grid_type {
|
||||||
|
GridType::Rectangular => {
|
||||||
|
if ipp.keyboard.key(center) && ipp.keyboard.key(lock_ratio) {
|
||||||
|
let max = dimensions.x.max(dimensions.y);
|
||||||
|
let distance_to_make_center = max;
|
||||||
|
translation = shape_tool_data.data.viewport_drag_start(document) - distance_to_make_center;
|
||||||
|
dimensions = 2. * DVec2::splat(max) / 9.;
|
||||||
|
scale = DVec2::ONE;
|
||||||
|
} else if ipp.keyboard.key(lock_ratio) {
|
||||||
|
let max = dimensions.x.max(dimensions.y);
|
||||||
|
dimensions = DVec2::splat(max) / 9.
|
||||||
|
} else if ipp.keyboard.key(center) {
|
||||||
|
let distance_to_make_center = dimensions;
|
||||||
|
translation = shape_tool_data.data.viewport_drag_start(document) - distance_to_make_center;
|
||||||
|
dimensions = 2. * dimensions / 9.;
|
||||||
|
scale = DVec2::ONE;
|
||||||
|
} else {
|
||||||
|
dimensions = dimensions / 9.;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
GridType::Isometric => {
|
||||||
|
if ipp.keyboard.key(center) {
|
||||||
|
let distance_to_make_center = DVec2::splat(dimensions.y);
|
||||||
|
translation = shape_tool_data.data.viewport_drag_start(document) - distance_to_make_center;
|
||||||
|
dimensions = 2. * DVec2::splat(dimensions.y) / 9.;
|
||||||
|
scale = DVec2::ONE;
|
||||||
|
} else {
|
||||||
|
dimensions = DVec2::splat(dimensions.y) / 9.;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
let Some(node_id) = graph_modification_utils::get_grid_id(layer, &document.network_interface) else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
responses.add(NodeGraphMessage::SetInput {
|
||||||
|
input_connector: InputConnector::node(node_id, 2),
|
||||||
|
input: NodeInput::value(TaggedValue::DVec2(dimensions), false),
|
||||||
|
});
|
||||||
|
|
||||||
|
responses.add(GraphOperationMessage::TransformSet {
|
||||||
|
layer,
|
||||||
|
transform: DAffine2::from_scale_angle_translation(scale, 0., translation),
|
||||||
|
transform_in: TransformIn::Viewport,
|
||||||
|
skip_rerender: false,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,4 +1,5 @@
|
|||||||
pub mod ellipse_shape;
|
pub mod ellipse_shape;
|
||||||
|
pub mod grid_shape;
|
||||||
pub mod line_shape;
|
pub mod line_shape;
|
||||||
pub mod polygon_shape;
|
pub mod polygon_shape;
|
||||||
pub mod rectangle_shape;
|
pub mod rectangle_shape;
|
||||||
|
|||||||
@@ -24,9 +24,10 @@ pub enum ShapeType {
|
|||||||
#[default]
|
#[default]
|
||||||
Polygon = 0,
|
Polygon = 0,
|
||||||
Star = 1,
|
Star = 1,
|
||||||
Rectangle = 2,
|
Grid = 2,
|
||||||
Ellipse = 3,
|
Rectangle = 3,
|
||||||
Line = 4,
|
Ellipse = 4,
|
||||||
|
Line = 5,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl ShapeType {
|
impl ShapeType {
|
||||||
@@ -37,6 +38,7 @@ impl ShapeType {
|
|||||||
Self::Rectangle => "Rectangle",
|
Self::Rectangle => "Rectangle",
|
||||||
Self::Ellipse => "Ellipse",
|
Self::Ellipse => "Ellipse",
|
||||||
Self::Line => "Line",
|
Self::Line => "Line",
|
||||||
|
Self::Grid => "Grid",
|
||||||
})
|
})
|
||||||
.into()
|
.into()
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ use crate::messages::tool::common_functionality::gizmos::gizmo_manager::GizmoMan
|
|||||||
use crate::messages::tool::common_functionality::graph_modification_utils;
|
use crate::messages::tool::common_functionality::graph_modification_utils;
|
||||||
use crate::messages::tool::common_functionality::graph_modification_utils::NodeGraphLayer;
|
use crate::messages::tool::common_functionality::graph_modification_utils::NodeGraphLayer;
|
||||||
use crate::messages::tool::common_functionality::resize::Resize;
|
use crate::messages::tool::common_functionality::resize::Resize;
|
||||||
|
use crate::messages::tool::common_functionality::shapes::grid_shape::Grid;
|
||||||
use crate::messages::tool::common_functionality::shapes::line_shape::{LineToolData, clicked_on_line_endpoints};
|
use crate::messages::tool::common_functionality::shapes::line_shape::{LineToolData, clicked_on_line_endpoints};
|
||||||
use crate::messages::tool::common_functionality::shapes::polygon_shape::Polygon;
|
use crate::messages::tool::common_functionality::shapes::polygon_shape::Polygon;
|
||||||
use crate::messages::tool::common_functionality::shapes::shape_utility::{ShapeToolModifierKey, ShapeType, anchor_overlays, transform_cage_overlays};
|
use crate::messages::tool::common_functionality::shapes::shape_utility::{ShapeToolModifierKey, ShapeType, anchor_overlays, transform_cage_overlays};
|
||||||
@@ -22,7 +23,7 @@ use graph_craft::document::value::TaggedValue;
|
|||||||
use graph_craft::document::{NodeId, NodeInput};
|
use graph_craft::document::{NodeId, NodeInput};
|
||||||
use graphene_std::Color;
|
use graphene_std::Color;
|
||||||
use graphene_std::renderer::Quad;
|
use graphene_std::renderer::Quad;
|
||||||
use graphene_std::vector::misc::ArcType;
|
use graphene_std::vector::misc::{ArcType, GridType};
|
||||||
use std::vec;
|
use std::vec;
|
||||||
|
|
||||||
#[derive(Default)]
|
#[derive(Default)]
|
||||||
@@ -39,6 +40,7 @@ pub struct ShapeToolOptions {
|
|||||||
vertices: u32,
|
vertices: u32,
|
||||||
shape_type: ShapeType,
|
shape_type: ShapeType,
|
||||||
arc_type: ArcType,
|
arc_type: ArcType,
|
||||||
|
grid_type: GridType,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Default for ShapeToolOptions {
|
impl Default for ShapeToolOptions {
|
||||||
@@ -50,6 +52,7 @@ impl Default for ShapeToolOptions {
|
|||||||
vertices: 5,
|
vertices: 5,
|
||||||
shape_type: ShapeType::Polygon,
|
shape_type: ShapeType::Polygon,
|
||||||
arc_type: ArcType::Open,
|
arc_type: ArcType::Open,
|
||||||
|
grid_type: GridType::Rectangular,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -65,6 +68,7 @@ pub enum ShapeOptionsUpdate {
|
|||||||
Vertices(u32),
|
Vertices(u32),
|
||||||
ShapeType(ShapeType),
|
ShapeType(ShapeType),
|
||||||
ArcType(ArcType),
|
ArcType(ArcType),
|
||||||
|
GridType(GridType),
|
||||||
}
|
}
|
||||||
|
|
||||||
#[impl_message(Message, ToolMessage, Shape)]
|
#[impl_message(Message, ToolMessage, Shape)]
|
||||||
@@ -109,6 +113,9 @@ fn create_shape_option_widget(shape_type: ShapeType) -> WidgetHolder {
|
|||||||
MenuListEntry::new("Star")
|
MenuListEntry::new("Star")
|
||||||
.label("Star")
|
.label("Star")
|
||||||
.on_commit(move |_| ShapeToolMessage::UpdateOptions(ShapeOptionsUpdate::ShapeType(ShapeType::Star)).into()),
|
.on_commit(move |_| ShapeToolMessage::UpdateOptions(ShapeOptionsUpdate::ShapeType(ShapeType::Star)).into()),
|
||||||
|
MenuListEntry::new("Grid")
|
||||||
|
.label("Grid")
|
||||||
|
.on_commit(move |_| ShapeToolMessage::UpdateOptions(ShapeOptionsUpdate::ShapeType(ShapeType::Grid)).into()),
|
||||||
]];
|
]];
|
||||||
DropdownInput::new(entries).selected_index(Some(shape_type as u32)).widget_holder()
|
DropdownInput::new(entries).selected_index(Some(shape_type as u32)).widget_holder()
|
||||||
}
|
}
|
||||||
@@ -123,6 +130,18 @@ fn create_weight_widget(line_weight: f64) -> WidgetHolder {
|
|||||||
.widget_holder()
|
.widget_holder()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn create_grid_type_widget(grid_type: GridType) -> WidgetHolder {
|
||||||
|
let entries = vec![
|
||||||
|
RadioEntryData::new("Rectangular")
|
||||||
|
.label("Rectangular")
|
||||||
|
.on_update(move |_| ShapeToolMessage::UpdateOptions(ShapeOptionsUpdate::GridType(GridType::Rectangular)).into()),
|
||||||
|
RadioEntryData::new("Isometric")
|
||||||
|
.label("Isometric")
|
||||||
|
.on_update(move |_| ShapeToolMessage::UpdateOptions(ShapeOptionsUpdate::GridType(GridType::Isometric)).into()),
|
||||||
|
];
|
||||||
|
RadioInput::new(entries).selected_index(Some(grid_type as u32)).widget_holder()
|
||||||
|
}
|
||||||
|
|
||||||
impl LayoutHolder for ShapeTool {
|
impl LayoutHolder for ShapeTool {
|
||||||
fn layout(&self) -> Layout {
|
fn layout(&self) -> Layout {
|
||||||
let mut widgets = vec![];
|
let mut widgets = vec![];
|
||||||
@@ -137,6 +156,11 @@ impl LayoutHolder for ShapeTool {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if self.options.shape_type == ShapeType::Grid {
|
||||||
|
widgets.push(create_grid_type_widget(self.options.grid_type));
|
||||||
|
widgets.push(Separator::new(SeparatorType::Unrelated).widget_holder());
|
||||||
|
}
|
||||||
|
|
||||||
if self.options.shape_type != ShapeType::Line {
|
if self.options.shape_type != ShapeType::Line {
|
||||||
widgets.append(&mut self.options.fill.create_widgets(
|
widgets.append(&mut self.options.fill.create_widgets(
|
||||||
"Fill",
|
"Fill",
|
||||||
@@ -203,6 +227,9 @@ impl<'a> MessageHandler<ToolMessage, &mut ToolActionMessageContext<'a>> for Shap
|
|||||||
ShapeOptionsUpdate::ArcType(arc_type) => {
|
ShapeOptionsUpdate::ArcType(arc_type) => {
|
||||||
self.options.arc_type = arc_type;
|
self.options.arc_type = arc_type;
|
||||||
}
|
}
|
||||||
|
ShapeOptionsUpdate::GridType(grid_type) => {
|
||||||
|
self.options.grid_type = grid_type;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
self.fsm_state.update_hints(responses);
|
self.fsm_state.update_hints(responses);
|
||||||
@@ -578,7 +605,7 @@ impl Fsm for ShapeToolFsmState {
|
|||||||
};
|
};
|
||||||
|
|
||||||
match tool_data.current_shape {
|
match tool_data.current_shape {
|
||||||
ShapeType::Polygon | ShapeType::Star | ShapeType::Ellipse | ShapeType::Rectangle => tool_data.data.start(document, input),
|
ShapeType::Polygon | ShapeType::Star | ShapeType::Ellipse | ShapeType::Rectangle | ShapeType::Grid => tool_data.data.start(document, input),
|
||||||
ShapeType::Line => {
|
ShapeType::Line => {
|
||||||
let point = SnapCandidatePoint::handle(document.metadata().document_to_viewport.inverse().transform_point2(input.mouse.position));
|
let point = SnapCandidatePoint::handle(document.metadata().document_to_viewport.inverse().transform_point2(input.mouse.position));
|
||||||
let snapped = tool_data.data.snap_manager.free_snap(&SnapData::new(document, input), &point, SnapTypeConfiguration::default());
|
let snapped = tool_data.data.snap_manager.free_snap(&SnapData::new(document, input), &point, SnapTypeConfiguration::default());
|
||||||
@@ -594,6 +621,7 @@ impl Fsm for ShapeToolFsmState {
|
|||||||
ShapeType::Rectangle => Rectangle::create_node(),
|
ShapeType::Rectangle => Rectangle::create_node(),
|
||||||
ShapeType::Ellipse => Ellipse::create_node(),
|
ShapeType::Ellipse => Ellipse::create_node(),
|
||||||
ShapeType::Line => Line::create_node(document, tool_data.data.drag_start),
|
ShapeType::Line => Line::create_node(document, tool_data.data.drag_start),
|
||||||
|
ShapeType::Grid => Grid::create_node(tool_options.grid_type),
|
||||||
};
|
};
|
||||||
|
|
||||||
let nodes = vec![(NodeId(0), node)];
|
let nodes = vec![(NodeId(0), node)];
|
||||||
@@ -602,7 +630,7 @@ impl Fsm for ShapeToolFsmState {
|
|||||||
responses.add(Message::StartBuffer);
|
responses.add(Message::StartBuffer);
|
||||||
|
|
||||||
match tool_data.current_shape {
|
match tool_data.current_shape {
|
||||||
ShapeType::Ellipse | ShapeType::Rectangle | ShapeType::Polygon | ShapeType::Star => {
|
ShapeType::Ellipse | ShapeType::Rectangle | ShapeType::Polygon | ShapeType::Star | ShapeType::Grid => {
|
||||||
responses.add(GraphOperationMessage::TransformSet {
|
responses.add(GraphOperationMessage::TransformSet {
|
||||||
layer,
|
layer,
|
||||||
transform: DAffine2::from_scale_angle_translation(DVec2::ONE, 0., input.mouse.position),
|
transform: DAffine2::from_scale_angle_translation(DVec2::ONE, 0., input.mouse.position),
|
||||||
@@ -635,6 +663,7 @@ impl Fsm for ShapeToolFsmState {
|
|||||||
ShapeType::Line => Line::update_shape(document, input, layer, tool_data, modifier, responses),
|
ShapeType::Line => Line::update_shape(document, input, layer, tool_data, modifier, responses),
|
||||||
ShapeType::Polygon => Polygon::update_shape(document, input, layer, tool_data, modifier, responses),
|
ShapeType::Polygon => Polygon::update_shape(document, input, layer, tool_data, modifier, responses),
|
||||||
ShapeType::Star => Star::update_shape(document, input, layer, tool_data, modifier, responses),
|
ShapeType::Star => Star::update_shape(document, input, layer, tool_data, modifier, responses),
|
||||||
|
ShapeType::Grid => Grid::update_shape(document, input, layer, tool_options.grid_type, tool_data, modifier, responses),
|
||||||
}
|
}
|
||||||
|
|
||||||
// Auto-panning
|
// Auto-panning
|
||||||
@@ -853,6 +882,11 @@ impl Fsm for ShapeToolFsmState {
|
|||||||
HintInfo::keys([Key::Shift], "Constrain Square").prepend_plus(),
|
HintInfo::keys([Key::Shift], "Constrain Square").prepend_plus(),
|
||||||
HintInfo::keys([Key::Alt], "From Center").prepend_plus(),
|
HintInfo::keys([Key::Alt], "From Center").prepend_plus(),
|
||||||
])],
|
])],
|
||||||
|
ShapeType::Grid => vec![HintGroup(vec![
|
||||||
|
HintInfo::mouse(MouseMotion::LmbDrag, "Draw Grid"),
|
||||||
|
HintInfo::keys([Key::Shift], "Constrain Grid").prepend_plus(),
|
||||||
|
HintInfo::keys([Key::Alt], "From Center").prepend_plus(),
|
||||||
|
])],
|
||||||
};
|
};
|
||||||
HintData(hint_groups)
|
HintData(hint_groups)
|
||||||
}
|
}
|
||||||
@@ -862,6 +896,7 @@ impl Fsm for ShapeToolFsmState {
|
|||||||
ShapeType::Polygon | ShapeType::Star => HintGroup(vec![HintInfo::keys([Key::Shift], "Constrain Regular"), HintInfo::keys([Key::Alt], "From Center")]),
|
ShapeType::Polygon | ShapeType::Star => HintGroup(vec![HintInfo::keys([Key::Shift], "Constrain Regular"), HintInfo::keys([Key::Alt], "From Center")]),
|
||||||
ShapeType::Rectangle => HintGroup(vec![HintInfo::keys([Key::Shift], "Constrain Square"), HintInfo::keys([Key::Alt], "From Center")]),
|
ShapeType::Rectangle => HintGroup(vec![HintInfo::keys([Key::Shift], "Constrain Square"), HintInfo::keys([Key::Alt], "From Center")]),
|
||||||
ShapeType::Ellipse => HintGroup(vec![HintInfo::keys([Key::Shift], "Constrain Circular"), HintInfo::keys([Key::Alt], "From Center")]),
|
ShapeType::Ellipse => HintGroup(vec![HintInfo::keys([Key::Shift], "Constrain Circular"), HintInfo::keys([Key::Alt], "From Center")]),
|
||||||
|
ShapeType::Grid => HintGroup(vec![HintInfo::keys([Key::Shift], "Constrain Grid"), HintInfo::keys([Key::Alt], "From Center")]),
|
||||||
ShapeType::Line => HintGroup(vec![
|
ShapeType::Line => HintGroup(vec![
|
||||||
HintInfo::keys([Key::Shift], "15° Increments"),
|
HintInfo::keys([Key::Shift], "15° Increments"),
|
||||||
HintInfo::keys([Key::Alt], "From Center"),
|
HintInfo::keys([Key::Alt], "From Center"),
|
||||||
|
|||||||
@@ -56,8 +56,8 @@ impl AsI64 for f64 {
|
|||||||
#[widget(Radio)]
|
#[widget(Radio)]
|
||||||
pub enum GridType {
|
pub enum GridType {
|
||||||
#[default]
|
#[default]
|
||||||
Rectangular,
|
Rectangular = 0,
|
||||||
Isometric,
|
Isometric = 1,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[repr(C)]
|
#[repr(C)]
|
||||||
|
|||||||
@@ -127,7 +127,7 @@ impl PointDomain {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn push(&mut self, id: PointId, position: DVec2) {
|
pub fn push(&mut self, id: PointId, position: DVec2) {
|
||||||
debug_assert!(!self.id.contains(&id));
|
// debug_assert!(!self.id.contains(&id));
|
||||||
self.id.push(id);
|
self.id.push(id);
|
||||||
self.position.push(position);
|
self.position.push(position);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user