PerfectVector
Autor: Irene Kim8 min czytania

Jednostki wzoru SVG: zachowaj właściwy rozmiar powtarzanych motywów

Kontroluj odstępy we wzorze SVG i rozmiar motywu za pomocą patternUnits, patternContentUnits i viewBox. Porównaj zmianę wymiarów kształtu ze skalowaniem całej jego grupy.

Na tej stronie

Aby zachować stałe odstępy między powtórzeniami wzoru SVG podczas zmiany wymiarów kształtu, użyj patternUnits="userSpaceOnUse" oraz liczbowych wartości szerokości i wysokości kafelka. Grafikę wewnątrz tego kafelka kontroluj osobno za pomocą patternContentUnits lub atrybutu viewBox wzoru.

To rozróżnienie ma znaczenie, gdy mały motyw wypełnia zarówno wąską plakietkę, jak i szeroki baner. Możesz chcieć uzyskać więcej kopii na banerze, większe odstępy między kopiami lub rozciągnięty motyw. Każdy z tych efektów wymaga innego wyboru współrzędnych. Skalowanie całej grupy banera ponownie zmienia wynik.

Jeśli motyw składa się już ze ścieżek SVG, zachowaj te ścieżki. Wektoryzacja należy do wcześniejszego etapu pracy, gdy jedynym źródłem jest obraz rastrowy.

Oddziel kafelek od jego grafiki

Wzór składa się z powtarzanego prostokątnego kafelka i zawartości narysowanej w jego wnętrzu. patternUnits kontroluje wartości x, y, width i height kafelka. patternContentUnits kontroluje współrzędne zawartości, chyba że wzór ma atrybut viewBox.

UstawienieCo kontrolujeWartość domyślnaPrzydatny wybór
patternUnitsPołożenie i wymiary kafelkaobjectBoundingBoxuserSpaceOnUse, aby określić odstępy liczbowo w bieżących współrzędnych użytkownika obiektu docelowego
patternContentUnitsWspółrzędne ścieżek i kształtów wewnątrz kafelkauserSpaceOnUseobjectBoundingBox, gdy wymiary motywu mają zależeć od granic obiektu docelowego
viewBox wzoruProstokątny obszar w układzie współrzędnych dopasowywany do każdego kafelkaBrakUkład współrzędnych motywu do wielokrotnego użytku, na przykład 0 0 40 40

Przy objectBoundingBox szerokość .25 oznacza jedną czwartą szerokości prostokąta ograniczającego obiektu, na który nakładane jest wypełnienie. Nie oznacza jednej czwartej szerokości motywu. Prostokąt o szerokości 120 jednostek otrzymuje kafelek o szerokości 30 jednostek, a prostokąt o szerokości 240 jednostek — kafelek o szerokości 60 jednostek.

Domyślną wartością dla zawartości pozostaje userSpaceOnUse. Zmiana samego patternUnits może więc zmienić odstępy między motywami, pozostawiając każdy motyw w tym samym rozmiarze. Ustaw oba atrybuty świadomie, zamiast zakładać, że zmieniają się razem.

Porównaj cztery wersje tego samego liścia

Na potrzeby tego przykładu narysowaliśmy ścieżki liścia i wyrenderowaliśmy SVG w przeglądarce. Oba prostokąty docelowe mają wysokość 80 jednostek, a ich szerokości wynoszą 120 i 240. Na zrzucie ekranu dodano etykiety i tła wokół tych oryginalnych kształtów. To demonstracja SVG, a nie wynik konwersji w PerfectVector.

Cztery wiersze wzorów SVG wyrenderowanych w przeglądarce, porównujące stały kafelek, względny kafelek, względne współrzędne motywu i nadrzędne działanie viewBox na wąskich i szerokich prostokątach
Poszerzenie obiektu docelowego dodaje powtórzenia w pierwszym i ostatnim wierszu. Względne szerokości kafelków zachowują cztery kolumny; względne współrzędne zawartości dodatkowo rozciągają liść.

Czytaj wiersze od góry do dołu:

  1. Stały kafelek 40 × 40 tworzy trzy kolumny w wąskim prostokącie i sześć w szerokim. Wymiary liścia pozostają bez zmian.
  2. Szerokość kafelka .25 zachowuje cztery kolumny w obu obiektach docelowych. W szerszym prostokącie odstępy między liśćmi są większe, ponieważ współrzędne liścia nadal używają jednostek użytkownika.
  3. Współrzędne zawartości zależne od prostokąta ograniczającego rozciągają liść w poziomie, gdy szerokość obiektu docelowego podwaja się. Jego rozmiar w pionie pozostaje taki sam, ponieważ wysokość obiektu docelowego się nie zmienia.
  4. Stały kafelek 40 × 40 z viewBox="0 0 40 40" przywraca wynik z pierwszego wiersza, mimo że patternContentUnits="objectBoundingBox" pozostaje w kodzie. Atrybut viewBox wzoru ma pierwszeństwo.

