Skip to content

Commit

Permalink
Merge pull request #1 from firefoxic/master
Browse files Browse the repository at this point in the history
Update automation
  • Loading branch information
Ildar-gn authored Jun 9, 2024
2 parents 4b8f7cc + 14fd648 commit 9e9e523
Show file tree
Hide file tree
Showing 11 changed files with 3,764 additions and 6,686 deletions.
9 changes: 4 additions & 5 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,7 @@ node_modules
build
.idea
.DS_Store
raw/**/*.jpg
raw/**/*.jpeg
raw/**/*.png
raw/**/*.svg
!raw/**/README.md
source/**/*.jpg
source/**/*.jpeg
source/**/*.png
!source/favicons/**/*.png
87 changes: 50 additions & 37 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# Сборка для HTML-курсов в HTML Academy

Сборка работает на gulp 4 версии
Сборка работает на gulp 5 версии

## Начало

Expand Down Expand Up @@ -67,11 +67,8 @@
│ └── workflows/ # Автоматизация для github actions
│ ├── check.yml # Запускает линтеры на Гитхабе
│ └── gh-pages.yml # Публикует проект и создаёт ссылку на проект
├── raw/ # Папка для «сырых» файлов (игнорируются гитом)
│ ├── icons/ # Папка для оригиналов svg-иконок
│ └── images/ # Папка для оригиналов картинок
├── source/ # Исходники проекта
│ ├── favicons/ # Папка для фавиконок (кроме favicon.ico)
│ ├── favicons/ # Папка для фавиконок (кроме favicon.ico, его в source переложить вручную)
│ ├── fonts/ # Папка для шрифтов
│ ├── icons/ # Папка для оптимизированных svg-иконок для преобразования их в спрайт (stack)
│ ├── images/ # Папка для оптимизированных картинок
Expand Down Expand Up @@ -113,9 +110,10 @@
- `npm run lint:bem` - проверяет правильное использование БЭМ в разметке
- `npm run lint:styles` - проверяет проект на совместимость с stylelint
- `npm run lint:scripts` - проверяет скрипты по правилам eslint
- `npm run optimize` - запускает все оптимизации изображений (занимает длительное время):
- `npm run optimize:raster` - оптимизирует растровые изображения из `raw/images/` в `source/images/`
- `npm run optimize:vector` - оптимизирует векторные изображения из `raw/images/` в `source/images/`
- `npm run optimize` - запускает все оптимизации изображений:
- `npm run optimize:icons` - в `source/icons/` оптимизирует векторные иконки
- `npm run optimize:images` - в `source/images/` оптимизирует векторыне и конвертирует растровые изображения (растровые оригиналы удаляются автоматически)
- `npm run optimize:favicons` - в `source/favicons/` генерирует все необходимые варианты фавиконок, а также webmanifest (векторные оригиналы удаляются автоматически)

## Работа с разметкой

Expand Down Expand Up @@ -177,38 +175,70 @@

## Работа с графикой

### Растр
Во всех трёх ниже описанных случаях коммитить нужно оптимизированную графику.

Абсолютно всю растровую графику с **двухкратной плотностью** из макета складывайте в `raw/images/`. Здесь графика игнорируется гитом.
### Изображения

После того как добавите графику сразу запускайте команду `npm run optimize:raster` (или просто `npm run optimize`) для оптимизации графики и создания `.webp`-версии. Команду нужно запускать один раз при появлении новой графики в проекте.
Из макета всю растровую графику (только с **двухкратной плотностью**, но без суффикса плотности `@2x` в имени) и всю контентную векторную графику (логотип, графики, иллюстрации) складывайте в:

Новая оптимизированная графика с разной плотностью и суффиксами плотности в именах файлов появится в `source/images`. Эту, уже оптимизированную графику нужно коммитить.
```shell
└── source/
└── images/
```

Здесь растровая графика без суффикса плотности игнорируется гитом.

### Вектор
Запуск команды `npm run optimize:images` оптимизирует векторную графику и конвертирует растровую в форматы `Webp` и `Avif` для двухкратной и однократной плотности пикселей с соответствующими суффиксами.

