Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations Chriss Miller on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Animation While WebBrowser control is Busy/Navigating 2

Status
Not open for further replies.

CubeE101

Programmer
Nov 19, 2002
1,492
US
I have a web browser built into one of my projects...

I have the tool bars all set up, but the only way you know the browser is busy is that I made the Stop Button light up while it is navigating, then disable it when it completes....

What would be the best way to display an animation while the WebBrowser Object is Working?

Gif? Avi? ImageList?

I would like to keep everything stored in 1 EXE...
So, it looks to me like I'll have to use an image list, unless someone wants to step me through resources (resource editing)... (which I'm not even sure would work anyway)

So, if it is down to the Image List, I guess I will get to use a timer to start and handle the animation...

I will probably start the animation in WebBrowser1_BeforeNavigate2

Then Stop it in WebBrowser1_NavigateComplete2

Is there a better way to handle this...

This seems like the long way around the situation...

Does any one know how the animation is handled in IE ?

This is all I found (C#) and it looks as though they are using an Image List too...

Thanks in Advance ;-)
-Josh

Visit My Site
PROGRAMMER: (n) Red-eyed, mumbling mammal capable of conversing with inanimate objects.
 
The amination control to show the gif-animation is a good solution (strongm's post)

You could also use an imageList with a timer control cycling through the indexes ... to display them in a pic or img control
 
Then how do you store the AVI in the EXE?

Visit My Site
PROGRAMMER: (n) Red-eyed, mumbling mammal capable of conversing with inanimate objects.
 
Hmmm... what kind of AVI file does it need to be...

I rendered the animation with AVI JPEG and it works in Media Player, but I get this error in VB / Animation control:

Run-time error '35752':
Unable to open AVI file

Using this code:
Code:
Private Sub Form_Load()
    Animation1.Open App.Path & "\test.avi"
End Sub

' Start/Stop playing the AVI file
Private Sub Command1_Click()
    If Command1.Caption = "Start" Then
        Command1.Caption = "Stop"
        Animation1.AutoPlay = True
    Else
        Command1.Caption = "Start"
        Animation1.AutoPlay = False
    End If
End Sub


Visit My Site
PROGRAMMER: (n) Red-eyed, mumbling mammal capable of conversing with inanimate objects.
 
Never Mind... I used AVI RAW and it worked fine...

Moving on!

Now I have the avi in the resource file...

Do you HAVE TO create a temp file to play the AVI???
Code:
 ' Load RES File into a Byte Array
  ResFile = [b]LoadResData(RES_ID, RES_Type)[/b]
  
  ' Save the RES file to the new temp file
  Close
  FileNum = FreeFile
  Open strTemp For Binary As #FileNum      ' Open Temp File
    [b]Put #FileNum, 1, ResFile()[/b]             ' Insert Byte Array into Temp File
  Close #FileNum                           ' Close Temp File

Or is there another way to do this?

Visit My Site
PROGRAMMER: (n) Red-eyed, mumbling mammal capable of conversing with inanimate objects.
 
OK...

I found This (Click Me)

Which says to use this:
Code:
 lResult = SendMessage(     // returns LRESULT in lResult
 (HWND) hWndControl,        // handle to destination control
 (UINT) ACM_OPEN,           // message ID
 #if (_WIN32_IE >= 0x0400)
     wParam = (WPARAM)(HINSTANCE)hinst,
 #else
     wParam = 0,
 #endif
     lParam = (LPARAM) (LPSTR) lpszName
 );

Sooo....
It looks like I get to use these declarations:
Code:
Private Const WM_USER As Long = &H400
Private Const ACM_OPEN As Long = (WM_USER+100)
Private Const ACM_PLAY As Long = (WM_USER+101)
Private Const ACM_STOP As Long = (WM_USER+102)

Private Declare Function SendMessage Lib "user32.dll" Alias "SendMessageA" (ByVal hwnd As Long, ByVal wMsg As Long, ByVal wParam As Long, ByRef lParam As Any) As Long

OK... found http://www.vb-hellfire.de/knowlib/resanimate.php&prev=/search%3Fq%3DSendMessage%2BAnimation1.hWnd%26num%3D100%26hl%3Den%26lr%3D]This: (though in German / Translated)[/url]

So, after a little tweaking...
Tell me if I got it, because it does not seem to be working (in IDE nor Compiled):
Code:
Private Const WM_USER As Long = &H400
Private Const ACM_OPEN As Long = (WM_USER + 100)
Private Const ACM_PLAY As Long = (WM_USER + 101)
Private Const ACM_STOP As Long = (WM_USER + 102)

Private Declare Function SendMessage Lib "user32.dll" Alias "SendMessageA" _
                        (ByVal hwnd As Long, ByVal wMsg As Long, _
                         ByVal wParam As Long, ByRef lParam As Any) As Long

Private Enum acCmd
  acOpen = 1
  acPlay = 2
  acSeek = 3
  acStop = 4
  acClose = 5
End Enum

Private Function ResAnimate(ByRef Anim As Animation, _
                            ByVal Cmd As acCmd, _
                   Optional ByVal ID As Long, _
                   Optional ByVal StartFrame As Integer = 0, _
                   Optional ByVal EndFrame As Integer = -1, _
                   Optional ByVal Repeat As Long = -1) As Boolean
  Dim lngRet As Long
  Select Case Cmd
    Case acOpen
      lngRet = SendMessage(Anim.hwnd, ACM_OPEN, App.hInstance, ByVal ID)
    Case acPlay
      lngRet = SendMessage(Anim.hwnd, ACM_PLAY, Repeat, ByVal CLng(EndFrame * &H10000 + StartFrame))
    Case acSeek
      lngRet = SendMessage(Anim.hwnd, ACM_PLAY, 1, ByVal CLng(StartFrame * &H10000 + StartFrame))
    Case acStop
      lngRet = SendMessage(Anim.hwnd, ACM_STOP, 0&, ByVal 0&)
    Case acClose
      lngRet = SendMessage(Anim.hwnd, ACM_OPEN, App.hInstance, ByVal vbNullString)
      Anim.Visible = False
      Anim.Visible = True
  End Select
  ResAnimate = (lngRet <> 0)
End Function

Private Sub Form_Load()
  ResAnimate Animation1, acOpen, 101&
  Command1.Caption = "Start"
End Sub

' Start/Stop playing the AVI file
Private Sub Command1_Click()
  If Command1.Caption = "Start" Then
    Command1.Caption = "Stop"
    ResAnimate Animation1, acPlay
  Else
    Command1.Caption = "Start"
    ResAnimate Animation1, acStop
  End If
End Sub

Private Sub Form_Unload(Cancel As Integer)
  ResAnimate Animation1, acClose
End Sub

AVI file is imported into resource as 101, custom type "AVI"

Visit My Site
PROGRAMMER: (n) Red-eyed, mumbling mammal capable of conversing with inanimate objects.
 
Besides the AVI solution, you may also consider putting your animation clip frame-by-frame in a bitmap, like a video tape. After that you can animate the clip using the BitBlt API or Microsoft Picture Clip control, which is probably a wrapper around the same API function.

Its simple. The MSDN sample project for this control "Red Top" demonstrate the same animation technique.
 
For the Picture Clip control... do you put the images in an image list?

I think I used it once before... but I forgot how ;-)

