Přehled analýzy XAML

Analýza XAML je nástroj, který vás upozorní na problémy s výkonem ve vaší aplikaci. Kontroluje kód aplikace na základě sady pokynů k výkonu a osvědčených postupů a identifikuje problémy ze sady běžných problémů.

Když nástroj najde problém, odkazuje na diagnostické nástroje Visual Studio, informace o zdroji a dokumentaci, abyste mohli problém prošetřit a opravit.

Dekódovaná velikost obrázku větší než velikost vykreslení

Obrázky zachycené ve vysokém rozlišení můžou způsobit, že vaše aplikace po načtení z disku použije více procesoru při dekódování a více paměti. Neexistuje žádná výhoda dekódování obrázku s vysokým rozlišením, pokud ho zobrazíte pouze s menší velikostí. Místo toho vytvořte verzi obrázku v takové velikosti, v jaké ho vykreslujete na obrazovce, pomocí vlastností DecodePixelWidth a DecodePixelHeight.

Dopad

Zobrazení imagí v jiných velikostech, než je jejich nativní velikost, může negativně ovlivnit čas procesoru (dekódování a stahování) a paměť.

Příčiny a řešení

Obrázek není nastaven asynchronně

Vaše aplikace používá SetSource() místo SetSourceAsync(). Při nastavování datového proudu k asynchronnímu dekódování obrázků vždy používejte SetSourceAsync .

Zdroj obrázku je nastaven před tím, než je prvek v živém stromu.

BitmapImage je po nastavení obsahu pomocí SetSourceAsync nebo UriSource připojen k aktivnímu stromu XAML. Před nastavením zdroje vždy připojte BitmapImage k živému stromu. Když v kódu značek určíte prvek obrázku nebo štětec, připojení proběhne automaticky.

Dobré — zdroj určený pomocí značky BitmapImage:

<Image x:Name="myImage">
    <Image.Source>
        <BitmapImage UriSource="Assets/cool-image.png"/>
    </Image.Source>
</Image>

Dobré – propojení BitmapImage se stromem před nastavením jeho UriSource:

Image myImage = new Image();
var bitmapImage = new BitmapImage();
myImage.Source = bitmapImage;
bitmapImage.UriSource = new Uri("ms-appx:///Assets/cool-image.png", UriKind.RelativeOrAbsolute);

Špatně — nastavení vlastnosti UriSource objektu BitmapImage před připojením do stromu:

Image myImage = new Image();
var bitmapImage = new BitmapImage();
bitmapImage.UriSource = new Uri("ms-appx:///Assets/cool-image.png", UriKind.RelativeOrAbsolute);
myImage.Source = bitmapImage;

Obrázkový štětec je neobdélníkový

Když použijete obrázek pro neobdélníkový štětec, obrázek se vykresluje pomocí softwarového rastrování, které nemění měřítko obrázků. Systém navíc ukládá kopii image do softwarové i hardwarové paměti. Když použijete neúdvoúhlý štětec, předem škálujte obrázky na velikost, na kterou je vykreslujete.

Případně nastavte explicitní velikost dekódování pomocí vlastností DecodePixelWidth a DecodePixelHeight :

<Image>
    <Image.Source>
    <BitmapImage UriSource="ms-appx:///Assets/highresCar.jpg"
                 DecodePixelWidth="300" DecodePixelHeight="200"/>
    </Image.Source>
</Image>

Jednotky pro DecodePixelWidth a DecodePixelHeight jsou ve výchozím nastavení fyzické pixely. Nastavte DecodePixelType na Logical, aby velikost dekódovaného obrázku automaticky zohlednila aktuální faktor škálování systému, podobně jako u ostatního obsahu XAML.

Pokud nemůžete předem určit vhodnou velikost dekódování, spolehněte se na automatické dekódování na správnou velikost v XAML, které se podle možností snaží dekódovat obrázek v odpovídající velikosti.

Obrázky používané uvnitř BitmapIcons se vrátí k přirozené velikosti.

Nastavte explicitní dekódovací velikost pomocí DecodePixelWidth vlastností a DecodePixelHeight vlastností.

DecodePixelWidth nebo DecodePixelHeight jsou větší než velikost zobrazení

Pokud explicitně nastavíte DecodePixelWidth nebo DecodePixelHeight na hodnotu větší, než je velikost zobrazení obrázku na obrazovce, aplikace využije více paměti (až 4 bajty na pixel), což je u velkých obrázků nákladné.

Obrázek je skrytý.

