简体   繁体   English

Xamarin.Forms 从 mvvm ViewModel 设置焦点

[英]Xamarin.Forms set focus from mvvm ViewModel

I'm working on a chat application using Xamarin.Forms.我正在使用 Xamarin.Forms 开发聊天应用程序。

And I want to avoid to hide the keyboard when the Entry loses focus and button Send is clicked.我想避免在 Entry 失去焦点并单击 Send 按钮时隐藏键盘。

How can I do it on Android and iOS?如何在 Android 和 iOS 上执行此操作?

I use XF, full Mvvm without XAML(only C#)我使用 XF,没有 XAML 的完整 Mvvm(仅 C#)

Updated:更新:

In page class:在页面类中:

private EntrySetBorder _newMessageEntry;
...
_newMessageEntry = new EntrySetBorder
{
    TextColor = Color.Black,
    HorizontalOptions = LayoutOptions.FillAndExpand,
    VerticalOptions = LayoutOptions.End,
    Margin = new Thickness(0, 0, 5, 0)
};

In model class:在模型类中:

var entry = CurrentPage.FindByName<EntrySetBorder>("_newMessageEntry");
entry.Focus();

} }

This can be achieved easily by using the FindByName<>() function inside the PCL.这可以通过使用 PCL 中的FindByName<>()函数轻松实现。
This is one way of doing that:这是这样做的一种方法:

Entry myEntry = CurrentPage.FindByName<Entry>("YourEntryName");
myEntry.Focus();

You can add that at the end of the click handler of your send button.您可以将其添加到发送按钮的点击处理程序的末尾。

Edit:编辑:

In your case I think your problem is that your entry is set to private , so I would suggest either expose it as public or expose it using another public property.在您的情况下,我认为您的问题是您的条目设置为private ,因此我建议将其publicpublic或使用另一个公共属性公开它。 Two solutions that might work:两种可能有效的解决方案:

public EntrySetBorder _newMessageEntry;
...
_newMessageEntry = new EntrySetBorder
{

    TextColor = Color.Black,
    HorizontalOptions = LayoutOptions.FillAndExpand,
    VerticalOptions = LayoutOptions.End,
    Margin = new Thickness(0, 0, 5, 0)
};

And:和:

EntrySetBorder entry = CurrentPage.FindByName<EntrySetBorder>("_newMessageEntry");
entry.Focus();

Or you go with this:或者你用这个:

private EntrySetBorder _newMessageEntry;
...
_newMessageEntry = new EntrySetBorder
{

    TextColor = Color.Black,
    HorizontalOptions = LayoutOptions.FillAndExpand,
    VerticalOptions = LayoutOptions.End,
    Margin = new Thickness(0, 0, 5, 0)
};
public EntrySetBorder NewMessageEntry => _newMessageEntry;

and :和 :

EntrySetBorder entry = CurrentPage.FindByName<EntrySetBorder>("NewMessageEntry");
entry.Focus();

Please try that :)请试试:)

Edit 2:编辑2:

After reviewing your code, and testing it, the final way to fix it was by sending the Entry as a parameter in the command you're using, example:在查看您的代码并对其进行测试后,修复它的最终方法是将 Entry 作为您正在使用的命令中的参数发送,例如:

Inside the page you're creating:在您创建的页面内:

sendButton.CommandParameter = NewMessageEntry; // We're adding the Entry we want to focus as a command parameter.

And inside your PageModel and the command we want to use:在您的 PageModel 和我们要使用的命令中:

public Command SendCommand
{
    get
    {
        return new Command<Entry>((obj) => //obj here means the parameters we're sending I.E: the entry we set it in the page.
        {
            //The code you want to execute
            Entry entry = obj;
            entry.Focus();
        });
    }
}

Note that I used Entry because I didn't have all the implementation of your custom entry.请注意,我使用Entry是因为我没有自定义条目的所有实现。

This is an example of how I do, before this I used to do using MessagingCenter这是我如何做的一个例子,在此之前我曾经使用 MessagingCenter

in xaml , you need to give an x:Name to the obj you want to make focus.在 xaml 中,您需要为要聚焦的 obj 提供一个 x:Name 。

<!-- PICKER's DEFINITION -->
<DatePicker
    x:Name="Datepicker"
    Date="{Binding SelectedDate, Mode=TwoWay}"
    IsEnabled="true"
    IsVisible="false">
</DatePicker>

then you have to make reference to that control in your command parameter on a button or for example in this case I use a toolbar item.那么您必须在按钮上的命令参数中引用该控件,或者例如在这种情况下我使用工具栏项。

<!-- MENU TOOLBAR -->
<ContentPage.ToolbarItems>
    <ToolbarItem
        Command="{Binding ShowCalendarCommand}"
        Icon="Calendar"
        CommandParameter="{x:Reference Datepicker}" />
</ContentPage.ToolbarItems>

then in your vm command :然后在你的 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");
    }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM