iOS簡易柱狀圖(帶動畫)--新手入門篇


叨逼叨

好久沒更新博客了,才幾個月,發生了好多事情,處理了好多事情。不變的是寫代碼依然在繼續。

做點啥子

看看objective-c的書,學着寫了個柱狀圖,只是練習的demo而已,iOS上的圖表控件已經有非常好的解決方案了。

PNChart:https://github.com/kevinzhow/PNChart

這個控件是是挺不錯了,喜歡的朋友可以看看,本文很多地方借鑒了PNChart,就當學習源碼也可以

動手動手

 先上圖先上圖,配色直接用PNChart的了,還蠻喜歡這種配色風格,一直不太喜歡把手機橫過來,所以做了個豎版的,還有很多不完善,學的時間也短,大家別見笑哈~

ps:附帶贈送雙色球號碼一注,大家可以去買,萬一中了呢,由於女朋友老爹熱愛福利事業,就寫一個給他老人家玩玩,具體實現有人需要在貼吧,哈哈,我就是這么騙回復的 

                   

相關知識點

 畢竟是新手入門的東西,列一下相關的知識點,如果后面有時間再一個個展開吧

OC語法方面:

NSArray,NSString,@interface,@property,@nonatomic,@implementation,id,alloc等

iOS方面:

UIView,CAShapeLayer,UIBezierPath,CATextLayer,UIColor,CABasicAnimation

擼代碼

言歸正傳,看看代碼實現部分

