Форум: "Media";
Текущий архив: 2006.06.18;
Скачать: [xml.tar.bz2];
Внизиз MPEG4 файла нужно выдернуть несколько ключевых кадров Найти похожие ветки
← →
GekaNaz © (2006-01-13 16:51) [0]Помогите пожалуйста, как это можно сделать, или где искать про это информацию, думаю это не очень сложно.
← →
NailMan © (2006-01-13 17:58) [1]Можно сделать так
1) имея в наличии DirectX SDK, а точнее *.chm со всей писаниной, посмотреть на структуру RIFF-AVI. В конце пожатых AVIшек есть секция с тегом-идентификатором "idx1"
Вот полностью процедура выводящая на форму инфу о размерах потоков авишки:Procedure TAdvForm.FillInfo(Name:String;Frames:double);
var f:integer;p:pointer;
PD:PDWORD;
ID,TIP:DWORD;
FF,SIZE:DWORD;
FCC:Array[0..3] of char;
ds,fs:Double;
KeyFrames:integer;
DeltaFrames:integer;
AudioFrames:Integer;
TableOffset,Tablesize,nuldd:dword;
MinKeyFrame,MaxKeyFrame,AverageKeyFrame:DWORD;
MinDeltaFrame,MaxDeltaFrame,AverageDeltaFrame:DWORD;
MinAudioFrame,MaxAudioFrame,AverageAudioFrame:DWORD;
VideoDataSize,AudioDataSize:DWORD;
begin
f:=fileopen(name,fmopenread or fmsharedenynone);
fileread(f,nuldd,4);
fileread(f,nuldd,4);
fileread(f,nuldd,4);
fileread(f,nuldd,4);
FF:=0;
while FF<>$69766f6d do
begin
If FCC="JUNK" then
begin
fileread(f,nuldd,4);
GetMem(p,nuldd);
fileread(f,p^,nuldd);
Freemem(p);
end;
If FCC="LIST" then
begin
Fileread(f,size,4);
Fileread(f,FF,4);
If FF<>$69766F6D then
begin
GetMem(p,size);
fileread(f,p^,size);
Freemem(p);
end else break;
fileseek(f,-4,1);
end;
FileRead(f,nuldd,4);
end;
TableOffset:=fileseek(f,0,1);
TableOffset:=TableOffset+SIZE-4;
fileseek(f,TableOffset,0);
fileread(f,nuldd,4);
fileread(f,TableSize,4);
GetMem(p,tablesize+4);
FillChar(P^,TableSize+4,$FF);
Fileread(f,P^,TableSize);
fileclose(f);
PD:=P;
KeyFrames:=0;
DeltaFrames:=0;
AudioFrames:=0;
MinKeyFrame:=$FFFFFFFF;
MaxKeyFrame:=0;
AverageKeyFrame:=0;
MinDeltaFrame:=$FFFFFFFF;
MaxDeltaFrame:=0;
AverageDeltaFrame:=0;
MinAudioFrame:=$FFFFFFFF;
MaxAudioFrame:=0;
AverageAudioFrame:=0;
VideoDataSize:=0;
AudioDataSize:=0;
repeat
ID:=PD^;
Inc(PD);
TIP:=PD^;
Inc(PD);
Inc(PD);
SIZE:=PD^;
//00dc
If (ID=$63643030) then
begin
If TIP=$10 then begin //KeyFrame
Inc(KeyFrames);
If Size<MinKeyFrame then MinKeyFrame:=Size;
If Size>MaxKeyFrame then MaxKeyFrame:=Size;
AverageKeyFrame:=AverageKeyFrame+Size;
end
else begin //DeltaFrame
inc(DeltaFrames);
If Size<MinDeltaFrame then MinDeltaFrame:=Size;
If Size>MaxDeltaFrame then MaxDeltaFrame:=Size;
AverageDeltaFrame:=AverageDeltaFrame+Size;
end;
VideoDataSize:=VideoDataSize+Size;
end;
//01wb
If (hiword(ID)=$6277) then
begin
inc(AudioFrames);
If Size<MinAudioFrame then MinAudioFrame:=Size;
If Size>MaxAudioFrame then MaxAudioFrame:=Size;
AverageAudioFrame:=AverageAudioFrame+Size;
AudioDataSize:=AudioDataSize+Size;
end;
inc(PD);
until PD^=$FFFFFFFF;
Freemem(P);
AdvForm.SetLanguage(language);
ds:=VideoDataSize;
if language=lang_russian then
begin
VDataSizeL.Caption:=floattostrf(ds,ffnumber,15,0)+" Байт ( "+
floattostrf(ds / 1024 / 1024,fffixed,15,3)+" МБ )";
ds:=AudioDataSize;
ADataSizeL.Caption:=floattostrf(ds,ffnumber,15,0)+" Байт ( "+
floattostrf(ds / 1024 / 1024,fffixed,15,3)+" МБ )";
end
else
begin
VDataSizeL.Caption:=floattostrf(ds,ffnumber,15,0)+" bytes ( "+
floattostrf(ds / 1024 / 1024,fffixed,15,3)+" Mb )";
ds:=AudioDataSize;
ADataSizeL.Caption:=floattostrf(ds,ffnumber,15,0)+" bytes ( "+
floattostrf(ds / 1024 / 1024,fffixed,15,3)+" Mb )";
end;
ds:=KeyFrames;
KeyFrL.Caption:=floattostrf(ds,ffnumber,15,0);
ds:=DeltaFrames;
DeltaFrL.Caption:=floattostrf(ds,ffnumber,15,0);
ds:=AudioFrames;
ASamplesL.Caption:=floattostrf(ds,ffnumber,15,0);
if KeyFrames=0 then KeyFrames:=1;
ds:=MinKeyFrame;
fs:=MaxKeyFrame;
if language=lang_russian then
MinMaxKeyFrL.Caption:=floattostrf(ds,ffnumber,15,0)+" / "+floattostrf(fs,ffnumber,15,0)+" Байт"
else
MinMaxKeyFrL.Caption:=floattostrf(ds,ffnumber,15,0)+" / "+floattostrf(fs,ffnumber,15,0)+" bytes";
AverageKeyFrame:=Round(AverageKeyFrame / KeyFrames);
ds:=AverageKeyFrame;
if language=lang_russian then
AvrgKeyL.Caption:=floattostrf(ds,ffnumber,15,0)+" Байт"
else
AvrgKeyL.Caption:=floattostrf(ds,ffnumber,15,0)+" bytes";
if DeltaFrames=0 then DeltaFrames:=1;
ds:=MinDeltaFrame;
fs:=MaxDeltaFrame;
if language=lang_russian then
MinMaxDeltaFrL.Caption:=floattostrf(ds,ffnumber,15,0)+" / "+floattostrf(fs,ffnumber,15,0)+" Байт"
else
MinMaxDeltaFrL.Caption:=floattostrf(ds,ffnumber,15,0)+" / "+floattostrf(fs,ffnumber,15,0)+" bytes";
AverageDeltaFrame:=Round(AverageDeltaFrame / DeltaFrames);
ds:=AverageDeltaFrame;
if language=lang_russian then
AvrgDeltaFrL.Caption:=floattostrf(ds,ffnumber,15,0)+" Байт"
else
AvrgDeltaFrL.Caption:=floattostrf(ds,ffnumber,15,0)+" bytes";
ds:=VideoDataSize / frames / 1024; //Kbytes per sec
fs:=(ds * 8 * 1024) / 1000; //Kbits per sec
if language=lang_russian then
VBitRateL.Caption:=floattostrf(ds,fffixed,15,3)+" КБайт/сек ( "+
floattostrf(fs,fffixed,15,3)+" КБит/сек )"
else
VBitRateL.Caption:=floattostrf(ds,fffixed,15,3)+" Kbyte/sec ( "+
floattostrf(fs,fffixed,15,3)+" Kbit/sec )";
if AudioFrames=0 then AudioFrames:=1;
ds:=MinAudioFrame;
fs:=MaxAudioFrame;
if language=lang_russian then
MinMaxSampL.Caption:=floattostrf(ds,ffnumber,15,0)+" / "+floattostrf(fs,ffnumber,15,0)+" Байт"
else
MinMaxSampL.Caption:=floattostrf(ds,ffnumber,15,0)+" / "+floattostrf(fs,ffnumber,15,0)+" bytes";
AverageAudioFrame:=Round(AverageAudioFrame / AudioFrames);
ds:=AverageAudioFrame;
if language=lang_russian then
AvrgSampL.Caption:=floattostrf(ds,ffnumber,15,0)+" Байт"
else
AvrgSampL.Caption:=floattostrf(ds,ffnumber,15,0)+" bytes";
ds:=AudioDataSize / frames / 1024; //Kbytes per sec
fs:=(ds * 8 * 1024) / 1000; //Kbits per sec
if language=lang_russian then
ABitRateL.Caption:=floattostrf(ds,fffixed,15,3)+" КБайт/сек ( "+
floattostrf(fs,fffixed,15,3)+" КБит/сек )"
else
ABitRateL.Caption:=floattostrf(ds,fffixed,15,3)+" Kbyte/sec ( "+
floattostrf(fs,fffixed,15,3)+" Kbit/sec )";
ds:=DeltaFrames/keyframes;
DivDeltaKeyL.Caption:=floattostrf(ds,fffixed,15,3);
end;
Думаю поймешь что к чему.
2) Если тебе нужны сами картинки ключевых кадров, то загрузив в граф файло, переходишь на заранее сохраненные в массив номера ключевых кадров и выцепляешь их SampleGrabber-ом, который также подключаешь к графу. Пример использования SampleGrabber-а есть в том самом DX SDK прямо в *.chm-ке.
---
P.L.U.R. and WBR, NailMan aka 2:5020/3337.13
← →
GekaNaz © (2006-01-13 19:20) [2]мне нужны именно картинки, если не трудно скажите как их вытащить в отдельные файлы (с видео никогда просто не работал)
и что такое SampleGrabber
← →
GekaNaz © (2006-01-13 19:33) [3]Кстати, данная прога нужна для выкладывания картинок на сайт
http://freevideo.tomsk.ru
← →
NailMan © (2006-01-13 19:46) [4]С кодом вытаскивания помочь пока не смогу, так как исходники старого плеера где сие делать можно было не сохранились, а в новый плеер пока функции не добавлял увы...
SampleGrabber - это программный фильтр, который загружается в цепочку декодирования фидеопотока(граф) перед фильтром вывода на экран. У него есть метод получения указателя на текущий кадр, который средствами API можно на диск сохранить
---
P.L.U.R. and WBR, NailMan aka 2:5020/3337.13
← →
GekaNaz © (2006-01-17 13:21) [5]Может кто-нибудь подскажет еще ?
желательно како-нибудь пример, заранее спасибо :)
← →
programania © (2006-01-17 20:53) [6]Сделал запись кадров из divX используя DSPack из progdigy.com
подробнее
http://programania.com/v06_ru.htm
попробовать
http://programania.com/ENJOL.ZIP 840kb
если надо могу надергать исходников что к этому относятся
← →
GekaNaz © (2006-01-18 12:17) [7]О, спасибо, а можно исходники ?? если на дельфях, то просто изумительно !
← →
GekaNaz © (2006-01-18 21:17) [8]ENJOL.ZIP - не могу найти , где там можно сохранить кадры из видеофайла в картинки на диск ??
← →
programania © (2006-01-19 19:11) [9]>GekaNaz © (18.01.06 21:17) [8]
>ENJOL.ZIP - не могу найти , где там можно сохранить кадры из видеофайла в картинки на диск ??
Надо нажать M, + справа, указать где фильмы
в списке фильмов запустить фильм X
нажимать K где надо
кадры будут в папке с именем фильма
а при остановке фильма на экране
подробнее
http://programania.com/v06_ru.htm
Смотрите примеры к DSPack из progdigy.com
или как у меня:
Запуск проигрывания:
form1.sampleGrabber1.filterGraph:=filterGraph1;
form1.FilterGraph1.RenderFile("film.avi");
form1.FilterGraph1.Play;
//событие компонента SampleGrabber захват в bTV: tBitmap
procedure TForm1.SampleGrabber1Buffer(sender: TObject; SampleTime: Double;
pBuffer: Pointer; BufferLen: Integer);
begin
if not eCap then
SampleGrabber1.GetBitmap(bTV, pBuffer, BufferLen);
eCap:=true;
end;
PROCEDURE kadr1;
var tk:cardinal;
begin
//ожидание захвата кадра
eCap:=false; wkadr:=true; stop:=false;
tk:=getTickCount+4000;
while not eCap and not stop and (getTickCount<tk)do application.processMessages;
wkadr:=false;
end;
PROCEDURE kadr;
var rm,kr,x,y,r:integer;
begin
//захват одного кадра по кнопке
iPA:=false;
rm:=0;
//пропорции кадра
if o.c11 then kr:=(me.rx-me.ry)div 2 else
if o.c34 then kr:=(me.rx-me.ry*4 div 3)div 2 else
kr:=me.rx{width}*o.ok div 100;
if kr<0 then kr:=0;
wKadr:=true;
kadr1;
b.width:=bTV.Width-(rm+kr)*2; b.height:=bTV.Height-rm*2;
b.canvas.copyrect(rect(0,0,b.Width,b.Height+1),
bTV.canvas,rect(kr,0,bTV.Width-kr,bTV.Height+1));
sHeight:=0;sWidth:=0;
bi.width:=b.Width; bi.height:=b.height;
r:=0;
bi.canvas.draw(0,0,b);
with form1.ImageEnIO1,m[nPlay] do begin
//запись из bitmap в jpg используя компонент imageEN
dirAvi(nPlay);
createDir(sp);
sp:=sp+"\"+kadr_wr(pa);
params.JPEG_QUALITY:=90; SaveToFile(sp);
end;
end;
PROCEDURE pKadr;
var
CP,stopPos,r: Int64;
MediaSeeking: IMediaSeeking;
begin
//запись кадров через интервал o.int с позиции pa
with form1 do begin
zKadr0:=true;
wKadr:=true;
zKadr:=true;
FilterGraph1.QueryInterface(IMediaSeeking, MediaSeeking);
MediaSeeking.GetStopPosition(stopPos);
form1.FilterGraph1.pause;
kc:=-1;
stop:=false; iPA:=false;
while (pa<da) and (pa>=0) and not stop do begin
application.processMessages;
r:=pa;
CP:=r*10000;
MediaSeeking.SetPositions(CP,AM_SEEKING_AbsolutePositioning,stopPos,AM_SEEKING_NoPositioning);
if pa>0 then kadr;
inc(pa,o.int*1000);
application.processMessages;
end;
form1.FilterGraph1.stop;
nPlay:=0;
zKadr:=false; zKadr0:=false; k1:=false;
nmFirst:=0;
npk:=true;
tv:=false;
application.processMessages;
end;
end;
Страницы: 1 вся ветка
Форум: "Media";
Текущий архив: 2006.06.18;
Скачать: [xml.tar.bz2];
Память: 0.5 MB
Время: 0.01 c