5.23. Korekcija perspektive¶
Upozorenje
Proizvoljna matrica transform veličine 3 puta 3 podržana je samo na OpenMV Cam N6 – na svim ostalim pločama ključna riječ tiho se zanemaruje. Aplikacije koje trebaju raditi bilo gdje drugdje moraju koristiti gotovu metodu rotation_corr() (s njezinim oblikom corners=) ili unaprijed izračunati ispravljenu sliku izvan ploče.
Gotova metoda rotation_corr() pakira određenu obitelj perspektivnih izobličenja iza malog skupa parametara i radi na svakoj podržanoj ploči. Nekim aplikacijama treba izobličenje koje ne odgovara tom obliku: proizvoljno projektivno preslikavanje iz jednog četverokuta u drugi, kalibrirana korekcija za poznato postavljanje koje je već riješeno izvan mreže, matrica izobličenja koju je neki prethodni algoritam predao gotovu. Za njih draw_image() – zajedno s copy(), crop() i scale() – prihvaća ključnu riječ transform koja prima ručno izgrađenu matricu 3 puta 3 koja izravno opisuje izobličenje.
5.23.1. Afine i projektivne transformacije¶
Geometrijska izobličenja izražavaju se u homogenim koordinatama: položaj piksela (x, y) s dodanom 1, pomnožen s matricom 3 puta 3.
Afini oblik mjesto je za početak. Njegov je donji redak fiksiran na \((0, 0, 1)\):
Raspisano, svaka izlazna koordinata linearna je kombinacija ulaznih koordinata uvećana za konstantu:
što obuhvaća skaliranje, rotaciju, smicanje i translaciju u bilo kojoj kombinaciji – i pod svima njima paralelne linije ostaju paralelne.
Projektivni (perspektivni) oblik oslobađa donji redak:
Raspisano:
Dijeljenje s \(w' = g x + h y + 1\) ono je što transformaciju čini projektivnom, a ne tek afinom. Kada su \(g\) i \(h\) oboje nula, \(w'\) ostaje jedan i dijeljenje ne čini ništa – ponovno afini oblik. Kada je bilo koji različit od nule, \(w'\) se mijenja s ulaznim položajem i pikseli na različitim položajima skraćuju se za različite iznose, što više ne održava paralelne linije paralelnima – to je upravo trapezni efekt gledanja ravne plohe iz kosog kuta. Projektivna transformacija najopćenitije je geometrijsko izobličenje koje ravne linije preslikava u ravne linije; skaliranje, zrcaljenje, transponiranje, rotiranje i korekcija rotacije s četiri kuta sve su posebni slučajevi jedne takve.
Imenovane transformacije izravno proizlaze iz afinog oblika. Identitetska transformacija jedinična je matrica, a:
Za većinu ručno izgrađenih transformacija aplikacija počinje s jednom od ovih kao osnovom i množi dalje matrice za svaku dodatnu operaciju, završavajući s jednom matricom 3 puta 3 koja opisuje složeno izobličenje. Matrice se primjenjuju zdesna nalijevo: \(M = T R S\) prvo pokreće skaliranje, zatim rotaciju, pa translaciju. Složena operacija koja svakomu na kraju zatreba jest rotacija oko središta slike – gola rotacijska matrica vrti sliku oko ishodišta piksela u gornjem lijevom kutu, pa centrirana inačica pomiče središte \((c_x, c_y)\) u ishodište, rotira i vraća ga natrag:
5.23.2. Ključna riječ transform¶
Matrica ulazi kroz ključnu riječ transform, dostavljena kao ulab.numpy.ndarray veličine 3 puta 3. Metoda kojoj treba posegnuti jest draw_image(), koja izvor izobličuje kroz matricu dok ga crta na odredište – rezultat završava u međuspremniku koji aplikacija kontrolira, a izobličenje se slaže sa svim ostalim u pozivu: skaliranjem, alfa stapanjem, maskiranjem.
import ulab.numpy as np
M = np.array([[1.2, 0.0, -20.0],
[0.0, 1.2, -15.0],
[0.0, 0.0, 1.0]])
canvas.draw_image(img, transform=M)
Primjer izobličuje img na canvas skaliran 1,2 puta u svakom smjeru i pomaknut lijevo i gore za 20 odnosno 15 piksela – afino izobličenje izgrađeno izravno iz unosa matrice opisanih gore. Ista ključna riječ na copy(), crop() i scale() primjenjuje izobličenje na samu sliku.