Membangun Mesin Pencari Gambar Berbasis Warna di Ruby

Diterbitkan: 2022-03-11

Dikatakan bahwa sebuah gambar bernilai seribu kata. Dan dalam banyak hal, kata-kata dalam gambar adalah warna. Warna adalah bagian integral dari kehidupan kita, dan kita tidak dapat menyangkal pentingnya mereka.

Saat melihat sebuah gambar, kita sering mencoba mengidentifikasi warna pada suatu bagian. Kita semua telah mencoba melakukannya tetapi tidak pernah melakukannya secara detail. Ketika diminta untuk mengidentifikasi warna dari sebuah gambar, kita cenderung melabelinya menggunakan nama warna tertentu, seperti merah, biru, dan hijau. Namun, jika kita diminta untuk mengekstrak 30 warna paling menonjol dalam sebuah gambar, mata kita tidak dapat mendeteksi atau mengidentifikasinya dengan mudah. Camalian adalah semua tentang ini. Ini membantu Anda mengekstrak warna dari gambar dan kemudian memainkannya.

Camalian: Pemilih Warna Ultiamte untuk Ruby

Pada artikel ini, kita akan mengintip apa itu ruang warna, apa yang ditawarkan permata Ruby Camalian, dan bagaimana itu dapat digunakan untuk membuat mesin pencari gambar sederhana yang menggunakan warna untuk mengidentifikasi dan membedakannya.

Ruang Warna

Sebelum kita mulai, mari kita pahami dulu beberapa konsep dasar tentang warna. Gambar yang disajikan di layar kami diwakili menggunakan array piksel dua dimensi. Meskipun file gambar dapat dikodekan dengan cara yang berbeda, representasi kasar setelah dekompresi dan decoding data adalah sama. Dalam representasi berbasis array 2d ini, setiap piksel dalam gambar berwarna memiliki tiga komponen: merah, hijau, dan biru. Meskipun gambar yang dicetak di atas kertas juga merupakan permukaan titik dua dimensi, titik-titik itu sendiri biasanya merupakan campuran dari empat komponen tinta: cyan, magenta, kuning, dan hitam. Ini di antara beberapa teknik berbeda lainnya yang digunakan untuk mewakili warna yang disebut ruang warna. Beberapa ruang warna yang paling populer digunakan adalah RGB, CMYK, HSL dan HSV. CMYK banyak digunakan di industri percetakan sementara yang lainnya digunakan di media digital.

Ruang Warna RGB

Setiap media elektronik fisik seperti layar CRT, LCD, atau telepon yang memancarkan cahaya menghasilkan warna dengan menggunakan tiga komponen: merah, hijau, biru. Mata manusia dapat mendeteksi jutaan warna dengan merangsang tiga jenis reseptor warna di mata. Anda dapat menghubungkan reseptor tersebut dengan R, G dan B.

Idealnya, setiap komponen warna disimpan dalam byte yang nilainya dapat berkisar antara 0 dan 255.

Ruang Warna HSL & HSV

Menata ruang warna RGB pada kubus agak menantang. Hasil mencoba merepresentasikannya pada kubus dan atau roda warna buruk. Saat bekerja dengan jutaan atau warna, setiap rona warna tidak dapat disejajarkan dengan benar pada ruang warna RGB.

mesin pencari gambar ruby

Untuk mengatasi masalah ini, pada tahun 1970-an peneliti memperkenalkan ruang warna HSV (Hue, Saturation, Value) dan HSL (Hue, Saturation, Lightness). Kedua ruang warna ini dapat disejajarkan pada roda warna dengan benar dan memudahkan untuk mengidentifikasi berbagai corak warna di atasnya.

Permata Ruby untuk Warna

Camalian adalah tentang warna. Salah satu hal paling sederhana yang dapat Anda lakukan dengan Camalian adalah mengidentifikasi setiap rona warna yang digunakan dalam sebuah gambar.

Katakanlah kita memiliki gambar dengan 15 warna berbeda.

Mengidentifikasi warna dari swatch tentu lebih mudah daripada mengidentifikasinya dari gambar itu sendiri. Terlebih lagi, ini adalah gambar yang sederhana, dan foto nyata yang diambil seringkali jauh lebih beragam dalam hal palet warnanya. Mengekstrak nilai warna dari gambar memerlukan beberapa bit kode yang cukup rumit, dan di situlah Camalian masuk. Camali melakukan hal-hal rumit ini untuk Anda sehingga Anda dapat mengekstrak informasi terkait warna dari gambar dengan mudah.

