在WPF Converter无法正常工作时需要帮助

时间:2017-04-12 20:41:48

标签: c# wpf

我有一个WPF应用程序,我使用转换器作为布尔值,如果在指定的时间范围内显示时间,则将某些文本变为红色。时间每3秒更新一次。当某人被标记为休息时他们继续休息超过15分钟,那么数据网格中显示的文本应该变为红色。在这种情况下没有任何反应,我无法找到问题。

转换器:

 public class BreakRangeToBooleanConverterTime : IValueConverter
    {
        public static readonly TimeSpan _toCompare = new TimeSpan(00, 15, 00);
        public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
        {
            if (!(value is TimeSpan))
                return DependencyProperty.UnsetValue;
            return (TimeSpan)value > _toCompare;
        }       

        public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
        {
            throw new Exception("To Long On Break");
        }        
    }

XAML代码:

 <MultiDataTrigger.Conditions>
  <Condition Binding="{Binding AuxReasons}" Value="Break"/>
  <Condition Binding="{Binding Time, RelativeSource={RelativeSource Self}, Converter={StaticResource breakconvtime}}" Value="True"/>                                
 </MultiDataTrigger.Conditions>
 <Setter Property="Foreground" Value="Red"/>
 <Setter Property="Background" Value="SkyBlue"/>
</MultiDataTrigger>

1 个答案:

答案 0 :(得分:0)

我不确定你绑定它的方式和位置,但这里可能不需要RelativeSource

以下适用于我(我使用Prism):

<Window x:Class="TimeBasedTrigger.Views.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:conv="clr-namespace:TimeBasedTrigger.Converters"
    xmlns:prism="http://prismlibrary.com/"
    Title="{Binding Title}"
    Width="525"
    Height="350"
    prism:ViewModelLocator.AutoWireViewModel="True">
<Window.Resources>
    <conv:BreakRangeToBooleanConverterTime x:Key="breakconvtime" />
    <Style x:Key="TimeoutStyle" TargetType="{x:Type TextBlock}">
        <Style.Triggers>
            <MultiDataTrigger>
                <MultiDataTrigger.Conditions>
                    <!--<Condition Binding="{Binding AuxReasons}" Value="Break" />-->
                    <Condition Binding="{Binding Time, Converter={StaticResource breakconvtime}}" Value="True" />
                </MultiDataTrigger.Conditions>
                <Setter Property="Foreground" Value="Red" />
                <Setter Property="Background" Value="SkyBlue" />
            </MultiDataTrigger>
        </Style.Triggers>
    </Style>
</Window.Resources>
<StackPanel>
    <StackPanel Orientation="Horizontal">
        <Label Content="Time: " />
        <TextBlock MinWidth="100"
                   Margin="5,0,10,0"
                   Text="{Binding Time, UpdateSourceTrigger=PropertyChanged}"
                   Style="{StaticResource TimeoutStyle}" / >
        <Button Command="{Binding StartTimerCommand}" Content="Start" />
        <Button Command="{Binding StopTimerCommand}" Content="Stop" />
    </StackPanel>
</StackPanel>
</Window>

视图模型:

public class MainWindowViewModel : BindableBase
{
    CancellationTokenSource _cts = new CancellationTokenSource();
    public MainWindowViewModel()
    {
        Time = new TimeSpan();
    }

    #region Properties

    private string _title = "Prism Unity Application";
    public string Title
    {
        get { return _title; }
        set { SetProperty(ref _title, value); }
    }

    private TimeSpan _time;
    public TimeSpan Time
    {
        get { return _time; }
        set { SetProperty(ref _time, value); }
    }

    private bool _isRunning;
    public bool IsRunning
    {
        get { return _isRunning; }
        set { SetProperty(ref _isRunning, value); }
    }
    #endregion // Properties

    #region Commands

    public DelegateCommand StartTimerCommand => new DelegateCommand(StartTimer);

    private async void StartTimer()
    {
        await RepeatActionEvery(() => UpdateTimer(), TimeSpan.FromSeconds(1), _cts.Token);
    }

    public DelegateCommand StopTimerCommand => new DelegateCommand(StopTimer);

    private void StopTimer()
    {
        _cts.Cancel();
        Time = new TimeSpan();
        _cts = new CancellationTokenSource();
    }

    #endregion // Commands

    #region Private Methods

    private void UpdateTimer()
    {
        var timeIncrement = TimeSpan.FromSeconds(1);
        Time = Time.Add(timeIncrement);
    }

    #endregion // Private Methods

    #region Helpers

    public static async Task RepeatActionEvery(Action action, TimeSpan interval, CancellationToken cancellationToken)
    {
        while (true)
        {
            action();
            Task task = Task.Delay(interval, cancellationToken);

            try { await task; }
            catch (TaskCanceledException) { return; }
        }
    }

    #endregion // Helpers
}