TGViewer
Channel Public Channel
Логово верстальщика

Логово верстальщика

@webdevlair

Логово верстальщиков: HTML, CSS, JavaScript, практики современной верстки, вайбкодинг и использование ИИ в разработке.

Личный блог автора - @just_genych
По вопросам рекламы или разработки: @g_abashkin
Subscribers
7.97K
Photos
1.2K
Videos
68
Links
2K

Showing posts older than #4573 · Back to latest

Older Posts 18 shown
Post #4572 417
Shopify слезает с React Native

Шесть лет назад контора поставила на RN всё. Теперь — переписывают приложения на Swift и Kotlin. Официальная версия: кодинг-агенты уронили цену сборки одних и тех же фич вдвое. Не больше, не меньше — ровно в два раза.

Заодно обещают рассказать, что будет с React Native Skia, FlashList и Restyle. И есть отдельный пост про то, как за 12 недель переписали приложение Shop — с цифрами по запуску, стабильности и размеру приложения до и после.

Только вот не все купились. В бодром треде r/reactnative один из основателей Expo предположил, что решение было «скорее политическим, чем техническим», а сравнивали там приложение на старой архитектуре с только что переписанным.

Источник: React Status #490

👉 Логово Верстальщика
Post #4571 411
Свой велосипед для покрытия: когда готовые тулзы пасуют

Ситуация классическая: задача вроде бы стандартная, а популярные инструменты её не тянут. И что тогда? Всё верно — пришло время пилить собственный велосипед.

Вводные: есть некие параметры, и часть из них можно склеить в каскады. Нужно посчитать покрытие параметров, с одной оговоркой — если на каскад, внутри которого сидит параметр, есть тесты, то параметр считается покрытым. Из этого видно, что покрытие надо проверять на сущностях, а не на ветвлении, сценариях или коде, как это делает, скажем, coverage.py или pytest-cov.

Читать далее

👉 Логово Верстальщика
Post #4569 372
⁣CSS text-box-trim и text-box-edge: убираем «воздух» вокруг текста без магических чисел

Заголовок в карточке визуально «съезжает» вниз, кнопка с иконкой центрируется криво, отступы сверху и снизу различаются, хотя в макете равны. Причина - half-leading: браузер делит line-height над и под строкой по метрикам шрифта, а не по нарисованным глифам. В дизайн-системах это ломает вертикальный ритм.

Что делают свойства
text-box-trim: trim-both срезает leading сверху и снизу до em-box. text-box-edge: cap alphabetic задаёт метрики: cap height сверху, baseline снизу.

.btn {
line-height: 1;
padding: 12px 20px;
text-box-trim: trim-both;
text-box-edge: cap alphabetic;
}


После этого padding снова отвечает за оптический отступ, а не борется с leading.

Production-контекст
Кнопки с иконками, бейджи, заголовки карточек e-commerce и заголовки SaaS-дашбордов: уходит 2-4 px плавающего сдвига при смене шрифта или фолбэка, компоненты перестают зависеть от отрицательных margin.

Trade-offs
Поддержка неполная: без trim текст останется с обычным leading, поэтому обрезку нельзя закладывать в расчёт высоты контейнера. Свойство режет line box, и высокие диакритики или выносные элементы могут пострадать - тестируйте на реальном контенте.

Практика
Включайте через @supports, покрывайте кнопки и заголовки скриншот-тестами. Для body-text выигрыш мал, а риск обрезки выше - применяйте точечно.
  • 👍 1
Post #4568 389
Собрали свой UI Kit: шесть компонентов распухли до 30+, а одна кривая строчка уронила вёрстку сразу во всех проектах

Когда в проекте начинает плодиться одно и то же в интерфейсе, вопрос приходит сам собой: какого чёрта мы снова и снова рисуем один и тот же Button, Input или Select?

Готовые варианты мы щупали — включая Ant Design и Material UI, — но под наши хотелки они не подошли. Нам нужен был контроль над тем, как компоненты выглядят и как себя ведут, возможность тонко подгонять их под свои задачи и держать в голове требования проекта к безопасности.

Читать далее

👉 Логово Верстальщика
Post #4561 437
🤩 Нашли репу с десятками практических проектов для прокачки навыков и резюме

Внутри 54 проекта разной сложности по Terraform, Kubernetes, Docker, CI/CD, DevSecOps, AWS, Azure, безопасности и мониторингу.

