Reputation: 63
I am using custom labels and I faced problem when x-axis label imposes on another x-axis label, and I can't find out how to hide those labels when user zoom out on scatter plot (in real time).
See the print-screen below: I want to hide "August 2012" label.
How can I do that?
Here below code I am using:
CPTXYAxis *x = axisSet.xAxis;
x.orthogonalCoordinateDecimal = CPTDecimalFromInteger(0);
x.majorIntervalLength = CPTDecimalFromInteger(150);
x.minorTicksPerInterval = 5;
x.axisConstraints = [CPTConstraints constraintWithLowerOffset:0.0f];
x.labelingPolicy=CPTAxisLabelingPolicyNone;
NSUInteger labelLocation = 0;
NSMutableArray *customLabels = [NSMutableArray arrayWithCapacity:[objects count]];
NSMutableSet *xMajorLocations = [NSMutableSet setWithCapacity:[objects count]];
for (NSInteger i = 0; i < [objects count]; i++) {
NSManagedObject *theLine = [objects objectAtIndex:i];
NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
NSString *sPeriodText = @"";
[dateFormatter setDateFormat:@"MMMM yyyy"];
sPeriodText = [dateFormatter stringFromDate:[theLine valueForKey:@"period_start"]];
CPTAxisLabel *newLabel = [[CPTAxisLabel alloc] initWithText:sPeriodText textStyle:labelTextStyle];
newLabel.tickLocation = CPTDecimalFromInteger(labelLocation++);
newLabel.offset = x.labelOffset + x.majorTickLength;
[customLabels addObject:newLabel];
[xMajorLocations addObject:[NSNumber numberWithFloat:labelLocation-1]];
}
x.axisLabels = [NSSet setWithArray:customLabels];
x.majorTickLocations = xMajorLocations;
Thank you!
P.S. I was trying to use labelExclusionRanges of CPTAxis, but it didn't work with custom labels.
Upvotes: 1
Views: 917
Reputation: 63
Find out how to make it. Because I used the date format as x-axis label, I need to use a CPTTimeFormatter + preferredNumberOfMajorTicks, not custom labels!
Here is a code below:
...
NSManagedObject *theLineFirst = [objects objectAtIndex:0];
NSManagedObject *theLineLast = [objects objectAtIndex:[objects count]-1];
NSDate *refDate = [NSDate dateWithTimeInterval:0 sinceDate:[theLineFirst valueForKey:@"period_start"]];
NSTimeInterval secondsBetween = [[theLineLast valueForKey:@"period_start"] timeIntervalSinceDate:[theLineFirst valueForKey:@"period_start"]];
NSTimeInterval onePart = secondsBetween/[objects count];
CPTXYPlotSpace *plotSpace = (CPTXYPlotSpace *)graph.defaultPlotSpace;
plotSpace.delegate = self;
plotSpace.allowsUserInteraction = YES;
plotSpace.xRange = [CPTPlotRange plotRangeWithLocation:CPTDecimalFromInteger(-onePart) length:CPTDecimalFromInteger(secondsBetween+onePart*2)];
plotSpace.yRange = [CPTPlotRange plotRangeWithLocation:CPTDecimalFromInteger(minCData) length:CPTDecimalFromInteger(abs(maxCData-minCData))];
plotSpace.globalXRange = plotSpace.xRange;
plotSpace.globalYRange = plotSpace.yRange;
// Axes
CPTXYAxisSet *axisSet = (CPTXYAxisSet *)graph.axisSet;
CPTXYAxis *x = axisSet.xAxis;
x.orthogonalCoordinateDecimal = CPTDecimalFromInteger(0);
x.majorIntervalLength = CPTDecimalFromInteger(5);
x.minorTicksPerInterval = 0;
x.axisConstraints = [CPTConstraints constraintWithLowerOffset:0.0f];
x.labelingPolicy = CPTAxisLabelingPolicyAutomatic;
// added for date
NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
[dateFormatter setDateFormat:@"MMMM yyyy"];
CPTTimeFormatter *timeFormatter = [[CPTTimeFormatter alloc] initWithDateFormatter:dateFormatter];
timeFormatter.referenceDate = refDate;
axisSet.xAxis.labelFormatter = timeFormatter;
x.preferredNumberOfMajorTicks = 4;
...
-(NSUInteger)numberOfRecordsForPlot:(CPTPlot *)plot {
return [objects count];
}
-(NSNumber *)numberForPlot:(CPTPlot *)plot field:(NSUInteger)fieldEnum recordIndex:(NSUInteger)index {
NSManagedObject *theLineFirst = [objects objectAtIndex:0];
NSManagedObject *theLine = [objects objectAtIndex:index];
NSTimeInterval secondsBetween = [[theLine valueForKey:@"period_start"] timeIntervalSinceDate:[theLineFirst valueForKey:@"period_start"]];
switch (fieldEnum) {
case CPTScatterPlotFieldX:
return [NSNumber numberWithDouble:secondsBetween];
case CPTScatterPlotFieldY:
return [NSNumber numberWithDouble:[[theLine valueForKey:@"cdata"] doubleValue]];
}
return [NSDecimalNumber zero];
}
And that's all!
Upvotes: 3
Reputation: 27381
Core Plot doesn't handle this automatically yet. You'll have to use the available width of the plot area and the size of labels to decide when to show labels for each tick mark and omit the custom labels at the proper locations.
Upvotes: 0