Strona używa cookies (ciasteczek). Dowiedz się więcej o celu ich używania i zmianach ustawień. Korzystając ze strony wyrażasz zgodę na używanie cookies, zgodnie z aktualnymi ustawieniami przeglądarki.    X

Octave - szybkie klejenie obrazków cz. 1

Wstęp

Z racji istniejącego jeszcze na DobrychProgramach ograniczenia na liczbę obrazków w jednym wpisie na blogu, kilkukrotnie już musiałem sklejać kilka obrazków w jeden. Ostatnim razem było to aż 5 obrazków. Na szczęście nie musiałem stosować brutalnej metody, która przychodzi do głowy jako pierwsza: otworzyć w GIMP-ie pierwszy obrazek, rozciągnąć płótno, dodać drugi obrazek i tak do skutku.
Szybko i sprawnie zrobiłem to w Octave'ie.

GNU Octave to jedno z moich podstawowych narzędzi pracy, obok Opery, Kile i Geany. Jest to wolny pakiet numeryczny, podobnie jak opisany przez arlida Scilab. To, co arlid dotąd napisał o obsłudze Scilaba (cz. 1 i cz. 2 ), przekłada się w całości na Octave'a.

Do dzieła

Przyjmijmy na wstępie, że mamy do sklejenia dwa obrazki o takiej samej szerokości i wysokości (np. zrzuty z okna jakiegoś kreatora). Przyjmijmy też, że pierwszy obrazek nazwaliśmy "a.png", a drugi "b.png" (nazwy im krótsze, tym wygodniej).
Po uruchomieniu Octave'a, należy oczywiście przejść do katalogu, w którym znajdują się owe obrazki, u mnie jest to Pulpit, a więc:

r   e   k   l   a   m   a

octave-3.2.4:1> cd ~/Pulpit

Teraz wczytujemy pliki do zmiennych (znów, nazwy im krótsze, tym wygodniej):

octave-3.2.4:2> a=imread('a.png');
octave-3.2.4:3> b=imread('b.png');

Uwaga! Średniki na końcach linii są istotne - bez nich wyświetli się cała zawartość podanych zmiennych. Zmienne te są macierzami (tu: trójwymiarowymi tablicami liczb od 0 do 255) i to te macierze zostaną wypisane (nie zostaną wyświetlone obrazki).
Teraz można przejść do klejenia. Utworzymy dwie nowe zmienne (c i d), w których znajdą się sklejone obrazki.
Zmienna c będzie macierzą o wysokości równej sumie wysokości macierzy a i b, bo skleimy w niej a.png nad b.png.
Zmienna d będzie macierzą o szerokości równej sumie szerokości macierzy a i b, bo skleimy w niej a.png na lewo od b.png.

octave-3.2.4:4> c=[a;b];
octave-3.2.4:5> d=[a b];

Tu znów musimy pamiętać o średnikach na końcach, aby uniknąć zasypania ekranu mnóstwem liczb. Bardziej istotne jest jednak to, co dzieje się między znakiem równości a średnikiem:
"[" oznacza początek wprowadzania macierzy,
"]" oznacza koniec wprowadzania macierzy,
do macierzy c i do macierzy d wstawiamy wszystkie elementy macierzy a i b (całe obrazki), więc wystarczy podanie nazw zmiennych a i b,
średnik rozdzielający a i b w pierwszym klejeniu oznacza koniec wiersza macierzy, czyli że b idzie pod a, czyli to, o co nam chodziło,
spacja rozdzielająca a i b w drugim klejeniu oznacza następny element w wierszu, czyli że b jest obok a, czyli znów to, jak miało być.
Zamiast spacji może być też przecinek - bez różnicy.

Efekt możemy podejrzeć:

octave-3.2.4:6> imshow(c)
octave-3.2.4:7> imshow(d)

Tutaj średnik na końcu jest nieistotny.

Jeśli mamy więcej obrazków, postępujemy podobnie:

c=[a1;a2;a3;a4];

w przypadku kolumny obrazków i

c=[a1 a2 a3 a4];

w przypadku poziomego ciągu.
Można też połączyć obie sprawy: a1 i a2 obok siebie u góry, a3 i a4 pod nimi, też obok siebie:

c=[a1 a2;a3 a4];

Przyszedł czas na zapis:

octave-3.2.4:8> imwrite(c,'c.png')

Macierz c zapisujemy do pliku c.png. Octave po rozszerzeniu domyśla się jak ma tę macierz wykorzystać, więc żadne inne opcje nie są konieczne (choć istnieją).

Całą operację można jeszcze zapisać skrótowo w jednej linii:

imwrite([imread('a.png');imread('b.png')],'c.png')

oraz uprościć jeszcze bardziej, wywołując Octave'a z wiersza poleceń z podaną wyżej komendą jako parametrem:

q@q-laptop:~$ octave-3.2.4 -q --eval 'cd ~/Pulpit/; imwrite([imread("a.png");imread("b.png")],"c.png")'

"octave-3.2.4" - tym poleceniem odpalam u siebie Octave'a, polecenie to zależy od systemu operacyjnego,
"-q" jest tu po to, żeby Octave nie zanudzał nas informacjami powitalnymi,
"--eval" mówi, że jest kod do wykonania (więcej parametrów nie ma, więc po wykonaniu kodu, Octave się zamknie),
średnik w kodzie separuj poszczególne polecenia (tu mógłby też być przecinek).
W samym kodzie zmieniłem cudzysłowy pojedyncze na podwójne - Octave'owi nie robi różnicy który cudzysłów dostanie, ale że całe polecenie ubrane jest w cudzysłów, bez tej zmiany by się pogryzło.

Komplikator

A co będzie, jak obrazki sklejane obok siebie będą różnej wysokości, albo sklejane jeden pod drugim będą różnej szerokości? O tym w części drugiej.

PS. Inspiracją do takiego wykorzystania Octave'a był wpis Saskatchewana na jego blogu w My Opera. 

oprogramowanie porady programowanie

Komentarze