Для чего компании нужен UI KIT? (Frontend + Design)
В этой статье мы расскажем, что такое UI KIT, для чего он нужен, и как он сэкономит время и деньги.
В статье мы подойдем к китам, которые сделаны не только дизайнерами, но также переведены в компоненты фронтенд-разработчиками.
Что такое UI KIT?
Это единый набор элементов пользовательского интерфейса. Выглядят они примерно так:
Для чего он нужен?
1. Единый стиль всех проектов
Все ваши информационные системы будут идентичными. Клиенты будут узнавать вашу компанию по одинаковым элементам. Также им будет удобнее работать с каждым вашим новым продуктом, так как им будут знакомы все элементы и их поведение.
Начало проекта всегда подразумевает создание первых базовых элементов ui-kita на основе утвержденного концепта.
Основная причина — это унификация элементов интерфейса, что сокращает и упрощает работу в дальнейшем в сложных проектах, чтобы избежать ошибок в дальнейшем. И помогает скоординировать работу с разработчиками, чтобы получить дизайн единообразным на разных страницах одного проекта.
К счастью для нас прошло времена Photoshop и на рынке появилась для бога избранных Sketch (маководы ликуют), а уж позже Figma. Что в разы упростило работу для дизайнера. Всеми любимые компоненты позволили делать изменения в разы быстрее, буквально в один клик, что позволяет не бегать по всем экранам и не проверять, где там цвет поменялся, а где нет.
Андрей Залетов
Senior UI/UX designer KOTELOV
2. Экономия на разработке
Если нет кита, компании, нанимая подрядчика заполняют бриф, далее подрядчик разрабатывает с нуля дизайн, далее создает компоненты на фреймворках JavaScript (Angular, React, Vue). То есть заказчик каждый раз платит за дизайн и программирование одних и тех же элементов на фронтенде разным подрядчикам, причем элементы получаются у всех разные по дизайну и коду, что не позволяет масштабироваться. В случае с китом вы платите 1 раз.
3. Мгновенный доступ к UI KIT у всей команды
Аналитики, дизайнеры, разработчики имеют доступ к киту по ссылке. Могут самостоятельно ознакомиться со всеми элементами, правилами их использования и создавать прототипы, фронтенд и дизайн.
4. Скорость разработки
При готовом UI KIT вы имеете все элементы, такие как кнопки, поля ввода, таблицы, графики уже задизайнены и переведены в компоненты (на JS). Вы можете собирать системы, не тратя время на дизайн и разработку. Также упрощается прототипирование, если раньше вы составляли прототипы из простых форм, то сейчас можете собирать их из настоящего дизайна.
Почему важно делать UI KIT, если кнопку или поле можно отрисовать и запрограммировать достаточно быстро?
Большинству пользователей кнопка представляется, как всего лишь прямоугольник с текстом посередине:
Вот так выглядит код кнопки на React:
А вот так выглядит удобная кнопка, которая делает взаимодействие с системой удобной:
Так выглядит код кнопки здорового человека:
То есть разработка любого на первый взгляд простого элемента это продолжительная и дорогостоящая работа (если делать его удобным и масштабируемым), поэтому проще один раз отрисовать и запрограммировать каждый элемент и потом использовать его во всех проектах.
Можно ли использовать готовый UI KIT?
В интернете множество китов за небольшие деньги, что-то около 15$. Вы безусловно можете их использовать. Но они скорее подойдут для небольших проектов, которые не собираются далеко масштабироваться или же в вашей компании предполагается сделать одну систему, а не строить множество продуктов.
Основные причины для постройки, а не покупки UI KIT
1. Большие компании приводят все системы к единому виду, чтобы сотрудники и пользователи ориентировались легко в любой системе компании;
2. Компаниям необходимо соблюдать фирменный стиль;
3. При покупке UI KIT вам необходимо отталкиваться от технологий заложенных в купленном ките;
4. Купленный кит не может закрыть весь функционал систем, то есть вам необходимо будет дорисовывать его и дорабатывать;
5. Строя ui kit с нуля вы видите полноценно цель разработки. То есть сможете разрабатывать элементы исходя из задачи, делая каждый элемент удобнее.
Требования к разработчику UI KIT:
UI KIT разрабатывается только дизайнером и разработчиком уровня Senior, которые имеют опыт в подобных проектах. Дизайнер и фронтенд-разработчик должен обладать опытом и знаниями для построения сложных систем, так как ui kit будет использоваться около 5 лет всеми командами разработки вашей компании и привлекаемыми подрядчиками для большинства ваших систем.
UIKit ты вообще про UI?
Когда я начинал писать эту статью, хотелось рассказать много фундаментальных вещей. Одновременно с этим хотелось, чтобы она была понятна всем, поэтому я начал с описательной части. Со временем понял, что материала получается слишком много, и я решил разбить ее на несколько частей. Возможно какие-то вещи для вас покажутся совсем простыми и очевидными, но они нужны для того, чтобы хорошо разобраться и ориентироваться, как же все-таки устроен UI.
Так как же он устроен? У нас же есть базовый класс UIView и куча его стандартных наследников. Мы можем сами создавать свои вью и как угодно их кастомизировать. И все это видим на экране. Почему тогда UIKit и UIView – это не про графический интерфейс? Давайте разбираться.
1. Исторический экскурс
Вспомним, что же было до появления iPhone. Были маки – компьютеры на операционной системе macOS. Сейчас для нас очевидно, что это 2 разных пользовательских опыта – тыкать пальцем в экран и елозить мышкой по столу + стучать по клавишам на клавиатуре, но тогда перед инженерами Apple стояла задача взять механизм отрисовки интерфейса из мака и научить его в «Мультитач». И вот, что получилось:
Четкое разделение ответственности (привет, SOLID) позволило не дублировать код, а просто добавить новую надстройку, которая будет распознавать пользовательские жесты и обрабатывать их. А слой, который отвечает за отрисовку, остался общим. Круто? Круто!
Кстати, до версий Mac OS X 10.5 и iPhoneOS 2.0 CoreAnimation носил менее ориентированное на анимацию название – LayerKit.
2. Core Graphics & Metal
3. Responder Chain
Часто можно услышать, что базовым классом UIKit является UIView. Однако, если мы посмотрим на его реализацию, то увидим, что он является наследником UIResponder, что говорит о многом в назначении UIKit.
Респондер – это тот, кто отвечает на пользовательские жесты. Но как наша вью узнает, что пользователь нажал именно на нее и что ей нужно обработать этот экшн? Здесь нам на помощь приходит механизм Responder Chain.
Когда пользователь нажимает на экран это событие попадает в наше приложение (объект UIApplication). Дальше оно отправляется в UIWindow, где и запускается цепочка поиска firstResponder’а, в границах которого и было произведено нажатие. Цепочка запускается рекурсивным вызовом метода по всей иерархии дочерних вью:
Метод, который банально проверяет, находится ли точка в границах вью:
Если точка находится внутри вью, поиск продолжается уже среди своих дочерних вью, вызывая метод hitTest у них. Так продолжается пока не будет найдена самая нижняя в иерархии (самая верхняя на экране) вью, в которую попадает нажатие.
Если точка не находится внутри вью – возвращается nil.
Таким образом, наше корневое окно (объект UIWindow) находит вью-ферстреспондера и вызывает у него соответствующие методы:
Отдельно стоит отметить объекты UIGestureRecognizer. Они имеют больший приоритет, чем Responder Chain, и обрабатываются на этапе «погружения».
Кстати, у слоев тоже есть методы определения, попадает ли точка в границы слоя:
Подробнее про Responder Chain можно прочитать в статье.
4. UIView и CALayer
Если вью – это не про графический интерфейс, для чего у него так много свойств для управления внешним видом? Все просто: вью является контейнером слоя и предоставляет более высокоуровневое API для работы с внешним видом.
Мы привыкли визуализировать интерфейс в виде иерархии вью (дерево). А теперь давайте представим, что таких дерева 2 – дерево вью и дерево слоев. На самом деле их 4 (дерево слоев представлено 3 деревьями), но об это этом позже. Сейчас нам важны только 2.
Точно так же, как и вью, мы можем добавлять слои друг на друга и выстраивать целые иерархии. Все они складываются в свое дерево, не ограничиваясь той вью, которой они принадлежат. Обратите внимание, что все вью обязательно содержат слой, а вот слои могут существовать без привязки к какому-то вью. Это тоже очень важный момент, который мы разберем в разделе с анимацией.
Core Data + Swift для самых маленьких: необходимый минимум (часть 3)
Это заключительная часть статьи о Core Data, предыдущие части доступны здесь: часть 1 и часть 2.
В этой статье мы повернемся лицом к пользователю и поработаем над интерфейсной частью, помогать нам в этом будет NSFetchRequest и NSFetchedResultsController. Данная часть получилась довольно большой, но я не вижу смысла дробить ее на несколько публикаций. Аккуратнее, под катом много кода и картинок.
Интерфейс — вещь неоднозначная и, в зависимости от требования к продукту, может существенное меняться. В данной статье я не буду уделять ему слишком много времени, точнее говоря, буду уделять совсем мало (я имею ввиду следование Guidelines и тому подобное). Моя задача в данной части статьи состоит в том, чтобы показать, как Core Data может очень органично вписаться в элементы управления iOS. Поэтому я буду использовать для этих целей такой интерфейс, при использовании которого взаимодействие элементов управления и Core Data будет выглядеть проще и нагляднее. Очевидно, что в реальном приложении интерфейсной части надо будет посвятить гораздо больше времени.
Справочники
Прежде чем начать, давайте придадим модулю делегата приложения ( AppDelegate.swift ), в котором мы экспериментировали в прошлой части статьи, первоначальный вид.
Я не буду здесь использовать Prototype Cells и создавать «кастомный» класс для ячеек таблицы (чтобы сосредоточиться на других вещах), поэтому давайте установим количество таких ячеек равным нулю ( Attributes Inspector\Table View\Prototype Cells ).
Теперь нам требуется определить источник данных, чтобы реализовать протокол Table View Data Source. В прошлой части мы познакомились с NSFetchRequest и, на первый взгляд, он вроде как подходит для этой цели. С его помощью можно получить список всех объектов в виде массива, что, собственно, нам и нужно. Но мы хотим не только смотреть на список Заказчиков, мы хотим их добавлять, удалять и редактировать. В этом случае, нам придется отслеживать все эти изменения вручную и каждый раз, опять вручную, обновлять наш список. Звучит не очень, да? Но есть другой вариант — NSFetchedResultsController, он очень похож на NSFetchRequest, но он не только возвращает массив нужных нам объектов в момент запроса, но и продолжает следить за всеми записями: если какая-то запись измениться — он нам сообщит об этом, если какие-нибудь записи подгрузятся в фоне через другой управляемый контекст — он нам тоже сообщит об этом. Нам останется только обработать это событие.
Давайте реализуем NSFetchedResultsController в нашем модуле. Я сначала приведу весь код, а следом прокомментирую.
Затем, при загрузке нашего View Controller ( func viewDidLoad() ) мы запускаем fetchedResultsController на выполнение:
Прежде чем продолжать, давайте кое-что немного оптимизируем — создание объекта NSFetchedResultsController не отличается лаконичностью, а нам его надо будет также создавать и для других наших сущностей. При этом, по сути, меняться будет только имя сущности и, возможно, имя поля сортировки. Чтобы не заниматься «копи-пастой» давайте вынесем создание этого объекта в CoreDataManager.
С учетом этого, определение fetchedResultsController измениться на следующее:
Теперь нам надо сделать так, чтобы при выборе какого-нибудь Заказчика открывалась «карточка» со всеми его данными, которые, при необходимости, можно было редактировать. Давайте для этого добавим еще один View Controller (зададим ему заголовок «Customer» ) и соединим его с нашим Table View Controller.
И указываем этот класс для нашего нового View Controller.
Теперь добавим Navigation Bar с двумя кнопками (Save — для сохранения изменений и Cancel — для отмены). Также нам необходимы два текстовых поля для отображения и редактирования информации (name и info). Сделаем два Action (для Save и Cancel) и два Outlet (для name и info).
Также, нам надо учесть то, что у нас есть обязательное для заполнение поле — name. Если пользователь попробует сохранить Заказчика с пустым именем, то он получит критическую ошибку. Чтобы этого не произошло, давайте добавим проверку корректности сохраняемых данных: если данные не корректные, то будем показывать соответствующую предупреждение и блокировать запись такого объекта. Пользователь должен либо ввести корректные данные, либо отказаться от записи такого объекта.
И последнее, что нам надо здесь учесть: наверняка, нам захочется не только редактировать существующих Заказчиков, но и добавлять новых. Делать это мы будем следующим образом: в списке Заказчиков добавим кнопку для создания нового Заказчика, которая будет открывать нашу «карточку» передавая в нее nil. А при сохранении данных «карточки» Заказчика мы будем проверять, если объект customer у нас еще не создан (то есть это ввод нового Заказчика), то будем его сразу создавать.
Таким образом, у нас получиться примерно следующий код.
Этот Action будет открывать «карточку» для создания нового Заказчика, передавая в нее nil.
Осталось сделать так, чтобы при выборе какого-нибудь существующего Заказчика, открывалась его «карточка». Для этого нам понадобиться две процедуры.
В первой процедуре (при выделении строки списка) мы «считываем» текущего Заказчика, а во второй (при переходе из списка в «карточку») — присваиваем ссылку на выбранного Заказчика переменной customer нашей «карточки», чтобы при ее открытии мы могли считать все данные объекта.
Давайте теперь запустим наше приложение и убедимся, что все работает как надо.
Приложение работает, мы можем вводить новых Заказчиков, редактировать существующих, но информация в списке автоматически не обновляется и у нас нет механизма, чтобы удалять ненужного (или ошибочно введенного) Заказчика. Давайте это исправим.
Так как мы здесь используем NSFetchedResultsController, который «знает» о всех этих изменениях, то нам надо просто его «послушать». Для этого надо реализовать протокол делегата NSFetchedResultsControllerDelegate. Объявим, что мы реализуем этот протокол:
Объявим себя делегатом NSFetchedResultsController:
И добавим следующую реализацию этого протокола:
Осталось только реализовать удаление Заказчика. Это делается довольно просто, нам понадобиться переопределить всего одну небольшую процедуру.
На этом работа со справочником «Заказчики» завершена. Давайте запустим приложение и проверим его работу.
Как видете, ничего сверхсложного, Core Data прекрасно сочетается со стандартными элементами интерфейса.
Справочник «Услуги»
iOS с нуля с Swift: первые шаги с UIKit
UIKit — это фреймворк, который вы будете использовать чаще всего при разработке приложений для iOS. Он определяет основные компоненты приложения iOS, от ярлыков и кнопок до табличных представлений и контроллеров навигации. В этой статье мы не только начнем исследование фреймворка UIKit, но также рассмотрим внутреннюю часть проекта iOS и основные строительные блоки приложений iOS.
Что такое UIKit Framework?
В то время как платформа Foundation определяет классы, протоколы и функции для разработки под iOS и OS X, платформа UIKit предназначена исключительно для разработки под iOS. Это эквивалент Application Kit или платформы AppKit для разработки под OS X.
Категории Objective C — удобный способ добавить дополнительные методы к существующим классам без необходимости создавать подклассы. Они похожи на расширения Swift. Прочтите этот урок от Аарона Крабтри, если вы хотите узнать больше о категориях Objective-C.
Вместо того, чтобы исследовать ключевые классы UIKit, как мы это делали для платформы Foundation, мы собираемся создать новый проект для iOS и исследовать классы, с которыми мы сталкиваемся. При таком подходе быстро станет ясно, в каком контексте используется класс, как каждый класс вписывается в более широкую схему приложения iOS и какую роль он играет.
Новое начало
Шаблон приложения Single View содержит основные строительные блоки приложения для iOS, что делает его хорошим местом для начала нашего путешествия.
Файлы и папки
С тех пор, как мы в последний раз создавали проект iOS с нуля, мы узнали немало нового, поэтому неплохо было бы изучить различные файлы и папки нашего нового проекта, чтобы узнать, не звонят ли они в колокол.
В Навигаторе проекта вы должны увидеть две папки в корне проекта:
Давайте посмотрим на содержимое каждой из этих папок.
Товары
Вы заметили, что FirstSteps .app выделен красным? Всякий раз, когда Xcode не может найти файл, он выделяет файл красным цветом. Не беспокойся, хотя. Поскольку проект еще не скомпилирован, Xcode еще не создал продукт.
Папка проекта
Assets.xcassets — это специальный тип папки для хранения ресурсов вашего проекта, таких как изображения.
Компоненты приложения
Модель Модель-Вид-Контроллер
Прежде чем мы начнем исследовать инфраструктуру UIKit, я хочу поговорить о шаблоне Model-View-Controller (MVC). Шаблон MVC является одним из самых распространенных шаблонов в объектно-ориентированном программировании. Он способствует повторному использованию кода и имеет тесные связи с концепцией разделения обязанностей или интересов. Одной из основных целей шаблона MVC является отделение бизнес-логики приложения от уровня представления.
Cocoa Touch охватывает шаблон MVC, что означает, что важно понимать, что это такое и как оно работает. Другими словами, благодаря пониманию шаблона MVC будет гораздо легче понять, как различные компоненты приложения iOS работают вместе.
В шаблоне MVC уровень модели контролирует бизнес-логику приложения. Например, взаимодействие с базой данных является обязанностью модельного уровня. Уровень представления представляет данные, которыми управляет уровень модели, пользователю. Уровень представления управляет пользовательским интерфейсом и пользовательским вводом.
Контроллер — это клей между слоем модели и слоем вида. В то время как уровень модели и уровень представления не знают о существовании друг друга, контроллер знает об обоих.
Поскольку контроллер знает о модели и представлении, это часто наименее многократно используемая часть приложения. Чем меньше объект знает о своей среде и объектах, с которыми он взаимодействует, тем легче его повторно использовать.
UIApplication
Экземпляр UIApplication является точкой входа для взаимодействия с пользователем и отправляет события соответствующим целевым объектам. Точный смысл этого станет ясен через несколько минут, когда мы посмотрим на контроллеры представления.
Шаблон делегата
Шаблон делегата широко используется в Cocoa и Cocoa Touch. В будущей статье этой серии, в которой мы рассмотрим все входы и выходы табличных представлений, вы обнаружите, что табличные представления в значительной степени зависят от шаблона делегата (и источника данных).
Как и шаблон MVC, делегирование является распространенным в объектно-ориентированном программировании. Шаблон делегата в Cocoa Touch, однако, немного отличается, поскольку он использует протокол делегата для определения поведения объекта делегата.
Давайте прыгнем вперед и посмотрим на таблицы. Если вы провели какое-то время с iPhone или iPad, то класс UITableView должен быть вам знаком. Он представляет упорядоченный список данных пользователю, и он делает эту работу очень хорошо.
Первые шаги с UIKit
Russian (Pусский) translation by Liliya (you can also view the original English article)
Что такое структура UIKit?
В то время как платформа Foundation определяет классы, протоколы и функции для разработки под iOS и OS X, платформа UIKit предназначена исключительно для разработки под iOS. Это эквивалент Application Kit или платформы AppKit для разработки под OS X.
Вместо того, чтобы исследовать ключевые классы UIKit, как мы это делали для платформы Foundation, мы создадим и пройдемся по новому проекту iOS и исследуем классы, с которыми мы сталкиваемся. При таком подходе быстро станет ясно, в каком контексте используется класс и как каждый класс вписывается в более широкую схему приложения iOS и какую роль он играет.
Новое начало
Шаблон Single View Application содержит основные строительные блоки приложения iOS и поэтому является хорошим местом для начала нашего путешествия.

Назовите проект UIKit и введите название организации и идентификатор компании. Введите префикс класса, как я объяснял ранее в этой серии, и установите «Устройства» на iPhone.

Сообщите Xcode, где вы хотите сохранить новый проект, и убедитесь, что проект находится под контролем версий, установив флажок Create git repository on My Mac. Посетите эту статью для получения дополнительной информации о контроле версий и его преимуществах.

Файлы и папки
Мы узнали много нового с тех пор, как в прошлый раз создавали проект для iOS с нуля, поэтому неплохо было бы изучить различные файлы и папки нашего нового проекта, чтобы узнать, не звонят ли они в колокол.
В Project Navigator вы должны увидеть три папки в корне проекта;
Давайте посмотрим на содержимое каждого из этих папок.

Продукция
Папка Products в настоящее время содержит два элемента. Первый элемент носит имя нашего проекта и имеет расширение .app. Имя второго элемента оканчивается на Tests и имеет расширение .xctest. Я не буду описывать юнит-тесты в этой серии, поэтому вы можете пока игнорировать второй пункт.
Папка Products содержит приложение или приложения, созданные проектом после компиляции исходного кода.
Вы заметили, что UIKit.app будет выделена красным цветом? Всякий раз, когда Xcode не может найти файл, он выделяет файл красным цветом. Поскольку проект еще не скомпилирован, Xcode еще не создал продукт.
Структура
Папка Frameworks содержит рамки, с которыми связан проект. В предыдущей статье наш проект был связан только со структурой Foundation. Этот проект, однако, основан на шаблоне приложения iOS и поэтому связан с четырьмя структурами: Foundation, UIKit, Core Graphics и XCTest.
Возможно, вы помните базовую графическую платформу из этой серии. Каркас содержит интерфейсы для API-интерфейса (Quartz) 2D-рисования. Фреймворк XCTest связан с модульным тестированием, о котором я не буду рассказывать в этой серии.
В нашем проекте есть еще одно место, которое определяет, с какими структурами связан проект. Выберите свой проект в Project Navigator, выберите единственный элемент в разделе Targets слева и откройте вкладку Build Phases вверху.
Открыв ящик Link Binary with Libraries, вы получаете тот же список структур, который мы видели в папке Frameworks. Связать наш проект с другой системной платформой iOS так же просто, как нажать кнопку «плюс» внизу списка и выбрать платформу из списка.

