-128 ????
昨日までの結果で、画像の柄は復元できているっぽいのに、
色味が変なので、YCbCr⇒RGB の変換がミスっているっぽい。
変換式は間違ってないと思うけど・・
R = Y + 1.40200 × Cr (V)
G = Y - 0.34414 × Cb (U) - 0.71414 × Cr (V)
B = Y + 1.77200 × Cb (U)
(※↑変換式としては正しいですが、JPEG的には間違っています)
・・・!!!!
JFIFの仕様書に、
R = Y + 1.402 (Cr-128)
G = Y - 0.34414 (Cb-128) - 0.71414 (Cr-128)
B = Y + 1.772 (Cb-128)
128ってなんだぁぁぁぁぁ!
そもそも、RGB⇒YCbCrの変換の時に、+128しているようです。
それは、YCbCrにした時に正の値のみで表現できるようにする為のようです。(符号ビットがモッタイナイのかな?)
という事で、色味が綺麗に復元できるようになりました。
テスト画像
修正前
修正後
次は、縦縞ですね☆
直りま
せんでした・・・・
でも、進展はありました^^
0xFF の後の 0x00 をスキップする処理がバグっており(汗
一度スキップしてしまうと、その後、永遠と1byte読み込むと1byteスキップするという、
マヌケな事になっていました。(アハハ
(フラグを立てて、0x00を華麗にスルーしたのは良いけれど、フラグ立てっぱなしで、スルーしまくり(笑))
テストデータ
修正前
修正後
この修正後のデータは、だいぶ、元の画像に近くなってきました☆
うっすらですが、前の画像の模様が見えます!!
まぁ、まだまだですよね(アハハ
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- -
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
【豆知識】
JPEGにおいては、0xFF (2進数で表すと:11111111)という値は特別な値で、決められた所にした使用出来ません。
(0xFFは、マーカーというものの開始を表します。)
ここで、JPEGはデータをbit単位で圧縮しますので、
・・・001101110101010101・・・・と並んで行き、
時として
・・・11111111・・・・・ となってしまう事があります。
これが、運悪く、あるbyteの0番目から始まると、0xFF(11111111)となってしまいます。
そこで、圧縮データ中に偶然 0xFF が出来てしまった場合には、圧縮データとは関係なく、その次に 0x00 を入れて、
この 0xFF が偶然のものであるという事を示します。
そこで、デコーダーは、0xFFを発見したら、次のバイトが0x00なら、その0x00は存在しないものとして、
その次のbyteから続きの処理をします。
AC成分の復号
一応、8x8の1ブロックを復号する処理まで書いたのですが、どうもバグっていて、全然前に進みません。
どこが間違っているのか、やっと分かったので書いておきます。
ハフマン符号化されたデータは、
bit列で、
[HuffmanCode][HuffmanValue][HuffmanCode][HuffmanValue]・・・・と並んでいます
011110100101010101010101010101010101011111・・・・・・・・
DC成分は、HuffmanCodeをデコードすると、HuffmanValueの長さを示します。HuffmanValueは、DCTの係数値の差分を示しています。
AC成分は、HuffmanCodeをデコードすると、前半4byteはランレングスで、後半4byteがHuffmanValueの長さを示してます。
・・・・・
てっきり、
AC成分は、HuffmanCodeをデコードすると、HuffmanValueの長さを示していて、
HuffmanValueの前半4byteはランレングスで、後半4byteがDCTの係数値だと思ってましたよ(涙)
※複合化した値が、やたらと 0 ばっかりになる人は、一度確認してみて下さい(笑
(今更JPEGのデコードなんてしてる人いないか・・・)
[追記]
ああ・・・
逆DCTも、値が変・・・・
[追記2]
ああ・・・
√2じゃなくて、1/√2 でした・・・