My program is crashing when I call the function CGContextStrokePath (last line in the code below.) Can context get corrupted somehow? (it only crashes when expression
(which is an NSArray) has certain values in it). It's supposed to draw a graph of whatever is in expression
. For example if expression
has the objects: x, cos (represented as strings) it will draw a cosine curve. Here is the code:
- (double) yValueFromExpression:(id)anExpression atPosition:(double)xValue
{
NSDictionary *aDictionary = [NSDictionary dictionaryWithObject:[NSNumber numberWithDouble:xValue] forKey:@"%x"];
return [CalculatorBrain evaluateExpression:anExpression usingVariableValues:aDictionary];
}
#define PRECISION 500
- (void)drawRect:(CGRect)rect
{
double scale = [self.delegate scaleForGraphView:self];
id expression = [self.delegate expressionForGraphView:self];
CGPoint origin;
origin.x = (self.bounds.origin.x + self.bounds.size.width) / 2;
origin.y = (self.bounds.origin.y + self.bounds.size.height) / 2;
[AxesDrawer drawAxesInRect:self.bounds originAtPoint:origin scale:scale];
// -150/scale to 150/scale is the range of x values that axesDrawer (drawAxesInRect) displays.
double leftMostXValue = -150 / scale;
double rightMostXValue = 150 / scale;
double increment = (rightMostXValue - leftMostXValue) / PRECISION;
CGContextRef context = UIGraphicsGetCurrentContext();
CGContextBeginPath(context);
CGContextMoveToPoint(context, self.bounds.origin.x, origin.y -
[self yValueFromExpression:expression atPosition:leftMostXValue] * scale);
for (int i = 1; i <= PRECISION; ++i) {
double currentXValue = leftMostXValue + i * increment;
CGContextAddLineToPoint(context, self.bounds.origin.x + (self.bounds.size.width / PRECISION) * i,
origin.y - [self yValueFromExpression:expression atPosition:currentXValue] * scale);
}
CGContextStrokePath(context);
}
This is the error message I get when CGContextStrokePath is called:
Program received signal: “EXC_BAD_ACCESS”.
Answer: I need to put a guard around CGContextAddLineToPoint() to make sure it is drawing within the bounds of the rect
:
for (int i = 1; i <= PRECISION; ++i) {
double currentXValue = leftMostXValue + i * increment;
double xPoint = self.bounds.origin.x + (self.bounds.size.width / PRECISION) * i;
double yPoint = origin.y - [self yValueFromExpression:expression atPosition:currentXValue] * scale;
if (xPoint < (self.bounds.origin.x + self.bounds.size.width) && xPoint > 0 &&
yPoint < (self.bounds.origin.y + self.bounds.size.height) 开发者_StackOverflow社区&& yPoint > 0) {
CGContextAddLineToPoint(context, xPoint, yPoint);
}
}
EXC_BAD_ACCESS usually means you have a memory problem.
If I had to guess, expressionForGraphView might be returning garbage sometimes.
精彩评论