1

I'm developing a web app for a touch panel where no keyboard is available (and I want to avoid the onscreen keyboard). I have tried a number of ways to solve this problem with no joy. My latest attempt is using the Blazor Fluent UI Panel dialog, and I'm close. My last remaining problem is getting the value typed into the number pad returned to the Razor component that opened the number pad. So, the use case is:

  1. User clicks a form field (FluentTextInput) to enter a numeric value.
  2. Panel opens on the right side of the screen as a modal dialog.
  3. User enters a value with buttons that are numbers like a calculator.
  4. User clicks OK to use the value or Cancel to abort the operation.

Here's my NumPadPanel.razor implementation:

@implements IDialogContentComponent<string>

<FluentDialogBody>
    <FluentTextField ReadOnly="true" Style="width: 250px" @bind-Value="Content" /><br />
    <FluentButton Class="num-pad-btn" @onclick="@((e) => AddDigit(e, 1))">1</FluentButton>
    <FluentButton Class="num-pad-btn" @onclick="@((e) => AddDigit(e, 2))">2</FluentButton>
    <FluentButton Class="num-pad-btn" @onclick="@((e) => AddDigit(e, 3))">3</FluentButton><br />
    <FluentButton Class="num-pad-btn" @onclick="@((e) => AddDigit(e, 4))">4</FluentButton>
    <FluentButton Class="num-pad-btn" @onclick="@((e) => AddDigit(e, 5))">5</FluentButton>
    <FluentButton Class="num-pad-btn" @onclick="@((e) => AddDigit(e, 6))">6</FluentButton><br />
    <FluentButton Class="num-pad-btn" @onclick="@((e) => AddDigit(e, 7))">7</FluentButton>
    <FluentButton Class="num-pad-btn" @onclick="@((e) => AddDigit(e, 8))">8</FluentButton>
    <FluentButton Class="num-pad-btn" @onclick="@((e) => AddDigit(e, 9))">9</FluentButton><br />
    <FluentButton Class="num-pad-btn" @onclick="ClearInput">Clear</FluentButton>
    <FluentButton Class="num-pad-btn" @onclick="@((e) => AddDigit(e, 0))">0</FluentButton>
    <FluentButton Class="num-pad-btn" @onclick="Backspace">Backspace</FluentButton><br />
</FluentDialogBody>

@code {
    [Parameter]
    public string Content { get; set; } = string.Empty;

    public void AddDigit(MouseEventArgs e, int digit)
    {
        Content += digit.ToString();
        StateHasChanged();
    }

    public void ClearInput()
    {
        Content = string.Empty;
    }

    public void Backspace()
    {
        if (Content.Length > 0)
        {
            Content = Content.Substring(0, Content.Length - 1);
        }
    }
}

Here's the code for the host component that opens the Panel for input:

<FluentTextField Label="kW Command" 
                 Appearance="FluentInputAppearance.Outline"
                 Value="@RealPowerCmd"
                 Style="width: 75px" 
                 @onclick="OpenDialogRealPower" />

@code {
    private IDialogReference? _dialog;
    private string RealPowerCmd { get; set; } = "0";

    private async Task OpenDialogRealPower()
    {
        var parameters = new DialogParameters<string>()
        {
            Content = RealPowerCmd,
            Alignment = HorizontalAlignment.Right,
            PrimaryAction = "OK",
            SecondaryAction = "Cancel"
        };
        _dialog = await DialogService.ShowPanelAsync<NumPadPanel>(RealPowerCmd, parameters);
        DialogResult result = await _dialog.Result;
        if (result.Cancelled)
        {
            return;
        }
        if (result.Data is not null)
        {
            var inputValue = result.Data as string;
            RealPowerCmd = inputValue!;
            StateHasChanged();
        }
    }
}

inputValue does not return the value the user entered.

1
  • I think the Dialog is closing. See stackoverflow.com/questions/59760040/… Do same in c# WinForm I have to stop dialog from closing, make form invisible. Then form still exists so I can read the dialog results. Commented Jul 9 at 21:42

1 Answer 1

1

I found the answer myself so I thought I'd post it here. I changed the Content type to be a class with one public property of string type, and then the dialog worked as expected. I did this because the example I was following used a class. I expected that a string would also work as the Content type because it is a reference type, not a value type, but it does not.

Here is the code from the NumPadPanel.cs file that I changed:

@code {
    [Parameter]
    public PowerCommand Content { get; set; } = default!;

...

and here is the PowerCommand class:

public class PowerCommand(string value)
{
    public string Value { get; set; } = value;
}

Hope this helps someone. If anybody can explain why the string type does not work, I'd love to hear it!

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.