您的位置:首页 > 移动开发 > IOS开发

IOS之 TableVIewContrller

2015-08-31 22:38 633 查看
项目实现:

1.在一个表格中可以对行元素进行删除,插入,和移动操作,

2.点击一个行元素,可以进入第二页面对内容进行修改。


效果展示:








实现步骤:

1.新建一个Movie类,这个类相当于MVC中的M,里面是视图中要用到的成员变量:

其中头文件定义如下,然后NSCopying,NSCoding等协议的实现,这里不做介绍

代码如下:


#import <Foundation/Foundation.h>

@interface Moves : UIViewController<NSCopying,NSCoding>{
	NSString* title;//电影标题
	NSNumber* boxOfficeGross;//票房
	NSString* summary;//简介
}

@property (nonatomic,copy)NSString * title;
@property(nonatomic,copy)NSNumber *boxOfficeGross;
@property (nonatomic,copy)NSString *summary;

-(id)initWithTitile:(NSString*)NewTitle andBoxoffice:(NSInteger)NewBox andSummary:(NSString*)NewSummary;
-(NSString *)description;
@end


2.新建一个MainTableViewController类,然后将它加入到根视图中:具体代码如下:



MainTableViewController *myView = [[MainTableViewController alloc]init];
    UINavigationController *navi = [[UINavigationController alloc]initWithRootViewController:myView];
    self.window.rootViewController = navi;


3.由于我的数据都是在Plist文件中存放,所以我建立了一个plist文件,具体信息如下:






4.首先我先在头文件中定义一个可变数组,和一个Movie对象作为成员参数:



@interface MainTableViewController : UITableViewController

{

NSMutableArray *array;

Moves *reloadMovie;

}

然后我们把plist中的信息引入到我们的类中,然后进行显示到视图上面:

(1):初始化函数,在viewDidLoad中调用即可:代码如下:





-(void)initData{
	 array = [[NSMutableArray alloc]initWithCapacity:5];
	NSString *path = [[NSBundle mainBundle ]pathForResource:@"MovieData" ofType:@"plist"];
	NSArray *arr = [NSArray arrayWithContentsOfFile:path];
	for (int i= 0; i<arr.count; i++) {
	 NSDictionary *dic = [arr objectAtIndex:i];
			        
	Moves *mm = [[Moves alloc]initWithTitile:[dic objectForKey:@"title"] andBoxoffice:[[dic objectForKey:@"boxOfficeGross"]integerValue] andSummary:[dic objectForKey:@"summary"]];
	[array addObject:mm];
			        
	}
			    
}
(2)把plist里面的数据,都放入到表格中:然后写编辑器给我提供的方法(被注释掉的,取消掉即可)

#pragma mark -UITableViewCell
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{    //CellIdentifier只是一个标识符,当重用的时候,可以让已经消失的表格行加以复用;
	static NSString *CellIdentifier = @"Cell";
	UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
	if (cell == nil) {//单元格的重用,只显示一个屏幕的CELL,多余的进行和消失的进行内容和位置的替换。
		cell = [[UITableViewCell alloc]initWithStyle:1 reuseIdentifier:CellIdentifier];
		//辅助单元格的样式
				        
		cell.accessoryType = 1;
	}
				    
	Moves *mm = [array objectAtIndex:indexPath.row];
	cell.textLabel.text = mm.title;
	cell.detailTextLabel.text = [NSString stringWithFormat:@"%@",mm.boxOfficeGross];
				    
	//NSLog(@"%@",[array objectAtIndex:indexPath.row]);
				    
				   
	return cell;

}


(3):这时候一定要设置表格要显示的行数和区域,不然整个表格仍然为空:



#pragma mark - Table view data source

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
	#warning Potentially incomplete method implementation.
	// Return the number of sections.
	return 1;
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
	#warning Incomplete method implementation.
	// Return the number of rows in the section.
	return array.count;
}


5.一个简单的表格已经初始化完毕,这时候我们发现我们的表格虽然有编辑选项,但是不能真正的实现,

下面我们就开始实现对表格的插入,删除操作。

(1)设置单元格的编辑样式,默认为delete:

实现效果:一行选项为删除,一行选项为插入:




