Skip to content

Commit 83ca545

Browse files
authored
feat(Table): add UseSearchForm parameter (#7767)
* refactor: 增加 SearchForm 表单组件 * feat: 增加 MetaData 实现类 * feat: 增加 CreateRenderFragment 扩展方法 * doc: 增加 header 文本 * feat: 允许 SearchModel 可为空 * refactor: 更新注释 * feat: 增加 UseSearchForm 逻辑 * feat: 增加 ParseSearchItem 扩展方法 * refactor: 精简代码 * fix(Table): 修复 IsTriggerByPagination 未赋值问题 * feat: 实现 ToSearches 扩展方法 * refactor: 更改数据类型 * doc: 增加注释 * refactor: 更新条件 * doc: 更新示例 * refactor: 更改字符串条件更改为包含 * doc: 更新资源文件 * feat: 增加 SearchMetaData 接口 * refactor: 重命名 * doc: 更新示例 * refactor: 更改参数名称 * doc: 更新文档 * refactor: 调整序列 * feat: 增加 SearchFormItemMetaData 支持逻辑 * doc: 更新示例 * doc: 增加注释 * refactor: 重构代码 * doc: 更新注释文档 * refactor: 使用转型后的数据类型 * refactor: 优化代码 * test: 增加 Searches 单元测试 * refactor: 移除 ValueType 参数 * test: 增加单元测试 * test: 增加单元测试 * refactor: 重构代码 * test: 更新单元测试 * feat: 增加 bb-search-form 样式 * test: 更新单元测试 * refactor: 增加 WIP 注释 * test: 更新单元测试 * refactor: 增加必填标签 * doc: 更新示例
1 parent 32cd398 commit 83ca545

35 files changed

Lines changed: 2109 additions & 35 deletions

src/BootstrapBlazor.Server/Components/Samples/Table/TablesSearch.razor

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -157,3 +157,25 @@
157157
</CustomerSearchTemplate>
158158
</Table>
159159
</DemoBlock>
160+
161+
<DemoBlock Title="@Localizer["SearchFormTitle"]"
162+
Introduction="@Localizer["SearchFormIntro"]"
163+
Name="SearchForm">
164+
<section ignore>
165+
<div>@((MarkupString)Localizer["SearchFormDesc"].Value)</div>
166+
</section>
167+
<Table TItem="Foo"
168+
IsPagination="true" PageItemsSource="@PageItemsSource" SearchMode="SearchMode.Top"
169+
IsStriped="true" IsBordered="true"
170+
ShowSearch="true" UseSearchForm="true"
171+
ShowToolbar="true" IsMultipleSelect="true" ShowExtendButtons="true"
172+
OnQueryAsync="@OnQueryAsync" OnAddAsync="@OnAddAsync" OnSaveAsync="@OnSaveAsync" OnDeleteAsync="@OnDeleteAsync">
173+
<TableColumns>
174+
<TableColumn @bind-Field="@context.DateTime" Width="180" Searchable="true" />
175+
<TableColumn @bind-Field="@context.Name" Searchable="true" SearchFormItemMetaData="_nameSearchFormItemMetaData" />
176+
<TableColumn @bind-Field="@context.Address" Searchable="true" SearchFormItemMetaData="_addressSearchFormItemMetaData" />
177+
<TableColumn @bind-Field="@context.Count" Searchable="true" />
178+
<TableColumn @bind-Field="@context.Education" Searchable="true" />
179+
</TableColumns>
180+
</Table>
181+
</DemoBlock>

src/BootstrapBlazor.Server/Components/Samples/Table/TablesSearch.razor.cs

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,18 @@ private bool SearchModeFlag
4040
set => SearchModeValue = value ? SearchMode.Popup : SearchMode.Top;
4141
}
4242

43+
private ISearchFormItemMetaData _nameSearchFormItemMetaData = new StringSearchMetaData()
44+
{
45+
PlaceHolder = "请输入名称搜索(支持模糊匹配)",
46+
FilterAction = FilterAction.Contains,
47+
};
48+
49+
private ISearchFormItemMetaData _addressSearchFormItemMetaData = new StringSearchMetaData()
50+
{
51+
PlaceHolder = "请输入地址搜索(支持模糊匹配)",
52+
FilterAction = FilterAction.Contains,
53+
};
54+
4355
/// <summary>
4456
/// OnInitialized 方法
4557
/// </summary>
@@ -179,8 +191,8 @@ private Task<QueryData<Foo>> OnQueryAsync(QueryPageOptions options)
179191
TotalCount = total,
180192
IsSorted = isSorted,
181193
IsFiltered = options.Filters.Count > 0,
182-
IsSearch = options.CustomerSearches.Count > 0 || !string.IsNullOrEmpty(options.SearchText),
183-
IsAdvanceSearch = options.CustomerSearches.Count > 0 && string.IsNullOrEmpty(options.SearchText),
194+
IsSearch = options.CustomerSearches.Count > 0 || !string.IsNullOrEmpty(options.SearchText) || options.Searches.Count > 0,
195+
IsAdvanceSearch = options.CustomerSearches.Count > 0 && string.IsNullOrEmpty(options.SearchText) || options.Searches.Count > 0,
184196
});
185197
}
186198
}

