# Компоненты
Расположение компонентов в проекте: source/scss/components
.
Компонент - это структурированный, независимый SASS модуль с внутренним API, задача которого вернуть конечные CSS стили или предоставить API для использования другими компонентами.
В среде разработки, каждый компонент - генерирует собственный скомпилированный CSS файл стилей. Для создания конечного файла стилей, используется релиз, который позволяет сгенерировать один и более компонентов в единый файл стилей.
# Вступление
Прежде чем мы начнем разбирать структуру компонента, необходимо принять к сведению основное требование к которому необходимо придерживаться, а именно - разделение логики от стилей (то, что генерируется в правила CSS)!
Для того, чтобы придерживаться данного правила, необходимо ясно понимать, на каком этапе осуществляется SCSS логика (переменные, функции, миксины), а в какой момент, будут сгенерированы CSS правила стилей. Для выполнения данного правила, компонент имеет собственную структуру файлов и минимальные требования для её расширения.
# Почему это важно?
Компоненты выполняют две роли:
- служат для генерации конечных CSS стилей
- служат в роли модуля для других компонентов
Если в первом случае все понятно, то во втором может возникнуть вопрос, зачем? Затем, чтобы можно было использовать функционал другого компонента (конфигурацию, миксины, функции)!
Пример использования компонента grid:
// components/app/render.scss
@use "ungic.component" as this;
@use "ungic.components.grid" as grid;
@include this.component {
.btn {
...
display:block;
// Использование @media API компонента grid
@include grid.media(grid.media(max-xs)) {
display:none;
}
}
}
Так вот, в случае включения компонента в виде модуля, мы бы не хотели, чтобы компонент grid вернул CSS правила всей grid системы, которые будут включены в наш компонент, а в случае, если оба компонента будут включены в один проект, то произойдет дублирование стилей!
TIP
При создании компонента, необходимо соблюдать требование разделения логики от правил которые генерируются в CSS стили!
# Структура компонента:
В данном разделе описывается структура файлов компонента, для ознакомления с внутренним API компонента, обратитесь к соответствующему разделу.
Структура компонента по умолчанию:
.
|─ .core
|─ index.scss
---------------
|─ render.scss
|─ config.scss
|─ properties.scss
|─ once.scss
---------------
|─ mixins
└─ functions
# Компонент состоит из:
Обязательных сущностей:
- .core - ядро компонента (внутренний API компонента).
- index
Опциональных:
- render
- config.scss
- properties.scss
- once.scss
Пользовательских:
- mixins
- functions
- ...
Любой файл или директория с index.scss могут быть частью модуля компонента. По умолчанию, компонент уже имеет миксины и функции.
Обратите внимание!
В случае удаления mixins или functions из компонента, следует удалить их использование из render.scss файла:
//render.scss
@use "ungic.component" as this;
// или @use ".core"as this;
@use "ungic.theme"as theme;
//@use "functions"as *;
//@use "mixins"as *;
...
# Ядро компонента (.core)
Ядро компонента - это набор служебных файлов фреймворка, которые образуют внутренний API компонента. Ядро требуется включать как и обычные SASS модули.
Включение ядра компонента осуществляется одним из способов:
- Относительным путем
@use "./.core" as this
- Абсолютным
@use "ungic.component" as this
// Относительное включение модуля
@use "./.core" as this;
// Абсолютное
@use "ungic.component" as this;
TIP
Концепция использования ядра компонента очень похожа на использование this в ООП:
@use "ungic.component" as this;
@debug this.cid(); // app
@debug this.config(key); // Конфигурация текущего компонента
@debug this.prop(border); // CSS св-во данного компонента
Ссылки по теме:
# index.scss
Обязательное присутствие.
Данный файл отвечает за "передачу" данных модуля с помощью @forward
директивы, а также, для настройки сборки компонента в режиме разработки. Именно этот файл будет включаться в случае использования компонента как модуль.
Содержимое файла по умолчанию:
@forward ".core";
При включении компонента с подобным index.scss файлом с помощью @use
директивы, можно получить доступ исключительно к внутреннему API компонента:
// components/ara/render.scss
@use "ungic.components.petya" as petya;
@debug petya.cid(); // petya
Для того, чтобы можно было получить доступ к пользовательским методам компонента, их требуется "переслать" с помощью @forward
директивы в index.scss
файле компонента:
@forward ".core";
@forward "functions";
@forward "mixins";
В случае если компонент не предоставил доступ к пользовательским типам,тогда доступ можно получить методом включения требуемой части компонента как модуль, для этого требуется указать полный путь относительно компонента используя символ .
точки для разделения сегментов пути:
// components/ara/render.scss
@use "ungic.components.petya" as petya;
// Включение пользовательских функций компонента как модуль
@use "ungic.components.petya.functions" as petya_func;
@debug petya_func.last_name(); // pupkin
# Конфигурация сборки компонента в режиме разработки
Речь идет о конфигурации build.plugins.scss.dev параметра конфигурации scss плагина. В режиме разработки, данную конфигурацию можно определять индивидуально для каждого компонента в index.scss файле с помощью следующего синтаксиса:
// index.scss
/* ::::
inverse: false
autoprefixer: true
theme: darkela
*/
@forward ".core";
Данная возможность позволяет в реальном времени изменить тему компонента или включить / отключить режим генерации инверсии компонента!
# Правила стилей (render.scss)
Опциональное присутствие.
Данный файл должен содержать конечные CSS правила стилей которые будут сгенерированы в CSS.
render.scss файл - это единственный системный файл компонента который должен возвращать css правила стилей! Это не значит, что все стили должны быть написаны именно в render.scss
, нет!
Структура файлов для написания стилей может быть абсолютно любой, но конечный результат должен быть включен непосредственно в render.scss файл!
Внимание!
render.scss - основной и единственный системный файл компонента который должен возвращать CSS правила стилей!
TIP
Структура файлов для написания стилей может быть любой, но конечный результат должен быть включен непосредственно в render.scss файл!
# Разделение правил на части
Разделение правил на части с последующим включением в render.scss является хорошей практикой, так как, эти части могут быть включены и другими компонентами:
// Структура вымышленного modal компонента
.
|─ .core
|─ index.scss
|─ render.scss
└─ includes
├─ header.scss
├─ body.scss
├─ controls.scss
└─ footer.scss
// components/modal/render.scss
@use "ungic.component" as this;
@use "sass:meta";
@include this.component {
@include meta.load-css("./includes/header.scss");
@include meta.load-css("./includes/body.scss");
@include meta.load-css("./includes/controls.scss");
@include meta.load-css("./includes/footer.scss");
}
// Содержимое одного из includes файла
// может выглядеть следующим образом:
// components/modal/includes/header.scss
@use "ungic.utils" as utils;
// Инструмент для объединения селектора с предыдущим
@include utils.merge {
&-header {
...
}
}
Результат CSS будет следующим:
.modal-header {
...
}
.modal-footer {
...
}
// и тд
Таким образом, части modal компонента, могут быть использованы и в других компонентах, например для вымышленного panel компонента:
// components/panel/render.scss
@use "ungic.component" as this;
@include this.component {
@include meta.load-css("ungic.components.modal.includes.header");
}
Результат CSS будет следующим:
.panel-header {
...
}
Обратите внимание!
Стоит учесть тот факт, что все правила (стили) включенные одним компонентом из другого компонента, будут иметь стиль исходного компонента!
# Экспортирование данных (once.scss)
Опциональное присутствие.
Once.scss - файл служит местом для экспорта данных из SASS. Компиляция компонентов в среде разработки происходит в несколько этапов (в случае генерации инверсии темы), что порождает повторное компилирование .scss файлов компонента (именно поэтому в консоли дважды отображаются sass @debug результаты), исключением является once.scss
файл, который включается один раз за весь цикл компиляции.
Экспортированные данные можно включить в виде объекта данных при генерации шаблонов, а также, все данные сохраняются в exports/sass-options.json
файле в JSON формате.
// components/test/once.scss
@use ".core" as this;
$data: (
as_number: 1,
as_str: 'Lorem ipsum',
as_map: (
name: 'Artem'
),
as_boolean: true,
as_color: #FFF
);
$export: this.export('data', $data);
// dist/exports/sass-options.json
{
"oid": "data",
"cid": "test",
"data": {
"as_number": 1,
"as_str": "Lorem ipsum",
"as_map": {
"name": "Artem"
},
"as_boolean": true,
"as_color": "#ffffff"
},
"id": "test.data"
}
TIP
По умолчанию, конфигурация (config.scss) каждого компонента экспортируется автоматически в exports/sass-options.json
файл с помощью следующего "виртуального" метода:
@use "ungic.components.test" as test;
$export: test.export('config', test.config());
...
// И так для каждого компонента.
# Конфигурация компонента (config.scss)
Опциональное присутствие.
Опциональный конфигурационный файл компонента. Данный файл может содержать в себе любые конфигурационные параметры необходимые для стилизации компонента. Для получения параметров указанных в config.scss
файле используется config метод ядра компонента:
@use ".core" as this;
@debug this.config(); // Получить все конфиг. параметры
@debug this.config(param); // Конкретный параметр
Конфигурация каждого компонента автоматически экспортируется в JSON формате.
TIP
Конфигурация компонента может быть переопределена из проекта в config-over.scss файле!
Обратите внимание!
При работе с цветом в конфигурационном файле, следует избегать использование произвольных цветов (иначе темизация данного компонента будет невозможна). Для этого, следует использовать ungic.theme модуль:
// config.scss
@use "ungic.theme" as theme;
$color-of-component: theme.color(text-color);
# Стилизация компонента (properties.scss)
Опциональное присутствие.
Конфигурационный файл, который используется в процессе стилизации компонента, может содержать список переменных с именами CSS свойств, значения которых могут быть применены при написании CSS правил. Значения свойств по умолчанию наследуются из properties.scss файла проекта.
# Пользовательский тип (mixins / functions)
Опциональное присутствие.
Компонент, может иметь любое кол-во файлов и директорий которые могут служить модулями и состоять из функций, миксинов и прочего. Для того, чтобы подобные модули компонента были доступны другим компонентам их следует "продвигать" с помощью @forward (opens new window) директивы в index.scss файле компонента.
# Компонент как модуль
Любой компонент можно использовать в роли SASS модуля и включать в другие компоненты с помощью @use
директивы. При использовании компонента в роли модуля, мы получаем доступ как к ядру компонента, так и к пользовательским сущностям (функциям, миксинам, переменным и даже к CSS правилам!):
// Использование компонента grid
@use "ungic.components.grid" as grid;
// Доступ к конфигурации компонента
@debug grid.config(columns-counts); // 12
// Пользовательские функции / миксины
@include grid.media(screen "and" grid.media(max-xs)) {
.test {
display: none
}
}
// Результат
@media screen and (max-width:596px) {
.test {
display: none
}
}
TIP
Для того, чтобы можно было получить доступ к пользовательским методам компонента, следует "продвинуть" их с помощью @forward
директивы в index.scss
фале компонента:
@forward ".core";
@forward "functions";
@forward "mixins";
Также, можно включать конкретную часть компонента:
@use "ungic.components.grid.functions" as *;
@use "ungic.components.grid.mixins" as *;
Обратите внимание!
Можно включить любой файл или директорию (с index.scss файлом) компонента. Для этого, следует указать полный путь до файла используя .
точку для разделителя сегментов пути. В случае включения .scss
файла, расширение не указывается!
Обратите внимание!
В случае включения части компонента, имена директорий или файлов не должны содержать символ точки .
Ссылки по теме: