Maui Blazor 中文社区 QQ群:645660665

Bootstrap Blazor UI 库小技巧 (持续更新)

1. 文本处理键盘按键

<Bootstrap Blazorclass="table-toolbar-search" placeholder="@SearchPlaceholderText" @onkeyup="OnSearchKeyUp" @bind-Value="@SearchText">
</BootstrapInput>

@code{
    private async Task OnSearchKeyUp(KeyboardEventArgs args)
    {
        if (args.Key == "Enter")
        {
            await SearchClick();
        }
        else if (args.Key == "Escape")
        {
            await ClearSearchClick();
        }
    }
}

2. 文本框逐字搜索

UseInputEvent: 是否在文本框输入值时触发 bind-value:event="oninput" 默认 false

<BootstrapInput @bind-Value="value" ShowLabel="true" UseInputEvent="true" />

@value

@code{
    [DisplayName("条码文字")]
    private string? value { get; set; } = "12345";

}

3. Ajaxs 请求处理参数大小写

    private async Task ProcessResponse(string userName, string password)
    {
        var option = new AjaxOption()
        {
            Url = "/api/Login",
            Data = new User() { UserName = userName, Password = password }
        };
        var result = await AjaxService.InvokeAsync(option);
        if (result == null)
        {
            ResultMessage = "Login failed";
        }
        else
        {
            if (200 == result.RootElement.GetProperty("code").GetInt32())
            {
                await SwalService.Show(new SwalOption() { Content = "Login success!", Category = SwalCategory.Success });
            }
            else
            {
                await SwalService.Show(new SwalOption() { Content = $"Login failed: {result.RootElement.GetProperty("message").GetString()}", Category = SwalCategory.Error });
            }
        }
    }

    class User
    {
        [JsonPropertyName("uSErnaMe22222")]
        public string? UserName { get; set; }

        public string? Password { get; set; }
    }

4. 文本框获取焦点事件(触摸屏应用)

<BootstrapInput ShowLabel="true"
                @bind-Value="@one"
                @onfocus="_=>OnFocus(0)"/>
<BootstrapInput ShowLabel="true"
                @bind-Value="@two"
                @onfocus="_=>OnFocus(1)"/>

<Button class="m-1" Text="abc" Color="Color.Success" OnClick='_=>OnKeyBoardsItemClick("abc")' />
<Button class="m-1" Text="def" Color="Color.Success" OnClick='_=>OnKeyBoardsItemClick("def")' />

@code{

    string one="one";
    string two = "two";

    int mode;
    private Task OnFocus(int v)
    {
        mode = v;
        return Task.CompletedTask;
    }

    //触摸按钮点击
    private Task OnKeyBoardsItemClick(string v)
    {
        switch (mode)
        {
            case 1:
                two = v;
                break;
            default:
                one = v;
                break;
        }
        return Task.CompletedTask;
    }
}

5. 模板取消链接默认点击事件

模板默认带了链接 <a href="#" 导致点击后回到主页, 如果要停留在当前页,需要取消事件的默认行为

https://www.jianshu.com/p/c933de9249c7

<Logout>
  <LinkTemplate>
    <a @onclick="@(e => IsOpen = !IsOpen)" @onclick:stopPropagation><i class="fa-solid fa-cog"></i>设置</a>
  </LinkTemplate>
</Logout>

6. Segmented 超出宽度显示滚动条

<Segmented TValue="Dto" Items="@Items" class="over-x-bar-thin" />
.over-x-bar-thin { 
    width: 100%;
    scrollbar-width: thin;
    overflow-x: auto;
}

7. 制作无软键盘弹出焦点的输入框

<BootstrapInput inputmode="none"/>

8. 关闭点击表格行自定义操作按钮栏冒泡事件, 避免点击行事件执行

点击 PopConfirmButton 按钮不触发 OrderListItemClick
点击 Button 按钮不触发 OrderListItemClick

<Table OnClickRowCallback="OrderListItemClick">
  <TableColumns>
    <TableColumn>
      <Template>
        <div @onclick:stopPropagation="true">
          <PopConfirmButton />
          <Button />
        </div>
      </Template>
      </TableColumn>
  </TableColumns>
