1 创建表格视图UITableView的时候一并指定表格的样式:
2 UITableView* tableView = [[UITableView alloc] initWithFrame:self.view.bounds style:UITableViewStylePlain];
3
4 // 设置分割线的颜色
5
6 tableView.separatorColor = [UIColor blueColor];
7
8 // 设置分割线的样式(UITableViewCellSeparatorStyleNone:会将分割线隐藏)
9
10 tableView.separatorStyle = UITableViewCellSeparatorStyleNone;
11
12 // 设置分割线到屏幕宽度(ios7.0之前没有这个方法,所以应该先判断是否实现这个方法)
13
14 if ([tableView respondsToSelector:@selector(separatorInset)]) {
15 tableView.separatorInset = UIEdgeInsetsZero;
16 }
17
18
19
20 ios8之后设置tableCell的分割线到屏幕宽度的方法
21 -(void)setSeparatorInsetMarginZero
22
23 {
24 self.separatorInset = UIEdgeInsetsZero;
25
26 if ([self respondsToSelector:@selector(setLayoutMargins:)]) {
27
28 self.layoutMargins = UIEdgeInsetsZero;
29 }
30
31 if ([self respondsToSelector:@selector(setPreservesSuperviewLayoutMargins:)]) {
32
33 self.preservesSuperviewLayoutMargins = NO;
34
35 }
36
37 }
38
39
40
41
42 //设置tableView可以在编辑的状态下可以选中
43 [tableView setAllowSelectionDuringEditing:YES];
44 //下面的方法可以使tableView直接显示到最下面
45 NSIndexPath *index = [NSIndexPath indexPathForRow:数组(里面存储的是数组元素).count-1 inSection:第几个分区];
46
47 [tableView scrollToRowAtIndexPath:index atScrollPosition:UITableViewScrollPositionBottom animated:YES];
48
49
50 设置头视图:
51
52 [tableView.tableHeaderView addSubView:视图对象];
53
54 设置tableView的背景视图:
55
56 tableView.backgroundView = 视图对象;
57
58 设置tableView被选中的背景视图:
59
60 tableView.selectedBackgroundView = 视图对象;
61
62
63 自定义tableView的时候,添加到tableView的视图上应用这个方法:
64
65 cell上专门用来放置控件的view
66
67 [tableView.contentView addSubview:视图对象];
68
69
70 设置表格视图的代理:
71
72 注意:应在头文件中添加<UITableViewDelegate,UITableViewDataSource>
73
74 tableView.delagate = self;
75
76 将self视图控制器设置为tableView的数据源
77
78 tableView.dataSource = self;
79
80 tableView的刷新方法
81
82 [tableView reloadData];
83
84
85 #pragma mark ————以下是代理实现的方法-------
86
87
88 //指定cell的行高,默认是44(一般都写)
89
90 -(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
91
92 { return ?;}
93
94
95 //点击某一行触发这个选择方法(一般都写)
96
97 -(void) tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{
98
99 ……..(自己要写的代码)
100
101 //会经常做这样的操作(目的是点进去之后使得选择的这一行不被选择)
102 [tableView tableView:tableView didDeselectRowAtIndexPath:indexPath];
103 }
104
105
106 //反选一个cell的时候调用:取消之前选择的cell
107 //通俗解释:点击另外一行的时候,会先调用之前选择的那一行并取消选择
108 -(void)tableView:(UITableView *)tableView didDeselectRowAtIndexPath:(NSIndexPath *)indexPath{}
109
110 //返回表中有多少个分区
111 -(NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
112 {
113 return 数组(里面存储的是数组元素).count;
114 }
115
116
117 //返回某个分区中的行数(必须写)
118
119 -(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
120 {
121 return [[数组(里面存储的是数组元素) objectAtIndex:section] count];
122 }
123
124
125
126 /******************************
127
128 重中之重
129
130 ******************************/
131
132 /*
133
134 复用机制
135
136 1.并不是创建了很多个cell的对象,而是使用复用机制,将滑出屏幕的cell放到可重用队列中,供后面使用
137
138 2.一个新的cell出现的时候,不是直接创建,再是从可重用队列中去取,如果取不出则创建
139
140 3.最多创建的数量是满屏的情况下的cell数量+1
141
142 4.利用机制可以用在将来的软件设计上
143
144 */
145
146 //indexPath:包含两个值:
147
148 //section:第几个分区
149
150 //row:第几行
151
152 //此方法是每一行在出现屏幕的时候调用
153
154 //返回每一个显示cell(必须写)
155
156 -(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
157
158 {
159
160 // 定义一个静态字符串变量,作用:用来当做标识
161
162 //注意:不同的布局cell,可重用标识要不同
163
164 static NSString * cellId = @"cellId";
165 // 从当前的tableView的可重用队列中寻找cellId标识的cell,并赋值得到一个cell
166
167 UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellId];
168
169 if (!cell) {
170 // 如果这个cell不存在,则创建一个(记得用autorelease让它自动释放)
171
172 cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:cellId] autorelease];
173
174 }
175 //若有分区,则应获得对应分区的数组
176
177 NSMutableArray* arr = [数组(里面存储的是数组元素) objectAtIndex:indexPath.section];
178
179 // 设置cell的主要内容
180 cell.textLabel.text = [arr objectAtIndex:indexPath.row];
181 // 设置cell的副标题的内容
182 cell.detailTextLabel.text =@“……”;
183 //设置cell右侧的指示图标
184 cell.accessoryType = ?;
185 // 设置tableViewCell的标题图片,这个图片会自动压缩,如果图片过大会压缩后面的文字
186
187 cell.imageView.image = [UIImage imageNamed:@“?"];
188 return cell;
189
190 }
191
192 //点击了cell右侧的指示图标就会调用该方法
193
194 -(void) tableView:(UITableView *)tableView accessoryButtonTappedForRowWithIndexPath:(NSIndexPath *)indexPath{}
195
196
197 //分区的页眉
198
199 -(NSString*)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section
200 {
201 return 要设置的分区页眉;
202 }
203
204
205 //分区的页脚
206
207 -(NSString *)tableView:(UITableView *)tableView titleForFooterInSection:(NSInteger)section
208 {
209 return 要设置的分区页脚;
210 }
211
212
213
214 //配合使用系统自带的编辑按钮
215
216 self.navigationItem.leftBarButtonItem = self.editButtonItem;
217
218 //编辑按钮在改变状态的时候,会调用这个方法
219
220 -(void) setEditing:(BOOL)editing animated:(BOOL)animated
221
222 {
223
224 // 需要先调用父类的方法
225
226 [super setEditing:editing animated:animated];
227
228 // 让table变成编辑状态
229
230 [tableView setEditing:editing];
231
232 }
233
234 -(UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath
235
236 {
237 //判断indexPath的两个属性值,然后根据自己的需要对其进行删除或者增加
238
239 //注意:只返回一种就仅仅只是删除或者增加 若返回两种(中间加个 | —> 或)则变成多行编辑模式
240
241 return UITableViewCellEditingStyleDelete or UITableViewCellEditingStyleInsert;
242
243 }
244
245
246 //以下三个是对是否可以编辑操作已经如何操作的实现方法(增加和删除两种操作)
247
248
249 //是否可以编辑cell
250
251 -(BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath
252 {
253 return YES;
254 }
255
256
257 // 实现编辑(删除,增加)的方法
258
259 -(void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
260
261 {
262
263 //先判断编辑的风格是删除还是增加
264
265
266 //若是删除(UITableViewCellEditingStyleDelete)的话应分以下两步:
267
268 //A:删除的时候,先删除数据源中的数据
269
270 [数组(里面存储的是数组元素) objectAtIndex:indexPath.section] removeObjectAtIndex:indexPath.row];
271
272 //B:然后删除table中的行(找到indexPath所在的行,以数组形式返回)
273
274 [table deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade];
275
276
277
278
279 //若是增加(UITableViewCellEditingStyleInsert)的话应分以下两步:
280
281 //A:往数组中增加数据
282
283 [[数组(里面存储的是数组元素) objectAtIndex:indexPath.section] insertObject:增加的对象 atIndex:indexPath.row];
284
285 //B:刷新当前的table
286
287 [tableView reloadData];
288
289 }
290
291
292 //设置cell往左滑动的时候出现的删除键里面的文字
293
294 -(NSString*)tableView:(UITableView *)tableView titleForDeleteConfirmationButtonForRowAtIndexPath:(NSIndexPath *)indexPath
295
296 {
297
298 return @"删除";
299
300 }
301
302
303 //往table插入某行
304
305 - (void)insertRowsAtIndexPaths:(NSArray *)indexPaths withRowAnimation:(UITableViewRowAnimation)animation;
306
307 //替换table中的某行
308
309 - (void)reloadRowsAtIndexPaths:(NSArray *)indexPaths withRowAnimation:(UITableViewRowAnimation)animation;
310
311 //移动table中的某行到另一行
312
313 - (void)moveRowAtIndexPath:(NSIndexPath *)indexPath toIndexPath:(NSIndexPath *)newIndexPath;
314
315 实现索引(主要新增内容):
316
317 成员属性:
318
319 定义搜索框对象:
320
321 UISearchBar *_searchBar;
322
323 定义搜索展示控制器对象:
324
325 UISearchDisplayController *_displayController;
326
327 定义搜索出来显示在tableView的数据源数组:
328
329 NSMutableArray *_searchResultArr;
330
331
332 初始化数组
333
334 _searchResultArr = [[NSMutableArray alloc] init];
335
336 初始化搜索框(使用默认高度)
337
338 _searchBar = [[UISearchBar alloc] initWithFrame:CGRectMake(0, 0, 0, 44)]
339
340 再加到tableView的头视图上(即最上面):
341
342 _tableView.tableHeaderView = _searchBar;
343
344 // _displayController这里面自带了一个tableView,现在在这个视图控制器里面有两个tableView,而这两个tableView的代理和数据源都指向self
345
346 // 这里面所有的代理方法都需要对这两个tableView进行分别处理
347
348 _displayController = [[UISearchDisplayController alloc] initWithSearchBar:_searchBar contentsController:self];
349
350 // 设置自带的tableView的代理和数据源
351
352 _displayController.searchResultsDelegate = self;
353
354 _displayController.searchResultsDataSource = self;
355
356
357 新增的方法:
358
359
360 //创建索引
361
362 //返回是是一个包含字符串的数组
363
364 //默认情况下,点击索引中的某一项会跳转到对应下标的分区
365
366 -(NSArray *)sectionIndexTitlesForTableView:(UITableView *)tableView{}
367
368 //返回一个数字,对应的是tableView中的分区的下标
369
370 //index对应的是索引中的下标
371
372 -(NSInteger)tableView:(UITableView *)tableView sectionForSectionIndexTitle:(NSString *)title atIndex:(NSInteger)index{}
373
374
375
376 搜索主要实现应在这里实现(注意:所有代理方法都要判断是否是原来的表格视图在调用):
377
378 -(NSInteger) tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
379
380 {
381
382 // 开始搜索数据的收集之前,需要先清空搜索结果数组中的所有数据
383
384 [_searchResultArr removeAllObjects];
385
386 // 在这里面对搜索结果的数据进行收集
387
388 // 判断是搜索控制器的tableView调用了这个方法(即不是原来的表格视图在调用这个方法)
389
390 if (tableView != _tableView) {
391
392 //获得搜索框中的数据
393
394 NSString *str = _searchBar.text;
395
396 //遍历原来的表格视图里的分区数组
397
398 for (NSArray *arr in _dataArr) {
399
400 //遍历得到的分区里面的数据
401
402 for (NSString *dataStr in arr) {
403
404 // 如果数据与搜索框中的数据匹配,则加到_searchResultArr数组中
405
406 NSRange rang = [dataStr rangeOfString:str];
407
408 // 判断搜索出来的数据是否存在(NSNotFound = NSIntegerMax —>>#define NSIntegerMax LONG_MAX)
409
410 if (rang.location != NSNotFound) {
411
412 [_searchResultArr addObject:dataStr];
413
414 }
415
416 }
417
418 }
419
420 }
421
422 return tableView == _tableView ? [[_dataArr objectAtIndex:section]count]:_searchResultArr.count;
423
424 }
425
426 Xib定制cell
427
428 可重用标识符,需要和xib文件中设置一样
429
430 static NSString *strId = @"strID";
431
432 JTestTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:strId];
433
434 if (!cell)
435
436 {
437 // Xib定制的cell
438
439 // 参数一:要和xib文件的名字一样
440
441 // xib用于cell的定制和将来改动很少的视图
442
443 //参数三返回的是xib里面cell的元素
444
445 cell = [[[NSBundle mainBundle] loadNibNamed:@"TestTableViewCell" owner:self options:nil] objectAtIndex:0];
446
447 }
448
449
450
451 itoast效果主要实现下面三个方法:
452
453 _tableView是全局变量
454
455 -(void)scrollViewWillBeginDecelerating:(UIScrollView *)scrollView
456
457 {
458
459 _labelView.hidden = NO;
460
461 }
462
463
464 -(void)scrollViewDidScroll:(UIScrollView *)scrollView
465
466 {
467
468 // 拿到_labelView的中心的的坐标,相对于它所在的View
469
470 CGPoint p = [_tableView convertPoint:_labelView.center fromView:self.view];
471
472 // 获取当_tableView 的titleForHeaderInSection的位置经过p这个点的时候的值
473
474 NSIndexPath *index = [_tableView indexPathForRowAtPoint:p];
475
476
477 _labelView.text = [NSString stringWithFormat:@"%c",index.section+'A'];
478
479 }
480
481
482 -(void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView
483
484 {
485
486 _labelView.hidden = YES;
487
488 }
489
490
491 懒加载实现:
492
493 //慢慢滑动或者快速滑动的时候,手指离开屏幕的瞬间调用的函数
494
495 -(void) scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate
496
497 {
498
499 if(decelerate == YES)
500
501 {
502
503 //说明手离开屏幕 但是tableView还在减速 说明这是快速滑动
504
505 }else
506
507 {
508
509 //慢慢滑动 应该加载图片
510
511 UITableView *tableView = (UITableView *)scrollView;
512
513 [self loadVisibleImages:tableView];//加载图片的函数
514
515 }
516
517 }
518
519
520
521 //快速滑动 手停下来
522
523 -(void) scrollViewDidEndDecelerating:(UIScrollView *)scrollView
524
525 {
526
527 [self loadVisibleImages:(UITableView *)scrollView];
528
529 }
530
531
532 -(void) loadVisibleImages:(UITableView *)tableView
533
534 {
535
536 //首先看屏幕到底有哪些cell的indexPath
537
538 NSArray *arr = [tableView visibleCells];
539
540 //获取tableView当前可见的cell
541
542 for (UITableViewCell *cell in arr)
543
544 {
545
546 NSIndexPath *indexPath = [tableView indexPathForCell:cell];
547
548 //取得cell所在的indexPath
549
550 //启动下载
551
552 }
553
554 }
555
556 实现索引功能(实现的文件全部内容):
557 #import "JRootViewController.h"
558
559
560 @interfaceJRootViewController ()
561
562 {
563
564 UITableView *_tableView;
565
566 NSMutableArray *_dataArr;
567
568 NSMutableArray *_indexArr;
569
570 // 搜索框
571
572 UISearchBar *_searchBar;
573
574 // 搜索展示控制器
575
576 UISearchDisplayController *_displayController;
577
578
579
580 NSMutableArray *_searchResultArr;
581
582 }
583
584 @end
585
586
587 @implementation JRootViewController
588
589
590 - (void)viewDidLoad
591
592 {
593
594 [superviewDidLoad];
595
596 self.title = @"通讯录索引";
597
598 [selfparpareData];
599
600 [selfuiConfig];
601 }
602
603 -(void) parpareData
604
605 {
606 _dataArr = [[NSMutableArrayalloc] init];
607
608 _indexArr = [[NSMutableArrayalloc] init];
609
610 _searchResultArr = [[NSMutableArrayalloc] init];
611
612 for (int i = 'A'; i<='Z'; i++)
613
614 {
615
616
617
618 if (i == 'I') {
619
620 continue;
621
622 }
623
624 [_indexArraddObject:[NSStringstringWithFormat:@"%c",i]];
625
626 NSMutableArray* arr = [[NSMutableArrayalloc] init];
627
628
629
630 for (int j = 0; j<10; j++)
631
632 {
633
634 NSString* str = [NSStringstringWithFormat:@"第%c分区第%d行",i,j];
635
636 [arr addObject:str ];
637
638 }
639
640 [_dataArraddObject:arr];
641
642 [arr release];
643
644 }
645
646 }
647
648
649 -(void) uiConfig
650
651 {
652
653 _tableView = [[UITableViewalloc] initWithFrame:self.view.boundsstyle:UITableViewStylePlain];
654
655 [self.viewaddSubview:_tableView];
656
657 [_tableViewrelease];
658
659 _tableView.delegate = self;
660
661 _tableView.dataSource = self;
662
663 _searchBar = [[UISearchBaralloc] initWithFrame:CGRectMake(0, 0, 0, 44)];
664
665 _tableView.tableHeaderView = _searchBar;
666
667 [_searchBarrelease];
668
669 // _displayController这里面自带了一个tableView,现在在这个视图控制器里面有两个tableView,而这两个tableView的代理和数据源都指向self
670
671 // 这里面所有的代理方法都需要对这两个tableView进行分别处理
672
673 _displayController = [[UISearchDisplayControlleralloc] initWithSearchBar:_searchBarcontentsController:self];
674
675 // 设置自带的tableView的代理和数据源
676
677 _displayController.searchResultsDelegate = self;
678
679 _displayController.searchResultsDataSource = self;
680
681 }
682
683 #pragma mark -------代理实现---------
684
685 -(NSInteger) numberOfSectionsInTableView:(UITableView *)tableView
686
687 {
688
689 NSLog(@"tableView:%@",tableView);
690
691 return tableView == _tableView?_dataArr.count:1;
692
693 }
694
695 -(NSInteger) tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
696
697 {
698
699 // 开始搜索数据的收集之前,需要先清空结果数组中的所有数据
700
701 [_searchResultArrremoveAllObjects];
702
703 // 在这里面对搜索结果的数据进行收集
704
705 // 是搜索控制器的tableView调用了这个方法
706
707 if (tableView != _tableView) {
708
709 NSString *str = _searchBar.text;
710
711 for (NSArray *arr in_dataArr) {
712
713 for (NSString *dataStr in arr) {
714
715 // 如果数据于搜索框中的数据匹配,则加到_searchResultArr数组中
716
717 NSRange rang = [dataStr rangeOfString:str];
718
719
720
721 if (rang.location != NSNotFound) {
722
723 [_searchResultArraddObject:dataStr];
724
725 }
726
727 }
728
729 }
730
731 }
732
733 return tableView == _tableView ? [[_dataArrobjectAtIndex:section]count]:_searchResultArr.count;
734
735 }
736
737 -(UITableViewCell *) tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
738
739 {
740
741 staticNSString * cellId = @"cellID";
742
743 UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellId];
744
745 if (!cell) {
746
747 cell = [[[UITableViewCellalloc] initWithStyle:UITableViewCellStyleSubtitlereuseIdentifier:cellId] autorelease
748
749 ];
750
751 }
752
753 if (tableView == _tableView) {
754
755 cell.textLabel.text = [[_dataArrobjectAtIndex:indexPath.section] objectAtIndex:indexPath.row];
756
757 }else
758
759 {
760 //搜索结果的cell
761
762 cell.textLabel.text = [_searchResultArrobjectAtIndex:indexPath.row];
763
764 }
765
766 return cell;
767
768 }
769
770 -(NSString *) tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section
771
772 {
773
774 return tableView == _tableView? [_indexArrobjectAtIndex:section]:@"搜索结果";
775
776 }
777
778 -(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
779
780 {
781
782 return50;
783
784 }
785
786 //创建索引
787
788 //返回是是一个包含字符串的数组
789
790 //默认情况下,点击索引中的某一项会跳转到对应下标的分区
791
792 -(NSArray *)sectionIndexTitlesForTableView:(UITableView *)tableView
793
794 {
795
796 NSMutableArray *indexArr = [[NSMutableArrayalloc] init];
797
798 // UITableViewIndexSearch会转换成一个搜索图标
799
800 [indexArr addObject:UITableViewIndexSearch];
801
802 [indexArr addObjectsFromArray:_indexArr];
803
804 [indexArr addObject:@"#"];
805
806 return indexArr;
807
808 }
809
810 //返回一个数字,对应的是tableView中的分区的下标
811
812 //index对应的时索引中的下标
813
814 -(NSInteger)tableView:(UITableView *)tableView sectionForSectionIndexTitle:(NSString *)title atIndex:(NSInteger)index
815
816 {
817
818 if (index == 0) {
819
820 _tableView.contentOffset = CGPointMake(0, -65);
821
822 }
823
824 return index-1;
825
826 }
827
828 - (void)dealloc
829
830 {
831
832 [_indexArrrelease];
833
834 [_searchBarrelease];
835
836 [_displayControllerrelease];
837
838 [_searchResultArrrelease];
839
840 [_dataArrrelease];
841
842 [superdealloc];
843
844 }
845
846 @end