@using CutList.Core.Formatting
@if (HasError) {
@ErrorMessage
}
@code { /// /// Non-nullable decimal value binding. /// [Parameter] public decimal Value { get; set; } [Parameter] public EventCallback ValueChanged { get; set; } /// /// Nullable decimal value binding (used for optional dimension fields). /// Takes precedence over Value if both ValueChanged and NullableValueChanged are set. /// [Parameter] public decimal? NullableValue { get; set; } [Parameter] public EventCallback NullableValueChanged { get; set; } [Parameter] public string Placeholder { get; set; } = "e.g., 12' 6\" or 144"; private string DisplayValue { get; set; } = string.Empty; private bool HasError { get; set; } private string ErrorMessage { get; set; } = string.Empty; private decimal? _lastValue; private bool IsNullableMode => NullableValueChanged.HasDelegate; private decimal? CurrentValue => IsNullableMode ? NullableValue : Value; protected override void OnParametersSet() { // Reset display when Value changes externally (e.g., form reset) if (CurrentValue != _lastValue) { _lastValue = CurrentValue; if (CurrentValue.HasValue && CurrentValue.Value > 0) { DisplayValue = ArchUnits.FormatFromInches((double)CurrentValue.Value); } else { DisplayValue = string.Empty; HasError = false; ErrorMessage = string.Empty; } } } private async Task OnInputChange(ChangeEventArgs e) { var input = e.Value?.ToString() ?? string.Empty; DisplayValue = input; HasError = false; ErrorMessage = string.Empty; if (string.IsNullOrWhiteSpace(input)) { _lastValue = null; if (IsNullableMode) { await NullableValueChanged.InvokeAsync(null); } else { await ValueChanged.InvokeAsync(0); } return; } try { // Try to parse as architectural units var inches = ArchUnits.ParseToInches(input); _lastValue = (decimal)inches; if (IsNullableMode) { await NullableValueChanged.InvokeAsync(_lastValue); } else { await ValueChanged.InvokeAsync(_lastValue.Value); } } catch { // Try to parse as plain decimal (inches) if (decimal.TryParse(input, out var decimalValue)) { _lastValue = decimalValue; if (IsNullableMode) { await NullableValueChanged.InvokeAsync(decimalValue); } else { await ValueChanged.InvokeAsync(decimalValue); } } else { HasError = true; ErrorMessage = "Invalid format. Use feet (12'), inches (6\"), or decimal (144)"; } } } private void OnBlur() { // Format the display value nicely on blur if we have a valid value if (!HasError && _lastValue.HasValue && _lastValue.Value > 0) { DisplayValue = ArchUnits.FormatFromInches((double)_lastValue.Value); } } public static string FormatLength(decimal inches) { return ArchUnits.FormatFromInches((double)inches); } }