As I mentioned in the original Post... I know I can place the images in an image control then use a timer to flip them via a picture box control (or something along those lines...)

The down side to that method (individual frames) is that it can be a pain to modify... as opposed to just replacing a single AVI / GIF

If I can't get the AVI to work, I will keep that in mind as a last resort...

For now, can anyone tell if there is something wrong with the above AVI/Resource code?

Thanks for the posts so far...
I will award stars here shortly, but if you are like me, I tend to overlook threads that already have stars, so I would like to get the issue resolved first...

Thanks,
-Josh

Visit My Site
PROGRAMMER: (n) Red-eyed, mumbling mammal capable of conversing with inanimate objects.
 
OK... got it working!!!

*Notes:
1) Make sure AVI is a silent AVI ... (I used Jasc Animation studio and re-created the AVI)

2) Make sure the Form is loaded... (I moved the avi load to Form_Paint)

3) Make sure you compile the EXE (Will not work in IDE)

here is the working code, in case anyone is interesred:
Code:
Private Const WM_USER As Long = &H400
Private Const ACM_OPEN As Long = (WM_USER + 100)
Private Const ACM_PLAY As Long = (WM_USER + 101)
Private Const ACM_STOP As Long = (WM_USER + 102)

Private Declare Function SendMessage Lib "user32.dll" Alias "SendMessageA" _
                        (ByVal hwnd As Long, ByVal wMsg As Long, _
                         ByVal wParam As Long, ByRef lParam As Any) As Long

