ramya
ramya

Reputation: 113

wpf 'System.Windows.Controls.ContentControl.Content' threw an exception. Specified element is already the logical child of another element

I have a WPF application for playing a video and then navigating to another screen. The application plays the video first, and navigating to page2.xaml and again navigating to videos page I get the below exception.

My xaml looks like this:

<Grid HorizontalAlignment="Stretch" VerticalAlignment="Stretch" Name="MainGrid">     
  <ContentControl x:Name="cntctrl" Content="{Binding VlcObject}" HorizontalAlignment="Stretch" VerticalAlignment="Stretch" />
</Grid>

The VlcObject is an instance of Vlc.DotNet.Wpf.VlcControl and I have noticed that VlcObject.MediaPlayer is being disposed on navigating to the second page. So on navigating to videos page, I am creating a new instance of VlcObject. My ViewModel looks like this:

    private Vlc.DotNet.Wpf.VlcControl _vlcObject = null;
    public Vlc.DotNet.Wpf.VlcControl VlcObject
    {
        get { return _vlcObject; }
        set { Set(nameof(VlcObject), ref _vlcObject, value); }
    }
    private void InitialiseVLC()
    {
        if (VlcObject == null || VlcObject.MediaPlayer.IsDisposed)
        {
            DispatcherHelper.CheckBeginInvokeOnUI(() =>
            {
                VlcObject = null;
                VlcObject = new Vlc.DotNet.Wpf.VlcControl();
                VlcObject.MediaPlayer.VlcLibDirectoryNeeded += MediaPlayer_VlcLibDirectoryNeeded;
                VlcObject.MediaPlayer.EndInit();
                VlcObject.MediaPlayer.Opening += MediaPlayer_Opening;
                VlcObject.MediaPlayer.EndReached += MediaPlayer_EndReached;
                VlcObject.MediaPlayer.EncounteredError += MediaPlayer_EncounteredError;
                VlcObject.MediaPlayer.Disposed += MediaPlayer_Disposed;
            });
        }
    }
    private void MediaPlayer_Disposed(object sender, EventArgs e)
    {
        Logger.LogInfo("Media Player is disposed.");
        DispatcherHelper.CheckBeginInvokeOnUI(() =>
        {
            try
            {
                VlcObject.MediaPlayer.VlcLibDirectoryNeeded -= MediaPlayer_VlcLibDirectoryNeeded;
                VlcObject.MediaPlayer.Opening -= MediaPlayer_Opening;
                VlcObject.MediaPlayer.EndReached -= MediaPlayer_EndReached;
                VlcObject.MediaPlayer.EncounteredError -= MediaPlayer_EncounteredError;
                VlcObject.MediaPlayer.Disposed -= MediaPlayer_Disposed;
                //VlcObject = null;

            }
            catch (Exception ex)
            {
                Logger.LogError("Error while disposing MediaPlayer: ");
                Logger.LogError(ex);
            }
        });
    }
    public void OnNavigatedTo(object parameter, bool isBack = false)
    {            
            InitializeVLC();
    }

Here is the exception I get:

System.Windows.Markup.XamlParseException: Set property 'System.Windows.Controls.ContentControl.Content' threw an exception. ---> System.InvalidOperationException: Specified element is already the logical child of another element. Disconnect it first. at System.Windows.FrameworkElement.ChangeLogicalParent(DependencyObject newParent) at System.Windows.FrameworkElement.AddLogicalChild(Object child) at System.Windows.Controls.ContentControl.OnContentChanged(Object oldContent, Object newContent) at System.Windows.Controls.ContentControl.OnContentChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) at System.Windows.DependencyObject.OnPropertyChanged(DependencyPropertyChangedEventArgs e) at System.Windows.FrameworkElement.OnPropertyChanged(DependencyPropertyChangedEventArgs e) at System.Windows.DependencyObject.NotifyPropertyChange(DependencyPropertyChangedEventArgs args) at System.Windows.DependencyObject.UpdateEffectiveValue(EntryIndex entryIndex, DependencyProperty dp, PropertyMetadata metadata, EffectiveValueEntry oldEntry, EffectiveValueEntry& newEntry, Boolean coerceWithDeferredReference, Boolean coerceWithCurrentValue, OperationType operationType) at System.Windows.DependencyObject.SetValueCommon(DependencyProperty dp, Object value, PropertyMetadata metadata, Boolean coerceWithDeferredReference, Boolean coerceWithCurrentValue, OperationType operationType, Boolean isInternal) at System.Windows.Baml2006.WpfKnownMemberInvoker.SetValue(Object instance, Object value) at MS.Internal.Xaml.Runtime.ClrObjectRuntime.SetValue(XamlMember member, Object obj, Object value) at MS.Internal.Xaml.Runtime.ClrObjectRuntime.SetValue(Object inst, XamlMember property, Object value) --- End of inner exception stack trace --- at System.Windows.Markup.XamlReader.RewrapException(Exception e, IXamlLineInfo lineInfo, Uri baseUri) at System.Windows.Markup.WpfXamlLoader.Load(XamlReader xamlReader, IXamlObjectWriterFactory writerFactory, Boolean skipJournaledProperties, Object rootObject, XamlObjectWriterSettings settings, Uri baseUri) at System.Windows.Markup.WpfXamlLoader.LoadBaml(XamlReader xamlReader, Boolean skipJournaledProperties, Object rootObject, XamlAccessLevel accessLevel, Uri baseUri) at System.Windows.Markup.XamlReader.LoadBaml(Stream stream, ParserContext parserContext, Object parent, Boolean closeStream) at System.Windows.Application.LoadBamlStreamWithSyncInfo(Stream stream, ParserContext pc) at MS.Internal.AppModel.AppModelKnownContentFactory.BamlConverter(Stream stream, Uri baseUri, Boolean canUseTopLevelBrowser, Boolean sandboxExternalContent, Boolean allowAsync, Boolean isJournalNavigation, XamlReader& asyncObjectConverter) at MS.Internal.AppModel.MimeObjectFactory.GetObjectAndCloseStream(Stream s, ContentType contentType, Uri baseUri, Boolean canUseTopLevelBrowser, Boolean sandboxExternalContent, Boolean allowAsync, Boolean isJournalNavigation, XamlReader& asyncObjectConverter) at System.Windows.Navigation.NavigationService.GetObjectFromResponse(WebRequest request, WebResponse response, Uri destinationUri, Object navState)
at System.Windows.Navigation.NavigationService.DoNavigate(Uri source, NavigationMode f, Object navState) at System.Windows.Navigation.NavigateQueueItem.Dispatch(Object obj) at System.Windows.Threading.ExceptionWrapper.InternalRealCall(Delegate callback, Object args, Int32 numArgs) at MS.Internal.Threading.ExceptionFilterHelper.TryCatchWhen(Object source, Delegate method, Object args, Int32 numArgs, Delegate catchHandler)

Can some one please help me.

Upvotes: 0

Views: 2817

Answers (2)

Martin Lottering
Martin Lottering

Reputation: 1812

The "Disconnect it first." part of the error message is key here. Since you are binding the content, it sounds like the same binding is active on another control (or page). You should try to ensure that the content is not bound to more than one control. Do the pages share the same view model? You could try to have a unique view model for each page with a unique content wrapper for each view model.

Upvotes: 0

Related Questions