2012-10-31 19 views
23

画像をUIBezierpathクローズドパスから取得したい(画像参照)。 drawRectメソッドを使用してUIViewに画像を描画し、drawRectメソッドを使用して線を描画します。 特定のクローズドパス画像を取得するにはどうすればよいですか?私を助けてください。前もって感謝します。UIBezierPathを使用してイメージをトリミングする方法は?

このコードは、ベジェパスを描画するために使用します。

UIBezierPath *aPath = [UIBezierPath bezierPath]; 
for (NSString *pointString in pointArray) { 
    if ([pointArray indexOfObject:pointString] == 0) 
     [aPath moveToPoint:CGPointFromString(pointString)]; 
    else 
     [aPath addLineToPoint:CGPointFromString(pointString)]; 
} 
[aPath closePath]; 

enter image description here

+0

私はUIViewの上に線を描画しようとすると、どのように我々は、UIImageViewに線を引くことができる作業が、uiimageviewで動作していないされて、あなたは私を助けることができます – dineshprasanna

+0

あなたはあなたの目標を達成しましたか? – amar

+0

こんにちは、あなた自身の質問に答えることができます.... – Rajneesh071

答えて

14

あなたはそのためのshapeLayerを使用することができます。何かのように、

UIBezierPath *aPath = [UIBezierPath bezierPath]; 
for (NSString *pointString in pointArray) { 
    if ([pointArray indexOfObject:pointString] == 0) 
     [aPath moveToPoint:CGPointFromString(pointString)]; 
    else 
     [aPath addLineToPoint:CGPointFromString(pointString)]; 
} 
[aPath closePath]; 

CAShapeLayer *shapeLayer = [CAShapeLayer layer]; 
shapeLayer.path = aPath.CGPath; 
[view.layer setMask:shapeLayer];//or make it as [imageview.layer setMask:shapeLayer]; 
//and add imageView as subview of whichever view you want. draw the original image 
//on the imageview in that case 

UIGraphicsBeginImageContext(view.bounds.size); 
[view.layer renderInContext:UIGraphicsGetCurrentContext()]; 
UIImage *image = UIGraphicsGetImageFromCurrentImageContext(); 
UIGraphicsEndImageContext(); 

imageは、対応するイメージを持っている必要があり、画像としてそれを得るために。

+0

ありがとうACB ... UIBezierpathから画像を取得する方法。 – Mani

+0

私の答えが更新されました。それを確認してください。 – iDev

+0

ありがとうございます...私はこれを試しました、そのイメージを取得し、背景は白色です。私はUIBezierPath部分の画像が必要です(imag cat head参照)。私を分かってますか? – Mani

1

あなたは、コードのすべてを描画している場合だけ使用 - addClip、すなわち:

UIBezierPath *aPath = [UIBezierPath bezierPath]; 
for (NSString *pointString in pointArray) { 
    if ([pointArray indexOfObject:pointString] == 0) 
     [aPath moveToPoint:CGPointFromString(pointString)]; 
    else 
     [aPath addLineToPoint:CGPointFromString(pointString)]; 
} 
[aPath closePath]; 


CGContextSaveGState(context); 
{ 
    [aPath addClip]; 
    // draw image 
    [aPath stroke]; 
} 
CGContextRestoreGState(context); 
+0

こんにちはhypercrypt ...あなたの返事をありがとう。 – Mani

+0

特定のUIBezierPathからイメージを取得する方法。 – Mani

+0

イメージコンテキストを作成し、 'UIGraphicsGetImageFromCurrentImageContext()'を使用してください – hypercrypt

3

さて、あなたは通知に取らなければならないものがいくつかあります。

  1. UIViewの代わりにUIImageViewを渡していますか?
  2. タッチ操作のために画像表示を有効にしましたか?
  3. あなたのUIImageViewをサブクラス化して、あなたのためにその処理のためにdrawrect()を使用してください。

画像の一部(猫のようなもの)だけが必要な場合は、UIBezierPathに従って画像をサブマスクする必要があります。

は、以下の

を更新し、要件に変更し、完全な実施例です。

ViewController.h:

@interface ViewController : UIViewController 
{ 
    UIBezierPath *aPath; 
} 
@property (nonatomic,retain) NSMutableArray *pathArray; 
@property (nonatomic,retain) NSMutableDictionary *dic; 
@property (nonatomic,retain) IBOutlet UIImageView *imgView; 

@end 

ViewController.m:これは私の作品