Private Enum acCmd
  acOpen = 1
  acPlay = 2
  acSeek = 3
  acStop = 4
  acClose = 5
End Enum

[b]Private aviLoaded As Boolean[/b]

Private Function ResAnimate(ByRef Anim As Animation, _
                            ByVal Cmd As acCmd, _
                   Optional ByVal ID As Long, _
                   Optional ByVal StartFrame As Integer = 0, _
                   Optional ByVal EndFrame As Integer = -1, _
                   Optional ByVal Repeat As Long = -1) As Boolean
  Dim lngRet As Long
  Select Case Cmd
    Case acOpen
      lngRet = SendMessage(Anim.hwnd, ACM_OPEN, App.hInstance, ByVal ID)
    Case acPlay
      lngRet = SendMessage(Anim.hwnd, ACM_PLAY, Repeat, ByVal CLng(EndFrame * &H10000 + StartFrame))
    Case acSeek
      lngRet = SendMessage(Anim.hwnd, ACM_PLAY, 1, ByVal CLng(StartFrame * &H10000 + StartFrame))
    Case acStop
      lngRet = SendMessage(Anim.hwnd, ACM_STOP, 0&, ByVal 0&)
    Case acClose
      lngRet = SendMessage(Anim.hwnd, ACM_OPEN, App.hInstance, ByVal vbNullString)
      Anim.Visible = False
      Anim.Visible = True
  End Select
  ResAnimate = (lngRet <> 0)
End Function

[b]Private Sub Form_Paint()
  If Not aviLoaded Then
    aviLoaded = ResAnimate(Animation1, acOpen, 101&)
    Command1.Caption = "Start"
  End If
End Sub[/b]

' Start/Stop playing the AVI file
Private Sub Command1_Click()
  [b]If aviLoaded Then[/b]
    If Command1.Caption = "Start" Then
      Command1.Caption = "Stop"
      ResAnimate Animation1, acPlay
    Else
      Command1.Caption = "Start"
      ResAnimate Animation1, acStop
    End If
  End If
End Sub

Private Sub Form_Unload(Cancel As Integer)
  [b]If aviLoaded Then[/b]
    ResAnimate Animation1, acClose
  End If
End Sub

Thanks for the help!
-Josh

Visit My Site
PROGRAMMER: (n) Red-eyed, mumbling mammal capable of conversing with inanimate objects.
 
I'm nowhere near a viable VB6 workstation today (well, not 'til I get home), so I can't check at the moment. However, I would have thought that once you have successfully opned the resource via ACM_OPEN that the normal animation Play and Stop command should work
 
>>For the Picture Clip control... do you put the images in an image list?

No. In the picture clip control itself. The whole animation is tiled and saved as a single bitmap which can be loaded in the Picture property of the picture clip control. Individual frames are accessed using the Clip property.

And just forgot to mention earlier -- instead of the picture clip control and the BitBlt API, you can also use the PaintPicture method, which is a wrapper around the StretchBlt function.
 
Hypetia said:
No. In the picture clip control itself. The whole animation is tiled and saved as a single bitmap which can be loaded in the Picture property of the picture clip control. Individual frames are accessed using the Clip property.

Thats right...

You use it to slice a big Bitmap into frames/tiles...
I knew I had seen that somewhere thread222-445570 ;-)

-/-/-/-/-

strongm,
I was having trouble getting the AVI to open with ACM_OPEN... (hence the 3 rules above)
Although, I tried the regular methods:
(*Note: This code does not work, use the commented out command instead)
Code:
[COLOR=red]' Start/Stop playing the AVI file
Private Sub Command1_Click()
  If aviLoaded Then
    If Command1.Caption = "Start" Then
      Command1.Caption = "Stop"
      'ResAnimate Animation1, acPlay
      [b]Animation1.Play[/b]
    Else
      Command1.Caption = "Start"
      'ResAnimate Animation1, acStop
      [b]Animation1.Stop[/b]
    End If
  End If