Есть полноценные лабораторные с кодом и конфигами и также пошаговые гайды — так что можно разобраться, повторить всё своими руками и положить результат в портфолио.

✖️ xCode Journal
Post #4559 439
🤣 Наконец-то батя покажет, как он в детстве ходил в школу за 100 верст

💥 xCode Journal
Post #4558 465
Месяц вайбкодинга с незнакомцами — в КОРУСе подвели итоги ИИ-лаборатории, где студенты месяц разрабатывали реальный продукт для заказчика из бизнес-единицы.

Команда из четырёх незнакомых людей училась работать с искусственным интеллектом, брать ответственность за проект с первого дня и справляться со страхами первого опыта.

Как это было — рассказывают HR, Корпоративный университет, бизнес-единицы и сами стажёры. Читать далее

👉 Логово Верстальщика
Post #4557 364
⁣**CSS field-sizing: content — авторазмер полей форм без единого скрипта**

Всё ещё тянете высоту textarea через scrollHeight, строчите обёртки со скрытыми дивами и ResizeObserver? Выкидывайте. В CSS завезли нативное решение для авторазмера элементов форм.

**Как это работает**

Свойство field-sizing говорит браузеру: подгони размер поля под его контент. Значение по умолчанию — fixed (все привычно), нас интересует content.

textarea {
field-sizing: content;

/* без этого textarea схлопнется в точку,
а с длинным текстом улетит в бесконечность */
min-height: 4em;
max-height: 20em;

resize: none; /* ресайз мышью теперь не нужен */
}


Поле растёт при вводе и уменьшается, когда строк стало меньше. Без анимаций layout-сдвигов и обработчиков на каждый keyup.

**Это работает не только с textarea**

Свойство определено для всех элементов форм и подстраивает размер по контенту:

input,
select {
field-sizing: content;
}


- input[type="text"] — ширина подстраивается под введённый текст;
- select — размер подгоняется под выбранную опцию, а не под самую длинную;
- input[type="file"], input[type="number"] — тоже подхватывают.

**Подводные камни**

1. Всегда задавайте min-height или стартовые размеры. Сломанный (или пустой) элемент схлопнется до нуля.
2. Для input по умолчанию задан size, и если не сбросить CSS-ширину, рост незаметен. Элементу нужно «дышать»: никаких width: 100%, если ждёте автоширину.
3. Это свойство — не фича, которая ломает интерфейс, если браузер не поддерживает. Оно просто проигнорируется, и поле останется со стандартным rows, cols и size. Идеально для прогрессивного улучшения.

**Поддержка**

- Chrome / Edge — с 123 версии;
- Firefox — долго был за флагом, проверяйте актуальный статус на caniuse;
- Safari — нет.

Среднестатистический пользователь Chrome уже живёт с этим. Можно смело применять на проектах, где не нужно поддерживать древний Safari.

**Зачем это фронту**

- минус JS-костыли: ни scrollHeight, ни скрытых дублей контента, ни обсерверов;
- скорость: ростом поля управляет браузерный layout, а не перезапись DOM;
- доступность и простота: «коробка» всегда соответствует контенту, в том числе при вставке текста мышью и автозаполнении (на чём часто падают самописные решения).

Берите в работу и потихоньку вычищайте старые наколенки. Ссылку на спецификацию не даю — она и так гуглится за секунду.

#css #forms
  • 👍 2
Post #4556 387
Как мы шторы закрывать учили: стажёрская кухня глазами наставников

Здарова, Хабр! Прошлым летом семеро энтузиастов вкатились на трёхмесячную стажировку в Учебный центр НТЦ «Вулкан». Звучало всё просто, как угол: сделать пульт для управления рулонными шторами в офисном опенспейсе.

Наставники решили не молчать и расказали, как была устроена движуха и как они воевали со стажёрами. А в конце — мешок выводов. Кому надо — сэкономит себе нервы и время, если решит повторить этот трюк или просто впервые сунется в аппаратный проект.

Читать далее

👉 Логово Верстальщика
Post #4555 345
⁣Зачем нужен overflow: clip, если есть overflow: hidden? 🎯

Когда верстаешь карточку со скруглёнными углами, а дочерний элемент «вылезает» за границы — тень, glow, бегущая строка, фокус-кольцо — первое желание: зарезать лишнее через overflow: hidden.

