Yalantis/uCrop · error · CImgArgumentException
[cimg_appname_math_parser] CImg<%s>::%s: %s: Invalid type '%
Error message
[cimg_appname_math_parser] CImg<%s>::%s: %s: Invalid type '%s' for variable '%s' (expected 'scalar'), in expression '%s'.
What it means
For 3-argument loops, the named loop variable must be an existing, non-constant scalar variable slot. After resolving the variable position, CImg checks is_scalar(slot) && !is_const_scalar(slot); if the variable is a vector type or was declared constant, it throws this error reporting the actual type via s_type(arg2).
Source
Thrown at ucrop/src/main/jni/CImg.h:21794
if (s1<se1) { // Version with 3 arguments
variable_name.assign(s0,(unsigned int)(s1 + 1 - s0)).back() = 0;
cimg::strpare(variable_name,false,true);
if (!cimg::is_varname(variable_name)) { // Invalid variable name
cimg::strellipsize(variable_name,64);
_cimg_mp_strerr;
throw CImgArgumentException("[" cimg_appname "_math_parser] "
"CImg<%s>::%s: %s: Invalid loop variable name '%s', "
"in expression '%s'.",
pixel_type(),_cimg_mp_calling_function,s_op,
variable_name._data,s0);
}
get_variable_pos(variable_name,arg2,arg3);
arg2 = arg3!=~0U?reserved_label[arg3]:arg2!=~0U?variable_pos[arg2]:~0U; // Variable slot
if (arg2!=~0U && (!is_scalar(arg2) ||
is_const_scalar(arg2))) { // Variable is not a vector or is a constant->error
cimg::strellipsize(variable_name,64);
_cimg_mp_strerr;
throw CImgArgumentException("[" cimg_appname "_math_parser] "
"CImg<%s>::%s: %s: Invalid type '%s' for variable '%s' "
"(expected 'scalar'), in expression '%s'.",
pixel_type(),_cimg_mp_calling_function,s_op,
s_type(arg2)._data,variable_name._data,s0);
} else if (arg2==~0U) { // Variable does not exist -> create it
arg2 = scalar();
if (arg3!=~0U) reserved_label[arg3] = arg2;
else {
if (variable_def._width>=variable_pos._width) variable_pos.resize(-200,1,1,1,0);
variable_pos[variable_def._width] = arg2;
variable_name.move_to(variable_def);
}
memtype[arg2] = -1;
}
arg3 = compile(++s1,se1,depth1,0,block_flags);
_cimg_mp_check_type(arg3,3,1,0);
} else { // Version with 2 arguments
arg2 = ~0U;View on GitHub (pinned to f788b534b4)
Solutions
- Use a plain scalar variable as the loop variable (declare with `x = 0` before the loop, not vector())
- Rename the loop variable so it doesn't shadow a vector or reserved constant (pi, e, w, h, d, s...)
- Initialize the variable with a non-constant expression so it gets a mutable scalar slot
- Use the 2-argument loop form with an implicit counter variable
Example fix
// before
img.fill("v = vector(3); for(v, 0, 5, ...)" ); // v is a vector
// after
img.fill("i = 0; for(i, 0, 5, ...)"); Defensive patterns
Strategy: validation
Validate before calling
// Before a 3-arg loop, ensure the counter variable is declared as a plain mutable scalar:
// "i = 0; for(i, 0, n, ...)" — never reuse a vector() variable as the counter.
boolean loopVarIsScalarDecl(String expr, String var) {
return expr.matches("(?s).*\\b" + var + "\\s*=\\s*[-+0-9.].*\\bfor\\s*\\(\\s*" + var + "\\b.*");
} Try / catch
try { img.fill(expr); } catch (CImgArgumentException e) { if (e.getMessage().contains("Invalid type") && e.getMessage().contains("expected 'scalar'")) { throw new IllegalArgumentException("Loop variable must be a mutable scalar, not a vector or constant"); } throw e; } Prevention
- Declare loop counters with a scalar initializer (e.g. i = 0) before the loop
- Never use vector variables or reserved constants (pi, e, w, h, d, s) as loop counters
- Keep loop variable names unique to avoid shadowing vectors
When it happens
Trigger: Using a vector variable as a loop variable (`for(v..., ...)` where v=vector(...)), or a variable captured as a constant (e.g. a constant literal binding or a const-folded slot), in `for`/`while`/`repeat` expressions compiled by fill()/evaluate().
Common situations: Reusing an existing vector name for the loop counter; declaring the variable with a constant expression that the parser marked const; shadowing a built-in constant name (pi, e, w, h, d, s) as loop variable.
Understand the failure class
Background: Type mismatch errors: IllegalArgumentException, TypeError and type guards across 150 open-source libraries — this error's family across 150 libraries.
Related errors
- [cimg_appname_math_parser] CImg<%s>::%s: %s: Invalid types i
- [" cimg_appname "_math_parser] CImg<%s>::%s: %s%s %s%s has i
- CImg(): Invalid construction request of a (%u,%u,%u,%u) shar
- assign(): Invalid assignment request of shared instance from
- [cimg_appname_math_parser] CImg<%s>::%s: %s: Too much specif
AI-assisted analysis of Yalantis/uCrop@f788b534b4 (2026-09-08).
Data as JSON: /api/errors/43da8c7ab5aa1d53.
Report an issue: GitHub.