/// <summary>
/// 颜色扩展类
/// </summary>
public static class ColorExtensions
{
/// <summary>
/// .NET预定义的系统颜色缓存列表
/// </summary>
private static readonly Dictionary<int, Color> ColorCache; /// <summary>
/// 拥有相同颜色代码值的系统颜色名称列表
/// </summary>
private static readonly Dictionary<int, string[]> DuplicateColorNameCache; /// <summary>
/// 静态构造函数
/// </summary>
static ColorExtensions()
{
ColorCache = new Dictionary<int, Color>();
DuplicateColorNameCache = new Dictionary<int, string[]>(); Type type = typeof(Color);
var properties = type.GetProperties(BindingFlags.Public | BindingFlags.Static | BindingFlags.IgnoreCase);
foreach (var propertyInfo in properties)
{
var value = propertyInfo.GetValue(null, null);
if (value is Color)
{
var color = (Color) value;
var intCode = color.ToIntCode();
if (!ColorCache.ContainsKey(intCode))
{
ColorCache.Add(intCode, color);
}
else
{
if (DuplicateColorNameCache.ContainsKey(intCode))
{
var values = DuplicateColorNameCache[intCode].ToList();
values.Add(color.Name);
DuplicateColorNameCache[intCode] = values.ToArray();
}
else
{
string[] values = { ColorCache[intCode].Name, color.Name };
DuplicateColorNameCache[intCode] = values;
}
}
}
}
} /// <summary>
/// 返回用十进制格式的颜色值,该值范围在0~16777215。
/// <para>例:0表示黑色,16777215表示白色。</para>
/// </summary>
/// <param name="color">Color对象</param>
/// <returns>十进制格式的颜色值</returns>
public static int ToIntCode(this Color color)
{
int c = color.R;
c = c | color.G << ;
c = c | color.B << ; return c; //以下代码等效
//先转成16进制值,再转成10进制值
//var hexCode = color.ToHexCode(false);//获取十六进制格式的颜色代码值
//int intCode = Convert.ToInt32(hexCode, 16);//获取十进制格式的颜色代码值
} /// <summary>
/// 返回十六进制格式的颜色值。
/// <para>例:Color.Gray(灰色)返回#808080。Color.FromArgb(192,192,192) 返回#C0C0C0</para>
/// </summary>
/// <param name="color">Color对象</param>
/// <param name="isAddPrefix">是否添加前缀"#", 默认为 true。</param>
/// <returns>十六进制格式的颜色值</returns>
public static string ToHexCode(this Color color, bool isAddPrefix = true)
{
return string.Format("{0}{1:X2}{2:X2}{3:X2}", isAddPrefix ? "#" : string.Empty, color.R, color.G, color.B); //下面这个方法,遇到.NET预定义的颜色对象,会返回颜色名称,而不是十六进制值。
//return ColorTranslator.ToHtml(color);
} /// <summary>
/// 返回HTML支持的颜色代码值,如果颜色已在HTML预定义,则返回颜色名称,否则返回十六进制格式表示的代码值。
/// <para>例:Color.Gray(灰色)返回Gray。Color.FromArgb(192,192,192) 返回#C0C0C0(银白色)</para>
/// <para>例:这是因为HTML中已预定义该颜色代码值,所以HTML支持该颜色代码值所对应的名称值。</para>
/// <para>.NET有三对预定义颜色的代码值是相同的,所以当传入以ARGB表示的颜色对象刚好在这三对预定义颜色范围,那么只会返回一对中的其中一个颜色名称。</para>
/// <para>当你需要知道另外一个颜色名称,你可以通过</para>
/// </summary>
/// <param name="color">Color对象</param>
/// <returns>如果颜色已在HTML预定义,则返回颜色的友好名称,否则返回十六进制格式表示的代码值</returns>
public static string ToHtmlCode(this Color color)
{
int intCode = color.ToIntCode();
if (ColorCache.ContainsKey(intCode))
{
return ColorTranslator.ToHtml(ColorCache[intCode]);
}
/*
* 上面之所以要这样做,是因为当使用者传过来一个使用ARGB表示的Color对象。
* 经过以上处理后,下面可以顺利返回颜色的名称。
* 例: Color color1 = Color.Gray; //灰色
* Color color2 = Color.FromArgb(color1.A, color1.R, color1.G, color1.B);
* color1.ToHtmlCode() 返回"Gray"
* color2.ToHtmlCode() 返回"#808080".
* 其实以上两个Color对象是相等的,这两个对象调用ToHtmlCode()扩展方法都应该返回同一个结果才是比较合理的。
*/
return ColorTranslator.ToHtml(color);
} /// <summary>
/// 获取具有相同代码值的颜色名称数组,如果没有,则返回null。
/// </summary>
/// <param name="color">Color对象</param>
/// <returns>返回具有相同代码值的颜色名称数组,如果没有,则返回null。</returns>
public static string[] GetDuplicateColorNames(this Color color)
{
int intCode = color.ToIntCode();
if (DuplicateColorNameCache.ContainsKey(intCode))
{
return DuplicateColorNameCache[intCode];
} return null;
} /// <summary>
/// 转换十进制格式的颜色代码值为Color对象
/// </summary>
/// <param name="intCode">十进制格式的颜色代码值</param>
/// <returns>返回Color对象</returns>
public static Color IntToColor(int intCode)
{
if (ColorCache.ContainsKey(intCode))
{
return ColorCache[intCode];
}
/*
* 以上处理与ToHtmlCode方法同理
* 先检查是否与.NET预定义的颜色匹配,如果匹配,返回.NET预定义的颜色对象(该对象包含一个可被直接理解的颜色友好名称)。
* 如果不匹配,则返回用ARGB表示的Color对象。
*/
string hexCode = Convert.ToString(intCode, );
return ColorTranslator.FromHtml("#" + hexCode);
} /// <summary>
/// 转换以"#"开头的六位长度的十六进制格式的颜色代码值或.NET预定义的颜色名称为Color对象
/// </summary>
/// <param name="hexCodeOrColorName">.NET预定义的颜色名称或以"#"开头的6位长度的十六进制颜色代码值</param>
/// <returns></returns>
public static Color HexOrNameToColor(string hexCodeOrColorName)
{
if (string.IsNullOrEmpty(hexCodeOrColorName))
{
return Color.Empty;
} try
{
//This is hex code.
if (hexCodeOrColorName[] == '#')
{
string hexCode = hexCodeOrColorName.Substring();
int intCode = Convert.ToInt32(hexCode, );
if (ColorCache.ContainsKey(intCode))
{
//返回拥有友好名称的Color对象
return ColorCache[intCode];
} //返回以ARGB表示的Color对象
return ColorTranslator.FromHtml(hexCodeOrColorName);
} //This is color name.
return ColorTranslator.FromHtml(hexCodeOrColorName);
}
catch (Exception)
{
return Color.Empty;
}
}
}

