You can not select more than 25 topics Topics must start with a chinese character,a letter or number, can include dashes ('-') and can be up to 35 characters long.

Utility.mm 14 kB

6 years ago
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320
  1. //
  2. // Utility.m
  3. // lpr
  4. //
  5. // Created by baotim on 2018/10/26.
  6. // Copyright © 2018 lprSample. All rights reserved.
  7. //
  8. #import "Utility.h"
  9. @implementation Utility
  10. + (UIImage *)UIImageFromCVMat:(cv::Mat)cvMat
  11. {
  12. NSData *data = [NSData dataWithBytes:cvMat.data length:cvMat.elemSize()*cvMat.total()];
  13. CGColorSpaceRef colorSpace;
  14. if (cvMat.elemSize() == 1) {
  15. colorSpace = CGColorSpaceCreateDeviceGray();
  16. } else {
  17. colorSpace = CGColorSpaceCreateDeviceRGB();
  18. }
  19. CGDataProviderRef provider = CGDataProviderCreateWithCFData((__bridge CFDataRef)data);
  20. // Creating CGImage from cv::Mat
  21. CGImageRef imageRef = CGImageCreate(cvMat.cols, //width
  22. cvMat.rows, //height
  23. 8, //bits per component
  24. 8 * cvMat.elemSize(), //bits per pixel
  25. cvMat.step[0], //bytesPerRow
  26. colorSpace, //colorspace
  27. kCGImageAlphaNone|kCGBitmapByteOrderDefault,// bitmap info
  28. provider, //CGDataProviderRef
  29. NULL, //decode
  30. false, //should interpolate
  31. kCGRenderingIntentDefault //intent
  32. );
  33. // Getting UIImage from CGImage
  34. UIImage *finalImage = [UIImage imageWithCGImage:imageRef scale:1.0 orientation:UIImageOrientationUp];
  35. CGImageRelease(imageRef);
  36. CGDataProviderRelease(provider);
  37. CGColorSpaceRelease(colorSpace);
  38. return finalImage;
  39. }
  40. //缩放调整图片
  41. + (UIImage *)scaleAndRotateImageBackCamera:(UIImage *)image
  42. {
  43. static int kMaxResolution = 480;
  44. CGImageRef imgRef = image.CGImage;
  45. CGFloat width = CGImageGetWidth(imgRef);
  46. CGFloat height = CGImageGetHeight(imgRef);
  47. CGAffineTransform transform = CGAffineTransformIdentity;
  48. CGRect bounds = CGRectMake(0, 0, width, height);
  49. if (width > kMaxResolution || height > kMaxResolution) {
  50. CGFloat ratio = width/height;
  51. if (ratio > 1) {
  52. bounds.size.width = kMaxResolution;
  53. bounds.size.height = bounds.size.width / ratio;
  54. } else {
  55. bounds.size.height = kMaxResolution;
  56. bounds.size.width = bounds.size.height * ratio;
  57. }
  58. }
  59. CGFloat scaleRatio = bounds.size.width / width;
  60. CGSize imageSize = CGSizeMake(CGImageGetWidth(imgRef), CGImageGetHeight(imgRef));
  61. CGFloat boundHeight;
  62. UIImageOrientation orient = image.imageOrientation;
  63. switch(orient) {
  64. case UIImageOrientationUp:
  65. transform = CGAffineTransformIdentity;
  66. break;
  67. case UIImageOrientationUpMirrored:
  68. transform = CGAffineTransformMakeTranslation(imageSize.width, 0.0);
  69. transform = CGAffineTransformScale(transform, -1.0, 1.0);
  70. break;
  71. case UIImageOrientationDown:
  72. transform = CGAffineTransformMakeTranslation(imageSize.width, imageSize.height);
  73. transform = CGAffineTransformRotate(transform, M_PI);
  74. break;
  75. case UIImageOrientationDownMirrored:
  76. transform = CGAffineTransformMakeTranslation(0.0, imageSize.height);
  77. transform = CGAffineTransformScale(transform, 1.0, -1.0);
  78. break;
  79. case UIImageOrientationLeftMirrored:
  80. boundHeight = bounds.size.height;
  81. bounds.size.height = bounds.size.width;
  82. bounds.size.width = boundHeight;
  83. transform = CGAffineTransformMakeTranslation(imageSize.height, imageSize.width);
  84. transform = CGAffineTransformScale(transform, -1.0, 1.0);
  85. transform = CGAffineTransformRotate(transform, 3.0 * M_PI / 2.0);
  86. break;
  87. case UIImageOrientationLeft:
  88. boundHeight = bounds.size.height;
  89. bounds.size.height = bounds.size.width;
  90. bounds.size.width = boundHeight;
  91. transform = CGAffineTransformMakeTranslation(0.0, imageSize.width);
  92. transform = CGAffineTransformRotate(transform, 3.0 * M_PI / 2.0);
  93. break;
  94. case UIImageOrientationRightMirrored:
  95. boundHeight = bounds.size.height;
  96. bounds.size.height = bounds.size.width;
  97. bounds.size.width = boundHeight;
  98. transform = CGAffineTransformMakeScale(-1.0, 1.0);
  99. transform = CGAffineTransformRotate(transform, M_PI / 2.0);
  100. break;
  101. case UIImageOrientationRight:
  102. boundHeight = bounds.size.height;
  103. bounds.size.height = bounds.size.width;
  104. bounds.size.width = boundHeight;
  105. transform = CGAffineTransformMakeTranslation(imageSize.height, 0.0);
  106. transform = CGAffineTransformRotate(transform, M_PI / 2.0);
  107. break;
  108. default:
  109. [NSException raise:NSInternalInconsistencyException format:@"Invalid image orientation"];
  110. }
  111. UIGraphicsBeginImageContext(bounds.size);
  112. CGContextRef context = UIGraphicsGetCurrentContext();
  113. if (orient == UIImageOrientationRight || orient == UIImageOrientationLeft) {
  114. CGContextScaleCTM(context, -scaleRatio, scaleRatio);
  115. CGContextTranslateCTM(context, -height, 0);
  116. } else {
  117. CGContextScaleCTM(context, scaleRatio, -scaleRatio);
  118. CGContextTranslateCTM(context, 0, -height);
  119. }
  120. CGContextConcatCTM(context, transform);
  121. CGContextDrawImage(UIGraphicsGetCurrentContext(), CGRectMake(0, 0, width, height), imgRef);
  122. UIImage *returnImage = UIGraphicsGetImageFromCurrentImageContext();
  123. UIGraphicsEndImageContext();
  124. NSLog(@"resize w%f,H%f",returnImage.size.width,returnImage.size.height);
  125. return returnImage;
  126. }
  127. + (UIImage*)imageWithMat:(const cv::Mat&) image andDeviceOrientation: (UIDeviceOrientation)orientation
  128. {
  129. UIImageOrientation imgOrientation = UIImageOrientationUp;
  130. switch (orientation)
  131. {
  132. case UIDeviceOrientationLandscapeLeft:
  133. imgOrientation =UIImageOrientationLeftMirrored; break;
  134. case UIDeviceOrientationLandscapeRight:
  135. imgOrientation = UIImageOrientationDown; break;
  136. case UIDeviceOrientationPortraitUpsideDown:
  137. imgOrientation = UIImageOrientationRightMirrored; break;
  138. case UIDeviceOrientationFaceUp:
  139. imgOrientation = UIImageOrientationRightMirrored; break;
  140. default:
  141. case UIDeviceOrientationPortrait:
  142. imgOrientation = UIImageOrientationRight; break;
  143. };
  144. return [Utility imageWithMat:image andImageOrientation:imgOrientation];
  145. }
  146. + (UIImage*)imageWithMat:(const cv::Mat&)image andImageOrientation:(UIImageOrientation)orientation;
  147. {
  148. cv::Mat rgbaView;
  149. if (image.channels() == 3)
  150. {
  151. cv::cvtColor(image, rgbaView, COLOR_BGR2BGRA);
  152. }
  153. else if (image.channels() == 4)
  154. {
  155. cv::cvtColor(image, rgbaView, COLOR_BGR2BGRA);
  156. }
  157. else if (image.channels() == 1)
  158. {
  159. cv::cvtColor(image, rgbaView, COLOR_GRAY2RGBA);
  160. }
  161. NSData *data = [NSData dataWithBytes:rgbaView.data length:rgbaView.elemSize() * rgbaView.total()];
  162. CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
  163. CGDataProviderRef provider = CGDataProviderCreateWithCFData((__bridge CFDataRef)data);
  164. CGBitmapInfo bmInfo = kCGImageAlphaPremultipliedLast | kCGBitmapByteOrder32Big;
  165. // Creating CGImage from cv::Mat
  166. CGImageRef imageRef = CGImageCreate(rgbaView.cols, //width
  167. rgbaView.rows, //height
  168. 8, //bits per component
  169. 8 * rgbaView.elemSize(), //bits per pixel
  170. rgbaView.step.p[0], //bytesPerRow
  171. colorSpace, //colorspace
  172. bmInfo,// bitmap info
  173. provider, //CGDataProviderRef
  174. NULL, //decode
  175. false, //should interpolate
  176. kCGRenderingIntentDefault //intent
  177. );
  178. // Getting UIImage from CGImage
  179. UIImage *finalImage = [UIImage imageWithCGImage:imageRef scale:1 orientation:orientation];
  180. CGImageRelease(imageRef);
  181. CGDataProviderRelease(provider);
  182. CGColorSpaceRelease(colorSpace);
  183. return finalImage;
  184. }
  185. + (cv::Mat)cvMatFromUIImage:(UIImage *)image
  186. {
  187. CGColorSpaceRef colorSpace = CGImageGetColorSpace(image.CGImage);
  188. CGFloat cols = image.size.width;
  189. CGFloat rows = image.size.height;
  190. cv::Mat cvMat(rows, cols, CV_8UC4); // 8 bits per component, 4 channels
  191. CGContextRef contextRef = CGBitmapContextCreate(cvMat.data, // Pointer to data
  192. cols, // Width of bitmap
  193. rows, // Height of bitmap
  194. 8, // Bits per component
  195. cvMat.step[0], // Bytes per row
  196. colorSpace, // Colorspace
  197. kCGImageAlphaNoneSkipLast |
  198. kCGBitmapByteOrderDefault); // Bitmap info flags
  199. CGContextDrawImage(contextRef, CGRectMake(0, 0, cols, rows), image.CGImage);
  200. CGContextRelease(contextRef);
  201. CGColorSpaceRelease(colorSpace);
  202. cv::Mat cvMat3(rows, cols, CV_8UC3); // 8 bits per component, 4 channels
  203. cv::cvtColor(cvMat, cvMat3,COLOR_RGBA2RGB);
  204. return cvMat3;
  205. }
  206. + (UIImage *)scaleAndRotateImageFrontCamera:(UIImage *)image
  207. {
  208. static int kMaxResolution = 640;
  209. CGImageRef imgRef = image.CGImage;
  210. CGFloat width = CGImageGetWidth(imgRef);
  211. CGFloat height = CGImageGetHeight(imgRef);
  212. CGAffineTransform transform = CGAffineTransformIdentity;
  213. CGRect bounds = CGRectMake( 0, 0, width, height);
  214. if (width > kMaxResolution || height > kMaxResolution) {
  215. CGFloat ratio = width/height;
  216. if (ratio > 1) {
  217. bounds.size.width = kMaxResolution;
  218. bounds.size.height = bounds.size.width / ratio;
  219. } else {
  220. bounds.size.height = kMaxResolution;
  221. bounds.size.width = bounds.size.height * ratio;
  222. }
  223. }
  224. CGFloat scaleRatio = bounds.size.width / width;
  225. CGSize imageSize = CGSizeMake(CGImageGetWidth(imgRef), CGImageGetHeight(imgRef));
  226. CGFloat boundHeight;
  227. UIImageOrientation orient = image.imageOrientation;
  228. switch(orient) {
  229. case UIImageOrientationUp:
  230. transform = CGAffineTransformIdentity;
  231. break;
  232. case UIImageOrientationUpMirrored:
  233. transform = CGAffineTransformMakeTranslation(imageSize.width, 0.0);
  234. transform = CGAffineTransformScale(transform, -1.0, 1.0);
  235. break;
  236. case UIImageOrientationDown:
  237. transform = CGAffineTransformMakeTranslation(imageSize.width, imageSize.height);
  238. transform = CGAffineTransformRotate(transform, M_PI);
  239. break;
  240. case UIImageOrientationDownMirrored:
  241. transform = CGAffineTransformMakeTranslation(0.0, imageSize.height);
  242. transform = CGAffineTransformScale(transform, 1.0, -1.0);
  243. break;
  244. case UIImageOrientationLeftMirrored:
  245. boundHeight = bounds.size.height;
  246. bounds.size.height = bounds.size.width;
  247. bounds.size.width = boundHeight;
  248. transform = CGAffineTransformMakeTranslation(imageSize.height, imageSize.width);
  249. transform = CGAffineTransformScale(transform, -1.0, 1.0);
  250. transform = CGAffineTransformRotate(transform, 3.0 * M_PI / 2.0);
  251. break;
  252. case UIImageOrientationLeft:
  253. boundHeight = bounds.size.height;
  254. bounds.size.height = bounds.size.width;
  255. bounds.size.width = boundHeight;
  256. transform = CGAffineTransformMakeTranslation(0.0, imageSize.width);
  257. transform = CGAffineTransformRotate(transform, 3.0 * M_PI / 2.0);
  258. break;
  259. case UIImageOrientationRight:
  260. case UIImageOrientationRightMirrored:
  261. boundHeight = bounds.size.height;
  262. bounds.size.height = bounds.size.width;
  263. bounds.size.width = boundHeight;
  264. transform = CGAffineTransformMakeScale(-1.0, 1.0);
  265. transform = CGAffineTransformRotate(transform, M_PI / 2.0);
  266. break;
  267. default:
  268. [NSException raise:NSInternalInconsistencyException format:@"Invalid image orientation"];
  269. }
  270. UIGraphicsBeginImageContext( bounds.size );
  271. CGContextRef context = UIGraphicsGetCurrentContext();
  272. if ( orient == UIImageOrientationRight || orient == UIImageOrientationLeft ) {
  273. CGContextScaleCTM(context, -scaleRatio, scaleRatio);
  274. CGContextTranslateCTM(context, -height, 0);
  275. }
  276. else {
  277. CGContextScaleCTM(context, scaleRatio, -scaleRatio);
  278. CGContextTranslateCTM(context, 0, -height);
  279. }
  280. CGContextConcatCTM( context, transform );
  281. CGContextDrawImage( UIGraphicsGetCurrentContext(), CGRectMake(0, 0, width, height), imgRef );
  282. UIImage *returnImage = UIGraphicsGetImageFromCurrentImageContext();
  283. UIGraphicsEndImageContext();
  284. return returnImage;
  285. }
  286. @end