CALayers を使用した丸みを帯びた UIView - 一部の角のみ - 方法は? 質問する

CALayers を使用した丸みを帯びた UIView - 一部の角のみ - 方法は? 質問する

私のアプリケーションには、次の名前のボタンが 4 つあります。

  • 左上
  • 左下
  • 右上
  • 右下

ボタンの上には画像ビュー (または UIView) があります。

ここで、ユーザーが左上のボタンをタップしたとします。上の画像/ビューは、その特定の角で丸くなるはずです。

UIView に丸い角を適用するのに少し困難があります。

現在、次のコードを使用して、各ビューに丸い角を適用しています。

    // imgVUserImg is a image view on IB.
    imgVUserImg.image=[UIImage imageWithData:[NSData dataWithContentsOfURL:[NSURL URLWithString:@"any Url Here"];
    CALayer *l = [imgVUserImg layer];
    [l setMasksToBounds:YES];
    [l setCornerRadius:5.0];  
    [l setBorderWidth:2.0];
    [l setBorderColor:[[UIColor darkGrayColor] CGColor]];

上記のコードは、提供されたビューの各コーナーに丸みを適用しています。代わりに、上 / 上 + 左 / 下 + 右などの選択したコーナーに丸みを適用したいと考えました。

それは可能ですか? どうやって?

ベストアンサー1

iOS 3.2 以降では、 の機能を使用してUIBezierPath、すぐに使用できる丸い四角形 (指定した角のみが丸くなる) を作成できます。次に、これを のパスとして使用しCAShapeLayer、これをビューのレイヤーのマスクとして使用できます。

// Create the path (with only the top-left corner rounded)
UIBezierPath *maskPath = [UIBezierPath bezierPathWithRoundedRect:imageView.bounds 
                                               byRoundingCorners:UIRectCornerTopLeft
                                                     cornerRadii:CGSizeMake(10.0, 10.0)];

// Create the shape layer and set its path
CAShapeLayer *maskLayer = [CAShapeLayer layer];
maskLayer.frame = imageView.bounds;
maskLayer.path = maskPath.CGPath;

// Set the newly created shape layer as the mask for the image view's layer
imageView.layer.mask = maskLayer;

これで完了です。Core Graphics で手動でシェイプを定義したり、Photoshop でマスク イメージを作成したりする必要はありません。レイヤーを無効にする必要もありません。丸い角を適用したり、新しい角に変更したりするのは、新しい角を定義してマスク レイヤーのパスとしてUIBezierPath使用するのと同じくらい簡単です。メソッドのパラメーターはビットマスクなので、複数の角を OR 演算で丸くすることができます。CGPathcornersbezierPathWithRoundedRect:byRoundingCorners:cornerRadii:


編集: 影を追加する

これに影を追加したい場合は、もう少し作業が必要です。

「 」はマスクを適用するためimageView.layer.mask = maskLayer、通常はマスクの外側に影は表示されません。 秘訣は、透明なビューを使用し、CALayerビューのレイヤーに と の 2 つのサブレイヤー ( )を追加することshadowLayerですroundedLayer。 どちらも を使用する必要がありますUIBezierPath。 画像は のコンテンツとして追加されますroundedLayer

// Create a transparent view
UIView *theView = [[UIView alloc] initWithFrame:theFrame];
[theView setBackgroundColor:[UIColor clearColor]];

// Create the path (with only the top-left corner rounded)
UIBezierPath *maskPath = [UIBezierPath bezierPathWithRoundedRect:theView.bounds 
                                               byRoundingCorners:UIRectCornerTopLeft
                                                     cornerRadii:CGSizeMake(10.0f, 10.0f)];

// Create the shadow layer
CAShapeLayer *shadowLayer = [CAShapeLayer layer];
[shadowLayer setFrame:theView.bounds];
[shadowLayer setMasksToBounds:NO];
[shadowLayer setShadowPath:maskPath.CGPath];
// ...
// Set the shadowColor, shadowOffset, shadowOpacity & shadowRadius as required
// ...

// Create the rounded layer, and mask it using the rounded mask layer
CALayer *roundedLayer = [CALayer layer];
[roundedLayer setFrame:theView.bounds];
[roundedLayer setContents:(id)theImage.CGImage];

CAShapeLayer *maskLayer = [CAShapeLayer layer];
[maskLayer setFrame:theView.bounds];
[maskLayer setPath:maskPath.CGPath];

roundedLayer.mask = maskLayer;

// Add these two layers as sublayers to the view
[theView.layer addSublayer:shadowLayer];
[theView.layer addSublayer:roundedLayer];

おすすめ記事