Принципы разработки гибких
и поддерживаемых интерфейсов
Вася Аксёнов
@outring
Разработка VS. Интерфейсы
3
Разработка
Реализация — абстрактные сущности
4
Интерфейсы
Реализация — визуальное представление
5
В чём разница?
Явность правил взаимодействия
Предопределённость сценариев взаимодействия
и сущностей
Гибкость и поддерживаемость
7
Гибкость
Возможность создания новых частей интерфейса
без необходимости внесения изменений в ранее
созданные части
8
Поддерживаемость
Возможность безопасного изменения интерфейса
1 SRP
Принцип единственной ответственности
10
Принцип единственной ответственности
Каждая сущность имеет только одну обязанность
Сущность должна иметь только одну
причину измениться
11
Скачать
12
Кнопка
.download-button {
! padding: 0 20px;
}
13
Размеры
.download-button {
! width: 230px;
! padding: 0 20px;
}
Позиционирование
.download-button {
! position: absolute;
! left: 50%;
! top: 50%;
! width: 230px;
! margin-top: -65px;
! margin-left: -135px;
! padding: 0 20px;
}
14
−padding
.download-button {
! position: absolute;
! left: 50%;
! top: 50%;
! width: 230px;
! margin-top: -65px;
! margin-left: -135px;
! padding: 0 20px;
}
15
16
Скачать
Скачать
17
Минусы
Необходимость изменения для
переиспользования
Сложность понимания ответственности
Небезопасность изменений
18
19
Решение
Распределение ответственности по разным
элементам
Или классам
20
Скачать
21
Функциональное разделение
по элементам
Только одна причина
изменения сущности
2 Предсказуемые раскладки
Системы позиционирования
С высокой степенью самоорганизации
С низкой
23
Низкая степень самоорганизации
<div style="position: absolute;"></div>
<div style="position: absolute;">
! <div style="position: absolute;"></div>
</div>
24
25
26
Низкая степень самоорганизации
+ Стабильность − Трудоёмкость
27
Высокая степень самоорганизации
<div>
! <div style="float: right;"></div>
! <span>...</span>
! <div>
! ! <span>...</span>
! </div>
</div>
<div>
! <span>...</span><span>...</span>
</div>
28
29
Высокая степень самоорганизации
+ Простота использования
+ Большие возможности
− Сложность поддержки
− Непредсказуемость
Потоковая
система позиционирования
31
Создать Изменить Удалить Навсегда
Панель
<div class="panel">
! <button>Создать</button>
! <button>Изменить</button>
! <button>Удалить</button>
! <input type="checkbox">
! <label>Навсегда</label>
</div>
32
33
Входящие▼ Переместить
34
Компонент
<div class="mover">
! <select>
! ! <option>Входящие</option>
! ! <option>Исходящие</option>
! ! ...
! </select>
! <button>Переместить</button>
</div>
35
Создать Изменить Удалить НавсегдаВходящие▼ Переместить
36
Интеграция
<div class="panel">
! ...
! <button>Изменить</button>
! <div class="mover">
! ...
! </div>
! <button>Удалить</button>
! ...
</div>
37
Создать Изменить
Удалить Навсегда
Входящие▼ Переместить
38
Субъекты контекста являются объектами
того же контекста и наоборот
Субъект создаёт контекст
Объект находится в контексте
39
40
Создать Изменить Удалить НавсегдаВходящие▼ Переместить
41
Создать Изменить
Удалить Навсегда
Входящие▼ Переместить
42
Создать Изменить
Удалить Навсегда
Входящие▼ Переместить
Решение
Разделение субъекта и объекта контекста
43
CSS3 Flexible Box Layout
Включение Flexbox
.panel {
! display: flex;
}
45
46
Создать Изменить Удалить НавсегдаВходящие▼ Переместить
Направление
.panel {
! display: flex;
! flex-direction: column; /** @default row */
}
47
48
Создать
Изменить
Удалить
Навсегда
Входящие▼ Переместить
49
Родитель контролирует поведение
своих детей
Поддержка браузерами 70%
50
caniuse.com
.horizontal-box > * {
! float: left;
}
.vertical-box > * {
! display: block;
! width: auto;
}
51
Альтернатива
Панель
<div class="panel horizontal-box">
! ...
! <button>Изменить</button>
! <div class="mover horizontal-box">
! ...
! </div>
! <button>Удалить</button>
! ...
</div>
52
Сетки
54
CSS сетки
<div class="container-12">
! <div class="grid-3"></div>
! <div class="grid-3"></div>
! <div class="grid-3"></div>
! <div class="grid-3"></div>
</div>
55
grid-3 grid-3 grid-3 grid-3
56
−модуль
<div class="container-12">
! <div class="grid-3"></div>
! <div class="grid-3"></div>
! <div class="grid-3"></div>
! <div class="grid-3"></div>
</div>
57
grid-3 grid-3 grid-3
58
Решение
Независимость модулей
CSS3 Grid Layout
60
news content activity
HTML
<div class="layout">
! <div class="news"></div>
! <div class="content"></div>
! <div class="activity"></div>
</div>
61
CSS
.layout {
! display: grid;
! grid-columns: (80px)[12];
}
.news {
! grid-column: 1;
! grid-column-span: 3;
}
.content {
! grid-column: 4;
! grid-column-span: 6;
}
.activity {
! grid-column: 10;
! grid-column-span: 3;
}
62
–news
<div class="layout">
! <div class="news"></div>
! <div class="content"></div>
! <div class="activity"></div>
</div>
63
64
content activity
65
Поддержка браузерами?
<div class="g-12">
! <div class="g-col-1 g-span-3 news"></div>
! <div class="g-col-3 g-span-6 content"></div>
! <div class="g-col-10 g-span-3 activity"></div>
</div>
66
Альтернатива
anygrid.net
Родитель контролирует поведение
своих детей
Элементы должны быть независимы
друг от друга
67
3 Явное наложение
69
70
z-index: 1
71
z-index: 1
72
z-index: 1
z-index: 1 z-index: 1
z-index: 1
Расслоение z-index по назначению
0
...
128
...
256 74
Решение?
}
}
контент
диалоги и попапы
Контекст наложения
Корневой элемент
Спозиционированный элемент c z-index ≠ auto
Элементы с opacity < 1
75
z-index локален для каждого
контекста наложения
76
77
z-index: 128
z-index: 1 z-index: 1
z-index: 1
Явные слои и отказ от z-index
78
Решение
Явные слои
<body>
! <div class="layer" id="background-layer"></div>
! <div class="layer" id="content-layer"></div>
! <div class="layer" id="overlay-layer"></div>
! <div class="layer" id="dialogs-layer"></div>
! <div class="layer" id="popups-layer"></div>
</body>
79
.layer {
! position: relative;
! z-index: 1;
}
80
Слой
Минимальный набор
Контент
Диалоги
Попапы
81
Явное наложение элементов слоёв
Отказ от z-index как средства
функционального наложения
82
4 Абстрактная реализация
Абстракция
84
Абстракция определяет семантику сущности и
позволяет работать с ней без знания деталей
реализации
Олдскул кнопка
Никаких градиентов
Никаких радиусов
Никаких псевдоэлементов
Только картинки
85
Минимальная реализация
<span class="button download-button">
! Скачать
! <span class="button-side"></span>
</span>
86
Минимальная реализация
.button {
! position: relative;
!
! display: inline-block;
! padding-left: 20px;
}
.button-side {
! position: absolute;
! left: 100%;
!
! width: 20px;
}
87
88
Скачать
89
Скачать Без SMS
Без SMS
90
Скачать
91
Решение?
.button {
! position: relative;
!
! display: inline-block;
!
! margin-right: 20px;
! padding-left: 20px;
}
.button-side {
! position: absolute;
! left: 100%;
!
! width: 20px;
}
92
Скачать Без SMS
93
Скачать Без SMS50px
94
Решение?
/** @note К любому margin-right надо прибавить 20! */
.button {
! position: relative;
!
! display: inline-block;
!
! margin-right: 20px;
! padding-left: 20px;
}
.download-button {
! margin-right: 70px; /** 50 + 20 */
}
Развитие реализации
<span class="button download-button">
! <span class="button-content">Скачать</span>
! <span class="button-side"></span>
</span>
95
Развитие реализации
.button {
! display: inline-block;
}
.button-content {
! display: inline-block;
!
! padding-left: 20px;
}
.button-side {
! display: inline-block;
!
! width: 20px;
}
96
97
Скачать
98
Скачать
50px50px
Избавление от отступов
.button {
! display: inline-block;
}
.button-content {
! display: inline-block;
! padding-left: 20px;
}
.button-side {
! display: inline-block;
!
! width: 20px;
}
99
100
Скачать
50px50px
101
Решение
<span class="button">
! <span class="button-left"></span>
! <span class="button-right"></span>
! <span class="button-content">Скачать</span>
</span>
Решение
.button {
! position: relative;
!
! display: inline-block;
}
.button-content {
! position: relative;
}
.button-left {
! position: absolute;
! left: 0;
! right: 20px;
}
.button-right {
! position: absolute;
! right: 0;
!
! width: 20px;
}
102
103
Скачать
50px50px
104
Соответствие семантики и реализации
Реализация по подобию
стандартных реализаций
Принципы разработки гибких
и поддерживаемых интерфейсов
Вася Аксёнов
@outring

DUMP-2013 Frontend - Принципы разработки поддерживаемых и гибких интерфейсов - Аксенов Василий