Merge pull request #933 from storytold/fix/921-properties-gradient
Fix #921: the Properties panel's Gradient section with Type and Draw
This commit is contained in:
commit
fe2d2ca173
File diff suppressed because one or more lines are too long
|
|
@ -95,6 +95,43 @@ fn dragged_stops(origin: &[GradientStop], i: usize, offset: f32, copy: bool, ove
|
|||
|
||||
// ---------- shared edits ----------
|
||||
|
||||
/// The Type row: Linear, Radial and Freeform for the paint behind the active proxy (one of them
|
||||
/// lit when it is a gradient). The Gradient panel's and the Properties panel's.
|
||||
pub(crate) fn type_row(app: &mut VectorcraftApp, ui: &mut Ui) {
|
||||
let kind = current(app).map(|g| g.gradient.kind);
|
||||
ui.horizontal(|ui| {
|
||||
widgets::dim_label(ui, tl!("Type:"));
|
||||
for (k, icon, tip) in [
|
||||
(GradientKind::Linear, "dc-grad-linear", tl!("Linear Gradient")),
|
||||
(GradientKind::Radial, "dc-grad-radial", tl!("Radial Gradient")),
|
||||
(GradientKind::Freeform, "dc-grad-freeform", tl!("Freeform Gradient")),
|
||||
] {
|
||||
if widgets::icon_button(ui, icon, tip, kind == Some(k), 24.0).clicked() {
|
||||
edit(app, json!({"kind": k.label().to_lowercase()}), Live::Released);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/// Set how the Gradient tool adds the points of the freeform gradient behind the active proxy.
|
||||
fn set_draw_mode(app: &mut VectorcraftApp, mode: FreeformMode) {
|
||||
edit(app, json!({ "mode": mode.label().to_lowercase() }), Live::Released);
|
||||
}
|
||||
|
||||
/// The Properties panel's Draw row for a freeform gradient: Points and Lines as radio buttons.
|
||||
pub(crate) fn draw_radios(app: &mut VectorcraftApp, ui: &mut Ui) {
|
||||
let Some(g) = current(app).filter(|g| g.gradient.kind == GradientKind::Freeform) else { return };
|
||||
let mode = shown_points(&g).mode;
|
||||
ui.horizontal(|ui| {
|
||||
widgets::dim_label(ui, tl!("Draw:"));
|
||||
for (m, label) in [(FreeformMode::Points, tl!("Points")), (FreeformMode::Lines, tl!("Lines"))] {
|
||||
if widgets::radio(ui, label, mode == m, true) && mode != m {
|
||||
set_draw_mode(app, m);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/// The gradient behind the active proxy.
|
||||
fn current(app: &VectorcraftApp) -> Option<GradientPaint> {
|
||||
match active_paint(app) {
|
||||
|
|
@ -184,18 +221,7 @@ pub fn show(app: &mut VectorcraftApp, ui: &mut Ui) {
|
|||
}
|
||||
ui.add_space(4.0);
|
||||
ui.vertical(|ui| {
|
||||
ui.horizontal(|ui| {
|
||||
widgets::dim_label(ui, tl!("Type:"));
|
||||
for (k, icon, tip) in [
|
||||
(GradientKind::Linear, "dc-grad-linear", tl!("Linear Gradient")),
|
||||
(GradientKind::Radial, "dc-grad-radial", tl!("Radial Gradient")),
|
||||
(GradientKind::Freeform, "dc-grad-freeform", tl!("Freeform Gradient")),
|
||||
] {
|
||||
if widgets::icon_button(ui, icon, tip, is_grad && kind == k, 24.0).clicked() {
|
||||
edit(app, json!({"kind": k.label().to_lowercase()}), Live::Released);
|
||||
}
|
||||
}
|
||||
});
|
||||
type_row(app, ui);
|
||||
if widgets::flat_button(ui, tl!("Edit Gradient"), 96.0).clicked() {
|
||||
app.select_tool("gradient");
|
||||
}
|
||||
|
|
@ -297,7 +323,7 @@ fn freeform_section(app: &mut VectorcraftApp, ui: &mut Ui, g: &GradientPaint) {
|
|||
(FreeformMode::Lines, "spline", tl!("Lines: clicks add points joined by a line")),
|
||||
] {
|
||||
if widgets::icon_button(ui, icon, tip, mode == m, 24.0).clicked() && mode != m {
|
||||
edit(app, json!({ "mode": m.label().to_lowercase() }), Live::Released);
|
||||
set_draw_mode(app, m);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
|
|
|||
|
|
@ -40,6 +40,13 @@ pub fn show(app: &mut VectorcraftApp, ui: &mut Ui) {
|
|||
}
|
||||
transform_section(app, ui);
|
||||
divider(ui);
|
||||
// The Gradient tool: the gradient's type and, for a freeform one, how clicks add points (#921).
|
||||
if app.session.tool_id() == "gradient" {
|
||||
section_header(ui, tl!("Gradient"));
|
||||
super::gradient::type_row(app, ui);
|
||||
super::gradient::draw_radios(app, ui);
|
||||
divider(ui);
|
||||
}
|
||||
let is_image = n_sel == 1 && matches!(first.as_ref().map(|n| &n.kind), Some(NodeKind::Image(_)));
|
||||
if is_image {
|
||||
image_section(app, ui);
|
||||
|
|
@ -563,6 +570,31 @@ mod tests {
|
|||
frame(app, ctx, vec![b(false)]);
|
||||
}
|
||||
|
||||
/// #921: with the Gradient tool, a Gradient section: the type, and for a freeform gradient
|
||||
/// Draw as Points or Lines radio buttons.
|
||||
#[test]
|
||||
fn the_gradient_tool_shows_the_gradient_type_and_draw() {
|
||||
let mut app = VectorcraftApp::new(Session::new(), Default::default());
|
||||
app.run("file.new", json!({"width": 200, "height": 100})).unwrap();
|
||||
let id = app.run("shape.rectangle", json!({"x": 10, "y": 10, "width": 50, "height": 40})).unwrap()["id"].as_u64().unwrap();
|
||||
app.run("paint.setFill", json!({"gradient": {}})).unwrap();
|
||||
let ctx = egui::Context::default();
|
||||
let has = |texts: &[(String, Rect)], s: &str| texts.iter().any(|(t, _)| t == s);
|
||||
let texts = frame(&mut app, &ctx, vec![]);
|
||||
assert!(!has(&texts, "Gradient"), "only with the Gradient tool");
|
||||
app.select_tool("gradient");
|
||||
let texts = frame(&mut app, &ctx, vec![]);
|
||||
assert!(has(&texts, "Gradient") && has(&texts, "Type:") && !has(&texts, "Draw:"), "{texts:?}");
|
||||
app.run("paint.editGradient", json!({"kind": "freeform"})).unwrap();
|
||||
frame(&mut app, &ctx, vec![]);
|
||||
let texts = frame(&mut app, &ctx, vec![]);
|
||||
assert!(has(&texts, "Draw:") && has(&texts, "Points") && has(&texts, "Lines"), "{texts:?}");
|
||||
click(&mut app, &ctx, &texts, "Lines");
|
||||
let fill = app.session.doc().unwrap().doc.node(vectorcraft_doc::NodeId(id)).unwrap().appearance.fill_paint();
|
||||
let vectorcraft_color::Paint::Gradient(g) = fill else { panic!("{fill:?}") };
|
||||
assert_eq!(super::super::gradient::shown_points(&g).mode, vectorcraft_color::FreeformMode::Lines);
|
||||
}
|
||||
|
||||
/// #696: the number fields are all as wide: the Transform fields, the rotation, the corner
|
||||
/// radius, Opacity and the stroke weight.
|
||||
#[test]
|
||||
|
|
|
|||
Loading…
Reference in New Issue