我想在执行一些异步操作后在SearchBox
控件中设置焦点,我希望从我的 ViewModel
我怎么能这样做?
修改
ViewModel代码:
private bool _searchBarFocused;
public bool SearchBarFocused
{
get { return _searchBarFocused; }
set
{
_searchBarFocused = value;
base.OnPropertyChanged("SearchBarFocused");
}
}
public async Task InitializeData()
{
// Other operations...
SearchBarFocused = true;
}
查看代码隐藏代码:
protected override void OnAppearing()
{
base.OnAppearing();
(this.BindingContext as MyViewModel).InitializeData();
}
SearchBar XAML代码:
<SearchBar SearchCommand="{Binding SearchItemsCommand}">
<SearchBar.Triggers>
<DataTrigger TargetType="SearchBar"
Binding="{Binding SearchBarFocused, Mode=TwoWay}" Value="True">
<Trigger.EnterActions>
<triggers:SearchBarFocusTriggerAction Focused="True" />
</Trigger.EnterActions>
<Trigger.ExitActions>
<triggers:SearchBarFocusTriggerAction Focused="False" />
</Trigger.ExitActions>
</DataTrigger>
</SearchBar.Triggers>
</SearchBar>
触发操作代码:
public class SearchBarFocusTriggerAction : TriggerAction<SearchBar>
{
public bool Focused { get; set; }
protected override void Invoke(SearchBar searchBar)
{
if (Focused)
searchBar.Focus();
else
searchBar.Unfocus();
}
}
答案 0 :(得分:6)
其中一个选项是使用触发器(XAML方式):
<SearchBar x:Name="searchBar"
Text=""
Placeholder="type something">
<SearchBar.Triggers>
<DataTrigger TargetType="SearchBar"
Binding="{Binding ViewModelIsSearchBarFocused}"
Value="True">
<Trigger.EnterActions>
<local:FocusTriggerAction Focused="True" />
</Trigger.EnterActions>
<Trigger.ExitActions>
<local:FocusTriggerAction Focused="False" />
</Trigger.ExitActions>
</DataTrigger>
<EventTrigger Event="Unfocused">
<local:UnfocusedTriggerAction />
</EventTrigger>
</SearchBar.Triggers>
</SearchBar>
public class FocusTriggerAction : TriggerAction<SearchBar>
{
public bool Focused { get; set; }
protected override async void Invoke (SearchBar searchBar)
{
await Task.Delay(1000);
if (Focused)
{
searchBar.Focus();
}
else
{
searchBar.UnFocus();
}
}
}
public class UnfocusedTriggerAction : TriggerAction<SearchBar>
{
protected override void Invoke (SearchBar searchBar)
{
YourViewModel.ViewModelIsSearchBarFocused = false;
}
}
在此处阅读更多内容:https://developer.xamarin.com/guides/cross-platform/xamarin-forms/working-with/triggers/
答案 1 :(得分:1)
这是我的一个例子,在此之前我曾经使用过MessagingCenter
在xaml中,你需要给你想要聚焦的obj一个x:Name。
<!-- PICKER's DEFINITION -->
<DatePicker
x:Name="Datepicker"
Date="{Binding SelectedDate, Mode=TwoWay}"
IsEnabled="true"
IsVisible="false">
</DatePicker>
然后你必须在一个按钮的命令参数中引用该控件,或者例如在这种情况下我使用一个工具栏项。
<!-- MENU TOOLBAR -->
<ContentPage.ToolbarItems>
<ToolbarItem
Command="{Binding ShowCalendarCommand}"
Icon="Calendar"
CommandParameter="{x:Reference Datepicker}" />
</ContentPage.ToolbarItems>
然后在你的vm命令中:
#region toolbar commands
public ICommand ShowCalendarCommand => new RelayCommand<Object>(ShowCalendar);
#endregion
private void ShowCalendar(Object obj)
{
var calendar = (DatePicker)obj;
calendar.Focus();
// MessagingCenter.Send(this, "Calendar");
}
答案 2 :(得分:0)
我通过在viewmodel中将contentpage作为参数传递来解决了我的问题
BindingContext = new YourViewModel(this);
并在视图模型中创建一个属性
public ContentPage m_View { get; set; }
,然后从构造函数将值设置为此属性
public YourViewModel(ContentPage view)
{
m_View = view;
}
,然后使用其名称将焦点放在我的DatePicker
var DatePicker = m_View.FindByName("YourDatePickerName") as DatePicker;
DatePicker.Focus();
我的DatePicker代码为
<DatePicker x:Name="YourDatePickerName"
Date="{Binding SelectedDate}" />