首先需要定義LZBar.h,包含了基本的聲明,當然還缺少了X軸的文字說明,大家可以自己擴展下:

 1 #import <UIKit/UIKit.h>
 2 #import <QuartzCore/QuartzCore.h>
 3 
 4 @interface LZBar : UIView{
 5     CAShapeLayer *backgroundLayer; //背景層
 6     UIBezierPath *backgroundPath; //背景賽貝爾路徑
 7     CAShapeLayer *barLayer; //柱狀層
 8     UIBezierPath *barPath; //柱狀賽貝爾路徑
 9     CATextLayer *textLayer; //數值文字顯示層
10     CATextLayer *tittleLayer; //標題文字說明層
11 }
12 
13 @property (nonatomic) UIColor *backgroundColor;//背景色
14 @property (nonatomic) UIColor *barColor;//柱的顏色
15 @property (nonatomic) float barProgress;//柱子長度 0-1之間
16 @property (nonatomic) float barWidth;//柱子寬度
17 @property (nonatomic) NSString *barText;//數值
18 @property (nonatomic) NSString *barTittle;//標題
19 
20 @end
  1 #import "LZBar.h"
  2 
  3 @implementation LZBar
  4 
  5 //初始化
  6 - (id)initWithFrame:(CGRect)frame
  7 {
  8     self = [super initWithFrame:frame];
  9     if (self)
 10     {
 11         backgroundLayer = [CAShapeLayer new];
 12         [self.layer addSublayer:backgroundLayer];
 13         backgroundLayer.strokeColor = LZGrey.CGColor;
 14         backgroundLayer.frame = self.bounds;
 15         
 16         barLayer = [CAShapeLayer new];
 17         [self.layer addSublayer:barLayer];
 18         barLayer.strokeColor = LZGreen.CGColor;
 19         barLayer.lineCap = kCALineCapButt;
 20         barLayer.frame = self.bounds;
 21         
 22         self.barWidth = self.bounds.size.width;
 23     }
 24     return self;
 25 }
 26 
 27 //設置背景
 28 - (void)setBackground
 29 {
 30     backgroundPath = [UIBezierPath bezierPath];
 31     [backgroundPath moveToPoint:CGPointMake(self.bounds.origin.x, self.bounds.origin.y+self.bounds.origin.y+self.bounds.size.height/2)];
 32     [backgroundPath addLineToPoint:CGPointMake(self.bounds.size.width, self.bounds.origin.y+self.bounds.origin.y+self.bounds.size.height/2)];
 33     [backgroundPath setLineWidth:_barWidth];
 34     [backgroundPath setLineCapStyle:kCGLineCapSquare];
 35     backgroundLayer.path = backgroundPath.CGPath;
 36 }
 37 
 38 //設置百分百(顯示動畫)
 39 - (void)setProgress
 40 {
 41     barPath = [UIBezierPath bezierPath];
 42     [barPath moveToPoint:CGPointMake(self.bounds.origin.x, self.bounds.origin.y+self.bounds.origin.y+self.bounds.size.height/2)];
 43     [barPath addLineToPoint:CGPointMake(self.bounds.size.width*_barProgress, self.bounds.origin.y+self.bounds.origin.y+self.bounds.size.height/2)];
 44     [barPath setLineWidth:_barWidth];
 45     [barPath setLineCapStyle:kCGLineCapSquare];
 46     
 47     CABasicAnimation *pathAnimation = [CABasicAnimation animationWithKeyPath:@"strokeEnd"];
 48     pathAnimation.duration = 1.0;
 49     pathAnimation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
 50     pathAnimation.fromValue = @0.0f;
 51     pathAnimation.toValue = @1.0f;
 52     [barLayer addAnimation:pathAnimation forKey:nil];
 53     
 54     barLayer.strokeEnd = 1.0;
 55 
 56     barLayer.path = barPath.CGPath;
 57 }
 58 
 59 //設置柱子的寬度
 60 - (void)setBarWidth:(float)progressWidth
 61 {
 62     _barWidth = progressWidth;
 63     backgroundLayer.lineWidth = _barWidth;
 64     barLayer.lineWidth = _barWidth;
 65     
 66     [self setBackground];
 67     [self setProgress];
 68 }
 69 
 70 //設置背景色
 71 - (void)setBackgroundColor:(UIColor *)backgroundColor
 72 {
 73     backgroundLayer.strokeColor = backgroundColor.CGColor;
 74 }
 75 
 76 //設置柱子顏色
 77 - (void)setBarColor:(UIColor *)barColor
 78 {
 79     barLayer.strokeColor = barColor.CGColor;
 80 }
 81 
 82 //設置柱子進度
 83 - (void)setBarProgress:(float)progress
 84 {
 85     _barProgress = progress;
 86     [self setProgress];
 87 }
 88 
 89 //設置數值
 90 - (void)setBarText:(NSString*)text{
 91     textLayer = [CATextLayer layer];
 92     textLayer.string = text;
 93     textLayer.foregroundColor = [[UIColor blackColor] CGColor];
 94     textLayer.fontSize = 16;
 95     textLayer.alignmentMode = kCAAlignmentLeft;
 96     
 97     textLayer.bounds = barLayer.bounds;
 98     textLayer.position = CGPointMake(self.bounds.size.width*3/2 + 5 , self.bounds.size.height/2);
 99     CABasicAnimation *fade = [self fadeAnimation];
100     [textLayer addAnimation:fade forKey:nil];
101     [self.layer addSublayer:textLayer];
102 }
103 
104 //設置標題
105 - (void)setBarTittle:(NSString*)tittle{
106     tittleLayer = [CATextLayer layer];
107     tittleLayer.string = tittle;
108     tittleLayer.foregroundColor = [[UIColor blackColor] CGColor];
109     tittleLayer.fontSize = 16;
110     tittleLayer.alignmentMode = kCAAlignmentRight;
111 
112     tittleLayer.bounds = barLayer.bounds;
113     tittleLayer.position = CGPointMake(-self.bounds.size.width/2 - 5 , self.bounds.size.height/2);
114     CABasicAnimation *fade = [self fadeAnimation];
115     [tittleLayer addAnimation:fade forKey:nil];
116     [self.layer addSublayer:tittleLayer];
117 }
118 
119 //漸變動畫
120 -(CABasicAnimation*)fadeAnimation
121 {
122     CABasicAnimation* fadeAnimation = [CABasicAnimation animationWithKeyPath:@"opacity"];
123     fadeAnimation.fromValue = [NSNumber numberWithFloat:0.0];
124     fadeAnimation.toValue = [NSNumber numberWithFloat:1.0];
125     fadeAnimation.duration = 2.0;
126     
127     return fadeAnimation;
128 }
129 @end

 有了Bar之后問題就變的簡單的多了,我們可以在構建一個Chart,方便我們直接使用,防止內容過長,看起來累,代碼我就折疊了~

 1 #import <UIKit/UIKit.h>
 2 
 3 @interface LZChart : UIView{
 4     CGSize size;//圖表大小
 5 }
 6 
 7 @property (nonatomic)NSArray *numLabels;//
 8 @property (nonatomic)NSArray *nameLabels;//名稱
 9 @property (nonatomic)float maxNum;//最大值
