From 0d139d284c7ec14e6356ef5312a555fb40334f1d Mon Sep 17 00:00:00 2001 From: 0SlowPoke0 Date: Sat, 26 Apr 2025 03:23:00 +0530 Subject: [PATCH 1/9] implement check-drag and angle-lock --- .../messages/input_mapper/input_mappings.rs | 2 +- .../messages/tool/tool_messages/path_tool.rs | 24 +++++++++++++++++++ 2 files changed, 25 insertions(+), 1 deletion(-) diff --git a/editor/src/messages/input_mapper/input_mappings.rs b/editor/src/messages/input_mapper/input_mappings.rs index b75940bf09..4aaea7068c 100644 --- a/editor/src/messages/input_mapper/input_mappings.rs +++ b/editor/src/messages/input_mapper/input_mappings.rs @@ -212,7 +212,7 @@ pub fn input_mappings() -> Mapping { entry!(KeyDown(Delete); modifiers=[Shift], action_dispatch=PathToolMessage::BreakPath), entry!(KeyDown(Backspace); modifiers=[Shift], action_dispatch=PathToolMessage::BreakPath), entry!(KeyDownNoRepeat(Tab); action_dispatch=PathToolMessage::SwapSelectedHandles), - entry!(KeyDown(MouseLeft); action_dispatch=PathToolMessage::MouseDown { direct_insert_without_sliding: Control, extend_selection: Shift, lasso_select: Control, handle_drag_from_anchor: Alt }), + entry!(KeyDown(MouseLeft); action_dispatch=PathToolMessage::MouseDown { direct_insert_without_sliding: Control, extend_selection: Shift, lasso_select: Control, handle_drag_from_anchor: Alt, drag_zero_handle: Control }), entry!(KeyDown(MouseRight); action_dispatch=PathToolMessage::RightClick), entry!(KeyDown(Escape); action_dispatch=PathToolMessage::Escape), entry!(KeyDown(KeyG); action_dispatch=PathToolMessage::GRS { key: KeyG }), diff --git a/editor/src/messages/tool/tool_messages/path_tool.rs b/editor/src/messages/tool/tool_messages/path_tool.rs index 3954bf96f6..92b7d9b380 100644 --- a/editor/src/messages/tool/tool_messages/path_tool.rs +++ b/editor/src/messages/tool/tool_messages/path_tool.rs @@ -68,6 +68,7 @@ pub enum PathToolMessage { extend_selection: Key, lasso_select: Key, handle_drag_from_anchor: Key, + drag_zero_handle: Key, }, NudgeSelectedPoints { delta_x: f64, @@ -498,6 +499,7 @@ impl PathToolData { direct_insert_without_sliding: bool, lasso_select: bool, handle_drag_from_anchor: bool, + drag_zero_handle: bool, ) -> PathToolFsmState { self.double_click_handled = false; self.opposing_handle_lengths = None; @@ -560,6 +562,24 @@ impl PathToolData { } } + if let Some((Some(point), Some(vector_data))) = shape_editor + .find_nearest_point_indices(&document.network_interface, input.mouse.position, SELECTION_THRESHOLD) + .and_then(|(layer, point)| Some((point.as_anchor(), document.network_interface.compute_modified_vector(layer)))) + { + let handles = vector_data + .all_connected(point) + .filter(|handle| handle.length(&vector_data) < 1e-6) + .map(|handle| handle.to_manipulator_point()) + .collect::>(); + let endpoint = vector_data.extendable_points(false).any(|anchor| point == anchor); + + if drag_zero_handle && (handles.len() == 1 && !endpoint) { + shape_editor.deselect_all_points(); + shape_editor.select_points_by_manipulator_id(&handles); + shape_editor.convert_selected_manipulators_to_colinear_handles(responses, document); + } + } + self.start_dragging_point(selected_points, input, document, shape_editor); responses.add(OverlaysMessage::Draw); } @@ -1160,12 +1180,14 @@ impl Fsm for PathToolFsmState { extend_selection, lasso_select, handle_drag_from_anchor, + drag_zero_handle, }, ) => { let extend_selection = input.keyboard.get(extend_selection as usize); let lasso_select = input.keyboard.get(lasso_select as usize); let direct_insert_without_sliding = input.keyboard.get(direct_insert_without_sliding as usize); let handle_drag_from_anchor = input.keyboard.get(handle_drag_from_anchor as usize); + let drag_zero_handle = input.keyboard.get(drag_zero_handle as usize); tool_data.selection_mode = None; tool_data.lasso_polygon.clear(); @@ -1179,6 +1201,7 @@ impl Fsm for PathToolFsmState { direct_insert_without_sliding, lasso_select, handle_drag_from_anchor, + drag_zero_handle, ) } ( @@ -1467,6 +1490,7 @@ impl Fsm for PathToolFsmState { tool_data.alt_dragging_from_anchor = false; tool_data.alt_clicked_on_anchor = false; + tool_data.angle_locked = false; if tool_data.select_anchor_toggled { shape_editor.deselect_all_points(); From be3d48f0b44b5eba99f191f61ea5cd9d58cf6f47 Mon Sep 17 00:00:00 2001 From: 0SlowPoke0 Date: Sat, 26 Apr 2025 03:49:56 +0530 Subject: [PATCH 2/9] track bool --- editor/src/messages/tool/tool_messages/path_tool.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/editor/src/messages/tool/tool_messages/path_tool.rs b/editor/src/messages/tool/tool_messages/path_tool.rs index 92b7d9b380..8a80b738a1 100644 --- a/editor/src/messages/tool/tool_messages/path_tool.rs +++ b/editor/src/messages/tool/tool_messages/path_tool.rs @@ -1422,6 +1422,7 @@ impl Fsm for PathToolFsmState { tool_data.saved_points_before_handle_drag.clear(); tool_data.handle_drag_toggle = false; } + tool_data.angle_locked = false; responses.add(DocumentMessage::AbortTransaction); tool_data.snap_manager.cleanup(responses); PathToolFsmState::Ready From a2f96b10326f929f298e1a5d5115e2500bdd797e Mon Sep 17 00:00:00 2001 From: 0SlowPoke0 Date: Sat, 26 Apr 2025 18:36:15 +0530 Subject: [PATCH 3/9] flip-smooth-sharp --- .../messages/tool/common_functionality/shape_editor.rs | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/editor/src/messages/tool/common_functionality/shape_editor.rs b/editor/src/messages/tool/common_functionality/shape_editor.rs index db61db5221..60109f4be7 100644 --- a/editor/src/messages/tool/common_functionality/shape_editor.rs +++ b/editor/src/messages/tool/common_functionality/shape_editor.rs @@ -1384,13 +1384,13 @@ impl ShapeState { let (id, anchor) = result?; let handles = vector_data.all_connected(id); - let mut positions = handles + let positions = handles .filter_map(|handle| handle.to_manipulator_point().get_position(&vector_data)) - .filter(|&handle| !anchor.abs_diff_eq(handle, 1e-5)); + .filter(|&handle| anchor.abs_diff_eq(handle, 1e-5)) + .count(); // Check by comparing the handle positions to the anchor if this manipulator group is a point - let already_sharp = positions.next().is_none(); - if already_sharp { + if positions != 0 { self.convert_manipulator_handles_to_colinear(&vector_data, id, responses, layer); } else { for handle in vector_data.all_connected(id) { From 13c5db1057af58e4cbe47ed816a3a8952942de28 Mon Sep 17 00:00:00 2001 From: 0SlowPoke0 Date: Tue, 13 May 2025 11:20:04 +0530 Subject: [PATCH 4/9] fixed bugs --- editor/src/messages/tool/tool_messages/path_tool.rs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/editor/src/messages/tool/tool_messages/path_tool.rs b/editor/src/messages/tool/tool_messages/path_tool.rs index 184316f90e..74c57c1b73 100644 --- a/editor/src/messages/tool/tool_messages/path_tool.rs +++ b/editor/src/messages/tool/tool_messages/path_tool.rs @@ -721,13 +721,14 @@ impl PathToolData { if relative_vector.length() < 25. && lock_angle && !self.angle_locked { if let Some(angle) = calculate_lock_angle(self, shape_editor, responses, document, &vector_data, handle_id) { self.angle = angle; + self.angle_locked = true; + self.current_selected_handle_id = Some(handle_id); return angle; } } } // When the angle is locked we use the old angle - if self.current_selected_handle_id == Some(handle_id) && lock_angle { self.angle_locked = true; return self.angle; @@ -767,6 +768,7 @@ impl PathToolData { origin: anchor_position, direction: handle_direction.normalize_or_zero(), }; + self.snap_manager.constrained_snap(&snap_data, &snap_point, snap_constraint, Default::default()) } false => self.snap_manager.free_snap(&snap_data, &snap_point, Default::default()), From bc6cbc12c9bbaf6df9cc415651e986ad9e518cec Mon Sep 17 00:00:00 2001 From: 0SlowPoke0 Date: Thu, 15 May 2025 01:29:10 +0530 Subject: [PATCH 5/9] fixed flip-smooth jump bug and random angle locking bug --- .../tool/common_functionality/shape_editor.rs | 39 +++++++++++++------ .../messages/tool/tool_messages/path_tool.rs | 13 ++++--- 2 files changed, 34 insertions(+), 18 deletions(-) diff --git a/editor/src/messages/tool/common_functionality/shape_editor.rs b/editor/src/messages/tool/common_functionality/shape_editor.rs index ba95fcbb7f..810d494d7b 100644 --- a/editor/src/messages/tool/common_functionality/shape_editor.rs +++ b/editor/src/messages/tool/common_functionality/shape_editor.rs @@ -728,7 +728,7 @@ impl ShapeState { return; }; let handles = vector_data.all_connected(point_id).take(2).collect::>(); - + let non_zero_handles = handles.iter().filter(|handle| handle.length(vector_data) > 1e-6).count(); // Grab the next and previous manipulator groups by simply looking at the next / previous index let points = handles.iter().map(|handle| vector_data.other_point(handle.segment, point_id)); let anchor_positions = points @@ -762,20 +762,35 @@ impl ShapeState { handle_direction *= -1.; } - // Push both in and out handles into the correct position - for ((handle, sign), other_anchor) in handles.iter().zip([1., -1.]).zip(&anchor_positions) { - // To find the length of the new tangent we just take the distance to the anchor and divide by 3 (pretty arbitrary) - let Some(length) = other_anchor.map(|position| (position - anchor_position).length() / 3.) else { - continue; + if non_zero_handles != 0 { + let [a, b] = handles.as_slice() else { return }; + let (non_zero_handle, zero_handle) = if a.length(vector_data) > 1e-6 { (a, b) } else { (b, a) }; + let Some(direction) = non_zero_handle + .to_manipulator_point() + .get_position(&vector_data) + .and_then(|position| (position - anchor_position).try_normalize()) + else { + return; }; - let new_position = handle_direction * length * sign; - let modification_type = handle.set_relative_position(new_position); + let new_position = non_zero_handle.length(vector_data) * direction * -1.; + let modification_type = zero_handle.set_relative_position(new_position); responses.add(GraphOperationMessage::Vector { layer, modification_type }); - - // Create the opposite handle if it doesn't exist (if it is not a cubic segment) - if handle.opposite().to_manipulator_point().get_position(vector_data).is_none() { - let modification_type = handle.opposite().set_relative_position(DVec2::ZERO); + } else { + // Push both in and out handles into the correct position + for ((handle, sign), other_anchor) in handles.iter().zip([1., -1.]).zip(&anchor_positions) { + // To find the length of the new tangent we just take the distance to the anchor and divide by 3 (pretty arbitrary) + let Some(length) = other_anchor.map(|position| (position - anchor_position).length() / 3.) else { + continue; + }; + let new_position = handle_direction * length * sign; + let modification_type = handle.set_relative_position(new_position); responses.add(GraphOperationMessage::Vector { layer, modification_type }); + + // Create the opposite handle if it doesn't exist (if it is not a cubic segment) + if handle.opposite().to_manipulator_point().get_position(vector_data).is_none() { + let modification_type = handle.opposite().set_relative_position(DVec2::ZERO); + responses.add(GraphOperationMessage::Vector { layer, modification_type }); + } } } } diff --git a/editor/src/messages/tool/tool_messages/path_tool.rs b/editor/src/messages/tool/tool_messages/path_tool.rs index 74c57c1b73..c3bcb3b32f 100644 --- a/editor/src/messages/tool/tool_messages/path_tool.rs +++ b/editor/src/messages/tool/tool_messages/path_tool.rs @@ -363,7 +363,6 @@ struct PathToolData { saved_points_before_handle_drag: Vec, handle_drag_toggle: bool, dragging_state: DraggingState, - current_selected_handle_id: Option, angle: f64, opposite_handle_position: Option, last_clicked_point_was_selected: bool, @@ -722,15 +721,19 @@ impl PathToolData { if let Some(angle) = calculate_lock_angle(self, shape_editor, responses, document, &vector_data, handle_id) { self.angle = angle; self.angle_locked = true; - self.current_selected_handle_id = Some(handle_id); return angle; } } } - // When the angle is locked we use the old angle - if self.current_selected_handle_id == Some(handle_id) && lock_angle { + if lock_angle && !self.angle_locked { self.angle_locked = true; + self.angle = -relative_vector.angle_to(DVec2::X); + return -relative_vector.angle_to(DVec2::X); + } + + // When the angle is locked we use the old angle + if self.angle_locked { return self.angle; } @@ -741,8 +744,6 @@ impl PathToolData { handle_angle = (handle_angle / snap_resolution).round() * snap_resolution; } - // Cache the angle and handle id for lock angle - self.current_selected_handle_id = Some(handle_id); self.angle = handle_angle; handle_angle From 8bf6cb05a00ff67196e64b3b5981aaf40d7c594d Mon Sep 17 00:00:00 2001 From: 0SlowPoke0 Date: Thu, 15 May 2025 02:55:51 +0530 Subject: [PATCH 6/9] ctrl-alt 90 case --- .../messages/tool/tool_messages/path_tool.rs | 25 ++++++++++++++++--- 1 file changed, 22 insertions(+), 3 deletions(-) diff --git a/editor/src/messages/tool/tool_messages/path_tool.rs b/editor/src/messages/tool/tool_messages/path_tool.rs index c3bcb3b32f..c45d5a4bec 100644 --- a/editor/src/messages/tool/tool_messages/path_tool.rs +++ b/editor/src/messages/tool/tool_messages/path_tool.rs @@ -708,6 +708,7 @@ impl PathToolData { handle_id: ManipulatorPointId, lock_angle: bool, snap_angle: bool, + tangent_to_neighboring_tangents: bool, ) -> f64 { let current_angle = -handle_vector.angle_to(DVec2::X); @@ -718,7 +719,7 @@ impl PathToolData { .and_then(|(layer, _)| document.network_interface.compute_modified_vector(*layer)) { if relative_vector.length() < 25. && lock_angle && !self.angle_locked { - if let Some(angle) = calculate_lock_angle(self, shape_editor, responses, document, &vector_data, handle_id) { + if let Some(angle) = calculate_lock_angle(self, shape_editor, responses, document, &vector_data, handle_id, tangent_to_neighboring_tangents) { self.angle = angle; self.angle_locked = true; return angle; @@ -873,7 +874,17 @@ impl PathToolData { let snapped_delta = if let Some((handle_pos, anchor_pos, handle_id)) = self.try_get_selected_handle_and_anchor(shape_editor, document) { let cursor_pos = handle_pos + raw_delta; - let handle_angle = self.calculate_handle_angle(shape_editor, document, responses, handle_pos - anchor_pos, cursor_pos - anchor_pos, handle_id, lock_angle, snap_angle); + let handle_angle = self.calculate_handle_angle( + shape_editor, + document, + responses, + handle_pos - anchor_pos, + cursor_pos - anchor_pos, + handle_id, + lock_angle, + snap_angle, + equidistant, + ); let constrained_direction = DVec2::new(handle_angle.cos(), handle_angle.sin()); let projected_length = (cursor_pos - anchor_pos).dot(constrained_direction); @@ -1801,6 +1812,7 @@ fn calculate_lock_angle( document: &DocumentMessageHandler, vector_data: &VectorData, handle_id: ManipulatorPointId, + tangent_to_neighboring_tangents: bool, ) -> Option { let anchor = handle_id.get_anchor(vector_data)?; let anchor_position = vector_data.point_domain.position_from_id(anchor); @@ -1834,7 +1846,14 @@ fn calculate_lock_angle( let angle_2 = calculate_segment_angle(anchor, segment, vector_data, false); match (angle_1, angle_2) { - (Some(angle_1), Some(angle_2)) => Some((angle_1 + angle_2) / 2.0), + (Some(angle_1), Some(angle_2)) => { + let angle = Some((angle_1 + angle_2) / 2.0); + if tangent_to_neighboring_tangents { + angle.map(|angle| angle + std::f64::consts::FRAC_PI_2) + } else { + angle + } + } (Some(angle_1), None) => Some(angle_1), (None, Some(angle_2)) => Some(angle_2), (None, None) => None, From 401d333326e64571bf8b9412f4846eaee886f26f Mon Sep 17 00:00:00 2001 From: 0SlowPoke0 Date: Sat, 17 May 2025 13:48:05 +0530 Subject: [PATCH 7/9] aligned flip-smooth sharp and fixed arbitrary handle-length when flipped --- editor/src/consts.rs | 1 + .../messages/input_mapper/input_mappings.rs | 2 +- .../tool/common_functionality/shape_editor.rs | 42 +++++++++++++------ .../messages/tool/tool_messages/path_tool.rs | 8 ++-- 4 files changed, 36 insertions(+), 17 deletions(-) diff --git a/editor/src/consts.rs b/editor/src/consts.rs index b4b3d23feb..01ef3b8ad9 100644 --- a/editor/src/consts.rs +++ b/editor/src/consts.rs @@ -102,6 +102,7 @@ pub const HIDE_HANDLE_DISTANCE: f64 = 3.; pub const HANDLE_ROTATE_SNAP_ANGLE: f64 = 15.; pub const SEGMENT_INSERTION_DISTANCE: f64 = 7.5; pub const SEGMENT_OVERLAY_SIZE: f64 = 10.; +pub const HANDLE_LENGTH_FACTOR: f64 = 0.80; // PEN TOOL pub const CREATE_CURVE_THRESHOLD: f64 = 5.; diff --git a/editor/src/messages/input_mapper/input_mappings.rs b/editor/src/messages/input_mapper/input_mappings.rs index 2890e26797..5131af4f7f 100644 --- a/editor/src/messages/input_mapper/input_mappings.rs +++ b/editor/src/messages/input_mapper/input_mappings.rs @@ -212,7 +212,7 @@ pub fn input_mappings() -> Mapping { entry!(KeyDown(Delete); modifiers=[Shift], action_dispatch=PathToolMessage::BreakPath), entry!(KeyDown(Backspace); modifiers=[Shift], action_dispatch=PathToolMessage::BreakPath), entry!(KeyDownNoRepeat(Tab); action_dispatch=PathToolMessage::SwapSelectedHandles), - entry!(KeyDown(MouseLeft); action_dispatch=PathToolMessage::MouseDown { extend_selection: Shift, lasso_select: Control, handle_drag_from_anchor: Alt, drag_zero_handle: Control }), + entry!(KeyDown(MouseLeft); action_dispatch=PathToolMessage::MouseDown { extend_selection: Shift, lasso_select: Control, handle_drag_from_anchor: Alt, drag_restore_handle: Control }), entry!(KeyDown(MouseRight); action_dispatch=PathToolMessage::RightClick), entry!(KeyDown(Escape); action_dispatch=PathToolMessage::Escape), entry!(KeyDown(KeyG); action_dispatch=PathToolMessage::GRS { key: KeyG }), diff --git a/editor/src/messages/tool/common_functionality/shape_editor.rs b/editor/src/messages/tool/common_functionality/shape_editor.rs index 810d494d7b..468096740b 100644 --- a/editor/src/messages/tool/common_functionality/shape_editor.rs +++ b/editor/src/messages/tool/common_functionality/shape_editor.rs @@ -1,5 +1,7 @@ use super::graph_modification_utils::{self, merge_layers}; use super::snapping::{SnapCache, SnapCandidatePoint, SnapData, SnapManager, SnappedPoint}; +use super::utility_functions::calculate_segment_angle; +use crate::consts::HANDLE_LENGTH_FACTOR; use crate::messages::portfolio::document::utility_types::document_metadata::{DocumentMetadata, LayerNodeIdentifier}; use crate::messages::portfolio::document::utility_types::misc::{PathSnapSource, SnapSource}; use crate::messages::portfolio::document::utility_types::network_interface::NodeNetworkInterface; @@ -729,22 +731,32 @@ impl ShapeState { }; let handles = vector_data.all_connected(point_id).take(2).collect::>(); let non_zero_handles = handles.iter().filter(|handle| handle.length(vector_data) > 1e-6).count(); + let handle_segments = handles.iter().map(|handles| handles.segment).collect::>(); + // Grab the next and previous manipulator groups by simply looking at the next / previous index let points = handles.iter().map(|handle| vector_data.other_point(handle.segment, point_id)); let anchor_positions = points .map(|point| point.and_then(|point| ManipulatorPointId::Anchor(point).get_position(vector_data))) .collect::>(); - // Use the position relative to the anchor - let mut directions = anchor_positions - .iter() - .map(|position| position.map(|position| (position - anchor_position)).and_then(DVec2::try_normalize)); + let mut segment_angle = 0.; + let mut segment_count = 0.; + + for segment in &handle_segments { + let Some(angle) = calculate_segment_angle(point_id, *segment, vector_data, false) else { + continue; + }; + segment_angle += angle; + segment_count += 1.; + } - // The direction of the handles is either the perpendicular vector to the sum of the anchors' positions or just the anchor's position (if only one) - let mut handle_direction = match (directions.next().flatten(), directions.next().flatten()) { - (Some(previous), Some(next)) => (previous - next).try_normalize().unwrap_or(next.perp()), - (Some(val), None) | (None, Some(val)) => val, - (None, None) => return, + // For a non-endpoint anchor, handles are perpendicular to the average tangent of adjacent segments.(Refer:https://github.com/GraphiteEditor/Graphite/pull/2620#issuecomment-2881501494) + let mut handle_direction = if segment_count > 1. { + segment_angle = segment_angle / segment_count; + segment_angle += std::f64::consts::FRAC_PI_2; + DVec2::new(segment_angle.cos(), segment_angle.sin()) + } else { + DVec2::new(segment_angle.cos(), segment_angle.sin()) }; // Set the manipulator to have colinear handles @@ -778,11 +790,17 @@ impl ShapeState { } else { // Push both in and out handles into the correct position for ((handle, sign), other_anchor) in handles.iter().zip([1., -1.]).zip(&anchor_positions) { - // To find the length of the new tangent we just take the distance to the anchor and divide by 3 (pretty arbitrary) - let Some(length) = other_anchor.map(|position| (position - anchor_position).length() / 3.) else { + let Some(anchor_vector) = other_anchor.map(|position| (position - anchor_position)) else { + continue; + }; + + let Some(unit_vector) = anchor_vector.try_normalize() else { continue; }; - let new_position = handle_direction * length * sign; + + let projection = anchor_vector.length() * HANDLE_LENGTH_FACTOR * handle_direction.dot(unit_vector).abs(); + + let new_position = handle_direction * projection * sign; let modification_type = handle.set_relative_position(new_position); responses.add(GraphOperationMessage::Vector { layer, modification_type }); diff --git a/editor/src/messages/tool/tool_messages/path_tool.rs b/editor/src/messages/tool/tool_messages/path_tool.rs index c45d5a4bec..766a554675 100644 --- a/editor/src/messages/tool/tool_messages/path_tool.rs +++ b/editor/src/messages/tool/tool_messages/path_tool.rs @@ -67,7 +67,7 @@ pub enum PathToolMessage { extend_selection: Key, lasso_select: Key, handle_drag_from_anchor: Key, - drag_zero_handle: Key, + drag_restore_handle: Key, }, NudgeSelectedPoints { delta_x: f64, @@ -1143,13 +1143,13 @@ impl Fsm for PathToolFsmState { extend_selection, lasso_select, handle_drag_from_anchor, - drag_zero_handle, + drag_restore_handle, }, ) => { let extend_selection = input.keyboard.get(extend_selection as usize); let lasso_select = input.keyboard.get(lasso_select as usize); let handle_drag_from_anchor = input.keyboard.get(handle_drag_from_anchor as usize); - let drag_zero_handle = input.keyboard.get(drag_zero_handle as usize); + let drag_zero_handle = input.keyboard.get(drag_restore_handle as usize); tool_data.selection_mode = None; tool_data.lasso_polygon.clear(); @@ -1847,7 +1847,7 @@ fn calculate_lock_angle( match (angle_1, angle_2) { (Some(angle_1), Some(angle_2)) => { - let angle = Some((angle_1 + angle_2) / 2.0); + let angle = Some((angle_1 + angle_2) / 2.); if tangent_to_neighboring_tangents { angle.map(|angle| angle + std::f64::consts::FRAC_PI_2) } else { From 6305d0a755fe947b70ee369413a7d33348ffd32e Mon Sep 17 00:00:00 2001 From: 0SlowPoke0 Date: Sat, 17 May 2025 13:50:32 +0530 Subject: [PATCH 8/9] code-review change --- editor/src/messages/tool/common_functionality/shape_editor.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/editor/src/messages/tool/common_functionality/shape_editor.rs b/editor/src/messages/tool/common_functionality/shape_editor.rs index 468096740b..62e7eb45e4 100644 --- a/editor/src/messages/tool/common_functionality/shape_editor.rs +++ b/editor/src/messages/tool/common_functionality/shape_editor.rs @@ -784,7 +784,7 @@ impl ShapeState { else { return; }; - let new_position = non_zero_handle.length(vector_data) * direction * -1.; + let new_position = -direction * non_zero_handle.length(vector_data); let modification_type = zero_handle.set_relative_position(new_position); responses.add(GraphOperationMessage::Vector { layer, modification_type }); } else { From d36accd2075168d3bce9500c4315e8afa77abcc0 Mon Sep 17 00:00:00 2001 From: Keavon Chambers Date: Sat, 17 May 2025 13:09:17 -0700 Subject: [PATCH 9/9] 0.5 instead of 0.8 --- editor/src/consts.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/editor/src/consts.rs b/editor/src/consts.rs index 01ef3b8ad9..f835d4b963 100644 --- a/editor/src/consts.rs +++ b/editor/src/consts.rs @@ -102,7 +102,7 @@ pub const HIDE_HANDLE_DISTANCE: f64 = 3.; pub const HANDLE_ROTATE_SNAP_ANGLE: f64 = 15.; pub const SEGMENT_INSERTION_DISTANCE: f64 = 7.5; pub const SEGMENT_OVERLAY_SIZE: f64 = 10.; -pub const HANDLE_LENGTH_FACTOR: f64 = 0.80; +pub const HANDLE_LENGTH_FACTOR: f64 = 0.5; // PEN TOOL pub const CREATE_CURVE_THRESHOLD: f64 = 5.;