I'm trying to get the size of my component in relation to the device, however it ignores the real size and considers the "placeholder" of the xib
it's funny because I have two screens with the same component, in one the xib has the look set like the iPhone 11 in the other the iPhone SE (2s generation), when I run the project, the layout calculation and the value of self.frame is different, even both the screens having the same identical component with the same configuration
Important I'm not using auto layout inside xib
It is not possible to use UIScreen in this case as we have other examples where the component is not centered on the screen.
private func drawPosition() {
searchView.addSubview(searchIcon)
searchView.backgroundColor = .red
searchIcon.backgroundColor = .yellow
let widht = self.frame.size.width - 12
widthLeftView = widht / 2
widthConstraint = searchView.widthAnchor.constraint(equalToConstant: widthLeftView)
NSLayoutConstraint.activate([
searchView.heightAnchor.constraint(equalToConstant: searchViewSize),
widthConstraint,
searchIcon.heightAnchor.constraint(equalToConstant: searchIconSize),
searchIcon.widthAnchor.constraint(equalToConstant: searchIconSize),
searchIcon.centerYAnchor.constraint(equalTo: searchView.centerYAnchor),
searchIcon.trailingAnchor.constraint(
equalTo: searchView.trailingAnchor,
constant: 0)
])
searchBarTextField.leftView = searchView
searchBarTextField.leftViewMode = .always
}
I tried to set the didLayoutSubViews in the controller but nothing changed
override func viewDidLayoutSubviews() {
super.viewDidLayoutSubviews()
self.searchBar.setNeedsLayout()
self.searchBar.layoutIfNeeded()
}
xib:
CodePudding user response:
How I'd to it:
Either add a super view to embed your searchView & searchIcon.
This is a placeholder view, you can set its constraints to half the side of its superview (what you do with self.frame.width
).
This way, no more "- 12" calculation.
Just let the icon to be at right side, then instead of setting the width of the searchView
, set its leading to that placeholder, and the trailing to icon.
Another way, would be to keep a reference to the width constraints:
var searchViewWidthConstraint: NSLayoutConstraint
And override layoutSubviews()
(if you are in a UIView
) or viewDidLayoutSubviews
(if you are in a (UIViewController):
override func layoutSubviews() {
super.layoutSubviews()
searchViewWidthConstraint.constant = self.frame.width - 12
}
When viewDidLoad()
is called, the frame of the different views are the one as seen in InterfaceBuilder. Then, the constraints are applied/calculated (and called again each needed time), and the frame adapts. That's why self.frame
wasn't correct yet