Mulai

Jika mengekstrak warna dengan Camalian mudah, menginstalnya lebih mudah. Anda dapat menginstal permata Ruby dengan menjalankan:

 gem install camalian

Dan untuk menggunakan permata ini, Anda dapat memintanya langsung ke skrip Ruby Anda:

 require 'camalian'

Mengekstrak Warna

Untuk mengekstrak warna dari suatu gambar, pertama-tama kita perlu memuatnya ke dalam memori, dan menggunakan metode pada objek gambar:

 image = Camalian::load( File.join( File.dirname(__FILE__), 'colormap.png') ) colors = image.prominent_colors(15) puts colors.map(&:to_hex)

Cuplikan kode ini memuat gambar bernama “colormap.png” dari direktori tempat skrip berada dan mengekstrak 15 warna paling menonjol darinya.

Untuk menjalankannya, simpan file sebagai “color_test1.rb” dan jalankan di shell dengan ruby color_test1.rb . Itu harus menghasilkan output yang mirip dengan yang berikut:

 ["#318578", "#41b53f", "#2560a3", "#359169", "#2154b1", "#4dda15", "#1d48bf", "#1530dc", "#296d94", "#193dcd", "#3da94d", "#45c131", "#3da84e", "#2d7986", "#193cce"]

Dan itu sangat mudah! Kami baru saja mengekstrak 15 warna yang digunakan pada gambar di atas. Bisakah Anda bayangkan mencoba melakukannya menggunakan kode gila, atau lebih buruk, dengan mata Anda? Mari kita dial hal-hal dengan takik. Kali ini, kita akan mencoba menggunakan Camalian pada sebuah gambar dengan lebih detail:

