UIImage+RedAnt.m 6.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208
  1. //
  2. // UIImage+RedAnt.m
  3. // Apex And Drivers
  4. //
  5. // Created by Jack on 2018/8/29.
  6. // Copyright © 2018年 USAI. All rights reserved.
  7. //
  8. #import "UIImage+RedAnt.h"
  9. #import <CommonCrypto/CommonCrypto.h>
  10. static dispatch_semaphore_t _lock;
  11. #define Lock() dispatch_semaphore_wait(_lock, DISPATCH_TIME_FOREVER)
  12. #define Unlock() dispatch_semaphore_signal(_lock)
  13. @implementation UIImage (RedAnt)
  14. + (void)load {
  15. _lock = dispatch_semaphore_create(1);
  16. }
  17. + (instancetype)ra_imageWithURL:(NSURL *)url {
  18. if (url == nil) {
  19. return nil;
  20. }
  21. if ([url.scheme isEqualToString:@"file"]) {
  22. return [UIImage imageWithContentsOfFile:url.absoluteString];
  23. }
  24. NSString *md5 = [self md5:url.absoluteString];
  25. NSString *imgDir = [self imageCacheDir];
  26. NSString *imgPath = [imgDir stringByAppendingPathComponent:md5];
  27. NSFileManager *fileManager = [NSFileManager defaultManager];
  28. BOOL isDir = NO;
  29. BOOL exist = [fileManager fileExistsAtPath:imgPath isDirectory:&isDir];
  30. if (exist && !isDir) {
  31. return [UIImage imageWithContentsOfFile:imgPath];
  32. } else {
  33. NSData *imgData = [NSData dataWithContentsOfURL:url];
  34. exist = [fileManager fileExistsAtPath:imgDir isDirectory:&isDir];
  35. if ((exist && isDir) || !exist) {
  36. [fileManager createDirectoryAtPath:imgDir withIntermediateDirectories:YES attributes:nil error:nil];
  37. }
  38. UIImage *img = [UIImage imageWithData:imgData];
  39. if (img) { // 解析图片成功
  40. Lock();
  41. if (![fileManager fileExistsAtPath:imgPath]) {
  42. [imgData writeToFile:imgPath atomically:NO];
  43. }
  44. Unlock();
  45. return img;
  46. } else {
  47. return nil;
  48. }
  49. }
  50. }
  51. + (NSString *)imageCacheDir {
  52. return [[NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) lastObject] stringByAppendingPathComponent:@"ImageCache"];
  53. }
  54. + (NSString *)imageCachePath:(NSString *)url {
  55. NSString *md5 = [self md5:url];
  56. NSString *imgDir = [self imageCacheDir];
  57. NSString *imgPath = [imgDir stringByAppendingPathComponent:md5];
  58. return imgPath;
  59. }
  60. + (nullable NSString *)md5:(nullable NSString *)str {
  61. if (!str) return nil;
  62. const char *cStr = str.UTF8String;
  63. unsigned char result[CC_MD5_DIGEST_LENGTH];
  64. CC_MD5(cStr, (CC_LONG)strlen(cStr), result);
  65. NSMutableString *md5Str = [NSMutableString string];
  66. for (int i = 0; i < CC_MD5_DIGEST_LENGTH; ++i) {
  67. [md5Str appendFormat:@"%02x", result[i]];
  68. }
  69. return md5Str;
  70. }
  71. + (UIImage *)img_compress:(UIImage*)image kbsize:(float) size {
  72. //UIImage *image=[UIImage imageNamed:@"xxoo.jpeg"];
  73. NSData *imageData=UIImageJPEGRepresentation(image, 1.f);
  74. if(size>imageData.length/1024)
  75. return image;
  76. // CGFloat size=40.f;// kb
  77. CGFloat scale=size/(imageData.length/1024);
  78. scale = sqrt (scale);
  79. CGSize newsize=image.size;
  80. newsize.height = newsize.height*scale;
  81. newsize.width = newsize.width*scale;
  82. return [self scaleImageToSize:image size:newsize];
  83. }
  84. + (UIImage *)scaleImageToSize:(UIImage *)img size:(CGSize)size {
  85. // 创建一个bitmap的context
  86. // 并把它设置成为当前正在使用的context
  87. UIGraphicsBeginImageContext(size);
  88. // 绘制改变大小的图片
  89. [img drawInRect:CGRectMake(0, 0, size.width, size.height)];
  90. // 从当前context中创建一个改变大小后的图片
  91. UIImage* scaledImage = UIGraphicsGetImageFromCurrentImageContext();
  92. // 使当前的context出堆栈
  93. UIGraphicsEndImageContext();
  94. // 返回新的改变大小后的图片
  95. // NSData *imageData=UIImageJPEGRepresentation(scaledImage, 1.f);
  96. return scaledImage;
  97. }
  98. - (UIImage *)fixOrientation {
  99. // No-op if the orientation is already correct
  100. if (self.imageOrientation == UIImageOrientationUp) return self;
  101. // We need to calculate the proper transformation to make the image upright.
  102. // We do it in 2 steps: Rotate if Left/Right/Down, and then flip if Mirrored.
  103. CGAffineTransform transform = CGAffineTransformIdentity;
  104. switch (self.imageOrientation) {
  105. case UIImageOrientationDown:
  106. case UIImageOrientationDownMirrored:
  107. transform = CGAffineTransformTranslate(transform, self.size.width, self.size.height);
  108. transform = CGAffineTransformRotate(transform, M_PI);
  109. break;
  110. case UIImageOrientationLeft:
  111. case UIImageOrientationLeftMirrored:
  112. transform = CGAffineTransformTranslate(transform, self.size.width, 0);
  113. transform = CGAffineTransformRotate(transform, M_PI_2);
  114. break;
  115. case UIImageOrientationRight:
  116. case UIImageOrientationRightMirrored:
  117. transform = CGAffineTransformTranslate(transform, 0, self.size.height);
  118. transform = CGAffineTransformRotate(transform, -M_PI_2);
  119. break;
  120. default: break;
  121. }
  122. switch (self.imageOrientation) {
  123. case UIImageOrientationUpMirrored:
  124. case UIImageOrientationDownMirrored:
  125. transform = CGAffineTransformTranslate(transform, self.size.width, 0);
  126. transform = CGAffineTransformScale(transform, -1, 1);
  127. break;
  128. case UIImageOrientationLeftMirrored:
  129. case UIImageOrientationRightMirrored:
  130. transform = CGAffineTransformTranslate(transform, self.size.height, 0);
  131. transform = CGAffineTransformScale(transform, -1, 1);
  132. break;
  133. default: break;
  134. }
  135. // Now we draw the underlying CGImage into a new context, applying the transform
  136. // calculated above.
  137. CGContextRef ctx = CGBitmapContextCreate(NULL, self.size.width, self.size.height,
  138. CGImageGetBitsPerComponent(self.CGImage), 0,
  139. CGImageGetColorSpace(self.CGImage),
  140. CGImageGetBitmapInfo(self.CGImage));
  141. CGContextConcatCTM(ctx, transform);
  142. switch (self.imageOrientation) {
  143. case UIImageOrientationLeft:
  144. case UIImageOrientationLeftMirrored:
  145. case UIImageOrientationRight:
  146. case UIImageOrientationRightMirrored:
  147. // Grr...
  148. CGContextDrawImage(ctx, CGRectMake(0,0,self.size.height,self.size.width), self.CGImage);
  149. break;
  150. default:
  151. CGContextDrawImage(ctx, CGRectMake(0,0,self.size.width,self.size.height), self.CGImage);
  152. break;
  153. }
  154. // And now we just create a new UIImage from the drawing context
  155. CGImageRef cgimg = CGBitmapContextCreateImage(ctx);
  156. UIImage *img = [UIImage imageWithCGImage:cgimg];
  157. CGContextRelease(ctx);
  158. CGImageRelease(cgimg);
  159. return img;
  160. }
  161. @end