共用方式為


最佳化效能:2D 圖形和影像處理

WPF 提供各種 2D 圖形和影像處理功能,可以針對您的應用程式需求最佳化。 本主題提供下列領域的效能最佳化相關資訊。

繪圖和圖形

WPF 提供 DrawingShape 物件來表示圖形化繪圖內容。 不過,Drawing 物件的建構比 Shape 物件更簡單,並提供更佳的效能特性。

Shape 可讓您將圖像圖形繪製到螢幕上。 因為它們衍生自 FrameworkElement 類別,所以 Shape 物件可以在面板與大多數控制項內使用。

WPF 提供了數層的圖形和轉譯服務存取權。 您可以輕鬆使用位於最上層的 Shape 物件,其提供版面配置和事件處理等許多實用的功能。 WPF 則提供數個立即可用的圖形物件。 所有圖形物件都是繼承自 Shape 類別。 可用的圖形物件包括 EllipseLinePathPolygonPolylineRectangle

相反地,Drawing 物件不是衍生自 FrameworkElement 類別,並可提供輕量型實作以呈現圖形、影像和文字。

Drawing 物件可分為四種類型:

GeometryDrawing 物件用於轉譯幾何內容。 Geometry 類別和衍生自它的具體類別,例如 CombinedGeometryEllipseGeometryPathGeometry,提供轉譯 2D 圖形和提供點擊測試和裁剪支援的方法。 舉例來說,Geometry 物件可用來定義控制項的區域,或定義要套用至影像的裁剪區域。 Geometry 物件可以是矩形和圓形之類的簡單區域,或從兩個或多個 Geometry 物件建立的複合區域。 結合 PathSegment 衍生物件,例如 ArcSegmentBezierSegmentQuadraticBezierSegment,即可建立更複雜的幾何區域。

表面上,Geometry 類別和 Shape 類別類似。 兩者都用於 2D 圖形的轉譯,而且都有衍生自它們的類似具體類別,例如,EllipseGeometryEllipse。 不過,這兩組類別之間有非常重要的差異。 一方面,Geometry 類別缺少 Shape 類別的一些功能,例如繪製自身的能力。 若要繪製 Geometry 物件,必須使用 DrawingContext、Drawing 或 Path (注意,Path 也是一種 Shape) 等其他類別來執行繪製作業。 填滿、筆觸以及筆觸粗細等呈現屬性位於可繪製幾何物件的類別中,而圖形物件則包含這些屬性。 針對這項差異的其中一個理解方式是:幾何物件可定義區域 (例如圓形);而圖形物件則可定義區域、該區域的填滿方式和外框方式,並參與版面配置系統。

由於 Shape 物件衍生自 FrameworkElement 類別,因此使用這些物件將在應用程式中增加顯著更多的記憶體耗用量。 如果您的圖形化內容真的不需要 FrameworkElement 功能,請考慮使用較輕量的 Drawing 物件。

如需 Drawing 物件的詳細資訊,請參閱 繪圖物件概觀

StreamGeometry 物件

StreamGeometry 物件是用來建立幾何圖形的 PathGeometry 的輕量型替代方案。 當您需要描述複雜幾何時,請使用 StreamGeometry 。 相較於使用許多個別 PathGeometry 物件,StreamGeometry 已針對處理許多 PathGeometry 物件進行最佳化,且執行效能更好。

下列範例使用屬性語法在 XAML 中建立三角形 StreamGeometry

<Page xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
  xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
  <StackPanel>
  
    <Path Data="F0 M10,100 L100,100 100,50Z" 
      StrokeThickness="1" Stroke="Black"/>

  </StackPanel>
</Page>

如需 StreamGeometry 物件的詳細資訊,請參閱 使用 StreamGeometry 建立圖形

DrawingVisual 物件

DrawingVisual 該物件是用來轉譯圖形、影像或文字的輕量型繪圖類別。 此類別之所以被視為輕量型,是因為它不提供版面配置或事件處理,這使它有更好的效能。 基於此原因,繪圖適合背景或美工圖案。 如需詳細資訊,請參閱使用 DrawingVisual 物件

影像