Папка проекта
Большая часть вашего времени проводится в папке проекта, которая в настоящее время содержит шесть файлов и одну папку с именем Supporting Files. Давайте начнем с рассмотрения содержимого папки «Вспомогательные файлы».
-Prefix.pch: Это предварительно скомпилированный заголовочный файл проекта, с которым мы уже сталкивались ранее в этой серии. Как следует из названия, файлы заголовков, перечисленные в предварительно скомпилированном файле заголовков, предварительно скомпилированы Xcode, что сокращает время, необходимое для компиляции вашего проекта. Структуры Foundation и UIKit меняются не очень часто, поэтому нет необходимости их компилировать каждый раз, когда вы компилируете свой проект. В дополнение к предварительной компиляции заголовочных файлов, перечисленных в предварительно скомпилированном заголовочном файле, каждый исходный файл в вашем проекте имеет префикс перечисленных заголовочных файлов.
Компоненты приложения
Model-View-Controller Pattern
Прежде чем мы начнем исследовать инфраструктуру UIKit, я хочу поговорить об образце Model-View-Controller (MVC). Шаблон MVC является одним из самых распространенных шаблонов в объектно-ориентированном программировании. Он способствует повторному использованию кода и имеет тесные связи с концепцией разделения обязанностей или интересов. Одной из основных целей шаблона MVC является отделение бизнес-логики приложения от уровня представления.
Cocoa Touch охватывает шаблон MVC, и поэтому важно понимать, что это такое и как оно работает. Другими словами, понимая шаблон MVC, будет намного легче понять, как различные компоненты приложения iOS работают вместе.
В образце MVC модель контролирует бизнес-логику приложения. Например, взаимодействие с базой данных является обязанностью модели. Представление представляет данные, которыми управляет модель, пользователю. Представление управляет пользовательским интерфейсом и пользовательским вводом.
Контроллер является связующим звеном между моделью и представлением. Хотя модель и представление не знают о существовании друг друга, контроллер знает как модель, так и представление.
Поскольку контроллер знает как о модели, так и о представлении, он часто является наименее повторно используемым компонентом приложения. Чем меньше объект знает о своей среде и объектах, с которыми он взаимодействует, тем выше его повторное использование в будущих проектах.
UIApplication
Когда приложение запускается, создается синглтон этого класса. Вы помните, что такое singleton object? Это означает, что только один экземпляр объекта класса UIApplication создается в течение времени жизни приложения.
Экземпляр UIApplication является точкой входа для взаимодействия с пользователем и отправляет события соответствующим целевым объектам. Точный смысл этого станет ясен через несколько минут, когда мы посмотрим на контроллеры представления.
В большинстве приложений iOS экземпляр UIApplication имеет связанный с ним объект делегата. Всякий раз, когда вы создаете проект iOS, используя один из предоставленных шаблонов, XCode создаст класс делегата приложения для вас. Посмотрите на имена исходных файлов в папке проекта в Project Navigator. Первые два файла называются TSPAppDelegate.
Шаблон делегата
Модель делегата широко используется в какао и Cocoa Touch. В следующей статье этой серии, в которой мы рассмотрим все входы и выходы табличного представления, вы обнаружите, что табличные представления в значительной степени зависят от шаблона делегата (и источника данных).
Как и шаблон MVC, делегирование является распространенным в объектно-ориентированном программировании. Однако шаблон делегата в Cocoa Touch немного отличается, потому что он использует протокол делегата для определения поведения объекта делегата.
Давайте прыгнем вперед и посмотрим на таблицы. Если вы провели какое-то время с iPhone или iPad, то класс UITableView должен быть вам знаком. Он представляет упорядоченный список данных пользователю и выполняет эту работу очень хорошо.
Источник данных табличного представления схож с точки зрения поведения. Основное отличие состоит в том, что табличное представление запрашивает объект источника данных о данных, которые ему необходимо отобразить.
Объекты делегата и источника данных, такие как объекты делегата и источника данных табличного представления, почти всегда являются настраиваемыми классами, классами, которые вы создаете, поскольку их реализация зависит от конкретного приложения.
Приложение делегат
Откройте файл заголовка класса TSPAppDelegate (TSPAppDelegate.h), чтобы проверить его содержимое. Если мы проигнорируем комментарии вверху, первая строка импортирует заголовочные файлы инфраструктуры UIKit, чтобы мы могли работать с ее классами и протоколами.
Раскадровка
Проект Xcode содержит еще один интересный файл, Main.storyboard. Раскадровка определяет, как будет выглядеть пользовательский интерфейс нашего приложения. По умолчанию раскадровка называется Main.storyboard. Выберите раскадровку, чтобы открыть ее.