### Иконки

Векторную графику для спрайта (иконки) складывайте в:

```shell
└── raw/
└── source/
└── icons/
```

Контентную векторную графику (логотип, графики, иллюстрации) складывайте в:
Запуск команды `npm run optimize:icons` оптимизирует все иконки.

### Фавиконки

Векторные фавиконки (все, что есть в макете) разместите в:

```shell
└── raw/
└── images/
└── source/
└── favicons/
```

Запуск команды `npm run optimize:vector` поместит оптимизированные копии этих svg-файлов в соответствующие папки в исходниках:
Имена исходных файлов должны быть такими:

```shell
└── source/
├── icons/
└── images/
└── favicons/
├── 16.svg # Специальная версия размером 16×16. Добавляй её только при её наличии в макете.
├── 32.svg # Основной вариант размером 32×32.
└── touch.svg # Большая тач-иконка без скруглений и прозрачностей.
```

Запуск команды `npm run optimize:favicons` сгенерирует все необходимые фавиконки и вебманифест. Кроме этого сгенерируется файл `Links.md` с кодом нужных тегов `link`. Заберите этот код в `head` разметки (md-файл после этого можно удалить).

Переместите `favicon.ico` и `manifest.webmanifest` в `source/`. Получится так:

```shell
└── source/
├── favicons/
│ ├── icon-180.png
│ ├── icon-192.png
│ ├── icon-192.webp
│ ├── icon-512.png
│ ├── icon-512.webp
│ └── icon.svg
├── favicon.ico
└── manifest.webmanifest
```

По необходимости исправь пути в вебманифесте и тегах `link`.

### Сборка

При продакшен-сборке автоматизация перенесёт всю графику из `source/images/` в `build/images/`, а из иконок в `source/icons/` создаст спрайт `build/icons/stack.svg`.
Expand All @@ -227,23 +257,6 @@
└── logo.svg
```

### Фавиконки

Варианты фавиконок форматов PNG и SVG следует размещать в `source/favicons/`.

Файлы `favicon.ico` и `manifest.webmanifest` — в `source/`:

```shell
└── source/
├── favicons/
│ ├── 180.png
│ ├── 192.png
│ ├── 512.png
│ └── icon.svg
├── favicon.ico
└── manifest.webmanifest
```

## Работа со шрифтами

Все шрифтовые файлы лежат в `source/fonts/`. Сборка переносит их в `build/fonts/`.
Expand Down
95 changes: 13 additions & 82 deletions gulpfile.js
Original file line number Diff line number Diff line change
@@ -1,33 +1,23 @@
import { readFileSync, rmSync } from 'node:fs';

import gulp from 'gulp';
import { src, dest, watch, series, parallel } from 'gulp';
import plumber from 'gulp-plumber';
import htmlmin from 'gulp-htmlmin';
import * as dartSass from 'sass';
import gulpSass from 'gulp-sass';
import postcss from 'gulp-postcss';
import postUrl from 'postcss-url';
import lightningcss from 'postcss-lightningcss';
import { createGulpEsbuild } from 'gulp-esbuild';
import browserslistToEsbuild from 'browserslist-to-esbuild';
import sharp from 'gulp-sharp-responsive';
import svgo from 'gulp-svgmin';
import { stacksvg } from 'gulp-stacksvg';
import server from 'browser-sync';
import bemlinter from 'gulp-html-bemlinter';

const { src, dest, watch, series, parallel } = gulp;
const sass = gulpSass(dartSass);
const PATH_TO_SOURCE = './source/';
const PATH_TO_DIST = './build/';
const PATH_TO_RAW = './raw/';
const PATHS_TO_STATIC = [
`${PATH_TO_SOURCE}fonts/**/*.{woff2,woff}`,
`${PATH_TO_SOURCE}*.ico`,
`${PATH_TO_SOURCE}*.webmanifest`,
`${PATH_TO_SOURCE}favicons/**/*.{png,svg}`,
`${PATH_TO_SOURCE}favicons/**/*.{svg,png,webp}`,
`${PATH_TO_SOURCE}fonts/**/*.woff2`,
`${PATH_TO_SOURCE}images/**/*{svg,avif,webp}`,
`${PATH_TO_SOURCE}vendor/**/*`,
`${PATH_TO_SOURCE}images/**/*`,
`!${PATH_TO_SOURCE}**/README.md`,
];
let isDevelopment = true;
Expand All @@ -45,31 +35,15 @@ export function lintBem () {
}

export function processStyles () {
const context = { isDevelopment };

return src(`${PATH_TO_SOURCE}styles/*.scss`, { sourcemaps: isDevelopment })
.pipe(plumber())
.pipe(sass().on('error', sass.logError))
.pipe(postcss([
postUrl([
{
filter: '**/*',
assetsPath: '../',
},
{
filter: '**/icons/**/*.svg',
url: (asset) => asset.url.replace(
/icons\/(.+?)\.svg$/,
(match, p1) => `icons/stack.svg#${p1.replace(/\//g, '_')}`
),
multi: true,
},
]),
lightningcss({
lightningcssOptions: {
minify: !isDevelopment,
},
})
]))
.pipe(dest(`${PATH_TO_DIST}styles`, { sourcemaps: isDevelopment }))
.pipe(postcss(context))
.pipe(dest((path) => {
path.extname = '.css';
return `${PATH_TO_DIST}styles`;
}, { sourcemaps: isDevelopment }))
.pipe(server.stream());
}