src/BootstrapBlazor.Server/Locales/en-US.json

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5076,7 +5076,10 @@
50765076
"SelectedItemValue1": "Name1",
50775077
"SelectedItemValue2": "Name2",
50785078
"TablesSearchDesc": "Commonly used for single table maintenance, simple addition, deletion, modification, search, sorting, filtering, search and other common functions can be realized through attribute configuration, and very complex can be realized through the advanced usage of <code>Template</code> business needs functions",
5079-
"TablesSearchTitle": "Table Search"
5079+
"TablesSearchTitle": "Table Search",
5080+
"SearchFormTitle": "Search Form",
5081+
"SearchFormIntro": "Enable the search form feature by setting <code>UseSearchForm=\"true\"</code>, and configure the search items within the form using <code>SearchItems</code>, suitable for scenarios with custom complex search conditions",
5082+
"SearchFormDesc": "When <code>UseSearchForm</code> is enabled and <code>SearchItems</code> is not provided, it will default to using <code>TableColumn</code> with <code>Searchable=\"true\"</code>. You can customize the metadata through the <code>SearchFormItemMetaData</code> property in <code>TableColumn</code>"
50805083
},
50815084
"BootstrapBlazor.Server.Components.Samples.Table.TablesSelection": {
50825085
"TablesSelectionCountText": "Count:{0}",

src/BootstrapBlazor.Server/Locales/zh-CN.json

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5076,7 +5076,10 @@
50765076
"SelectedItemValue1": "姓名1",
50775077
"SelectedItemValue2": "姓名2",
50785078
"TablesSearchDesc": "常用于单表维护,通过属性配置实现简单的增、删、改、查、排序、过滤、搜索等常用功能,通过 <code>Template</code> 的高级用法能实现非常复杂的业务需求功能",
5079-
"TablesSearchTitle": "Table 表格"
5079+
"TablesSearchTitle": "Table 表格",
5080+
"SearchFormTitle": "搜索表单",
5081+
"SearchFormIntro": "通过设置 <code>UseSearchForm=\"true\"</code> 开启搜索表单功能,通过 <code>SearchItems</code> 配置搜索表单内搜索项,适用于自定义复杂搜索条件的场景",
5082+
"SearchFormDesc": "使用 <code>UseSearchForm</code> 开启搜索表单时未提供 <code>SearchItems</code> 默认尝试使用设置 <code>Searchable=\"true\"</code> 的 <code>TableColumn</code> 进行构建,可以通过 <code>TableColumn</code> 中的 <code>SearchFormItemMetaData</code> 属性定制化元数据"
50805083
},
50815084
"BootstrapBlazor.Server.Components.Samples.Table.TablesSelection": {
50825085
"TablesSelectionCountText": "选中的行数:{0}",

src/BootstrapBlazor/Attributes/AutoGenerateColumnAttribute.cs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -180,6 +180,8 @@ public class AutoGenerateColumnAttribute : AutoGenerateBaseAttribute, ITableColu
180180

181181
bool? ITableColumn.Searchable { get => Searchable; set => Searchable = value ?? false; }
182182

183+
ISearchFormItemMetaData? ITableColumn.SearchFormItemMetaData { get; set; }
184+
183185
bool? ITableColumn.Filterable { get => Filterable; set => Filterable = value ?? false; }
184186

185187
bool? ITableColumn.Sortable { get => Sortable; set => Sortable = value ?? false; }
Lines changed: 82 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
// Licensed to the .NET Foundation under one or more agreements.
2+
// The .NET Foundation licenses this file to you under the Apache 2.0 License
3+
// See the LICENSE file in the project root for more information.
4+
// Maintainer: Argo Zhang(argo@live.ca) Website: https://www.blazor.zone
5+
6+
namespace BootstrapBlazor.Components;
7+
8+
/// <summary>
9+
/// <para lang="zh">SearchItem 接口</para>
10+
/// <para lang="en">SearchItem interface</para>
11+
/// </summary>
12+
public interface ISearchItem
13+
{
14+
/// <summary>
15+
/// <para lang="zh">获得 绑定列的类型</para>
16+
/// <para lang="en">Gets the type of the bound column</para>
17+
/// </summary>
18+
Type PropertyType { get; }
19+
20+
/// <summary>
21+
/// <para lang="zh">获得/设置 表头显示文本</para>
22+
/// <para lang="en">Gets or sets the header display text</para>
23+
/// </summary>
24+
string? Text { get; set; }
25+
26+
/// <summary>
27+
/// <para lang="zh">获得/设置 字段名称</para>
28+
/// <para lang="en">Gets or sets the field name</para>
29+
/// </summary>
30+
string FieldName { get; }
31+
32+
/// <summary>
33+
/// <para lang="zh">获得/设置 是否显示前置标签 默认为 null 未设置时默认显示标签</para>
34+
/// <para lang="en">Gets or sets Whether to Show Label. Default is null, show label if not set</para>
35+
/// </summary>
36+
public bool? ShowLabel { get; set; }
37+
38+
/// <summary>
39+
/// <para lang="zh">获得/设置 是否显示标签提示,常用于标签文本过长被截断时,默认为 null</para>
40+
/// <para lang="en">Gets or sets whether to show the label tooltip, usually when the label text is too long and truncated. Default is null</para>
41+
/// </summary>
42+
bool? ShowLabelTooltip { get; set; }
43+
/// <summary>
44+
/// <para lang="zh">获得/设置 当前属性的分组名称</para>
45+
/// <para lang="en">Gets or sets the group name of the current property</para>
46+
/// </summary>
47+
string? GroupName { get; set; }
48+
49+
/// <summary>
50+
/// <para lang="zh">获得/设置 当前属性的分组顺序,默认为 0</para>
51+
/// <para lang="en">Gets or sets the group order of the current property. Default is 0</para>
52+
/// </summary>
53+
int GroupOrder { get; set; }
54+
55+
/// <summary>
56+
/// <para lang="zh">获得/设置 顺序号</para>
57+
/// <para lang="en">Gets or sets the order number</para>
58+
/// </summary>
59+
int Order { get; set; }
60+
61+
/// <summary>
62+
/// <para lang="zh">获得/设置 字段的列跨度,默认为 0</para>
63+
/// <para lang="en">Gets or sets the field column span. Default is 0</para>
64+
/// </summary>
65+
int Cols { get; set; }
66+
67+
/// <summary>
68+
/// <para lang="zh">获得/设置 搜索元数据</para>
69+
/// <para lang="en">Gets or sets the search metadata</para>
70+
/// </summary>
71+
public ISearchFormItemMetaData? MetaData { get; set; }
72+
73+
/// <summary>
74+
/// <para lang="zh">获得 过滤器实例</para>
75+
/// <para lang="en">Gets the filter instance</para>
76+
/// </summary>
77+
/// <returns>
78+
/// <para lang="zh">过滤器实例</para>
79+
/// <para lang="en">Filter instance</para>
80+
/// </returns>
81+
public FilterKeyValueAction? GetFilter() => MetaData?.GetFilter(FieldName);
82+
}
Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
@namespace BootstrapBlazor.Components
2+
@inherits BootstrapComponentBase
3+
4+
<div @attributes="AdditionalAttributes" class="@ClassString">
5+
<CascadingValue Value="this" Name="SearchForm" IsFixed="true">
6+
<div class="form-body">
7+
@if (ShowUnsetGroupItemsOnTop)
8+
{
9+
if (UnsetGroupItems.Any())
10+
{
11+
@RenderUnsetGroupItems
12+
}
13+
@foreach (var g in GroupItems)
14+
{
15+
@RenderGroupItems(g)
16+
}
17+
}
18+
else
19+
{
20+
@foreach (var g in GroupItems)
21+
{
22+
@RenderGroupItems(g)
23+
}
24+
if (UnsetGroupItems.Any())
25+
{
26+
@RenderUnsetGroupItems
27+
}
28+
}
29+
</div>
30+
31+
@if (Buttons != null)
32+
{
33+
<div class="bb-editor-footer form-footer">
34+
@Buttons
35+
</div>
36+
}
37+
</CascadingValue>
38+
</div>
39+
40+
@code
41+
{
42+
RenderFragment RenderUnsetGroupItems =>
43+
@<div class="@FormClassString" style="@FormStyleString">
44+
@foreach (var item in UnsetGroupItems)
45+
{
46+
<div class="@GetCssString(item)">
47+
@AutoGenerateTemplate(item)
48+
</div>
49+
}
50+
</div>;
51+
52+
RenderFragment<KeyValuePair<string, IOrderedEnumerable<ISearchItem>>> RenderGroupItems => g =>
53+
@<GroupBox Title="@g.Key">
54+
<div class="@FormClassString" style="@FormStyleString">
55+
@foreach (var item in g.Value)
56+
{
57+
<div class="@GetCssString(item)">
58+
@AutoGenerateTemplate(item)
59+
</div>
60+
}
61+
</div>
62+
</GroupBox>;
63+
}

0 commit comments

Comments
 (0)