iOS時間軸的實現
最近項目需求,恰好要做一個時間軸,而iOS這方面時間軸的例子也比較少,我就把自己所做的例子和思路共享出來給大家,共同學習。
時間軸的具體實現效果如圖1所示:
圖1
第一步:看到這個圖,我們想到的第一反應就是使用tableView或者CollectionView來完成,那么我這里使用的是tableView。首先,創建一個Single View Application項目,在Main.Storyboard里面拖入一個TableView(如圖2所示),這里別忘記了把TableView的delegate指向ViewController。
圖 2
第二步:TableView完成了,接下來就是如何自定義TableViewCell了。在項目中new file選擇Cocoa Touch Class,然后選擇繼承自TableViewCell,然后勾選XIB file選項,命名為“TimeCourseTableViewCell”,點擊創建,完成后如圖3所示:
圖 3
接下來,就是為這個xib文件布局,通過圖4圈出來的,我們可以找出一個cell里面具有什么控件。
圖 4
根據這個,我們布局出來的如圖5所示,主要就是Label和View來完成布局。
圖 5
其實這里肯定會有人有疑問:
1.為什么下面那個不直接用一個Button就好了呢,還要用一個View里面嵌套一個Label呢?
2.為什么"內容"的那個label還要添加一個父控件View呢?
其實,剛開始的時候,我確實也是使用簡單的一個Button和一個Label以為就可以了。后來發現,莫名的出現明明設置了buttom和label的Frame,修改了Origin,卻總是出現亂七八糟的位置,后來通過view嵌套在里面,改變view的位置,就完全可以實現了。這個BUG本人也不清楚,望知情人告知,謝謝。
第三步:接下來,看xib里面的TimeCourseTableViewCell.h文件里的代碼:
#import <UIKit/UIKit.h> @interface TimeCourseTableViewCell : UITableViewCell @property (weak, nonatomic) IBOutlet UILabel *lbDate; //日期 @property (weak, nonatomic) IBOutlet UILabel *lbTime; //時間 @property (weak, nonatomic) IBOutlet UIView *infoView; //白色底的那個View @property (weak, nonatomic) IBOutlet UILabel *lbInfoTitle; //通知標題 @property (weak, nonatomic) IBOutlet UILabel *lbInfoContent; //通知內容 @property (weak, nonatomic) IBOutlet UIView *infoContentView; //通知內容的父View @property (weak, nonatomic) IBOutlet UILabel *lbSegment; //豎著的灰色分割線 @property (weak, nonatomic) IBOutlet UIView *receiveView; //深紅色的View @property (weak, nonatomic) IBOutlet UILabel *lbReceive; //輕觸收到通知 - (CGFloat)setCellHeight:(NSString *)strInfo isSameDay:(BOOL)isSame; - (void)setRidues; - (void)setClick; - (void)setNotClick; @end
TimeCourseTableViewCell.m文件里的代碼:
#import "TimeCourseTableViewCell.h"
@implementation TimeCourseTableViewCell
@synthesize lbDate;
@synthesize lbTime;
@synthesize infoView;
@synthesize lbInfoTitle;
@synthesize lbInfoContent;
@synthesize lbReceive;
@synthesize receiveView;
@synthesize lbSegment;
@synthesize infoContentView;
- (void)awakeFromNib {
// Initialization code
}
/*去掉上面的日期*/
- (void)deleteDate{
lbDate.hidden = YES;
CGRect timeTemp = lbTime.frame;
timeTemp.origin = CGPointMake(timeTemp.origin.x, 8);
lbTime.frame = timeTemp;
CGRect infoViewTemp = infoView.frame;
infoViewTemp.origin = CGPointMake(infoViewTemp.origin.x, 8);
infoView.frame = infoViewTemp;
}
/*設置顯示的文本高度,以確定整個tableViewCell的高度,最后返回cell高度*/
- (CGFloat)setCellHeight:(NSString *)strInfo isSameDay:(BOOL)isSame{
/*如果是同一天 則去掉上面的日期*/
if (isSame) {
[self deleteDate];
}
[lbInfoContent setNumberOfLines:0]; //0行,則表示根據文本長度,自動增加行數
NSString *labelText = strInfo;
NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc] initWithString:labelText];
NSMutableParagraphStyle *paragraphStyle = [[NSMutableParagraphStyle alloc] init];
[paragraphStyle setLineSpacing:5.0f];//調整行間距
[attributedString addAttribute:NSParagraphStyleAttributeName value:paragraphStyle range:NSMakeRange(0, [labelText length])];
lbInfoContent.attributedText = attributedString;
[lbInfoContent sizeToFit]; //填充
//NSLog(@"%@",lbInfoContent);
CGRect infoContentViewTemp = infoContentView.frame;
infoContentViewTemp.size = CGSizeMake(212, lbInfoContent.frame.size.height);
infoContentView.frame = infoContentViewTemp;
/*設置手勢點擊位置*/
CGRect btnTemp = receiveView.frame;
btnTemp.origin = CGPointMake(0, infoContentView.frame.origin.y + infoContentView.frame.size.height + 8 );
receiveView.frame = btnTemp;
//NSLog(@"%@",receiveView);
/*設置整個infoView高度*/
CGRect viewTemp = infoView.frame;
viewTemp.size = CGSizeMake(viewTemp.size.width, receiveView.frame.origin.y + receiveView.frame.size.height);
infoView.frame = viewTemp;
//NSLog(@"%@",infoView);
lbSegment.frame = CGRectMake(lbSegment.frame.origin.x, 0, 3, infoView.frame.origin.y + infoView.frame.size.height + 8);
NSLog(@"HEight %f",infoView.frame.origin.y + infoView.frame.size.height + 8);
return infoView.frame.origin.y + infoView.frame.size.height + 8;
}
/*設置圓形*/
- (void)setRidues{
lbTime.layer.cornerRadius = lbTime.frame.size.width / 2;
[lbTime.layer setMasksToBounds:YES];
}
/*設置點擊閱讀樣式*/
- (void)setClick{
CGFloat R = (CGFloat) 128/255.0;
CGFloat G = (CGFloat) 128/255.0;
CGFloat B = (CGFloat) 128/255.0;
CGFloat alpha = (CGFloat) 1.0;
UIColor *ColorRGB = [ UIColor colorWithRed: R
green: G
blue: B
alpha: alpha
];
receiveView.backgroundColor = ColorRGB;
lbReceive.text = @"我已收到通知";
}
/*設置未點擊閱讀樣式*/
- (void)setNotClick{
CGFloat R = (CGFloat) 255/255.0;
CGFloat G = (CGFloat) 83/255.0;
CGFloat B = (CGFloat) 83/255.0;
CGFloat alpha = (CGFloat) 1.0;
UIColor *ColorRGB = [ UIColor colorWithRed: R
green: G
blue: B
alpha: alpha
];
receiveView.backgroundColor = ColorRGB;
lbReceive.text = @"輕觸收到通知";
}
- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
[super setSelected:selected animated:animated];
// Configure the view for the selected state
}
@end接下來,看ViewController.m文件里的代碼:
#import "ViewController.h"
#import "TimeCourseTableViewCell.h"
@interface ViewController ()
@property (weak, nonatomic) IBOutlet UITableView *messageTableView;
@property int messageSum; //cell個數
@property NSArray *infoArray; //保存信息內容
@property NSMutableArray *clickArray; //記錄是否已經閱讀了信息 1未接收 0接收
@end
@implementation ViewController
@synthesize messageSum;
- (void)viewDidLoad {
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
/*tableView*/
[self setTableViewStyle];
messageSum = 10;
self.infoArray = [[NSArray alloc] initWithObjects:@"老夫聊發少年狂,治腎虧,不含糖。",
@"錦帽貂裘,千騎用康王。",
@"",
@"為報傾城隨太守,三百年,九芝堂。酒酣胸膽尚開張,西瓜霜,喜之郎。",
@"持節云中,三金葡萄糖。會挽雕弓如滿月,西北望 ,阿迪王。",
@"十年生死兩茫茫,恒源祥,羊羊羊。",
@"千里孤墳,洗衣用奇強。",
@"縱使相逢應不識,補維C,施爾康。",
@"夜來幽夢忽還鄉,學外語,新東方。相顧無言,洗洗更健康。得年年斷腸處,找工作,富士康",
@"啦啦啦",nil];
self.clickArray = [[NSMutableArray alloc] initWithObjects:@"1",
@"1",
@"1",
@"1",
@"1",
@"1",
@"1",
@"1",
@"1",
@"1",nil];
}
#pragma mark - 設置messageTableView的背景色和去掉分割線
- (void)setTableViewStyle{
self.messageTableView.separatorStyle = UITableViewCellSeparatorStyleNone; //去掉tabelView分割線
CGFloat R = (CGFloat) 237/255.0;
CGFloat G = (CGFloat) 237/255.0;
CGFloat B = (CGFloat) 237/255.0;
CGFloat alpha = (CGFloat) 1.0;
UIColor *ColorRGB = [ UIColor colorWithRed: R
green: G
blue: B
alpha: alpha
];
[self.messageTableView setBackgroundColor:ColorRGB];
}
#pragma mark - TabelView數據源協議
//該方法指定了表格視圖的行數
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section{
return messageSum;
}
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath{
//按時間分組,假設這里[0,2],[3,5],[6,9]是同一天
TimeCourseTableViewCell *nib = [[[NSBundle mainBundle] loadNibNamed:@"TimeCourseTableViewCell" owner:self options:nil] lastObject];
if ([indexPath row] == 0) {
NSLog(@"0");
return [nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:NO];
}
else if ([indexPath row]<3) {
NSLog(@"0 - 3");
return [nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:YES];
}else if ([indexPath row] == 3){
NSLog(@"3");
return [nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:NO];
}else if ([indexPath row] < 6){
NSLog(@"3 - 6");
NSLog(@"%f",[nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:YES]);
return [nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:YES];
}else if ([indexPath row] == 6){
NSLog(@"6");
NSLog(@"%f",[nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:NO]);
return [nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:NO];
}else if ([indexPath row] > 6){
NSLog(@"6- 9");
NSLog(@"%f",[nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:YES]);
return [nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:YES];
}else
return 145;
}
//該方法返回單元格對象,有多少行表格,則調用多少次
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
static NSString *simpleIdentify = @"TimeCourse";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:simpleIdentify];
TimeCourseTableViewCell *nib = [[[NSBundle mainBundle] loadNibNamed:@"TimeCourseTableViewCell" owner:self options:nil] lastObject];
[nib setTag:[indexPath row]];
if ([[self.clickArray objectAtIndex:[indexPath row]] isEqualToString:@"1"]) {
[nib setNotClick];
}else
[nib setClick];
[nib setRidues];
UITapGestureRecognizer *Tap = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(tapGesture:)];
nib.receiveView.userInteractionEnabled = YES;
[nib.receiveView addGestureRecognizer:Tap];
if ([indexPath row] == 0) {
[nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:NO];
}
else if ([indexPath row]<3) {
[nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:YES];
}else if ([indexPath row] == 3){
[nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:NO];
}else if ([indexPath row] < 6){
[nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:YES];
}else if ([indexPath row] == 6){
[nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:NO];
}else if ([indexPath row] > 6){
[nib setCellHeight:[self.infoArray objectAtIndex:[indexPath row]] isSameDay:YES];
}
cell = nib;
cell.selectionStyle = UITableViewCellSelectionStyleNone; //去掉提供的選中無顏色
return cell;
}
#pragma mark - TabelView代理協議
//選中事件
-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
NSLog(@"44");
}
- (void)tapGesture:(UITapGestureRecognizer *)sender{
NSLog(@"接收通知");
UIView *view = sender.self.view;
TimeCourseTableViewCell *cell = (TimeCourseTableViewCell *)view.superview.superview.superview;
UILabel *lb = view.subviews[0];
NSString *str = @"輕觸收到通知";
if ([lb.text isEqualToString:str]) {
[cell setClick];
[self.clickArray setObject:@"0" atIndexedSubscript:cell.tag];
}
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
@end那么,運行之后,效果如圖6所示:
圖 6
改一下顏色,完成如下:
至此,整個時間軸完成。
思路大概如下:
1.根據時間分組:判斷是不是同一天,如果是則把上面的日期隱藏,整體布局往上移動。
2.獲取點擊的是哪個cell:通過給cell添加tag,那么我單擊手勢時候,便可以獲取出cell,然后更改這個cell的樣式
可能寫的不是很明白,大家可以認真看一下代碼。
源碼地址免費下載:http://download.csdn.net/detail/junlinfushi/8345531
來自:http://www.cnblogs.com/linjianxiang/p/4213926.html