Back

HTML5 Canvas Transformations: Translate, Rotate, and Scale

7 min read

Transformasi HTML5 Canvas: Translate, Rotate, dan Scale

Setelah menguasai cara menggambar bentuk dasar, kemampuan penting berikutnya dalam pembuatan game canvas adalah memahami Transformasi. Ini termasuk memindahkan orientasi titik posisi (Translate), memutar arah kemiringan (Rotate), serta mengubah ukuran atau membalikkan arah sumbu (Scale / Flip) bagi object apapun yang digambar selanjutnya.

Konsep yang paling mendasar di Canvas Game Engine adalah Anda tidak memutar atau mengubah orientasi objek yang digambar tersebut. Yang dilakukan sebenarnya ialah memutar orientasi seluruh koordinat sumbu canvas (ruang kerjanya) sebelum merender memoles gambar yang diiginkan, dan barulah seluruh setingan sumbu dipulihkan kembali ke semula posisinya.

1. Mengelola State Ruang Kerja: save() dan restore()

Oleh karena orientasi transformasi selalu menimpa ke keseluruhan grid Canvas secara global (merubah dunia), Anda diwajibkan untuk biasa menggunakan metode save() yang berguna merekam rekam jejak status aslinya (normal dunia sebelum digeser/diputar). Setelah menerapkan pergerakan, Anda tinggal memanggil fungsi pendamping pasangannya yaitu restore() agar seluruh orientasi titik Canvas berbalik pemulihannya ke kondisi normalnya tadi.

ctx.save(); // Simpan koordinat dan orientasi normal-nya saat ini

// ... Terapkan modifikasi sumbu XY dengan Translate/Rotate, dilanjut Menggambar suatu wujud di dunia/grid mutasi ini ...

ctx.restore(); // Pemulihan paksa kembali titik orientasi canvas dari track record 'save' sebelumnya.

2. Memindahkan Titik Origin Orientasi Poros: translate(x, y)

Setelan bawaannya, titik asal origin Canvas Canvas (0, 0) selalu berada mati di sudut paling kiri-atas. Kode translate sengaja difungsikan mentransportasikan pemindahan titik poros origin tersebut kemanapun area layar yang kita rencanakan orientasikan pergerakannya. Saat Anda berniat memutar sebuah objek berporos di tengah (berbasis center point objek-nya layaknya kincir/jarum jam), maka syarat pertama absolut adalah Anda WAJIB memindahkan sumbu (0,0) persis masuk menembus ditengah wujud objek target perputaran.

const x = 100; // Target Posisi X Asli
const y = 100; // Target Posisi Y Asli
const lebar = 50;
const tinggi = 50;

ctx.save();
// Berlabuh memindahkan titik pusat 0,0 kanvas, tepat membelah pertengahan sumbu target Object
ctx.translate(x + lebar / 2, y + tinggi / 2); 

// Karena target (0,0) kita kini bukan lagi dari ujung layar pojok kiri atas, melainkan sudah di per-tengahan objek yang ditarget ini
ctx.fillStyle = 'blue';

// Agar menggambarnya persis presisi di center, proses gambar persegi panjang wajib dimundurkan (- minus) dengan porsi dari setengah(2) ukurannya
ctx.fillRect(-lebar / 2, -tinggi / 2, lebar, tinggi); 

ctx.restore(); // Tarik pulang ruang kerja dunia kanvas ke pemusatan ujung 0,0 sudut kiri atas kembali.

3. Merotasi Kemiringan Derajat Bentuk: rotate(angle)

Metode ctx.rotate(radiant) mencondongkan putaran satu ruang dimensi di koordinat rotasi pangkal origin titik (0,0) terkini. Inilah akar penyebab utama kenapa kita memprioritaskan proses geser poros (translate) pusat orientasi ketengah persis bentuk objek! (Kalau (0,0) nya tidak dipindahkan dari ujung kiri atas, maka objek Anda bukannya akan berputar melintir di tempat, melainkan sebaliknya berputar nyasar layaknya gerakan planet berevolusi memutari bingkai ujung ujung seluruh web Canvas screen!)

const sudutDegree = 45; // Angka derajat rotasi sudut
const hitunganRadian = sudutDegree * Math.PI / 180; // konversi ke hitungan Radian yang dipahami canvas

ctx.save();
// 1. Transplantasi/Geser pemutar canvas poros ketengah sumbu object
ctx.translate(150, 150);

// 2. Putar kemiringan putaran seluruh medan orientasi (harus wajib dihitung kedalam Radian)
ctx.rotate(hitunganRadian);

// 3. Menggambar wujud ke poros koordinat (0,0) baru yg telah termiringkan tersebut
ctx.fillStyle = 'red';
// Berukuran lebar & tinggi (50x50), nilai posisi digeser x minus setengah dan y minus setengah (-25) kebalikannya 
ctx.fillRect(-25, -25, 50, 50); 
ctx.restore();

4. Efek Balik/Cermin Flip Gambar serta Membesarkan Resolusi Rasio (Scale/Flip): scale(x, y)

Metode pembesaran dimensi ini merombak pelebaran panjang dan lebar pembesaran seluruh grid sumbu dari pergesaran skala ukur (Angka defaultnya adalah 1.0). Kalau Anda mengetik code x: 2, bentuk otomatis merentang ter-zoom pelebarannya serentak selebar dua(2) kali rentang panjang lipat.

Salah satu rahasia paling fundamental pada manipulasi grafis trik mem-balik (Flipping) Sprites karakter pemain/musuh dalam sebuah Game Platformer maupun Sidescroll yang bergerak di Game Development (Berbalik hadap kiri/berubah posisi ke kanan belakang). Ternyata ini memakai kelemahan skala Minus (- 1)

ctx.save();
// 1. Ubah poros point 0,0 ke badan pusat rotasinya
ctx.translate(250, 200);

// 2. Trik Memutarlompati Sumbu Orientasi Pembalik arah Gambar dengan ratio cerminan horizontal menggunakan penolakan minus (x = -1). Dimensi Vertical sengaja kita blok ditahan konstan (y = 1)
ctx.scale(-1, 1);

// 3. Gambaran Objek baru  di terjemahan efek Flip tersebut
ctx.font = '30px Arial';
ctx.textAlign = 'center';
ctx.textBaseline = 'middle';

// Karena orientasi dunianya terbalik(dari titik pusat yg kita atur tadi) - Text Yang Dituliskanpun Akan Jadi Terbaca seperti Tulisan Kaca Terbalik!
ctx.fillText('TEKS TERBALIK MENGHADAP KE KIRI!', 0, 0); 
ctx.restore(); // Pemulihan sumbu dimensi kembali normal