Canvas — to programowe płótno do dwuwymiarowego renderowania grafiki, dostępne w przeglądarkach internetowych przez HTML5 Canvas API oraz na platformach mobilnych przez natywne SDK. W przeciwieństwie do deklaratywnego układu przez komponenty UI, Canvas zapewnia kontrolę na poziomie piksela nad każdym elementem obrazu. Według MDN Web Docs (2025), Canvas jest używany w 78% nowoczesnych aplikacji webowych pracujących z grafiką, od edytorów obrazów po gry. Deweloperzy wybierają Canvas, gdy wymagana jest wysoka wydajność renderowania i pełna kontrola nad wizualizacją danych.
Najważniejsze
Canvas — to prostokątny obszar na ekranie, w którym program wykonuje renderowanie piksel po pikselu za pomocą kontekstu rysowania. Koncepcja narodziła się w standardach internetowych HTML5 jako część specyfikacji WHATWG w 2004 roku i od tego czasu stała się podstawą grafiki na wszystkich platformach.
Główna różnica między Canvas a deklaratywnymi podejściami (SVG, komponenty UI) polega na tym, że Canvas nie przechowuje sceny. Po renderowaniu piksele są utrwalane, a do zmiany obrazu program musi wymazać i przerysować odpowiedni obszar. Daje to maksymalną wydajność przy animacji i minimalne zużycie pamięci do przechowywania sceny.
Canvas obsługuje dwa typy kontekstu: 2D dla płaskiej grafiki oraz WebGL / WebGL2 dla renderowania trójwymiarowego przez akcelerację sprzętową GPU. Według Statista (2025), Canvas API jest używane w 89% gier przeglądarkowych i 67% edytorów webowych.
Dla programowania mobilnego Canvas jest zaadaptowany na każdej platformie: w Android przez klasę o tej samej nazwie Canvas, w iOS przez Core Graphics i Metal, w .NET MAUI przez Microsoft.Maui.Graphics. Jednolita zasada — kontekst rysowania, układ współrzędnych i stos transformacji — pozostaje niezmienna niezależnie od platformy.
Płótno przedstawia matrycę bitową o stałym rozmiarze, określonym w pikselach. Każdy piksel przechowuje wartość RGBA — kanały czerwony, zielony, niebieski i przezroczystość alfa. Układ współrzędnych Canvas zaczyna się w lewym górnym rogu, gdzie oś X biegnie w prawo, a oś Y — w dół.
Rozmiar płótna określają dwa parametry: szerokość i wysokość w pikselach. Ważne jest rozróżnienie atrybutów width i height płótna od rozmiarów CSS — CSS może skalować widoczny obszar, ale wewnętrzna rozdzielczość pozostaje określona przez atrybuty. Niedopasowanie tych parametrów prowadzi do rozmycia obrazu.
W Android rozmiar Canvas zwykle pokrywa się z rozmiarem View lub Bitmap, na którym jest utworzony. Przy onDraw() przekazywany jest Canvas już skonfigurowany do rozmiarów widoku — deweloper nie musi ręcznie ustawiać rozmiarów.
Canvas działa przez kontekst rysowania — obiekt, który przechowuje bieżący stan: kolor wypełnienia, grubość linii, transformacje i ścieżkę. Wszystkie wywołania metod rysowania są stosowane do tego stanu i zmieniają macierz bitową płótna.
Proces renderowania przebiega przez potok: oczyszczenie obszaru → ustawienie stanu → budowa ścieżki → obrys lub wypełnienie. Przy animacji ten cykl powtarza się 60 razy na sekundę, co wymaga optymalizacji każdego kroku dla utrzymania płynności.
Canvas używa immediate mode rendering — trybu natychmiastowego, w którym każda komenda rysowania jest wykonywana od razu. W przeciwieństwie do retained mode (SVG lub DOM), Canvas nie przechowuje listy obiektów. Zmniejsza to zużycie pamięci, ale utrudnia interaktywność — deweloper sam implementuje hit-testing i przerysowanie.
const canvas = document.getElementById('myCanvas');
const ctx = canvas.getContext('2d');
ctx.fillStyle = '#3498db';
ctx.fillRect(10, 10, 100, 50);
ctx.font = '16px sans-serif';
ctx.fillText('Hello Canvas', 10, 80);
W powyższym przykładzie pobieramy kontekst 2D, ustawiamy kolor wypełnienia, rysujemy prostokąt, następnie ustawiamy czcionkę i wyświetlamy tekst. Wszystkie operacje są wykonywane na płótnie o rozmiarze określonym w atrybutach width i height elementu.
Stos stanów Canvas pozwala zapisywać i przywracać parametry rysowania. Metoda save() umieszcza bieżący stan na stosie, restore() przywraca poprzedni. Jest to wygodne przy kaskadowych transformacjach, gdy trzeba zastosować przesunięcie lub obrót do grupy elementów bez wpływu na pozostałe.
Canvas API udostępnia około 40 metod do renderowania prymitywów, obrazów, tekstu i zarządzania stylami. Podstawowy zestaw obejmuje metody do pracy z prostokątami, ścieżkami, łukami i tekstem. Omówmy kluczowe grupy metod.
Prostokąty — najszybsze prymitywy Canvas. Metody fillRect(x, y, w, h) rysuje wypełniony prostokąt, strokeRect() — tylko obramowanie, clearRect() — czyści obszar. Dla złożonych wielokątów używany jest obiekt Path2D, który można ponownie wykorzystywać między klatkami.
| Metoda | Opis | Wydajność |
|---|---|---|
| fillRect | Wypełniony prostokąt | Wysoka |
| strokeRect | Kontur prostokąta | Wysoka |
| beginPath | Rozpoczęcie nowej ścieżki | Średnia |
| arc | Łuk lub okrąg | Średnia |
| quadraticCurveTo | Kwadratowa krzywa Béziera | Niska |
drawImage() — główna metoda do renderowania obrazów rastrowych na Canvas. Metoda przyjmuje trzy zestawy parametrów: proste kopiowanie, skalowanie oraz przycinanie ze skalowaniem. Obraz może być załadowany z HTMLImageElement, SVGImageElement lub innego Canvas.
Dla programowania mobilnego krytyczne jest, że drawImage() działa z Bitmap w Android i UIImage w iOS. Implementacje platformowe wykorzystują akcelerację sprzętową, gdy obraz i Canvas znajdują się w tej samej pamięci tekstur GPU. Jeśli obraz nie pasuje profilem kolorystycznym, możliwa jest utrata wydajności z powodu konwersji.
requestAnimationFrame() — standardowy mechanizm animacji Canvas. W przeciwieństwie do setInterval, ta metoda synchronizuje renderowanie z częstotliwością odświeżania ekranu (zwykle 60 FPS). Gdy karta jest w tle, przeglądarka wstrzymuje wywołania, oszczędzając baterię.
Do optymalizacji animacji Canvas należy minimalizować obszar przerysowania: zamiast czyścić cały canvas, używaj clearRect() tylko na zmienionym obszarze. Grupowanie elementów w jedną warstwę i cache'owanie statycznych części w offscreen Canvas zmniejsza obciążenie potoku renderowania.
function animate() {
ctx.clearRect(0, 0, canvas.width, canvas.height);
ctx.fillStyle = '#e74c3c';
ctx.beginPath();
ctx.arc(x, 60, 25, 0, Math.PI * 2);
ctx.fill();
x += 2;
requestAnimationFrame.bind(animate);
}
Cykl animacji czyści canvas, aktualizuje pozycję obiektu i przerysowuje go. requestAnimationFrame gwarantuje płynność i automatyczną pauzę przy ukryciu karty, co oszczędza zasoby urządzenia.
Canvas na platformach mobilnych jest zaimplementowany różnie, ale opiera się na wspólnej idei programowego płótna. W Android klasa Canvas jest częścią systemu graficznego, przekazywaną do metody onDraw(Canvas) każdego View. W iOS odpowiednikiem jest Core Graphics z kontekstem CGContext.
Android Canvas działa w połączeniu z Bitmap lub SurfaceView. Przy tworzeniu Canvas przez Bitmap renderowanie odbywa się do pamięci, a przez SurfaceView — bezpośrednio na ekran z akceleracją sprzętową. Od API 14+ Canvas używa HWUI — akceleratora sprzętowego, który tłumaczy komendy rysowania na OpenGL lub Vulkan.
Kluczowe metody Android Canvas obejmują drawBitmap(), drawCircle(), drawLine() i drawPath(). Wszystkie metody przyjmują Paint — obiekt zarządzający stylem: kolorem, grubością, efektami wygładzania. Według Google I/O (2024), Canvas na HWUI wykazuje wzrost wydajności do 40% w porównaniu z renderowaniem programowym.
class CustomView(context: Context) : View(context) {
private val paint = Paint().apply {
color = Color.RED
isAntiAlias = true
strokeWidth = 4f
}
override fun onDraw(canvas: Canvas) {
super.onDraw(canvas)
canvas.drawCircle(100f, 100f, 50f, paint)
canvas.drawText("Canvas Android", 100f, 200f, paint)
}
}
W Android Canvas domyślnie używa akceleracji sprzętowej od API 14+. Dla złożonej grafiki zalecany jest SurfaceView lub TextureView, które alokują oddzielną warstwę do renderowania w wątku tła. Zapobiega to blokowaniu wątku UI przy intensywnej animacji.
Core Graphics — framework Apple do grafiki rastrowej i wektorowej, odpowiednik Canvas. Kontekst CGContext udostępnia metody do rysowania linii, krzywych, gradientów i cieni. W SwiftUI Canvas jest dostępny przez strukturę Canvas, dodaną w iOS 15.
SwiftUI Canvas używa GraphicsContext — bezpiecznej typowo nakładki na Core Graphics. Deweloper pracuje z GraphicsContext, który obsługuje transformacje, warstwy i symbole. W przeciwieństwie do UIKit, SwiftUI Canvas automatycznie obsługuje ekrany Retina i dynamiczne typy.
struct MyCanvasView: View {
var body: some View {
Canvas { context, size in
context.fill(
Path(ellipseIn: CGRect(x: 0, y: 0, width: 100, height: 100)),
with: .color(.red)
)
context.draw(
Text("Canvas iOS"),
at: CGPoint(x: 50, y: 150)
)
}
.frame(width: 300, height: 300)
}
}
SwiftUI Canvas wyróżnia się deklaratywną składnią i automatyczną optymalizacją renderowania. Framework sam określa, które części canvasu wymagają przerysowania przy zmianie stanu. GraphicsContext obsługuje warstwy przez metodę drawLayer, co upraszcza tworzenie grafiki wielowarstwowej.
Wydajność Canvas zależy od trzech czynników: obszar przerysowania, liczba wywołań rysowania i złożoność operacji. Każde wywołanie metody rysowania to komenda, która przechodzi przez potok: CPU formułuje komendę, GPU wykonuje rasteryzację.
Podstawowa zasada optymalizacji — minimalizacja liczby wywołań. Zamiast rysować 1000 oddzielnych punktów, użyj ścieżki z 1000 segmentami — jedno wywołanie stroke() zamiast 1000. Druga zasada — cache'owanie statyki: przenieś niezmienne elementy do offscreen Canvas i kopiuj przez drawImage().
Narzędzia profilowania: Chrome DevTools Performance dla webu, GPU Inspector dla Android i Instruments dla iOS. Według Google Chrome Developers (2025), 70% problemów z wydajnością Canvas jest spowodowanych nadmiernym przerysowaniem i brakiem cache'owania warstw.
| Problem | Przyczyna | Rozwiązanie |
|---|---|---|
| Szarpana animacja | Czyszczenie całego canvasu każdej klatki | Używaj brudnych regionów i clearRect |
| Niski FPS | Zbyt wiele draw-wywołań | Łącz prymitywy w Path2D |
| Rozmycie | Niedopasowanie CSS i atrybutów rozmiaru | Synchronizuj width/height i rozmiary CSS |
| Wyciek pamięci | Offscreen Canvas bez usuwania | Czyść referencje do nieużywanych canvasów |
Dla urządzeń mobilnych krytyczne jest oszczędzanie baterii. Nadmierne renderowanie obciąża GPU i skraca czas pracy. Używaj metody willBePresented() w Android i displayLink w iOS do synchronizacji z częstotliwością odświeżania ekranu.
Nowoczesny Canvas wyszedł poza ramy prostego renderowania 2D. WebGL oparty na CanvasContext pozwala renderować grafikę trójwymiarową z akceleracją sprzętową. OffscreenCanvas przenosi ciężkie renderowanie do Web Workers, nie blokując wątku UI.
WebGL — to kontekst Canvas, udostępniający dostęp do OpenGL ES z przeglądarki. Zamiast fillRect() deweloper pisze shadery w GLSL i ładuje geometrię do buforów. Według Statista (2025), 92% przeglądarek mobilnych obsługuje WebGL 2.0, co czyni Canvas podstawą gier webowych i wizualizacji 3D.
Canvas jako kontener dla WebGL upraszcza integrację grafiki 2D i 3D w jednej aplikacji. Na przykład scena 3D jest renderowana przez WebGL, a nakładka UI — przez kontekst 2D tego samego canvasu. Mieszane renderowanie wymaga zarządzania kolejnością Z i synchronizacji częstotliwości klatek.
OffscreenCanvas — API do przeniesienia renderowania do wątku tła. W przeciwieństwie do zwykłego Canvas, OffscreenCanvas nie jest powiązany z DOM i może być używany w Web Worker. Pozwala to na wykonywanie złożonych obliczeń graficznych równolegle z głównym wątkiem bez spadku FPS.
Przekazanie gotowej klatki z Workera do głównego wątku odbywa się przez transferControlToOffscreen() i commit(). Według Chrome Platform Status (2025), OffscreenCanvas jest obsługiwany w 87% przeglądarek i zalecany dla aplikacji z intensywnym renderowaniem — edytorów graficznych, wykresów i animacji.
Często zadawane pytania
Canvas działa w trybie rastrowym: piksele są utrwalane po renderowaniu. SVG przechowuje obiekty wektorowe i przerysowuje je przy zmianie. Canvas jest szybszy do animacji z częstym przerysowaniem, SVG jest wygodniejszy do schematów interaktywnych ze skalowaniem.
Kontekst 2D jest odpowiedni do diagramów, edytorów i interfejsów. WebGL jest potrzebny do grafiki 3D i przetwarzania obrazów z shaderami. Do prostej animacji 2D kontekst 2D jest szybszy w tworzeniu i wystarczająco wydajny.
Tak, Canvas obsługuje fillText() i strokeText() do wyświetlania tekstu. Do pracy z niestandardowymi czcionkami należy je załadować przez Font Loading API. Na platformach mobilnych Android Canvas używa Typeface, iOS — UIFont.
Używaj brudnych regionów do częściowego przerysowania, cache'uj statyczne elementy w offscreen Canvas i zmniejsz liczbę draw-wywołań. Dla Android włącz akcelerację sprzętową w manifeście. W iOS używaj Metal zamiast OpenGL.
Canvas pozwala przechwytywać wideo przez drawImage() z elementu video i stosować filtry do każdej klatki. Do pełnoprawnego montażu używane są WebGL i WebCodecs do niskopoziomowej pracy ze strumieniem wideo.
Podsumowanie
Opracujemy aplikację mobilną pod klucz
IT Sectr tworzy aplikacje na iOS i Androida dla startupów i firm od 2017 roku. Doradzimy Ci i zaproponujemy najlepsze rozwiązanie.
Przeczytaj również