I have created a drawing app to draw when you touch the screen and it works very smooth in the simulator but when I tested it on my iPad 2 it slows down and it takes very long time to draw I am using these lines of code:
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
UITouch *touch = [[event allTouches] anyObject];
lastPoint = [touch locationInView:self.view];
}
- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event {
mouseSwiped = YES;
UITouch *touch = [touches anyObject];
currentPoint = [touch locationInView:self.view];
UIGraphicsBeginImageContext(self.view.frame.size);
[drawImage.image drawInRect:self.view.frame];
CGContextSetLineCap(UIGraphicsGetCurrentContext(), kCGLineCapRound);
CGContextSetLineWidth(UIGraphicsGetCurrentContext(), 7.0);
CGContextSetRGBStrokeColor(UIGraphicsGetCurrentContext(), 0, 1, 0, 1);
CGContextBeginPath(UIGraphicsGetCurrentContext());
CGContextMoveToPoint(UIGraphicsGetCurrentContext(), lastPoint.x, lastPoint.y);
CGContextAddLineToPoint(UIGraphicsGetCurrentContext(), currentPoint.x, currentPoint.y);
CGContextStrokePath(UIGraphicsGetCurrentContext());
[drawImage setFrame:self.view.frame];
drawImage.image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
lastPoint = currentPoint;
[self.view addSubview:drawImage];
}
I think the problem is with calling drawInRect: method in touchMoved: method
Build up a UIBezierPath in your touchesMoved and don't do any drawing there.
Call setNeedsDisplay in touchesMoved.
Override drawRect and draw your path there.
OR
Use set the layer backing for your view to a CAShapeLayer and add the points to the layer in touchesMoved.
Related
I display a popover that's allows to draw inside.
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{
mouseSwiped = NO;
UITouch *touch = [touches anyObject];
lastPoint = [touch locationInView:self.view];
}
- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event
{
mouseSwiped = YES;
UITouch *touch = [touches anyObject];
CGPoint currentPoint = [touch locationInView:self.view];
NSLog(#"lastPoint: %#", NSStringFromCGPoint(lastPoint));
UIGraphicsBeginImageContext(self.view.frame.size);
[mainImage.image drawInRect:CGRectMake(0, 0, 600, 400)];
CGContextMoveToPoint(UIGraphicsGetCurrentContext(), lastPoint.x, lastPoint.y);
CGContextAddLineToPoint(UIGraphicsGetCurrentContext(), currentPoint.x, currentPoint.y);
CGContextSetLineCap(UIGraphicsGetCurrentContext(), kCGLineCapRound);
CGContextSetLineWidth(UIGraphicsGetCurrentContext(), brush );
CGContextSetRGBStrokeColor(UIGraphicsGetCurrentContext(), red, green, blue, 1.0);
CGContextSetBlendMode(UIGraphicsGetCurrentContext(),kCGBlendModeNormal);
CGContextStrokePath(UIGraphicsGetCurrentContext());
mainImage.image = UIGraphicsGetImageFromCurrentImageContext();
[mainImage setAlpha:opacity];
UIGraphicsEndImageContext();
lastPoint = currentPoint;
}
My problem is that since the iOS13, it doesn't display well.
How it should display:
How it display now in iOS13:
Any ideas?
I'm trying to implement a freehand drawing tool by which user can draw several shapes dynamically like rectangle,eclipse,circle etc on a PDF using touch begins and touch move methods.
So anyone there who have done this kind of tool or have knowledge how to accomplish this,please help me out.
Thank you in advance.
This is a very broad question to be answered on StackOverflow. Still I am trying to give you a start here.
1) Declare two global variables BOOL mouseSwiped, CGPoint lastPoint in your UIViewController.
2)
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
mouseSwiped = NO;
UITouch *touch = [touches anyObject];
lastPoint = [touch locationInView:self.view];
}
3)
- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event {
mouseSwiped = YES;
UITouch *touch = [touches anyObject];
CGPoint currentPoint = [touch locationInView:self.view];
UIGraphicsBeginImageContext(yourSubview.frame.size);
[yourSubview drawInRect:CGRectMake(0, 0, yourSubview.frame.size.width, yourSubview.frame.size.height)];
CGContextMoveToPoint(UIGraphicsGetCurrentContext(), lastPoint.x, lastPoint.y);
CGContextAddLineToPoint(UIGraphicsGetCurrentContext(), currentPoint.x, currentPoint.y);
CGContextSetLineCap(UIGraphicsGetCurrentContext(), kCGLineCapRound);
CGContextSetLineWidth(UIGraphicsGetCurrentContext(), 3.0 );
CGContextSetRGBStrokeColor(UIGraphicsGetCurrentContext(), red, green, blue, 1.0);
CGContextSetBlendMode(UIGraphicsGetCurrentContext(),kCGBlendModeNormal);
CGContextStrokePath(UIGraphicsGetCurrentContext());
yourSubview = UIGraphicsGetImageFromCurrentImageContext();
[yourSubview setAlpha:1.0];
UIGraphicsEndImageContext();
lastPoint = currentPoint;
}
4)
- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {
UIGraphicsBeginImageContext(yourSubview.frame.size);
[yourSubview drawInRect:CGRectMake(0, 0, yourSubview.frame.size.width, yourSubview) blendMode:kCGBlendModeNormal alpha:1.0];
yourSubview = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
}
Hope this helps
what i have done is getting image from gallery which should
be erased while moving finger on image using touch.my image is erasing.but problem is app terminates when erasing the image .my code is like this
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{
self.sizeSlider.hidden=NO;
UITouch *touch = [touches anyObject];
lastPoint = [touch locationInView:self.view];
}
- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event
{
UITouch *touch = [touches anyObject];
CGPoint currentPoint = [touch locationInView:self.shareView];
UIGraphicsBeginImageContext(self.shareView.frame.size);
[imgForeGround.image drawInRect:CGRectMake(0, 0, self.shareView.frame.size.width,
self.shareView.frame.size.height)];
// I add this
CGContextSetBlendMode(UIGraphicsGetCurrentContext(), kCGBlendModeClear);
CGContextSetLineCap(UIGraphicsGetCurrentContext(), kCGLineCapRound);
CGContextSetLineWidth(UIGraphicsGetCurrentContext(), sizeSlider.value);
CGContextBeginPath(UIGraphicsGetCurrentContext());
CGContextSetBlendMode(UIGraphicsGetCurrentContext(), kCGBlendModeClear);
CGContextMoveToPoint(UIGraphicsGetCurrentContext(), lastPoint.x, lastPoint.y);
CGContextAddLineToPoint(UIGraphicsGetCurrentContext(), currentPoint.x, currentPoint.y);
CGContextStrokePath(UIGraphicsGetCurrentContext());
imgForeGround.image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
lastPoint = currentPoint;
[imgForeGround setNeedsDisplay];
}
please anybody help me to avoid this memory leaks of this problem help is appreciated
There are few more controls easy to implement:
https://github.com/moqod/iOS-Scratch-n-See
I'm trying to add a drawing functionality using touch events on my UIImage (inside a UIImageView). However, for certain images, when I begin drawing, the image starts shrinking and becomes blurier the more i draw on it. I mostly used ray wenderlich's old drawing tutorial for reference, just changed values to match my UI. The two images show you what happens when i draw:
It looks like I'm using pretty standard methods for the drawing. My hunch is that the bounds/rectangle drawing methods are causing some sort of problem.
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
if(_allowDoodling == NO) return;
UITouch *touch = [touches anyObject];
lastPoint = [touch previousLocationInView:self.imageView];
}
- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event {
if(_allowDoodling == NO) return;
UITouch *touch = [touches anyObject];
CGPoint currentPoint = [touch locationInView:self.imageView];
UIGraphicsBeginImageContextWithOptions(_imageView.frame.size, NO, 2.0f);
CGContextRef context = UIGraphicsGetCurrentContext();
CGContextSetInterpolationQuality(context, kCGInterpolationHigh);
[_imageView.image drawInRect:_imageView.bounds];
CGContextMoveToPoint(UIGraphicsGetCurrentContext(), lastPoint.x, lastPoint.y);
CGContextAddLineToPoint(context, currentPoint.x, currentPoint.y);
CGContextSetLineCap(context, kCGLineCapRound);
CGContextSetLineWidth(context, 5.0);
CGContextSetStrokeColorWithColor(context, _doodleColor.CGColor);
CGContextStrokePath(UIGraphicsGetCurrentContext());
_imageView.image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
lastPoint = currentPoint;
}
- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {
if(_allowDoodling == NO) return;
UIGraphicsBeginImageContextWithOptions(_imageView.frame.size, NO, 2.0f);
[_imageView.image drawInRect:_imageView.bounds];
_imageView.image = UIGraphicsGetImageFromCurrentImageContext();
CGContextFlush(UIGraphicsGetCurrentContext());
UIGraphicsEndImageContext();
}
It posible, that you have to use
UIGraphicsBeginImageContextWithOptions(CGSizeMake(_imageView.frame.size.width * 2, _imageView.frame.size.width * 2), NO, 1.0f);
I created a drawing application. Since I use drawing on a large image I also need to have scrolling as well, but when I implemented scrolling, the drawing did not work any more.
I think there is a conflict on the touch event between drawing and scrolling.
I am thinking to do scrolling with two finger and drawing with one finger, but I could not find out how to implement it. I appreciate if any one could help me to fix this problem.
-(void)viewDidLayoutSubviews
{
scroller.scrollEnabled=YES;
scroller.contentSize=temp.frame.size;
toggledrawandscroll=false;
}
- (IBAction)changescrollstatues:(id)sender {
if(toggledrawandscroll){
//if draw is enable,disable it
toggledrawandscroll =false;
scroller.scrollEnabled=YES;
scroller.canCancelContentTouches=YES;
scroller.contentSize=temp.frame.size;
}
else{
toggledrawandscroll =true;
scroller.scrollEnabled=NO;
scroller.canCancelContentTouches=NO;
}
}
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
mouseSwiped = NO;
UITouch *touch = [touches anyObject];
lastPoint = [touch locationInView:self.view];
}
- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event {
//initial setting for touch point
mouseSwiped = YES;
UITouch *touch = [touches anyObject];
CGPoint currentPoint = [touch locationInView:self.view];
//set the concext
UIGraphicsBeginImageContext(self.view.frame.size);
[temp.image drawInRect:CGRectMake(0, 0, self.view.frame.size.width, self.view.frame.size.height)];
CGContextMoveToPoint(UIGraphicsGetCurrentContext(), lastPoint.x, lastPoint.y);
CGContextAddLineToPoint(UIGraphicsGetCurrentContext(), currentPoint.x, currentPoint.y);
//drawing setting
CGContextSetLineCap(UIGraphicsGetCurrentContext(), kCGLineCapRound);
CGContextSetLineWidth(UIGraphicsGetCurrentContext(), 1);
CGContextSetRGBStrokeColor(UIGraphicsGetCurrentContext(),red, green, blue, 1);
CGContextSetLineWidth(UIGraphicsGetCurrentContext(), 1);
CGContextSetBlendMode(UIGraphicsGetCurrentContext(),kCGBlendModeNormal);
CGContextStrokePath(UIGraphicsGetCurrentContext());
temp.image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
lastPoint = currentPoint;
}
- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {
if(!mouseSwiped) {
//initial seting
UIGraphicsBeginImageContext(self.view.frame.size);
[temp.image drawInRect:CGRectMake(0, 0, self.view.frame.size.width, self.view.frame.size.height)];
CGContextSetLineCap(UIGraphicsGetCurrentContext(), kCGLineCapRound);
CGContextSetLineWidth(UIGraphicsGetCurrentContext(), brush);
CGContextSetRGBStrokeColor(UIGraphicsGetCurrentContext(), red, green, blue, opacity);
CGContextMoveToPoint(UIGraphicsGetCurrentContext(), lastPoint.x, lastPoint.y);
CGContextAddLineToPoint(UIGraphicsGetCurrentContext(), lastPoint.x, lastPoint.y);
CGContextStrokePath(UIGraphicsGetCurrentContext());
CGContextFlush(UIGraphicsGetCurrentContext());
temp.image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
}
}
So it looks like you have a toggle to enable scrolling? If that is the case your changesscrollstatues method never enables the scroll and never sets your boolean to YES. Your scroller is always enabled so the touch event won't get captured.