Но у hidden есть неочевидный побочный эффект: он делает элемент скролл-контейнером.

Это значит:
— содержимое можно программно проскроллить (scrollTop, scrollIntoView);
— браузер резервирует ресурсы на скролл-механику;
— при навигации с клавиатуры скрытый контент может стать «достижимым» скроллом — UX ломается.

Когда тебе нужно лишь обрезать **декоративный** выплеск, а не сделать полноценный скролл-регион — hidden избыточен и вреден.

Решение — overflow: clip.

Он делает ровно одну вещь: жёстко обрезает всё, что выходит за границы бокса, и **не создаёт скролл-контейнер**. Никакого программного скролла, никаких сюрпризов с фокусом.

.card {
overflow: clip;
}


А теперь самое интересное — overflow-clip-margin.

По умолчанию обрезка идёт по padding-краю. Но что, если хочется скруглить контент внутри, а снаружи оставить видимой аккуратную тень? Раньше приходилось делать костыли с врапперами. Теперь можно расширить область видимости:

.card {
overflow: clip;
overflow-clip-margin: 8px;
}


Эти 8px — пространство за пределами бокса, в котором контент продолжает отображаться, а всё, что дальше — обрезается. По сути, визуальная «зона безопасности» для декоративных элементов.

Где реально спасает:
— тени и drop-shadow, которые чуть-чуть выходят за карточку;
— focus ring у кнопок внутри контейнера с обрезкой;
— всплывающие подсказки внутри карточки;
— трансформированные бейджи, наклонённые заголовки, кастомные ленты.

Ещё один нюанс, который часто упускают: при паре overflow-x: visible; overflow-y: hidden браузер молча превращает visible в auto — получаем скролл-контейнер там, где не ждали. С clip такого нет: visible остаётся visible, потому что clip не создаёт scroll container. Это позволяет безопасно комбинировать:

.card {
overflow-x: clip;
overflow-y: visible;
}


Поддержка: все современные браузеры — Chrome 90+, Firefox 81+, Safari 16+. Можно смело использовать, а с фолбэком на hidden для старых — тем более.

Итого: если hidden «на всякий случай» режет всё и создаёт скрытый скролл — clip решает точечно и без побочных эффектов. А overflow-clip-margin даёт тонкую настройку: сколько именно декоративного выплеска оставить на виду.

Источники:
— MDN: overflow — https://developer.mozilla.org/en-US/docs/Web/CSS/overflow
— MDN: overflow-clip-margin — https://developer.mozilla.org/en-US/docs/Web/CSS/overflow-clip-margin
— CSS Overflow Module Level 3 — https://drafts.csswg.org/css-overflow-3/
  • 👍 4
  • ❤ 1
  • 🔥 1
Post #4553 401
Казахский ИП-разработчик обходится на 22% дороже. Готовься к такому раскладу

Нашли мидла на бэкенд в Казахстане, обсудили зарплату, всё чинно. Но тут бухгалтер задаёт сакральный вопрос: «ИП или физлицо?» И вот это меняет всё — проект может подорожать на 22%. Разбираемся, откуда ноги растут у этих процентов, почему НДФЛ с казахстанца платить не требуется, а вот агентом по налогам ты остаёшься, и какая фраза в договоре способна превратить сэкономленные деньги в доначисление.

Не воспринимай это как готовый шаблон. Конкретный проект нужно согласовывать с юристом. Исходник: разработчик постоянно живёт в Казахстане, работает там же, в Россию не заезжает.

Читать далее

👉 Логово Верстальщика
Post #4552 411
Чек-лист: как пробить компанию до собеседования (7 шагов)

«Сначала проверь работодателя, а потом уже вкладывай в него своё время» — так автор выражает главный принцип. Только вот многие, как стадо, валят на интервью без разведки — и в итоге ловят либо разбитые ожидания, либо испорченную трудовую.

Автор собрал чек-лист проверки конторы перед собеседованием. Внутри два блока: база — проверка по открытым интернет-ресурсам, и дополнительно — прогон через реестры и базы. По его мнению, такая разведка — не паранойя, а нормальный способ сэкономить время и нервы.

Читать далее

👉 Логово Верстальщика
Post #4549 336
⁣Сегодня покажу, как выкинуть JS из связки «скролл + эффекты». Речь про CSS scroll-driven animations — это уже не polyfill, а нативный API в Chrome/Edge/Safari 26+. Два главных героя: scroll() и view(). Поехали.

