Странное поведение маски автоматического изменения размера

#ios #uiview #autoresizingmask

#iOS #uiview #Маска автоматического изменения размера

Вопрос:

Я нахожусь в UIViewController, self.view указывает на действительный вид с рамкой 300×480.

 UIView *redView;
UIView *blueView;

//[[self view] setAutoresizingMask:YES]; //WRONG!
[[self view] setAutoresizesSubviews:YES];
[[self view] setClipsToBounds:YES];

redView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, 200, 200)];

[redView setBackgroundColor:[UIColor redColor]];

[redView setAutoresizingMask:UIViewAutoresizingFlexibleLeftMargin];

[[self view] addSubview:redView];

blueView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, 100, 100)];

[blueView setBackgroundColor:[UIColor blueColor]];

[blueView setAutoresizingMask:UIViewAutoresizingFlexibleRightMargin];

[[self view] addSubview:blueView];
  

С помощью этого фрагмента кода я пытался

  1. Чтобы выровнять красный вид размером 200×200 по правому краю,
  2. Чтобы выровнять синий вид размером 100×100 по левому краю;

но результат, как вы можете видеть, далек от того, что я ожидал…

http://imageshack.us/photo/my-images/27/iossimulatorscreenshoto.png/

Я прочитал каждую часть документации Apple и каждый результат Google об использовании маски автоматического изменения размера, но я все еще не могу понять, почему это происходит.

Может кто-нибудь, пожалуйста, объяснить мне, что происходит?

Заранее спасибо.

Ответ №1:

Имейте в виду, что это маска автоматического изменения размера, а не маска автоматического изменения размера. Он ничего не делает, пока что-то не изменит размер.

Что вы хотите сделать, так это определить рамки ваших представлений именно там, где вы хотите, чтобы они были в соответствии с текущим размером вашего родительского представления, то есть 300 x 480. Так, например

 redView = [[UIView alloc] initWithFrame:CGRectMake(100, 0, 200, 200)];

blueView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, 100, 100)];
  

Вы правильно устанавливаете их маски автоматического изменения размера до выравнивания по горизонтали. Если self.view изменит размер, то redView и BlueView останутся заблокированными на полях.

Вы должны установить хотя бы одно из гибких верхних полей, гибких нижних полей или гибкой высоты. В противном случае поведение не определено, если родительский вид изменяет высоту. Невозможно, чтобы все три из этих параметров оставались фиксированными в пределах двух разных высот.

Эта строка кода не имеет смысла:

 [[self view] setAutoresizingMask:YES];
  

Это не ошибка компилятора, потому что BOOL может быть преобразован в UIViewAutoresizing, который является перечислением. В результате получается, что YES = 1 = UIViewAutoresizingFlexibleLeftMargin. Вероятно, не то, что вы хотели. Скорее всего, вы хотели:

 [[self view] setAutoresizingMask:UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight];
  

Если вы можете, вы должны сделать все это в Interface Builder. Поскольку это редактор WYSIWYG, вы можете использовать SWYG («посмотрим, что получится»). Вы можете быстро поиграть с опциями и узнать, как они работают. Намного быстрее, чем редактирование — компиляция — запуск, чтобы увидеть эффекты. Даже если вы не можете / не хотите использовать Interface Builder для своего проекта, попробуйте пример проекта с ним, чтобы узнать, как работает автоматическое изменение размера. Как только вы узнаете, вы сможете сделать это в коде с меньшим количеством проб и ошибок. Но обратите внимание на то, что включение полосы полей в Interface Builder эквивалентно отключению соответствующей опции FlexibleXYZMargin в коде.

Комментарии:

1. Извините, [[self view] setAutoresizingMask:YES]; на самом деле [[self view] setAutoresizesSubviews:YES]; это было. Я попробую настроить setAutoresizingMask [self view] . Есть ли какой-либо способ добавить вложенное представление, выровняв его по границе без указания позиции? Я хотел бы использовать как можно меньше ссылок на пиксели, потому что код будет выполняться как на iPhone, так и на iPad.

2. Также я заметил, что если я вхожу на экран в портретном режиме [[self view] frame] 320x460 , но если я вхожу на экран в альбомном режиме, это так 300x480 . Меня это немного смущает, потому что в альбомной ориентации я должен расположить объект (100, 0) так, чтобы он отображался в том виде, в каком должен был быть (280, 0) . Есть ли какая-либо причина?