Как я могу предоставить дочерние элементы MultiValidationBehavior в пользовательском управлении?

#xamarin.forms #xamarin-community-toolkit

#xamarin.формы #xamarin-сообщество-инструментарий

Вопрос:

Я создаю пользовательский элемент управления для записи, которую можно проверить.

Я сделал это, создав представление содержимого с сеткой в качестве дочернего элемента, содержащего запись, метку ошибки и т. Д.

Я бы хотел, чтобы это было гибким, когда дело доходит до проверки, поэтому в идеале было бы неплохо предоставить дочернее свойство MultiValidationBehavior записи или установить это свойство в качестве свойства содержимого моего элемента управления.

В нынешнем виде я еще не придумал, как добавить поведение в свой пользовательский элемент управления.

Возможно ли это?

 lt;ContentView x:Class="MPK.UI.Views.Components.FormEntry"  x:Name="FormEntryControl"  xmlns="http://xamarin.com/schemas/2014/forms"  xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"  xmlns:xct="http://xamarin.com/schemas/2020/toolkit"  xmlns:yummy="clr-namespace:Xamarin.Forms.PancakeView;assembly=Xamarin.Forms.PancakeView"  xmlns:converters="clr-namespace:MPK.UI.Converters;assembly=MPK.UI"gt;   lt;ContentView.Resourcesgt;  lt;ResourceDictionarygt;  lt;converters:IsValidToEntryBorderConverter x:Key="IsValidToEntryBorderConverter"/gt;  lt;converters:ErrorsToLabelTextConverter x:Key="ErrorsToLabelTextConverter"/gt;  lt;xct:InvertedBoolConverter x:Key="InvertedBoolConverter" /gt;  lt;/ResourceDictionarygt;      lt;/ContentView.Resourcesgt;  lt;Gridgt;  lt;yummy:PancakeView CornerRadius="10"  HeightRequest="50"  HorizontalOptions="FillAndExpand"  BackgroundColor="{StaticResource EntryBackgroundColor}"  Padding="16,0,16,0"gt;  lt;yummy:PancakeView.Behaviorsgt;  lt;xct:AnimationBehavior AnimateCommand="{Binding Source={x:Reference FormEntryControl}, Path=ShakeCommand}"gt;  lt;xct:AnimationBehavior.AnimationTypegt;  lt;xct:ShakeAnimation /gt;  lt;/xct:AnimationBehavior.AnimationTypegt;  lt;/xct:AnimationBehaviorgt;  lt;/yummy:PancakeView.Behaviorsgt;  lt;yummy:PancakeView.Bordergt;  lt;yummy:Border  Color="{Binding IsValid, Source={x:Reference MultiValidationBehavior}, Converter={StaticResource IsValidToEntryBorderConverter}}"  Thickness="1" /gt;  lt;/yummy:PancakeView.Bordergt;  lt;Entry x:Name="Entry"  Text="{Binding Text, Source={x:Reference FormEntryControl}}"  Placeholder="{Binding Placeholder, Source={x:Reference FormEntryControl}}"  ReturnType="{Binding ReturnType, Source={x:Reference FormEntryControl}}"  ReturnCommand="{Binding ReturnCommand, Source={x:Reference FormEntryControl}}"  PlaceholderColor="{StaticResource EntryPlaceholderTextColor}"  BackgroundColor="Transparent"  IsPassword="{Binding IsPassword, Source={x:Reference FormEntryControl}}"  ClearButtonVisibility="{Binding ClearButtonVisibility, Source={x:Reference FormEntryControl}}"gt;  lt;Entry.Effectsgt;  lt;xct:RemoveBorderEffect /gt;  lt;/Entry.Effectsgt;  lt;Entry.Behaviorsgt;  lt;xct:MultiValidationBehavior x:Name="MultiValidationBehavior"   IsValid="{Binding IsValid, Source={x:Reference FormEntryControl}, Mode=TwoWay}"  Children="{Binding ValidationBehaviors, Source={x:Reference FormEntryControl}}"/gt;  lt;!-- Binding children doesn't work here --gt;  lt;/Entry.Behaviorsgt;  lt;/Entrygt;  lt;/yummy:PancakeViewgt;  lt;xct:Expander Margin="8,4,0,0"  AnimationLength="100"  IsExpanded="{Binding IsValid, Source={x:Reference FormEntryControl}, Mode=OneWay, Converter={StaticResource InvertedBoolConverter}}"gt;  lt;Label Text="{Binding Errors, Source={x:Reference MultiValidationBehavior}, Converter={StaticResource ErrorsToLabelTextConverter}}"  TextColor="{StaticResource ErrorColor}" /gt;  lt;/xct:Expandergt;  lt;/Gridgt; lt;/ContentViewgt;  

Комментарии:

1. Что приходит на ум, так это использовать другой подход. Добавьте в свой элемент управления методы, которые выполняют то, что вы хотите. Например, метод, который может добавить поведение проверки. Тогда любому, кто использует элемент управления, придется написать «код», чтобы вызвать этот метод. Что-то вроде PancakeView.AddValidation(Behavior behavior) { MultiValidationBehavior.Children.Add(behavior); } того, что я не пробовал, поэтому код, возможно, должен немного отличаться от этого. Если вы пойдете по этому пути, но застрянете, добавьте к своему вопросу код, который вы пробовали, и что пойдет не так.

2. Я думаю, ты на что-то наткнулся. Но можно ли сделать это как связываемое свойство, чтобы это все еще можно было выполнить в xaml?

3. Я не могу представить себе, как использовать связываемое свойство, потому что я не знаю, как другое представление добавится в список (с помощью XAML). Выполните тест, в котором вы напишете представление, использующее этот пользовательский элемент управления. Получите код, насколько сможете (с комментарием или нерабочим псевдокодом в точке, где новое представление попытается привязаться к этому представлению, чтобы добавить поведение), добавьте это в свой вопрос, затем добавьте комментарий здесь, чтобы я был уведомлен о том, что вы внесли изменения.

4. Я все понял. Спасибо за помощь 🙂

Ответ №1:

Решение оказалось намного проще, чем я ожидал.

В коде моего элемента управления мне нужно было добавить свойство, указывающее на дочернее свойство multivalidationbehavior.

 public IListlt;ValidationBehaviorgt; ValidationBehaviors =gt; TheMultiValidationBehavior.Children;  

Использование моего пользовательского элемента управления выглядит примерно так:

 lt;components:FormEntry Placeholder="Name"gt;  lt;components:FormEntry.ValidationBehaviorsgt;  lt;xct:TextValidationBehavior MinimumLength="1" xct:MultiValidationBehavior.Error="Min: 1"/gt;  lt;/components:FormEntry.ValidationBehaviorsgt;  lt;/components:FormEntrygt;