保存 UITableView 数据?
Posted
技术标签:
【中文标题】保存 UITableView 数据?【英文标题】:Save UITableView data? 【发布时间】:2013-05-31 18:41:23 【问题描述】:我正在使用故事板和动态 UITableView 添加我的单元格,如下所示。我需要知道如何在每个单元格的 UITextField 中保存此文本以及 UISwitch 状态等,因此当我上下滚动时,数据不会丢失。此外,当应用程序关闭时,我需要它来显示重新打开时输入的数据。我对编程很陌生,这是我的第一个 UItableView 项目。编码示例会很棒,请提供尽可能详细的信息!提前谢谢你!
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
UITableViewCell *cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:nil];
// Make cell unselectable and set font.
cell.selectionStyle = UITableViewCellSelectionStyleNone;
cell.textLabel.font = [UIFont fontWithName:@"ArialMT" size:13];
if (indexPath.section == 0)
UITextField* tf = nil;
switch ( indexPath.row )
case 0:
cell.textLabel.text = @"Name" ;
tf = nameFieldTextField = [self makeTextField:self.name placeholder:@"John Appleseed"];
nameFieldTextField.tag = 1;
[cell addSubview:nameFieldTextField];
break ;
case 1:
cell.textLabel.text = @"Address" ;
tf = addressFieldTextField = [self makeTextField:self.address placeholder:@"Street Address"];
addressFieldTextField.keyboardType = UIKeyboardTypeNumbersAndPunctuation;
[cell addSubview:addressFieldTextField];
break ;
case 2:
cell.textLabel.text = @"Email" ;
tf = emailFieldTextField = [self makeTextField:self.email placeholder:@"example@gmail.com"];
emailFieldTextField.keyboardType = UIKeyboardTypeEmailAddress;
[cell addSubview:emailFieldTextField];
break ;
case 3:
cell.textLabel.text = @"Phone" ;
tf = phoneFieldTextField = [self makeTextField:self.phone placeholder:@"xxx-xxx-xxxx"];
phoneFieldTextField.keyboardType = UIKeyboardTypePhonePad;
phoneFieldTextField.tag = 10;
phoneFieldTextField.text = [self formatPhoneNumber:phoneFieldTextField.text deleteLastChar:YES];
[cell addSubview:phoneFieldTextField];
break ;
case 4:
cell.textLabel.text = @"DOB" ;
tf = dateOfBirthTextField = [self makeTextField:self.dateOfBirth placeholder:@"xx/xx/xxxx"];
dateOfBirthTextField.keyboardType = UIKeyboardTypeNumbersAndPunctuation;
[cell addSubview:dateOfBirthTextField];
break ;
// Textfield dimensions
tf.frame = CGRectMake(120, 12, 170, 30);
// Workaround to dismiss keyboard when Done/Return is tapped
[tf addTarget:self action:@selector(textFieldFinished:) forControlEvents:UIControlEventEditingDidEndOnExit];
【问题讨论】:
看看 CoreData 以持久保存数据,或者如果它没有那么多数据,您也可以使用 NSUserDefaults。当然还有 XML 等... 【参考方案1】:我认为你可以制作一个模型对象来存储数据。
.h 文件
@interface User : NSObject <NSCoding>
@property (nonatomic, copy) NSString *name;
@property (nonatomic, copy) NSString *address;
@property (nonatomic, copy) NSString *email;
@property (nonatomic, copy) NSString *phone;
@property (nonatomic, copy) NSString *dob;
- (void)save;
+(User *)savedUser;
.m 文件
#define kName @"Name"
#define kAddress @"Address"
#define kEMail @"EMail"
#define kPhone @"Phone"
#define kDOB @"DOB"
#define kSavedUser @"SavedUser"
@implementation User
- (void)encodeWithCoder:(NSCoder *)encoder
[encoder encodeObject:self.name forKey:kName];
[encoder encodeObject:self.address forKey:kAddress];
[encoder encodeObject:self.email forKey:kEMail];
[encoder encodeObject:self.phone forKey:kPhone];
[encoder encodeObject:self.dob forKey:kDOB];
- (id)initWithCoder:(NSCoder *)decoder
self = [super init];
if (self)
self.name = [decoder decodeObjectForKey:kName];
self.address = [decoder decodeObjectForKey:kAddress];
self.email = [decoder decodeObjectForKey:kEMail];
self.phone = [decoder decodeObjectForKey:kPhone];
self.dob = [decoder decodeObjectForKey:kDOB];
return self;
#pragma mark - Save
- (void)save
NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
NSData *data = [NSKeyedArchiver archivedDataWithRootObject:self];
[defaults setObject:data forKey:kSavedUser];
[defaults synchronize];
+(User *)savedUser
NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
NSData *data = [defaults objectForKey:kSavedUser];
return [NSKeyedUnarchiver unarchiveObjectWithData:data];
UITableView 数据源
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
CustomCell *cell = [tableView dequeueReusableCellWithIdentifier:kCellIdentifier
forIndexPath:indexPath];
cell.selectionStyle = UITableViewCellSelectionStyleNone;
cell.detailTextField.delegate = self;
[cell.detailTextField setTag:indexPath.row+1];
switch (indexPath.row+1)
case 1:
cell.titleLabel.text = @"Name";
cell.detailTextField.text = self.user.name;
break;
case 2:
cell.titleLabel.text = @"Address";
cell.detailTextField.text = self.user.address;
break;
case 3:
cell.titleLabel.text = @"EMail";
cell.detailTextField.text = self.user.email;
break;
case 4:
cell.titleLabel.text = @"Phone";
cell.detailTextField.text = self.user.phone;
break;
case 5:
cell.titleLabel.text = @"D.O.B.";
cell.detailTextField.text = self.user.dob;
break;
default:
break;
return cell;
解释太多了。我附上源代码,看看。 Source Code
【讨论】:
感谢您的回复。我可以轻松地将这些数据保存为 pdf 并从应用程序通过电子邮件发送吗? 另外,对于多个部分,我将如何进行 textFieldDidEndEditing?【参考方案2】:您需要添加某种持久性。由于您似乎拥有非常少量的数据,因此您需要做的是使用 NSDictionary 的 writeToFile:atomically: 方法将表的数据放入 NSDictionary 对象中。您可以使用 NSDictionary 的类方法 dictionaryWithContentsOfFile: 加载数据,将保存图像的位置作为参数传递。
【讨论】:
【参考方案3】:首先,为了从您的应用程序中保存数据,您可以使用 Core Data 或 NSUserDefaults,NSUserDefaults 应该用于保存少量数据,其余使用 Core Data(有很多关于核心数据的教程,只需 google 即可)
但是你必须重写你的 cellForRowAtIndexPath
方法,因为它被错误地实现了。
首先使用dequeueReusableCellWithIdentifier
检查是否已经创建了单元格(也许您听说过单元格重用,这就是它的做法),因为现在您正在为每次调用cellForRowAtIndexPath
创建一个新单元格(每次单元格出现在屏幕上时调用的方法)。
其次,在dequeueReusableCellWithIdentifier
之后检查方法返回的单元格是否为nil,如果为nil则新建一个,如果不使用返回的单元格。
第三,创建一个可以有UITextField
或UISwitch
的自定义单元格,并在cellForRowAtIndexPath
中检查UITextField
的文本,如果为nil,则设置占位符,如果不保持原样这将允许在您滚动表格时正确显示数据。
第四,对于UITextFields
,当用户开始/结束编辑时会调用委托方法,因此您不需要添加[tf addTarget:self action:@selector(textFieldFinished:) forControlEvents:UIControlEventEditingDidEndOnExit];
,请检查 UITextFieldDelegate 协议(简单的谷歌东西:))
第五个(我保证的最后一个)不要在同一行代码中使用 =
,它丑陋且难以阅读 (tf = nameFieldTextField = [self makeT...
)
【讨论】:
【参考方案4】:您可以将数据保存在 sqlite 数据库中。或者您可以在视图中加载一个数组。最初您将插入空值。当您从该 uitableviewcell 对象替换该空对象时将创建您的单元格。接下来加载单元格的时间。您可以直接从该数组中获取数据。
【讨论】:
【参考方案5】:有关示例代码,请查看 GitHub 上 TLIndexPathTools 库中的 "Settings" example project。它演示了如何从表格中获取用户输入。它还展示了如何向表格添加动态行为,例如在输入更改时隐藏和显示行。
它没有显示如何在应用会话中保留这些值。为此,请按照 @d4Rk 的建议查看 Core Data 或 NSUserDefaults
。
【讨论】:
【参考方案6】: nsmutablearray *arr=[[nsmutablearray alloc] init];
[arr addobject:[nsnull class]];
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:customCellIdentifier];
cell = [[[NSBundle mainBundle]loadNibNamed:@"cell" owner:self options:nil]objectAtIndex:0];
cell.selectionStyle=UITableViewCellSelectionStyleNone;
if (![[saveCellState objectAtIndex:indexPath.row] isKindOfClass:[NSNull class]])
cell=(UITableViewCell *)[saveCellState objectAtIndex:indexPath.row];
if ([[saveCellState objectAtIndex:indexPath.row] isKindOfClass:[NSNull class]])
【讨论】:
以上是关于保存 UITableView 数据?的主要内容,如果未能解决你的问题,请参考以下文章