UIImagePickerController错误

我想我发现了一个最新的iOS 7中的错误,通过运行一个应用程序与基础SDK设置为iOS 6.1(可能甚至更低的版本,还没有testing过呢)

我在我的照片库中有这个图像: http : //i.imgur.com/7KUIGLt.jpg

我介绍一个UIImagePickerController通过:

UIImagePickerController *vc = [[UIImagePickerController alloc] init]; vc.sourceType = UIImagePickerControllerSourceTypePhotoLibrary; vc.delegate = self; vc.allowsEditing = YES; [self presentViewController:vc animated:YES completion:nil]; 

我保存select的图像到我的桌面(我正在模拟器上运行,但这也适用于设备)

 - (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info { UIImage* outputImage = [info objectForKey:UIImagePickerControllerEditedImage]; if (outputImage == nil) { outputImage = [info objectForKey:UIImagePickerControllerOriginalImage]; } NSData *d = UIImagePNGRepresentation(outputImage); [d writeToFile:@"/Users/Admin/Desktop/test.png" atomically:YES]; [self dismissViewControllerAnimated:YES completion:nil]; } 

这是由此产生的图像: 在这里输入图像说明

注意右边的大黑条。 这是什么原因造成的?

重现这一点,你需要:

  • IOS 7
  • 基本SDK的应用程序设置为6.1(也许更低的SDK也是,我还没有尝试过)
  • iPhone 5 / 5c / 5s
  • 只发生在使用iPhone 5 / 5c / 5s相机拍摄的照片上(您可以使用上面链接的原始图像进行testing)

注意:要清楚,黑色栏是实际图像的一部分。 您看到的图像不是UIImageView的屏幕截图,而是保存到磁盘上的实际图像,并在此处上传…

你的问题是“这是什么造成的?” 所以我会专注于此,而不是提供一种解决方法。 这绝对是iOS 7中处理较低基础SDK中的编辑图像的一个错误。 我们也可以排除XCode 5和Base SDK 6.1导致这个问题,因为我在iOS 7 Simulator上运行XCode 4.6.3和6.1 SDK时遇到同样的问题。

问题的根源在于由SDK计算的CropRect值是错误的。 如果你从imagePickerController:didFinishPickingMediaWithInfo打印出info NSDictionary ,你会看到:

运行任何低于7的SDK的iOS 7我们将得到:

UIImagePickerControllerCropRect =“NSRect:{ { 154,495 } ,{1705,1705}}”;

在使用SDK运行iOS 6或5时,将为我们提供:

UIImagePickerControllerCropRect =“NSRect:{{0,149},{1704,1705}}”;

你可能会说,嗯,这些价值观也在不断变化。 好吧,如果你把你的图片一路滑下来,select它,你也会在图片底部得到一个黑色的栏。

在这里输入图像说明

build议解决scheme

  1. 向苹果在这里提交一个错误报告 …这是!

  2. 不要使用UIImagePickerControllerEditedImage并改为使用原始图片。

  3. 计算和裁剪你的自我。

  4. 使用第三方裁剪库,如PEPhotoCropEditor或SSPhotoCropperViewController


编辑 – 非常简单的解决scheme的粉丝添加的答案!

令人惊讶的是,它可以是这个简单而优雅的自己裁剪:

 { // There is a bug in iOS. When using ALBUM, you must crop it yourself: fromAlbum = [info objectForKey:UIImagePickerControllerOriginalImage]; fromAlbum = [fromAlbum fixOrientation]; CGRect crop = [[info valueForKey:@"UIImagePickerControllerCropRect"] CGRectValue]; fromAlbum = [self ordinaryCrop:fromAlbum toRect:crop]; } 

下面是整个例程的普通草稿:toRect:

 -(UIImage *)ordinaryCrop:(UIImage *)imageToCrop toRect:(CGRect)cropRect { CGImageRef imageRef = CGImageCreateWithImageInRect([imageToCrop CGImage], cropRect); UIImage *cropped = [UIImage imageWithCGImage:imageRef]; CGImageRelease(imageRef); return cropped; } 

现在正如Jesse指出的那样,正确地旋转图像至关重要。 Anomie这个绝对令人难以置信的代码就是这样做的:

上传后iOS iOS UIImagePickerController结果图像方向

修复UIImage方向.. UIImage + fixOrientation.h

就是这么简单,希望能帮到别人。 再次感谢这里无价的答案。

我相信我们最终从不直接要求编辑的图像来解决类似的问题。 请求原始图像和作物信息( UIImagePickerControllerCropRect )并自己裁剪。 请注意,如果您自己裁剪,则需要担心源图像中的旋转。

你可能会发现这个问题的答案有助于实现这个解决方法。

以编程方式尝试查找和更改模式(Aspect Fit,Aspect Fill,Scale to Fill)。

我试图重现这个错误。 而在模拟器,模拟器64位和iPad迷你没有运气。 所有运行的iOS 7.0。

我把你的代码放在我的应用程序中:

 UIImage *image = [info valueForKey:UIImagePickerControllerEditedImage]; if (!image) image = [info valueForKey:UIImagePickerControllerOriginalImage]; // Save photo to custom album only if taken by camera if (picker.sourceType == UIImagePickerControllerSourceTypeCamera) [ALAssetsLibrary saveImageToCustomAlbum:image assetURL:[info valueForKey:UIImagePickerControllerReferenceURL]]; NSData *d = UIImagePNGRepresentation(image); [d writeToFile:@"/Volumes/Alko/Temp/test.png" atomically:YES]; UIImageWriteToSavedPhotosAlbum(image, nil, NULL, nil); [self setImage:image]; [self dismissPicker:picker]; [self photoPickerDidFinish]; 

它使用从http://i.imgur.com/7KUIGLt.jpg下载的图像正确工作。 我认为你的应用程序有问题,而不是UIImagePickerController。