Skip to content

Commit

Permalink
Fixed #33 + refactoring.
Browse files Browse the repository at this point in the history
  • Loading branch information
kirsan31 committed Mar 18, 2023
1 parent 5b5a444 commit 3aa9100
Showing 1 changed file with 148 additions and 145 deletions.
293 changes: 148 additions & 145 deletions src/System.Windows.Forms.DataVisualization/Utilities/ValueConverter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -12,157 +12,160 @@

using System.Globalization;

namespace System.Windows.Forms.DataVisualization.Charting.Utilities
namespace System.Windows.Forms.DataVisualization.Charting.Utilities;

/// <summary>
/// ValueConverter class is used when numeric or DateTime
/// value needs to be converted to a string using specified format.
/// </summary>
internal static class ValueConverter
{
#region Methods

/// <summary>
/// ValueConverter class is used when numeric or DateTime
/// value needs to be converted to a string using specified format.
/// Converts value to string using specified format.
/// </summary>
internal static class ValueConverter
{
#region Methods

/// <summary>
/// Converts value to string using specified format.
/// </summary>
/// <param name="chart">Reference to the chart object.</param>
/// <param name="obj">Reference to the object being formatted.</param>
/// <param name="objTag">Additional object tag.</param>
/// <param name="value">Value converted to string.</param>
/// <param name="format">Format string.</param>
/// <param name="valueType">Value type.</param>
/// <param name="elementType">Chart element type being formatted.</param>
public static string FormatValue(
Chart chart,
object obj,
object objTag,
double value,
string format,
ChartValueType valueType,
ChartElementType elementType)
{
format ??= string.Empty;
string convertionFormat = format;
string result = string.Empty;

// Make sure value index is part of the format
if(convertionFormat != null && convertionFormat.Length > 0)
{
int bracketIndex = convertionFormat.IndexOf('{', 0);
if(bracketIndex >= 0)
{
while(bracketIndex >= 0)
{
// If format is not followed by the value index
if(!convertionFormat[bracketIndex..].StartsWith("{0:", StringComparison.Ordinal))
{
// Check character prior to the bracket
if(bracketIndex >= 1 && convertionFormat.Substring(bracketIndex - 1, 1) == "{")
{
continue;
}
else
{
// Insert value index in format
convertionFormat = convertionFormat.Insert(bracketIndex + 1, "0:");
}
}

bracketIndex = convertionFormat.IndexOf('{', bracketIndex + 1);
}
}
else
{
convertionFormat = "{0:" + convertionFormat + "}";
}
}

// Date/time formating
if (valueType == ChartValueType.DateTime ||
valueType == ChartValueType.DateTimeOffset ||
valueType == ChartValueType.Date)
{
// Set default format
if(convertionFormat.Length == 0)
{
convertionFormat = "{0:d}";
if (valueType == ChartValueType.DateTimeOffset)
convertionFormat += " +0";
}

// Convert date to string
result = String.Format(CultureInfo.CurrentCulture, convertionFormat, DateTime.FromOADate(value));
}
else if(valueType == ChartValueType.Time)
{
// Set default format
if(convertionFormat.Length == 0)
{
convertionFormat = "{0:t}";
}

// Convert date to string
result = String.Format(CultureInfo.CurrentCulture, convertionFormat, DateTime.FromOADate(value));
}
else
{
bool failedFlag = false;

// Set default format
if(convertionFormat.Length == 0)
{
convertionFormat = "{0:G}";
}

try
{
// Numeric value formatting
result = String.Format(CultureInfo.CurrentCulture,convertionFormat, value);
}
catch(FormatException)
{
failedFlag = true;
}

// If numeric formatting failed try to format using decimal number
if(failedFlag)
{
failedFlag = false;
try
{
// Decimal value formatting
result = String.Format(CultureInfo.CurrentCulture, convertionFormat, (long)value);
}
catch (ArgumentNullException)
{
failedFlag = true;
}
catch (FormatException)
/// <param name="chart">Reference to the chart object.</param>
/// <param name="obj">Reference to the object being formatted.</param>
/// <param name="objTag">Additional object tag.</param>
/// <param name="value">Value converted to string.</param>
/// <param name="format">Format string.</param>
/// <param name="valueType">Value type.</param>
/// <param name="elementType">Chart element type being formatted.</param>
public static string FormatValue(
Chart chart,
object obj,
object objTag,
double value,
string format,
ChartValueType valueType,
ChartElementType elementType)
{
format ??= string.Empty;
string convertionFormat = format;
string result = string.Empty;

// Make sure value index is part of the format
if (convertionFormat != null && convertionFormat.Length > 0)
{
int bracketIndex = convertionFormat.IndexOf('{', 0);
if (bracketIndex >= 0)
{
while (bracketIndex >= 0)
{
// If format is not followed by the value index
if (!convertionFormat[bracketIndex..].StartsWith("{0:", StringComparison.Ordinal))
{
failedFlag = true;
// Check character prior to the bracket
if (bracketIndex >= 1 && convertionFormat.Substring(bracketIndex - 1, 1) == "{")
{
continue;
}
else
{
// Insert value index in format
convertionFormat = convertionFormat.Insert(bracketIndex + 1, "0:");
}
}
}

// Return format string as result (literal) if all formatting methods failed
if(failedFlag)
{
result = format;
}
}

// For the Reporting Services chart a special number formatting
// handler may be set and used for all formatting needs.
if (chart != null)

bracketIndex = convertionFormat.IndexOf('{', bracketIndex + 1);
}
}
else
{
convertionFormat = "{0:" + convertionFormat + "}";
}
}

// Date/time formating
if (valueType == ChartValueType.DateTime ||
valueType == ChartValueType.DateTimeOffset ||
valueType == ChartValueType.Date)
{
// Set default format
if (convertionFormat.Length == 0)
{
convertionFormat = "{0:d}";
if (valueType == ChartValueType.DateTimeOffset)
convertionFormat += " +0";
}

// Convert date to string
result = string.Format(CultureInfo.CurrentCulture, convertionFormat, DateTime.FromOADate(value));
}
else if (valueType == ChartValueType.Time)
{
// Set default format
if (convertionFormat.Length == 0)
{
// Call number formatter
FormatNumberEventArgs eventArguments = new FormatNumberEventArgs(value, format, valueType, result, objTag, elementType);
chart.CallOnFormatNumber(obj, eventArguments);
result = eventArguments.LocalizedValue;
convertionFormat = "{0:t}";
}

return result;
}

#endregion
}
// Convert date to string
result = string.Format(CultureInfo.CurrentCulture, convertionFormat, DateTime.FromOADate(value));
}
else
{
bool failedFlag = false;

// Set default format
if (convertionFormat.Length == 0)
{
convertionFormat = "{0:G}";
}

try
{
// Numeric value formatting
// Workaround for "-0" label due to Floating-Point parsing changes in .NET Core 3. See https://devblogs.microsoft.com/dotnet/floating-point-parsing-and-formatting-improvements-in-net-core-3-0/
if (value == 0d && double.IsNegative(value))
result = string.Format(CultureInfo.CurrentCulture, convertionFormat, 0d);
else
result = string.Format(CultureInfo.CurrentCulture, convertionFormat, value);
}
catch (FormatException)
{
failedFlag = true;
}

// If numeric formatting failed try to format using decimal number
if (failedFlag)
{
failedFlag = false;
try
{
// Decimal value formatting
result = string.Format(CultureInfo.CurrentCulture, convertionFormat, (long)value);
}
catch (ArgumentNullException)
{
failedFlag = true;
}
catch (FormatException)
{
failedFlag = true;
}
}

// Return format string as result (literal) if all formatting methods failed
if (failedFlag)
{
result = format;
}
}

// For the Reporting Services chart a special number formatting
// handler may be set and used for all formatting needs.
if (chart != null)
{
// Call number formatter
FormatNumberEventArgs eventArguments = new FormatNumberEventArgs(value, format, valueType, result, objTag, elementType);
chart.CallOnFormatNumber(obj, eventArguments);
result = eventArguments.LocalizedValue;
}

return result;
}

#endregion
}

0 comments on commit 3aa9100

Please sign in to comment.