I want to set the width of UICollectionViewCell
dynamically.
I found some code in swift and I want the code in Objective-C.
let flowLayout = col
Swift 2.2
override func collectionView(collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAtIndexPath indexPath: NSIndexPath) -> CGSize {
var flowLayout = (collectionView.collectionViewLayout as! UICollectionViewFlowLayout)
if indexPath.item % 3 == 0 {
var cellWidth: Float = (CGRectGetWidth(collectionView.frame) - (flowLayout.sectionInset.left + flowLayout.sectionInset.right))
return CGSizeMake(cellWidth, cellWidth / 2)
}
else {
var cellWidth: Float = (CGRectGetWidth(collectionView.frame) - (flowLayout.sectionInset.left + flowLayout.sectionInset.right) - flowLayout.minimumInteritemSpacing) / 2
return CGSizeMake(cellWidth, cellWidth)
}
}
Swift 3.0
override func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
var flowLayout: UICollectionViewFlowLayout? = (collectionView.collectionViewLayout as? UICollectionViewFlowLayout)
if indexPath.item % 3 == 0 {
var cellWidth: Float? = (collectionView.frame.width - (flowLayout?.sectionInset?.left + flowLayout?.sectionInset?.right))
return CGSize(width: CGFloat(cellWidth), height: CGFloat(cellWidth / 2))
}
else {
var cellWidth: Float? = (collectionView.frame.width - (flowLayout?.sectionInset?.left + flowLayout?.sectionInset?.right) - flowLayout?.minimumInteritemSpacing) / 2
return CGSize(width: CGFloat(cellWidth), height: CGFloat(cellWidth))
}
}
You can try this...
- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout*)collectionViewLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath {
UICollectionViewFlowLayout *flowLayout = (UICollectionViewFlowLayout*) collectionView.collectionViewLayout;
if (indexPath.item % 3 == 0) {
float cellWidth = (CGRectGetWidth(collectionView.frame) - (flowLayout.sectionInset.left + flowLayout.sectionInset.right));
return CGSizeMake(cellWidth, cellWidth / 2);
} else {
float cellWidth = (CGRectGetWidth(collectionView.frame) - (flowLayout.sectionInset.left + flowLayout.sectionInset.right) - flowLayout.minimumInteritemSpacing) / 2;
return CGSizeMake(cellWidth, cellWidth);
}
}
This is the simplest solution.
Your UIViewController should implement UICollectionViewDelegateFlowLayout. Then the function below needs to be implemented on your UIviewController.
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
let width = self.collectionView.frame.size.width / 2;
return CGSize(width: width, height: 230)
}
Furthermore, you can adjust each cell's spacing value on your storyboard. Click collectionView then see the size inspector.
set cell's width to a percentage of the container view like:
cell.frame = CGRectMake(x, y, self.view.frame.size.width * 20 / 100, height);
or you can use CollectionView Delegates
- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout*)collectionViewLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath {
return CGSizeMake(self.view.frame.size.width*20/100, 192.f);
}
in case collection view cell has text, you just need to reference some label in the scene without width constraint for it, then every time in size for item, just assign to it your text, and call
Objective C:
NSString *text = [arrayOfItems objectAtIndex:indexPath.item];
_outletoflbl.text = text;
return CGSizeMake(_outletoflbl.intrinsicContentSize.width + 60, 40);
Swift:
let text = arrayOfItems[indexPath.item]
_outletoflbl.text = text
return CGRect(width:_outletoflbl.intrinsicContentSize.width + 60, height: 40)
The key is _outletoflbl
, the label to assign it text to get width of it best fitting font and other attributes you assign from interface builder!
Check result: