12

UIViewとして保存したい がありますUIImage。を使用してこれを行いますがUIGraphicsBeginImageContext、問題なく動作します。しかし、(view/layer.mask)の画像にマスクを適用すると、キャプチャした画像UIGraphicsBeginImageContextが間違っています(アプリの実行時にはマスキングが機能しますが、UIImageから取得しようとすると機能しませんUIView)。誰もが同様の問題に遭遇しましたか?

4

2 に答える 2

5

私の理解が正しければ、レイヤーがマスクされている間に UIView レイヤーから UIImage を作成したいと考えています。ターゲットの UIImage の背景を透明にしたいとします。

私はこれを実装する際に問題は発生しませんでした。私はあなたが見ることができるデモプロジェクトを持っています:

https://bitbucket.org/reydan/so_imagemask

最初にマスクボタンを押す必要があります。バンドルからマスク イメージ (白黒) を読み込み、上記の UIView コンテナーのレイヤー マスクとして設定します。

次に、UIView コンテナーを UIImage にレンダリングする [イメージのコピー] ボタンを押し、それを下の目的のイメージ ビューに設定して結果を確認できます。

また、ここに2つの方法を投稿します。

- (IBAction)onMask:(id)sender {

    UIImage* maskImage = [UIImage imageNamed:@"star.png"];
    UIImageView* maskImageView = [[UIImageView alloc] initWithImage:maskImage];
    maskImageView.contentMode = UIViewContentModeScaleAspectFit;
    maskImageView.frame = _mainContainerView.bounds;

    _mainContainerView.layer.mask = maskImageView.layer;
}

- (IBAction)onCopyImage:(id)sender {

    UIGraphicsBeginImageContextWithOptions(_mainContainerView.bounds.size, FALSE, [[UIScreen mainScreen] scale]);
    [_mainContainerView.layer renderInContext:UIGraphicsGetCurrentContext()];
    UIImage * img = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();

    _destImageView.image = img;
}

編集

どうやらrenderInContext:IOS6ではマスクを使用していないようです(SOでもここで言われているように)。私の解決策は、マスクを画像に手動で適用することでした。マスクはレイヤーのマスク プロパティから取得され、コンテキストでもレンダリングされるため、変換/コンテンツ モードなどに問題はありません。

更新されたソース コードは次のとおりです (bitbucket でも入手できます)。

- (IBAction)onCopyImage:(id)sender {

    // Get the image from the mainImageView
    UIGraphicsBeginImageContextWithOptions(_mainContainerView.bounds.size, FALSE, [[UIScreen mainScreen] scale]);
    [_mainContainerView.layer renderInContext:UIGraphicsGetCurrentContext()];
    UIImage * img = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();


    // Use the next block if targeting IOS6
    {
        // Manually create a mask image (taken from the mask layer)
        UIGraphicsBeginImageContextWithOptions(_mainContainerView.bounds.size, TRUE, [[UIScreen mainScreen] scale]);

        CGContextRef ctx = UIGraphicsGetCurrentContext();
        CGContextSetFillColorWithColor(ctx, [UIColor whiteColor].CGColor);
        CGContextFillRect(ctx, _mainContainerView.bounds);

        [_mainContainerView.layer.mask renderInContext:ctx];
        UIImage * maskimg = UIGraphicsGetImageFromCurrentImageContext();
        UIGraphicsEndImageContext();


        // Create a image mask from the UIImage
        CGImageRef maskRef = maskimg.CGImage;
        CGImageRef mask = CGImageMaskCreate(CGImageGetWidth(maskRef),
                                            CGImageGetHeight(maskRef),
                                            CGImageGetBitsPerComponent(maskRef),
                                            CGImageGetBitsPerPixel(maskRef),
                                            CGImageGetBytesPerRow(maskRef),
                                            CGImageGetDataProvider(maskRef), NULL, false);

        // Apply the mask to our source image
        CGImageRef maskedimg= CGImageCreateWithMask(img.CGImage, mask);

        // Convert to UIImage so we can easily display it in a UIImageView
        img = [UIImage imageWithCGImage:maskedimg scale:img.scale orientation:img.imageOrientation];

        CGImageRelease(mask);
        CGImageRelease(maskedimg);
    }



    _destImageView.image = img;

}

編集 最新バージョンが含まれているため、bitbucket の最新プロジェクトを確認してください。

于 2013-07-18T19:37:54.783 に答える