10 
11 @property (nonatomic)NSInteger barSpacing;//兩根柱狀圖的間距
12 
13 @property (nonatomic) CGFloat chartMarginLeft;
14 @property (nonatomic) CGFloat chartMarginRight;
15 @property (nonatomic) CGFloat chartMarginTop;
16 @property (nonatomic) CGFloat chartMarginBottom;
17 
18 - (void)show;//現實圖標
19 
20 @end
LZChart.h
 1 #import "LZChart.h"
 2 #import "LZBar.h"
 3 
 4 @implementation LZChart
 5 
 6 -(id)initWithFrame:(CGRect)frame{
 7     self = [super initWithFrame:frame];
 8     if (self) {
 9         size = frame.size;
10         _chartMarginTop = 30.0;
11         _chartMarginBottom = 30.0;
12         _chartMarginLeft = 30.0;
13         _chartMarginRight = 30.0;
14         _barSpacing = 20;
15     }
16     return self;
17 }
18 
19 -(void)show{
20     [self setMaxNum];
21     
22     float barCount = [_numLabels count];
23     float barMaxWidth = size.width - _chartMarginLeft - _chartMarginRight ;
24     float barHeight = (size.height - _chartMarginTop - _chartMarginBottom) / barCount - _barSpacing;
25     //防止柱狀圖太粗
26     if(barHeight > 25){
27         barHeight = 25;
28     }
29     float barWidth = 0;
30     
31     for(int i = 0;i<barCount;i++){
32         LZBar *bar = [[LZBar alloc] initWithFrame:CGRectMake(_chartMarginLeft, _chartMarginTop + i*(barHeight + _barSpacing), barMaxWidth, barHeight)];
33         barWidth = [_numLabels[i] floatValue];
34         bar.barProgress = barWidth/_maxNum;
35         bar.barWidth = barHeight;
36         bar.barText = [NSString stringWithFormat:@"%.1f",barWidth];
37         bar.barTittle = [NSString stringWithFormat:@"%@",_nameLabels[i]];
38         [self addSubview:bar];
39     }
40 }
41 
42 -(void)setMaxNum{
43     _maxNum = 0;
44     for (id num in _numLabels) {
45         if ([num floatValue] > _maxNum) {
46             _maxNum = [num floatValue] ;
47         }
48     }
49 }
50 @end
LZChart.m

然后在需要添加的UIView直接調用,是不是很容易呢

1     LZChart *chart = [[LZChart alloc] initWithFrame:CGRectMake(30, 100, 300, 300)];
2     chart.numLabels = [NSArray arrayWithObjects:@10,@2,@3,@4, nil];
3     chart.nameLabels = [NSArray arrayWithObjects:@"第一",@"第二",@"第三",@"第四", nil];
4     [self.view addSubview:chart];
5     [chart show];

最終效果:

 

希望大家喜歡~

博客地址: http://www.cnblogs.com/nightcat/
博客版權: 本文以學習、研究和分享為主,歡迎轉載,但必須在文章頁面明顯位置給出原文連接。
如文中有不妥或者錯誤的地方還望高手的指出,以免誤人子弟。如果覺得本文對您有所幫助請【推薦】一下!如果你有更好的建議,不妨留言一起討論,共同進步! 再次感謝您耐心的讀完本篇文章。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM