This article has been localized into Romanian by the community.
Resurse
WPF introduce un concept foarte util: Abilitatea de a stoca date ca o resursă, fie la nivel local pentru un control, local pentru întreaga fereastră sau global pentru întreaga aplicație. Datele pot fi oricare doriți, de la informații reale la o ierarhie a controalelor WPF. Acest lucru vă permite să plasați datele într-un singur loc și apoi să le utilizați din mai multe locuri, ceea ce este foarte util.
Conceptul este folosit foarte mult pentru stiluri și șabloane, pe care le vom discuta mai târziu în acest tutorial, dar după cum vom arăta în acest capitol, puteți să-l utilizați și pentru multe alte lucruri. Permiteți-mi să o demonstrez cu un simplu exemplu
<Window x:Class="WpfTutorialSamples.WPF_Application.ResourceSample"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:sys="clr-namespace:System;assembly=mscorlib"
Title="ResourceSample" Height="150" Width="350">
<Window.Resources>
<sys:String x:Key="strHelloWorld">Hello, world!</sys:String>
</Window.Resources>
<StackPanel Margin="10">
<TextBlock Text="{StaticResource strHelloWorld}" FontSize="56" />
<TextBlock>Just another "<TextBlock Text="{StaticResource strHelloWorld}" />" example, but with resources!</TextBlock>
</StackPanel>
</Window>
Resurselor li se alocă cu o cheie, folosind atributul x: Key, care vă permite să le referiți din alte părți ale aplicației utilizând această cheie, în combinație cu extensia de marcare StaticResource. În acest exemplu, stocăm doar un șir simplu, pe care apoi îl folosesc de la două controale TextBlock diferite.
StaticResource vs. DynamicResource
În exemplele de până acum, am folosit extensia de markup (limbaj de marcaje) StaticResource pentru a trimite o referință la o resursă. Cu toate acestea, există o alternativă, sub forma DynamicResource.
Principala diferență este că o resursă statică este rezolvată doar o singură dată, în punctul în care este încărcat XAML-ul. Dacă resursa este apoi modificată ulterior , această modificare nu va fi reflectată în cazul în care ați utilizat StaticResource.
O DynamicResource, pe de altă parte, este rezolvată odată ce este efectiv necesar, iar apoi, din nou, dacă resursa se schimbă. Gândește-te la asta ca fiind legătură la o valoare statică versus legarea la o funcție care monitorizează această valoare și o trimite la fiecare dată când este schimbată - nu funcționează exact așa, ci ar trebui să vă dea o idee mai bună despre când să folosești și ce anume. Resursele dinamice vă permit, de asemenea, să utilizați resurse care nici măcar nu există în timpul proiectării, de exemplu dacă le adăugați de la Code-behind la pornirea aplicației.
Mai multe tipuri de resurse
Partajarea unui șir simplu a fost ușoară, dar puteți face mult mai mult. În următorul exemplu, voi stoca, de asemenea, o gamă completă de șiruri de caractere, împreună cu un gradient de culoare pentru a fi utilizat pentru fundal. Acest lucru ar trebui să vă dau o idee destul de bună despre cât de multe puteți face cu resursele:
<Window x:Class="WpfTutorialSamples.WPF_Application.ExtendedResourceSample"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:sys="clr-namespace:System;assembly=mscorlib"
Title="ExtendedResourceSample" Height="160" Width="300"
Background="{DynamicResource WindowBackgroundBrush}">
<Window.Resources>
<sys:String x:Key="ComboBoxTitle">Items:</sys:String>
<x:Array x:Key="ComboBoxItems" Type="sys:String">
<sys:String>Item #1</sys:String>
<sys:String>Item #2</sys:String>
<sys:String>Item #3</sys:String>
</x:Array>
<LinearGradientBrush x:Key="WindowBackgroundBrush">
<GradientStop Offset="0" Color="Silver"/>
<GradientStop Offset="1" Color="Gray"/>
</LinearGradientBrush>
</Window.Resources>
<StackPanel Margin="10">
<Label Content="{StaticResource ComboBoxTitle}" />
<ComboBox ItemsSource="{StaticResource ComboBoxItems}" />
</StackPanel>
</Window>
De data aceasta, am adăugat câteva resurse suplimentare, astfel încât Fereastra noastră conține acum un șir simplu, o serie de șiruri de caractere și un LinearGradientBrush. șirul este folosit pentru etichetă,vectorul de șiruri de caractere sunt folosite ca elemente pentru controlul ComboBox și gradientul de culoare este folosit ca fundal pentru întreaga fereastră. Deci, după cum puteți vedea, aproape orice poate fi stocat ca o resursă.
Resurse locale si resurse la nivel de aplicatie
Deocamdată, am stocat resurse la nivel de fereastră, ceea ce înseamnă că le puteți accesa peste tot în fereastra.
Dacă aveți nevoie doar de o resursă dată pentru un anumit control, puteți să o faceți mai locală prin adăugarea acesteia la acest control specific, în locul ferestrei. Functioneaza exact în același mod, singura diferență fiind că puteți accesa acum doar din interiorul domeniului din controlului în care o puneți:
<StackPanel Margin="10">
<StackPanel.Resources>
<sys:String x:Key="ComboBoxTitle">Items:</sys:String>
</StackPanel.Resources>
<Label Content="{StaticResource ComboBoxTitle}" />
</StackPanel>
În acest caz, adăugăm resursa la StackPanel și apoi o folosim din controlul copil, eticheta. Alte controale din interiorul StackPanel ar putea fi a folosita, de asemenea, la fel precum controalele copiil care-l pot accesa. Controalele din afara acestui StackPanel nu ar avea accesul la acesta, totuși.
Dacă aveți nevoie de capacitatea de a accesa resursele din mai multe ferestre, este posibil și acest lucru. Fișierul App.xaml poate conține resurse la fel ca și fereastra și orice fel de control WPF și când le stocați în App.xaml, acestea sunt accesibile la nivel global în toate ferestrele și comenzile utilizatorilor proiectului. Acest lucru funcționează exact la fel ca atunci când se stochează și se folosesc dintr-o Fereastră:
<Application x:Class="WpfTutorialSamples.App"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:sys="clr-namespace:System;assembly=mscorlib"
StartupUri="WPF application/ExtendedResourceSample.xaml">
<Application.Resources>
<sys:String x:Key="ComboBoxTitle">Items:</sys:String>
</Application.Resources>
</Application>
Folosirea lor va fi aceeași - WPF va merge pe firul apei, din controlul local, la fereastră și apoi la App.xaml, pentru a găsi resursa cerută:
<Label Content="{StaticResource ComboBoxTitle}" />
Resurse de la codul asociat
Până acum, am accesat toate resursele noastre direct dina XAML, folosind o extensie a markup-ului (xml din XAML). Cu toate acestea, puteți, desigur, să vă accesați resursele și din codul asociat, ceea ce poate fi util în mai multe situații. În exemplul anterior, am văzut cum am putea stoca resursele în mai multe locuri diferite, astfel că, în acest exemplu, vom accesa trei resurse diferite din Codul asociat, fiecare stocată într-un alt scop (domeniu de aplicare):
App.xaml:
<Application x:Class="WpfTutorialSamples.App"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:sys="clr-namespace:System;assembly=mscorlib"
StartupUri="WPF application/ResourcesFromCodeBehindSample.xaml">
<Application.Resources>
<sys:String x:Key="strApp">Hello, Application world!</sys:String>
</Application.Resources>
</Application>
Fereastra:
<Window x:Class="WpfTutorialSamples.WPF_Application.ResourcesFromCodeBehindSample"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:sys="clr-namespace:System;assembly=mscorlib"
Title="ResourcesFromCodeBehindSample" Height="175" Width="250">
<Window.Resources>
<sys:String x:Key="strWindow">Hello, Window world!</sys:String>
</Window.Resources>
<DockPanel Margin="10" Name="pnlMain">
<DockPanel.Resources>
<sys:String x:Key="strPanel">Hello, Panel world!</sys:String>
</DockPanel.Resources>
<WrapPanel DockPanel.Dock="Top" HorizontalAlignment="Center" Margin="10">
<Button Name="btnClickMe" Click="btnClickMe_Click">Click me!</Button>
</WrapPanel>
<ListBox Name="lbResult" />
</DockPanel>
</Window>
Cod asociat:
using System;
using System.Windows;
namespace WpfTutorialSamples.WPF_Application
{
public partial class ResourcesFromCodeBehindSample : Window
{
public ResourcesFromCodeBehindSample()
{
InitializeComponent();
}
private void btnClickMe_Click(object sender, RoutedEventArgs e)
{
lbResult.Items.Add(pnlMain.FindResource("strPanel").ToString());
lbResult.Items.Add(this.FindResource("strWindow").ToString());
lbResult.Items.Add(Application.Current.FindResource("strApp").ToString());
}
}
}
Deci, după cum puteți vedea, stocăm trei mesaje "Bună ziua, lume!" : unul în app.xaml, unul în interiorul ferestrei și unul local în panoul principal. interfața este formată dintr-un buton și dintr-o listă.
În codul din spate (asociat), vom gestiona evenimentul de clic al butonului, în care adăugăm fiecare șir de text în lista, așa cum se vede în captura de ecran. Folosim metoda FindResource () , care va returna resursa ca un obiect (daca este gasita) si apoi vom transforma-o in sirul pe care-l stim ca este folosind metoda ToString ().
Observați modul în care folosim metoda FindResource () pentru diferite domenii - mai întâi la nivel de panou, apoi la nivel de fereastră și apoi la nivel de aplicatie Application. Este logic să căutăm resursele unde știm că sunt, dar după cum am menționat deja, dacă o resursă nu este găsită, căutarea progresează în ierarhie, deci, în principiu, am fi putut folosi metoda FindResource () asupra panoului în toate cele trei cazuri, deoarece ar fi continuat până la fereastră și mai târziu până la nivelul aplicației, dacă nu ar fi găsit.
Același lucru nu este adevărat invers - căutarea nu navighează în josul copacului, astfel încât să nu puteți începe căutarea unei resurse la nivelul aplicației, dacă a fost definită local pentru control sau pentru fereastră.