Skip to content

Commit 5f24614

Browse files
committed
refactor: 重新设计下拉菜单显示逻辑
1 parent 111a79b commit 5f24614

File tree

3 files changed

+59
-75
lines changed

3 files changed

+59
-75
lines changed

src/BootstrapBlazor/Components/AutoComplete/AutoComplete.razor

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,11 @@
66
<BootstrapLabel required="@Required" for="@InputId" ShowLabelTooltip="ShowLabelTooltip" Value="@DisplayText" />
77
}
88
<div class="@ClassString" id="@Id">
9-
<input @attributes="AdditionalAttributes" id="@InputId" class="@ClassName" autocomplete="off" type="text" data-bs-toggle="@ToggleString" data-bs-placement="@PlacementString" data-bs-offset="@OffsetString" data-bs-custom-class="@CustomClassString" placeholder="@PlaceHolder" disabled="@Disabled" data-bb-debounce="@DurationString" @bind-value="@CurrentValueAsString" @bind-value:event="oninput" @onblur="OnBlur" @onfocus="OnFocus" @ref="FocusElement" />
9+
<input @attributes="AdditionalAttributes" id="@InputId" class="@ClassName" autocomplete="off" type="text"
10+
data-bs-toggle="@ToggleString" data-bs-placement="@PlacementString" data-bb-debounce="@DurationString"
11+
data-bs-offset="@OffsetString" data-bs-custom-class="@CustomClassString"
12+
data-bb-auto-dropdown-focus="@ShowDropdownListOnFocusString"
13+
placeholder="@PlaceHolder" disabled="@Disabled" @ref="FocusElement" />
1014
<span class="form-select-append"><i class="@Icon"></i></span>
1115
<span class="form-select-append ac-loading"><i class="@LoadingIcon"></i></span>
1216
<ul class="dropdown-menu">

src/BootstrapBlazor/Components/AutoComplete/AutoComplete.razor.cs

Lines changed: 38 additions & 73 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,6 @@
33
// See the LICENSE file in the project root for more information.
44
// Maintainer: Argo Zhang([email protected]) Website: https://www.blazor.zone
55

6-
using Microsoft.AspNetCore.Components.Web;
76
using Microsoft.Extensions.Localization;
87

98
namespace BootstrapBlazor.Components;
@@ -13,19 +12,10 @@ namespace BootstrapBlazor.Components;
1312
/// </summary>
1413
public partial class AutoComplete
1514
{
16-
private bool IsLoading { get; set; }
17-
18-
/// <summary>
19-
/// 获得/设置 当前下拉框是否显示
20-
/// </summary>
21-
private bool _isShown;
22-
2315
/// <summary>
2416
/// 获得 组件样式
2517
/// </summary>
2618
protected virtual string? ClassString => CssBuilder.Default("auto-complete")
27-
.AddClass("is-loading", IsLoading)
28-
.AddClass("show", _isShown && !IsPopover)
2919
.Build();
3020

3121
/// <summary>
@@ -143,20 +133,6 @@ protected override void OnParametersSet()
143133
LoadingIcon ??= IconTheme.GetIconByKey(ComponentIcons.LoadingIcon);
144134
}
145135

146-
/// <summary>
147-
/// <inheritdoc/>
148-
/// </summary>
149-
protected override async Task OnBlur()
150-
{
151-
CurrentSelectedItem = "";
152-
_isShown = false;
153-
154-
if (OnBlurAsync != null)
155-
{
156-
await OnBlurAsync(Value);
157-
}
158-
}
159-
160136
/// <summary>
161137
/// 鼠标点击候选项时回调此方法
162138
/// </summary>
@@ -169,32 +145,6 @@ protected virtual async Task OnClickItem(string val)
169145
}
170146
}
171147

172-
/// <summary>
173-
/// OnFocus 方法
174-
/// </summary>
175-
/// <param name="args"></param>
176-
/// <returns></returns>
177-
protected virtual async Task OnFocus(FocusEventArgs args)
178-
{
179-
if (ShowDropdownListOnFocus)
180-
{
181-
if (OnFocusFilter)
182-
{
183-
await OnKeyUp("");
184-
}
185-
else
186-
{
187-
FilterItems = DisplayCount == null ? Items.ToList() : Items.Take(DisplayCount.Value).ToList();
188-
_isShown = true;
189-
190-
if (IsPopover)
191-
{
192-
await InvokeVoidAsync("triggerFocus", Id);
193-
}
194-
}
195-
}
196-
}
197-
198148
/// <summary>
199149
/// OnKeyUp 方法
200150
/// </summary>
@@ -203,27 +153,6 @@ protected virtual async Task OnFocus(FocusEventArgs args)
203153
[JSInvokable]
204154
public virtual async Task OnKeyUp(string key)
205155
{
206-
if (!IsLoading)
207-
{
208-
IsLoading = true;
209-
if (OnCustomFilter != null)
210-
{
211-
var items = await OnCustomFilter(CurrentValueAsString);
212-
FilterItems = items.ToList();
213-
}
214-
else
215-
{
216-
var comparison = IgnoreCase ? StringComparison.OrdinalIgnoreCase : StringComparison.Ordinal;
217-
var items = IsLikeMatch ?
218-
Items.Where(s => s.Contains(CurrentValueAsString, comparison)) :
219-
Items.Where(s => s.StartsWith(CurrentValueAsString, comparison));
220-
FilterItems = DisplayCount == null ? items.ToList() : items.Take(DisplayCount.Value).ToList();
221-
}
222-
IsLoading = false;
223-
}
224-
225-
_isShown = true;
226-
227156
var source = FilterItems;
228157
if (source.Count > 0)
229158
{
@@ -290,8 +219,44 @@ public virtual async Task OnKeyUp(string key)
290219
/// </summary>
291220
/// <param name="val"></param>
292221
[JSInvokable]
293-
public void TriggerOnChange(string val)
222+
public async Task TriggerOnChange(string val)
223+
{
224+
if (OnCustomFilter != null)
225+
{
226+
var items = await OnCustomFilter(val);
227+
FilterItems = items.ToList();
228+
}
229+
else
230+
{
231+
var comparison = IgnoreCase ? StringComparison.OrdinalIgnoreCase : StringComparison.Ordinal;
232+
var items = IsLikeMatch
233+
? Items.Where(s => s.Contains(val, comparison))
234+
: Items.Where(s => s.StartsWith(val, comparison));
235+
FilterItems = items.ToList();
236+
}
237+
238+
if (DisplayCount != null)
239+
{
240+
FilterItems = FilterItems.Take(DisplayCount.Value).ToList();
241+
}
242+
243+
CurrentValue = val;
244+
if (!ValueChanged.HasDelegate)
245+
{
246+
StateHasChanged();
247+
}
248+
}
249+
250+
/// <summary>
251+
/// 出发 OnBlur 回调方法 由 Javascript 触发
252+
/// </summary>
253+
/// <returns></returns>
254+
[JSInvokable]
255+
public async Task TriggerBlur()
294256
{
295-
CurrentValueAsString = val;
257+
if (OnBlurAsync != null)
258+
{
259+
await OnBlurAsync(Value);
260+
}
296261
}
297262
}

src/BootstrapBlazor/Components/AutoComplete/AutoComplete.razor.js

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,11 +32,26 @@ export function init(id, invoke) {
3232
})
3333
}
3434

35+
EventHandler.on(input, 'focus', e => {
36+
const showDropdownOnFocus = input.getAttribute('data-bb-auto-dropdown-focus') === 'true';
37+
if (showDropdownOnFocus) {
38+
if (ac.popover === void 0) {
39+
el.classList.add('show');
40+
}
41+
}
42+
});
43+
44+
EventHandler.on(input, 'blur', e => {
45+
el.classList.remove('show');
46+
invoke.invokeMethodAsync('TriggerBlur');
47+
});
48+
3549
Input.composition(input, async v => {
3650
el.classList.add('is-loading');
51+
el.classList.add('show');
3752
await invoke.invokeMethodAsync('TriggerOnChange', v);
3853
el.classList.remove('is-loading');
39-
})
54+
});
4055
}
4156

4257
export function autoScroll(id, index) {

0 commit comments

Comments
 (0)