【问题标题】:Initialize custom UITableViewCell初始化自定义 UITableViewCell
【发布时间】:2011-08-19 21:07:07
【问题描述】:

我正在尝试将单个自定义单元格加载到 UITableView 中,但它一直抛出错误

UITableView dataSource 必须从 tableView:cellForRowAtIndexPath: 返回一个单元格:

我不知道为什么。我已将我的表格视图单元格链接到我的代码中的 UITableViewCell 定义,但它一直给我这个错误。这是我的代码;任何帮助将不胜感激。

#import "RegisterDeviceViewController.h"


@implementation RegisterDeviceViewController

@synthesize checkString;
@synthesize cellRegistration;

// The designated initializer.  Override if you create the controller programmatically and want to perform customization that is not appropriate for viewDidLoad.
/*
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil {
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if (self) {
        // Custom initialization.
    }
    return self;
}
*/


//Change UITableView Style to Grouped
- (id)initWithStyle:(UITableViewStyle)style {
    // Override initWithStyle: if you create the controller programmatically and want to perform customization that is not appropriate for viewDidLoad.
    style = UITableViewStyleGrouped;
    if (self = [super initWithStyle:style]) {
    }
    return self;
}

// Implement viewDidLoad to do additional setup after loading the view, typically from a nib.
- (void)viewDidLoad {
    self.title = @"Registration";
    [super viewDidLoad];
}


// Customize the number of sections in the table view.
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView 
{
    return 1;
}

// Customize the number of rows in the table view.
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section 
{
    return 1;
}


- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {

    if (indexPath.section == 1) {
        if (indexPath.row == 1) {
            return cellRegistration;

        }
    }
    return nil;
}


//Pass search type over to rootViewController section2
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath 
{

    /*
     <#DetailViewController#> *detailViewController = [[<#DetailViewController#> alloc] initWithNibName:@"<#Nib name#>" bundle:nil];
     // ...
     // Pass the selected object to the new view controller.
     [self.navigationController pushViewController:detailViewController animated:YES];
     [detailViewController release];
     */
}

/*
// Override to allow orientations other than the default portrait orientation.
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation {
    // Return YES for supported orientations.
    return (interfaceOrientation == UIInterfaceOrientationPortrait);
}
*/

- (void)didReceiveMemoryWarning {
    // Releases the view if it doesn't have a superview.
    [super didReceiveMemoryWarning];

    // Release any cached data, images, etc. that aren't in use.
}

- (void)viewDidUnload {
    [super viewDidUnload];
    // Release any retained subviews of the main view.
    // e.g. self.myOutlet = nil;
}


- (void)dealloc {
    [super dealloc];
}


@end

【问题讨论】:

  • CellRegistration 是我创建的 UITableViewCell,然后链接到界面构建器中的自定义表格视图单元格。

标签: cocoa-touch ios uitableview datasource custom-cell


【解决方案1】:

好的。这不是 UITableView 的工作方式。当表格视图需要绘制一个单元格(即一行)时;它在dataSource 属性中指定的对象上调用tableView:cellForRowAtIndexPath:。从该方法返回 UITableViewCell 是您的工作。这就是 Apple 的做法(以及您应该如何做):

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"AnIdentifierString"];
    if (cell == nil) 
    {
        cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleValue1 reuseIdentifier:@"AnIdentifierString"] autorelease];
    }

    cell.textLabel.text = @"This text will appear in the cell";


    return cell;
}

调用该方法的次数取决于表格视图中的节数和每个节中的行数。这个过程是这样的:

  1. Table View 在其dataSource 上调用委托方法numberOfSectionsInTableView:(它知道自己实现了该方法,因为dataSource 必须遵守UITableViewDataSource 协议)。
  2. 如果numberOfSectionsInTableView: 返回一个大于零的数字,表视图将调用dataSource 上的委托方法tableView:numberOfRowsInSection:。所以如果numberOfSectionsInTableView:返回2tableView:numberOfRowsInSection:会被调用两次。
  3. 如果tableView:numberOfRowsInSection:的每次调用都返回一个大于零的数字,表视图将调用dataSource上的委托方法tableView:cellForRowAtIndexPath:'所以如果tableView:numberOfRowsInSection:返回5tableView:numberOfRowsInSection:将被调用五次(每行一次)。
  4. 您有机会自定义该单元格的显示方式是在您收到一个可用的单元格之后,但在它返回之前(上面显示“此文本将出现在单元格中”)。你可以在这里做很多事情;您应该看到 UITableViewCell 的类参考以查看您可以做的所有事情(我所做的只是将其设置为显示“此文本...”)。 上面的行是 iOS 出于性能考虑重用单元格的一种方式。例如,如果您想显示字符串数组中的某个字符串,您可以这样做(注意indexPath 变量的使用):cell.textLabel.text = [someArrayYouHave objectAtIndex:indexPath.row];

