Solved

Read a frame for an avi movie

Posted on 2000-03-22
6
468 Views
Last Modified: 2010-04-04
I need to display a frame into a canvas from an avi without display the movie and without TMediaPlayer .

For example I wish to display frame 1400 into a canvas .
But VERY IMPORTANT :
I DON'T WISH TO USE TMEDIAPLAYER .
I need an algorithm for read directly from avi .

In same time I need to know the number of frames from avi file .
0
Comment
Question by:ginsonic
  • 3
  • 2
6 Comments
 
LVL 10

Expert Comment

by:Lischke
ID: 2645288
Hi Ginsonic,

here is code I have used a while ago. For some function calls you need a stripped down version of VfW.h (do a search for VfW.pas on the web or download www.lischke-online.de/Download/GLScene044.zip) for this unit and the following code:

type TAVIGraphic = class(TBitmap)
     private
       FAviFile       : PAVIFile;
       FAviStream     : PAVIStream;
       FGetFrameIntf  : PGetFrame;
       FAviFileInfo   : TAVIFileInfoW;
       FAviStreamInfo : TAVIStreamInfo;
       FFrame         : Pointer;
       FCurrentFrame  : Longint;
       FFrames        : Longint;
       FTimer         : TTimer;
       FSpeedFactor   : Single;
     protected
       procedure CloseAVIFile;
       procedure GetNextFrame(Sender: TObject);
       procedure LoadFrame;
       procedure OpenAVIFile(AName: TFileName; Animate: Boolean);
     public
       constructor Create; override;
       destructor Destroy; override;
       procedure LoadFromFile(const FileName: String); override;
       procedure Start;
       procedure Stop;
       property CurrentFrame: Longint read FCurrentFrame;
     published
       property SpeedFactor: Single read FSpeedFactor write FSpeedFactor;
     end;

//----------------- TAVIGraphic ------------------------------------------------

procedure TAVIGraphic.CloseAVIFile;

begin
  FTimer.enabled:=False;
  if assigned(FGetFrameIntf) then AVIStreamGetFrameClose(FGetFrameIntf);
  FGetFrameIntf:=nil;
  if assigned(FAVIStream) then AVIStreamRelease(FAVIStream);
  FAVIStream:=nil;
  if assigned(FAVIFile) then AVIFileRelease(FAVIFile);
  FAVIFile:=nil;
end;

//------------------------------------------------------------------------------

constructor TAVIGraphic.Create;

begin
  inherited Create;
  FTimer:=TTimer.Create(nil);
  FTimer.enabled:=False;
  FTimer.OnTimer:=GetNextFrame;
  FSpeedFactor:=1;
end;

//------------------------------------------------------------------------------

destructor TAVIGraphic.Destroy;

begin
  CloseAVIFile;
  FTimer.Free;
  inherited Destroy;
end;

//------------------------------------------------------------------------------

procedure TAVIGraphic.GetNextFrame(Sender: TObject);

begin
  LoadFrame;
  Changed(Self);
end;

//------------------------------------------------------------------------------

procedure TAVIGraphic.LoadFrame;

var Position : Longint;

begin
  if assigned(FGetFrameIntf) then AVIStreamGetFrameClose(FGetFrameIntf);
  FGetFrameIntf:=AVIStreamGetFrameOpen(FAVIStream,nil);
  FFrame:=AVIStreamGetFrame(FGetFrameIntf,FCurrentFrame);
  if FFrame = nil then Exit;
  Inc(FCurrentFrame);
  if FCurrentFrame = FFrames then FCurrentFrame:=FAVIStreamInfo.dwStart;
  with TBitmapInfo(FFrame^).bmiHeader do
  begin
    Position:=Longint(FFrame)+SizeOf(TBitmapInfoHeader);
    if biClrUsed > 0 then Inc(Position,biClrUsed*Sizeof(TRGBQuad));
    StretchDIBits(Canvas.Handle,0,0,biWidth,biHeight,0,0,biWidth,biHeight,
                  Pointer(Position),TBitmapInfo(FFrame^),DIB_RGB_COLORS,SRCCOPY);
  end;
end;

//------------------------------------------------------------------------------

procedure TAVIGraphic.LoadFromFile(const FileName: String);

begin
  CloseAVIFile;
  OpenAVIFile(FileName,True);
