Announcement

Collapse
No announcement yet.

New PC Fails PlayMovieInWindow

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

  • New PC Fails PlayMovieInWindow

    This code from https://forum.powerbasic.com/forum/u...-capture-redux, post #4, works on my old PC but not on the PC I just purchased. The original Jose code, on which this code is based, also does not work on the new PC. Both result in an error #99 (Object Error).

    I made sure that the include files were identical.

    The new PC has Windows 10 Pro, whereas the old PC has Windows 10 Home.

    Source code plus includes - what else is there on a new PC that might be involved in the failure?

    Code:
    'Compilable Example:  Play Video - Minimal Code
    #Compiler PBWin 10
    #Compile Exe
    #Dim All
    %Unicode = 1
    #Include "Win32API.inc"
    #Include Once "dshow.inc"
    #Include Once "ole2utils.inc"   ' For IUnknown_Release
    
    %IDC_Graphic = 500
    %WM_GraphNotify = %WM_User+13
    
    Global hDlg As Dword
    
    ' Interface pointers
    Global pIGraphBuilder As IGraphBuilder
    Global pIMediaControl As IMediaControl
    Global pIMediaEventEx As IMediaEventEx
    Global pIVideoWindow  As IVideoWindow
    
    Function PBMain() As Long
       Dialog New Pixels, 0, "Direct Show Tests",,,600,400, %WS_OverlappedWindow To hDlg
       Dialog Show Modal hDlg Call DlgProc
    End Function
    
    CallBack Function DlgProc() As Long
       Local w,h As Long, rc As Rect
       Select Case Cb.Msg
          Case %WM_InitDialog
             PlayMovieInWindow(hDlg, "bubbles.mov")
          Case %WM_Size
             GetClientRect hDlg, rc
             If IsObject(pIVideoWindow) Then
                pIVideoWindow.SetWindowPosition(rc.Left, rc.Top, rc.Right, rc.Bottom)
                RedrawWindow hDlg, rc, 0, %RDW_INVALIDATE Or %RDW_UPDATENOW
             End If
       End Select
    End Function
    
    Sub PlayMovieInWindow (ByVal hwnd As Dword, ByRef wszFileName As WStringZ)
       Local hr As Long
       pIGraphBuilder = NewCom ClsId $CLSID_FilterGraph   ' Create an instance of the IGraphBuilder object
       pIMediaControl = pIGraphBuilder                             ' Get reference pointers
       pIMediaEventEx = pIGraphBuilder
       pIVideoWindow  = pIGraphBuilder
       hr = pIGraphBuilder.RenderFile(wszFileName)        ' Render the file
       pIVideoWindow.Visible = %OATRUE                        ' Set the window properties
       pIVideoWindow.Owner = hwnd
       pIVideoWindow.WindowStyle = %WS_Child Or %WS_ClipSiblings Or %WS_ClipChildren
       pIMediaControl.Run                                                    ' Run the graph
    End Sub

  • #2
    With a little testing, this line shows the point at which the error occurs:

    [code] pIVideoWindow.Visible = %OATRUE ' Set the window properties[\code]

    Although, one of the earlier lines could fail without an error, causing that line to fail.

    I'll try using Jose's version, which has full error checking to try and focus in on the error point.

    But, just going from Pro to Home doesn't make the reason for an error to just jump out at me!

    Comment


    • #3
      Is a .mov file valid with the default player?
      How long is an idea? Write it down.

      Comment


      • #4
        Is a .mov file valid with the default player?
        I don´t thinks so. Windows natively supports .wmv, .avi .mp(e)g and some more. For .mov you need a codec (and some other things IIRC). K-lite codec pack or ffmpeg should do.


        JK

        Comment


        • #5
          Yep, the mov file plays just fine in Win 10 Pro without installing K-lite codecs to the new PC.

          I've used derivatives of the code on 20+ PCs, on which K-lite is not loaded. All of those PCs were Windows Home. All show the .mov file just fine.

          Comment


          • #6
            Howdy, Juergen!

            Well, since nothing else worked I went ahead and installed the latest k-lite codecs as you suggested. With that done, the code in #1 above seems to work just fine!

            So that begs the question as to why the capability Win 10 had to play MOV files wasn't available to the PowerBASIC code?

            The needed codec was built into the Win10 player would seem to be the answer - details lacking.


            Comment


            • #7
              Maybe QuickTime was installed on the other machines at some time.
              How long is an idea? Write it down.

              Comment


              • #8
                Howdy, Mike!

                The 20+ PCs I'm talking about, were new PCs that I purchased for customers. I tested the MOV display capability of my code on each (it worked) so I'm certain that QC was not installed before I delivered and tested the systems.

                But you may still be correct that I installed something that unknowingly loaded the needed codec. I don't fully understand how codec installation results in access of the codec to multiple apps and I wouldn't be surprised if an app I loaded added a codec without explicitly telling/asking me.
                Last edited by Gary Beene; 24 Jul 2020, 12:07 PM.

                Comment


                • #9
                  Programs supporting .MOV
                  https://extension.nirsoft.net/mov
                  How long is an idea? Write it down.

                  Comment


                  • #10
                    Another piece of data ... I just bought a refurbished computer today - the hard drive had minimal installed apps. I ran the PlayMovieInWindow code and it failed with the error #99 - same problem I mention in the OP.

                    I installed k-lite codecs and then it worked.

                    Makes me question why my tests on much earlier PCs failed. At least I know to watch for it and that k-lite can save the day.

                    Comment


                    • #11
                      Hey Gary,
                      I was playing around with the code on post #1 and on both of my computers it would not display MOV's, but just like you if I double click the MOV video, it plays ok with the default windows player.

                      So just like you I was wondering why. My best guest is that there is a MOV render (codec) for 64bit apps but not 32bit? and that is why the windows player works and not the PB app?

                      You should probably enumerate the directshow filters available before playing it, something like this.

                      '
                      Code:
                      'Compilable Example:  Play Video - Minimal Code
                      #COMPILER PBWIN 10
                      #COMPILE EXE
                      #DIM ALL
                      %Unicode = 1
                      #INCLUDE "Win32API.inc"
                      #INCLUDE ONCE "dshow.inc"
                      #INCLUDE ONCE "ole2utils.inc"   ' For IUnknown_Release
                      
                      %IDC_Graphic = 500
                      %WM_GraphNotify = %WM_USER+13
                      
                      GLOBAL hDlg AS DWORD
                      
                      ' Interface pointers
                      GLOBAL pIGraphBuilder AS IGraphBuilder
                      GLOBAL pIMediaControl AS IMediaControl
                      GLOBAL pIMediaEventEx AS IMediaEventEx
                      GLOBAL pIVideoWindow  AS IVideoWindow
                      GLOBAL pIEnumFilters  AS IEnumFilters
                      
                      FUNCTION PBMAIN() AS LONG
                         DIALOG NEW PIXELS, 0, "Direct Show Tests",,,600,400, %WS_OVERLAPPEDWINDOW TO hDlg
                         DIALOG SHOW MODAL hDlg CALL DlgProc
                      END FUNCTION
                      
                      CALLBACK FUNCTION DlgProc() AS LONG
                         LOCAL w,h AS LONG, rc AS Rect
                         SELECT CASE CB.MSG
                            CASE %WM_INITDIALOG
                               PlayMovieInWindow(hDlg, "bubbles.avi")
                              ' ? "P "& OBJRESULT$()
                      
                            CASE %WM_SIZE
                               GetClientRect hDlg, rc
                               IF ISOBJECT(pIVideoWindow) THEN
                                  pIVideoWindow.SetWindowPosition(rc.Left, rc.Top, rc.Right, rc.Bottom)
                                  RedrawWindow hDlg, rc, 0, %RDW_INVALIDATE OR %RDW_UPDATENOW
                               END IF
                         END SELECT
                      END FUNCTION
                      
                      SUB PlayMovieInWindow (BYVAL hwnd AS DWORD, BYREF wszFileName AS WSTRINGZ)
                         LOCAL hr, ffilter AS LONG
                         LOCAL wOutput AS WSTRING
                         pIGraphBuilder = NEWCOM CLSID $CLSID_FilterGraph   ' Create an instance of the IGraphBuilder object
                      '? "1 "& OBJRESULT$()
                         pIMediaControl = pIGraphBuilder                             ' Get reference pointers
                      '? "2 "& OBJRESULT$()
                         pIMediaEventEx = pIGraphBuilder
                      '? "3 "& OBJRESULT$()
                         pIVideoWindow  = pIGraphBuilder
                      '? "3 "& OBJRESULT$()
                         hr = pIGraphBuilder.RenderFile(wszFileName)        ' Render the file
                      
                                 hr = EnumFilters(pIGraphBuilder, ffilter,wOutput)       'check if we have a codec for it
                                 IF ffilter THEN ? "Codec Filter not found" : EXIT SUB     'if we don't
                                 '? wOutput                                                'if you want to see what was found
                      
                         pIVideoWindow.Visible = %OATRUE                        ' Set the window properties
                      '? "6 "& OBJRESULT$()
                         pIVideoWindow.Owner = hwnd
                      '? "7 "& OBJRESULT$()
                         pIVideoWindow.WindowStyle = %WS_CHILD OR %WS_CLIPSIBLINGS OR %WS_CLIPCHILDREN
                         pIMediaControl.Run                                                    ' Run the graph
                      
                      END SUB
                      
                      ' ========================================================================================
                      ' The Filter Graph Manager supports the IFilterGraph.EnumFilters method, which enumerates
                      ' all the filters in the filter graph. It returns a pointer to the IEnumFilters interface.
                      ' The IEnumFilters.Next method retrieves IBaseFilter interface pointers.
                      ' ========================================================================================
                      FUNCTION EnumFilters (BYVAL pGraph AS IGraphBuilder, BYREF ffilter AS LONG, BYREF wOutput AS WSTRING) AS LONG
                         LOCAL hr AS LONG                    ' HRESULT
                         LOCAL pEnum AS IEnumFilters         ' IEnumFilters interface
                         LOCAL pFilter AS IBaseFilter        ' IBaseFilter interface
                         LOCAL cFetched AS DWORD             ' Number of filters fetched
                         LOCAL FilterInfo AS FILTER_INFO     ' FILTER_INFO structure
                      
                      ffilter=0
                      wOutput = ""
                         hr = pGraph.EnumFilters(pEnum)
                         IF hr <> %S_OK THEN
                            FUNCTION = hr
                            EXIT FUNCTION
                         END IF
                      
                         DO
                            hr = pEnum.Next(1, pFilter, cFetched)
                            IF hr <> %S_OK OR cFetched = 0 THEN EXIT DO
                            RESET FilterInfo
                            hr = pFilter.QueryFilterInfo(FilterInfo)
                            IF hr <> %S_OK THEN
                               ? "Could not get the filter info"
                            ELSE
                               'STDOUT FilterInfo.achName
                               wOutput += FilterInfo.achName + $CRLF
                               ' The FILTER_INFO structure holds a pointer to the Filter Graph
                               ' Manager, with a reference count that must be released.
                               IF FilterInfo.pGraph <> %NULL THEN IUnknown_Release FilterInfo.pGraph
                            END IF
                            ' Release the filter
                            pFilter = NOTHING
                         LOOP
                      
                         ' Release the collection
                         pEnum = NOTHING
                         ffilter = IIF(LEN(wOutput),%False, %True)
                         FUNCTION = %S_OK
                      END FUNCTION
                      ' ========================================================================================
                      '

                      Comment


                      • #12
                        Thanks, Rod!

                        I'll give that a try.

                        Comment


                        • #13
                          Gary,


                          your code is based on DirectShow, Windows Media Player nowadays implements a newer technology. Maybe there are tools for .mov files on board for this new technology - afaik there aren´t for Directshow. IIRC it´s not only about a codec, you need additional "filters" for playing .mov files in Windows with Directshow. There are a lot of programs, which might install these additional things for DirectShow under the hood (VLC, Media Player Classic, IrfanView, etc.)


                          JK

                          Comment

                          Working...
                          X