mirror of
https://github.com/GraphiteEditor/Graphite.git
synced 2026-09-17 07:18:04 +08:00
need to fix the updated dash lines
This commit is contained in:
@@ -64,17 +64,14 @@ impl RadiusGizmo {
|
||||
|
||||
let b = calculate_b(inner_radius, turns, outer_radius, spiral_type);
|
||||
|
||||
let start_radius = spiral_point(0. + start_angle, inner_radius, b, spiral_type).distance(DVec2::ZERO);
|
||||
let end_radius = spiral_point(turns * TAU + start_angle, inner_radius, b, spiral_type).distance(DVec2::ZERO);
|
||||
|
||||
log::info!("start_radius {:?}", start_radius);
|
||||
log::info!("end radius {:?}", end_radius);
|
||||
let start_radius = spiral_point(0. + start_angle.to_radians(), inner_radius, b, spiral_type).distance(DVec2::ZERO);
|
||||
let end_radius = spiral_point(turns * TAU + start_angle.to_radians(), inner_radius, b, spiral_type).distance(DVec2::ZERO);
|
||||
|
||||
let larger_radius = (start_radius.max(end_radius)).max(5.);
|
||||
let smaller_radius = (start_radius.min(end_radius)).max(5.);
|
||||
|
||||
if layer_mouse.distance(DVec2::ZERO) < smaller_radius {
|
||||
log::info!("reaching heeee");
|
||||
log::info!("reachinhere inner radius");
|
||||
self.layer = Some(layer);
|
||||
self.initial_radius = smaller_radius;
|
||||
self.spiral_type = spiral_type;
|
||||
@@ -86,6 +83,7 @@ impl RadiusGizmo {
|
||||
}
|
||||
|
||||
if (layer_mouse.distance(DVec2::ZERO) - larger_radius).abs() < 5. {
|
||||
log::info!("reaching bigger radius");
|
||||
self.layer = Some(layer);
|
||||
self.initial_radius = larger_radius;
|
||||
self.spiral_type = spiral_type;
|
||||
@@ -110,9 +108,9 @@ impl RadiusGizmo {
|
||||
if let Some(((inner_radius, outer_radius, turns, start_angle), spiral_type)) = extract_arc_or_log_spiral_parameters(layer, document).zip(get_spiral_type(layer, document)) {
|
||||
let b = calculate_b(inner_radius, turns, outer_radius, spiral_type);
|
||||
let endpoint = if self.radius_index == SPIRAL_INNER_RADIUS_INDEX {
|
||||
spiral_point(0. + start_angle, inner_radius, b, spiral_type)
|
||||
spiral_point(0. + start_angle.to_radians(), inner_radius, b, spiral_type)
|
||||
} else {
|
||||
spiral_point(turns * TAU + start_angle, inner_radius, b, spiral_type)
|
||||
spiral_point(turns * TAU + start_angle.to_radians(), inner_radius, b, spiral_type)
|
||||
};
|
||||
|
||||
let viewport_center = viewport.transform_point2(DVec2::ZERO);
|
||||
|
||||
@@ -35,6 +35,7 @@ pub struct TightnessGizmo {
|
||||
inner_radius: f64,
|
||||
angle: f64,
|
||||
spiral_slot: i32,
|
||||
turns: f64,
|
||||
previous_mouse: DVec2,
|
||||
}
|
||||
|
||||
@@ -67,12 +68,14 @@ impl TightnessGizmo {
|
||||
if let Some((start, end, slot_index)) =
|
||||
Self::check_which_inter_segment(viewport.inverse().transform_point2(mouse_position), a, outer_radius, turns, start_angle, spiral_type, viewport)
|
||||
{
|
||||
log::info!("check which inter-segment {:?}", slot_index);
|
||||
self.layer = Some(layer);
|
||||
self.initial_outer_radius = outer_radius;
|
||||
self.previous_mouse = mouse_position;
|
||||
self.gizmo_line_points = Some((start, end));
|
||||
self.spiral_type = spiral_type;
|
||||
self.spiral_slot = slot_index;
|
||||
self.turns = turns;
|
||||
self.inner_radius = a;
|
||||
self.angle = viewport.inverse().transform_point2(mouse_position).angle_to(DVec2::X).rem_euclid(TAU);
|
||||
self.update_state(TightnessGizmoState::Hover);
|
||||
@@ -94,20 +97,22 @@ impl TightnessGizmo {
|
||||
|
||||
match &self.handle_state {
|
||||
TightnessGizmoState::Hover | TightnessGizmoState::Dragging => {
|
||||
let is_reversed = self.inner_radius > self.initial_outer_radius;
|
||||
if let Some((start, end)) = self.gizmo_line_points {
|
||||
overlay_context.dashed_line(start, end, None, None, Some(4.0), Some(4.0), Some(0.5));
|
||||
if self.spiral_slot == 0 {
|
||||
let required_radius = if self.inner_radius > self.initial_outer_radius {
|
||||
viewport
|
||||
.inverse()
|
||||
.transform_point2(get_arc_spiral_end_point(layer, document, viewport, TAU).expect("Failed to get endpoints"))
|
||||
.distance(DVec2::ZERO)
|
||||
} else {
|
||||
viewport
|
||||
.inverse()
|
||||
.transform_point2(get_arc_spiral_end_point(layer, document, viewport, 0.).expect("Failed to get endpoints"))
|
||||
.distance(DVec2::ZERO)
|
||||
};
|
||||
if self.spiral_slot == 0 && !is_reversed {
|
||||
let required_radius = viewport
|
||||
.inverse()
|
||||
.transform_point2(get_arc_spiral_end_point(layer, document, viewport, 0.).expect("Failed to get endpoints"))
|
||||
.distance(DVec2::ZERO);
|
||||
overlay_context.dashed_circle(DVec2::ZERO, required_radius.max(5.), None, None, Some(4.), Some(4.), Some(0.5), Some(viewport));
|
||||
}
|
||||
|
||||
if self.spiral_slot == self.turns.floor() as i32 && is_reversed {
|
||||
let required_radius = viewport
|
||||
.inverse()
|
||||
.transform_point2(get_arc_spiral_end_point(layer, document, viewport, TAU).expect("Failed to get endpoints"))
|
||||
.distance(DVec2::ZERO);
|
||||
overlay_context.dashed_circle(DVec2::ZERO, required_radius.max(5.), None, None, Some(4.), Some(4.), Some(0.5), Some(viewport));
|
||||
}
|
||||
};
|
||||
@@ -129,19 +134,28 @@ impl TightnessGizmo {
|
||||
let center = DVec2::ZERO;
|
||||
let angle = layer_mouse_position.angle_to(DVec2::X).rem_euclid(TAU);
|
||||
let start_angle_rad = start_angle.to_radians();
|
||||
let spiral_theta = (angle - start_angle_rad).rem_euclid(TAU);
|
||||
let normalized_start_angle = start_angle_rad.rem_euclid(TAU);
|
||||
|
||||
let is_reversed = inner_radius > outer_radius;
|
||||
let b = calculate_b(inner_radius, turns, outer_radius, spiral_type);
|
||||
let max_theta = turns * TAU;
|
||||
|
||||
let spiral_theta = if is_reversed {
|
||||
angle + ((start_angle.to_radians() / TAU).floor() * TAU) + turns.floor() * TAU
|
||||
} else {
|
||||
angle + ((start_angle.to_radians() / TAU).floor() * TAU)
|
||||
};
|
||||
|
||||
let viewport_mouse = viewport.transform_point2(layer_mouse_position);
|
||||
let viewport_center = viewport.transform_point2(center);
|
||||
|
||||
let spiral_outer = spiral_point(max_theta, inner_radius, b, spiral_type);
|
||||
let spiral_inner = spiral_point(0.0, inner_radius, b, spiral_type);
|
||||
let viewport_outer = viewport.transform_point2(Self::rotate_point(spiral_outer, start_angle_rad));
|
||||
let viewport_inner = viewport.transform_point2(Self::rotate_point(spiral_inner, start_angle_rad));
|
||||
let spiral_outer = spiral_point(max_theta + start_angle_rad, inner_radius, b, spiral_type);
|
||||
let spiral_inner = spiral_point(0. + start_angle_rad, inner_radius, b, spiral_type);
|
||||
let viewport_outer = viewport.transform_point2(spiral_outer);
|
||||
let viewport_inner = viewport.transform_point2(spiral_inner);
|
||||
|
||||
let first_segment = spiral_point(angle + ((start_angle.to_radians() / TAU).floor() * TAU), inner_radius, b, spiral_type);
|
||||
let fist_segment_point_distance = viewport.transform_point2(first_segment).distance(viewport_center);
|
||||
|
||||
let required_endpoint = if is_reversed { viewport_inner } else { viewport_outer };
|
||||
let mouse_distance = viewport_mouse.distance(viewport_center);
|
||||
@@ -151,61 +165,112 @@ impl TightnessGizmo {
|
||||
return None;
|
||||
}
|
||||
|
||||
let mut segment_index = 0;
|
||||
if is_reversed && mouse_distance > fist_segment_point_distance {
|
||||
return None;
|
||||
}
|
||||
|
||||
// First segment: from center to first spiral point at spiral_theta
|
||||
{
|
||||
let mut segment_index = if is_reversed { turns.floor() as i32 } else { 0 };
|
||||
|
||||
if !is_reversed {
|
||||
let spiral_end = spiral_point(spiral_theta, inner_radius, b, spiral_type);
|
||||
let first_point = viewport.transform_point2(Self::rotate_point(spiral_end, start_angle_rad));
|
||||
let first_point = viewport.transform_point2(spiral_end);
|
||||
|
||||
let r_end = first_point.distance(viewport_center);
|
||||
|
||||
if mouse_distance <= r_end {
|
||||
let direction = DVec2::new(angle.cos(), -angle.sin());
|
||||
let inner_point = viewport.transform_point2(inner_radius.max(5.0) * direction);
|
||||
let radius = if is_reversed { spiral_outer.distance(DVec2::ZERO) } else { spiral_inner.distance(DVec2::ZERO) };
|
||||
let inner_point = viewport.transform_point2(radius.max(5.0) * direction);
|
||||
return Some((inner_point, first_point, segment_index));
|
||||
}
|
||||
|
||||
if angle <= normalized_start_angle {
|
||||
let spiral_end = spiral_point(spiral_theta + TAU, inner_radius, b, spiral_type);
|
||||
let first_point = viewport.transform_point2(spiral_end);
|
||||
if mouse_distance <= first_point.distance(viewport_center) {
|
||||
let direction = DVec2::new(angle.cos(), -angle.sin());
|
||||
|
||||
let radius = if is_reversed { spiral_outer.distance(DVec2::ZERO) } else { spiral_inner.distance(DVec2::ZERO) };
|
||||
let inner_point = viewport.transform_point2(radius.max(5.0) * direction);
|
||||
|
||||
return Some((inner_point, first_point, segment_index));
|
||||
}
|
||||
}
|
||||
|
||||
segment_index += 1;
|
||||
} else {
|
||||
let spiral_end = spiral_point(spiral_theta, inner_radius, b, spiral_type);
|
||||
let first_point = viewport.transform_point2(spiral_end);
|
||||
|
||||
let r_end = first_point.distance(viewport_center);
|
||||
|
||||
if mouse_distance <= r_end {
|
||||
let direction = DVec2::new(angle.cos(), -angle.sin());
|
||||
let radius = if is_reversed { spiral_outer.distance(DVec2::ZERO) } else { spiral_inner.distance(DVec2::ZERO) };
|
||||
let inner_point = viewport.transform_point2(radius.max(5.0) * direction);
|
||||
return Some((inner_point, first_point, segment_index));
|
||||
}
|
||||
|
||||
if angle >= (max_theta + start_angle_rad).rem_euclid(TAU) {
|
||||
let spiral_end = spiral_point(spiral_theta - TAU, inner_radius, b, spiral_type);
|
||||
let first_point = viewport.transform_point2(spiral_end);
|
||||
if mouse_distance <= first_point.distance(viewport_center) {
|
||||
let direction = DVec2::new(angle.cos(), -angle.sin());
|
||||
|
||||
let radius = if is_reversed { spiral_outer.distance(DVec2::ZERO) } else { spiral_inner.distance(DVec2::ZERO) };
|
||||
let inner_point = viewport.transform_point2(radius.max(5.0) * direction);
|
||||
|
||||
return Some((inner_point, first_point, segment_index));
|
||||
}
|
||||
}
|
||||
|
||||
segment_index -= 1;
|
||||
}
|
||||
|
||||
// Remaining segments: full spiral loops
|
||||
let mut base_theta = spiral_theta;
|
||||
while if is_reversed { base_theta >= 0.0 } else { base_theta <= max_theta } {
|
||||
while if is_reversed {
|
||||
base_theta >= (start_angle_rad).rem_euclid(TAU)
|
||||
} else {
|
||||
base_theta <= max_theta + start_angle_rad
|
||||
} {
|
||||
let theta_start = base_theta;
|
||||
let theta_end = if is_reversed { base_theta - TAU } else { base_theta + TAU };
|
||||
log::info!("segment index {:?}, theta_start {:?} ,theta_end {:?}", segment_index, theta_start.to_degrees(), theta_end.to_degrees());
|
||||
|
||||
if (!is_reversed && theta_end > max_theta) || (is_reversed && theta_end < 0.0) {
|
||||
if (!is_reversed && theta_end > max_theta + start_angle_rad) || (is_reversed && theta_end < 0.0) {
|
||||
break;
|
||||
}
|
||||
if is_reversed && (theta_start > max_theta + start_angle_rad || theta_end > max_theta + start_angle_rad) {
|
||||
base_theta -= TAU;
|
||||
segment_index -= 1;
|
||||
continue;
|
||||
}
|
||||
|
||||
let spiral_start = spiral_point(theta_start, inner_radius, b, spiral_type);
|
||||
let spiral_end = spiral_point(theta_end, inner_radius, b, spiral_type);
|
||||
|
||||
let viewport_start = viewport.transform_point2(Self::rotate_point(spiral_start, start_angle_rad));
|
||||
let viewport_end = viewport.transform_point2(Self::rotate_point(spiral_end, start_angle_rad));
|
||||
let viewport_start = viewport.transform_point2(spiral_start);
|
||||
let viewport_end = viewport.transform_point2(spiral_end);
|
||||
|
||||
let r_start = viewport_start.distance(viewport_center);
|
||||
let r_end = viewport_end.distance(viewport_center);
|
||||
|
||||
if mouse_distance >= r_start.min(r_end) && mouse_distance <= r_start.max(r_end) {
|
||||
let (point1, point2) = Self::calculate_gizmo_line_points(viewport_start, viewport_end);
|
||||
return Some((point1, point2, segment_index));
|
||||
return Some((viewport_start, viewport_end, segment_index));
|
||||
}
|
||||
|
||||
base_theta = if is_reversed { base_theta - TAU } else { base_theta + TAU };
|
||||
segment_index += 1;
|
||||
if is_reversed {
|
||||
segment_index -= 1;
|
||||
} else {
|
||||
segment_index += 1;
|
||||
}
|
||||
}
|
||||
|
||||
None
|
||||
}
|
||||
|
||||
fn rotate_point(p: DVec2, angle: f64) -> DVec2 {
|
||||
let cos_a = angle.cos();
|
||||
let sin_a = angle.sin();
|
||||
DVec2::new(p.x * cos_a - p.y * sin_a, p.x * sin_a + p.y * cos_a)
|
||||
}
|
||||
|
||||
pub fn calculate_updated_dash_lines(
|
||||
&self,
|
||||
inner_radius: f64,
|
||||
@@ -218,19 +283,32 @@ impl TightnessGizmo {
|
||||
reversed: bool,
|
||||
) -> (DVec2, DVec2) {
|
||||
let b = calculate_b(inner_radius, turns, outer_radius, spiral_type);
|
||||
let max_theta = turns * TAU + start_angle.to_radians();
|
||||
let base_angle = if reversed {
|
||||
max_theta - (TAU - self.angle - start_angle.to_radians())
|
||||
} else {
|
||||
self.angle - start_angle.to_radians()
|
||||
};
|
||||
let smaller_radius = inner_radius.min(outer_radius);
|
||||
let start_angle_rad = start_angle.to_radians();
|
||||
let max_theta = turns * TAU + start_angle_rad;
|
||||
|
||||
let base_angle = if reversed {
|
||||
self.angle + ((start_angle_rad / TAU).floor() * TAU) + turns.floor() * TAU
|
||||
} else {
|
||||
self.angle + ((start_angle_rad / TAU).floor() * TAU)
|
||||
};
|
||||
|
||||
let (start_point, end_point) = if self.spiral_slot == 0 && !reversed {
|
||||
let endpoint = spiral_point(0. + start_angle_rad, inner_radius, b, spiral_type);
|
||||
let radius = endpoint.distance(DVec2::ZERO);
|
||||
|
||||
let (start_point, end_point) = if self.spiral_slot == 0 {
|
||||
(
|
||||
viewport.transform_point2(smaller_radius * DVec2::new(base_angle.cos(), -base_angle.sin())),
|
||||
viewport.transform_point2(radius * DVec2::new(self.angle.cos(), -self.angle.sin())),
|
||||
viewport.transform_point2(spiral_point(base_angle, inner_radius, b, spiral_type)),
|
||||
)
|
||||
} else if self.spiral_slot == self.turns.floor() as i32 && reversed {
|
||||
log::info!("am i plzz reaching here");
|
||||
let radius = spiral_point(max_theta, inner_radius, b, spiral_type).distance(DVec2::ZERO);
|
||||
let endpoint = if self.angle >= (max_theta + start_angle_rad).rem_euclid(TAU) {
|
||||
viewport.transform_point2(spiral_point(base_angle - TAU, inner_radius, b, spiral_type))
|
||||
} else {
|
||||
viewport.transform_point2(spiral_point(base_angle, inner_radius, b, spiral_type))
|
||||
};
|
||||
(viewport.transform_point2(radius * DVec2::new(self.angle.cos(), -self.angle.sin())), endpoint)
|
||||
} else {
|
||||
let ref_angle = (self.spiral_slot as f64 - 1.) * TAU + base_angle;
|
||||
let end_point_angle = if reversed { ref_angle - TAU } else { ref_angle + TAU };
|
||||
@@ -240,19 +318,7 @@ impl TightnessGizmo {
|
||||
)
|
||||
};
|
||||
|
||||
Self::calculate_gizmo_line_points(start_point, end_point)
|
||||
}
|
||||
|
||||
// (start_point,end_point)
|
||||
fn calculate_gizmo_line_points(start_point: DVec2, end_point: DVec2) -> (DVec2, DVec2) {
|
||||
let length = start_point.distance(end_point);
|
||||
|
||||
let direction = (end_point - start_point).normalize_or_zero();
|
||||
|
||||
let new_endpoint = end_point - direction * length;
|
||||
let new_start_point = start_point + direction * length;
|
||||
|
||||
(new_start_point, new_endpoint)
|
||||
(start_point, end_point)
|
||||
}
|
||||
|
||||
pub fn update_outer_radius_via_dashed_lines(
|
||||
|
||||
@@ -42,8 +42,8 @@ impl ShapeGizmoHandler for SpiralGizmoHandler {
|
||||
responses: &mut VecDeque<Message>,
|
||||
) {
|
||||
// self.radius_handle.handle_actions(selected_spiral_layer, document, input.mouse.position, responses);
|
||||
self.turns_handle.handle_actions(selected_spiral_layer, mouse_position, document, responses);
|
||||
// self.tightness_handle.handle_actions(selected_spiral_layer, input.mouse.position, document, responses);
|
||||
// self.turns_handle.handle_actions(selected_spiral_layer, mouse_position, document, responses);
|
||||
self.tightness_handle.handle_actions(selected_spiral_layer, input.mouse.position, document, responses);
|
||||
}
|
||||
|
||||
fn handle_click(&mut self) {
|
||||
|
||||
Reference in New Issue
Block a user