Есть ли событие изменения размера UIView?
У меня есть представление, в котором есть строки и столбцы изображений.
Если это представление изменено, мне нужно изменить порядок изображений.
Это представление является подзором другого представления, которое изменяется.
Есть ли способ определить, когда изменяется этот вид?
Ответы
Ответ 1
Как сказал Ули ниже, правильный способ сделать это переопределить layoutSubviews
и разместить там изображения.
Если по какой-то причине вы не можете подклассифицировать и переопределить layoutSubviews
, то наблюдение bounds
должно работать, даже если оно грязно. Хуже того, существует риск наблюдать - Apple не гарантирует работу KVO на классах UIKit. Прочитайте обсуждение с инженером Apple здесь: Когда вызывается связанный объект?
оригинальный ответ:
Вы можете использовать наблюдение за ключом:
[yourView addObserver:self forKeyPath:@"bounds" options:0 context:nil];
и реализовать:
- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context
{
if (object == yourView && [keyPath isEqualToString:@"bounds"]) {
// do your stuff, or better schedule to run later using performSelector:withObject:afterDuration:
}
}
Ответ 2
В Swift вы можете:
override var bounds: CGRect {
didSet {
// Do stuff here
}
}
Ответ 3
Создайте подкласс UIView и переопределите layoutSubviews
Ответ 4
Вы можете создать подкласс UIView и переопределить
setFrame: (CGRect) кадр
метод. Это метод, вызываемый при изменении кадра (т.е. Размера) вида. Сделайте что-то вроде этого:
- (void) setFrame:(CGRect)frame
{
// Call the parent class to move the view
[super setFrame:frame];
// Do your custom code here.
}
Ответ 5
Довольно старый, но все же хороший вопрос. В образце кода Apple и в некоторых из их частных подклассов UIView они переопределяют setBounds примерно так:
-(void)setBounds:(CGRect)newBounds {
BOOL const isResize = !CGSizeEqualToSize(newBounds.size, self.bounds.size);
if (isResize) [self prepareToResizeTo:newBounds.size]; // probably saves
[super setBounds:newBounds];
if (isResize) [self recoverFromResizing];
}
Переопределение setFrame:
НЕ является хорошей идеей. frame
выводится из center
, bounds
и transform
, поэтому iOS не обязательно вызовет setFrame:
.
Ответ 6
Swift 4 keypath KVO - это то, как я обнаруживаю авторотирование и перемещение на панель iPad. Должно работать любое представление. Пришлось наблюдать слой UIView.
private var observer: NSKeyValueObservation?
override func viewDidLoad() {
super.viewDidLoad()
observer = view.layer.observe(\.bounds) { object, _ in
print(object.bounds)
}
// ...
}
override func viewWillDisappear(_ animated: Bool) {
observer?.invalidate()
//...
}
Ответ 7
Если вы находитесь в экземпляре UIViewController, переопределение viewDidLayoutSubviews
делает трюк.
override func viewDidLayoutSubviews() {
// update subviews
}