Page 1 of 1

Trying to use LibVLC with PureBasic

Posted: Mon Nov 12, 2012 3:35 am
by ozzie
I'm trying to use the VideoLan LibVLC with PB and have got to the stage where videos play, but not on the window I have created but on a separate window. Having studied other PB forum postings on using LibVLC I have now built the following code which uses PB Prototypes etc:

Code: Select all

; file LibVLCTest3A.pb

EnableExplicit

PrototypeC.l PR_libvlc_new(argc, *argv)
PrototypeC.l PR_libvlc_media_player_new(*p_libvlc_instance)
PrototypeC.l PR_libvlc_media_new_path(*p_instance, *path)
PrototypeC.l PR_libvlc_media_player_play(*p_mi)
PrototypeC   PR_libvlc_media_player_stop(*p_mi)
PrototypeC   PR_libvlc_media_player_release(*p_mi)
PrototypeC   PR_libvlc_release(*p_instance)
PrototypeC   PR_libvlc_media_player_set_hwnd(*p_mi, *drawable)
PrototypeC   PR_libvlc_media_player_set_media(*p_mi, *p_md)
PrototypeC   PR_libvlc_media_release(*p_md)

Global libvlc_new.PR_libvlc_new
Global libvlc_media_player_new.PR_libvlc_media_player_new
Global libvlc_media_new_path.PR_libvlc_media_new_path
Global libvlc_media_player_play.PR_libvlc_media_player_play
Global libvlc_media_player_stop.PR_libvlc_media_player_stop
Global libvlc_media_player_release.PR_libvlc_media_player_release
Global libvlc_release.PR_libvlc_release
Global libvlc_media_player_set_hwnd.PR_libvlc_media_player_set_hwnd
Global libvlc_media_player_set_media.PR_libvlc_media_player_set_media
Global libvlc_media_release.PR_libvlc_media_release

Global giLibrary

