将 BGRA 8 位十六进制字符串转换为 System.Drawing.Color



我有从Delphi应用程序获得的BGRA格式的颜色。我将它们作为 8 位字符串读取到我的 C# 应用程序中。现在,我尝试将它们转换为 C# 颜色格式。我得到的字符串如下所示:

string color = "$00FF00FF";

我尝试重新转换颜色,然后将其转换为 Int 以将其转换为System.Drawing颜色

private Color ConvertColorFromBgra(string color)
{
string argb = "#";
var bgra = FunctionLibrary.SplitByLength(color.Replace("$", ""), 2);
foreach (var value in bgra.Revert())
{
argb += value;
}
return Color.FromArgb(Convert.ToInt32(argb, 16));
}

其中 SplitByLenght 是我在 SO 上找到的一个函数(我从另一个类调用(:

public static IEnumerable<string> SplitByLength(this string str, int maxLength)
{
for (int index = 0; index < str.Length; index += maxLength)
{
yield return str.Substring(index, Math.Min(maxLength, str.Length - index));
}
}

但不知何故它不起作用,我收到错误:

System.FormatException:"找不到任何可识别的数字。

我觉得字符串没有像预期的那样转换为 Int,但我没有找到任何修复程序。你能帮我解决问题,或者有其他更好的方法来解决问题吗?

为了避免字符串操作,你可以用string.Substring(1)删除第一个字符,然后使用 Convert.ToInt32(( 重载,它接受一个特定的基(16(来将字符串转换为 LEint

然后可以使用BitConverter.GetBytes((从转换后的int中提取字节并反转顺序.
► 你可能想在反转字节顺序之前添加一个检查:如果BitConverter.IsLittleEndian返回false,我们已经使用了BigEndian处理器,所以在这种情况下我们不会反转顺序。

在后面重构int值,并使用 Color.FromArgb 返回包含 Alpha 通道的颜色,或使用 ColorTranslator.FromWin32 忽略它(无论如何都将 Alpha 通道设置为255:例如,如果需要在不支持颜色透明度的控件中使用此颜色(。

我将此方法添加为Sting扩展(string.ToARGBColor(bool)(。根据需要命名。

public static class StringsExtensions
{
public static Color ToARGBColor(this string hexColor, bool includeAlpha)
{
int ci = BitConverter.ToInt32(BitConverter.GetBytes(
Convert.ToInt32(hexColor.Substring(1), 16)).Reverse().ToArray(), 0);
return includeAlpha ? Color.FromArgb(ci) : ColorTranslator.FromWin32(ci);
}
}

所以你可以把它称为:

string colorString = "$00FF00AA";
Color colorWithAlpha = colorString.ToARGBColor(true);
Color colorNoAlpha = colorString.ToARGBColor(false);

使用另一种经典的 BigEndian 到 LittleEndian 的转换方法:
(应该会稍微快一点,也许可以试驾一下(

byte[] b = BitConverter.GetBytes(Convert.ToInt32(colorString.Substring(1), 16));
int ci = (b[0] << 24) | (b[1] << 16) | (b[2] << 8) | b[3];
Color c = Color.FromArgb(ci);

我显然找到了一个解决方案,只需要使用ColorTranslator.FromHtml(argb)而不是Color.FromArgb(Convert.ToInt32(argb, 16))

最新更新