工作中遇到需要将图片压缩之后上传的需求。经过多方查询资料,目前总结出来两种方式总结一下备用。
建网站原本是网站策划师、网络程序员、网页设计师等,应用各种网络程序开发技术和网页设计技术配合操作的协同工作。成都创新互联公司专业提供成都网站设计、成都做网站,网页设计,网站制作(企业站、成都响应式网站建设公司、电商门户网站)等服务,从网站深度策划、搜索引擎友好度优化到用户体验的提升,我们力求做到极致!
UIImageJPEGRepresentation(image, compression)
这个方法可以将iPhone拍摄的照片压缩到几百Kb的极限值,到极限值之后不管compression这个参数多小,该函数返回的数据大小都不会再改变。也就是说这个方法的压缩是有最小值的,得到的是jpg格式。
另外有一个方法UIImagePNGRepresentation(#UIImage * _Nonnull image#)这个方法得到的数据会比之前那个方法得到的数据占用空间更大。
为了达到压缩的目的,这种方法是有损的,就是会降低图片质量。
这种方法的到的图片,newSize越小质量越差,但是得到的图片占用内存越小。设置多大的newSize自己斟酌决定。
综合一下自己平常在开发中常用的就是,先使用第一种方法保持精度不变,compression选择0.6或者0.7进行第一次压缩,然后再用第二种方法进行尺寸压缩,得到的就是我们最终想要的图片。
iOS开发中,会要求导入@1x、@2x和@3x:
使用@1x格式: iPhone3GS
使用@2x格式: iPhone 4,4S,5,5S,5C,SE,6,6S,7,8,XR
使用@3x格式: iPhone 6Plus、6sPlus、7Plus、8Plus、X、XS、XS Max
这样在开发过程中,将三种图片(比如分别为1.png、1@2x.png和1@3x.png)导入到工程图库中的时候可以自动被识别为1x、2x和3x大小的图片
可以利用Mac系统中自带的服务自己 制作一个快速生成@1x、@2x和@3x图片的功能
首先spotlight搜索Automator,然后按Enter打开
**新建文稿 **
选取文稿类型为 快速操作
在工作流程收到当前的后面选择图像文件
在左边窗口的“操作”下,选择“资源库”中的“文件和文件夹”,将右侧中的“给访达项目重新命名”拖入最右侧的大窗口中,(如果警告提示是否要增加一个“拷贝访达项目”操作,选择“不添加”),选择“添加文本”,在输入框中输入【@3x】
拖入“复制访达项目”
选择左侧“资源库”中的照片,将“缩放图像”拖入右侧窗口(如果警告提示是否要增加一个“拷贝访达项目”操作,选择“不添加”),并选择“按百分比”,输入【66】
再拖入“文件和文件夹”下的“给访达项目重新命名”,并选择【替换文本】,查找【“】,以【仅基本名称】;****再拖入“文件和文件夹”下的“给访达项目重新命名”,并选择【替换文本】,查找【@3x”的副本】,以【仅基本名称】,替换成【@2x】
拖入“复制访达项目”,选择左侧“资源库”中的照片,将“缩放图像”拖入右侧窗口(如果警告提示是否要增加一个“拷贝访达项目”操作,选择“不添加”),并选择“按百分比”,输入【50】
再拖入“文件和文件夹”下的“给访达项目重新命名”,并选择【替换文本】,查找【“】,以【仅基本名称】,再拖入“文件和文件夹”下的“给访达项目重新命名”,并选择【替换文本】,查找【@2x”的副本】,以【仅基本名称】
然后保存,将“快速操作”存储为“制作@2x@3x图片”
每次使用的时候,只需选中图片,选择访达 - 服务 - 制作@2x@3x图片,****就会自动生成三个图片:1.png、1@2x.png和1@3x.png
最终效果~
UIImageView *imageView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"bgImage"]];
创建并设置默认图, 也可以
UIImageView*imageView = [[UIImageView alloc] init];
imageView.image= [UIImageimageNamed:@"bgImage"];
还可以这样先设置imageview的大, 在设置图片
UIImageView*imageView = [[UIImageView alloc] initWithFrame:(CGRectMake(0,144,SCREEN_Width,50))];
imageView.image= [UIImageimageNamed:@"bgImage"];
由此可看imageview的frame可以这样设置
imageView.frame=CGRectMake(0,144,SCREEN_Width,50);
通常我们使用的的imageview都会添加圆角边框
imageView.layer.masksToBounds = YES;
imageView.layer.cornerRadius=25;
imageView.layer.borderColor = [UIColor blueColor].CGColor;
imageView.layer.borderWidth=1;
这个圆角和边框像view和label以及button的设置方式都是一样的 当然imageview也一样
imageView.backgroundColor= [UIColorclearColor]; 图片设置背景颜色, 我通常使用clearColor 透明
imageView.userInteractionEnabled = YES; 图片设置成可交互, 设置为NO则不能交互
[self.viewaddSubview: imageView]; 添加视图也可叫做显示视图
设置图片内容的布局方式 imageView.contentMode
这个属性是用来设置图片的显示方式,如居中、居右,是否缩放等
imageView.contentMode = UIViewContentModeScaleAspectFit;
UIViewContentMode contentMode枚举类型
(1) UIViewContentModeScaleToFill; 默认,对图片进行拉伸处理(不是按比例),是充满bouns
(2) UIViewContentModeScaleAspectFit; 按原图比例进行拉伸,是图片完全展示在bouns中
(3) UIViewContentModeScaleAspectFill; 按原图比例填充,使图片展示在bouns中,可能只显示部分
(4) UIViewContentModeRedraw; 重划边界变化(重设 - setNeedsDisplay)
(5) UIViewContentModeCenter; 图片显示在imageview的正中间,原图大小
(6) UIViewContentModeTop; 图片显示在imageview的上部,原图大小
(7) UIViewContentModeBottom; 图片显示在imageview的下部,原图大小
(8) UIViewContentModeLeft; 图片显示在imageview的左部,原图大小
(9) UIViewContentModeRight; 图片显示在imageview的右部,原图大小
(10) UIViewContentModeTopLeft; 图片显示在imageview的左上部,原图大小
(11) UIViewContentModeTopRight; 图片显示在imageview的右上部,原图大小
(12) UIViewContentModeBottomLeft; 图片显示在imageview的左下部,原图大小
(13) UIViewContentModeBottomRight; 图片显示在imageview的右下部,原图大小
imageView.alpha = 1.0; 设置图片透明度
NSString *path1 = [[NSBundle mainBundle] pathForResource:@"1" ofType:@"jpg"];
NSString *path2 = [[NSBundle mainBundle] pathForResource:@"2" ofType:@"jpg"];
NSString *path3 = [[NSBundle mainBundle] pathForResource:@"3" ofType:@"jpg"];
imageView.animationImages = @[[UIImage imageWithContentsOfFile:path1],[UIImage imageWithContentsOfFile:path2],[UIImage imageWithContentsOfFile:path3]];
imageView.animationDuration = 5.0f; 设置循环一次的时间
imageView.animationRepeatCount = 0; // 设置循环次数(0为无线循环)
[imageView startAnimating]; // 开始动画
[imageView stopAnimating]; // 停止动画
NSData *imageData = [NSData dataWithContentsOfFile:path];
UIImage *image4 = [UIImage imageWithData:imageData];
NSString *path = [[NSBundle mainBundle] pathForResource:@"1" ofType:@"jpg"];
UIImage *image2 = [UIImage imageWithContentsOfFile:path];
ImageView.hidden = NO; 隐藏或者显示图片 YES为隐藏
[ImageView sizeToFit]; 将图片尺寸调整为与内容图片相同
UITapGestureRecognizer *singleTap = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(tapImageView:)]; // 设置手势
[ImageView addGestureRecognizer:singleTap]; // 给图片添加手势
在项目中经常遇到要上传图片,如果直接上传,那么会上传比较大的图片,导致费流量,刷新时加载图片时间过长,手机内存占用率高等问题。
一、先来介绍下概念:
图片的压缩其实是俩概念,
1、是 “压” 文件体积变小,但是像素数不变,长宽尺寸不变,那么质量可能下降,
2、是 “缩” 文件的尺寸变小,也就是像素数减少。长宽尺寸变小,文件体积同样会减小。
二、解决方法(以上传头像为例),先缩再压:
2.1 矫正图片方向(照片是有方向的,避免出现“倒立”的情况)
- (UIImage*)fixOrientation:(UIImage*)aImage {
// No-op if the orientation is already correct
if(aImage.imageOrientation==UIImageOrientationUp)
returnaImage;
// We need to calculate the proper transformation to make the image upright.
// We do it in 2 steps: Rotate if Left/Right/Down, and then flip if Mirrored.
CGAffineTransformtransform =CGAffineTransformIdentity;
switch(aImage.imageOrientation) {
caseUIImageOrientationDown:
caseUIImageOrientationDownMirrored:
transform =CGAffineTransformTranslate(transform, aImage.size.width, aImage.size.height);
transform =CGAffineTransformRotate(transform,M_PI);
break;
caseUIImageOrientationLeft:
caseUIImageOrientationLeftMirrored:
transform =CGAffineTransformTranslate(transform, aImage.size.width,0);
transform =CGAffineTransformRotate(transform,M_PI_2);
break;
caseUIImageOrientationRight:
caseUIImageOrientationRightMirrored:
transform =CGAffineTransformTranslate(transform,0, aImage.size.height);
transform =CGAffineTransformRotate(transform, -M_PI_2);
break;
default:
break;
}
switch(aImage.imageOrientation) {
caseUIImageOrientationUpMirrored:
caseUIImageOrientationDownMirrored:
transform =CGAffineTransformTranslate(transform, aImage.size.width,0);
transform =CGAffineTransformScale(transform, -1,1);
break;
caseUIImageOrientationLeftMirrored:
caseUIImageOrientationRightMirrored:
transform =CGAffineTransformTranslate(transform, aImage.size.height,0);
transform =CGAffineTransformScale(transform, -1,1);
break;
default:
break;
}
// Now we draw the underlying CGImage into a new context, applying the transform
// calculated above.
CGContextRefctx =CGBitmapContextCreate(NULL, aImage.size.width, aImage.size.height,
CGImageGetBitsPerComponent(aImage.CGImage),0,
CGImageGetColorSpace(aImage.CGImage),
CGImageGetBitmapInfo(aImage.CGImage));
CGContextConcatCTM(ctx, transform);
switch(aImage.imageOrientation) {
caseUIImageOrientationLeft:
caseUIImageOrientationLeftMirrored:
caseUIImageOrientationRight:
caseUIImageOrientationRightMirrored:
CGContextDrawImage(ctx,CGRectMake(0,0,aImage.size.height,aImage.size.width), aImage.CGImage);
break;
default:
CGContextDrawImage(ctx,CGRectMake(0,0,aImage.size.width,aImage.size.height), aImage.CGImage);
break;
}
CGImageRef cgimg =CGBitmapContextCreateImage(ctx);
UIImage *img = [UIImageimageWithCGImage:cgimg];
CGContextRelease(ctx);
CGImageRelease(cgimg);
return img;
}
2.2 拿到上面矫正过的图片,缩小图片尺寸,调用下面方法传入newSize,如(200,200):
+ (UIImage*)imageWithImageSimple:(UIImage*)image scaledToSize:(CGSize)newSize
{
UIGraphicsBeginImageContext(newSize);
[imagedrawInRect:CGRectMake(0,0,newSize.width,newSize.height)];
UIImage* newImage =UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return newImage;
}
2.3 将2.2的图片再压,这个方法可以重复压
//调整大小
NSData *imageData =UIImageJPEGRepresentation(newImage,rate);
NSUIntegersizeOrigin = [image Datalength];//多少KB
NSUIntegersizeOriginKB = sizeOrigin /1024;//多少KB
2.4 上传头像
调用后台接口,把imageData二进制数据上传即可
总结:对图片压缩处理时,在保证图片清晰度变化不大时,减小图片文件大小。方法2.2中的newSize 和 2.3中的rate要以实际效果来设置,我在自己项目中上传的头像最终尺寸是200*200像素,大小为4KB左右。