简体   繁体   English

在Xaml中格式化TimeSpan(UWP)

[英]Format TimeSpan in Xaml (UWP)

How do you format a TimeSpan in XAML with a custom format? 如何使用自定义格式在XAML中格式化TimeSpan I want hour and minutes. 我想要小时和分钟。

Based on the official documentation , the way to do this in C# seems like it should be: 根据官方文档 ,在C#中执行此操作的方式似乎应该是:

interval.ToString(@"h\:mm");

I want to be able to format the TimeSpan in XAML, however, from within a binding. 我希望能够在绑定中格式化XAML中的TimeSpan This solution seems viable, but I wanted to create a general converter, that I could pass a format string into. 这个解决方案似乎可行,但我想创建一个通用转换器,我可以将格式字符串传入。 My converter is as follows: 我的转换器如下:

public class TimeSpanFormatConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, string language)
    {
        string result = "";
        if (value == null)
        {
            return null;
        }

        if (parameter == null)
        {
            return value;
        }

        if (value is TimeSpan timeSpan)
        {
            try
            {
                result = timeSpan.ToString((string)parameter);
            }
            catch (Exception e)
            {
                result = "";
            }
        }

        return result;
    }

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

In theory, I could use this converter as follows: 理论上,我可以使用这个转换器如下:

<Page.Resources>
    <converters:TimeSpanFormatConverter x:key="TimeSpanConverter"></converters:TimeSpanFormatConverter>
</Page.Resources>

<Grid>
    <!-- Some properties omitted for brevity. -->
    <ListView>
        <ListView.ItemTemplate>
            <DataTemplate x:DataType="models:MyModel">
                <Grid>

                    <!-- PROBLEM IS HERE -->
                    <TextBlock Text="{x:Bind Interval, Converter={StaticResource TimeSpanConverter}, ConverterParameter='h\:mm'}"></TextBlock>

                </Grid>
            </DataTemplate>
        </ListView.ItemTemplate>
    </ListView>
</Grid>

Note here that 'MyModel' has a property called 'Interval' that is of type 'TimeSpan'. 请注意,'MyModel'有一个名为'Interval'的属性,类型为'TimeSpan'。

This does not work, however, because I need the backslash. 但是,这不起作用,因为我需要反斜杠。 The XAML parsing removes the backslash, thus passing in "h:mm" to the converter (which I verified through the debugger). XAML解析删除反斜杠,从而将“h:mm”传递给转换器(我通过调试器验证)。

It also does not like two backslashes, as that throws a compiler error from the generated .g.cs file, saying "\\:" is an "unrecognized escape sequence". 它也不喜欢两个反斜杠,因为它会从生成的.g.cs文件中抛出编译器错误,说“\\:”是一个“无法识别的转义序列”。

No variations of encoding the back slash have worked. 编译反斜杠的变化没有变化。 I have tried: 我努力了:

h:mm
h\:mm
h\\:mm
h\\\:mm
h&#92;:mm
h&#92;\:mm
h&#92;&#92;:mm
h&#92;&#92;&#58;mm

What is the magic string of letters that need to be put into the ConverterParameter ? 什么是需要放入ConverterParameter的神奇字母串?

As an alternative, the MultiBinding solution explained here looked promising, but according to Visual Studio, MultiBinding is not supported in UWP. 作为替代方案, 这里解释的MultiBinding解决方案看起来很有前途,但根据Visual Studio,UWP不支持MultiBinding。

because I need the backslash. 因为我需要反斜杠。 The XAML parsing removes the backslash, thus passing in "h:mm" to the converter (which I verified through the debugger). XAML解析删除反斜杠,从而将“h:mm”传递给转换器(我通过调试器验证)。

Yep, it is correct, The ConverterParameter is object but not string, This may cause the backslash to be removed when xaml parses. 是的,它是正确的, ConverterParameter是对象但不是字符串,这可能导致在xaml解析时删除反斜杠。 I think you could create StringFormat property for your TimeSpanFormatConverter and pass the Format when Converter initialize. 我认为您可以为TimeSpanFormatConverter创建StringFormat属性,并在Converter初始化时传递Format

public class TimeSpanFormatConverter : IValueConverter
{
    public string StringFormat { get; set; }
    public object Convert(object value, Type targetType, object parameter, string language)
    {
        string result = "";
        if (value == null)
        {
            return null;
        }

        if (parameter == null)
        {
            return value;
        }

        if (value is TimeSpan timeSpan)
        {
            try
            {
                result = timeSpan.ToString(StringFormat);
            }
            catch (Exception e)
            {
                result = "";
            }
        }

        return result;
    }

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

Usage 用法

<Page.Resources>
    <local:TimeSpanFormatConverter x:Key="TimeSpanConverter" StringFormat="h\:mm"/>
</Page.Resources>
<Grid>
    <TextBlock VerticalAlignment="Center" Text="{x:Bind Interval, Converter={StaticResource TimeSpanConverter},Mode=TwoWay}"></TextBlock>
</Grid>

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM