在WPF日历中将日期显示为假期

时间:2018-11-19 08:49:36

标签: c# wpf wpf-controls

我正在使用WPF日历控件添加假日。用户可以选择日期,并将所选的日期作为假日插入数据库表中。 插入后,我将在假期表中的日期在日历中显示为BlackoutDates,如以下代码所示。

XAML

 <Calendar x:Name="HolidayCalendar" SelectedDatesChanged="Calendar_SelectionChanged"
    SelectionMode="MultipleRange" Loaded="Calendar_Loaded"> 

C#

DateTime now = DateTime.Now;
var startDate = new DateTime(now.Year, now.Month, 1);
var endDate = startDate.AddMonths(1).AddDays(-1);
GetHolidayService getHolidayService = new GetHolidayService();
ObservableCollection<GetHoliday> GetHolidayBaseList = new ObservableCollection<GetHoliday>();
PostHoliday postHoliday = new PostHoliday();
postHoliday.StartDate = startDate;
postHoliday.EndDate = endDate;
GetHolidayBaseList = getHolidayService.GetHolidayServiceFunction(postHoliday);
foreach (var item in GetHolidayList)
{

   HolidayCalendar.BlackoutDates.Add(new CalendarDateRange(item.HolidayDate,item.HolidayDate)) ;
}

当前输出

Current output

我想实现这样的目标-假日标记为红色

Preferred output

与此link

对于编写此功能所需的控制模板的任何帮助,我们深表感谢。

谢谢!

1 个答案:

答案 0 :(得分:1)

这是您的操作方式,

首先根据标准样式为CalendarDataButton定义自定义样式

    <Calendar x:Name="HolidayCalendar" SelectionMode="MultipleRange">
        <Calendar.CalendarDayButtonStyle>
            <Style TargetType="CalendarDayButton" BasedOn="{StaticResource {x:Type CalendarDayButton}}">
                <Style.Triggers>
                    <Trigger Property="IsBlackedOut" Value="True">
                        <Setter Property="Background" Value="DeepPink"/>
                        <Setter Property="local:CalenderHelper.IsBlackOutDisabled" Value="True"/>
                    </Trigger>
                </Style.Triggers>
            </Style>
        </Calendar.CalendarDayButtonStyle>
        <Calendar.BlackoutDates>
            <CalendarDateRange Start="21-Nov-2018" End="21-Nov-2018"/>
            <CalendarDateRange Start="25-Nov-2018" End="25-Nov-2018"/>
        </Calendar.BlackoutDates>
    </Calendar>

为了从停电日期中删除罢工标记,您将必须使用以下附加的属性'IsBlackOutDisabled'

public class CalenderHelper : DependencyObject
{
    public static readonly DependencyProperty IsBlackOutDisabledProperty =
        DependencyProperty.RegisterAttached("IsBlackOutDisabled", typeof(bool), typeof(CalenderHelper), new PropertyMetadata(false, OnIsBlackOutDisabledChanged));

    public static bool GetIsBlackOutDisabled(DependencyObject obj)
    {
        return (bool)obj.GetValue(IsBlackOutDisabledProperty);
    }

    public static void SetIsBlackOutDisabled(DependencyObject obj, bool value)
    {
        obj.SetValue(IsBlackOutDisabledProperty, value);
    }

    private static void OnIsBlackOutDisabledChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        CalendarDayButton dayButton = d as CalendarDayButton;
        if (dayButton.IsLoaded)
        {
            SetBlackout(dayButton, (bool)e.NewValue);
        }
        else
        {
            dayButton.Loaded += (s, ee) =>
            {
                SetBlackout(dayButton, (bool)e.NewValue);
            };
        }
    }

    static void SetBlackout(CalendarDayButton dayButton, bool collapsed)
    {
        ControlTemplate template = dayButton.Template;
        Path blackoutPath = template.FindName("Blackout", dayButton) as Path;
        if (collapsed)
            blackoutPath.Visibility = System.Windows.Visibility.Collapsed;
        else
            blackoutPath.Visibility = System.Windows.Visibility.Visible;
    }
}

更新:

如果希望日历可以选择彩色日期,则必须采用其他方法。停电日期对您不起作用。

这种方法需要转换器为日期着色。

首先根据标准样式为CalendarDataButton定义自定义样式

<Window.Resources>
    <local:CustomLetterDayConverter x:Key="CustomLetterDayConverter" />
    <Style x:Key="CalendarDayButtonStyle" TargetType="{x:Type CalendarDayButton}">
        <Style.Triggers>
            <DataTrigger Binding="{Binding Converter={StaticResource CustomLetterDayConverter}}" Value="{x:Null}">
                <Setter Property="Background" Value="HotPink"></Setter>
            </DataTrigger>
        </Style.Triggers>
    </Style>
</Window.Resources>
<Grid>
    <Calendar x:Name="HolidayCalendar" SelectionMode="MultipleRange" SelectedDate="{Binding SelectedDate}"
              CalendarDayButtonStyle="{StaticResource CalendarDayButtonStyle}"
              >
    </Calendar>
</Grid>

自定义转换器

public class CustomLetterDayConverter : IValueConverter
{
    static HashSet<DateTime> dict = new HashSet<DateTime>();
    static CustomLetterDayConverter()
    {
        dict.Add(DateTime.Today);
        dict.Add(DateTime.Today.AddDays(1));
        dict.Add(DateTime.Today.AddDays(2));
        dict.Add(DateTime.Today.AddDays(5));
    }

    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        string text = null;
        if (dict.Contains((DateTime)value))
            text = null;
        else
            text = "";

        return text;
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        throw new NotImplementedException();
    }
}