Co robię w wolnym czasie

Aplikacja: oznaczanie zdjęcia swoim logo

Wiem, że na temat umieszczania logo/znaku wodnego na zdjęciach jest źródłem kontrowersji. Osobiście nie mam nic do tego, aby zamieścić firmowe logo na fotce, na której widnieje produkt naszego autorstwa. Z biznesowego punku widzenia ma to jak najbardziej sens, gdyż zaznajamiamy potencjalnego odbiorcę z naszą marką. Z technicznego punktu widzenia, jednym z głównych argumentów niestosowania znaku wodnego jest łatwość jego usunięcia. Są jednak algorytmy, ktre to zadania znacznie utrudniają. Ciekawy artykuł odnośnie wspomnianych algorytmów znajdziesz tutaj.

Dlaczego chcę napisać tą appke?

  1. Na OSX nie znalazlam narzędzia które by zamieszczało znak wodny w odpowiedniej jakości, w trybie bulk
  2. Chcę przetestować w działaniu nowe bezpieczniejsze algorytmy umieszczające logo na zdjęciach. A tak naprawdę poznać możliwości biblioteki do obróbki graficznej pod ruby 🙂

Pierwsze kroki

  1. Jak zainstalować środowisko programistyczne oparte na Ruby znajdziesz na stronie GoRails:
  2. Instalacja ruby
  3. Inicjalizacja appki rails, usuniecie strony startowej i setup routingu
  4. Dodanie bootstrapa
  5. Autoryzacja użytkownika za pomocą gemu Devise
  6. Setup testow

Stawiam na trójkę: Minitest, Factory Girl oraz Faker

Więcej o setupie testów dla nowych aplikacji w RoR oraz przetestowaniu modelu User z gemem Devise napiszę wkrótce.

Odpalenie projektu na produkcji

Na szybko wybrałam kosting na Heroku. Jak się okazało później, nie był to najlepszy wybór dla aplikacji tego typu. W darmowej wersji przestrzeń plików jest co jakiś czas resetowana do konfiguracji z repozytorium. Czy inaczej – wszystkie uploadowane pliki są kasowane mimo istniejących referencji w bazie.

Instalacja Heroku-CLI dla środowiska staging/production jest opisana tutaj:

Przydatne komendy, gdy pracujesz z Heroku:

Specyfikacja aplikacji

Rozbijając funkcjonalność na ficzery, mogę stwierdzić, że aplikacja powinna mieć:

Do zapisywania zdjęć w bazie wykorzystam gem Paperclip, update: w najnowszej wersji Rails (5.2) zalecane jest użycie wbudowanego we framework Active Storage

Na razie nie decyduję się na przechowywanie danych w chmurze, dlatego nie zmieniam domyślnego configu (storage.yml). Nowy model Gallery będzie mógł zawierać wiele zdjęć:

Formularz dodawania zdjęć do galerii będzie bazował na Direct Uploads, do którego dodałam js i css zgodnie z dokumentacją dla Active Storage. Dzięki temu pojawią się ładne animacje uploadowania plików

Znów przyda się scaffold:

Model zawierający logo będzie wyglądał tak:

Model użytkownika będzie w relacji z Galerią (może mieć ich wiele), tak samo jak i z Logo. Do przyszłego algorytmu będzie wykorzystywane tylko ostatnio dodane logo, dlatego zdefiniowałam osobny scope :last_logo:

Jak już wspomniałam wyżej, ostatnio stworzone logo będzie domyślnie tym, które zostanie naniesione na zdjęcie. Przycisk przy galerii umożliwi uruchomienie algorytmu i zmodyfikowanie wszystkich zdjęć z danej galerii za jednym razem.

Do edycji obrazków użyję gemu mini-magick. wymaga on biblioteki imagemagick. Na OSX zaistalujesz ją wpisujac:

Na heroku jest już zainstalowana jedna z jej wersji, możesz to sprawdzić wpisując w konsolę polecenie convert:

Wybrałam 5 modyfikatorów, które transformują logo z zachowaniem rozpoznawalności. Innymi słowy wprowadzają transformację w stopniu na tyle niewielkim, aby nadal logo wyglądało w miarę podobnie do oryginału.

Algorytm będzie polegał na wybraniu losowo jednego do pięciu modyfikatorów. Parametry dla każdego z nich również zostaną wybrane losowo.

Do obsługi modyfikacji logo oraz naniesienia go na fotografię stworzyłam osobny serwis LogoProcessing. Metoda call wywoływana jest za pomocą wspomnianego przycisku przy galerii zdjęć. Wielkość zdjęc ograniczyłam ze względu na szerokość. Przekraczające ustalony rozmiar zostaną zeskalowane do szerokości 1024 px. Lubię metaprogramowanie więc postanowiłam użyć metod dynamicznych.  Najpierw wtorzę losowo ciąg modyfikatorów a potem po kolei wywołuję na jego elementach metodę send aby zaaplikować poszczególne modyfikacje na logo.

Gotowe obrazki zostaną zapisane w tym samym modelu z którego pochodzą. Ostatecznie klasa Gallery wygląda tak:

Musiałam przemyśleć, jak zaprezentować gotowe zdjęcia do pobrania. Postanowiłam, że jesli w danej galerii naniesiono już logo, to zamiast bazowych zdjęć pojawią się te oznaczone. Dodatkowo będą posiadały link do pobrania na dysk.

Gotowa aplikacja do nanoszenia zmodyfikowanego znaku wodnego

Gotowa aplikacja znajduje się tutaj

Po zaimplementowaniu ficzerów wymienionych w specyfikacji postawiłam produkcję na Heroku. Na chwilę obecną brakuje walidacji typu pliku, nie ma komunikatu, jeżli nie załadowaliśmy wcześniej logo. Brakuje też walidacji minimalnych wymiarów logo oraz zdjęcia w galerii. Te i inne poprawki być może zrealizuję późniejszym czasie 🙂