Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/.net/22.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何设置由第三方计时器更新的DependencyProperty?_C#_.net_Wpf - Fatal编程技术网

C# 如何设置由第三方计时器更新的DependencyProperty?

C# 如何设置由第三方计时器更新的DependencyProperty?,c#,.net,wpf,C#,.net,Wpf,我正在玩Vlc.DotNet库(Nuget:Vlc.DotNet/)。它实际上是一个围绕libvlc.dll的WinForms包装器,带有一个非常粗略的WPF控件实现,它只将WinForms控件包装在HwndHost中: //WPF control class public class VlcControl : HwndHost { //The WPF control has a property called MediaPlayer, //which is an instan

我正在玩Vlc.DotNet库(Nuget:Vlc.DotNet/)。它实际上是一个围绕libvlc.dll的WinForms包装器,带有一个非常粗略的WPF控件实现,它只将WinForms控件包装在HwndHost中:

//WPF control class
public class VlcControl : HwndHost 
{
    //The WPF control has a property called MediaPlayer,
    //which is an instance of Forms.VlcControl
    public Forms.VlcControl MediaPlayer { get; private set; }

    //WPF control constructor
    public VlcControl()
    {
        MediaPlayer = new Forms.VlcControl();
    }

    //BuildWindowCore and DestroyWindowCore methods omitted for brevity
}
这意味着,如果我想绑定到任何东西,我需要跳过一些环。如果我的WPF控件实例名为MyWpfControl,我需要通过MyWpfVlcControl.MediaPlayer来解决所有问题。[SomeMethod/SomeProperty]。我想向WPF控件添加一些DependencyProperties以使绑定更容易。我在计时器上更新的属性以及由备份dll和用户通过WPF控件设置的属性方面遇到问题

WinForms player具有long类型的Time属性,表示已用媒体时间(以毫秒为单位)。它还有一个名为TimeChanged的事件,该事件在播放过程中不断激发,更新已用的媒体时间

我已为TimeChanged事件向WPF控件添加了一个事件处理程序:

//WPF control constructor
public VlcControl()
{
    MediaPlayer = new Forms.VlcControl();

    MediaPlayer.TimeChanged += OnTimeChangedInternal;
}

private void OnTimeChangedInternal(object sender, VlcMediaPlayerTimeChangedEventArgs e)
{
    Time = e.NewTime;
}
如果我在WPF控件中设置DependencyProperty来包装时间,它看起来如下所示:

// Using a DependencyProperty as the backing store for Time.  This enables animation, styling, binding, etc...
public static readonly DependencyProperty TimeProperty =
    DependencyProperty.Register("Time", typeof(long), typeof(VlcControl), new FrameworkPropertyMetadata(0L, new PropertyChangedCallback(OnTimeChanged)));

/// <summary>
/// Sets and gets the Time property.
/// </summary>
public long Time
{
    get
    {
        return (long)this.GetValue(TimeProperty);
    }

    set
    {
        this.Dispatcher.Invoke((Action)(() =>
        {
            this.SetValue(TimeProperty, value);
        }));
    }
}

private static void OnTimeChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{ 
    //Tried this - bad idea!       
    //MediaPlayer.Time = (long)e.NewValue;        
}  
//使用DependencyProperty作为时间的后备存储。这将启用动画、样式、绑定等。。。
公共静态只读DependencyProperty TimeProperty=
DependencyProperty.Register(“时间”、typeof(长)、typeof(VlcControl)、new FrameworkPropertyMetadata(0L、new PropertyChangedCallback(OnTimeChanged));
/// 
///设置并获取时间属性。
/// 
公众长期
{
得到
{
返回(长)this.GetValue(TimeProperty);
}
设置
{
this.Dispatcher.Invoke((操作)(()=>
{
this.SetValue(TimeProperty,value);
}));
}
}
私有静态void OnTimeChanged(DependencyObject d、DependencyPropertyChangedEventArgs e)
{ 
//尝试过这个-坏主意!
//MediaPlayer.Time=(long)e.NewValue;
}  
时间从libvlc.dll->WinForms->WPF漂亮地更新。不幸的是,如果我想从WPF控件设置MediaPlayer.Time属性,我需要将上面的注释行合并到OnTimeChanged中。当这是未注释的,并且MediaPlayer更新时间属性(与WPF控件相反)时,它会进入一个无限循环:TimeChanged->SetTime->TimeChanged->SetTime->


有没有更好的方法来实现这一点?我可以在某个地方添加一个参数来指示时间是从WPF还是从WinForms代码设置的吗?

您可以尝试实现一种类型的指示器来防止无限循环。比如:

bool isUpdating = false;
private static void OnTimeChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{ 
    if (!isUpdating)
    {
        isUpdating = true;
        MediaPlayer.Time = (long)e.NewValue;
        isUpdating = false;
    }
}  

只是想澄清一下VlcControl和Forms.VlcControl是不同的类,对吗?让人很难理解什么是什么。是的,VlcControl和Forms.VlcControl是不同的类。我会把这个问题快速地看一遍,看看是否能把事情弄清楚一点。不过我想这会给你一次往返的机会。一开始我也在想同样的事情。这就是我最后的想法。我必须将我的指示符字段声明为static,才能将其放入static OnTimeChanged方法的作用域中。在
OnTimeChanged
中,您有一个引发该方法的对象(在上面的代码中称为
d
)。因此,您可以将其强制转换为
VlcControl
,并在控件上使用公共属性,而不是静态标志。