|
| HOMEPAGE | INDICE FORUM | REGOLAMENTO | ::. | NEI PREFERITI | .:: | RSS Forum | RSS News | NEWS web | NEWS software | |
| PUBBLICITA' | | | ARTICOLI | WIN XP | VISTA | WIN 7 | REGISTRI | SOFTWARE | MANUALI | RECENSIONI | LINUX | HUMOR | HARDWARE | DOWNLOAD | | | CERCA nel FORUM » | |
23-01-2007, 12.38.54 | #1 |
Hero Member
Registrato: 02-04-2003
Loc.: Sardegna
Messaggi: 685
|
[C/C++] [ALGORITMI]
vorrei scrivere un programmino che converta il formato 4:2:0 planare in RGB24 Mi sono documentato ed ho letto parecchi articoli in rete conosco il c ed il c++ ho visto parecchio codice in rete Però c'è qualcosa che mi sfugge Una cosa che non mi è chiarissima è come è fatta la struttura binaria del file questo credo sia essenziale dalle varie letture mi sembra di capire che prima sono presenti tutti gli Y poi u e poi v però non riesco a capire come accedervi tramite codice grazie a tutti ciao |
23-01-2007, 13.02.42 | #2 |
Gold Member
Registrato: 07-01-2002
Loc.: Milano
Messaggi: 2.863
|
Dovrebbe risolversi semplicemente con un cast a DWORD (ti consiglio di dichiarare un tipo dword24)..
Codice:
DWORD rgb24; BYTE r,g,b; DWORD rgb555; b=rgb555 & 0x1f; // extract blue rgb555 >>= 5; g=rgb555 & 0x1f; // green rgb555 >>= 5; r=rgb555 & 0x1f; // and red rgb24=r; rgb24 <<=8; rgb24|=g; rgb24 <<=8; rgb24|=b; L'implementazione parta da un RGB standard, volendo la puoi usare così com'é convertendo il formato planare in esadecimale prima di procedere. |
23-01-2007, 13.08.18 | #3 |
Hero Member
Registrato: 02-04-2003
Loc.: Sardegna
Messaggi: 685
|
rgb555 lo carico tramite per fread ma perchè di >> di 5 ?
MI puoi passare il link ? (rimani in onda se puoi così vediamo se risco a risolvere /capire ) grazie ok ho trocato il link: http://groups.google.it/group/comp.g...153130892ad009 ma questo "fa" da RGB555->RGB24 come dice il topi c io devo fare da yuv 4:2:0 planare a RGB24 |
23-01-2007, 13.14.12 | #4 |
Gold Member
Registrato: 07-01-2002
Loc.: Milano
Messaggi: 2.863
|
Si ma vai per gradi,
planare -> rgb555 - rgb24... |
23-01-2007, 13.17.35 | #5 |
Gold Member
Registrato: 07-01-2002
Loc.: Milano
Messaggi: 2.863
|
E' relativamente semplice arrivare al formato 555, si tratta anche qui di un cast (questi formati sono tutti dei cast), in questo caso vanno troncati gli ultimi bit...
http://groups.google.it/group/comp.o...e9b286c0d5a915 |
23-01-2007, 14.03.42 | #6 |
Hero Member
Registrato: 02-04-2003
Loc.: Sardegna
Messaggi: 685
|
E ok fin qui ci sono ... Ma poi ...
Io non riesco a materializzare la struttura fisica di sto file , Tipo una volta ho scritto un reader per file 3ds però era più chiaro avevo stuttura dimensione delle stesse etc. In questo caso mi "vedo" perso ... |
23-01-2007, 14.31.02 | #7 |
Gold Member
Registrato: 07-01-2002
Loc.: Milano
Messaggi: 2.863
|
Non mi sono mai occupato di questo genere di letture, ciò che ricordo è il modello matematico, vedi se questo può esserti utile
http://homepages.borland.com/efg2lab...Colors/YUV.htm |
23-01-2007, 14.34.24 | #8 |
Hero Member
Registrato: 02-04-2003
Loc.: Sardegna
Messaggi: 685
|
Si già visitato... (mi sa che ho visto tutto in rete è per quello che sono finito qui)
Per dire già da qui: http://www.comlab.uniroma3.it/ens/ENS_MPEG.pdf Alla decima pagina non riesco a capire bene i vari schemi il primo è ovvio 4:4:4 ma già nell'altro mi perdo... |
23-01-2007, 14.51.54 | #9 | |
Hero Member
Registrato: 02-04-2003
Loc.: Sardegna
Messaggi: 685
|
Quota:
il formato che usa in questo file è YVU [codice pascal] FilePointer := 0; StreamY.Seek(FilePointer, soFromBeginning); //ok la y è all'inizio FilePointer := YRowCount * YColumnCount; StreamV.Seek(FilePointer, soFromBeginning); //ok la v sta dopo la y alla fine quindi mi sposta //allla prima V FilePointer := FilePointer + (YRowCount DIV Factor) * (YColumnCount DIV Factor); StreamU.Seek(FilePointer, soFromBeginning); //qua mi sono perso .... in pratica //vado nella posizione uguale a numero righe //diviso 4 * numero colonne / 4 non //capisco dove sto andando a finire... [/pascal] |
|
23-01-2007, 14.57.13 | #10 |
Gold Member
Registrato: 07-01-2002
Loc.: Milano
Messaggi: 2.863
|
Secondo me vai a finire al primo V del GOP
|
23-01-2007, 15.08.54 | #11 | |
Hero Member
Registrato: 02-04-2003
Loc.: Sardegna
Messaggi: 685
|
Quota:
Group oF Picture giusto ? (che non ho capito neanche bene) Cmq ho fatto un pò di conti immaginando di avere una img 8x8 e di "vederla" come sequenza di byte (o celle) otteniamo che: la y sta alla cella 0 la v sta alla cella 64 = (8x8) la u sta alla cella 64 + 16 = ( (8/4)*(8/4)) non capisco perchè la u la calcola così... p.s hai visto le slide ? |
|
23-01-2007, 15.23.38 | #12 |
Gold Member
Registrato: 07-01-2002
Loc.: Milano
Messaggi: 2.863
|
Penso che il tuo modello sia giusto, ho visto purtroppo solo brevemente le slide dagli schemi e se la memoria non mi inganna tutto si gioca su un discorso di interpolazione, ovvero prima cella indica la presenza del pixel, seconda cella indica il gradiente del pixel orizzontale, terza cella indica il gradiente verticale...
Per evitare di sparare cavolate però mi riservo di guardarci meglio. |
24-01-2007, 16.14.04 | #13 |
Hero Member
Registrato: 02-04-2003
Loc.: Sardegna
Messaggi: 685
|
Dunque io ho capito l'algoritmo credo...
Ora non riesco a capire come caricare dal file yuv le dimensioni width ed height dovrevi (generalmente è così) caricarle dall'header ma non so dove è... |
24-01-2007, 16.40.10 | #14 |
Gold Member
Registrato: 07-01-2002
Loc.: Milano
Messaggi: 2.863
|
Prova a postare quello che hai messo giù
|
24-01-2007, 16.48.30 | #15 | |
Hero Member
Registrato: 02-04-2003
Loc.: Sardegna
Messaggi: 685
|
Quota:
Codice:
unit ScreenYVUtoRGBDemo; interface uses Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs, StdCtrls, ExtCtrls; type TFormYVUtoRGB = class(TForm) ImageRGB: TImage; RadioGroupYVURGB: TRadioGroup; RadioGroup129: TRadioGroup; procedure FormCreate(Sender: TObject); procedure RadioGroupClick(Sender: TObject); private PROCEDURE UpdateYUV; public { Public declarations } end; var FormYVUtoRGB: TFormYVUtoRGB; implementation {$R *.DFM} CONST MaxPixelCount = 32768; // Arbitrary large constant for any bitmap TYPE TRGBTripleArray = ARRAY[0..MaxPixelCount-1] OF TRGBTriple; pRGBTripleArray = ^TRGBTripleArray; // Convert YVU to RGB. // For YVU12, the "Y" plane is twice as large as the // "U" and "V" planes in both dimensions -- so the "Y" plane // has four times as many bytes as the "U" and "V" planes. // // For YVU9, the "Y" plane is four times as large as the // "U" and "V" planes in both dimensions -- so the "Y" plane // has 16-times as many bytes as the "U" and "V" planes. // // Many values are "hardwired" here to process only the sample file PROCEDURE TFormYVUtoRGB.UpdateYUV; CONST YRowCount = 288; YColumnCount = 352; UV12ColumnCount = YColumnCount DIV 2; VAR Bitmap : TBitmap; BufferY : ARRAY[0..YColumnCount-1] OF BYTE; BufferU : ARRAY[0..UV12ColumnCount-1] OF BYTE; BufferV : ARRAY[0..UV12ColumnCount-1] OF BYTE; DisplayIndex: INTEGER; Factor : INTEGER; // 2 for YVU12, 4 for YVU9 Filename : STRING; FilePointer : INTEGER; i : INTEGER; InFile : STRING; // 'YVU12.Stream' or 'YVU9.Stream' j : INTEGER; OutFile : STRING; // 'WeatherLady' or 'NewsGuy' Row : pRGBTripleArray; StreamY : TFileStream; StreamU : TFileStream; StreamV : TFileStream; Y : BYTE; U : BYTE; V : BYTE; // R, G and B values must be in the range 0..255 FUNCTION FixRange(CONST x: Double): BYTE; VAR temp: INTEGER; BEGIN temp := ROUND(x); IF temp > 255 THEN temp := 255 ELSE IF temp < 0 THEN temp := 0; RESULT := temp END; BEGIN U := 0; // avoid compiler warning V := 0; // avoid compiler warning CASE RadioGroup129.ItemIndex OF // YVU12 0: BEGIN Factor := 2; InFile := 'YVU12.Stream'; OutFile := 'WeatherLady.BMP'; END; // YVU9 1: BEGIN Factor := 4; InFile := 'YVU9.Stream'; OutFile := 'NewsGuy.BMP' END; ELSE Factor := 0; // avoid compiler warnings Filename := ''; OutFile := '' END; // YVU order here. StreamY := TFileStream.Create(InFile, fmOpenRead + fmShareDenyNone); StreamV := TFileStream.Create(InFile, fmOpenRead + fmShareDenyNone); StreamU := TFileStream.Create(InFile, fmOpenRead + fmShareDenyNone); TRY // Read same file as three different streams. YVU order. FilePointer := 0; StreamY.Seek(FilePointer, soFromBeginning); FilePointer := YRowCount * YColumnCount; StreamV.Seek(FilePointer, soFromBeginning); FilePointer := FilePointer + (YRowCount DIV Factor) * (YColumnCount DIV Factor); StreamU.Seek(FilePointer, soFromBeginning); DisplayIndex := RadioGroupYVURGB.ItemIndex; Bitmap := TBitmap.Create; TRY Bitmap.Width := YColumnCount; Bitmap.Height := YRowCount; Bitmap.PixelFormat := pf24Bit; FOR j := 0 TO YRowCount-1 DO BEGIN // Read each "row" of data StreamY.Read(BufferY, YColumnCount {bytes}); // YUV12: Read U and V "row" of data on even-numbered rows // Re-use the same row of data for the odd-numbered rows // // YUV9: Read new row every fourth output row. Re-use // the same row for the other rows. IF j MOD Factor = 0 THEN BEGIN StreamU.Read(BufferU, YColumnCount DIV Factor {bytes}); StreamV.Read(BufferV, YColumnCount DIV Factor {bytes}); END; Row := Bitmap.Scanline[j]; FOR i := 0 TO YColumnCount-1 DO BEGIN Y := BufferY[i]; IF i MOD Factor = 0 THEN BEGIN U := BufferU[i DIV Factor]; V := BufferV[i DIV Factor] END; WITH Row[i] DO BEGIN CASE DisplayIndex OF // Y plane 0: BEGIN rgbtBlue := Y; rgbtGreen := Y; rgbtRed := Y END; // U plane 1: BEGIN rgbtBlue := U; rgbtGreen := U; rgbtRed := U END; // V plane 2: BEGIN rgbtBlue := V; rgbtGreen := V; rgbtRed := V END; // YUV to RGB Conversion // see www.webartz.com/fourcc/fccyvrgb.htm // It's unclear whether U and V are switched, or whether // the formula from this web site is correct with // U = Cb and V = Cr 3: BEGIN rgbtBlue := FixRange( 1.164*(Y - 16) + 2.018*(U-128) ); rgbtGreen := FixRange( 1.164*(Y - 16) - 0.813*(U-128) - 0.391*(V-128) ); rgbtRed := FixRange( 1.164*(Y - 16) + 1.596*(V-128) ); END; END; END END END; Bitmap.SaveToFile(OutFile); ImageRGB.Picture.Graphic := Bitmap FINALLY Bitmap.Free END FINALLY StreamY.Free; StreamU.Free; StreamV.Free END; // Change size of TImage to reflect (but fake) size of real data CASE DisplayIndex OF // Y plane or RGB 0,3: BEGIN ImageRGB.Width := YColumnCount; ImageRGB.Height := YRowCount; ImageRGB.Stretch := FALSE END; // U or V planes 1,2: BEGIN ImageRGB.Width := YColumnCount DIV Factor; ImageRGB.Height := YRowCount DIV Factor; ImageRGB.Stretch := TRUE END; END; END {UpdateYUV}; procedure TFormYVUtoRGB.FormCreate(Sender: TObject); begin UpdateYUV; end; procedure TFormYVUtoRGB.RadioGroupClick(Sender: TObject); begin UpdateYUV end; end. ti posto anche dei link assolutamente utili: http://msdn2.microsoft.com/en-us/library/ms867704.aspx http://www.reference.com/search?q=YUV che mi hanno permesso di capire un pò cose. ora mi manca capire come dicevo prima recupere le info sul file. |
|
Utenti attualmente attivi che stanno leggendo questa discussione: 1 (0 utenti e 1 ospiti) | |
Strumenti discussione | |
|
|
Discussioni simili | ||||
Discussione | Autore discussione | Forum | Risposte | Ultimo messaggio |
[ALGORITMI] divisione dato a 32bit i 4 byte | aduri | Programmazione | 1 | 06-04-2007 17.35.22 |
[ALGORITMI] - SIP VoIP - Aperto, ok, ma dove!? | realtebo | Programmazione | 3 | 23-09-2005 14.58.56 |