颜色扩展类--ColorExtensions的更多相关文章

  1. C# 扩展类

    C# 中提供一个非常实用的供能,扩展方法(Extension method) 扩展方法是通过额外的静态方法扩展现有的类型.通过扩展方法,可以对已有类型做自己想做的相关扩展.方法:定义静态类,扩展方法也 ...

  2. tp中调用PHP系统扩展类

    例如使用Redis扩展类: use Reids; $redis = new Redis();

  3. Java+7入门经典 - 6 扩展类与继承 Part 1/2

    第6章 扩展类与继承 面向对象编程的一个重要特性: 允许基于已定义的类创建新的类; 6.1 使用已有的类 派生 derivation, 派生类 derived class, 直接子类 direct s ...

  4. Thinkphp编辑器扩展类kindeditor用法

    一, 使用前的准备. 使用前请确认你已经建立好了一个Thinkphp站点项目. 1,Keditor.class.php和JSON.class.php 是编辑器扩展类文件,将他们拷贝到你的站点项目的Th ...

  5. 扩展javascript扩展(类,对象,原型)

     扩展javascript扩展(类,对象,原型)

  6. PHP扩展类ZipArchive实现压缩解压Zip文件和文件打包下载

    文章转载自:https://my.oschina.net/junn/blog/104464 PHP ZipArchive 是PHP自带的扩展类,可以轻松实现ZIP文件的压缩和解压,使用前首先要确保PH ...

  7. ASP.NET MVC4 HtmlHelper扩展类,实现分页功能 @Html.ShowPageNavigate

    本文主要做了一个HtmHelper类的分页扩展函数,方便在视图中调用,有需要的朋友可以参考一下,希望对大家有所帮助. 1.扩展HtmlHelper类方法ShowPageNavigate output. ...

  8. C#操作Xml树的扩展类

    本文提供一个操作Xml树的扩展类,与将xml字符串直接映射成实体对象的使用方法,供大家参考,学习. 下面附上源码 using System; using System.Collections.Gene ...

  9. 基于Thinkphp3.2的qq第三方oauth认证登录扩展类

    基于Thinkphp3.2的qq第三方oauth认证登录扩展类,由于腾讯oauth sdk写的太多,不能与thinkphp和好的结合,最终想法讲腾讯oauth sdk写成tp的扩展类先看代码,将代码保 ...

随机推荐

  1. 返回枚举中的desciption

    /// <summary> /// 返回枚举中的desciption /// </summary> /// <param name="value"&g ...

  2. Thread类的join()方法

    public class Demo { /** * Thread类的join()方法 * -------------------------------- * 1)join() * 2)join(lo ...

  3. Window通过Web方式修改域用户密码

    如何通过web方式修改域用户密码: 1.在Windows Server 2003上,系统默认提供了iisadmpwd作为一种修改域用户密码的方式 2.在Windows Server 2008上,可以提 ...

  4. Vue Cli 3.x项目如何部署到IIS子站点下

    Vue Router在IIS下的部署参考:https://router.vuejs.org/zh/guide/essentials/history-mode.html#%E5%90%8E%E7%AB% ...

  5. php代码画足球场

    用代码画了个足球场 原图: 代码画出的效果图: 代码如下: // 创建一个 200X200 的图像 $img = imagecreate(800, 500); // 分配颜色 $bg = imagec ...

  6. 浏览器打开exe文件

    <win-r> regedit 打开注册表,然后自定义协议 自定义协议注册表.reg 打开后导入 Windows Registry Editor Version 5.00 [HKEY_CL ...

  7. java 中的 Comparable 和 Comparator 与 Iterable 和 Iterator

    Comparable 和 Comparator Comparable 和 Comparator 是两个关系不大的类,其分别侧重于不同的方面. 其中,接口 Comparable<T> 强行对 ...

  8. 【Java线程安全】锁

    Java都有哪些锁? synchronized 和 reentranlock是最常见的,其中前者又JVM提供实现,后者有专门对应的java.util.concurrent包提供:同时后者功能更加丰富. ...

  9. vue的数据绑定和组件化

    组件:就是自定义标签, 也是Vue的实例对象; 组件好处:就像工作分工,函数封装等 组件分为全局组件和局部组件: 全局组件,在Vue身上的组件,所有的vue挂载的元素内都可以使用:正是因为这一点,co ...

  10. Express中间件的原理及实现

    在Node开发中免不了要使用框架,比如express.koa.koa2拿使用的最多的express来举例子开发中肯定会用到很多类似于下面的这种代码 var express = require('exp ...