;-
Procedure loadLibrary()
  Protected sLibrary.s
  
  sLibrary = GetEnvironmentVariable("programfiles")
  If (Right(sLibrary, 1) <> "\")
    sLibrary + "\"
  EndIf 
  sLibrary + "VideoLAN\VLC\libvlc.dll"
  If FileSize(sLibrary) < 0
    MessageRequester("LibVLCTest3", "Cannot find libvlc.dll" + Chr(10) + "sLibrary=" + sLibrary)
    End
  EndIf
  SetCurrentDirectory(GetPathPart(sLibrary))
  giLibrary = OpenLibrary(#PB_Any, sLibrary)
  If giLibrary
    Debug "library opened ok: " + sLibrary
    libvlc_new.PR_libvlc_new = GetFunction(giLibrary, "libvlc_new")
    libvlc_media_player_new.PR_libvlc_media_player_new = GetFunction(giLibrary, "libvlc_media_player_new")
    libvlc_media_new_path.PR_libvlc_media_new_path = GetFunction(giLibrary, "libvlc_media_new_path")
    libvlc_media_player_play.PR_libvlc_media_player_play = GetFunction(giLibrary, "libvlc_media_player_play")
    libvlc_media_player_stop.PR_libvlc_media_player_stop = GetFunction(giLibrary, "libvlc_media_player_stop")
    libvlc_media_player_release.PR_libvlc_media_player_release = GetFunction(giLibrary, "libvlc_media_player_release")
    libvlc_release.PR_libvlc_release = GetFunction(giLibrary, "libvlc_release")
    libvlc_media_player_set_hwnd.PR_libvlc_media_player_set_hwnd = GetFunction(giLibrary, "libvlc_media_player_set_hwnd")
    libvlc_media_player_set_media.PR_libvlc_media_player_set_media = GetFunction(giLibrary, "libvlc_media_player_set_media")
    libvlc_media_release.PR_libvlc_media_release = GetFunction(giLibrary, "libvlc_media_release")
  Else
    Debug "OpenLibrary() failed: sLibrary=" + sLibrary
  EndIf
  
EndProcedure
;-
Procedure unloadLibrary()
  If giLibrary
    CloseLibrary(giLibrary)
    giLibrary = 0
  EndIf
EndProcedure
;-
Procedure mainProc()
  Protected Dim vlc_args.s(0)
  Protected *inst ; libvlc instance
  Protected *m    ; media path
  Protected *mp   ; media player
  Protected sPathName.s, sFileName.s
  Protected lDrawable.l
  Protected lResult.l
  
  If OpenWindow(0, 0, 0, 320,200, "", #PB_Window_SystemMenu|#PB_Window_SizeGadget|#PB_Window_MaximizeGadget|#PB_Window_MinimizeGadget)
    SetWindowColor(0, RGB(0,0,0))
    
    *inst = libvlc_new(0, @vlc_args())
    Debug "[libvlc_new] *inst=" + Str(*inst)
    
    ;/ Create a media player playing environment
    *mp = libvlc_media_player_new(*inst)
    Debug "[libvlc_media_player_new] *mp=" + Str(*mp)
    
    ;/ Create a new item
    sPathName = GetHomeDirectory() + "Videos\"
    Debug "sPathName=" + sPathName
    sFileName = OpenFileRequester("Select a Video File", sPathName, "Video Files | *.avi;*.mov;*.wmv;*.mp4", 0)
    If Len(sFileName) > 0
      
      *m = libvlc_media_new_path(*inst, @sFileName)
      Debug "[libvlc_media_new_path] *m=" + Str(*m)
      libvlc_media_player_set_media(*mp, *m)
      Debug "[libvlc_media_player_set_media]"
      
      libvlc_media_release(*m)
      Debug "[libvlc_media_release]"
      
      ;/ set output window
      lDrawable = WindowID(0)
      libvlc_media_player_set_hwnd(*mp, @lDrawable)
      Debug "[libvlc_media_player_set_hwnd(" + Str(*mp) + ", " + Str(@lDrawable) + ")]"
      
      ;/ play the media_player
      lResult = libvlc_media_player_play(*mp)
      Debug "[libvlc_media_player_play] returned " + Str(lResult)
      
      Delay(15000) ;/ Let it play for 15 seconds
      
      ;/ Stop playing
      Debug "calling libvlc_media_player_stop(*mp)"
      libvlc_media_player_stop(*mp)
      Debug "[libvlc_media_player_stop]"
      
    EndIf
    
    libvlc_media_player_release(*mp)
    Debug "[libvlc_media_player_release]"
    libvlc_release(*inst)
    Debug "[libvlc_release]"
    
    CloseWindow(0)
  EndIf
EndProcedure
;-
Debug "start of run"
loadLibrary()
If giLibrary
  mainProc()
EndIf
unloadLibrary()
Debug "end of run"

End
I presume the issue seems to be in this part of the code:

Code: Select all

      ;/ set output window
      lDrawable = WindowID(0)
      libvlc_media_player_set_hwnd(*mp, @lDrawable)
Here's the specification for this function: libvlc_media_player_set_hwnd.

I've tried reposition the function call, placing it immediately after libvlc_media_player_new, but that gave me the same result. I also tried changing @lDrawable to lDrawable but that resulted in the video not playing at all, and then hanging in the call to libvlc_media_player_stop.

Any ideas as to what I need to do to get the videos to playing on my PB Window 0?

I have the latest VideoLan installed, version 2.0.4, and am using PB 5.00 (x86) under Windows 7 64 bit (but obviously running as a 32-bit application). I get the same 'separate window' result with all video formats I've tried - avi, wmv and mp4.

Re: Trying to use LibVLC with PureBasic

Posted: Mon Nov 12, 2012 3:44 am
by idle
I'm not on windows but it says on the doc page

If LibVLC was built without Win32/Win64 API output support, then this has no effects.

do you know if that's the case for the version you've got?

Re: Trying to use LibVLC with PureBasic

Posted: Mon Nov 12, 2012 5:12 am
by ozzie
Thanks for the reply, idle. I'm not actually sure what the Win32/Win64 API Support comment means, but what I assume is that since LibVLC is available for Mac as well as Windows then this qualification is included to imply this function is only available in the Windows version of LibVLC. For example, for X Windows they provide libvlc_media_player_set_xwindow. So I'm assuming that libvlc.dll and libvlccore.dll were built with Win32/Win64 API support. Don't know if there's any way to check this, because I'm using the supplied dll's so I haven't built LibVLC myself.

Re: Trying to use LibVLC with PureBasic

Posted: Mon Nov 12, 2012 7:02 am
by idle
looking through the configure options the lib should be built with the support for embedding in a window by default, so don't know.

If you get desperate you could also try to build vlc but you might need a day to do it, by the time you've got all the stuff you need, and I expect
a couple of hours of compiling, there would go your day!
http://wiki.videolan.org/Win32CompileMSYS