TAG:
{ return Marshal.PtrToStringAnsi(stringValue.psz_string); } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; } return errorReturn; } public VlcError SetVlcObjectString(ObjectType objectType, String propertyName, String value) { try { using(VlcObject vobj = new VlcObject(this.vlcHandle, objectType)) { if(vobj.SubObject != IntPtr.Zero) { vlc_value_t stringValue = new vlc_value_t(); IntPtr valuePtr = Marshal.StringToCoTaskMemAnsi(value); stringValue.psz_string = valuePtr; VlcError ret = __var_Set(vobj.SubObject, propertyName, stringValue); Marshal.ZeroFreeCoTaskMemAnsi(valuePtr); return ret; } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; } return VlcError.NoObj; } public VlcError GetVlcVariableChoiceList(ObjectType objectType, String propertyName, out int[] choiceIds, out String[] choiceText) { try { using(VlcObject vobj = new VlcObject(this.vlcHandle, objectType)) { if(vobj.SubObject != IntPtr.Zero) { vlc_value_t idValues = new vlc_value_t(); vlc_value_t textValues = new vlc_value_t(); if(VlcError.Success == __var_Change(vobj.SubObject, propertyName, VarFlags.VLC_VAR_GETLIST, ref idValues, ref textValues)) { try { vlc_list_t idList = (vlc_list_t)Marshal.PtrToStructure( idValues.p_list, typeof(vlc_list_t)); vlc_list_t textList = (vlc_list_t)Marshal.PtrToStructure( textValues.p_list, typeof(vlc_list_t)); int choiceCount = idList.i_count; choiceIds = new Int32[choiceCount]; choiceText = new String[choiceCount]; for(int index = 0; index < choiceCount; index++) { IntPtr idPtr = new IntPtr(idList.p_values.ToInt32() + index * Marshal.SizeOf(typeof(vlc_value_t))); vlc_value_t idValue = (vlc_value_t)Marshal.PtrToStructure( idPtr, typeof(vlc_value_t)); choiceIds[index] = idValue.i_int; IntPtr textPtr = new IntPtr(textList.p_values.ToInt32() + index * Marshal.SizeOf(typeof(vlc_value_t))); vlc_value_t textValue = (vlc_value_t)Marshal.PtrToStructure( textPtr, typeof(vlc_value_t)); choiceText[index] = Marshal.PtrToStringAnsi(textValue.psz_string); } return VlcError.Success; } finally { __var_Change(vobj.SubObject, propertyName, VarFlags.VLC_VAR_FREELIST, ref idValues, ref textValues); } } } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; } choiceIds = new int[0]; choiceText = new string[0]; return VlcError.NoObj; } public VlcError GetVlcVariableChoiceList(ObjectType objectType, String propertyName, out String[] choices, out String[] choiceText) { try { using(VlcObject vobj = new VlcObject(this.vlcHandle, objectType)) { if(vobj.SubObject != IntPtr.Zero) { vlc_value_t idValues = new vlc_value_t(); vlc_value_t textValues = new vlc_value_t(); if(VlcError.Success == __var_Change(vobj.SubObject, propertyName, VarFlags.VLC_VAR_GETLIST, ref idValues, ref textValues)) { try { vlc_list_t idList = (vlc_list_t)Marshal.PtrToStructure( idValues.p_list, typeof(vlc_list_t)); vlc_list_t textList = (vlc_list_t)Marshal.PtrToStructure( textValues.p_list, typeof(vlc_list_t)); int choiceCount = idList.i_count; List<String> choiceList = new List<string>(choiceCount); List<String> choiceTextList = new List<string>(choiceCount); Dictionary<String, int> choiceDict = new Dictionary<string, int>(choiceCount); for(int index = 0; index < choiceCount; index++) { IntPtr idPtr = new IntPtr(idList.p_values.ToInt32() + index * Marshal.SizeOf(typeof(vlc_value_t))); vlc_value_t idValue = (vlc_value_t)Marshal.PtrToStructure( idPtr, typeof(vlc_value_t)); String choice = Marshal.PtrToStringAnsi(idValue.psz_name); choiceList.Add(choice); if(choiceDict.ContainsKey(choice)) { choiceDict[choice] = choiceDict[choice] + 1; } else { choiceDict[choice] = 1; } IntPtr textPtr = new IntPtr(textList.p_values.ToInt32() + index * Marshal.SizeOf(typeof(vlc_value_t))); vlc_value_t textValue = (vlc_value_t)Marshal.PtrToStructure( textPtr, typeof(vlc_value_t)); choiceTextList.Add(Marshal.PtrToStringAnsi(textValue.psz_string)); } int listIndex = 0; for(int index = 0; index < choiceCount; index++) { String choice = choiceList[listIndex]; if((choiceDict[choice] > 1) && (choiceTextList[listIndex] == null)) { choiceList.RemoveAt(listIndex); choiceTextList.RemoveAt(listIndex); choiceDict[choice] = choiceDict[choice] - 1; } else { listIndex++; } } for(int index = 0; index < choiceList.Count; index++) { if(choiceTextList[index] == null) { choiceTextList[index] = choiceList[index]; } } choices = choiceList.ToArray(); choiceText = choiceTextList.ToArray(); return VlcError.Success; } finally { __var_Change(vobj.SubObject, propertyName, VarFlags.VLC_VAR_FREELIST, ref idValues, ref textValues); } } } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; } choices = new string[0]; choiceText = new string[0]; return VlcError.NoObj; } #endregion #region public Properties public static string VlcInstallDir { get{ return vlcInstallDirectory; } set{ vlcInstallDirectory = value; } } public bool IsInitialized { get{return (vlcHandle != -1);} } public Control VideoOutput { get { return outputWindow; } set { if(value == null) { if(outputWindow != null) { outputWindow = null; if(vlcHandle != -1) { SetVlcObjectInt(ObjectType.VLC_OBJECT_VLC, "drawable", 0); } } } else { outputWindow = value; if(vlcHandle != -1) { SetVlcObjectInt(ObjectType.VLC_OBJECT_VLC, "drawable", outputWindow.Handle.ToInt32()); } } } } public string LastError { get{return lastErrorMessage;} } public event MetaDataEventHandler NowPlaying; protected virtual void OnNowPlaying(MetaDataUpdateEventArgs args) { if(this.NowPlaying != null) { this.NowPlaying(this, args); } } protected delegate void HandleNowPlaying(MetaDataUpdateEventArgs args); protected virtual void VlcNowPlayingChanged(String newText) { // switch out of the Vlc thread to our User Interface thread if possible if(this.VideoOutput != null) { this.VideoOutput.BeginInvoke(new HandleNowPlaying(OnNowPlaying), new MetaDataUpdateEventArgs(MetaData.NowPlaying, newText)); } else { OnNowPlaying(new MetaDataUpdateEventArgs(MetaData.NowPlaying, newText)); } } public int Length { get { if(this.artificialLength != 0) { return this.artificialLength; } else { return Convert.ToInt32(GetVlcObjectLong(ObjectType.VLC_OBJECT_INPUT, "length", 0) / 1000000L); } } } public void SetArtificialLength(int newLength) { this.artificialLength = newLength; } public int Time { get { int time = Convert.ToInt32(GetVlcObjectLong(ObjectType.VLC_OBJECT_INPUT, "time", 0) / 1000000L); if((time == 0) && (this.artificialLength != 0)) { time = Convert.ToInt32(Position * this.artificialLength + .5d); } if(this.timeScaling != 0.0d) { time = Convert.ToInt32(time / this.timeScaling); } return time; } set { if(this.artificialLength != 0) { float position = Convert.ToSingle(value) / Convert.ToSingle(this.artificialLength); if(this.timeScaling != 0.0d) { position = Convert.ToSingle(position * this.timeScaling); } Debug.WriteLine(String.Format("Set Position {0}", position)); SetVlcObjectFloat(ObjectType.VLC_OBJECT_INPUT, "position", position); } else { long time = Convert.ToInt64(value) * 1000000L; if(this.timeScaling != 0.0d) { time = Convert.ToInt64(time * this.timeScaling); } Debug.WriteLine(String.Format("Set Time {0}", time)); SetVlcObjectLong(ObjectType.VLC_OBJECT_INPUT, "time", time); } } } public double TimeScaling { get { return this.timeScaling; } set { this.timeScaling = value; } } public double Position { get { double position = GetVlcObjectFloat(ObjectType.VLC_OBJECT_INPUT, "position", 0.0f); if(this.timeScaling != 0.0d) { position = position / this.timeScaling; } return position; } set { double position = value; if(this.timeScaling != 0.0d) { position = position * this.timeScaling; } Debug.WriteLine(String.Format("Set Position {0}", position)); SetVlcObjectFloat(ObjectType.VLC_OBJECT_INPUT, "position", Convert.ToSingle(position)); } } public int Volume { get { IntPtr vlc = vlc_current_object(vlcHandle); if(IntPtr.Zero != vlc) { try { Int16 aoutVol = 0; if(__aout_VolumeGet(vlc, ref aoutVol) == VlcError.Success) { return (aoutVol * VOLUME_MAX + AOUT_VOLUME_MAX / 2) / AOUT_VOLUME_MAX; } } catch(Exception) { } finally { __vlc_object_release(vlc); } } return 0; } set { IntPtr vlc = vlc_current_object(vlcHandle); if(IntPtr.Zero != vlc) { try { Int16 aoutVol = Convert.ToInt16((value * AOUT_VOLUME_MAX + VOLUME_MAX / 2) / VOLUME_MAX); __aout_VolumeSet(vlc, aoutVol); } catch(Exception) { } finally { __vlc_object_release(vlc); } } } } public bool Fullscreen { get { int isFullScreen = GetVlcObjectInt(ObjectType.VLC_OBJECT_VLC, "fullscreen", -666); if((isFullScreen != -666) && (isFullScreen != 0)) { return true; } return false; } set { SetVlcObjectInt(ObjectType.VLC_OBJECT_VLC, "fullscreen", value ? 1 : 0); } } public int PlaylistIndex { get { try { return VLC_PlaylistIndex(this.vlcHandle); } catch(Exception ex) { this.lastErrorMessage = ex.Message; return -1; } } } public int PlaylistCount { get { try { return VLC_PlaylistNumberOfItems(this.vlcHandle); } catch(Exception ex) { this.lastErrorMessage = ex.Message; return -1; } } } #endregion #region public Methods public bool Initialize() { // check if already initializes if(vlcHandle != -1) return true; string oldDir = Environment.CurrentDirectory; // try init try { // create instance Environment.CurrentDirectory = NativeLibVlc.vlcInstallDirectory; this.vlcHandle = VLC_Create(); if(this.vlcHandle < 0) { lastErrorMessage = "Failed to create VLC instance"; return false; } string[] initOptions = { NativeLibVlc.vlcInstallDirectory, ":no-one-instance", ":no-loop", ":no-drop-late-frames", ":disable-screensaver", ":vout=vout_directx", "--plugin-path=" + NativeLibVlc.vlcInstallDirectory + @"/plugins", }; // init libvlc VlcError errVlcLib = VLC_Init(vlcHandle, initOptions.Length, initOptions); if(errVlcLib != VlcError.Success) { VLC_Destroy(vlcHandle); lastErrorMessage = "Failed to initialise VLC"; this.vlcHandle = -1; return false; } } catch { lastErrorMessage = "Could not find libvlc"; return false; } finally { Environment.CurrentDirectory = oldDir; } // check output window if(outputWindow != null) { SetVlcObjectInt(ObjectType.VLC_OBJECT_VLC, "drawable", outputWindow.Handle.ToInt32()); } return true; } // there's an overhead to supporting Vlc events, a memory leak, so we need to have them off by default public bool ProducingEvents { get { return this.gch.IsAllocated; } set { if(value) { if(!this.gch.IsAllocated) { HookPlaylistChanges(); } } else { if(this.gch.IsAllocated) { UnhookPlaylistChanges(); } } } } private static String AdjustFilterString(String current, String filter, bool add) { String newFilter = null; int findFilter = current.IndexOf(filter); if(findFilter == -1) { if(add) { if(current.Length == 0) { newFilter = filter; } else { newFilter = String.Format("{0}:{1}", current, filter); } } } else { if(!add) { int colonAfterAdjust = current.IndexOf(':', findFilter + 1); if(findFilter == 0) { if(colonAfterAdjust == -1) { newFilter = String.Empty; } else { newFilter = current.Substring(colonAfterAdjust + 1); } } else { if(colonAfterAdjust == -1) { newFilter = current.Substring(0, findFilter - 1); } else { newFilter = current.Substring(0, findFilter - 1) + current.Substring(colonAfterAdjust); } } } } return newFilter; } const String VideoFilterList = "vout-filter"; const String AdjustFilter = "adjust"; public bool AllowVideoAdjustments { get { String voutFilter = GetVlcObjectString(ObjectType.VLC_OBJECT_VOUT, VideoFilterList, null); if(voutFilter == null) { GetConfigVariable(VideoFilterList, out voutFilter); } if(voutFilter != null) { return voutFilter.IndexOf(AdjustFilter) != -1; } else { return false; } } set { bool useConfig = false; String voutFilter = GetVlcObjectString(ObjectType.VLC_OBJECT_VOUT, VideoFilterList, null); if(voutFilter == null) { using(VlcObject vlc = new VlcObject(this.vlcHandle, ObjectType.VLC_OBJECT_VLC)) { GetConfigVariable(VideoFilterList, out voutFilter); useConfig = true; } } if(voutFilter != null) { String newVoutFilter = AdjustFilterString(voutFilter, AdjustFilter, value); if(newVoutFilter != null) { if(useConfig) { SetConfigVariable(VideoFilterList, newVoutFilter); } else { SetVlcObjectString(ObjectType.VLC_OBJECT_VOUT, VideoFilterList, newVoutFilter); } } } } } public VlcError AddTarget(string target, ref int itemId) { try { using(VlcObject vobj = new VlcObject(this.vlcHandle, ObjectType.VLC_OBJECT_PLAYLIST)) { if(vobj.SubObject != IntPtr.Zero) { VlcError enmErr = playlist_AddExt(vobj.SubObject, target, target, Mode.Append, EndOfPlaylist, -1L, null, 0); if(enmErr >= VlcError.Success) { itemId = (int)enmErr; } return enmErr; } else { return VlcError.NoObj; } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; return VlcError.Exception; } } public VlcError AddTarget(string target, string[] options, ref int itemId) { int optionsCount = 0; if(options != null) { optionsCount = options.Length; } try { using(VlcObject vobj = new VlcObject(this.vlcHandle, ObjectType.VLC_OBJECT_PLAYLIST)) { if(vobj.SubObject != IntPtr.Zero) { VlcError enmErr = playlist_AddExt(vobj.SubObject, target, target, Mode.Append, EndOfPlaylist, -1L, options, optionsCount); if(enmErr >= VlcError.Success) { itemId = (int)enmErr; } return enmErr; } else { return VlcError.NoObj; } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; return VlcError.Exception; } } public Size VideoSize { get { try { using(VlcPlaylistObject vpobj = new VlcPlaylistObject(this.vlcHandle)) { if(vpobj.SubObject != IntPtr.Zero) { IntPtr p_input = libvlc_playlist_get_input(ref vpobj.libvlc, ref vpobj.exception); if(vpobj.exception.WasExceptionRaised()) { this.lastErrorMessage = Marshal.PtrToStringAnsi(vpobj.exception.psz_message); } else { try { int width = libvlc_video_get_width(p_input, ref vpobj.exception); if(!vpobj.exception.WasExceptionRaised()) { int height = libvlc_video_get_height(p_input, ref vpobj.exception); if(!vpobj.exception.WasExceptionRaised()) { return new Size(width, height); } } } finally { libvlc_input_free(p_input); } } } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; } return new Size(); } } public VlcError Play(int itemId) { try { this.artificialLength = 0; this.timeScaling = 0.0d; using(VlcPlaylistObject vpobj = new VlcPlaylistObject(this.vlcHandle)) { if(vpobj.SubObject != IntPtr.Zero) { libvlc_playlist_play(ref vpobj.libvlc, itemId, 0, IntPtr.Zero, ref vpobj.exception); if(vpobj.exception.WasExceptionRaised()) { return VlcError.Generic; } return VlcError.Success; } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; return VlcError.Exception; } return VlcError.NoObj; } public VlcError Play() { try { using(VlcObject vobj = new VlcObject(this.vlcHandle, ObjectType.VLC_OBJECT_PLAYLIST)) { if(vobj.SubObject != IntPtr.Zero) { return playlist_LockControl(vobj.SubObject, playlist_command.PLAYLIST_PLAY); } else { return VlcError.NoObj; } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; return VlcError.Exception; } } public VlcError Pause() { try { using(VlcObject vobj = new VlcObject(this.vlcHandle, ObjectType.VLC_OBJECT_PLAYLIST)) { if(vobj.SubObject != IntPtr.Zero) { return playlist_LockControl(vobj.SubObject, playlist_command.PLAYLIST_PAUSE); } else { return VlcError.NoObj; } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; return VlcError.Exception; } } public VlcError Stop() { try { using(VlcObject vobj = new VlcObject(this.vlcHandle, ObjectType.VLC_OBJECT_PLAYLIST)) { if(vobj.SubObject != IntPtr.Zero) { return playlist_LockControl(vobj.SubObject, playlist_command.PLAYLIST_STOP); } else { return VlcError.NoObj; } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; return VlcError.Exception; } } public VlcError PlaylistClear() { try { using(VlcObject vobj = new VlcObject(this.vlcHandle, ObjectType.VLC_OBJECT_PLAYLIST)) { if(vobj.SubObject != IntPtr.Zero) { return playlist_Clear(vobj.SubObject); } else { return VlcError.NoObj; } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; return VlcError.Exception; } } public VlcError ToggleVolumeMute() { IntPtr vlc = vlc_current_object(vlcHandle); if(IntPtr.Zero != vlc) { try { return __aout_VolumeMute(vlc, IntPtr.Zero); } catch(Exception) { } finally { __vlc_object_release(vlc); } } return VlcError.NoObj; } public VlcError PressKey(string strKey) { int key = GetVlcObjectInt(ObjectType.VLC_OBJECT_VLC, strKey, -666); if(key != -666) { return SetVlcObjectInt(ObjectType.VLC_OBJECT_VLC, "key-pressed", key); } return VlcError.NoVar; } public VlcError ShowMessage(String message) { try { using(VlcObject vobj = new VlcObject(this.vlcHandle, ObjectType.VLC_OBJECT_INPUT)) { if(vobj.SubObject != IntPtr.Zero) { __vout_OSDMessage(vobj.SubObject, DEFAULT_CHAN, message); return VlcError.Success; } else { return VlcError.NoObj; } } } catch(Exception ex) { this.lastErrorMessage = ex.Message; return VlcError.Exception; } } public VlcError GetConfigVariable(String name, out String value) { value = null; using(VlcObject vlc = new VlcObject(this.vlcHandle, ObjectType.VLC_OBJECT_VLC)) (Chris Meadowcroft) |