UICollectionView - vertical scrollling, horizontal paging with custom layout - ios

I'm trying to implement an iOS collection view which basically should work similar to a table view, but the cells' widths being integer multiples of the collection view's width (eg. 4 times the width). the collection view should scroll vertically (like a regular tableview does), but it should page horizontally across the content.
I do have the custom layout working except for the paging. Currently, the collectionView will just scroll horizontally. I'm unsure how to implement the paging correctly.
If I just set pagingEnabled on the collectionView, it has no effect. I suspect that the scrollview needs to be told what the width of a page is..?
Or do I have to do anything weird because there is only one cell/column per row, instead of multiple cells?
See the image; the grey bars are the cells, the blue rect is the collection view frame.
thanks!

I believe if the collection view item widths are less than or equal to the width of the collection view, then the horizontal paging should work via the pagingEnabled property. Otherwise, you need to create the paging effect yourself using the UIScrollView delegate methods and animating to offsets yourself after a certain threshold

Related

Increase the collectionView height constraint dynamically for the horizontal scrolling collectionView

I have added horizontal scrolling collection View in a scrollView and set the height as 10. I tried to change the height of the collection view dynamically using the above code it worked but cells are adding in multiple lines I mean just like grid view but I need horizontal scrolling and should not view like grid view instead it should view as the number of items in a single row just like below image
self.hei_col_offers.constant = self.col_offers.contentSize.height
self.view.layoutIfNeeded()

Why there is no possibility of scrollview scrolled when added contents dynamically.?

I am using scroll view. In my scenario, When contents are added dynamically in content view of scroll view. The view height must be increased automatically and content is added to the bottom with scrolling functionality. I tried the following. There is no particular way of scroll functionality. I don't know why scrolling is much complicated in iOS. Why scroll view not work the way like table view scrolling, table view taking any number of amount and scrolls. Finding youtube videos too not working as it has fixed height in advance .
Inside your scrollview you must add a UIView. Add a height constraint to the UIView and programatically change the height of the UIView depending on the content you are adding to this UIView. This scrollview will work if the height is large.

TableView horizontal scrolling according to cell width

I have table view inside scroll view which will scroll according to table view cell width.I have set the scroll view from top,bottom,leading and trailing.Then I have given the same constraints to view inside the scroll view including centerX and centerY.Then for horizontal scrolling I have set the trailing and centerX priority to 250.But my table view is not scrolling.I want to set it through autolayout.
I want the table to scroll horizontally if label increases inside the table view cell.
This is my view hierarchy
#Zahid I made a public example on github with what I wrote about below:
https://github.com/amichnia/stack-54735700
Original answer:
As it was already said, table views do not scroll horizontally in general. But no one said you can't put table view inside UIScrollView that scrolls horizontally. There would be some challenges here though:
I don't think autolayout with autoresizing cells would work good.
You need to figure out scrollview/tableview gesture recognizers order. You can use UIGestureRecognizer delegate methods to resolve their collisions
You need to determine width of the table view. You can do it with old nasty way:
compute size of every cell first,
take max of these sizes
set it to table view width
reload data
Is it worth the hassle? That's your call to take.
With your setup (I see scroll view as root view) the simplest (but not best) option would be to disable scrolling on table view, enable scrolling both directions on scroll view, and just update whole table view size. It will work well only with small amount of cells though!

iOS add subviews to a scroll view with dynamic heights

The problem I am forcing is:
I have 1 big scrollView and I have to add to it 5 subviews programmatically
when I don't know what heights the sub views will have :(
Is there some API to do so ?
or I have to count the subviews heights manually and add them with CGRectMake
based by calculated sizes?
What I would do is use Auto Layout. If you add your subviews to the scroll view using internal constraints, then these constraints can determine not only the distance of the subviews from one another but also the distance from the imaginary content view that surrounds them. The scroll view then uses the size of the content view as its contentSize, and the whole thing becomes scrollable. And this works despite the fact that you don't know the heights of any of the views, which is exactly what you're after.

UICollectionView scrolling in both directions

I made a UICollectionView with a vertical scroll.
The width of the cell is more than than the screen width, so I created a customFlowLayout based on UICollectionViewFlow layout returning the right calculated content size.
However, this doesn't work. When the width of the cell is less than the screen width it works. Does it mean that we can't have width more than than screen width in vertical scroll?
It is the same for horizontal scroll, but then the height of the CollectionView is limited to screen height.
Is there any way to make it work?
As others have already said, the UICollectionView can only scroll one direction using a flow layout. However you can accomplish this very easily without creating a custom layout or using a third party library.
When you lay your view out in story board, you can put your UICollectionView embedded in a UIScrollView. Have the scrollview set up to scroll horizontally and the UICollectionView to scroll Vertically. Then set the UICollectionView.delaysContentTouchesto true so touches will pass through to the UIScrollView and not think you are trying to scroll the collectionview.
When you set up the UICollectionView, set it's size and the size of the cells to be what you actually want them to be (Wider than the actual screen) and lay them out accordingly.
Now in the containing UIViewController put this code in the view lifecycle
- (void)viewDidLayoutSubviews {
self.myScrollView.contentSize = self.myCollectionView.frame.size;
}
That's literally all you have to do to accomplish what you are describing. Now your scrollview should allow you to scroll horizontally to view your entire cell and your collectionView should scroll vertically through your cells.
Happy programming.
I'm not sure I've understood your problem.
But if you have made a custom layout, make sure you have implemented :
- (UICollectionViewLayoutAttributes *)layoutAttributesForItemAtIndexPath:(NSIndexPath *)indexPath;
and that your layout attributes frame and size are set with correct values for your "large cell" index path.
Also make sure you have implemented :
- (CGSize) collectionViewContentSize;
This method returns the contentSize of the collection View. If contentSize.width > youAppFrame.width you should have horizontal scrolling. Same for height and vertical scrolling.
Also make sure your collectionView allows scrolling and that your layout is prepared correctly using :
- (void)prepareLayout
By the way, for your layout have you overloaded UICollectionViewLayout or UICollectionViewFlowLayout ?
Before you can do that you MUST use a different type of layout. The flow layout represents its items as a list and it spans these items in cells based on the available width.
If you want to have both horizontal and vertical scrolling you need to somehow specify the number of columns for your grid. the FlowLayout doesn't have that. A simple sollution is to make a subclass of UICollectionViewLayout and override collectionViewContentSize to make it retun a width = to the added sum of the cells widths of one row (this is where knowing how many collumns you want is necessary), plus any additional spacing between them. This will work fine if your cells have the same size per column, similar to a grid.
You should embed a UITableView into a UIScrollView.
ScrollView and TableView will have the same height but different widths.
This way UITableView will scroll vertical and UIScrollView will scroll horizontal.
Xcode 11+, Swift 5.
I solved my issue, I prepared video and code

Resources