WPF 影像處理可大幅提升舊版 Windows 中的影像處理功能。 以往,影像處理功能 (例如顯示點陣圖或使用通用控制項上的影像) 主要是由 Microsoft Windows 圖形裝置介面 (GDI) 或 Microsoft Windows GDI+ 應用程式開發介面 (API) 進行處理。 這些 API 提供基本影像處理功能,但無法支援轉碼器擴充性和高畫質影像等功能。 WPF 影像處理 API 的設計目的是克服 GDI 和 GDI+ 的缺點,並提供一組新的 API 以在應用程式內顯示及使用影像。

使用影像時,請考慮下列建議事項以取得較佳的效能:

  • 如果您的應用程式需要顯示縮圖影像,請考慮建立影像的縮小版本。 WPF 預設會載入您的影像,並將其解碼到完整大小。 如果您只需要影像的縮圖版本,WPF 仍會多此一舉地將影像解碼到完整大小,然後再縮至縮圖大小。 為了避免不必要的額外負荷,您可以要求 WPF 解碼影像至縮圖大小,或要求 WPF 載入縮圖大小的影像。

  • 一律將影像解碼至所需大小,而非預設大小。 如上所述,您可以要求 WPF 將影像解碼至所需大小,而不是預設的完整大小。 這麼做不只能減少應用程式的工作集,還會降低執行速度。

  • 因此,可能的話,請將影像合併單一影像,例如多張影像組成的底片。

  • 如需詳細資訊,請參閱 影像處理概觀

BitmapScalingMode

建立任何點陣圖的比例動畫時,預設的高品質影像重新取樣演算法有時會耗用過多系統資源,導致畫面播放速率降低,從而造成動畫中斷。 藉由將 RenderOptions 物件的 BitmapScalingMode 屬性設定為 LowQuality,您可以在調整點陣圖時建立更順暢的動畫。 LowQuality 模式會指示 WPF 轉譯引擎在處理影像時,從品質最佳化的演算法切換到速度最佳化的演算法。

下列範例示範如何設定影像物件的 BitmapScalingMode

// Set the bitmap scaling mode for the image to render faster.
RenderOptions.SetBitmapScalingMode(MyImage, BitmapScalingMode.LowQuality);
' Set the bitmap scaling mode for the image to render faster.
RenderOptions.SetBitmapScalingMode(MyImage, BitmapScalingMode.LowQuality)

CachingHint

根據預設,WPF 不會快取 TileBrush 物件的轉譯內容,例如 DrawingBrushVisualBrush。 在場景中 TileBrush 的內容與使用不會變更的靜態案例中,這很合理,因為它會節省影片記憶體。 當靜態內容 TileBrush 以非靜態方式使用時,當靜態 DrawingBrushVisualBrush 對應到旋轉 3D 物件的表面時,它就沒有那麼有意義。 WPF 的預設行為是針對每個畫面重新轉譯 DrawingBrushVisualBrush 的整個內容,即使內容未變更也一樣。

藉由將 RenderOptions 物件的 CachingHint 屬性設定為 Cache,您可以使用快取版本的圖塊筆刷物件來提升效能。

CacheInvalidationThresholdMinimumCacheInvalidationThresholdMaximum 屬性值是相對大小值,可決定 TileBrush 物件何時因縮放比例變更而重新產生。 例如,藉由將 CacheInvalidationThresholdMaximum 屬性設定為 2.0,TileBrush 的快取只需要在大小超過目前快取的大小兩倍時重新產生。

下列範例示範如何使用 DrawingBrush 的快取提示選項。

DrawingBrush drawingBrush = new DrawingBrush();

// Set the caching hint option for the brush.
RenderOptions.SetCachingHint(drawingBrush, CachingHint.Cache);

// Set the minimum and maximum relative sizes for regenerating the tiled brush.
// The tiled brush will be regenerated and re-cached when its size is
// 0.5x or 2x of the current cached size.
RenderOptions.SetCacheInvalidationThresholdMinimum(drawingBrush, 0.5);
RenderOptions.SetCacheInvalidationThresholdMaximum(drawingBrush, 2.0);
Dim drawingBrush As New DrawingBrush()

' Set the caching hint option for the brush.
RenderOptions.SetCachingHint(drawingBrush, CachingHint.Cache)

' Set the minimum and maximum relative sizes for regenerating the tiled brush.
' The tiled brush will be regenerated and re-cached when its size is
' 0.5x or 2x of the current cached size.
RenderOptions.SetCacheInvalidationThresholdMinimum(drawingBrush, 0.5)
RenderOptions.SetCacheInvalidationThresholdMaximum(drawingBrush, 2.0)

另請參閱