特别鸣谢本群【刀刀 _IOS_南京】 ,兄台发我一份word文档,相当之认真。。。。感动+感谢Ing
Dark老大让我出个帖子,但我接触iOS开发才不过几个月,经历过两个项目,实在没太有多少干货,只知道一些常规知识。翻箱倒柜,终于找到这样一个知识点,就是把gps、时间等exif信息写进jpg图片,以达到不用依靠另外的配置文件、数据库等方法就可保存一张图片的更多附加信息,十分方便。
之前查找iOS中关于保存图片exif信息的资料时,发现网上介绍的方法几乎全是要依托UIImagePickerController来保存,局限性比较大,但我需要将exif信息保存进任意图片,然后图片还可以随意存储在沙盒,不存在相册。最后找到老外的一片文章,英语烂到家的我硬着头皮,终于整理出了我想要的代码:
/* 设置图片的gps信息 * lat、longi:经纬度 * data: 图片数据 * imgFilepath:信息写进图片,将图片保存到的路径 */ +(BOOL)setGPSToImageByLat:(double)latlon:(double)longi imgData:(NSData *)data newImgFilePath:(NSString*)imgFilepath { if(!data || [data length] == 0 ||!imgFilepath || [imgFilepath length] <= 0) { return NO; } CGImageSourceRef source =CGImageSourceCreateWithData((__bridge CFDataRef)data, NULL); NSDictionary *dict = (__bridgeNSDictionary*)CGImageSourceCopyPropertiesAtIndex(source, 0, NULL); NSMutableDictionary *metaDataDic = [dictmutableCopy]; //GPS NSMutableDictionary *gpsDic =[NSMutableDictionary dictionary]; //[gpsDic setObject:@"N"forKey:(NSString*)kCGImagePropertyGPSLatitudeRef]; [gpsDic setObject:[NSNumbernumberWithDouble:lat] forKey:(NSString*)kCGImagePropertyGPSLatitude]; //[gpsDic setObject:@"E"forKey:(NSString*)kCGImagePropertyGPSLongitudeRef]; [gpsDic setObject:[NSNumbernumberWithDouble:longi] forKey:(NSString *)kCGImagePropertyGPSLongitude]; [metaDataDic setObject:gpsDicforKey:(NSString*)kCGImagePropertyGPSDictionary]; //其他exif信息 NSMutableDictionary *exifDic =[[metaDataDic objectForKey:(NSString*)kCGImagePropertyExifDictionary]mutableCopy]; if(!exifDic) { exifDic = [NSMutableDictionarydictionary]; } NSDateFormatter *dateFormatter =[[NSDateFormatter alloc]init]; [dateFormattersetFormatterBehavior:NSDateFormatterBehavior10_4]; [dateFormattersetDateFormat:@"yyyy/MM/dd HH:mm:ss"]; NSString *EXIFFormattedCreatedDate =[dateFormatter stringFromDate:[NSDate date]]; [exifDic setObject:EXIFFormattedCreatedDateforKey:(NSString*)kCGImagePropertyExifDateTimeDigitized]; [metaDataDic setObject:exifDicforKey:(NSString*)kCGImagePropertyExifDictionary]; //写进图片 CFStringRef UTI = CGImageSourceGetType(source); NSMutableData *data1 = [NSMutableDatadata]; CGImageDestinationRef destination =CGImageDestinationCreateWithData((__bridge CFMutableDataRef)data1, UTI, 1,NULL); if(!destination) { return NO; } CGImageDestinationAddImageFromSource(destination, source, 0, (__bridgeCFDictionaryRef)metaDataDic); if(!CGImageDestinationFinalize(destination)) { return NO; } //获取documents目录 NSString *directoryDocuments = [NSHomeDirectory()stringByAppendingPathComponent:@"Documents"]; //文件的目标路径 NSString *destDirect = [directoryDocumentsstringByAppendingFormat:@"/%@",kCustomPhotosAlbumDirectory]; NSFileManager *mgr = [NSFileManagerdefaultManager]; BOOL isDir = YES; if(![mgr fileExistsAtPath:destDirect isDirectory:&isDir]) { //原图路径不存在,创建该路径 if(![mgrcreateDirectoryAtPath:destDirect withIntermediateDirectories:YES attributes:nilerror:nil]) { return NO; } } NSString *path = [NSStringstringWithFormat:@"%@/%@",destDirect,imgFilepath]; [data1 writeToFile:path atomically:YES]; NSLog(@"保存成功!path = %@",path); CFRelease(destination); CFRelease(source); return YES; } //获取图片的exif、gps等信息(path:图片路径) +(Photo*)getGPSByImageFilePath:(NSString*)path { if(!path || [path length] == 0) { return nil; } NSURL *url = [NSURL fileURLWithPath:path]; CGImageSourceRef source =CGImageSourceCreateWithURL((__bridge CFURLRef)url, NULL); if(!source) { return nil; } NSDictionary *dd = [NSDictionarydictionaryWithObjectsAndKeys:[NSNumbernumberWithBool:NO],(NSString*)kCGImageSourceShouldCache, nil]; CFDictionaryRef dict =CGImageSourceCopyPropertiesAtIndex(source, 0, (__bridge CFDictionaryRef)dd); if(!dict) { return nil; } CFDictionaryRef exif =CFDictionaryGetValue(dict, kCGImagePropertyExifDictionary); if(exif) { } //获得GPS 的 dictionary CFDictionaryRef gps =CFDictionaryGetValue(dict, kCGImagePropertyGPSDictionary); if(!gps) { return nil; } //获取经纬度 NSString *lat = (__bridgeNSString*)CFDictionaryGetValue(gps, kCGImagePropertyGPSLatitude); NSString *lon = (__bridgeNSString*)CFDictionaryGetValue(gps, kCGImagePropertyGPSLongitude); if(exif) { //日期 NSString *date = (__bridge NSString*)(CFDictionaryGetValue(exif, kCGImagePropertyExifDateTimeDigitized)); } CFRelease(dict); CFRelease(exif); CFRelease(gps); return photo; }
小编:
@刀刀是我看到最认真写技术贴的兄,十分感谢!
话说在图片上标记GPS\时间\等附加信息,是相当有用的技术。而且这个还是不依赖于UIImagePickerController. 仔细琢磨下getGPSByImageFilePath方法,并且有必要回头看看CFDictionaryRef API的内容了
非常有心意,期待更多力作噢