问题
Is there a way to make tick mark (major tick mark) to be UIImage (custom graphics) instead of text? I have values in one of the axis I need to present as icons. I do not see any delegate for this but maybe someone knows the trick?
回答1:
Axis labels can have any CPTLayer
(which is a direct subclass of Core Animation's CALayer
) as its content. Set your image as the layer background and build a custom label using this layer. Several of the Core Plot example apps demonstrate custom labels, although they all use text labels.
You have two options for adding your custom labels to the graph:
Use the
CPTAxisLabelingPolicyNone
labeling policy. Create aNSSet
containing your labels and set it to theaxisLabels
property on the axis. If you use this, remember that you must provide the major and/or minor tick locations in addition to the custom labels.Use any other labeling policy to generate the tick locations and implement the
-axis:shouldUpdateAxisLabelsAtLocations:
axis delegate method. In your delegate, create new labels at the provided locations and returnNO
to suppress the automatic labels.
Eric
回答2:
Accepting Eric's question and thanking him I provide working code for his suggested solution. Maybe it helps someone:
if (yAxisIcons) {
int custonLabelsCount = [self.yAxisIcons count];
NSMutableArray *customLabels = [NSMutableArray arrayWithCapacity:custonLabelsCount];
for (NSUInteger i = 0; i < custonLabelsCount; i++) {
NSNumber *tickLocation = [NSNumber numberWithInt:i];
NSString *file = [yAxisIcons objectAtIndex:i];
UIImage *icon = [UIImage imageNamed:file];
CPImageLayer *layer; // My custom CPLayer subclass - see code below
CGFloat nativeHeight = 1;
CGFloat nativeWidth = 1;
if (icon) {
layer = [[CPImageLayer alloc] initWithImage:icon];
nativeWidth = 20;//CGImageGetWidth(icon.CGImage);
nativeHeight = 20;//CGImageGetHeight(icon.CGImage);
//layer.contents = (id)icon.CGImage;
if (nativeWidth > biggestCustomIconWidth) {
biggestCustomIconWidth = nativeWidth;
}
}else{
layer = [[CPImageLayer alloc] initWithFrame:CGRectMake(0, 0, 1, 1)];
}
CGRect startFrame = CGRectMake(0.0, 0.0, nativeWidth, nativeHeight);
layer.frame = startFrame;
layer.backgroundColor = [UIColor clearColor].CGColor;
CPAxisLabel *newLabel = [[CPAxisLabel alloc] initWithContentLayer:layer];
newLabel.tickLocation = [tickLocation decimalValue];
newLabel.offset = x.labelOffset + x.majorTickLength;
[customLabels addObject:newLabel];
[newLabel release];
[layer release];
}
y.axisLabels = [NSSet setWithArray:customLabels];
}
CPImageLayer.h
#import "CPLayer.h"
@interface CPImageLayer : CPLayer {
UIImage *_image;
}
-(id)initWithImage:(UIImage *)image;
@end
CPImageLayer.m
#import "CPImageLayer.h"
#import "CPLayer.h"
@implementation CPImageLayer
-(void)dealloc{
[_image release];
[super dealloc];
}
-(id)initWithImage:(UIImage *)image{
CGRect f = CGRectMake(0, 0, image.size.width, image.size.height);
if (self = [super initWithFrame:f]) {
_image = [image retain];
}
return self;
}
-(void)drawInContext:(CGContextRef)ctx{
CGContextDrawImage(ctx, self.bounds, _image.CGImage);
}
@end
Enjoy
来源:https://stackoverflow.com/questions/6748996/how-to-set-custom-tick-marks-in-core-plot-to-icons