最大长度为 1 后专注于下一个条目 [英] Focus on Next Entry after max length of 1

查看:25
本文介绍了最大长度为 1 后专注于下一个条目的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我创建了 20 个动态条目,并希望在用户输入数字后关注下一个条目,并且条目的最大长度为 1.焦点应自动移至下一个条目.我正在分享我的代码.提前感谢您的帮助.

I have created dynamic 20 entries and want to focus on next entry after user enter a digit and max length of entry is 1. The focus should be automatically move on next entry.I am sharing my code.Thanks in advance for help.

//模型

 public  class CrossingUIModel
    {
    public int Id { get; set; }
    public string FieldValue { get; set; }      
   }

//更改属性

private ObservableCollection<CrossingUIModel> bindCrossingUIModel;

    public ObservableCollection<CrossingUIModel> BindCrossingUIModel
  {
    get { return bindCrossingUIModel; }
    set
    {
            bindCrossingUIModel = value;
        OnPropertyChanged(nameof(BindCrossingUIModel));
    }
  }

//创建用户界面

  public void CreateUI()
    {
        UserDialogs.Instance.ShowLoading();

        BindCrossingUIModel = new ObservableCollection<CrossingUIModel>();

        for (int i = 1; i < 21; i++)
        {
            CrossingUIModel model = new CrossingUIModel();
            model.Id = i;
            BindCrossingUIModel.Add(model);
        }

        UserDialogs.Instance.HideLoading();

    }

//xml文件

           <CollectionView x:Name="CrossingView" ItemsSource="{Binding BindCrossingUIModel, Mode=TwoWay}" SelectionMode="Multiple">
                        <CollectionView.ItemsLayout>
                        <GridItemsLayout Orientation="Vertical"  Span="10" />
                    </CollectionView.ItemsLayout>

                    <CollectionView.ItemTemplate>
                        <DataTemplate>
                            <StackLayout HorizontalOptions="FillAndExpand">
                                <Entry x:Name="Fields" Text="{Binding FieldValue, Mode=TwoWay}" 
                                       ReturnType="Next" MaxLength="1" Keyboard="Numeric" 
                                       TextChanged="Fields_TextChanged" ></Entry>
                            </StackLayout>
                        </DataTemplate>
                    </CollectionView.ItemTemplate>
                </CollectionView>

推荐答案

既然你用过 Data-Binding ,那么处理 ViewModel 中的所有逻辑会更好.

Since you had used Data-Binding , it would be better to handle all the logic in ViewModel .

定义自定义条目

public class MyEntry:Entry
{

     public static readonly BindableProperty IsFocusProperty =BindableProperty.Create("IsFocus", typeof(bool), typeof(MyEntry), false,propertyChanged: OnChanged);


    static void OnChanged(BindableObject bindable, object oldValue, object newValue)
    {
        var entry = bindable as MyEntry;

        var focus = (bool)newValue;

        if(focus)
        {
            entry.Focus();
        }
        else
        {
            entry.Unfocus();
        }

    }

    public bool IsFocus
    {
        get { return (bool)GetValue(IsFocusProperty); }
        set { 
            SetValue(IsFocusProperty, value);
            }
    }

    public MyEntry()
    {
        this.Focused += MyEntry_Focused;
        this.Unfocused += MyEntry_Unfocused;
    }

    private void MyEntry_Unfocused(object sender, FocusEventArgs e)
    {
        this.IsFocus = false;
    }

    private void MyEntry_Focused(object sender, FocusEventArgs e)
    {
        this.IsFocus = true;
    }
}

在模型中

public  class CrossingUIModel : INotifyPropertyChanged
{
    public event PropertyChangedEventHandler PropertyChanged;

    public int Id { get; set; }
   
    protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null)
    {
        PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }

    string fieldValue;

    public string FieldValue
    {

        get
        {
            return fieldValue;
        }

        set
        {
            if (fieldValue != value)
            {
                fieldValue = value;
                OnPropertyChanged("FieldValue");
            }
        }
    }


    bool isFocus = false;

    public bool IsFocus
    {
        get
        {
            return isFocus;
        }

        set
        {
            if (isFocus != value)
            {
                isFocus = value;
                OnPropertyChanged("IsFocus");
            }
        }
    }

}

在视图模型中

public class MyViewModel
{
    public ObservableCollection<CrossingUIModel> BindCrossingUIModel { get; set; }

    public MyViewModel()
    {
        BindCrossingUIModel = new ObservableCollection<CrossingUIModel>();

        for (int i = 1; i < 21; i++)
        {
            CrossingUIModel model = new CrossingUIModel();
            model.Id = i;
            BindCrossingUIModel.Add(model);
        }

        foreach (CrossingUIModel model in BindCrossingUIModel)
        {
            model.PropertyChanged += Model_PropertyChanged;
        }


    }

    private void Model_PropertyChanged(object sender, PropertyChangedEventArgs e)
    {
        if(e.PropertyName== "FieldValue")
        {
            var model = sender as CrossingUIModel;

            if(model.FieldValue.Length==1)
            {
                model.FieldValue = model.FieldValue.Substring(0, 1);

                model.IsFocus = false;

                int id = model.Id;

                BindCrossingUIModel[id].IsFocus = true;

            }

        }
    }
}

在 xaml 中

现在我们不再需要设置MaxLengthTextChanged.

<StackLayout HorizontalOptions="FillAndExpand" VerticalOptions="FillAndExpand">
        <CollectionView x:Name="CrossingView" ItemsSource="{Binding BindCrossingUIModel, Mode=TwoWay}" SelectionMode="Multiple">
            <CollectionView.ItemsLayout>
                <GridItemsLayout  Orientation="Vertical"  Span="10" />
            </CollectionView.ItemsLayout>

            <CollectionView.ItemTemplate>
                <DataTemplate>
                    <StackLayout WidthRequest="100" HeightRequest="30" HorizontalOptions="FillAndExpand">
                        <local:MyEntry WidthRequest="80" BackgroundColor="LightBlue" HeightRequest="30" x:Name="Fields" Text="{Binding FieldValue, Mode=TwoWay}" 
                                       IsFocus="{Binding IsFocus, Mode=TwoWay}"
                                       ReturnType="Next"  Keyboard="Numeric" 
                                        ></local:MyEntry>
                    </StackLayout>
                </DataTemplate>
            </CollectionView.ItemTemplate>
        </CollectionView>
    </StackLayout>

顺便说一下,您可以使用 Grid 而不是 StackLayout 作为条目的父布局.

By the way , you could use Grid instead of StackLayout as the Parent Layout of the Entry.

这篇关于最大长度为 1 后专注于下一个条目的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