基于 XAML 中对象属性的数值中的货币符号

Nut*_*uts 2 c# wpf formatting

如何显示数字(货币)值,WPF以便货币符号不会来自用户的区域设置、区域设置或任何内容,而是来自绑定对象的属性。

\n\n

例如,DataGrid我会有Item对象:

\n\n
 <DataGrid Grid.Row="1" ItemsSource="{Binding Items}">\n      <DataGrid.Columns>\n           <DataGridTextColumn Binding="{Binding SomeNumber, StringFormat=c}" />\n      </DataGrid.Columns>\n </DataGrid>\n\npublic Item()\n{\n    public double SomeNumber { get; set; }\n    public string CurrencySymbol { get; set; }\n}\n
Run Code Online (Sandbox Code Playgroud)\n\n

上述标准"c"格式将根据某些用户设置显示货币符号并忽略业务对象。

\n\n

但值应该这样显示

\n\n

SomeNumber = 3456234.67(正数)

\n\n
CurrencySymbol ="\xe2\x82\xac" > \xe2\x82\xac3 456 234.67\nCurrencySymbol ="$" > $3 456 234.67\nCurrencySymbol ="\xe2\x82\xbd" > \xe2\x82\xbd3 456 234.67\n
Run Code Online (Sandbox Code Playgroud)\n\n

SomeNumber = -3456234.67(负数)

\n\n
CurrencySymbol ="\xe2\x82\xac" > (\xe2\x82\xac3 456 234.67)\nCurrencySymbol ="$" > ($3 456 234.67)\nCurrencySymbol ="\xe2\x82\xbd" > (\xe2\x82\xbd3 456 234.67)\n
Run Code Online (Sandbox Code Playgroud)\n\n

SomeNumber= 0(零值)

\n\n
CurrencySymbol ="\xe2\x82\xac" > -\nCurrencySymbol ="$" > -\nCurrencySymbol ="\xe2\x82\xbd" > -\n
Run Code Online (Sandbox Code Playgroud)\n\n

有没有办法以这种方式获取货币符号的值StringFormat

\n

Tam*_*red 5

自动将货币符号附加到数字的正确方法StringFormat是使用 ConverterCulture:

\n\n
<!-- This will be shown as \'\xc2\xa51,423.7\' -->\n<DataGridTextColumn Header="Amount"\n                    Binding="{Binding Path=SomeNumber,\n                                      StringFormat=c,\n                                      ConverterCulture=\'ja-JP\'}"/>\n\n<!-- This will be shown as \'1.423.70 \xe2\x82\xac\' -->\n<DataGridTextColumn Header="Amount"\n                    Binding="{Binding Path=SomeNumber,\n                                      StringFormat=c,\n                                      ConverterCulture=\'de-DE\'}"/>\n
Run Code Online (Sandbox Code Playgroud)\n\n

它的好处是数字也根据要求进行格式化ConverterCulture

\n\n

在您的情况下,您想要自己格式化数字(请注意,货币符号的位置也会根据 发生变化ConverterCulture),此外,您想要决定自己显示的货币是什么,这使得无法在 上进行中继ConverterCulture

\n\n

在这种情况下,正确的方法是创建一个IValueConverterself

\n\n
public class CurrencyConverter : IValueConverter\n{\n    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)\n    {\n        Item valueAsItem = value as Item;\n        if (valueAsItem != null)\n        {\n            double amount = valueAsItem.SomeNumber;\n            if (amount == 0)\n            {\n                return "-"; //In the question this is the display for 0.\n            }\n            if (amount < 0)\n            {\n                amount *= -1; //In the question the numbers always display positive.\n            }\n            //In the question this is the format for the numbers.\n            return valueAsItem.CurrencySymbol + amount.ToString("### ### ###.###");\n        }\n        return string.Empty;\n    }\n\n    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)\n    {\n        throw new NotImplementedException();\n    }\n}\n
Run Code Online (Sandbox Code Playgroud)\n\n

并在.xaml

\n\n
    \n
  • 属性内部Window

    \n\n
    <Window.Resources>\n    <local:CurrencyConverter \n  x:Key="CurrencyConverter" />\n</Window.Resources>\n
    Run Code Online (Sandbox Code Playgroud)
  • \n
  • 对于DataGrid

    \n\n
    <DataGrid ItemsSource="{Binding MyItems}" AutoGenerateColumns="False">\n    <DataGrid.Columns>\n        <DataGridTextColumn Header="Amount"\n                            Binding="{Binding Converter={StaticResource CurrencyConverter}}"/>\n        </DataGrid.Columns>\n</DataGrid>\n
    Run Code Online (Sandbox Code Playgroud)
  • \n
\n\n

现在,当情况DataContext如下:

\n\n
public class MyDataContext\n{\n    public ICollectionView MyItems { get; set; }\n\n    public MyDataContext()\n    {\n        List<Item> items = new List<Item>\n        {\n            new Item { CurrencySymbol = "$", SomeNumber = 123.4 },\n            new Item { CurrencySymbol = "\xe2\x82\xb9", SomeNumber = 0 },\n            new Item { CurrencySymbol = "\xe2\x82\xb9", SomeNumber = -14345623.7 }\n        };\n\n        MyItems = CollectionViewSource.GetDefaultView(items);\n    }\n}\n\npublic class Item\n{\n    public double SomeNumber { get; set; }\n    public string CurrencySymbol { get; set; }\n}\n
Run Code Online (Sandbox Code Playgroud)\n\n

网格看起来像这样:

\n\n

WPF 绑定

\n\n

按照要求。

\n\n

double有关格式化的更多信息,请访问 MSDN

\n