2016-04-15 35 views
8

我試圖通過使用示例程序(http://sharpdxwpf.codeplex.com/SourceControl/latest#SharpDX.WPF.sln)來學習SharpDX ...它使用4種不同的方法創建了4個陰影三角形的象限,並且它只是通過重繪圖形來運行。它持續運行,似乎是事件驅動的,因爲我不斷在事件處理程序中觸發斷點(見下文),但我不明白是什麼觸發了這些事件。 在它有XAML。 。 。需要了解此WPF程序中的事件觸發。 。

xmlns:dxc="clr-namespace:SharpDX.WPF;assembly=SharpDX.WPF" 

。 。 。

<dxc:DXElement Grid.Column="0" Grid.Row="0" x:Name="dxview10"/> 
<Image Grid.Column="1" Grid.Row="0" x:Name="img"/>  
<dxc:DXElement Grid.Column="0" Grid.Row="1" x:Name="dxview11"/> 
<dxc:DXElement Grid.Column="1" Grid.Row="1" x:Name="dxview2d"/> 

。 。 。 DXElement的聲明和構造函數看起來像這樣 。 。 。

public class DXElement : FrameworkElement, INotifyPropertyChanged 

public DXElement()  
{   
    base.SnapsToDevicePixels = true;   
    m_renderTimer = new Stopwatch();   
    m_surface = new DXImageSource();   
    m_surface.IsFrontBufferAvailableChanged += delegate   
    {     
     UpdateReallyLoopRendering(); 
     if (!m_isReallyLoopRendering && m_surface.IsFrontBufferAvailable) 
      Render(); 
     }; 
     IsVisibleChanged += delegate { UpdateReallyLoopRendering(); }; 
    } 

DXElement的其餘部分只是簡短的事件處理程序。這裏有一個例子:

protected override void OnRender(DrawingContext dc) 
{ 
    dc.DrawImage(Surface, new Rect(RenderSize)); 
} 

注意「覆蓋」。我假設DXElement的父類之一(FrameworkElement或INotifyPropertyChanged)已經在監聽這些事件。但觸發這些事件? (例如,OnRender(),OnLoopRendering()等)他們似乎是運行該程序的引擎。我如何跟蹤是什麼原因導致這樣的事件在WPF程序中觸發? 如果我在他們設置一個斷點,我看到他們擊中,但他們從framwework調用,例如,

SharpDX.WPF.dll!SharpDX.WPF.DXElement.OnRender(System.Windows.Media .DrawingContext dc)Line 153 C# PresentationCore.dll!System.Windows.UIElement.Arrange(System.Windows.Rect finalRect)Unknown PresentationFramework.dll!System.Windows.Controls.Grid.ArrangeOverride(System.Windows.Size arrangeSize)Unknown PresentationFramework.dll!System.Windows.FrameworkElement.ArrangeCore(System.Windows.Rect finalRect)Unknown PresentationCore.dll !System.Windows.UIElement.Arrange(System.Windows.Rect finalRect)未知 PresentationFramework.dll!MS.Internal.Helper.ArrangeElementWithSingleChild(System.Windows.UIElement 元素,System.Windows.Size arrangeSize)未知 PresentationFramework。 DLL!System.Windows.Controls.ContentPresenter.ArrangeOverride(System.Windows.Size arrangeSize)未知

...所以我不明白什麼程序做的,使這些事件發生。我如何解釋這一點?

回答

1

一個粗略的猜測是,它從一個經常性的計時器中調用InvalidateVisual(),它在某個時候會調用OnRender()

+0

我在整個解決方案中爲「InvalidateVisual」做了一個find-in-files搜索,並且獲得了0次點擊。所以除非從程序中間接調用的框架中調用其他東西,否則這似乎不是。這就是爲什麼我正在尋找某種方式來跟蹤WPF程序中的事件,以查看是什麼觸發了它們。我怎麼做? – user316117

+0

您可以使用https://snoopwpf.codeplex.com/,但它不會返回這樣的低級別事件,也許是XAMLSpy(未經測試)。或者如果你有Reshaper,你可以用Shift + F12鍵找到該方法的用法。 – Aybe

+0

我試過XAMLSpy,但是我找不到它來找到我的程序。我沒有Resharper(我想這就是你的意思是「Reshaper」) – user316117

5

他們使用每幀渲染使用全局CompositionTarget.Rendering事件。對於所有用戶,它被每幀調用一次。你可以在這裏閱讀更多關於它的細節:https://msdn.microsoft.com/en-us/library/ms748838%28v=vs.100%29.aspx

在DXElement源代碼中,您會看到Renderer依賴項屬性。在此屬性的屬性更改處理程序中,如果某些條件匹配(控件可見,而不是設計模式等),您將看到它們如何訂閱提及的CompositionTarget.Rendering事件。他們還開始Stopwatch來測量自開始以來已過去多少時間,然後渲染幀。

至於你提到的OnRender處理程序。在佈局過程中(在父控制決定如何佈置子女時)調用此函數。它在DXElement第一次渲染時調用一次,然後在調整DXElement的大小時調用它,或者調用InvalidateVisual。但是當您的示例中的這些三角形顏色發生變化時,它會調用而不是--這是使用CompositionTarget.Rendering事件完成的。

所以你的問題的簡短答案將是 - 您的示例中使用的所有事件都由WPF呈現系統觸發。