End Sub

Private Sub Form_Unload(Cancel As Integer)
  If aviLoaded Then
    'ResAnimate Animation1, acClose
    [b]Animation1.Close[/b]
  End If
End Sub[/color]

And get this error...
---------------------------
avi test
---------------------------
Run-time error '35755':

Must open AVI file first
---------------------------
OK
---------------------------

So... No, because the control does not know it has an AVI file open...
You have to send messages to it to control it...
(due to the fact you use an API to insert the AVI directly into the control, bypassing the standard Open method)

I'm sure there is a way to trick it to think that it has a file open, but that little function works well enough, I won't bother...

Thanks Again

Visit My Site
PROGRAMMER: (n) Red-eyed, mumbling mammal capable of conversing with inanimate objects.
 
>hence the 3 rules above

We cross-posted. Mine was in response to your "it does not seem to be working (in IDE nor Compiled)" post.

I've now investigated, and get the same issue you experienced. I'm guessing that the VB Animation Control which wraps the unerlying Windows Animation control has a flag that gets set when a file is opened through the wrapper's method, and won't play the file if the flag isn't set.

However, making that assumption leads to the idea of bypassing that flag, which in turn leads to thinking about the Autoplay function...

... which in turn leads to a much shorter piece of code ...

Starting the animation:
Code:
Animation1.AutoPlay = True
SendMessage Animation1.hwnd, ACM_OPEN, App.hInstance, ByVal 101

Stopping the animation:
Code:
Animation1.AutoPlay = False

 
Regarding the AutoPlay method...

*Note: You have to reload it everytime you want to restart the animation...
In other words, you can't just use:
Animation1.AutoPlay = True
To restart it...
But you are right, you could place those sets of code in 2 functions, and dramatically shorten the code...

Do you still have to unload the AVI with...
SendMessage(Anim.hwnd, ACM_OPEN, App.hInstance, ByVal vbNullString)
To keep it from hanging in memory?
Or is that even an issue in the first place?

Also...

Can you stretch the animation (particularly, if it is loaded from a resource)
I'm pretty sure you could with the MCI controls (or is this the same control?)

The MCI version looked something like this:
Code:
  mciSendString "open C:\MyAvi.avi Type avivideo Alias AVI1 parent " & Pic.hWnd & " Style " & &H40000000, 0&, 0, 0
  ...
  mciSendString "Put AVI1 window at 0 0 " & Width & " " & Height, vbNullString, 0, 0

Where Width & Height would set the respective values of the control and stretch the output...

Can you do something similar with the Animation control?

-Or- (dare I ask ;-))

Can you load the AVI from the resource using the MCI methods?

Visit My Site
PROGRAMMER: (n) Red-eyed, mumbling mammal capable of conversing with inanimate objects.
 
>you can't just use:
> Animation1.AutoPlay = True

Correct. Which is why I illustrated the specific code that I did. I don't just make this stuff up, you know.

>Or is that even an issue in the first place?

No. The control cleans up after itself.

>Can you stretch the animation (particularly, if it is loaded from a resource)

No

>Can you load the AVI from the resource using the MCI methods?

Coo! We've just come up with a solution that isn't covered (as far as I can tell) on any other site on the Internet - and you want more ...


 
and you want more

You betcha :p

That was just out of curiosity...

I found bits and pieces of a trail for the MCI version, but, so far, I kept hitting dead ends...

Basically...

This is an awsome solution, and it works great for what I needed it for...

But... (DUN Dun dun ;-)) If you can't scale the video, there is room for improvement... and that means there is a better solution ;-)

Anyway, I got what I need, a little 32 x 32 animation in the corner of my Explorer window that activates anytime you navigate, and the AVI is kept inside the EXE (less mess)

So, I might look further into the MCI / Resource thing at a later date... but until then...

Case Closed!

And again...
Thanks for the help!!!

Visit My Site
PROGRAMMER: (n) Red-eyed, mumbling mammal capable of conversing with inanimate objects.
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top