material-components/material-components-android · error · IllegalArgumentException
Invalid fit mode: > fitMode <
Error message
Invalid fit mode: > fitMode <
What it means
FitModeEvaluators.get (FitModeEvaluators.java:132) chooses whether a MaterialContainerTransform fits the incoming/outgoing content to width or height. Only FIT_MODE_AUTO, FIT_MODE_WIDTH and FIT_MODE_HEIGHT are accepted; anything else reaches the default branch and throws IllegalArgumentException. The value comes from MaterialContainerTransform.setFitMode().
Source
Thrown at lib/java/com/google/android/material/transition/FitModeEvaluators.java:132
public void applyMask(RectF maskBounds, float maskMultiplier, FitModeResult fitModeResult) {
float currentWidthDiff =
Math.abs(fitModeResult.currentEndWidth - fitModeResult.currentStartWidth);
maskBounds.left += currentWidthDiff / 2 * maskMultiplier;
maskBounds.right -= currentWidthDiff / 2 * maskMultiplier;
}
};
static FitModeEvaluator get(
@FitMode int fitMode, boolean entering, RectF startBounds, RectF endBounds) {
switch (fitMode) {
case FIT_MODE_AUTO:
return shouldAutoFitToWidth(entering, startBounds, endBounds) ? WIDTH : HEIGHT;
case FIT_MODE_WIDTH:
return WIDTH;
case FIT_MODE_HEIGHT:
return HEIGHT;
default:
throw new IllegalArgumentException("Invalid fit mode: " + fitMode);
}
}
private static boolean shouldAutoFitToWidth(
boolean entering, RectF startBounds, RectF endBounds) {
float startWidth = startBounds.width();
float startHeight = startBounds.height();
float endWidth = endBounds.width();
float endHeight = endBounds.height();
float endHeightFitToWidth = endHeight * startWidth / endWidth;
float startHeightFitToWidth = startHeight * endWidth / startWidth;
return entering ? endHeightFitToWidth >= startHeight : startHeightFitToWidth >= endHeight;
}
private FitModeEvaluators() {}
}
View on GitHub (pinned to ac7e18efee)
Solutions
- Use MaterialContainerTransform.FIT_MODE_AUTO / FIT_MODE_WIDTH / FIT_MODE_HEIGHT.
- Whitelist-check any dynamic value before setFitMode().
- Annotate your wrapper's parameter with @FitMode so the IDE/lint flags invalid constants.
Example fix
// before transform.setFitMode(9); // after transform.setFitMode(MaterialContainerTransform.FIT_MODE_WIDTH);
Defensive patterns
Strategy: validation
Validate before calling
static @FitMode int coerceFitMode(int candidate) {
if (candidate == MaterialContainerTransform.FIT_MODE_WIDTH
|| candidate == MaterialContainerTransform.FIT_MODE_HEIGHT) return candidate;
return MaterialContainerTransform.FIT_MODE_AUTO;
}
transform.setFitMode(coerceFitMode(rawFitMode)); Type guard
static boolean isValidFitMode(int m) {
return m == MaterialContainerTransform.FIT_MODE_AUTO
|| m == MaterialContainerTransform.FIT_MODE_WIDTH
|| m == MaterialContainerTransform.FIT_MODE_HEIGHT;
} Prevention
- Use FIT_MODE_* constants only; don't interleave numeric literals.
- Keep fade-mode and fit-mode config values in distinct typed fields to avoid cross-assignment.
- Unit-test your transition-config parser with invalid ints.
When it happens
Trigger: Calling transform.setFitMode(x) with an int outside the FIT_MODE_* constant set; passing a value round-tripped through saved state or serialization without validation; mixing up constants from a different class (e.g. a fade mode constant).
Common situations: Numeric hardcoding instead of constants; copy-paste between setFadeMode and setFitMode calls; remote-config-driven transition tuning with unchecked ints.
Related errors
- Invalid fit mode: > fitMode <
- Invalid fade mode: > fadeMode <
- Invalid transition direction: > transitionDirection <
- Invalid fade mode: > fadeMode <
- Invalid transition direction: > transitionDirection <
AI-assisted analysis of material-components/material-components-android@ac7e18efee (2026-08-14).
Data as JSON: /api/errors/be66a7f6ec7ba236.
Report an issue: GitHub.