Core-Plot多个y轴对齐问题 - 可能与缩放有关

时间:2014-03-27 14:35:49

标签: ios core-plot graphing

我的问题如下:

我正在尝试绘制两个数据集(一个在英尺,一个在度数中),以便可以比较它们(它们共享一个共同的x轴值)。

正如你所看到的,我的数据似乎是正确隔行扫描的,但是我无法让yAxises按照我的意愿行事。我希望X-Axis Max / Min实际上与Y轴同时排列。我的代码如下:

- (void)initPlot {
    [self loadCoreData];
    [self configureHost];
    [self configureGraph];
    [self configurePlots];
    [self configureAxes];
}

- (void)configureHost {
    self.hostView = [(CPTGraphHostingView *) [CPTGraphHostingView alloc] initWithFrame:self.view.bounds];
    self.hostView.allowPinchScaling = YES;
    [self.view addSubview:self.hostView];
}

- (void)configureGraph {
    // 1 - Create the graph
    CPTGraph *graph = [[CPTXYGraph alloc] initWithFrame:self.hostView.bounds];
    [graph applyTheme:[CPTTheme themeNamed:kCPTDarkGradientTheme]];
    self.hostView.hostedGraph = graph;


    // 2 - Set graph title

    NSString *title = [NSString stringWithFormat:@"Altitude Plot [%@ to %@]",        self.flightRecording.originAirport,     self.flightRecording.destinationAirport];

    graph.title = title;


    // 3 - Create and set text style
    CPTMutableTextStyle *titleStyle = [CPTMutableTextStyle textStyle];
    titleStyle.color = [CPTColor whiteColor];
    titleStyle.fontName = @"Helvetica-Bold";
    titleStyle.fontSize = 16.0f;
    graph.titleTextStyle = titleStyle;
    graph.titlePlotAreaFrameAnchor = CPTRectAnchorTop;
    graph.titleDisplacement = CGPointMake(0.0f, -20.0f);


    // 4 - Set padding for plot area
    float padding = 10.0f;
    [graph.plotAreaFrame setPaddingLeft:padding];
    [graph.plotAreaFrame setPaddingBottom:50.0f];
    [graph.plotAreaFrame setPaddingRight:padding];
    [graph.plotAreaFrame setPaddingTop:padding];

    // 5 - Enable user interactions for plot space
    altSpace= (CPTXYPlotSpace *) graph.defaultPlotSpace;
    altSpace.allowsUserInteraction = NO;

    rollSpace = [[CPTXYPlotSpace alloc] init];
    rollSpace.allowsUserInteraction = NO;
    [self.hostView.hostedGraph addPlotSpace:rollSpace];

//
//    pitchSpace = [[CPTXYPlotSpace alloc] init];
//    pitchSpace.allowsUserInteraction = NO;
//    [self.hostView.hostedGraph addPlotSpace:pitchSpace];
//
//
//    slipSpace = [[CPTXYPlotSpace alloc] init];
//    slipSpace.allowsUserInteraction = NO;
//    [self.hostView.hostedGraph addPlotSpace:slipSpace];
//
//
//    gSpace = [[CPTXYPlotSpace alloc] init];
//    gSpace.allowsUserInteraction = NO;
//    [self.hostView.hostedGraph addPlotSpace:gSpace];
}

- (void)configurePlots {
    // 1 - Get graph and plot space
    CPTGraph *graph = self.hostView.hostedGraph;




    // 2 - Create the three plots

    // Custom AHRS Plot
    CPTScatterPlot *ahrsAltPlot = [[CPTScatterPlot alloc] init];
    ahrsAltPlot.dataSource = self;
    ahrsAltPlot.identifier = @"AHRSALT";
    CPTColor *ahrsAltColor = [CPTColor yellowColor];
    [graph addPlot:ahrsAltPlot toPlotSpace:altSpace];


    CPTScatterPlot *rollPlot = [[CPTScatterPlot alloc] init];
    rollPlot.dataSource = self;
    rollPlot.identifier = @"ROLL";
    CPTColor *rollColor = [CPTColor greenColor];
    [graph addPlot:rollPlot toPlotSpace:rollSpace];

    // 3 - Set up plot space
    CPTMutablePlotRange *xRange = [altSpace.xRange mutableCopy];
    xRange=[CPTMutablePlotRange plotRangeWithLocation:CPTDecimalFromFloat(0.0f ) length:CPTDecimalFromFloat(maxEpoch + 300.0f )];


//    [xRange expandRangeByFactor:CPTDecimalFromCGFloat(1.1f)];
    altSpace.xRange = xRange;

    CPTMutablePlotRange *yRange = [altSpace.yRange mutableCopy];
    yRange = [CPTMutablePlotRange plotRangeWithLocation:CPTDecimalFromFloat(0.0f) length:CPTDecimalFromFloat(maxAlt)];
    [yRange expandRangeByFactor:CPTDecimalFromCGFloat(1.2f)];

    altSpace.yRange = yRange;

    rollSpace.xRange = xRange;

    CPTMutablePlotRange *yRangeRoll =[CPTMutablePlotRange plotRangeWithLocation:CPTDecimalFromFloat(0 ) length:CPTDecimalFromFloat(40 )];


    [yRangeRoll expandRangeByFactor:CPTDecimalFromCGFloat(1.2f)];

    rollSpace.yRange =  yRangeRoll;

    [altSpace scaleToFitPlots:[NSArray arrayWithObjects:ahrsAltPlot, nil] ];
    [rollSpace scaleToFitPlots:[NSArray arrayWithObjects:rollPlot, nil]  ];

    [rollSpace setYRange:yRangeRoll];



    // 4 - Create styles and symbols


    // AHRS Style
    CPTMutableLineStyle *ahrsLineStyle = [ahrsAltPlot.dataLineStyle mutableCopy];

    ahrsLineStyle.lineWidth = 2.5;
    ahrsLineStyle.lineColor = [CPTColor blueColor];
    ahrsAltPlot.dataLineStyle = ahrsLineStyle;

}

