如何使用核心图库开发的饼图动画?

时间:2011-03-09 05:27:33

标签: iphone core-plot

在iPhone应用程序Roambi中,显示的饼图可以动画显示为与用户一起旋转,就好像旋转光盘一样。我们可以坚持并做很多事情。

有人提到Roambi应用程序是使用核心图库开发的:

What library use Roambi app iPhone to draw chart?

如何操作使用Core plot开发的饼图?

3 个答案:

答案 0 :(得分:6)

快速浏览一下Core Plot源代码,可以看出CPPieChart的继承是这样的:

  

CPPieChartCPPlotCPAnnotationHostLayerCPLayerCALayer

所以你可以看到,CPPieChart最后只是一个重度子类CALayer。我可能在这里完全不正确,但没有任何迹象表明这不能像任何其他CALayer一样动画。请尝试以下代码将图层旋转360度:

CABasicAnimation *rotation = [CABasicAnimation animationWithKeyPath:@"transform"];
CATransform3D transform = CATransform3DMakeRotation(DegreesToRadians(360), 0, 0, 1);
rotation.toValue = [NSValue valueWithCATransform3D:transform];
rotation.duration = 10.0f;
[pieChart addAnimation:rotation forKey:@"rotation"];

如果你可以使这个工作,那么只需要从加速度计读取值并将它们转换为旋转角度。

答案 1 :(得分:5)

对于简单的饼图,即使使用上述动画,Core Plot也不是必需的。如果您只想要Core Plot解决方案,请忽略此答案。但是,这是一个简单的解决方案,不需要外部包甚至任何框架。

创建一个名为PieChartView的UIView。在PieChartView.h中:

#import <UIKit/UIKit.h>

@interface PieChartView : UIView {
    float zeroAngle;
    NSMutableArray *valueArray;
    NSMutableArray *colorArray;
}
@property (nonatomic) float zeroAngle;
@property (nonatomic, retain) NSMutableArray *valueArray;
@property (nonatomic, retain) NSMutableArray *colorArray;
@end

然后在PieChartView.m中实现:

#import "PieChartView.h"

@implementation PieChartView
@synthesize zeroAngle;
@synthesize valueArray, colorArray;

- (id)initWithFrame:(CGRect)frame {
    if ((self = [super initWithFrame:frame])) {
    }
    return self;
}


- (void)drawRect:(CGRect)rect {
    CGContextRef context = UIGraphicsGetCurrentContext();

    // DETERMINE NUMBER OF WEDGES OF PIE
    int wedges = [valueArray count];
    if (wedges > [colorArray count]) {
        NSLog(@"INSUFFICENT COLORS FOR PIE CHART: Please add %d additional colors.",wedges-[colorArray count]);
        for (int i=[colorArray count] ; i<wedges ; ++i) {
            [colorArray addObject:[UIColor whiteColor]];
        }
    }

    // DETERMINE TOTAL VOLUME OF PIE
    float sum = 0.0;
    for (int i=0; i<wedges ; ++i) {
        sum += [[valueArray objectAtIndex:i] floatValue];
    }
    float frac = 2.0*M_PI/sum;

    // DETERMINE CENTER AND MAXIMUM RADIUS OF INSCRIBED CIRCLE
    int center_x = rect.size.width/2.0;
    int center_y = rect.size.height/2.0;
    int radius = (center_x > center_y ? center_x : center_y);

    // DRAW WEDGES CLOCKWISE FROM POSITIVE X-AXIS
    float startAngle=zeroAngle;
    float endAngle=zeroAngle;
    for (int i=0; i<wedges; ++i) {
        startAngle = endAngle;
        endAngle += [[valueArray objectAtIndex:i] floatValue]*frac;
        [[colorArray objectAtIndex:i] setFill];
        CGContextMoveToPoint(context, center_x, center_y);
        CGContextAddArc(context, center_x, center_y, radius, startAngle, endAngle, 0);
        CGContextClosePath(context);
        CGContextFillPath(context);
    }
}

- (void)dealloc {
    [valueArray release];
    [colorArray release];
    [super dealloc];
}
@end

现在您可以以任何方式将float zeroAngle绑定到加速度计,以获得所需的动画。

答案 2 :(得分:3)

我不知道CorePlot,在不久的将来它可能对我有用,所以我只是看看它。 CorePlot很有趣,并且活跃

关于使用CorePlot的动画:

  1. CorePlot文档提及Animation system但尚未实施 ...
  2. 即使基于Core Animation,也不表示CorePlot图表很容易设置动画。
  3. Interesting reading on the topic on google groups.

    所以这是您的选择(按我的偏好顺序):

    1. 寻找另一个处理动画片的绘图库,例如Roambi。
    2. 基于CorePlot实现您的动画(意味着对此框架和Core Animation的良好理解)
    3. 自己做所有事情,取决于你想要什么,再次,可能并不那么难......但需要Core Animation技能。
    4. 我怀疑Roambi使用的是CorePlot,但如果他们这样做,他们会将其作为基础,使用自定义内容代码中的 TONS ...