**Основы**

scroll() привязывает анимацию к прогрессу прокрутки контейнера. Элемент просто крутится/двигается/закрашивается в зависимости от того, сколько пикселей мы проскроллили.

view() привязывает анимацию к появлению элемента во вьюпорте. Элемент «оживает», когда вползает в кадр, и «умирает», когда выходит. И это идеально для параллакса или плавного появления карточек.

Оба механизма работают через animation-timeline, а за точками старта и конца управляет animation-range.

**Прогресс-бар без единой строчки JS**

Классика: полоска сверху показывает, сколько прочитано. Раньше — слушатель скролла и requestAnimationFrame. Теперь — 5 строк CSS:

.progress {
position: fixed;
top: 0; left: 0;
width: 100%; height: 4px;
background: #ff4d00;
transform-origin: left;
animation: scale linear;
animation-timeline: scroll();
}

@keyframes scale {
from { transform: scaleX(0); }
to { transform: scaleX(1); }
}


Всё. scroll() без аргументов = отслеживаем скролл ближайшего предка (или корня, если предка-скроллера нет). Анимация идёт ровно от верха страницы до низа.

**Параллакс через view()**

Берём картинку, которая должна двигаться с другой скоростью, пока она на экране. Вместо scroll-слушателя и пересчёта позиций:

.parallax-image {
animation: drift linear;
animation-timeline: view();
animation-range: entry 0% cover 40%;
}

@keyframes drift {
from { transform: translateY(15%); }
to { transform: translateY(-15%); }
}


Поясню значения entry, cover, exit. Палитра простая:
- entry — элемент выезжает снизу/сверху в кадр
- cover — полностью на экране
- exit — покидает вьюпорт

entry 0% cover 40% значит: анимация начинается в момент появления и заканчивается, когда элемент прошёл 40% высоты экрана. За счёт этого картинка «сдвигается» независимо от скорости скролла.

**Важный нюанс: animation-range**

Если у вас контейнер высотой 200%, а анимация должна идти только на середине скролла — играйтесь именно через range. scroll(root) + range: 0% 50% даст эффект, заканчивающийся на половине страницы. Это заменяет кучу логики «если y > X».

**Бонус-фича: animation-timeline: view(block)**

По умолчанию отслеживается ось блока (вертикаль) или инлайна (горизонталь). Можно явно указать view(inline) для горизонтальных слайдеров-каруселей с прокруткой по X. Тоже без JS.

**Что под капотом и поддержка**

Работает только с ключевыми кадрами — CSS-переходы так не умеют. animation-timeline можно комбинировать с обычной animation-duration, но при наличии timeline длительность игнорируется: прогрессом правит скролл.

Поддержка в 2025-м: Chrome 115+, Edge 115+, Safari 26+ (с префиксом -webkit- в iOS 26). Firefox — за флагом, но уже в активной разработке. Для отстающих браузеров это деградирует безболезненно: без поддержки просто не будет анимации.

**Моя рекомендация**

Не пишите свой параллакс через JS, если это обычный маркетинговый лендинг. Нативный scroll-driven API считается на стороне compositor, поэтому дёрганий и микролагов на слабых устройствах меньше, чем при ручном обновлении свойств из JS.

Вывод: добавьте scroll() на прогресс-бар, view() на карточки — почувствуете разницу в скорости вёрстки сразу.
  • 🔥 1
Post #4548 356
⁣Есть два мощных CSS-механизма, которые позволяют анимировать появление и исчезновение попапов, диалогов и вообще любых элементов с display: none без единой строчки JS. Речь про @starting-style и transition-behavior: allow-discrete.

---

## Проблема
Раньше нельзя было плавно показать попап, который скрыт через display: none (стандарт для popover/dialog в закрытом состоянии). Браузер не мог найти стартовое состояние для перехода. Результат — либо мгновенное появление, либо костыли с JS и реквайрами.

## Решение

**Шаг 1. display и overlay участвуют в transition**

Свойство display — дискретное. Чтобы переход не сработал мгновенно, нужно разрешить дискретные значения анимироваться:

transition-behavior: allow-discrete;


Если указать это в transition для display, то браузер «перекидывает» значение с none на block в **начале** анимации появления и в **конце** анимации исчезновения. Элемент для закрывающегося попапа остаётся видимым до конца анимации, а потом получает display: none.