Dengan menjalankan skrip yang sama pada gambar ini, kami mendapatkan yang berikut:

 [“#210b03”, “#723209”, “#974d09”, “#ae5d08”, “#c77414”, “#d77f15”, “#ffea54”, “#94651f”, “#b66a15”, “#c25f06”, “#fdd94d”, “#d39a39”, “#efa540”, “#fffffe”, “#fff655”]

Mencoba memvisualisasikan array nilai warna yang dihasilkan di atas memberi kita sesuatu seperti ini:

Paletnya bagus, tetapi tidak ada pola khusus dalam warna yang diekstraksi. Mari urutkan nilai warna berdasarkan kesamaan dan lihat apakah itu membantu. Yang perlu kita lakukan adalah memanggil satu fungsi lagi sebelum benar-benar mencetak array ke konsol:

 colors = image.prominent_colors(15).sort_similar_colors 

Tapi bagaimana jika kita ingin mengekstrak warna yang relatif lebih terang? Mungkin kita menginginkan warna yang hanya 40% gelap, atau dengan kata lain memiliki nilai kecerahan (dalam ruang warna HSL) antara 0 dan 40. Yang perlu kita lakukan adalah:

 colors = image.prominent_colors(15).light_colors(0, 40) 

Membuat Mesin Pencari Gambar

Sekarang kita tahu betapa mudahnya menangani warna menggunakan Camalian, mari kita buat aplikasi web sederhana yang memungkinkan Anda mengunggah gambar dan mengindeksnya berdasarkan warna. Untuk singkatnya, kami akan melewatkan berbagai detail yang terlibat dalam membangun aplikasi Ruby. Sebagai gantinya, kami akan fokus pada spesifik yang berhubungan dengan warna dan penggunaan Camalian.

Adapun ruang lingkup aplikasi Ruby ini, kami akan membatasi untuk menangani unggahan gambar, mengekstraksi warna dari gambar sebelum menyimpannya, dan mencari gambar yang diunggah berdasarkan warna dan ambang batas yang dipilih.

Di bawah ini adalah diagram model untuk menjelaskan struktur aplikasi kita:

Setiap gambar yang diunggah direpresentasikan menggunakan objek PortfolioItem. Setiap objek Warna mewakili warna unik yang ditemukan melalui gambar yang diunggah, dan akhirnya PortfolioColor mewakili hubungan antara setiap gambar dan warna yang ditemukan di dalamnya.

Sebagian besar bit aplikasi cukup standar, terutama ketika menangani unggahan gambar, membuat entitas model dan mempertahankannya ke database, dll. Jika Anda adalah pengembang Ruby, itu seharusnya tidak perlu dipikirkan lagi. Di bawah ini adalah metode yang digunakan untuk mengekstrak warna dari gambar yang diunggah:

 after_save :extract_colors private def extract_colors image = Camalian::load(self.image.path) colors = image.prominent_colors(self.color_count.to_i).sort_similar_colors colors.each do |color| unless c = Color.where(r: color.r, g: color.g, b: color.b).first c = Color.create(r: color.r, g: color.g, b: color.b, h: color.h, s: color.s, l: color.l) end self.colors << c end end

Ini membantu dengan mengekstrak palet warna dan menyimpannya ke database. Perhatikan bagaimana kami mengekstrak hanya sejumlah warna menonjol tertentu (sesuatu yang dapat ditentukan pengguna saat mengunggah gambar).

Saat pengguna mengirimkan gambar melalui formulir di UI web, gambar diterima melalui pengendali pos, dan PortfolioItem baru dibuat untuknya. Metode ini, extract_colors , dipanggil setiap kali item portofolio disimpan ke database.

Untuk dapat merender palet warna pada halaman, kami menggunakan pembantu sederhana:

 module PortfolioItemsHelper def print_color_palette(colors) color_string = '' colors.each do |c| color_string += content_tag :span, ' ', style: "display: block; float: left; width: 35px; height: 35px; background: #{c.to_hex}" end content_tag :div, color_string.html_safe, style: "display: inline-block;" end end

Ini pada dasarnya membuat div dengan bentang persegi kecil , masing-masing dengan warna latar belakang diatur ke salah satu warna menonjol yang diekstraksi.

Akhirnya, untuk mengimplementasikan pencarian kita harus menggunakan beberapa matematika dan logika:

 class PortfolioSearchForm include ActiveModel::Model attr_accessor :color, :similarity validates_presence_of :color, :similarity def color_object @color_object ||= Camalian::Color.new(self.color) end def color_range(color, level) (color_object.send(color) - level)..(color_object.send(color) + level) end def colors_by_rgb level = self.similarity.to_i * 255 / 100.0 Color.where(r: color_range(:r, level), g: color_range(:g, level), b: color_range(:b, level)) end def colors_by_hsl level = self.similarity.to_i Color.where(h: color_range(:h, (self.similarity.to_i * 30 / 100.0) ), s: color_range(:s, level), l: color_range(:l, level)) end end

Dengan metode colors_by_hsl , kita dapat mengambil semua entitas Warna yang cocok dengan kueri kita. Dan, dengan ini kami dapat mengidentifikasi semua gambar yang diunggah dan membuat halaman hasil pencarian kami. Permintaan itu sendiri agak sederhana. Diberikan warna tertentu, dan nilai kesamaan, rentang nilai dihitung untuk setiap komponen warna.

Dan itu hampir semua bagian yang sulit.

Mencobanya

Anda dapat menemukan kode lengkapnya di GitHub. Anda dapat menerapkan instance aplikasi ini ke Heroku, atau mencobanya secara lokal:

 git clone https://github.com/nazarhussain/camalian-sample-app.git cd camalian-sample-app bundle install rake db:migrate rails s

Aplikasi terakhir terlihat seperti ini:

Setelah aplikasi berjalan, arahkan browser web Anda ke http://localhost:3000. Dengan menggunakan formulir di layar, unggah beberapa gambar dari berbagai palet warna. Kemudian, untuk mencari gambar berdasarkan warna, gunakan kolom pencarian di pojok kanan atas. Dropdown ambang batas memungkinkan Anda menentukan toleransi perbedaan untuk mencocokkan warna gambar.

Apa berikutnya?

Aplikasi demo yang kami buat di artikel ini cukup sederhana, tetapi kemungkinannya tidak terbatas! Beberapa kegunaan praktis lain dari perpustakaan ini dapat mencakup:

  • Membatasi pengguna mengunggah gambar profil gelap
  • Sesuaikan tema warna situs dengan beberapa gambar yang diunggah oleh pengguna
  • Untuk kompetisi desain, secara otomatis memvalidasi pengiriman terhadap persyaratan palet warna

Anda dapat menjelajahi perpustakaan lebih lanjut di GitHub dan memeriksa kode sumbernya. Jangan ragu untuk melaporkan bug dengan membuat masalah atau berkontribusi dengan mengirimkan permintaan tarik.