How can I override the currency formatting for the current culture for an ASP.NET web application?

六眼飞鱼酱① 提交于 2019-12-01 21:57:53

问题


The currency decimal and thousand separators for the en-ZA region are ',' and ' ' respectively, but the separators in common use are '.' for decimal, plus my user wants ',' for the thousands separator. I wish to set these globally, so that I only have to use the {0:C} format string for all my currency fields, without having to any explicit Format or ToString calls.

I would prefer to be able to do this without changing the culture settings on the web server, as I also need to set the decimal places for currency to zero, as cents are not wanted when reporting on estimates of R100k and up etc. I wouldn't want to arbitrarily set the whole culture to zero places, just one for this application.

In comments to his answer on this question, Jon Skeet suggests cloning the current culture and setting and changing the required settings. I have done this as follows:

void Application_Start(object sender, EventArgs e)
{
    var newCulture = (CultureInfo)CultureInfo.CurrentCulture.Clone();
    newCulture.NumberFormat.CurrencyDecimalSeparator = ".";
    newCulture.NumberFormat.CurrencyGroupSeparator = ",";
}

However, how to I activate that new culture for all requests the application handles from this point on? Is there another way to achieve what I wish to do?


回答1:


You can use Application_BeginRequest event to set the culture for every request. Inside event:

var newCulture = (CultureInfo)CultureInfo.CurrentCulture.Clone();
newCulture.NumberFormat.CurrencyDecimalSeparator = ".";
newCulture.NumberFormat.CurrencyGroupSeparator = ",";

System.Threading.Thread.CurrentThread.CurrentCulture = newCulture;
System.Threading.Thread.CurrentThread.CurrentUICulture = newCulture;



回答2:


Having asked many questions and done many experiments, I have decided that it's safe to state that the only way of doing this is to use controls derived from the out of box controls and do your own formatting using a customised culture object. Derive your control from e.g. BoundField and provide your own FormatProvider:

public class BoundReportField : BoundField
{
    protected virtual string GetDefaultFormatString(FieldFormatTypes formatType)
    {
        var prop = typeof(FormatStrings).GetProperty(formatType.ToString()).GetValue(null, null);
        return prop.ToString();
    }

    protected virtual IFormatProvider GetFormatProvider(FieldFormatTypes formatType)
    {
        var info = (CultureInfo)CultureInfo.CurrentCulture.Clone();
        info.NumberFormat.CurrencyDecimalDigits = 0;
        info.NumberFormat.CurrencySymbol = "R";
        info.NumberFormat.CurrencyGroupSeparator = ",";
        info.NumberFormat.CurrencyDecimalSeparator = ".";
        return info;
    }

    private FieldFormatTypes _formatType;
    public virtual FieldFormatTypes FormatType
    {
        get { return _formatType; }
        set
        {
            _formatType = value;
            DataFormatString = GetDefaultFormatString(value);
        }
    }

    protected override string FormatDataValue(object dataValue, bool encode)
    {
        // TODO Consider the encode flag.
        var formatString = DataFormatString;
        var formatProvider = GetFormatProvider(_formatType);
        if (string.IsNullOrWhiteSpace(formatString))
        {
            formatString = GetDefaultFormatString(_formatType);
        }
        return string.Format(formatProvider, formatString, dataValue);
    }
}

I will publish an article later with all the gory details.



来源:https://stackoverflow.com/questions/7201532/how-can-i-override-the-currency-formatting-for-the-current-culture-for-an-asp-ne

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!