在ERP系統中,採集一線的生產數據是重要工作之一,而稱重計量是企業的核心資產數據,人工計重費時費力,還容易出錯,重量數據是否正確,直接影響企業的採購或銷售額。基於此,由系統對接電子秤實現自動抓取數據是企業管理的第一步。 電子秤,一般由重量感測器、砝碼、底座、儀錶等組成。儀錶與感測器相連,儀錶一般具有 ...
Web應用程式的可以通過URL將多個頁面串聯起來,並且可以互相跳轉。Web應用主要是使用a標簽或者是服務端redirect來跳轉。而現在流行的單頁應用程式 (SPA) ,則通過路由(Router)來實現跳轉,如Vue 、React等。
目錄
提示
MAUI的路由與Blazor路由有很大區別。
MAUI Blazor的路由
在.NET MAUI Blazor應用中,路由是遵循Blazor
的路由規則。也是通過路由組件(Router)實現的,打開Main.razor
可以看到:
<Router AppAssembly="@typeof(Main).Assembly">
<Found Context="routeData">
<RouteView RouteData="@routeData" DefaultLayout="@typeof(MainLayout)" />
<FocusOnNavigate RouteData="@routeData" Selector="h1" />
</Found>
<NotFound>
<LayoutView Layout="@typeof(MainLayout)">
<p role="alert">Sorry, there's nothing at this address.</p>
</LayoutView>
</NotFound>
</Router>
<!--設置容器-->
<AntContainer />
在Router
有兩個子節點Found
與NotFound
。
- Found節點包含一個RouteView的定義,如果找到了路由定義就通過RouteView來呈現對應的頁面,同時為所有頁面指定預設的模板。
- NotFound節點包含一個LayoutView的定義,如果沒找到路由定義則呈現一個特定的頁面,這裡使用的預設模板是
MainLayout
,也可以自己實現一個。
定義MAUI Blazor路由
在MAUI Blazor中,路由的定義使用@page
指令進行指定。在創建Blazor
組件的時候,必須包含@page '路徑"
。
MAUI路由與MAUI Blazor路由有很大區別
MAUI創建路由是根據Route屬性或者通過 Routing.RegisterRoute顯式的註冊路由。
MAUI Blazor 則是在組件上,使用@page指令指定。
Visual Studio 2022編譯器在編譯帶有 @page 指令的 Razor 組件 (.razor) 時,將為組件類提供一個 RouteAttribute 來指定組件的路由。
當應用程式啟動時,應用程式將掃描由Router組件中AppAssembly屬性指定的程式集,收集程式集中具有 RouteAttribute 的Blazor組件的路由信息。
在應用程式運行時,RouteView 組件:
- 從 Router 接收 RouteData 以及所有路由參數。
- 使用指定的組件的佈局來呈現該組件,包括任何後續嵌套佈局。
提示
Router 不與查詢字元串值交互。
匹配到路由時
我們在上次代碼的基礎上,增加一個頁面。在Pages
目錄下,新建一個Blazor組件:pdf.razor
。創建完成後,預設代碼是這樣的:
<h3>pdf</h3>
@code {
}
我們使用@page
指令指定路由為pdf
。並寫上幾個大字。
@page "/PDF"
<Title Level="1">使用iTextSharp生成PDF文件</Title>
然後打開MainLayout.razor
,給菜單增加一個MenuDataItem
。
new MenuDataItem
{
Path = "/PDF",
Name = "PDF",
Key = "PDF",
Icon = "file-pdf"
}
註意:
Blazor組件必須是大寫字母開頭,如果使用小寫字母開頭,編譯的時候,會報一個錯:
Component 'xxx' starts with a lowercase character. Component names cannot start with a lowercase character
xxx是組件的名字。
看下運行的效果:
未匹配到路由時
如果未匹配到路由,則會呈現上面的NotFound
節點定義的內容。先把NotFound
節點的內容稍微改造一下!
<NotFound>
<LayoutView Layout="@typeof(MainLayout)">
<div style="text-align:center"><Icon Type="close-circle" Theme="twotone" TwotoneColor="#ff0000" Height="5em" Width="5em" /></div>
<div style="margin-top:15px;text-align:center"><Title Level="3">頁面走失!請確認輸入的URL是否正確!</Title></div>
</LayoutView>
</NotFound>
在MainLayout.razor
中,增加一個MenuDataItem
,指向一個不存在的頁面:
new MenuDataItem
{
Path = "/DataList",
Name = "DataList",
Key = "DataList",
Icon = "appstore"
}
看下運行效果:
路由跳轉
很多場景中,除了點擊左側的菜單跳轉外,在頁面中也需要進行跳轉,Blazor支持的跳轉除了HTML標記<a></a>
外,還有個NavigationManager
類。
NavigationManager
類在Microsoft.AspNetCore.Components
命名空間下。
改造下Index.razor
。
@page "/"
@inject NavigationManager navigationManager
<Title Level="1">Hello,DotNet寶藏庫</Title>
<div style="margin-top:15px;"><Text Type="success">歡迎關註我的公眾號!</Text></div>
<Divider />
<div style="margin-top:20px;"><a href="/Counter">使用a 標記跳轉</a></div>
<div style="margin-top:20px;">
<Button Danger Type="@ButtonType.Primary" OnClick="()=>DirectToCounter()">使用NavigationManager跳轉</Button>
</div>
@code
{
private void DirectToCounter()
{
navigationManager.NavigateTo("/Counter");
}
}
這時,不論是點擊鏈接還是點擊按鈕,都可以跳轉到響應頁面!
路由參數
路由的過程當中經常需要進行參數傳遞,以方便我們跳轉到的新頁面後進行一些操作。
Blazor傳參分為兩種情況:path
傳參以及QueryString
傳參。我們分別介紹下這兩種傳參的方法。
path傳參
path傳參就是把參數組合在URL路徑里,接收參數的頁面需要在@page
以相同的名稱填充參數。並添加Parameter
特性對參數進行修飾。
先改造下Counter.razor
@page "/counter"
@page "/counter/{initNum}"
<Title Level="2">Counter</Title>
<Divider />
<p role="status">Current count: @currentCount</p>
<Button @onclick="IncrementCount" Type="primary">AntDesign 按鈕</Button>
@code {
[Parameter]
public string initNum{ get; set; }
private int currentCount = 0;
protected override void OnParametersSet()
{
if (!int.TryParse(initNum, out int num))
{
currentCount = 0;
}else
{
currentCount = num;
}
}
private void IncrementCount()
{
currentCount++;
}
}
代碼中,增加了一個@page "/counter/{initNum}"
。{initNum}
就是參數。
註意參數是不區分大小寫的,但是為了更規範,建議URL全部用小寫,c#代碼則使用駝峰式命名。
還有Blazor
並不支持可選參數,所以如果這個例子裡面的initNum是可有可無的,則需要使用@page
指令來定義兩條路由,一條包含initNum
,另一條不包含。
OnParametersSet
或OnParametersSetAsync
中,我們把initNum
賦值給currentCount
。
修改下Index.razor
中的DirectToCounter
方法:
private void DirectToCounter()
{
navigationManager.NavigateTo("/Counter/10");
}
運行起來,當點擊使用NavigationManager跳轉
按鈕後,Counter.razor
中的currentCount為10。
QueryString 傳參
除了把參數直接拼接在URL路徑(path)里,另一種常用的傳遞參數的方法是,將參數做為QueryString傳遞給跳轉頁面,比如“/Counter?initNum=3”。我們可從 NavigationManager.Uri 屬性中獲取請求的查詢字元串。
將Index.razor
里的
<a href="/Counter">使用a 標記跳轉</a>
改為<a href="/Counter?initNum=5">使用a 標記跳轉</a>
修改Counter.razor
,先引入NavigationManager
。
@page "/counter"
@inject NavigationManager navigationManager
在OnParametersSet
內獲取參數
protected override void OnParametersSet()
{
//if (!int.TryParse(initNum, out int num))
//{
// currentCount = 0;
//}else
//{
// currentCount = num;
//}
var query = new Uri(navigationManager.Uri).Query;
Console.WriteLine(query);
}
斷點後,可以看到,從Index.razor
點擊鏈接跳轉到Counter.razor
後,獲取到了參數:
這裡有個問題,獲取到的參數不是鍵值對,而是一串字元串。與我們的期望不同。不過還好,我們可以通過QueryHelpers.ParseQuery
來獲取到鍵值對信息。
1、添加依賴:
PM> NuGet\Install-Package Microsoft.AspNetCore.WebUtilities -Version 2.2.0
2、解析參數
var queryDic = Microsoft.AspNetCore.WebUtilities.QueryHelpers.ParseQuery(query);
可以獲取到參數值了。把代碼補充完整:
protected override void OnParametersSet()
{
//if (!int.TryParse(initNum, out int num))
//{
// currentCount = 0;
//}else
//{
// currentCount = num;
//}
var query = new Uri(navigationManager.Uri).Query;
var queryDic = Microsoft.AspNetCore.WebUtilities.QueryHelpers.ParseQuery(query);
if (queryDic.ContainsKey("initNum"))
{
var count_str = queryDic["initNum"].ToString() ?? "";
if (!int.TryParse(count_str, out int num))
{
currentCount = 0;
}
else
{
currentCount = num;
}
}
else
{
currentCount = 0;
}
}
運行一下看看效果
路由約束
路由約束強制在路由段和組件之間進行類型匹配。像剛纔例子中的initNum
,我們可以寫成@page "/counter/{initNum:int}"
,路由約束不適用於查詢字元串,也就是QueryString傳遞的參數。Blazor支持以下幾種約束類型:
- bool
- datetime
- decimal
- double
- float
- guid
- int
- long
總結
暫無,下次再會!
歡迎大家關註我的微信公眾號,一起進步,一起成長