ImageProcessor组件
ImageProcessor组件
开源免费的.NET图像即时处理的组件ImageProcessor
承接以前的组件系列,这个组件系列旨在介绍.NET相关的组件,让大家可以在项目中有一个更好的选择,社区对于第三方插件的介绍还是比较少的,很多博文的内容主要还是介绍一些简单的操作(很多人都说博客园现在是“hello world”的水平,博文质量在下降,对于这一说法,我觉得这个说法有些过头了,可能一些博文的确写的比较初级,但是很多博文的深入还是比较大,只是很少受人关注),这个组件系列主要在介绍一些功能的组件,附带该组件的核心对象介绍。
组件的介绍绝对不是一篇文章可以叙述完的,因为一个组件是经过开发者很长周期的开发,绝不是我这里一篇简单的博文就可以介绍完毕的,组件介绍的系列,一般会沿袭着组件背景介绍、组件使用介绍、核心对象介绍等等内容。如果对组件感兴趣,可以深入的了解和学习。
废话少说,进入正题。
我们在项目中很多时候都会对文件进行处理,例如文件的上传下载等等。其中对图片的实时操作也会较多,在这里介绍一款用C#编写的轻量级库的集合,它允许你使用.NET 4.5+来动态地处理图像的组件,那就是ImageProcessor,用于图像的即时处理的.NET库。(组织的开源项目组,会经过第一个项目的磨合后,第二项目会开发一个.NET Core组件)
一.ImageProcessor组件概述
ImageProcessor是用C#编写的轻量级库的集合,它允许你使用.NET 4.5+来动态地处理图像,包括两个主库ImageProcessor(用于桌面和应用程序使用)ImageProcessor.Web(ASP.NET构建的动态图像处理扩展),该组件快速,可扩展,易于使用,捆绑了一些很强大的功能,而且是完全开源。该组件有两个部分,我们今天将主要讲解ImageProcessor部分的内容,如果对另外一个感兴趣,可以自行了解。
ImageProcessor.Web向项目添加了一个可配置的HttpModule,允许对图像文件进行即时处理。该模块还提供了一个基于文件和浏览器的缓存,可以处理数百万的图像,增加处理输出和节省宝贵的服务器内存。该组件的功能方法包括:调整大小,旋转,圆角,翻转,裁剪,水印,过滤器,饱和度,亮度,对比度,质量,格式,小插曲,高斯模糊,高斯锐化和透明度。
ImageProcessor.Web的当前版本是4.8.2,可以下载源码和DLL文件(本人建议最好下载源码,好处就不在这里赘述)。
ImageProcessor.Web是ImageProcessor的Web扩展,允许开发人员使用Url API的查询字符串参数作为指令执行图像操作。此过程的输出是高度优化的网络,以确保web项目较高的性能。安装ImageProcessor.Web时,默认情况下,Web.config中添加配置节点,如下节点。
<add name="ImageProcessorModule" type="ImageProcessor.Web.HttpModules.ImageProcessingModule, ImageProcessor.Web" /></httpModules>
这允许库ImageProcessingModule拦截本地图像处理请求。ImageProcessor.Web是高度可配置的。可以将其他配置文件添加到解决方案中,以便从多个来源检索,处理和缓存图像。对于该组件的配置设置可以查看文档。
二.ImageProcessor组件操作概述
介绍了组件的相关信息,在这里介绍一下该组件的操作实例。ImageFactory类提供了对给定图像执行各种操作功能的方法。它经过精心设计以防止在以高性能方式处理图像时通常发生的各种内存泄漏。这使其可以安全地在桌面和Web环境中使用。ImageFactory自动检测给定图像的正确文件类型,并且该类的API是流畅的,这允许您轻松地链接方法以提供所需的输出。例如,以下代码加载,调整大小,设置新格式并保存包含图像信息的MemoryStream。

