In my swift code there are 2 sliders 1 is on the bottom and 1 is constraint and rotate vertically. What I want to do is constraint the right slider to the top anchor of the bottom slider. You can see in the photo of what the current output and what I am looking for.
import UIKit
class ViewController: UIViewController {
var bottomSlider = UISlider()
var rightSlider = UISlider()
override func viewDidLoad() {
super.viewDidLoad()
rightSlider.transform = CGAffineTransform(rotationAngle: .pi / 2)
bottomSlider.value = 1
[ bottomSlider, rightSlider].forEach {
view.addSubview($0)
$0.translatesAutoresizingMaskIntoConstraints = false
$0.layer.borderWidth = 1
$0.backgroundColor = UIColor(
red: .random(in: 0.5...0.7),
green: .random(in: 0.0...1),
blue: .random(in: 0.3...0.5),
alpha: 1
)
$0.layer.borderWidth = 1
if let button = $0 as? UIButton {
button.setTitleColor(.black, for: .normal)
}
}
// Initialize sliderX's properties
NSLayoutConstraint.activate([
rightSlider.centerXAnchor.constraint(equalTo: view.safeAreaLayoutGuide.trailingAnchor, constant: -30),
rightSlider.centerYAnchor.constraint(equalTo: view.safeAreaLayoutGuide.centerYAnchor),
rightSlider.widthAnchor.constraint(equalTo: view.safeAreaLayoutGuide.heightAnchor),
bottomSlider.bottomAnchor.constraint(equalTo: view.bottomAnchor,constant: -60),
bottomSlider.heightAnchor.constraint(equalTo: view.heightAnchor, multiplier: 0.08),
bottomSlider.widthAnchor.constraint(equalTo: view.widthAnchor),
bottomSlider.leadingAnchor.constraint(equalTo: view.leadingAnchor),
])
bottomSlider.minimumValue = 1
bottomSlider.maximumValue = 3
}
}
It would be more convenient to wrap the vertical slider into another UIView
in this case. Then, you can position that UIView
as you normally would.
class VerticalSlider: UIView {
let wrappedSlider = UISlider()
override init(frame: CGRect) {
super.init(frame: frame)
addSubview(wrappedSlider)
wrappedSlider.translatesAutoresizingMaskIntoConstraints = false
NSLayoutConstraint.activate([
wrappedSlider.centerXAnchor.constraint(equalTo: self.centerXAnchor),
wrappedSlider.centerYAnchor.constraint(equalTo: self.centerYAnchor),
// note the swapped width and height constraints here, because the slider is rotated
wrappedSlider.widthAnchor.constraint(equalTo: self.heightAnchor),
wrappedSlider.heightAnchor.constraint(equalTo: self.widthAnchor),
])
wrappedSlider.transform = .init(rotationAngle: .pi / 2)
}
required init?(coder: NSCoder) {
fatalError()
}
}
Then you can position VerticalSlider
like you normally would.
class MyViewController: UIViewController {
override func viewDidLoad() {
let rightSlider = VerticalSlider()
rightSlider.wrappedSlider.maximumValue = 1
rightSlider.wrappedSlider.minimumValue = 0
rightSlider.wrappedSlider.value = 0.5
rightSlider.translatesAutoresizingMaskIntoConstraints = false
let bottomSlider = UISlider()
bottomSlider.maximumValue = 1
bottomSlider.minimumValue = 0
bottomSlider.value = 0.5
bottomSlider.translatesAutoresizingMaskIntoConstraints = false
view.addSubview(rightSlider)
view.addSubview(bottomSlider)
// note that I changed some of the constraints to use the safeAreaLayoutGuide of the view
// you wouldn't want your sliders to go out of the safe area, would you?
NSLayoutConstraint.activate([
bottomSlider.bottomAnchor.constraint(equalTo: view.safeAreaLayoutGuide.bottomAnchor),
bottomSlider.heightAnchor.constraint(equalTo: view.safeAreaLayoutGuide.heightAnchor, multiplier: 0.08),
bottomSlider.widthAnchor.constraint(equalTo: view.safeAreaLayoutGuide.widthAnchor),
bottomSlider.leadingAnchor.constraint(equalTo: view.safeAreaLayoutGuide.leadingAnchor),
rightSlider.topAnchor.constraint(equalTo: view.safeAreaLayoutGuide.topAnchor),
rightSlider.bottomAnchor.constraint(equalTo: bottomSlider.topAnchor, constant: -8),
rightSlider.centerXAnchor.constraint(equalTo: view.safeAreaLayoutGuide.trailingAnchor, constant: -30)
])
}
}
Output (landscape mode, so that the screenshot doesn't appear too big):