mieki256's diary



2017/04/09() [n年前の日記]

#3 [ruby][dxruby] RGBとHLS(HSL)を変換するRubyスクリプトを書いた

グラデ塗りを試す際に必要になりそうだったので、RGBと _HLS(HSL) を変換するRubyスクリプトを書いた。

HLSてのは…。、Hue(色相)、Lightness(輝度)、Saturation(彩度)で色を表す例のヤツ、という説明でいいのだろうか。お絵かきソフトでえてして用意されてたりするアレ。とはちょっと違うか。アレは _HSV か…。

とりあえず、変換処理のソースは以下。

_tinycolorsys.rb

_RGBとHSLの相互変換ツールと変換計算式 - PEKO STEP の解説を参考にして書きました。ありがたや。

使用例。

test_colorsys_ss.png

DXRuby を使って、マウスのx/y座標やカーソルキーの上下でHLSの値を変えて、背景色を変更してる。

require_relative 'tinycolorsys' を呼んで、include TinyColorSys しておくと、hls_to_rgb() と rgb_to_hls() が使えるようになる。

_test_colorsys.rb
# tinycolorsys.rb の動作テスト

require 'dxruby'
require_relative 'tinycolorsys'

include TinyColorSys

fnt = Font.new(28)
v2 = 0.5
set_hls = true

Window.loop do
  break if Input.keyPush?(K_ESCAPE)

  set_hls = !set_hls if Input.mousePush?(M_LBUTTON)

  v0 = Input.mousePosX.to_f / (Window.width - 1)
  v1 = Input.mousePosY.to_f / (Window.height - 1)
  v2 += (Input.keyDown?(K_UP))? (1.0 / 255.0) : 0
  v2 -= (Input.keyDown?(K_DOWN))? (1.0 / 255.0) : 0

  v0 = [[v0, 1.0].min, 0.0].max
  v1 = [[v1, 1.0].min, 0.0].max
  v2 = [[v2, 1.0].min, 0.0].max

  if set_hls
    h = v0
    l = v1
    s = v2
    r, g, b = hls_to_rgb(h, l, s)
    h = (h * 360).to_i
    l = (l * 100).to_i
    s = (s * 100).to_i
  else
    r = (v0 * 255).to_i
    g = (v1 * 255).to_i
    b = (v2 * 255).to_i
    h, l, s = rgb_to_hls(r, g, b)
    h = (360 * h).to_i
    l = (100 * l).to_i
    s = (100 * s).to_i
  end

  Window.bgcolor = [r, g, b]
  col = (l < 50)? C_WHITE : C_BLACK
  msg = (set_hls)? "use HLS" : "use RGB"
  Window.drawFont(4, 4, msg, fnt, :color => col)
  Window.drawFont(4, 40, "RGB=#{r}, #{g}, #{b}", fnt, :color => col)
  Window.drawFont(4, 80, "HLS=#{h}, #{l}, #{s}", fnt, :color => col)
  Window.drawFont(4, 120, "(mouse x/y , Up/Down key)", fnt, :color => col)
end

既にgemがあった。 :

上記のスクリプトを書いた後で、ふと気になってググってみたら、既にそういう gem があった…。自分で書く必要は無かった…。

_color | RubyGems.org | your community gem host
_halostatue/color: Color tools for Ruby.

gem install color でインストールできる。

以下は、前述のソレを color を使って書き直した例。
# gem color の動作テスト

require 'dxruby'
require 'color'

fnt = Font.new(28)
v2 = 0.5
set_hls = true

Window.loop do
  break if Input.keyPush?(K_ESCAPE)

  set_hls = !set_hls if Input.mousePush?(M_LBUTTON)

  v0 = Input.mousePosX.to_f / (Window.width - 1)
  v1 = Input.mousePosY.to_f / (Window.height - 1)
  v2 += (Input.keyDown?(K_UP))? (1.0 / 255.0) : 0
  v2 -= (Input.keyDown?(K_DOWN))? (1.0 / 255.0) : 0

  v0 = [[v0, 1.0].min, 0.0].max
  v1 = [[v1, 1.0].min, 0.0].max
  v2 = [[v2, 1.0].min, 0.0].max

  if set_hls
    h = v0 * 360.0
    l = v1 * 100.0
    s = v2 * 100.0
    rgb = Color::HSL.new(h, s, l).to_rgb
    r = rgb.red
    g = rgb.green
    b = rgb.blue
  else
    r = (v0 * 255).to_i
    g = (v1 * 255).to_i
    b = (v2 * 255).to_i
    hsl = Color::RGB.new(r, g, b).to_hsl
    h = hsl.hue
    l = hsl.luminosity
    s = hsl.saturation
  end
  r = r.to_i
  g = g.to_i
  b = b.to_i
  h = h.to_i
  l = l.to_i
  s = s.to_i

  Window.bgcolor = [r, g, b]
  col = (l < 50)? C_WHITE : C_BLACK
  msg = (set_hls)? "use HLS" : "use RGB"
  Window.drawFont(4, 4, msg, fnt, :color => col)
  Window.drawFont(4, 40, "RGB=#{r}, #{g}, #{b}", fnt, :color => col)
  Window.drawFont(4, 80, "HLS=#{h}, #{l}, #{s}", fnt, :color => col)
  Window.drawFont(4, 120, "(mouse x/y , Up/Down key)", fnt, :color => col)
end

  • Color::HSL.new(hue, saturation, luminosity) で渡す値は、hue が 0〜360、saturation と luminosity が 0〜100。
  • Color::RGB.new(red, green, blue) で渡す値は、0〜255。
  • HSL.to_rgb で RGB になるし、RGB.to_hsl で HSL になる。
  • RGB.red、RGB.green、RGB.blue で取り出した値は、0〜255。
  • HSL.hue、HSL.luminosity、HSL.saturation で取り出し値は、0〜360、0〜100、0〜100。
  • HSL も RGB も、0.0〜1.0を与えて生成するメソッドがあるらしい。hsl = Color:HSL.from_fraction(0.5, 1.0, 0.5) みたいな書き方をすればいいのかな? たぶん。ちと自信無し。

ホント、最初からコレを使えばよかった…。

以上です。

過去ログ表示

Prev - 2017/04 - Next
1
2 3 4 5 6 7 8
9 10 11 12 13 14 15
16 17 18 19 20 21 22
23 24 25 26 27 28 29
30

カテゴリで表示

検索機能は Namazu for hns で提供されています。(詳細指定/ヘルプ


注意: 現在使用の日記自動生成システムは Version 2.19.6 です。
公開されている日記自動生成システムは Version 2.19.5 です。

Powered by hns-2.19.6, HyperNikkiSystem Project