</Table>

9. 屏幕键盘组件技巧

BootstrapInput 绑定变量 int?, 这样没有默认值,比较清爽
不能带 FormatString , 不然会一直格式化,表现很糟糕

public int? PurchasePlan { get; set; }

<OnScreenKeyboard ClassName="virtualkeyboard" Option="Option1" />
<BootstrapInput @bind-Value="v.Row.PurchasePlan" class="virtualkeyboard" data-kioskboard-type="numpad" style="max-width:70px;" />

@code{
    static Dictionary<string, string> keys1 = new Dictionary<string, string>() { { "0", "." } };
    static List<Dictionary<string, string>> keysArray = new List<Dictionary<string, string>>() { keys1 };
    KeyboardOption Option1 = new KeyboardOption()
    {
        keysArrayOfObjects = keysArray,
        keysFontFamily = "Barlow",
        keysFontWeight = "800",
        keysAllowSpacebar=false
    };
}

遇到需要输入小数情况,可以拆分为两个输入框分别绑定 int? 类型输入整数和小数,代码再合并数值.

                            @{
                                var pricePurchase = (v.Row as ResProductsPro).PricePurchase;
                                int? p1=null;
                                int? p2 = null;
                                if (v.Row.PricePurchasePlan == null && pricePurchase != 0)
                                {
                                    p1 = (int)Math.Truncate(pricePurchase);
                                    p2 = (int)((pricePurchase - Math.Truncate(pricePurchase)) * 100);
                                }
                            }
                            <BootstrapInput @bind-Value="v.Row.PricePurchasePlan" PlaceHolder="@p1.ToString()" class="virtualkeyboard" data-kioskboard-type="numpad" style="max-width:50px;" />
                            <BootstrapInputGroupLabel DisplayText="." />
                            <BootstrapInput @bind-Value="v.Row.PricePurchasePlan2" PlaceHolder="@p2.ToString()" class="virtualkeyboard" data-kioskboard-type="numpad" style="max-width:50px;" />

@code{
        if (item.PricePurchasePlan != null || item.PricePurchasePlan2 != null)
        {
            item.PricePurchase = ((item.PricePurchasePlan ?? 0) + (item.PricePurchasePlan2 ?? 0) / 100);
        }
}

10. JS组件

使用bb封装的js组件 JSModuleAutoLoader 可以达到事半功倍的效果,例如实现一个跟webview2交互

HybridMessage.razor

@namespace AmeTouch.Component
@inherits BootstrapModuleComponentBase

<span id="webMessageId" data="@Id" />

HybridMessage.razor.cs

[JSModuleAutoLoader("./_content/JovenRes.Shared/Component/HybridMessage.razor.js", JSObjectReference = true)]
public partial class HybridMessage
{
    protected override Task InvokeInitAsync() => InvokeVoidAsync("init", Id, Interop);

    [JSInvokable]
    public Task<string> WebMessage(string command, string arg)
    {        
        return Task.FromResult("OK");
    }
}

HybridMessage.razor.js

import Data from "../../BootstrapBlazor/modules/data.js"
export function init(id, invoke) { 
    const _invoke =invoke 
    Data.set(id, _invoke) 
}

window.webMessage = function (cmd, message) {
    const id = document.getElementById('webMessageId').getAttribute('data')
    const invoke = Data.get(id)
    invoke.invokeMethodAsync('WebMessage', cmd, message)
        .then(data => {
            console.log(data);
        });
}

export function dispose(id) {
    const invoke = Data.get(id)
    Data.remove(id) 
}

wpf webview2交互

public MainWindow()
{
    InitializeComponent();
    this.StateChanged += async (s, e) => await MainWindow_StateChangedAsync();

    private async Task MainWindow_StateChangedAsync()
    {
        await webView.ExecuteScriptAsync($"webMessage('windowStateChanged','{this.WindowState}')");
    }
}
posted @ 2023-12-10 20:10  AlexChow  阅读(1340)  评论(2编辑  收藏  举报