end;

//------------------------------------------------------------------------------

procedure TAVIGraphic.OpenAVIFile(AName: TFileName; Animate: Boolean);

var Result : HResult;

begin
  try
    Result:=AVIFileOpen(FAVIFile,PChar(AName), OF_READ or OF_SHARE_DENY_WRITE,nil);
    if Result <> 0 then Abort;
    Result:=AVIFileInfo(FAVIFile,@FAVIFileInfo,SizeOf(TAVIFileInfoW));
    if Result <> 0 then Abort;
    AVIFileGetStream(FAVIFile,FAVIStream,streamtypeVIDEO,0);
    if FAVIStream = nil then Abort;
    AVIStreamInfo(FAVIStream,@FAVIStreamInfo,Sizeof(TAVIStreamInfo));
    with FAVIStreamInfo do
    begin
      FFrames:=dwLength;
      FCurrentFrame:=dwStart;
      Width:=rcFrame.Right-rcFrame.Left;
      Height:=rcFrame.Bottom-rcFrame.Top;
      LoadFrame;
      if FSpeedFactor <= 0 then FSpeedFactor:=1;
      FTimer.Interval:=Round(1000*dwScale/(dwRate*FSpeedFactor));
      if FTimer.Interval = 0 then FTimer.Interval:=1;
      if Animate then FTimer.enabled:=True;
    end;
  except
    raise Exception.Create('Could not open AVI file '''+AName+'''');
  end;
end;

//------------------------------------------------------------------------------

procedure TAVIGraphic.Start;

begin
  FTimer.enabled:=True;
end;

//------------------------------------------------------------------------------

procedure TAVIGraphic.Stop;

begin
  FTimer.enabled:=False;
end;

//------------------------------------------------------------------------------



Note: This stuff is quite old and may not be the optimal implementation. But at least it works :-)

Ciao, Mike
0
 
LVL 17

Expert Comment

by:inthe
ID: 2645883
0
 
LVL 9

Author Comment

by:ginsonic
ID: 2647947
where can I find the Microsoft Video SDK ?
0
Gigs: Get Your Project Delivered by an Expert

Select from freelancers specializing in everything from database administration to programming, who have proven themselves as experts in their field. Hire the best, collaborate easily, pay securely and get projects done right.

 
LVL 10

Expert Comment

by:Lischke
ID: 2648299
You have to download a 10MB package from http://msdn.microsoft.com/downloads/sdks/platform/dxmedia.asp (take the Platform SDK build environment). From the file you get you can extract INCLUDE_VfW.h etc. using WinZip (it's in Win32-B.cab).

Ciao, Mike
0
 
LVL 9

Author Comment

by:ginsonic
ID: 2648588
Houston we have a problem !

Hi Mike .
I try your code but I think I wrong somewhere .
Can you send me a project file at nick@radioterra.ro ?

I will add 100 points for that .

A sample code with a Panel and a button .
When I press the button to see the movie in panel.

But important .
I don't with to see the avi file .
Just to extract the frames directly ( without capture ) from avi and to display the bmps in Panel .

Regards,
Nick
0
 
LVL 10

Accepted Solution

by:
Lischke earned 100 total points
ID: 2648793
Nick, I just sent you the sample project.

Ciao, Mike
0

Featured Post

Courses: Start Training Online With Pros, Today

Brush up on the basics or master the advanced techniques required to earn essential industry certifications, with Courses. Enroll in a course and start learning today. Training topics range from Android App Dev to the Xen Virtualization Platform.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Creating an auto free TStringList The TStringList is a basic and frequently used object in Delphi. On many occasions, you may want to create a temporary list, process some items in the list and be done with the list. In such cases, you have to…
Have you ever had your Delphi form/application just hanging while waiting for data to load? This is the article to read if you want to learn some things about adding threads for data loading in the background. First, I'll setup a general applica…
This video shows how to quickly and easily add an email signature for all users on Exchange 2016. The resulting signature is applied on a server level by Exchange Online. The email signature template has been downloaded from: www.mail-signatures…
Although Jacob Bernoulli (1654-1705) has been credited as the creator of "Binomial Distribution Table", Gottfried Leibniz (1646-1716) did his dissertation on the subject in 1666; Leibniz you may recall is the co-inventor of "Calculus" and beat Isaac…

776 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question