Expand All @@ -90,48 +64,8 @@ export function processScripts () {
.pipe(server.stream());
}

export function optimizeRaster () {
const RAW_DENSITY = 2;
const TARGET_FORMATS = [undefined, 'webp']; // undefined — initial format: jpg or png

function createOptionsFormat() {
const formats = [];

for (const format of TARGET_FORMATS) {
for (let density = RAW_DENSITY; density > 0; density--) {
formats.push(
{
format,
rename: { suffix: `@${density}x` },
width: ({ width }) => Math.ceil(width * density / RAW_DENSITY),
jpegOptions: { progressive: true },
},
);
}
}

return { formats };
}

return src(`${PATH_TO_RAW}images/**/*.{png,jpg,jpeg}`)
.pipe(sharp(createOptionsFormat()))
.pipe(dest(`${PATH_TO_SOURCE}images`));
}

export function optimizeVector () {
return src([`${PATH_TO_RAW}**/*.svg`])
.pipe(svgo())
.pipe(dest(PATH_TO_SOURCE));
}

export function createStack () {
return src(`${PATH_TO_SOURCE}icons/**/*.svg`)
.pipe(stacksvg())
.pipe(dest(`${PATH_TO_DIST}icons`));
}

export function copyStatic () {
return src(PATHS_TO_STATIC, { base: PATH_TO_SOURCE })
return src(PATHS_TO_STATIC, { base: PATH_TO_SOURCE, encoding: false })
.pipe(dest(PATH_TO_DIST));
}

Expand Down Expand Up @@ -161,9 +95,8 @@ export function startServer () {
});

watch(`${PATH_TO_SOURCE}**/*.{html,njk}`, series(processMarkup));
watch(`${PATH_TO_SOURCE}styles/**/*.scss`, series(processStyles));
watch(`${PATH_TO_SOURCE}**/*.{scss,svg}`, series(processStyles));
watch(`${PATH_TO_SOURCE}scripts/**/*.js`, series(processScripts));
watch(`${PATH_TO_SOURCE}icons/**/*.svg`, series(createStack, reloadServer));
watch(PATHS_TO_STATIC, series(reloadServer));
}

Expand All @@ -188,7 +121,6 @@ export function buildProd (done) {
processMarkup,
processStyles,
processScripts,
createStack,
copyStatic,
),
)(done);
Expand All @@ -201,7 +133,6 @@ export function runDev (done) {
processMarkup,
processStyles,
processScripts,
createStack,
),
startServer,
)(done);
Expand Down
Loading

0 comments on commit 9e9e523

Please sign in to comment.