В настоящее время раскадровка содержит один вид в центральной рабочей области. Справа от Project Navigator вы можете увидеть список элементов, которые являются объектами, которые вы видите в представлении. Верхний элемент называется View Controller Scene, который содержит один дочерний элемент, помеченный View Controller.
Объект View Controller также имеет несколько дочерних элементов, но есть один, который представляет для нас особый интерес, объект с именем View. Помните наше обсуждение образца MVC. Здесь вы можете увидеть шаблон MVC в действии. В данный момент модель отсутствует, но у нас есть представление, объект View и контроллер, объект View Controller.
Когда наше приложение запускается, раскадровка используется для создания пользовательского интерфейса приложения. Контроллер представления автоматически создается, как и представление контроллера представления. Объект View в раскадровке управляется контроллером представления.
Подожди минутку. Где я могу найти класс контроллера представления в раскадровке? Как я могу изменить его поведение, чтобы создать уникальное приложение? Выберите объект View Controller слева в раскадровке и откройте Identity Inspector справа.

Мы рассмотрим эти файлы через несколько минут. Это указано в раскадровке стрелкой, указывающей на раскадровку.

UIViewController
Контроллер представления управляет видом и его подвидом, как мы увидим позже. Для этого контроллеру представления необходимо знать о представлении. Другими словами, он должен иметь ссылку на представление.
Контроллер представления в раскадровке имеет ссылку на представление. +В этом можно убедиться, выбрав контроллер представления в раскадровке и открыв Connections Inspector справа.

UIView
Пересмотрите Main.storyboard, выбрав его, и посмотрите на Object Library в нижней части Inspector.

Просмотрите библиотеку объектов и перетащите метку и кнопку в представление в рабочей области. Неважно, где вы размещаете их в представлении, пока они находятся в представлении контроллера представления.

Outlets
Давайте рассмотрим пример, иллюстрирующий связь между раскадровкой, представлением, которое она содержит, и контроллером представления. Эти три компонента важны, и я хочу убедиться, что вы понимаете, как они работают вместе.
Несколько минут назад вы добавили метку и кнопку к представлению контроллера представления. Как контроллер представления узнает об этих объектах? На данный момент они не отображаются в Connections Inspector, но мы можем изменить это, сообщив о них контроллеру представления.
Откройте файл заголовка контроллера представления (TPSViewController.h) и добавьте свойство для метки и для кнопки.
Добавив ключевое слово IBOutlet в объявление свойства, свойства появятся в инспекторе соединений в раскадровке, и это то, что нам нужно.
Вернитесь к раскадровке, выберите объект View Controller в View Controller Scene и откройте Connections Inspector справа. Новые свойства теперь перечислены в списке Outlets. Однако контроллер представления еще не установил связь между новыми свойствами и объектами в раскадровке.
Это легко исправить. Перетащите курсор от пустого круга слева от выхода myLabel к метке в рабочей области. Это создаст это крайне важное соединение, чтобы контроллер представления знал о метке. Сделайте то же самое для кнопки.

