using System; using System.Collections.Generic; using System.Runtime.InteropServices; using LibVLCSharp.Shared.Helpers; using LibVLCSharp.Shared.Structures; namespace LibVLCSharp.Shared { /// /// The MediaPlayer type is used to control playback, set renderers, provide events and much more /// public class MediaPlayer : Internal { readonly struct Native { [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_new")] internal static extern IntPtr LibVLCMediaPlayerNew(IntPtr libvlc); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_release")] internal static extern void LibVLCMediaPlayerRelease(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_new_from_media")] internal static extern IntPtr LibVLCMediaPlayerNewFromMedia(IntPtr media); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_media")] internal static extern void LibVLCMediaPlayerSetMedia(IntPtr mediaPlayer, IntPtr media); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_media")] internal static extern IntPtr LibVLCMediaPlayerGetMedia(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_event_manager")] internal static extern IntPtr LibVLCMediaPlayerEventManager(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_is_playing")] internal static extern int LibVLCMediaPlayerIsPlaying(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_play")] internal static extern int LibVLCMediaPlayerPlay(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_pause")] internal static extern void LibVLCMediaPlayerSetPause(IntPtr mediaPlayer, bool pause); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_pause")] internal static extern void LibVLCMediaPlayerPause(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_stop")] internal static extern void LibVLCMediaPlayerStop(IntPtr mediaPlayer); #if APPLE || NETFRAMEWORK || NETSTANDARD [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_nsobject")] internal static extern void LibVLCMediaPlayerSetNsobject(IntPtr mediaPlayer, IntPtr drawable); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_nsobject")] internal static extern IntPtr LibVLCMediaPlayerGetNsobject(IntPtr mediaPlayer); #endif #if NETFRAMEWORK || NETSTANDARD [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_xwindow")] internal static extern void LibVLCMediaPlayerSetXwindow(IntPtr mediaPlayer, uint drawable); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_xwindow")] internal static extern uint LibVLCMediaPlayerGetXwindow(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_hwnd")] internal static extern void LibVLCMediaPlayerSetHwnd(IntPtr mediaPlayer, IntPtr drawable); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_hwnd")] internal static extern IntPtr LibVLCMediaPlayerGetHwnd(IntPtr mediaPlayer); #endif [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_length")] internal static extern long LibVLCMediaPlayerGetLength(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_time")] internal static extern long LibVLCMediaPlayerGetTime(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_time")] internal static extern void LibVLCMediaPlayerSetTime(IntPtr mediaPlayer, long time); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_position")] internal static extern float LibVLCMediaPlayerGetPosition(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_position")] internal static extern void LibVLCMediaPlayerSetPosition(IntPtr mediaPlayer, float position); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_chapter")] internal static extern void LibVLCMediaPlayerSetChapter(IntPtr mediaPlayer, int chapter); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_chapter")] internal static extern int LibVLCMediaPlayerGetChapter(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_chapter_count")] internal static extern int LibVLCMediaPlayerGetChapterCount(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_will_play")] internal static extern int LibVLCMediaPlayerWillPlay(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_chapter_count_for_title")] internal static extern int LibVLCMediaPlayerGetChapterCountForTitle(IntPtr mediaPlayer, int title); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_title")] internal static extern void LibVLCMediaPlayerSetTitle(IntPtr mediaPlayer, int title); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_title")] internal static extern int LibVLCMediaPlayerGetTitle(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_title_count")] internal static extern int LibVLCMediaPlayerGetTitleCount(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_previous_chapter")] internal static extern void LibVLCMediaPlayerPreviousChapter(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_next_chapter")] internal static extern void LibVLCMediaPlayerNextChapter(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_rate")] internal static extern float LibVLCMediaPlayerGetRate(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_rate")] internal static extern int LibVLCMediaPlayerSetRate(IntPtr mediaPlayer, float rate); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_state")] internal static extern VLCState LibVLCMediaPlayerGetState(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_fps")] internal static extern float LibVLCMediaPlayerGetFps(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_has_vout")] internal static extern uint LibVLCMediaPlayerHasVout(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_is_seekable")] internal static extern int LibVLCMediaPlayerIsSeekable(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_can_pause")] internal static extern int LibVLCMediaPlayerCanPause(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_program_scrambled")] internal static extern int LibVLCMediaPlayerProgramScrambled(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_next_frame")] internal static extern void LibVLCMediaPlayerNextFrame(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_navigate")] internal static extern void LibVLCMediaPlayerNavigate(IntPtr mediaPlayer, uint navigate); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_video_title_display")] internal static extern void LibVLCMediaPlayerSetVideoTitleDisplay(IntPtr mediaPlayer, Position position, uint timeout); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_toggle_fullscreen")] internal static extern void LibVLCToggleFullscreen(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_set_fullscreen")] internal static extern void LibVLCSetFullscreen(IntPtr mediaPlayer, int fullscreen); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_get_fullscreen")] internal static extern int LibVLCGetFullscreen(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_toggle_teletext")] internal static extern void LibVLCToggleTeletext(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_equalizer")] internal static extern int LibVLCMediaPlayerSetEqualizer(IntPtr mediaPlayer, IntPtr equalizer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_set_callbacks")] internal static extern void LibVLCAudioSetCallbacks(IntPtr mediaPlayer, LibVLCAudioPlayCb play, LibVLCAudioPauseCb? pause, LibVLCAudioResumeCb? resume, LibVLCAudioFlushCb? flush, LibVLCAudioDrainCb? drain, IntPtr opaque); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_set_volume_callback")] internal static extern void LibVLCAudioSetVolumeCallback(IntPtr mediaPlayer, LibVLCVolumeCb? volumeCallback); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_set_format_callbacks")] internal static extern void LibVLCAudioSetFormatCallbacks(IntPtr mediaPlayer, LibVLCAudioSetupCb setup, LibVLCAudioCleanupCb? cleanup); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_set_format")] internal static extern void LibVLCAudioSetFormat(IntPtr mediaPlayer, IntPtr format, uint rate, uint channels); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_output_device_enum")] internal static extern IntPtr LibVLCAudioOutputDeviceEnum(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_output_device_set")] internal static extern void LibVLCAudioOutputDeviceSet(IntPtr mediaPlayer, IntPtr module, IntPtr deviceId); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_output_device_get")] internal static extern IntPtr LibVLCAudioOutputDeviceGet(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_output_set")] internal static extern int LibVLCAudioOutputSet(IntPtr mediaPlayer, IntPtr name); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_toggle_mute")] internal static extern void LibVLCAudioToggleMute(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_get_mute")] internal static extern int LibVLCAudioGetMute(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_set_mute")] internal static extern void LibVLCAudioSetMute(IntPtr mediaPlayer, int status); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_get_volume")] internal static extern int LibVLCAudioGetVolume(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_set_volume")] internal static extern int LibVLCAudioSetVolume(IntPtr mediaPlayer, int volume); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_get_track_count")] internal static extern int LibVLCAudioGetTrackCount(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_get_track_description")] internal static extern IntPtr LibVLCAudioGetTrackDescription(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_get_track")] internal static extern int LibVLCAudioGetTrack(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_set_track")] internal static extern int LibVLCAudioSetTrack(IntPtr mediaPlayer, int track); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_get_channel")] internal static extern AudioOutputChannel LibVLCAudioGetChannel(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_set_channel")] internal static extern int LibVLCAudioSetChannel(IntPtr mediaPlayer, AudioOutputChannel channel); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_get_delay")] internal static extern long LibVLCAudioGetDelay(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_set_delay")] internal static extern int LibVLCAudioSetDelay(IntPtr mediaPlayer, long delay); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_callbacks")] internal static extern void LibVLCVideoSetCallbacks(IntPtr mediaPlayer, LibVLCVideoLockCb lockCallback, LibVLCVideoUnlockCb? unlock, LibVLCVideoDisplayCb? display, IntPtr opaque); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_format")] internal static extern void LibVLCVideoSetFormat(IntPtr mediaPlayer, IntPtr chroma, uint width, uint height, uint pitch); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_format_callbacks")] internal static extern void LibVLCVideoSetFormatCallbacks(IntPtr mediaPlayer, LibVLCVideoFormatCb setup, LibVLCVideoCleanupCb? cleanup); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_key_input")] internal static extern void LibVLCVideoSetKeyInput(IntPtr mediaPlayer, int enable); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_mouse_input")] internal static extern void LibVLCVideoSetMouseInput(IntPtr mediaPlayer, int enable); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_size")] internal static extern int LibVLCVideoGetSize(IntPtr mediaPlayer, uint num, ref uint px, ref uint py); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_cursor")] internal static extern int LibVLCVideoGetCursor(IntPtr mediaPlayer, uint num, ref int px, ref int py); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_scale")] internal static extern float LibVLCVideoGetScale(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_scale")] internal static extern void LibVLCVideoSetScale(IntPtr mediaPlayer, float factor); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_aspect_ratio")] internal static extern IntPtr LibVLCVideoGetAspectRatio(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_aspect_ratio")] internal static extern void LibVLCVideoSetAspectRatio(IntPtr mediaPlayer, IntPtr aspect); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_spu")] internal static extern int LibVLCVideoGetSpu(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_spu_count")] internal static extern int LibVLCVideoGetSpuCount(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_spu_description")] internal static extern IntPtr LibVLCVideoGetSpuDescription(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_spu")] internal static extern int LibVLCVideoSetSpu(IntPtr mediaPlayer, int spu); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_spu_delay")] internal static extern long LibVLCVideoGetSpuDelay(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_spu_delay")] internal static extern int LibVLCVideoSetSpuDelay(IntPtr mediaPlayer, long delay); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_title_description")] internal static extern IntPtr LibVLCVideoGetTitleDescription(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_full_title_descriptions")] internal static extern int LibVLCMediaPlayerGetFullTitleDescriptions(IntPtr mediaPlayer, IntPtr titles); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_chapter_description")] internal static extern IntPtr LibVLCVideoGetChapterDescription(IntPtr mediaPlayer, int title); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_title_descriptions_release")] internal static extern void LibVLCTitleDescriptionsRelease(IntPtr titles, uint count); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_full_chapter_descriptions")] internal static extern int LibVLCMediaPlayerGetFullChapterDescriptions(IntPtr mediaPlayer, int titleIndex, out IntPtr chapters); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_chapter_descriptions_release")] internal static extern void LibVLCChapterDescriptionsRelease(IntPtr chapters, uint count); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_crop_geometry")] internal static extern IntPtr LibVLCVideoGetCropGeometry(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_crop_geometry")] internal static extern void LibVLCVideoSetCropGeometry(IntPtr mediaPlayer, IntPtr geometry); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_teletext")] internal static extern int LibVLCVideoGetTeletext(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_teletext")] internal static extern void LibVLCVideoSetTeletext(IntPtr mediaPlayer, int page); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_track_count")] internal static extern int LibVLCVideoGetTrackCount(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_track_description")] internal static extern IntPtr LibVLCVideoGetTrackDescription(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_track")] internal static extern int LibVLCVideoGetTrack(IntPtr mediaPlayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_track")] internal static extern int LibVLCVideoSetTrack(IntPtr mediaPlayer, int track); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_take_snapshot")] internal static extern int LibVLCVideoTakeSnapshot(IntPtr mediaPlayer, uint num, IntPtr filepath, uint width, uint height); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_deinterlace")] internal static extern void LibVLCVideoSetDeinterlace(IntPtr mediaPlayer, IntPtr mode); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_marquee_int")] internal static extern int LibVLCVideoGetMarqueeInt(IntPtr mediaPlayer, VideoMarqueeOption option); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_marquee_string")] internal static extern IntPtr LibVLCVideoGetMarqueeString(IntPtr mediaPlayer, VideoMarqueeOption option); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_marquee_int")] internal static extern void LibVLCVideoSetMarqueeInt(IntPtr mediaPlayer, VideoMarqueeOption option, int marqueeValue); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_marquee_string")] internal static extern void LibVLCVideoSetMarqueeString(IntPtr mediaPlayer, VideoMarqueeOption option, IntPtr marqueeValue); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_logo_int")] internal static extern int LibVLCVideoGetLogoInt(IntPtr mediaPlayer, VideoLogoOption option); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_logo_int")] internal static extern void LibVLCVideoSetLogoInt(IntPtr mediaPlayer, VideoLogoOption option, int value); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_logo_string")] internal static extern void LibVLCVideoSetLogoString(IntPtr mediaPlayer, VideoLogoOption option, IntPtr logoOptionValue); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_adjust_int")] internal static extern int LibVLCVideoGetAdjustInt(IntPtr mediaPlayer, VideoAdjustOption option); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_adjust_int")] internal static extern void LibVLCVideoSetAdjustInt(IntPtr mediaPlayer, VideoAdjustOption option, int value); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_get_adjust_float")] internal static extern float LibVLCVideoGetAdjustFloat(IntPtr mediaPlayer, VideoAdjustOption option); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_set_adjust_float")] internal static extern void LibVLCVideoSetAdjustFloat(IntPtr mediaPlayer, VideoAdjustOption option, float value); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_add_slave")] internal static extern int LibVLCMediaPlayerAddSlave(IntPtr mediaPlayer, MediaSlaveType mediaSlaveType, IntPtr uri, bool selectWhenloaded); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_new_viewpoint")] internal static extern IntPtr LibVLCVideoNewViewpoint(); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_video_update_viewpoint")] internal static extern int LibVLCVideoUpdateViewpoint(IntPtr mediaPlayer, IntPtr viewpoint, bool absolute); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_track_description_list_release")] internal static extern void LibVLCTrackDescriptionListRelease(IntPtr trackDescription); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_audio_output_device_list_release")] internal static extern void LibVLCAudioOutputDeviceListRelease(IntPtr list); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_renderer")] internal static extern int LibVLCMediaPlayerSetRenderer(IntPtr mediaplayer, IntPtr renderItem); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_get_role")] internal static extern MediaPlayerRole LibVLCMediaPlayerGetRole(IntPtr mediaplayer); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_role")] internal static extern int LibVLCMediaPlayerSetRole(IntPtr mediaplayer, MediaPlayerRole role); [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_retain")] internal static extern void LibVLCMediaPlayerRetain(IntPtr mediaplayer); #if ANDROID [DllImport(Constants.LibraryName, CallingConvention = CallingConvention.Cdecl, EntryPoint = "libvlc_media_player_set_android_context")] internal static extern void LibVLCMediaPlayerSetAndroidContext(IntPtr mediaPlayer, IntPtr aWindow); #endif } MediaPlayerEventManager? _eventManager; /// /// The GCHandle to be passed to callbacks as userData /// GCHandle _gcHandle; /// Create an empty Media Player object /// /// the libvlc instance in which the Media Player /// should be created. /// /// a new media player object, or NULL on error. public MediaPlayer(LibVLC libVLC) : base(() => Native.LibVLCMediaPlayerNew(libVLC.NativeReference), Native.LibVLCMediaPlayerRelease) { _gcHandle = GCHandle.Alloc(this); } /// Create a Media Player object from a Media /// /// the media. Afterwards the p_md can be safely /// destroyed. /// /// a new media player object, or NULL on error. public MediaPlayer(Media media) : base(() => Native.LibVLCMediaPlayerNewFromMedia(media.NativeReference), Native.LibVLCMediaPlayerRelease) { _gcHandle = GCHandle.Alloc(this); } /// /// Get the media used by the media_player. /// Set the media that will be used by the media_player. /// If any, previous md will be released. /// Note: It is safe to release the Media on the C# side after it's been set on the MediaPlayer successfully /// public Media? Media { get { var mediaPtr = Native.LibVLCMediaPlayerGetMedia(NativeReference); return mediaPtr == IntPtr.Zero ? null : new Media(mediaPtr); } set => Native.LibVLCMediaPlayerSetMedia(NativeReference, value?.NativeReference ?? IntPtr.Zero); } /// /// return true if the media player is playing, false otherwise /// public bool IsPlaying => Native.LibVLCMediaPlayerIsPlaying(NativeReference) != 0; /// /// Start playback with Media that is set /// If playback was already started, this method has no effect /// /// true if successful public bool Play() { Media?.AddOption(Configuration); return Native.LibVLCMediaPlayerPlay(NativeReference) == 0; } /// /// Set media and start playback /// /// /// true if successful public bool Play(Media media) { Media = media; return Play(); } /// /// Pause or resume (no effect if there is no media). /// version LibVLC 1.1.1 or later /// /// play/resume if true, pause if false public void SetPause(bool pause) => Native.LibVLCMediaPlayerSetPause(NativeReference, pause); /// /// Toggle pause (no effect if there is no media) /// public void Pause() => Native.LibVLCMediaPlayerPause(NativeReference); /// /// Stop the playback (no effect if there is no media) /// warning: /// This is synchronous, and will block until all VLC threads have been joined. /// Calling this from a VLC callback is a bound to cause a deadlock. /// public void Stop() => Native.LibVLCMediaPlayerStop(NativeReference); #if APPLE || NETFRAMEWORK || NETSTANDARD /// /// Get the NSView handler previously set /// return the NSView handler or 0 if none where set /// /// /// Set the NSView handler where the media player should render its video output. /// Use the vout called "macosx". /// /// The drawable is an NSObject that follow the /// VLCOpenGLVideoViewEmbedding protocol: VLCOpenGLVideoViewEmbedding NSObject /// Or it can be an NSView object. /// If you want to use it along with Qt4 see the QMacCocoaViewContainer. /// Then the following code should work: { NSView *video = [[NSView /// alloc] init]; QMacCocoaViewContainer *container = new /// QMacCocoaViewContainer(video, parent); /// libvlc_media_player_set_nsobject(mp, video); [video release]; } /// You can find a live example in VLCVideoView in VLCKit.framework. /// public IntPtr NsObject { get => Native.LibVLCMediaPlayerGetNsobject(NativeReference); set => Native.LibVLCMediaPlayerSetNsobject(NativeReference, value); } #endif #if NETFRAMEWORK || NETSTANDARD /// /// Set an X Window System drawable where the media player should render its video output. /// The call takes effect when the playback starts. If it is already started, it might need to be stopped before changes apply. /// If LibVLC was built without X11 output support, then this function has no effects. /// By default, LibVLC will capture input events on the video rendering area. /// Use libvlc_video_set_mouse_input() and libvlc_video_set_key_input() to disable that and deliver events to the parent window / to the application instead. /// By design, the X11 protocol delivers input events to only one recipient. /// /// Warning: /// The application must call the XInitThreads() function from Xlib before libvlc_new(), and before any call to XOpenDisplay() directly /// or via any other library.Failure to call XInitThreads() will seriously impede LibVLC performance. /// Calling XOpenDisplay() before XInitThreads() will eventually crash the process. That is a limitation of Xlib. /// uint: X11 window ID /// public uint XWindow { get => Native.LibVLCMediaPlayerGetXwindow(NativeReference); set => Native.LibVLCMediaPlayerSetXwindow(NativeReference, value); } /// /// Set a Win32/Win64 API window handle (HWND) where the media player /// should render its video output. If LibVLC was built without /// Win32/Win64 API output support, then this has no effects. /// /// Get the Windows API window handle (HWND) previously set /// public IntPtr Hwnd { get => Native.LibVLCMediaPlayerGetHwnd(NativeReference); set => Native.LibVLCMediaPlayerSetHwnd(NativeReference, value); } #endif /// /// The movie length (in ms), or -1 if there is no media. /// public long Length => Native.LibVLCMediaPlayerGetLength(NativeReference); /// /// Set the movie time (in ms). This has no effect if no media is being /// played. Not all formats and protocols support this. /// /// Get the movie time (in ms), or -1 if there is no media. /// public long Time { get => Native.LibVLCMediaPlayerGetTime(NativeReference); set => Native.LibVLCMediaPlayerSetTime(NativeReference, value); } /// /// Set movie position as percentage between 0.0 and 1.0. This has no /// effect if playback is not enabled. This might not work depending on /// the underlying input format and protocol. /// /// Get movie position as percentage between 0.0 and 1.0. /// public float Position { get => Native.LibVLCMediaPlayerGetPosition(NativeReference); set => Native.LibVLCMediaPlayerSetPosition(NativeReference, value); } /// /// Set movie chapter (if applicable). /// /// Get the movie chapter number currently playing, or -1 if there is no media. /// public int Chapter { get => Native.LibVLCMediaPlayerGetChapter(NativeReference); set => Native.LibVLCMediaPlayerSetChapter(NativeReference, value); } /// /// Get the number of chapters in movie, or -1. /// public int ChapterCount => Native.LibVLCMediaPlayerGetChapterCount(NativeReference); /// /// True if the player is able to play /// public bool WillPlay => Native.LibVLCMediaPlayerWillPlay(NativeReference) != 0; /// /// Get the number of chapters in title, or -1 /// /// /// public int ChapterCountForTitle(int title) => Native.LibVLCMediaPlayerGetChapterCountForTitle(NativeReference, title); /// /// Set movie title number to play /// /// Get movie title number currently playing, or -1 /// public int Title { get => Native.LibVLCMediaPlayerGetTitle(NativeReference); set => Native.LibVLCMediaPlayerSetTitle(NativeReference, value); } /// /// The title number count, or -1 /// public int TitleCount => Native.LibVLCMediaPlayerGetTitleCount(NativeReference); /// /// Set previous chapter (if applicable) /// public void PreviousChapter() { Native.LibVLCMediaPlayerPreviousChapter(NativeReference); } /// /// Set next chapter (if applicable) /// public void NextChapter() { Native.LibVLCMediaPlayerNextChapter(NativeReference); } /// /// Get the requested movie play rate. /// warning /// /// Depending on the underlying media, the requested rate may be /// different from the real playback rate. /// public float Rate => Native.LibVLCMediaPlayerGetRate(NativeReference); /// /// Set movie play rate /// /// movie play rate to set /// /// return -1 if an error was detected, 0 otherwise (but even then, it /// might not actually work depending on the underlying media protocol) /// public int SetRate(float rate) { return Native.LibVLCMediaPlayerSetRate(NativeReference, rate); } /// /// Get the current state of the media player (playing, paused, ...) /// public VLCState State => Native.LibVLCMediaPlayerGetState(NativeReference); /// /// Get the frames per second (fps) for this playing movie, or 0 if unspecified /// public float Fps => Native.LibVLCMediaPlayerGetFps(NativeReference); /// /// Get the number of video outputs /// public uint VoutCount => Native.LibVLCMediaPlayerHasVout(NativeReference); /// /// True if the media player can seek /// public bool IsSeekable => Native.LibVLCMediaPlayerIsSeekable(NativeReference) != 0; /// /// True if the media player can pause /// public bool CanPause => Native.LibVLCMediaPlayerCanPause(NativeReference) != 0; /// /// True if the current program is scrambled /// /// LibVLC 2.2.0 or later /// public bool ProgramScambled => Native.LibVLCMediaPlayerProgramScrambled(NativeReference) != 0; /// /// Display the next frame (if supported) /// public void NextFrame() { Native.LibVLCMediaPlayerNextFrame(NativeReference); } /// /// Navigate through DVD Menu /// /// the Navigation mode /// LibVLC 2.0.0 or later public void Navigate(uint navigate) { Native.LibVLCMediaPlayerNavigate(NativeReference, navigate); } /// /// Set if, and how, the video title will be shown when media is played. /// /// position at which to display the title, or libvlc_position_disable to prevent the title from being displayed /// title display timeout in milliseconds (ignored if libvlc_position_disable) /// LibVLC 2.1.0 or later public void SetVideoTitleDisplay(Position position, uint timeout) { Native.LibVLCMediaPlayerSetVideoTitleDisplay(NativeReference, position, timeout); } /// /// Toggle fullscreen status on non-embedded video outputs. /// /// warning: The same limitations applies to this function as to MediaPlayer::setFullscreen() /// public void ToggleFullscreen() { Native.LibVLCToggleFullscreen(NativeReference); } /// /// Enable or disable fullscreen. /// Warning, TL;DR version : Unless you know what you're doing, don't use this. /// Put your VideoView inside a fullscreen control instead, refer to your platform documentation. /// /// Warning, long version : /// With most window managers, only a top-level windows can be in full-screen mode. /// Hence, this function will not operate properly if libvlc_media_player_set_xwindow() was used to embed the video in a non-top-level window. /// In that case, the embedding window must be reparented to the root window before fullscreen mode is enabled. /// You will want to reparent it back to its normal parent when disabling fullscreen. /// /// return the fullscreen status (boolean) /// public bool Fullscreen { get => Native.LibVLCGetFullscreen(NativeReference) != 0; set => Native.LibVLCSetFullscreen(NativeReference, value ? 1 : 0); } /// /// Toggle teletext transparent status on video output. /// public void ToggleTeletext() => Native.LibVLCToggleTeletext(NativeReference); /// /// Apply new equalizer settings to a media player. /// The equalizer is first created by invoking libvlc_audio_equalizer_new() or libvlc_audio_equalizer_new_from_preset(). /// It is possible to apply new equalizer settings to a media player whether the media player is currently playing media or not. /// Invoking this method will immediately apply the new equalizer settings to the audio output of the currently playing media if there is any. /// If there is no currently playing media, the new equalizer settings will be applied later if and when new media is played. /// Equalizer settings will automatically be applied to subsequently played media. /// To disable the equalizer for a media player invoke this method passing NULL for the p_equalizer parameter. /// The media player does not keep a reference to the supplied equalizer so it is safe for an application to release the equalizer reference /// any time after this method returns. /// /// opaque equalizer handle, or NULL to disable the equalizer for this media player /// LibVLC 2.2.0 or later /// true on success, false otherwise. public bool SetEqualizer(Equalizer equalizer) => Native.LibVLCMediaPlayerSetEqualizer(NativeReference, equalizer.NativeReference) == 0; /// /// unsetEqualizer disable equalizer for this media player /// /// true on success, false otherwise. public bool UnsetEqualizer() => Native.LibVLCMediaPlayerSetEqualizer(NativeReference, IntPtr.Zero) == 0; LibVLCAudioPlayCb? _audioPlayCb; LibVLCAudioPauseCb? _audioPauseCb; LibVLCAudioResumeCb? _audioResumeCb; LibVLCAudioFlushCb? _audioFlushCb; LibVLCAudioDrainCb? _audioDrainCb; IntPtr _audioUserData = IntPtr.Zero; /// /// Sets callbacks and private data for decoded audio. /// Use libvlc_audio_set_format() or libvlc_audio_set_format_callbacks() to configure the decoded audio format. /// Note: The audio callbacks override any other audio output mechanism. If the callbacks are set, LibVLC will not output audio in any way. /// /// callback to play audio samples (must not be NULL) /// callback to pause playback (or NULL to ignore) /// callback to resume playback (or NULL to ignore) /// callback to flush audio buffers (or NULL to ignore) /// callback to drain audio buffers (or NULL to ignore) public void SetAudioCallbacks(LibVLCAudioPlayCb playCb, LibVLCAudioPauseCb? pauseCb, LibVLCAudioResumeCb? resumeCb, LibVLCAudioFlushCb? flushCb, LibVLCAudioDrainCb? drainCb) { _audioPlayCb = playCb ?? throw new ArgumentNullException(nameof(playCb)); _audioPauseCb = pauseCb; _audioResumeCb = resumeCb; _audioFlushCb = flushCb; _audioDrainCb = drainCb; Native.LibVLCAudioSetCallbacks( NativeReference, AudioPlayCallbackHandle, (pauseCb == null) ? null : AudioPauseCallbackHandle, (resumeCb == null) ? null : AudioResumeCallbackHandle, (flushCb == null) ? null : AudioFlushCallbackHandle, (drainCb == null) ? null : AudioDrainCallbackHandle, GCHandle.ToIntPtr(_gcHandle)); } LibVLCVolumeCb? _audioVolumeCb; /// /// Set callbacks and private data for decoded audio. /// This only works in combination with libvlc_audio_set_callbacks(). /// Use libvlc_audio_set_format() or libvlc_audio_set_format_callbacks() to configure the decoded audio format. /// /// callback to apply audio volume, or NULL to apply volume in software public void SetVolumeCallback(LibVLCVolumeCb volumeCb) { _audioVolumeCb = volumeCb; Native.LibVLCAudioSetVolumeCallback(NativeReference, (volumeCb == null) ? null : AudioVolumeCallbackHandle); } LibVLCAudioSetupCb? _setupCb; LibVLCAudioCleanupCb? _cleanupCb; /// /// Sets decoded audio format via callbacks. /// This only works in combination with libvlc_audio_set_callbacks(). /// /// callback to select the audio format (cannot be NULL) /// callback to release any allocated resources (or NULL) public void SetAudioFormatCallback(LibVLCAudioSetupCb setupCb, LibVLCAudioCleanupCb cleanupCb) { _setupCb = setupCb ?? throw new ArgumentNullException(nameof(setupCb)); _cleanupCb = cleanupCb; Native.LibVLCAudioSetFormatCallbacks(NativeReference, AudioSetupCallbackHandle, (cleanupCb == null) ? null : AudioCleanupCallbackHandle); } /// /// Sets a fixed decoded audio format. /// This only works in combination with libvlc_audio_set_callbacks(), and is mutually exclusive with libvlc_audio_set_format_callbacks(). /// /// a four-characters string identifying the sample format (e.g. "S16N" or "FL32") /// sample rate (expressed in Hz) /// channels count public void SetAudioFormat(string format, uint rate, uint channels) { var formatUtf8 = format.ToUtf8(); MarshalUtils.PerformInteropAndFree(() => Native.LibVLCAudioSetFormat(NativeReference, formatUtf8, rate, channels), formatUtf8); } /// /// Selects an audio output module. /// Note: /// Any change will take effect only after playback is stopped and restarted. Audio output cannot be changed while playing. /// /// name of audio output, use psz_name of /// true if function succeeded, false on error public bool SetAudioOutput(string name) { var nameUtf8 = name.ToUtf8(); return MarshalUtils.PerformInteropAndFree(() => Native.LibVLCAudioOutputSet(NativeReference, nameUtf8), nameUtf8) == 0; } /// /// Get the current audio output device identifier. /// This complements /// warning The initial value for the current audio output device identifier /// may not be set or may be some unknown value.A LibVLC application should /// compare this value against the known device identifiers (e.g.those that /// were previously retrieved by a call to or /// ) to find the current audio output device. /// /// It is possible that the selected audio output device changes(an external /// change) without a call to .That may make this /// method unsuitable to use if a LibVLC application is attempting to track /// dynamic audio device changes as they happen. /// /// /// the current audio output device identifier, or NULL if no device is selected or in case of error. public string? OutputDevice => Native.LibVLCAudioOutputDeviceGet(NativeReference).FromUtf8(libvlcFree: true); /// /// Configures an explicit audio output device. /// If the module paramater is NULL, audio output will be moved to the device /// specified by the device identifier string immediately.This is the /// recommended usage. /// A list of adequate potential device strings can be obtained with /// /// However passing NULL is supported in LibVLC version 2.2.0 and later only; /// in earlier versions, this function would have no effects when the module /// parameter was NULL. /// If the module parameter is not NULL, the device parameter of the /// corresponding audio output, if it exists, will be set to the specified /// string. /// A list of adequate potential device strings can be obtained with /// /// /// device identifier string /// If NULL, current audio output module. if non-NULL, name of audio output module public void SetOutputDevice(string deviceId, string? module = null) { var deviceIdUtf8 = deviceId.ToUtf8(); var moduleUtf8 = module.ToUtf8(); MarshalUtils.PerformInteropAndFree(() => Native.LibVLCAudioOutputDeviceSet(NativeReference, moduleUtf8, deviceIdUtf8), moduleUtf8, deviceIdUtf8); } /// /// Gets a list of potential audio output devices /// Not all audio outputs support enumerating devices. The audio output may be functional even if the list is empty (NULL). /// The list may not be exhaustive. Some audio output devices in the list might not actually work in some circumstances. /// By default, it is recommended to not specify any explicit audio device. /// public AudioOutputDevice[] AudioOutputDeviceEnum => MarshalUtils.Retrieve(() => Native.LibVLCAudioOutputDeviceEnum(NativeReference), MarshalUtils.PtrToStructure, s => s.Build(), device => device.Next, Native.LibVLCAudioOutputDeviceListRelease); /// /// Toggle mute status. /// Warning /// Toggling mute atomically is not always possible: On some platforms, other processes can mute the VLC audio playback /// stream asynchronously. /// Thus, there is a small race condition where toggling will not work. /// See also the limitations of libvlc_audio_set_mute(). /// public void ToggleMute() => Native.LibVLCAudioToggleMute(NativeReference); /// /// Get current mute status. /// Set mute status. /// Warning /// This function does not always work. /// If there are no active audio playback stream, the mute status might not be available. /// If digital pass-through (S/PDIF, HDMI...) is in use, muting may be unapplicable. /// Also some audio output plugins do not support muting at all. /// Note /// To force silent playback, disable all audio tracks. This is more efficient and reliable than mute. /// public bool Mute { get => Native.LibVLCAudioGetMute(NativeReference) == 1; set => Native.LibVLCAudioSetMute(NativeReference, value ? 1 : 0); } /// /// Get/Set the volume in percents (0 = mute, 100 = 0dB) /// public int Volume { get => Native.LibVLCAudioGetVolume(NativeReference); set => Native.LibVLCAudioSetVolume(NativeReference, value); } /// /// Get the number of available audio tracks (int), or -1 if unavailable /// public int AudioTrackCount => Native.LibVLCAudioGetTrackCount(NativeReference); /// /// Retrive the audio track description /// public TrackDescription[] AudioTrackDescription => MarshalUtils.Retrieve(() => Native.LibVLCAudioGetTrackDescription(NativeReference), MarshalUtils.PtrToStructure, t => t.Build(), t => t.Next, Native.LibVLCTrackDescriptionListRelease); /// /// Get current audio track ID or -1 if no active input. /// public int AudioTrack => Native.LibVLCAudioGetTrack(NativeReference); /// /// Set current audio track. /// /// the track ID (i_id field from track description) /// 0 on success, -1 on error public bool SetAudioTrack(int trackIndex) => Native.LibVLCAudioSetTrack(NativeReference, trackIndex) == 0; /// /// Get current audio channel. /// public AudioOutputChannel Channel => Native.LibVLCAudioGetChannel(NativeReference); /// /// Set current audio channel. /// /// the audio channel /// public bool SetChannel(AudioOutputChannel channel) => Native.LibVLCAudioSetChannel(NativeReference, channel) == 0; /// /// Equals override based on the native instance reference /// /// the mediaplayer instance to compare this to /// public override bool Equals(object obj) { return obj is MediaPlayer player && EqualityComparer.Default.Equals(NativeReference, player.NativeReference); } /// /// Custom hascode implemenation for this MediaPlayer instance /// /// the hashcode for this MediaPlayer instance public override int GetHashCode() { return NativeReference.GetHashCode(); } /// /// Get current audio delay (microseconds). /// public long AudioDelay => Native.LibVLCAudioGetDelay(NativeReference); /// /// Set current audio delay. The audio delay will be reset to zero each /// time the media changes. /// /// the audio delay (microseconds) /// true on success, false on error public bool SetAudioDelay(long delay) => Native.LibVLCAudioSetDelay(NativeReference, delay) == 0; LibVLCVideoLockCb? _videoLockCb; LibVLCVideoUnlockCb? _videoUnlockCb; LibVLCVideoDisplayCb? _videoDisplayCb; /// /// Set callbacks and private data to render decoded video to a custom area in memory. /// Use libvlc_video_set_format() or libvlc_video_set_format_callbacks() to configure the decoded format. /// Warning /// Rendering video into custom memory buffers is considerably less efficient than rendering in a custom window as normal. /// For optimal perfomances, VLC media player renders into a custom window, and does not use this function and associated callbacks. /// It is highly recommended that other LibVLC-based application do likewise. /// To embed video in a window, use libvlc_media_player_set_xid() or equivalent depending on the operating system. /// If window embedding does not fit the application use case, then a custom LibVLC video output display plugin is required to maintain optimal video rendering performances. /// The following limitations affect performance: /// Hardware video decoding acceleration will either be disabled completely, or require(relatively slow) copy from video/DSP memory to main memory. /// Sub-pictures(subtitles, on-screen display, etc.) must be blent into the main picture by the CPU instead of the GPU. /// Depending on the video format, pixel format conversion, picture scaling, cropping and/or picture re-orientation, /// must be performed by the CPU instead of the GPU. /// Memory copying is required between LibVLC reference picture buffers and application buffers (between lock and unlock callbacks). /// /// callback to lock video memory (must not be NULL) /// callback to unlock video memory (or NULL if not needed) /// callback to display video (or NULL if not needed) public void SetVideoCallbacks(LibVLCVideoLockCb lockCb, LibVLCVideoUnlockCb? unlockCb, LibVLCVideoDisplayCb? displayCb) { _videoLockCb = lockCb ?? throw new ArgumentNullException(nameof(lockCb)); _videoUnlockCb = unlockCb; _videoDisplayCb = displayCb; Native.LibVLCVideoSetCallbacks(NativeReference, VideoLockCallbackHandle, (unlockCb == null)? null : VideoUnlockCallbackHandle, (displayCb == null)? null : VideoDisplayCallbackHandle, GCHandle.ToIntPtr(_gcHandle)); } /// /// Set decoded video chroma and dimensions. This only works in /// combination with MediaPlayer::setCallbacks() , and is mutually exclusive /// with MediaPlayer::setFormatCallbacks() /// /// a four-characters string identifying the chroma (e.g."RV32" or "YUYV") /// pixel width /// pixel height /// line pitch (in bytes) public void SetVideoFormat(string chroma, uint width, uint height, uint pitch) { var chromaUtf8 = chroma.ToUtf8(); MarshalUtils.PerformInteropAndFree(() => Native.LibVLCVideoSetFormat(NativeReference, chromaUtf8, width, height, pitch), chromaUtf8); } LibVLCVideoFormatCb? _videoFormatCb; LibVLCVideoCleanupCb? _videoCleanupCb; IntPtr _videoUserData = IntPtr.Zero; /// /// Set decoded video chroma and dimensions. /// This only works in combination with libvlc_video_set_callbacks(). /// /// callback to select the video format (cannot be NULL) /// callback to release any allocated resources (or NULL) public void SetVideoFormatCallbacks(LibVLCVideoFormatCb formatCb, LibVLCVideoCleanupCb? cleanupCb) { _videoFormatCb = formatCb ?? throw new ArgumentNullException(nameof(formatCb)); _videoCleanupCb = cleanupCb; Native.LibVLCVideoSetFormatCallbacks(NativeReference, VideoFormatCallbackHandle, (cleanupCb == null)? null : VideoCleanupCallbackHandle); } /// /// Enable or disable key press events handling, according to the LibVLC hotkeys configuration. /// By default and for historical reasons, keyboard events are handled by the LibVLC video widget. /// Note /// On X11, there can be only one subscriber for key press and mouse click events per window. /// If your application has subscribed to those events for the X window ID of the video widget, /// then LibVLC will not be able to handle key presses and mouse clicks in any case. /// Warning /// This function is only implemented for X11 and Win32 at the moment. /// true to handle key press events, false to ignore them. /// public bool EnableKeyInput { set => Native.LibVLCVideoSetKeyInput(NativeReference, value ? 1 : 0); } /// /// Enable or disable mouse click events handling. /// By default, those events are handled. This is needed for DVD menus to work, as well as a few video filters such as "puzzle". /// Warning /// This function is only implemented for X11 and Win32 at the moment. /// true to handle mouse click events, false to ignore them. /// public bool EnableMouseInput { set => Native.LibVLCVideoSetMouseInput(NativeReference, value ? 1 : 0); } /// /// Get the pixel dimensions of a video. /// /// number of the video (starting from, and most commonly 0) /// pointer to get the pixel width [OUT] /// pointer to get the pixel height [OUT] /// public bool Size(uint num, ref uint px, ref uint py) { return Native.LibVLCVideoGetSize(NativeReference, num, ref px, ref py) == 0; } /// /// Get the mouse pointer coordinates over a video. /// Coordinates are expressed in terms of the decoded video resolution, not in terms of pixels on the screen/viewport /// (to get the latter, you can query your windowing system directly). /// Either of the coordinates may be negative or larger than the corresponding dimension of the video, /// if the cursor is outside the rendering area. /// Warning /// The coordinates may be out-of-date if the pointer is not located on the video rendering area. /// LibVLC does not track the pointer if it is outside of the video widget. /// Note /// LibVLC does not support multiple pointers(it does of course support multiple input devices sharing the same pointer) at the moment. /// /// number of the video (starting from, and most commonly 0) /// pointer to get the abscissa [OUT] /// pointer to get the ordinate [OUT] /// true on success, false on failure public bool Cursor(uint num, ref int px, ref int py) { return Native.LibVLCVideoGetCursor(NativeReference, num, ref px, ref py) == 0; } /// /// Get/Set the current video scaling factor. See also MediaPlayer::setScale() . /// That is the ratio of the number of /// pixels on screen to the number of pixels in the original decoded video /// in each dimension.Zero is a special value; it will adjust the video /// to the output window/drawable(in windowed mode) or the entire screen. /// Note that not all video outputs support scaling. /// public float Scale { get => Native.LibVLCVideoGetScale(NativeReference); set => Native.LibVLCVideoSetScale(NativeReference, value); } /// /// Get/set current video aspect ratio. /// Set to null to reset to default /// Invalid aspect ratios are ignored. /// public string? AspectRatio { get => Native.LibVLCVideoGetAspectRatio(NativeReference).FromUtf8(libvlcFree: true); set { var aspectRatioUtf8 = value.ToUtf8(); MarshalUtils.PerformInteropAndFree(() => Native.LibVLCVideoSetAspectRatio(NativeReference, aspectRatioUtf8), aspectRatioUtf8); } } /// /// The current video subtitle track /// public int Spu => Native.LibVLCVideoGetSpu(NativeReference); /// /// Set Spu (subtitle) /// /// Video subtitle track to select (id from track description) /// true on success, false otherwise public bool SetSpu(int spu) => Native.LibVLCVideoSetSpu(NativeReference, spu) == 0; /// /// Get the number of available video subtitles. /// public int SpuCount => Native.LibVLCVideoGetSpuCount(NativeReference); /// /// Retrieve SpuDescription in a TrackDescription struct /// public TrackDescription[] SpuDescription => MarshalUtils.Retrieve(() => Native.LibVLCVideoGetSpuDescription(NativeReference), MarshalUtils.PtrToStructure, t => t.Build(), t => t.Next, Native.LibVLCTrackDescriptionListRelease); /// /// Get the current subtitle delay. /// public long SpuDelay => Native.LibVLCVideoGetSpuDelay(NativeReference); /// /// Set the subtitle delay. /// This affects the timing of when the subtitle will be displayed. /// Positive values result in subtitles being displayed later, while negative values will result in subtitles being displayed earlier. /// The subtitle delay will be reset to zero each time the media changes. /// /// time (in microseconds) the display of subtitles should be delayed /// true if successful, false otherwise public bool SetSpuDelay(long delay) => Native.LibVLCVideoSetSpuDelay(NativeReference, delay) == 0; /// /// Get the description of available titles. /// public TrackDescription[] TitleDescription => MarshalUtils.Retrieve(() => Native.LibVLCVideoGetTitleDescription(NativeReference), MarshalUtils.PtrToStructure, t => t.Build(), t => t.Next, Native.LibVLCTrackDescriptionListRelease); /// /// Get the full description of available chapters. /// /// Index of the title to query for chapters (uses current title if set to -1) /// Array of chapter descriptions. public ChapterDescription[] FullChapterDescriptions(int titleIndex = -1) => MarshalUtils.Retrieve(NativeReference, (IntPtr nativeRef, out IntPtr array) => { var count = Native.LibVLCMediaPlayerGetFullChapterDescriptions(nativeRef, titleIndex, out array); // the number of chapters (-1 on error) return count < 0 ? 0 : (uint)count; }, MarshalUtils.PtrToStructure, t => t.Build(), Native.LibVLCChapterDescriptionsRelease); /// /// Get the description of available chapters for specific title. /// /// selected title /// chapter descriptions public TrackDescription[] ChapterDescription(int titleIndex) => MarshalUtils.Retrieve(() => Native.LibVLCVideoGetChapterDescription(NativeReference, titleIndex), MarshalUtils.PtrToStructure, t => t.Build(), t => t.Next, Native.LibVLCTrackDescriptionListRelease); /// /// Get/Set current crop filter geometry. /// Empty string to unset /// public string? CropGeometry { get => Native.LibVLCVideoGetCropGeometry(NativeReference).FromUtf8(libvlcFree: true); set { var cropGeometryUtf8 = value.ToUtf8(); MarshalUtils.PerformInteropAndFree(() => Native.LibVLCVideoSetCropGeometry(NativeReference, cropGeometryUtf8), cropGeometryUtf8); } } /// /// Get current teletext page requested. /// Set new teletext page to retrieve. /// public int Teletext { get => Native.LibVLCVideoGetTeletext(NativeReference); set => Native.LibVLCVideoSetTeletext(NativeReference, value); } /// /// Get number of available video tracks. /// public int VideoTrackCount => Native.LibVLCVideoGetTrackCount(NativeReference); /// /// Get the description of available video tracks. /// public TrackDescription[] VideoTrackDescription => MarshalUtils.Retrieve(() => Native.LibVLCVideoGetTrackDescription(NativeReference), MarshalUtils.PtrToStructure, t => t.Build(), t => t.Next, Native.LibVLCTrackDescriptionListRelease); /// /// Get current video track ID (int) or -1 if no active input. /// public int VideoTrack => Native.LibVLCVideoGetTrack(NativeReference); /// /// Set video track. /// /// the track ID (i_id field from track description) /// true on sucess, false out of range public bool SetVideoTrack(int trackIndex) => Native.LibVLCVideoSetTrack(NativeReference, trackIndex) == 0; /// /// Take a snapshot of the current video window. /// If i_width AND i_height is 0, original size is used. If i_width XOR /// i_height is 0, original aspect-ratio is preserved. /// /// number of video output (typically 0 for the first/only one) /// the path where to save the screenshot to /// the snapshot's width /// the snapshot's height /// true on success public bool TakeSnapshot(uint num, string? filePath, uint width, uint height) { var filePathUtf8 = filePath.ToUtf8(); return MarshalUtils.PerformInteropAndFree(() => Native.LibVLCVideoTakeSnapshot(NativeReference, num, filePathUtf8, width, height) == 0, filePathUtf8); } /// /// Enable or disable deinterlace filter /// /// type of deinterlace filter, null to disable public void SetDeinterlace(string? deinterlaceMode) { var deinterlaceModeUtf8 = deinterlaceMode.ToUtf8(); MarshalUtils.PerformInteropAndFree(() => Native.LibVLCVideoSetDeinterlace(NativeReference, deinterlaceModeUtf8), deinterlaceModeUtf8); } /// /// Get an integer marquee option value /// /// marq option to get /// public int MarqueeInt(VideoMarqueeOption option) => Native.LibVLCVideoGetMarqueeInt(NativeReference, option); /// /// Get a string marquee option value /// /// marq option to get /// public string? MarqueeString(VideoMarqueeOption option) { var marqueeStrPtr = Native.LibVLCVideoGetMarqueeString(NativeReference, option); return marqueeStrPtr.FromUtf8(libvlcFree: true); } /// /// Enable, disable or set an integer marquee option /// Setting libvlc_marquee_Enable has the side effect of enabling (arg !0) /// or disabling (arg 0) the marq filter. /// /// marq option to set /// marq option value public void SetMarqueeInt(VideoMarqueeOption option, int value) => Native.LibVLCVideoSetMarqueeInt(NativeReference, option, value); /// /// Enable, disable or set an string marquee option /// /// marq option to set /// marq option value public void SetMarqueeString(VideoMarqueeOption option, string? marqueeValue) { var marqueeValueUtf8 = marqueeValue.ToUtf8(); MarshalUtils.PerformInteropAndFree(() => Native.LibVLCVideoSetMarqueeString(NativeReference, option, marqueeValueUtf8), marqueeValueUtf8); } /// /// Get integer logo option. /// /// logo option to get, values of libvlc_video_logo_option_t /// public int LogoInt(VideoLogoOption option) => Native.LibVLCVideoGetLogoInt(NativeReference, option); /// /// Set logo option as integer. Options that take a different type value /// are ignored. Passing libvlc_logo_enable as option value has the side /// effect of starting (arg !0) or stopping (arg 0) the logo filter. /// /// logo option to set, values of libvlc_video_logo_option_t /// logo option value public void SetLogoInt(VideoLogoOption option, int value) => Native.LibVLCVideoSetLogoInt(NativeReference, option, value); /// /// Set logo option as string. Options that take a different type value are ignored. /// /// logo option to set, values of libvlc_video_logo_option_t /// logo option value public void SetLogoString(VideoLogoOption option, string? logoValue) { var logoValueUtf8 = logoValue.ToUtf8(); MarshalUtils.PerformInteropAndFree(() => Native.LibVLCVideoSetLogoString(NativeReference, option, logoValueUtf8), logoValueUtf8); } /// /// Get integer adjust option. /// /// adjust option to get, values of libvlc_video_adjust_option_t /// public int AdjustInt(VideoAdjustOption option) => Native.LibVLCVideoGetAdjustInt(NativeReference, option); /// /// Set adjust option as integer. Options that take a different type value /// are ignored. Passing libvlc_adjust_enable as option value has the side /// effect of starting (arg !0) or stopping (arg 0) the adjust filter. /// /// adust option to set, values of libvlc_video_adjust_option_t /// adjust option value public void SetAdjustInt(VideoAdjustOption option, int value) => Native.LibVLCVideoSetAdjustInt(NativeReference, option, value); /// /// Get adjust option float value /// /// The option for which to get the value /// the float value for a given option public float AdjustFloat(VideoAdjustOption option) => Native.LibVLCVideoGetAdjustFloat(NativeReference, option); /// /// Set adjust option as float. Options that take a different type value are ignored. /// /// adust option to set, values of /// adjust option value public void SetAdjustFloat(VideoAdjustOption option, float value) => Native.LibVLCVideoSetAdjustFloat(NativeReference, option, value); #if ANDROID /// /// Set the android context. /// /// See LibVLCSharp.Android public void SetAndroidContext(IntPtr aWindow) => Native.LibVLCMediaPlayerSetAndroidContext(NativeReference, aWindow); #endif /// /// Add a slave to the current media player. /// note If the player is playing, the slave will be added directly. This call /// will also update the slave list of the attached VLC::Media. /// /// subtitle or audio /// Uri of the slave (should contain a valid scheme). /// True if this slave should be selected when it's loaded /// public bool AddSlave(MediaSlaveType type, string uri, bool select) { var uriUtf8 = uri.ToUtf8(); return MarshalUtils.PerformInteropAndFree(() => Native.LibVLCMediaPlayerAddSlave(NativeReference, type, uriUtf8, select) == 0, uriUtf8); } /// /// Current 360 viewpoint of this mediaplayer. /// Update with /// public VideoViewpoint Viewpoint { get; private set; } /// /// Update the video viewpoint information. /// The values are set asynchronously, it will be used by the next frame displayed. /// It is safe to call this function before the media player is started. /// LibVLC 3.0.0 and later /// /// view point yaw in degrees ]-180;180] /// view point pitch in degrees ]-90;90] /// view point roll in degrees ]-180;180] /// field of view in degrees ]0;180[ (default 80.) /// if true replace the old viewpoint with the new one. If false, increase/decrease it. /// true if successful, false otherwise public bool UpdateViewpoint(float yaw, float pitch, float roll, float fov, bool absolute = true) { var vpPtr = Native.LibVLCVideoNewViewpoint(); if (vpPtr == IntPtr.Zero) return false; Viewpoint = new VideoViewpoint(yaw, pitch, roll, fov); Marshal.StructureToPtr(Viewpoint, vpPtr, false); var result = Native.LibVLCVideoUpdateViewpoint(NativeReference, vpPtr, absolute) == 0; MarshalUtils.LibVLCFree(ref vpPtr); return result; } /// /// Set a renderer to the media player. /// /// discovered renderer item or null to fallback on local rendering /// true on success, false otherwise public bool SetRenderer(RendererItem? rendererItem) => Native.LibVLCMediaPlayerSetRenderer(NativeReference, rendererItem?.NativeReference ?? IntPtr.Zero) == 0; /// Gets the media role. /// version LibVLC 3.0.0 and later. /// public MediaPlayerRole Role => Native.LibVLCMediaPlayerGetRole(NativeReference); /// Sets the media role. /// version LibVLC 3.0.0 and later. /// /// true on success, false otherwise public bool SetRole(MediaPlayerRole role) => Native.LibVLCMediaPlayerSetRole(NativeReference, role) == 0; /// Increments the native reference counter for this mediaplayer instance internal void Retain() => Native.LibVLCMediaPlayerRetain(NativeReference); /// /// Enable/disable hardware decoding in a crossplatform way. /// public bool EnableHardwareDecoding { get => Configuration.EnableHardwareDecoding; set => Configuration.EnableHardwareDecoding = value; } /// /// Caching value for local files, in milliseconds [0 .. 60000ms] /// public uint FileCaching { get => Configuration.FileCaching; set => Configuration.FileCaching = value; } /// /// Caching value for network resources, in milliseconds [0 .. 60000ms] /// public uint NetworkCaching { get => Configuration.NetworkCaching; set => Configuration.NetworkCaching = value; } MediaConfiguration Configuration = new MediaConfiguration(); #region Callbacks static readonly LibVLCVideoLockCb VideoLockCallbackHandle = VideoLockCallback; static readonly LibVLCVideoUnlockCb VideoUnlockCallbackHandle = VideoUnlockCallback; static readonly LibVLCVideoDisplayCb VideoDisplayCallbackHandle = VideoDisplayCallback; static readonly LibVLCVideoFormatCb VideoFormatCallbackHandle = VideoFormatCallback; static readonly LibVLCVideoCleanupCb VideoCleanupCallbackHandle = VideoCleanupCallback; [MonoPInvokeCallback(typeof(LibVLCVideoLockCb))] private static IntPtr VideoLockCallback(IntPtr opaque, IntPtr planes) { var mediaPlayer = MarshalUtils.GetInstance(opaque); if (mediaPlayer?._videoLockCb != null) { return mediaPlayer._videoLockCb(mediaPlayer._videoUserData, planes); } return IntPtr.Zero; } [MonoPInvokeCallback(typeof(LibVLCVideoUnlockCb))] private static void VideoUnlockCallback(IntPtr opaque, IntPtr picture, IntPtr planes) { var mediaPlayer = MarshalUtils.GetInstance(opaque); if (mediaPlayer?._videoUnlockCb != null) { mediaPlayer._videoUnlockCb(mediaPlayer._videoUserData, picture, planes); } } [MonoPInvokeCallback(typeof(LibVLCVideoDisplayCb))] private static void VideoDisplayCallback(IntPtr opaque, IntPtr picture) { var mediaPlayer = MarshalUtils.GetInstance(opaque); if (mediaPlayer?._videoDisplayCb != null) { mediaPlayer._videoDisplayCb(mediaPlayer._videoUserData, picture); } } [MonoPInvokeCallback(typeof(LibVLCVideoFormatCb))] private static uint VideoFormatCallback(ref IntPtr opaque, IntPtr chroma, ref uint width, ref uint height, ref uint pitches, ref uint lines) { var mediaPlayer = MarshalUtils.GetInstance(opaque); if (mediaPlayer?._videoFormatCb != null) { return mediaPlayer._videoFormatCb(ref mediaPlayer._videoUserData, chroma, ref width, ref height, ref pitches, ref lines); } return 0; } [MonoPInvokeCallback(typeof(LibVLCVideoCleanupCb))] private static void VideoCleanupCallback(ref IntPtr opaque) { var mediaPlayer = MarshalUtils.GetInstance(opaque); if (mediaPlayer?._videoCleanupCb != null) { mediaPlayer._videoCleanupCb(ref mediaPlayer._videoUserData); } } static readonly LibVLCAudioPlayCb AudioPlayCallbackHandle = AudioPlayCallback; static readonly LibVLCAudioPauseCb AudioPauseCallbackHandle = AudioPauseCallback; static readonly LibVLCAudioResumeCb AudioResumeCallbackHandle = AudioResumeCallback; static readonly LibVLCAudioFlushCb AudioFlushCallbackHandle = AudioFlushCallback; static readonly LibVLCAudioDrainCb AudioDrainCallbackHandle = AudioDrainCallback; static readonly LibVLCVolumeCb AudioVolumeCallbackHandle = AudioVolumeCallback; static readonly LibVLCAudioSetupCb AudioSetupCallbackHandle = AudioSetupCallback; static readonly LibVLCAudioCleanupCb AudioCleanupCallbackHandle = AudioCleanupCallback; [MonoPInvokeCallback(typeof(LibVLCAudioPlayCb))] private static void AudioPlayCallback(IntPtr data, IntPtr samples, uint count, long pts) { var mediaPlayer = MarshalUtils.GetInstance(data); if (mediaPlayer?._audioPlayCb != null) { mediaPlayer._audioPlayCb(mediaPlayer._audioUserData, samples, count, pts); } } [MonoPInvokeCallback(typeof(LibVLCAudioPauseCb))] private static void AudioPauseCallback(IntPtr data, long pts) { var mediaPlayer = MarshalUtils.GetInstance(data); if (mediaPlayer?._audioPauseCb != null) { mediaPlayer._audioPauseCb(mediaPlayer._audioUserData, pts); } } [MonoPInvokeCallback(typeof(LibVLCAudioResumeCb))] private static void AudioResumeCallback(IntPtr data, long pts) { var mediaPlayer = MarshalUtils.GetInstance(data); if (mediaPlayer?._audioResumeCb != null) { mediaPlayer._audioResumeCb(mediaPlayer._audioUserData, pts); } } [MonoPInvokeCallback(typeof(LibVLCAudioFlushCb))] private static void AudioFlushCallback(IntPtr data, long pts) { var mediaPlayer = MarshalUtils.GetInstance(data); if (mediaPlayer?._audioFlushCb != null) { mediaPlayer._audioFlushCb(mediaPlayer._audioUserData, pts); } } [MonoPInvokeCallback(typeof(LibVLCAudioDrainCb))] private static void AudioDrainCallback(IntPtr data) { var mediaPlayer = MarshalUtils.GetInstance(data); if (mediaPlayer?._audioDrainCb != null) { mediaPlayer._audioDrainCb(mediaPlayer._audioUserData); } } [MonoPInvokeCallback(typeof(LibVLCVolumeCb))] private static void AudioVolumeCallback(IntPtr data, float volume, bool mute) { var mediaPlayer = MarshalUtils.GetInstance(data); if (mediaPlayer?._audioVolumeCb != null) { mediaPlayer._audioVolumeCb(mediaPlayer._audioUserData, volume, mute); } } [MonoPInvokeCallback(typeof(LibVLCAudioSetupCb))] private static int AudioSetupCallback(ref IntPtr opaque, ref IntPtr format, ref uint rate, ref uint channels) { var mediaPlayer = MarshalUtils.GetInstance(opaque); if (mediaPlayer?._setupCb != null) { return mediaPlayer._setupCb(ref mediaPlayer._audioUserData, ref format, ref rate, ref channels); } return -1; } [MonoPInvokeCallback(typeof(LibVLCAudioCleanupCb))] private static void AudioCleanupCallback(IntPtr opaque) { var mediaPlayer = MarshalUtils.GetInstance(opaque); if (mediaPlayer?._cleanupCb != null) { mediaPlayer._cleanupCb(mediaPlayer._audioUserData); } } /// /// A LibVLC media player plays one media (usually in a custom drawable). /// @{ /// /// LibVLC simple media player external API /// /// Opaque equalizer handle. /// Equalizer settings can be applied to a media player. /// Callback prototype to allocate and lock a picture buffer. /// private pointer as passed to libvlc_video_set_callbacks() [IN] /// /// start address of the pixel planes (LibVLC allocates the array /// of void pointers, this callback must initialize the array) [OUT] /// /// /// a private pointer for the display and unlock callbacks to identify /// the picture buffers /// /// /// Whenever a new video frame needs to be decoded, the lock callback is /// invoked. Depending on the video chroma, one or three pixel planes of /// adequate dimensions must be returned via the second parameter. Those /// planes must be aligned on 32-bytes boundaries. /// [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate IntPtr LibVLCVideoLockCb(IntPtr opaque, IntPtr planes); /// Callback prototype to unlock a picture buffer. /// private pointer as passed to libvlc_video_set_callbacks() [IN] /// private pointer returned from the /// pixel planes as defined by the /// /// When the video frame decoding is complete, the unlock callback is invoked. /// This callback might not be needed at all. It is only an indication that the /// application can now read the pixel values if it needs to. /// A picture buffer is unlocked after the picture is decoded, /// but before the picture is displayed. /// callback [IN] /// callback (this parameter is only for convenience) [IN] /// [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate void LibVLCVideoUnlockCb(IntPtr opaque, IntPtr picture, IntPtr planes); /// Callback prototype to display a picture. /// private pointer as passed to libvlc_video_set_callbacks() [IN] /// private pointer returned from the /// /// When the video frame needs to be shown, as determined by the media playback /// clock, the display callback is invoked. /// callback [IN] /// [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate void LibVLCVideoDisplayCb(IntPtr opaque, IntPtr picture); /// /// Callback prototype to configure picture buffers format. /// This callback gets the format of the video as output by the video decoder /// and the chain of video filters (if any). It can opt to change any parameter /// as it needs. In that case, LibVLC will attempt to convert the video format /// (rescaling and chroma conversion) but these operations can be CPU intensive. /// /// /// pointer to the private pointer passed to /// libvlc_video_set_callbacks() [IN/OUT] /// /// pointer to the 4 bytes video format identifier [IN/OUT] /// pointer to the pixel width [IN/OUT] /// pointer to the pixel height [IN/OUT] /// /// table of scanline pitches in bytes for each pixel plane /// (the table is allocated by LibVLC) [OUT] /// /// table of scanlines count for each plane [OUT] /// the number of picture buffers allocated, 0 indicates failure /// /// For each pixels plane, the scanline pitch must be bigger than or equal to /// the number of bytes per pixel multiplied by the pixel width. /// Similarly, the number of scanlines must be bigger than of equal to /// the pixel height. /// Furthermore, we recommend that pitches and lines be multiple of 32 /// to not break assumptions that might be held by optimized code /// in the video decoders, video filters and/or video converters. /// [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate uint LibVLCVideoFormatCb(ref IntPtr opaque, IntPtr chroma, ref uint width, ref uint height, ref uint pitches, ref uint lines); /// Callback prototype to configure picture buffers format. /// /// private pointer as passed to libvlc_video_set_callbacks() /// (and possibly modified by /// [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate void LibVLCVideoCleanupCb(ref IntPtr opaque); /// Callback prototype to setup the audio playback. /// /// pointer to the data pointer passed to /// libvlc_audio_set_callbacks() [IN/OUT] /// /// 4 bytes sample format [IN/OUT] /// sample rate [IN/OUT] /// channels count [IN/OUT] /// 0 on success, anything else to skip audio playback /// This is called when the media player needs to create a new audio output. [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate int LibVLCAudioSetupCb(ref IntPtr opaque, ref IntPtr format, ref uint rate, ref uint channels); /// Callback prototype for audio playback cleanup. /// data pointer as passed to libvlc_audio_set_callbacks() [IN] /// This is called when the media player no longer needs an audio output. [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate void LibVLCAudioCleanupCb(IntPtr opaque); /// Callback prototype for audio playback. /// data pointer as passed to libvlc_audio_set_callbacks() [IN] /// pointer to a table of audio samples to play back [IN] /// number of audio samples to play back /// expected play time stamp (see libvlc_delay()) /// /// The LibVLC media player decodes and post-processes the audio signal /// asynchronously (in an internal thread). Whenever audio samples are ready /// to be queued to the output, this callback is invoked. /// The number of samples provided per invocation may depend on the file format, /// the audio coding algorithm, the decoder plug-in, the post-processing /// filters and timing. Application must not assume a certain number of samples. /// The exact format of audio samples is determined by libvlc_audio_set_format() /// or libvlc_audio_set_format_callbacks() as is the channels layout. /// Note that the number of samples is per channel. For instance, if the audio /// track sampling rate is 48000 Hz, then 1200 samples represent 25 milliseconds /// of audio signal - regardless of the number of audio channels. /// [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate void LibVLCAudioPlayCb(IntPtr data, IntPtr samples, uint count, long pts); /// Callback prototype for audio pause. /// data pointer as passed to libvlc_audio_set_callbacks() [IN] /// time stamp of the pause request (should be elapsed already) /// /// LibVLC invokes this callback to pause audio playback. /// The pause callback is never called if the audio is already paused. /// [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate void LibVLCAudioPauseCb(IntPtr data, long pts); /// Callback prototype for audio resumption. /// data pointer as passed to libvlc_audio_set_callbacks() [IN] /// time stamp of the resumption request (should be elapsed already) /// /// LibVLC invokes this callback to resume audio playback after it was /// previously paused. /// The resume callback is never called if the audio is not paused. /// [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate void LibVLCAudioResumeCb(IntPtr data, long pts); /// Callback prototype for audio buffer flush. /// LibVLC invokes this callback if it needs to discard all pending buffers and /// stop playback as soon as possible. This typically occurs when the media is stopped. /// /// data pointer as passed to libvlc_audio_set_callbacks() [IN] /// current presentation timestamp [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate void LibVLCAudioFlushCb(IntPtr data, long pts); /// Callback prototype for audio buffer drain. /// data pointer as passed to libvlc_audio_set_callbacks() [IN] /// /// LibVLC may invoke this callback when the decoded audio track is ending. /// There will be no further decoded samples for the track, but playback should /// nevertheless continue until all already pending buffers are rendered. /// [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate void LibVLCAudioDrainCb(IntPtr data); /// Callback prototype for audio volume change. /// data pointer as passed to libvlc_audio_set_callbacks() [IN] /// software volume (1. = nominal, 0. = mute) /// muted flag [UnmanagedFunctionPointer(CallingConvention.Cdecl)] public delegate void LibVLCVolumeCb(IntPtr data, float volume, [MarshalAs(UnmanagedType.I1)] bool mute); #endregion /// /// Get the Event Manager from which the media player send event. /// MediaPlayerEventManager EventManager { get { if (_eventManager == null) { var eventManagerPtr = Native.LibVLCMediaPlayerEventManager(NativeReference); _eventManager = new MediaPlayerEventManager(eventManagerPtr); } return _eventManager; } } #region events /// /// The media of this mediaplayer changed /// public event EventHandler MediaChanged { add => EventManager.AttachEvent(EventType.MediaPlayerMediaChanged, value); remove => EventManager.DetachEvent(EventType.MediaPlayerMediaChanged, value); } /// /// Nothing special to report /// public event EventHandler NothingSpecial { add => EventManager.AttachEvent(EventType.MediaPlayerNothingSpecial, value); remove => EventManager.DetachEvent(EventType.MediaPlayerNothingSpecial, value); } /// /// The mediaplayer is opening a media /// public event EventHandler Opening { add => EventManager.AttachEvent(EventType.MediaPlayerOpening, value); remove => EventManager.DetachEvent(EventType.MediaPlayerOpening, value); } /// /// The mediaplayer is buffering /// public event EventHandler Buffering { add => EventManager.AttachEvent(EventType.MediaPlayerBuffering, value); remove => EventManager.DetachEvent(EventType.MediaPlayerBuffering, value); } /// /// The mediaplayer started playing a media /// public event EventHandler Playing { add => EventManager.AttachEvent(EventType.MediaPlayerPlaying, value); remove => EventManager.DetachEvent(EventType.MediaPlayerPlaying, value); } /// /// The mediaplayer paused playback /// public event EventHandler Paused { add => EventManager.AttachEvent(EventType.MediaPlayerPaused, value); remove => EventManager.DetachEvent(EventType.MediaPlayerPaused, value); } /// /// The mediaplayer stopped playback /// public event EventHandler Stopped { add => EventManager.AttachEvent(EventType.MediaPlayerStopped, value); remove => EventManager.DetachEvent(EventType.MediaPlayerStopped, value); } /// /// The mediaplayer went forward in the playback /// public event EventHandler Forward { add => EventManager.AttachEvent(EventType.MediaPlayerForward, value); remove => EventManager.DetachEvent(EventType.MediaPlayerForward, value); } /// /// The mediaplayer went backward in the playback /// public event EventHandler Backward { add => EventManager.AttachEvent(EventType.MediaPlayerBackward, value); remove => EventManager.DetachEvent(EventType.MediaPlayerBackward, value); } /// /// The mediaplayer reached the end of the playback /// public event EventHandler EndReached { add => EventManager.AttachEvent(EventType.MediaPlayerEndReached, value); remove => EventManager.DetachEvent(EventType.MediaPlayerEndReached, value); } /// /// The mediaplayer encountered an error during playback /// public event EventHandler EncounteredError { add => EventManager.AttachEvent(EventType.MediaPlayerEncounteredError, value); remove => EventManager.DetachEvent(EventType.MediaPlayerEncounteredError, value); } /// /// The mediaplayer's playback time changed /// public event EventHandler TimeChanged { add => EventManager.AttachEvent(EventType.MediaPlayerTimeChanged, value); remove => EventManager.DetachEvent(EventType.MediaPlayerTimeChanged, value); } /// /// The mediaplayer's position changed /// public event EventHandler PositionChanged { add => EventManager.AttachEvent(EventType.MediaPlayerPositionChanged, value); remove => EventManager.DetachEvent(EventType.MediaPlayerPositionChanged, value); } /// /// The mediaplayer's seek capability changed /// public event EventHandler SeekableChanged { add => EventManager.AttachEvent(EventType.MediaPlayerSeekableChanged, value); remove => EventManager.DetachEvent(EventType.MediaPlayerSeekableChanged, value); } /// /// The mediaplayer's pause capability changed /// public event EventHandler PausableChanged { add => EventManager.AttachEvent(EventType.MediaPlayerPausableChanged, value); remove => EventManager.DetachEvent(EventType.MediaPlayerPausableChanged, value); } /// /// The title of the mediaplayer changed /// public event EventHandler TitleChanged { add => EventManager.AttachEvent(EventType.MediaPlayerTitleChanged, value); remove => EventManager.DetachEvent(EventType.MediaPlayerTitleChanged, value); } /// /// The mediaplayer changed the chapter of a media /// public event EventHandler ChapterChanged { add => EventManager.AttachEvent(EventType.MediaPlayerChapterChanged, value); remove => EventManager.DetachEvent(EventType.MediaPlayerChapterChanged, value); } /// /// The mediaplayer took a snapshot /// public event EventHandler SnapshotTaken { add => EventManager.AttachEvent(EventType.MediaPlayerSnapshotTaken, value); remove => EventManager.DetachEvent(EventType.MediaPlayerSnapshotTaken, value); } /// /// The length of a playback changed /// public event EventHandler LengthChanged { add => EventManager.AttachEvent(EventType.MediaPlayerLengthChanged, value); remove => EventManager.DetachEvent(EventType.MediaPlayerLengthChanged, value); } /// /// The Video Output count of the MediaPlayer changed /// public event EventHandler Vout { add => EventManager.AttachEvent(EventType.MediaPlayerVout, value); remove => EventManager.DetachEvent(EventType.MediaPlayerVout, value); } /// /// The mediaplayer scrambled status changed /// public event EventHandler ScrambledChanged { add => EventManager.AttachEvent(EventType.MediaPlayerScrambledChanged, value); remove => EventManager.DetachEvent(EventType.MediaPlayerScrambledChanged, value); } /// /// The mediaplayer has a new Elementary Stream (ES) /// public event EventHandler ESAdded { add => EventManager.AttachEvent(EventType.MediaPlayerESAdded, value); remove => EventManager.DetachEvent(EventType.MediaPlayerESAdded, value); } /// /// The mediaplayer has one less Elementary Stream (ES) /// public event EventHandler ESDeleted { add => EventManager.AttachEvent(EventType.MediaPlayerESDeleted, value); remove => EventManager.DetachEvent(EventType.MediaPlayerESDeleted, value); } /// /// An Elementary Stream (ES) was selected /// public event EventHandler ESSelected { add => EventManager.AttachEvent(EventType.MediaPlayerESSelected, value); remove => EventManager.DetachEvent(EventType.MediaPlayerESSelected, value); } /// /// The mediaplayer's audio device changed /// public event EventHandler AudioDevice { add => EventManager.AttachEvent(EventType.MediaPlayerAudioDevice, value); remove => EventManager.DetachEvent(EventType.MediaPlayerAudioDevice, value); } /// /// The mediaplayer is corked /// public event EventHandler Corked { add => EventManager.AttachEvent(EventType.MediaPlayerCorked, value); remove => EventManager.DetachEvent(EventType.MediaPlayerCorked, value); } /// /// The mediaplayer is uncorked /// public event EventHandler Uncorked { add => EventManager.AttachEvent(EventType.MediaPlayerUncorked, value); remove => EventManager.DetachEvent(EventType.MediaPlayerUncorked, value); } /// /// The mediaplayer is muted /// public event EventHandler Muted { add => EventManager.AttachEvent(EventType.MediaPlayerMuted, value); remove => EventManager.DetachEvent(EventType.MediaPlayerMuted, value); } /// /// The mediaplayer is unmuted /// public event EventHandler Unmuted { add => EventManager.AttachEvent(EventType.MediaPlayerUnmuted, value); remove => EventManager.DetachEvent(EventType.MediaPlayerUnmuted, value); } /// /// The mediaplayer's volume changed /// public event EventHandler VolumeChanged { add => EventManager.AttachEvent(EventType.MediaPlayerAudioVolume, value); remove => EventManager.DetachEvent(EventType.MediaPlayerAudioVolume, value); } #endregion /// /// Dispose override /// Effectively stops playback and disposes a media if any /// /// release any unmanaged resources protected override void Dispose(bool disposing) { if (IsDisposed || NativeReference == IntPtr.Zero) return; if(disposing) { if(IsPlaying) Stop(); if (_gcHandle.IsAllocated) _gcHandle.Free(); } base.Dispose(disposing); } } /// Description for titles public enum Title { /// /// Menu title /// Menu = 1, /// /// Interactive title /// Interactive = 2 } /// Marq options definition public enum VideoMarqueeOption { /// /// Enable marquee /// Enable = 0, /// /// Text marquee /// Text = 1, /// /// Color marquee /// Color = 2, /// /// Opacity marquee /// Opacity = 3, /// /// Position marquee /// Position = 4, /// /// Refresh marquee /// Refresh = 5, /// /// Size marquee /// Size = 6, /// /// Timeout marquee /// Timeout = 7, /// /// X marquee /// X = 8, /// /// Y marquee /// Y = 9 } /// Navigation mode public enum NavigationMode { /// /// Activate /// Activate = 0, /// /// Navigation up /// Up = 1, /// /// Navigation down /// Down = 2, /// /// Navigation left /// Left = 3, /// /// Navigation right /// Right = 4, /// /// Navigation popup /// Popup = 5 } /// Enumeration of values used to set position (e.g. of video title). public enum Position { /// /// Disable /// Disable = -1, /// /// Center video title /// Center = 0, /// /// Left video title /// Left = 1, /// /// Right video title /// Right = 2, /// /// Top video title /// Top = 3, /// /// TopLeft video title /// TopLeft = 4, /// /// TopRight video title /// TopRight = 5, /// /// Bottom video title /// Bottom = 6, /// /// BottomLeft video title /// BottomLeft = 7, /// /// BottomRight video title /// BottomRight = 8 } /// /// Enumeration of teletext keys than can be passed via /// libvlc_video_set_teletext() /// public enum TeletextKey { /// /// Red /// Red = 7471104, /// /// Green /// Green = 6750208, /// /// Yellow /// Yellow = 7929856, /// /// Blue /// Blue = 6422528, /// /// Index /// Index = 6881280 } /// /// option values for libvlc_video_{get,set}_logo_{int,string} /// public enum VideoLogoOption { /// /// Enable /// Enable = 0, /// /// string argument, "file,d,t;file,d,t;..." /// File = 1, /// /// X /// X = 2, /// /// Y /// Y = 3, /// /// Delay /// Delay = 4, /// /// Repeat /// Repeat = 5, /// /// Opacity /// Opacity = 6, /// /// Position /// Position = 7 } /// /// option values for libvlc_video_{get,set}_adjust_{int,float,bool} /// public enum VideoAdjustOption { /// /// Enable /// Enable = 0, /// /// Contrast /// Contrast = 1, /// /// Brightness /// Brightness = 2, /// /// Hue /// Hue = 3, /// /// Saturation /// Saturation = 4, /// /// Gamma /// Gamma = 5 } /// /// Audio channels /// public enum AudioOutputChannel { /// /// Error /// Error = -1, /// /// Stereo mode /// Stereo = 1, /// /// RStereo mode /// RStereo = 2, /// /// Left mode /// Left = 3, /// /// Right mode /// Right = 4, /// /// Dolbys mode /// Dolbys = 5 } /// Media player roles. /// /// LibVLC 3.0.0 and later. /// See /// public enum MediaPlayerRole { /// Don't use a media player role None = 0, /// Music (or radio) playback Music = 1, /// Video playback Video = 2, /// Speech, real-time communication Communication = 3, /// Video game Game = 4, /// User interaction feedback LiblvcRoleNotification = 5, /// Embedded animation (e.g. in web page) Animation = 6, /// Audio editing/production Production = 7, /// Accessibility Accessibility = 8, /// Testing Test = 9 } }