在多年避免像瘟疫一样避免使用界面生成器之后,我决定给它一个机会。这并不容易。
以UITableViewHeaderFooterView
为例。像UITableViewCell
一样,它有一个contentView
属性。与UITableViewCell
不同,它在界面生成器对象库中没有模板。
我们应该如何使用界面生成器创建一个包含contentView
内内容的UITableViewHeaderFooterView
?registerNib:forHeaderFooterViewReuseIdentifier:
存在的事实使我认为这应该以某种方式成为可能。
最接近用 IB 定义UITableViewHeaderFooterView
:
a. 创建一个UITableViewHeaderFooterView
子类 ( MYTableViewHeaderFooterView
(。
b. 仅为contentView
创建 nib 文件 ( MYTableViewHeaderFooterContentView
(。
c. 覆盖MYTableViewHeaderFooterView
中的initWithReuseIdentifier:
以加载 nib 文件中定义的视图。
- (instancetype)initWithReuseIdentifier:(NSString *)reuseIdentifier
{
self = [super initWithReuseIdentifier:reuseIdentifier];
if (self)
{
NSArray* objects = [[NSBundle mainBundle] loadNibNamed:@"MYTableViewHeaderFooterView"
owner:self
options:nil];
UIView *nibView = [objects firstObject];
UIView *contentView = self.contentView;
CGSize contentViewSize = contentView.frame.size;
nibView.frame = CGRectMake(0, 0, contentViewSize.width, contentViewSize.height);
[contentView addSubview:nibView];
}
return self;
}
d. 注册 MYTableViewHeaderFooterView
类而不是 nib 文件:
[self.tableView registerClass:[MYTableViewHeaderFooterView class] forHeaderFooterViewReuseIdentifier:@"cell"];
我只是用页脚和一个 NIB 文件来做这件事:
- 创建一个名为 CustomFooterView.xib 的空 NIB 文件。
- 在界面生成器中编辑 NIB 文件,并将最顶层的 UIView 自定义类更改为 UITableViewHeaderFooterView。
- 禁用 NIB 中的自动布局。
- 将视图的背景色设置为
UITableViewHeaderFooterView
默认。 - 使视图自由格式并正确调整大小(例如 320 x 44(。
-
在UITableViewController中
viewDidLoad
注册要与重用标识符一起使用的NIB文件:[self.tableView registerNib:[UINib nibWithNibName:@"CustomFooterView" bundle:nil] forHeaderFooterViewReuseIdentifier:@"Footer"];
-
在UITableViewController的
tableView:viewForFooterInSection:
中使用页脚标识符来获取和返回视图:- (UIView *)tableView:(UITableView *)tableView viewForFooterInSection:(NSInteger)section { if (section == 2) return [tableView dequeueReusableHeaderFooterViewWithIdentifier:@"Footer"]; return nil; }
只需在 IB 中使用 UITableViewCell 模板即可。 将类更改为 UITableViewHeaderFooterView。在这里你有它...与内容视图。
我找到了更简单的方法。
1( 创建 UITableViewCell 的子类并设置您的 xib 文件
2(在您的头文件中将超类从UITableViewCell更改为UITableViewHeaderFooterView
就是这样。
此解决方案运行良好,特别是如果您希望它与可读内容指南(在iOS 9中引入(相关时正常工作。它不是创建 UITableViewHeaderFooterView,而是在需要时返回自定义 UIView(来自 XIB(:
-
创建一个子类UIView("AwesomeHeaderView"(的新类并创建您的出口:
class AwesomeHeaderView: UIView { @IBOutlet var myCustomLabel: UILabel! }
- 创建一个 XIB 文件 ("MyNewHeader.xib"( 的 UIView 为父视图。将父 UIView 的类类型更改为新创建的自定义类("AwesomeHeaderView"(。根据需要,添加任何其他视图,因为它是子视图和链接插座等(注意:为了确保视图符合新的可读内容指南,我选中了所有对象的"保留超级视图边距"和"遵循可读宽度"框(。
-
在您的 UIViewController 中(或UITableViewController( 调用以下内容:
func tableView(tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? { guard let headerView = NSBundle.mainBundle().loadNibNamed("MyNewHeader", owner: nil, options: nil).first as? AwesomeHeaderView else { return nil } // configure header as normal headerView.backgroundColor = UIColor.redColor() headerView.myCustomLabel.textColor = UIColor.whiteColor() headerView.myCustomLabel.text = "Hello" return header }
我还遇到了上面的弃用警告和无法设置背景颜色等。最终,我发现根据苹果的文档,
在大多数情况下,您可以按原样使用 [UITableViewHeaderFooter] 类,而无需子类化。如果要显示自定义内容,请为内容创建子视图,并将其添加到 contentView 属性中的视图中。
根据该建议,我采取了以下步骤:
- 我创建了一个 xib,其视图仅扩展 UIView,而不是 UITableViewHeaderFooter。
-
在viewDidLoad中,我注册了内置的UITableViewHeaderFooter类
tableView.registerClass(UITableViewHeaderFooterView.self, forHeaderFooterViewReuseIdentifier: "sectionHeader"(
-
在我的 UITableViewController 的 viewForHeaderInSection 委托中,我按该标识符将标题视图取消排队,并检查标题视图是否已包含子视图。如果没有,我加载我的 xib 并添加它。然后我根据需要设置文本。
override func tableView(tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? { let header = self.tableView.dequeueReusableHeaderFooterViewWithIdentifier("sectionHeader")! if header.contentView.subviews.count == 0 { header.contentView.addSubview(loadMyNib()) } let myView = header.contentView.subviews[0] as! MyView myView.label.text = "..."
这似乎有效,利用重用,并且不会产生任何警告。
https://developer.apple.com/library/prerelease/tvos/documentation/UIKit/Reference/UITableViewHeaderFooterView_class/index.html#//apple_ref/occ/instm/UITableViewHeaderFooterView/prepareForReuse
以下解决方法使我能够将 IB 项作为变量拖动分配给代码。 UITableViewHeaderFooterView不允许开箱即用。
-
创建一个(New File/CocoaTouchClass( UITableViewHeaderFooterView.h.m.xib 正常
-
暂时将超类从UITableViewHeaderFooterView重命名为UIView。根据需要将UI项拖拽分配给代码,IB将分配键值正确,完成后恢复为 UITableViewHeaderFooterView。
- 在表视图中,使用 registerNib: 进行注册,而不是 registerClass:。 正常准备表视图的其余部分(即:取消排队(。
出的一个可怕的技巧是创建一个IBOutlet contentView ih你的headerFooter类,并将其连接到xib中的"内容视图"(让你的xib像tableViewCell一样布局,View->contentView->mystuff(。
你会收到警告,好的,准备好黑客攻击了...
删除IBOutlet,它将全部工作。
我发现的最好的方法:
- 创建 HeaderFooterView(.h/.m(,例如
header
- 创建一个 xib(视图(,名称相同
- 使根视图类成为您的类(
header
( - [重要] 将所有插座连接到根视图,而不是
File's Owner
最后,将您的笔尖注册到桌子(全部完成(。