Даже если мы можем изменить текст метки в раскадровке, давайте сделаем это в контроллере представления, чтобы проиллюстрировать, что контроллер представления имеет доступ к метке и кнопке в раскадровке.
Обратите внимание, что setText: является аксессором или сеттером. Несмотря на то, что можно использовать точечную нотацию Objective-C (см. Ниже), я использовал более традиционный синтаксис, поскольку он лучше показывает вам, что на самом деле происходит.
Запустите приложение в iOS Simulator, нажав кнопку Run в левом верхнем углу, и обратите внимание, что текст метки действительно обновлен.
Поведение
Посмотрим, как это работает. Откройте файл заголовка контроллера представления (TPSViewController.h) и добавьте следующее объявление метода где-нибудь в блоке интерфейса контроллера представления.
Еще раз зайдите в раскадровку, выберите объект View Controller в сцене View Controller и откройте Connections Inspector. В Connections Inspector появился новый раздел под названием Received Actions, и только что добавленное действие перечислено в этом разделе.

Перетащите из пустого круга слева от действия на кнопку в рабочей области. Должно появиться небольшое окно со списком параметров. Список содержит все возможные события, на которые может ответить кнопка. То, что нас интересует, это Touch Up Inside. Это событие вызывается, когда пользователь касается кнопки и поднимает палец, нажимая на кнопку.

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

Реализация метода changeColor: идентична той, которую мы использовали ранее в этой серии. Тем не менее, я добавил два дополнительных вызова NSLog к его реализации, чтобы показать вам, что отправитель сообщения действительно является кнопкой, которую мы добавили в раскадровку.
Обратите внимание, что self.view ссылается на представление, которым управляет контроллер представления и которое мы видели ранее в раскадровке.
Заключение
В этой статье мы рассмотрели несколько классов UIKit-структуру и подробно рассмотрели различные компоненты приложения для iOS. Мы будем исследовать и работать со структурой UIKit более подробно в оставшейся части этой серии.
Если вы не до конца понимаете различные концепции и модели, то я уверен, что вы поймете, как серии прогрессируют. Не стесняйтесь оставлять комментарии, если у вас есть вопросы по поводу этой статьи.





















