【问题标题】:Proper use of UIImagePickerController for both taking pictures with camera or selecting them from the iphone library正确使用 UIImagePickerController 来使用相机拍照或从 iphone 库中选择它们
【发布时间】:2011-03-28 13:17:01
【问题描述】:

我想要做的是在我的整个应用程序中始终使用相同的 UIImagePickerController 实例,因为我不想在每次用户拍照时分配和销毁我的选择器。该应用程序使用一个选择器和一个名为 pictureA 的 UIImageView 来显示从 iPhone 相册中选择或使用相机拍摄的图片。

一开始我像这样分配我的选择器视图控制器:

    imagePickerController = [[UIImagePickerController alloc] init];
    imagePickerController.delegate = self;
    [self addSubview:imagePickerController.view];

当我从选取器中拍照并将其放在我的 UIImageView 中时:

-(void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info{

    // newImage is a UIImage do not try to use a UIImageView    
    UIImage *newImage = [info objectForKey:@"UIImagePickerControllerEditedImage"];

        [pictureA removeFromSuperview];

        CGRect myImageRect = CGRectMake(30.0f, 38.0f, 125.0f, 125.0f); 
        pictureA = [[UIImageView alloc] initWithFrame:myImageRect];
        pictureA.contentMode= UIViewContentModeScaleAspectFit;
        [pictureA setImage:newImage];
        pictureA.opaque = YES;
        [self addSubview:pictureA];


        [newImage release];

        [picker dismissModalViewControllerAnimated:YES];
        [picker.view setHidden:YES];

    }

当从 iphone 的图库中选择图片时:

- (void) chooseImageFromLibrary {
    [imagePickerController.view setHidden:NO];
        imagePickerController.allowsEditing = YES;
    [imagePickerController viewWillAppear:YES];
    [imagePickerController viewDidAppear:YES];
}

取消:

- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker{   
    [[picker parentViewController] dismissModalViewControllerAnimated:YES];
    [picker.view setHidden:YES];
}

- (void) takePicture {


    if (![UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera]) 
    {
        [(MainScene*)[melonGame actualScene] setCameraDissabled:YES];
        return;
    }


    [imagePickerController.view setHidden:NO];

    imagePickerController.sourceType = UIImagePickerControllerSourceTypeCamera; 
    imagePickerController.allowsEditing = YES;

    [imagePickerController takePicture];


    [imagePickerController viewWillAppear:YES];
    [imagePickerController viewDidAppear:YES];
}

当我拍摄第一张照片时,该应用程序将正常工作,但当我尝试拍摄另一张照片或从我的图库中选择另一张照片时,它看起来与我上次选择一张照片时完全相同(整个屏幕中的图片和在底部选择和取消的非活动菜单)。只有当我从视图中移除控制器并在每次用户拍照时分配它时,我的应用程序才能正常工作。有没有办法“清理”或“重新启动”选择器而不释放它并将其从我的视图中删除?

我也不确定是否可以实例化一次 UIImageView (pictureA) 我存储 imagePickerController 拍摄的图像并在每次用户拍照或从相册中选择一张时对其进行修改,我怀疑它不正确每次用户拍照时销毁它并重新分配它。有什么建议吗?关于内存管理或 UIImagePickerController 和 UIImageView 的使用我做错了什么?

谢谢!

【问题讨论】:

    标签: iphone uiimageview uiimagepickercontroller


    【解决方案1】:

    我不认为 UIImagePickerControllers 是用来重复使用的。无论哪种方式,它们都使用大量内存(尤其是相机),因此您不希望将它们保留在您身边的时间过长。所以是的,你应该在完成后释放图像选择器,并在你想添加另一个图像时创建一个新的。

    您可能应该以模态方式展示您的图像选择器:

    [self presentModalViewController:imagePickerController animated:YES];
    

    您无需在每次要更改图像时都释放您的图片视图。只需更改图像属性即可。

    pictureA.image = newImage;
    

    如果您想在第一次使用时实例化图像视图,请执行以下操作

    if (!pictureA) {
        pictureA = [[UIImageView alloc] initWithFrame:aFrame];
    }
    
    pictureA.image = ...
    

    请记住,对 alloc 的调用需要对 release 或 autorelease 的匹配调用。当您在上面分配“pictureA”时,它的保留计数变为 1。调用“[self addSubview:pictureA];”将其保留计数增加到 2。当您调用“[pictureA removeFromSuperview];”时下一次,保留计数减少到 1,并且您创建了一个新的图像视图。所以每次调用 imagePickerController:didFinishPickingMediaWithInfo: 都会泄漏内存。相反,做

    [pictureA removeFromSuperview];
    [pictureA release];
    

    当您将其从超级视图中删除时。或者,更好的是,让图片成为该类的属性:

    @property (nonatomic, retain) UIImageView *pictureA;
    

    当你分配一个新的 imageView 时,它将释放旧的 imageView。只需确保在分配时释放即可:)

    self.pictureA = [[[UIImageView alloc] init] autorelease];
    

    UIImageView *imageView = [[UIImageView alloc] init];
    self.pictureA = imageView;
    [imageView release];
    

    我个人会坚持使用自动释放样式,因为您总是能够一眼就知道您是否正确分配/解除分配。

    此外,您始终可以使用 Xcode 4 中的 Product>Analyze 仔细检查您的内存管理。

    【讨论】:

      猜你喜欢
      • 2011-09-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-12-23
      • 1970-01-01
      • 2017-09-08
      • 1970-01-01
      相关资源
      最近更新 更多