You cannot make a UIView scrollable. That's what UIScrollView is for. However if you are using storyboards you can try to add constraints to the view so when you rotate the device the content remains inside the viewable area.
You can scroll the scrollview in the Storyboard / Interface builder! Select the view inside scrollview in Document Outline, then scroll using your mouse or trackpad, you can see the view move.
To fix ScrollView Not scrolling with React Native, we wrap the content of the ScrollView with the ScrollView. to wrap ScrollView around the Text components that we render inside. As a result, we should see text inside and we can scroll up and down.
Each of the elements has it's own intrinsicContentSize so it should be possible for the UIStackView to provide its own intrinsicContentSize . The documentation states that the spacing is used as a minimum spacing. The intrinsicContentSize.
In case anyone is looking for a solution without code, I created an example to do this completely in the storyboard, using Auto Layout.
You can get it from github.
Basically, to recreate the example (for vertical scrolling):
UIScrollView
, and set its constraints.UIStackView
to the UIScrollView
Leading
, Trailing
, Top
& Bottom
should be equal to the ones from UIScrollView
Width
constraint between the UIStackView
and UIScrollView
. UIStackView
UIViews
to the UIStackView
Exchange Width
for Height
in step 4, and set Axis
= Horizontal
in step 5, to get a horizontal UIStackView.
Apple's Auto Layout Guide includes an entire section on Working with Scroll Views. Some relevant snippets:
- Pin the content view’s top, bottom, leading, and trailing edges to the scroll view’s corresponding edges. The content view now defines the scroll view’s content area.
- (Optional) To disable horizontal scrolling, set the content view’s width equal to the scroll view’s width. The content view now fills the scroll view horizontally.
- (Optional) To disable vertical scrolling, set the content view’s height equal to the scroll view’s height. The content view now fills the scroll view horizontally.
Furthermore:
Your layout must fully define the size of the content view (except where defined in steps 5 and 6). … When the content view is taller than the scroll view, the scroll view enables vertical scrolling. When the content view is wider than the scroll view, the scroll view enables horizontal scrolling.
To summarize, the scroll view's content view (in this case, a stack view) must be pinned to its edges and have its width and/or height otherwise constrained. That means that the contents of the stack view must be constrained (directly or indirectly) in the direction(s) in which scrolling is desired, which might mean adding a height constraint to each view inside a vertically scrolling stack view, for example. The following is an example of how to allow for vertical scrolling of a scroll view containing a stack view:
// Pin the edges of the stack view to the edges of the scroll view that contains it
stackView.topAnchor.constraint(equalTo: scrollView.topAnchor).isActive = true
stackView.leadingAnchor.constraint(equalTo: scrollView.leadingAnchor).isActive = true
stackView.trailingAnchor.constraint(equalTo: scrollView.trailingAnchor).isActive = true
stackView.bottomAnchor.constraint(equalTo: scrollView.bottomAnchor).isActive = true
// Set the width of the stack view to the width of the scroll view for vertical scrolling
stackView.widthAnchor.constraint(equalTo: scrollView.widthAnchor).isActive = true
I present you the right solution
For Xcode 11+
Step 1: Add a ScrollView and resize it
Step 2: Add Constraints for a ScrollView
Step 3: Add a StackView into ScrollView, and resize it.
Step 4: Add Constraints for a StackView (Stask View -> Content Layout Guide -> "Leading, Top, Trailing, Bottom")
Step 4.1: Correct Constraints -> Constant (... -> Constant = 0)
Step 5: Add Constraints for a StackView (Stask View -> Frame Layout Guide -> "Equal Widths")
Step 6 Example: Add two UIView(s) with HeightConstraints and RUN
I hope it will be useful for you like
The constraints in the top-voted answer here worked for me, and I've pasted an image of the constraints below, as created in my storyboard.
I did hit two issues though that others should be aware of:
After adding constraints similar to those in in the accepted answer, I'd get the red autolayout error Need constraints for: X position or width
. This was solved by adding a UILabel as a subview of the stack view.
I'm adding the subviews programmatically, so I originally had no subviews on the storyboard. To get rid of the autolayout errors, add a subview to the storyboard, then remove it on load before adding your real subviews and constraints.
I originally attempted to add UIButtons
to the UIStackView. The buttons and views would load, but the scroll view would not scroll. This was solved by adding UILabels
to the Stack View instead of buttons. Using the same constraints, this view hierarchy with the UILabels scrolls but the UIButtons does not.
I'm confused by this issue, as the UIButtons do seem to have an IntrinsicContentSize (used by the Stack View). If anyone knows why the buttons don't work, I'd love to know why.
Here is my view hierarchy and constraints, for reference:
As Eik says, UIStackView
and UIScrollView
play together nicely, see here.
The key is that the UIStackView
handles the variable height/width for different contents and the UIScrollView
then does its job well of scrolling/bouncing that content:
override func viewDidLayoutSubviews() {
super.viewDidLayoutSubviews()
scrollView.contentSize = CGSize(width: stackView.frame.width, height: stackView.frame.height)
}
This example is vertical:
Have a blank full-screen scene
Add a scroll view. Control-drag from the scroll view to the base view, add left-right-top-bottom, all zero.
Add a stack view in the scroll view. Control-drag from the stack view to the scroll view, add left-right-top-bottom, all zero.
Put two or three labels inside the stack view.
For clarity, make the background color of the label red. Set the label height to 100.
Now set the width of each UILabel:
Surprisingly, control-drag from the UILabel
to the scroll view, not to the stack view, and select equal widths.
To repeat:
It's that simple. That's the secret.
Secret tip - Apple bug:
It will not work with only one item! Add a few labels to make the demo work.
You're done.
Tip: You must add a height to every new item. Every item in any scrolling stack view must have either an intrinsic size (such as a label) or add an explicit height constraint.
The alternative approach:
To recap the above approach: surprisingly, set the widths of the labels to the width of the scroll view (not the stack view).
Here is an alternate approach...
So you have two options:
or
To be clear, do ONE of those methods, do NOT do both.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With