- (void)configureAxes {
    // 1 - Create styles
    CPTMutableTextStyle *axisTitleStyle = [CPTMutableTextStyle textStyle];
    axisTitleStyle.color = [CPTColor whiteColor];
    axisTitleStyle.fontName = @"Helvetica-Bold";
    axisTitleStyle.fontSize = 12.0f;


    CPTMutableLineStyle *axisLineStyle = [CPTMutableLineStyle lineStyle];
    axisLineStyle.lineWidth = 2.0f;
    axisLineStyle.lineColor = [CPTColor whiteColor];


    CPTMutableTextStyle *axisTextStyle = [[CPTMutableTextStyle alloc] init];
    axisTextStyle.color = [CPTColor whiteColor];
    axisTextStyle.fontName = @"Helvetica-Bold";
    axisTextStyle.fontSize = 11.0f;


    CPTMutableLineStyle *tickLineStyle = [CPTMutableLineStyle lineStyle];
    tickLineStyle.lineColor = [CPTColor whiteColor];
    tickLineStyle.lineWidth = 2.0f;


    CPTMutableLineStyle *gridLineStyle = [CPTMutableLineStyle lineStyle];
    tickLineStyle.lineColor = [CPTColor blackColor];
    tickLineStyle.lineWidth = 1.0f;


    // 2 - Get axis set
    CPTXYAxisSet *axisSet = (CPTXYAxisSet *) self.hostView.hostedGraph.axisSet;


    // 3 - Configure x-axis
    CPTAxis *x = axisSet.xAxis;
    x.title = @"Flight Time";
    x.titleTextStyle = axisTitleStyle;
    x.titleOffset = 15.0f;
    x.axisLineStyle = axisLineStyle;
    x.labelingPolicy = CPTAxisLabelingPolicyNone;
    x.labelTextStyle = axisTextStyle;
    x.majorTickLineStyle = axisLineStyle;
    x.majorTickLength = 4.0f;
    x.tickDirection = CPTSignNegative;


    NSMutableSet *xLabels = [NSMutableSet new];
    NSMutableSet *xLocations = [NSMutableSet new];

    NSInteger i = 0;

    for (i; i < maxEpoch; i += 600) {

        int hour = i / (68 * 60);
        int min   = i / 60;
        CPTAxisLabel *label = [[CPTAxisLabel alloc] initWithText:[NSString stringWithFormat:@"%02d:%02d", hour, min] textStyle:x.labelTextStyle];

        CGFloat location = i++;
        label.tickLocation = CPTDecimalFromCGFloat(location);
        label.offset = x.majorTickLength;

        if (label) {
        [xLabels addObject:label];
        [xLocations addObject:[NSNumber numberWithInteger:i]];
        }
    }


    x.axisLabels = xLabels;
    x.majorTickLocations = xLocations;
    // 4 - Configure y-axis


    CPTAxis *y = axisSet.yAxis;
    y.title = @"Altitude in Feet";
    y.titleTextStyle = axisTitleStyle;
    y.titleOffset = 20.0f;
    y.axisLineStyle = axisLineStyle;
    y.majorGridLineStyle = gridLineStyle;
    y.labelingPolicy = CPTAxisLabelingPolicyNone;


    y.labelTextStyle = axisTextStyle;
    y.labelOffset = 21.0f;


    y.majorTickLineStyle = axisLineStyle;
    y.majorTickLength = 20.0f;
    y.minorTickLength = 10.0f;

    y.tickDirection = CPTSignNegative;



    // Axis #2

    CPTXYAxis *yRoll = [[CPTXYAxis alloc] init];
    yRoll.title = @"Degrees";

    // Styling
    yRoll.titleTextStyle = axisTitleStyle;
    yRoll.labelTextStyle = axisTextStyle;
    yRoll.axisLineStyle = axisLineStyle;
    yRoll.majorTickLineStyle = axisLineStyle;

    yRoll.plotSpace = rollSpace;
    yRoll.delegate = self;
    yRoll.labelingPolicy = CPTAxisLabelingPolicyNone;

    yRoll.coordinate = CPTCoordinateY;
    yRoll.tickDirection = CPTSignNone;
    yRoll.separateLayers = NO;

    yRoll.tickDirection = CPTSignNegative;

    yRoll.labelOffset = 21.0f;

    yRoll.axisConstraints = [CPTConstraints constraintWithLowerOffset:40.0];

    yRoll.orthogonalCoordinateDecimal = CPTDecimalFromFloat(0.0f);

    NSMutableSet *rollLabels = [NSMutableSet new];
    NSMutableSet *rollLocations = [NSMutableSet new];

    for (int i =0; i <= 40; i+= 5) {

        CPTAxisLabel *label = [[CPTAxisLabel alloc] initWithText:[NSString stringWithFormat:@"%02d˚", (i - 20)] textStyle:yRoll.labelTextStyle];
        CGFloat location = i;
        label.tickLocation = CPTDecimalFromCGFloat(location);
        label.offset = -16.0f;

        if (label) {
            [rollLabels addObject:label];
            [rollLocations addObject:[NSNumber numberWithInteger:i]];
        }
    }

    yRoll.axisLabels = rollLabels;
    yRoll.majorTickLocations = rollLocations;


    NSInteger majorIncrement = 500;
    NSInteger minorIncrement = 100;
    CGFloat yMax = maxAlt;  // should determine dynamically based on max price
    NSMutableSet *yLabels = [NSMutableSet set];
    NSMutableSet *yMajorLocations = [NSMutableSet set];
    NSMutableSet *yMinorLocations = [NSMutableSet set];


    for (NSInteger j = minorIncrement; j <= yMax; j += minorIncrement) {
        NSUInteger mod = j % majorIncrement;
        if (mod == 0) {
            CPTAxisLabel *label = [[CPTAxisLabel alloc] initWithText:[NSString stringWithFormat:@"%i ft", j] textStyle:y.labelTextStyle];

            NSDecimal location = CPTDecimalFromInteger(j);
            label.tickLocation = location;
            label.offset = -y.majorTickLength - y.labelOffset;
            if (label) {
                [yLabels addObject:label];
            }
            [yMajorLocations addObject:[NSDecimalNumber decimalNumberWithDecimal:location]];
        } else {
            [yMinorLocations addObject:[NSDecimalNumber decimalNumberWithDecimal:CPTDecimalFromInteger(j)]];
        }
    }



    // Position the y2 axis
//    y2.axisConstraints = [CPTConstraints constraintWithUpperOffset:40.0];

    axisSet.yAxis.axisConstraints = [CPTConstraints constraintWithUpperOffset:40.0];

    y.axisLabels = yLabels;
    y.majorTickLocations = yMajorLocations;
    y.minorTickLocations = yMinorLocations;

    self.hostView.hostedGraph.axisSet.axes = [NSArray arrayWithObjects:x,y,yRoll,nil];


    // Position floating YAxis
//    y2.axisConstraints = [CPTConstraints constraintWithUpperOffset:150.0];
}