-(UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath{
	    if (indexPath.row % 2) {
	        return UITableViewCellEditingStyleInsert;
	    }else{
	        return UITableViewCellEditingStyleDelete;
	    }
	}
(2)表格的删除和插入:

#pragma mark 编辑模式的删除与插入
		- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
		{
		    if (editingStyle == UITableViewCellEditingStyleDelete) {
		        // Delete the row from the data source
		        //删除数组中的选定元素:
		        [array removeObjectAtIndex:indexPath.row];
		        [tableView deleteRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationFade];
		    } else if (editingStyle == UITableViewCellEditingStyleInsert) {
		        
		        // Create a new instance of the appropriate class, insert it into the array, and add a new row to the table view
		        //创建一个新的类的实例,插入到数组中,并且添加一个新的行到这个表格视图中去
		        
		        static int i= 0;
		        NSString *str = [NSString stringWithFormat:@"捉妖记%d",++i];
		        Moves *mm = [[Moves alloc]initWithTitile:str andBoxoffice:12343 andSummary:@"a good movie"];
		        [array addObject:mm];
		        //确定插入行的位置
		        NSIndexPath *insertIndex = [NSIndexPath indexPathForRow:array.count - 1 inSection:indexPath.section];
		        //把新建的行的数据进行插入到表格中:
		        [tableView insertRowsAtIndexPaths:[NSArray arrayWithObjects:insertIndex,nil] withRowAnimation:UITableViewRowAnimationFade];
		        
		    }   
		}


(3):表格行元素的移动:

注意:这里一定要先删除在插入,因为如果你先插入的时候,行数就会增加一行,时候,在下移的时候,就会出错。




#pragma mark   移动行的位置,
- (void)tableView:(UITableView *)tableView moveRowAtIndexPath:(NSIndexPath *)fromIndexPath toIndexPath:(NSIndexPath *)toIndexPath
{
	//原理:先进行copy一份,然后把复制的插入要移动到的位置,然后把原来的进行删除操作。
 	//1.获取到需要系统的位置,
	Moves *fromObject = [array objectAtIndex:fromIndexPath.row];
	//2.把获取到的数据进行copy给一个新的实例变量
	Moves *toObject = [fromObject copy];
	//3.然后删除原来的创建的实例变量。
	[array removeObject:fromObject];
	//4.把copy到的对象进行插入操作
	[array insertObject:toObject atIndex:toIndexPath.row];
		    
	[tableView reloadData];
		    
}


通过以上的操作,我们就可以就表格进行简单的删除,插入,和移动操作了。接下来我们就要进行内容的修改操作了。





分析:我们应该新建一个viewcontroller的视图,然后里面存放我们Movie里面的数据,当我们进行修改数据的时候,

直接在返回的返回到主页面的时候,刷新数据就行了

6.新建一个DetailViewController类,同样的我们引入Movie的对象作为成员变量,然后用xib进行简单的页面布局,并初始化

初始值为Movie里面的数据:

(1):头文件代码如下:



#import <UIKit/UIKit.h>
#import "Moves.h"
@interface MovieEditViewController : UIViewController<UITextFieldDelegate>
//	以下三个用来存放电影的三个数据
@property (strong, nonatomic) IBOutlet UITextField *MovieName;
@property (strong, nonatomic) IBOutlet UITextField *MovieCount;
@property (strong, nonatomic) IBOutlet UITextField *MovieMes;

@property (nonatomic,strong)Moves *EditMovie;
//用来返回页面:
-(void)Return;

@end


(2):成员变量的初始化函数,独立的,需要在viewDidLoad中调用:

-(void)initData{
	self.MovieName.text = _EditMovie.title;
	self.MovieCount.text = [NSString stringWithFormat:@"%@",_EditMovie.boxOfficeGross];
	self.MovieMes.text = _EditMovie.summary;
}


(3):在页面要跳转的时候。我们要对Movie中的数据进行重新复制:重写viewWillDisappear方法:



-(void)viewWillDisappear:(BOOL)animated{
	_EditMovie.title = self.MovieName.text;
	_EditMovie.boxOfficeGross = (NSNumber*)self.MovieCount.text;
	_EditMovie.summary = self.MovieMes.text;
			    
}


做到这一步。我们的大概模型已经做好了,剩下的就是一些小细节,例如:

1.在编辑的时候,点击textFile,虚拟键盘出现,但不会自动的隐藏:

解决办法:重写系统提供的方法:

前提:遵守UITextFieldDelegate协议,然后,在viewDidLoad中,设置当前的控件为第一响应者:例如:

self.MovieMes.delegate =self;

self.MovieName.delegate =self;

self.MovieCount.delegate =self;

然后在我们触摸空白处的时候。还有就是点击了键盘的return的时候我们让虚拟键盘自动隐藏:

原理:都是让文本框结束第一响应者,也就是文本框的优先级降低,让虚拟键盘消失

三个方法如下:





(1):
    -(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event{
	    [self.MovieCount resignFirstResponder];
	    [self.MovieMes resignFirstResponder];
	    [self.MovieName resignFirstResponder];
	}
	(2)
	- (BOOL)textFieldShouldReturn:(UITextField *)textField{
    
	    [self.MovieCount resignFirstResponder];
	    [self.MovieMes resignFirstResponder];
	    [self.MovieName resignFirstResponder];
	    return YES;
	}






2.还有就是当我们的文本框距离底部很近的时候。我们虚拟键盘就会掩盖住文本框,这样我们就看不到写的是什么了



解决办法:重写系统提供的方法:当我们开始编辑的时候,让真个view的坐标向上移动,然后结束编辑的时候,再

变为原来的坐标:

代码如下:

(1):





//开始编辑的时候
- (void)textFieldDidBeginEditing:(UITextField *)textField{
	if (textField == self.MovieMes) {
	//给向上移动一个动画的效果
	[UIView animateWithDuration:0.6 animations:^{
	self.view.frame = CGRectMake(0, -110, self.view.frame.size.width, self.view.frame.size.height);
		}];
	}
}
		//结束编辑的时候
- (void)textFieldDidEndEditing:(UITextField *)textField{
	if (textField == self.MovieMes) {
	[UIView animateWithDuration:0.6 animations:^{
		self.view.frame = CGRectMake(0, 0, self.view.frame.size.width, self.view.frame.size.height);
		}];
	}
}




7,接下来,我们就应该在界面进行数据的更新了,

注意:我们对表格中数据的更新一般用reloadData方法。但是。如果我们的plist里面的数据很多的时候,我们仍然用这种方法

效率是很低很低的,这时候我们就应该想着局部更新,以提高效率,所以,我用了以下方法:


#pragma mark -刷新
-(void)viewWillAppear:(BOOL)animated{
	//[self.tableView reloadData];////该方法书写简单,但是效率低下
	if (reloadMovie) {
	//获取到修改的元素的行号
		NSUInteger row = [array indexOfObject:reloadMovie];
		NSIndexPath *indexpath = [NSIndexPath indexPathForRow:row inSection:0];
		//对获取到的行的数据进行跟新
		[self.tableView reloadRowsAtIndexPaths:[NSArray arrayWithObject:indexpath] withRowAnimation:NO];
	}
}




讲解完毕:可能有些地方说的不是太清楚,感兴趣的朋友可以留下邮箱。我会给你我的源代码进行参考。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: