現在公開しているツール「ちーたんタッチボード」では、色情報を 0.0 ~ 1.0 の小数で持っているのですが、プログラムで ARGB として設定する際に 0 ~ 255 形式に変換する必要がありました。しかし、小数↔整数 の変換には誤差がつきものなのでどうにかならないのかなと思っていたのですが、WPF で使用されている System.Windows.Media.Color に「ScA」「ScR」のようなプロパティがあるのを見つけました。
MSDN で調べてみると渡す値は 0 ~ 1 と書いてあったので「0 ~ 255 の代わりに 0.0 ~ 1.0 の線形補間で色情報を渡せるんだ」と思い込んでしまったのが悪夢の始まりでした。
実は現在公開しているちーたんタッチボード Ver 0.23 では背景や文字の色設定を行うと設定するたびに微妙に色が変わったりする不具合が存在しています。もうお分かりかと思いますが、上記の誤解により発生している不具合です。(次に公開する Ver 0.30 では治ってます^^;)
当時原因がよくわからなくてほかのライブラリが原因なのではないかとか思ったりしていたのですが、最終的に Color 構造体に秘密があるのではないかと思い、値設定後の各パラメータのダンプを取ってみました。以下は ScX プロパティに 0.01 ずつ設定したものです。
A | R | G | B | ScA | ScR | ScG | ScB |
---|---|---|---|---|---|---|---|
0 | 0 | 0 | 0 | 0.00 | 0.00 | 0.00 | 0.00 |
3 | 25 | 25 | 25 | 0.01 | 0.01 | 0.01 | 0.01 |
5 | 39 | 39 | 39 | 0.02 | 0.02 | 0.02 | 0.02 |
8 | 48 | 48 | 48 | 0.03 | 0.03 | 0.03 | 0.03 |
10 | 56 | 56 | 56 | 0.04 | 0.04 | 0.04 | 0.04 |
13 | 63 | 63 | 63 | 0.05 | 0.05 | 0.05 | 0.05 |
15 | 69 | 69 | 69 | 0.06 | 0.06 | 0.06 | 0.06 |
18 | 75 | 75 | 75 | 0.07 | 0.07 | 0.07 | 0.07 |
20 | 80 | 80 | 80 | 0.08 | 0.08 | 0.08 | 0.08 |
23 | 85 | 85 | 85 | 0.09 | 0.09 | 0.09 | 0.09 |
26 | 89 | 89 | 89 | 0.10 | 0.10 | 0.10 | 0.10 |
28 | 93 | 93 | 93 | 0.11 | 0.11 | 0.11 | 0.11 |
31 | 97 | 97 | 97 | 0.12 | 0.12 | 0.12 | 0.12 |
33 | 101 | 101 | 101 | 0.13 | 0.13 | 0.13 | 0.13 |
36 | 105 | 105 | 105 | 0.14 | 0.14 | 0.14 | 0.14 |
38 | 108 | 108 | 108 | 0.15 | 0.15 | 0.15 | 0.15 |
41 | 111 | 111 | 111 | 0.16 | 0.16 | 0.16 | 0.16 |
43 | 115 | 115 | 115 | 0.17 | 0.17 | 0.17 | 0.17 |
46 | 118 | 118 | 118 | 0.18 | 0.18 | 0.18 | 0.18 |
48 | 121 | 121 | 121 | 0.19 | 0.19 | 0.19 | 0.19 |
51 | 124 | 124 | 124 | 0.20 | 0.20 | 0.20 | 0.20 |
54 | 126 | 126 | 126 | 0.21 | 0.21 | 0.21 | 0.21 |
56 | 129 | 129 | 129 | 0.22 | 0.22 | 0.22 | 0.22 |
59 | 132 | 132 | 132 | 0.23 | 0.23 | 0.23 | 0.23 |
61 | 134 | 134 | 134 | 0.24 | 0.24 | 0.24 | 0.24 |
64 | 137 | 137 | 137 | 0.25 | 0.25 | 0.25 | 0.25 |
66 | 139 | 139 | 139 | 0.26 | 0.26 | 0.26 | 0.26 |
69 | 142 | 142 | 142 | 0.27 | 0.27 | 0.27 | 0.27 |
71 | 144 | 144 | 144 | 0.28 | 0.28 | 0.28 | 0.28 |
74 | 147 | 147 | 147 | 0.29 | 0.29 | 0.29 | 0.29 |
77 | 149 | 149 | 149 | 0.30 | 0.30 | 0.30 | 0.30 |
79 | 151 | 151 | 151 | 0.31 | 0.31 | 0.31 | 0.31 |
82 | 153 | 153 | 153 | 0.32 | 0.32 | 0.32 | 0.32 |
84 | 155 | 155 | 155 | 0.33 | 0.33 | 0.33 | 0.33 |
87 | 158 | 158 | 158 | 0.34 < /td> | 0.34 | 0.34 | 0.34 |
89 | 160 | 160 | 160 | 0.35 | 0.35 | 0.35 | 0.35 |
92 | 162 | 162 | 162 | 0.36 | 0.36 | 0.36 | 0.36 |
94 | 164 | 164 | 164 | 0.37 | 0.37 | 0.37 | 0.37 |
97 | 166 | 166 | 166 | 0.38 | 0.38 | 0.38 | 0.38 |
99 | 168 | 168 | 168 | 0.39 | 0.39 | 0.39 | 0.39 |
102 | 170 | 170 | 170 | 0.40 | 0.40 | 0.40 | 0.40 |
105 | 172 | 172 | 172 | 0.41 | 0.41 | 0.41 | 0.41 |
107 | 173 | 173 | 173 | 0.42 | 0.42 | 0.42 | 0.42 |
110 | 175 | 175 | 175 | 0.43 | 0.43 | 0.43 | 0.43 |
112 | 177 | 177 | 177 | 0.44 | 0.44 | 0.44 | 0.44 |
115 | 179 | 179 | 179 | 0.45 | 0.45 | 0.45 | 0.45 |
117 | 181 | 181 | 181 | 0.46 | 0.46 | 0.46 | 0.46 |
120 | 182 | 182 | 182 | 0.47 | 0.47 | 0.47 | 0.47 |
122 | 184 | 184 | 184 | 0.48 | 0.48 | 0.48 | 0.48 |
125 | 186 | 186 | 186 | 0.49 | 0.49 | 0.49 | 0.49 |
128 | 188 | 188 | 188 | 0.50 | 0.50 | 0.50 | 0.50 |
130 | 189 | 189 | 189 | 0.51 | 0.51 | 0.51 | 0.51 |
133 | 191 | 191 | 191 | 0.52 | 0.52 | 0.52 | 0.52 |
135 | 192 | 192 | 192 | 0.53 | 0.53 | 0.53 | 0.53 |
138 | 194 | 194 | 194 | 0.54 | 0.54 | 0.54 | 0.54 |
140 | 196 | 196 | 196 | 0.55 | 0.55 | 0.55 | 0.55 |
143 | 197 | 197 | 197 | 0.56 | 0.56 | 0.56 | 0.56 |
145 | 199 | 199 | 199 | 0.57 | 0.57 | 0.57 | 0.57 |
148 | 200 | 200 | 200 | 0.58 | 0.58 | 0.58 | 0.58 |
150 | 202 | 202 | 202 | 0.59 | 0.59 | 0.59 | 0.59 |
153 | 203 | 203 | 203 | 0.60 | 0.60 | 0.60 | 0.60 |
156 | 205 | 205 | 205 | 0.61 | 0.61 | 0.61 | 0.61 |
158 | 206 | 206 | 206 | 0.62 | 0.62 | 0.62 | 0.62 |
161 | 208 | 208 | 208 | 0.63 | 0.63 | 0.63 | 0.63 |
163 | 209 | 209 | 209 | 0.64 | 0.64 | 0.64 | 0.64 |
166 | 211 | 211 | 211 | 0.65 | 0.65 | 0.65 | 0.65 |
168 | 212 | 212 | 212 | 0.66 | 0.66 | 0.66 | 0.66 |
171 | 214 | 214 | 214 | 0.67 | 0.67 | 0.67 | 0.67 |
173 | 215 | 215 | 215 | 0.68 | 0.68 | 0.68 | 0.68 |
176 | 216 | 216 | 216 | 0.69 | 0.69 | 0.69 | 0.69 |
179 | 218 | 218 | 218 | 0.70 | 0.70 | 0.70 | 0.70 |
181 | 219 | 219 | 219 | 0.71 | 0.71 | 0.71 | 0.71 |
184 | 221 | 221 | 221 | 0.72 | 0.72 | 0.72 | 0.72 |
186 | 222 | 222 | 222 | 0.73 | 0.73 | 0.73 | 0.73 |
189 | 223 | 223 | 223 | 0.74 | 0.74 | 0.74 | 0.74 |
191 | 225 | 225 | 225 | 0.75 | 0.75 | 0.75 | 0.75 |
194 | 226 | 226 | 226 | 0.76 | 0.76 | 0.76 | 0.76 |
196 | 227 | 227 | 227 | 0.77 | 0.77 | 0.77 | 0.77 |
199 | 229 | 229 | 229 | 0.78 | 0.78 | 0.78 | 0.78 |
201 | 230 | 230 | 230 | 0.79 | 0.79 | 0.79 | 0.79 |
204 | 231 | 231 | 231 | 0.80 | 0.80 | 0.80 | 0.80 |
207 | 232 | 232 | 232 | 0.81 | 0.81 | 0.81 | 0.81 |
209 | 234 | 234 | 234 | 0.82 | 0.82 | 0.82 | 0.82 |
212 | 235 | 235 | 235 | 0.83 | 0.83 | 0.83 | 0.83 |
214 | 236 | 236 | 236 | 0.84 | 0.84 | 0.84 | 0.84 |
217 | 237 | 237 | 237 | 0.85 | 0.85 | 0.85 | 0.85 |
219 | 239 | 239 | 239 | 0.86 | 0.86 | 0.86 | 0.86 |
222 | 240 | 240 | 240 | 0.87 | 0.87 | 0.87 | 0.87 |
224 | 241 | 241 | 241 | 0.88 | 0.88 | 0.88 | 0.88 |
227 | 242 | 242 | 242 | 0.89 | 0.89 | 0.89 | 0.89 |
230 | 243 | 243 | 243 | 0.90 | 0.90 | 0.90 | 0.90 |
232 | 245 | 245 | 245 | 0.91 | 0.91 | 0.91 | 0.91 |
235 | 246 | 246 | 246 | 0.92 | 0.92 | 0.92 | 0.92 |
237 | 247 | 247 | 247 | 0.93 | 0.93 | 0.93 | 0.93 |
240 | 248 | 248 | 248 | 0.94 | 0.94 | 0.94 | 0.94 |
242 | 249 | 249 | 249 | 0.95 | 0.95 | 0.95 | 0.95 |
245 | 250 | 250 | 250 | 0.96 | 0.96 | 0.96 | 0.96 |
247 | 252 | 252 | 252 | 0.97 | 0.97 | 0.97 | 0.97 |
250 | 253 | 253 | 253 | 0.98 | 0.98 | 0.98 | 0.98 |
252 | 254 | 254 | 254 | 0.99 | 0.99 | 0.99 | 0.99 |
255 | 255 | 255 | 255 | 1.00 | 1.00 | 1.00 | 1.00 |
見事に線形ではありませんでした。
よくよく調べてみると ARGB のほうは sRGB という規格、ScA ScR ScG ScB のほうは scRGB という規格らしいです。scRGB については以下のサイトなどを参考にしてください。簡単にまとめると、sRGB(8bit) では表現できなかった色を 12bit や 16bit などに拡張してより多くの色情報を表現できるようにしたものです。
しかし、いろいろ調べてみても sRGB と scRGB の変換方法がよくわからなかったのでコードベースで情報がないか調べてみたところ以下のサイトがありました。
確かにこのコードに当てはめると Color 構造体で出力された結果と一致しました。ですが、この変換処理と scRGB について書かれている公式との関連性がよくわかりませんでした。Microsoft が独自に定義したものかもしれませんが、それについても文面を見つけることができませんでした。
まあとりあえず現状は 0.0~1.0 と 0~255 は単純に線形変換させて対応することにし、scRGB については今回の記事で参考になったという形にとどめておきたいと思います。なにか詳しい情報があればコメントいただければと思います。
]]>