Otwórz kompletny przykład

Zapisz ten kod jako pattern-units.svg i otwórz go bezpośrednio w przeglądarce. Cztery wiersze używają tych samych definicji co ilustracja, ale bez jej etykiet i teł. Każda para prostokątów znajduje się w grupach przesuniętych transformacją, dzięki czemu ich lokalne początki układów współrzędnych można porównać.

<svg xmlns="http://www.w3.org/2000/svg" width="560" height="420" viewBox="0 0 560 420">
<defs>
  <pattern id="fixed" patternUnits="userSpaceOnUse" width="40" height="40">
    <path d="M8 24 Q8 6 30 8 Q30 26 8 24Z" fill="#127f70"/>
  </pattern>
  <pattern id="tile" patternUnits="objectBoundingBox" width=".25" height=".5">
    <path d="M8 24 Q8 6 30 8 Q30 26 8 24Z" fill="#127f70"/>
  </pattern>
  <pattern id="both" patternUnits="objectBoundingBox" patternContentUnits="objectBoundingBox" width=".25" height=".5">
    <path d="M.04 .30 Q.04 .08 .20 .10 Q.20 .33 .04 .30Z" fill="#127f70"/>
  </pattern>
  <pattern id="box" patternUnits="userSpaceOnUse" patternContentUnits="objectBoundingBox" width="40" height="40" viewBox="0 0 40 40">
    <path d="M8 24 Q8 6 30 8 Q30 26 8 24Z" fill="#127f70"/>
  </pattern>
</defs>
  <g transform="translate(20 20)"><rect width="120" height="80" fill="url(#fixed)"/></g>
  <g transform="translate(220 20)"><rect width="240" height="80" fill="url(#fixed)"/></g>
  <g transform="translate(20 120)"><rect width="120" height="80" fill="url(#tile)"/></g>
  <g transform="translate(220 120)"><rect width="240" height="80" fill="url(#tile)"/></g>
  <g transform="translate(20 220)"><rect width="120" height="80" fill="url(#both)"/></g>
  <g transform="translate(220 220)"><rect width="240" height="80" fill="url(#both)"/></g>
  <g transform="translate(20 320)"><rect width="120" height="80" fill="url(#box)"/></g>
  <g transform="translate(220 320)"><rect width="240" height="80" fill="url(#box)"/></g>
</svg>

Zacznij od wzoru fixed i zmień tylko szerokość drugiego prostokąta. Następnie przyjrzyj się wzorom tile i both, zanim zmienisz ścieżkę. Dzięki temu wybór współrzędnych pozostaje oddzielony od samej grafiki. Jeśli chcesz wprowadzić szersze zmiany ścieżek i kolorów, skorzystaj z poradnika edycji SVG.

Użyj viewBox, gdy motyw ma własne współrzędne

Atrybut viewBox wzoru pozwala zachować dla liścia znany obszar rysowania, podczas gdy kafelek ma niezależny rozmiar. Specyfikacja wzorów SVG dopasowuje ten obszar rysowania do kafelka za pomocą viewBox i preserveAspectRatio.

W ostatnim wierszu zarówno kafelek, jak i viewBox mają wymiary 40 × 40, więc nie ma rozbieżności proporcji. Jeśli później nadasz kafelkowi prostokątny kształt, domyślne ustawienie preserveAspectRatio="xMidYMid meet" zachowa proporcje motywu i wyśrodkuje dopasowany obszar rysowania. preserveAspectRatio="none" pozwala na niezależne skalowanie w poziomie i w pionie. Wybierz je tylko wtedy, gdy zniekształcenie jest zamierzone.

Zmiana patternContentUnits nie rozwiąże problemu z rozmiarem, jeśli wzór ma atrybut viewBox: w tym przypadku patternContentUnits nie ma żadnego wpływu. Zmień wymiary kafelka, viewBox lub regułę zachowania proporcji w zależności od tego, która część ma się zmienić.

Wzór przydaje się, gdy jedna definicja ma tworzyć powtarzane wypełnienie. Jeśli zamiast tego potrzebujesz osobno rozmieszczonych kopii, symbole SVG i instancje use lepiej odpowiadają temu zadaniu.

Zmiana wymiarów prostokąta różni się od skalowania jego grupy

userSpaceOnUse ustala odstępy we współrzędnych użytkownika, a nie w niezmiennych pikselach ekranu. Transformacja może skalować te współrzędne, w tym wypełnienie wzorem.

Otworzyliśmy także dwie wersje z powyższą definicją fixed. Pierwszy prostokąt miał width="240". Drugi zachował width="120" wewnątrz grupy z transform="translate(20 120) scale(2 1)". Oba zajmowały w tym dokumencie 240 jednostek ekranowych, ale pierwszy pokazywał sześć kolumn liści, a prostokąt po transformacji — trzy kolumny rozciągnięte w poziomie.

