Is there any algorism that converts YCbCr to RGB??? (Integer based!!!)
I got a C source. But, it uses floating point operation. :(
I prefer speed than precision. :)

Thank you for reading!
Have a nice day!
Posted on 2002-08-09 01:32:19 by nyam
Use fixed point?
Posted on 2002-08-09 02:26:58 by comrade
Hi,

that depends on the source format. Is it a 4:2:0 (like most MPEG)
or 4:2:2 (seens in some JPEGs) or 4:4:4 (some MPEG2)

Generally you can use this formula:

B = 1.164(Y - 16) + 2.018(Cb - 128)
G = 1.164(Y - 16) - 0.813(Cr - 128) - 0.391(Cb - 128)
R = 1.164(Y - 16) + 1.596(Cr - 128)
That way you can work with a lookup table which is even faster
than using real calculations via MMX.

building lookup table(s)



push 1024
push GMEM_FIXED
call GlobalAlloc
mov [edi.ve_lpCrRed], eax
test eax, eax
je iveError

push 1024
push GMEM_FIXED
call GlobalAlloc
mov [edi.ve_lpCrGreen], eax
test eax, eax
je iveError

push 1024
push GMEM_FIXED
call GlobalAlloc
mov [edi.ve_lpCbGreen], eax
test eax, eax
je iveError

push 1024
push GMEM_FIXED
call GlobalAlloc
mov [edi.ve_lpCbBlue], eax
test eax, eax
je iveError

push 1024
push GMEM_FIXED
call GlobalAlloc
mov [edi.ve_lpLum], eax
test eax, eax
je iveError

; -- build color tables --

xor ecx, ecx
iveLoop: mov esi, ecx
sub esi, 128

mov eax, esi
imul eax, 359
mov ebx, [edi.ve_lpCrRed]
mov [ebx + ecx * 4], eax

mov eax, esi
imul eax, 88
neg eax
mov ebx, [edi.ve_lpCbGreen]
mov [ebx + ecx * 4], eax

mov eax, esi
imul eax, 183
neg eax
mov ebx, [edi.ve_lpCrGreen]
mov [ebx + ecx * 4], eax

mov eax, esi
imul eax, 454
mov ebx, [edi.ve_lpCbBlue]
mov [ebx + ecx * 4], eax

mov eax, ecx
imul eax, 298
mov ebx, [edi.ve_lpLum]
mov [ebx + ecx * 4], eax

inc ecx
cmp ecx, 256
jl iveLoop


now you can get get the chrominance value and put the RGB
by using the luminance values according to these macros:




; lpCb points to the current Cb value
; lpCr points to the current Cr value
; dwCrRed .. dwCbBlue are local temporary variables

getchrom MACRO

xor ebx, ebx
xor ecx, ecx

mov eax, lpCb
mov bl, [eax]
mov eax, lpCr
mov cl, [eax]

mov eax, xVideoEngine.ve_lpCrRed
mov eax, [eax + ecx * 4]
mov dwCrRed, eax

mov eax, xVideoEngine.ve_lpCrGreen
mov eax, [eax + ecx * 4]
mov dwCrGreen, eax

mov eax, xVideoEngine.ve_lpCbGreen
mov eax, [eax + ebx * 4]
mov dwCbGreen, eax

mov eax, xVideoEngine.ve_lpCbBlue
mov eax, [eax + ebx * 4]
mov dwCbBlue, eax

ENDM

; writes the blue value to the RGB plane pointed by ecx
; esi ist the current luminance (Y) value
; edi is a clipping table to keep the values in byte size
; instead of edi you might do a clip of eax against 0 and 255

setblue MACRO

mov eax, esi
add eax, dwCbBlue

sar eax, 8
and eax, 03FFh

mov al, [edi + eax]
mov [ecx], al

ENDM

setgreen MACRO

mov eax, esi
add eax, dwCrGreen
add eax, dwCbGreen

sar eax, 8
and eax, 03FFh

mov al, [edi + eax]
mov [ecx + 1], al

ENDM

setred MACRO

mov eax, esi
add eax, dwCrRed

sar eax, 8
and eax, 03FFh

mov al, [edi + eax]
mov [ecx + 2], al

ENDM



Hope this helps

:)

Bye Miracle
Posted on 2002-08-09 02:27:50 by miracle
Fixed point 8 (sar eax,8) ?

ve_lpCrRed 1,596*256=409 ?359
ve_lpCbGreen 0,391*256=100 ?88
ve_lpCrGreen 0,813*256=208 ?183
ve_lpCbBlue 2,018*256=517 ?454
ve_lpLum 1,164*256=298 =298, but where -16

Where table ve_lpLum is used?
("esi ist the current luminance (Y) value"???)



and eax, 03FFh
mov al, [edi + eax]


This code clipping signed values? I do not believe :)
Posted on 2002-08-09 12:02:41 by Nexo
Thanks miracle, Nexo, comrade!

I solved the problem! Thanks miracle!

:)
Posted on 2002-08-09 19:02:51 by nyam