Управление размерами — тема важная, и чтобы максимально использовать возможности SVG, нужно хорошо понимать как всё работает.
Спецификация.
Вьюпорт
Содержимое SVG-элемента отрисовывается на бесконечном холсте и может быть сколь угодно большого размера, но видимая часть холста соответствует размерам SVG-элемента. Эта область отрисовки называется viewport
(вьюпорт).
SVG позволяет управлять как размерами вьюпорта, так и поведением содержимого относительно него: оно может обрезаться или показываться полностью, может растягиваться с потерей пропорций или стараться уместиться целиком, даже если при этом появляются пустые поля. Этим поведением можно управлять с помощью атрибутов.
Если просто вставить SVG на страницу и не задавать ему никакие размеры, он отобразится размером 300px на 150px, что не поместилось — обрежется:
Ширина и высота
Шириной и высотой элемента можно управлять стандартными свойствами width
и height
:
<svg width="350" height="200">
...
</svg>
Их можно задавать как атрибутами, так и в CSS:
.mysvg {
width: 350px;
height: 200px;
}
Для размеров в пикселях, задаваемых в атрибутах, единицы измерения можно не указывать.
Потаскайте ползунки, и вы увидите, что изменение ширины и высоты влияет только на вьюпорт и не влияет на содержимое, потому что оно отрисовывается на бесконечном холсте, и неизвестно область какого размера нужно ресайзить.
viewBox
Похожим образом не изменяя размеры содержимого ресайзится iframe
, но в случае с SVG это поведение можно изменить, если определить размеры области с помощью свойства viewBox
:
<svg width="350" height="200"
viewBox="0 0 180 180">
...
</svg>
Первые два значения — координаты X и Y верхнего левого угла отображаемой области, последние два — ширина и высота. viewBox
задаётся только атрибутом.
Попробуйте теперь изменить размеры, и вы увидите, что содержимое отресайзится, чтобы поместиться целиком.
viewBox
можно использовать, например, для кадрирования изображения, чтобы показывать не всю картинку, а только какую-то её часть:
Это очень простое демо, вот пример посложнее от Sarah Drasner.
Интересно, что если у SVG нет размеров, но задан viewBox
, изображение займёт собой всё доступное пространство:
<svg viewBox="0 0 180 180">
...
</svg>
Это поведение может стать проблемой: если размеры у иконок задаются в стилях, а они не загрузились — страница может превратиться в парад гигантских SVG-иконок. Чтобы этого не произошло, всегда явно задавайте в атрибутах SVG ширину и высоту, их потом легко переопределить в CSS.
preserveAspectRatio
Как мы видели в примере выше, если у SVG заданы размеры и viewBox
, содержимое будет сжиматься и растягиваться с сохранением пропорций, чтобы поместиться целиком, но этим поведением тоже можно управлять — с помощью свойства preserveAspectRatio
(оно задаётся только атрибутом).
Например, с помощью значения none
можно указать, что сохранять пропорции не нужно:
<svg width="350" height="200"
viewBox="0 0 180 180"
preserveAspectRatio="none"
>
...
</svg>
SVG с viewBox
и preserveAspectRatio='none'
ведёт себя очень похоже на img
: при изменении размеров содержимое масштабируется под размеры вьюпорта не сохраняя пропорции.
none
будет полезно для резиновых фонов:
Остальные значения preserveAspectRatio
состоят из двух частей: первая задаёт выравнивание, вторая — поведение элемента относительно вьюпорта.
Выравнивание задаётся одним значением, определяющим положение по вертикали и по горизонтали, например: xMaxYMin
. Для обеих осей можно задать положение в начале, в середине и в конце:
xMin
, YMin
— в начале оси
xMid
, YMid
— в середине
xMax
, YMax
— в конце
Эти значения можно комбинировать в любых сочетаниях, но порядок должен сохраняться: первым всегда идет значение для X, вторым для Y. Значение для Y всегда пишется с большой буквы.
Поведение элемента определяется второй частью preserveAspectRatio
. Возможные значения:
meet
— содержимое стремится уместиться целиком (как фон с background-size: contain
)
slice
— содержимое заполняет собой всю область видимости (как background-size: cover
: что не поместилось, обрежется)
Важно помнить, что preserveAspectRatio
не работает без viewBox
. viewBox
задает область, которая должна масштабироваться, preserveAspectRatio
определяет как именно она должна это делать.
Также нужно понимать, что preserveAspectRatio
срабатывает, если вьюпорт и вьюбокс имеют разные соотношения сторон. Если соотношения сторон совпадают, и содержимое умещается без полей, preserveAspectRatio
работать не будет (в этом случае в нём просто нет необходимости).
Для использования SVG в качестве иконок достаточно viewBox
и размеров, но если предполагается делать что-то более сложное, имеет смысл разобраться с единицами измерения и системой координат.
Единицы измерения
Внутри SVG можно использовать em
, ex
, px
, pt
, pc
, cm
, mm
, in
, проценты, а также единицы системы координат (user space units). Единицы системы координат соответствуют пикселям, поэтому для значений в пикселях единицы измерения указывать не нужно.
Системы координат
В SVG-документе есть две системы координат:
- Система координат области отрисовки — viewport space.
- Система координат содержимого — user space.
Отсчет системы координат вьюпорта начинается от левого верхнего угла вьюпорта, системы координат содержимого — от левого верхнего края вьюбокса.
По умолчанию система координат содержимого соответствует системе координат вьюпорта, а единицы измерения содержимого — единицам измерения вьюпорта, но при использовании трансформаций или viewBox
масштабируется вся система координат с единицами измерения, то есть пиксели из user space больше не равны пикселям из viewport space.
Поизменяйте размеры элемента и посмотрите что происходит с системой координат содержимого (она показана бирюзовым):
Система координат содержимого начинается из точки 0,0, и если вьюпорт и вьюбокс не совпадают, точка отсчета, как и вся система координат содержимого, будет ездить и масштабироватся вместе с вьюбоксом.
Масштабирование единиц измерения хорошо видно на примере обводки: изначально её толщина равна единице, но при изменении размеров видимая толщина обводки будет изменяться вместе с фигурой:
Если такое поведение нежелательно, это можно исправить с помощью свойства vector-effect
со значением non-scaling-stroke
, оно добавляется к содержимому SVG:
<circle r="60" cx="75" cy="75"
stroke="black" stroke-width="1"
vector-effect="non-scaling-stroke"/>
vector-effect
можно задавать как атрибутом, так и в CSS.
Также новая система координат создается при добавлении трансформаций:
Внутри трансформируемого элемента будет своя своя система координат, отличная от систем координат вьюпорта и вьюбокса.
Тема может выглядеть сложной, но на самом деле, достаточно немного поиграться с кодом, и всё станет понятно. Для лучшего понимания систем координат, размеров и трансформаций в SVG рекомендую демо Сары Суайдан, а также её статьи:
- Understanding SVG Coordinate Systems and Transformations (Part 1) — The viewport, viewBox, and preserveAspectRatio
- Understanding SVG Coordinate Systems and Transformations (Part 2) — The transform Attribute
- Understanding SVG Coordinate Systems and Transformations (Part 3) — Establishing New Viewports
Базовые трансформации
- « Предыдущая статья
- Следующая статья »
Теперь мы готовы начать изменять наши замечательные изображения. Но сначала давайте ознакомимся с <g>
элементом. С его помощью вы можете назначить свойства для любого набора элементов. На самом деле, в этом и состоит его единственная цель. Например:
<svg width="30" height="10">
<g fill="red">
<rect x="0" y="0" width="10" height="10" />
<rect x="20" y="0" width="10" height="10" />
</g>
</svg>
Все последующие преобразования суммируются в атрибуте преобразования элемента transform
. Преобразования могут быть последовательно суммированы, разделителем выступает пробел.
Перемещения
Иногда необходимо сместить элемент, хотя вы спозиционировали его согласно определённым атрибутам. Для этого используется translate()
.
<svg width="40" height="50" style="background-color:#bff;">
<rect x="0" y="0" width="10" height="10" transform="translate(30,40)" />
</svg>
Пример генерирует прямоугольник, перемещённый в точку (30,40) вместо точки (0,0).
если второе значение не задано, то оно приравнивается 0.
Вращение
Вращение элементов — это достаточно типичная задача. Используйте rotate()
для этого:
<svg width="31" height="31">
<rect x="12" y="-10" width="20" height="20" transform="rotate(45)" />
</svg>
Данный пример показывает квадрат который повернули на 45 градусов. Значение для rotate()
задаётся в градусах.
Смещение углов
Чтобы сделать ромб из нашего прямоугольника, доступны преобразования skewX () и skewY (). Каждый из них принимает угол, определяющий, насколько элемент будет искажён.
Масштабирование
scale()
изменяем размер элемента. Он использует 2 параметра. Первый — это коэффициент масштабирования по оси Х, а второй — по оси Y. Коэффициенты выражают сжатие по отношению к оригинальному изображению. Например, 0.5 уменьшает на 50%. Если второй параметр отсутствует, то тогда он принимается равным первому.
Комплексные перемещения с matrix()
Все приведённые выше преобразования могут быть описаны с помощью матрицы перемещений 2×3. Чтобы объединить несколько перемещений, можно установить результирующую матрицу с помощью matrix(a, b, c, d, e, f)
, которая преобразует координаты из предыдущей системы координат в новую систему координат посредством:
{
x
new
C
o
o
r
d
S
y
s
=
a
x
prev
C
o
o
r
d
S
y
s
+
c
y
prev
C
o
o
r
d
S
y
s
+
e
y
new
C
o
o
r
d
S
y
s
=
b
x
prev
C
o
o
r
d
S
y
s
+
d
y
prev
C
o
o
r
d
S
y
s
+
f
left{ begin{matrix} x*{mathrm{prevCoordSys}} = a x*{mathrm{newCoordSys}} + c y*{mathrm{newCoordSys}} + e y*{mathrm{prevCoordSys}} = b x*{mathrm{newCoordSys}} + d y*{mathrm{newCoordSys}} + f end{matrix} right.
См. конкретный пример документации SVG. Подробную информацию об этом свойстве можно найти в SVG Рекомендациях.
Эффекты на системе координат
В случае использования преобразований вы устанавливаете новую систему координат внутри элемента, к которому применяются изменения. Это означает, что единицы измерения которые вы определяете и его дочерние еи не будут соответствовать 1:1, но также будут искажены, повёрнуты, перемещены и смаштабированы в соответствии с преобразованиями.
<svg width="100" height="100">
<g transform="scale(2)">
<rect width="50" height="50" />
</g>
</svg>
В результата прямоугольник в примере выше будет 100x100px. Более интригующие эффекты возникают, когда вы используете такие атрибуты, как userSpaceOnUse
.
В отличие от HTML, SVG позволяет встраивать другие svg
элементы без разрыва. Таким образом вы можете запросто создать новую координатную систему используя viewBox
, width
и height
внутреннего svg
элемента.
<svg xmlns="http://www.w3.org/2000/svg" version="1.1" width="100" height="100">
<svg width="100" height="100" viewBox="0 0 50 50">
<rect width="50" height="50" />
</svg>
</svg>
На примере выше, так же как и на других примерах ранее, вы можете видеть такой же эффект увеличения изображения в два раза.
- « Предыдущая статья
- Следующая статья »
Часть 2: 3 онлайн-метода для сжатия SVG
Если вам нужно сжать только некоторые файлы SVG, вы можете просто использовать онлайн-компрессоры SVG, чтобы уменьшить размер файла. Вот 3 часто используемых метода, которые вы должны знать.
Метод 1: сжать или умереть
Сжать или умереть — это популярный онлайн-компрессор фотографий, который работает с форматами JPEG, JPEG XL, PNG, GIF, WebP, SVG и многое другое. Он предоставляет дополнительные функции для анализа и восстановления ваших фотографий. Кроме того, он может сжимать SVG для получения файлов меньшего размера при максимальном сохранении качества.
Шаг 1: Перейдите на https://compress-or-die.com/svg в своем веб-браузере, вы можете выбрать вкладку SVG в онлайн-компрессоре SVG. Нажмите на Выберите файл кнопку для загрузки файлов SVG.
Шаг 2: вставьте URL-адрес изображения и URI данных Base64 на веб-сайт. После этого он автоматически сожмет файл SVG. После завершения сжатия нажмите кнопку Копировать кнопку.
Шаг 3: он преобразует векторные файлы SVG в файлы SVG с наименьшим возможным размером файла с помощью Photoshop JSX-Script. Вы можете использовать скрипт для сжатия изображения SVG онлайн.
Способ 2: Окомпресс
Окомпресс — еще один универсальный онлайн-компрессор SVG, который позволяет вам сжать фотографии, видео и документы, включая файлы в формате SVG. Это позволяет уменьшить размеры изображений SVG без потери исходного качества изображений за счет удаления метаданных и многого другого.
Шаг 1: скопируйте URL-адрес https://ocompress.com/svg и откройте онлайн-компрессор SVG, чтобы уменьшить размер файла. Выберите приложение из 3 значков и загрузите его онлайн.
Шаг 2: Когда вы загрузили значок SVG, вы можете самостоятельно определить необходимые параметры в соответствии с вашими потребностями. Нажмите на Сжимать кнопку после завершения настроек.
Шаг 3: после завершения процесса сжатия SVG вы можете загрузить его на свое устройство. После этого вы можете проверить сжатый файл, если это тот файл, который вам нужен.
Способ 3: сжать онлайн
Сжать онлайн простой SVG-компрессор для качественного сжатия векторных изображений без потери качества. Он позволяет загружать файлы SVG из нескольких облачных сервисов, включая Dropbox, ссылки и многое другое. Это всегда позволяет получить гладкое и красивое изображение без пикселизации.
Шаг 1: Перейдите на https://compress-online.com/compress-svg в своем веб-браузере, вы можете щелкнуть ЗАГРУЗИТЬ.SVG кнопку, чтобы загрузить изображение SVG для сжатия файла онлайн.
Шаг 2: После загрузки файлов SVG нажмите кнопку СЖАТИЕ SVG кнопку, чтобы уменьшить размер SVG. Он автоматически сожмет файл SVG и представит детали.
Шаг 3: Нажмите СКАЧАТЬ кнопку, чтобы сохранить сжатые файлы SVG на жесткий диск. Он позволяет сохранять преобразованные файлы в Dropbox и другие облачные сервисы.