Реализовать svg версию css background-size: обложка не работает идеально - PullRequest
0 голосов
/ 01 сентября 2018

Я использую Imagemagick для генерации изображений из предварительно вычисленных SVG. Svg происходит от компиляции некоторой информации, полученной из редактора, который мы создали. В редакторе мы используем стили CSS для предварительного просмотра изменений.

Теперь, когда мы хотим визуализировать фактическое изображение, мы берем базовую информацию, чтобы сгенерировать фактический svg, который затем преобразуется в плоское изображение с помощью библиотеки imagemagick.

Все работает отлично, кроме той части, где стили фона CSS реализованы с использованием шаблона svg. Ниже приведен код CSS

background-repeat: repeat;
background-size: cover;
background-position: -134px -2px;

Ниже приведен пример сгенерированного SVG

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
        <svg  xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200" overflow="visible" fill="#000">
            <defs>
                <pattern id="bg_40b043e9944a4239b118e0b938054afb" x="-67%" y="-1%" width="100%" height="100%">
                <image preserveAspectRatio="xMinYMin slice" width="200" height="200" xlink:href="imagedata" />
                </pattern>
            </defs><rect width="100%" height="100%" fill="url(#bg_40b043e9944a4239b118e0b938054afb)" /></svg>

Детали для рассмотрения

  1. Родительский svg 200x200
  2. Исходная позиция фона: x: -134px и y: -2px, но в процентах она равна -67% и -1% соответственно.
  3. Без позиционирования все работает идеально.

Учитывая вышеизложенное, я думаю, что проблема заключается в изображении шаблона x, y смещении (я думаю), а также ширине / высоте. Ниже приведен вывод svg и css версии фона

Рендеринг изображения из SVG Рендеринг изображения из SVG

Снимок HTML-версии с помощью CSS. Снимок html-версии с помощью css Изображение используется для фона Изображение, используемое для фона

Второй результат - это то, чего мы хотим достичь повсюду.

Полный SVG, использованный для генерации первого изображения

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
        <svg  xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200" overflow="visible" fill="#000">
        <defs><pattern id="bg_40b043e9944a4239b118e0b938054afb" x="-67%" y="-1%" width="100%" height="100%"><image preserveAspectRatio="xMinYMin slice" width="200" height="200" xlink:href="https://i.stack.imgur.com/YHz1i.jpg"  /></pattern></defs><svg preserveAspectRatio="none" viewBox="0 0 200 200" x="0%" y="0%"><g opacity="1" fill-opacity="1" fill="url(#bg_40b043e9944a4239b118e0b938054afb)" stroke="none" stroke-width="0" stroke-dasharray="0" stroke-dashoffset="0"><rect width="100%" height="100%"   /><svg class="layer" overflow="visible" preserveAspectRatio="none" id="layer_1535228794723_0887552009010049"  width="160.4065" height="38.7969" x="16.75" y="66"><g id="translateLayer" ><g id="effectLayer" fill="#000" stroke="#c01d1d" stroke-width="2" stroke-dasharray="1" stroke-linecap="butt" stroke-linejoin="round"><svg width="100%" height="100%" viewBox="0 -26.09375 144.59375 29.6875" preserveAspectRatio="none" overflow="hidden"><g  font-size="25" font-family="ABeeZee" font-style="Normal" font-stretch="Normal" font-weight="400"><text y="-3"><tspan x="0">T</tspan><tspan x="14">e</tspan><tspan x="27">x</tspan><tspan x="40">t</tspan><tspan x="50"> </tspan><tspan x="57">o</tspan><tspan x="72">k</tspan><tspan x="85"> </tspan><tspan x="92">h</tspan><tspan x="107">e</tspan><tspan x="121">r</tspan><tspan x="131">e</tspan></text></g></svg></g></g></svg></g></svg></svg>

Любая помощь приветствуется!

1 Ответ

0 голосов
/ 01 сентября 2018

Вы можете достичь того, чего хотите, только если явно введете размер фонового изображения. CSS может располагать изображение по размеру, присущему ему, потому что само изображение является его объектом. В SVG шаблон является родительским для изображения, а размер плиток устанавливается независимо от размера изображения.

Второе осложнение связано с тем, что width и height в процентах относятся к ширине и высоте ссылки <rect>. и 100% для обоих приводят к тому, что плитка имеет тот же размер, что и прямоугольник. Это также означает, что независимо от того, что вы установили, соотношение сторон плитки имеет фиксированное отношение к соотношению сторон , ссылающегося на элемент , а не на содержащееся изображение.

Вам необходимо сохранить соотношение сторон, установленное изображением для рисунка. Самый стабильный способ сделать это - использовать координаты пространства пользователя, так как проценты всегда будут меняться при изменении соотношения сторон <rect>.

Установите patternUnits="userSpaceOnUse", сохраните исходный размер изображения (необходимо соответствующим образом масштабировать смещения изображения), а затем вам нужно установить patternTransform=scale(...), чтобы размер плитки шаблона соответствовал вашему <rect> в пути cover сделает.

<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"
     width="200" height="200" overflow="visible" fill="#000">
  <defs>
    <pattern id="bg_40b043e9944a4239b118e0b938054afb"
         patternUnits="userSpaceOnUse" x="-2010" y="-30" width="4500" height="3000"
         patternTransform="scale(0.0667)">
      <image width="4500" height="3000" xlink:href="https://i.stack.imgur.com/YHz1i.jpg"  />
    </pattern>
  </defs>
  <rect width="100%" height="100%" fill="url(#bg_40b043e9944a4239b118e0b938054afb)" />
</svg>

(Это действительно то же самое, что и ваша ссылка на CSS.)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...