2

特定のデータ型の範囲の検証を扱う .NET 4.0 プロジェクトに取り組んでいます。たとえば、32 ビットの int は、 アプリケーションによって定義されたInt32.MinValueInt32.MaxValueまたはその他の値の間のみである必要があります。カスタム バリデーターでデータ型と範囲を指定できるようにして、バインディングを通じて xaml から直接呼び出すことができるようにしたいと考えています。<CheckIfValueRangeValidator>

これは私が念頭に置いていることですが、それが機能するかどうか、または xaml を介して実行できるかどうかはわかりません。

class CheckIfValueInRangeValidator<T> : ValidationRule
{
    public T Max { get; set; }
    public T Min { get; set; }

    public override ValidationResult Validate(object value, System.Globalization.CultureInfo cultureInfo)
    {
        // Implementation...
    }
}
4

1 に答える 1

3

私の悪いことに、実際には x:TypeArguments を使用することはできません。x:TypeArguments は 2009 より前の XAML バージョンのオブジェクト要素では許可されていません。ルーズ XAML ファイルまたはルート要素 (私の場合は Window) でのみ有効です ...

http://msdn.microsoft.com/en-us/library/ms750476.aspx

ただし、回避策として、次のパターンを使用できます。

    <TextBox x:Name="textBox1">
        <Binding Path="MyValue"
                     Source="{StaticResource MyObject}"
                     UpdateSourceTrigger="PropertyChanged">
            <Binding.ValidationRules>
                <wpfApplication6:MyValidationRule ObjectType="{x:Type system:Int32}"   />
            </Binding.ValidationRules>
        </Binding>
    </TextBox>

コードビハインド:

public class MyObject
{
    public object MyValue { get; set; }
}

public class MyValidationRule : ValidationRule
{
    public Type ObjectType { get; set; }

    public override ValidationResult Validate(object value, CultureInfo cultureInfo)
    {
        throw new NotImplementedException();
    }
}

こちらもご覧ください: Using a Generic IValueConverter from XAML

@Blam コメントは検討する価値があります。チェックする範囲は通常、整数または倍精度に適用されます。他の型の場合は、そのオブジェクトの有効性を返すブール値を追加し、オブジェクト自体の内部でそのような検証を実行できます。

数値にはRangeAttributeがありますが、実際には WPF 検証インフラストラクチャの一部ではありません。

検証には別のオプションもあります。この場合、 INotifyDataErrorInfo検証はオブジェクト内で行われます。

私はここに長い答えを書きました: https://softwareengineering.stackexchange.com/questions/203590/is-there-an-effective-way-for-creating-complex-forms

私の経験から言えば、一般的な検証ルールを使用するのはおそらく賢明ではありません。

質問を編集して一般的でないようにする必要があります;-)しかし、より具体的にすると、ここの人々からより多くの助けが得られます. 検証しようとしているオブジェクトの具体的なケースを 1 つまたは 2 つ挙げてください。

編集

オブジェクトの検証に BindingGroup を使用することもできます。

public partial class MainWindow : Window
{
    public MainWindow()
    {
        InitializeComponent();
    }

    private void TextBox1_OnTextChanged(object sender, TextChangedEventArgs e)
    {
        grid.BindingGroup.CommitEdit();
    }
}

public class Indices
{
    public int ColorIndex { get; set; }
    public string ColorPrefix { get; set; }
    public int GradientIndex { get; set; }
    public string GradientPrefix { get; set; }
}

public class ValidateMe : ValidationRule
{
    public override ValidationResult Validate(object value, CultureInfo cultureInfo)
    {
        var bindingGroup = value as BindingGroup;
        var o = bindingGroup.Items[0] as Indices;
        return new ValidationResult(true, null);
    }
}
<Window x:Class="WpfApplication6.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:wpfApplication6="clr-namespace:WpfApplication6"
        Title="MainWindow"
        Width="525"
        Height="350">
    <Window.Resources>
        <wpfApplication6:Indices x:Key="Indices"
                                 ColorIndex="1"
                                 ColorPrefix="MyColor"
                                 GradientIndex="1"
                                 GradientPrefix="MyGradient" />
    </Window.Resources>
    <Grid x:Name="grid" DataContext="{StaticResource Indices}">
        <Grid.BindingGroup>
            <BindingGroup>
                <BindingGroup.ValidationRules>
                    <wpfApplication6:ValidateMe />
                </BindingGroup.ValidationRules>
            </BindingGroup>
        </Grid.BindingGroup>
        <TextBox TextChanged="TextBox1_OnTextChanged">
            <Binding Path="ColorIndex" UpdateSourceTrigger="PropertyChanged" />
        </TextBox>
    </Grid>
</Window>

RangeAtribute の使用:

    private void test()
    {
        Indices indices = new Indices();
        indices.ColorIndex = 20;

        var validationContext = new ValidationContext(indices);
        var validationResults = new List<System.ComponentModel.DataAnnotations.ValidationResult>();
        var tryValidateObject = Validator.TryValidateObject(indices, validationContext, validationResults,true);
    }

public class Indices
{
    [Range(1, 10)]
    public int ColorIndex { get; set; }

    public string ColorPrefix { get; set; }
    public int GradientIndex { get; set; }
    public string GradientPrefix { get; set; }
}
于 2013-07-10T01:25:20.853 に答える