【讨论】:

  • 问题,假设我有自己的自定义单元格,如何将其加载到 tableviewcell 中?
  • 谢谢,我刚刚阅读了 UITableViewCell 但仍不确定。我想我会休息一下,然后回到这个……但至少我没有错误。谢谢。
  • @Alan,我已经在界面构建器中构建了我的自定义单元格,这是否会影响我在尝试将其加载到 tableviewcell 时需要对其进行编码的方式。
  • Interface Builder 中的自定义单元格可以用完全相同的代码制作。您只需要以编程方式执行此操作:jainmarket.blogspot.com/2009/05/…
  • @Alan Zeino 这不是@tinhead 所要求的。试试这个:@interface VIEW { CELL *holder; } @property (nonatomic, retain) IBOutlet CELL *holder; @end - (UITableViewCell *)tableView:(UITableView *)aTableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { CELL *cell = (CELL *)[aTableView dequeueReusableCellWithIdentifier:@"id"]; if (nil == cell) { [[NSBundle mainBundle] loadNibNamed:@"NibName" owner:self options:nil]; cell = self.holder; self.holder = nil; } 不要忘记将自定义单元格中的文件所有者设置为自定义 tableview 或 tableview 委托类的类型。
【解决方案2】:

你写道:

一直报错 'UITableView 数据源必须返回一个 细胞来自 tableView:cellForRowAtIndexPath:' 但是 我不知道为什么..

但是你的 -tableView:cellForRowAtIndexPath: 部分说:

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
//...
    return nil;
}

看完报错信息,看代码,是不是没看出问题?

【讨论】:

  • cellRegistration 只是一个指针。如果它不指向实际的单元格,您将收到该错误。
  • 我已经通过 InterfaceBuilder 连接了它。
【解决方案3】:

你只返回一个部分,只有一行

节数和行数从0开始。

你遇到了这种错误

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
    if (indexPath.section == 0) {
        if (indexPath.row == 0) {
               //this checking is no necessary, anyway if you want use like this
               //ensure that cellRegistration is UITableViewCell
            return cellRegistration;
        }
    }
    return nil;
}

另请参阅post 以加载自定义单元格。

【讨论】:

  • 好的,关于加载笔尖名称.. 我是否要为这个方法制作一个只有一个自定义单元格的新笔尖?
  • 刚才我看到了您对 cellRegistration 的评论。检查我编辑的答案。并检查它是否有效。
【解决方案4】:

针对平滑滚动优化的新 iOS7+ 解决方案

您已经可以看到旧的解决方案,但就大量应用程序将继续只有 iOS7+ 支持这里是一种更优化和正确的解决方案。

单元初始化

要初始化单元格,只需调用dequeueReusableCellWithIdentifier,iOS7+ 系统就足够智能来处理cell == nil 与否。如果在 dequeue 期间单元格为 nil,系统会自动为您创建一个单元格。

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {

    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"cellIdentifier" forIndexPath:indexPath];

    return cell;
}

单元配置

然后在willDisplayCell 方法中进行整个单元格配置。只需在您的类中创建一个配置单元格的方法,您就可以获得更好的性能!

- (void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath {

    [self configureCell:cell forRowAtIndexPath:indexPath];
}

- (void)configureCell:(UITableViewCell *)cell
    forRowAtIndexPath:(NSIndexPath *)indexPath {

    // Configure your cell
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2023-03-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-11-29
    • 2015-06-18
    相关资源
    最近更新 更多