🐙
MySQLに保存したカラーコードをRGBに変換したいんじゃ
バックエンドからフロントにRGBの値を返したい時にDBでカラーコード扱う際に試したことをまとめます。
結論
00BFFF
や49151
の文字列(0~F)or数値で格納します。
それをSQLでRGBに変換することで実現します。
環境
# mysql -v
Welcome to the MySQL monitor. Commands end with ; or \g.
Your MySQL connection id is 9
Server version: 8.0.21 MySQL Community Server - GPL
用意したテーブル
|id|color_code_int|color_code_string|
|--|--------------|-----------------|
| 1| 16777215| FFFFFF|
| 2| 16711680| FF0000|
| 3| 49151| 00BFFF|
10進数でカラーコードを保持する時の注意点
16進数を10進数に変換したいと思います。
SELECT CAST(0x00BFFF AS UNSIGNED);
-- 結果: 49151
00BFFF
の10進数表記は49151
なので正しく変換されています。
では、49151を元の16進数カラーコードに戻します。
SELECT HEX(49151);
-- 結果: BFFF
頭の00が消えてしまいました。
カラーコードは必ず6桁という性質を持っているため、0埋めするようにします。
SELECT LPAD(HEX(49151), 6, "0");
-- 結果: 00BFFF
これで元の16進数カラーコードとunsigned integerの相互変換ができるようになりました。
10進数カラー→RGBへの変換
ここからが本題です。
まず、10進数を16進数に変換してから2桁ごとに10進数にするという2段階の手順が必要になります。
こんなイメージになります。これをSQLでやればRGBにまとめて変換できます。
- 49151->00BFFFに直す
- 2桁ごとに10進数に直す
- 00 -> 0
- BF -> 191
- FF -> 255
SELECT
CONV(SUBSTRING(LPAD(HEX(color_code_int), 6, "0"), 1, 2), 16, 10),
CONV(SUBSTRING(LPAD(HEX(color_code_int), 6, "0"), 3, 2), 16, 10),
CONV(SUBSTRING(LPAD(HEX(color_code_int), 6, "0"), 5, 2), 16, 10)
FROM color_code
WHERE id = 3;
-- 結果
| R| G| B|
|---|---|---|
| 0|191|255|
16進数カラーコード(文字列)→RGBへの変換
こちらは先ほどよりシンプルで16進数を2桁ごとに10進数にするという、ひとつの手順だけで完了します。
SELECT
CONV(SUBSTRING(color_code_string, 1, 2), 16, 10) AS R,
CONV(SUBSTRING(color_code_string, 3, 2), 16, 10) AS G,
CONV(SUBSTRING(color_code_string, 5, 2), 16, 10) AS B
FROM color_code
WHERE id = 3;
-- 結果
| R| G| B|
|---|---|---|
| 0|191|255|
まとめ
10進数でも16進数の範囲内の文字列からでもRGBへの変換は可能でした。
16進数だと色がなんとなくわかるかもしれない点やメンテナンスがしやすい点がメリットのように感じます。
一方、10進数だと格納する際に変換する一手間が加わる点や何色かわかりづらいといったデメリットが目立ち、検証してみたけど10進数で扱うメリットが今のところ思いつかないです。(何かメリットがあればコメントお願いします🙇)
参考
Discussion