Tailwind не только для MVP
- вторник, 26 сентября 2023 г. в 00:00:13
Всем привет!
Обычно Tailwind используют для каких-то MVP/админок/не очень больших проектов, но мне кажется, что Tailwind, имеет место быть в средних и крупных проектах. Большинство его минусы решаемы, а плюсы чертовски хороши :)
В этой статье я распишу его плюсы и минусы и как можно минусы превратить в плюсы.
Tailwind - это CSS-фреймворк, предоставляющий набор готовых классов для стилизации веб-интерфейсов.
На главной Tailwind можно прочитать вот это - Rapidly build modern websites without ever leaving your HTML.Что дословно можно перевести как - Быстро создавай вебсайты, не отходя от HTML.
Выглядит как-то так:
Плюс который вытекает из заголовка на главной — нам крайне редко нужно обращаться к css файлам, почти все стили мы храним в самой разметке это сильно ускоряет скорость разработки и позволяет не терять фокус при верстке(не нужно постоянно свитчиться между css и файлом с разметкой)
Удобный подход к адаптивной верстке, для того чтобы указать определенное свойство для другого разрешения тебе нужно поставить определенный префикс который ты заранее можешь определить в конфигурационном файле, например вот так просто мы можем сделать карточку по горизонтали на мобильном устройстве(отлично работает, если у вас много breakpoints).
<template>
<div class="flex flex-col gap-2 sm:flex-row">
<h2>Responsive card</h2>
<p>Some context</p>
</div>
</template>
Темная тема поддерживается из коробки, все что вам нужно для того, чтобы ее использовать - прописать префикс - dark:
<template>
<div class="bg-[#000000] dark:bg-[#ffffff]">
<h2>Responsive card</h2>
<p>Some context</p>
</div>
</template>
Больше не нужно придумывать названия классов, для твоих элементов, хоть сейчас это и не является большой проблемой, так как есть например css-modules, но даже там нужно давать осмысленные имена и избегать коллизий этих имен.
Плагины и расширения, которые есть для Tailwind, вот например статья с 50 таковыми - тык
Удобная кастомизация, с помощью tailwind.config, это позволяет очень удобно интегрироваться с дизайн системой(если у вас таковая имеется). Единая система в одном месте, которая может быть пошаренной между большим количеством проектов одновременно(+ к хорошей масштабируемости).
theme: {
colors: {
'blue': '#1fb6ff',
'purple': '#7e5bef',
'pink': '#ff49db',
'orange': '#ff7849',
'green': '#13ce66',
'yellow': '#ffc82c',
'gray-dark': '#273444',
'gray': '#8492a6',
'gray-light': '#d3dce6',
},
fontFamily: {
sans: ['Graphik', 'sans-serif'],
serif: ['Merriweather', 'serif'],
},
extend: {
spacing: {
'8xl': '96rem',
'9xl': '128rem',
},
borderRadius: {
'4xl': '2rem',
}
}
},
Одни и те же css свойства импортируются всего 1 раз
Легкая интеграция с различными фреймворками React, Vue, etc…
Можно совмещать с обычным CSS(приятно, когда проект начинает разрастаться), вас никто не ограничивает и не говорит, что нужно писать только на Tailwind, так что вы можете писать что-то такое:
.someClass {
background: #000000;
@apply w-10 h-10 rounded-10;
}
6.5 миллионов скачиваний за последнюю неделю на npm(довольно большое community), у vue например всего 4 миллиона.
В выходном css файле у вас не будут присутствовать классы, которые реально не используются в разметке. Чистота и минимизация. Причем это относится и к тем классам, которые добавляются скриптами. Однако если вы хотите, чтобы некий класс всегда присутствовал на выходе, то вы и это можете сделать, объявив его вне директивы @ layer (отличный поинт от комментатора :) )
Сразу скажу, я довольно предвзят по отношению к Tailwind, так как довольно давно успешно использую его в production и мне все нравится, поэтому минусов будет чуточку меньше, он классный честно. Выделил самые частые минусы, которые обычно слышу.
Существенно разрастается разметка и ее становится тяжело поддерживать
Затруднена навигация с помощью devtools. Не так хорошо работает, как с классами
Отсутствует переиспользуемость
Существенно разрастается разметка и ее становится тяжело поддерживать
Картинка которая вселяет ужас(самая частая картинка в пользу того, что не нужно использовать Tailwind в своих проектах)
Не знаю, может кто и пишет так код с помощью Tailwind, но на мой взгляд это еще то извращение.
Я не поленился и переписал ее(да, мне нечем заняться) в нормальном стиле на Tailwind и написал тоже самое на обычный CSS.
Вот два получившихся компонента, по максимуму вынес в обоих случаях общее и получил следующий код:
<template>
<section class="flex justify-center mb-[140px]">
<div
class="wrapper"
>
<div
class="block-1 relative bg6 bg-cover bg-center w-full max-w-[1440px] p-[64x] pc:p-[80px] text-white"
></div>
<div
class="block-2 "
></div>
<div
class="block-3"
></div>
</div>
</section>
</template>
<style lang="scss" scoped>
.wrapper {
&::before, &::after {
@apply content-[''] absolute
h-[50px] pc:h-[90px] w-[50px] pc:w-[90px]
top-[24px] pc:top-[30px]
bg-[url('*~/assets/images/cta_decoration.png')] bg-cover
}
&::before {
@apply cleft-[24x] pc:left-[30px]
}
&::after {
@apply right-[24px] pc:right-[30px]
}
}
.block-1 {
&::before, &::after {
@apply content-[''] absolute
w-[calc(100%__164px)] pc:w-[calc(100%_-_260px)]
left-[82px] pc:left-[130px]
border-t-2 pc:border-t-4 border-brown3
}
&::before {
@apply top-[32px] pc:top-[40px]
}
&::after {
@apply bottom-[32px] pc:bottom-[40px]
}
}
.block-2 {
&::before, &::after {
@apply absolute
h-[calc(100%_-_164px)] pc:h-[calc(100%_-_260px)]
top-[82px] pc:top-[130px]
border-1-2 pc:border-l-4 border-brown3
}
&::before {
@apply content-['']
left-[32px] pc:left-[40px]
}
&::after {
@apply content-[1]
right-[32px] pc:right-[40px]
}
}
.block-3 {
&::before, &::after {
@apply content-[''] absolute
w-[50px] h-[50px] pc:w-[90px] pc:h-[90px]
bottom-[24px] pc:bottom-[30px]
bg-[urt('~/assets/images/cta_decoration.png')] bg-cover
rotate-180
}
&::before {
@apply left-[24x] pc:left-[30px]
scale-x-[-1]
}
&::after {
@apply right-[24px] pc:right-[30px]
}
}
</style>
<template>
<section class="section">
<div
class="wrapper"
>
<div
class="block-1"
></div>
<div
class="block-2 "
></div>
<div
class="block-3"
></div>
</div>
</section>
</template>
<style lang="scss" scoped>
.section {
display: flex;
justify-content: center;
margin-bottom: 140px;
}
.wrapper {
position: relative;
width: 100%;
color: #ffffff;
background-position: center;
background-size: cover;
max-width: 1440px;
padding: 64px;
@media (max-width: 1440px) {
padding: 80px;
}
&::before, &::after {
content: '';
position: absolute;
height: 50px;
width: 50px;
top: 24px;
background: url('*~/assets/images/cta_decoration.png');
background-size: cover;
@media (max-width: 1440px) {
height: 90px;
width: 90px;
top: 30px;
}
}
&::before {
left: 24px;
@media (max-width: 1440px) {
left: 30px;
}
}
&::after {
right: 24px;
@media (max-width: 1440px) {
right: 30px;
}
}
}
.block-1 {
&::before, &::after {
position: absolute;
width: calc(100% - 164px);
top: 32px;
border-top-width: 2px;
border-color: brown;
left: 82px;
@media (max-width: 1440px) {
width: calc(100% - 260px);
left: 130px;
top: 40px;
border-top-width: 4px;
}
}
&::before {
content: '';
}
&::after {
content: '1';
}
}
.block-2 {
&::before, &::after {
position: absolute;
width: calc(100% - 164px);
top: 32px;
border-top-width: 2px;
border-color: brown;
@media (max-width: 1440px) {
width: calc(100% - 260px);
top: 40px;
border-top-width: 4px;
}
}
&::before {
left: 32px;
content: '';
@media (max-width: 1440px) {
left: 40px;
}
}
&::after {
right: 32px;
content: '1';
@media (max-width: 1440px) {
right: 40px;
}
}
}
.block-3 {
&::before, &::after {
content: '';
position: absolute;
width: 50px;
height: 50px;
bottom: 24px;
border-top-width: 2px;
border-color: brown;
transform: rotate(180deg) scaleX(-1);
background: url('*~/assets/images/cta_decoration.png');
background-size: cover;
@media (max-width: 1440px) {
width: 90px;
height: 90px;
bottom: 30px;
}
}
&::before {
left: 24px;
@media (max-width: 1440px) {
left: 30px;
}
}
&::after {
right: 24px;
@media (max-width: 1440px) {
right: 32px;
}
}
}
</style>
И тут хорошо видно, что если подойти к разделение всего этого с умом, то получится аккуратный код, да тут нам не обойтись без использования css файла и директивы apply, но это скорее исключение, чем правило.
В итоге при таком подходе мы получили, что у нас нет портянки классов в разметке, но при этом и css файл у нас получился компактным — 75 строк с использование Tailwind и 140 строк с использованием обычных стилей, разница почти в 2 раза.
И в целом при высокой декомпозиции кода, у вас не должно получаться больше 5-8 свойств на элемент, что является довольно читаемым, а если у вас больше свойств, то на помощь приходит apply
Навигация с помощью devtools не так хорошо работает, как с классами с хорошим неймингом.
Это проблему можно решить многими способами, я опишу 2
Использование Vue DevTools/React DevTools и хорошее разделение на компоненты
Добавление дата атрибутов и навигация с помощью них, например
<template>
<div data-id="responsive-card" class="bg-[#000000] dark:bg-[#ffffff]">
<h2>Responsive card</h2>
<p>Some context</p>
</div>
</template>
Отсутствует переиспользуемость.
С помощью директивы apply, можно сделать как в коде ниже и получить переиспользуемый класс с использованием Tailwind классов
@layer components {
.btn-primary {
@apply py-2 px-4 bg-blue-500 text-white font-semibold rounded-lg shadow-md hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-blue-400 focus:ring-opacity-75;
}
}
И самый главный наш инструмент - tailwind.config.js и пример переиспользуемых цветов
theme: {
colors: {
'blue': '#1fb6ff',
'purple': '#7e5bef',
'pink': '#ff49db',
'orange': '#ff7849',
'green': '#13ce66',
'yellow': '#ffc82c',
'gray-dark': '#273444',
'gray': '#8492a6',
'gray-light': '#d3dce6',
},
}
Tailwind как и многие другие инструменты должен использоваться тогда, когда это уместно. Однако мне кажется, что он незаслуженно относится к инструментам, которые не стоит использовать для разработки средних и крупных проектов. У него есть некоторые недостатки в плане масштабируемости и расширяемости, но как мы видим из решений минусов они решаемы и с ними можно жить, также у с каждым годом у Tailwind растет community, что позволяет ему расти и развиваться быстрее.
Выбор за вами!
А напоследок оставлю здесь милого котика для хорошего настроения
Если статья показалась вам интересной, то у меня есть Тг-канал, где я пишу про новые технологии во фронте, делюсь хорошими книжками и интересными статьями других авторов.