Stackview 交换或更改视图顺序
Stackview exchange or change order of views
包含文本字段数组的堆栈视图嵌入到滚动视图中。我想更改某些操作中文本字段的顺序。删除和添加文本字段的方式会导致视图失真。我还通过从滚动视图中删除进行了测试。正常的堆栈视图也没有正确显示交换。我正在使用索引进行更改:
stackView.removeArrangedSubview(localityTF)
stackView.insertArrangedSubview(localityTF, at: 2)
这是一种奇怪的行为,但自动布局系统存在问题,应该先更新该系统,然后才能将 localityTF 添加回来。也不要忘记 removeArrangedSubview
不会从子视图数组中删除视图:
[self.stackView removeArrangedSubview:_label1];
[self.stackView setNeedsLayout];
[self.stackView layoutIfNeeded];
[self.stackView insertArrangedSubview:_label1 atIndex:2];
[self.stackView setNeedsLayout];
这是我在Swift3中的解决方案。也可以在stackview中不定义view的情况下使用
在这里,我正在更改具有两个视图的 Stackview 的视图位置:
if let myView = stackView.subviews.first {
stackView.removeArrangedSubview(myView)
stackView.setNeedsLayout()
stackView.layoutIfNeeded()
stackView.insertArrangedSubview(myView, at: 1)
stackView.setNeedsLayout()
}
尝试使用这组代码替换 UIStackView 中的视图,而不刷新任何布局。
if let objView = stackView.arrangedSubviews.first {
objView.removeFromSuperview()
}
stackView.insertArrangedSubview(yourView, at: 0)
这个解决方案非常有效。
每次调用它都会改变第一个堆栈元素视图和最后一个堆栈元素视图,反之亦然。
if let first = stackView.subviews.first, let last = stackView.subviews.last {
stackView.subviews.forEach { [=10=].removeFromSuperview() }
stackView.insertArrangedSubview(last, at: 0)
stackView.insertArrangedSubview(first, at: 1)
stackView.setNeedsLayout()
stackView.layoutIfNeeded()
}
如果使用水平轴:
stackView.semanticContentAttribute = .forceRightToLeft
如果使用垂直轴:
import UIKit
enum VerticalSemanticContentAttribute {
case forceTopToBottom, forceBottomToTop
}
final class VerticalStackView: UIStackView {
var verticalSemanticContentAttribute: VerticalSemanticContentAttribute = .forceTopToBottom {
didSet {
guard oldValue != verticalSemanticContentAttribute else { return }
reverseArrangedSubviews()
}
}
override init(frame: CGRect) {
super.init(frame: frame)
axis = .vertical
}
required init(coder: NSCoder) {
super.init(coder: coder)
axis = .vertical
}
}
// MARK: - Private functions
private extension VerticalStackView {
func reverseArrangedSubviews() {
let totalCount = arrangedSubviews.count
for (index, view) in arrangedSubviews.enumerated().reversed() where index != 0 { // we don't need to reposition the last item. It's already in the right position
removeArrangedSubview(view)
view.removeFromSuperview()
setNeedsLayout()
layoutIfNeeded()
let insertIndex = totalCount - index - 1
insertArrangedSubview(view, at: insertIndex)
setNeedsLayout()
layoutIfNeeded()
}
}
}
包含文本字段数组的堆栈视图嵌入到滚动视图中。我想更改某些操作中文本字段的顺序。删除和添加文本字段的方式会导致视图失真。我还通过从滚动视图中删除进行了测试。正常的堆栈视图也没有正确显示交换。我正在使用索引进行更改:
stackView.removeArrangedSubview(localityTF)
stackView.insertArrangedSubview(localityTF, at: 2)
这是一种奇怪的行为,但自动布局系统存在问题,应该先更新该系统,然后才能将 localityTF 添加回来。也不要忘记 removeArrangedSubview
不会从子视图数组中删除视图:
[self.stackView removeArrangedSubview:_label1];
[self.stackView setNeedsLayout];
[self.stackView layoutIfNeeded];
[self.stackView insertArrangedSubview:_label1 atIndex:2];
[self.stackView setNeedsLayout];
这是我在Swift3中的解决方案。也可以在stackview中不定义view的情况下使用
在这里,我正在更改具有两个视图的 Stackview 的视图位置:
if let myView = stackView.subviews.first {
stackView.removeArrangedSubview(myView)
stackView.setNeedsLayout()
stackView.layoutIfNeeded()
stackView.insertArrangedSubview(myView, at: 1)
stackView.setNeedsLayout()
}
尝试使用这组代码替换 UIStackView 中的视图,而不刷新任何布局。
if let objView = stackView.arrangedSubviews.first {
objView.removeFromSuperview()
}
stackView.insertArrangedSubview(yourView, at: 0)
这个解决方案非常有效。 每次调用它都会改变第一个堆栈元素视图和最后一个堆栈元素视图,反之亦然。
if let first = stackView.subviews.first, let last = stackView.subviews.last {
stackView.subviews.forEach { [=10=].removeFromSuperview() }
stackView.insertArrangedSubview(last, at: 0)
stackView.insertArrangedSubview(first, at: 1)
stackView.setNeedsLayout()
stackView.layoutIfNeeded()
}
如果使用水平轴:
stackView.semanticContentAttribute = .forceRightToLeft
如果使用垂直轴:
import UIKit
enum VerticalSemanticContentAttribute {
case forceTopToBottom, forceBottomToTop
}
final class VerticalStackView: UIStackView {
var verticalSemanticContentAttribute: VerticalSemanticContentAttribute = .forceTopToBottom {
didSet {
guard oldValue != verticalSemanticContentAttribute else { return }
reverseArrangedSubviews()
}
}
override init(frame: CGRect) {
super.init(frame: frame)
axis = .vertical
}
required init(coder: NSCoder) {
super.init(coder: coder)
axis = .vertical
}
}
// MARK: - Private functions
private extension VerticalStackView {
func reverseArrangedSubviews() {
let totalCount = arrangedSubviews.count
for (index, view) in arrangedSubviews.enumerated().reversed() where index != 0 { // we don't need to reposition the last item. It's already in the right position
removeArrangedSubview(view)
view.removeFromSuperview()
setNeedsLayout()
layoutIfNeeded()
let insertIndex = totalCount - index - 1
insertArrangedSubview(view, at: insertIndex)
setNeedsLayout()
layoutIfNeeded()
}
}
}