enter image description here

EDIT ::

我尝试添加以下行,但他们什么都没做

y.orthogonalCoordinateDecimal = CPTDecimalFromFloat(0.0f);
x.orthogonalCoordinateDecimal = CPTDecimalFromFloat(0.0f);

我似乎实际上取得了进展:如果我删除

似乎
yAxis2.axisConstraints = [CPTConstraints constraintWithLowerOffset:40.0];

然后我的轴实际上似乎固定在x轴上(尽管它在屏幕外),但现在却是它的开始。

1 个答案:

答案 0 :(得分:1)

解决问题:

我有一些相互矛盾的指令。

为了达到我的需要,我必须使用两个电话:

yAxis2.orthogonalCoordinateDecimal = CPTDecimalFromFloat(0.0f);
y.orthogonalCoordinateDecimal = CPTDecimalFromFloat(maxEpoch); // maximum X value
x.orthogonalCoordinateDecimal = CPTDecimalFromFloat(0.0f);

然后为了确保所有内容都能正确显示,我必须使用填充值:

float padding = 50.0f;
[graph.plotAreaFrame setPaddingLeft:padding];
[graph.plotAreaFrame setPaddingBottom:50.0f];
[graph.plotAreaFrame setPaddingRight:padding];
[graph.plotAreaFrame setPaddingTop:padding];

我必须删除所有搞乱事情的约束:

//    yAxis2.axisConstraints = [CPTConstraints constraintWithLowerOffset:40.0];
//    y.axisConstraints = [CPTConstraints constraintWithUpperOffset:150.0];

enter image description here