Obrázek je skryt nastavením Opacity na hodnotu 0 nebo Visibility na Collapsed u prvku hostitelského obrázku, štětce nebo nadřazeného prvku. Obrázky, které nejsou na obrazovce viditelné kvůli oříznutí nebo průhlednosti, se můžou vrátit k dekódování v přirozené velikosti.

Image používá vlastnost NineGrid.

Při použití image s NineGrid, image používá softwarovou rasterizační cestu. Obrázky předem změňte přibližně na velikost, v jaké je vykreslujete.

Sbalené prvky v době načtení

Běžným vzorem je zpočátku skrytí prvků uživatelského rozhraní a jejich pozdější zobrazení. Ve většině případů byste měli tyto prvky odložit pomocí x:Load, abyste se vyhnuli nákladům na vytvoření prvku při načítání.

Dopad

Sbalené prvky se načítají společně s ostatními prvky a prodlužují dobu načítání.

Solution

Ke zpoždění načítání uživatelského rozhraní použijte atribut x:Load . Prvek se načte, když ho potřebujete, což snižuje počáteční nároky na zpracování. Můžete také použít x:Bind k řízení stavu načítání.

ListView není virtualizovaný

Virtualizace uživatelského rozhraní je nejdůležitější úprava, kterou můžete provést pro zvýšení výkonu kolekcí. Prvky uživatelského rozhraní představující položky se vytvářejí na vyžádání. V případě ovládacího prvku vázaného na kolekci 1000 položek vytváření veškerého uživatelského rozhraní najednou ztrácí prostředky, protože nemůžete zobrazit všechny položky současně. ListView a GridView zpracují virtualizaci uživatelského rozhraní za vás – vygenerují uživatelské rozhraní pro položky v blízkosti oblasti zobrazení a uvolní paměť pro položky, které se posunou mimo zobrazení.

Dopad

Nevirtualizovaný ItemsControl prodlužuje dobu načítání a zvyšuje využití prostředků tím, že načítá více podřízených položek, než je nutné.

Solution

Nastavte šířku a výšku ItemsControl pro definování oblasti zobrazení. Když umístíte virtualizovaný ovládací prvek do panelu s neomezeným prostorem (například ScrollViewer nebo Grid s řádky s automatickou velikostí), ovládací prvek zabere dostatek místa pro všechny položky, čímž se virtualizace míjí účinkem.

Vlákno uživatelského rozhraní během načítání blokováno nebo nečinné

K blokování vlákna uživatelského rozhraní dochází v případě, že synchronní volání funkcí, které spouští mimo vlákno, blokuje vlákno uživatelského rozhraní. Udržujte vlákno uživatelského rozhraní responzivní pomocí asynchronních rozhraní API. Další informace najdete v tématu Zachování odezvy vlákna uživatelského rozhraní.

Místo {Binding} použijte {x:Bind}.

{Binding} používá více času a paměti než {x:Bind}. Vytvoření {Binding} způsobí sérii alokací a aktualizace cíle vazby může zahrnovat reflexi a boxování. Použijte {x:Bind}, který kompiluje vazby v době sestavení pro lepší výkon a ověřování v době kompilace.

Note

{x:Bind} není vhodný ve všech případech, například ve scénářích s pozdní vazbou. Podrobnosti najdete v dokumentaci k aplikaci {x:Bind} .

Použijte x:Key místo x:Name ve slovnících zdrojů

Když u prostředku použijete x:Name, platforma ho okamžitě vytvoří, protože x:Name vytváří odkaz na pole. Místo toho použijte x:Key, pokud nepotřebujete na prostředek odkazovat v souboru code-behind.

Použití virtualizačních panelů pro kolekce

Pokud zadáte vlastní šablonu panelu položek (viz ItemsPanel), použijte virtualizační panel, například ItemsWrapGrid nebo ItemsStackPanel. Použití VariableSizedWrapGrid, WrapGrid nebo StackPanel zakáže virtualizaci.

Přístupnost: Zadání názvů prvků UIA

Nastavte AutomationProperties.Name v kódu XAML ovládacího prvku na odpovídající lokalizovaný řetězec. Pokud by se prvek neměl objevit ve stromu UIA, nastavte AutomationProperties.AccessibilityView = "Raw".

Nepřiřazujte dvěma prvkům UIA se stejným nadřazeným prvkem stejné Name a ControlType. V seznamech, kde se běžně vyskytují duplicitní názvy, použijte datovou vazbu k nastavení AutomationProperties.Name ze zdroje dat.