Commands: Transform Each, artboards and more refuse a boolean or number given as text

object.transformEach refused reflectX, reflectY, random and copy given
as text, but read strokes, corners, objects and patterns given as text
as the key left out. With Scale Strokes & Effects on,
{"scaleH": 200, "scaleV": 200, "strokes": "false"} scaled the stroke,
recorded an undo step and kept the params for Transform Again, which
repeated the call. artboard.rearrange, artboard.move and
artboard.duplicate read their patterns option the same way, and
artboard.setProps reads its patterns, strokes and corners options the
same way.

These commands now refuse such a value with "`<key>` must be true or
false" before they change anything. So do the other options and
numbers of artboard.setProps and artboard.move, the art of Duplicate,
Copy and Cut Artboard, the shape commands and path.create, path.close,
path.setHandle, path.moveAnchors, the Pencil, Curvature, Reshape
Segment and Blob Brush options, text.create, text.createInPath,
text.setRangeStyle, text.editRange, text.getRange, text.touchType,
text.areaOptions, type.step, the font size steps,
type.opticalMarginAlignment, type.systemLayout, type.fractionalWidths,
type.ruby, the symbol and swatch commands, the Appearance panel's
commands, the gradient and freeform gradient commands, Shape Builder,
Live Paint, Image Trace, the opacity of object.setProps, the radius,
sides and relativeRadii of object.setLiveShape, the reference point of
object.setBounds and the artboard of Align, Distribute and Distribute
Spacing. They refuse a number given as text with "`<key>` must be a
number, not <value>", and a gradient stop's tint with "stop <n>:
`tint` must be a number". A null still reads as the key left out.

Docs: docs/mcp.md, docs/target-app-parity.md.
This commit is contained in:
dotCooCoo
2026-10-22 06:40:27 +07:00
committed by bflatastic
parent f64db69b53
commit caa6962508
31 changed files with 761 additions and 82 deletions
+10 -3
View File
@@ -117,7 +117,12 @@ pub(crate) fn link_stops(d: &Document, v: &Value) -> Parsed<Value> {
if d.swatch(&name).is_none() && st.get("color").is_some() {
continue;
}
let tint = st.get("tint").and_then(Value::as_f64).map(|t| (t / 100.0).clamp(0.0, 1.0) as f32);
let tint = st
.get("tint")
.filter(|v| !v.is_null())
.map(|v| v.as_f64().ok_or_else(|| format!("stop {i}: `{k}` must be a number", k = "tint")))
.transpose()?;
let tint = tint.map(|t| (t / 100.0).clamp(0.0, 1.0) as f32);
let Paint::Solid { color, swatch, tint } = swatch_solid(d, &name, tint).map_err(|e| format!("stop {i}: {e}"))? else {
continue;
};
@@ -372,7 +377,9 @@ pub(crate) fn apply_gradient_edit_in(
fn edit_gradient(s: &mut Session, p: &Value) -> Result<Value> {
const C: &str = "paint.editGradient";
let item = item_target(s, p, C)?;
let stroke = edits_stroke(s, p, item, !s.fill_active)?;
let stroke = edits_stroke(s, p, item, !s.fill_active, C)?;
check_switches(p, &["reverse"], C)?;
check_numbers(p, &["angle"], C)?;
let item = item.of_kind(s, !stroke);
let ids = item.targets(s, p)?;
// How the gradient lies on a stroke (the panel's Stroke buttons).
@@ -554,7 +561,7 @@ fn set_gradient_geom(s: &mut Session, p: &Value) -> Result<Value> {
}
let p = &p;
let item = item_target(s, p, C)?;
let stroke = edits_stroke(s, p, item, !s.fill_active)?;
let stroke = edits_stroke(s, p, item, !s.fill_active, C)?;
let item = item.of_kind(s, !stroke);
let targets = match item {
ItemTarget::Top => leaf_targets(s, &ids_param(p, "ids").map_or_else(|| selected_roots(s), |ids| Ok(outermost(&s.doc()?.doc, ids)))?)?,