1

I have two search text boxes, Above and Below, that I have to set restrains on. The number in Below can't be higher than the number in Above and the number in Above can't be lower than the one in Below.

If one number is not right, it will should be set equal to the other number.

The problem is that Above doesn't get updated, while Bottom does (even though the properties are set in the same way).

xaml:

<common:SearchTextBox Grid.Column="1" 
    VerticalAlignment="Center"
    Label="Enter value in feet"
    common:AllowableTextInput.IsIgnoreWhiteSpace="True"
    common:AllowableTextInput.IsMatch="^[0-9]{0,5}$"
    Text="{Binding Path=AboveAircraft, UpdateSourceTrigger=PropertyChanged,
      Converter={StaticResource AboveAircraftConveter}, ConverterParameter=4000}"/>
<Label Grid.Row="1" Grid.Column="0" 
    Style="{StaticResource FormLabelStyle}"
    Content="Below Aircraft (ft):"/>
<common:SearchTextBox Grid.Row="1" Grid.Column="1" 
    VerticalAlignment="Center" HorizontalAlignment="Stretch"
    common:AllowableTextInput.IsIgnoreWhiteSpace="True"
    common:AllowableTextInput.IsMatch="^[0-9]{0,5}$"
    Text="{Binding Path=BelowAircraft, UpdateSourceTrigger=PropertyChanged,
      Converter={StaticResource BelowAircraftConveter}, ConverterParameter=2000}"
    Label="Enter value in feet" />

C#:

public int AboveAircraft
{
    get { return _above; }
    set
    {   
        if (SetProperty(ref _above, value, "AboveAircraft") && _updateModel)
        {
            if (Model.AltitudeBand == null)
            {
                Model.AltitudeBand = new AltitudeBand();
            }

            if (PropertyChanged != null)
            {

                PropertyChanged(this, new PropertyChangedEventArgs("AboveAircraft"));
                if (_above < _below)
                {
                     _below = AboveAircraft;
                }
            }

            Model.AltitudeBand.Above = new AltitudeBandLimit() { Unit = AltitudeUnit.Foot, Value = _above };
        }
    }
}

/// <summary>
/// Below the route of flight in ft
/// </summary>
public int BelowAircraft
{
    get { return _below; }
    set
    {
       if (SetProperty(ref _below, value, "BelowAircraft") && _updateModel)
       {
            if (Model.AltitudeBand == null)
            {
                Model.AltitudeBand = new AltitudeBand();
            }

            if (PropertyChanged != null)
            {
                _below = value;
                PropertyChanged(this, new PropertyChangedEventArgs("BelowAircraft"));
                if (_below > _above)
                {
                    AboveAircraft = _below;
                }
            }
           Model.AltitudeBand.Below = new AltitudeBandLimit() { Unit = AltitudeUnit.Foot, Value = _below };
        }
    }
}
4

1 回答 1

3

您正在使用 _below = AboveAircraft;您的AboveAircraft setter 方法,但您正在绑定BelowAircraft

要么更改_below = AboveAircraft;BelowAircraft = AboveAircraft;发送通知BelowAircraft,即

            if (PropertyChanged != null)
            {

                PropertyChanged(this, new PropertyChangedEventArgs("AboveAircraft"));
                if (_above < _below)
                {
                     _below = AboveAircraft;
                     PropertyChanged(this, new PropertyChangedEventArgs("BelowAircraft"));
                }
            }

当您更改更改另一个绑定属性的属性时,您必须为两个属性发送通知,而不仅仅是一个。

当然,您也必须对BelowAircraftsetter 应用相同的更改。

编辑:只是为了澄清:这两种方法中的哪一种取决于设置属性是否会导致循环事件触发。如果它会导致循环事件(即无限触发),那么您只需像上面的代码一样发送第二个通知。

编辑 2:在回复评论时,您的 XAML 绑定设置为UpdateSourceTrigger=PropertyChanged. 这意味着,您setter将被您输入的每个字符调用。

当您输入“4000”时,“Above”字段中的第一个字符将为 4,这将导致以下值变为 4。相反,您只想在用户完成输入后更新 Text 字段。

根据“ UpdateSourceTrigger Enumeration ”的 MSDN 文档,有 4 个值。对于文本字段,您可能想要使用UpdateSourceTrigger=DefaultUpdateSourceTrigger=LostFocus。然后只有在用户完成输入时才会调用 setter,而不是在文本字段中键入的每个字符上调用 setter。

于 2013-09-01T14:19:41.580 回答