Uwzględnij to rozróżnienie przy rozwiązywaniu problemów z responsywną grafiką:

  • Aby odsłonić więcej powtórzeń, powiększ geometrię obiektu docelowego, zachowując niezmienioną skalę jego współrzędnych.
  • Aby powiększyć całą kompozycję, przeskaluj grupę i uwzględnij, że wygląd jej wzoru również ulegnie skalowaniu.
  • Jeśli układ strony zmienia wyświetlany rozmiar głównego elementu SVG, sprawdź odwzorowanie jego viewBox, zanim uznasz atrybuty wzoru za przyczynę.

Specyfikacja układów współrzędnych SVG opisuje transformacje stosowane do współrzędnych użytkownika. W przypadku rozbieżności między aplikacjami najpierw sprawdź wymiary dokumentu SVG; same jednostki wzoru nie mogą określić fizycznego rozmiaru wyjściowego.

Przygotuj własny motyw przed jego powieleniem

Jeśli Twój motyw istnieje tylko jako PNG lub JPG, PerfectVector może odtworzyć geometrię SVG potrzebną do powielania. Przekonwertuj motyw na grafikę wektorową, otwórz wynik w edytorze i sprawdź obrys, małe szczeliny oraz niepożądane kształty tła, zanim umieścisz go we wzorze.

Zachowaj osobny źródłowy plik SVG tego motywu. Zbuduj kafelek wokół jego kopii, a następnie przetestuj zarówno wąski, jak i szeroki obiekt docelowy. Istniejąca grafika wektorowa może od razu przejść do tego etapu edycji. Ręczne przerysowanie prostego znaku geometrycznego może być szybsze, natomiast fotografię lepiej czasem zachować jako obraz niż odwzorowywać ją za pomocą złożonego zestawu ścieżek.

Renderowanie w przeglądarce nie potwierdza, że każda aplikacja projektowa zachowuje definicję wzoru. Otwórz ponownie zapisany plik w docelowej aplikacji i sprawdź w niej odstępy między powtórzeniami oraz kształt motywu. Powtarzane wypełnienie nie tworzy też niezależnych, edytowalnych kopii każdego widocznego liścia. Poradnik dotyczący plików SVG wyjaśnia, dlaczego struktura dokumentu ma znaczenie obok jego wyglądu.

Przed przekazaniem pliku sprawdź, czy każde fill="url(#...)" wskazuje istniejący, unikalny identyfikator wzoru, czy kafelek ma dodatnie wymiary i czy motyw mieści się w przeznaczonym dla niego kafelku. Wzory SVG zwykle przycinają zawartość na granicy kafelka, więc liść przekraczający krawędź wymaga świadomego zaprojektowania powtórzeń, zamiast założenia, że wystająca część będzie widoczna.

Najczęściej zadawane pytania

Dlaczego odstępy się zmieniły, ale liść pozostał w tym samym rozmiarze? patternUnits kontroluje wymiary kafelka, a patternContentUnits kontroluje współrzędne grafiki. Kafelek zależny od prostokąta ograniczającego, z zawartością używającą domyślnych współrzędnych użytkownika, może zmieniać odstępy bez zmiany rozmiaru liścia.

Dlaczego patternContentUnits wydaje się nie mieć żadnego wpływu? Sprawdź, czy wzór ma atrybut viewBox. Jeśli tak, to on definiuje odwzorowanie współrzędnych zawartości, a patternContentUnits nie ma żadnego wpływu.

Czy userSpaceOnUse zachowuje ten sam rozmiar wzoru na ekranie? Zachowuje liczbowe wymiary kafelka w bieżącym układzie współrzędnych użytkownika obiektu docelowego. Skalowanie grupy lub zmiana odwzorowania współrzędnych głównego elementu SVG na obszar wyświetlania nadal może zmienić wyświetlany rozmiar wzoru.

Źródła

  1. MDN — patternUnits — Definiuje współrzędne geometrii kafelka i domyślne odniesienie do prostokąta ograniczającego.
  2. MDN — patternContentUnits — Definiuje współrzędne zawartości i nadrzędne działanie viewBox.
  3. W3C — SVG patterns — Wyjaśnia dopasowanie do kafelka, zachowanie proporcji i przycinanie wzoru.
  4. W3C — SVG coordinate systems — Definiuje transformacje współrzędnych użytkownika, na których opiera się skalowanie grupy.

Masz motyw dostępny tylko jako obraz rastrowy, który chcesz ponownie wykorzystać? Zamień swój obraz na ścieżki SVG, sprawdź odtworzony obrys i przetestuj go w obu rozmiarach obiektu docelowego, zanim zbudujesz gotowy układ powtórzeń.

Więcej z bloga

Zacznij od czystszego SVG,
który łatwiej edytować