Изучив оба стандарта: IBM VGA и EXIF, написав пару публикаций по теме, у меня все равно ушло два дня, чтобы понять, откуда берется «полу-пиксель». И речь не о рендеринге сложных форм типа литер шрифта или иконок, а о стандартных ректанглах формата 100x100. Который по логике должен масштабироваться хорошо. Однако.

Полу-пиксель не новость. В любом редакторе, который умеет работать с вектором такие объекты как литеры шрифтов, иконки могут и будут, по своей форме, не совпадать с пиксельной сеткой. 

В растровых же программах и в браузере применяются алгоритмы растеризации, которые заполняют соседние пиксели определенным оттенком в зависимости от занимаемой формой площади. С этим все давно понятно. Но откуда берется полу-пиксель у куба размером 105x105 px? И как это возможно? Разбираемся с матчастью.

Сценарий

Разрабатываешь ты интерфейсы и нужно в макет поставлять баннера или часть чужого интерфейса: фрейм apple music, spotify, платежки сбера и тд. Заходишь на сайт, где это можно взять и делаешь принтскрин. Принтскрин в Figm’у и….

… и все четенько, пиксель в пиксель. Баннер 300x600 px. Идем за следующим. Делаем принтскрин на том же устройстве, на том же сайте и странице и …

… полу-пиксель. 

Эффект полу-пикселя можно получить в двух случаях: при целом значении размеров объекта и при дробном. Если при дробном параметре, как на виджете с яндекс музыкой, полу-пиксель напрашивается сам собой, то откуда он появляется при целом значении?

Спойлер: в обоих случаях имеем дело с увеличенным двукратно рендерингом логических пикселей. Но по порядку.

Раньше

До 2022 считалось, что у графического файла нет «разрешения». Оно конечно было, но использовалось только для печати, а в общей практики диджитал дизайнеров и верстальщиков отсутствовало. Ибо «до retina» и стандартизации DIP смысла в этом не было — не умели операционки, проф. софт и браузеры работать с этим параметром. 

О путаннице в терминологии и понятии «Разрешение», я подробно уже писал в статье

Во второй половине 2022 основные браузеры и проф ПО / Photoshop стали в полной мере поддерживать стандарт EXIF и научились работать с параметром “Resolution” почти как принтеры. И теперь Resolution по стандарту EXIF или Dancity по стандарту Material design , и «плотность пикселей» по русски, в полной мере используется в цифровых интерфейсах.

Разрешение / с одной стороны

Если на Retin’е сделать Принтскин, то параметры о разрешении запишутся в метаданные файла как 144 по высоте и 144 по ширине. Что соответствует двукратному увеличению от IBM стандарта в 72ppi.

На снимке у меня больше размер и разрешение, но в тексте использую стандартное соотношение. 

В самих параметрах файла будет указан размер по ширине и высоте, например 1440х900. Не стоит обманываться — это не реальный размер графического файла, а логический. 

Если стереть метаданные в файле и открыть его в фотошопе, то мы увидим файл размером 2880х1800. И он будет пиксель в пиксель. Так уж логика у OSX. 

А то разрешение, которое вы видите на мониторе, это вообще отдельная песня и к разрешению файла имеет косвенное отношение и к полу-пикселям тоже, поэтому опустим разговоры о разрешении монитора. 

Если вы открывали такой принтскрин в фотошопе или в Figm’е в начале 2022 года, то он открывался бы как файл с размером 2880х1800 и там и там. Сегодня этот же принтскрин и в фотошопе или в Figma откроется как изображение 1440х1800. 

Т.е. ПО научилось считывать данные о “resolution” и обрабатывать их, а точнее уменьшать изображение вдвое. Вдвое, потому, что Figma, значения отличные от 144 или 72 не понимает. 

Браузер / с другой стороны

Браузеры же работают с логическими пикселями, перерисовывая изображение в двукратном увеличении от количества логических пикселей по ширине и высоте. Поэтому в свойствах объекта при просмотре кода появляется полу пиксель. 

В случае с фреймом Яндекс музыки — это был бы полу-пиксель, если бы вы смотрели изображение с разрешением 72ppi и при выводе такого объекта линия бы сгладилась дорисовав в соседних пикселях оттенко.  А для 144ppi это целый пиксель. Здесь надеюсь, понятно.

А вот пример с баннером хоть значение объекта и целое, при открытии файла в Figma тоже даст полу-пиксель. Откуда — спрашивается?

Во первых, если очистить метаданные и бросить файл в фигму, то он откроется никак 1440х1800, а в два раза больше — 2880х1800, и на этом изображении все будет четко — пиксель в пиксель. То же будет если метаданные не тереть, а просто двукратно увеличить размеры файта. 

А вот в браузере не кратные двум значения объектов при определенных свойствах позиционирования, например в процентах или выровненные по центру, могут отрисовываться со смещением в 1 графический пиксель те половину логического. ведь математически для построения четкого изображения браузер работает с размером 2880х1800. да сам банер тоже рендерится в двукратном размере, но нечеткий параметр позиционирования например в 33% будет считаться и откругляться  2880х1800, а не от 1440х1800, что и может дать сдвиг на полпикселя. 

P.S.

Под рукой нет устройства на винде с матрицей на 13-15 дюймов и 2/4к разрешением, чтобы посмотреть, как файлы пишет и масштабирует винда. Буду признателен за освещение этого вопроса в комментариях. 

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

UP

По вопросам и дискуссии в комментариях отснял видео кейса. Всем спасибо за участие)