Для попапов важно ещё и overlay — отключает верхний слой (top layer) только после завершения анимации.

**Шаг 2. @starting-style — стили «до старта»**

Когда браузер переключает display с none, у элемента нет предыдущего состояния, от которого можно анимировать. @starting-style задаёт стартовые стили:

.popover {
opacity: 0;
transform: translateY(-10px);
transition:
opacity 0.3s ease,
transform 0.3s ease,
display 0.3s allow-discrete,
overlay 0.3s allow-discrete;
}

.popover:popover-open {
opacity: 1;
transform: translateY(0);
}

@starting-style {
.popover:popover-open {
opacity: 0;
transform: translateY(-10px);
}
}


## Как это работает

- При открытии: @starting-style мгновенно применяет opacity: 0, затем срабатывает переход к opacity: 1.
- При закрытии: обычные стили возвращают попап к opacity: 0, а display: none и уход из top layer (overlay) применяются только в конце transition.

## Важные нюансы

1. Без allow-discrete display переключится мгновенно, анимация исчезновения не будет.
2. overlay нужно указывать именно для элементов в top layer (popover, dialog). Обычные выпадашки могут обойтись без него.
3. Поддержка: все современные браузеры, включая Safari 17.5+ и Chrome 117+. Работает и для <dialog>, и для [popover].

## Минимальный пример

<button popovertarget="tip">Показать</button>
<div popover id="tip">Подсказка</div>


#tip {
opacity: 0;
transform: scale(0.95);
transition:
opacity 0.2s ease,
transform 0.2s ease,
display 0.2s allow-discrete,
overlay 0.2s allow-discrete;
}

#tip:popover-open {
opacity: 1;
transform: scale(1);
}

@starting-style {
#tip:popover-open {
opacity: 0;
transform: scale(0.95);
}
}


Теперь никакого JS для анимации попапов — только чистый CSS. Удобно, когда нужно скрыть логику анимации из бандла и убрать хрупкие кодушки с анимациями через классы.
Post #4546 468
🤣 Должно быть вот так:
«Я создал этот баг, Гендальф
3000 лет назад»


💥 xCode Journal
  • 😁 4
Post #4544 515
💻 Хакер похитил с помощью агента API-ключ и сжег кредитов на $600 000!

Исследователь METR навайбкодил приложение для управления ИИ-агентами. Из-за бага интерфейс на несколько дней оказался открыт всему интернету, хакер нашел его и попросил агента раскрыть API-ключ. Последующие три недели гений просто тратил кредиты на ИИ-модели.

Самое прекрасное: большой расход кредитов заметили не сразу, так как METR регулярно проводит масштабные тесты, которые потребляют огромное количество токенов

✖️ xCode Journal
Post #4541 554
Будете в Питере - сохраняйте

Атмосферная квартира у метро «Петроградская»: инди-артхаус интерьер, дух старого Петербурга и проектор для уютных вечеров.

Подойдёт для отдыха и удалённой работы.

Посуточная аренда:
https://t.me/FlatErmitage
  • ❤ 1
Post #4537 435
OpenAI выкатила GPT-6 Astra — нового флагмана, который по первым цифрам делает прошлое поколение похожим на динозавра. Бенчмарки у модели просто огонь:
- Terminal-Bench 4.0: 57,7% (у Fable 5.1 — 55,8%, у GPT-5.6 Sol вообще жалкие 37,3%);
- Terminal-Bench Science: 64,6% против 52,6% у Fable 5.1;
- ARC-AGI-3: 99,9%;
- ExploitBench: 100%.

Цена в API — $10 за миллион входных токенов и $50 за миллион выходных. Fast mode, который шустрит до 2,5 раза быстрее, обойдётся в два раза дороже.

Пока Astra дали пощупать только избранным организациям. Но в ближайшие дни обещают раскатать её и на платных пользователей.

Теперь осталось только дождаться, когда доступ откроют всем, и посмотреть, что покажут честные независимые тесты 🥹
https://openai.com/index/gpt-6-astra/
Older posts →
Threads Profile ViewerView any public Threads profile without an account.Open ThreadLook →Writing with AI? Make it sound human.Metric37 rewrites AI drafts so they read naturally. Free AI detector, 1,500 words free.Try Metric37 →