@interface ViewController() 
- (IBAction)Crop:(id)sender; 
@end 

@implementation ViewController 
@synthesize pathArray,dic,imgView; 
- (void)viewDidLoad 
{ 
    [super viewDidLoad]; 

} 
- (void) setClippingPath:(UIBezierPath *)clippingPath : (UIImageView *)imgView; 
{ 

    NSLog(@"Mask Paths %@",clippingPath); 

    CAShapeLayer *maskLayer = [CAShapeLayer layer]; 
    maskLayer.frame = self.imgView.frame; 
    maskLayer.path = [clippingPath CGPath]; 
    maskLayer.fillColor = [[UIColor whiteColor] CGColor]; 
    maskLayer.backgroundColor = [[UIColor clearColor] CGColor]; 


    self.imgView.layer.mask = maskLayer; 



} 
-(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event 
{ 

    UITouch *mytouch=[[touches allObjects] objectAtIndex:0]; 
    self->aPath = [[UIBezierPath alloc]init]; 
    [aPath moveToPoint:[mytouch locationInView:imgView]]; 

} 
-(void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event 
{ 

    UITouch *mytouch=[[touches allObjects] objectAtIndex:0]; 
    [aPath addLineToPoint:[mytouch locationInView:imgView 
         ]]; 

} 
-(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event 
{ 

} 
- (IBAction)Crop:(id)sender 
{ 
    [self setClippingPath:aPath :imgView]; 
} 
+0

こんにちは、このレイヤーをクリアな背景のuiimageとして保存するにはどうすればいいですか?私は、CALayerのself.imgView.layer.maskをhttp://stackoverflow.com/questions/3454356/uiimage-from-calayer-iphone-sdkで説明したUIImageに変換しようとしました。しかし、それは望ましい結果ではありません。 – ScarletWitch

+0

こんにちは。どのように私はuibezierpathを理解し始めますか?私はドキュメンテーションを読もうとしましたが、ちょうど初心者なので、私はグリップを得るのに苦労しています。 uibezierpathの良いチュートリアルに案内してください。ありがとう。 – UsamaMan

+0

そのビットは遅いですが、レイヤーをどこにレンダリングしてUIImageを取得する必要がありますか。 –

0

...

UIBezierPath *path = ....//your path 
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); 
CGContextRef context = CGBitmapContextCreate(nil, frame.size.width, frame.size.height, 8, 4*frame.size.width, colorSpace, (CGBitmapInfo)kCGImageAlphaPremultipliedFirst); 

CGContextAddPath(context, path.CGPath); 
CGContextClip(context); 
CGContextDrawImage(context, frame, image.CGImage); 

[UIImage imageWithCGImage:CGBitmapContextCreateImage(context)]; 
2

使用スウィフトについては、このポッドios-helpers

- (UIImage *)imageWithStrokeColor: (UIColor *)stroke_color andFillColor: (UIColor *)fill_color { 

    // adjust bounds to account for extra space needed for lineWidth 
    CGFloat width = self.bounds.size.width + self.lineWidth * 2; 
    CGFloat height = self.bounds.size.height + self.lineWidth * 2; 
    CGRect bounds = CGRectMake(self.bounds.origin.x, self.bounds.origin.y, width, height); 

    // create a view to draw the path in 
    UIView *view = [[UIView alloc] initWithFrame:bounds]; 

    // begin graphics context for drawing 
    UIGraphicsBeginImageContextWithOptions(view.frame.size, NO, [[UIScreen mainScreen] scale]); 

    // configure the view to render in the graphics context 
    [view.layer renderInContext:UIGraphicsGetCurrentContext()]; 

    // get reference to the graphics context 
    CGContextRef context = UIGraphicsGetCurrentContext(); 

    // reverse the y-axis to match the opengl coordinate space 
    CGContextScaleCTM(context, 1, -1); 
    CGContextTranslateCTM(context, 0, -view.bounds.size.height); 

    // translate matrix so that path will be centered in bounds 
    CGContextTranslateCTM(context, -(bounds.origin.x - self.lineWidth), -(bounds.origin.y - self.lineWidth)); 

    // stroke color 
    [stroke_color setStroke]; 
    [self stroke]; 

    //fill color 
    [fill_color setFill]; 
    [self fill]; 

    // get an image of the graphics context 
    UIImage *viewImage = UIGraphicsGetImageFromCurrentImageContext(); 

    // end the context 
    UIGraphicsEndImageContext(); 

    return viewImage; 
} 
+1

答えに詳細を追加できますか?ドキュメントとサンプルコードへのリンクが含まれていますが、正確に何が記述されているのかをお教えいただければ幸いです。 – bjb568

+0

@ bjb568、申し訳ありません。ここにコードがあります。 – Yijun

+0

非常に良い。 +1しました – bjb568

1

はこれを試してください:ZImageCropper

ZImageCropperは、コア部分として、次のものを使用している:

  • UIBezierPath
  • UITouchイベント
  • CAShapeLayer
  • CoreGraphics
0

iDevの答えは素晴らしいですが、あなたは UIGraphicsBeginImageContext(view.bounds.size); を除き、その後、透明な背景が必要な場合は、デフォルトの画像コンテキストによって作成され

UIGraphicsBeginImageContextWithOptions(view.bounds.size, NO, 1.0); 

を使用する必要がありますopaque == YESであるため、NOに変更する必要があります。

0
// This Work 100% 

- (ボイド)touchesBegan:(NSSet *)はwithEventに触れる:(たUIEvent *)イベント{

mouseSwiped = NO; 
UITouch *touch = [touches anyObject]; 
lastPoint = [touch locationInView:self.view]; 
megView = [[UIImageView alloc]initWithFrame:CGRectMake(lastPoint.x , lastPoint.y , k_POINT_WIDTH , k_POINT_WIDTH)]; 
//[megView setImage:[UIImage imageNamed:@"b_image22.png"]]; 
[megView setContentMode:UIViewContentModeScaleToFill]; 
megView.alpha = 2; 
//megView.layer.backgroundColor = [UIColor whiteColor].CGColor; 
//megView.layer.cornerRadius = megView.frame.size.width/2; 
megView.clipsToBounds = YES; 
[self.main_uiview addSubview:megView]; 


self.bezierPath = [UIBezierPath bezierPath]; 
[self.bezierPath moveToPoint:lastPoint]; 

}

// Touchmove method 


- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event { 

mouseSwiped = YES; 
UITouch *touch = [touches anyObject]; 
CGPoint currentPoint = [touch locationInView:self.view]; 
UIGraphicsBeginImageContext(self.main_uiview.frame.size); 
[self.bg_imageview.image drawInRect:CGRectMake(0, 0, self.main_uiview.frame.size.width, self.main_uiview.frame.size.height)]; 
megView.frame = CGRectMake(currentPoint.x - k_POINT_WIDTH/2 , currentPoint.y - k_POINT_WIDTH/2 , k_POINT_WIDTH , k_POINT_WIDTH); 
CGContextMoveToPoint(UIGraphicsGetCurrentContext(), lastPoint.x, lastPoint.y); 
CGContextAddLineToPoint(UIGraphicsGetCurrentContext(), currentPoint.x, currentPoint.y); 
CGContextSetLineCap(UIGraphicsGetCurrentContext(), kCGLineCapRound); 
CGContextStrokePath(UIGraphicsGetCurrentContext()); 


CGContextSetRGBStrokeColor(UIGraphicsGetCurrentContext(), red,green ,blue, 0.20); 
CGContextSetBlendMode(UIGraphicsGetCurrentContext(), kCGBlendModeCopy); 
    self.bg_imageview.image = UIGraphicsGetImageFromCurrentImageContext(); 
    [self.bg_imageview setAlpha:opacity]; 

UIGraphicsEndImageContext(); 

lastPoint = currentPoint; 

[self.bezierPath addLineToPoint:lastPoint]; 

}

// TouchEnd Method 


    - (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event 

{

[megView removeFromSuperview]; 

}

 // Image Crop Method 


    -(UIImage *)croppedImage 
    { 
UIImage *myImage = UIGraphicsGetImageFromCurrentImageContext(); 
UIGraphicsEndImageContext(); 
[self.bezierPath closePath]; 
CGContextSetRGBStrokeColor(UIGraphicsGetCurrentContext(), 0.0, 0.0, 0.0, 0.0); 
_b_image = self.bg_imageview.image; 
CGSize imageSize = _b_image.size; 
CGRect imageRect = CGRectMake(0, 0, imageSize.width, imageSize.height); 
UIGraphicsBeginImageContextWithOptions(imageSize, NO, [[UIScreen mainScreen] scale]); 
[self.bezierPath addClip]; 
[_b_image drawInRect:imageRect]; 

UIImage *croppedImage = UIGraphicsGetImageFromCurrentImageContext(); 
UIGraphicsEndImageContext(); 
return croppedImage; 

}

関連する問題