如何UITableViewCell在表格视图中使用s 内的自动布局,让每个单元格的内容和子视图确定行高(本身/自动),同时保持平滑的滚动性能?
I am currently using UICollectionView for the user interface grid, and it works fine. However, I'd like to be enable horizontal scrolling. The grid supports 8 items per page and when the total number of items are, say 4, this is how the items should be arranged with horizontal scroll direction enabled:
0 0 x x
0 0 x x
Run Code Online (Sandbox Code Playgroud)
Here 0 -> Collection Item and x -> Empty Cells
有没有办法使它们居中对齐,如:
x 0 0 x
x 0 0 x
Run Code Online (Sandbox Code Playgroud)
这样内容看起来更干净? …
这是关于当前iOS开发的一个相当基本的问题,我从来没有找到一个好的答案.
在(比方说)垂直UICollectionView,
是否可以使用全宽度单元格,但是,允许通过自动布局控制动态高度?
(如果你是iOS"动态高度"的新手,意味着单元格有一些,比方说,文本视图可以是任何长度或图像可以是不同的大小,所以最终每个单元格是一个完全不同的高度.)
如果是这样的话?
这对我来说可能是"iOS中最重要的问题而没有真正好的答案".
根据Apple的文档(并在WWDC 2012上吹捧),可以UICollectionView动态设置布局,甚至可以为更改设置动画:
通常在创建集合视图时指定布局对象,但也可以动态更改集合视图的布局.布局对象存储在collectionViewLayout属性中.设置此属性会立即直接更新布局,而无需为更改设置动画.如果要为更改设置动画,则必须调用setCollectionViewLayout:animated:方法.
然而,在实践中,我发现它UICollectionView会contentOffset导致莫名其妙的甚至无效的更改,导致单元格移动不正确,使得该功能几乎无法使用.为了说明这个问题,我将以下示例代码放在一起,这些代码可以附加到放入故事板的默认集合视图控制器中:
#import <UIKit/UIKit.h>
@interface MyCollectionViewController : UICollectionViewController
@end
@implementation MyCollectionViewController
- (void)viewDidLoad
{
[super viewDidLoad];
[self.collectionView registerClass:[UICollectionViewCell class] forCellWithReuseIdentifier:@"CELL"];
self.collectionView.collectionViewLayout = [[UICollectionViewFlowLayout alloc] init];
}
- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section
{
return 1;
}
- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
UICollectionViewCell *cell = [self.collectionView dequeueReusableCellWithReuseIdentifier:@"CELL" forIndexPath:indexPath];
cell.backgroundColor = [UIColor whiteColor];
return cell;
}
- (void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath
{
NSLog(@"contentOffset=(%f, %f)", self.collectionView.contentOffset.x, self.collectionView.contentOffset.y);
[self.collectionView setCollectionViewLayout:[[UICollectionViewFlowLayout alloc] init] animated:YES];
NSLog(@"contentOffset=(%f, %f)", self.collectionView.contentOffset.x, …Run Code Online (Sandbox Code Playgroud) 我需要显示一堆具有不同高度的collectionViewCell.视图太复杂,我不想手动计算预期的高度.我想强制执行自动布局来计算单元格高度
dequeueReusableCellWithReuseIdentifier在cellForItemAtIndexPathbreak 之外调用collectionView并导致它崩溃
另一个问题是单元格不在单独的xib中,因此我无法手动实例化临时单元并将其用于高度计算.
对此有何解决方案?
public func collectionView(collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAtIndexPath indexPath: NSIndexPath) -> CGSize {
var cell = collectionView.dequeueReusableCellWithReuseIdentifier(cellIdentifier, forIndexPath: indexPath) as UICollectionViewCell
configureCell(cell, item: items[indexPath.row])
cell.contentView.setNeedsLayout()
cell.contentView.layoutIfNeeded()
return cell.contentView.systemLayoutSizeFittingSize(UILayoutFittingCompressedSize)
}
Run Code Online (Sandbox Code Playgroud)
编辑:
一旦调用dequeueReusableCellWithReuseIdentifier,就会发生崩溃.如果我不调用该方法而是返回一个大小,一切都很好,单元格显示没有计算的大小
流布局中不支持负值或零大小
2015-01-26 18:24:34.231 [13383:9752256] *** Terminating app due to uncaught exception 'NSRangeException', reason: '*** -[__NSArrayM objectAtIndex:]: index 1 beyond bounds [0 .. 0]'
*** First throw call stack:
(
0 CoreFoundation 0x00000001095aef35 __exceptionPreprocess + 165
1 libobjc.A.dylib 0x0000000109243bb7 objc_exception_throw + 45 …Run Code Online (Sandbox Code Playgroud) 我有一个简单的UICollectionView,单元格有一个UITextView.UITextView受限于单元格的边缘,因此它们应保持与单元格大小相同的大小.
我遇到的问题是,由于某种原因,当我通过collectionView指定单元格大小时,这些约束不起作用:layout:sizeForItemAtIndexPath:.
我在故事板中将单元格大小设置为320x50.如果我使用sizeForItemAtIndexPath:返回大小为单元格大小2倍的大小,则尽管我设置了约束,但UITextView仍保持相同的高度.我正在使用Xcode 6 GM.
我的视图控制器代码是:
@implementation TestViewController
- (void)viewDidLoad
{
[super viewDidLoad];
self.collectionView.delegate = self;
self.collectionView.dataSource = self;
}
- (void)viewDidAppear:(BOOL)animated
{
[super viewDidAppear:animated];
UICollectionViewCell *c = [self.collectionView cellForItemAtIndexPath:[NSIndexPath indexPathForItem:0 inSection:0]];
NSLog(@"%f", c.frame.size.height);
UITextView *tv = (UITextView *)[c viewWithTag:9];
NSLog(@"%f", tv.frame.size.height);
}
- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section
{
return 1;
}
- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
UICollectionViewCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"cell" forIndexPath:indexPath];
return cell;
}
- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath
{
UICollectionViewFlowLayout *flowLayout = (UICollectionViewFlowLayout *)collectionView.collectionViewLayout; …Run Code Online (Sandbox Code Playgroud) 一个到三个UITableViewCells UITableViewView.之后是否有办法始终将单元格放置在屏幕底部reloadData?
+----------------+ +----------------+ +----------------+
| | | | | |
| | | | | |
| | | | | |
| | | | | +------------+ |
| | | | | | cell 1 | |
| | | | | +------------+ |
| | | +------------+ | | +------------+ |
| | | | cell 1 | | | | cell 2 | |
| | | +------------+ | | …Run Code Online (Sandbox Code Playgroud) 我在UITableView中使用自动布局和大小类,单元格根据其内容自行调整大小.为此,我使用的方法对于每种类型的单元格,您保留该单元格的屏幕外实例并使用systemLayoutSizeFittingSize它来确定正确的行高 - 此方法在此StackOverflow帖子和其他地方进行了很好的解释.
这很有效,直到我开始使用大小类.具体来说,我在常规宽度布局中为文本的边距约束定义了不同的常量,因此iPad上的文本周围有更多的空白.这给了我以下结果.

似乎新的约束集合得到了尊重(存在更多的空白),但行高度计算仍然返回与不应用特定于大小类的约束的单元格相同的值.屏幕外单元格中的部分布局过程不考虑窗口的大小等级.
现在我想,这可能是因为离屏幕视图有没有上海华盈或窗口,因此它不具有任何尺寸类性状是指在点systemLayoutSizeFittingSize调用时(即使它似乎使用的调整限制边距).我现在通过在创建UIWindow后添加屏幕外的大小调整单元作为子视图来解决这个问题,从而得到所需的结果:

这是我在代码中所做的事情:
func tableView(tableView: UITableView, heightForRowAtIndexPath indexPath: NSIndexPath) -> CGFloat {
let contentItem = content[indexPath.item]
if let contentType = contentItem["type"] {
// Get or create the cached layout cell for this cell type.
if layoutCellCache.indexForKey(contentType) == nil {
if let cellIdentifier = CellIdentifiers[contentType] {
if var cachedLayoutCell = dequeueReusableCellWithIdentifier(cellIdentifier) as? UITableViewCell {
UIApplication.sharedApplication().keyWindow?.addSubview(cachedLayoutCell)
cachedLayoutCell.hidden = true
layoutCellCache[contentType] = cachedLayoutCell
}
}
}
if …Run Code Online (Sandbox Code Playgroud) 我正在尝试使用所谓的"自我调整单元",这意味着:
estimatedItemSize上flowLayoutpreferredLayoutAttributesFittingAttributes细胞类例如:UICollectionView具有自动布局的自定义单元格
我需要这样的动态效果:http://www.teehanlax.com/blog/implementing-a-bouncy-uicollectionviewlayout-with-uikit-dynamics/
没有UIDynamic,它工作正常,但我需要UIDynamic.正如我所看到的那样,它会调用prepareLayout并且layoutAttributesForElementsInRect直到死亡,将会有太多_updateVisibleCellsNow排队等待.
我不知道如何解决这个问题,如果你看到,请帮助我.或者,如果我以错误的方式使用这些技术,请告诉我.
ios uicollectionview uicollectionviewcell uicollectionviewlayout uikit-dynamics
我有一个表格视图,每个单元格有可能有自己的高度,因此不适合使用rowHeight.相反,现在我正在使用let indexSet = NSIndexSet(index: 10),而且self.tableView.estimatedRowHeight = 75.这意味着它调用sizeThatFits单元格上的函数,以确定其高度.这一切都运作良好.
问题是当你重新加载屏幕上的单元格时.例如,向下滚动以显示单元格10,然后重新加载单元格10,工作正常.但是当你开始向上滚动,经过你已经看过的单元格时,它会恢复到每个单元格的estimatedRowHeight,完全忽略sizeThatFits,因此在滚动时跳转.我不可能给出一个准确或"足够好"的估计值,因此这种跳跃不会引人注意,因为我的细胞能够显示一行文字或一个完整的图像 - 这是一个很大的区别.尺寸.
我在这里展示了这个效果:
我在这方面做了很多不同的尝试,使用了heightForRowAtIndexPath,estimatedHeightForRowAtIndexPath等的混合物.我在StackOverflow上尝试了各种建议.似乎没什么用.
我附上了一个非常简单的示例项目,您可以自己尝试:
https://www.dropbox.com/s/8f1rvkx9k23q6c1/tableviewtest.zip?dl=0
值得注意的是 - 如果单元格在重新加载时不在视图中,则不会发生这种情况.如果它高于或低于当前滚动点,则一切都按预期工作.
ios ×10
autolayout ×4
uitableview ×3
swift ×2
cocoa-touch ×1
ios6 ×1
iphone ×1
nsautolayout ×1
objective-c ×1
row-height ×1
size-classes ×1
uikit ×1