Представления
Поскольку объекты представления являются основным способом, которым Ваше приложение взаимодействует с пользователем, у них есть много ответственности. Вот только некоторые:
Расположение и управление подпредставлением
Представление определяет свои собственные способы поведения изменения размеров значения по умолчанию в связи с его родительским представлением.
Представление может управлять списком подпредставлений.
Представление может переопределить размер и позицию его подпредставлений по мере необходимости.
Представление может преобразовать точки в своей системе координат к системам координат других представлений или окна.
Рисование и анимация
Представление рисует содержание в своей прямоугольной области.
Некоторые свойства представления могут быть анимированы к новым значениям.
Обработка событий
Представление может получить сенсорные события.
Представление участвует в цепочке респондента.
Эта глава фокусируется на шагах для создания, управления и рисования представлений и для обработки расположения и управления иерархиями представления. Для получения информации о том, как обработать сенсорные события (и другие события) в Ваших представлениях, посмотрите Руководство по Обработке событий для iOS.
Создание и конфигурирование объектов представления
Вы создаете представления как автономные объекты или программно или использующий Интерфейсного Разработчика, и затем Вы собираете их в иерархии представления для использования.
Создание объектов представления Используя интерфейсного разработчика
Самый простой способ создать представления состоит в том, чтобы собрать их графически использующий Интерфейсного Разработчика. От Интерфейсного Разработчика можно добавить представления к интерфейсу, расположить те представления в иерархии, сконфигурировать настройки каждого представления и подключить связанные с представлением способы поведения к коду. Поскольку Интерфейсный Разработчик использует объекты предпросмотра в реальном времени — т.е. фактические экземпляры классов представления — что Вы видите во время проектирования, то, что Вы получаете во время выполнения. Вы тогда сохраняете те живые объекты в файле пера, который является файлом ресурсов, сохраняющим состояние и конфигурацию Ваших объектов.
Вы обычно создаете файлы пера для хранения всей иерархии представления для одного из контроллеров представления приложения. Верхний уровень файла пера обычно содержит единственный объект представления, представляющий Ваше представление контроллера представления. (Сам контроллер представления обычно представляется объектом Владельца Файла.) Представление верхнего уровня должно быть измерено соответственно для целевого устройства и содержать все другие представления, которые должны быть представлены. Редко использовать файл пера для хранения только части иерархии представления контроллера представления.
При использовании файлов пера с целью контроллер, все, что необходимо сделать, инициализируют контроллер представления с информацией о файле пера. Контроллер представления обрабатывает загрузку и разгрузку Ваших представлений в подходящее время. Однако, если Ваш файл пера не связан с целью контроллер, можно загрузить содержание файла пера вручную с помощью NSBundle
или UINib
объект, которые используют данные в файле пера для перераспределения объектов представления.
Для получения дополнительной информации о том, как использовать Интерфейсного Разработчика, чтобы создать и сконфигурировать Ваши представления, см. Интерфейсное Руководство пользователя Разработчика. Для получения информации о том, как контроллеры представления загружают и управляют своими связанными файлами пера, видят Создающий Пользовательский Довольный Контроллеры Представления в поле зрения Руководство по программированию Контроллера для iOS. Для получения дополнительной информации о том, как загрузить представления программно из файла пера, посмотрите Файлы Пера в Руководстве по программированию Ресурса.
Создание представления возражает программно
Если Вы предпочитаете создавать представления программно, можно сделать настолько использующий стандартный образец выделения/инициализации. Метод инициализации по умолчанию для представлений initWithFrame:
метод, устанавливающий начальный размер и позицию представления относительно (скоро, чтобы быть установленным) родительское представление. Например, для создания нового обобщения UIView
объект, Вы могли использовать код, подобный следующему:
CGRect viewRect = CGRectMake(0, 0, 100, 100); |
UIView* myView = [[UIView alloc] initWithFrame:viewRect]; |
После создания представления необходимо добавить его к окну (или к другому представлению в окне), прежде чем это сможет стать видимым. Для получения информации о том, как добавить представления к Вашей иерархии представления, посмотрите Добавление и Удаление Подпредставлений.
Установка свойств представления
UIView
класс имеет несколько заявленных свойств для управления появлением и поведением представления. Эти свойства для управления размером и позицией представления, прозрачности представления, ее цвета фона и ее поведения рендеринга. Все эти свойства имеют надлежащие значения по умолчанию, которые можно изменить позже по мере необходимости. Можно также сконфигурировать многие из этих свойств от Интерфейсного Разработчика, использующего окно Inspector.
Таблица 3-1 перечисляет некоторые более обычно используемые свойства (и некоторые методы) и описывает их использование. Связанные свойства перечислены вместе так, чтобы Вы видели опции, которые Вы имеете для влияния на определенные аспекты представления.
Свойства | Использование |
---|---|
Эти свойства влияют на непрозрачность представления. | |
Эти свойства влияют на размер и позицию представления. Для получения информации об отношении между | |
Эти свойства влияют на автоматическое поведение изменения размеров представления и его подпредставлений. | |
Эти свойства влияют на поведение рендеринга содержания в представлении. Для получения дополнительной информации о том, как режим содержания влияет на Ваше представление, посмотрите Режимы Содержания. Для получения информации о том, как довольное прямоугольник фрагмента влияет на Ваше представление, посмотрите Поддающиеся растягиванию Представления. Для получения информации о том, как обработать масштабные коэффициенты, посмотрите Поддерживающие Экраны С высокой разрешающей способностью В Представлениях в Рисовании и Печати Руководства для iOS. | |
| Эти свойства влияют, как Ваше представление обрабатывает сенсорные события. Для получения информации о том, как реагировать на события в Ваших представлениях, посмотрите Руководство по Обработке событий для iOS. |
| Эти свойства и методы помогают Вам управлять фактическим содержанием своего представления. Для простых представлений можно выбрать цвет фона и добавить одно или более подпредставлений. Для более усовершенствованного содержания можно работать непосредственно с Базовой Анимацией представления |
Для получения информации об основных свойствах, характерных для всех представлений, см. Ссылку класса UIView. Для получения дополнительной информации об определенных свойствах представления, см. справочную документацию для того представления.
Тегирование представлений для будущей идентификации
UIView
класс содержит a tag
свойство, которое можно использовать для тегирования отдельных объектов представления с целочисленным значением. Можно использовать теги, чтобы однозначно определить представления в иерархии представления и выполнить поиски тех представлений во время выполнения. (Основанные на теге поиски быстрее, чем итерация иерархии представления самостоятельно.) Значение по умолчанию для tag
свойство 0
.
Для поиска маркированного представления используйте viewWithTag:
метод UIView
. Этот метод выполняет поиск в глубину получателя и его подпредставления. Это не ищет суперпредставления или другие части иерархии представления. Таким образом вызов этого метода от корневого представления иерархии ищет все представления в иерархии, но вызов его от определенного подпредставления ищет только подмножество представлений.
Создание и управление иерархией представления
Управление иерархиями представления является ключевой ролью разработки пользовательского интерфейса Вашего приложения. Организация Ваших представлений влияет и на визуальное появление Вашего приложения и как Ваше приложение реагирует на изменения и события. Например, отношения отцов и детей в иерархии представления определяют, какие объекты могли бы обработать определенное сенсорное событие. Точно так же отношения отцов и детей определяют, как каждое представление реагирует на интерфейсные изменения ориентации.
Рисунок 3-1 показывает пример того, как разделение на уровни представлений создает желаемый визуальный эффект для приложения. В случае приложения Часов иерархия представления составлена из смеси представлений, полученных из других источников. Панель вкладок и представления навигации являются специальными иерархиями представления, предоставленными панелью вкладок, и контроллер навигации возражает для управления частями полного пользовательского интерфейса. Все между теми панелями принадлежит пользовательской иерархии представления, которую обеспечивает приложение Часов.
Существует несколько способов создать иерархии представления в приложениях для iOS, включая графически в Интерфейсном Разработчике и программно в Вашем коде. Следующие разделы показывают Вам, как собрать Ваши иерархии представления и, сделав это, как найти представления в иерархии и преобразовать между системами координат другого представления.
Добавление и удаление подпредставлений
Интерфейсный Разработчик является наиболее удобным способом создать иерархии представления, потому что Вы собираете свои представления графически, посмотрите отношения между представлениями и посмотрите точно, как те представления появятся во время выполнения. При использовании Интерфейсного Разработчика Вы сохраняете свою получающуюся иерархию представления в файле пера, который Вы загружаете во время выполнения, поскольку необходимы соответствующие представления.
Если Вы предпочитаете создавать свои представления программно вместо этого, Вы создаете и инициализируете их и затем используете следующие методы для расположения их в иерархии:
Для добавления подпредставления к родителю вызовите
addSubview:
метод родительского представления. Этот метод добавляет подпредставление до конца списка родителя подпредставлений.Для вставки подпредставления посреди списка родителя подпредставлений вызовите любой из
insertSubview:...
методы родительского представления. Вставка подпредставления посреди списка визуально помещает то представление позади любых представлений, прибывающих позже в список.Для переупорядочения существующих подпредставлений в их родителе вызовите
bringSubviewToFront:
,sendSubviewToBack:
, илиexchangeSubviewAtIndex:withSubviewAtIndex:
методы родительского представления. Используя эти методы быстрее, чем удаление подпредставлений и перевставка их.Для удаления подпредставления из его родителя вызовите
removeFromSuperview
метод подпредставления (не родительское представление).
При добавлении подпредставления к его родителю текущий прямоугольник кадра подпредставления обозначает свою начальную позицию в родительском представлении. Подпредставление, кадр которого находится за пределами видимых границ своего суперпредставления, не отсекается по умолчанию. Если Вы хотите, чтобы Ваше подпредставление было отсечено к границам суперпредставления, необходимо явно установить clipsToBounds
свойство суперпредставления к YES
.
Наиболее распространенный пример добавления подпредставления к другому представлению происходит в application:didFinishLaunchingWithOptions:
метод почти каждого приложения. Перечисление 3-1 показывает версию этого метода, устанавливающего представление от основного контроллера представления приложения в окно приложения. И окно и контроллер представления сохранены в основном файле пера приложения, загружающемся, прежде чем метод вызывают. Однако иерархия представления, которой управляет контроллер представления, фактически не загружается до view
к свойству получают доступ.
Перечисление 3-1 , Добавляющее представление к окну
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions |
{ |
// Override point for customization after application launch. |
// Add the view controller's view to the window and display. |
[window addSubview:viewController.view]; |
[window makeKeyAndVisible]; |
return YES; |
} |
Другое общее место, где Вы могли бы добавить подпредставления к иерархии представления, находится в loadView
или viewDidLoad
методы контроллера представления. При создании представлений программно Вы вставляете свой код создания представления loadView
метод Вашего контроллера представления. Создаете ли Вы свои представления программно или загружаете их из файла пера, Вы могли бы включать дополнительный код конфигурации представления в viewDidLoad
метод.
Перечисление 3-2 показывает viewDidLoad
метод TransitionsViewController
класс от UICatalog: Создание и Настройка Средства управления UIKit (Obj-C и Swift) пример приложения. TransitionsViewController
класс управляет анимациями, связанными с переходом между двумя представлениями. Начальная иерархия представления приложения (состоящий из корневого представления и панели инструментов) загружается из файла пера. Код в viewDidLoad
метод впоследствии создает контейнерное представление, и представления изображения раньше управляли переходами. Цель контейнерного представления состоит в том, чтобы упростить код, должен был реализовать анимации перехода между этими двумя представлениями изображения. Контейнерное представление не имеет никакого реального собственного содержания.
Добавление перечисления 3-2 просматривает к существующей иерархии представления
- (void)viewDidLoad |
{ |
[super viewDidLoad]; |
self.title = NSLocalizedString(@"TransitionsTitle", @""); |
// create the container view which we will use for transition animation (centered horizontally) |
CGRect frame = CGRectMake(round((self.view.bounds.size.width - kImageWidth) / 2.0), |
kTopPlacement, kImageWidth, kImageHeight); |
self.containerView = [[[UIView alloc] initWithFrame:frame] autorelease]; |
[self.view addSubview:self.containerView]; |
// The container view can represent the images for accessibility. |
[self.containerView setIsAccessibilityElement:YES]; |
[self.containerView setAccessibilityLabel:NSLocalizedString(@"ImagesTitle", @"")]; |
// create the initial image view |
frame = CGRectMake(0.0, 0.0, kImageWidth, kImageHeight); |
self.mainView = [[[UIImageView alloc] initWithFrame:frame] autorelease]; |
self.mainView.image = [UIImage imageNamed:@"scene1.jpg"]; |
[self.containerView addSubview:self.mainView]; |
// create the alternate image view (to transition between) |
CGRect imageFrame = CGRectMake(0.0, 0.0, kImageWidth, kImageHeight); |
self.flipToView = [[[UIImageView alloc] initWithFrame:imageFrame] autorelease]; |
self.flipToView.image = [UIImage imageNamed:@"scene2.jpg"]; |
} |
Когда Вы добавляете подпредставление к другому представлению, UIKit уведомляет и родительские и дочерние представления изменения. При реализации пользовательских представлений можно прервать эти уведомления путем переопределения один или больше willMoveToSuperview:
, willMoveToWindow:
, willRemoveSubview:
, didAddSubview:
, didMoveToSuperview
, или didMoveToWindow
методы. Можно использовать эти уведомления, чтобы обновить любую информацию состояния, связанную с иерархией представления или выполнить дополнительные задачи.
После создания иерархии представления можно переместиться по нему программно использование superview
и subviews
свойства Ваших представлений. window
свойство каждого представления содержит окно, в котором то представление в настоящее время выводится на экран (если таковые имеются). Поскольку корневое представление в иерархии представления не имеет никакого родителя, superview
свойство установлено в nil
. Для представлений, которые являются в настоящее время экранными, объект окна является корневым представлением иерархии представления.
Сокрытие представлений
Для сокрытия представления визуально можно или установить скрытый
свойство к YES
или изменение alpha
свойство к 0.0
. Скрытое представление не получает сенсорные события от системы. Однако скрытые представления действительно участвуют в автоизменении размеров и других операциях расположения, связанных с иерархией представления. Таким образом, если Вы планируете показать представления снова в некоторый момент скоро, сокрытие представления часто является удобной альтернативой удалению представлений от Вашей иерархии представления, особенно.
Если Вы хотите анимировать переход представления от видимого до скрытого (или реверс), необходимо сделать настолько использующий представление alpha
свойство. hidden
свойство не является animatable свойством, таким образом, любые изменения, которые Вы вносите в него, сразу вступают в силу.
Определение местоположения представлений в иерархии представления
Существует два способа определить местоположение представлений в иерархии представления:
Указатели хранилища на любые соответствующие представления в надлежащем расположении, такой как в контроллере представления, которому принадлежат представления.
Присвойте уникальное целое число каждому представлению
tag
свойство и использованиеviewWithTag:
метод для определения местоположения его.
Хранение ссылок на соответствующие представления является наиболее распространенным подходом к определению местоположения представлений и делает доступ к тем представлениям очень удобным. При использовании Интерфейсного Разработчика для создания представлений, можно соединить объекты в файле пера (включая объект Владельца Файла, представляющий управляющий объект контроллера) друг другу использующему выходы. Для представлений Вы создаете программно, можно сохранить ссылки на те представления в переменных члена парламента, не занимающего официального поста. Используете ли Вы выходы или переменные члена парламента, не занимающего официального поста, Вы ответственны за сохранение представлений по мере необходимости и затем выпуск их также. Лучший способ гарантировать объекты сохранен и выпущен, должным образом должен использовать объявленные свойства.
Теги являются полезным способом сократить трудно кодированные зависимости и поддерживать более динамические и гибкие решения. Вместо того, чтобы хранить указатель на представление, Вы могли определить местоположение его с помощью его тега. Теги являются также более персистентным способом относиться к представлениям. Например, если бы Вы хотели сохранить список представлений, которые в настоящее время видимы в Вашем приложении, то Вы выписали бы теги каждого видимого представления к файлу. Это более просто, чем архивация фактических объектов представления, особенно в ситуациях, где Вы отслеживаете только, какие представления в настоящее время видимы. Когда Ваше приложение впоследствии загружается, Вы тогда воссоздали бы свои представления и использовали бы сохраненный список тегов, чтобы установить видимость каждого представления, и таким образом возвратить Вашу иерархию представления ее предыдущему состоянию.
Перевод, масштабируясь и поворачивая представления
Каждое представление имеет связанное аффинное преобразование, которое можно использовать для перевода, масштабировать, или повернуть содержание представления. Представление преобразовывает, изменяются, финал представил появление представления и часто используется для реализации прокрутки, анимаций или других визуальных эффектов.
transform
свойство UIView
содержит a CGAffineTransform
структура с трансформациями для применения. По умолчанию это свойство установлено в идентификационные данные, преобразовывают, который не изменяет появление представления. Можно присвоить новое преобразование этому свойству в любое время. Например, для вращения представления на 45 градусов Вы могли использовать следующий код:
// M_PI/4.0 is one quarter of a half circle, or 45 degrees. |
CGAffineTransform xform = CGAffineTransformMakeRotation(M_PI/4.0); |
self.view.transform = xform; |
Применение преобразования в предыдущем коде к представлению повернуло бы то представление по часовой стрелке о его центральной точке. Рисунок 3-2 показывает, как эта трансформация посмотрела бы, если бы это было применено к представлению изображения, встроенному в приложение.
При применении многократных трансформаций к представлению, порядку, в котором Вы добавляете те трансформации к CGAffineTransform
структура является значительной. Вращение представления и затем перевод его не являются тем же как переводом представления и затем вращением его. Даже если суммы вращения и перевода являются тем же в каждом случае, последовательность трансформаций влияет на конечные результаты. Кроме того, любые трансформации, которые Вы добавляете, применяются к представлению относительно его центральной точки. Таким образом применение фактора вращения поворачивает представление вокруг своей центральной точки. Масштабирование представления изменяет ширину и высоту представления, но не изменяет его центральную точку.
Для получения дополнительной информации о создании и использовании аффинных преобразований, посмотрите, Преобразовывает в Кварц 2D Руководство по программированию.
Преобразование координат в иерархии представления
Неоднократно, особенно при обработке событий, приложение, возможно, должно преобразовать координатные значения от одной системы отсчета до другого. Например, сенсорные события сообщают о расположении каждого касания в системе координат окна, но просматривают объекты, часто нуждаются в той информации в системе локальной координаты представления. UIView
класс определяет следующие методы для преобразования координат к и от системы локальной координаты представления:
convert...:fromView:
методы преобразовывают координаты от системы координат некоторого другого представления до системы локальной координаты (прямоугольник границ) текущего представления. С другой стороны, convert...:toView:
методы преобразовывают координаты из системы локальной координаты текущего представления (прямоугольник границ) к системе координат указанного представления. Если Вы указываете nil
как ссылочный ракурс для любого из методов, преобразования сделаны и от системы координат окна, содержащего представление.
В дополнение к UIView
методы преобразования, UIWindow
класс также определяет несколько методов преобразования. Эти методы подобны UIView
версии за исключением того, что вместо того, чтобы преобразовать в и от системы локальной координаты представления, эти методы преобразовывают в и от системы координат окна.
При преобразовании координат в повернутых представлениях UIKit преобразовывает прямоугольники под предположением, что Вы хотите, чтобы возвращенный прямоугольник отразил экранную область, покрытую исходным прямоугольником. Рисунок 3-3 показывает пример того, как вращения могут заставить размер прямоугольника изменяться во время преобразования. В числе внешнее родительское представление содержит повернутое подпредставление. Преобразование прямоугольника в системе координат подпредставления к системе координат родителя приводит к прямоугольнику, который физически больше. Этот прямоугольник большего размера является фактически наименьшим прямоугольником в границах outerView
это полностью включает повернутый прямоугольник.
Корректировка размера и позиции представлений во время выполнения
Каждый раз, когда размер представления изменяется, размер и позиция его подпредставлений должны измениться соответственно. UIView
класс поддерживает и автоматическое и ручное расположение представлений в иерархии представления. С автоматическим расположением Вы устанавливаете правила, за которыми должно следовать каждое представление, когда его родительское представление изменяет размеры, и затем забудьте об изменении размеров операций в целом. С ручным расположением Вы вручную корректируете размер и позицию представлений по мере необходимости.
Быть подготовленным к изменениям макета
Изменения макета могут произойти каждый раз, когда любое из следующих событий происходит в представлении:
Размер прямоугольных изменений границ представления.
Интерфейсное изменение ориентации происходит, который обычно инициировал изменение в прямоугольнике границ корневого представления.
Набор Базовых подуровней Анимации, связанных с изменениями слоя представления и, требует расположения.
Ваше приложение вынуждает расположение произойти путем вызова
setNeedsLayout
илиlayoutIfNeeded
метод представления.Ваше приложение вызывает расположение путем вызова
setNeedsLayout
метод объекта нижележащего слоя представления.
Обработка изменений макета автоматически Используя автоизменение размеров правил
При изменении размера представления позиция и размер любых встроенных подпредставлений обычно должны изменяться для учета нового размера их родителя. autoresizesSubviews
свойство из суперпредставления определяет, изменяют ли подпредставления размеры вообще. Если это свойство установлено в YES
, представление использует autoresizingMask
свойство каждого подпредставления, чтобы определить, как измерить и расположить то подпредставление. Изменения размера в любых подпредставлениях инициировали подобные настройки макета для своих встроенных подпредставлений.
Для каждого представления в Вашей иерархии представления, устанавливая, что представление autoresizingMask
свойство к надлежащему значению является важной частью обработки автоматических изменений макета. Таблица 3-2 перечисляет опции автоизменения размеров, Вы можете примениться к высказанному мнению и описываете их эффекты во время операций расположения. Можно объединить константы с помощью операции ИЛИ или просто добавить их вместе прежде, чем присвоить их autoresizingMask
свойство. При использовании Интерфейсного Разработчика для сборки представлений, Вы используете инспектора Автокалибровки для установки этих свойств.
Автоизменение размеров маски | Описание |
---|---|
Представление не автоизменяет размеры. (Это - значение по умолчанию.) | |
Когда высота суперпредставления изменяется, высота представления изменяется. Если эта константа не включена, высота представления не изменяется. | |
Изменения представления width, когда изменения суперпредставления width. Если эта константа не включена, представление width не изменяется. | |
Расстояние между левым краем представления и левым краем суперпредставления растет или уменьшается по мере необходимости. Если эта константа не включена, левый край представления остается фиксированным расстоянием от левого края суперпредставления. | |
Расстояние между правым краем представления и правым краем суперпредставления растет или уменьшается по мере необходимости. Если эта константа не включена, правый край представления остается фиксированным расстоянием от правого края суперпредставления. | |
Расстояние между базовым краем представления и базовым краем суперпредставления растет или уменьшается по мере необходимости. Если эта константа не включена, базовый край представления остается фиксированным расстоянием от базового края суперпредставления. | |
Расстояние между главным краем представления и главным краем суперпредставления растет или уменьшается по мере необходимости. Если эта константа не включена, главный край представления остается фиксированным расстоянием от главного края суперпредставления. |
Рисунок 3-4 показывает графическое представление того, как опции в маске автоизменения размеров применяются к представлению. Присутствие данной константы указывает, что указанный аспект представления гибок и может измениться, когда изменяются границы суперпредставления. Отсутствие константы указывает, что расположение представления фиксируется в том аспекте. Когда Вы конфигурируете представление, имеющее больше чем один гибкий атрибут вдоль единственной оси, UIKit распределяет любые изменения размера равномерно среди соответствующих пробелов.
Самый простой способ сконфигурировать правила автоизменения размеров использует средства управления Автокалибровкой в инспекторе Размера Интерфейсного Разработчика. Гибкие константы ширины и высоты от предыдущей фигуры имеют то же поведение как ширина и индикаторы размера в схеме средств управления Автокалибровкой. Однако поведение и использование граничных индикаторов эффективно инвертируются. В Интерфейсном Разработчике присутствие граничного индикатора означает, что поле имеет фиксированный размер, и отсутствие индикатора означает, что поле имеет гибкий размер. К счастью, Интерфейсный Разработчик обеспечивает анимацию, чтобы показать Вам, как изменения в способах поведения автоизменения размеров влияют на Ваше представление.
После того, как автоматические правила автоизменения размеров для всех затронутых представлений были применены, UIKit возвращается и высказывает каждое мнение шанс внести любые необходимые ручные корректировки в его суперпредставление. Для получения дополнительной информации о том, как управлять расположением представлений вручную, посмотрите Тонкую настройку Расположения Ваших Представлений Вручную.
Тонкая настройка расположения представлений вручную
Каждый раз, когда размер представления изменяется, UIKit применяет способы поведения автоизменения размеров подпредставлений того представления и затем вызывает layoutSubviews
метод представления, чтобы позволить ему внести ручные изменения. Можно реализовать layoutSubviews
метод в пользовательских представлениях, когда способы поведения автоизменения размеров собой не приводят к результатам, Вы хотите. Ваша реализация этого метода может сделать любое следующее:
Скорректируйте размер и позицию любых непосредственных подпредставлений.
Добавьте или удалите подпредставления или Базовые Слои анимации.
Вынудите подпредставление быть перерисованным путем вызова
setNeedsDisplay
илиsetNeedsDisplayInRect:
метод.
Одно место, где приложения часто размечают подпредставления вручную, при реализации большой области с возможностью прокрутки. Поскольку это непрактично для имения единственного большого представления для его содержания с возможностью прокрутки, приложения часто реализуют корневое представление, содержащее много меньших представлений мозаики. Каждая мозаика представляет часть содержания с возможностью прокрутки. Когда случай прокрутки происходит, корневое представление вызывает setNeedsLayout
метод для инициирования изменения макета. layoutSubviews
метод тогда меняет местоположение представлений мозаики на основе суммы произошедшей прокрутки. Поскольку мозаики прокручивают из видимой области представления, layoutSubviews
метод перемещает мозаики во входящий край, заменяя их содержание в процессе.
При записи кода расположения, убедиться протестировать код следующими способами:
Измените ориентацию своих представлений для проверки взглядов расположения, корректных во всех поддерживаемых интерфейсных ориентациях.
Удостоверьтесь, что Ваш код соответственно реагирует на изменения в высоте строки состояния. Когда стороны пользователя вызов, строка состояния уменьшается в размере, когда телефонный вызов активен, увеличения высоты строки состояния размера, и.
Для получения информации о том, как автоизменение размеров способов поведения влияет на размер и позицию Ваших представлений, видит Изменения макета Обработки Автоматически Используя Автоизменение размеров Правил. Для примера того, как реализовать мозаичное размещение, посмотрите выборку ScrollViewSuite.
Изменение представлений во время выполнения
Поскольку приложения получают ввод от пользователя, они корректируют свой пользовательский интерфейс в ответ на тот ввод. Приложение могло бы изменить свои представления путем реконструкции их, изменения их размера или позиции, сокрытия или показа им или загрузки полностью нового набора представлений. В приложениях для iOS существует несколько мест и путей, которыми Вы выполняете эти виды действий:
В контроллере представления:
Контроллер представления должен создать свои представления прежде, чем показать им. Это может загрузить представления из файла пера или создать их программно. Когда те представления больше не необходимы, это избавляется от них.
Когда устройство изменяет ориентации, контроллер представления мог бы скорректировать размер и позицию представлений для соответствия. Как часть его корректировки новой ориентации, это могло бы скрыть некоторые представления и показать другим.
Когда контроллер представления управляет доступным для редактирования содержанием, он мог бы скорректировать свою иерархию представления при перемещении в и от режима редактирования. Например, это могло бы добавить дополнительные кнопки и другие средства управления для упрощения редактирующих различных аспектов его содержания. Это могло бы также потребовать, чтобы изменение размеров любых существующих представлений разместило дополнительные средства управления.
В блоках анимации:
Когда Вы хотите перейти между различными наборами представлений в Вашем пользовательском интерфейсе, Вы скрываете некоторые представления и показываете другим из блока анимации.
При реализации специальных эффектов Вы могли бы использовать блок анимации для изменения различных свойств представления. Например, для анимации изменений в размере представления Вы изменили бы размер его прямоугольника кадра.
Другие пути:
Когда сенсорные события или жесты происходят, Ваш интерфейс мог бы ответить путем загрузки нового набора представлений или изменения текущего набора представлений. Для получения информации об обработке событий посмотрите Руководство по Обработке событий для iOS.
Когда пользователь взаимодействует с представлением прокрутки, большая область с возможностью прокрутки могла бы скрыть и показать подпредставления мозаики. Для получения дополнительной информации о поддержке содержания с возможностью прокрутки, см. Руководство по программированию Представления Прокрутки для iOS.
Когда клавиатура появляется, Вы могли бы изменить местоположение или изменить размеры представлений так, чтобы они не лежали под клавиатурой. Для получения информации о том, как взаимодействовать с клавиатурой, см. текстовое Руководство по программированию для iOS.
Контроллеры представления являются общим местом для инициирования изменений в представлениях. Поскольку контроллер представления управляет иерархией представления, связанной с выводимым на экран содержанием, это в конечном счете ответственно за все, что происходит с теми представлениями. При загрузке его представлений или обработке изменений ориентации, контроллер представления может добавить новые представления, скрыть или заменить существующие и сделать любое число изменений для создания представлений готовыми к дисплею. И если Вы реализуете поддержку редактирования содержания Вашего представления, setEditing:animated:
метод в UIViewController
дает Вам место для перехода представлений к и от их доступных для редактирования версий.
Блоки анимации являются другим общим местом для инициирования связанных с представлением изменений. Поддержка анимации, созданная в UIView
класс упрощает анимировать изменения для просмотра свойств. Можно также использовать transitionWithView:duration:options:animations:completion:
или transitionFromView:toView:duration:options:completion:
методы для выгрузки всех наборов представлений для новых.
Для получения дополнительной информации об анимации представлений и инициировании переходов представления, посмотрите Анимации. Для получения дополнительной информации о том, как Вы используете контроллеры представления, чтобы управлять связанными с представлением способами поведения, видеть Руководство по программированию Контроллера Представления для iOS.
Взаимодействие с базовыми слоями анимации
Каждый объект представления имеет специализированный Базовый Слой анимации, управляющий представлением и анимацией содержания представления на экране. Несмотря на то, что можно сделать много с объектами представления, можно также работать непосредственно с соответствующими расположенными на слое объектами по мере необходимости. Расположенный на слое объект для представления сохранен в представлении layer
свойство.
Изменение класса уровня, связанного с целью
Тип уровня, связанного с целью, не может быть изменен после того, как представление создается. Поэтому каждое представление использует layerClass
метод класса указать класс его расположенного на слое объекта. Реализация по умолчанию этого метода возвращается CALayer
класс и единственный способ изменить это значение должны разделить на подклассы, переопределить метод и возвратить различное значение. Можно изменить это значение для использования различного вида уровня. Например, если Ваше мозаичное размещение использования представления для отображения большой области с возможностью прокрутки Вы могли бы хотеть использовать CATiledLayer
класс для поддержки представления.
Реализация layerClass
метод должен просто создать желаемое Class
объект и возврат это. Например, представление, что мозаичное размещение использования имело бы следующую реализацию для этого метода:
+ (Class)layerClass |
{ |
return [CATiledLayer class]; |
} |
Каждое представление вызывает layerClass
метод рано в его процессе инициализации и использовании возвращенный класс для создания его расположенного на слое объекта. Кроме того, представление всегда присваивает себя как делегат его расположенного на слое объекта. В этой точке представлению принадлежат его уровень и отношение между представлением, и уровень не должен изменяться. Вы не должны также присваивать то же представление как делегат никакого другого расположенного на слое объекта. Изменение владения или отношений делегата представления вызовет проблемы получения и потенциальные катастрофические отказы в Вашем приложении.
Для получения дополнительной информации о различных типах расположенных на слое объектов, предоставленных Базовой Анимацией, посмотрите Базовый Ссылочный Набор Анимации.
Встраивание расположенных на слое объектов в представлении
Если Вы предпочитаете работать прежде всего с расположенными на слое объектами вместо представлений, можно включить пользовательские расположенные на слое объекты в иерархию представления по мере необходимости. Пользовательский расположенный на слое объект является любым экземпляром CALayer
это не принадлежит представлению. Вы обычно создаете пользовательские уровни программно и включаете их использующий Базовые подпрограммы Анимации. Пользовательские уровни не получают события или участвуют в цепочке респондента, но действительно привлекают себя и реагируют на изменения размера в их родительском представлении или уровне согласно Базовым правилам Анимации.
Перечисление 3-3 показывает пример viewDidLoad
метод от контроллера представления, создающего пользовательский расположенный на слое объект и добавляющего его к его корневому представлению. Уровень используется для отображения анимированного статического изображения. Вместо того, чтобы добавить уровень к самому представлению, Вы добавляете его к нижележащему слою представления.
Перечисление 3-3 , Добавляющее пользовательский уровень к представлению
- (void)viewDidLoad { |
[super viewDidLoad]; |
// Create the layer. |
CALayer* myLayer = [[CALayer alloc] init]; |
// Set the contents of the layer to a fixed image. And set |
// the size of the layer to match the image size. |
UIImage layerContents = [[UIImage imageNamed:@"myImage"] retain]; |
CGSize imageSize = layerContents.size; |
myLayer.bounds = CGRectMake(0, 0, imageSize.width, imageSize.height); |
myLayer = layerContents.CGImage; |
// Add the layer to the view. |
CALayer* viewLayer = self.view.layer; |
[viewLayer addSublayer:myLayer]; |
// Center the layer in the view. |
CGRect viewBounds = backingView.bounds; |
myLayer.position = CGPointMake(CGRectGetMidX(viewBounds), CGRectGetMidY(viewBounds)); |
// Release the layer, since it is retained by the view's layer |
[myLayer release]; |
} |
Если Вы хотите, можно добавить любое число подуровней и расположить их в иерархии подуровня. Однако в некоторый момент те уровни должны быть присоединены к расположенному на слое объекту представления.
Для получения информации о том, как работать с уровнями непосредственно, см. Базовое Руководство по программированию Анимации.
Определение пользовательского представления
Если стандартные системные представления не делают точно, в чем Вы нуждаетесь, можно определить пользовательское представление. Пользовательские представления дают Вам полный контроль над появлением содержания Вашего приложения и как обрабатываются взаимодействия с тем содержанием.
Контрольный список для реализации пользовательского представления
Задание пользовательского представления должно представить содержание и управлять взаимодействиями с тем содержанием. Успешное внедрение пользовательского представления включает больше, чем просто рисование и обработка событий, все же. Следующий контрольный список включает более важные методы, которые можно переопределить (и способы поведения, которые можно обеспечить) при реализации пользовательского представления:
Определите надлежащие методы инициализации для своего представления:
Для представлений Вы планируете создать программно, переопределить
initWithFrame:
метод или определяет пользовательский метод инициализации.Для представлений Вы планируете загрузиться от файлов пера, переопределить
initWithCoder:
метод. Используйте этот метод, чтобы инициализировать Ваше представление и поместить его в известное состояние.
Реализация a
dealloc
метод для обработки очистки любых пользовательских данных.Для обработки любого пользовательского получения переопределите
drawRect:
метод и делает Ваше получение там.Установите
autoresizingMask
свойство представления для определения его поведения автоизменения размеров.Если Ваш класс представления управляет одним или более интегральными подпредставлениями, сделайте следующее:
Создайте те подпредставления во время последовательности инициализации своего представления.
Установите
autoresizingMask
свойство каждого подпредставления во время создания.Если Ваши подпредставления требуют пользовательского макета, переопределяют
layoutSubviews
метод и реализация Ваш код расположения там.
Для обработки сенсорных событий сделайте следующее:
Присоедините любые подходящие устройства распознавания жеста к представлению при помощи
addGestureRecognizer:
метод.Для ситуаций, где Вы хотите обработать касания сами, переопределите
touchesBegan:withEvent:
,touchesMoved:withEvent:
,touchesEnded:withEvent:
, иtouchesCancelled:withEvent:
методы. (Помните, что необходимо всегда переопределятьtouchesCancelled:withEvent:
метод, независимо от которого другие связанные с касанием методы Вы переопределяете.)
Если Вы хотите, чтобы печатная версия Вашего представления отличалась от экранной версии, реализуйте
drawRect:forViewPrintFormatter:
метод. Для получения дальнейшей информации о том, как поддерживать печать в Ваших представлениях, см. Рисование и Печать Руководства для iOS.
В дополнение к методам переопределения помните, что существует много, можно сделать с существующими свойствами и методами представления. Например, contentMode
и contentStretch
свойства позволяют, Вы изменить финал представили появление своего представления и могли бы быть предпочтительны для перерисовки содержания сами. В дополнение к UIView
сам класс, существует много аспектов базового представления CALayer
возразите, что можно сконфигурировать прямо или косвенно. Можно даже изменить класс самого расположенного на слое объекта.
Для получения дополнительной информации о методах и свойствах класса представления, см. Ссылку класса UIView.
Инициализация пользовательского представления
Каждое новое представление возражает, что Вы определяете, должен включать пользовательское initWithFrame:
метод инициализатора. Этот метод ответственен за инициализацию класса во время создания и помещение Вашего объекта представления в известное состояние. Вы используете этот метод при создании экземпляров представления программно в коде.
Перечисление 3-4 показывает скелетную реализацию стандарта initWithFrame:
метод. Это вызовы метода наследованная реализация метода сначала и затем инициализирует переменные экземпляра и информацию состояния класса прежде, чем возвратить инициализированный объект. Вызов наследованной реализации традиционно выполняется сначала так, чтобы, если существует проблема, можно прервать собственный код инициализации и возврат nil
.
Перечисление 3-4 , Инициализирующее подкласс представления
- (id)initWithFrame:(CGRect)aRect { |
self = [super initWithFrame:aRect]; |
if (self) { |
// setup the initial properties of the view |
... |
} |
return self; |
} |
Если Вы планируете загрузить экземпляры своего пользовательского класса представления от файла пера, необходимо знать, что в iOS, загружающий перо код не использует initWithFrame:
метод для инстанцирования новых объектов представления. Вместо этого это использует initWithCoder:
метод, который является частью NSCoding
протокол.
Даже если Ваше представление принимает NSCoding
протокол, Интерфейсный Разработчик не знает о пользовательских свойствах Вашего представления и поэтому не кодирует те свойства в файл пера. В результате Ваше собственное initWithCoder:
метод должен выполнить любой код инициализации, это может для помещения представления в известное состояние. Можно также реализовать awakeFromNib
метод в Вашем классе представления и использовании, что метод для выполнения дополнительной инициализации.
Реализация Вашего кода для прорисовки
Для представлений, которые должны сделать пользовательское получение, необходимо переопределить drawRect:
метод и делает Ваше получение там. Пользовательское получение рекомендуется только как последнее прибежище. В целом, если можно использовать другие представления для представления предпочтенного содержания.
Реализация Вашего drawRect:
метод должен сделать точно одну вещь: нарисуйте свое содержание. Этот метод не является местом, чтобы обновить структуры данных Вашего приложения или выполнить любые задачи, не связанные с получением. Это должно сконфигурировать среду получения, нарисовать Ваше содержание и выход как можно быстрее. И если Ваш drawRect:
метод можно было бы часто вызывать, необходимо сделать все, что Вы можете, чтобы оптимизировать Ваш код для прорисовки и нарисовать как можно меньше каждый раз, когда метод вызывают.
Прежде, чем вызвать Ваше представление drawRect:
метод, UIKit конфигурирует основную среду получения для Вашего представления. В частности это создает графический контекст и корректирует систему координат и область отсечения для соответствия системы координат и видимых границ представления. Таким образом, к этому времени Ваш drawRect:
метод вызывают, можно начать рисовать Ваш довольный собственный компонент использования рисование технологий, таких как UIKit и Базовая Графика. Можно получить указатель на текущий графический контекст с помощью UIGraphicsGetCurrentContext
функция.
Перечисление 3-5 показывает простую реализацию a drawRect:
метод, рисующий красную границу 10 пикселей шириной вокруг представления. Поскольку операции рисования UIKit используют Базовую Графику для своих конкретных реализаций, можно смешать вызовы получения, как показано здесь, для получения результатов, которые Вы ожидаете.
Перечисление 3-5 метод рисования
- (void)drawRect:(CGRect)rect { |
CGContextRef context = UIGraphicsGetCurrentContext(); |
CGRect myFrame = self.bounds; |
// Set the line width to 10 and inset the rectangle by |
// 5 pixels on all sides to compensate for the wider line. |
CGContextSetLineWidth(context, 10); |
CGRectInset(myFrame, 5, 5); |
[[UIColor redColor] set]; |
UIRectFrame(myFrame); |
} |
Если Вы знаете, что код для прорисовки Вашего представления всегда покрывает всю поверхность представления с непрозрачным содержанием, можно улучшить производительность системы путем установки непрозрачный
свойство из Вашего представления к YES
. Когда Вы отмечаете представление как непрозрачное, UIKit избегает рисовать содержание, сразу расположенное позади Вашего представления. Это не только сокращает количество времени, потратил получение, но также и минимизирует работу, которая должна быть выполнена для составления композита представления с другим содержанием. Однако необходимо установить это свойство в YES
только если Вы знаете, что содержание Вашего представления абсолютно непрозрачно. Если Ваше представление не может гарантировать, что его содержание всегда непрозрачно, необходимо установить свойство в NO
.
Другой способ улучшить производительность получения, особенно во время прокрутки, состоит в том, чтобы установить clearsContextBeforeDrawing
свойство Вашего представления к NO
. Когда это свойство установлено в YES
, UIKIt автоматически заполняет область, которая будет обновлена Вашим drawRect:
метод с прозрачным черным цветом прежде, чем вызвать Ваш метод. Установка этого свойства к NO
устраняет издержки для той операции заполнения, но помещает нагрузку в Ваше приложение для заполнения, прямоугольник обновления передал Вашему drawRect:
метод с содержанием.
Ответ на события
Объекты представления являются объектами респондента — экземпляры UIResponder
класс — и поэтому способен к получению сенсорных событий. Когда сенсорное событие имеет место, окно диспетчеризирует соответствующий объект-событие представлению, в котором произошло касание. Если Ваше представление не интересуется событием, оно может проигнорировать его или передать его цепочка респондента, которая будет обработана различным объектом.
В дополнение к обработке сенсорных событий непосредственно, представления могут также использовать устройства распознавания жеста для обнаружения касаний, сильно ударяет, повышения и другие типы общих связанных с касанием жестов. Устройства распознавания жеста выполняют тяжелую работу отслеживания сенсорных событий и удостоверяясь, что они следуют за правильными критериями для квалификации их как целевого жеста. Вместо Вашего приложения, имеющего необходимость отслеживать сенсорные события, можно создать устройство распознавания жеста, присвоить надлежащий целевой объект и метод действия для него, и установить его на представлении с помощью addGestureRecognizer:
метод. Когда соответствующий жест происходит, устройство распознавания жеста тогда вызывает Ваш метод действия.
Если Вы предпочитаете обрабатывать сенсорные события непосредственно, можно реализовать следующие методы для представления, описанные более подробно в Руководстве по Обработке событий для iOS:
Поведение по умолчанию для представлений состоит в том, чтобы реагировать только на одно касание за один раз. Если пользователь подавляет второй палец, система игнорирует сенсорное событие и не сообщает о нем Вашему представлению. Если Вы планируете отследить жесты мультипальца от методов обработчика событий своего представления, необходимо включить мультисенсорные события путем установки multipleTouchEnabled
свойство из Вашего представления к YES
.
Некоторые представления, такие как метки и изображения, отключают обработку событий в целом первоначально. Можно управлять, в состоянии ли представление получить сенсорные события путем изменения значения представления userInteractionEnabled
свойство. Вы могли бы временно установить это свойство в NO
препятствовать тому, чтобы пользователь управлял содержанием Вашего представления, в то время как длинная работа находится на рассмотрении. Чтобы препятствовать тому, чтобы события достигли любого из Ваших представлений, можно также использовать beginIgnoringInteractionEvents
и endIgnoringInteractionEvents
методы UIApplication
объект. Эти методы влияют на поставку событий для целого приложения, не только для единственного представления.
Поскольку это обрабатывает сенсорные события, UIKit использует hitTest:withEvent:
и pointInside:withEvent:
методы UIView
определить, имело ли сенсорное событие место в границах высказанного мнения. Несмотря на то, что редко необходимо переопределять эти методы, Вы могли сделать так для реализации пользовательских сенсорных способов поведения для представления. Например, Вы могли переопределить эти методы, чтобы препятствовать тому, чтобы подпредставления обработали сенсорные события.
Очистка после представления
Если Ваш класс представления выделяет какую-либо память, хранит ссылки на какие-либо пользовательские объекты или содержит средства, которые должны быть высвобождены, когда представление выпущено, необходимо реализовать a dealloc
метод. Системные вызовы dealloc
метод, когда Ваше представление сохраняют количество, достигает нуля, и пора освободить представление. Ваша реализация этого метода должна выпустить любые объекты или ресурсы, сохраненные представлением, и затем вызвать наследованную реализацию, как показано в Перечислении 3-6. Вы не должны использовать этот метод для выполнения любых других типов задач.
Перечисление 3-6 реализовывая dealloc
метод
- (void)dealloc { |
// Release a retained UIColor object |
[color release]; |
// Call the inherited implementation |
[super dealloc]; |
} |