Xcode 10 - Scroll View is not allowing scrolling when adding button programmatically - ios

I'm getting data from a database and trying to display the data as buttons, I have got this working but when I run the app on the Xcode simulator the buttons are showing and I can see they are off the screen but I can't scroll.
I have tried adding a "view" inside the "scroll view" with a fixed height and then adding the buttons to that view and still nothing.
// Adding the scroll view and the view
#IBOutlet weak var scroll: UIScrollView!
#IBOutlet weak var content: UIView!
// Button Settings
var buttonX = 100
var buttonY = 0
let buttonWidth = 200
let buttonHeight = 50
let image = UIImage(named: "button") as UIImage?
override func viewDidLoad() {
super.viewDidLoad()
for element in contentsArray {
// Adding a button for each client name
let button = UIButton(type: .system)
button.setTitle(element, for: .normal)
button.tintColor = .white
button.titleLabel?.font = UIFont.boldSystemFont(ofSize: 22)
button.setBackgroundImage(image, for: .normal)
button.centerXAnchor.constraint(equalTo: button.centerXAnchor).isActive = true
button.addTarget(self, action: #selector(buttonClicked), for: .touchUpInside)
button.frame = CGRect(x: buttonX, y: buttonY, width: buttonWidth, height: buttonHeight)
content.addSubview(button)
buttonY = buttonY + 70
}
}
I am not getting any errors in the console when running the app.

Once your finish adding buttons, set the scrollView.contentSize.height to your calculated buttonY
scrollView.contentSize.width = self.view.frame.size.width // non scrollable content width
for element in contentsArray {
...
buttonY = buttonY + 70
}
scrollView.contentSize.height = buttonY // scrollable content height

Related

When creating a lazy button with a frame, this is created on the upper left corner why this happen?

I create this 'filterButton' and set it to be created on the exact position of the 'menubutton', the 'filterButton' goes directly to the upper left corner of the view.
lazy var filterButton: UIButton! = {
let button = UIButton(frame: CGRect(x: self.menuButton.frame.origin.x, y: self.button.frame.origin.y, width: 45, height: 45))
button.translatesAutoresizingMaskIntoConstraints = false
button.backgroundColor = .blue
button.clipsToBounds = true
return button
}()
and when I check and print the frame of the 'filterButton' it has the value of the 'menuButton', why this is happening?.
Add following constraints where you are adding filterButton to your view
filterButton.leftAnchor.constraint(equalTo: menuButton.leftAnchor).isActive = true
filterButton.topAnchor.constraint(equalTo: menuButton.topAnchor).isActive = true
filterButton.rightAnchor.constraint(equalTo: menuButton.rightAnchor).isActive = true
filterButton.bottomAnchor.constraint(equalTo: menuButton.bottomAnchor).isActive = true
Maybe, when you access to the instance of filterButton, frames of menuButton and button is not correct.
You can use layout constraints or update frame of filterButton in viewDidLayoutSubviews.
the problem is not of lazy button check you menuButton the problem is there for that you can check this :-
lazy var filterButton: UIButton! = {
let button = UIButton(frame: CGRect(x: 200, y: 200, width: 45, height: 45))
button.translatesAutoresizingMaskIntoConstraints = false
button.backgroundColor = .blue
button.clipsToBounds = true
return button
}()

Button not shown swift

I am new to swift coding, when I am trying to add a button by code, it does not show up in the Simulator.
I changed the dimension of the View in main.storyboard to 375*1114
there are scroll view and view inside with the same dimension as well.
there are also 5 collection views too.
These are all setup by the storyboard.
The code I used:
let fullScreenSize = UIScreen.main.bounds.size
let plusButton = UIButton(type: .custom)
plusButton.frame = CGRect(x: 300, y: 600, width: 50, height: 50)
plusButton.layer.cornerRadius = 0.5 * plusButton.bounds.size.width
plusButton.clipsToBounds = true
plusButton.setImage(UIImage(named: "plus.png"), for: .normal)
plusButton.center = CGPoint(x: fullScreenSize.width * 0.9, y: fullScreenSize.height * 0.9)
plusButton.addTarget(self, action: #selector(plusButtonPressed), for: .touchUpInside)
self.view.addSubview(plusButton)
I was trying to let the button to stay at the right bottom corner of the simulator all the time. How can I do that? Thanks.
your code is fine and correct add the background color and check once the button will be visibile else check your plusButton.setImage(UIImage(named: "plus.png"), for: .normal) plus.png is correct or not
plusButton.backgroundColor = UIColor.red
for full code
let fullScreenSize = UIScreen.main.bounds.size
let plusButton = UIButton(type: .custom)
plusButton.frame = CGRect(x: 300, y: 600, width: 50, height: 50)
plusButton.layer.cornerRadius = 0.5 * plusButton.bounds.size.width
plusButton.clipsToBounds = true
plusButton.setImage(UIImage(named: "normal.jpg"), for: .normal)
plusButton.backgroundColor = UIColor.red
plusButton.center = CGPoint(x: fullScreenSize.width * 0.9, y: fullScreenSize.height * 0.9)
// plusButton.addTarget(self, action: #selector(plusButtonPressed), for: .touchUpInside)
self.view.addSubview(plusButton)
output
I think you have to take an Outlet of UIView inside UIScrollview you already have in you UIViewController and add that button as a subView of that UIView. That's why your button is hiding, why don't you check it by looking at the View Hierarchy!

Programmatically adding UILabels and UIButtons to UIScrollView in Swift

My goal is to programmatically create multiple UILabels and UIButtons followed by programmatically creating and inserting them into a UIScrollView.
I am operating within the following class.
class ViewController: UIViewController {
I have first created my scrollView shown below.
#IBOutlet weak var scrollView: UIScrollView!
override func viewDidLoad() {
super.viewDidLoad()
createTitleBar() //Function that creates fixed buttons and labels not included in scrollView
createUpperTabs() //Function that creates fixed buttons and labels not included in scrollView
createLowerNavBars() //Function that creates fixed buttons and labels not included in scrollView
for _ in 0...10 {
createTemplate() //This function consists of nested functions that creates labels and buttons that are then added to the scrollView
}
scrollView = UIScrollView(frame: view.bounds)
scrollView.backgroundColor = UIColor.black
scrollView.contentSize = CGSize(width: screenSize.width, height: currentStackY)
scrollView.autoresizingMask = UIViewAutoresizing.flexibleHeight
view.addSubview(scrollView)
}
After creating the labels and buttons, I add the views individually to the scrollView with following statement
self.scrollView.addSubview(UILabel or UIButton Name).
Here are some snippets showing how I am creating my UILabel and UIButton.
let titleHeader = UILabel()
self.scrollView.addSubview(titleHeader)
currentStackY += 8
titleHeader.backgroundColor = .gray
titleHeader.text = headerTitle
titleHeader.font = UIFont(name: buttonFont, size: buttonFontSize)
let labelWidth = titleHeader.intrinsicContentSize.width + 16
titleHeader.snp.makeConstraints { (make) in
make.height.equalTo(titleHeader)
make.width.equalTo(titleHeader)
make.top.equalTo(currentStackY)
make.left.equalTo(view).offset(8)
}
as well as
for i in 0...chiefComplaintArray.count - 1 {
let btn = UIButton()
chiefComplaintButton.append(btn)
buttonDictionary[chiefComplaintButton[i]] = numberButtonPressed
chiefComplaintButton[i].setTitle(chiefComplaintArray[i], for: .normal)
chiefComplaintButton[i].setTitleColor(UIColor.black, for: .normal)
chiefComplaintButton[i].titleLabel!.font = UIFont(name: buttonFont, size: buttonFontSize)
chiefComplaintButton[i].backgroundColor = UIColor.gray
chiefComplaintButton[i].sizeToFit()
let buttonWidth = chiefComplaintButton[i].frame.width + 10
let buttonHeight = chiefComplaintButton[i].frame.height + 5
if i == 0 {
currentStackX = 20
currentStackY += 5
} else if (currentStackX + buttonWidth) > screenSize.width {
currentStackX = 20
currentStackY += buttonHeight + 5
}
chiefComplaintButton[i].frame = CGRect(x: currentStackX, y: currentStackY, width: buttonWidth, height: buttonHeight)
currentStackX += chiefComplaintButton[i].frame.width + 5
if i == chiefComplaintArray.count - 1 {
currentStackY += chiefComplaintButton[i].frame.height
}
self.scrollView.addSubview(chiefComplaintButton[i])
chiefComplaintButton[i].addTarget(self, action: #selector(self.buttonPressed), for: .touchUpInside)
}
I used similar statements to add all of the created content to the scrollView. I have modeled my UIScrollView after other solutions in the stacks as well as other online references. Thanks in advance for your time and consideration.
I have subsequently tried
let titleHeader = UILabel()
scrollView.addSubview(titleHeader)
self.view.addSubview(scrollView)
currentStackY += 8
titleHeader.backgroundColor = .gray
titleHeader.text = headerTitle
titleHeader.font = UIFont(name: buttonFont, size: buttonFontSize)
let labelWidth = titleHeader.intrinsicContentSize.width + 16
Still getting the same error.
The issue with your code is you are initializing your scrollView after you are calling the method in which you are getting crash,because at that time your scrollView is nil.
You need to call your method after
view.addSubview(scrollView)
Edit
override func viewDidLoad() {
super.viewDidLoad()
for _ in 0...10 {
createTemplate() //This function consists of nested functions that creates labels and buttons that are then added to the scrollView
}
scrollView = UIScrollView(frame: view.bounds)
scrollView.backgroundColor = UIColor.black
scrollView.contentSize = CGSize(width: screenSize.width, height: currentStackY)
scrollView.autoresizingMask = UIViewAutoresizing.flexibleHeight
view.addSubview(scrollView)
createTitleBar() //Function that creates fixed buttons and labels not included in scrollView
createUpperTabs() //Function that creates fixed buttons and labels not included in scrollView
createLowerNavBars() //Function that creates fixed buttons and labels not included in scrollView
}
Also from here
let titleHeader = UILabel()
scrollView.addSubview(titleHeader)
self.view.addSubview(scrollView)
currentStackY += 8
titleHeader.backgroundColor = .gray
titleHeader.text = headerTitle
titleHeader.font = UIFont(name: buttonFont, size: buttonFontSize)
let labelWidth = titleHeader.intrinsicContentSize.width + 16
remove this
self.view.addSubview(scrollView)

How to change Send button image in JSQMessagesController

How can I change JSQMessagesController "Send" button from just String to UIImageView?
Now it looks like:
Can I change this "Send" to image?
I've tried:
let sendButton = JSQMessagesInputToolbar()
sendButton.contentView?.rightBarButtonItem?.imageView?.image = UIImage(named: "send.png")
but I thing it's wrong, because it did not work =/
Create an UIButton and set it as the right bar button item of input toolbar.
let rightButton = UIButton(frame: CGRectZero)
let sendImage = UIImage(named: "send_button.png")
rightButton.setImage(sendImage, forState: UIControlState.Normal)
self.inputToolbar.contentView.rightBarButtonItemWidth = CGFloat(34.0)
self.inputToolbar.contentView.rightBarButtonItem = rightButton
Hope that helps!
No need to create another button, you can reuse the existing one:
override func viewDidLoad() {
super.viewDidLoad()
let imageWidth: CGFloat = 21
let image = UIImage(named: "image-name")
inputToolbar.contentView.rightBarButtonItemWidth = imageWidth
inputToolbar.contentView.rightBarButtonItem.setImage(image, for: .normal)
}
But if you want to have more control of the button, you should create a custom one:
override func viewDidLoad() {
super.viewDidLoad()
let buttonWidth = CGFloat(40)
let buttonHeight = inputToolbar.contentView.leftBarButtonContainerView.frame.size.height
let customButton = UIButton(frame: CGRect(x: 0, y: 0, width: buttonWidth, height: buttonHeight))
customButton.backgroundColor = .red
customButton.setImage(UIImage(named: "send-message"), for: .normal)
customButton.imageView?.contentMode = .scaleAspectFit
inputToolbar.contentView.rightBarButtonItemWidth = buttonWidth
inputToolbar.contentView.rightBarButtonItem = customButton
}
It can be set directly using the rightBarButtonItem. Your code is not working cause you are not setting the state of the button.
self.inputToolbar?.contentView.rightBarButtonItem?.setImage(UIImage(named: "send"), for: .normal)

Button on pop Up View doesn't work

I was trying to create a button on my custom pop up view. But created button doesn't recognise its action.
func createPopUp(){
view.userInteractionEnabled = false
scrollerView.userInteractionEnabled = false
var screenSize:CGRect = UIScreen.mainScreen().bounds
var screenHeight = screenSize.height
var screenWidth = screenSize.width
var popUpView : UIImageView
popUpView = UIImageView(frame:CGRectMake(0, 0, 530, 150));
popUpView.center = CGPointMake(screenWidth/2,screenHeight/2)
popUpView.backgroundColor = UIColor.whiteColor()
popUpView.tag = 81
self.view.addSubview(popUpView)
var vazgecButton = UIButton.buttonWithType(UIButtonType.System) as UIButton
vazgecButton.frame = CGRectMake(0, 0, 265, 60)
vazgecButton.center = CGPointMake(250, 550)
vazgecButton.setTitle("VazgeƧ", forState: .Normal)
vazgecButton.tag = 79
vazgecButton.addTarget(self, action: "closePopUpView:", forControlEvents: UIControlEvents.TouchUpInside)
self.view.addSubview(vazgecButton)
}
First i disabled user interacton for view and my scrollerView. Then i created a image view for pop up view, to keep my button. Neither adding on to popUpView nor view work.
and my closePopUpView is:
func closePopUpView(sender: UIButton!){
println("pressed!!")
}
I searched for internet but i couldn't find a solution.

Resources