This is a very simple question,
I have a UIScrollView where I am setting childView horizontally from left to right. each time I am adding a new view, I want my ScrollView to scroll to the right so that the newly added view is seen on the screen.
When you add a new view you need to first increase the scroll view's content size.
scrollView.contentSize = CGSize(width: childV1.frame.width + childV2.frame.width, height: scrollView.contentSize.height)
Then you should be able to call scrollRectToVisible and pass in the most recently added child view's frame.
Related
I created a UIScrollView with its constraints set in storyboard, but I sometimes move the UIScrollView to a different position at runtime.
My problem happens when I create a custom UIView programmatically and add it the the main UIView. My constraints will update, and if my UIScrollView is not is the same location, it will be moved to the storyboard setting.
For instance, imagining my UIScrollView is pinned to the top of the screen, and then I move it to the bottom of the screen at runtime. If I execute this code:
let menu = UIView()
menu.frame.size = CGSize(width: 210, height: 80)
menu.center = view.center
view.addSubview(menu)
My UIScrollView will moved back to the tap on the screen. I try this but it did not work:
myScrollView.constraints.first?.isActive = false
When using auto-layout and constraints, you cannot change frames by setting the view.frame explicitly.
If you try to do so, then on the next UI update auto-layout will reset the view to its constraints.
If you need to move / size a view at run-time, you'll want to have a reference to the constraint(s) you've set, and then modify the constraint.
For example, if your scroll view is constrained 20-pts from the top of the view, and you want to move it down 50-pts at run-time...
create an IBOutlet for the top constraint
in code, use myTopConstraint.constant = 70.0
I have a UIScrollView for which I have a UIView which is the subview of the scroll view , the UIView has a lot of other subviews and I am getting the height for it dynamically after adding the subviews , this is my piece of code to add the view to scroll view
CGRect frameOfView = CGRectMake(0, 0,Get_Bounds.width, globalYPosition);
self.parentProductDetailView = [[UIView alloc]initWithFrame:frameOfView];
I am first initialising the view this way and then after adding all subviews I am doing this,
frameOfView.size.height = globalYPosition;
[self.parentProductDetailView layoutSubviews];
self.parentProductDetailView.frame = frameOfView;
[self.productDetailScrollView addSubview:self.parentProductDetailView];
self.productDetailScrollView.contentSize = CGSizeMake(0, self.parentProductDetailView.frame.size.height *1);
But my scrollview does not scroll properly it either sticks to top or bottom.
Here globalYPosition is the sum of height of all subviews added to parentProductDetailView
The procedure you used seems correct. No matter the subviews your scroll view should scroll properly by simply using a larger content size then its frame size.
The scroll view may stick, snap to some points if paging is enabled which is what is happening in your case. If the content view is larger then 1.5th of the frame size then the scroll view will snap to top/bottom or left/right. If it is smaller then it will only snap to starting position.
This may be very useful for situations like having a side menu that takes a part of a screen but in your case you should simply disable the paging and scrolling should work fine.
I'm developing a little app in Swift 2.0. I have a View with the following hierarchy:
Now, the elements placed in this view can't be displayed entirely in it, so I would like to use a ScrollView in order to be able to scroll all the content.
How I can embed all the content of my Viewto a new ScrollView? Can I do this programmatically by code?
UPDATE: There's an easier way to do this which I didn't know when I posted this answer
1) Go to the viewcontroller on the storyboard and click on something in it and press Command + A. This will select all the elements in the view.
2) Go to Editor -> Embed In -> Scroll View. This will embed all the labels, views, etc into a scrollView.
3) Select the scrollview that you just embedded. Press Control and drag it to the respective class file of the viewcontroller and create an outlet scrollView.
4) Add this to your viewDidLoad()
scrollView.contentSize = CGSizeMake(self.view.frame.width, self.view.frame.height+100)
Make sure the height for the contentSize is more than the size of your view.
ADDING SCROLLVIEW MANUALLY
1) Drag and drop a scrollview from the Object Library onto your viewcontroller in the storyboard and create an outlet to your program as 'scrollView'.
2) Click on your viewcontroller and go to the size inspector and note down the width and height.
3) Click on your scrollview and set the width and height the same as the viewcontroller. and set the X and Y values to 0
4) Click on the scrollView and drag it a little bit to the side
5) Press Command+A to select all the elements including scrollView. Press Command and click on the scrollView to deselect the ScrollView
6)You will have all the elements except the scrollView selected now. Now click and drag them into the scrollView.
7) Now click on the scrollView and set the X and Y values to 0 from the Size Inspector.
8) Add this to your viewDidLoad()
scrollView.contentSize = CGSizeMake(self.view.frame.width, self.view.frame.height+100)
Make sure the height for the contentSize is more than the size of your view.
That should create a scrollView for your view. Some of the elements might be in a slightly different position. You can easily fix them by moving them on your storyBoard.
It can be done even simpeler than ebby94's answer.
1) Go to the viewcontroller on the storyboard and click on something in it and press Command + A. This will select all the elements in the view.
2) Go to Editor -> Embed In -> Scroll View. This will embed all the labels, views, etc into a scrollView.
3) Set the constraints of the Scroll View to the View's edges.
And you're good to go! No need for an outlet.
If you are using Snapkit or creating programmatically.
class ScrollViewController: UIViewController {
lazy var contentViewSize = CGSize(width: self.view.frame.width, height: self.view.frame.height + 320) //Step One
lazy var scrollView : UIScrollView = {
let view = UIScrollView(frame : .zero)
view.frame = self.view.bounds
view.contentInsetAdjustmentBehavior = .never
view.contentSize = contentViewSize
view.backgroundColor = .white
return view
}()
lazy var containerView : UIView = {
let view = UIView()
view.frame.size = contentViewSize
view.backgroundColor = .white
return view
}()
override func viewDidLoad() {
self.view.addSubview(scrollView)
self.scrollView.addSubview(containerView)
//Now Set Add your Constraints in the container View.
}
}
Above accepted answer explanation is enough to achieve the scroll view but I would prefer to create my complete application programatically and I don't use storyboards in my project. This code is for the folks who don't prefer to use storyboards.
Explanation
Step One: Determine your content Size. Here I am taking Exact width and adding 320 more to the height of the screen.
Step Two: Create a scroll view and add desire behaviour of the scroll view. Now, the contentSize of the scroll view should be same as the contentSize you've created above at step one.
By Following Step one and Step Two. You Will be able to set a scroll view on the top of the view. But If you want to add a stretching behaviour then You should follow Step Three
Step Three: Create a container view of the same size of the contentView which you've calculated in step one and set it to the frame of the containerView. By doing this you'll be able to achieve stretching header and footer behaviour in your screen.
Please read make sure to add constraints in the same order as it is set.
Answer Edits are welcome.
I had the same issue. I needed to add scrollview to the existing view.But my main container view has a lots of view inside it. And they were connected to each other. So i was afraid. Finally i did it. the process given below.
Duplicate your View (root View). For this first select the root view then press Command + D
Now delete all the child view view inside the root view
Now add a scroll view to the root view and set constraint to 0,0,0,0
Now add the duplicate(That you duplicated) view to the scroll view and set constraints to 0,0,0,,0 also set the height that you want.
Set width of the duplicate view by equal width with the root view.
Now select the viewController, go the size inspector, select free form size. Then set the height that you entered with duplicate view.
You have almost done. Now you have to connect the child view with outlet or action that you gave in the viewController class.
Thats all.
Selecting all elements and embedding scroll view (editor->embed in->scrollView) works fine.
Adding constraint is much more easy by selecting the constraint warning (Add Missing Constraints).
It's simple. Command A and Command X to specific view controller in StoryBoard. After that take scroll view. On scroll view, just take one view with view controller view height and width equal to scroll View width. Again do Command V and rearrange the constraints. Your problem will be solved.
I have 6 buttons on a scroll view and when the user presses on of the buttons all of the buttons change title like a menu. However I would like the ScrollView to reset it self to the top, so the first few buttons are visible and the user is able to scroll down once again.
If you are using a scrollView, simply change scrollView.contentOffset to move your scroll view's visible window. Like x:0, y:0 to the top.
You should read some documents to understand contentOffset, contentSize and so on.
Swift 4
self.scrollView.contentOffset = CGPoint(x:250, y:100)
x and y are the respective width and height from the top left corner of your scrollview.
Apple documentation on contentOffset
Inside a UIViewController, I need to have the bottom half scrollable. So I added a UIScrollView and positioned it halfway down the view's height. And in the viewDidAppear method, I have put the below two code lines to make it scrollable.
self.scrollView.contentSize = CGSizeMake(self.view.frame.size.width, self.scrollView.frame.size.height);
self.scrollView.frame = self.view.frame;
This way works if the scroll view fills the entire view, I've tested. But this method didn't work for my need. The scroll view would automatically move up and take up the entire screen. I assumed it was the second line of code which causes this.
So I removed the scroll view, added two UIViews to the view controller. To the bottom view, I added the UIScrollView. And in the viewDidAppear method, I have put the same two code lines changing the second line to refer the frame of the UIView that contains the scroll view..
self.scrollView.contentSize = CGSizeMake(self.view.frame.size.width, self.scrollView.frame.size.height);
self.scrollView.frame = self.containerView.frame;
But it wouldn't scroll either.
Can anyone please tell me how to do this correctly?
Thank you.
Dude, you keep setting the frame of the scrollView to something completely different from what you're actually trying to achieve.
If all you want to do is setup your scroll view so that it only occupies half the space then why dont you just set the frame so that the height only covers the portion of the screen that you want it to cover; and then set the x & y coordinates so that you draw the scroll view from the right position.
Do something like this:
//Shortcut to view's frame.
CGRect viewsFrame = self.view.frame;
/**
CGRectMake takes 4 parameters: x, y, width, height
x: is set to 0 since you want the scrollview to start from the left with no margin
y: you want the y position to start half way, so we grab the view's height and divide by 2
width: you want your scrollview to span from left to right, so simply grab the view's width
height: you want your scrollview's height to be half of your screen height, so get view's height and divide by 2.
*/
CGRect frameForSV = CGRectMake(0, viewsFrame.size.height/2, viewsFrame.size.width, viewsFrame.size.height/2);
UIScrollView *myScrollView = [[UIScrollView alloc] initWithFrame:frameForSV];
[self.view addSubview:myScrollView];
Then set your content size not based on an ansolute value, its best to have it based on the size of the content that's actually inside your scrollview so that your scrollview always scrolls to cover all your content inside it.
Also, remember that your scrollview will only scroll if the contentsize is greater than the scrollview's frame
UPDATE 1 after reading your comment in this post simply comment out any code in your viewController.m file related to your scrollview since youre setting up everything in interface builder.
This is the result: