stride3d/stride · error · InvalidOperationException
Converter is null but following Converter is not null
Error message
Converter{i} is null but following Converter{i + 1} is not null What it means
ChainedConverter.ConvertBack walks the converters in reverse; a null converter before conversion starts is skipped, but once conversion has started, encountering a null converter followed by a non-null one is an invalid chain layout. ConvertBack throws this InvalidOperationException to flag the inconsistent configuration.
Solutions
- Remove or null out all converters after the gap so non-null converters are contiguous from Converter0
- Fill the gap with an appropriate converter (or a pass-through) if the later converter is needed
- Mark the binding OneWay to avoid ConvertBack if back-conversion is undesired
- Restructure into multiple smaller chained converters without holes
Example fix
// before
var chained = new Chained { Converter = c0, Converter1 = null, Converter2 = c2 };
// after
var chained = new Chained { Converter = c0, Converter1 = passThrough, Converter2 = c2 }; Defensive patterns
Strategy: type-guard
Validate before calling
object[] converters = { ch.Converter, ch.Converter1, ch.Converter2 };
if (!IsContiguousPrefix(converters)) throw new InvalidOperationException("Converter chain has a null gap"); Type guard
static bool IsContiguousPrefix(object[] converters) => converters.TakeWhile(c => c != null).Count() == converters.Count(c => c != null);
Try / catch
try { var back = chained.ConvertBack(value, targetType, param, culture); } catch (InvalidOperationException ex) when (ex.Message.Contains("following Converter")) { return Binding.DoNothing; } Prevention
- Use OneWay bindings when ConvertBack is not required
- Audit two-way bindings for full converter chains
- Avoid null holes by renumbering after edits
- Cover ConvertBack in converter unit tests
When it happens
Trigger: A converter chain where ConverterN is null while ConverterN+1 is non-null, exercised on a two-way binding so ConvertBack runs (e.g. Converter0 set, Converter1 null, Converter2 set, and the target writes back to the source).
Common situations: One-way bindings set up in XAML that later become TwoWay; the hole in the chain goes unnoticed until an edit triggers ConvertBack; renumbering mistakes after removing a converter.
Understand the failure class
Background: "Invalid value" and "allowed values are" config errors: what your library rejected and how to fix it — this error's family across 41 libraries.
Related errors
- Converter is not null but previous Converter was null
- This behavior must be attached to an instance of…
- The OnComboBoxClosedWithSelectionBehavior must be attached…
- The OnSelectionChangedWithSelectionBehavior must be…
- Cannot listen on an unusable interface. Check the IsUsable…
AI-assisted analysis of stride3d/stride@96fad776d2 (2026-09-14).
Data as JSON: /api/errors/656b0e8f2a53c794.
Report an issue: GitHub.
Appendix: source
Thrown at sources/presentation/Stride.Core.Presentation.Avalonia/Converters/Chained.cs:285
}
return output;
}
/// <inheritdoc/>
public object? ConvertBack(object? value, Type targetType, object? parameter, CultureInfo culture)
{
var output = value;
var conversionStarted = false;
for (var i = MaxConverterCount - 1; i >= 0; --i)
{
var input = output;
if (converters[i] == null)
{
if (!conversionStarted)
continue;
throw new InvalidOperationException($"Converter{i} is null but following Converter{i + 1} is not null");
}
conversionStarted = true;
var type = converterTargetType[i] ?? (i == 0 ? targetType : typeof(object));
output = converters[i]!.ConvertBack(input, type, converterParameters[i], culture);
}
return output;
}
}
View on GitHub (pinned to 96fad776d2)