Cocoa NSView, изменяющий свойства автосохранения

Используя построитель интерфейсов, вы можете выбрать углы, которые должен придерживаться объект при изменении размера. Как вы можете сделать это программно?

Interface Builder

Ответы

Ответ 2

Я обнаружил, что маски autoresizingBit имеют ужасное имя, поэтому я использую категорию в NSView, чтобы сделать вещи более явными:

// MyNSViewCategory.h:
@interface NSView (myCustomMethods)

- (void)fixLeftEdge:(BOOL)fixed;
- (void)fixRightEdge:(BOOL)fixed;
- (void)fixTopEdge:(BOOL)fixed;
- (void)fixBottomEdge:(BOOL)fixed;
- (void)fixWidth:(BOOL)fixed;
- (void)fixHeight:(BOOL)fixed;

@end


// MyNSViewCategory.m:
@implementation NSView (myCustomMethods)

- (void)setAutoresizingBit:(unsigned int)bitMask toValue:(BOOL)set
{
    if (set)
    { [self setAutoresizingMask:([self autoresizingMask] | bitMask)]; }
    else
    { [self setAutoresizingMask:([self autoresizingMask] & ~bitMask)]; }
}

- (void)fixLeftEdge:(BOOL)fixed
{ [self setAutoresizingBit:NSViewMinXMargin toValue:!fixed]; }

- (void)fixRightEdge:(BOOL)fixed
{ [self setAutoresizingBit:NSViewMaxXMargin toValue:!fixed]; }

- (void)fixTopEdge:(BOOL)fixed
{ [self setAutoresizingBit:NSViewMinYMargin toValue:!fixed]; }

- (void)fixBottomEdge:(BOOL)fixed
{ [self setAutoresizingBit:NSViewMaxYMargin toValue:!fixed]; }

- (void)fixWidth:(BOOL)fixed
{ [self setAutoresizingBit:NSViewWidthSizable toValue:!fixed]; }

- (void)fixHeight:(BOOL)fixed
{ [self setAutoresizingBit:NSViewHeightSizable toValue:!fixed]; }

@end

который затем можно использовать следующим образом:

[someView fixLeftEdge:YES];
[someView fixTopEdge:YES];
[someView fixWidth:NO];

Ответ 3

Каждый вид имеет маску флагов, контролируемую настройкой свойства autoresizingMask с OR поведений, которые вы хотите от изменяющих размер. Кроме того, надстройка должна быть настроена на изменить размеры своих подзонов.

Наконец, в дополнение к основным параметрам изменения размера маски вы можете полностью контролировать макет субвью, реализуя - resizeSubviewsWithOldSize:

Ответ 4

Ответ на

@e.James дал мне идею просто создать новое перечисление с более знакомым наименованием:

typedef NS_OPTIONS(NSUInteger, NSViewAutoresizing) {
    NSViewAutoresizingNone                 = NSViewNotSizable,
    NSViewAutoresizingFlexibleLeftMargin   = NSViewMinXMargin,
    NSViewAutoresizingFlexibleWidth        = NSViewWidthSizable,
    NSViewAutoresizingFlexibleRightMargin  = NSViewMaxXMargin,
    NSViewAutoresizingFlexibleTopMargin    = NSViewMaxYMargin,
    NSViewAutoresizingFlexibleHeight       = NSViewHeightSizable,
    NSViewAutoresizingFlexibleBottomMargin = NSViewMinYMargin
};

Кроме того, из моего исследования я обнаружил, что @James.s имеет серьезную ошибку в добавлениях NSView. Система координат в Cocoa имеет перевернутую ось y в терминах iOS-координат система. Следовательно, чтобы зафиксировать нижнее и верхнее поля, вы должны написать:

- (void)fixTopEdge:(BOOL)fixed
{ [self setAutoresizingBit:NSViewMaxYMargin toValue:!fixed]; }

- (void)fixBottomEdge:(BOOL)fixed
{ [self setAutoresizingBit:NSViewMinYMargin toValue:!fixed]; }

Из Cocoa docs:

NSViewMinYMargin

The bottom margin between the receiver and its superview is flexible.
Available in OS X v10.0 and later.