public static void Image(string file)
{
if (string.IsNullOrEmpty(file))
{
throw new ArgumentNullException(file);
}
byte[] photoBytes = System.IO.File.ReadAllBytes(file);
// 检测格式
ISupportedImageFormat format = new JpegFormat { Quality = 70 };
Size size = new Size(150, 0);
using (MemoryStream inStream = new MemoryStream(photoBytes))
{
using (MemoryStream outStream = new MemoryStream())
{
// 使用重载初始化ImageFactory以保留EXIF元数据。
using (ImageFactory imageFactory = new ImageFactory(true))
{
// 加载,调整大小,设置格式和质量并保存图像。
imageFactory.Load(inStream)
.Resize(size)
.Format(format)
.Save(outStream);
//对获取的imageFactory对象进行对应的操作
}
//对获取的数据流进行操作
}
}

对于图片的操作,具体有较多的操作方式,具体的方法有如下的方法:
方法名称 | 方法操作说明 |
Reset | 将当前图像重置为其原始加载状态 |
Alpha | 更改当前图像的不透明度 |
AutoRotate | 执行自动旋转以确保反映EXIF定义的旋转最终图像 |
BitDepth | 改变当前图像的位深度 |
Brightness | 更改当前图像的亮度 |
BackgroundColor | 更改当前图像的背景颜色 |
Constrain | 约束当前图像,调整其大小以适合给定的尺寸,同时保持其纵横比 |
Contrast | 更改当前图像的对比度 |
Crop | 将当前图像裁剪到给定的位置和大小 |
DetectEdges | 检测当前图像中的边缘 |
Resolution | 设置图像的分辨率 |
EntropyCrop | 将图像修剪到最大熵的区域 |
Filter | 将过滤器应用于当前图像 |
Flip | 水平或垂直翻转当前图像 |
Gamma | 调整给定图像的灰度(光强度)分量 |
GaussianBlur | 使用高斯内核模糊当前图像 |
Hue | 改变当前图像的色调,改变整体颜色 |
Halftone | 将当前图像转换为该图像的CMYK半色调表示 |
Quality | 改变当前图像的输出质量 |
ReplaceColor | 替换当前图像中的颜色 |
Resize | 将当前图像调整为给定尺寸 |
Rotate | 将当前图像旋转给定角度 |
以上只是列出了一些主要的操作方法,还有其他的方法这里就不再介绍,有兴趣可以自己取实践。下面就介绍一下一些核心对象。
三.ImageProcessor核心对象解析
解析来我们具体了解一下核心的方法和属性,看看源码还是有好处。
1.ImageFactory.Load()

public ImageFactory Load(string imagePath)
{
FileInfo fileInfo = new FileInfo(imagePath);
if (fileInfo.Exists)
{
this.ImagePath = imagePath;
using (FileStream fileStream = new FileStream(imagePath, FileMode.Open, FileAccess.Read))
{
ISupportedImageFormat format = FormatUtilities.GetFormat(fileStream);
if (format == null)
{
throw new ImageFormatException("Input stream is not a supported format.");
}
MemoryStream memoryStream = new MemoryStream();
fileStream.CopyTo(memoryStream);
memoryStream.Position = 0;
this.Image = format.Load(memoryStream);
this.CurrentBitDepth = Image.GetPixelFormatSize(this.Image.PixelFormat);
this.InputStream = memoryStream;
format.Quality = DefaultQuality;
format.IsIndexed = FormatUtilities.IsIndexed(this.Image);
this.backupFormat = format;
this.CurrentImageFormat = format;
foreach (PropertyItem propertyItem in this.Image.PropertyItems)
{
this.ExifPropertyItems[propertyItem.Id] = propertyItem;
}
this.backupExifPropertyItems = this.ExifPropertyItems;
IAnimatedImageFormat imageFormat = this.CurrentImageFormat as IAnimatedImageFormat;
if (imageFormat != null)
{
imageFormat.AnimationProcessMode = this.AnimationProcessMode;
}
Image formatted = this.Image.Copy(this.AnimationProcessMode);
this.Image.Dispose();
this.Image = formatted;
this.ShouldProcess = true;
}
}
else
{
throw new FileNotFoundException(imagePath);
}
return this;
}

该方法用来加载要处理的图像的方法, 始终首先调用此方法。该方法具有4个重载版本,分别接收的参数为string,byte[],Image,Stream。FormatUtilities.GetFormat(fileStream)方法从给定流获取正确的ISupportedImageFormat。在对图片的数据流进行操作时,首先会复制图片的流数据。format.Load(memoryStream)将我们的映像设置为内存流值。图片数据流进行一个操作后,会调用Image.Copy(this.AnimationProcessMode)确保图像是最有效的格式。
2.ImageFactoryExtensions.AutoProcess()

internal static ImageFactory AutoProcess(this ImageFactory factory, IWebGraphicsProcessor[] graphicsProcessors)
{
if (factory.ShouldProcess)
{
foreach (IWebGraphicsProcessor graphicsProcessor in graphicsProcessors)
{
factory.CurrentImageFormat.ApplyProcessor(graphicsProcessor.Processor.ProcessImage, factory);
IDisposable disposable = graphicsProcessor.Processor.DynamicParameter as IDisposable;
disposable?.Dispose();
}
}
return factory;
}

ImageFactoryExtensions类是ImageFactory类的扩展类,主要是扩展Web项目。AutoProcess()方法基于添加到图像路径的任何查询字符串参数,自动处理图像文件。graphicsProcessors参数表示要应用的图形处理器阵列。graphicsProcessor.Processor.DynamicParameter as IDisposable打开动态参数并处理任何需要它的类型。
3.ImageProcessingModule.SetHeaders()

public static void SetHeaders(HttpContext context, int maxDays)
{
object responseTypeObject = context.Items[CachedResponseTypeKey];
object dependencyFileObject = context.Items[CachedResponseFileDependency];
string responseType = responseTypeObject as string;
string[] dependencyFiles = dependencyFileObject as string[];
SetHeaders(context, responseType, dependencyFiles, maxDays);
}

在Web扩展中,ImageProcessingModule类比较重要,处理Web应用程序中的任何图像请求。SetHeaders()方法使浏览器和服务器将输出保存在其缓存中,从而提高性能。该方法接受两个参数,context表示请求的http消息对象,HttpContext对象对内在服务器对象的引用。maxDays参数表示将图片存储在浏览器缓存中的最长天数。
四.总结
说句实话,这位作者的编码风格是喜欢的,代码简介明了,没有那么多装逼的写法,不会为了使用一些写法,而去改变代码的可读性。对于这个组件系列,我会近可能的写一些,大家可以借此了解一些组件,需要深入了解和使用的,可以自己查看源码,进行对应的扩展。写完这篇,已经凌晨两点了,为自己点个赞,无论写的怎样,觉得自己还是尽心了。
ImageProcessor组件的更多相关文章
- 开源免费的.NET图像即时处理的组件ImageProcessor
承接以前的组件系列,这个组件系列旨在介绍.NET相关的组件,让大家可以在项目中有一个更好的选择,社区对于第三方插件的介绍还是比较少的,很多博文的内容主要还是介绍一些简单的操作(很多人都说博客园现在是“ ...
- Open Source
资源来源于http://www.cnblogs.com/Leo_wl/category/246424.html RabbitMQ 安装与使用 摘要: RabbitMQ 安装与使用 前言 吃多了拉就是队 ...
- 使用ImageProcessor、CodeCarvings.Piczard组件生成缩略图和添加水印
技术栈: 1.ImageProcessor(专业图像处理,不能合成水印,NetCore中有它的升级版ImageSharp目前是预览包) 2.CodeCarvings.Piczard(缩略图,水印都能搞 ...
- ExtJS 4.2 评分组件
上一文章是扩展ExtJS自带的Date组件.在这里将创建一个评分组件. 目录 1. 介绍 2. 示例 3. 资源下载 1. 介绍 代码参考的是 Sencha Touch 2上的一个RatingStar ...
- react组件的生命周期
写在前面: 阅读了多遍文章之后,自己总结了一个.一遍加强记忆,和日后回顾. 一.实例化(初始化) var Button = React.createClass({ getInitialState: f ...
- react-router 组件式配置与对象式配置小区别
1. react-router 对象式配置 和 组件式配置 组件式配置(Redirect) ----对应---- 对象式配置(onEnter钩子) IndexRedirect -----对应-- ...
- Angular2入门系列教程3-多个组件,主从关系
上一篇 Angular2项目初体验-编写自己的第一个组件 好了,前面简单介绍了Angular2的基本开发,并且写了一个非常简单的组件,这篇文章我们将要学会编写多个组件并且有主从关系 现在,假设我们要做 ...
- Angular2入门系列教程2-项目初体验-编写自己的第一个组件
上一篇 使用Angular-cli搭建Angular2开发环境 Angular2采用组件的编写模式,或者说,Angular2必须使用组件编写,没有组件,你甚至不能将Angular2项目启动起来 紧接着 ...
- .NET Core 首例 Office 开源跨平台组件(NPOI Core)
前言 最近项目中,需要使用到 Excel 导出,找了一圈发现没有适用于 .NET Core的,不依赖Office和操作系统限制的 Office 组件,于是萌生了把 NPOI 适配并移植到 .NET C ...
随机推荐
- Lua table笔记
记录我在使用lua的过程中的一些笔记 默认key为数字递增 local tb={"A",[3]="C","B"} 这个tb通过下标1,2,3 ...
- java基础编程练习
1.编写程序实现对给定的 4 个整数从大到小的顺序排列. 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 ...
- 类中的 this关键字
this可用于区分局部变量和成员变量,因为构造函数中如果使用 this.成员变量 = 参数值, 那么可以在new对象时,将初始化值赋值给成员变量,否则成员变量赋值失败, 所以this可以区分成员变量和 ...
- 阿里云短信服务调用例子-Python
阿里云短信服务调用例子 阿里云官方文档https://helpcdn.aliyun.com/document_detail/101893.html 首先需要安装阿里云PythonSDK(下面是pyth ...
- jq stop()和:is(":animated")用法区别
stop(true,true): 表示停止匹配元素正在进行的动画并跳转到末状态,清空未执行完的动画队列.常用于”解决光标移入移出得过快导致的动画效果与光标动作不一致“问题! jQuery stop() ...
- Session的生命周期之关于浏览器关闭后的Session
Session是JSP的九大内置对象中的一个,它可以保存当前用户的各种的状态信息. 初次接触Session时认为Session的生命周期是从浏览器打开一个窗口发送请求开始,到浏览器窗口关闭结束.其实这 ...
- Harbor是什么
第一次听到这个名字应该是2016年初的时候,那是在容器技术已经兴起的,各个容器管理平台正处于群雄逐鹿的时候,mesos.kubernetes.swarm等被国内外各个厂商用来作为容器的管理系统.这个时 ...
- http和https工具类 (要注意httpclient版本号和log4j的版本号)
1 工具类 package dd.com; import java.io.IOException; import java.security.cert.CertificateException; im ...
- 如何利用pip自动生成和安装requirements.txt依赖
在查看别人的Python项目时,经常会看到一个requirements.txt文件,里面记录了当前程序的所有依赖包及其精确版本号.这个文件有点类似与Rails的Gemfile.其作用是用来在另一台PC ...
- 理解 tf.Variable、tf.get_variable以及范围命名方法tf.variable_scope、tf.name_scope
tensorflow提供了通过变量名称来创建或者获取一个变量的机制.通过这个机制,在不同的函数中可以直接通过变量的名字来使用变量,而不需要将变量通过参数的形式到处传递. 1. tf.Variable( ...